@@ -3196,14 +3196,17 @@ ieee80211_eht_mcs_nss_size(const struct ieee80211_he_cap_elem *he_cap,
{
u8 count = 0;
- /* on 2.4 GHz, if it supports 40 MHz, the result is 3 */
- if (he_cap->phy_cap_info[0] &
- IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_IN_2G)
- return 3;
+ /* 20 MHz-only non-AP STA */
+ if (!from_ap && (he_cap->phy_cap_info[0] &
+ (IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_IN_2G |
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_80MHZ_IN_5G |
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G |
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G)) == 0)
+ return 4;
- /* on 2.4 GHz, these three bits are reserved, so should be 0 */
if (he_cap->phy_cap_info[0] &
- IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_80MHZ_IN_5G)
+ (IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_IN_2G |
+ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_80MHZ_IN_5G))
count += 3;
if (he_cap->phy_cap_info[0] &
Mediatek's chipsets MT7927 and MT7925 with Windows driver 5.4.0.3044 (and earlier versions) set the IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_40MHZ_IN_2G bit in 5 & 6Ghz band, which is supposed to be reserved. Currently, the kernel assumes a reserved bit to be set to 0 and uses the bit value to deduce that the current band used is 2.4GHz. This causes the kernel to miscalculate mcs_nss_size to 3 bytes, resulting in incorrect rx/tx nss map, so the sta is believed to have 0 NSS for 160/320. Signed-off-by: Pablo Martin-Gomez <pmartin-gomez@freebox.fr> --- include/linux/ieee80211.h | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-)