mac80211: enable DFS with channel contexts
authorMichal Kazior <michal.kazior@tieto.com>
Fri, 10 Oct 2014 10:43:23 +0000 (12:43 +0200)
committerJohannes Berg <johannes.berg@intel.com>
Fri, 10 Oct 2014 15:08:33 +0000 (17:08 +0200)
It is okay to enable DFS for channel contexts
based drivers as long as no combination advertises
radar detection and multi-channel operation at the
same time.

Signed-off-by: Michal Kazior <michal.kazior@tieto.com>
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
net/mac80211/main.c
net/mac80211/util.c

index 107d1c884de35285ff117162ad1b30563b550d7e..9e322dce64ec7060e5df5cd6ce10db7ea70599a1 100644 (file)
@@ -785,13 +785,14 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
                if (local->hw.wiphy->interface_modes & BIT(NL80211_IFTYPE_WDS))
                        return -EINVAL;
 
-               /* DFS currently not supported with channel context drivers */
+               /* DFS is not supported with multi-channel combinations yet */
                for (i = 0; i < local->hw.wiphy->n_iface_combinations; i++) {
                        const struct ieee80211_iface_combination *comb;
 
                        comb = &local->hw.wiphy->iface_combinations[i];
 
-                       if (comb->radar_detect_widths)
+                       if (comb->radar_detect_widths &&
+                           comb->num_different_channels > 1)
                                return -EINVAL;
                }
        }
index 3c61060a4d2b75bd89d4a792dde8b4721eb435dc..c76c9d7294ae63c9706fd55136bf55cc1ba715a6 100644 (file)
@@ -2526,11 +2526,23 @@ void ieee80211_dfs_radar_detected_work(struct work_struct *work)
        struct ieee80211_local *local =
                container_of(work, struct ieee80211_local, radar_detected_work);
        struct cfg80211_chan_def chandef = local->hw.conf.chandef;
+       struct ieee80211_chanctx *ctx;
+       int num_chanctx = 0;
+
+       mutex_lock(&local->chanctx_mtx);
+       list_for_each_entry(ctx, &local->chanctx_list, list) {
+               if (ctx->replace_state == IEEE80211_CHANCTX_REPLACES_OTHER)
+                       continue;
+
+               num_chanctx++;
+               chandef = ctx->conf.def;
+       }
+       mutex_unlock(&local->chanctx_mtx);
 
        ieee80211_dfs_cac_cancel(local);
 
-       if (local->use_chanctx)
-               /* currently not handled */
+       if (num_chanctx > 1)
+               /* XXX: multi-channel is not supported yet */
                WARN_ON(1);
        else
                cfg80211_radar_event(local->hw.wiphy, &chandef, GFP_KERNEL);