diff --git a/src/common/ieee802_11_defs.h b/src/common/ieee802_11_defs.h index 1e09e1610..86d71c156 100644 --- a/src/common/ieee802_11_defs.h +++ b/src/common/ieee802_11_defs.h @@ -2359,4 +2359,9 @@ enum scs_request_type { SCS_REQ_CHANGE = 2, }; +/* Optional subelement IDs for MSCS Descriptor element */ +enum mscs_description_subelem { + MCSC_SUBELEM_STATUS = 1, +}; + #endif /* IEEE802_11_DEFS_H */ diff --git a/wpa_supplicant/events.c b/wpa_supplicant/events.c index 3b169dae4..80b803f5c 100644 --- a/wpa_supplicant/events.c +++ b/wpa_supplicant/events.c @@ -2678,11 +2678,11 @@ static int wpa_supplicant_event_associnfo(struct wpa_supplicant *wpa_s, { int l, len, found = 0, found_x = 0, wpa_found, rsn_found; const u8 *p; -#if defined(CONFIG_IEEE80211R) || defined(CONFIG_OWE) u8 bssid[ETH_ALEN]; -#endif /* CONFIG_IEEE80211R || CONFIG_OWE */ + bool bssid_known; wpa_dbg(wpa_s, MSG_DEBUG, "Association info event"); + bssid_known = wpa_drv_get_bssid(wpa_s, bssid) == 0; if (data->assoc_info.req_ies) wpa_hexdump(MSG_DEBUG, "req_ies", data->assoc_info.req_ies, data->assoc_info.req_ies_len); @@ -2799,7 +2799,7 @@ static int wpa_supplicant_event_associnfo(struct wpa_supplicant *wpa_s, #ifdef CONFIG_OWE if (wpa_s->key_mgmt == WPA_KEY_MGMT_OWE && - (wpa_drv_get_bssid(wpa_s, bssid) < 0 || + (!bssid_known || owe_process_assoc_resp(wpa_s->wpa, bssid, data->assoc_info.resp_ies, data->assoc_info.resp_ies_len) < 0)) { @@ -2834,7 +2834,7 @@ no_pfs: #ifdef CONFIG_IEEE80211R #ifdef CONFIG_SME if (wpa_s->sme.auth_alg == WPA_AUTH_ALG_FT) { - if (wpa_drv_get_bssid(wpa_s, bssid) < 0 || + if (!bssid_known || wpa_ft_validate_reassoc_resp(wpa_s->wpa, data->assoc_info.resp_ies, data->assoc_info.resp_ies_len, @@ -2894,7 +2894,7 @@ no_pfs: /* Process FT when SME is in the driver */ if (!(wpa_s->drv_flags & WPA_DRIVER_FLAGS_SME) && wpa_ft_is_completed(wpa_s->wpa)) { - if (wpa_drv_get_bssid(wpa_s, bssid) < 0 || + if (!bssid_known || wpa_ft_validate_reassoc_resp(wpa_s->wpa, data->assoc_info.resp_ies, data->assoc_info.resp_ies_len, @@ -2912,6 +2912,11 @@ no_pfs: data->assoc_info.resp_ies_len); #endif /* CONFIG_IEEE80211R */ + if (bssid_known) + wpas_handle_assoc_resp_mscs(wpa_s, bssid, + data->assoc_info.resp_ies, + data->assoc_info.resp_ies_len); + /* WPA/RSN IE from Beacon/ProbeResp */ p = data->assoc_info.beacon_ies; l = data->assoc_info.beacon_ies_len; diff --git a/wpa_supplicant/robust_av.c b/wpa_supplicant/robust_av.c index f7e4100e5..86f47d295 100644 --- a/wpa_supplicant/robust_av.c +++ b/wpa_supplicant/robust_av.c @@ -9,6 +9,7 @@ #include "utils/includes.h" #include "utils/common.h" #include "common/wpa_ctrl.h" +#include "common/ieee802_11_common.h" #include "wpa_supplicant_i.h" #include "driver_i.h" #include "bss.h" @@ -119,3 +120,29 @@ void wpas_handle_robust_av_recv_action(struct wpa_supplicant *wpa_s, wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_MSCS_RESULT "bssid=" MACSTR " status_code=%u", MAC2STR(src), status_code); } + + +void wpas_handle_assoc_resp_mscs(struct wpa_supplicant *wpa_s, const u8 *bssid, + const u8 *ies, size_t ies_len) +{ + const u8 *mscs_desc_ie, *mscs_status; + u16 status; + + /* Process optional MSCS Status subelement when MSCS IE is in + * (Re)Association Response frame */ + if (!ies || ies_len == 0 || !wpa_s->robust_av.valid_config) + return; + + mscs_desc_ie = get_ie_ext(ies, ies_len, WLAN_EID_EXT_MSCS_DESCRIPTOR); + if (!mscs_desc_ie || mscs_desc_ie[1] < 1) + return; + + mscs_status = get_ie(mscs_desc_ie, mscs_desc_ie[1], + MCSC_SUBELEM_STATUS); + if (!mscs_status || mscs_status[1] < 2) + return; + + status = WPA_GET_LE16(mscs_status + 2); + wpa_msg(wpa_s, MSG_INFO, WPA_EVENT_MSCS_RESULT "bssid=" MACSTR + " status_code=%u", MAC2STR(bssid), status); +} diff --git a/wpa_supplicant/wpa_supplicant_i.h b/wpa_supplicant/wpa_supplicant_i.h index 9ed886ff5..775590058 100644 --- a/wpa_supplicant/wpa_supplicant_i.h +++ b/wpa_supplicant/wpa_supplicant_i.h @@ -1641,5 +1641,7 @@ void wpas_populate_mscs_descriptor_ie(struct robust_av_data *robust_av, void wpas_handle_robust_av_recv_action(struct wpa_supplicant *wpa_s, const u8 *src, const u8 *buf, size_t len); +void wpas_handle_assoc_resp_mscs(struct wpa_supplicant *wpa_s, const u8 *bssid, + const u8 *ies, size_t ies_len); #endif /* WPA_SUPPLICANT_I_H */