PERFORCE change 77351 for review

Sam Leffler sam at FreeBSD.org
Mon May 23 17:07:11 GMT 2005


http://perforce.freebsd.org/chv.cgi?CH=77351

Change 77351 by sam at sam_ebb on 2005/05/23 17:06:17

	o split out power save code into it's own file/module (will grow soon)
	o move ieee80211_match_bss from scan code to ibss merge which is the
	  only user now that the scan cache is a private data structure
	o shuffle vap sysctl attach/detach so modules can craft sysctls that
	  reference private data
	o expose net.wlan sysctl node so modules can add sysctls that
	  reference private data
	o make bgscan delay for pwr sav frame xmit tunable for testing
	o make beacon switch time for returning on-channel tunable for testing

Affected files ...

.. //depot/projects/vap/sys/net80211/ieee80211.c#12 edit
.. //depot/projects/vap/sys/net80211/ieee80211_freebsd.c#9 edit
.. //depot/projects/vap/sys/net80211/ieee80211_freebsd.h#7 edit
.. //depot/projects/vap/sys/net80211/ieee80211_input.c#15 edit
.. //depot/projects/vap/sys/net80211/ieee80211_node.c#10 edit
.. //depot/projects/vap/sys/net80211/ieee80211_output.c#14 edit
.. //depot/projects/vap/sys/net80211/ieee80211_power.c#1 add
.. //depot/projects/vap/sys/net80211/ieee80211_power.h#1 add
.. //depot/projects/vap/sys/net80211/ieee80211_proto.h#6 edit
.. //depot/projects/vap/sys/net80211/ieee80211_scan.c#6 edit
.. //depot/projects/vap/sys/net80211/ieee80211_scan.h#4 edit
.. //depot/projects/vap/sys/net80211/ieee80211_var.h#15 edit

Differences ...

==== //depot/projects/vap/sys/net80211/ieee80211.c#12 (text+ko) ====

@@ -164,6 +164,7 @@
 
 	ieee80211_crypto_attach(ic);
 	ieee80211_node_attach(ic);
+	ieee80211_power_attach(ic);
 	ieee80211_proto_attach(ic);
 	ieee80211_scan_attach(ic);
 	ieee80211_regdomain_attach(ic);
@@ -213,6 +214,7 @@
 	ieee80211_scan_detach(ic);
 	ieee80211_proto_detach(ic);
 	ieee80211_crypto_detach(ic);
+	ieee80211_power_detach(ic);
 	ieee80211_node_detach(ic);
 	ifmedia_removeall(&ic->ic_media);
 
@@ -291,8 +293,10 @@
 
 	IEEE80211_ADDR_COPY(vap->iv_myaddr, ic->ic_myaddr);
 
+	ieee80211_sysctl_vattach(vap);
 	ieee80211_crypto_vattach(vap);
 	ieee80211_node_vattach(vap);
+	ieee80211_power_vattach(vap);
 	ieee80211_proto_vattach(vap);
 	ieee80211_scan_vattach(vap);
 	ieee80211_regdomain_vattach(vap);
@@ -300,7 +304,6 @@
 	ieee80211_vlan_vattach(vap);
 	ieee80211_ioctl_vattach(vap);
 #endif
-	ieee80211_sysctl_vattach(vap);
 
 	return 1;
 #undef IEEE80211_C_OPMODE
@@ -316,6 +319,7 @@
 	int maxrate;
 
 	ieee80211_node_latevattach(vap);	/* XXX move into vattach */
+	ieee80211_power_latevattach(vap);	/* XXX move into vattach */
 
 	ether_ifattach(ifp, vap->iv_myaddr);
 	bpfattach2(ifp, DLT_IEEE802_11, ifp->if_hdrlen, &vap->iv_rawbpf);
@@ -359,7 +363,6 @@
 
 	ifmedia_removeall(&vap->iv_media);
 
-	ieee80211_sysctl_vdetach(vap);
 #if 0
 	ieee80211_ioctl_vdetach(vap);
 	ieee80211_vlan_vdetach(vap);
@@ -368,7 +371,9 @@
 	ieee80211_scan_vdetach(vap);
 	ieee80211_proto_vdetach(vap);
 	ieee80211_crypto_vdetach(vap);
+	ieee80211_power_vdetach(vap);
 	ieee80211_node_vdetach(vap);
+	ieee80211_sysctl_vdetach(vap);
 }
 
 void

==== //depot/projects/vap/sys/net80211/ieee80211_freebsd.c#9 (text+ko) ====

@@ -38,7 +38,6 @@
 #include <sys/mbuf.h>   
 #include <sys/module.h>
 #include <sys/proc.h>
-#include <sys/sysctl.h>
 
 #include <sys/socket.h>
 
@@ -118,7 +117,6 @@
 		"debug", CTLFLAG_RW, &vap->iv_debug, 0,
 		"control debugging printfs");
 #endif
-	/* XXX inherit from tunables */
 	SYSCTL_ADD_PROC(ctx, SYSCTL_CHILDREN(oid), OID_AUTO,
 		"inact_run", CTLTYPE_INT | CTLFLAG_RW, &vap->iv_inact_run, 0,
 		ieee80211_sysctl_inact, "I",

==== //depot/projects/vap/sys/net80211/ieee80211_freebsd.h#7 (text+ko) ====

@@ -179,6 +179,8 @@
 struct ieee80211com;
 struct ieee80211vap;
 
+#include <sys/sysctl.h>
+SYSCTL_DECL(_net_wlan);
 void	ieee80211_sysctl_attach(struct ieee80211com *);
 void	ieee80211_sysctl_detach(struct ieee80211com *);
 void	ieee80211_sysctl_vattach(struct ieee80211vap *);

==== //depot/projects/vap/sys/net80211/ieee80211_input.c#15 (text+ko) ====

@@ -115,8 +115,7 @@
 	struct mbuf *);
 static void ieee80211_send_error(struct ieee80211_node *, const u_int8_t *,
 	int subtype, int arg);
-static void ieee80211_node_pwrsave(struct ieee80211_node *, int enable);
-static void ieee80211_recv_pspoll(struct ieee80211_node *, struct mbuf *);
+static void ieee80211_recv_pspoll(struct ieee80211_node *, struct mbuf *);;
 
 /*
  * Process a received frame.  The node associated with the sender
@@ -2942,125 +2941,9 @@
 #undef IEEE80211_VERIFY_ELEMENT
 
 /*
- * Handle station power-save state change.
+ * Process a received ps-poll frame.
  */
-static void
-ieee80211_node_pwrsave(struct ieee80211_node *ni, int enable)
-{
-	struct ieee80211vap *vap = ni->ni_vap;
-	struct mbuf *m;
-
-	if (enable) {
-		if ((ni->ni_flags & IEEE80211_NODE_PWR_MGT) == 0)
-			vap->iv_ps_sta++;
-		ni->ni_flags |= IEEE80211_NODE_PWR_MGT;
-		IEEE80211_NOTE(vap, IEEE80211_MSG_POWER, ni,
-		    "power save mode on, %u sta's in ps mode", vap->iv_ps_sta);
-		return;
-	}
-
-	if ((ni->ni_flags & IEEE80211_NODE_PWR_MGT))
-		vap->iv_ps_sta--;
-	ni->ni_flags &= ~IEEE80211_NODE_PWR_MGT;
-	IEEE80211_NOTE(vap, IEEE80211_MSG_POWER, ni,
-	    "power save mode off, %u sta's in ps mode", vap->iv_ps_sta);
-	/* XXX if no stations in ps mode, flush mc frames */
-
-	/*
-	 * Flush queued unicast frames.
-	 */
-	if (IEEE80211_NODE_SAVEQ_QLEN(ni) == 0) {
-		if (vap->iv_set_tim != NULL)
-			vap->iv_set_tim(ni, 0);		/* just in case */
-		return;
-	}
-	IEEE80211_NOTE(vap, IEEE80211_MSG_POWER, ni,
-	    "flush ps queue, %u packets queued", IEEE80211_NODE_SAVEQ_QLEN(ni));
-	for (;;) {
-		int qlen;
-
-		IEEE80211_NODE_SAVEQ_DEQUEUE(ni, m, qlen);
-		if (m == NULL)
-			break;
-		/* 
-		 * If this is the last packet, turn off the TIM bit.
-		 * If there are more packets, set the more packets bit
-		 * in the packet dispatched to the station.
-		 */
-		if (qlen != 0) {
-			struct ieee80211_frame_min *wh =
-				mtod(m, struct ieee80211_frame_min *);
-			wh->i_fc[1] |= IEEE80211_FC1_MORE_DATA;
-		}
-		/* XXX need different driver interface */
-		/* XXX bypasses q max */
-		IF_ENQUEUE(&vap->iv_arp.ac_if.if_snd, m);
-	}
-}
-
-/*
- * Handle power-save state change in station mode.
- */
 void
-ieee80211_sta_pwrsave(struct ieee80211vap *vap, int enable)
-{
-	struct ieee80211_node *ni = vap->iv_bss;
-	int qlen;
-
-	IEEE80211_NOTE(vap, IEEE80211_MSG_POWER, ni,
-	    "sta power save mode %s", enable ? "on" : "off");
-	if (!enable) {
-		if (ni->ni_flags & IEEE80211_NODE_PWR_MGT) {
-			ni->ni_flags &= ~IEEE80211_NODE_PWR_MGT;
-			ieee80211_send_nulldata(ieee80211_ref_node(ni));
-			/*
-			 * Flush any queued frames; we can do this immediately
-			 * because we know they'll be queued behind the null
-			 * data frame we send the ap.
-			 * XXX can we use a data frame to take us out of ps?
-			 */
-			qlen = IEEE80211_NODE_SAVEQ_QLEN(ni);
-			if (qlen != 0) {
-				struct ifnet *ifp = &vap->iv_arp.ac_if;
-				struct ifaltq *ifq = &ifp->if_snd;
-				struct ifqueue *psq = &ni->ni_savedq;
-				int active;
-
-				IEEE80211_NOTE(vap, IEEE80211_MSG_POWER, ni,
-				    "flush ps queue, %u packets queued", qlen);
-				active = 1;
-				IF_LOCK(ifq);
-				IF_LOCK(psq);
-				for (;;) {
-					struct mbuf *m;
-
-					if (_IF_QLEN(psq) == 0)
-						break;
-					if (_IF_QFULL(ifq))
-						break;
-					_IF_DEQUEUE(psq, m);
-					/* NB: no accounting, already done */
-					_IF_ENQUEUE(ifq, m);
-					active = ifp->if_flags & IFF_OACTIVE;
-				}
-				IF_UNLOCK(psq);
-				IF_UNLOCK(ifq);
-				if (!active)
-					if_start(ifp);
-			}
-		}
-	} else {
-		if ((ni->ni_flags & IEEE80211_NODE_PWR_MGT) == 0) {
-			ni->ni_flags |= IEEE80211_NODE_PWR_MGT;
-			ieee80211_send_nulldata(ieee80211_ref_node(ni));
-		}
-	}
-}
-
-/*
- * Process a received ps-poll frame.
- */
-static void
 ieee80211_recv_pspoll(struct ieee80211_node *ni, struct mbuf *m0)
 {
 	struct ieee80211vap *vap = ni->ni_vap;

==== //depot/projects/vap/sys/net80211/ieee80211_node.c#10 (text+ko) ====

@@ -66,16 +66,12 @@
 static void node_cleanup(struct ieee80211_node *);
 static void node_free(struct ieee80211_node *);
 static u_int8_t node_getrssi(const struct ieee80211_node *);
-static int node_saveq_drain(struct ieee80211_node *);
-static int node_saveq_age(struct ieee80211_node *);
 
 static void _ieee80211_free_node(struct ieee80211_node *);
 
 static void ieee80211_timeout_stations(struct ieee80211_node_table *);
 static void ieee80211_node_timeout(void *);
 
-static void ieee80211_set_tim(struct ieee80211_node *, int set);
-
 static void ieee80211_node_table_init(struct ieee80211com *ic,
 	struct ieee80211_node_table *nt, const char *name, int inact);
 static	void ieee80211_node_table_reset(struct ieee80211_node_table *,
@@ -117,12 +113,6 @@
 	vap->iv_inact_auth = IEEE80211_INACT_AUTH;
 	vap->iv_inact_run = IEEE80211_INACT_RUN;
 	vap->iv_inact_probe = IEEE80211_INACT_PROBE;
-
-	if (vap->iv_opmode == IEEE80211_M_HOSTAP ||
-	    vap->iv_opmode == IEEE80211_M_IBSS) {
-		/* NB: driver should override */
-		vap->iv_set_tim = ieee80211_set_tim;
-	}
 }
 
 void
@@ -148,15 +138,6 @@
 			printf("%s: no memory for AID bitmap!\n", __func__);
 			vap->iv_max_aid = 0;
 		}
-
-		vap->iv_tim_len = howmany(vap->iv_max_aid,8) * sizeof(u_int8_t);
-		MALLOC(vap->iv_tim_bitmap, u_int8_t *, vap->iv_tim_len,
-			M_DEVBUF, M_NOWAIT | M_ZERO);
-		if (vap->iv_tim_bitmap == NULL) {
-			printf("%s: no memory for TIM bitmap!\n", __func__);
-			/* XXX good enough to keep from crashing? */
-			vap->iv_tim_len = 0;
-		}
 	}
 
 	ieee80211_reset_bss(vap);
@@ -335,6 +316,105 @@
 		ieee80211_free_node(obss);
 	}
 }
+
+/*
+ * Test a node for suitability/compatibility.
+ */
+static int
+check_bss(struct ieee80211vap *vap, struct ieee80211_node *ni)
+{
+	struct ieee80211com *ic = ni->ni_ic;
+        u_int8_t rate;
+
+	if (isclr(ic->ic_chan_active, ieee80211_chan2ieee(ic, ni->ni_chan)))
+		return 0;
+	if (vap->iv_opmode == IEEE80211_M_IBSS) {
+		if ((ni->ni_capinfo & IEEE80211_CAPINFO_IBSS) == 0)
+			return 0;
+	} else {
+		if ((ni->ni_capinfo & IEEE80211_CAPINFO_ESS) == 0)
+			return 0;
+	}
+	if (vap->iv_flags & IEEE80211_F_PRIVACY) {
+		if ((ni->ni_capinfo & IEEE80211_CAPINFO_PRIVACY) == 0)
+			return 0;
+	} else {
+		/* XXX does this mean privacy is supported or required? */
+		if (ni->ni_capinfo & IEEE80211_CAPINFO_PRIVACY)
+			return 0;
+	}
+	rate = ieee80211_fix_rate(ni, IEEE80211_F_DONEGO | IEEE80211_F_DOFRATE);
+	if (rate & IEEE80211_RATE_BASIC)
+		return 0;
+	if (vap->iv_des_esslen != 0 &&
+	    (ni->ni_esslen != vap->iv_des_esslen ||
+	     memcmp(ni->ni_essid, vap->iv_des_essid, vap->iv_des_esslen) != 0))
+		return 0;
+	if ((vap->iv_flags & IEEE80211_F_DESBSSID) &&
+	    !IEEE80211_ADDR_EQ(vap->iv_des_bssid, ni->ni_bssid))
+		return 0;
+	return 1;
+}
+
+#ifdef IEEE80211_DEBUG
+/*
+ * Display node suitability/compatibility.
+ */
+static void
+check_bss_debug(struct ieee80211vap *vap, struct ieee80211_node *ni)
+{
+	struct ieee80211com *ic = ni->ni_ic;
+        u_int8_t rate;
+        int fail;
+
+	fail = 0;
+	if (isclr(ic->ic_chan_active, ieee80211_chan2ieee(ic, ni->ni_chan)))
+		fail |= 0x01;
+	if (vap->iv_opmode == IEEE80211_M_IBSS) {
+		if ((ni->ni_capinfo & IEEE80211_CAPINFO_IBSS) == 0)
+			fail |= 0x02;
+	} else {
+		if ((ni->ni_capinfo & IEEE80211_CAPINFO_ESS) == 0)
+			fail |= 0x02;
+	}
+	if (vap->iv_flags & IEEE80211_F_PRIVACY) {
+		if ((ni->ni_capinfo & IEEE80211_CAPINFO_PRIVACY) == 0)
+			fail |= 0x04;
+	} else {
+		/* XXX does this mean privacy is supported or required? */
+		if (ni->ni_capinfo & IEEE80211_CAPINFO_PRIVACY)
+			fail |= 0x04;
+	}
+	rate = ieee80211_fix_rate(ni, IEEE80211_F_DONEGO | IEEE80211_F_DOFRATE);
+	if (rate & IEEE80211_RATE_BASIC)
+		fail |= 0x08;
+	if (vap->iv_des_esslen != 0 &&
+	    (ni->ni_esslen != vap->iv_des_esslen ||
+	     memcmp(ni->ni_essid, vap->iv_des_essid, vap->iv_des_esslen) != 0))
+		fail |= 0x10;
+	if ((vap->iv_flags & IEEE80211_F_DESBSSID) &&
+	    !IEEE80211_ADDR_EQ(vap->iv_des_bssid, ni->ni_bssid))
+		fail |= 0x20;
+
+	printf(" %c %s", fail ? '-' : '+', ether_sprintf(ni->ni_macaddr));
+	printf(" %s%c", ether_sprintf(ni->ni_bssid), fail & 0x20 ? '!' : ' ');
+	printf(" %3d%c",
+	    ieee80211_chan2ieee(ic, ni->ni_chan), fail & 0x01 ? '!' : ' ');
+	printf(" %+4d", ni->ni_rssi);
+	printf(" %2dM%c", (rate & IEEE80211_RATE_VAL) / 2,
+	    fail & 0x08 ? '!' : ' ');
+	printf(" %4s%c",
+	    (ni->ni_capinfo & IEEE80211_CAPINFO_ESS) ? "ess" :
+	    (ni->ni_capinfo & IEEE80211_CAPINFO_IBSS) ? "ibss" :
+	    "????",
+	    fail & 0x02 ? '!' : ' ');
+	printf(" %3s%c ",
+	    (ni->ni_capinfo & IEEE80211_CAPINFO_PRIVACY) ?  "wep" : "no",
+	    fail & 0x04 ? '!' : ' ');
+	ieee80211_print_essid(ni->ni_essid, ni->ni_esslen);
+	printf("%s\n", fail & 0x10 ? "!" : "");
+}
+#endif /* IEEE80211_DEBUG */
  
 /*
  * Handle 802.11 ad hoc network merge.  The
@@ -359,10 +439,14 @@
 		/* unchanged, nothing to do */
 		return 0;
 	}
-	if (ieee80211_match_bss(vap, ni) != 0) {
+	if (!check_bss(vap, ni)) {
 		/* capabilities mismatch */
 		IEEE80211_DPRINTF(vap, IEEE80211_MSG_ASSOC,
 		    "%s: merge failed, capabilities mismatch\n", __func__);
+#ifdef IEEE80211_DEBUG
+		if (ieee80211_msg_assoc(vap))
+			check_bss_debug(vap, ni);
+#endif
 		vap->iv_stats.is_ibss_capmismatch++;
 		return 0;
 	}
@@ -545,7 +629,7 @@
 	/*
 	 * Drain power save queue and, if needed, clear TIM.
 	 */
-	if (node_saveq_drain(ni) != 0 && vap->iv_set_tim != NULL)
+	if (ieee80211_node_saveq_drain(ni) != 0 && vap->iv_set_tim != NULL)
 		vap->iv_set_tim(ni, 0);
 
 	ni->ni_associd = 0;
@@ -597,73 +681,6 @@
 }
 
 /*
- * Clear any frames queued on a node's power save queue.
- * The number of frames that were present is returned.
- */
-static int
-node_saveq_drain(struct ieee80211_node *ni)
-{
-	struct mbuf *m;
-	int qlen;
-
-	IEEE80211_NODE_SAVEQ_LOCK(ni);
-	qlen = IEEE80211_NODE_SAVEQ_QLEN(ni);
-	for (;;) {
-		_IF_DEQUEUE(&ni->ni_savedq, m);
-		if (m == NULL)
-			break;
-		m_freem(m);
-	}
-	IEEE80211_NODE_SAVEQ_UNLOCK(ni);
-
-	return qlen;
-}
-
-/*
- * Age frames on the power save queue. The aging interval is
- * 4 times the listen interval specified by the station.  This
- * number is factored into the age calculations when the frame
- * is placed on the queue.  We store ages as time differences
- * so we can check and/or adjust only the head of the list.
- * If a frame's age exceeds the threshold then discard it.
- * The number of frames discarded is returned so the caller
- * can check if it needs to adjust the tim.
- */
-static int
-node_saveq_age(struct ieee80211_node *ni)
-{
-	int discard = 0;
-
-	/* XXX racey but good 'nuf? */
-	if (IEEE80211_NODE_SAVEQ_QLEN(ni) != 0) {
-#ifdef IEEE80211_DEBUG
-		struct ieee80211vap *vap = ni->ni_vap;
-#endif
-		struct mbuf *m;
-
-		IEEE80211_NODE_SAVEQ_LOCK(ni);
-		while (IF_POLL(&ni->ni_savedq, m) != NULL &&
-		     M_AGE_GET(m) < IEEE80211_INACT_WAIT) {
-			IEEE80211_NOTE(vap, IEEE80211_MSG_POWER, ni,
-				"discard frame, age %u", M_AGE_GET(m));
-
-			/* XXX could be optimized */
-			_IF_DEQUEUE(&ni->ni_savedq, m);
-			m_freem(m);
-			discard++;
-		}
-		if (m != NULL)
-			M_AGE_SUB(m, IEEE80211_INACT_WAIT);
-		IEEE80211_NODE_SAVEQ_UNLOCK(ni);
-
-		IEEE80211_NOTE(vap, IEEE80211_MSG_POWER, ni,
-		    "discard %u frames for age", discard);
-		IEEE80211_NODE_STAT_ADD(ni, ps_discard, discard);
-	}
-	return discard;
-}
-
-/*
  * Create an entry in the specified node table.  The node
  * is setup with the mac address, an initial reference count,
  * and some basic parameters obtained from global state.
@@ -1210,7 +1227,7 @@
 			/*
 			 * Age frames on the power save queue.
 			 */
-			if (node_saveq_age(ni) != 0 && 
+			if (ieee80211_node_saveq_age(ni) != 0 && 
 			    IEEE80211_NODE_SAVEQ_QLEN(ni) == 0 &&
 			    vap->iv_set_tim != NULL)
 				vap->iv_set_tim(ni, 0);
@@ -1652,34 +1669,3 @@
 	return rssi_total / NZ(rssi_samples);
 #undef NZ
 }
-
-/*
- * Indicate whether there are frames queued for a station in power-save mode.
- */
-static void
-ieee80211_set_tim(struct ieee80211_node *ni, int set)
-{
-	struct ieee80211vap *vap = ni->ni_vap;
-	u_int16_t aid;
-
-	KASSERT(vap->iv_opmode == IEEE80211_M_HOSTAP ||
-		vap->iv_opmode == IEEE80211_M_IBSS,
-		("operating mode %u", vap->iv_opmode));
-
-	aid = IEEE80211_AID(ni->ni_associd);
-	KASSERT(aid < vap->iv_max_aid,
-		("bogus aid %u, max %u", aid, vap->iv_max_aid));
-
-	IEEE80211_BEACON_LOCK(ni->ni_ic);
-	if (set != (isset(vap->iv_tim_bitmap, aid) != 0)) {
-		if (set) {
-			setbit(vap->iv_tim_bitmap, aid);
-			vap->iv_ps_pending++;
-		} else {
-			clrbit(vap->iv_tim_bitmap, aid);
-			vap->iv_ps_pending--;
-		}
-		vap->iv_flags |= IEEE80211_F_TIMUPDATE;
-	}
-	IEEE80211_BEACON_UNLOCK(ni->ni_ic);
-}

==== //depot/projects/vap/sys/net80211/ieee80211_output.c#14 (text+ko) ====

@@ -2231,49 +2231,3 @@
 
 	return len_changed;
 }
-
-/*
- * Save an outbound packet for a node in power-save sleep state.
- * The new packet is placed on the node's saved queue, and the TIM
- * is changed, if necessary.
- */
-void
-ieee80211_pwrsave(struct ieee80211_node *ni, struct mbuf *m)
-{
-	struct ieee80211vap *vap = ni->ni_vap;
-	struct ieee80211com *ic = ni->ni_ic;
-	int qlen, age;
-
-	IEEE80211_NODE_SAVEQ_LOCK(ni);
-	if (_IF_QFULL(&ni->ni_savedq)) {
-		_IF_DROP(&ni->ni_savedq);
-		IEEE80211_NODE_SAVEQ_UNLOCK(ni);
-		IEEE80211_NOTE(vap, IEEE80211_MSG_ANY, ni,
-		    "pwr save q overflow, drops %d (size %d)",
-		    ni->ni_savedq.ifq_drops, IEEE80211_PS_MAX_QUEUE);
-#ifdef IEEE80211_DEBUG
-		if (ieee80211_msg_dumppkts(vap))
-			ieee80211_dump_pkt(ni->ni_ic, mtod(m, caddr_t), m->m_len, -1, -1);
-#endif
-		m_freem(m);
-		return;
-	}
-	/*
-	 * Tag the frame with it's expiry time and insert
-	 * it in the queue.  The aging interval is 4 times
-	 * the listen interval specified by the station. 
-	 * Frames that sit around too long are reclaimed
-	 * using this information.
-	 */
-	/* XXX handle overflow? */
-	/* XXX per/vap beacon interval? */
-	age = ((ni->ni_intval * ic->ic_lintval) << 2) / 1024; /* TU -> secs */
-	_IEEE80211_NODE_SAVEQ_ENQUEUE(ni, m, qlen, age);
-	IEEE80211_NODE_SAVEQ_UNLOCK(ni);
-
-	IEEE80211_NOTE(vap, IEEE80211_MSG_POWER, ni,
-	    "save frame, %u now queued", qlen);
-
-	if (qlen == 1 && vap->iv_set_tim != NULL)
-		vap->iv_set_tim(ni, 1);
-}

==== //depot/projects/vap/sys/net80211/ieee80211_proto.h#6 (text+ko) ====

@@ -71,7 +71,6 @@
 void	ieee80211_saveath(struct ieee80211_node *, u_int8_t *);
 void	ieee80211_recv_mgmt(struct ieee80211_node *, struct mbuf *,
 		int, int, u_int32_t);
-void	ieee80211_sta_pwrsave(struct ieee80211vap *, int enable);
 void	ieee80211_start(struct ifnet *);
 int	ieee80211_send_nulldata(struct ieee80211_node *);
 int	ieee80211_send_probereq(struct ieee80211_node *,
@@ -82,7 +81,6 @@
 		const void *optie, size_t optielen);
 int	ieee80211_send_mgmt(struct ieee80211_node *, int, int);
 struct mbuf *ieee80211_encap(struct ieee80211_node *, struct mbuf *);
-void	ieee80211_pwrsave(struct ieee80211_node *, struct mbuf *);
 
 void	ieee80211_reset_erp(struct ieee80211com *, enum ieee80211_phymode);
 void	ieee80211_set_shortslottime(struct ieee80211com *, int onoff);

==== //depot/projects/vap/sys/net80211/ieee80211_scan.c#6 (text+ko) ====

@@ -62,6 +62,14 @@
 
 static void scan_next(void *arg);
 
+#include <sys/sysctl.h>
+static int bgscandelay = 1;			/* default 1ms */
+SYSCTL_INT(_net_wlan, OID_AUTO, bgscandelay, CTLFLAG_RW, &bgscandelay,
+	    0, "bg scan pwr sav delay (ms)");
+static int beaconswitch = 10;			/* default 10ms */
+SYSCTL_INT(_net_wlan, OID_AUTO, beaconswitch, CTLFLAG_RW, &beaconswitch,
+	    0, "beacon switch time (ms)");
+
 MALLOC_DEFINE(M_80211_SCAN, "80211scan", "802.11 scan state");
 
 void
@@ -239,12 +247,12 @@
 		if ((vap->iv_bss->ni_flags & IEEE80211_NODE_PWR_MGT) == 0) {
 			/*
 			 * Initiate power save before going off-channel.
-			 * Use an initial 1ms delay to insure the null
+			 * Use an initial tunable delay to insure the null
 			 * data frame has a chance to go out.
 			 * XXX bogus, need to trigger on on tx complete.
 			 */
 			ieee80211_sta_pwrsave(vap, 1);
-			delay = hz/1000;
+			delay = bgscandelay*hz/1000;
 			if (delay < 1)
 				delay = 1;
 		}
@@ -399,8 +407,8 @@
 		 * or (more likely) arrange to start at the next beacon.
 		 */
 		duration = IEEE80211_TU_TO_TICKS(vap->iv_bss->ni_intval);
-		fudge = hz/1000;
-		if (fudge == 0)
+		fudge = beaconswitch*hz/1000;
+		if (fudge < 1)
 			fudge = 1;
 		if (duration > fudge)
 			duration -= fudge;
@@ -644,71 +652,6 @@
 	}
 }
 
-/*
- * Test a scan candidate for suitability/compatibility.
- */
-int
-ieee80211_match_bss(struct ieee80211vap *vap, struct ieee80211_node *ni)
-{
-	struct ieee80211com *ic = ni->ni_ic;
-        u_int8_t rate;
-        int fail;
-
-	fail = 0;
-	if (isclr(ic->ic_chan_active, ieee80211_chan2ieee(ic, ni->ni_chan)))
-		fail |= 0x01;
-	if (vap->iv_opmode == IEEE80211_M_IBSS) {
-		if ((ni->ni_capinfo & IEEE80211_CAPINFO_IBSS) == 0)
-			fail |= 0x02;
-	} else {
-		if ((ni->ni_capinfo & IEEE80211_CAPINFO_ESS) == 0)
-			fail |= 0x02;
-	}
-	if (vap->iv_flags & IEEE80211_F_PRIVACY) {
-		if ((ni->ni_capinfo & IEEE80211_CAPINFO_PRIVACY) == 0)
-			fail |= 0x04;
-	} else {
-		/* XXX does this mean privacy is supported or required? */
-		if (ni->ni_capinfo & IEEE80211_CAPINFO_PRIVACY)
-			fail |= 0x04;
-	}
-	rate = ieee80211_fix_rate(ni, IEEE80211_F_DONEGO | IEEE80211_F_DOFRATE);
-	if (rate & IEEE80211_RATE_BASIC)
-		fail |= 0x08;
-	if (vap->iv_des_esslen != 0 &&
-	    (ni->ni_esslen != vap->iv_des_esslen ||
-	     memcmp(ni->ni_essid, vap->iv_des_essid, vap->iv_des_esslen) != 0))
-		fail |= 0x10;
-	if ((vap->iv_flags & IEEE80211_F_DESBSSID) &&
-	    !IEEE80211_ADDR_EQ(vap->iv_des_bssid, ni->ni_bssid))
-		fail |= 0x20;
-#ifdef IEEE80211_DEBUG
-	if (ieee80211_msg_scan(vap)) {
-		printf(" %c %s", fail ? '-' : '+',
-		    ether_sprintf(ni->ni_macaddr));
-		printf(" %s%c", ether_sprintf(ni->ni_bssid),
-		    fail & 0x20 ? '!' : ' ');
-		printf(" %3d%c", ieee80211_chan2ieee(ic, ni->ni_chan),
-			fail & 0x01 ? '!' : ' ');
-		printf(" %+4d", ni->ni_rssi);
-		printf(" %2dM%c", (rate & IEEE80211_RATE_VAL) / 2,
-		    fail & 0x08 ? '!' : ' ');
-		printf(" %4s%c",
-		    (ni->ni_capinfo & IEEE80211_CAPINFO_ESS) ? "ess" :
-		    (ni->ni_capinfo & IEEE80211_CAPINFO_IBSS) ? "ibss" :
-		    "????",
-		    fail & 0x02 ? '!' : ' ');
-		printf(" %3s%c ",
-		    (ni->ni_capinfo & IEEE80211_CAPINFO_PRIVACY) ?
-		    "wep" : "no",
-		    fail & 0x04 ? '!' : ' ');
-		ieee80211_print_essid(ni->ni_essid, ni->ni_esslen);
-		printf("%s\n", fail & 0x10 ? "!" : "");
-	}
-#endif
-	return fail;
-}
-
 #ifdef IEEE80211_DEBUG
 static void
 dump_probe_beacon(u_int8_t subtype, int isnew,

==== //depot/projects/vap/sys/net80211/ieee80211_scan.h#4 (text+ko) ====

@@ -87,8 +87,6 @@
 int	ieee80211_check_scan(struct ieee80211vap *, int flags, u_int duration);
 void	ieee80211_cancel_scan(struct ieee80211vap *);
 
-int	ieee80211_match_bss(struct ieee80211vap *, struct ieee80211_node *);
-
 struct ieee80211_scanparams;
 void	ieee80211_add_scan(struct ieee80211vap *,
 		const struct ieee80211_scanparams *,

==== //depot/projects/vap/sys/net80211/ieee80211_var.h#15 (text+ko) ====

@@ -56,6 +56,7 @@
 #include <net80211/ieee80211_crypto.h>
 #include <net80211/ieee80211_ioctl.h>		/* for ieee80211_stats */
 #include <net80211/ieee80211_node.h>
+#include <net80211/ieee80211_power.h>
 #include <net80211/ieee80211_proto.h>
 #include <net80211/ieee80211_scan.h>
 
@@ -502,6 +503,8 @@
 	((_vap)->iv_debug & IEEE80211_MSG_RADKEYS)
 #define	ieee80211_msg_scan(_vap) \
 	((_vap)->iv_debug & IEEE80211_MSG_SCAN)
+#define	ieee80211_msg_assoc(_vap) \
+	((_vap)->iv_debug & IEEE80211_MSG_ASSOC)
 #else
 #define	IEEE80211_DPRINTF(_vap, _m, _fmt, ...)
 #define	IEEE80211_NOTE_FRAME(_vap, _m, _wh, _fmt, ...)


More information about the p4-projects mailing list