eap_server_pax.c
Go to the documentation of this file.
00001 /*
00002  * hostapd / EAP-PAX (RFC 4746) server
00003  * Copyright (c) 2005-2007, Jouni Malinen <j@w1.fi>
00004  *
00005  * This program is free software; you can redistribute it and/or modify
00006  * it under the terms of the GNU General Public License version 2 as
00007  * published by the Free Software Foundation.
00008  *
00009  * Alternatively, this software may be distributed under the terms of BSD
00010  * license.
00011  *
00012  * See README and COPYING for more details.
00013  */
00014 
00015 #include "includes.h"
00016 
00017 #include "common.h"
00018 #include "eap_server/eap_i.h"
00019 #include "eap_common/eap_pax_common.h"
00020 
00021 /*
00022  * Note: only PAX_STD subprotocol is currently supported
00023  *
00024  * TODO: Add support with PAX_SEC with the mandatory to implement ciphersuite
00025  * (HMAC_SHA1_128, IANA DH Group 14 (2048 bits), RSA-PKCS1-V1_5) and
00026  * recommended ciphersuite (HMAC_SHA256_128, IANA DH Group 15 (3072 bits),
00027  * RSAES-OAEP).
00028  */
00029 
00030 struct eap_pax_data {
00031         enum { PAX_STD_1, PAX_STD_3, SUCCESS, FAILURE } state;
00032         u8 mac_id;
00033         union {
00034                 u8 e[2 * EAP_PAX_RAND_LEN];
00035                 struct {
00036                         u8 x[EAP_PAX_RAND_LEN]; /* server rand */
00037                         u8 y[EAP_PAX_RAND_LEN]; /* client rand */
00038                 } r;
00039         } rand;
00040         u8 ak[EAP_PAX_AK_LEN];
00041         u8 mk[EAP_PAX_MK_LEN];
00042         u8 ck[EAP_PAX_CK_LEN];
00043         u8 ick[EAP_PAX_ICK_LEN];
00044         int keys_set;
00045         char *cid;
00046         size_t cid_len;
00047 };
00048 
00049 
00050 static void * eap_pax_init(struct eap_sm *sm)
00051 {
00052         struct eap_pax_data *data;
00053 
00054         data = os_zalloc(sizeof(*data));
00055         if (data == NULL)
00056                 return NULL;
00057         data->state = PAX_STD_1;
00058         /*
00059          * TODO: make this configurable once EAP_PAX_HMAC_SHA256_128 is
00060          * supported
00061          */
00062         data->mac_id = EAP_PAX_MAC_HMAC_SHA1_128;
00063 
00064         return data;
00065 }
00066 
00067 
00068 static void eap_pax_reset(struct eap_sm *sm, void *priv)
00069 {
00070         struct eap_pax_data *data = priv;
00071         os_free(data->cid);
00072         os_free(data);
00073 }
00074 
00075 
00076 static struct wpabuf * eap_pax_build_std_1(struct eap_sm *sm,
00077                                            struct eap_pax_data *data, u8 id)
00078 {
00079         struct wpabuf *req;
00080         struct eap_pax_hdr *pax;
00081         u8 *pos;
00082 
00083         wpa_printf(MSG_DEBUG, "EAP-PAX: PAX_STD-1 (sending)");
00084 
00085         if (os_get_random(data->rand.r.x, EAP_PAX_RAND_LEN)) {
00086                 wpa_printf(MSG_ERROR, "EAP-PAX: Failed to get random data");
00087                 data->state = FAILURE;
00088                 return NULL;
00089         }
00090 
00091         req = eap_msg_alloc(EAP_VENDOR_IETF, EAP_TYPE_PAX,
00092                             sizeof(*pax) + 2 + EAP_PAX_RAND_LEN +
00093                             EAP_PAX_ICV_LEN, EAP_CODE_REQUEST, id);
00094         if (req == NULL) {
00095                 wpa_printf(MSG_ERROR, "EAP-PAX: Failed to allocate memory "
00096                            "request");
00097                 data->state = FAILURE;
00098                 return NULL;
00099         }
00100 
00101         pax = wpabuf_put(req, sizeof(*pax));
00102         pax->op_code = EAP_PAX_OP_STD_1;
00103         pax->flags = 0;
00104         pax->mac_id = data->mac_id;
00105         pax->dh_group_id = EAP_PAX_DH_GROUP_NONE;
00106         pax->public_key_id = EAP_PAX_PUBLIC_KEY_NONE;
00107 
00108         wpabuf_put_be16(req, EAP_PAX_RAND_LEN);
00109         wpabuf_put_data(req, data->rand.r.x, EAP_PAX_RAND_LEN);
00110         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: A = X (server rand)",
00111                     data->rand.r.x, EAP_PAX_RAND_LEN);
00112 
00113         pos = wpabuf_put(req, EAP_PAX_MAC_LEN);
00114         eap_pax_mac(data->mac_id, (u8 *) "", 0,
00115                     wpabuf_mhead(req), wpabuf_len(req) - EAP_PAX_ICV_LEN,
00116                     NULL, 0, NULL, 0, pos);
00117         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: ICV", pos, EAP_PAX_ICV_LEN);
00118 
00119         return req;
00120 }
00121 
00122 
00123 static struct wpabuf * eap_pax_build_std_3(struct eap_sm *sm,
00124                                            struct eap_pax_data *data, u8 id)
00125 {
00126         struct wpabuf *req;
00127         struct eap_pax_hdr *pax;
00128         u8 *pos;
00129 
00130         wpa_printf(MSG_DEBUG, "EAP-PAX: PAX_STD-3 (sending)");
00131 
00132         req = eap_msg_alloc(EAP_VENDOR_IETF, EAP_TYPE_PAX,
00133                             sizeof(*pax) + 2 + EAP_PAX_MAC_LEN +
00134                             EAP_PAX_ICV_LEN, EAP_CODE_REQUEST, id);
00135         if (req == NULL) {
00136                 wpa_printf(MSG_ERROR, "EAP-PAX: Failed to allocate memory "
00137                            "request");
00138                 data->state = FAILURE;
00139                 return NULL;
00140         }
00141 
00142         pax = wpabuf_put(req, sizeof(*pax));
00143         pax->op_code = EAP_PAX_OP_STD_3;
00144         pax->flags = 0;
00145         pax->mac_id = data->mac_id;
00146         pax->dh_group_id = EAP_PAX_DH_GROUP_NONE;
00147         pax->public_key_id = EAP_PAX_PUBLIC_KEY_NONE;
00148 
00149         wpabuf_put_be16(req, EAP_PAX_MAC_LEN);
00150         pos = wpabuf_put(req, EAP_PAX_MAC_LEN);
00151         eap_pax_mac(data->mac_id, data->ck, EAP_PAX_CK_LEN,
00152                     data->rand.r.y, EAP_PAX_RAND_LEN,
00153                     (u8 *) data->cid, data->cid_len, NULL, 0, pos);
00154         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: MAC_CK(B, CID)",
00155                     pos, EAP_PAX_MAC_LEN);
00156         pos += EAP_PAX_MAC_LEN;
00157 
00158         /* Optional ADE could be added here, if needed */
00159 
00160         pos = wpabuf_put(req, EAP_PAX_MAC_LEN);
00161         eap_pax_mac(data->mac_id, data->ick, EAP_PAX_ICK_LEN,
00162                     wpabuf_mhead(req), wpabuf_len(req) - EAP_PAX_ICV_LEN,
00163                     NULL, 0, NULL, 0, pos);
00164         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: ICV", pos, EAP_PAX_ICV_LEN);
00165 
00166         return req;
00167 }
00168 
00169 
00170 static struct wpabuf * eap_pax_buildReq(struct eap_sm *sm, void *priv, u8 id)
00171 {
00172         struct eap_pax_data *data = priv;
00173 
00174         switch (data->state) {
00175         case PAX_STD_1:
00176                 return eap_pax_build_std_1(sm, data, id);
00177         case PAX_STD_3:
00178                 return eap_pax_build_std_3(sm, data, id);
00179         default:
00180                 wpa_printf(MSG_DEBUG, "EAP-PAX: Unknown state %d in buildReq",
00181                            data->state);
00182                 break;
00183         }
00184         return NULL;
00185 }
00186 
00187 
00188 static Boolean eap_pax_check(struct eap_sm *sm, void *priv,
00189                              struct wpabuf *respData)
00190 {
00191         struct eap_pax_data *data = priv;
00192         struct eap_pax_hdr *resp;
00193         const u8 *pos;
00194         size_t len, mlen;
00195         u8 icvbuf[EAP_PAX_ICV_LEN], *icv;
00196 
00197         pos = eap_hdr_validate(EAP_VENDOR_IETF, EAP_TYPE_PAX, respData, &len);
00198         if (pos == NULL || len < sizeof(*resp)) {
00199                 wpa_printf(MSG_INFO, "EAP-PAX: Invalid frame");
00200                 return TRUE;
00201         }
00202 
00203         mlen = sizeof(struct eap_hdr) + 1 + len;
00204         resp = (struct eap_pax_hdr *) pos;
00205 
00206         wpa_printf(MSG_DEBUG, "EAP-PAX: received frame: op_code 0x%x "
00207                    "flags 0x%x mac_id 0x%x dh_group_id 0x%x "
00208                    "public_key_id 0x%x",
00209                    resp->op_code, resp->flags, resp->mac_id, resp->dh_group_id,
00210                    resp->public_key_id);
00211         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: received payload",
00212                     (u8 *) (resp + 1), len - sizeof(*resp) - EAP_PAX_ICV_LEN);
00213 
00214         if (data->state == PAX_STD_1 &&
00215             resp->op_code != EAP_PAX_OP_STD_2) {
00216                 wpa_printf(MSG_DEBUG, "EAP-PAX: Expected PAX_STD-2 - "
00217                            "ignore op %d", resp->op_code);
00218                 return TRUE;
00219         }
00220 
00221         if (data->state == PAX_STD_3 &&
00222             resp->op_code != EAP_PAX_OP_ACK) {
00223                 wpa_printf(MSG_DEBUG, "EAP-PAX: Expected PAX-ACK - "
00224                            "ignore op %d", resp->op_code);
00225                 return TRUE;
00226         }
00227 
00228         if (resp->op_code != EAP_PAX_OP_STD_2 &&
00229             resp->op_code != EAP_PAX_OP_ACK) {
00230                 wpa_printf(MSG_DEBUG, "EAP-PAX: Unknown op_code 0x%x",
00231                            resp->op_code);
00232         }
00233 
00234         if (data->mac_id != resp->mac_id) {
00235                 wpa_printf(MSG_DEBUG, "EAP-PAX: Expected MAC ID 0x%x, "
00236                            "received 0x%x", data->mac_id, resp->mac_id);
00237                 return TRUE;
00238         }
00239 
00240         if (resp->dh_group_id != EAP_PAX_DH_GROUP_NONE) {
00241                 wpa_printf(MSG_INFO, "EAP-PAX: Expected DH Group ID 0x%x, "
00242                            "received 0x%x", EAP_PAX_DH_GROUP_NONE,
00243                            resp->dh_group_id);
00244                 return TRUE;
00245         }
00246 
00247         if (resp->public_key_id != EAP_PAX_PUBLIC_KEY_NONE) {
00248                 wpa_printf(MSG_INFO, "EAP-PAX: Expected Public Key ID 0x%x, "
00249                            "received 0x%x", EAP_PAX_PUBLIC_KEY_NONE,
00250                            resp->public_key_id);
00251                 return TRUE;
00252         }
00253 
00254         if (resp->flags & EAP_PAX_FLAGS_MF) {
00255                 /* TODO: add support for reassembling fragments */
00256                 wpa_printf(MSG_INFO, "EAP-PAX: fragmentation not supported");
00257                 return TRUE;
00258         }
00259 
00260         if (resp->flags & EAP_PAX_FLAGS_CE) {
00261                 wpa_printf(MSG_INFO, "EAP-PAX: Unexpected CE flag");
00262                 return TRUE;
00263         }
00264 
00265         if (data->keys_set) {
00266                 if (len - sizeof(*resp) < EAP_PAX_ICV_LEN) {
00267                         wpa_printf(MSG_INFO, "EAP-PAX: No ICV in the packet");
00268                         return TRUE;
00269                 }
00270                 icv = wpabuf_mhead_u8(respData) + mlen - EAP_PAX_ICV_LEN;
00271                 wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: ICV", icv, EAP_PAX_ICV_LEN);
00272                 eap_pax_mac(data->mac_id, data->ick, EAP_PAX_ICK_LEN,
00273                             wpabuf_mhead(respData),
00274                             wpabuf_len(respData) - EAP_PAX_ICV_LEN,
00275                             NULL, 0, NULL, 0, icvbuf);
00276                 if (os_memcmp(icvbuf, icv, EAP_PAX_ICV_LEN) != 0) {
00277                         wpa_printf(MSG_INFO, "EAP-PAX: Invalid ICV");
00278                         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: Expected ICV",
00279                                     icvbuf, EAP_PAX_ICV_LEN);
00280                         return TRUE;
00281                 }
00282         }
00283 
00284         return FALSE;
00285 }
00286 
00287 
00288 static void eap_pax_process_std_2(struct eap_sm *sm,
00289                                   struct eap_pax_data *data,
00290                                   struct wpabuf *respData)
00291 {
00292         struct eap_pax_hdr *resp;
00293         u8 mac[EAP_PAX_MAC_LEN], icvbuf[EAP_PAX_ICV_LEN];
00294         const u8 *pos;
00295         size_t len, left;
00296         int i;
00297 
00298         if (data->state != PAX_STD_1)
00299                 return;
00300 
00301         wpa_printf(MSG_DEBUG, "EAP-PAX: Received PAX_STD-2");
00302 
00303         pos = eap_hdr_validate(EAP_VENDOR_IETF, EAP_TYPE_PAX, respData, &len);
00304         if (pos == NULL || len < sizeof(*resp) + EAP_PAX_ICV_LEN)
00305                 return;
00306 
00307         resp = (struct eap_pax_hdr *) pos;
00308         pos = (u8 *) (resp + 1);
00309         left = len - sizeof(*resp);
00310 
00311         if (left < 2 + EAP_PAX_RAND_LEN ||
00312             WPA_GET_BE16(pos) != EAP_PAX_RAND_LEN) {
00313                 wpa_printf(MSG_INFO, "EAP-PAX: Too short PAX_STD-2 (B)");
00314                 return;
00315         }
00316         pos += 2;
00317         left -= 2;
00318         os_memcpy(data->rand.r.y, pos, EAP_PAX_RAND_LEN);
00319         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: Y (client rand)",
00320                     data->rand.r.y, EAP_PAX_RAND_LEN);
00321         pos += EAP_PAX_RAND_LEN;
00322         left -= EAP_PAX_RAND_LEN;
00323 
00324         if (left < 2 || (size_t) 2 + WPA_GET_BE16(pos) > left) {
00325                 wpa_printf(MSG_INFO, "EAP-PAX: Too short PAX_STD-2 (CID)");
00326                 return;
00327         }
00328         data->cid_len = WPA_GET_BE16(pos);
00329         os_free(data->cid);
00330         data->cid = os_malloc(data->cid_len);
00331         if (data->cid == NULL) {
00332                 wpa_printf(MSG_INFO, "EAP-PAX: Failed to allocate memory for "
00333                            "CID");
00334                 return;
00335         }
00336         os_memcpy(data->cid, pos + 2, data->cid_len);
00337         pos += 2 + data->cid_len;
00338         left -= 2 + data->cid_len;
00339         wpa_hexdump_ascii(MSG_MSGDUMP, "EAP-PAX: CID",
00340                           (u8 *) data->cid, data->cid_len);
00341 
00342         if (left < 2 + EAP_PAX_MAC_LEN ||
00343             WPA_GET_BE16(pos) != EAP_PAX_MAC_LEN) {
00344                 wpa_printf(MSG_INFO, "EAP-PAX: Too short PAX_STD-2 (MAC_CK)");
00345                 return;
00346         }
00347         pos += 2;
00348         left -= 2;
00349         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: MAC_CK(A, B, CID)",
00350                     pos, EAP_PAX_MAC_LEN);
00351 
00352         if (eap_user_get(sm, (u8 *) data->cid, data->cid_len, 0) < 0) {
00353                 wpa_hexdump_ascii(MSG_DEBUG, "EAP-PAX: unknown CID",
00354                                   (u8 *) data->cid, data->cid_len);
00355                 data->state = FAILURE;
00356                 return;
00357         }
00358 
00359         for (i = 0;
00360              i < EAP_MAX_METHODS &&
00361                      (sm->user->methods[i].vendor != EAP_VENDOR_IETF ||
00362                       sm->user->methods[i].method != EAP_TYPE_NONE);
00363              i++) {
00364                 if (sm->user->methods[i].vendor == EAP_VENDOR_IETF &&
00365                     sm->user->methods[i].method == EAP_TYPE_PAX)
00366                         break;
00367         }
00368 
00369         if (i >= EAP_MAX_METHODS ||
00370             sm->user->methods[i].vendor != EAP_VENDOR_IETF ||
00371             sm->user->methods[i].method != EAP_TYPE_PAX) {
00372                 wpa_hexdump_ascii(MSG_DEBUG,
00373                                   "EAP-PAX: EAP-PAX not enabled for CID",
00374                                   (u8 *) data->cid, data->cid_len);
00375                 data->state = FAILURE;
00376                 return;
00377         }
00378 
00379         if (sm->user->password == NULL ||
00380             sm->user->password_len != EAP_PAX_AK_LEN) {
00381                 wpa_hexdump_ascii(MSG_DEBUG, "EAP-PAX: invalid password in "
00382                                   "user database for CID",
00383                                   (u8 *) data->cid, data->cid_len);
00384                 data->state = FAILURE;
00385                 return;
00386         }
00387         os_memcpy(data->ak, sm->user->password, EAP_PAX_AK_LEN);
00388 
00389         if (eap_pax_initial_key_derivation(data->mac_id, data->ak,
00390                                            data->rand.e, data->mk, data->ck,
00391                                            data->ick) < 0) {
00392                 wpa_printf(MSG_INFO, "EAP-PAX: Failed to complete initial "
00393                            "key derivation");
00394                 data->state = FAILURE;
00395                 return;
00396         }
00397         data->keys_set = 1;
00398 
00399         eap_pax_mac(data->mac_id, data->ck, EAP_PAX_CK_LEN,
00400                     data->rand.r.x, EAP_PAX_RAND_LEN,
00401                     data->rand.r.y, EAP_PAX_RAND_LEN,
00402                     (u8 *) data->cid, data->cid_len, mac);
00403         if (os_memcmp(mac, pos, EAP_PAX_MAC_LEN) != 0) {
00404                 wpa_printf(MSG_INFO, "EAP-PAX: Invalid MAC_CK(A, B, CID) in "
00405                            "PAX_STD-2");
00406                 wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: Expected MAC_CK(A, B, CID)",
00407                             mac, EAP_PAX_MAC_LEN);
00408                 data->state = FAILURE;
00409                 return;
00410         }
00411 
00412         pos += EAP_PAX_MAC_LEN;
00413         left -= EAP_PAX_MAC_LEN;
00414 
00415         if (left < EAP_PAX_ICV_LEN) {
00416                 wpa_printf(MSG_INFO, "EAP-PAX: Too short ICV (%lu) in "
00417                            "PAX_STD-2", (unsigned long) left);
00418                 return;
00419         }
00420         wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: ICV", pos, EAP_PAX_ICV_LEN);
00421         eap_pax_mac(data->mac_id, data->ick, EAP_PAX_ICK_LEN,
00422                     wpabuf_head(respData),
00423                     wpabuf_len(respData) - EAP_PAX_ICV_LEN, NULL, 0, NULL, 0,
00424                     icvbuf);
00425         if (os_memcmp(icvbuf, pos, EAP_PAX_ICV_LEN) != 0) {
00426                 wpa_printf(MSG_INFO, "EAP-PAX: Invalid ICV in PAX_STD-2");
00427                 wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: Expected ICV",
00428                             icvbuf, EAP_PAX_ICV_LEN);
00429                 return;
00430         }
00431         pos += EAP_PAX_ICV_LEN;
00432         left -= EAP_PAX_ICV_LEN;
00433 
00434         if (left > 0) {
00435                 wpa_hexdump(MSG_MSGDUMP, "EAP-PAX: ignored extra payload",
00436                             pos, left);
00437         }
00438 
00439         data->state = PAX_STD_3;
00440 }
00441 
00442 
00443 static void eap_pax_process_ack(struct eap_sm *sm,
00444                                 struct eap_pax_data *data,
00445                                 struct wpabuf *respData)
00446 {
00447         if (data->state != PAX_STD_3)
00448                 return;
00449 
00450         wpa_printf(MSG_DEBUG, "EAP-PAX: Received PAX-ACK - authentication "
00451                    "completed successfully");
00452         data->state = SUCCESS;
00453 }
00454 
00455 
00456 static void eap_pax_process(struct eap_sm *sm, void *priv,
00457                             struct wpabuf *respData)
00458 {
00459         struct eap_pax_data *data = priv;
00460         struct eap_pax_hdr *resp;
00461         const u8 *pos;
00462         size_t len;
00463 
00464         if (sm->user == NULL || sm->user->password == NULL) {
00465                 wpa_printf(MSG_INFO, "EAP-PAX: Plaintext password not "
00466                            "configured");
00467                 data->state = FAILURE;
00468                 return;
00469         }
00470 
00471         pos = eap_hdr_validate(EAP_VENDOR_IETF, EAP_TYPE_PAX, respData, &len);
00472         if (pos == NULL || len < sizeof(*resp))
00473                 return;
00474 
00475         resp = (struct eap_pax_hdr *) pos;
00476 
00477         switch (resp->op_code) {
00478         case EAP_PAX_OP_STD_2:
00479                 eap_pax_process_std_2(sm, data, respData);
00480                 break;
00481         case EAP_PAX_OP_ACK:
00482                 eap_pax_process_ack(sm, data, respData);
00483                 break;
00484         }
00485 }
00486 
00487 
00488 static Boolean eap_pax_isDone(struct eap_sm *sm, void *priv)
00489 {
00490         struct eap_pax_data *data = priv;
00491         return data->state == SUCCESS || data->state == FAILURE;
00492 }
00493 
00494 
00495 static u8 * eap_pax_getKey(struct eap_sm *sm, void *priv, size_t *len)
00496 {
00497         struct eap_pax_data *data = priv;
00498         u8 *key;
00499 
00500         if (data->state != SUCCESS)
00501                 return NULL;
00502 
00503         key = os_malloc(EAP_MSK_LEN);
00504         if (key == NULL)
00505                 return NULL;
00506 
00507         *len = EAP_MSK_LEN;
00508         eap_pax_kdf(data->mac_id, data->mk, EAP_PAX_MK_LEN,
00509                     "Master Session Key", data->rand.e, 2 * EAP_PAX_RAND_LEN,
00510                     EAP_MSK_LEN, key);
00511 
00512         return key;
00513 }
00514 
00515 
00516 static u8 * eap_pax_get_emsk(struct eap_sm *sm, void *priv, size_t *len)
00517 {
00518         struct eap_pax_data *data = priv;
00519         u8 *key;
00520 
00521         if (data->state != SUCCESS)
00522                 return NULL;
00523 
00524         key = os_malloc(EAP_EMSK_LEN);
00525         if (key == NULL)
00526                 return NULL;
00527 
00528         *len = EAP_EMSK_LEN;
00529         eap_pax_kdf(data->mac_id, data->mk, EAP_PAX_MK_LEN,
00530                     "Extended Master Session Key",
00531                     data->rand.e, 2 * EAP_PAX_RAND_LEN,
00532                     EAP_EMSK_LEN, key);
00533 
00534         return key;
00535 }
00536 
00537 
00538 static Boolean eap_pax_isSuccess(struct eap_sm *sm, void *priv)
00539 {
00540         struct eap_pax_data *data = priv;
00541         return data->state == SUCCESS;
00542 }
00543 
00544 
00545 int eap_server_pax_register(void)
00546 {
00547         struct eap_method *eap;
00548         int ret;
00549 
00550         eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION,
00551                                       EAP_VENDOR_IETF, EAP_TYPE_PAX, "PAX");
00552         if (eap == NULL)
00553                 return -1;
00554 
00555         eap->init = eap_pax_init;
00556         eap->reset = eap_pax_reset;
00557         eap->buildReq = eap_pax_buildReq;
00558         eap->check = eap_pax_check;
00559         eap->process = eap_pax_process;
00560         eap->isDone = eap_pax_isDone;
00561         eap->getKey = eap_pax_getKey;
00562         eap->isSuccess = eap_pax_isSuccess;
00563         eap->get_emsk = eap_pax_get_emsk;
00564 
00565         ret = eap_server_method_register(eap);
00566         if (ret)
00567                 eap_server_method_free(eap);
00568         return ret;
00569 }


wpa_supplicant
Author(s): Package maintained by Blaise Gassend
autogenerated on Thu Apr 24 2014 15:34:34