Add support to retrieve EHT capabilities and EHT operation elements passed by the userspace in the beacon template and store the pointers in struct cfg80211_ap_settings to be used by the drivers. Co-developed-by: Vikram Kandukuri <quic_vikram@xxxxxxxxxxx> Signed-off-by: Vikram Kandukuri <quic_vikram@xxxxxxxxxxx> Co-developed-by: Veerendranath Jakkam <quic_vjakkam@xxxxxxxxxxx> Signed-off-by: Veerendranath Jakkam <quic_vjakkam@xxxxxxxxxxx> Signed-off-by: Aloka Dixit <quic_alokad@xxxxxxxxxxx> --- v3: Rolled v2 patch #1 and #2 into a single patch and added checks for element lengths. Dropped patch #3 for now. include/net/cfg80211.h | 4 ++++ net/wireless/nl80211.c | 26 ++++++++++++++++++++++++-- 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/include/net/cfg80211.h b/include/net/cfg80211.h index 97a5804ccdcf..a7a68bf26333 100644 --- a/include/net/cfg80211.h +++ b/include/net/cfg80211.h @@ -1290,6 +1290,8 @@ struct cfg80211_unsol_bcast_probe_resp { * @ht_cap: HT capabilities (or %NULL if HT isn't enabled) * @vht_cap: VHT capabilities (or %NULL if VHT isn't enabled) * @he_cap: HE capabilities (or %NULL if HE isn't enabled) + * @eht_cap: EHT capabilities (or %NULL if EHT isn't enabled) + * @eht_oper: EHT operation IE (or %NULL if EHT isn't enabled) * @ht_required: stations must support HT * @vht_required: stations must support VHT * @twt_responder: Enable Target Wait Time @@ -1326,6 +1328,8 @@ struct cfg80211_ap_settings { const struct ieee80211_vht_cap *vht_cap; const struct ieee80211_he_cap_elem *he_cap; const struct ieee80211_he_operation *he_oper; + const struct ieee80211_eht_cap_elem *eht_cap; + const struct ieee80211_eht_operation *eht_oper; bool ht_required, vht_required, he_required, sae_h2e_required; bool twt_responder; u32 flags; diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c index 740b29481bc6..3c62969107f0 100644 --- a/net/wireless/nl80211.c +++ b/net/wireless/nl80211.c @@ -5436,7 +5436,7 @@ static void nl80211_check_ap_rate_selectors(struct cfg80211_ap_settings *params, * HT/VHT requirements/capabilities, we parse them out of the IEs for the * benefit of drivers that rebuild IEs in the firmware. */ -static void nl80211_calculate_ap_params(struct cfg80211_ap_settings *params) +static int nl80211_calculate_ap_params(struct cfg80211_ap_settings *params) { const struct cfg80211_beacon_data *bcn = ¶ms->beacon; size_t ies_len = bcn->tail_len; @@ -5462,6 +5462,26 @@ static void nl80211_calculate_ap_params(struct cfg80211_ap_settings *params) cap = cfg80211_find_ext_elem(WLAN_EID_EXT_HE_OPERATION, ies, ies_len); if (cap && cap->datalen >= sizeof(*params->he_oper) + 1) params->he_oper = (void *)(cap->data + 1); + cap = cfg80211_find_ext_elem(WLAN_EID_EXT_EHT_CAPABILITY, ies, ies_len); + if (cap) { + if (!cap->datalen) + return -EINVAL; + params->eht_cap = (void *)(cap->data + 1); + if (!ieee80211_eht_capa_size_ok((const u8 *)params->he_cap, + (const u8 *)params->eht_cap, + cap->datalen - 1)) + return -EINVAL; + } + cap = cfg80211_find_ext_elem(WLAN_EID_EXT_EHT_OPERATION, ies, ies_len); + if (cap) { + if (!cap->datalen) + return -EINVAL; + params->eht_oper = (void *)(cap->data + 1); + if (!ieee80211_eht_oper_size_ok((const u8 *)params->eht_oper, + cap->datalen - 1)) + return -EINVAL; + } + return 0; } static bool nl80211_get_ap_channel(struct cfg80211_registered_device *rdev, @@ -5770,7 +5790,9 @@ static int nl80211_start_ap(struct sk_buff *skb, struct genl_info *info) goto out; } - nl80211_calculate_ap_params(params); + err = nl80211_calculate_ap_params(params); + if (err) + goto out; if (info->attrs[NL80211_ATTR_AP_SETTINGS_FLAGS]) params->flags = nla_get_u32( base-commit: 9335156ac0e174721921c404bd173526c8509124 -- 2.31.1