From 0e3e3a9ab54428310236248cc1b8cf77d5337073 Mon Sep 17 00:00:00 2001 From: Jouni Malinen Date: Fri, 28 Feb 2020 00:51:07 +0200 Subject: [PATCH] wlantest: Update BSS IEs based on EAPOL-Key msg 3/4 If no Beacon or Probe Response frame has been seen in the capture, use the IEs from EAPOL-Key msg 3/4 to set up BSS information. Signed-off-by: Jouni Malinen --- wlantest/bss.c | 21 ++++++++++++++------- wlantest/rx_eapol.c | 42 +++++++++++++++++++++++++++++------------- wlantest/rx_mgmt.c | 4 ++-- wlantest/sta.c | 3 ++- wlantest/wlantest.h | 3 ++- 5 files changed, 49 insertions(+), 24 deletions(-) diff --git a/wlantest/bss.c b/wlantest/bss.c index 298a902c7..0556c72e2 100644 --- a/wlantest/bss.c +++ b/wlantest/bss.c @@ -129,7 +129,7 @@ static void bss_add_pmk(struct wlantest *wt, struct wlantest_bss *bss) void bss_update(struct wlantest *wt, struct wlantest_bss *bss, - struct ieee802_11_elems *elems) + struct ieee802_11_elems *elems, int beacon) { struct wpa_ie_data data; int update = 0; @@ -137,15 +137,18 @@ void bss_update(struct wlantest *wt, struct wlantest_bss *bss, if (bss->capab_info != bss->prev_capab_info) update = 1; - if (elems->ssid == NULL || elems->ssid_len > 32) { - wpa_printf(MSG_INFO, "Invalid or missing SSID in a Beacon " - "frame for " MACSTR, MAC2STR(bss->bssid)); + if (beacon && (!elems->ssid || elems->ssid_len > 32)) { + wpa_printf(MSG_INFO, + "Invalid or missing SSID in a %s frame for " MACSTR, + beacon == 1 ? "Beacon" : "Probe Response", + MAC2STR(bss->bssid)); bss->parse_error_reported = 1; return; } - if (bss->ssid_len != elems->ssid_len || - os_memcmp(bss->ssid, elems->ssid, bss->ssid_len) != 0) { + if (beacon && + (bss->ssid_len != elems->ssid_len || + os_memcmp(bss->ssid, elems->ssid, bss->ssid_len) != 0)) { wpa_printf(MSG_DEBUG, "Store SSID '%s' for BSSID " MACSTR, wpa_ssid_txt(elems->ssid, elems->ssid_len), MAC2STR(bss->bssid)); @@ -223,7 +226,11 @@ void bss_update(struct wlantest *wt, struct wlantest_bss *bss, if (!update) return; - bss->beacon_seen = 1; + if (beacon == 1) + bss->beacon_seen = 1; + else if (beacon == 2) + bss->proberesp_seen = 1; + bss->ies_set = 1; bss->prev_capab_info = bss->capab_info; bss->proto = 0; bss->pairwise_cipher = 0; diff --git a/wlantest/rx_eapol.c b/wlantest/rx_eapol.c index c58b82c16..2e49929c1 100644 --- a/wlantest/rx_eapol.c +++ b/wlantest/rx_eapol.c @@ -222,6 +222,25 @@ static void derive_ptk(struct wlantest *wt, struct wlantest_bss *bss, } +static void elems_from_eapol_ie(struct ieee802_11_elems *elems, + struct wpa_eapol_ie_parse *ie) +{ + os_memset(elems, 0, sizeof(*elems)); + if (ie->wpa_ie) { + elems->wpa_ie = ie->wpa_ie + 2; + elems->wpa_ie_len = ie->wpa_ie_len - 2; + } + if (ie->rsn_ie) { + elems->rsn_ie = ie->rsn_ie + 2; + elems->rsn_ie_len = ie->rsn_ie_len - 2; + } + if (ie->osen) { + elems->osen = ie->osen + 2; + elems->osen_len = ie->osen_len - 2; + } +} + + static void rx_data_eapol_key_2_of_4(struct wlantest *wt, const u8 *dst, const u8 *src, const u8 *data, size_t len) { @@ -268,19 +287,7 @@ static void rx_data_eapol_key_2_of_4(struct wlantest *wt, const u8 *dst, if (!sta->assocreq_seen) { struct ieee802_11_elems elems; - os_memset(&elems, 0, sizeof(elems)); - if (ie.wpa_ie) { - elems.wpa_ie = ie.wpa_ie + 2; - elems.wpa_ie_len = ie.wpa_ie_len - 2; - } - if (ie.rsn_ie) { - elems.rsn_ie = ie.rsn_ie + 2; - elems.rsn_ie_len = ie.rsn_ie_len - 2; - } - if (ie.osen) { - elems.osen = ie.osen + 2; - elems.osen_len = ie.osen_len - 2; - } + elems_from_eapol_ie(&elems, &ie); wpa_printf(MSG_DEBUG, "Update STA data based on IEs in EAPOL-Key 2/4"); sta_update_assoc(sta, &elems); @@ -750,6 +757,15 @@ static void rx_data_eapol_key_3_of_4(struct wlantest *wt, const u8 *dst, return; } + if (!bss->ies_set) { + struct ieee802_11_elems elems; + + elems_from_eapol_ie(&elems, &ie); + wpa_printf(MSG_DEBUG, + "Update BSS data based on IEs in EAPOL-Key 3/4"); + bss_update(wt, bss, &elems, 0); + } + if ((ie.wpa_ie && os_memcmp(ie.wpa_ie, bss->wpaie, ie.wpa_ie_len) != 0) || (ie.wpa_ie == NULL && bss->wpaie[0])) { diff --git a/wlantest/rx_mgmt.c b/wlantest/rx_mgmt.c index 086db4a66..78fd3c80a 100644 --- a/wlantest/rx_mgmt.c +++ b/wlantest/rx_mgmt.c @@ -86,7 +86,7 @@ static void rx_mgmt_beacon(struct wlantest *wt, const u8 *data, size_t len) return; } - bss_update(wt, bss, &elems); + bss_update(wt, bss, &elems, 1); mme = get_ie(mgmt->u.beacon.variable, len - offset, WLAN_EID_MMIE); if (!mme) { @@ -173,7 +173,7 @@ static void rx_mgmt_probe_resp(struct wlantest *wt, const u8 *data, size_t len) return; } - bss_update(wt, bss, &elems); + bss_update(wt, bss, &elems, 2); } diff --git a/wlantest/sta.c b/wlantest/sta.c index 3e5ff51b6..62dae0790 100644 --- a/wlantest/sta.c +++ b/wlantest/sta.c @@ -156,7 +156,8 @@ void sta_update_assoc(struct wlantest_sta *sta, struct ieee802_11_elems *elems) MAC2STR(sta->addr), sta->pairwise_cipher, MAC2STR(bss->bssid), bss->pairwise_cipher); } - if (sta->proto && data.group_cipher != bss->group_cipher) { + if (sta->proto && data.group_cipher != bss->group_cipher && + bss->ies_set) { wpa_printf(MSG_INFO, "Mismatch in group cipher: STA " MACSTR " 0x%x != BSS " MACSTR " 0x%x", MAC2STR(sta->addr), data.group_cipher, diff --git a/wlantest/wlantest.h b/wlantest/wlantest.h index 69aa155d1..2cf51966a 100644 --- a/wlantest/wlantest.h +++ b/wlantest/wlantest.h @@ -135,6 +135,7 @@ struct wlantest_bss { size_t ssid_len; int beacon_seen; int proberesp_seen; + int ies_set; int parse_error_reported; u8 wpaie[257]; u8 rsnie[257]; @@ -265,7 +266,7 @@ struct wlantest_bss * bss_find(struct wlantest *wt, const u8 *bssid); struct wlantest_bss * bss_get(struct wlantest *wt, const u8 *bssid); void bss_deinit(struct wlantest_bss *bss); void bss_update(struct wlantest *wt, struct wlantest_bss *bss, - struct ieee802_11_elems *elems); + struct ieee802_11_elems *elems, int beacon); void bss_flush(struct wlantest *wt); int bss_add_pmk_from_passphrase(struct wlantest_bss *bss, const char *passphrase);