u16 he_6ghz_capa;
};
+/* struct eht_capabilities - IEEE 802.11be EHT capabilities */
+struct eht_capabilities {
+ bool eht_supported;
+ u16 mac_cap;
+ u8 phy_cap[EHT_PHY_CAPAB_LEN];
+ u8 mcs[EHT_MCS_NSS_CAPAB_LEN];
+ u8 ppet[EHT_PPE_THRESH_CAPAB_LEN];
+};
+
#define HOSTAPD_MODE_FLAG_HT_INFO_KNOWN BIT(0)
#define HOSTAPD_MODE_FLAG_VHT_INFO_KNOWN BIT(1)
* for IEEE 802.11ay EDMG configuration.
*/
struct ieee80211_edmg_config edmg;
+
+ /**
+ * eht_capab - EHT (IEEE 802.11be) capabilities
+ */
+ struct eht_capabilities eht_capab[IEEE80211_MODE_NUM];
};
}
-static void phy_info_iftype_copy(struct he_capabilities *he_capab,
+static void phy_info_iftype_copy(struct hostapd_hw_modes *mode,
enum ieee80211_op_mode opmode,
struct nlattr **tb, struct nlattr **tb_flags)
{
enum nl80211_iftype iftype;
size_t len;
+ struct he_capabilities *he_capab = &mode->he_capab[opmode];
+ struct eht_capabilities *eht_capab = &mode->eht_capab[opmode];
switch (opmode) {
case IEEE80211_MODE_INFRA:
capa = nla_get_u16(tb[NL80211_BAND_IFTYPE_ATTR_HE_6GHZ_CAPA]);
he_capab->he_6ghz_capa = le_to_host16(capa);
}
+
+ if (!tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_MAC] ||
+ !tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_PHY])
+ return;
+
+ eht_capab->eht_supported = true;
+
+ if (tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_MAC] &&
+ nla_len(tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_MAC]) >= 2) {
+ const u8 *pos;
+
+ pos = nla_data(tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_MAC]);
+ eht_capab->mac_cap = WPA_GET_LE16(pos);
+ }
+
+ if (tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_PHY]) {
+ len = nla_len(tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_PHY]);
+ if (len > sizeof(eht_capab->phy_cap))
+ len = sizeof(eht_capab->phy_cap);
+ os_memcpy(eht_capab->phy_cap,
+ nla_data(tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_PHY]),
+ len);
+ }
+
+ if (tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_MCS_SET]) {
+ len = nla_len(tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_MCS_SET]);
+ if (len > sizeof(eht_capab->mcs))
+ len = sizeof(eht_capab->mcs);
+ os_memcpy(eht_capab->mcs,
+ nla_data(tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_MCS_SET]),
+ len);
+ }
+
+ if (tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_PPE]) {
+ len = nla_len(tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_PPE]);
+ if (len > sizeof(eht_capab->ppet))
+ len = sizeof(eht_capab->ppet);
+ os_memcpy(&eht_capab->ppet,
+ nla_data(tb[NL80211_BAND_IFTYPE_ATTR_EHT_CAP_PPE]),
+ len);
+ }
}
return NL_STOP;
for (i = 0; i < IEEE80211_MODE_NUM; i++)
- phy_info_iftype_copy(&mode->he_capab[i], i, tb, tb_flags);
+ phy_info_iftype_copy(mode, i, tb, tb_flags);
return NL_OK;
}