Maintain BSS entries for 5 seconds after interface is disabled
This is targeting the case of MAC address change for an association which may require the interface to be set down for a short moment. Previously, this ended up flushing the BSS table that wpa_supplicant maintained and that resulted in having to scan again if the MAC address was changed between the previous scan and the connection attempt. This is unnecessary extra latency, so maintain the BSS entries for 5 seconds (i.e., the same time that the old scan results are consider valid for a new connection attempt) after an interface goes down. Signed-off-by: Jouni Malinen <j@w1.fi>
This commit is contained in:
parent
988f14448a
commit
ad2f096609
3 changed files with 35 additions and 2 deletions
|
@ -2253,7 +2253,8 @@ int wpa_supplicant_fast_associate(struct wpa_supplicant *wpa_s)
|
|||
return -1;
|
||||
|
||||
os_get_reltime(&now);
|
||||
if (os_reltime_expired(&now, &wpa_s->last_scan, 5)) {
|
||||
if (os_reltime_expired(&now, &wpa_s->last_scan,
|
||||
SCAN_RES_VALID_FOR_CONNECT)) {
|
||||
wpa_printf(MSG_DEBUG, "Fast associate: Old scan results");
|
||||
return -1;
|
||||
}
|
||||
|
@ -4321,6 +4322,7 @@ void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
|
|||
{
|
||||
struct wpa_supplicant *wpa_s = ctx;
|
||||
int resched;
|
||||
struct os_reltime age, clear_at;
|
||||
#ifndef CONFIG_NO_STDOUT_DEBUG
|
||||
int level = MSG_DEBUG;
|
||||
#endif /* CONFIG_NO_STDOUT_DEBUG */
|
||||
|
@ -4859,6 +4861,8 @@ void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
|
|||
case EVENT_INTERFACE_ENABLED:
|
||||
wpa_dbg(wpa_s, MSG_DEBUG, "Interface was enabled");
|
||||
if (wpa_s->wpa_state == WPA_INTERFACE_DISABLED) {
|
||||
eloop_cancel_timeout(wpas_clear_disabled_interface,
|
||||
wpa_s, NULL);
|
||||
wpa_supplicant_update_mac_addr(wpa_s);
|
||||
wpa_supplicant_set_default_scan_ies(wpa_s);
|
||||
if (wpa_s->p2p_mgmt) {
|
||||
|
@ -4927,7 +4931,20 @@ void wpa_supplicant_event(void *ctx, enum wpa_event_type event,
|
|||
wpa_s, WLAN_REASON_DEAUTH_LEAVING, 1);
|
||||
}
|
||||
wpa_supplicant_mark_disassoc(wpa_s);
|
||||
wpa_bss_flush(wpa_s);
|
||||
os_reltime_age(&wpa_s->last_scan, &age);
|
||||
if (age.sec >= SCAN_RES_VALID_FOR_CONNECT) {
|
||||
clear_at.sec = SCAN_RES_VALID_FOR_CONNECT;
|
||||
clear_at.usec = 0;
|
||||
} else {
|
||||
struct os_reltime tmp;
|
||||
|
||||
tmp.sec = SCAN_RES_VALID_FOR_CONNECT;
|
||||
tmp.usec = 0;
|
||||
os_reltime_sub(&tmp, &age, &clear_at);
|
||||
}
|
||||
eloop_register_timeout(clear_at.sec, clear_at.usec,
|
||||
wpas_clear_disabled_interface,
|
||||
wpa_s, NULL);
|
||||
radio_remove_works(wpa_s, NULL, 0);
|
||||
|
||||
wpa_supplicant_set_state(wpa_s, WPA_INTERFACE_DISABLED);
|
||||
|
|
|
@ -476,6 +476,17 @@ void wpas_flush_fils_hlp_req(struct wpa_supplicant *wpa_s)
|
|||
}
|
||||
|
||||
|
||||
void wpas_clear_disabled_interface(void *eloop_ctx, void *timeout_ctx)
|
||||
{
|
||||
struct wpa_supplicant *wpa_s = eloop_ctx;
|
||||
|
||||
if (wpa_s->wpa_state != WPA_INTERFACE_DISABLED)
|
||||
return;
|
||||
wpa_dbg(wpa_s, MSG_DEBUG, "Clear cached state on disabled interface");
|
||||
wpa_bss_flush(wpa_s);
|
||||
}
|
||||
|
||||
|
||||
static void wpa_supplicant_cleanup(struct wpa_supplicant *wpa_s)
|
||||
{
|
||||
int i;
|
||||
|
@ -551,6 +562,7 @@ static void wpa_supplicant_cleanup(struct wpa_supplicant *wpa_s)
|
|||
#endif /* CONFIG_DELAYED_MIC_ERROR_REPORT */
|
||||
|
||||
eloop_cancel_timeout(wpas_network_reenabled, wpa_s, NULL);
|
||||
eloop_cancel_timeout(wpas_clear_disabled_interface, wpa_s, NULL);
|
||||
|
||||
wpas_wps_deinit(wpa_s);
|
||||
|
||||
|
|
|
@ -47,6 +47,9 @@ struct ctrl_iface_global_priv;
|
|||
struct wpas_dbus_priv;
|
||||
struct wpas_binder_priv;
|
||||
|
||||
/* How many seconds to consider old scan results valid for association. */
|
||||
#define SCAN_RES_VALID_FOR_CONNECT 5
|
||||
|
||||
/**
|
||||
* struct wpa_interface - Parameters for wpa_supplicant_add_iface()
|
||||
*/
|
||||
|
@ -1399,6 +1402,7 @@ int wpas_beacon_rep_scan_process(struct wpa_supplicant *wpa_s,
|
|||
struct scan_info *info);
|
||||
void wpas_clear_beacon_rep_data(struct wpa_supplicant *wpa_s);
|
||||
void wpas_flush_fils_hlp_req(struct wpa_supplicant *wpa_s);
|
||||
void wpas_clear_disabled_interface(void *eloop_ctx, void *timeout_ctx);
|
||||
|
||||
|
||||
/* MBO functions */
|
||||
|
|
Loading…
Reference in a new issue