EAP-SIM/AKA server: Allow method specific identity exchange to be skipped
While the EAP-SIM/AKA RFCs recommend against doing this, some deployed authentication servers use the identity from the EAP-Response/Identity directly without using an EAP method specific indication (AT_IDENTITY). Having a capability to configure hostapd EAP server to behave in this manner helps in increasing testing coverage for the EAP peer implementation. Signed-off-by: Jouni Malinen <quic_jouni@quicinc.com>
This commit is contained in:
parent
40af6560ba
commit
c6268e103f
4 changed files with 61 additions and 6 deletions
|
@ -1465,6 +1465,14 @@ eap_server=0
|
|||
# 1 = use pseudonyms, but not fast reauthentication
|
||||
# 2 = do not use pseudonyms, but use fast reauthentication
|
||||
# 3 = use pseudonyms and use fast reauthentication (default)
|
||||
# 4 = do not use pseudonyms or fast reauthentication and allow
|
||||
# EAP-Response/Identity to be used without method specific identity exchange
|
||||
# 5 = use pseudonyms, but not fast reauthentication and allow
|
||||
# EAP-Response/Identity to be used without method specific identity exchange
|
||||
# 6 = do not use pseudonyms, but use fast reauthentication and allow
|
||||
# EAP-Response/Identity to be used without method specific identity exchange
|
||||
# 7 = use pseudonyms and use fast reauthentication and allow
|
||||
# EAP-Response/Identity to be used without method specific identity exchange
|
||||
#eap_sim_id=3
|
||||
|
||||
# IMSI privacy key (PEM encoded RSA 2048-bit private key) for decrypting
|
||||
|
|
|
@ -160,6 +160,7 @@ struct eap_sm {
|
|||
size_t identity_len;
|
||||
char *serial_num;
|
||||
char imsi[20];
|
||||
char sim_aka_permanent[20];
|
||||
/* Whether Phase 2 method should validate identity match */
|
||||
int require_identity_match;
|
||||
int lastId; /* Identifier used in the last EAP-Packet */
|
||||
|
|
|
@ -134,10 +134,17 @@ static void eap_aka_check_identity(struct eap_sm *sm,
|
|||
struct eap_aka_data *data)
|
||||
{
|
||||
char *username;
|
||||
const u8 *identity = sm->identity;
|
||||
size_t identity_len = sm->identity_len;
|
||||
|
||||
if (sm->sim_aka_permanent[0]) {
|
||||
identity = (const u8 *) sm->sim_aka_permanent;
|
||||
identity_len = os_strlen(sm->sim_aka_permanent);
|
||||
}
|
||||
|
||||
/* Check if we already know the identity from EAP-Response/Identity */
|
||||
|
||||
username = sim_get_username(sm->identity, sm->identity_len);
|
||||
username = sim_get_username(identity, identity_len);
|
||||
if (username == NULL)
|
||||
return;
|
||||
|
||||
|
@ -150,6 +157,16 @@ static void eap_aka_check_identity(struct eap_sm *sm,
|
|||
return;
|
||||
}
|
||||
|
||||
if (sm->sim_aka_permanent[0] && data->state == IDENTITY) {
|
||||
/* Skip AKA/Identity exchange since the permanent identity
|
||||
* was recognized. */
|
||||
os_free(username);
|
||||
os_strlcpy(data->permanent, sm->sim_aka_permanent,
|
||||
sizeof(data->permanent));
|
||||
eap_aka_fullauth(sm, data);
|
||||
return;
|
||||
}
|
||||
|
||||
if ((data->eap_method == EAP_TYPE_AKA_PRIME &&
|
||||
username[0] == EAP_AKA_PRIME_PSEUDONYM_PREFIX) ||
|
||||
(data->eap_method == EAP_TYPE_AKA &&
|
||||
|
|
|
@ -106,12 +106,28 @@ static struct wpabuf * eap_sim_build_start(struct eap_sm *sm,
|
|||
{
|
||||
struct eap_sim_msg *msg;
|
||||
u8 ver[2];
|
||||
bool id_req = true;
|
||||
|
||||
wpa_printf(MSG_DEBUG, "EAP-SIM: Generating Start");
|
||||
msg = eap_sim_msg_init(EAP_CODE_REQUEST, id, EAP_TYPE_SIM,
|
||||
EAP_SIM_SUBTYPE_START);
|
||||
data->start_round++;
|
||||
if (data->start_round == 1) {
|
||||
|
||||
if (data->start_round == 1 && (sm->cfg->eap_sim_id & 0x04)) {
|
||||
char *username;
|
||||
|
||||
username = sim_get_username(sm->identity, sm->identity_len);
|
||||
if (username && username[0] == EAP_SIM_REAUTH_ID_PREFIX &&
|
||||
eap_sim_db_get_reauth_entry(sm->cfg->eap_sim_db_priv,
|
||||
username))
|
||||
id_req = false;
|
||||
|
||||
os_free(username);
|
||||
}
|
||||
|
||||
if (!id_req) {
|
||||
wpa_printf(MSG_DEBUG, " No identity request");
|
||||
} else if (data->start_round == 1) {
|
||||
/*
|
||||
* RFC 4186, Chap. 4.2.4 recommends that identity from EAP is
|
||||
* ignored and the SIM/Start is used to request the identity.
|
||||
|
@ -434,6 +450,7 @@ static void eap_sim_process_start(struct eap_sm *sm,
|
|||
struct wpabuf *respData,
|
||||
struct eap_sim_attrs *attr)
|
||||
{
|
||||
const u8 *identity;
|
||||
size_t identity_len;
|
||||
u8 ver_list[2];
|
||||
u8 *new_identity;
|
||||
|
@ -449,9 +466,13 @@ static void eap_sim_process_start(struct eap_sm *sm,
|
|||
goto skip_id_update;
|
||||
}
|
||||
|
||||
if ((sm->cfg->eap_sim_id & 0x04) &&
|
||||
(!attr->identity || attr->identity_len == 0))
|
||||
goto skip_id_attr;
|
||||
|
||||
/*
|
||||
* We always request identity in SIM/Start, so the peer is required to
|
||||
* have replied with one.
|
||||
* Unless explicitly configured otherwise, we always request identity
|
||||
* in SIM/Start, so the peer is required to have replied with one.
|
||||
*/
|
||||
if (!attr->identity || attr->identity_len == 0) {
|
||||
wpa_printf(MSG_DEBUG, "EAP-SIM: Peer did not provide any "
|
||||
|
@ -467,9 +488,17 @@ static void eap_sim_process_start(struct eap_sm *sm,
|
|||
os_memcpy(sm->identity, attr->identity, attr->identity_len);
|
||||
sm->identity_len = attr->identity_len;
|
||||
|
||||
skip_id_attr:
|
||||
if (sm->sim_aka_permanent[0]) {
|
||||
identity = (const u8 *) sm->sim_aka_permanent;
|
||||
identity_len = os_strlen(sm->sim_aka_permanent);
|
||||
} else {
|
||||
identity = sm->identity;
|
||||
identity_len = sm->identity_len;
|
||||
}
|
||||
wpa_hexdump_ascii(MSG_DEBUG, "EAP-SIM: Identity",
|
||||
sm->identity, sm->identity_len);
|
||||
username = sim_get_username(sm->identity, sm->identity_len);
|
||||
identity, identity_len);
|
||||
username = sim_get_username(identity, identity_len);
|
||||
if (username == NULL)
|
||||
goto failed;
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue