Date: Thu, 3 Jun 2021 16:38:16 GMT From: Cy Schubert <cy@FreeBSD.org> To: src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org Subject: git: 40c7ff83e74e - vendor/wpa - wpa: Import wpa_supplicant/hostapd commit e8662e9d4 Message-ID: <202106031638.153GcGhh069766@gitrepo.freebsd.org>
next in thread | raw e-mail | index | archive | help
The branch vendor/wpa has been updated by cy: URL: https://cgit.FreeBSD.org/src/commit/?id=40c7ff83e74eabba5a7e2caefeea12372b2d3f9a commit 40c7ff83e74eabba5a7e2caefeea12372b2d3f9a Author: Cy Schubert <cy@FreeBSD.org> AuthorDate: 2021-06-03 16:15:01 +0000 Commit: Cy Schubert <cy@FreeBSD.org> CommitDate: 2021-06-03 16:15:01 +0000 wpa: Import wpa_supplicant/hostapd commit e8662e9d4 This is the June update to vendor/wpa committed upstream 2021/06/03. --- hostapd/Android.mk | 4 + hostapd/config_file.c | 2 + hostapd/ctrl_iface.c | 68 ++++ hostapd/hostapd.conf | 10 + src/ap/acs.c | 52 ++- src/ap/ap_config.c | 1 + src/ap/ap_config.h | 1 + src/ap/beacon.c | 5 + src/ap/dpp_hostapd.c | 9 +- src/ap/hostapd.c | 21 ++ src/ap/hw_features.c | 10 +- src/ap/ieee802_11_he.c | 24 +- src/ap/ieee802_11_vht.c | 2 +- src/ap/pmksa_cache_auth.c | 3 +- src/ap/wpa_auth.c | 32 +- src/ap/wpa_auth.h | 5 + src/ap/wpa_auth_glue.c | 6 +- src/common/dpp.h | 3 +- src/common/dpp_tcp.c | 40 ++- src/common/ieee802_11_defs.h | 2 +- src/common/qca-vendor.h | 365 ++++++++++++++++++++- src/drivers/driver.h | 1 + src/drivers/driver_nl80211.c | 43 ++- src/drivers/nl80211_copy.h | 22 ++ src/rsn_supp/pmksa_cache.c | 3 +- src/rsn_supp/tdls.c | 2 + tests/fuzzing/eap-aka-peer/eap-aka-peer.c | 4 +- tests/fuzzing/eap-sim-peer/eap-sim-peer.c | 4 +- tests/hwsim/auth_serv/index.txt | 2 +- tests/hwsim/auth_serv/ocsp-multi-server-cache.der | Bin 493 -> 493 bytes tests/hwsim/auth_serv/ocsp-req.der | Bin 76 -> 76 bytes tests/hwsim/auth_serv/ocsp-responder.pem | 52 +-- tests/hwsim/auth_serv/ocsp-server-cache.der | Bin 490 -> 490 bytes tests/hwsim/auth_serv/server-certpol.pem | 54 +-- tests/hwsim/auth_serv/server-certpol2.pem | 54 +-- tests/hwsim/auth_serv/server-eku-client-server.pem | 52 +-- tests/hwsim/auth_serv/server-eku-client.pem | 54 +-- tests/hwsim/auth_serv/server-expired.pem | 48 +-- tests/hwsim/auth_serv/server-extra.pkcs12 | Bin 3418 -> 3562 bytes tests/hwsim/auth_serv/server-long-duration.pem | 52 +-- tests/hwsim/auth_serv/server-no-dnsname.pem | 54 +-- tests/hwsim/auth_serv/server.pem | 52 +-- tests/hwsim/auth_serv/server.pkcs12 | Bin 2549 -> 2549 bytes tests/hwsim/auth_serv/user.pem | 54 +-- tests/hwsim/auth_serv/user.pkcs12 | Bin 2517 -> 2517 bytes tests/hwsim/auth_serv/user2.pkcs12 | Bin 3558 -> 3558 bytes tests/hwsim/auth_serv/user3.pkcs12 | Bin 3524 -> 3524 bytes tests/hwsim/test_ap_eap.py | 4 +- tests/hwsim/test_ap_psk.py | 20 ++ tests/hwsim/test_ap_vht.py | 5 + tests/hwsim/test_dpp.py | 59 ++++ tests/hwsim/test_eap_proto.py | 2 +- tests/hwsim/test_fils.py | 49 +++ tests/hwsim/test_hapd_ctrl.py | 6 + tests/hwsim/test_he.py | 35 +- tests/hwsim/test_owe.py | 25 ++ tests/hwsim/test_sae.py | 55 ++++ wlantest/ccmp.c | 2 +- wlantest/gcmp.c | 2 +- wlantest/rx_data.c | 49 ++- wlantest/test_vectors.c | 2 +- wlantest/tkip.c | 76 ++++- wlantest/wlantest.c | 2 + wlantest/wlantest.h | 18 +- wpa_supplicant/ctrl_iface.c | 43 +++ wpa_supplicant/dpp_supplicant.c | 3 +- wpa_supplicant/events.c | 2 +- wpa_supplicant/scan.c | 219 ++++++++++++- wpa_supplicant/scan.h | 6 +- wpa_supplicant/wpa_supplicant.c | 42 ++- wpa_supplicant/wpa_supplicant_i.h | 2 + wpa_supplicant/wpas_glue.c | 4 +- wpa_supplicant/wpas_glue.h | 2 + 73 files changed, 1618 insertions(+), 388 deletions(-) diff --git a/hostapd/Android.mk b/hostapd/Android.mk index b3af96886996..dd8aa2450d7e 100644 --- a/hostapd/Android.mk +++ b/hostapd/Android.mk @@ -34,6 +34,10 @@ ifeq ($(BOARD_HOSTAPD_PRIVATE_LIB),) L_CFLAGS += -DANDROID_LIB_STUB endif +ifneq ($(BOARD_HOSTAPD_PRIVATE_LIB_EVENT),) +L_CFLAGS += -DANDROID_LIB_EVENT +endif + # Use Android specific directory for control interface sockets L_CFLAGS += -DCONFIG_CTRL_IFACE_CLIENT_DIR=\"/data/misc/wifi/sockets\" L_CFLAGS += -DCONFIG_CTRL_IFACE_DIR=\"/data/system/hostapd\" diff --git a/hostapd/config_file.c b/hostapd/config_file.c index e05c81366d9b..9bc1dc7756e9 100644 --- a/hostapd/config_file.c +++ b/hostapd/config_file.c @@ -3511,6 +3511,8 @@ static int hostapd_config_fill(struct hostapd_config *conf, conf->he_op.he_default_pe_duration = atoi(pos); } else if (os_strcmp(buf, "he_twt_required") == 0) { conf->he_op.he_twt_required = atoi(pos); + } else if (os_strcmp(buf, "he_twt_responder") == 0) { + conf->he_op.he_twt_responder = atoi(pos); } else if (os_strcmp(buf, "he_rts_threshold") == 0) { conf->he_op.he_rts_threshold = atoi(pos); } else if (os_strcmp(buf, "he_basic_mcs_nss_set") == 0) { diff --git a/hostapd/ctrl_iface.c b/hostapd/ctrl_iface.c index b39f40252f29..4a2d60627070 100644 --- a/hostapd/ctrl_iface.c +++ b/hostapd/ctrl_iface.c @@ -1946,6 +1946,52 @@ static int hostapd_ctrl_iface_eapol_rx(struct hostapd_data *hapd, char *cmd) } +static int hostapd_ctrl_iface_eapol_tx(struct hostapd_data *hapd, char *cmd) +{ + char *pos, *pos2; + u8 dst[ETH_ALEN], *buf; + int used, ret; + size_t len; + unsigned int prev; + int encrypt = 0; + + wpa_printf(MSG_DEBUG, "External EAPOL TX: %s", cmd); + + pos = cmd; + used = hwaddr_aton2(pos, dst); + if (used < 0) + return -1; + pos += used; + while (*pos == ' ') + pos++; + + pos2 = os_strchr(pos, ' '); + if (pos2) { + len = pos2 - pos; + encrypt = os_strstr(pos2, "encrypt=1") != NULL; + } else { + len = os_strlen(pos); + } + if (len & 1) + return -1; + len /= 2; + + buf = os_malloc(len); + if (!buf || hexstr2bin(pos, buf, len) < 0) { + os_free(buf); + return -1; + } + + prev = hapd->ext_eapol_frame_io; + hapd->ext_eapol_frame_io = 0; + ret = hostapd_wpa_auth_send_eapol(hapd, dst, buf, len, encrypt); + hapd->ext_eapol_frame_io = prev; + os_free(buf); + + return ret; +} + + static u16 ipv4_hdr_checksum(const void *buf, size_t len) { size_t i; @@ -2524,6 +2570,22 @@ static int hostapd_ctrl_resend_group_m1(struct hostapd_data *hapd, } +static int hostapd_ctrl_rekey_ptk(struct hostapd_data *hapd, const char *cmd) +{ + struct sta_info *sta; + u8 addr[ETH_ALEN]; + + if (hwaddr_aton(cmd, addr)) + return -1; + + sta = ap_get_sta(hapd, addr); + if (!sta || !sta->wpa_sm) + return -1; + + return wpa_auth_rekey_ptk(hapd->wpa_auth, sta->wpa_sm); +} + + static int hostapd_ctrl_get_pmksa_pmk(struct hostapd_data *hapd, const u8 *addr, char *buf, size_t buflen) { @@ -3635,6 +3697,9 @@ static int hostapd_ctrl_iface_receive_process(struct hostapd_data *hapd, } else if (os_strncmp(buf, "EAPOL_RX ", 9) == 0) { if (hostapd_ctrl_iface_eapol_rx(hapd, buf + 9) < 0) reply_len = -1; + } else if (os_strncmp(buf, "EAPOL_TX ", 9) == 0) { + if (hostapd_ctrl_iface_eapol_tx(hapd, buf + 9) < 0) + reply_len = -1; } else if (os_strncmp(buf, "DATA_TEST_CONFIG ", 17) == 0) { if (hostapd_ctrl_iface_data_test_config(hapd, buf + 17) < 0) reply_len = -1; @@ -3670,6 +3735,9 @@ static int hostapd_ctrl_iface_receive_process(struct hostapd_data *hapd, } else if (os_strncmp(buf, "RESEND_GROUP_M1 ", 16) == 0) { if (hostapd_ctrl_resend_group_m1(hapd, buf + 16) < 0) reply_len = -1; + } else if (os_strncmp(buf, "REKEY_PTK ", 10) == 0) { + if (hostapd_ctrl_rekey_ptk(hapd, buf + 10) < 0) + reply_len = -1; } else if (os_strcmp(buf, "REKEY_GTK") == 0) { if (wpa_auth_rekey_gtk(hapd->wpa_auth) < 0) reply_len = -1; diff --git a/hostapd/hostapd.conf b/hostapd/hostapd.conf index 7932cb862f48..b5d15061f850 100644 --- a/hostapd/hostapd.conf +++ b/hostapd/hostapd.conf @@ -831,12 +831,22 @@ wmm_ac_vo_acm=0 # 1 = required #he_twt_required=0 +#he_twt_responder: Whether TWT (HE) responder is enabled +# 0 = disabled +# 1 = enabled if supported by the driver (default) +#he_twt_responder=1 + #he_rts_threshold: Duration of STA transmission # 0 = not set (default) # unsigned integer = duration in units of 16 us #he_rts_threshold=0 # HE operating channel information; see matching vht_* parameters for details. +# he_oper_centr_freq_seg0_idx field is used to indicate center frequency of 80 +# and 160 MHz bandwidth operation. In 80+80 MHz operation, it is the center +# frequency of the lower frequency segment. he_oper_centr_freq_seg1_idx field +# is used only with 80+80 MHz bandwidth operation and it is used to transmit +# the center frequency of the second segment. # On the 6 GHz band the center freq calculation starts from 5.950 GHz offset. # For example idx=3 would result in 5965 MHz center frequency. In addition, # he_oper_chwidth is ignored, and the channel width is derived from the diff --git a/src/ap/acs.c b/src/ap/acs.c index aa2ceb0d1848..a112045364e3 100644 --- a/src/ap/acs.c +++ b/src/ap/acs.c @@ -372,40 +372,47 @@ acs_survey_chan_interference_factor(struct hostapd_iface *iface, } -static int acs_usable_ht40_chan(const struct hostapd_channel_data *chan) +static int acs_usable_bw40_chan(const struct hostapd_channel_data *chan) { - const int allowed[] = { 36, 44, 52, 60, 100, 108, 116, 124, 132, 149, - 157, 184, 192 }; + const int allowed[] = { 5180, 5220, 5260, 5300, 5500, 5540, 5580, 5620, + 5660, 5745, 5785, 4920, 4960, 5955, 5995, 6035, + 6075, 6115, 6155, 6195, 6235, 6275, 6315, 6355, + 6395, 6435, 6475, 6515, 6555, 6595, 6635, 6675, + 6715, 6755, 6795, 6835, 6875, 6915, 6955, 6995, + 7035, 7075 }; unsigned int i; for (i = 0; i < ARRAY_SIZE(allowed); i++) - if (chan->chan == allowed[i]) + if (chan->freq == allowed[i]) return 1; return 0; } -static int acs_usable_vht80_chan(const struct hostapd_channel_data *chan) +static int acs_usable_bw80_chan(const struct hostapd_channel_data *chan) { - const int allowed[] = { 36, 52, 100, 116, 132, 149 }; + const int allowed[] = { 5180, 5260, 5550, 5580, 5660, 5745, 5955, 6035, + 6115, 6195, 6275, 6355, 6435, 6515, 6595, 6675, + 6755, 6835, 6915, 6995 }; unsigned int i; for (i = 0; i < ARRAY_SIZE(allowed); i++) - if (chan->chan == allowed[i]) + if (chan->freq == allowed[i]) return 1; return 0; } -static int acs_usable_vht160_chan(const struct hostapd_channel_data *chan) +static int acs_usable_bw160_chan(const struct hostapd_channel_data *chan) { - const int allowed[] = { 36, 100 }; + const int allowed[] = { 5180, 5500, 5955, 6115, 6275, 6435, 6595, 6755, + 6915 }; unsigned int i; for (i = 0; i < ARRAY_SIZE(allowed); i++) - if (chan->chan == allowed[i]) + if (chan->freq == allowed[i]) return 1; return 0; @@ -678,10 +685,12 @@ acs_find_ideal_chan_mode(struct hostapd_iface *iface, /* HT40 on 5 GHz has a limited set of primary channels as per * 11n Annex J */ if (mode->mode == HOSTAPD_MODE_IEEE80211A && - iface->conf->ieee80211n && - iface->conf->secondary_channel && - !acs_usable_ht40_chan(chan)) { - wpa_printf(MSG_DEBUG, "ACS: Channel %d: not allowed as primary channel for HT40", + ((iface->conf->ieee80211n && + iface->conf->secondary_channel) || + is_6ghz_freq(chan->freq)) && + !acs_usable_bw40_chan(chan)) { + wpa_printf(MSG_DEBUG, + "ACS: Channel %d: not allowed as primary channel for 40 MHz bandwidth", chan->chan); continue; } @@ -690,18 +699,18 @@ acs_find_ideal_chan_mode(struct hostapd_iface *iface, (iface->conf->ieee80211ac || iface->conf->ieee80211ax)) { if (hostapd_get_oper_chwidth(iface->conf) == CHANWIDTH_80MHZ && - !acs_usable_vht80_chan(chan)) { + !acs_usable_bw80_chan(chan)) { wpa_printf(MSG_DEBUG, - "ACS: Channel %d: not allowed as primary channel for VHT80", + "ACS: Channel %d: not allowed as primary channel for 80 MHz bandwidth", chan->chan); continue; } if (hostapd_get_oper_chwidth(iface->conf) == CHANWIDTH_160MHZ && - !acs_usable_vht160_chan(chan)) { + !acs_usable_bw160_chan(chan)) { wpa_printf(MSG_DEBUG, - "ACS: Channel %d: not allowed as primary channel for VHT160", + "ACS: Channel %d: not allowed as primary channel for 160 MHz bandwidth", chan->chan); continue; } @@ -832,6 +841,12 @@ acs_find_ideal_chan(struct hostapd_iface *iface) u32 bw; struct hostapd_hw_modes *mode; + if (is_6ghz_op_class(iface->conf->op_class)) { + bw = op_class_to_bandwidth(iface->conf->op_class); + n_chans = bw / 20; + goto bw_selected; + } + /* TODO: HT40- support */ if (iface->conf->ieee80211n && @@ -857,6 +872,7 @@ acs_find_ideal_chan(struct hostapd_iface *iface) bw = num_chan_to_bw(n_chans); +bw_selected: /* TODO: VHT/HE80+80. Update acs_adjust_center_freq() too. */ wpa_printf(MSG_DEBUG, diff --git a/src/ap/ap_config.c b/src/ap/ap_config.c index 7b6249bbe5cf..7b6d54c35fc2 100644 --- a/src/ap/ap_config.c +++ b/src/ap/ap_config.c @@ -274,6 +274,7 @@ struct hostapd_config * hostapd_config_defaults(void) conf->he_op.he_bss_color_disabled = 1; conf->he_op.he_bss_color_partial = 0; conf->he_op.he_bss_color = 1; + conf->he_op.he_twt_responder = 1; conf->he_6ghz_max_mpdu = 2; conf->he_6ghz_max_ampdu_len_exp = 7; conf->he_6ghz_rx_ant_pat = 1; diff --git a/src/ap/ap_config.h b/src/ap/ap_config.h index 95bd79873a59..ced36f9cc828 100644 --- a/src/ap/ap_config.h +++ b/src/ap/ap_config.h @@ -914,6 +914,7 @@ struct he_operation { u8 he_bss_color_partial; u8 he_default_pe_duration; u8 he_twt_required; + u8 he_twt_responder; u16 he_rts_threshold; u16 he_basic_mcs_nss_set; }; diff --git a/src/ap/beacon.c b/src/ap/beacon.c index 7d9e8b9230c2..15fc2b3db064 100644 --- a/src/ap/beacon.c +++ b/src/ap/beacon.c @@ -1753,6 +1753,11 @@ int ieee802_11_set_beacon(struct hostapd_data *hapd) struct wpabuf *beacon, *proberesp, *assocresp; int res, ret = -1; + if (!hapd->drv_priv) { + wpa_printf(MSG_ERROR, "Interface is disabled"); + return -1; + } + if (hapd->csa_in_progress) { wpa_printf(MSG_ERROR, "Cannot set beacons during CSA period"); return -1; diff --git a/src/ap/dpp_hostapd.c b/src/ap/dpp_hostapd.c index aaeb94c2f53b..93ffd8cf7c36 100644 --- a/src/ap/dpp_hostapd.c +++ b/src/ap/dpp_hostapd.c @@ -757,7 +757,7 @@ static void hostapd_dpp_rx_auth_req(struct hostapd_data *hapd, const u8 *src, if (!own_bi) { if (dpp_relay_rx_action(hapd->iface->interfaces->dpp, src, hdr, buf, len, freq, i_bootstrap, - r_bootstrap) == 0) + r_bootstrap, hapd) == 0) return; } #endif /* CONFIG_DPP2 */ @@ -1276,7 +1276,7 @@ hostapd_dpp_rx_presence_announcement(struct hostapd_data *hapd, const u8 *src, if (!peer_bi) { if (dpp_relay_rx_action(hapd->iface->interfaces->dpp, src, hdr, buf, len, freq, NULL, - r_bootstrap) == 0) + r_bootstrap, hapd) == 0) return; wpa_printf(MSG_DEBUG, "DPP: No matching bootstrapping information found"); @@ -1366,7 +1366,7 @@ hostapd_dpp_rx_reconfig_announcement(struct hostapd_data *hapd, const u8 *src, if (!conf) { if (dpp_relay_rx_action(hapd->iface->interfaces->dpp, src, hdr, buf, len, freq, NULL, - NULL) == 0) + NULL, hapd) == 0) return; wpa_printf(MSG_DEBUG, "DPP: No matching Configurator information found"); @@ -1892,7 +1892,8 @@ void hostapd_dpp_rx_action(struct hostapd_data *hapd, const u8 *src, #ifdef CONFIG_DPP2 if (dpp_relay_rx_action(hapd->iface->interfaces->dpp, - src, hdr, buf, len, freq, NULL, NULL) == 0) + src, hdr, buf, len, freq, NULL, NULL, + hapd) == 0) return; #endif /* CONFIG_DPP2 */ diff --git a/src/ap/hostapd.c b/src/ap/hostapd.c index e9aae6dcf2f5..913a8e29e16d 100644 --- a/src/ap/hostapd.c +++ b/src/ap/hostapd.c @@ -1674,6 +1674,26 @@ static int configured_fixed_chan_to_freq(struct hostapd_iface *iface) } +static void hostapd_set_6ghz_sec_chan(struct hostapd_iface *iface) +{ + int bw, seg0; + + if (!is_6ghz_op_class(iface->conf->op_class)) + return; + + seg0 = hostapd_get_oper_centr_freq_seg0_idx(iface->conf); + bw = center_idx_to_bw_6ghz(seg0); + /* Assign the secondary channel if absent in config for + * bandwidths > 20 MHz */ + if (bw > 20 && !iface->conf->secondary_channel) { + if (((iface->conf->channel - 1) / 4) % 2) + iface->conf->secondary_channel = -1; + else + iface->conf->secondary_channel = 1; + } +} + + static int setup_interface2(struct hostapd_iface *iface) { iface->wait_channel_update = 0; @@ -1693,6 +1713,7 @@ static int setup_interface2(struct hostapd_iface *iface) ch_width = op_class_to_ch_width(iface->conf->op_class); hostapd_set_oper_chwidth(iface->conf, ch_width); + hostapd_set_6ghz_sec_chan(iface); } ret = hostapd_select_hw_mode(iface); diff --git a/src/ap/hw_features.c b/src/ap/hw_features.c index 7849be181c21..bb5404fa7dd4 100644 --- a/src/ap/hw_features.c +++ b/src/ap/hw_features.c @@ -917,8 +917,14 @@ static int hostapd_is_usable_chans(struct hostapd_iface *iface) return 1; if (hostapd_is_usable_chan(iface, iface->freq + - iface->conf->secondary_channel * 20, 0)) - return 1; + iface->conf->secondary_channel * 20, 0)) { + if (iface->conf->secondary_channel == 1 && + (pri_chan->allowed_bw & HOSTAPD_CHAN_WIDTH_40P)) + return 1; + if (iface->conf->secondary_channel == -1 && + (pri_chan->allowed_bw & HOSTAPD_CHAN_WIDTH_40M)) + return 1; + } if (!iface->conf->ht40_plus_minus_allowed) return 0; diff --git a/src/ap/ieee802_11_he.c b/src/ap/ieee802_11_he.c index c27bb1fcdbd0..cbe5e639588f 100644 --- a/src/ap/ieee802_11_he.c +++ b/src/ap/ieee802_11_he.c @@ -216,7 +216,10 @@ u8 * hostapd_eid_he_operation(struct hostapd_data *hapd, u8 *eid) params |= HE_OPERATION_6GHZ_OPER_INFO; - /* 6 GHz Operation Information field */ + /* 6 GHz Operation Information field + * IEEE P802.11ax/D8.0, 9.4.2.249 HE Operation element, + * Figure 9-788k + */ *pos++ = hapd->iconf->channel; /* Primary Channel */ /* Control: Channel Width */ @@ -226,6 +229,18 @@ u8 * hostapd_eid_he_operation(struct hostapd_data *hapd, u8 *eid) *pos++ = center_idx_to_bw_6ghz(seg0); /* Channel Center Freq Seg0/Seg1 */ + if (hapd->iconf->he_oper_chwidth == 2) { + /* + * Seg 0 indicates the channel center frequency index of + * the 160 MHz channel. + */ + seg1 = seg0; + if (hapd->iconf->channel < seg0) + seg0 -= 8; + else + seg0 += 8; + } + *pos++ = seg0; *pos++ = seg1; /* Minimum Rate */ @@ -434,8 +449,8 @@ u16 copy_sta_he_capab(struct hostapd_data *hapd, struct sta_info *sta, enum ieee80211_op_mode opmode, const u8 *he_capab, size_t he_capab_len) { - if (!he_capab || !hapd->iconf->ieee80211ax || - hapd->conf->disable_11ax || + if (!he_capab || !(sta->flags & WLAN_STA_WMM) || + !hapd->iconf->ieee80211ax || hapd->conf->disable_11ax || !check_valid_he_mcs(hapd, he_capab, opmode) || ieee80211_invalid_he_cap_size(he_capab, he_capab_len) || he_capab_len > sizeof(struct ieee80211_he_capabilities)) { @@ -499,5 +514,6 @@ int hostapd_get_he_twt_responder(struct hostapd_data *hapd, mac_cap = hapd->iface->current_mode->he_capab[mode].mac_cap; - return !!(mac_cap[HE_MAC_CAPAB_0] & HE_MACCAP_TWT_RESPONDER); + return !!(mac_cap[HE_MAC_CAPAB_0] & HE_MACCAP_TWT_RESPONDER) && + hapd->iface->conf->he_op.he_twt_responder; } diff --git a/src/ap/ieee802_11_vht.c b/src/ap/ieee802_11_vht.c index d0370229c417..828f0abb5aad 100644 --- a/src/ap/ieee802_11_vht.c +++ b/src/ap/ieee802_11_vht.c @@ -171,7 +171,7 @@ u16 copy_sta_vht_capab(struct hostapd_data *hapd, struct sta_info *sta, const u8 *vht_capab) { /* Disable VHT caps for STAs associated to no-VHT BSSes. */ - if (!vht_capab || + if (!vht_capab || !(sta->flags & WLAN_STA_WMM) || !hapd->iconf->ieee80211ac || hapd->conf->disable_11ac || !check_valid_vht_mcs(hapd->iface->current_mode, vht_capab)) { sta->flags &= ~WLAN_STA_VHT; diff --git a/src/ap/pmksa_cache_auth.c b/src/ap/pmksa_cache_auth.c index fe5f8171754b..b67b8522e744 100644 --- a/src/ap/pmksa_cache_auth.c +++ b/src/ap/pmksa_cache_auth.c @@ -516,7 +516,8 @@ struct rsn_pmksa_cache_entry * pmksa_cache_get_okc( for (entry = pmksa->pmksa; entry; entry = entry->next) { if (os_memcmp(entry->spa, spa, ETH_ALEN) != 0) continue; - if (wpa_key_mgmt_sae(entry->akmp)) { + if (wpa_key_mgmt_sae(entry->akmp) || + wpa_key_mgmt_fils(entry->akmp)) { if (os_memcmp(entry->pmkid, pmkid, PMKID_LEN) == 0) return entry; continue; diff --git a/src/ap/wpa_auth.c b/src/ap/wpa_auth.c index 59cd46aa4601..83805681ed97 100644 --- a/src/ap/wpa_auth.c +++ b/src/ap/wpa_auth.c @@ -1001,6 +1001,18 @@ static int wpa_try_alt_snonce(struct wpa_state_machine *sm, u8 *data, } +static bool wpa_auth_gtk_rekey_in_process(struct wpa_authenticator *wpa_auth) +{ + struct wpa_group *group; + + for (group = wpa_auth->group; group; group = group->next) { + if (group->GKeyDoneStations) + return true; + } + return false; +} + + void wpa_receive(struct wpa_authenticator *wpa_auth, struct wpa_state_machine *sm, u8 *data, size_t data_len) @@ -1368,7 +1380,11 @@ continue_processing: wpa_auth_logger(wpa_auth, sm->addr, LOGGER_INFO, "received EAPOL-Key Request for GTK rekeying"); eloop_cancel_timeout(wpa_rekey_gtk, wpa_auth, NULL); - wpa_rekey_gtk(wpa_auth, NULL); + if (wpa_auth_gtk_rekey_in_process(wpa_auth)) + wpa_auth_logger(wpa_auth, NULL, LOGGER_DEBUG, + "skip new GTK rekey - already in process"); + else + wpa_rekey_gtk(wpa_auth, NULL); } } else { /* Do not allow the same key replay counter to be reused. */ @@ -3678,6 +3694,8 @@ SM_STATE(WPA_PTK, PTKINITDONE) wpa_auth_vlogger(sm->wpa_auth, sm->addr, LOGGER_INFO, "pairwise key handshake completed (%s)", sm->wpa == WPA_VERSION_WPA ? "WPA" : "RSN"); + wpa_msg(sm->wpa_auth->conf.msg_ctx, MSG_INFO, "EAPOL-4WAY-HS-COMPLETED " + MACSTR, MAC2STR(sm->addr)); #ifdef CONFIG_IEEE80211R_AP wpa_ft_push_pmk_r1(sm->wpa_auth, sm->addr); @@ -5627,6 +5645,18 @@ int wpa_auth_rekey_gtk(struct wpa_authenticator *wpa_auth) } +int wpa_auth_rekey_ptk(struct wpa_authenticator *wpa_auth, + struct wpa_state_machine *sm) +{ + if (!wpa_auth || !sm) + return -1; + wpa_auth_logger(wpa_auth, sm->addr, LOGGER_DEBUG, "rekeying PTK"); + wpa_request_new_ptk(sm); + wpa_sm_step(sm); + return 0; +} + + void wpa_auth_set_ft_rsnxe_used(struct wpa_authenticator *wpa_auth, int val) { if (wpa_auth) diff --git a/src/ap/wpa_auth.h b/src/ap/wpa_auth.h index eaa2cafc8088..fe47723b9e6b 100644 --- a/src/ap/wpa_auth.h +++ b/src/ap/wpa_auth.h @@ -553,7 +553,12 @@ int wpa_auth_resend_m3(struct wpa_state_machine *sm, int wpa_auth_resend_group_m1(struct wpa_state_machine *sm, void (*cb)(void *ctx1, void *ctx2), void *ctx1, void *ctx2); +int wpa_auth_rekey_ptk(struct wpa_authenticator *wpa_auth, + struct wpa_state_machine *sm); int wpa_auth_rekey_gtk(struct wpa_authenticator *wpa_auth); +int hostapd_wpa_auth_send_eapol(void *ctx, const u8 *addr, + const u8 *data, size_t data_len, + int encrypt); void wpa_auth_set_ptk_rekey_timer(struct wpa_state_machine *sm); void wpa_auth_set_ft_rsnxe_used(struct wpa_authenticator *wpa_auth, int val); diff --git a/src/ap/wpa_auth_glue.c b/src/ap/wpa_auth_glue.c index c3b2e81e2e72..7ca292530dc1 100644 --- a/src/ap/wpa_auth_glue.c +++ b/src/ap/wpa_auth_glue.c @@ -505,9 +505,9 @@ static int hostapd_wpa_auth_get_seqnum(void *ctx, const u8 *addr, int idx, } -static int hostapd_wpa_auth_send_eapol(void *ctx, const u8 *addr, - const u8 *data, size_t data_len, - int encrypt) +int hostapd_wpa_auth_send_eapol(void *ctx, const u8 *addr, + const u8 *data, size_t data_len, + int encrypt) { struct hostapd_data *hapd = ctx; struct sta_info *sta; diff --git a/src/common/dpp.h b/src/common/dpp.h index 65ee905a78f9..75de3cae93e9 100644 --- a/src/common/dpp.h +++ b/src/common/dpp.h @@ -669,7 +669,8 @@ int dpp_relay_add_controller(struct dpp_global *dpp, struct dpp_relay_config *config); int dpp_relay_rx_action(struct dpp_global *dpp, const u8 *src, const u8 *hdr, const u8 *buf, size_t len, unsigned int freq, - const u8 *i_bootstrap, const u8 *r_bootstrap); + const u8 *i_bootstrap, const u8 *r_bootstrap, + void *cb_ctx); int dpp_relay_rx_gas_req(struct dpp_global *dpp, const u8 *src, const u8 *data, size_t data_len); int dpp_controller_start(struct dpp_global *dpp, diff --git a/src/common/dpp_tcp.c b/src/common/dpp_tcp.c index 609c243a6856..c373f107791c 100644 --- a/src/common/dpp_tcp.c +++ b/src/common/dpp_tcp.c @@ -82,6 +82,7 @@ static void dpp_controller_auth_success(struct dpp_connection *conn, int initiator); static void dpp_tcp_build_csr(void *eloop_ctx, void *timeout_ctx); static void dpp_tcp_gas_query_comeback(void *eloop_ctx, void *timeout_ctx); +static void dpp_relay_conn_timeout(void *eloop_ctx, void *timeout_ctx); static void dpp_connection_free(struct dpp_connection *conn) @@ -97,6 +98,7 @@ static void dpp_connection_free(struct dpp_connection *conn) conn, NULL); eloop_cancel_timeout(dpp_tcp_build_csr, conn, NULL); eloop_cancel_timeout(dpp_tcp_gas_query_comeback, conn, NULL); + eloop_cancel_timeout(dpp_relay_conn_timeout, conn, NULL); wpabuf_free(conn->msg); wpabuf_free(conn->msg_out); dpp_auth_deinit(conn->auth); @@ -154,6 +156,24 @@ dpp_relay_controller_get(struct dpp_global *dpp, const u8 *pkhash) } +static struct dpp_relay_controller * +dpp_relay_controller_get_ctx(struct dpp_global *dpp, void *cb_ctx) +{ + struct dpp_relay_controller *ctrl; + + if (!dpp) + return NULL; + + dl_list_for_each(ctrl, &dpp->controllers, struct dpp_relay_controller, + list) { + if (cb_ctx == ctrl->cb_ctx) + return ctrl; + } + + return NULL; +} + + static void dpp_controller_gas_done(struct dpp_connection *conn) { struct dpp_authentication *auth = conn->auth; @@ -352,6 +372,16 @@ static int dpp_ipaddr_to_sockaddr(struct sockaddr *addr, socklen_t *addrlen, } +static void dpp_relay_conn_timeout(void *eloop_ctx, void *timeout_ctx) +{ + struct dpp_connection *conn = eloop_ctx; + + wpa_printf(MSG_DEBUG, + "DPP: Timeout while waiting for relayed connection to complete"); + dpp_connection_remove(conn); +} + + static struct dpp_connection * dpp_relay_new_conn(struct dpp_relay_controller *ctrl, const u8 *src, unsigned int freq) @@ -412,8 +442,8 @@ dpp_relay_new_conn(struct dpp_relay_controller *ctrl, const u8 *src, goto fail; conn->write_eloop = 1; - /* TODO: eloop timeout to clear a connection if it does not complete - * properly */ + eloop_cancel_timeout(dpp_relay_conn_timeout, conn, NULL); + eloop_register_timeout(20, 0, dpp_relay_conn_timeout, conn, NULL); dl_list_add(&ctrl->conn, &conn->list); return conn; @@ -465,7 +495,8 @@ static int dpp_relay_tx(struct dpp_connection *conn, const u8 *hdr, int dpp_relay_rx_action(struct dpp_global *dpp, const u8 *src, const u8 *hdr, const u8 *buf, size_t len, unsigned int freq, - const u8 *i_bootstrap, const u8 *r_bootstrap) + const u8 *i_bootstrap, const u8 *r_bootstrap, + void *cb_ctx) { struct dpp_relay_controller *ctrl; struct dpp_connection *conn; @@ -493,8 +524,7 @@ int dpp_relay_rx_action(struct dpp_global *dpp, const u8 *src, const u8 *hdr, type == DPP_PA_RECONFIG_ANNOUNCEMENT) { /* TODO: Could send this to all configured Controllers. For now, * only the first Controller is supported. */ - ctrl = dl_list_first(&dpp->controllers, - struct dpp_relay_controller, list); + ctrl = dpp_relay_controller_get_ctx(dpp, cb_ctx); } else { if (!r_bootstrap) return -1; diff --git a/src/common/ieee802_11_defs.h b/src/common/ieee802_11_defs.h index 710186e5d36a..7d2f36b8f1e6 100644 --- a/src/common/ieee802_11_defs.h +++ b/src/common/ieee802_11_defs.h @@ -22,7 +22,7 @@ #define WLAN_FC_PWRMGT 0x1000 #define WLAN_FC_MOREDATA 0x2000 #define WLAN_FC_ISWEP 0x4000 -#define WLAN_FC_ORDER 0x8000 +#define WLAN_FC_HTC 0x8000 #define WLAN_FC_GET_TYPE(fc) (((fc) & 0x000c) >> 2) #define WLAN_FC_GET_STYPE(fc) (((fc) & 0x00f0) >> 4) diff --git a/src/common/qca-vendor.h b/src/common/qca-vendor.h index 32c93bb84d54..ce588cc00a59 100644 --- a/src/common/qca-vendor.h +++ b/src/common/qca-vendor.h @@ -512,7 +512,9 @@ enum qca_radiotap_vendor_ids { * @QCA_NL80211_VENDOR_SUBCMD_PEER_CFR_CAPTURE_CFG: This command is used to * configure parameters per peer to capture Channel Frequency Response * (CFR) and enable Periodic CFR capture. The attributes for this command - * are defined in enum qca_wlan_vendor_peer_cfr_capture_attr. + * are defined in enum qca_wlan_vendor_peer_cfr_capture_attr. This command + * can also be used to send CFR data from the driver to userspace when + * netlink events are used to send CFR data. * * @QCA_NL80211_VENDOR_SUBCMD_THROUGHPUT_CHANGE_EVENT: Event to indicate changes * in throughput dynamically. The driver estimates the throughput based on @@ -700,6 +702,23 @@ enum qca_radiotap_vendor_ids { * used with this event are defined in enum * qca_wlan_vendor_attr_mbssid_tx_vdev_status. * + * @QCA_NL80211_VENDOR_SUBCMD_CONCURRENT_MULTI_STA_POLICY: Vendor command to + * configure the concurrent session policies when multiple STA interfaces + * are (getting) active. The attributes used by this command are defined + * in enum qca_wlan_vendor_attr_concurrent_sta_policy. + * + * @QCA_NL80211_VENDOR_SUBCMD_USABLE_CHANNELS: Userspace can use this command + * to query usable channels for different interface types such as STA, + * AP, P2P GO, P2P Client, NAN, etc. The driver shall report all usable + * channels in the response based on country code, different static + * configurations, concurrency combinations, etc. The attributes used + * with this command are defined in + * enum qca_wlan_vendor_attr_usable_channels. + * + * @QCA_NL80211_VENDOR_SUBCMD_GET_RADAR_HISTORY: This vendor subcommand is used + * to get DFS radar history from the driver to userspace. The driver + * returns QCA_WLAN_VENDOR_ATTR_RADAR_HISTORY_ENTRIES attribute with an + * array of nested entries. */ enum qca_nl80211_vendor_subcmds { QCA_NL80211_VENDOR_SUBCMD_UNSPEC = 0, @@ -886,6 +905,9 @@ enum qca_nl80211_vendor_subcmds { QCA_NL80211_VENDOR_SUBCMD_UPDATE_SSID = 194, QCA_NL80211_VENDOR_SUBCMD_WIFI_FW_STATS = 195, QCA_NL80211_VENDOR_SUBCMD_MBSSID_TX_VDEV_STATUS = 196, + QCA_NL80211_VENDOR_SUBCMD_CONCURRENT_MULTI_STA_POLICY = 197, + QCA_NL80211_VENDOR_SUBCMD_USABLE_CHANNELS = 198, + QCA_NL80211_VENDOR_SUBCMD_GET_RADAR_HISTORY = 199, }; enum qca_wlan_vendor_attr { @@ -2399,6 +2421,33 @@ enum qca_wlan_vendor_attr_config { */ QCA_WLAN_VENDOR_ATTR_CONFIG_RX_NSS = 78, + /* + * 8-bit unsigned value. This attribute, when set, indicates whether the + * specified interface is the primary STA interface when there are more + * than one STA interfaces concurrently active. + * + * This configuration helps the firmware/hardware to support certain + * features (e.g., roaming) on this primary interface, if the same + * cannot be supported on the concurrent STA interfaces simultaneously. + * + * This configuration is only applicable for a single STA interface on + * a device and gives the priority for it only over other concurrent STA + * interfaces. + * + * If the device is a multi wiphy/soc, this configuration applies to a + * single STA interface across the wiphys. + * + * 1-Enable (is the primary STA), 0-Disable (is not the primary STA) + */ + QCA_WLAN_VENDOR_ATTR_CONFIG_CONCURRENT_STA_PRIMARY = 79, + + /* + * 8-bit unsigned value. This attribute can be used to configure the + * driver to enable/disable FT-over-DS feature. Possible values for + * this attribute are 1-Enable and 0-Disable. + */ + QCA_WLAN_VENDOR_ATTR_CONFIG_FT_OVER_DS = 80, + /* keep last */ QCA_WLAN_VENDOR_ATTR_CONFIG_AFTER_LAST, QCA_WLAN_VENDOR_ATTR_CONFIG_MAX = @@ -4545,7 +4594,13 @@ enum qca_vendor_attr_roam_candidate_selection_criteria { * @QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD: Signed 32-bit value in dBm, * signifying the RSSI threshold of the candidate AP, indicating * the driver to trigger roam only to the candidate AP with RSSI - * better than this threshold. + * better than this threshold. If RSSI thresholds for candidate APs found + * in the 2.4 GHz, 5 GHz, and 6 GHz bands are configured separately using + * QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_2P4GHZ, + * QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_5GHZ, and/or + * QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_6GHZ, those values will + * take precedence over the value configured using the + * QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD attribute. * * @QCA_ATTR_ROAM_CONTROL_USER_REASON: Unsigned 32-bit value. Represents the * user defined reason code to be sent to the AP in response to AP's @@ -4564,6 +4619,31 @@ enum qca_vendor_attr_roam_candidate_selection_criteria { * If both QCA_ATTR_ROAM_CONTROL_SCAN_SCHEME and * QCA_ATTR_ROAM_CONTROL_SCAN_SCHEME_TRIGGERS are not specified, the * driver shall proceed with the default behavior. + * + * @QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_2P4GHZ: Signed 32-bit value + * in dBm, signifying the RSSI threshold of the candidate AP found in the + * 2.4 GHz band. The driver/firmware shall trigger roaming to the candidate + * AP found in the 2.4 GHz band only if its RSSI value is better than this + * threshold. Optional attribute. If this attribute is not included, the + * threshold value specified by the + * QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD attribute shall be used. + * + * @QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_5GHZ: Signed 32-bit value in + * dBm, signifying the RSSI threshold of the candidate AP found in the 5 + * GHz band. The driver/firmware shall trigger roaming to the candidate AP + * found in the 5 GHz band only if its RSSI value is better than this + * threshold. Optional attribute. If this attribute is not included, the + * threshold value specified by tge + * QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD attribute shall be used. + * + * @QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_6GHZ: Signed 32-bit value in + * dBm, signifying the RSSI threshold of the candidate AP found in the 6 + * GHz band. The driver/firmware shall trigger roaming to the candidate AP + * found in the 6 GHz band only if its RSSI value is better than this + * threshold. Optional attribute. If this attribute is not included, the + * threshold value specified by the + * QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD attribute shall be used. + * */ enum qca_vendor_attr_roam_control { QCA_ATTR_ROAM_CONTROL_ENABLE = 1, @@ -4579,6 +4659,9 @@ enum qca_vendor_attr_roam_control { QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD = 11, QCA_ATTR_ROAM_CONTROL_USER_REASON = 12, QCA_ATTR_ROAM_CONTROL_SCAN_SCHEME_TRIGGERS = 13, + QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_2P4GHZ = 14, + QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_5GHZ = 15, + QCA_ATTR_ROAM_CONTROL_CANDIDATE_RSSI_THRESHOLD_6GHZ = 16, /* keep last */ QCA_ATTR_ROAM_CONTROL_AFTER_LAST, @@ -6486,6 +6569,8 @@ enum qca_wlan_vendor_hang_reason { QCA_WLAN_HANG_SUSPEND_NO_CREDIT = 25, /* Bus failure */ QCA_WLAN_HANG_BUS_FAILURE = 26, + /* tasklet/credit latency found */ + QCA_WLAN_HANG_TASKLET_CREDIT_LATENCY_DETECT = 27, }; /** @@ -7491,6 +7576,21 @@ enum qca_wlan_he_om_ctrl_ch_bw { QCA_WLAN_HE_OM_CTRL_BW_160M = 3, }; +/** + * enum qca_wlan_keep_alive_data_type - Keep alive data type configuration + * + * Indicates the frame types to use for keep alive data. + * + * @QCA_WLAN_KEEP_ALIVE_DEFAULT: Driver default type used for keep alive. + * @QCA_WLAN_KEEP_ALIVE_DATA: Data frame type for keep alive. + * @QCA_WLAN_KEEP_ALIVE_MGMT: Management frame type for keep alive. + */ +enum qca_wlan_keep_alive_data_type { + QCA_WLAN_KEEP_ALIVE_DEFAULT = 0, + QCA_WLAN_KEEP_ALIVE_DATA = 1, + QCA_WLAN_KEEP_ALIVE_MGMT = 2, +}; + /** * enum qca_wlan_vendor_attr_he_omi_tx: Represents attributes for * HE operating mode control transmit request. These attributes are @@ -8004,6 +8104,22 @@ enum qca_wlan_vendor_attr_wifi_test_config { */ QCA_WLAN_VENDOR_ATTR_WIFI_TEST_CONFIG_6GHZ_SECURITY_TEST_MODE = 51, + /* 8-bit unsigned value to configure the driver to transmit data with + * ER SU PPDU type. + * + * 0 - Default behavior, 1 - Enable ER SU PPDU type TX. + * This attribute is used for testing purposes. *** 2683 LINES SKIPPED ***
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?202106031638.153GcGhh069766>