Made it 2.0.0, and removed the changes that are in 1.1.x, as
[freeradius.git] / src / modules / rlm_eap / eap.c
1 /*
2  * eap.c    rfc2284 & rfc2869 implementation
3  *
4  * Version:     $Id$
5  *
6  *   This program is free software; you can redistribute it and/or modify
7  *   it under the terms of the GNU General Public License as published by
8  *   the Free Software Foundation; either version 2 of the License, or
9  *   (at your option) any later version.
10  *
11  *   This program is distributed in the hope that it will be useful,
12  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *   GNU General Public License for more details.
15  *
16  *   You should have received a copy of the GNU General Public License
17  *   along with this program; if not, write to the Free Software
18  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  *
20  * Copyright 2000-2003  The FreeRADIUS server project
21  * Copyright 2001  hereUare Communications, Inc. <raghud@hereuare.com>
22  * Copyright 2003  Alan DeKok <aland@freeradius.org>
23  */
24 /*
25  *  EAP PACKET FORMAT
26  *  --- ------ ------
27  *  0                   1                   2                   3
28  *  0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
29  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
30  * |     Code      |  Identifier   |            Length             |
31  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
32  * |    Data ...
33  * +-+-+-+-+
34  *
35  *
36  * EAP Request and Response Packet Format
37  * --- ------- --- -------- ------ ------
38  *  0                   1                   2                   3
39  *  0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
40  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
41  * |     Code      |  Identifier   |            Length             |
42  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
43  * |     Type      |  Type-Data ...
44  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-
45  *
46  *
47  * EAP Success and Failure Packet Format
48  * --- ------- --- ------- ------ ------
49  *  0                   1                   2                   3
50  *  0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
51  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
52  * |     Code      |  Identifier   |            Length             |
53  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
54  *
55  */
56
57 #include "rlm_eap.h"
58
59 static const char rcsid[] = "$Id$";
60
61 static const char *eap_codes[] = {
62   "",                           /* 0 is invalid */
63   "request",
64   "response",
65   "success",
66   "failure"
67 };
68
69 /*
70  * Load all the required eap authentication types.
71  * Get all the supported EAP-types from config file.
72  */
73 int eaptype_load(EAP_TYPES **type, int eap_type, CONF_SECTION *cs)
74 {
75         char            buffer[64];
76         char            namebuf[64];
77         const char      *eaptype_name;
78         lt_dlhandle     handle;
79         EAP_TYPES       *node;
80
81         eaptype_name = eaptype_type2name(eap_type, namebuf, sizeof(namebuf));
82         snprintf(buffer, sizeof(buffer), "rlm_eap_%s", eaptype_name);
83
84         /* Link the loaded EAP-Type */
85         handle = lt_dlopenext(buffer);
86         if (handle == NULL) {
87                 radlog(L_ERR, "rlm_eap: Failed to link EAP-Type/%s: %s",
88                        eaptype_name, lt_dlerror());
89                 return -1;
90         }
91
92         /* Make room for the EAP-Type */
93         node = (EAP_TYPES *)malloc(sizeof(EAP_TYPES));
94         if (node == NULL) {
95                 radlog(L_ERR, "rlm_eap: out of memory");
96                 return -1;
97         }
98         memset(node, 0, sizeof(*node));
99
100         /* fill in the structure */
101         node->handle = handle;
102         node->cs = cs;
103
104         /*
105          *      In general, this is a terrible idea.  It works here
106          *      solely because the eap_type2name function returns a
107          *      'static const char *' pointer sometimes, and we can
108          *      ONLY link to module which are named in that static
109          *      array.
110          */
111         node->typename = eaptype_name;
112         node->type_data = NULL;
113
114         node->type = (EAP_TYPE *)lt_dlsym(node->handle, buffer);
115         if (!node->type) {
116                 radlog(L_ERR, "rlm_eap: Failed linking to %s structure in %s: %s",
117                                 buffer, eaptype_name, lt_dlerror());
118                 lt_dlclose(node->handle);       /* ignore any errors */
119                 free(node);
120                 return -1;
121         }
122         if ((node->type->attach) &&
123             ((node->type->attach)(node->cs, &(node->type_data)) < 0)) {
124
125                 radlog(L_ERR, "rlm_eap: Failed to initialize type %s",
126                        eaptype_name);
127                 lt_dlclose(node->handle);
128                 free(node);
129                 return -1;
130         }
131
132         DEBUG("rlm_eap: Loaded and initialized type %s", eaptype_name);
133         *type = node;
134         return 0;
135 }
136
137 /*
138  * Call the appropriate handle with the right eap_type.
139  */
140 static int eaptype_call(EAP_TYPES *atype, EAP_HANDLER *handler)
141 {
142         int rcode = 1;
143
144         DEBUG2("  rlm_eap: processing type %s", atype->typename);
145
146         rad_assert(atype != NULL);
147
148         switch (handler->stage) {
149         case INITIATE:
150                 if (!atype->type->initiate(atype->type_data, handler))
151                         rcode = 0;
152                 break;
153
154         case AUTHORIZE:
155                 /*
156                  *   The called function updates the EAP reply packet.
157                  */
158                 if (!atype->type->authorize ||
159                     !atype->type->authorize(atype->type_data, handler))
160                         rcode = 0;
161                 break;
162
163         case AUTHENTICATE:
164                 /*
165                  *   The called function updates the EAP reply packet.
166                  */
167                 if (!atype->type->authenticate ||
168                     !atype->type->authenticate(atype->type_data, handler))
169                         rcode = 0;
170                 break;
171
172         default:
173                 /* Should never enter here */
174                 radlog(L_DBG, "rlm_eap: Invalid operation on eap_type");
175                 rcode = 0;
176                 break;
177         }
178
179         return rcode;
180 }
181
182 /*
183  * Based on TYPE, call the appropriate EAP-type handler
184  * Default to the configured EAP-Type
185  * for all Unsupported EAP-Types
186  */
187 int eaptype_select(rlm_eap_t *inst, EAP_HANDLER *handler)
188 {
189         unsigned int    default_eap_type = inst->default_eap_type;
190         eaptype_t       *eaptype;
191         VALUE_PAIR      *vp;
192         char            namebuf[64];
193         const char      *eaptype_name;
194
195         eaptype = &handler->eap_ds->response->type;
196
197         /*
198          *      Don't trust anyone.
199          */
200         if ((eaptype->type == 0) ||
201             (eaptype->type > PW_EAP_MAX_TYPES)) {
202                 DEBUG2(" rlm_eap: Asked to select bad type");
203                 return EAP_INVALID;
204         }
205
206         /*
207          *      Figure out what to do.
208          */
209         switch(eaptype->type) {
210         case PW_EAP_IDENTITY:
211                 DEBUG2("  rlm_eap: EAP Identity");
212
213                 /*
214                  *      Allow per-user configuration of EAP types.
215                  */
216                 vp = pairfind(handler->request->config_items,
217                               PW_EAP_TYPE);
218                 if (vp) default_eap_type = vp->lvalue;
219
220         do_initiate:
221                 /*
222                  *      Ensure it's valid.
223                  */
224                 if ((default_eap_type < PW_EAP_MD5) ||
225                     (default_eap_type > PW_EAP_MAX_TYPES) ||
226                     (inst->types[default_eap_type] == NULL)) {
227                         DEBUG2(" rlm_eap: No such EAP type %s",
228                                eaptype_type2name(default_eap_type,
229                                                  namebuf, sizeof(namebuf)));
230                         return EAP_INVALID;
231                 }
232
233                 handler->stage = INITIATE;
234                 handler->eap_type = default_eap_type;
235
236                 /*
237                  *      Wild & crazy stuff!  For TTLS & PEAP, we
238                  *      initiate a TLS session, and then pass that
239                  *      session data to TTLS or PEAP for the
240                  *      authenticate stage.
241                  *
242                  *      Handler->eap_type holds the TRUE type.
243                  */
244                 if ((default_eap_type == PW_EAP_TTLS) ||
245                     (default_eap_type == PW_EAP_PEAP)) {
246                         default_eap_type = PW_EAP_TLS;
247                 }
248
249
250                 /*
251                  *      We don't do TLS inside of TLS, as it's a bad
252                  *      idea...
253                  */
254                 if (((handler->request->options & RAD_REQUEST_OPTION_FAKE_REQUEST) != 0) &&
255                     (default_eap_type == PW_EAP_TLS)) {
256                         DEBUG2(" rlm_eap: Unable to tunnel TLS inside of TLS");
257                         return EAP_INVALID;
258                 }
259
260                 if (eaptype_call(inst->types[default_eap_type],
261                                  handler) == 0) {
262                         DEBUG2(" rlm_eap: Default EAP type %s failed in initiate",
263                                eaptype_type2name(default_eap_type,
264                                                  namebuf, sizeof(namebuf)));
265                         return EAP_INVALID;
266                 }
267                 break;
268
269         case PW_EAP_NAK:
270                 /*
271                  *      The NAK data is the preferred EAP type(s) of
272                  *      the client.
273                  *
274                  *      RFC 3748 says to list one or more proposed
275                  *      alternative types, one per octet, or to use
276                  *      0 for no alternative.
277                  */
278                 DEBUG2("  rlm_eap: EAP NAK");
279
280                 /*
281                  *      Delete old data, if necessary.
282                  */
283                 if (handler->opaque && handler->free_opaque) {
284                         handler->free_opaque(handler->opaque);
285                         handler->free_opaque = NULL;
286                         handler->opaque = NULL;
287                 }
288
289                 /*
290                  *      It is invalid to request identity,
291                  *      notification & nak in nak
292                  */
293                 if (eaptype->data == NULL) {
294                         DEBUG2(" rlm_eap: Empty NAK packet, cannot decide what EAP type the client wants.");
295                         return EAP_INVALID;
296                 }
297
298                 /*
299                  *      FIXME: Pick one type out of the one they asked
300                  *      for, as they may have asked for many.
301                  */
302                 if ((eaptype->data[0] < PW_EAP_MD5) ||
303                     (eaptype->data[0] > PW_EAP_MAX_TYPES)) {
304                         DEBUG2(" rlm_eap: NAK asked for bad type %d",
305                                eaptype->data[0]);
306                         return EAP_INVALID;
307                 }
308
309                 default_eap_type = eaptype->data[0];
310                 eaptype_name = eaptype_type2name(default_eap_type,
311                                                  namebuf, sizeof(namebuf));
312                 DEBUG2(" rlm_eap: EAP-NAK asked for EAP-Type/%s",
313                        eaptype_name);
314
315                 /*
316                  *      Prevent a firestorm if the client is confused.
317                  */
318                 if (handler->eap_type == default_eap_type) {
319                         DEBUG2(" rlm_eap: ERROR! Our request for %s was NAK'd with a request for %s, what is the client thinking?",
320                                eaptype_name, eaptype_name);
321                         return EAP_INVALID;
322                 }
323
324                 /*
325                  *      Enforce per-user configuration of EAP types.
326                  */
327                 vp = pairfind(handler->request->config_items,
328                               PW_EAP_TYPE);
329                 if (vp && (vp->lvalue != default_eap_type)) {
330                         char    mynamebuf[64];
331                         DEBUG2("  rlm_eap: Client wants %s, while we require %s, rejecting the user.",
332                                eaptype_name,
333                                eaptype_type2name(vp->lvalue,
334                                                  mynamebuf,
335                                                  sizeof(mynamebuf)));
336                         return EAP_INVALID;
337                 }
338                 goto do_initiate;
339                 break;
340
341                 /*
342                  *      Key off of the configured sub-modules.
343                  */
344                 default:
345                         eaptype_name = eaptype_type2name(eaptype->type,
346                                                          namebuf,
347                                                          sizeof(namebuf));
348                         DEBUG2("  rlm_eap: EAP/%s", eaptype_name);
349
350                         /*
351                          *      We haven't configured it, it doesn't exit.
352                          */
353                         if (!inst->types[eaptype->type]) {
354                                 DEBUG2(" rlm_eap: EAP type %d is unsupported",
355                                        eaptype->type);
356                                 return EAP_INVALID;
357                         }
358
359                         rad_assert(handler->stage == AUTHENTICATE);
360                         handler->eap_type = eaptype->type;
361                         if (eaptype_call(inst->types[eaptype->type],
362                                          handler) == 0) {
363                                 DEBUG2(" rlm_eap: Handler failed in EAP/%s",
364                                        eaptype_name);
365                                 return EAP_INVALID;
366                         }
367                 break;
368         }
369
370         return EAP_OK;
371 }
372
373
374 /*
375  *      EAP packet format to be sent over the wire
376  *
377  *      i.e. code+id+length+data where data = null/type+typedata
378  *      based on code.
379  */
380 static int eap_wireformat(EAP_PACKET *reply)
381 {
382         eap_packet_t    *hdr;
383         uint16_t total_length = 0;
384
385         if (reply == NULL) return EAP_INVALID;
386
387         total_length = EAP_HEADER_LEN;
388         if (reply->code < 3) {
389                 total_length += 1/*EAPtype*/;
390                 if (reply->type.data && reply->type.length > 0) {
391                         total_length += reply->type.length;
392                 }
393         }
394
395         reply->packet = (unsigned char *)malloc(total_length);
396         hdr = (eap_packet_t *)reply->packet;
397         if (!hdr) {
398                 radlog(L_ERR, "rlm_eap: out of memory");
399                 return EAP_INVALID;
400         }
401
402         hdr->code = (reply->code & 0xFF);
403         hdr->id = (reply->id & 0xFF);
404         total_length = htons(total_length);
405         memcpy(hdr->length, &total_length, sizeof(uint16_t));
406
407         /*
408          *      Request and Response packets are special.
409          */
410         if ((reply->code == PW_EAP_REQUEST) ||
411             (reply->code == PW_EAP_RESPONSE)) {
412                 hdr->data[0] = (reply->type.type & 0xFF);
413
414                 /*
415                  * Here since we cannot know the typedata format and length
416                  *
417                  * Type_data is expected to be wired by each EAP-Type
418                  *
419                  * Zero length/No typedata is supported as long as
420                  * type is defined
421                  */
422                 if (reply->type.data && reply->type.length > 0) {
423                         memcpy(&hdr->data[1], reply->type.data, reply->type.length);
424                         free(reply->type.data);
425                         reply->type.data = reply->packet + EAP_HEADER_LEN + 1/*EAPtype*/;
426                 }
427         }
428
429         return EAP_VALID;
430 }
431
432 /*
433  *      compose EAP reply packet in EAP-Message attr of RADIUS.  If
434  *      EAP exceeds 253, frame it in multiple EAP-Message attrs.
435  *
436  *      Set the RADIUS reply codes based on EAP request codes.  Append
437  *      any additonal VPs to RADIUS reply
438  */
439 int eap_compose(EAP_HANDLER *handler)
440 {
441         uint16_t eap_len, len;
442         VALUE_PAIR *eap_msg;
443         VALUE_PAIR *vp;
444         eap_packet_t *eap_packet;
445         unsigned char   *ptr;
446         REQUEST *request = handler->request;
447         EAP_DS *eap_ds = handler->eap_ds;
448         EAP_PACKET *reply = eap_ds->request;
449         int rcode;
450
451         /*
452          *      The Id for the EAP packet to the NAS wasn't set.
453          *      Do so now.
454          *
455          *      LEAP requires the Id to be incremented on EAP-Success
456          *      in Stage 4, so that we can carry on the conversation
457          *      where the client asks us to authenticate ourselves
458          *      in stage 5.
459          */
460         if (!eap_ds->set_request_id) {
461                 /*
462                  *      Id serves to suppport request/response
463                  *      retransmission in the EAP layer and as such
464                  *      must be different for 'adjacent' packets
465                  *      except in case of success/failure-replies.
466                  *
467                  *      RFC2716 (EAP-TLS) requires this to be
468                  *      incremented, RFC2284 only makes the above-
469                  *      mentioned restriction.
470                  */
471                 reply->id = handler->eap_ds->response->id;
472
473                 switch (reply->code) {
474                         /*
475                          *      The Id is a simple "ack" for success
476                          *      and failure.
477                          *
478                          *      RFC 3748 section 4.2 says
479                          *
480                          *      ... The Identifier field MUST match
481                          *      the Identifier field of the Response
482                          *      packet that it is sent in response
483                          *      to.
484                          */
485                 case PW_EAP_SUCCESS:
486                 case PW_EAP_FAILURE:
487                         break;
488
489                         /*
490                          *      We've sent a response to their
491                          *      request, the Id is incremented.
492                          */
493                 default:
494                         ++reply->id;
495                 }
496         } else {
497                 DEBUG2("  rlm_eap: Underlying EAP-Type set EAP ID to %d",
498                        reply->id);
499         }
500
501         /*
502          *      For Request & Response packets, set the EAP sub-type,
503          *      if the EAP sub-module didn't already set it.
504          *
505          *      This allows the TLS module to be "morphic", and means
506          *      that the TTLS and PEAP modules can call it to do most
507          *      of their dirty work.
508          */
509         if (((eap_ds->request->code == PW_EAP_REQUEST) ||
510              (eap_ds->request->code == PW_EAP_RESPONSE)) &&
511             (eap_ds->request->type.type == 0)) {
512                 rad_assert(handler->eap_type >= PW_EAP_MD5);
513                 rad_assert(handler->eap_type <= PW_EAP_MAX_TYPES);
514
515                 eap_ds->request->type.type = handler->eap_type;
516         }
517
518
519         if (eap_wireformat(reply) == EAP_INVALID) {
520                 return RLM_MODULE_INVALID;
521         }
522         eap_packet = (eap_packet_t *)reply->packet;
523
524         memcpy(&eap_len, &(eap_packet->length), sizeof(uint16_t));
525         len = eap_len = ntohs(eap_len);
526         ptr = (unsigned char *)eap_packet;
527
528         do {
529                 if (eap_len > 253) {
530                         len = 253;
531                         eap_len -= 253;
532                 } else {
533                         len = eap_len;
534                         eap_len = 0;
535                 }
536
537                 /*
538                  * create a value pair & append it to the request reply list
539                  * This memory gets freed up when request is freed up
540                  */
541                 eap_msg = paircreate(PW_EAP_MESSAGE, PW_TYPE_OCTETS);
542                 memcpy(eap_msg->vp_octets, ptr, len);
543                 eap_msg->length = len;
544                 pairadd(&(request->reply->vps), eap_msg);
545                 ptr += len;
546                 eap_msg = NULL;
547         } while (eap_len);
548
549         /*
550          *      EAP-Message is always associated with
551          *      Message-Authenticator but not vice-versa.
552          *
553          *      Don't add a Message-Authenticator if it's already
554          *      there.
555          */
556         vp = pairfind(request->reply->vps, PW_MESSAGE_AUTHENTICATOR);
557         if (!vp) {
558                 vp = paircreate(PW_MESSAGE_AUTHENTICATOR, PW_TYPE_OCTETS);
559                 memset(vp->vp_octets, 0, AUTH_VECTOR_LEN);
560                 vp->length = AUTH_VECTOR_LEN;
561                 pairadd(&(request->reply->vps), vp);
562         }
563
564         /* Set request reply code, but only if it's not already set. */
565         rcode = RLM_MODULE_OK;
566         if (!request->reply->code) switch(reply->code) {
567         case PW_EAP_RESPONSE:
568                 request->reply->code = PW_AUTHENTICATION_ACK;
569                 rcode = RLM_MODULE_HANDLED; /* leap weirdness */
570                 break;
571         case PW_EAP_SUCCESS:
572                 request->reply->code = PW_AUTHENTICATION_ACK;
573                 rcode = RLM_MODULE_OK;
574                 break;
575         case PW_EAP_FAILURE:
576                 request->reply->code = PW_AUTHENTICATION_REJECT;
577                 rcode = RLM_MODULE_REJECT;
578                 break;
579         case PW_EAP_REQUEST:
580                 request->reply->code = PW_ACCESS_CHALLENGE;
581                 rcode = RLM_MODULE_HANDLED;
582                 break;
583         default:
584                 /*
585                  *      When we're pulling MS-CHAPv2 out of EAP-MS-CHAPv2,
586                  *      we do so WITHOUT setting a reply code, as the
587                  *      request is being proxied.
588                  */
589                 if (request->options & RAD_REQUEST_OPTION_PROXY_EAP) {
590                         return RLM_MODULE_HANDLED;
591                 }
592
593                 /* Should never enter here */
594                 radlog(L_ERR, "rlm_eap: reply code %d is unknown, Rejecting the request.", reply->code);
595                 request->reply->code = PW_AUTHENTICATION_REJECT;
596                 reply->code = PW_EAP_FAILURE;
597                 rcode = RLM_MODULE_REJECT;
598                 break;
599         }
600
601         return rcode;
602 }
603
604 /*
605  * Radius criteria, EAP-Message is invalid without Message-Authenticator
606  * For EAP_START, send Access-Challenge with EAP Identity request.
607  */
608 int eap_start(rlm_eap_t *inst, REQUEST *request)
609 {
610         VALUE_PAIR *vp, *proxy;
611         VALUE_PAIR *eap_msg;
612
613         eap_msg = pairfind(request->packet->vps, PW_EAP_MESSAGE);
614         if (eap_msg == NULL) {
615                 DEBUG2("  rlm_eap: No EAP-Message, not doing EAP");
616                 return EAP_NOOP;
617         }
618
619         /*
620          *      Look for EAP-Type = None (FreeRADIUS specific attribute)
621          *      this allows you to NOT do EAP for some users.
622          */
623         vp = pairfind(request->packet->vps, PW_EAP_TYPE);
624         if (vp && vp->lvalue == 0) {
625                 DEBUG2("  rlm_eap: Found EAP-Message, but EAP-Type = None, so we're not doing EAP.");
626                 return EAP_NOOP;
627         }
628
629         /*
630          *      http://www.freeradius.org/rfc/rfc2869.html#EAP-Message
631          *
632          *      Checks for Message-Authenticator are handled by rad_recv().
633          */
634
635         /*
636          *      Check for a Proxy-To-Realm.  Don't get excited over LOCAL
637          *      realms (sigh).
638          */
639         proxy = pairfind(request->config_items, PW_PROXY_TO_REALM);
640         if (proxy) {
641                 REALM *realm;
642
643                 /*
644                  *      If it's a LOCAL realm, then we're not proxying
645                  *      to it.
646                  */
647                 realm = realm_find(proxy->vp_strvalue, 0);
648                 rad_assert(realm->ipaddr.af == AF_INET);
649                 if (realm && (realm->ipaddr.ipaddr.ip4addr.s_addr == htonl(INADDR_NONE))) {
650                         proxy = NULL;
651                 }
652         }
653
654         /*
655          *      Check the length before de-referencing the contents.
656          *
657          *      Lengths of zero are required by the RFC for EAP-Start,
658          *      but we've never seen them in practice.
659          *
660          *      Lengths of two are what we see in practice as
661          *      EAP-Starts.
662          */
663         if ((eap_msg->length == 0) || (eap_msg->length == 2)) {
664                 EAP_DS *eap_ds;
665                 EAP_HANDLER handler;
666
667                 /*
668                  *      It's a valid EAP-Start, but the request
669                  *      was marked as being proxied.  So we don't
670                  *      do EAP, as the home server will do it.
671                  */
672                 if (proxy) {
673                 do_proxy:
674                         DEBUG2("  rlm_eap: Request is supposed to be proxied to Realm %s.  Not doing EAP.", proxy->vp_strvalue);
675                         return EAP_NOOP;
676                 }
677                 
678                 DEBUG2("  rlm_eap: Got EAP_START message");
679                 if ((eap_ds = eap_ds_alloc()) == NULL) {
680                         DEBUG2("  rlm_eap: EAP Start failed in allocation");
681                         return EAP_FAIL;
682                 }
683                 
684                 /*
685                  *      It's an EAP-Start packet.  Tell them to stop wasting
686                  *      our time, and give us an EAP-Identity packet.
687                  *
688                  *      Hmm... we should probably check the contents of the
689                  *      EAP-Start packet for something...
690                  */
691                 eap_ds->request->code = PW_EAP_REQUEST;
692                 eap_ds->request->type.type = PW_EAP_IDENTITY;
693                 
694                 /*
695                  *      We don't have a handler, but eap_compose needs one,
696                  *      (for various reasons), so we fake it out here.
697                  */
698                 memset(&handler, 0, sizeof(handler));
699                 handler.request = request;
700                 handler.eap_ds = eap_ds;
701                 
702                 eap_compose(&handler);
703                 
704                 eap_ds_free(&eap_ds);
705                 return EAP_FOUND;
706         } /* end of handling EAP-Start */
707
708         /*
709          *      The EAP packet header is 4 bytes, plus one byte of
710          *      EAP sub-type.  Short packets are discarded, unless
711          *      we're proxying.
712          */
713         if (eap_msg->length < (EAP_HEADER_LEN + 1)) {
714                 if (proxy) goto do_proxy;
715
716                 DEBUG2("  rlm_eap: Ignoring EAP-Message which is too short to be meaningful.");
717                 return EAP_FAIL;
718         }
719
720         /*
721          *      Create an EAP-Type containing the EAP-type
722          *      from the packet.
723          */
724         vp = paircreate(PW_EAP_TYPE, PW_TYPE_INTEGER);
725         if (vp) {
726                 vp->lvalue = eap_msg->vp_octets[4];
727                 pairadd(&(request->packet->vps), vp);
728         }
729
730         /*
731          *      If the request was marked to be proxied, do it now.
732          *      This is done after checking for a valid length
733          *      (which may not be good), and after adding the EAP-Type
734          *      attribute.  This lets other modules selectively cancel
735          *      proxying based on EAP-Type.
736          */
737         if (proxy) goto do_proxy;
738
739         /*
740          *      From now on, we're supposed to be handling the
741          *      EAP packet.  We better understand it...
742          */
743
744         /*
745          *      We're allowed only a few codes.  Request, Response,
746          *      Success, or Failure.
747          */
748         if ((eap_msg->vp_octets[0] == 0) ||
749             (eap_msg->vp_octets[0] > PW_EAP_MAX_CODES)) {
750                 DEBUG2("  rlm_eap: Unknown EAP packet");
751         } else {
752                 DEBUG2("  rlm_eap: EAP packet type %s id %d length %d",
753                        eap_codes[eap_msg->vp_octets[0]],
754                        eap_msg->vp_octets[1],
755                        eap_msg->length);
756         }
757
758         /*
759          *      We handle request and responses.  The only other defined
760          *      codes are success and fail.  The client SHOULD NOT be
761          *      sending success/fail packets to us, as it doesn't make
762          *      sense.
763          */
764         if ((eap_msg->vp_octets[0] != PW_EAP_REQUEST) &&
765             (eap_msg->vp_octets[0] != PW_EAP_RESPONSE)) {
766                 DEBUG2("  rlm_eap: Ignoring EAP packet which we don't know how to handle.");
767                 return EAP_FAIL;
768         }
769
770         /*
771          *      We've been told to ignore unknown EAP types, AND it's
772          *      an unknown type.  Return "NOOP", which will cause the
773          *      eap_authorize() to return NOOP.
774          *
775          *      EAP-Identity, Notification, and NAK are all handled
776          *      internally, so they never have handlers.
777          */
778         if ((eap_msg->vp_octets[4] >= PW_EAP_MD5) &&
779             inst->ignore_unknown_eap_types &&
780             ((eap_msg->vp_octets[4] == 0) ||
781              (eap_msg->vp_octets[4] > PW_EAP_MAX_TYPES) ||
782              (inst->types[eap_msg->vp_octets[4]] == NULL))) {
783                 DEBUG2("  rlm_eap:  Ignoring Unknown EAP type");
784                 return EAP_NOOP;
785         }
786                 
787         /*
788          *      They're NAKing the EAP type we wanted to use, and
789          *      asking for one which we don't support.
790          *
791          *      NAK is code + id + length1 + length + NAK
792          *             + requested EAP type(s).
793          *
794          *      We know at this point that we can't handle the
795          *      request.  We could either return an EAP-Fail here, but
796          *      it's not too critical.
797          *
798          *      By returning "noop", we can ensure that authorize()
799          *      returns NOOP, and another module may choose to proxy
800          *      the request.
801          */
802         if ((eap_msg->vp_octets[4] == PW_EAP_NAK) &&
803             (eap_msg->length >= (EAP_HEADER_LEN + 2)) &&
804             inst->ignore_unknown_eap_types &&
805             ((eap_msg->vp_octets[5] == 0) ||
806              (eap_msg->vp_octets[5] > PW_EAP_MAX_TYPES) ||
807              (inst->types[eap_msg->vp_octets[5]] == NULL))) {
808                 DEBUG2("  rlm_eap: Ignoring NAK with request for unknown EAP type");
809                 return EAP_NOOP;
810         }
811
812         /*
813          *      Later EAP messages are longer than the 'start'
814          *      message, so if everything is OK, this function returns
815          *      'no start found', so that the rest of the EAP code can
816          *      use the State attribute to match this EAP-Message to
817          *      an ongoing conversation.
818          */
819         DEBUG2("  rlm_eap: No EAP Start, assuming it's an on-going EAP conversation");
820
821         return EAP_NOTFOUND;
822 }
823
824 /*
825  *      compose EAP FAILURE packet in EAP-Message
826  */
827 void eap_fail(EAP_HANDLER *handler)
828 {
829         handler->eap_ds->request->code = PW_EAP_FAILURE;
830         eap_compose(handler);
831 }
832
833 /*
834  *      compose EAP SUCCESS packet in EAP-Message
835  */
836 void eap_success(EAP_HANDLER *handler)
837 {
838         handler->eap_ds->request->code = PW_EAP_SUCCESS;
839         eap_compose(handler);
840 }
841
842 /*
843  * Basic EAP packet verfications & validations
844  */
845 static int eap_validation(eap_packet_t *eap_packet)
846 {
847         uint16_t len;
848
849         memcpy(&len, eap_packet->length, sizeof(uint16_t));
850         len = ntohs(len);
851
852         /*
853          *      High level EAP packet checks
854          */
855         if ((len <= EAP_HEADER_LEN) ||
856             ((eap_packet->code != PW_EAP_RESPONSE) &&
857              (eap_packet->code != PW_EAP_REQUEST)) ||
858             (eap_packet->data[0] <= 0) ||
859             (eap_packet->data[0] > PW_EAP_MAX_TYPES)) {
860
861                 radlog(L_AUTH, "rlm_eap: Incorrect EAP Message, "
862                                 "Ignoring the packet");
863                 return EAP_INVALID;
864         }
865
866         /* we don't expect notification, but we send it */
867         if (eap_packet->data[0] == PW_EAP_NOTIFICATION) {
868                 radlog(L_AUTH, "rlm_eap: Got NOTIFICATION, "
869                                 "Ignoring the packet");
870                 return EAP_INVALID;
871         }
872
873         return EAP_VALID;
874 }
875
876
877 /*
878  *  Get the user Identity only from EAP-Identity packets
879  */
880 static char *eap_identity(eap_packet_t *eap_packet)
881 {
882         int size;
883         uint16_t len;
884         char *identity;
885
886         if ((eap_packet == NULL) ||
887             (eap_packet->code != PW_EAP_RESPONSE) ||
888             (eap_packet->data[0] != PW_EAP_IDENTITY)) {
889                 return NULL;
890         }
891
892         memcpy(&len, eap_packet->length, sizeof(uint16_t));
893         len = ntohs(len);
894
895         if ((len <= 5) || (eap_packet->data[1] == 0x00)) {
896                 radlog(L_ERR, "rlm_eap: UserIdentity Unknown ");
897                 return NULL;
898         }
899
900         size = len - 5;
901         identity = (char *)malloc(size + 1);
902         if (identity == NULL) {
903                 radlog(L_ERR, "rlm_eap: out of memory");
904                 return NULL;
905         }
906         memcpy(identity, &eap_packet->data[1], size);
907         identity[size] = '\0';
908
909         return identity;
910 }
911
912
913 /*
914  *      Create our Request-Response data structure with the eap packet
915  */
916 static EAP_DS *eap_buildds(eap_packet_t **eap_packet_p)
917 {
918         EAP_DS          *eap_ds = NULL;
919         eap_packet_t    *eap_packet = *eap_packet_p;
920         int             typelen;
921         uint16_t        len;
922
923         if ((eap_ds = eap_ds_alloc()) == NULL) {
924                 return NULL;
925         }
926
927         eap_ds->response->packet = (unsigned char *)eap_packet;
928         eap_ds->response->code = eap_packet->code;
929         eap_ds->response->id = eap_packet->id;
930         eap_ds->response->type.type = eap_packet->data[0];
931
932         memcpy(&len, eap_packet->length, sizeof(uint16_t));
933         len = ntohs(len);
934         eap_ds->response->length = len;
935
936         /*
937          *      We've eaten the eap packet into the eap_ds.
938          */
939         *eap_packet_p = NULL;
940
941         /*
942          *      First 5 bytes in eap, are code + id + length(2) + type.
943          *
944          *      The rest is type-specific data.  We skip type while
945          *      getting typedata from data.
946          */
947         typelen = len - 5/*code + id + length + type */;
948         if (typelen > 0) {
949                 /*
950                  *      Since the packet contains the complete
951                  *      eap_packet, typedata will be a ptr in packet
952                  *      to its typedata
953                  */
954                 eap_ds->response->type.data = eap_ds->response->packet + 5/*code+id+length+type*/;
955                 eap_ds->response->type.length = typelen;
956         } else {
957                 eap_ds->response->type.length = 0;
958                 eap_ds->response->type.data = NULL;
959         }
960
961         return eap_ds;
962 }
963
964
965 /*
966  * If identity response then create a fresh handler & fill the identity
967  * else handler MUST be in our list, get that.
968  * This handler creation cannot fail
969  *
970  * username contains REQUEST->username which might have been stripped.
971  * identity contains the one sent in EAP-Identity response
972  */
973 EAP_HANDLER *eap_handler(rlm_eap_t *inst, eap_packet_t **eap_packet_p,
974                          REQUEST *request)
975 {
976         EAP_HANDLER     *handler = NULL;
977         eap_packet_t    *eap_packet = *eap_packet_p;
978         VALUE_PAIR      *vp;
979
980         /*
981          *      Ensure it's a valid EAP-Request, or EAP-Response.
982          */
983         if (eap_validation(eap_packet) == EAP_INVALID) {
984                 free(*eap_packet_p);
985                 *eap_packet_p = NULL;
986                 return NULL;
987         }
988
989         /*
990          *      EAP_HANDLER MUST be found in the list if it is not
991          *      EAP-Identity response
992          */
993         if (eap_packet->data[0] != PW_EAP_IDENTITY) {
994                 handler = eaplist_find(inst, request, eap_packet);
995                 if (handler == NULL) {
996                         /* Either send EAP_Identity or EAP-Fail */
997                         radlog(L_ERR, "rlm_eap: Either EAP-request timed out OR"
998                                 " EAP-response to an unknown EAP-request");
999                         free(*eap_packet_p);
1000                         *eap_packet_p = NULL;
1001                         return NULL;
1002                 }
1003
1004                 /*
1005                  *      Even more paranoia.  Without this, some weird
1006                  *      clients could do crazy things.
1007                  *
1008                  *      It's ok to send EAP sub-type NAK in response
1009                  *      to a request for a particular type, but it's NOT
1010                  *      OK to blindly return data for another type.
1011                  */
1012                 if ((eap_packet->data[0] != PW_EAP_NAK) &&
1013                     (eap_packet->data[0] != handler->eap_type)) {
1014                         radlog(L_ERR, "rlm_eap: Response appears to match, but EAP type is wrong.");
1015                         free(*eap_packet_p);
1016                         *eap_packet_p = NULL;
1017                         return NULL;
1018                 }
1019
1020                vp = pairfind(request->packet->vps, PW_USER_NAME);
1021                if (!vp) {
1022                        /*
1023                         *       NAS did not set the User-Name
1024                         *       attribute, so we set it here and
1025                         *       prepend it to the beginning of the
1026                         *       request vps so that autz's work
1027                         *       correctly
1028                         */
1029                        radlog(L_INFO, "rlm_eap: Broken NAS did not set User-Name, setting from EAP Identity");
1030                        vp = pairmake("User-Name", handler->identity, T_OP_EQ);
1031                        if (vp == NULL) {
1032                                radlog(L_ERR, "rlm_eap: out of memory");
1033                                free(*eap_packet_p);
1034                                *eap_packet_p = NULL;
1035                                return NULL;
1036                        }
1037                        vp->next = request->packet->vps;
1038                        request->packet->vps = vp;
1039
1040                } else {
1041                        /*
1042                         *      A little more paranoia.  If the NAS
1043                         *      *did* set the User-Name, and it doesn't
1044                         *      match the identity, (i.e. If they
1045                         *      change their User-Name part way through
1046                         *      the EAP transaction), then reject the
1047                         *      request as the NAS is doing something
1048                         *      funny.
1049                         */
1050                        if (strncmp(handler->identity, vp->vp_strvalue,
1051                                    MAX_STRING_LEN) != 0) {
1052                                radlog(L_ERR, "rlm_eap: Identity does not match User-Name.  Authentication failed.");
1053                                free(*eap_packet_p);
1054                                *eap_packet_p = NULL;
1055                                return NULL;
1056                        }
1057                }
1058         } else {                /* packet was EAP identity */
1059                 handler = eap_handler_alloc();
1060                 if (handler == NULL) {
1061                         radlog(L_ERR, "rlm_eap: out of memory");
1062                         free(*eap_packet_p);
1063                         *eap_packet_p = NULL;
1064                         return NULL;
1065                 }
1066
1067                 /*
1068                  *      All fields in the handler are set to zero.
1069                  */
1070                 handler->identity = eap_identity(eap_packet);
1071                 if (handler->identity == NULL) {
1072                         radlog(L_ERR, "rlm_eap: Identity Unknown, authentication failed");
1073                         free(*eap_packet_p);
1074                         *eap_packet_p = NULL;
1075                         eap_handler_free(handler);
1076                         return NULL;
1077                 }
1078
1079                vp = pairfind(request->packet->vps, PW_USER_NAME);
1080                if (!vp) {
1081                        /*
1082                         *       NAS did not set the User-Name
1083                         *       attribute, so we set it here and
1084                         *       prepend it to the beginning of the
1085                         *       request vps so that autz's work
1086                         *       correctly
1087                         */
1088                        radlog(L_INFO, "rlm_eap: WARNING NAS did not set User-Name.  Setting it locally from EAP Identity");
1089                        vp = pairmake("User-Name", handler->identity, T_OP_EQ);
1090                        if (vp == NULL) {
1091                                radlog(L_ERR, "rlm_eap: out of memory");
1092                                free(*eap_packet_p);
1093                                *eap_packet_p = NULL;
1094                                return NULL;
1095                        }
1096                        vp->next = request->packet->vps;
1097                        request->packet->vps = vp;
1098                } else {
1099                        /*
1100                         *      Paranoia.  If the NAS *did* set the
1101                         *      User-Name, and it doesn't match the
1102                         *      identity, the NAS is doing something
1103                         *      funny, so reject the request.
1104                         */
1105                        if (strncmp(handler->identity, vp->vp_strvalue,
1106                                    MAX_STRING_LEN) != 0) {
1107                                radlog(L_ERR, "rlm_eap: Identity does not match User-Name, setting from EAP Identity.");
1108                                free(*eap_packet_p);
1109                                *eap_packet_p = NULL;
1110                                eap_handler_free(handler);
1111                                return NULL;
1112                        }
1113                }
1114         }
1115
1116         handler->eap_ds = eap_buildds(eap_packet_p);
1117         if (handler->eap_ds == NULL) {
1118                 free(*eap_packet_p);
1119                 *eap_packet_p = NULL;
1120                 eap_handler_free(handler);
1121                 return NULL;
1122         }
1123
1124         handler->timestamp = request->timestamp;
1125         handler->request = request; /* LEAP needs this */
1126         return handler;
1127 }