aboutsummaryrefslogtreecommitdiff
path: root/sys
diff options
context:
space:
mode:
authorAdrian Chadd <adrian@FreeBSD.org>2012-01-31 00:03:49 +0000
committerAdrian Chadd <adrian@FreeBSD.org>2012-01-31 00:03:49 +0000
commit62f8a13a756be9727a38be25c07d9a3c96f7e96d (patch)
treec167ab2f6bcbdeb4e2c2bfff53571f9b1ce06efc /sys
parent7f925de11ae77354b8c86398970050f39b3bca25 (diff)
downloadsrc-62f8a13a756be9727a38be25c07d9a3c96f7e96d.tar.gz
src-62f8a13a756be9727a38be25c07d9a3c96f7e96d.zip
Notes
Diffstat (limited to 'sys')
-rw-r--r--sys/conf/options1
-rw-r--r--sys/net80211/ieee80211_dfs.c82
-rw-r--r--sys/net80211/ieee80211_dfs.h6
3 files changed, 73 insertions, 16 deletions
diff --git a/sys/conf/options b/sys/conf/options
index 5cbb0d306af4..ca1244371635 100644
--- a/sys/conf/options
+++ b/sys/conf/options
@@ -845,6 +845,7 @@ IEEE80211_SUPPORT_MESH opt_wlan.h
IEEE80211_SUPPORT_SUPERG opt_wlan.h
IEEE80211_SUPPORT_TDMA opt_wlan.h
IEEE80211_ALQ opt_wlan.h
+IEEE80211_DFS_DEBUG opt_wlan.h
# 802.11 TDMA support
TDMA_SLOTLEN_DEFAULT opt_tdma.h
diff --git a/sys/net80211/ieee80211_dfs.c b/sys/net80211/ieee80211_dfs.c
index ffb05e9dcd40..82e525d523ce 100644
--- a/sys/net80211/ieee80211_dfs.c
+++ b/sys/net80211/ieee80211_dfs.c
@@ -64,6 +64,28 @@ SYSCTL_INT(_net_wlan, OID_AUTO, cac_timeout, CTLFLAG_RW,
&ieee80211_cac_timeout, 0, "CAC timeout (secs)");
#define CAC_TIMEOUT msecs_to_ticks(ieee80211_cac_timeout*1000)
+/*
+ DFS* In order to facilitate debugging, a couple of operating
+ * modes aside from the default are needed.
+ *
+ * 0 - default CAC/NOL behaviour - ie, start CAC, place
+ * channel on NOL list.
+ * 1 - send CAC, but don't change channel or add the channel
+ * to the NOL list.
+ * 2 - just match on radar, don't send CAC or place channel in
+ * the NOL list.
+ */
+static int ieee80211_dfs_debug = DFS_DBG_NONE;
+
+/*
+ * This option must not be included in the default kernel
+ * as it allows users to plainly disable CAC/NOL handling.
+ */
+#ifdef IEEE80211_DFS_DEBUG
+SYSCTL_INT(_net_wlan, OID_AUTO, dfs_debug, CTLFLAG_RW,
+ &ieee80211_dfs_debug, 0, "DFS debug behaviour");
+#endif
+
static int
null_set_quiet(struct ieee80211_node *ni, u_int8_t *quiet_elm)
{
@@ -278,24 +300,44 @@ ieee80211_dfs_notify_radar(struct ieee80211com *ic, struct ieee80211_channel *ch
IEEE80211_LOCK_ASSERT(ic);
/*
- * Mark all entries with this frequency. Notify user
- * space and arrange for notification when the radar
- * indication is cleared. Then kick the NOL processing
- * thread if not already running.
+ * If doing DFS debugging (mode 2), don't bother
+ * running the rest of this function.
+ *
+ * Simply announce the presence of the radar and continue
+ * along merrily.
*/
- now = ticks;
- for (i = 0; i < ic->ic_nchans; i++) {
- struct ieee80211_channel *c = &ic->ic_channels[i];
- if (c->ic_freq == chan->ic_freq) {
- c->ic_state &= ~IEEE80211_CHANSTATE_CACDONE;
- c->ic_state |= IEEE80211_CHANSTATE_RADAR;
- dfs->nol_event[i] = now;
+ if (ieee80211_dfs_debug == DFS_DBG_NOCSANOL) {
+ announce_radar(ic->ic_ifp, chan, chan);
+ ieee80211_notify_radar(ic, chan);
+ return;
+ }
+
+ /*
+ * Don't mark the channel and don't put it into NOL
+ * if we're doing DFS debugging.
+ */
+ if (ieee80211_dfs_debug == DFS_DBG_NONE) {
+ /*
+ * Mark all entries with this frequency. Notify user
+ * space and arrange for notification when the radar
+ * indication is cleared. Then kick the NOL processing
+ * thread if not already running.
+ */
+ now = ticks;
+ for (i = 0; i < ic->ic_nchans; i++) {
+ struct ieee80211_channel *c = &ic->ic_channels[i];
+ if (c->ic_freq == chan->ic_freq) {
+ c->ic_state &= ~IEEE80211_CHANSTATE_CACDONE;
+ c->ic_state |= IEEE80211_CHANSTATE_RADAR;
+ dfs->nol_event[i] = now;
+ }
}
+ ieee80211_notify_radar(ic, chan);
+ chan->ic_state |= IEEE80211_CHANSTATE_NORADAR;
+ if (!callout_pending(&dfs->nol_timer))
+ callout_reset(&dfs->nol_timer, NOL_TIMEOUT,
+ dfs_timeout, ic);
}
- ieee80211_notify_radar(ic, chan);
- chan->ic_state |= IEEE80211_CHANSTATE_NORADAR;
- if (!callout_pending(&dfs->nol_timer))
- callout_reset(&dfs->nol_timer, NOL_TIMEOUT, dfs_timeout, ic);
/*
* If radar is detected on the bss channel while
@@ -310,7 +352,15 @@ ieee80211_dfs_notify_radar(struct ieee80211com *ic, struct ieee80211_channel *ch
*/
if (chan == ic->ic_bsschan) {
/* XXX need a way to defer to user app */
- dfs->newchan = ieee80211_dfs_pickchannel(ic);
+
+ /*
+ * Don't flip over to a new channel if
+ * we are currently doing DFS debugging.
+ */
+ if (ieee80211_dfs_debug == DFS_DBG_NONE)
+ dfs->newchan = ieee80211_dfs_pickchannel(ic);
+ else
+ dfs->newchan = chan;
announce_radar(ic->ic_ifp, chan, dfs->newchan);
diff --git a/sys/net80211/ieee80211_dfs.h b/sys/net80211/ieee80211_dfs.h
index 90760777a785..a5688e3bc491 100644
--- a/sys/net80211/ieee80211_dfs.h
+++ b/sys/net80211/ieee80211_dfs.h
@@ -31,6 +31,12 @@
* 802.11h/DFS definitions.
*/
+typedef enum {
+ DFS_DBG_NONE = 0,
+ DFS_DBG_NONOL = 1,
+ DFS_DBG_NOCSANOL = 2
+} dfs_debug_t;
+
struct ieee80211_dfs_state {
int nol_event[IEEE80211_CHAN_MAX];
struct callout nol_timer; /* NOL list processing */