|
@@ -38,6 +38,19 @@
|
|
|
static void wpa_bss_remove(struct wpa_supplicant *wpa_s, struct wpa_bss *bss,
|
|
|
const char *reason)
|
|
|
{
|
|
|
+ if (wpa_s->last_scan_res) {
|
|
|
+ unsigned int i;
|
|
|
+ for (i = 0; i < wpa_s->last_scan_res_used; i++) {
|
|
|
+ if (wpa_s->last_scan_res[i] == bss) {
|
|
|
+ os_memmove(&wpa_s->last_scan_res[i],
|
|
|
+ &wpa_s->last_scan_res[i + 1],
|
|
|
+ (wpa_s->last_scan_res_used - i - 1)
|
|
|
+ * sizeof(struct wpa_bss *));
|
|
|
+ wpa_s->last_scan_res_used--;
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
dl_list_del(&bss->list);
|
|
|
dl_list_del(&bss->list_id);
|
|
|
wpa_s->num_bss--;
|
|
@@ -169,15 +182,15 @@ static int wpa_bss_remove_oldest(struct wpa_supplicant *wpa_s)
|
|
|
}
|
|
|
|
|
|
|
|
|
-static void wpa_bss_add(struct wpa_supplicant *wpa_s,
|
|
|
- const u8 *ssid, size_t ssid_len,
|
|
|
- struct wpa_scan_res *res)
|
|
|
+static struct wpa_bss * wpa_bss_add(struct wpa_supplicant *wpa_s,
|
|
|
+ const u8 *ssid, size_t ssid_len,
|
|
|
+ struct wpa_scan_res *res)
|
|
|
{
|
|
|
struct wpa_bss *bss;
|
|
|
|
|
|
bss = os_zalloc(sizeof(*bss) + res->ie_len + res->beacon_ie_len);
|
|
|
if (bss == NULL)
|
|
|
- return;
|
|
|
+ return NULL;
|
|
|
bss->id = wpa_s->bss_next_id++;
|
|
|
bss->last_update_idx = wpa_s->bss_update_idx;
|
|
|
wpa_bss_copy_res(bss, res);
|
|
@@ -201,6 +214,7 @@ static void wpa_bss_add(struct wpa_supplicant *wpa_s,
|
|
|
"not get here!", (int) wpa_s->num_bss);
|
|
|
wpa_s->conf->bss_max_count = wpa_s->num_bss;
|
|
|
}
|
|
|
+ return bss;
|
|
|
}
|
|
|
|
|
|
|
|
@@ -376,6 +390,7 @@ void wpa_bss_update_start(struct wpa_supplicant *wpa_s)
|
|
|
wpa_s->bss_update_idx++;
|
|
|
wpa_dbg(wpa_s, MSG_DEBUG, "BSS: Start scan result update %u",
|
|
|
wpa_s->bss_update_idx);
|
|
|
+ wpa_s->last_scan_res_used = 0;
|
|
|
}
|
|
|
|
|
|
|
|
@@ -418,9 +433,28 @@ void wpa_bss_update_scan_res(struct wpa_supplicant *wpa_s,
|
|
|
* (to save memory) */
|
|
|
bss = wpa_bss_get(wpa_s, res->bssid, ssid + 2, ssid[1]);
|
|
|
if (bss == NULL)
|
|
|
- wpa_bss_add(wpa_s, ssid + 2, ssid[1], res);
|
|
|
+ bss = wpa_bss_add(wpa_s, ssid + 2, ssid[1], res);
|
|
|
else
|
|
|
wpa_bss_update(wpa_s, bss, res);
|
|
|
+
|
|
|
+ if (bss == NULL)
|
|
|
+ return;
|
|
|
+ if (wpa_s->last_scan_res_used >= wpa_s->last_scan_res_size) {
|
|
|
+ struct wpa_bss **n;
|
|
|
+ unsigned int siz;
|
|
|
+ if (wpa_s->last_scan_res_size == 0)
|
|
|
+ siz = 32;
|
|
|
+ else
|
|
|
+ siz = wpa_s->last_scan_res_size * 2;
|
|
|
+ n = os_realloc_array(wpa_s->last_scan_res, siz,
|
|
|
+ sizeof(struct wpa_bss *));
|
|
|
+ if (n == NULL)
|
|
|
+ return;
|
|
|
+ wpa_s->last_scan_res = n;
|
|
|
+ wpa_s->last_scan_res_size = siz;
|
|
|
+ }
|
|
|
+
|
|
|
+ wpa_s->last_scan_res[wpa_s->last_scan_res_used++] = bss;
|
|
|
}
|
|
|
|
|
|
|
|
@@ -470,9 +504,26 @@ void wpa_bss_update_end(struct wpa_supplicant *wpa_s, struct scan_info *info,
|
|
|
{
|
|
|
struct wpa_bss *bss, *n;
|
|
|
|
|
|
+ wpa_s->last_scan_full = 0;
|
|
|
+ os_get_time(&wpa_s->last_scan);
|
|
|
if (!new_scan)
|
|
|
return; /* do not expire entries without new scan */
|
|
|
|
|
|
+ if (info && !info->aborted && !info->freqs) {
|
|
|
+ size_t i;
|
|
|
+ if (info->num_ssids == 0) {
|
|
|
+ wpa_s->last_scan_full = 1;
|
|
|
+ } else {
|
|
|
+ for (i = 0; i < info->num_ssids; i++) {
|
|
|
+ if (info->ssids[i].ssid == NULL ||
|
|
|
+ info->ssids[i].ssid_len == 0) {
|
|
|
+ wpa_s->last_scan_full = 1;
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
dl_list_for_each_safe(bss, n, &wpa_s->bss, struct wpa_bss, list) {
|
|
|
if (wpa_bss_in_use(wpa_s, bss))
|
|
|
continue;
|
|
@@ -485,6 +536,11 @@ void wpa_bss_update_end(struct wpa_supplicant *wpa_s, struct scan_info *info,
|
|
|
wpa_bss_remove(wpa_s, bss, "no match in scan");
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+ wpa_printf(MSG_DEBUG, "BSS: last_scan_res_used=%u/%u "
|
|
|
+ "last_scan_full=%d",
|
|
|
+ wpa_s->last_scan_res_used, wpa_s->last_scan_res_size,
|
|
|
+ wpa_s->last_scan_full);
|
|
|
}
|
|
|
|
|
|
|