mac80211: mesh: Allow following CSA to DFS channels if userspace handles it
authorBenjamin Berg <benjamin@sipsolutions.net>
Tue, 16 May 2017 09:23:13 +0000 (11:23 +0200)
committerJohannes Berg <johannes.berg@intel.com>
Fri, 19 May 2017 11:26:05 +0000 (13:26 +0200)
If userspace has flagged support for DFS earlier, then we can follow CSA
to DFS channels. So instead of rejecting the switch, allow it to happen
if the flag has been set during mesh setup.

Signed-off-by: Benjamin Berg <benjamin@sipsolutions.net>
Signed-off-by: Simon Wunderlich <sw@simonwunderlich.de>
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
net/mac80211/cfg.c
net/mac80211/ieee80211_i.h
net/mac80211/mesh.c

index 6c2e6060cd549e3c4c39e78cc20ca9302472c4ac..6980a936a437da12d587aa5f0767ae953252d407 100644 (file)
@@ -1874,6 +1874,7 @@ static int copy_mesh_setup(struct ieee80211_if_mesh *ifmsh,
        ifmsh->user_mpm = setup->user_mpm;
        ifmsh->mesh_auth_id = setup->auth_id;
        ifmsh->security = IEEE80211_MESH_SEC_NONE;
+       ifmsh->userspace_handles_dfs = setup->userspace_handles_dfs;
        if (setup->is_authenticated)
                ifmsh->security |= IEEE80211_MESH_SEC_AUTHED;
        if (setup->is_secure)
index 60bed6c698013d68d5fc8e874bbe4989c0c249e7..c960e4999380a8df8f509aa7524cfe3149e5079c 100644 (file)
@@ -643,6 +643,8 @@ struct ieee80211_if_mesh {
        unsigned long wrkq_flags;
        unsigned long mbss_changed;
 
+       bool userspace_handles_dfs;
+
        u8 mesh_id[IEEE80211_MAX_MESH_ID_LEN];
        size_t mesh_id_len;
        /* Active Path Selection Protocol Identifier */
index f7dffdf5fc748391c4f76d44fbc0bf7037a48e3c..7e0498bb933768e0888c90eda738dad0442f13be 100644 (file)
@@ -978,7 +978,9 @@ ieee80211_mesh_process_chnswitch(struct ieee80211_sub_if_data *sdata,
        params.count = csa_ie.count;
 
        if (!cfg80211_chandef_usable(sdata->local->hw.wiphy, &params.chandef,
-                                    IEEE80211_CHAN_DISABLED)) {
+                                    IEEE80211_CHAN_DISABLED) ||
+           !cfg80211_reg_can_beacon(sdata->local->hw.wiphy, &params.chandef,
+                                    NL80211_IFTYPE_MESH_POINT)) {
                sdata_info(sdata,
                           "mesh STA %pM switches to unsupported channel (%d MHz, width:%d, CF1/2: %d/%d MHz), aborting\n",
                           sdata->vif.addr,
@@ -994,9 +996,16 @@ ieee80211_mesh_process_chnswitch(struct ieee80211_sub_if_data *sdata,
                                            NL80211_IFTYPE_MESH_POINT);
        if (err < 0)
                return false;
-       if (err > 0)
-               /* TODO: DFS not (yet) supported */
+       if (err > 0 && !ifmsh->userspace_handles_dfs) {
+               sdata_info(sdata,
+                          "mesh STA %pM switches to channel requiring DFS (%d MHz, width:%d, CF1/2: %d/%d MHz), aborting\n",
+                          sdata->vif.addr,
+                          params.chandef.chan->center_freq,
+                          params.chandef.width,
+                          params.chandef.center_freq1,
+                          params.chandef.center_freq2);
                return false;
+       }
 
        params.radar_required = err;