# 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
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;
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 &&
{
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.
struct wpabuf *respData,
struct eap_sim_attrs *attr)
{
+ const u8 *identity;
size_t identity_len;
u8 ver_list[2];
u8 *new_identity;
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 "
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;