[PATCH] roaming: start a scan if the SNR is below customized threshold

Holger Schurig hs4233 at mail.mn-solutions.de
Tue Sep 15 02:42:33 EDT 2009


Scanning is all what's needed, because wpa_supplicant already has logic
to sort the scan result by quality and tries to associate to the top-most
matching AP.

Signed-off-by: Holger Schurig <hs4233 at mail.mn-solutions.de>


Index: hostap/wpa_supplicant/roam.h
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ hostap/wpa_supplicant/roam.h	2009-09-14 14:08:51.000000000 +0200
@@ -0,0 +1,25 @@
+/*
+ * WPA Supplicant - Automatic roaming support
+ * Copyright (c) 2009 Holger Schurig
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ * Alternatively, this software may be distributed under the terms of BSD
+ * license.
+ *
+ * See README and COPYING for more details.
+ */
+
+#ifndef ROAM_H
+#define ROAM_H
+
+struct wpa_supplicant;
+
+#ifdef CONFIG_ROAM
+
+void roam_do_checks(struct wpa_supplicant *wpa_s, int connected);
+
+#endif /* CONFIG_ROAM */
+#endif
Index: hostap/wpa_supplicant/Makefile
===================================================================
--- hostap.orig/wpa_supplicant/Makefile	2009-09-14 13:50:29.000000000 +0200
+++ hostap/wpa_supplicant/Makefile	2009-09-14 14:08:51.000000000 +0200
@@ -1005,6 +1005,11 @@ CFLAGS += -DCONFIG_CLIENT_MLME
 NEED_80211_COMMON=y
 endif
 
+ifdef CONFIG_ROAM
+CFLAGS += -DCONFIG_ROAM
+OBJS += roam.o
+endif
+
 ifdef NEED_80211_COMMON
 OBJS += ../src/common/ieee802_11_common.o
 endif
Index: hostap/wpa_supplicant/roam.c
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ hostap/wpa_supplicant/roam.c	2009-09-14 14:14:10.000000000 +0200
@@ -0,0 +1,60 @@
+/*
+ * WPA Supplicant - Automatic roaming support
+ * Copyright (c) 2009 Holger Schurig
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ * Alternatively, this software may be distributed under the terms of BSD
+ * license.
+ *
+ * See README and COPYING for more details.
+ */
+
+#include "includes.h"
+
+#include "common.h"
+#include "eloop.h"
+#include "config_ssid.h"
+#include "wpa_supplicant_i.h"
+#include "driver_i.h"
+#include "roam.h"
+
+
+static void roam_check_snr(void *eloop_ctx, void *timeout_ctx)
+{
+	struct wpa_supplicant *wpa_s = eloop_ctx;
+
+	int sec  = wpa_s->current_ssid->roam_check_ms / 1000;
+	int usec = (wpa_s->current_ssid->roam_check_ms % 1000) * 1000;
+	int snr  =  wpa_drv_get_snr(wpa_s);
+	wpa_printf(MSG_DEBUG, "ROAM: SNR %d, roam_snr %d", snr, wpa_s->current_ssid->roam_snr);
+
+	if (snr != -1 &&
+	    // Scan if we have a SNR threshold defined
+	    snr < wpa_s->current_ssid->roam_snr)
+	    // only scan if the last scan isn't valid anymore
+	{
+		wpa_printf(MSG_ERROR, "ROAM: snr %d, search for a better AP", snr);
+		wpa_s->scan_req = 2;
+		//wpa_s->reassociate = 1;
+		wpa_supplicant_req_scan(wpa_s, 0, 1);
+	}
+
+	/* Schedule next check */
+	eloop_cancel_timeout(roam_check_snr, wpa_s, NULL);
+	eloop_register_timeout(sec, usec, roam_check_snr, wpa_s, NULL);
+}
+
+
+void roam_do_checks(struct wpa_supplicant *wpa_s, int connected)
+{
+	//wpa_printf(MSG_ERROR, "ROAM: connected %d", connected);
+
+	eloop_cancel_timeout(roam_check_snr, wpa_s, NULL);
+
+	if (connected && wpa_s->current_ssid->roam_snr > 0)
+		eloop_register_timeout(0, 100, roam_check_snr, wpa_s, NULL);
+}
+
Index: hostap/wpa_supplicant/wpa_supplicant.c
===================================================================
--- hostap.orig/wpa_supplicant/wpa_supplicant.c	2009-09-14 14:08:36.000000000 +0200
+++ hostap/wpa_supplicant/wpa_supplicant.c	2009-09-14 14:08:51.000000000 +0200
@@ -36,6 +36,7 @@
 #include "pmksa_cache.h"
 #include "wpa_ctrl.h"
 #include "mlme.h"
+#include "roam.h"
 #include "ieee802_11_defs.h"
 #include "blacklist.h"
 #include "wpas_glue.h"
@@ -520,6 +521,7 @@ void wpa_supplicant_set_state(struct wpa
 
 	wpas_notify_state_changed(wpa_s, state, wpa_s->wpa_state);
 
+	roam_do_checks(wpa_s, state == WPA_COMPLETED);
 	if (state == WPA_COMPLETED && wpa_s->new_connection) {
 #if defined(CONFIG_CTRL_IFACE) || !defined(CONFIG_NO_STDOUT_DEBUG)
 		struct wpa_ssid *ssid = wpa_s->current_ssid;
Index: hostap/wpa_supplicant/config_ssid.h
===================================================================
--- hostap.orig/wpa_supplicant/config_ssid.h	2009-09-14 13:50:29.000000000 +0200
+++ hostap/wpa_supplicant/config_ssid.h	2009-09-14 14:08:51.000000000 +0200
@@ -350,6 +350,19 @@ struct wpa_ssid {
 	 * known to not use all possible channels.
 	 */
 	int *scan_freq;
+
+#ifdef CONFIG_ROAM
+	/**
+	 * roam_snr - When to scan for a better AP
+	 */
+	int roam_snr;
+
+	/**
+	 * roam_check_ms - After how many milliseconds should we check the
+	 * SNR
+	 */
+	int roam_check_ms;
+#endif /* CONFIG_ROAM */
 };
 
 #endif /* CONFIG_SSID_H */
Index: hostap/wpa_supplicant/config.c
===================================================================
--- hostap.orig/wpa_supplicant/config.c	2009-09-14 13:50:29.000000000 +0200
+++ hostap/wpa_supplicant/config.c	2009-09-14 14:08:51.000000000 +0200
@@ -1399,6 +1399,10 @@ static const struct parse_data ssid_fiel
 	{ FUNC(group) },
 	{ FUNC(auth_alg) },
 	{ FUNC(scan_freq) },
+#ifdef CONFIG_ROAM
+	{ INT_RANGE(roam_snr, 5, 80) },
+	{ INT_RANGE(roam_check_ms, 100,60000) },
+#endif /* CONFIG_ROAM */
 #ifdef IEEE8021X_EAPOL
 	{ FUNC(eap) },
 	{ STR_LENe(identity) },
@@ -1779,6 +1783,10 @@ void wpa_config_set_network_defaults(str
 	ssid->eap_workaround = DEFAULT_EAP_WORKAROUND;
 	ssid->eap.fragment_size = DEFAULT_FRAGMENT_SIZE;
 #endif /* IEEE8021X_EAPOL */
+#ifdef CONFIG_ROAM
+	ssid->roam_snr = -1;
+	ssid->roam_check_ms = 2000;
+#endif /* CONFIG_ROAM */
 }
 
 

-- 
http://www.holgerschurig.de


More information about the HostAP mailing list