Message ID | 1c52bf51870d1c1ff78aa3aa9e7032087de0794d.1535403927.git.peter.oh@bowerswilkins.com |
---|---|
State | Changes Requested |
Headers | show |
Series | mesh: enable DFS channels in mesh mode | expand |
On Mon, Aug 27, 2018 at 02:28:46PM -0700, peter.oh@bowerswilkins.com wrote: > mac80211 does not allow mgmt tx to use off channel on > DFS channels in non-ETSI domain, because it will invalidate > CAC result on current operating channel. > (mac80211 commit: 34373d12f3cbb74960a73431138ef619d857996f) > Hence don't set offchanok for mgmt tx in case of DFS channels > in non-ETSI. > diff --git a/src/drivers/driver_nl80211.c b/src/drivers/driver_nl80211.c > @@ -7202,6 +7206,21 @@ static int wpa_driver_nl80211_send_action(struct i802_bss *bss, > + if (is_mesh_interface(drv->nlmode)) { > + modes = nl80211_get_hw_feature_data(bss, &num_modes, > + &flags, &dfs_domain); > + if (dfs_domain != HOSTAPD_DFS_REGION_ETSI && > + ieee80211_is_dfs(bss->freq, modes, num_modes)) This sounds unnecessarily heavy operation for every management frame TX operation. Couldn't this information about DFS-ETSI be cached instead? > + offchanok = 0; And this won't work if the channel on which the frame is supposed to be sent is not the operating channel. This should really be done conditionally based on the operating channel and if ETSI case allows somewhat more flexible rules for DFS channels, that could be considered as an optimization. I guess the main issue with clearing offchanok would be coming from trying to force the radio to remain active on the operating channel for some time. For that to work, remain-on-channel might actually be a better approach.
diff --git a/src/drivers/driver_nl80211.c b/src/drivers/driver_nl80211.c index 26df43b..0af109e 100644 --- a/src/drivers/driver_nl80211.c +++ b/src/drivers/driver_nl80211.c @@ -7178,6 +7178,10 @@ static int wpa_driver_nl80211_send_action(struct i802_bss *bss, int ret = -1; u8 *buf; struct ieee80211_hdr *hdr; + struct hostapd_hw_modes *modes; + int i, offchanok = 1; + u16 num_modes, flags; + u8 dfs_domain; wpa_printf(MSG_DEBUG, "nl80211: Send Action frame (ifindex=%d, " "freq=%u MHz wait=%d ms no_cck=%d)", @@ -7202,6 +7206,21 @@ static int wpa_driver_nl80211_send_action(struct i802_bss *bss, os_memset(bss->rand_addr, 0, ETH_ALEN); } + if (is_mesh_interface(drv->nlmode)) { + modes = nl80211_get_hw_feature_data(bss, &num_modes, + &flags, &dfs_domain); + if (dfs_domain != HOSTAPD_DFS_REGION_ETSI && + ieee80211_is_dfs(bss->freq, modes, num_modes)) + offchanok = 0; + if (modes) { + for (i = 0; i < num_modes; i++) { + os_free(modes[i].channels); + os_free(modes[i].rates); + } + os_free(modes); + } + } + if (is_ap_interface(drv->nlmode) && (!(drv->capa.flags & WPA_DRIVER_FLAGS_OFFCHANNEL_TX) || (int) freq == bss->freq || drv->device_ap_sme || @@ -7213,7 +7232,7 @@ static int wpa_driver_nl80211_send_action(struct i802_bss *bss, ret = nl80211_send_frame_cmd(bss, freq, wait_time, buf, 24 + data_len, &drv->send_action_cookie, - no_cck, 0, 1, NULL, 0); + no_cck, 0, offchanok, NULL, 0); os_free(buf); return ret;