FILS: Parse and report received FILS HLP Containers from response
The new FILS-HLP-RX control interface event is now used to report received FILS HLP responses from (Re)Association Response frame as a response to the HLP requests configured with FILS_HLP_REQ_ADD. Signed-off-by: Jouni Malinen <jouni@qca.qualcomm.com>
This commit is contained in:
parent
91d91abf6f
commit
124ddfa19e
5 changed files with 103 additions and 1 deletions
|
@ -300,6 +300,10 @@ extern "C" {
|
||||||
/* PMKSA cache entry removed; parameters: <BSSID> <network_id> */
|
/* PMKSA cache entry removed; parameters: <BSSID> <network_id> */
|
||||||
#define PMKSA_CACHE_REMOVED "PMKSA-CACHE-REMOVED "
|
#define PMKSA_CACHE_REMOVED "PMKSA-CACHE-REMOVED "
|
||||||
|
|
||||||
|
/* FILS HLP Container receive; parameters: dst=<addr> src=<addr> frame=<hexdump>
|
||||||
|
*/
|
||||||
|
#define FILS_HLP_RX "FILS-HLP-RX "
|
||||||
|
|
||||||
/* BSS command information masks */
|
/* BSS command information masks */
|
||||||
|
|
||||||
#define WPA_BSS_MASK_ALL 0xFFFDFFFF
|
#define WPA_BSS_MASK_ALL 0xFFFDFFFF
|
||||||
|
|
|
@ -3564,6 +3564,71 @@ struct wpabuf * fils_build_assoc_req(struct wpa_sm *sm, const u8 **kek,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void fils_process_hlp_resp(struct wpa_sm *sm, const u8 *resp, size_t len)
|
||||||
|
{
|
||||||
|
const u8 *pos, *end;
|
||||||
|
|
||||||
|
wpa_hexdump(MSG_MSGDUMP, "FILS: HLP response", resp, len);
|
||||||
|
if (len < 2 * ETH_ALEN)
|
||||||
|
return;
|
||||||
|
pos = resp + 2 * ETH_ALEN;
|
||||||
|
end = resp + len;
|
||||||
|
if (end - pos >= 6 &&
|
||||||
|
os_memcmp(pos, "\xaa\xaa\x03\x00\x00\x00", 6) == 0)
|
||||||
|
pos += 6; /* Remove SNAP/LLC header */
|
||||||
|
wpa_sm_fils_hlp_rx(sm, resp, resp + ETH_ALEN, pos, end - pos);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void fils_process_hlp_container(struct wpa_sm *sm, const u8 *pos,
|
||||||
|
size_t len)
|
||||||
|
{
|
||||||
|
const u8 *end = pos + len;
|
||||||
|
u8 *tmp, *tmp_pos;
|
||||||
|
|
||||||
|
/* Check if there are any FILS HLP Container elements */
|
||||||
|
while (end - pos >= 2) {
|
||||||
|
if (2 + pos[1] > end - pos)
|
||||||
|
return;
|
||||||
|
if (pos[0] == WLAN_EID_EXTENSION &&
|
||||||
|
pos[1] >= 1 + 2 * ETH_ALEN &&
|
||||||
|
pos[2] == WLAN_EID_EXT_FILS_HLP_CONTAINER)
|
||||||
|
break;
|
||||||
|
pos += 2 + pos[1];
|
||||||
|
}
|
||||||
|
if (end - pos < 2)
|
||||||
|
return; /* No FILS HLP Container elements */
|
||||||
|
|
||||||
|
tmp = os_malloc(end - pos);
|
||||||
|
if (!tmp)
|
||||||
|
return;
|
||||||
|
|
||||||
|
while (end - pos >= 2) {
|
||||||
|
if (2 + pos[1] > end - pos ||
|
||||||
|
pos[0] != WLAN_EID_EXTENSION ||
|
||||||
|
pos[1] < 1 + 2 * ETH_ALEN ||
|
||||||
|
pos[2] != WLAN_EID_EXT_FILS_HLP_CONTAINER)
|
||||||
|
break;
|
||||||
|
tmp_pos = tmp;
|
||||||
|
os_memcpy(tmp_pos, pos + 3, pos[1] - 1);
|
||||||
|
tmp_pos += pos[1] - 1;
|
||||||
|
pos += 2 + pos[1];
|
||||||
|
|
||||||
|
/* Add possible fragments */
|
||||||
|
while (end - pos >= 2 && pos[0] == WLAN_EID_FRAGMENT &&
|
||||||
|
2 + pos[1] <= end - pos) {
|
||||||
|
os_memcpy(tmp_pos, pos + 2, pos[1]);
|
||||||
|
tmp_pos += pos[1];
|
||||||
|
pos += 2 + pos[1];
|
||||||
|
}
|
||||||
|
|
||||||
|
fils_process_hlp_resp(sm, tmp, tmp_pos - tmp);
|
||||||
|
}
|
||||||
|
|
||||||
|
os_free(tmp);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
int fils_process_assoc_resp(struct wpa_sm *sm, const u8 *resp, size_t len)
|
int fils_process_assoc_resp(struct wpa_sm *sm, const u8 *resp, size_t len)
|
||||||
{
|
{
|
||||||
const struct ieee80211_mgmt *mgmt;
|
const struct ieee80211_mgmt *mgmt;
|
||||||
|
@ -3705,7 +3770,8 @@ int fils_process_assoc_resp(struct wpa_sm *sm, const u8 *resp, size_t len)
|
||||||
/* TK is not needed anymore in supplicant */
|
/* TK is not needed anymore in supplicant */
|
||||||
os_memset(sm->ptk.tk, 0, WPA_TK_MAX_LEN);
|
os_memset(sm->ptk.tk, 0, WPA_TK_MAX_LEN);
|
||||||
|
|
||||||
/* TODO: FILS HLP Container */
|
/* FILS HLP Container */
|
||||||
|
fils_process_hlp_container(sm, ie_start, end - ie_start);
|
||||||
|
|
||||||
/* TODO: FILS IP Address Assignment */
|
/* TODO: FILS IP Address Assignment */
|
||||||
|
|
||||||
|
|
|
@ -79,6 +79,8 @@ struct wpa_sm_ctx {
|
||||||
const u8 *kck, size_t kck_len,
|
const u8 *kck, size_t kck_len,
|
||||||
const u8 *replay_ctr);
|
const u8 *replay_ctr);
|
||||||
int (*key_mgmt_set_pmk)(void *ctx, const u8 *pmk, size_t pmk_len);
|
int (*key_mgmt_set_pmk)(void *ctx, const u8 *pmk, size_t pmk_len);
|
||||||
|
void (*fils_hlp_rx)(void *ctx, const u8 *dst, const u8 *src,
|
||||||
|
const u8 *pkt, size_t pkt_len);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -365,6 +365,15 @@ static inline int wpa_sm_key_mgmt_set_pmk(struct wpa_sm *sm,
|
||||||
return sm->ctx->key_mgmt_set_pmk(sm->ctx->ctx, pmk, pmk_len);
|
return sm->ctx->key_mgmt_set_pmk(sm->ctx->ctx, pmk, pmk_len);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static inline void wpa_sm_fils_hlp_rx(struct wpa_sm *sm,
|
||||||
|
const u8 *dst, const u8 *src,
|
||||||
|
const u8 *pkt, size_t pkt_len)
|
||||||
|
{
|
||||||
|
if (sm->ctx->fils_hlp_rx)
|
||||||
|
sm->ctx->fils_hlp_rx(sm->ctx->ctx, dst, src, pkt, pkt_len);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
int wpa_eapol_key_send(struct wpa_sm *sm, struct wpa_ptk *ptk,
|
int wpa_eapol_key_send(struct wpa_sm *sm, struct wpa_ptk *ptk,
|
||||||
int ver, const u8 *dest, u16 proto,
|
int ver, const u8 *dest, u16 proto,
|
||||||
u8 *msg, size_t msg_len, u8 *key_mic);
|
u8 *msg, size_t msg_len, u8 *key_mic);
|
||||||
|
|
|
@ -1090,6 +1090,7 @@ int wpa_supplicant_init_eapol(struct wpa_supplicant *wpa_s)
|
||||||
|
|
||||||
|
|
||||||
#ifndef CONFIG_NO_WPA
|
#ifndef CONFIG_NO_WPA
|
||||||
|
|
||||||
static void wpa_supplicant_set_rekey_offload(void *ctx,
|
static void wpa_supplicant_set_rekey_offload(void *ctx,
|
||||||
const u8 *kek, size_t kek_len,
|
const u8 *kek, size_t kek_len,
|
||||||
const u8 *kck, size_t kck_len,
|
const u8 *kck, size_t kck_len,
|
||||||
|
@ -1113,6 +1114,25 @@ static int wpa_supplicant_key_mgmt_set_pmk(void *ctx, const u8 *pmk,
|
||||||
else
|
else
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void wpa_supplicant_fils_hlp_rx(void *ctx, const u8 *dst, const u8 *src,
|
||||||
|
const u8 *pkt, size_t pkt_len)
|
||||||
|
{
|
||||||
|
struct wpa_supplicant *wpa_s = ctx;
|
||||||
|
char *hex;
|
||||||
|
size_t hexlen;
|
||||||
|
|
||||||
|
hexlen = pkt_len * 2 + 1;
|
||||||
|
hex = os_malloc(hexlen);
|
||||||
|
if (!hex)
|
||||||
|
return;
|
||||||
|
wpa_snprintf_hex(hex, hexlen, pkt, pkt_len);
|
||||||
|
wpa_msg(wpa_s, MSG_INFO, FILS_HLP_RX "dst=" MACSTR " src=" MACSTR
|
||||||
|
" frame=%s", MAC2STR(dst), MAC2STR(src), hex);
|
||||||
|
os_free(hex);
|
||||||
|
}
|
||||||
|
|
||||||
#endif /* CONFIG_NO_WPA */
|
#endif /* CONFIG_NO_WPA */
|
||||||
|
|
||||||
|
|
||||||
|
@ -1162,6 +1182,7 @@ int wpa_supplicant_init_wpa(struct wpa_supplicant *wpa_s)
|
||||||
#endif /* CONFIG_TDLS */
|
#endif /* CONFIG_TDLS */
|
||||||
ctx->set_rekey_offload = wpa_supplicant_set_rekey_offload;
|
ctx->set_rekey_offload = wpa_supplicant_set_rekey_offload;
|
||||||
ctx->key_mgmt_set_pmk = wpa_supplicant_key_mgmt_set_pmk;
|
ctx->key_mgmt_set_pmk = wpa_supplicant_key_mgmt_set_pmk;
|
||||||
|
ctx->fils_hlp_rx = wpa_supplicant_fils_hlp_rx;
|
||||||
|
|
||||||
wpa_s->wpa = wpa_sm_init(ctx);
|
wpa_s->wpa = wpa_sm_init(ctx);
|
||||||
if (wpa_s->wpa == NULL) {
|
if (wpa_s->wpa == NULL) {
|
||||||
|
|
Loading…
Reference in a new issue