mesh: Do not enable HE on 5 GHz without VHT

The commit ad9a1bfe78 ("nl80211: Share VHT channel configuration for
HE") always enforced that VHT is enabled when HE was enabled. This broke
the mesh functionality on 2.4 GHz with HE because ibss_mesh_setup_freq()
isn't setting up the VHT parameters for 2.4 GHz.

This problem was resolved for 2.4 GHz by commit df4f959988 ("nl80211:
Don't force VHT channel definition with HE"), but it is still possible
to disable VHT during the mesh/IBSS freq setup on 5 GHz - which would
result in the same problem as seen on 2.4 GHz.

The code enabling HE for IBSS/mesh must now make sure that it doesn't
enable HE when VHT could be enforced by the nl80211 driver code but
disabled by the user.

Fixes: 3459c54ac7 ("mesh: Add support for HE mode")
Signed-off-by: Sven Eckelmann <seckelmann@datto.com>
This commit is contained in:
Sven Eckelmann 2019-08-13 15:50:52 +02:00 committed by Jouni Malinen
parent 0497e41481
commit 6e711e7ab3

View file

@ -2169,6 +2169,7 @@ void ibss_mesh_setup_freq(struct wpa_supplicant *wpa_s,
struct hostapd_freq_params vht_freq;
int chwidth, seg0, seg1;
u32 vht_caps = 0;
int is_24ghz;
freq->freq = ssid->frequency;
@ -2220,8 +2221,8 @@ void ibss_mesh_setup_freq(struct wpa_supplicant *wpa_s,
if (!mode)
return;
/* HE can work without HT + VHT */
freq->he_enabled = mode->he_capab[ieee80211_mode].he_supported;
is_24ghz = hw_mode == HOSTAPD_MODE_IEEE80211G ||
hw_mode == HOSTAPD_MODE_IEEE80211B;
#ifdef CONFIG_HT_OVERRIDES
if (ssid->disable_ht) {
@ -2234,6 +2235,10 @@ void ibss_mesh_setup_freq(struct wpa_supplicant *wpa_s,
if (!freq->ht_enabled)
return;
/* Allow HE on 2.4 GHz without VHT: see nl80211_put_freq_params() */
if (is_24ghz)
freq->he_enabled = mode->he_capab[ieee80211_mode].he_supported;
/* Setup higher BW only for 5 GHz */
if (mode->mode != HOSTAPD_MODE_IEEE80211A)
return;
@ -2354,6 +2359,9 @@ skip_ht40:
if (!vht_freq.vht_enabled)
return;
/* Enable HE for VHT */
vht_freq.he_enabled = mode->he_capab[ieee80211_mode].he_supported;
/* setup center_freq1, bandwidth */
for (j = 0; j < ARRAY_SIZE(vht80); j++) {
if (freq->channel >= vht80[j] &&