PERFORCE change 77144 for review

Sam Leffler sam at FreeBSD.org
Wed May 18 13:23:59 PDT 2005


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

Change 77144 by sam at sam_ebb on 2005/05/18 20:23:41

	Add simple cache management:
	o ignore scan cache entries where we've failed to associate
	  (if the entry remains in the cache reset it's failure count
	  after a period of time so it can be retried)
	o purge stale scan cache entries
	
	This makes us ready to add roaming now that the cache is kept
	warm with background scanning.

Affected files ...

.. //depot/projects/vap/sys/net80211/ieee80211_scan_sta.c#4 edit

Differences ...

==== //depot/projects/vap/sys/net80211/ieee80211_scan_sta.c#4 (text+ko) ====

@@ -51,6 +51,19 @@
 
 #include <net80211/ieee80211_var.h>
 
+/*
+ * Parameters for managing cache entries:
+ *
+ * o a station with STA_FAILS_MAX failures is not considered
+ *   when picking a candidate
+ * o a station that hasn't had an update in STA_PURGE_SCANS
+ *   (background) scans is discarded
+ * o after STA_FAILS_AGE seconds we clear the failure count
+ */
+#define	STA_FAILS_MAX	2		/* assoc failures before purge */
+#define	STA_FAILS_AGE	(2*60)		/* time before clearing fails (secs) */
+#define	STA_PURGE_SCANS	2		/* age for purging entries (scans) */
+
 #define RSSI_LPF_LEN	10
 #define	RSSI_EP_MULTIPLIER	(1<<7)	/* pow2 to optimize out * and / */
 #define RSSI_IN(x)		((x) * RSSI_EP_MULTIPLIER)
@@ -70,6 +83,7 @@
 	u_int8_t	se_fails;		/* failure to associate count */
 	u_int32_t	se_avgrssi;		/* LPF rssi state */
 	u_int32_t	se_lastupdate;		/* time of last update */
+	u_int32_t	se_lastfail;		/* time of last failure */
 	u_int		se_scangen;		/* iterator scan gen# */
 };
 
@@ -84,11 +98,10 @@
 	LIST_HEAD(, sta_entry) st_hash[STA_HASHSIZE];
 	struct mtx	st_scanlock;		/* on st_scangen */
 	u_int		st_scangen;		/* gen# for iterator */
-	int		st_inact;		/* inactivity setting */
 };
 
 static void sta_flush_table(struct sta_table *);
-static int match_bss(struct ieee80211vap *, struct ieee80211_scan_entry *);
+static int match_bss(struct ieee80211vap *, const struct sta_entry *);
 
 /*
  * Attach prior to any scanning work.
@@ -105,7 +118,6 @@
 	mtx_init(&st->st_lock, "stacache", "802.11 sta scan cache", MTX_DEF);
 	mtx_init(&st->st_scanlock, "stascan", "802.11 sta scangen", MTX_DEF);
 	TAILQ_INIT(&st->st_entry);
-	st->st_inact = IEEE80211_INACT_SCAN;
 	ss->ss_priv = st;
 	return 1;
 }
@@ -237,6 +249,10 @@
 	saveie(&ise->se_wpa_ie, sp->wpa);
 	saveie(&ise->se_ath_ie, sp->ath);
 
+	/* clear failure count after STA_FAIL_AGE passes */
+	if (se->se_fails && (ticks - se->se_lastfail) > STA_FAILS_AGE*hz)
+		se->se_fails = 0;
+
 	se->se_lastupdate = ticks;		/* update time */
 
 	mtx_unlock(&st->st_lock);
@@ -602,9 +618,10 @@
  * Test a scan candidate for suitability/compatibility.
  */
 static int
-match_bss(struct ieee80211vap *vap, struct ieee80211_scan_entry *se)
+match_bss(struct ieee80211vap *vap, const struct sta_entry *se0)
 {
 	struct ieee80211com *ic = vap->iv_ic;
+	const struct ieee80211_scan_entry *se = &se0->base;
         u_int8_t rate;
         int fail;
 
@@ -636,8 +653,11 @@
 	if ((vap->iv_flags & IEEE80211_F_DESBSSID) &&
 	    !IEEE80211_ADDR_EQ(vap->iv_des_bssid, se->se_bssid))
 		fail |= 0x20;
+	if (se0->se_fails >= STA_FAILS_MAX)
+		fail |= 0x40;
 #ifdef IEEE80211_DEBUG
 	if (ieee80211_msg_scan(vap)) {
+		/* XXX se_fails */
 		printf(" %c %s", fail ? '-' : '+',
 		    ether_sprintf(se->se_macaddr));
 		printf(" %s%c", ether_sprintf(se->se_bssid),
@@ -717,7 +737,7 @@
 	TAILQ_FOREACH(se, &st->st_entry, se_list) {
 		/* update avg rssi */
 		se->base.se_rssi = RSSI_GET(se->se_avgrssi);
-		if (match_bss(vap, &se->base) == 0) {
+		if (match_bss(vap, se) == 0) {
 			if (selbs == NULL)
 				selbs = se;
 			else if (sta_compare(se, selbs) > 0)
@@ -737,11 +757,18 @@
 sta_age(struct ieee80211_scan_state *ss)
 {
 	struct sta_table *st = ss->ss_priv;
-	struct sta_entry *se;
+	struct sta_entry *se, *next;
+	u_int32_t droptime;
+
+	droptime = ticks - (STA_PURGE_SCANS * ss->ss_vap->iv_bgscanintvl);
 
 	mtx_lock(&st->st_lock);
-	TAILQ_FOREACH(se, &st->st_entry, se_list) {
-		/* XXX */
+	TAILQ_FOREACH_SAFE(se, &st->st_entry, se_list, next) {
+		if (time_before(se->se_lastupdate, droptime)) {
+			TAILQ_REMOVE(&st->st_entry, se, se_list);
+			LIST_REMOVE(se, se_hash);
+			FREE(se, M_80211_SCAN);
+		}
 	}
 	mtx_unlock(&st->st_lock);
 }
@@ -792,6 +819,7 @@
 	LIST_FOREACH(se, &st->st_hash[hash], se_hash)
 		if (IEEE80211_ADDR_EQ(se->base.se_macaddr, macaddr)) {
 			se->se_fails++;
+			se->se_lastfail = ticks;
 			break;
 		}
 	mtx_unlock(&st->st_lock);


More information about the p4-projects mailing list