1 /* 2 * WPA Supplicant - Scanning 3 * Copyright (c) 2003-2014, 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 "common/wpa_ctrl.h" 15 #include "config.h" 16 #include "wpa_supplicant_i.h" 17 #include "driver_i.h" 18 #include "wps_supplicant.h" 19 #include "p2p_supplicant.h" 20 #include "p2p/p2p.h" 21 #include "hs20_supplicant.h" 22 #include "notify.h" 23 #include "bss.h" 24 #include "scan.h" 25 26 27 static void wpa_supplicant_gen_assoc_event(struct wpa_supplicant *wpa_s) 28 { 29 struct wpa_ssid *ssid; 30 union wpa_event_data data; 31 32 ssid = wpa_supplicant_get_ssid(wpa_s); 33 if (ssid == NULL) 34 return; 35 36 if (wpa_s->current_ssid == NULL) { 37 wpa_s->current_ssid = ssid; 38 if (wpa_s->current_ssid != NULL) 39 wpas_notify_network_changed(wpa_s); 40 } 41 wpa_supplicant_initiate_eapol(wpa_s); 42 wpa_dbg(wpa_s, MSG_DEBUG, "Already associated with a configured " 43 "network - generating associated event"); 44 os_memset(&data, 0, sizeof(data)); 45 wpa_supplicant_event(wpa_s, EVENT_ASSOC, &data); 46 } 47 48 49 #ifdef CONFIG_WPS 50 static int wpas_wps_in_use(struct wpa_supplicant *wpa_s, 51 enum wps_request_type *req_type) 52 { 53 struct wpa_ssid *ssid; 54 int wps = 0; 55 56 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { 57 if (!(ssid->key_mgmt & WPA_KEY_MGMT_WPS)) 58 continue; 59 60 wps = 1; 61 *req_type = wpas_wps_get_req_type(ssid); 62 if (!ssid->eap.phase1) 63 continue; 64 65 if (os_strstr(ssid->eap.phase1, "pbc=1")) 66 return 2; 67 } 68 69 #ifdef CONFIG_P2P 70 if (!wpa_s->global->p2p_disabled && wpa_s->global->p2p && 71 !wpa_s->conf->p2p_disabled) { 72 wpa_s->wps->dev.p2p = 1; 73 if (!wps) { 74 wps = 1; 75 *req_type = WPS_REQ_ENROLLEE_INFO; 76 } 77 } 78 #endif /* CONFIG_P2P */ 79 80 return wps; 81 } 82 #endif /* CONFIG_WPS */ 83 84 85 /** 86 * wpa_supplicant_enabled_networks - Check whether there are enabled networks 87 * @wpa_s: Pointer to wpa_supplicant data 88 * Returns: 0 if no networks are enabled, >0 if networks are enabled 89 * 90 * This function is used to figure out whether any networks (or Interworking 91 * with enabled credentials and auto_interworking) are present in the current 92 * configuration. 93 */ 94 int wpa_supplicant_enabled_networks(struct wpa_supplicant *wpa_s) 95 { 96 struct wpa_ssid *ssid = wpa_s->conf->ssid; 97 int count = 0, disabled = 0; 98 while (ssid) { 99 if (!wpas_network_disabled(wpa_s, ssid)) 100 count++; 101 else 102 disabled++; 103 ssid = ssid->next; 104 } 105 if (wpa_s->conf->cred && wpa_s->conf->interworking && 106 wpa_s->conf->auto_interworking) 107 count++; 108 if (count == 0 && disabled > 0) { 109 wpa_dbg(wpa_s, MSG_DEBUG, "No enabled networks (%d disabled " 110 "networks)", disabled); 111 } 112 return count; 113 } 114 115 116 static void wpa_supplicant_assoc_try(struct wpa_supplicant *wpa_s, 117 struct wpa_ssid *ssid) 118 { 119 while (ssid) { 120 if (!wpas_network_disabled(wpa_s, ssid)) 121 break; 122 ssid = ssid->next; 123 } 124 125 /* ap_scan=2 mode - try to associate with each SSID. */ 126 if (ssid == NULL) { 127 wpa_dbg(wpa_s, MSG_DEBUG, "wpa_supplicant_assoc_try: Reached " 128 "end of scan list - go back to beginning"); 129 wpa_s->prev_scan_ssid = WILDCARD_SSID_SCAN; 130 wpa_supplicant_req_scan(wpa_s, 0, 0); 131 return; 132 } 133 if (ssid->next) { 134 /* Continue from the next SSID on the next attempt. */ 135 wpa_s->prev_scan_ssid = ssid; 136 } else { 137 /* Start from the beginning of the SSID list. */ 138 wpa_s->prev_scan_ssid = WILDCARD_SSID_SCAN; 139 } 140 wpa_supplicant_associate(wpa_s, NULL, ssid); 141 } 142 143 144 static void wpas_trigger_scan_cb(struct wpa_radio_work *work, int deinit) 145 { 146 struct wpa_supplicant *wpa_s = work->wpa_s; 147 struct wpa_driver_scan_params *params = work->ctx; 148 int ret; 149 150 if (deinit) { 151 if (!work->started) { 152 wpa_scan_free_params(params); 153 return; 154 } 155 wpa_supplicant_notify_scanning(wpa_s, 0); 156 wpas_notify_scan_done(wpa_s, 0); 157 wpa_s->scan_work = NULL; 158 return; 159 } 160 161 wpa_supplicant_notify_scanning(wpa_s, 1); 162 163 if (wpa_s->clear_driver_scan_cache) 164 params->only_new_results = 1; 165 ret = wpa_drv_scan(wpa_s, params); 166 wpa_scan_free_params(params); 167 work->ctx = NULL; 168 if (ret) { 169 wpa_supplicant_notify_scanning(wpa_s, 0); 170 wpas_notify_scan_done(wpa_s, 0); 171 radio_work_done(work); 172 return; 173 } 174 175 os_get_reltime(&wpa_s->scan_trigger_time); 176 wpa_s->scan_runs++; 177 wpa_s->normal_scans++; 178 wpa_s->own_scan_requested = 1; 179 wpa_s->clear_driver_scan_cache = 0; 180 wpa_s->scan_work = work; 181 } 182 183 184 /** 185 * wpa_supplicant_trigger_scan - Request driver to start a scan 186 * @wpa_s: Pointer to wpa_supplicant data 187 * @params: Scan parameters 188 * Returns: 0 on success, -1 on failure 189 */ 190 int wpa_supplicant_trigger_scan(struct wpa_supplicant *wpa_s, 191 struct wpa_driver_scan_params *params) 192 { 193 struct wpa_driver_scan_params *ctx; 194 195 if (wpa_s->scan_work) { 196 wpa_dbg(wpa_s, MSG_INFO, "Reject scan trigger since one is already pending"); 197 return -1; 198 } 199 200 ctx = wpa_scan_clone_params(params); 201 if (ctx == NULL) 202 return -1; 203 204 if (radio_add_work(wpa_s, 0, "scan", 0, wpas_trigger_scan_cb, ctx) < 0) 205 { 206 wpa_scan_free_params(ctx); 207 return -1; 208 } 209 210 return 0; 211 } 212 213 214 static void 215 wpa_supplicant_delayed_sched_scan_timeout(void *eloop_ctx, void *timeout_ctx) 216 { 217 struct wpa_supplicant *wpa_s = eloop_ctx; 218 219 wpa_dbg(wpa_s, MSG_DEBUG, "Starting delayed sched scan"); 220 221 if (wpa_supplicant_req_sched_scan(wpa_s)) 222 wpa_supplicant_req_scan(wpa_s, 0, 0); 223 } 224 225 226 static void 227 wpa_supplicant_sched_scan_timeout(void *eloop_ctx, void *timeout_ctx) 228 { 229 struct wpa_supplicant *wpa_s = eloop_ctx; 230 231 wpa_dbg(wpa_s, MSG_DEBUG, "Sched scan timeout - stopping it"); 232 233 wpa_s->sched_scan_timed_out = 1; 234 wpa_supplicant_cancel_sched_scan(wpa_s); 235 } 236 237 238 int wpa_supplicant_start_sched_scan(struct wpa_supplicant *wpa_s, 239 struct wpa_driver_scan_params *params, 240 int interval) 241 { 242 int ret; 243 244 wpa_supplicant_notify_scanning(wpa_s, 1); 245 ret = wpa_drv_sched_scan(wpa_s, params, interval * 1000); 246 if (ret) 247 wpa_supplicant_notify_scanning(wpa_s, 0); 248 else 249 wpa_s->sched_scanning = 1; 250 251 return ret; 252 } 253 254 255 int wpa_supplicant_stop_sched_scan(struct wpa_supplicant *wpa_s) 256 { 257 int ret; 258 259 ret = wpa_drv_stop_sched_scan(wpa_s); 260 if (ret) { 261 wpa_dbg(wpa_s, MSG_DEBUG, "stopping sched_scan failed!"); 262 /* TODO: what to do if stopping fails? */ 263 return -1; 264 } 265 266 return ret; 267 } 268 269 270 static struct wpa_driver_scan_filter * 271 wpa_supplicant_build_filter_ssids(struct wpa_config *conf, size_t *num_ssids) 272 { 273 struct wpa_driver_scan_filter *ssids; 274 struct wpa_ssid *ssid; 275 size_t count; 276 277 *num_ssids = 0; 278 if (!conf->filter_ssids) 279 return NULL; 280 281 for (count = 0, ssid = conf->ssid; ssid; ssid = ssid->next) { 282 if (ssid->ssid && ssid->ssid_len) 283 count++; 284 } 285 if (count == 0) 286 return NULL; 287 ssids = os_zalloc(count * sizeof(struct wpa_driver_scan_filter)); 288 if (ssids == NULL) 289 return NULL; 290 291 for (ssid = conf->ssid; ssid; ssid = ssid->next) { 292 if (!ssid->ssid || !ssid->ssid_len) 293 continue; 294 os_memcpy(ssids[*num_ssids].ssid, ssid->ssid, ssid->ssid_len); 295 ssids[*num_ssids].ssid_len = ssid->ssid_len; 296 (*num_ssids)++; 297 } 298 299 return ssids; 300 } 301 302 303 static void wpa_supplicant_optimize_freqs( 304 struct wpa_supplicant *wpa_s, struct wpa_driver_scan_params *params) 305 { 306 #ifdef CONFIG_P2P 307 if (params->freqs == NULL && wpa_s->p2p_in_provisioning && 308 wpa_s->go_params) { 309 /* Optimize provisioning state scan based on GO information */ 310 if (wpa_s->p2p_in_provisioning < 5 && 311 wpa_s->go_params->freq > 0) { 312 wpa_dbg(wpa_s, MSG_DEBUG, "P2P: Scan only GO " 313 "preferred frequency %d MHz", 314 wpa_s->go_params->freq); 315 params->freqs = os_zalloc(2 * sizeof(int)); 316 if (params->freqs) 317 params->freqs[0] = wpa_s->go_params->freq; 318 } else if (wpa_s->p2p_in_provisioning < 8 && 319 wpa_s->go_params->freq_list[0]) { 320 wpa_dbg(wpa_s, MSG_DEBUG, "P2P: Scan only common " 321 "channels"); 322 int_array_concat(¶ms->freqs, 323 wpa_s->go_params->freq_list); 324 if (params->freqs) 325 int_array_sort_unique(params->freqs); 326 } 327 wpa_s->p2p_in_provisioning++; 328 } 329 330 if (params->freqs == NULL && wpa_s->p2p_in_invitation) { 331 /* 332 * Optimize scan based on GO information during persistent 333 * group reinvocation 334 */ 335 if (wpa_s->p2p_in_invitation < 5 && 336 wpa_s->p2p_invite_go_freq > 0) { 337 wpa_dbg(wpa_s, MSG_DEBUG, "P2P: Scan only GO preferred frequency %d MHz during invitation", 338 wpa_s->p2p_invite_go_freq); 339 params->freqs = os_zalloc(2 * sizeof(int)); 340 if (params->freqs) 341 params->freqs[0] = wpa_s->p2p_invite_go_freq; 342 } 343 wpa_s->p2p_in_invitation++; 344 if (wpa_s->p2p_in_invitation > 20) { 345 /* 346 * This should not really happen since the variable is 347 * cleared on group removal, but if it does happen, make 348 * sure we do not get stuck in special invitation scan 349 * mode. 350 */ 351 wpa_dbg(wpa_s, MSG_DEBUG, "P2P: Clear p2p_in_invitation"); 352 wpa_s->p2p_in_invitation = 0; 353 } 354 } 355 #endif /* CONFIG_P2P */ 356 357 #ifdef CONFIG_WPS 358 if (params->freqs == NULL && wpa_s->after_wps && wpa_s->wps_freq) { 359 /* 360 * Optimize post-provisioning scan based on channel used 361 * during provisioning. 362 */ 363 wpa_dbg(wpa_s, MSG_DEBUG, "WPS: Scan only frequency %u MHz " 364 "that was used during provisioning", wpa_s->wps_freq); 365 params->freqs = os_zalloc(2 * sizeof(int)); 366 if (params->freqs) 367 params->freqs[0] = wpa_s->wps_freq; 368 wpa_s->after_wps--; 369 } else if (wpa_s->after_wps) 370 wpa_s->after_wps--; 371 372 if (params->freqs == NULL && wpa_s->known_wps_freq && wpa_s->wps_freq) 373 { 374 /* Optimize provisioning scan based on already known channel */ 375 wpa_dbg(wpa_s, MSG_DEBUG, "WPS: Scan only frequency %u MHz", 376 wpa_s->wps_freq); 377 params->freqs = os_zalloc(2 * sizeof(int)); 378 if (params->freqs) 379 params->freqs[0] = wpa_s->wps_freq; 380 wpa_s->known_wps_freq = 0; /* only do this once */ 381 } 382 #endif /* CONFIG_WPS */ 383 } 384 385 386 #ifdef CONFIG_INTERWORKING 387 static void wpas_add_interworking_elements(struct wpa_supplicant *wpa_s, 388 struct wpabuf *buf) 389 { 390 if (wpa_s->conf->interworking == 0) 391 return; 392 393 wpabuf_put_u8(buf, WLAN_EID_EXT_CAPAB); 394 wpabuf_put_u8(buf, 6); 395 wpabuf_put_u8(buf, 0x00); 396 wpabuf_put_u8(buf, 0x00); 397 wpabuf_put_u8(buf, 0x00); 398 wpabuf_put_u8(buf, 0x80); /* Bit 31 - Interworking */ 399 wpabuf_put_u8(buf, 0x00); 400 #ifdef CONFIG_HS20 401 wpabuf_put_u8(buf, 0x40); /* Bit 46 - WNM-Notification */ 402 #else /* CONFIG_HS20 */ 403 wpabuf_put_u8(buf, 0x00); 404 #endif /* CONFIG_HS20 */ 405 406 wpabuf_put_u8(buf, WLAN_EID_INTERWORKING); 407 wpabuf_put_u8(buf, is_zero_ether_addr(wpa_s->conf->hessid) ? 1 : 408 1 + ETH_ALEN); 409 wpabuf_put_u8(buf, wpa_s->conf->access_network_type); 410 /* No Venue Info */ 411 if (!is_zero_ether_addr(wpa_s->conf->hessid)) 412 wpabuf_put_data(buf, wpa_s->conf->hessid, ETH_ALEN); 413 } 414 #endif /* CONFIG_INTERWORKING */ 415 416 417 static struct wpabuf * wpa_supplicant_extra_ies(struct wpa_supplicant *wpa_s) 418 { 419 struct wpabuf *extra_ie = NULL; 420 #ifdef CONFIG_WPS 421 int wps = 0; 422 enum wps_request_type req_type = WPS_REQ_ENROLLEE_INFO; 423 #endif /* CONFIG_WPS */ 424 425 #ifdef CONFIG_INTERWORKING 426 if (wpa_s->conf->interworking && 427 wpabuf_resize(&extra_ie, 100) == 0) 428 wpas_add_interworking_elements(wpa_s, extra_ie); 429 #endif /* CONFIG_INTERWORKING */ 430 431 #ifdef CONFIG_WPS 432 wps = wpas_wps_in_use(wpa_s, &req_type); 433 434 if (wps) { 435 struct wpabuf *wps_ie; 436 wps_ie = wps_build_probe_req_ie(wps == 2 ? DEV_PW_PUSHBUTTON : 437 DEV_PW_DEFAULT, 438 &wpa_s->wps->dev, 439 wpa_s->wps->uuid, req_type, 440 0, NULL); 441 if (wps_ie) { 442 if (wpabuf_resize(&extra_ie, wpabuf_len(wps_ie)) == 0) 443 wpabuf_put_buf(extra_ie, wps_ie); 444 wpabuf_free(wps_ie); 445 } 446 } 447 448 #ifdef CONFIG_P2P 449 if (wps) { 450 size_t ielen = p2p_scan_ie_buf_len(wpa_s->global->p2p); 451 if (wpabuf_resize(&extra_ie, ielen) == 0) 452 wpas_p2p_scan_ie(wpa_s, extra_ie); 453 } 454 #endif /* CONFIG_P2P */ 455 456 #endif /* CONFIG_WPS */ 457 458 #ifdef CONFIG_HS20 459 if (wpa_s->conf->hs20 && wpabuf_resize(&extra_ie, 7) == 0) 460 wpas_hs20_add_indication(extra_ie, -1); 461 #endif /* CONFIG_HS20 */ 462 463 return extra_ie; 464 } 465 466 467 #ifdef CONFIG_P2P 468 469 /* 470 * Check whether there are any enabled networks or credentials that could be 471 * used for a non-P2P connection. 472 */ 473 static int non_p2p_network_enabled(struct wpa_supplicant *wpa_s) 474 { 475 struct wpa_ssid *ssid; 476 477 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { 478 if (wpas_network_disabled(wpa_s, ssid)) 479 continue; 480 if (!ssid->p2p_group) 481 return 1; 482 } 483 484 if (wpa_s->conf->cred && wpa_s->conf->interworking && 485 wpa_s->conf->auto_interworking) 486 return 1; 487 488 return 0; 489 } 490 491 #endif /* CONFIG_P2P */ 492 493 494 static struct hostapd_hw_modes * get_mode(struct hostapd_hw_modes *modes, 495 u16 num_modes, 496 enum hostapd_hw_mode mode) 497 { 498 u16 i; 499 500 for (i = 0; i < num_modes; i++) { 501 if (modes[i].mode == mode) 502 return &modes[i]; 503 } 504 505 return NULL; 506 } 507 508 509 static void wpa_setband_scan_freqs_list(struct wpa_supplicant *wpa_s, 510 enum hostapd_hw_mode band, 511 struct wpa_driver_scan_params *params) 512 { 513 /* Include only supported channels for the specified band */ 514 struct hostapd_hw_modes *mode; 515 int count, i; 516 517 mode = get_mode(wpa_s->hw.modes, wpa_s->hw.num_modes, band); 518 if (mode == NULL) { 519 /* No channels supported in this band - use empty list */ 520 params->freqs = os_zalloc(sizeof(int)); 521 return; 522 } 523 524 params->freqs = os_zalloc((mode->num_channels + 1) * sizeof(int)); 525 if (params->freqs == NULL) 526 return; 527 for (count = 0, i = 0; i < mode->num_channels; i++) { 528 if (mode->channels[i].flag & HOSTAPD_CHAN_DISABLED) 529 continue; 530 params->freqs[count++] = mode->channels[i].freq; 531 } 532 } 533 534 535 static void wpa_setband_scan_freqs(struct wpa_supplicant *wpa_s, 536 struct wpa_driver_scan_params *params) 537 { 538 if (wpa_s->hw.modes == NULL) 539 return; /* unknown what channels the driver supports */ 540 if (params->freqs) 541 return; /* already using a limited channel set */ 542 if (wpa_s->setband == WPA_SETBAND_5G) 543 wpa_setband_scan_freqs_list(wpa_s, HOSTAPD_MODE_IEEE80211A, 544 params); 545 else if (wpa_s->setband == WPA_SETBAND_2G) 546 wpa_setband_scan_freqs_list(wpa_s, HOSTAPD_MODE_IEEE80211G, 547 params); 548 } 549 550 551 static void wpa_set_scan_ssids(struct wpa_supplicant *wpa_s, 552 struct wpa_driver_scan_params *params, 553 size_t max_ssids) 554 { 555 unsigned int i; 556 struct wpa_ssid *ssid; 557 558 for (i = 0; i < wpa_s->scan_id_count; i++) { 559 unsigned int j; 560 561 ssid = wpa_config_get_network(wpa_s->conf, wpa_s->scan_id[i]); 562 if (!ssid || !ssid->scan_ssid) 563 continue; 564 565 for (j = 0; j < params->num_ssids; j++) { 566 if (params->ssids[j].ssid_len == ssid->ssid_len && 567 params->ssids[j].ssid && 568 os_memcmp(params->ssids[j].ssid, ssid->ssid, 569 ssid->ssid_len) == 0) 570 break; 571 } 572 if (j < params->num_ssids) 573 continue; /* already in the list */ 574 575 if (params->num_ssids + 1 > max_ssids) { 576 wpa_printf(MSG_DEBUG, 577 "Over max scan SSIDs for manual request"); 578 break; 579 } 580 581 wpa_printf(MSG_DEBUG, "Scan SSID (manual request): %s", 582 wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 583 params->ssids[params->num_ssids].ssid = ssid->ssid; 584 params->ssids[params->num_ssids].ssid_len = ssid->ssid_len; 585 params->num_ssids++; 586 } 587 588 wpa_s->scan_id_count = 0; 589 } 590 591 592 static void wpa_supplicant_scan(void *eloop_ctx, void *timeout_ctx) 593 { 594 struct wpa_supplicant *wpa_s = eloop_ctx; 595 struct wpa_ssid *ssid; 596 int ret; 597 struct wpabuf *extra_ie = NULL; 598 struct wpa_driver_scan_params params; 599 struct wpa_driver_scan_params *scan_params; 600 size_t max_ssids; 601 enum wpa_states prev_state; 602 603 if (wpa_s->pno || wpa_s->pno_sched_pending) { 604 wpa_dbg(wpa_s, MSG_DEBUG, "Skip scan - PNO is in progress"); 605 return; 606 } 607 608 if (wpa_s->wpa_state == WPA_INTERFACE_DISABLED) { 609 wpa_dbg(wpa_s, MSG_DEBUG, "Skip scan - interface disabled"); 610 return; 611 } 612 613 if (wpa_s->disconnected && wpa_s->scan_req == NORMAL_SCAN_REQ) { 614 wpa_dbg(wpa_s, MSG_DEBUG, "Disconnected - do not scan"); 615 wpa_supplicant_set_state(wpa_s, WPA_DISCONNECTED); 616 return; 617 } 618 619 if (wpa_s->scanning) { 620 /* 621 * If we are already in scanning state, we shall reschedule the 622 * the incoming scan request. 623 */ 624 wpa_dbg(wpa_s, MSG_DEBUG, "Already scanning - Reschedule the incoming scan req"); 625 wpa_supplicant_req_scan(wpa_s, 1, 0); 626 return; 627 } 628 629 if (!wpa_supplicant_enabled_networks(wpa_s) && 630 wpa_s->scan_req == NORMAL_SCAN_REQ) { 631 wpa_dbg(wpa_s, MSG_DEBUG, "No enabled networks - do not scan"); 632 wpa_supplicant_set_state(wpa_s, WPA_INACTIVE); 633 return; 634 } 635 636 if (wpa_s->conf->ap_scan != 0 && 637 (wpa_s->drv_flags & WPA_DRIVER_FLAGS_WIRED)) { 638 wpa_dbg(wpa_s, MSG_DEBUG, "Using wired authentication - " 639 "overriding ap_scan configuration"); 640 wpa_s->conf->ap_scan = 0; 641 wpas_notify_ap_scan_changed(wpa_s); 642 } 643 644 if (wpa_s->conf->ap_scan == 0) { 645 wpa_supplicant_gen_assoc_event(wpa_s); 646 return; 647 } 648 649 if (wpas_p2p_in_progress(wpa_s)) { 650 wpa_dbg(wpa_s, MSG_DEBUG, "Delay station mode scan while P2P operation is in progress"); 651 wpa_supplicant_req_scan(wpa_s, 5, 0); 652 return; 653 } 654 655 if (wpa_s->conf->ap_scan == 2) 656 max_ssids = 1; 657 else { 658 max_ssids = wpa_s->max_scan_ssids; 659 if (max_ssids > WPAS_MAX_SCAN_SSIDS) 660 max_ssids = WPAS_MAX_SCAN_SSIDS; 661 } 662 663 wpa_s->last_scan_req = wpa_s->scan_req; 664 wpa_s->scan_req = NORMAL_SCAN_REQ; 665 666 os_memset(¶ms, 0, sizeof(params)); 667 668 prev_state = wpa_s->wpa_state; 669 if (wpa_s->wpa_state == WPA_DISCONNECTED || 670 wpa_s->wpa_state == WPA_INACTIVE) 671 wpa_supplicant_set_state(wpa_s, WPA_SCANNING); 672 673 /* 674 * If autoscan has set its own scanning parameters 675 */ 676 if (wpa_s->autoscan_params != NULL) { 677 scan_params = wpa_s->autoscan_params; 678 goto scan; 679 } 680 681 if (wpa_s->last_scan_req != MANUAL_SCAN_REQ && 682 wpa_s->connect_without_scan) { 683 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { 684 if (ssid == wpa_s->connect_without_scan) 685 break; 686 } 687 wpa_s->connect_without_scan = NULL; 688 if (ssid) { 689 wpa_printf(MSG_DEBUG, "Start a pre-selected network " 690 "without scan step"); 691 wpa_supplicant_associate(wpa_s, NULL, ssid); 692 return; 693 } 694 } 695 696 #ifdef CONFIG_P2P 697 if ((wpa_s->p2p_in_provisioning || wpa_s->show_group_started) && 698 wpa_s->go_params) { 699 wpa_printf(MSG_DEBUG, "P2P: Use specific SSID for scan during P2P group formation (p2p_in_provisioning=%d show_group_started=%d)", 700 wpa_s->p2p_in_provisioning, 701 wpa_s->show_group_started); 702 params.ssids[0].ssid = wpa_s->go_params->ssid; 703 params.ssids[0].ssid_len = wpa_s->go_params->ssid_len; 704 params.num_ssids = 1; 705 goto ssid_list_set; 706 } 707 708 if (wpa_s->p2p_in_invitation) { 709 if (wpa_s->current_ssid) { 710 wpa_printf(MSG_DEBUG, "P2P: Use specific SSID for scan during invitation"); 711 params.ssids[0].ssid = wpa_s->current_ssid->ssid; 712 params.ssids[0].ssid_len = 713 wpa_s->current_ssid->ssid_len; 714 params.num_ssids = 1; 715 } else { 716 wpa_printf(MSG_DEBUG, "P2P: No specific SSID known for scan during invitation"); 717 } 718 goto ssid_list_set; 719 } 720 #endif /* CONFIG_P2P */ 721 722 /* Find the starting point from which to continue scanning */ 723 ssid = wpa_s->conf->ssid; 724 if (wpa_s->prev_scan_ssid != WILDCARD_SSID_SCAN) { 725 while (ssid) { 726 if (ssid == wpa_s->prev_scan_ssid) { 727 ssid = ssid->next; 728 break; 729 } 730 ssid = ssid->next; 731 } 732 } 733 734 if (wpa_s->last_scan_req != MANUAL_SCAN_REQ && 735 wpa_s->conf->ap_scan == 2) { 736 wpa_s->connect_without_scan = NULL; 737 wpa_s->prev_scan_wildcard = 0; 738 wpa_supplicant_assoc_try(wpa_s, ssid); 739 return; 740 } else if (wpa_s->conf->ap_scan == 2) { 741 /* 742 * User-initiated scan request in ap_scan == 2; scan with 743 * wildcard SSID. 744 */ 745 ssid = NULL; 746 } else if (wpa_s->reattach && wpa_s->current_ssid != NULL) { 747 /* 748 * Perform single-channel single-SSID scan for 749 * reassociate-to-same-BSS operation. 750 */ 751 /* Setup SSID */ 752 ssid = wpa_s->current_ssid; 753 wpa_hexdump_ascii(MSG_DEBUG, "Scan SSID", 754 ssid->ssid, ssid->ssid_len); 755 params.ssids[0].ssid = ssid->ssid; 756 params.ssids[0].ssid_len = ssid->ssid_len; 757 params.num_ssids = 1; 758 759 /* 760 * Allocate memory for frequency array, allocate one extra 761 * slot for the zero-terminator. 762 */ 763 params.freqs = os_malloc(sizeof(int) * 2); 764 if (params.freqs == NULL) { 765 wpa_dbg(wpa_s, MSG_ERROR, "Memory allocation failed"); 766 return; 767 } 768 params.freqs[0] = wpa_s->assoc_freq; 769 params.freqs[1] = 0; 770 771 /* 772 * Reset the reattach flag so that we fall back to full scan if 773 * this scan fails. 774 */ 775 wpa_s->reattach = 0; 776 } else { 777 struct wpa_ssid *start = ssid, *tssid; 778 int freqs_set = 0; 779 if (ssid == NULL && max_ssids > 1) 780 ssid = wpa_s->conf->ssid; 781 while (ssid) { 782 if (!wpas_network_disabled(wpa_s, ssid) && 783 ssid->scan_ssid) { 784 wpa_hexdump_ascii(MSG_DEBUG, "Scan SSID", 785 ssid->ssid, ssid->ssid_len); 786 params.ssids[params.num_ssids].ssid = 787 ssid->ssid; 788 params.ssids[params.num_ssids].ssid_len = 789 ssid->ssid_len; 790 params.num_ssids++; 791 if (params.num_ssids + 1 >= max_ssids) 792 break; 793 } 794 ssid = ssid->next; 795 if (ssid == start) 796 break; 797 if (ssid == NULL && max_ssids > 1 && 798 start != wpa_s->conf->ssid) 799 ssid = wpa_s->conf->ssid; 800 } 801 802 if (wpa_s->scan_id_count && 803 wpa_s->last_scan_req == MANUAL_SCAN_REQ) 804 wpa_set_scan_ssids(wpa_s, ¶ms, max_ssids); 805 806 for (tssid = wpa_s->conf->ssid; tssid; tssid = tssid->next) { 807 if (wpas_network_disabled(wpa_s, tssid)) 808 continue; 809 if ((params.freqs || !freqs_set) && tssid->scan_freq) { 810 int_array_concat(¶ms.freqs, 811 tssid->scan_freq); 812 } else { 813 os_free(params.freqs); 814 params.freqs = NULL; 815 } 816 freqs_set = 1; 817 } 818 int_array_sort_unique(params.freqs); 819 } 820 821 if (ssid && max_ssids == 1) { 822 /* 823 * If the driver is limited to 1 SSID at a time interleave 824 * wildcard SSID scans with specific SSID scans to avoid 825 * waiting a long time for a wildcard scan. 826 */ 827 if (!wpa_s->prev_scan_wildcard) { 828 params.ssids[0].ssid = NULL; 829 params.ssids[0].ssid_len = 0; 830 wpa_s->prev_scan_wildcard = 1; 831 wpa_dbg(wpa_s, MSG_DEBUG, "Starting AP scan for " 832 "wildcard SSID (Interleave with specific)"); 833 } else { 834 wpa_s->prev_scan_ssid = ssid; 835 wpa_s->prev_scan_wildcard = 0; 836 wpa_dbg(wpa_s, MSG_DEBUG, 837 "Starting AP scan for specific SSID: %s", 838 wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 839 } 840 } else if (ssid) { 841 /* max_ssids > 1 */ 842 843 wpa_s->prev_scan_ssid = ssid; 844 wpa_dbg(wpa_s, MSG_DEBUG, "Include wildcard SSID in " 845 "the scan request"); 846 params.num_ssids++; 847 } else if (wpa_s->last_scan_req == MANUAL_SCAN_REQ && 848 wpa_s->manual_scan_passive && params.num_ssids == 0) { 849 wpa_dbg(wpa_s, MSG_DEBUG, "Use passive scan based on manual request"); 850 } else { 851 wpa_s->prev_scan_ssid = WILDCARD_SSID_SCAN; 852 params.num_ssids++; 853 wpa_dbg(wpa_s, MSG_DEBUG, "Starting AP scan for wildcard " 854 "SSID"); 855 } 856 #ifdef CONFIG_P2P 857 ssid_list_set: 858 #endif /* CONFIG_P2P */ 859 860 wpa_supplicant_optimize_freqs(wpa_s, ¶ms); 861 extra_ie = wpa_supplicant_extra_ies(wpa_s); 862 863 if (wpa_s->last_scan_req == MANUAL_SCAN_REQ && 864 wpa_s->manual_scan_only_new) 865 params.only_new_results = 1; 866 867 if (wpa_s->last_scan_req == MANUAL_SCAN_REQ && params.freqs == NULL && 868 wpa_s->manual_scan_freqs) { 869 wpa_dbg(wpa_s, MSG_DEBUG, "Limit manual scan to specified channels"); 870 params.freqs = wpa_s->manual_scan_freqs; 871 wpa_s->manual_scan_freqs = NULL; 872 } 873 874 if (params.freqs == NULL && wpa_s->next_scan_freqs) { 875 wpa_dbg(wpa_s, MSG_DEBUG, "Optimize scan based on previously " 876 "generated frequency list"); 877 params.freqs = wpa_s->next_scan_freqs; 878 } else 879 os_free(wpa_s->next_scan_freqs); 880 wpa_s->next_scan_freqs = NULL; 881 wpa_setband_scan_freqs(wpa_s, ¶ms); 882 883 /* See if user specified frequencies. If so, scan only those. */ 884 if (wpa_s->conf->freq_list && !params.freqs) { 885 wpa_dbg(wpa_s, MSG_DEBUG, 886 "Optimize scan based on conf->freq_list"); 887 int_array_concat(¶ms.freqs, wpa_s->conf->freq_list); 888 } 889 890 /* Use current associated channel? */ 891 if (wpa_s->conf->scan_cur_freq && !params.freqs) { 892 unsigned int num = wpa_s->num_multichan_concurrent; 893 894 params.freqs = os_calloc(num + 1, sizeof(int)); 895 if (params.freqs) { 896 num = get_shared_radio_freqs(wpa_s, params.freqs, num); 897 if (num > 0) { 898 wpa_dbg(wpa_s, MSG_DEBUG, "Scan only the " 899 "current operating channels since " 900 "scan_cur_freq is enabled"); 901 } else { 902 os_free(params.freqs); 903 params.freqs = NULL; 904 } 905 } 906 } 907 908 params.filter_ssids = wpa_supplicant_build_filter_ssids( 909 wpa_s->conf, ¶ms.num_filter_ssids); 910 if (extra_ie) { 911 params.extra_ies = wpabuf_head(extra_ie); 912 params.extra_ies_len = wpabuf_len(extra_ie); 913 } 914 915 #ifdef CONFIG_P2P 916 if (wpa_s->p2p_in_provisioning || wpa_s->p2p_in_invitation || 917 (wpa_s->show_group_started && wpa_s->go_params)) { 918 /* 919 * The interface may not yet be in P2P mode, so we have to 920 * explicitly request P2P probe to disable CCK rates. 921 */ 922 params.p2p_probe = 1; 923 } 924 #endif /* CONFIG_P2P */ 925 926 scan_params = ¶ms; 927 928 scan: 929 #ifdef CONFIG_P2P 930 /* 931 * If the driver does not support multi-channel concurrency and a 932 * virtual interface that shares the same radio with the wpa_s interface 933 * is operating there may not be need to scan other channels apart from 934 * the current operating channel on the other virtual interface. Filter 935 * out other channels in case we are trying to find a connection for a 936 * station interface when we are not configured to prefer station 937 * connection and a concurrent operation is already in process. 938 */ 939 if (wpa_s->scan_for_connection && 940 wpa_s->last_scan_req == NORMAL_SCAN_REQ && 941 !scan_params->freqs && !params.freqs && 942 wpas_is_p2p_prioritized(wpa_s) && 943 wpa_s->p2p_group_interface == NOT_P2P_GROUP_INTERFACE && 944 non_p2p_network_enabled(wpa_s)) { 945 unsigned int num = wpa_s->num_multichan_concurrent; 946 947 params.freqs = os_calloc(num + 1, sizeof(int)); 948 if (params.freqs) { 949 num = get_shared_radio_freqs(wpa_s, params.freqs, num); 950 if (num > 0 && num == wpa_s->num_multichan_concurrent) { 951 wpa_dbg(wpa_s, MSG_DEBUG, "Scan only the current operating channels since all channels are already used"); 952 } else { 953 os_free(params.freqs); 954 params.freqs = NULL; 955 } 956 } 957 } 958 #endif /* CONFIG_P2P */ 959 960 ret = wpa_supplicant_trigger_scan(wpa_s, scan_params); 961 962 if (ret && wpa_s->last_scan_req == MANUAL_SCAN_REQ && params.freqs && 963 !wpa_s->manual_scan_freqs) { 964 /* Restore manual_scan_freqs for the next attempt */ 965 wpa_s->manual_scan_freqs = params.freqs; 966 params.freqs = NULL; 967 } 968 969 wpabuf_free(extra_ie); 970 os_free(params.freqs); 971 os_free(params.filter_ssids); 972 973 if (ret) { 974 wpa_msg(wpa_s, MSG_WARNING, "Failed to initiate AP scan"); 975 if (prev_state != wpa_s->wpa_state) 976 wpa_supplicant_set_state(wpa_s, prev_state); 977 /* Restore scan_req since we will try to scan again */ 978 wpa_s->scan_req = wpa_s->last_scan_req; 979 wpa_supplicant_req_scan(wpa_s, 1, 0); 980 } else { 981 wpa_s->scan_for_connection = 0; 982 } 983 } 984 985 986 void wpa_supplicant_update_scan_int(struct wpa_supplicant *wpa_s, int sec) 987 { 988 struct os_reltime remaining, new_int; 989 int cancelled; 990 991 cancelled = eloop_cancel_timeout_one(wpa_supplicant_scan, wpa_s, NULL, 992 &remaining); 993 994 new_int.sec = sec; 995 new_int.usec = 0; 996 if (cancelled && os_reltime_before(&remaining, &new_int)) { 997 new_int.sec = remaining.sec; 998 new_int.usec = remaining.usec; 999 } 1000 1001 if (cancelled) { 1002 eloop_register_timeout(new_int.sec, new_int.usec, 1003 wpa_supplicant_scan, wpa_s, NULL); 1004 } 1005 wpa_s->scan_interval = sec; 1006 } 1007 1008 1009 /** 1010 * wpa_supplicant_req_scan - Schedule a scan for neighboring access points 1011 * @wpa_s: Pointer to wpa_supplicant data 1012 * @sec: Number of seconds after which to scan 1013 * @usec: Number of microseconds after which to scan 1014 * 1015 * This function is used to schedule a scan for neighboring access points after 1016 * the specified time. 1017 */ 1018 void wpa_supplicant_req_scan(struct wpa_supplicant *wpa_s, int sec, int usec) 1019 { 1020 int res = eloop_deplete_timeout(sec, usec, wpa_supplicant_scan, wpa_s, 1021 NULL); 1022 if (res == 1) { 1023 wpa_dbg(wpa_s, MSG_DEBUG, "Rescheduling scan request: %d.%06d sec", 1024 sec, usec); 1025 } else if (res == 0) { 1026 wpa_dbg(wpa_s, MSG_DEBUG, "Ignore new scan request for %d.%06d sec since an earlier request is scheduled to trigger sooner", 1027 sec, usec); 1028 } else { 1029 wpa_dbg(wpa_s, MSG_DEBUG, "Setting scan request: %d.%06d sec", 1030 sec, usec); 1031 eloop_register_timeout(sec, usec, wpa_supplicant_scan, wpa_s, NULL); 1032 } 1033 } 1034 1035 1036 /** 1037 * wpa_supplicant_delayed_sched_scan - Request a delayed scheduled scan 1038 * @wpa_s: Pointer to wpa_supplicant data 1039 * @sec: Number of seconds after which to scan 1040 * @usec: Number of microseconds after which to scan 1041 * Returns: 0 on success or -1 otherwise 1042 * 1043 * This function is used to schedule periodic scans for neighboring 1044 * access points after the specified time. 1045 */ 1046 int wpa_supplicant_delayed_sched_scan(struct wpa_supplicant *wpa_s, 1047 int sec, int usec) 1048 { 1049 if (!wpa_s->sched_scan_supported) 1050 return -1; 1051 1052 eloop_register_timeout(sec, usec, 1053 wpa_supplicant_delayed_sched_scan_timeout, 1054 wpa_s, NULL); 1055 1056 return 0; 1057 } 1058 1059 1060 /** 1061 * wpa_supplicant_req_sched_scan - Start a periodic scheduled scan 1062 * @wpa_s: Pointer to wpa_supplicant data 1063 * Returns: 0 is sched_scan was started or -1 otherwise 1064 * 1065 * This function is used to schedule periodic scans for neighboring 1066 * access points repeating the scan continuously. 1067 */ 1068 int wpa_supplicant_req_sched_scan(struct wpa_supplicant *wpa_s) 1069 { 1070 struct wpa_driver_scan_params params; 1071 struct wpa_driver_scan_params *scan_params; 1072 enum wpa_states prev_state; 1073 struct wpa_ssid *ssid = NULL; 1074 struct wpabuf *extra_ie = NULL; 1075 int ret; 1076 unsigned int max_sched_scan_ssids; 1077 int wildcard = 0; 1078 int need_ssids; 1079 1080 if (!wpa_s->sched_scan_supported) 1081 return -1; 1082 1083 if (wpa_s->max_sched_scan_ssids > WPAS_MAX_SCAN_SSIDS) 1084 max_sched_scan_ssids = WPAS_MAX_SCAN_SSIDS; 1085 else 1086 max_sched_scan_ssids = wpa_s->max_sched_scan_ssids; 1087 if (max_sched_scan_ssids < 1 || wpa_s->conf->disable_scan_offload) 1088 return -1; 1089 1090 if (wpa_s->sched_scanning) { 1091 wpa_dbg(wpa_s, MSG_DEBUG, "Already sched scanning"); 1092 return 0; 1093 } 1094 1095 need_ssids = 0; 1096 for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { 1097 if (!wpas_network_disabled(wpa_s, ssid) && !ssid->scan_ssid) { 1098 /* Use wildcard SSID to find this network */ 1099 wildcard = 1; 1100 } else if (!wpas_network_disabled(wpa_s, ssid) && 1101 ssid->ssid_len) 1102 need_ssids++; 1103 1104 #ifdef CONFIG_WPS 1105 if (!wpas_network_disabled(wpa_s, ssid) && 1106 ssid->key_mgmt == WPA_KEY_MGMT_WPS) { 1107 /* 1108 * Normal scan is more reliable and faster for WPS 1109 * operations and since these are for short periods of 1110 * time, the benefit of trying to use sched_scan would 1111 * be limited. 1112 */ 1113 wpa_dbg(wpa_s, MSG_DEBUG, "Use normal scan instead of " 1114 "sched_scan for WPS"); 1115 return -1; 1116 } 1117 #endif /* CONFIG_WPS */ 1118 } 1119 if (wildcard) 1120 need_ssids++; 1121 1122 if (wpa_s->normal_scans < 3 && 1123 (need_ssids <= wpa_s->max_scan_ssids || 1124 wpa_s->max_scan_ssids >= (int) max_sched_scan_ssids)) { 1125 /* 1126 * When normal scan can speed up operations, use that for the 1127 * first operations before starting the sched_scan to allow 1128 * user space sleep more. We do this only if the normal scan 1129 * has functionality that is suitable for this or if the 1130 * sched_scan does not have better support for multiple SSIDs. 1131 */ 1132 wpa_dbg(wpa_s, MSG_DEBUG, "Use normal scan instead of " 1133 "sched_scan for initial scans (normal_scans=%d)", 1134 wpa_s->normal_scans); 1135 return -1; 1136 } 1137 1138 os_memset(¶ms, 0, sizeof(params)); 1139 1140 /* If we can't allocate space for the filters, we just don't filter */ 1141 params.filter_ssids = os_zalloc(wpa_s->max_match_sets * 1142 sizeof(struct wpa_driver_scan_filter)); 1143 1144 prev_state = wpa_s->wpa_state; 1145 if (wpa_s->wpa_state == WPA_DISCONNECTED || 1146 wpa_s->wpa_state == WPA_INACTIVE) 1147 wpa_supplicant_set_state(wpa_s, WPA_SCANNING); 1148 1149 if (wpa_s->autoscan_params != NULL) { 1150 scan_params = wpa_s->autoscan_params; 1151 goto scan; 1152 } 1153 1154 /* Find the starting point from which to continue scanning */ 1155 ssid = wpa_s->conf->ssid; 1156 if (wpa_s->prev_sched_ssid) { 1157 while (ssid) { 1158 if (ssid == wpa_s->prev_sched_ssid) { 1159 ssid = ssid->next; 1160 break; 1161 } 1162 ssid = ssid->next; 1163 } 1164 } 1165 1166 if (!ssid || !wpa_s->prev_sched_ssid) { 1167 wpa_dbg(wpa_s, MSG_DEBUG, "Beginning of SSID list"); 1168 if (wpa_s->conf->sched_scan_interval) 1169 wpa_s->sched_scan_interval = 1170 wpa_s->conf->sched_scan_interval; 1171 if (wpa_s->sched_scan_interval == 0) 1172 wpa_s->sched_scan_interval = 10; 1173 wpa_s->sched_scan_timeout = max_sched_scan_ssids * 2; 1174 wpa_s->first_sched_scan = 1; 1175 ssid = wpa_s->conf->ssid; 1176 wpa_s->prev_sched_ssid = ssid; 1177 } 1178 1179 if (wildcard) { 1180 wpa_dbg(wpa_s, MSG_DEBUG, "Add wildcard SSID to sched_scan"); 1181 params.num_ssids++; 1182 } 1183 1184 while (ssid) { 1185 if (wpas_network_disabled(wpa_s, ssid)) 1186 goto next; 1187 1188 if (params.num_filter_ssids < wpa_s->max_match_sets && 1189 params.filter_ssids && ssid->ssid && ssid->ssid_len) { 1190 wpa_dbg(wpa_s, MSG_DEBUG, "add to filter ssid: %s", 1191 wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 1192 os_memcpy(params.filter_ssids[params.num_filter_ssids].ssid, 1193 ssid->ssid, ssid->ssid_len); 1194 params.filter_ssids[params.num_filter_ssids].ssid_len = 1195 ssid->ssid_len; 1196 params.num_filter_ssids++; 1197 } else if (params.filter_ssids && ssid->ssid && ssid->ssid_len) 1198 { 1199 wpa_dbg(wpa_s, MSG_DEBUG, "Not enough room for SSID " 1200 "filter for sched_scan - drop filter"); 1201 os_free(params.filter_ssids); 1202 params.filter_ssids = NULL; 1203 params.num_filter_ssids = 0; 1204 } 1205 1206 if (ssid->scan_ssid && ssid->ssid && ssid->ssid_len) { 1207 if (params.num_ssids == max_sched_scan_ssids) 1208 break; /* only room for broadcast SSID */ 1209 wpa_dbg(wpa_s, MSG_DEBUG, 1210 "add to active scan ssid: %s", 1211 wpa_ssid_txt(ssid->ssid, ssid->ssid_len)); 1212 params.ssids[params.num_ssids].ssid = 1213 ssid->ssid; 1214 params.ssids[params.num_ssids].ssid_len = 1215 ssid->ssid_len; 1216 params.num_ssids++; 1217 if (params.num_ssids >= max_sched_scan_ssids) { 1218 wpa_s->prev_sched_ssid = ssid; 1219 do { 1220 ssid = ssid->next; 1221 } while (ssid && 1222 (wpas_network_disabled(wpa_s, ssid) || 1223 !ssid->scan_ssid)); 1224 break; 1225 } 1226 } 1227 1228 next: 1229 wpa_s->prev_sched_ssid = ssid; 1230 ssid = ssid->next; 1231 } 1232 1233 if (params.num_filter_ssids == 0) { 1234 os_free(params.filter_ssids); 1235 params.filter_ssids = NULL; 1236 } 1237 1238 extra_ie = wpa_supplicant_extra_ies(wpa_s); 1239 if (extra_ie) { 1240 params.extra_ies = wpabuf_head(extra_ie); 1241 params.extra_ies_len = wpabuf_len(extra_ie); 1242 } 1243 1244 if (wpa_s->conf->filter_rssi) 1245 params.filter_rssi = wpa_s->conf->filter_rssi; 1246 1247 scan_params = ¶ms; 1248 1249 scan: 1250 if (ssid || !wpa_s->first_sched_scan) { 1251 wpa_dbg(wpa_s, MSG_DEBUG, 1252 "Starting sched scan: interval %d timeout %d", 1253 wpa_s->sched_scan_interval, wpa_s->sched_scan_timeout); 1254 } else { 1255 wpa_dbg(wpa_s, MSG_DEBUG, 1256 "Starting sched scan: interval %d (no timeout)", 1257 wpa_s->sched_scan_interval); 1258 } 1259 1260 wpa_setband_scan_freqs(wpa_s, scan_params); 1261 1262 ret = wpa_supplicant_start_sched_scan(wpa_s, scan_params, 1263 wpa_s->sched_scan_interval); 1264 wpabuf_free(extra_ie); 1265 os_free(params.filter_ssids); 1266 if (ret) { 1267 wpa_msg(wpa_s, MSG_WARNING, "Failed to initiate sched scan"); 1268 if (prev_state != wpa_s->wpa_state) 1269 wpa_supplicant_set_state(wpa_s, prev_state); 1270 return ret; 1271 } 1272 1273 /* If we have more SSIDs to scan, add a timeout so we scan them too */ 1274 if (ssid || !wpa_s->first_sched_scan) { 1275 wpa_s->sched_scan_timed_out = 0; 1276 eloop_register_timeout(wpa_s->sched_scan_timeout, 0, 1277 wpa_supplicant_sched_scan_timeout, 1278 wpa_s, NULL); 1279 wpa_s->first_sched_scan = 0; 1280 wpa_s->sched_scan_timeout /= 2; 1281 wpa_s->sched_scan_interval *= 2; 1282 if (wpa_s->sched_scan_timeout < wpa_s->sched_scan_interval) { 1283 wpa_s->sched_scan_interval = 10; 1284 wpa_s->sched_scan_timeout = max_sched_scan_ssids * 2; 1285 } 1286 } 1287 1288 /* If there is no more ssids, start next time from the beginning */ 1289 if (!ssid) 1290 wpa_s->prev_sched_ssid = NULL; 1291 1292 return 0; 1293 } 1294 1295 1296 /** 1297 * wpa_supplicant_cancel_scan - Cancel a scheduled scan request 1298 * @wpa_s: Pointer to wpa_supplicant data 1299 * 1300 * This function is used to cancel a scan request scheduled with 1301 * wpa_supplicant_req_scan(). 1302 */ 1303 void wpa_supplicant_cancel_scan(struct wpa_supplicant *wpa_s) 1304 { 1305 wpa_dbg(wpa_s, MSG_DEBUG, "Cancelling scan request"); 1306 eloop_cancel_timeout(wpa_supplicant_scan, wpa_s, NULL); 1307 } 1308 1309 1310 /** 1311 * wpa_supplicant_cancel_delayed_sched_scan - Stop a delayed scheduled scan 1312 * @wpa_s: Pointer to wpa_supplicant data 1313 * 1314 * This function is used to stop a delayed scheduled scan. 1315 */ 1316 void wpa_supplicant_cancel_delayed_sched_scan(struct wpa_supplicant *wpa_s) 1317 { 1318 if (!wpa_s->sched_scan_supported) 1319 return; 1320 1321 wpa_dbg(wpa_s, MSG_DEBUG, "Cancelling delayed sched scan"); 1322 eloop_cancel_timeout(wpa_supplicant_delayed_sched_scan_timeout, 1323 wpa_s, NULL); 1324 } 1325 1326 1327 /** 1328 * wpa_supplicant_cancel_sched_scan - Stop running scheduled scans 1329 * @wpa_s: Pointer to wpa_supplicant data 1330 * 1331 * This function is used to stop a periodic scheduled scan. 1332 */ 1333 void wpa_supplicant_cancel_sched_scan(struct wpa_supplicant *wpa_s) 1334 { 1335 if (!wpa_s->sched_scanning) 1336 return; 1337 1338 wpa_dbg(wpa_s, MSG_DEBUG, "Cancelling sched scan"); 1339 eloop_cancel_timeout(wpa_supplicant_sched_scan_timeout, wpa_s, NULL); 1340 wpa_supplicant_stop_sched_scan(wpa_s); 1341 } 1342 1343 1344 /** 1345 * wpa_supplicant_notify_scanning - Indicate possible scan state change 1346 * @wpa_s: Pointer to wpa_supplicant data 1347 * @scanning: Whether scanning is currently in progress 1348 * 1349 * This function is to generate scanning notifycations. It is called whenever 1350 * there may have been a change in scanning (scan started, completed, stopped). 1351 * wpas_notify_scanning() is called whenever the scanning state changed from the 1352 * previously notified state. 1353 */ 1354 void wpa_supplicant_notify_scanning(struct wpa_supplicant *wpa_s, 1355 int scanning) 1356 { 1357 if (wpa_s->scanning != scanning) { 1358 wpa_s->scanning = scanning; 1359 wpas_notify_scanning(wpa_s); 1360 } 1361 } 1362 1363 1364 static int wpa_scan_get_max_rate(const struct wpa_scan_res *res) 1365 { 1366 int rate = 0; 1367 const u8 *ie; 1368 int i; 1369 1370 ie = wpa_scan_get_ie(res, WLAN_EID_SUPP_RATES); 1371 for (i = 0; ie && i < ie[1]; i++) { 1372 if ((ie[i + 2] & 0x7f) > rate) 1373 rate = ie[i + 2] & 0x7f; 1374 } 1375 1376 ie = wpa_scan_get_ie(res, WLAN_EID_EXT_SUPP_RATES); 1377 for (i = 0; ie && i < ie[1]; i++) { 1378 if ((ie[i + 2] & 0x7f) > rate) 1379 rate = ie[i + 2] & 0x7f; 1380 } 1381 1382 return rate; 1383 } 1384 1385 1386 /** 1387 * wpa_scan_get_ie - Fetch a specified information element from a scan result 1388 * @res: Scan result entry 1389 * @ie: Information element identitifier (WLAN_EID_*) 1390 * Returns: Pointer to the information element (id field) or %NULL if not found 1391 * 1392 * This function returns the first matching information element in the scan 1393 * result. 1394 */ 1395 const u8 * wpa_scan_get_ie(const struct wpa_scan_res *res, u8 ie) 1396 { 1397 const u8 *end, *pos; 1398 1399 pos = (const u8 *) (res + 1); 1400 end = pos + res->ie_len; 1401 1402 while (pos + 1 < end) { 1403 if (pos + 2 + pos[1] > end) 1404 break; 1405 if (pos[0] == ie) 1406 return pos; 1407 pos += 2 + pos[1]; 1408 } 1409 1410 return NULL; 1411 } 1412 1413 1414 /** 1415 * wpa_scan_get_vendor_ie - Fetch vendor information element from a scan result 1416 * @res: Scan result entry 1417 * @vendor_type: Vendor type (four octets starting the IE payload) 1418 * Returns: Pointer to the information element (id field) or %NULL if not found 1419 * 1420 * This function returns the first matching information element in the scan 1421 * result. 1422 */ 1423 const u8 * wpa_scan_get_vendor_ie(const struct wpa_scan_res *res, 1424 u32 vendor_type) 1425 { 1426 const u8 *end, *pos; 1427 1428 pos = (const u8 *) (res + 1); 1429 end = pos + res->ie_len; 1430 1431 while (pos + 1 < end) { 1432 if (pos + 2 + pos[1] > end) 1433 break; 1434 if (pos[0] == WLAN_EID_VENDOR_SPECIFIC && pos[1] >= 4 && 1435 vendor_type == WPA_GET_BE32(&pos[2])) 1436 return pos; 1437 pos += 2 + pos[1]; 1438 } 1439 1440 return NULL; 1441 } 1442 1443 1444 /** 1445 * wpa_scan_get_vendor_ie_beacon - Fetch vendor information from a scan result 1446 * @res: Scan result entry 1447 * @vendor_type: Vendor type (four octets starting the IE payload) 1448 * Returns: Pointer to the information element (id field) or %NULL if not found 1449 * 1450 * This function returns the first matching information element in the scan 1451 * result. 1452 * 1453 * This function is like wpa_scan_get_vendor_ie(), but uses IE buffer only 1454 * from Beacon frames instead of either Beacon or Probe Response frames. 1455 */ 1456 const u8 * wpa_scan_get_vendor_ie_beacon(const struct wpa_scan_res *res, 1457 u32 vendor_type) 1458 { 1459 const u8 *end, *pos; 1460 1461 if (res->beacon_ie_len == 0) 1462 return NULL; 1463 1464 pos = (const u8 *) (res + 1); 1465 pos += res->ie_len; 1466 end = pos + res->beacon_ie_len; 1467 1468 while (pos + 1 < end) { 1469 if (pos + 2 + pos[1] > end) 1470 break; 1471 if (pos[0] == WLAN_EID_VENDOR_SPECIFIC && pos[1] >= 4 && 1472 vendor_type == WPA_GET_BE32(&pos[2])) 1473 return pos; 1474 pos += 2 + pos[1]; 1475 } 1476 1477 return NULL; 1478 } 1479 1480 1481 /** 1482 * wpa_scan_get_vendor_ie_multi - Fetch vendor IE data from a scan result 1483 * @res: Scan result entry 1484 * @vendor_type: Vendor type (four octets starting the IE payload) 1485 * Returns: Pointer to the information element payload or %NULL if not found 1486 * 1487 * This function returns concatenated payload of possibly fragmented vendor 1488 * specific information elements in the scan result. The caller is responsible 1489 * for freeing the returned buffer. 1490 */ 1491 struct wpabuf * wpa_scan_get_vendor_ie_multi(const struct wpa_scan_res *res, 1492 u32 vendor_type) 1493 { 1494 struct wpabuf *buf; 1495 const u8 *end, *pos; 1496 1497 buf = wpabuf_alloc(res->ie_len); 1498 if (buf == NULL) 1499 return NULL; 1500 1501 pos = (const u8 *) (res + 1); 1502 end = pos + res->ie_len; 1503 1504 while (pos + 1 < end) { 1505 if (pos + 2 + pos[1] > end) 1506 break; 1507 if (pos[0] == WLAN_EID_VENDOR_SPECIFIC && pos[1] >= 4 && 1508 vendor_type == WPA_GET_BE32(&pos[2])) 1509 wpabuf_put_data(buf, pos + 2 + 4, pos[1] - 4); 1510 pos += 2 + pos[1]; 1511 } 1512 1513 if (wpabuf_len(buf) == 0) { 1514 wpabuf_free(buf); 1515 buf = NULL; 1516 } 1517 1518 return buf; 1519 } 1520 1521 1522 /* 1523 * Channels with a great SNR can operate at full rate. What is a great SNR? 1524 * This doc https://supportforums.cisco.com/docs/DOC-12954 says, "the general 1525 * rule of thumb is that any SNR above 20 is good." This one 1526 * http://www.cisco.com/en/US/tech/tk722/tk809/technologies_q_and_a_item09186a00805e9a96.shtml#qa23 1527 * recommends 25 as a minimum SNR for 54 Mbps data rate. 30 is chosen here as a 1528 * conservative value. 1529 */ 1530 #define GREAT_SNR 30 1531 1532 /* Compare function for sorting scan results. Return >0 if @b is considered 1533 * better. */ 1534 static int wpa_scan_result_compar(const void *a, const void *b) 1535 { 1536 #define IS_5GHZ(n) (n > 4000) 1537 #define MIN(a,b) a < b ? a : b 1538 struct wpa_scan_res **_wa = (void *) a; 1539 struct wpa_scan_res **_wb = (void *) b; 1540 struct wpa_scan_res *wa = *_wa; 1541 struct wpa_scan_res *wb = *_wb; 1542 int wpa_a, wpa_b, maxrate_a, maxrate_b; 1543 int snr_a, snr_b; 1544 1545 /* WPA/WPA2 support preferred */ 1546 wpa_a = wpa_scan_get_vendor_ie(wa, WPA_IE_VENDOR_TYPE) != NULL || 1547 wpa_scan_get_ie(wa, WLAN_EID_RSN) != NULL; 1548 wpa_b = wpa_scan_get_vendor_ie(wb, WPA_IE_VENDOR_TYPE) != NULL || 1549 wpa_scan_get_ie(wb, WLAN_EID_RSN) != NULL; 1550 1551 if (wpa_b && !wpa_a) 1552 return 1; 1553 if (!wpa_b && wpa_a) 1554 return -1; 1555 1556 /* privacy support preferred */ 1557 if ((wa->caps & IEEE80211_CAP_PRIVACY) == 0 && 1558 (wb->caps & IEEE80211_CAP_PRIVACY)) 1559 return 1; 1560 if ((wa->caps & IEEE80211_CAP_PRIVACY) && 1561 (wb->caps & IEEE80211_CAP_PRIVACY) == 0) 1562 return -1; 1563 1564 if ((wa->flags & wb->flags & WPA_SCAN_LEVEL_DBM) && 1565 !((wa->flags | wb->flags) & WPA_SCAN_NOISE_INVALID)) { 1566 snr_a = MIN(wa->level - wa->noise, GREAT_SNR); 1567 snr_b = MIN(wb->level - wb->noise, GREAT_SNR); 1568 } else { 1569 /* Not suitable information to calculate SNR, so use level */ 1570 snr_a = wa->level; 1571 snr_b = wb->level; 1572 } 1573 1574 /* best/max rate preferred if SNR close enough */ 1575 if ((snr_a && snr_b && abs(snr_b - snr_a) < 5) || 1576 (wa->qual && wb->qual && abs(wb->qual - wa->qual) < 10)) { 1577 maxrate_a = wpa_scan_get_max_rate(wa); 1578 maxrate_b = wpa_scan_get_max_rate(wb); 1579 if (maxrate_a != maxrate_b) 1580 return maxrate_b - maxrate_a; 1581 if (IS_5GHZ(wa->freq) ^ IS_5GHZ(wb->freq)) 1582 return IS_5GHZ(wa->freq) ? -1 : 1; 1583 } 1584 1585 /* use freq for channel preference */ 1586 1587 /* all things being equal, use SNR; if SNRs are 1588 * identical, use quality values since some drivers may only report 1589 * that value and leave the signal level zero */ 1590 if (snr_b == snr_a) 1591 return wb->qual - wa->qual; 1592 return snr_b - snr_a; 1593 #undef MIN 1594 #undef IS_5GHZ 1595 } 1596 1597 1598 #ifdef CONFIG_WPS 1599 /* Compare function for sorting scan results when searching a WPS AP for 1600 * provisioning. Return >0 if @b is considered better. */ 1601 static int wpa_scan_result_wps_compar(const void *a, const void *b) 1602 { 1603 struct wpa_scan_res **_wa = (void *) a; 1604 struct wpa_scan_res **_wb = (void *) b; 1605 struct wpa_scan_res *wa = *_wa; 1606 struct wpa_scan_res *wb = *_wb; 1607 int uses_wps_a, uses_wps_b; 1608 struct wpabuf *wps_a, *wps_b; 1609 int res; 1610 1611 /* Optimization - check WPS IE existence before allocated memory and 1612 * doing full reassembly. */ 1613 uses_wps_a = wpa_scan_get_vendor_ie(wa, WPS_IE_VENDOR_TYPE) != NULL; 1614 uses_wps_b = wpa_scan_get_vendor_ie(wb, WPS_IE_VENDOR_TYPE) != NULL; 1615 if (uses_wps_a && !uses_wps_b) 1616 return -1; 1617 if (!uses_wps_a && uses_wps_b) 1618 return 1; 1619 1620 if (uses_wps_a && uses_wps_b) { 1621 wps_a = wpa_scan_get_vendor_ie_multi(wa, WPS_IE_VENDOR_TYPE); 1622 wps_b = wpa_scan_get_vendor_ie_multi(wb, WPS_IE_VENDOR_TYPE); 1623 res = wps_ap_priority_compar(wps_a, wps_b); 1624 wpabuf_free(wps_a); 1625 wpabuf_free(wps_b); 1626 if (res) 1627 return res; 1628 } 1629 1630 /* 1631 * Do not use current AP security policy as a sorting criteria during 1632 * WPS provisioning step since the AP may get reconfigured at the 1633 * completion of provisioning. 1634 */ 1635 1636 /* all things being equal, use signal level; if signal levels are 1637 * identical, use quality values since some drivers may only report 1638 * that value and leave the signal level zero */ 1639 if (wb->level == wa->level) 1640 return wb->qual - wa->qual; 1641 return wb->level - wa->level; 1642 } 1643 #endif /* CONFIG_WPS */ 1644 1645 1646 static void dump_scan_res(struct wpa_scan_results *scan_res) 1647 { 1648 #ifndef CONFIG_NO_STDOUT_DEBUG 1649 size_t i; 1650 1651 if (scan_res->res == NULL || scan_res->num == 0) 1652 return; 1653 1654 wpa_printf(MSG_EXCESSIVE, "Sorted scan results"); 1655 1656 for (i = 0; i < scan_res->num; i++) { 1657 struct wpa_scan_res *r = scan_res->res[i]; 1658 u8 *pos; 1659 if ((r->flags & (WPA_SCAN_LEVEL_DBM | WPA_SCAN_NOISE_INVALID)) 1660 == WPA_SCAN_LEVEL_DBM) { 1661 int snr = r->level - r->noise; 1662 wpa_printf(MSG_EXCESSIVE, MACSTR " freq=%d qual=%d " 1663 "noise=%d level=%d snr=%d%s flags=0x%x " 1664 "age=%u", 1665 MAC2STR(r->bssid), r->freq, r->qual, 1666 r->noise, r->level, snr, 1667 snr >= GREAT_SNR ? "*" : "", r->flags, 1668 r->age); 1669 } else { 1670 wpa_printf(MSG_EXCESSIVE, MACSTR " freq=%d qual=%d " 1671 "noise=%d level=%d flags=0x%x age=%u", 1672 MAC2STR(r->bssid), r->freq, r->qual, 1673 r->noise, r->level, r->flags, r->age); 1674 } 1675 pos = (u8 *) (r + 1); 1676 if (r->ie_len) 1677 wpa_hexdump(MSG_EXCESSIVE, "IEs", pos, r->ie_len); 1678 pos += r->ie_len; 1679 if (r->beacon_ie_len) 1680 wpa_hexdump(MSG_EXCESSIVE, "Beacon IEs", 1681 pos, r->beacon_ie_len); 1682 } 1683 #endif /* CONFIG_NO_STDOUT_DEBUG */ 1684 } 1685 1686 1687 /** 1688 * wpa_supplicant_filter_bssid_match - Is the specified BSSID allowed 1689 * @wpa_s: Pointer to wpa_supplicant data 1690 * @bssid: BSSID to check 1691 * Returns: 0 if the BSSID is filtered or 1 if not 1692 * 1693 * This function is used to filter out specific BSSIDs from scan reslts mainly 1694 * for testing purposes (SET bssid_filter ctrl_iface command). 1695 */ 1696 int wpa_supplicant_filter_bssid_match(struct wpa_supplicant *wpa_s, 1697 const u8 *bssid) 1698 { 1699 size_t i; 1700 1701 if (wpa_s->bssid_filter == NULL) 1702 return 1; 1703 1704 for (i = 0; i < wpa_s->bssid_filter_count; i++) { 1705 if (os_memcmp(wpa_s->bssid_filter + i * ETH_ALEN, bssid, 1706 ETH_ALEN) == 0) 1707 return 1; 1708 } 1709 1710 return 0; 1711 } 1712 1713 1714 static void filter_scan_res(struct wpa_supplicant *wpa_s, 1715 struct wpa_scan_results *res) 1716 { 1717 size_t i, j; 1718 1719 if (wpa_s->bssid_filter == NULL) 1720 return; 1721 1722 for (i = 0, j = 0; i < res->num; i++) { 1723 if (wpa_supplicant_filter_bssid_match(wpa_s, 1724 res->res[i]->bssid)) { 1725 res->res[j++] = res->res[i]; 1726 } else { 1727 os_free(res->res[i]); 1728 res->res[i] = NULL; 1729 } 1730 } 1731 1732 if (res->num != j) { 1733 wpa_printf(MSG_DEBUG, "Filtered out %d scan results", 1734 (int) (res->num - j)); 1735 res->num = j; 1736 } 1737 } 1738 1739 1740 /** 1741 * wpa_supplicant_get_scan_results - Get scan results 1742 * @wpa_s: Pointer to wpa_supplicant data 1743 * @info: Information about what was scanned or %NULL if not available 1744 * @new_scan: Whether a new scan was performed 1745 * Returns: Scan results, %NULL on failure 1746 * 1747 * This function request the current scan results from the driver and updates 1748 * the local BSS list wpa_s->bss. The caller is responsible for freeing the 1749 * results with wpa_scan_results_free(). 1750 */ 1751 struct wpa_scan_results * 1752 wpa_supplicant_get_scan_results(struct wpa_supplicant *wpa_s, 1753 struct scan_info *info, int new_scan) 1754 { 1755 struct wpa_scan_results *scan_res; 1756 size_t i; 1757 int (*compar)(const void *, const void *) = wpa_scan_result_compar; 1758 1759 scan_res = wpa_drv_get_scan_results2(wpa_s); 1760 if (scan_res == NULL) { 1761 wpa_dbg(wpa_s, MSG_DEBUG, "Failed to get scan results"); 1762 return NULL; 1763 } 1764 if (scan_res->fetch_time.sec == 0) { 1765 /* 1766 * Make sure we have a valid timestamp if the driver wrapper 1767 * does not set this. 1768 */ 1769 os_get_reltime(&scan_res->fetch_time); 1770 } 1771 filter_scan_res(wpa_s, scan_res); 1772 1773 #ifdef CONFIG_WPS 1774 if (wpas_wps_searching(wpa_s)) { 1775 wpa_dbg(wpa_s, MSG_DEBUG, "WPS: Order scan results with WPS " 1776 "provisioning rules"); 1777 compar = wpa_scan_result_wps_compar; 1778 } 1779 #endif /* CONFIG_WPS */ 1780 1781 qsort(scan_res->res, scan_res->num, sizeof(struct wpa_scan_res *), 1782 compar); 1783 dump_scan_res(scan_res); 1784 1785 wpa_bss_update_start(wpa_s); 1786 for (i = 0; i < scan_res->num; i++) 1787 wpa_bss_update_scan_res(wpa_s, scan_res->res[i], 1788 &scan_res->fetch_time); 1789 wpa_bss_update_end(wpa_s, info, new_scan); 1790 1791 return scan_res; 1792 } 1793 1794 1795 /** 1796 * wpa_supplicant_update_scan_results - Update scan results from the driver 1797 * @wpa_s: Pointer to wpa_supplicant data 1798 * Returns: 0 on success, -1 on failure 1799 * 1800 * This function updates the BSS table within wpa_supplicant based on the 1801 * currently available scan results from the driver without requesting a new 1802 * scan. This is used in cases where the driver indicates an association 1803 * (including roaming within ESS) and wpa_supplicant does not yet have the 1804 * needed information to complete the connection (e.g., to perform validation 1805 * steps in 4-way handshake). 1806 */ 1807 int wpa_supplicant_update_scan_results(struct wpa_supplicant *wpa_s) 1808 { 1809 struct wpa_scan_results *scan_res; 1810 scan_res = wpa_supplicant_get_scan_results(wpa_s, NULL, 0); 1811 if (scan_res == NULL) 1812 return -1; 1813 wpa_scan_results_free(scan_res); 1814 1815 return 0; 1816 } 1817 1818 1819 /** 1820 * scan_only_handler - Reports scan results 1821 */ 1822 void scan_only_handler(struct wpa_supplicant *wpa_s, 1823 struct wpa_scan_results *scan_res) 1824 { 1825 wpa_dbg(wpa_s, MSG_DEBUG, "Scan-only results received"); 1826 if (wpa_s->last_scan_req == MANUAL_SCAN_REQ && 1827 wpa_s->manual_scan_use_id && wpa_s->own_scan_running) { 1828 wpa_msg_ctrl(wpa_s, MSG_INFO, WPA_EVENT_SCAN_RESULTS "id=%u", 1829 wpa_s->manual_scan_id); 1830 wpa_s->manual_scan_use_id = 0; 1831 } else { 1832 wpa_msg_ctrl(wpa_s, MSG_INFO, WPA_EVENT_SCAN_RESULTS); 1833 } 1834 wpas_notify_scan_results(wpa_s); 1835 wpas_notify_scan_done(wpa_s, 1); 1836 if (wpa_s->scan_work) { 1837 struct wpa_radio_work *work = wpa_s->scan_work; 1838 wpa_s->scan_work = NULL; 1839 radio_work_done(work); 1840 } 1841 } 1842 1843 1844 int wpas_scan_scheduled(struct wpa_supplicant *wpa_s) 1845 { 1846 return eloop_is_timeout_registered(wpa_supplicant_scan, wpa_s, NULL); 1847 } 1848 1849 1850 struct wpa_driver_scan_params * 1851 wpa_scan_clone_params(const struct wpa_driver_scan_params *src) 1852 { 1853 struct wpa_driver_scan_params *params; 1854 size_t i; 1855 u8 *n; 1856 1857 params = os_zalloc(sizeof(*params)); 1858 if (params == NULL) 1859 return NULL; 1860 1861 for (i = 0; i < src->num_ssids; i++) { 1862 if (src->ssids[i].ssid) { 1863 n = os_malloc(src->ssids[i].ssid_len); 1864 if (n == NULL) 1865 goto failed; 1866 os_memcpy(n, src->ssids[i].ssid, 1867 src->ssids[i].ssid_len); 1868 params->ssids[i].ssid = n; 1869 params->ssids[i].ssid_len = src->ssids[i].ssid_len; 1870 } 1871 } 1872 params->num_ssids = src->num_ssids; 1873 1874 if (src->extra_ies) { 1875 n = os_malloc(src->extra_ies_len); 1876 if (n == NULL) 1877 goto failed; 1878 os_memcpy(n, src->extra_ies, src->extra_ies_len); 1879 params->extra_ies = n; 1880 params->extra_ies_len = src->extra_ies_len; 1881 } 1882 1883 if (src->freqs) { 1884 int len = int_array_len(src->freqs); 1885 params->freqs = os_malloc((len + 1) * sizeof(int)); 1886 if (params->freqs == NULL) 1887 goto failed; 1888 os_memcpy(params->freqs, src->freqs, (len + 1) * sizeof(int)); 1889 } 1890 1891 if (src->filter_ssids) { 1892 params->filter_ssids = os_malloc(sizeof(*params->filter_ssids) * 1893 src->num_filter_ssids); 1894 if (params->filter_ssids == NULL) 1895 goto failed; 1896 os_memcpy(params->filter_ssids, src->filter_ssids, 1897 sizeof(*params->filter_ssids) * 1898 src->num_filter_ssids); 1899 params->num_filter_ssids = src->num_filter_ssids; 1900 } 1901 1902 params->filter_rssi = src->filter_rssi; 1903 params->p2p_probe = src->p2p_probe; 1904 params->only_new_results = src->only_new_results; 1905 params->low_priority = src->low_priority; 1906 1907 return params; 1908 1909 failed: 1910 wpa_scan_free_params(params); 1911 return NULL; 1912 } 1913 1914 1915 void wpa_scan_free_params(struct wpa_driver_scan_params *params) 1916 { 1917 size_t i; 1918 1919 if (params == NULL) 1920 return; 1921 1922 for (i = 0; i < params->num_ssids; i++) 1923 os_free((u8 *) params->ssids[i].ssid); 1924 os_free((u8 *) params->extra_ies); 1925 os_free(params->freqs); 1926 os_free(params->filter_ssids); 1927 os_free(params); 1928 } 1929 1930 1931 int wpas_start_pno(struct wpa_supplicant *wpa_s) 1932 { 1933 int ret, interval; 1934 size_t i, num_ssid, num_match_ssid; 1935 struct wpa_ssid *ssid; 1936 struct wpa_driver_scan_params params; 1937 1938 if (!wpa_s->sched_scan_supported) 1939 return -1; 1940 1941 if (wpa_s->pno || wpa_s->pno_sched_pending) 1942 return 0; 1943 1944 if ((wpa_s->wpa_state > WPA_SCANNING) && 1945 (wpa_s->wpa_state <= WPA_COMPLETED)) { 1946 wpa_printf(MSG_ERROR, "PNO: In assoc process"); 1947 return -EAGAIN; 1948 } 1949 1950 if (wpa_s->wpa_state == WPA_SCANNING) { 1951 wpa_supplicant_cancel_scan(wpa_s); 1952 if (wpa_s->sched_scanning) { 1953 wpa_printf(MSG_DEBUG, "Schedule PNO on completion of " 1954 "ongoing sched scan"); 1955 wpa_supplicant_cancel_sched_scan(wpa_s); 1956 wpa_s->pno_sched_pending = 1; 1957 return 0; 1958 } 1959 } 1960 1961 os_memset(¶ms, 0, sizeof(params)); 1962 1963 num_ssid = num_match_ssid = 0; 1964 ssid = wpa_s->conf->ssid; 1965 while (ssid) { 1966 if (!wpas_network_disabled(wpa_s, ssid)) { 1967 num_match_ssid++; 1968 if (ssid->scan_ssid) 1969 num_ssid++; 1970 } 1971 ssid = ssid->next; 1972 } 1973 1974 if (num_match_ssid == 0) { 1975 wpa_printf(MSG_DEBUG, "PNO: No configured SSIDs"); 1976 return -1; 1977 } 1978 1979 if (num_match_ssid > num_ssid) { 1980 params.num_ssids++; /* wildcard */ 1981 num_ssid++; 1982 } 1983 1984 if (num_ssid > WPAS_MAX_SCAN_SSIDS) { 1985 wpa_printf(MSG_DEBUG, "PNO: Use only the first %u SSIDs from " 1986 "%u", WPAS_MAX_SCAN_SSIDS, (unsigned int) num_ssid); 1987 num_ssid = WPAS_MAX_SCAN_SSIDS; 1988 } 1989 1990 if (num_match_ssid > wpa_s->max_match_sets) { 1991 num_match_ssid = wpa_s->max_match_sets; 1992 wpa_dbg(wpa_s, MSG_DEBUG, "PNO: Too many SSIDs to match"); 1993 } 1994 params.filter_ssids = os_calloc(num_match_ssid, 1995 sizeof(struct wpa_driver_scan_filter)); 1996 if (params.filter_ssids == NULL) 1997 return -1; 1998 i = 0; 1999 ssid = wpa_s->conf->ssid; 2000 while (ssid) { 2001 if (!wpas_network_disabled(wpa_s, ssid)) { 2002 if (ssid->scan_ssid && params.num_ssids < num_ssid) { 2003 params.ssids[params.num_ssids].ssid = 2004 ssid->ssid; 2005 params.ssids[params.num_ssids].ssid_len = 2006 ssid->ssid_len; 2007 params.num_ssids++; 2008 } 2009 os_memcpy(params.filter_ssids[i].ssid, ssid->ssid, 2010 ssid->ssid_len); 2011 params.filter_ssids[i].ssid_len = ssid->ssid_len; 2012 params.num_filter_ssids++; 2013 i++; 2014 if (i == num_match_ssid) 2015 break; 2016 } 2017 ssid = ssid->next; 2018 } 2019 2020 if (wpa_s->conf->filter_rssi) 2021 params.filter_rssi = wpa_s->conf->filter_rssi; 2022 2023 interval = wpa_s->conf->sched_scan_interval ? 2024 wpa_s->conf->sched_scan_interval : 10; 2025 2026 if (params.freqs == NULL && wpa_s->manual_sched_scan_freqs) { 2027 wpa_dbg(wpa_s, MSG_DEBUG, "Limit sched scan to specified channels"); 2028 params.freqs = wpa_s->manual_sched_scan_freqs; 2029 } 2030 2031 ret = wpa_supplicant_start_sched_scan(wpa_s, ¶ms, interval); 2032 os_free(params.filter_ssids); 2033 if (ret == 0) 2034 wpa_s->pno = 1; 2035 else 2036 wpa_msg(wpa_s, MSG_ERROR, "Failed to schedule PNO"); 2037 return ret; 2038 } 2039 2040 2041 int wpas_stop_pno(struct wpa_supplicant *wpa_s) 2042 { 2043 int ret = 0; 2044 2045 if (!wpa_s->pno) 2046 return 0; 2047 2048 ret = wpa_supplicant_stop_sched_scan(wpa_s); 2049 2050 wpa_s->pno = 0; 2051 wpa_s->pno_sched_pending = 0; 2052 2053 if (wpa_s->wpa_state == WPA_SCANNING) 2054 wpa_supplicant_req_scan(wpa_s, 0, 0); 2055 2056 return ret; 2057 } 2058