diff options
Diffstat (limited to 'src/eap_server')
27 files changed, 176 insertions, 176 deletions
diff --git a/src/eap_server/eap_methods.h b/src/eap_server/eap_methods.h index 0baa3279086e..3bf1495f76bf 100644 --- a/src/eap_server/eap_methods.h +++ b/src/eap_server/eap_methods.h @@ -15,7 +15,6 @@ const struct eap_method * eap_server_get_eap_method(int vendor, EapType method); struct eap_method * eap_server_method_alloc(int version, int vendor, EapType method, const char *name); -void eap_server_method_free(struct eap_method *method); int eap_server_method_register(struct eap_method *method); EapType eap_server_get_type(const char *name, int *vendor); diff --git a/src/eap_server/eap_server_aka.c b/src/eap_server/eap_server_aka.c index db9b6aa2db39..a8bb5eae6b56 100644 --- a/src/eap_server/eap_server_aka.c +++ b/src/eap_server/eap_server_aka.c @@ -1319,7 +1319,6 @@ static u8 * eap_aka_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_aka_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_AKA, "AKA"); @@ -1337,10 +1336,7 @@ int eap_server_aka_register(void) eap->get_emsk = eap_aka_get_emsk; eap->getSessionId = eap_aka_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } @@ -1348,7 +1344,6 @@ int eap_server_aka_register(void) int eap_server_aka_prime_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_AKA_PRIME, @@ -1367,10 +1362,6 @@ int eap_server_aka_prime_register(void) eap->get_emsk = eap_aka_get_emsk; eap->getSessionId = eap_aka_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - - return ret; + return eap_server_method_register(eap); } #endif /* EAP_SERVER_AKA_PRIME */ diff --git a/src/eap_server/eap_server_eke.c b/src/eap_server/eap_server_eke.c index ba82be9c3f3a..1eba8f515648 100644 --- a/src/eap_server/eap_server_eke.c +++ b/src/eap_server/eap_server_eke.c @@ -792,7 +792,6 @@ static u8 * eap_eke_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_eke_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_EKE, "EKE"); @@ -810,8 +809,5 @@ int eap_server_eke_register(void) eap->get_emsk = eap_eke_get_emsk; eap->getSessionId = eap_eke_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_fast.c b/src/eap_server/eap_server_fast.c index bd9018e78b56..20491726880e 100644 --- a/src/eap_server/eap_server_fast.c +++ b/src/eap_server/eap_server_fast.c @@ -180,42 +180,47 @@ static int eap_fast_session_ticket_cb(void *ctx, const u8 *ticket, size_t len, buf, end - buf); pos = buf; - while (pos + 1 < end) { - if (pos + 2 + pos[1] > end) + while (end - pos > 1) { + u8 id, elen; + + id = *pos++; + elen = *pos++; + if (elen > end - pos) break; - switch (*pos) { + switch (id) { case PAC_OPAQUE_TYPE_PAD: goto done; case PAC_OPAQUE_TYPE_KEY: - if (pos[1] != EAP_FAST_PAC_KEY_LEN) { - wpa_printf(MSG_DEBUG, "EAP-FAST: Invalid " - "PAC-Key length %d", pos[1]); + if (elen != EAP_FAST_PAC_KEY_LEN) { + wpa_printf(MSG_DEBUG, + "EAP-FAST: Invalid PAC-Key length %d", + elen); os_free(buf); return -1; } - pac_key = pos + 2; + pac_key = pos; wpa_hexdump_key(MSG_DEBUG, "EAP-FAST: PAC-Key from " "decrypted PAC-Opaque", pac_key, EAP_FAST_PAC_KEY_LEN); break; case PAC_OPAQUE_TYPE_LIFETIME: - if (pos[1] != 4) { + if (elen != 4) { wpa_printf(MSG_DEBUG, "EAP-FAST: Invalid " "PAC-Key lifetime length %d", - pos[1]); + elen); os_free(buf); return -1; } - lifetime = WPA_GET_BE32(pos + 2); + lifetime = WPA_GET_BE32(pos); break; case PAC_OPAQUE_TYPE_IDENTITY: - identity = pos + 2; - identity_len = pos[1]; + identity = pos; + identity_len = elen; break; } - pos += 2 + pos[1]; + pos += elen; } done: @@ -273,7 +278,7 @@ static void eap_fast_derive_key_auth(struct eap_sm *sm, * Extra key material after TLS key_block: session_key_seed[40] */ - sks = eap_fast_derive_key(sm->ssl_ctx, data->ssl.conn, "key expansion", + sks = eap_fast_derive_key(sm->ssl_ctx, data->ssl.conn, EAP_FAST_SKS_LEN); if (sks == NULL) { wpa_printf(MSG_DEBUG, "EAP-FAST: Failed to derive " @@ -300,7 +305,6 @@ static void eap_fast_derive_key_provisioning(struct eap_sm *sm, os_free(data->key_block_p); data->key_block_p = (struct eap_fast_key_block_provisioning *) eap_fast_derive_key(sm->ssl_ctx, data->ssl.conn, - "key expansion", sizeof(*data->key_block_p)); if (data->key_block_p == NULL) { wpa_printf(MSG_DEBUG, "EAP-FAST: Failed to derive key block"); @@ -407,11 +411,13 @@ static int eap_fast_update_icmk(struct eap_sm *sm, struct eap_fast_data *data) static void * eap_fast_init(struct eap_sm *sm) { struct eap_fast_data *data; - u8 ciphers[5] = { + u8 ciphers[7] = { TLS_CIPHER_ANON_DH_AES128_SHA, TLS_CIPHER_AES128_SHA, TLS_CIPHER_RSA_DHE_AES128_SHA, TLS_CIPHER_RC4_SHA, + TLS_CIPHER_RSA_DHE_AES256_SHA, + TLS_CIPHER_AES256_SHA, TLS_CIPHER_NONE }; @@ -1134,7 +1140,7 @@ static int eap_fast_parse_tlvs(struct wpabuf *data, pos = wpabuf_mhead(data); end = pos + wpabuf_len(data); - while (pos + 4 < end) { + while (end - pos > 4) { mandatory = pos[0] & 0x80; tlv_type = WPA_GET_BE16(pos) & 0x3fff; pos += 2; @@ -1559,7 +1565,10 @@ static u8 * eap_fast_getKey(struct eap_sm *sm, void *priv, size_t *len) if (eapKeyData == NULL) return NULL; - eap_fast_derive_eap_msk(data->simck, eapKeyData); + if (eap_fast_derive_eap_msk(data->simck, eapKeyData) < 0) { + os_free(eapKeyData); + return NULL; + } *len = EAP_FAST_KEY_LEN; return eapKeyData; @@ -1578,7 +1587,10 @@ static u8 * eap_fast_get_emsk(struct eap_sm *sm, void *priv, size_t *len) if (eapKeyData == NULL) return NULL; - eap_fast_derive_eap_emsk(data->simck, eapKeyData); + if (eap_fast_derive_eap_emsk(data->simck, eapKeyData) < 0) { + os_free(eapKeyData); + return NULL; + } *len = EAP_EMSK_LEN; return eapKeyData; @@ -1607,7 +1619,6 @@ static u8 * eap_fast_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_fast_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_FAST, "FAST"); @@ -1625,8 +1636,5 @@ int eap_server_fast_register(void) eap->isSuccess = eap_fast_isSuccess; eap->getSessionId = eap_fast_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_gpsk.c b/src/eap_server/eap_server_gpsk.c index 50f15c31d0dc..94e74ec9b2f7 100644 --- a/src/eap_server/eap_server_gpsk.c +++ b/src/eap_server/eap_server_gpsk.c @@ -631,7 +631,6 @@ static u8 * eap_gpsk_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_gpsk_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_GPSK, "GPSK"); @@ -649,8 +648,5 @@ int eap_server_gpsk_register(void) eap->get_emsk = eap_gpsk_get_emsk; eap->getSessionId = eap_gpsk_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_gtc.c b/src/eap_server/eap_server_gtc.c index 98ac3c6ec495..193a8517ac08 100644 --- a/src/eap_server/eap_server_gtc.c +++ b/src/eap_server/eap_server_gtc.c @@ -202,7 +202,6 @@ static Boolean eap_gtc_isSuccess(struct eap_sm *sm, void *priv) int eap_server_gtc_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_GTC, "GTC"); @@ -217,8 +216,5 @@ int eap_server_gtc_register(void) eap->isDone = eap_gtc_isDone; eap->isSuccess = eap_gtc_isSuccess; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_identity.c b/src/eap_server/eap_server_identity.c index 45015336b907..1b1db53f25b2 100644 --- a/src/eap_server/eap_server_identity.c +++ b/src/eap_server/eap_server_identity.c @@ -157,7 +157,6 @@ static Boolean eap_identity_isSuccess(struct eap_sm *sm, void *priv) int eap_server_identity_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_IDENTITY, @@ -174,8 +173,5 @@ int eap_server_identity_register(void) eap->isDone = eap_identity_isDone; eap->isSuccess = eap_identity_isSuccess; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_ikev2.c b/src/eap_server/eap_server_ikev2.c index 16e62764cc55..3a249d141e0c 100644 --- a/src/eap_server/eap_server_ikev2.c +++ b/src/eap_server/eap_server_ikev2.c @@ -550,7 +550,6 @@ static u8 * eap_ikev2_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_ikev2_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_IKEV2, @@ -569,8 +568,5 @@ int eap_server_ikev2_register(void) eap->get_emsk = eap_ikev2_get_emsk; eap->getSessionId = eap_ikev2_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_md5.c b/src/eap_server/eap_server_md5.c index 71e8d59e0396..cf5ceb1d1529 100644 --- a/src/eap_server/eap_server_md5.c +++ b/src/eap_server/eap_server_md5.c @@ -153,7 +153,6 @@ static Boolean eap_md5_isSuccess(struct eap_sm *sm, void *priv) int eap_server_md5_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_MD5, "MD5"); @@ -168,8 +167,5 @@ int eap_server_md5_register(void) eap->isDone = eap_md5_isDone; eap->isSuccess = eap_md5_isSuccess; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_methods.c b/src/eap_server/eap_server_methods.c index 9e9dc934eb77..79ed3447ac0a 100644 --- a/src/eap_server/eap_server_methods.c +++ b/src/eap_server/eap_server_methods.c @@ -87,7 +87,7 @@ struct eap_method * eap_server_method_alloc(int version, int vendor, * eap_server_method_free - Free EAP server method structure * @method: Method structure allocated with eap_server_method_alloc() */ -void eap_server_method_free(struct eap_method *method) +static void eap_server_method_free(struct eap_method *method) { os_free(method); } @@ -95,26 +95,31 @@ void eap_server_method_free(struct eap_method *method) /** * eap_server_method_register - Register an EAP server method - * @method: EAP method to register + * @method: EAP method to register from eap_server_method_alloc() * Returns: 0 on success, -1 on invalid method, or -2 if a matching EAP method * has already been registered * * Each EAP server method needs to call this function to register itself as a - * supported EAP method. + * supported EAP method. The caller must not free the allocated method data + * regardless of the return value. */ int eap_server_method_register(struct eap_method *method) { struct eap_method *m, *last = NULL; if (method == NULL || method->name == NULL || - method->version != EAP_SERVER_METHOD_INTERFACE_VERSION) + method->version != EAP_SERVER_METHOD_INTERFACE_VERSION) { + eap_server_method_free(method); return -1; + } for (m = eap_methods; m; m = m->next) { if ((m->vendor == method->vendor && m->method == method->method) || - os_strcmp(m->name, method->name) == 0) + os_strcmp(m->name, method->name) == 0) { + eap_server_method_free(method); return -2; + } last = m; } diff --git a/src/eap_server/eap_server_mschapv2.c b/src/eap_server/eap_server_mschapv2.c index 98d74e0d717e..460cd9c82ff5 100644 --- a/src/eap_server/eap_server_mschapv2.c +++ b/src/eap_server/eap_server_mschapv2.c @@ -571,7 +571,6 @@ static Boolean eap_mschapv2_isSuccess(struct eap_sm *sm, void *priv) int eap_server_mschapv2_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_MSCHAPV2, @@ -588,8 +587,5 @@ int eap_server_mschapv2_register(void) eap->getKey = eap_mschapv2_getKey; eap->isSuccess = eap_mschapv2_isSuccess; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_pax.c b/src/eap_server/eap_server_pax.c index 0e6b4a0698ed..782b8c316537 100644 --- a/src/eap_server/eap_server_pax.c +++ b/src/eap_server/eap_server_pax.c @@ -565,7 +565,6 @@ static u8 * eap_pax_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_pax_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_PAX, "PAX"); @@ -583,8 +582,5 @@ int eap_server_pax_register(void) eap->get_emsk = eap_pax_get_emsk; eap->getSessionId = eap_pax_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_peap.c b/src/eap_server/eap_server_peap.c index 51062b0987e4..18d31b527fdd 100644 --- a/src/eap_server/eap_server_peap.c +++ b/src/eap_server/eap_server_peap.c @@ -335,6 +335,18 @@ static int eap_peap_derive_cmk(struct eap_sm *sm, struct eap_peap_data *data) return -1; wpa_hexdump_key(MSG_DEBUG, "EAP-PEAP: TK", tk, 60); + if (tls_connection_resumed(sm->ssl_ctx, data->ssl.conn)) { + /* Fast-connect: IPMK|CMK = TK */ + os_memcpy(data->ipmk, tk, 40); + wpa_hexdump_key(MSG_DEBUG, "EAP-PEAP: IPMK from TK", + data->ipmk, 40); + os_memcpy(data->cmk, tk + 40, 20); + wpa_hexdump_key(MSG_DEBUG, "EAP-PEAP: CMK from TK", + data->cmk, 20); + os_free(tk); + return 0; + } + eap_peap_get_isk(data, isk, sizeof(isk)); wpa_hexdump_key(MSG_DEBUG, "EAP-PEAP: ISK", isk, sizeof(isk)); @@ -357,7 +369,6 @@ static int eap_peap_derive_cmk(struct eap_sm *sm, struct eap_peap_data *data) os_free(tk); - /* TODO: fast-connect: IPMK|CMK = TK */ os_memcpy(data->ipmk, imck, 40); wpa_hexdump_key(MSG_DEBUG, "EAP-PEAP: IPMK (S-IPMKj)", data->ipmk, 40); os_memcpy(data->cmk, imck + 40, 20); @@ -1267,8 +1278,9 @@ static void eap_peap_process(struct eap_sm *sm, void *priv, wpa_printf(MSG_DEBUG, "EAP-PEAP: Resuming previous session - skip Phase2"); - eap_peap_state(data, SUCCESS_REQ); - tls_connection_set_success_data_resumed(data->ssl.conn); + eap_peap_req_success(sm, data); + if (data->state == SUCCESS_REQ) + tls_connection_set_success_data_resumed(data->ssl.conn); } @@ -1351,7 +1363,6 @@ static u8 * eap_peap_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_peap_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_PEAP, "PEAP"); @@ -1368,8 +1379,5 @@ int eap_server_peap_register(void) eap->isSuccess = eap_peap_isSuccess; eap->getSessionId = eap_peap_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_psk.c b/src/eap_server/eap_server_psk.c index 12b5d25d67ff..857d421393bc 100644 --- a/src/eap_server/eap_server_psk.c +++ b/src/eap_server/eap_server_psk.c @@ -510,7 +510,6 @@ static u8 * eap_psk_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_psk_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_PSK, "PSK"); @@ -528,8 +527,5 @@ int eap_server_psk_register(void) eap->get_emsk = eap_psk_get_emsk; eap->getSessionId = eap_psk_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_pwd.c b/src/eap_server/eap_server_pwd.c index cb83ff7305bd..64bf708e039a 100644 --- a/src/eap_server/eap_server_pwd.c +++ b/src/eap_server/eap_server_pwd.c @@ -178,8 +178,13 @@ static void eap_pwd_build_id_req(struct eap_sm *sm, struct eap_pwd_data *data, return; } - /* an lfsr is good enough to generate unpredictable tokens */ - data->token = os_random(); + if (os_get_random((u8 *) &data->token, sizeof(data->token)) < 0) { + wpabuf_free(data->outbuf); + data->outbuf = NULL; + eap_pwd_state(data, FAILURE); + return; + } + wpabuf_put_be16(data->outbuf, data->group_num); wpabuf_put_u8(data->outbuf, EAP_PWD_DEFAULT_RAND_FUNC); wpabuf_put_u8(data->outbuf, EAP_PWD_DEFAULT_PRF); @@ -970,7 +975,7 @@ static void eap_pwd_process(struct eap_sm *sm, void *priv, /* * the first and all intermediate fragments have the M bit set */ - if (EAP_PWD_GET_MORE_BIT(lm_exch)) { + if (EAP_PWD_GET_MORE_BIT(lm_exch) || data->in_frag_pos) { if ((data->in_frag_pos + len) > wpabuf_size(data->inbuf)) { wpa_printf(MSG_DEBUG, "EAP-pwd: Buffer overflow " "attack detected! (%d+%d > %d)", @@ -981,6 +986,8 @@ static void eap_pwd_process(struct eap_sm *sm, void *priv, } wpabuf_put_data(data->inbuf, pos, len); data->in_frag_pos += len; + } + if (EAP_PWD_GET_MORE_BIT(lm_exch)) { wpa_printf(MSG_DEBUG, "EAP-pwd: Got a %d byte fragment", (int) len); return; @@ -990,8 +997,6 @@ static void eap_pwd_process(struct eap_sm *sm, void *priv, * buffering fragments so that's how we know it's the last) */ if (data->in_frag_pos) { - wpabuf_put_data(data->inbuf, pos, len); - data->in_frag_pos += len; pos = wpabuf_head_u8(data->inbuf); len = data->in_frag_pos; wpa_printf(MSG_DEBUG, "EAP-pwd: Last fragment, %d bytes", @@ -1094,7 +1099,6 @@ static u8 * eap_pwd_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_pwd_register(void) { struct eap_method *eap; - int ret; struct timeval tp; struct timezone tz; u32 sr; @@ -1121,9 +1125,6 @@ int eap_server_pwd_register(void) eap->isSuccess = eap_pwd_is_success; eap->getSessionId = eap_pwd_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_sake.c b/src/eap_server/eap_server_sake.c index de7077731899..84d0e0be4dd1 100644 --- a/src/eap_server/eap_server_sake.c +++ b/src/eap_server/eap_server_sake.c @@ -520,7 +520,6 @@ static u8 * eap_sake_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_sake_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_SAKE, "SAKE"); @@ -538,8 +537,5 @@ int eap_server_sake_register(void) eap->get_emsk = eap_sake_get_emsk; eap->getSessionId = eap_sake_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_sim.c b/src/eap_server/eap_server_sim.c index ddfb71cf4e2e..3a6ed795c768 100644 --- a/src/eap_server/eap_server_sim.c +++ b/src/eap_server/eap_server_sim.c @@ -846,7 +846,6 @@ static u8 * eap_sim_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_sim_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_SIM, "SIM"); @@ -864,8 +863,5 @@ int eap_server_sim_register(void) eap->get_emsk = eap_sim_get_emsk; eap->getSessionId = eap_sim_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_tls.c b/src/eap_server/eap_server_tls.c index bd18a4ba654c..7249858844ef 100644 --- a/src/eap_server/eap_server_tls.c +++ b/src/eap_server/eap_server_tls.c @@ -375,7 +375,6 @@ static u8 * eap_tls_get_session_id(struct eap_sm *sm, void *priv, size_t *len) int eap_server_tls_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_TLS, "TLS"); @@ -393,10 +392,7 @@ int eap_server_tls_register(void) eap->get_emsk = eap_tls_get_emsk; eap->getSessionId = eap_tls_get_session_id; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } @@ -404,7 +400,6 @@ int eap_server_tls_register(void) int eap_server_unauth_tls_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_UNAUTH_TLS, @@ -423,10 +418,7 @@ int eap_server_unauth_tls_register(void) eap->isSuccess = eap_tls_isSuccess; eap->get_emsk = eap_tls_get_emsk; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } #endif /* EAP_SERVER_UNAUTH_TLS */ @@ -435,7 +427,6 @@ int eap_server_unauth_tls_register(void) int eap_server_wfa_unauth_tls_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_WFA_NEW, @@ -454,9 +445,6 @@ int eap_server_wfa_unauth_tls_register(void) eap->isSuccess = eap_tls_isSuccess; eap->get_emsk = eap_tls_get_emsk; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } #endif /* CONFIG_HS20 */ diff --git a/src/eap_server/eap_server_tls_common.c b/src/eap_server/eap_server_tls_common.c index 05677b70e887..69096954b826 100644 --- a/src/eap_server/eap_server_tls_common.c +++ b/src/eap_server/eap_server_tls_common.c @@ -115,8 +115,8 @@ u8 * eap_server_tls_derive_key(struct eap_sm *sm, struct eap_ssl_data *data, if (out == NULL) return NULL; - if (tls_connection_prf(sm->ssl_ctx, data->conn, label, 0, 0, - out, len)) { + if (tls_connection_export_key(sm->ssl_ctx, data->conn, label, out, + len)) { os_free(out); return NULL; } diff --git a/src/eap_server/eap_server_tnc.c b/src/eap_server/eap_server_tnc.c index 21bd26f8296e..b568558fd42e 100644 --- a/src/eap_server/eap_server_tnc.c +++ b/src/eap_server/eap_server_tnc.c @@ -554,7 +554,6 @@ static Boolean eap_tnc_isSuccess(struct eap_sm *sm, void *priv) int eap_server_tnc_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_TNC, "TNC"); @@ -569,8 +568,5 @@ int eap_server_tnc_register(void) eap->isDone = eap_tnc_isDone; eap->isSuccess = eap_tnc_isSuccess; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_ttls.c b/src/eap_server/eap_server_ttls.c index 53ffa1ec6785..a53633f8f1fe 100644 --- a/src/eap_server/eap_server_ttls.c +++ b/src/eap_server/eap_server_ttls.c @@ -1335,7 +1335,6 @@ static u8 * eap_ttls_get_emsk(struct eap_sm *sm, void *priv, size_t *len) int eap_server_ttls_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_IETF, EAP_TYPE_TTLS, "TTLS"); @@ -1353,8 +1352,5 @@ int eap_server_ttls_register(void) eap->getSessionId = eap_ttls_get_session_id; eap->get_emsk = eap_ttls_get_emsk; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_vendor_test.c b/src/eap_server/eap_server_vendor_test.c index 30f600d3baf6..96399775945b 100644 --- a/src/eap_server/eap_server_vendor_test.c +++ b/src/eap_server/eap_server_vendor_test.c @@ -168,7 +168,6 @@ static Boolean eap_vendor_test_isSuccess(struct eap_sm *sm, void *priv) int eap_server_vendor_test_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_ID, EAP_VENDOR_TYPE, @@ -185,8 +184,5 @@ int eap_server_vendor_test_register(void) eap->getKey = eap_vendor_test_getKey; eap->isSuccess = eap_vendor_test_isSuccess; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_server_wsc.c b/src/eap_server/eap_server_wsc.c index 9d9c28d704c1..7d9d285c39d0 100644 --- a/src/eap_server/eap_server_wsc.c +++ b/src/eap_server/eap_server_wsc.c @@ -488,7 +488,6 @@ static int eap_wsc_getTimeout(struct eap_sm *sm, void *priv) int eap_server_wsc_register(void) { struct eap_method *eap; - int ret; eap = eap_server_method_alloc(EAP_SERVER_METHOD_INTERFACE_VERSION, EAP_VENDOR_WFA, EAP_VENDOR_TYPE_WSC, @@ -505,8 +504,5 @@ int eap_server_wsc_register(void) eap->isSuccess = eap_wsc_isSuccess; eap->getTimeout = eap_wsc_getTimeout; - ret = eap_server_method_register(eap); - if (ret) - eap_server_method_free(eap); - return ret; + return eap_server_method_register(eap); } diff --git a/src/eap_server/eap_sim_db.c b/src/eap_server/eap_sim_db.c index acf5435300dc..d84c3d27de6b 100644 --- a/src/eap_server/eap_sim_db.c +++ b/src/eap_server/eap_sim_db.c @@ -66,6 +66,7 @@ struct eap_sim_db_data { struct eap_sim_pseudonym *pseudonyms; struct eap_sim_reauth *reauths; struct eap_sim_db_pending *pending; + unsigned int eap_sim_db_timeout; #ifdef CONFIG_SQLITE sqlite3 *sqlite_db; char db_tmp_identity[100]; @@ -76,6 +77,10 @@ struct eap_sim_db_data { }; +static void eap_sim_db_del_timeout(void *eloop_ctx, void *user_ctx); +static void eap_sim_db_query_timeout(void *eloop_ctx, void *user_ctx); + + #ifdef CONFIG_SQLITE static int db_table_exists(sqlite3 *db, const char *name) @@ -397,6 +402,57 @@ static void eap_sim_db_add_pending(struct eap_sim_db_data *data, } +static void eap_sim_db_free_pending(struct eap_sim_db_data *data, + struct eap_sim_db_pending *entry) +{ + eloop_cancel_timeout(eap_sim_db_query_timeout, data, entry); + eloop_cancel_timeout(eap_sim_db_del_timeout, data, entry); + os_free(entry); +} + + +static void eap_sim_db_del_pending(struct eap_sim_db_data *data, + struct eap_sim_db_pending *entry) +{ + struct eap_sim_db_pending **pp = &data->pending; + + while (*pp != NULL) { + if (*pp == entry) { + *pp = entry->next; + eap_sim_db_free_pending(data, entry); + return; + } + pp = &(*pp)->next; + } +} + + +static void eap_sim_db_del_timeout(void *eloop_ctx, void *user_ctx) +{ + struct eap_sim_db_data *data = eloop_ctx; + struct eap_sim_db_pending *entry = user_ctx; + + wpa_printf(MSG_DEBUG, "EAP-SIM DB: Delete query timeout for %p", entry); + eap_sim_db_del_pending(data, entry); +} + + +static void eap_sim_db_query_timeout(void *eloop_ctx, void *user_ctx) +{ + struct eap_sim_db_data *data = eloop_ctx; + struct eap_sim_db_pending *entry = user_ctx; + + /* + * Report failure and allow some time for EAP server to process it + * before deleting the query. + */ + wpa_printf(MSG_DEBUG, "EAP-SIM DB: Query timeout for %p", entry); + entry->state = FAILURE; + data->get_complete_cb(data->ctx, entry->cb_session_ctx); + eloop_register_timeout(1, 0, eap_sim_db_del_timeout, data, entry); +} + + static void eap_sim_db_sim_resp_auth(struct eap_sim_db_data *data, const char *imsi, char *buf) { @@ -472,7 +528,7 @@ static void eap_sim_db_sim_resp_auth(struct eap_sim_db_data *data, parse_fail: wpa_printf(MSG_DEBUG, "EAP-SIM DB: Failed to parse response string"); - os_free(entry); + eap_sim_db_free_pending(data, entry); } @@ -563,7 +619,7 @@ static void eap_sim_db_aka_resp_auth(struct eap_sim_db_data *data, parse_fail: wpa_printf(MSG_DEBUG, "EAP-SIM DB: Failed to parse response string"); - os_free(entry); + eap_sim_db_free_pending(data, entry); } @@ -690,12 +746,13 @@ static void eap_sim_db_close_socket(struct eap_sim_db_data *data) /** * eap_sim_db_init - Initialize EAP-SIM DB / authentication gateway interface * @config: Configuration data (e.g., file name) + * @db_timeout: Database lookup timeout * @get_complete_cb: Callback function for reporting availability of triplets * @ctx: Context pointer for get_complete_cb * Returns: Pointer to a private data structure or %NULL on failure */ struct eap_sim_db_data * -eap_sim_db_init(const char *config, +eap_sim_db_init(const char *config, unsigned int db_timeout, void (*get_complete_cb)(void *ctx, void *session_ctx), void *ctx) { @@ -709,6 +766,7 @@ eap_sim_db_init(const char *config, data->sock = -1; data->get_complete_cb = get_complete_cb; data->ctx = ctx; + data->eap_sim_db_timeout = db_timeout; data->fname = os_strdup(config); if (data->fname == NULL) goto fail; @@ -796,7 +854,7 @@ void eap_sim_db_deinit(void *priv) while (pending) { prev_pending = pending; pending = pending->next; - os_free(prev_pending); + eap_sim_db_free_pending(data, prev_pending); } os_free(data); @@ -833,11 +891,11 @@ static int eap_sim_db_send(struct eap_sim_db_data *data, const char *msg, } -static void eap_sim_db_expire_pending(struct eap_sim_db_data *data) +static void eap_sim_db_expire_pending(struct eap_sim_db_data *data, + struct eap_sim_db_pending *entry) { - /* TODO: add limit for maximum length for pending list; remove latest - * (i.e., last) entry from the list if the limit is reached; could also - * use timeout to expire pending entries */ + eloop_register_timeout(data->eap_sim_db_timeout, 0, + eap_sim_db_query_timeout, data, entry); } @@ -891,7 +949,7 @@ int eap_sim_db_get_gsm_triplets(struct eap_sim_db_data *data, if (entry->state == FAILURE) { wpa_printf(MSG_DEBUG, "EAP-SIM DB: Pending entry -> " "failure"); - os_free(entry); + eap_sim_db_free_pending(data, entry); return EAP_SIM_DB_FAILURE; } @@ -911,7 +969,7 @@ int eap_sim_db_get_gsm_triplets(struct eap_sim_db_data *data, os_memcpy(sres, entry->u.sim.sres, num_chal * EAP_SIM_SRES_LEN); os_memcpy(kc, entry->u.sim.kc, num_chal * EAP_SIM_KC_LEN); - os_free(entry); + eap_sim_db_free_pending(data, entry); return num_chal; } @@ -945,7 +1003,8 @@ int eap_sim_db_get_gsm_triplets(struct eap_sim_db_data *data, entry->cb_session_ctx = cb_session_ctx; entry->state = PENDING; eap_sim_db_add_pending(data, entry); - eap_sim_db_expire_pending(data); + eap_sim_db_expire_pending(data, entry); + wpa_printf(MSG_DEBUG, "EAP-SIM DB: Added query %p", entry); return EAP_SIM_DB_PENDING; } @@ -1356,7 +1415,7 @@ int eap_sim_db_get_aka_auth(struct eap_sim_db_data *data, const char *username, entry = eap_sim_db_get_pending(data, imsi, 1); if (entry) { if (entry->state == FAILURE) { - os_free(entry); + eap_sim_db_free_pending(data, entry); wpa_printf(MSG_DEBUG, "EAP-SIM DB: Failure"); return EAP_SIM_DB_FAILURE; } @@ -1375,7 +1434,7 @@ int eap_sim_db_get_aka_auth(struct eap_sim_db_data *data, const char *username, os_memcpy(ck, entry->u.aka.ck, EAP_AKA_CK_LEN); os_memcpy(res, entry->u.aka.res, EAP_AKA_RES_MAX_LEN); *res_len = entry->u.aka.res_len; - os_free(entry); + eap_sim_db_free_pending(data, entry); return 0; } @@ -1406,7 +1465,8 @@ int eap_sim_db_get_aka_auth(struct eap_sim_db_data *data, const char *username, entry->cb_session_ctx = cb_session_ctx; entry->state = PENDING; eap_sim_db_add_pending(data, entry); - eap_sim_db_expire_pending(data); + eap_sim_db_expire_pending(data, entry); + wpa_printf(MSG_DEBUG, "EAP-SIM DB: Added query %p", entry); return EAP_SIM_DB_PENDING; } diff --git a/src/eap_server/eap_sim_db.h b/src/eap_server/eap_sim_db.h index 53a1a7c3b4e3..ca900b915852 100644 --- a/src/eap_server/eap_sim_db.h +++ b/src/eap_server/eap_sim_db.h @@ -31,7 +31,7 @@ enum eap_sim_db_method { struct eap_sim_db_data; struct eap_sim_db_data * -eap_sim_db_init(const char *config, +eap_sim_db_init(const char *config, unsigned int db_timeout, void (*get_complete_cb)(void *ctx, void *session_ctx), void *ctx); diff --git a/src/eap_server/ikev2.c b/src/eap_server/ikev2.c index 632598fac72a..5385cd89246f 100644 --- a/src/eap_server/ikev2.c +++ b/src/eap_server/ikev2.c @@ -133,7 +133,7 @@ static int ikev2_parse_transform(struct ikev2_initiator_data *data, t = (const struct ikev2_transform *) pos; transform_len = WPA_GET_BE16(t->transform_length); - if (transform_len < (int) sizeof(*t) || pos + transform_len > end) { + if (transform_len < (int) sizeof(*t) || transform_len > end - pos) { wpa_printf(MSG_INFO, "IKEV2: Invalid transform length %d", transform_len); return -1; @@ -221,7 +221,7 @@ static int ikev2_parse_proposal(struct ikev2_initiator_data *data, p = (const struct ikev2_proposal *) pos; proposal_len = WPA_GET_BE16(p->proposal_length); - if (proposal_len < (int) sizeof(*p) || pos + proposal_len > end) { + if (proposal_len < (int) sizeof(*p) || proposal_len > end - pos) { wpa_printf(MSG_INFO, "IKEV2: Invalid proposal length %d", proposal_len); return -1; @@ -256,7 +256,7 @@ static int ikev2_parse_proposal(struct ikev2_initiator_data *data, ppos = (const u8 *) (p + 1); pend = pos + proposal_len; - if (ppos + p->spi_size > pend) { + if (p->spi_size > pend - ppos) { wpa_printf(MSG_INFO, "IKEV2: Not enough room for SPI " "in proposal"); return -1; diff --git a/src/eap_server/tncs.c b/src/eap_server/tncs.c index dc6f689c0b5e..cfcbd3ed828c 100644 --- a/src/eap_server/tncs.c +++ b/src/eap_server/tncs.c @@ -140,7 +140,7 @@ static struct tncs_data * tncs_get_conn(TNC_ConnectionID connectionID) /* TNCS functions that IMVs can call */ -TNC_Result TNC_TNCS_ReportMessageTypes( +static TNC_Result TNC_TNCS_ReportMessageTypes( TNC_IMVID imvID, TNC_MessageTypeList supportedTypes, TNC_UInt32 typeCount) @@ -173,7 +173,7 @@ TNC_Result TNC_TNCS_ReportMessageTypes( } -TNC_Result TNC_TNCS_SendMessage( +static TNC_Result TNC_TNCS_SendMessage( TNC_IMVID imvID, TNC_ConnectionID connectionID, TNC_BufferReference message, @@ -222,7 +222,7 @@ TNC_Result TNC_TNCS_SendMessage( } -TNC_Result TNC_TNCS_RequestHandshakeRetry( +static TNC_Result TNC_TNCS_RequestHandshakeRetry( TNC_IMVID imvID, TNC_ConnectionID connectionID, TNC_RetryReason reason) @@ -233,7 +233,7 @@ TNC_Result TNC_TNCS_RequestHandshakeRetry( } -TNC_Result TNC_TNCS_ProvideRecommendation( +static TNC_Result TNC_TNCS_ProvideRecommendation( TNC_IMVID imvID, TNC_ConnectionID connectionID, TNC_IMV_Action_Recommendation recommendation, @@ -260,7 +260,7 @@ TNC_Result TNC_TNCS_ProvideRecommendation( } -TNC_Result TNC_TNCS_GetAttribute( +static TNC_Result TNC_TNCS_GetAttribute( TNC_IMVID imvID, TNC_ConnectionID connectionID, TNC_AttributeID attribureID, @@ -274,7 +274,7 @@ TNC_Result TNC_TNCS_GetAttribute( } -TNC_Result TNC_TNCS_SetAttribute( +static TNC_Result TNC_TNCS_SetAttribute( TNC_IMVID imvID, TNC_ConnectionID connectionID, TNC_AttributeID attribureID, @@ -287,7 +287,7 @@ TNC_Result TNC_TNCS_SetAttribute( } -TNC_Result TNC_TNCS_BindFunction( +static TNC_Result TNC_TNCS_BindFunction( TNC_IMVID imvID, char *functionName, void **pOutFunctionPointer) |