1 /* 2 * WPA Supplicant - Scanning 3 * Copyright (c) 2003-2010, Jouni Malinen <j (at) w1.fi> 4 * 5 * This software may be distributed under the terms of the BSD license. 6 * See README for more details. 7 */ 8 9 #include "utils/includes.h" 10 11 #include "utils/common.h" 12 #include "utils/eloop.h" 13 #include "common/ieee802_11_defs.h" 14 #include "config.h" 15 #include "wpa_supplicant_i.h" 16 #include "driver_i.h" 17 #include "wps_supplicant.h" 18 #include "p2p_supplicant.h" 19 #include "p2p/p2p.h" 20 #include "notify.h" 21 #include "bss.h" 22 #include "scan.h" 23 24 25 static void wpa_supplicant_gen_assoc_event(struct wpa_supplicant *wpa_s) 26 { 27 struct wpa_ssid *ssid; 28 union wpa_event_data data; 29 30 ssid = wpa_supplicant_get_ssid(wpa_s); 31 if (ssid == NULL) 32 return; 33 34 if (wpa_s->current_ssid == NULL) { 35 wpa_s->current_ssid = ssid; 36 if (wpa_s->current_ssid != NULL) 37 wpas_notify_network_changed(wpa_s); 38 } 39 wpa_supplicant_initiate_eapol(wpa_s); 40 wpa_dbg(wpa_s, MSG_DEBUG, "Already associated with a configured " 41 "network - generating associated event"); 42 os_memset(&data, 0, sizeof(data)); 43 wpa_supplicant_event(wpa_s, EVENT_ASSOC, &data); 44 } 45 46 47 #ifdef CONFIG_WPS 48 static int wpas_wps_in_use(struct wpa_supplicant *wpa_s, 49 enum wps_request_type *req_type) 50 { 51 struct wpa_ssid *ssid; 52 int wps = 0; 53 54 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { 55 if (!(ssid->key_mgmt & WPA_KEY_MGMT_WPS)) 56 continue; 57 58 wps = 1; 59 *req_type = wpas_wps_get_req_type(ssid); 60 if (!ssid->eap.phase1) 61 continue; 62 63 if (os_strstr(ssid->eap.phase1, "pbc=1")) 64 return 2; 65 } 66 67 #ifdef CONFIG_P2P 68 if (!wpa_s->global->p2p_disabled && wpa_s->global->p2p) { 69 wpa_s->wps->dev.p2p = 1; 70 if (!wps) { 71 wps = 1; 72 *req_type = WPS_REQ_ENROLLEE_INFO; 73 } 74 } 75 #endif /* CONFIG_P2P */ 76 77 return wps; 78 } 79 #endif /* CONFIG_WPS */ 80 81 82 int wpa_supplicant_enabled_networks(struct wpa_config *conf) 83 { 84 struct wpa_ssid *ssid = conf->ssid; 85 int count = 0; 86 while (ssid) { 87 if (!ssid->disabled) 88 count++; 89 ssid = ssid->next; 90 } 91 return count; 92 } 93 94 95 static void wpa_supplicant_assoc_try(struct wpa_supplicant *wpa_s, 96 struct wpa_ssid *ssid) 97 { 98 while (ssid) { 99 if (!ssid->disabled) 100 break; 101 ssid = ssid->next; 102 } 103 104 /* ap_scan=2 mode - try to associate with each SSID. */ 105 if (ssid == NULL) { 106 wpa_dbg(wpa_s, MSG_DEBUG, "wpa_supplicant_assoc_try: Reached " 107 "end of scan list - go back to beginning"); 108 wpa_s->prev_scan_ssid = WILDCARD_SSID_SCAN; 109 wpa_supplicant_req_scan(wpa_s, 0, 0); 110 return; 111 } 112 if (ssid->next) { 113 /* Continue from the next SSID on the next attempt. */ 114 wpa_s->prev_scan_ssid = ssid; 115 } else { 116 /* Start from the beginning of the SSID list. */ 117 wpa_s->prev_scan_ssid = WILDCARD_SSID_SCAN; 118 } 119 wpa_supplicant_associate(wpa_s, NULL, ssid); 120 } 121 122 123 static int int_array_len(const int *a) 124 { 125 int i; 126 for (i = 0; a && a[i]; i++) 127 ; 128 return i; 129 } 130 131 132 static void int_array_concat(int **res, const int *a) 133 { 134 int reslen, alen, i; 135 int *n; 136 137 reslen = int_array_len(*res); 138 alen = int_array_len(a); 139 140 n = os_realloc(*res, (reslen + alen + 1) * sizeof(int)); 141 if (n == NULL) { 142 os_free(*res); 143 *res = NULL; 144 return; 145 } 146 for (i = 0; i <= alen; i++) 147 n[reslen + i] = a[i]; 148 *res = n; 149 } 150 151 152 static int freq_cmp(const void *a, const void *b) 153 { 154 int _a = *(int *) a; 155 int _b = *(int *) b; 156 157 if (_a == 0) 158 return 1; 159 if (_b == 0) 160 return -1; 161 return _a - _b; 162 } 163 164 165 static void int_array_sort_unique(int *a) 166 { 167 int alen; 168 int i, j; 169 170 if (a == NULL) 171 return; 172 173 alen = int_array_len(a); 174 qsort(a, alen, sizeof(int), freq_cmp); 175 176 i = 0; 177 j = 1; 178 while (a[i] && a[j]) { 179 if (a[i] == a[j]) { 180 j++; 181 continue; 182 } 183 a[++i] = a[j++]; 184 } 185 if (a[i]) 186 i++; 187 a[i] = 0; 188 } 189 190 191 int wpa_supplicant_trigger_scan(struct wpa_supplicant *wpa_s, 192 struct wpa_driver_scan_params *params) 193 { 194 int ret; 195 196 wpa_supplicant_notify_scanning(wpa_s, 1); 197 198 ret = wpa_drv_scan(wpa_s, params); 199 if (ret) { 200 wpa_supplicant_notify_scanning(wpa_s, 0); 201 wpas_notify_scan_done(wpa_s, 0); 202 } else { 203 wpa_s->scan_runs++; 204 wpa_s->normal_scans++; 205 } 206 207 return ret; 208 } 209 210 211 static void 212 wpa_supplicant_delayed_sched_scan_timeout(void *eloop_ctx, void *timeout_ctx) 213 { 214 struct wpa_supplicant *wpa_s = eloop_ctx; 215 216 wpa_dbg(wpa_s, MSG_DEBUG, "Starting delayed sched scan"); 217 218 if (wpa_supplicant_req_sched_scan(wpa_s)) 219 wpa_supplicant_req_scan(wpa_s, 0, 0); 220 } 221 222 223 static void 224 wpa_supplicant_sched_scan_timeout(void *eloop_ctx, void *timeout_ctx) 225 { 226 struct wpa_supplicant *wpa_s = eloop_ctx; 227 228 wpa_dbg(wpa_s, MSG_DEBUG, "Sched scan timeout - stopping it"); 229 230 wpa_s->sched_scan_timed_out = 1; 231 wpa_supplicant_cancel_sched_scan(wpa_s); 232 } 233 234 235 static int 236 wpa_supplicant_start_sched_scan(struct wpa_supplicant *wpa_s, 237 struct wpa_driver_scan_params *params, 238 int interval) 239 { 240 int ret; 241 #ifndef ANDROID_P2P 242 wpa_supplicant_notify_scanning(wpa_s, 1); 243 #endif 244 ret = wpa_drv_sched_scan(wpa_s, params, interval * 1000); 245 if (ret) 246 wpa_supplicant_notify_scanning(wpa_s, 0); 247 else { 248 wpa_s->sched_scanning = 1; 249 #ifdef ANDROID_P2P 250 wpa_supplicant_notify_scanning(wpa_s, 1); 251 #endif 252 } 253 254 return ret; 255 } 256 257 258 static int wpa_supplicant_stop_sched_scan(struct wpa_supplicant *wpa_s) 259 { 260 int ret; 261 262 ret = wpa_drv_stop_sched_scan(wpa_s); 263 if (ret) { 264 wpa_dbg(wpa_s, MSG_DEBUG, "stopping sched_scan failed!"); 265 /* TODO: what to do if stopping fails? */ 266 return -1; 267 } 268 269 return ret; 270 } 271 272 273 static struct wpa_driver_scan_filter * 274 wpa_supplicant_build_filter_ssids(struct wpa_config *conf, size_t *num_ssids) 275 { 276 struct wpa_driver_scan_filter *ssids; 277 struct wpa_ssid *ssid; 278 size_t count; 279 280 *num_ssids = 0; 281 if (!conf->filter_ssids) 282 return NULL; 283 284 for (count = 0, ssid = conf->ssid; ssid; ssid = ssid->next) { 285 if (ssid->ssid && ssid->ssid_len) 286 count++; 287 } 288 if (count == 0) 289 return NULL; 290 ssids = os_zalloc(count * sizeof(struct wpa_driver_scan_filter)); 291 if (ssids == NULL) 292 return NULL; 293 294 for (ssid = conf->ssid; ssid; ssid = ssid->next) { 295 if (!ssid->ssid || !ssid->ssid_len) 296 continue; 297 os_memcpy(ssids[*num_ssids].ssid, ssid->ssid, ssid->ssid_len); 298 ssids[*num_ssids].ssid_len = ssid->ssid_len; 299 (*num_ssids)++; 300 } 301 302 return ssids; 303 } 304 305 306 static void wpa_supplicant_optimize_freqs( 307 struct wpa_supplicant *wpa_s, struct wpa_driver_scan_params *params) 308 { 309 #ifdef CONFIG_P2P 310 if (params->freqs == NULL && wpa_s->p2p_in_provisioning && 311 wpa_s->go_params) { 312 /* Optimize provisioning state scan based on GO information */ 313 if (wpa_s->p2p_in_provisioning < 5 && 314 wpa_s->go_params->freq > 0) { 315 wpa_dbg(wpa_s, MSG_DEBUG, "P2P: Scan only GO " 316 "preferred frequency %d MHz", 317 wpa_s->go_params->freq); 318 params->freqs = os_zalloc(2 * sizeof(int)); 319 if (params->freqs) 320 params->freqs[0] = wpa_s->go_params->freq; 321 } else if (wpa_s->p2p_in_provisioning < 8 && 322 wpa_s->go_params->freq_list[0]) { 323 wpa_dbg(wpa_s, MSG_DEBUG, "P2P: Scan only common " 324 "channels"); 325 int_array_concat(¶ms->freqs, 326 wpa_s->go_params->freq_list); 327 if (params->freqs) 328 int_array_sort_unique(params->freqs); 329 } 330 wpa_s->p2p_in_provisioning++; 331 } 332 #endif /* CONFIG_P2P */ 333 334 #ifdef CONFIG_WPS 335 if (params->freqs == NULL && wpa_s->after_wps && wpa_s->wps_freq) { 336 /* 337 * Optimize post-provisioning scan based on channel used 338 * during provisioning. 339 */ 340 wpa_dbg(wpa_s, MSG_DEBUG, "WPS: Scan only frequency %u MHz " 341 "that was used during provisioning", wpa_s->wps_freq); 342 params->freqs = os_zalloc(2 * sizeof(int)); 343 if (params->freqs) 344 params->freqs[0] = wpa_s->wps_freq; 345 wpa_s->after_wps--; 346 } 347 348 if (params->freqs == NULL && wpa_s->known_wps_freq && wpa_s->wps_freq) 349 { 350 /* Optimize provisioning scan based on already known channel */ 351 wpa_dbg(wpa_s, MSG_DEBUG, "WPS: Scan only frequency %u MHz", 352 wpa_s->wps_freq); 353 params->freqs = os_zalloc(2 * sizeof(int)); 354 if (params->freqs) 355 params->freqs[0] = wpa_s->wps_freq; 356 wpa_s->known_wps_freq = 0; /* only do this once */ 357 } 358 #endif /* CONFIG_WPS */ 359 } 360 361 362 #ifdef CONFIG_INTERWORKING 363 static void wpas_add_interworking_elements(struct wpa_supplicant *wpa_s, 364 struct wpabuf *buf) 365 { 366 if (wpa_s->conf->interworking == 0) 367 return; 368 369 wpabuf_put_u8(buf, WLAN_EID_EXT_CAPAB); 370 wpabuf_put_u8(buf, 4); 371 wpabuf_put_u8(buf, 0x00); 372 wpabuf_put_u8(buf, 0x00); 373 wpabuf_put_u8(buf, 0x00); 374 wpabuf_put_u8(buf, 0x80); /* Bit 31 - Interworking */ 375 376 wpabuf_put_u8(buf, WLAN_EID_INTERWORKING); 377 wpabuf_put_u8(buf, is_zero_ether_addr(wpa_s->conf->hessid) ? 1 : 378 1 + ETH_ALEN); 379 wpabuf_put_u8(buf, wpa_s->conf->access_network_type); 380 /* No Venue Info */ 381 if (!is_zero_ether_addr(wpa_s->conf->hessid)) 382 wpabuf_put_data(buf, wpa_s->conf->hessid, ETH_ALEN); 383 } 384 #endif /* CONFIG_INTERWORKING */ 385 386 387 static struct wpabuf * 388 wpa_supplicant_extra_ies(struct wpa_supplicant *wpa_s, 389 struct wpa_driver_scan_params *params) 390 { 391 struct wpabuf *extra_ie = NULL; 392 #ifdef CONFIG_WPS 393 int wps = 0; 394 enum wps_request_type req_type = WPS_REQ_ENROLLEE_INFO; 395 #endif /* CONFIG_WPS */ 396 397 #ifdef CONFIG_INTERWORKING 398 if (wpa_s->conf->interworking && 399 wpabuf_resize(&extra_ie, 100) == 0) 400 wpas_add_interworking_elements(wpa_s, extra_ie); 401 #endif /* CONFIG_INTERWORKING */ 402 403 #ifdef CONFIG_WPS 404 wps = wpas_wps_in_use(wpa_s, &req_type); 405 406 if (wps) { 407 struct wpabuf *wps_ie; 408 wps_ie = wps_build_probe_req_ie(wps == 2, &wpa_s->wps->dev, 409 wpa_s->wps->uuid, req_type, 410 0, NULL); 411 if (wps_ie) { 412 if (wpabuf_resize(&extra_ie, wpabuf_len(wps_ie)) == 0) 413 wpabuf_put_buf(extra_ie, wps_ie); 414 wpabuf_free(wps_ie); 415 } 416 } 417 418 #ifdef CONFIG_P2P 419 if (wps) { 420 size_t ielen = p2p_scan_ie_buf_len(wpa_s->global->p2p); 421 if (wpabuf_resize(&extra_ie, ielen) == 0) 422 wpas_p2p_scan_ie(wpa_s, extra_ie); 423 } 424 #endif /* CONFIG_P2P */ 425 426 #endif /* CONFIG_WPS */ 427 428 return extra_ie; 429 } 430 431 432 static void wpa_supplicant_scan(void *eloop_ctx, void *timeout_ctx) 433 { 434 struct wpa_supplicant *wpa_s = eloop_ctx; 435 struct wpa_ssid *ssid; 436 int scan_req = 0, ret; 437 struct wpabuf *extra_ie; 438 struct wpa_driver_scan_params params; 439 size_t max_ssids; 440 enum wpa_states prev_state; 441 442 if (wpa_s->wpa_state == WPA_INTERFACE_DISABLED) { 443 wpa_dbg(wpa_s, MSG_DEBUG, "Skip scan - interface disabled"); 444 return; 445 } 446 447 if (wpa_s->disconnected && !wpa_s->scan_req) { 448 wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED); 449 return; 450 } 451 452 if (!wpa_supplicant_enabled_networks(wpa_s->conf) && 453 !wpa_s->scan_req) { 454 wpa_dbg(wpa_s, MSG_DEBUG, "No enabled networks - do not scan"); 455 wpa_supplicant_set_state(wpa_s, WPA_INACTIVE); 456 return; 457 } 458 459 if (wpa_s->conf->ap_scan != 0 && 460 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_WIRED)) { 461 wpa_dbg(wpa_s, MSG_DEBUG, "Using wired authentication - " 462 "overriding ap_scan configuration"); 463 wpa_s->conf->ap_scan = 0; 464 wpas_notify_ap_scan_changed(wpa_s); 465 } 466 467 if (wpa_s->conf->ap_scan == 0) { 468 wpa_supplicant_gen_assoc_event(wpa_s); 469 return; 470 } 471 472 #ifdef CONFIG_P2P 473 if (wpas_p2p_in_progress(wpa_s)) { 474 if (wpa_s->wpa_state == WPA_SCANNING) { 475 wpa_dbg(wpa_s, MSG_DEBUG, "Delay station mode scan " 476 "while P2P operation is in progress"); 477 wpa_supplicant_req_scan(wpa_s, 5, 0); 478 } else { 479 wpa_dbg(wpa_s, MSG_DEBUG, "Do not request scan while " 480 "P2P operation is in progress"); 481 } 482 return; 483 } 484 #endif /* CONFIG_P2P */ 485 486 if (wpa_s->conf->ap_scan == 2) 487 max_ssids = 1; 488 else { 489 max_ssids = wpa_s->max_scan_ssids; 490 if (max_ssids > WPAS_MAX_SCAN_SSIDS) 491 max_ssids = WPAS_MAX_SCAN_SSIDS; 492 } 493 494 scan_req = wpa_s->scan_req; 495 wpa_s->scan_req = 0; 496 497 os_memset(¶ms, 0, sizeof(params)); 498 499 prev_state = wpa_s->wpa_state; 500 if (wpa_s->wpa_state == WPA_DISCONNECTED || 501 wpa_s->wpa_state == WPA_INACTIVE) 502 wpa_supplicant_set_state(wpa_s, WPA_SCANNING); 503 504 if (scan_req != 2 && wpa_s->connect_without_scan) { 505 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { 506 if (ssid == wpa_s->connect_without_scan) 507 break; 508 } 509 wpa_s->connect_without_scan = NULL; 510 if (ssid) { 511 wpa_printf(MSG_DEBUG, "Start a pre-selected network " 512 "without scan step"); 513 wpa_supplicant_associate(wpa_s, NULL, ssid); 514 return; 515 } 516 } 517 518 /* Find the starting point from which to continue scanning */ 519 ssid = wpa_s->conf->ssid; 520 if (wpa_s->prev_scan_ssid != WILDCARD_SSID_SCAN) { 521 while (ssid) { 522 if (ssid == wpa_s->prev_scan_ssid) { 523 ssid = ssid->next; 524 break; 525 } 526 ssid = ssid->next; 527 } 528 } 529 530 if (scan_req != 2 && wpa_s->conf->ap_scan == 2) { 531 wpa_s->connect_without_scan = NULL; 532 wpa_s->prev_scan_wildcard = 0; 533 wpa_supplicant_assoc_try(wpa_s, ssid); 534 return; 535 #ifndef ANDROID 536 } else if (wpa_s->conf->ap_scan == 2) { 537 /* 538 * User-initiated scan request in ap_scan == 2; scan with 539 * wildcard SSID. 540 */ 541 ssid = NULL; 542 #endif 543 } else { 544 struct wpa_ssid *start = ssid, *tssid; 545 int freqs_set = 0; 546 if (ssid == NULL && max_ssids > 1) 547 ssid = wpa_s->conf->ssid; 548 while (ssid) { 549 if (!ssid->disabled && ssid->scan_ssid) { 550 wpa_hexdump_ascii(MSG_DEBUG, "Scan SSID", 551 ssid->ssid, ssid->ssid_len); 552 params.ssids[params.num_ssids].ssid = 553 ssid->ssid; 554 params.ssids[params.num_ssids].ssid_len = 555 ssid->ssid_len; 556 params.num_ssids++; 557 if (params.num_ssids + 1 >= max_ssids) 558 break; 559 } 560 ssid = ssid->next; 561 if (ssid == start) 562 break; 563 if (ssid == NULL && max_ssids > 1 && 564 start != wpa_s->conf->ssid) 565 ssid = wpa_s->conf->ssid; 566 } 567 568 for (tssid = wpa_s->conf->ssid; tssid; tssid = tssid->next) { 569 if (tssid->disabled) 570 continue; 571 if ((params.freqs || !freqs_set) && tssid->scan_freq) { 572 int_array_concat(¶ms.freqs, 573 tssid->scan_freq); 574 } else { 575 os_free(params.freqs); 576 params.freqs = NULL; 577 } 578 freqs_set = 1; 579 } 580 int_array_sort_unique(params.freqs); 581 } 582 583 if (ssid && max_ssids == 1) { 584 /* 585 * If the driver is limited to 1 SSID at a time interleave 586 * wildcard SSID scans with specific SSID scans to avoid 587 * waiting a long time for a wildcard scan. 588 */ 589 if (!wpa_s->prev_scan_wildcard) { 590 params.ssids[0].ssid = NULL; 591 params.ssids[0].ssid_len = 0; 592 wpa_s->prev_scan_wildcard = 1; 593 wpa_dbg(wpa_s, MSG_DEBUG, "Starting AP scan for " 594 "wildcard SSID (Interleave with specific)"); 595 } else { 596 wpa_s->prev_scan_ssid = ssid; 597 wpa_s->prev_scan_wildcard = 0; 598 wpa_dbg(wpa_s, MSG_DEBUG, 599 "Starting AP scan for specific SSID: %s", 600 wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 601 } 602 } else if (ssid) { 603 /* max_ssids > 1 */ 604 605 wpa_s->prev_scan_ssid = ssid; 606 wpa_dbg(wpa_s, MSG_DEBUG, "Include wildcard SSID in " 607 "the scan request"); 608 params.num_ssids++; 609 } else { 610 wpa_s->prev_scan_ssid = WILDCARD_SSID_SCAN; 611 params.num_ssids++; 612 wpa_dbg(wpa_s, MSG_DEBUG, "Starting AP scan for wildcard " 613 "SSID"); 614 } 615 616 wpa_supplicant_optimize_freqs(wpa_s, ¶ms); 617 extra_ie = wpa_supplicant_extra_ies(wpa_s, ¶ms); 618 619 if (params.freqs == NULL && wpa_s->next_scan_freqs) { 620 wpa_dbg(wpa_s, MSG_DEBUG, "Optimize scan based on previously " 621 "generated frequency list"); 622 params.freqs = wpa_s->next_scan_freqs; 623 } else 624 os_free(wpa_s->next_scan_freqs); 625 wpa_s->next_scan_freqs = NULL; 626 627 params.filter_ssids = wpa_supplicant_build_filter_ssids( 628 wpa_s->conf, ¶ms.num_filter_ssids); 629 if (extra_ie) { 630 params.extra_ies = wpabuf_head(extra_ie); 631 params.extra_ies_len = wpabuf_len(extra_ie); 632 } 633 634 #ifdef CONFIG_P2P 635 if (wpa_s->p2p_in_provisioning) { 636 /* 637 * The interface may not yet be in P2P mode, so we have to 638 * explicitly request P2P probe to disable CCK rates. 639 */ 640 params.p2p_probe = 1; 641 } 642 #endif /* CONFIG_P2P */ 643 644 ret = wpa_supplicant_trigger_scan(wpa_s, ¶ms); 645 646 wpabuf_free(extra_ie); 647 os_free(params.freqs); 648 os_free(params.filter_ssids); 649 650 if (ret) { 651 wpa_msg(wpa_s, MSG_WARNING, "Failed to initiate AP scan"); 652 if (prev_state != wpa_s->wpa_state) 653 wpa_supplicant_set_state(wpa_s, prev_state); 654 wpa_supplicant_req_scan(wpa_s, 1, 0); 655 } 656 } 657 658 659 /** 660 * wpa_supplicant_req_scan - Schedule a scan for neighboring access points 661 * @wpa_s: Pointer to wpa_supplicant data 662 * @sec: Number of seconds after which to scan 663 * @usec: Number of microseconds after which to scan 664 * 665 * This function is used to schedule a scan for neighboring access points after 666 * the specified time. 667 */ 668 void wpa_supplicant_req_scan(struct wpa_supplicant *wpa_s, int sec, int usec) 669 { 670 #ifndef ANDROID 671 /* If there's at least one network that should be specifically scanned 672 * then don't cancel the scan and reschedule. Some drivers do 673 * background scanning which generates frequent scan results, and that 674 * causes the specific SSID scan to get continually pushed back and 675 * never happen, which causes hidden APs to never get probe-scanned. 676 */ 677 if (eloop_is_timeout_registered(wpa_supplicant_scan, wpa_s, NULL) && 678 wpa_s->conf->ap_scan == 1) { 679 struct wpa_ssid *ssid = wpa_s->conf->ssid; 680 681 while (ssid) { 682 if (!ssid->disabled && ssid->scan_ssid) 683 break; 684 ssid = ssid->next; 685 } 686 if (ssid) { 687 wpa_dbg(wpa_s, MSG_DEBUG, "Not rescheduling scan to " 688 "ensure that specific SSID scans occur"); 689 return; 690 } 691 } 692 #endif 693 wpa_dbg(wpa_s, MSG_DEBUG, "Setting scan request: %d sec %d usec", 694 sec, usec); 695 eloop_cancel_timeout(wpa_supplicant_scan, wpa_s, NULL); 696 eloop_register_timeout(sec, usec, wpa_supplicant_scan, wpa_s, NULL); 697 } 698 699 700 /** 701 * wpa_supplicant_delayed_sched_scan - Request a delayed scheduled scan 702 * @wpa_s: Pointer to wpa_supplicant data 703 * @sec: Number of seconds after which to scan 704 * @usec: Number of microseconds after which to scan 705 * 706 * This function is used to schedule periodic scans for neighboring 707 * access points after the specified time. 708 */ 709 int wpa_supplicant_delayed_sched_scan(struct wpa_supplicant *wpa_s, 710 int sec, int usec) 711 { 712 if (!wpa_s->sched_scan_supported) 713 return -1; 714 715 eloop_register_timeout(sec, usec, 716 wpa_supplicant_delayed_sched_scan_timeout, 717 wpa_s, NULL); 718 719 return 0; 720 } 721 722 723 /** 724 * wpa_supplicant_req_sched_scan - Start a periodic scheduled scan 725 * @wpa_s: Pointer to wpa_supplicant data 726 * 727 * This function is used to schedule periodic scans for neighboring 728 * access points repeating the scan continuously. 729 */ 730 int wpa_supplicant_req_sched_scan(struct wpa_supplicant *wpa_s) 731 { 732 struct wpa_driver_scan_params params; 733 enum wpa_states prev_state; 734 struct wpa_ssid *ssid; 735 struct wpabuf *wps_ie = NULL; 736 int ret; 737 unsigned int max_sched_scan_ssids; 738 int wildcard = 0; 739 int need_ssids; 740 741 if (!wpa_s->sched_scan_supported) 742 return -1; 743 744 if (wpa_s->max_sched_scan_ssids > WPAS_MAX_SCAN_SSIDS) 745 max_sched_scan_ssids = WPAS_MAX_SCAN_SSIDS; 746 else 747 max_sched_scan_ssids = wpa_s->max_sched_scan_ssids; 748 if (max_sched_scan_ssids < 1) 749 return -1; 750 751 if (wpa_s->sched_scanning) { 752 wpa_dbg(wpa_s, MSG_DEBUG, "Already sched scanning"); 753 return 0; 754 } 755 756 need_ssids = 0; 757 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { 758 if (!ssid->disabled && !ssid->scan_ssid) { 759 /* Use wildcard SSID to find this network */ 760 wildcard = 1; 761 } else if (!ssid->disabled && ssid->ssid_len) 762 need_ssids++; 763 } 764 if (wildcard) 765 need_ssids++; 766 767 if (wpa_s->normal_scans < 3 && 768 (need_ssids <= wpa_s->max_scan_ssids || 769 wpa_s->max_scan_ssids >= (int) max_sched_scan_ssids)) { 770 /* 771 * When normal scan can speed up operations, use that for the 772 * first operations before starting the sched_scan to allow 773 * user space sleep more. We do this only if the normal scan 774 * has functionality that is suitable for this or if the 775 * sched_scan does not have better support for multiple SSIDs. 776 */ 777 wpa_dbg(wpa_s, MSG_DEBUG, "Use normal scan instead of " 778 "sched_scan for initial scans (normal_scans=%d)", 779 wpa_s->normal_scans); 780 return -1; 781 } 782 783 os_memset(¶ms, 0, sizeof(params)); 784 785 /* If we can't allocate space for the filters, we just don't filter */ 786 params.filter_ssids = os_zalloc(wpa_s->max_match_sets * 787 sizeof(struct wpa_driver_scan_filter)); 788 789 prev_state = wpa_s->wpa_state; 790 #ifndef ANDROID_P2P 791 if (wpa_s->wpa_state == WPA_DISCONNECTED || 792 wpa_s->wpa_state == WPA_INACTIVE) 793 wpa_supplicant_set_state(wpa_s, WPA_SCANNING); 794 #endif 795 796 /* Find the starting point from which to continue scanning */ 797 ssid = wpa_s->conf->ssid; 798 if (wpa_s->prev_sched_ssid) { 799 while (ssid) { 800 if (ssid == wpa_s->prev_sched_ssid) { 801 ssid = ssid->next; 802 break; 803 } 804 ssid = ssid->next; 805 } 806 } 807 808 if (!ssid || !wpa_s->prev_sched_ssid) { 809 wpa_dbg(wpa_s, MSG_DEBUG, "Beginning of SSID list"); 810 811 wpa_s->sched_scan_interval = 10; 812 wpa_s->sched_scan_timeout = max_sched_scan_ssids * 2; 813 wpa_s->first_sched_scan = 1; 814 ssid = wpa_s->conf->ssid; 815 wpa_s->prev_sched_ssid = ssid; 816 } 817 818 if (wildcard) { 819 wpa_dbg(wpa_s, MSG_DEBUG, "Add wildcard SSID to sched_scan"); 820 params.num_ssids++; 821 } 822 823 while (ssid) { 824 if (ssid->disabled) 825 goto next; 826 827 if (params.num_filter_ssids < wpa_s->max_match_sets && 828 params.filter_ssids && ssid->ssid && ssid->ssid_len) { 829 wpa_dbg(wpa_s, MSG_DEBUG, "add to filter ssid: %s", 830 wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 831 os_memcpy(params.filter_ssids[params.num_filter_ssids].ssid, 832 ssid->ssid, ssid->ssid_len); 833 params.filter_ssids[params.num_filter_ssids].ssid_len = 834 ssid->ssid_len; 835 params.num_filter_ssids++; 836 } else if (params.filter_ssids && ssid->ssid && ssid->ssid_len) 837 { 838 wpa_dbg(wpa_s, MSG_DEBUG, "Not enough room for SSID " 839 "filter for sched_scan - drop filter"); 840 os_free(params.filter_ssids); 841 params.filter_ssids = NULL; 842 params.num_filter_ssids = 0; 843 } 844 845 if (ssid->scan_ssid && ssid->ssid && ssid->ssid_len) { 846 if (params.num_ssids == max_sched_scan_ssids) 847 break; /* only room for broadcast SSID */ 848 wpa_dbg(wpa_s, MSG_DEBUG, 849 "add to active scan ssid: %s", 850 wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 851 params.ssids[params.num_ssids].ssid = 852 ssid->ssid; 853 params.ssids[params.num_ssids].ssid_len = 854 ssid->ssid_len; 855 params.num_ssids++; 856 if (params.num_ssids >= max_sched_scan_ssids) { 857 wpa_s->prev_sched_ssid = ssid; 858 break; 859 } 860 } 861 862 next: 863 wpa_s->prev_sched_ssid = ssid; 864 ssid = ssid->next; 865 } 866 867 if (params.num_filter_ssids == 0) { 868 os_free(params.filter_ssids); 869 params.filter_ssids = NULL; 870 } 871 872 if (wpa_s->wps) 873 wps_ie = wpa_supplicant_extra_ies(wpa_s, ¶ms); 874 875 if (ssid || !wpa_s->first_sched_scan) { 876 wpa_dbg(wpa_s, MSG_DEBUG, 877 "Starting sched scan: interval %d (no timeout)", 878 wpa_s->sched_scan_interval); 879 } else { 880 wpa_dbg(wpa_s, MSG_DEBUG, 881 "Starting sched scan: interval %d timeout %d", 882 wpa_s->sched_scan_interval, wpa_s->sched_scan_timeout); 883 } 884 885 ret = wpa_supplicant_start_sched_scan(wpa_s, ¶ms, 886 wpa_s->sched_scan_interval); 887 wpabuf_free(wps_ie); 888 os_free(params.filter_ssids); 889 if (ret) { 890 wpa_msg(wpa_s, MSG_WARNING, "Failed to initiate sched scan"); 891 if (prev_state != wpa_s->wpa_state) 892 wpa_supplicant_set_state(wpa_s, prev_state); 893 return ret; 894 } 895 896 /* If we have more SSIDs to scan, add a timeout so we scan them too */ 897 if (ssid || !wpa_s->first_sched_scan) { 898 wpa_s->sched_scan_timed_out = 0; 899 eloop_register_timeout(wpa_s->sched_scan_timeout, 0, 900 wpa_supplicant_sched_scan_timeout, 901 wpa_s, NULL); 902 wpa_s->first_sched_scan = 0; 903 wpa_s->sched_scan_timeout /= 2; 904 wpa_s->sched_scan_interval *= 2; 905 } 906 907 return 0; 908 } 909 910 911 /** 912 * wpa_supplicant_cancel_scan - Cancel a scheduled scan request 913 * @wpa_s: Pointer to wpa_supplicant data 914 * 915 * This function is used to cancel a scan request scheduled with 916 * wpa_supplicant_req_scan(). 917 */ 918 void wpa_supplicant_cancel_scan(struct wpa_supplicant *wpa_s) 919 { 920 wpa_dbg(wpa_s, MSG_DEBUG, "Cancelling scan request"); 921 eloop_cancel_timeout(wpa_supplicant_scan, wpa_s, NULL); 922 #ifdef ANDROID 923 wpa_supplicant_notify_scanning(wpa_s, 0); 924 #endif 925 } 926 927 928 /** 929 * wpa_supplicant_cancel_sched_scan - Stop running scheduled scans 930 * @wpa_s: Pointer to wpa_supplicant data 931 * 932 * This function is used to stop a periodic scheduled scan. 933 */ 934 void wpa_supplicant_cancel_sched_scan(struct wpa_supplicant *wpa_s) 935 { 936 if (!wpa_s->sched_scanning) 937 return; 938 939 wpa_dbg(wpa_s, MSG_DEBUG, "Cancelling sched scan"); 940 eloop_cancel_timeout(wpa_supplicant_sched_scan_timeout, wpa_s, NULL); 941 wpa_supplicant_stop_sched_scan(wpa_s); 942 } 943 944 945 void wpa_supplicant_notify_scanning(struct wpa_supplicant *wpa_s, 946 int scanning) 947 { 948 if (wpa_s->scanning != scanning) { 949 #ifdef ANDROID_P2P 950 if(!wpa_s->sched_scanning) 951 wpa_s->scanning = scanning; 952 #else 953 wpa_s->scanning = scanning; 954 #endif 955 wpas_notify_scanning(wpa_s); 956 } 957 } 958 959 960 static int wpa_scan_get_max_rate(const struct wpa_scan_res *res) 961 { 962 int rate = 0; 963 const u8 *ie; 964 int i; 965 966 ie = wpa_scan_get_ie(res, WLAN_EID_SUPP_RATES); 967 for (i = 0; ie && i < ie[1]; i++) { 968 if ((ie[i + 2] & 0x7f) > rate) 969 rate = ie[i + 2] & 0x7f; 970 } 971 972 ie = wpa_scan_get_ie(res, WLAN_EID_EXT_SUPP_RATES); 973 for (i = 0; ie && i < ie[1]; i++) { 974 if ((ie[i + 2] & 0x7f) > rate) 975 rate = ie[i + 2] & 0x7f; 976 } 977 978 return rate; 979 } 980 981 982 const u8 * wpa_scan_get_ie(const struct wpa_scan_res *res, u8 ie) 983 { 984 const u8 *end, *pos; 985 986 pos = (const u8 *) (res + 1); 987 end = pos + res->ie_len; 988 989 while (pos + 1 < end) { 990 if (pos + 2 + pos[1] > end) 991 break; 992 if (pos[0] == ie) 993 return pos; 994 pos += 2 + pos[1]; 995 } 996 997 return NULL; 998 } 999 1000 1001 const u8 * wpa_scan_get_vendor_ie(const struct wpa_scan_res *res, 1002 u32 vendor_type) 1003 { 1004 const u8 *end, *pos; 1005 1006 pos = (const u8 *) (res + 1); 1007 end = pos + res->ie_len; 1008 1009 while (pos + 1 < end) { 1010 if (pos + 2 + pos[1] > end) 1011 break; 1012 if (pos[0] == WLAN_EID_VENDOR_SPECIFIC && pos[1] >= 4 && 1013 vendor_type == WPA_GET_BE32(&pos[2])) 1014 return pos; 1015 pos += 2 + pos[1]; 1016 } 1017 1018 return NULL; 1019 } 1020 1021 1022 struct wpabuf * wpa_scan_get_vendor_ie_multi(const struct wpa_scan_res *res, 1023 u32 vendor_type) 1024 { 1025 struct wpabuf *buf; 1026 const u8 *end, *pos; 1027 1028 buf = wpabuf_alloc(res->ie_len); 1029 if (buf == NULL) 1030 return NULL; 1031 1032 pos = (const u8 *) (res + 1); 1033 end = pos + res->ie_len; 1034 1035 while (pos + 1 < end) { 1036 if (pos + 2 + pos[1] > end) 1037 break; 1038 if (pos[0] == WLAN_EID_VENDOR_SPECIFIC && pos[1] >= 4 && 1039 vendor_type == WPA_GET_BE32(&pos[2])) 1040 wpabuf_put_data(buf, pos + 2 + 4, pos[1] - 4); 1041 pos += 2 + pos[1]; 1042 } 1043 1044 if (wpabuf_len(buf) == 0) { 1045 wpabuf_free(buf); 1046 buf = NULL; 1047 } 1048 1049 return buf; 1050 } 1051 1052 1053 struct wpabuf * wpa_scan_get_vendor_ie_multi_beacon( 1054 const struct wpa_scan_res *res, u32 vendor_type) 1055 { 1056 struct wpabuf *buf; 1057 const u8 *end, *pos; 1058 1059 if (res->beacon_ie_len == 0) 1060 return NULL; 1061 buf = wpabuf_alloc(res->beacon_ie_len); 1062 if (buf == NULL) 1063 return NULL; 1064 1065 pos = (const u8 *) (res + 1); 1066 pos += res->ie_len; 1067 end = pos + res->beacon_ie_len; 1068 1069 while (pos + 1 < end) { 1070 if (pos + 2 + pos[1] > end) 1071 break; 1072 if (pos[0] == WLAN_EID_VENDOR_SPECIFIC && pos[1] >= 4 && 1073 vendor_type == WPA_GET_BE32(&pos[2])) 1074 wpabuf_put_data(buf, pos + 2 + 4, pos[1] - 4); 1075 pos += 2 + pos[1]; 1076 } 1077 1078 if (wpabuf_len(buf) == 0) { 1079 wpabuf_free(buf); 1080 buf = NULL; 1081 } 1082 1083 return buf; 1084 } 1085 1086 1087 /* 1088 * Channels with a great SNR can operate at full rate. What is a great SNR? 1089 * This doc https://supportforums.cisco.com/docs/DOC-12954 says, "the general 1090 * rule of thumb is that any SNR above 20 is good." This one 1091 * http://www.cisco.com/en/US/tech/tk722/tk809/technologies_q_and_a_item09186a00805e9a96.shtml#qa23 1092 * recommends 25 as a minimum SNR for 54 Mbps data rate. 30 is chosen here as a 1093 * conservative value. 1094 */ 1095 #define GREAT_SNR 30 1096 1097 /* Compare function for sorting scan results. Return >0 if @b is considered 1098 * better. */ 1099 static int wpa_scan_result_compar(const void *a, const void *b) 1100 { 1101 #define IS_5GHZ(n) (n > 4000) 1102 #define MIN(a,b) a < b ? a : b 1103 struct wpa_scan_res **_wa = (void *) a; 1104 struct wpa_scan_res **_wb = (void *) b; 1105 struct wpa_scan_res *wa = *_wa; 1106 struct wpa_scan_res *wb = *_wb; 1107 int wpa_a, wpa_b, maxrate_a, maxrate_b; 1108 int snr_a, snr_b; 1109 1110 /* WPA/WPA2 support preferred */ 1111 wpa_a = wpa_scan_get_vendor_ie(wa, WPA_IE_VENDOR_TYPE) != NULL || 1112 wpa_scan_get_ie(wa, WLAN_EID_RSN) != NULL; 1113 wpa_b = wpa_scan_get_vendor_ie(wb, WPA_IE_VENDOR_TYPE) != NULL || 1114 wpa_scan_get_ie(wb, WLAN_EID_RSN) != NULL; 1115 1116 if (wpa_b && !wpa_a) 1117 return 1; 1118 if (!wpa_b && wpa_a) 1119 return -1; 1120 1121 /* privacy support preferred */ 1122 if ((wa->caps & IEEE80211_CAP_PRIVACY) == 0 && 1123 (wb->caps & IEEE80211_CAP_PRIVACY)) 1124 return 1; 1125 if ((wa->caps & IEEE80211_CAP_PRIVACY) && 1126 (wb->caps & IEEE80211_CAP_PRIVACY) == 0) 1127 return -1; 1128 1129 if ((wa->flags & wb->flags & WPA_SCAN_LEVEL_DBM) && 1130 !((wa->flags | wb->flags) & WPA_SCAN_NOISE_INVALID)) { 1131 snr_a = MIN(wa->level - wa->noise, GREAT_SNR); 1132 snr_b = MIN(wb->level - wb->noise, GREAT_SNR); 1133 } else { 1134 /* Not suitable information to calculate SNR, so use level */ 1135 snr_a = wa->level; 1136 snr_b = wb->level; 1137 } 1138 1139 /* best/max rate preferred if SNR close enough */ 1140 if ((snr_a && snr_b && abs(snr_b - snr_a) < 5) || 1141 (wa->qual && wb->qual && abs(wb->qual - wa->qual) < 10)) { 1142 maxrate_a = wpa_scan_get_max_rate(wa); 1143 maxrate_b = wpa_scan_get_max_rate(wb); 1144 if (maxrate_a != maxrate_b) 1145 return maxrate_b - maxrate_a; 1146 if (IS_5GHZ(wa->freq) ^ IS_5GHZ(wb->freq)) 1147 return IS_5GHZ(wa->freq) ? -1 : 1; 1148 } 1149 1150 /* use freq for channel preference */ 1151 1152 /* all things being equal, use SNR; if SNRs are 1153 * identical, use quality values since some drivers may only report 1154 * that value and leave the signal level zero */ 1155 if (snr_b == snr_a) 1156 return wb->qual - wa->qual; 1157 return snr_b - snr_a; 1158 #undef MIN 1159 #undef IS_5GHZ 1160 } 1161 1162 1163 #ifdef CONFIG_WPS 1164 /* Compare function for sorting scan results when searching a WPS AP for 1165 * provisioning. Return >0 if @b is considered better. */ 1166 static int wpa_scan_result_wps_compar(const void *a, const void *b) 1167 { 1168 struct wpa_scan_res **_wa = (void *) a; 1169 struct wpa_scan_res **_wb = (void *) b; 1170 struct wpa_scan_res *wa = *_wa; 1171 struct wpa_scan_res *wb = *_wb; 1172 int uses_wps_a, uses_wps_b; 1173 struct wpabuf *wps_a, *wps_b; 1174 int res; 1175 1176 /* Optimization - check WPS IE existence before allocated memory and 1177 * doing full reassembly. */ 1178 uses_wps_a = wpa_scan_get_vendor_ie(wa, WPS_IE_VENDOR_TYPE) != NULL; 1179 uses_wps_b = wpa_scan_get_vendor_ie(wb, WPS_IE_VENDOR_TYPE) != NULL; 1180 if (uses_wps_a && !uses_wps_b) 1181 return -1; 1182 if (!uses_wps_a && uses_wps_b) 1183 return 1; 1184 1185 if (uses_wps_a && uses_wps_b) { 1186 wps_a = wpa_scan_get_vendor_ie_multi(wa, WPS_IE_VENDOR_TYPE); 1187 wps_b = wpa_scan_get_vendor_ie_multi(wb, WPS_IE_VENDOR_TYPE); 1188 res = wps_ap_priority_compar(wps_a, wps_b); 1189 wpabuf_free(wps_a); 1190 wpabuf_free(wps_b); 1191 if (res) 1192 return res; 1193 } 1194 1195 /* 1196 * Do not use current AP security policy as a sorting criteria during 1197 * WPS provisioning step since the AP may get reconfigured at the 1198 * completion of provisioning. 1199 */ 1200 1201 /* all things being equal, use signal level; if signal levels are 1202 * identical, use quality values since some drivers may only report 1203 * that value and leave the signal level zero */ 1204 if (wb->level == wa->level) 1205 return wb->qual - wa->qual; 1206 return wb->level - wa->level; 1207 } 1208 #endif /* CONFIG_WPS */ 1209 1210 1211 static void dump_scan_res(struct wpa_scan_results *scan_res) 1212 { 1213 #ifndef CONFIG_NO_STDOUT_DEBUG 1214 size_t i; 1215 1216 if (scan_res->res == NULL || scan_res->num == 0) 1217 return; 1218 1219 wpa_printf(MSG_EXCESSIVE, "Sorted scan results"); 1220 1221 for (i = 0; i < scan_res->num; i++) { 1222 struct wpa_scan_res *r = scan_res->res[i]; 1223 if ((r->flags & (WPA_SCAN_LEVEL_DBM | WPA_SCAN_NOISE_INVALID)) 1224 == WPA_SCAN_LEVEL_DBM) { 1225 int snr = r->level - r->noise; 1226 wpa_printf(MSG_EXCESSIVE, MACSTR " freq=%d qual=%d " 1227 "noise=%d level=%d snr=%d%s flags=0x%x", 1228 MAC2STR(r->bssid), r->freq, r->qual, 1229 r->noise, r->level, snr, 1230 snr >= GREAT_SNR ? "*" : "", r->flags); 1231 } else { 1232 wpa_printf(MSG_EXCESSIVE, MACSTR " freq=%d qual=%d " 1233 "noise=%d level=%d flags=0x%x", 1234 MAC2STR(r->bssid), r->freq, r->qual, 1235 r->noise, r->level, r->flags); 1236 } 1237 } 1238 #endif /* CONFIG_NO_STDOUT_DEBUG */ 1239 } 1240 1241 1242 /** 1243 * wpa_supplicant_get_scan_results - Get scan results 1244 * @wpa_s: Pointer to wpa_supplicant data 1245 * @info: Information about what was scanned or %NULL if not available 1246 * @new_scan: Whether a new scan was performed 1247 * Returns: Scan results, %NULL on failure 1248 * 1249 * This function request the current scan results from the driver and updates 1250 * the local BSS list wpa_s->bss. The caller is responsible for freeing the 1251 * results with wpa_scan_results_free(). 1252 */ 1253 struct wpa_scan_results * 1254 wpa_supplicant_get_scan_results(struct wpa_supplicant *wpa_s, 1255 struct scan_info *info, int new_scan) 1256 { 1257 struct wpa_scan_results *scan_res; 1258 size_t i; 1259 int (*compar)(const void *, const void *) = wpa_scan_result_compar; 1260 1261 scan_res = wpa_drv_get_scan_results2(wpa_s); 1262 if (scan_res == NULL) { 1263 wpa_dbg(wpa_s, MSG_DEBUG, "Failed to get scan results"); 1264 return NULL; 1265 } 1266 1267 #ifdef CONFIG_WPS 1268 if (wpas_wps_in_progress(wpa_s)) { 1269 wpa_dbg(wpa_s, MSG_DEBUG, "WPS: Order scan results with WPS " 1270 "provisioning rules"); 1271 compar = wpa_scan_result_wps_compar; 1272 } 1273 #endif /* CONFIG_WPS */ 1274 1275 qsort(scan_res->res, scan_res->num, sizeof(struct wpa_scan_res *), 1276 compar); 1277 dump_scan_res(scan_res); 1278 1279 wpa_bss_update_start(wpa_s); 1280 for (i = 0; i < scan_res->num; i++) 1281 wpa_bss_update_scan_res(wpa_s, scan_res->res[i]); 1282 wpa_bss_update_end(wpa_s, info, new_scan); 1283 1284 return scan_res; 1285 } 1286 1287 1288 int wpa_supplicant_update_scan_results(struct wpa_supplicant *wpa_s) 1289 { 1290 struct wpa_scan_results *scan_res; 1291 scan_res = wpa_supplicant_get_scan_results(wpa_s, NULL, 0); 1292 if (scan_res == NULL) 1293 return -1; 1294 wpa_scan_results_free(scan_res); 1295 1296 return 0; 1297 } 1298