1 /* 2 * Copyright (c) 2017-2021 The Linux Foundation. All rights reserved. 3 * Copyright (c) 2021-2023 Qualcomm Innovation Center, Inc. All rights reserved. 4 * 5 * Permission to use, copy, modify, and/or distribute this software for 6 * any purpose with or without fee is hereby granted, provided that the 7 * above copyright notice and this permission notice appear in all 8 * copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL 11 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED 12 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE 13 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL 14 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR 15 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER 16 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 17 * PERFORMANCE OF THIS SOFTWARE. 18 */ 19 20 /** 21 * DOC: defines driver functions interfacing with linux kernel 22 */ 23 24 #include <qdf_list.h> 25 #include <qdf_status.h> 26 #include <qdf_module.h> 27 #include <linux/wireless.h> 28 #include <linux/netdevice.h> 29 #include <net/cfg80211.h> 30 #include <wlan_scan_utils_api.h> 31 #include <wlan_cfg80211.h> 32 #include <wlan_cfg80211_scan.h> 33 #include <wlan_osif_priv.h> 34 #include <wlan_scan_public_structs.h> 35 #include <wlan_scan_ucfg_api.h> 36 #include <wlan_cfg80211_scan.h> 37 #include <qdf_mem.h> 38 #include <wlan_utility.h> 39 #include "cfg_ucfg_api.h" 40 #ifdef WLAN_POLICY_MGR_ENABLE 41 #include <wlan_policy_mgr_api.h> 42 #endif 43 #include <wlan_reg_services_api.h> 44 #ifdef FEATURE_WLAN_DIAG_SUPPORT 45 #include "host_diag_core_event.h" 46 #endif 47 48 const struct nla_policy cfg80211_scan_policy[ 49 QCA_WLAN_VENDOR_ATTR_SCAN_MAX + 1] = { 50 [QCA_WLAN_VENDOR_ATTR_SCAN_FLAGS] = {.type = NLA_U32}, 51 [QCA_WLAN_VENDOR_ATTR_SCAN_TX_NO_CCK_RATE] = {.type = NLA_FLAG}, 52 [QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE] = {.type = NLA_U64}, 53 }; 54 55 /** 56 * wlan_cfg80211_is_colocated_6ghz_scan_supported() - Check whether colocated 57 * 6ghz scan flag present in scan request or not 58 * @scan_flag: Flags bitmap coming from kernel 59 * 60 * Return: True if colocated 6ghz scan flag present in scan req 61 */ 62 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 10, 0)) 63 static bool 64 wlan_cfg80211_is_colocated_6ghz_scan_supported(uint32_t scan_flag) 65 { 66 return !!(scan_flag & NL80211_SCAN_FLAG_COLOCATED_6GHZ); 67 } 68 #else 69 static inline bool 70 wlan_cfg80211_is_colocated_6ghz_scan_supported(uint32_t scan_flag) 71 { 72 return false; 73 } 74 #endif 75 76 #if defined(CFG80211_SCAN_RANDOM_MAC_ADDR) || \ 77 (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 4, 0)) 78 /** 79 * wlan_fill_scan_rand_attrs() - Populate the scan randomization attrs 80 * @vdev: pointer to objmgr vdev 81 * @flags: cfg80211 scan flags 82 * @mac_addr: random mac addr from cfg80211 83 * @mac_addr_mask: mac addr mask from cfg80211 84 * @randomize: output variable to check scan randomization status 85 * @addr: output variable to hold random addr 86 * @mask: output variable to hold mac mask 87 * 88 * Return: None 89 */ 90 static void wlan_fill_scan_rand_attrs(struct wlan_objmgr_vdev *vdev, 91 uint32_t flags, 92 uint8_t *mac_addr, 93 uint8_t *mac_addr_mask, 94 bool *randomize, 95 uint8_t *addr, 96 uint8_t *mask) 97 { 98 *randomize = false; 99 if (!(flags & NL80211_SCAN_FLAG_RANDOM_ADDR)) 100 return; 101 102 if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE) 103 return; 104 105 if (wlan_vdev_is_up(vdev) == QDF_STATUS_SUCCESS) 106 return; 107 108 *randomize = true; 109 memcpy(addr, mac_addr, QDF_MAC_ADDR_SIZE); 110 memcpy(mask, mac_addr_mask, QDF_MAC_ADDR_SIZE); 111 osif_debug("Random mac addr: "QDF_MAC_ADDR_FMT" and Random mac mask: "QDF_MAC_ADDR_FMT, 112 QDF_MAC_ADDR_REF(addr), QDF_MAC_ADDR_REF(mask)); 113 } 114 115 /** 116 * wlan_scan_rand_attrs() - Wrapper function to fill scan random attrs 117 * @vdev: pointer to objmgr vdev 118 * @request: pointer to cfg80211 scan request 119 * @req: pointer to cmn module scan request 120 * 121 * This is a wrapper function which invokes wlan_fill_scan_rand_attrs() 122 * to fill random attributes of internal scan request with cfg80211_scan_request 123 * 124 * Return: None 125 */ 126 static void wlan_scan_rand_attrs(struct wlan_objmgr_vdev *vdev, 127 struct cfg80211_scan_request *request, 128 struct scan_start_request *req) 129 { 130 bool *randomize = &req->scan_req.scan_random.randomize; 131 uint8_t *mac_addr = req->scan_req.scan_random.mac_addr; 132 uint8_t *mac_mask = req->scan_req.scan_random.mac_mask; 133 134 wlan_fill_scan_rand_attrs(vdev, request->flags, request->mac_addr, 135 request->mac_addr_mask, randomize, mac_addr, 136 mac_mask); 137 if (!*randomize) 138 return; 139 140 req->scan_req.scan_f_add_spoofed_mac_in_probe = true; 141 req->scan_req.scan_f_add_rand_seq_in_probe = true; 142 } 143 #else 144 /** 145 * wlan_scan_rand_attrs() - Wrapper function to fill scan random attrs 146 * @vdev: pointer to objmgr vdev 147 * @request: pointer to cfg80211 scan request 148 * @req: pointer to cmn module scan request 149 * 150 * This is a wrapper function which invokes wlan_fill_scan_rand_attrs() 151 * to fill random attributes of internal scan request with cfg80211_scan_request 152 * 153 * Return: None 154 */ 155 static void wlan_scan_rand_attrs(struct wlan_objmgr_vdev *vdev, 156 struct cfg80211_scan_request *request, 157 struct scan_start_request *req) 158 { 159 } 160 #endif 161 162 #ifdef FEATURE_WLAN_SCAN_PNO 163 #if ((LINUX_VERSION_CODE >= KERNEL_VERSION(4, 4, 0)) || \ 164 defined(CFG80211_MULTI_SCAN_PLAN_BACKPORT)) 165 166 /** 167 * wlan_config_sched_scan_plan() - configures the sched scan plans 168 * from the framework. 169 * @psoc: psoc object 170 * @pno_req: pointer to PNO scan request 171 * @request: pointer to scan request from framework 172 * 173 * Return: None 174 */ 175 static void 176 wlan_config_sched_scan_plan(struct wlan_objmgr_psoc *psoc, 177 struct pno_scan_req_params *pno_req, 178 struct cfg80211_sched_scan_request *request) 179 { 180 if (!ucfg_scan_get_user_config_sched_scan_plan(psoc) || 181 request->n_scan_plans == 1) { 182 pno_req->fast_scan_period = 183 request->scan_plans[0].interval * MSEC_PER_SEC; 184 /* 185 * if only one scan plan is configured from framework 186 * then both fast and slow scan should be configured with the 187 * same value that is why fast scan cycles are hardcoded to one 188 */ 189 pno_req->fast_scan_max_cycles = 1; 190 pno_req->slow_scan_period = 191 request->scan_plans[0].interval * MSEC_PER_SEC; 192 } 193 /* 194 * As of now max 2 scan plans were supported by firmware 195 * if number of scan plan supported by firmware increased below logic 196 * must change. 197 */ 198 else if (request->n_scan_plans == SCAN_PNO_MAX_PLAN_REQUEST) { 199 pno_req->fast_scan_period = 200 request->scan_plans[0].interval * MSEC_PER_SEC; 201 pno_req->fast_scan_max_cycles = 202 request->scan_plans[0].iterations; 203 pno_req->slow_scan_period = 204 request->scan_plans[1].interval * MSEC_PER_SEC; 205 } else { 206 osif_err("Invalid number of scan plans %d !!", 207 request->n_scan_plans); 208 } 209 } 210 #else 211 #define wlan_config_sched_scan_plan(psoc, pno_req, request) \ 212 __wlan_config_sched_scan_plan(pno_req, request, psoc) 213 214 static void 215 __wlan_config_sched_scan_plan(struct pno_scan_req_params *pno_req, 216 struct cfg80211_sched_scan_request *request, 217 struct wlan_objmgr_psoc *psoc) 218 { 219 uint32_t scan_timer_repeat_value, slow_scan_multiplier; 220 221 scan_timer_repeat_value = ucfg_scan_get_scan_timer_repeat_value(psoc); 222 slow_scan_multiplier = ucfg_scan_get_slow_scan_multiplier(psoc); 223 224 pno_req->fast_scan_period = request->interval; 225 pno_req->fast_scan_max_cycles = scan_timer_repeat_value; 226 pno_req->slow_scan_period = 227 (slow_scan_multiplier * pno_req->fast_scan_period); 228 } 229 #endif 230 231 #if LINUX_VERSION_CODE < KERNEL_VERSION(4, 12, 0) 232 static inline void 233 wlan_cfg80211_sched_scan_results(struct wiphy *wiphy, uint64_t reqid) 234 { 235 cfg80211_sched_scan_results(wiphy); 236 } 237 #else 238 static inline void 239 wlan_cfg80211_sched_scan_results(struct wiphy *wiphy, uint64_t reqid) 240 { 241 cfg80211_sched_scan_results(wiphy, reqid); 242 } 243 #endif 244 245 /** 246 * wlan_cfg80211_pno_callback() - pno callback function to handle 247 * pno events. 248 * @vdev: vdev ptr 249 * @event: scan events 250 * @args: argument 251 * 252 * Return: void 253 */ 254 static void wlan_cfg80211_pno_callback(struct wlan_objmgr_vdev *vdev, 255 struct scan_event *event, 256 void *args) 257 { 258 struct wlan_objmgr_pdev *pdev; 259 struct pdev_osif_priv *pdev_ospriv; 260 261 if (event->type != SCAN_EVENT_TYPE_NLO_COMPLETE) 262 return; 263 264 osif_debug("vdev id = %d", event->vdev_id); 265 266 pdev = wlan_vdev_get_pdev(vdev); 267 if (!pdev) { 268 osif_err("pdev is NULL"); 269 return; 270 } 271 272 pdev_ospriv = wlan_pdev_get_ospriv(pdev); 273 if (!pdev_ospriv) { 274 osif_err("pdev_ospriv is NULL"); 275 return; 276 } 277 wlan_cfg80211_sched_scan_results(pdev_ospriv->wiphy, 0); 278 } 279 280 #ifdef WLAN_POLICY_MGR_ENABLE 281 static bool wlan_cfg80211_is_ap_go_present(struct wlan_objmgr_psoc *psoc) 282 { 283 return policy_mgr_get_beaconing_mode_count(psoc, NULL); 284 } 285 286 static QDF_STATUS wlan_cfg80211_is_chan_ok_for_dnbs( 287 struct wlan_objmgr_psoc *psoc, 288 u16 chan_freq, bool *ok) 289 { 290 QDF_STATUS status = policy_mgr_is_chan_ok_for_dnbs( 291 psoc, chan_freq, ok); 292 293 if (QDF_IS_STATUS_ERROR(status)) { 294 osif_err("DNBS check failed"); 295 return status; 296 } 297 298 return QDF_STATUS_SUCCESS; 299 } 300 #else 301 static bool wlan_cfg80211_is_ap_go_present(struct wlan_objmgr_psoc *psoc) 302 { 303 return false; 304 } 305 306 static QDF_STATUS wlan_cfg80211_is_chan_ok_for_dnbs( 307 struct wlan_objmgr_psoc *psoc, 308 u16 chan_freq, 309 bool *ok) 310 { 311 if (!ok) 312 return QDF_STATUS_E_INVAL; 313 314 *ok = true; 315 return QDF_STATUS_SUCCESS; 316 } 317 #endif 318 319 #if defined(CFG80211_SCAN_RANDOM_MAC_ADDR) || \ 320 (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 4, 0)) 321 /** 322 * wlan_pno_scan_rand_attr() - Wrapper function to fill sched scan random attrs 323 * @vdev: pointer to objmgr vdev 324 * @request: pointer to cfg80211 sched scan request 325 * @req: pointer to cmn module pno scan request 326 * 327 * This is a wrapper function which invokes wlan_fill_scan_rand_attrs() 328 * to fill random attributes of internal pno scan 329 * with cfg80211_sched_scan_request 330 * 331 * Return: None 332 */ 333 static void wlan_pno_scan_rand_attr(struct wlan_objmgr_vdev *vdev, 334 struct cfg80211_sched_scan_request *request, 335 struct pno_scan_req_params *req) 336 { 337 bool *randomize = &req->scan_random.randomize; 338 uint8_t *mac_addr = req->scan_random.mac_addr; 339 uint8_t *mac_mask = req->scan_random.mac_mask; 340 341 wlan_fill_scan_rand_attrs(vdev, request->flags, request->mac_addr, 342 request->mac_addr_mask, randomize, mac_addr, 343 mac_mask); 344 } 345 #else 346 /** 347 * wlan_pno_scan_rand_attr() - Wrapper function to fill sched scan random attrs 348 * @vdev: pointer to objmgr vdev 349 * @request: pointer to cfg80211 sched scan request 350 * @req: pointer to cmn module pno scan request 351 * 352 * This is a wrapper function which invokes wlan_fill_scan_rand_attrs() 353 * to fill random attributes of internal pno scan 354 * with cfg80211_sched_scan_request 355 * 356 * Return: None 357 */ 358 static void wlan_pno_scan_rand_attr(struct wlan_objmgr_vdev *vdev, 359 struct cfg80211_sched_scan_request *request, 360 struct pno_scan_req_params *req) 361 { 362 } 363 #endif 364 365 /** 366 * wlan_hdd_sched_scan_update_relative_rssi() - update CPNO params 367 * @pno_request: pointer to PNO scan request 368 * @request: Pointer to cfg80211 scheduled scan start request 369 * 370 * This function is used to update Connected PNO params sent by kernel 371 * 372 * Return: None 373 */ 374 #if defined(CFG80211_REPORT_BETTER_BSS_IN_SCHED_SCAN) || \ 375 (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 11, 0)) 376 static inline void wlan_hdd_sched_scan_update_relative_rssi( 377 struct pno_scan_req_params *pno_request, 378 struct cfg80211_sched_scan_request *request) 379 { 380 pno_request->relative_rssi_set = request->relative_rssi_set; 381 pno_request->relative_rssi = request->relative_rssi; 382 if (NL80211_BAND_2GHZ == request->rssi_adjust.band) 383 pno_request->band_rssi_pref.band = WLAN_BAND_2_4_GHZ; 384 else if (NL80211_BAND_5GHZ == request->rssi_adjust.band) 385 pno_request->band_rssi_pref.band = WLAN_BAND_5_GHZ; 386 pno_request->band_rssi_pref.rssi = request->rssi_adjust.delta; 387 } 388 #else 389 static inline void wlan_hdd_sched_scan_update_relative_rssi( 390 struct pno_scan_req_params *pno_request, 391 struct cfg80211_sched_scan_request *request) 392 { 393 } 394 #endif 395 396 #ifdef FEATURE_WLAN_SCAN_PNO 397 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 4, 0)) 398 static uint32_t wlan_config_sched_scan_start_delay( 399 struct cfg80211_sched_scan_request *request) 400 { 401 return request->delay; 402 } 403 #else 404 static uint32_t wlan_config_sched_scan_start_delay( 405 struct cfg80211_sched_scan_request *request) 406 { 407 return 0; 408 } 409 #endif /*(LINUX_VERSION_CODE >= KERNEL_VERSION(4, 4, 0)) */ 410 #endif /* FEATURE_WLAN_SCAN_PNO */ 411 412 int wlan_cfg80211_sched_scan_start(struct wlan_objmgr_vdev *vdev, 413 struct cfg80211_sched_scan_request *request, 414 uint8_t scan_backoff_multiplier) 415 { 416 struct pno_scan_req_params *req; 417 int i, j, ret = 0; 418 QDF_STATUS status; 419 uint8_t num_chan = 0; 420 uint8_t updated_num_chan = 0; 421 uint16_t chan_freq; 422 struct wlan_objmgr_pdev *pdev = wlan_vdev_get_pdev(vdev); 423 struct wlan_objmgr_psoc *psoc; 424 uint32_t valid_ch[SCAN_PNO_MAX_NETW_CHANNELS_EX] = {0}; 425 bool enable_dfs_pno_chnl_scan; 426 427 if (ucfg_scan_get_pno_in_progress(vdev)) { 428 osif_debug("pno is already in progress"); 429 return -EBUSY; 430 } 431 432 if (ucfg_scan_get_pdev_status(pdev) != 433 SCAN_NOT_IN_PROGRESS) { 434 status = wlan_abort_scan(pdev, 435 wlan_objmgr_pdev_get_pdev_id(pdev), 436 INVAL_VDEV_ID, INVAL_SCAN_ID, true); 437 if (QDF_IS_STATUS_ERROR(status)) 438 return -EBUSY; 439 } 440 441 req = qdf_mem_malloc(sizeof(*req)); 442 if (!req) 443 return -ENOMEM; 444 445 wlan_pdev_obj_lock(pdev); 446 psoc = wlan_pdev_get_psoc(pdev); 447 wlan_pdev_obj_unlock(pdev); 448 449 req->networks_cnt = request->n_match_sets; 450 req->vdev_id = wlan_vdev_get_id(vdev); 451 req->vdev = vdev; 452 req->scan_policy_colocated_6ghz = 453 wlan_cfg80211_is_colocated_6ghz_scan_supported(request->flags); 454 455 if ((!req->networks_cnt) || 456 (req->networks_cnt > SCAN_PNO_MAX_SUPP_NETWORKS)) { 457 osif_err("Network input is not correct %d", 458 req->networks_cnt); 459 ret = -EINVAL; 460 goto error; 461 } 462 463 if (request->n_channels > SCAN_PNO_MAX_NETW_CHANNELS_EX) { 464 osif_err("Incorrect number of channels %d", 465 request->n_channels); 466 ret = -EINVAL; 467 goto error; 468 } 469 470 enable_dfs_pno_chnl_scan = ucfg_scan_is_dfs_chnl_scan_enabled(psoc); 471 if (request->n_channels) { 472 uint32_t buff_len; 473 char *chl; 474 int len = 0; 475 bool ap_or_go_present = wlan_cfg80211_is_ap_go_present(psoc); 476 477 buff_len = (request->n_channels * 5) + 1; 478 chl = qdf_mem_malloc(buff_len); 479 if (!chl) { 480 ret = -ENOMEM; 481 goto error; 482 } 483 for (i = 0; i < request->n_channels; i++) { 484 chan_freq = request->channels[i]->center_freq; 485 if ((!enable_dfs_pno_chnl_scan) && 486 (wlan_reg_is_dfs_for_freq(pdev, chan_freq))) { 487 osif_debug("Dropping DFS channel freq :%d", 488 chan_freq); 489 continue; 490 } 491 if (wlan_reg_is_dsrc_freq(chan_freq)) 492 continue; 493 494 if (ap_or_go_present) { 495 bool ok; 496 497 status = 498 wlan_cfg80211_is_chan_ok_for_dnbs(psoc, 499 chan_freq, 500 &ok); 501 if (QDF_IS_STATUS_ERROR(status)) { 502 osif_err("DNBS check failed"); 503 qdf_mem_free(chl); 504 chl = NULL; 505 ret = -EINVAL; 506 goto error; 507 } 508 if (!ok) 509 continue; 510 } 511 len += qdf_scnprintf(chl + len, buff_len - len, " %d", chan_freq); 512 valid_ch[num_chan++] = chan_freq; 513 } 514 osif_debug("Channel-List[%d]:%s", num_chan, chl); 515 qdf_mem_free(chl); 516 chl = NULL; 517 /* If all channels are DFS and dropped, 518 * then ignore the PNO request 519 */ 520 if (!num_chan) { 521 osif_notice("Channel list empty due to filtering of DSRC"); 522 ret = -EINVAL; 523 goto error; 524 } 525 } 526 527 /* Filling per profile params */ 528 for (i = 0; i < req->networks_cnt; i++) { 529 struct cfg80211_match_set *user_req = &request->match_sets[i]; 530 struct pno_nw_type *tgt_req = &req->networks_list[i]; 531 532 tgt_req->ssid.length = user_req->ssid.ssid_len; 533 534 if (!tgt_req->ssid.length || 535 tgt_req->ssid.length > WLAN_SSID_MAX_LEN) { 536 osif_err(" SSID Len %d is not correct for network %d", 537 tgt_req->ssid.length, i); 538 ret = -EINVAL; 539 goto error; 540 } 541 542 qdf_mem_copy(tgt_req->ssid.ssid, user_req->ssid.ssid, 543 tgt_req->ssid.length); 544 tgt_req->authentication = 0; /*eAUTH_TYPE_ANY */ 545 tgt_req->encryption = 0; /*eED_ANY */ 546 tgt_req->bc_new_type = 0; /*eBCAST_UNKNOWN */ 547 548 549 /*Copying list of valid channel into request */ 550 for (j = 0; j < num_chan; j++) 551 tgt_req->pno_chan_list.chan[j].freq = valid_ch[j]; 552 tgt_req->pno_chan_list.num_chan = num_chan; 553 554 if (ucfg_is_6ghz_pno_scan_optimization_supported(psoc)) { 555 uint32_t short_ssid = 556 wlan_construct_shortssid(tgt_req->ssid.ssid, 557 tgt_req->ssid.length); 558 updated_num_chan = num_chan; 559 ucfg_scan_add_flags_to_pno_chan_list(vdev, req, 560 &updated_num_chan, 561 short_ssid, i); 562 } 563 564 tgt_req->rssi_thresh = user_req->rssi_thold; 565 } 566 567 /* set scan to passive if no SSIDs are specified in the request */ 568 if (0 == request->n_ssids) 569 req->do_passive_scan = true; 570 else 571 req->do_passive_scan = false; 572 573 for (i = 0; i < request->n_ssids; i++) { 574 j = 0; 575 while (j < req->networks_cnt) { 576 if ((req->networks_list[j].ssid.length == 577 request->ssids[i].ssid_len) && 578 (!qdf_mem_cmp(req->networks_list[j].ssid.ssid, 579 request->ssids[i].ssid, 580 req->networks_list[j].ssid.length))) { 581 req->networks_list[j].bc_new_type = 582 SSID_BC_TYPE_HIDDEN; 583 break; 584 } 585 j++; 586 } 587 } 588 589 /* 590 * Before Kernel 4.4 591 * Driver gets only one time interval which is hard coded in 592 * supplicant for 10000ms. 593 * 594 * After Kernel 4.4 595 * User can configure multiple scan_plans, each scan would have 596 * separate scan cycle and interval. (interval is in unit of second.) 597 * For our use case, we would only have supplicant set one scan_plan, 598 * and firmware also support only one as well, so pick up the first 599 * index. 600 * 601 * Taking power consumption into account 602 * firmware after gPNOScanTimerRepeatValue times fast_scan_period 603 * switches slow_scan_period. This is less frequent scans and firmware 604 * shall be in slow_scan_period mode until next PNO Start. 605 */ 606 wlan_config_sched_scan_plan(psoc, req, request); 607 req->delay_start_time = wlan_config_sched_scan_start_delay(request); 608 req->scan_backoff_multiplier = scan_backoff_multiplier; 609 610 wlan_hdd_sched_scan_update_relative_rssi(req, request); 611 612 psoc = wlan_pdev_get_psoc(pdev); 613 ucfg_scan_register_pno_cb(psoc, 614 wlan_cfg80211_pno_callback, NULL); 615 ucfg_scan_get_pno_def_params(vdev, req); 616 617 if (req->scan_random.randomize) 618 wlan_pno_scan_rand_attr(vdev, request, req); 619 620 if (ucfg_ie_allowlist_enabled(psoc, vdev)) 621 ucfg_copy_ie_allowlist_attrs(psoc, &req->ie_allowlist); 622 623 osif_debug("Network count %d n_ssids %d fast_scan_period: %d msec slow_scan_period: %d msec, fast_scan_max_cycles: %d, relative_rssi %d band_pref %d, rssi_pref %d", 624 req->networks_cnt, request->n_ssids, req->fast_scan_period, 625 req->slow_scan_period, req->fast_scan_max_cycles, 626 req->relative_rssi, req->band_rssi_pref.band, 627 req->band_rssi_pref.rssi); 628 629 for (i = 0; i < req->networks_cnt; i++) 630 osif_debug("[%d] ssid: " QDF_SSID_FMT ", RSSI th %d bc NW type %u", 631 i, 632 QDF_SSID_REF(req->networks_list[i].ssid.length, 633 req->networks_list[i].ssid.ssid), 634 req->networks_list[i].rssi_thresh, 635 req->networks_list[i].bc_new_type); 636 637 status = ucfg_scan_pno_start(vdev, req); 638 if (QDF_IS_STATUS_ERROR(status)) { 639 osif_err("Failed to enable PNO"); 640 ret = -EINVAL; 641 goto error; 642 } 643 644 error: 645 qdf_mem_free(req); 646 return ret; 647 } 648 649 int wlan_cfg80211_sched_scan_stop(struct wlan_objmgr_vdev *vdev) 650 { 651 QDF_STATUS status; 652 653 status = ucfg_scan_pno_stop(vdev); 654 if (QDF_IS_STATUS_ERROR(status)) 655 osif_debug("Failed to disable PNO"); 656 657 return 0; 658 } 659 #endif /*FEATURE_WLAN_SCAN_PNO */ 660 661 /** 662 * wlan_copy_bssid_scan_request() - API to copy the bssid to Scan request 663 * @scan_req: Pointer to scan_start_request 664 * @request: scan request from Supplicant 665 * 666 * This API copies the BSSID in scan request from Supplicant and copies it to 667 * the scan_start_request 668 * 669 * Return: None 670 */ 671 #if defined(CFG80211_SCAN_BSSID) || \ 672 (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 7, 0)) 673 static inline void 674 wlan_copy_bssid_scan_request(struct scan_start_request *scan_req, 675 struct cfg80211_scan_request *request) 676 { 677 qdf_mem_copy(scan_req->scan_req.bssid_list[0].bytes, 678 request->bssid, QDF_MAC_ADDR_SIZE); 679 } 680 #else 681 static inline void 682 wlan_copy_bssid_scan_request(struct scan_start_request *scan_req, 683 struct cfg80211_scan_request *request) 684 { 685 686 } 687 #endif 688 689 /** 690 * wlan_schedule_scan_start_request() - Schedule scan start request 691 * @pdev: pointer to pdev object 692 * @req: Pointer to the scan request 693 * @source: source of the scan request 694 * @scan_start_req: pointer to scan start request 695 * 696 * Schedule scan start request and enqueue scan request in the global scan 697 * list. This list stores the active scan request information. 698 * 699 * Return: QDF_STATUS 700 */ 701 static QDF_STATUS 702 wlan_schedule_scan_start_request(struct wlan_objmgr_pdev *pdev, 703 struct cfg80211_scan_request *req, 704 uint8_t source, 705 struct scan_start_request *scan_start_req) 706 { 707 struct scan_req *scan_req; 708 QDF_STATUS status; 709 struct pdev_osif_priv *osif_ctx; 710 struct osif_scan_pdev *osif_scan; 711 712 scan_req = qdf_mem_malloc(sizeof(*scan_req)); 713 if (!scan_req) { 714 ucfg_scm_scan_free_scan_request_mem(scan_start_req); 715 return QDF_STATUS_E_NOMEM; 716 } 717 718 /* Get NL global context from objmgr*/ 719 osif_ctx = wlan_pdev_get_ospriv(pdev); 720 osif_scan = osif_ctx->osif_scan; 721 scan_req->scan_request = req; 722 scan_req->source = source; 723 scan_req->scan_id = scan_start_req->scan_req.scan_id; 724 scan_req->dev = req->wdev->netdev; 725 scan_req->scan_start_timestamp = qdf_get_time_of_the_day_ms(); 726 727 qdf_mutex_acquire(&osif_scan->scan_req_q_lock); 728 if (qdf_list_size(&osif_scan->scan_req_q) < WLAN_MAX_SCAN_COUNT) { 729 status = ucfg_scan_start(scan_start_req); 730 if (QDF_IS_STATUS_SUCCESS(status)) { 731 qdf_list_insert_back(&osif_scan->scan_req_q, 732 &scan_req->node); 733 } else { 734 osif_err("scan req failed with error %d", status); 735 if (status == QDF_STATUS_E_RESOURCES) 736 osif_err("HO is in progress.So defer the scan by informing busy"); 737 } 738 } else { 739 ucfg_scm_scan_free_scan_request_mem(scan_start_req); 740 status = QDF_STATUS_E_RESOURCES; 741 } 742 743 qdf_mutex_release(&osif_scan->scan_req_q_lock); 744 if (QDF_IS_STATUS_ERROR(status)) { 745 osif_rl_debug("Failed to enqueue Scan Req as max scan %d already queued", 746 qdf_list_size(&osif_scan->scan_req_q)); 747 qdf_mem_free(scan_req); 748 } 749 750 return status; 751 } 752 753 /** 754 * wlan_scan_request_dequeue() - dequeue scan request 755 * @pdev: pdev object 756 * @scan_id: scan id 757 * @req: scan request 758 * @source : returns source of the scan request 759 * @dev: returns source net device 760 * @scan_start_timestamp: returns scan start timestamp 761 * 762 * Return: QDF_STATUS 763 */ 764 static QDF_STATUS wlan_scan_request_dequeue( 765 struct wlan_objmgr_pdev *pdev, 766 uint32_t scan_id, struct cfg80211_scan_request **req, 767 uint8_t *source, struct net_device **dev, 768 qdf_time_t *scan_start_timestamp) 769 { 770 QDF_STATUS status = QDF_STATUS_E_FAILURE; 771 struct scan_req *scan_req; 772 qdf_list_node_t *node = NULL, *next_node = NULL; 773 struct pdev_osif_priv *osif_ctx; 774 struct osif_scan_pdev *scan_priv; 775 776 if ((!source) || (!req)) { 777 osif_err("source or request is NULL"); 778 return QDF_STATUS_E_NULL_VALUE; 779 } 780 781 /* Get NL global context from objmgr*/ 782 osif_ctx = wlan_pdev_get_ospriv(pdev); 783 if (!osif_ctx) { 784 osif_err("Failed to retrieve osif context"); 785 return status; 786 } 787 scan_priv = osif_ctx->osif_scan; 788 789 qdf_mutex_acquire(&scan_priv->scan_req_q_lock); 790 if (qdf_list_empty(&scan_priv->scan_req_q)) { 791 osif_info("Scan List is empty"); 792 qdf_mutex_release(&scan_priv->scan_req_q_lock); 793 return QDF_STATUS_E_FAILURE; 794 } 795 796 if (QDF_STATUS_SUCCESS != 797 qdf_list_peek_front(&scan_priv->scan_req_q, &next_node)) { 798 qdf_mutex_release(&scan_priv->scan_req_q_lock); 799 osif_err("Failed to remove Scan Req from queue"); 800 return QDF_STATUS_E_FAILURE; 801 } 802 803 do { 804 node = next_node; 805 scan_req = qdf_container_of(node, struct scan_req, node); 806 if (scan_req->scan_id == scan_id) { 807 status = qdf_list_remove_node(&scan_priv->scan_req_q, 808 node); 809 if (status == QDF_STATUS_SUCCESS) { 810 *req = scan_req->scan_request; 811 *source = scan_req->source; 812 *dev = scan_req->dev; 813 *scan_start_timestamp = 814 scan_req->scan_start_timestamp; 815 qdf_mem_free(scan_req); 816 qdf_mutex_release(&scan_priv->scan_req_q_lock); 817 osif_debug("removed Scan id: %d, req = %pK, pending scans %d", 818 scan_id, req, 819 qdf_list_size(&scan_priv->scan_req_q)); 820 return QDF_STATUS_SUCCESS; 821 } else { 822 qdf_mutex_release(&scan_priv->scan_req_q_lock); 823 osif_err("Failed to remove scan id %d, pending scans %d", 824 scan_id, 825 qdf_list_size(&scan_priv->scan_req_q)); 826 return status; 827 } 828 } 829 } while (QDF_STATUS_SUCCESS == 830 qdf_list_peek_next(&scan_priv->scan_req_q, node, &next_node)); 831 qdf_mutex_release(&scan_priv->scan_req_q_lock); 832 osif_debug("Failed to find scan id %d", scan_id); 833 834 return status; 835 } 836 837 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 7, 0)) 838 /** 839 * wlan_cfg80211_scan_done() - Scan completed callback to cfg80211 840 * @netdev: Net device 841 * @req : Scan request 842 * @aborted : true scan aborted false scan success 843 * @osif_priv: OS private structure 844 * 845 * This function notifies scan done to cfg80211 846 * 847 * Return: none 848 */ 849 void wlan_cfg80211_scan_done(struct net_device *netdev, 850 struct cfg80211_scan_request *req, 851 bool aborted, struct pdev_osif_priv *osif_priv) 852 { 853 struct cfg80211_scan_info info = { 854 .aborted = aborted 855 }; 856 bool driver_internal_netdev_state; 857 858 driver_internal_netdev_state = netdev->flags & IFF_UP; 859 if (osif_priv->osif_check_netdev_state) 860 driver_internal_netdev_state = 861 osif_priv->osif_check_netdev_state(netdev); 862 863 if (driver_internal_netdev_state) 864 cfg80211_scan_done(req, &info); 865 else 866 osif_debug("scan done callback has been dropped :%s", 867 (netdev)->name); 868 } 869 #elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0)) 870 /** 871 * wlan_cfg80211_scan_done() - Scan completed callback to cfg80211 872 * @netdev: Net device 873 * @req : Scan request 874 * @aborted : true scan aborted false scan success 875 * @osif_priv: OS private structure 876 * 877 * This function notifies scan done to cfg80211 878 * 879 * Return: none 880 */ 881 void wlan_cfg80211_scan_done(struct net_device *netdev, 882 struct cfg80211_scan_request *req, 883 bool aborted, struct pdev_osif_priv *osif_priv) 884 { 885 bool driver_internal_net_state; 886 887 driver_internal_netdev_state = netdev->flags & IFF_UP; 888 if (osif_priv->osif_check_netdev_state) 889 driver_internal_net_state = 890 osif_priv->osif_check_netdev_state(netdev); 891 892 if (driver_internal_netdev_state) 893 cfg80211_scan_done(req, aborted); 894 else 895 osif_debug("scan request has been dropped :%s", (netdev)->name); 896 } 897 #endif 898 899 /** 900 * wlan_vendor_scan_callback() - Scan completed callback event 901 * 902 * @req : Scan request 903 * @aborted : true scan aborted false scan success 904 * 905 * This function sends scan completed callback event to NL. 906 * 907 * Return: none 908 */ 909 static void wlan_vendor_scan_callback(struct cfg80211_scan_request *req, 910 bool aborted) 911 { 912 struct sk_buff *skb; 913 struct nlattr *attr; 914 int i; 915 uint8_t scan_status; 916 uint64_t cookie; 917 int index = QCA_NL80211_VENDOR_SUBCMD_SCAN_DONE_INDEX; 918 919 skb = wlan_cfg80211_vendor_event_alloc(req->wdev->wiphy, req->wdev, 920 SCAN_DONE_EVENT_BUF_SIZE + 4 + 921 NLMSG_HDRLEN, 922 index, 923 GFP_ATOMIC); 924 925 if (!skb) { 926 osif_err("skb alloc failed"); 927 qdf_mem_free(req); 928 return; 929 } 930 931 cookie = (uintptr_t)req; 932 933 attr = nla_nest_start(skb, QCA_WLAN_VENDOR_ATTR_SCAN_SSIDS); 934 if (!attr) 935 goto nla_put_failure; 936 for (i = 0; i < req->n_ssids; i++) { 937 if (nla_put(skb, i, req->ssids[i].ssid_len, req->ssids[i].ssid)) 938 goto nla_put_failure; 939 } 940 nla_nest_end(skb, attr); 941 942 attr = nla_nest_start(skb, QCA_WLAN_VENDOR_ATTR_SCAN_FREQUENCIES); 943 if (!attr) 944 goto nla_put_failure; 945 for (i = 0; i < req->n_channels; i++) { 946 if (nla_put_u32(skb, i, req->channels[i]->center_freq)) 947 goto nla_put_failure; 948 } 949 nla_nest_end(skb, attr); 950 951 if (req->ie && 952 nla_put(skb, QCA_WLAN_VENDOR_ATTR_SCAN_IE, req->ie_len, 953 req->ie)) 954 goto nla_put_failure; 955 956 if (req->flags && 957 nla_put_u32(skb, QCA_WLAN_VENDOR_ATTR_SCAN_FLAGS, req->flags)) 958 goto nla_put_failure; 959 960 if (wlan_cfg80211_nla_put_u64(skb, QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE, 961 cookie)) 962 goto nla_put_failure; 963 964 scan_status = (aborted == true) ? VENDOR_SCAN_STATUS_ABORTED : 965 VENDOR_SCAN_STATUS_NEW_RESULTS; 966 if (nla_put_u8(skb, QCA_WLAN_VENDOR_ATTR_SCAN_STATUS, scan_status)) 967 goto nla_put_failure; 968 969 wlan_cfg80211_vendor_event(skb, GFP_ATOMIC); 970 qdf_mem_free(req); 971 972 return; 973 974 nla_put_failure: 975 wlan_cfg80211_vendor_free_skb(skb); 976 qdf_mem_free(req); 977 } 978 979 /** 980 * wlan_scan_acquire_wake_lock_timeout() - acquire scan wake lock 981 * @psoc: psoc ptr 982 * @scan_wake_lock: Scan wake lock 983 * @timeout: timeout in ms 984 * 985 * Return: void 986 */ 987 static inline 988 void wlan_scan_acquire_wake_lock_timeout(struct wlan_objmgr_psoc *psoc, 989 qdf_wake_lock_t *scan_wake_lock, 990 uint32_t timeout) 991 { 992 if (!psoc || !scan_wake_lock) 993 return; 994 995 if (ucfg_scan_wake_lock_in_user_scan(psoc)) 996 qdf_wake_lock_timeout_acquire(scan_wake_lock, timeout); 997 } 998 999 1000 /** 1001 * wlan_scan_release_wake_lock() - release scan wake lock 1002 * @psoc: psoc ptr 1003 * @scan_wake_lock: Scan wake lock 1004 * 1005 * Return: void 1006 */ 1007 #ifdef FEATURE_WLAN_DIAG_SUPPORT 1008 static inline 1009 void wlan_scan_release_wake_lock(struct wlan_objmgr_psoc *psoc, 1010 qdf_wake_lock_t *scan_wake_lock) 1011 { 1012 if (!psoc || !scan_wake_lock) 1013 return; 1014 1015 if (ucfg_scan_wake_lock_in_user_scan(psoc)) 1016 qdf_wake_lock_release(scan_wake_lock, 1017 WIFI_POWER_EVENT_WAKELOCK_SCAN); 1018 } 1019 #else 1020 static inline 1021 void wlan_scan_release_wake_lock(struct wlan_objmgr_psoc *psoc, 1022 qdf_wake_lock_t *scan_wake_lock) 1023 { 1024 if (!psoc || !scan_wake_lock) 1025 return; 1026 1027 if (ucfg_scan_wake_lock_in_user_scan(psoc)) 1028 qdf_wake_lock_release(scan_wake_lock, 0); 1029 } 1030 #endif 1031 1032 static 1033 uint32_t wlan_scan_get_bss_count_for_scan(struct wlan_objmgr_pdev *pdev, 1034 qdf_time_t scan_start_ts) 1035 { 1036 struct scan_filter *filter; 1037 qdf_list_t *list = NULL; 1038 uint32_t count = 0; 1039 1040 if (!scan_start_ts) 1041 return count; 1042 1043 filter = qdf_mem_malloc(sizeof(*filter)); 1044 if (!filter) 1045 return count; 1046 1047 filter->ignore_auth_enc_type = true; 1048 filter->age_threshold = qdf_get_time_of_the_day_ms() - scan_start_ts; 1049 1050 list = ucfg_scan_get_result(pdev, filter); 1051 1052 qdf_mem_free(filter); 1053 1054 if (list) { 1055 count = qdf_list_size(list); 1056 ucfg_scan_purge_results(list); 1057 } 1058 1059 return count; 1060 } 1061 1062 /** 1063 * wlan_cfg80211_scan_done_callback() - scan done callback function called after 1064 * scan is finished 1065 * @vdev: vdev ptr 1066 * @event: Scan event 1067 * @args: Scan cb arg 1068 * 1069 * Return: void 1070 */ 1071 static void wlan_cfg80211_scan_done_callback( 1072 struct wlan_objmgr_vdev *vdev, 1073 struct scan_event *event, 1074 void *args) 1075 { 1076 struct cfg80211_scan_request *req = NULL; 1077 bool success = false; 1078 uint32_t scan_id; 1079 uint8_t source = NL_SCAN; 1080 struct wlan_objmgr_pdev *pdev; 1081 struct pdev_osif_priv *osif_priv; 1082 struct net_device *netdev = NULL; 1083 QDF_STATUS status; 1084 qdf_time_t scan_start_timestamp = 0; 1085 uint32_t unique_bss_count = 0; 1086 1087 if (!event) { 1088 osif_nofl_err("Invalid scan event received"); 1089 return; 1090 } 1091 1092 scan_id = event->scan_id; 1093 1094 qdf_mtrace(QDF_MODULE_ID_SCAN, QDF_MODULE_ID_OS_IF, event->type, 1095 event->vdev_id, scan_id); 1096 1097 if (event->type == SCAN_EVENT_TYPE_STARTED) 1098 osif_nofl_info("scan start scan id %d", scan_id); 1099 1100 if (!util_is_scan_completed(event, &success)) 1101 return; 1102 1103 pdev = wlan_vdev_get_pdev(vdev); 1104 osif_priv = wlan_pdev_get_ospriv(pdev); 1105 status = wlan_scan_request_dequeue( 1106 pdev, scan_id, &req, &source, &netdev, 1107 &scan_start_timestamp); 1108 if (QDF_IS_STATUS_ERROR(status)) { 1109 osif_err("Dequeue of scan request failed ID: %d", scan_id); 1110 goto allow_suspend; 1111 } 1112 1113 if (!netdev) { 1114 osif_err("net dev is NULL,Drop scan event Id: %d", scan_id); 1115 /* 1116 * Free scan request in case of VENDOR_SCAN as it is 1117 * allocated in driver. 1118 */ 1119 if (source == VENDOR_SCAN) 1120 qdf_mem_free(req); 1121 goto allow_suspend; 1122 } 1123 1124 /* Make sure vdev is active */ 1125 status = wlan_objmgr_vdev_try_get_ref(vdev, WLAN_OSIF_ID); 1126 if (QDF_IS_STATUS_ERROR(status)) { 1127 osif_err("Failed to get vdev reference: scan Id: %d", scan_id); 1128 /* 1129 * Free scan request in case of VENDOR_SCAN as it is 1130 * allocated in driver. 1131 */ 1132 if (source == VENDOR_SCAN) 1133 qdf_mem_free(req); 1134 goto allow_suspend; 1135 } 1136 1137 /* 1138 * Scan can be triggred from NL or vendor scan 1139 * - If scan is triggered from NL then cfg80211 scan done should be 1140 * called to updated scan completion to NL. 1141 * - If scan is triggred through vendor command then 1142 * scan done event will be posted 1143 */ 1144 if (NL_SCAN == source) 1145 wlan_cfg80211_scan_done(netdev, req, !success, osif_priv); 1146 else 1147 wlan_vendor_scan_callback(req, !success); 1148 1149 wlan_objmgr_vdev_release_ref(vdev, WLAN_OSIF_ID); 1150 1151 unique_bss_count = wlan_scan_get_bss_count_for_scan(pdev, 1152 scan_start_timestamp); 1153 osif_nofl_info("vdev %d, scan id %d type %s(%d) reason %s(%d) scan found %d bss", 1154 event->vdev_id, scan_id, 1155 util_scan_get_ev_type_name(event->type), event->type, 1156 util_scan_get_ev_reason_name(event->reason), 1157 event->reason, unique_bss_count); 1158 allow_suspend: 1159 qdf_mutex_acquire(&osif_priv->osif_scan->scan_req_q_lock); 1160 if (qdf_list_empty(&osif_priv->osif_scan->scan_req_q)) { 1161 struct wlan_objmgr_psoc *psoc; 1162 1163 qdf_mutex_release(&osif_priv->osif_scan->scan_req_q_lock); 1164 qdf_runtime_pm_allow_suspend( 1165 &osif_priv->osif_scan->runtime_pm_lock); 1166 1167 psoc = wlan_pdev_get_psoc(pdev); 1168 wlan_scan_release_wake_lock(psoc, 1169 &osif_priv->osif_scan->scan_wake_lock); 1170 /* 1171 * Acquire wakelock to handle the case where APP's tries 1172 * to suspend immediately after the driver gets connect 1173 * request(i.e after scan) from supplicant, this result in 1174 * app's is suspending and not able to process the connect 1175 * request to AP 1176 */ 1177 wlan_scan_acquire_wake_lock_timeout(psoc, 1178 &osif_priv->osif_scan->scan_wake_lock, 1179 SCAN_WAKE_LOCK_CONNECT_DURATION); 1180 } else { 1181 qdf_mutex_release(&osif_priv->osif_scan->scan_req_q_lock); 1182 } 1183 1184 } 1185 1186 QDF_STATUS wlan_scan_runtime_pm_init(struct wlan_objmgr_pdev *pdev) 1187 { 1188 struct pdev_osif_priv *osif_priv; 1189 struct osif_scan_pdev *scan_priv; 1190 1191 wlan_pdev_obj_lock(pdev); 1192 osif_priv = wlan_pdev_get_ospriv(pdev); 1193 wlan_pdev_obj_unlock(pdev); 1194 1195 scan_priv = osif_priv->osif_scan; 1196 1197 return qdf_runtime_lock_init(&scan_priv->runtime_pm_lock); 1198 } 1199 1200 void wlan_scan_runtime_pm_deinit(struct wlan_objmgr_pdev *pdev) 1201 { 1202 struct pdev_osif_priv *osif_priv; 1203 struct osif_scan_pdev *scan_priv; 1204 1205 wlan_pdev_obj_lock(pdev); 1206 osif_priv = wlan_pdev_get_ospriv(pdev); 1207 wlan_pdev_obj_unlock(pdev); 1208 1209 scan_priv = osif_priv->osif_scan; 1210 qdf_runtime_lock_deinit(&scan_priv->runtime_pm_lock); 1211 } 1212 1213 QDF_STATUS wlan_cfg80211_scan_priv_init(struct wlan_objmgr_pdev *pdev) 1214 { 1215 struct pdev_osif_priv *osif_priv; 1216 struct osif_scan_pdev *scan_priv; 1217 struct wlan_objmgr_psoc *psoc; 1218 wlan_scan_requester req_id; 1219 1220 psoc = wlan_pdev_get_psoc(pdev); 1221 1222 req_id = ucfg_scan_register_requester(psoc, "CFG", 1223 wlan_cfg80211_scan_done_callback, NULL); 1224 1225 osif_priv = wlan_pdev_get_ospriv(pdev); 1226 scan_priv = qdf_mem_malloc(sizeof(*scan_priv)); 1227 if (!scan_priv) 1228 return QDF_STATUS_E_NOMEM; 1229 1230 /* Initialize the scan request queue */ 1231 osif_priv->osif_scan = scan_priv; 1232 scan_priv->req_id = req_id; 1233 qdf_list_create(&scan_priv->scan_req_q, WLAN_MAX_SCAN_COUNT); 1234 qdf_mutex_create(&scan_priv->scan_req_q_lock); 1235 qdf_wake_lock_create(&scan_priv->scan_wake_lock, "scan_wake_lock"); 1236 1237 return QDF_STATUS_SUCCESS; 1238 } 1239 1240 QDF_STATUS wlan_cfg80211_scan_priv_deinit(struct wlan_objmgr_pdev *pdev) 1241 { 1242 struct pdev_osif_priv *osif_priv; 1243 struct osif_scan_pdev *scan_priv; 1244 struct wlan_objmgr_psoc *psoc; 1245 1246 psoc = wlan_pdev_get_psoc(pdev); 1247 osif_priv = wlan_pdev_get_ospriv(pdev); 1248 1249 wlan_cfg80211_cleanup_scan_queue(pdev, NULL); 1250 scan_priv = osif_priv->osif_scan; 1251 qdf_wake_lock_destroy(&scan_priv->scan_wake_lock); 1252 qdf_mutex_destroy(&scan_priv->scan_req_q_lock); 1253 qdf_list_destroy(&scan_priv->scan_req_q); 1254 ucfg_scan_unregister_requester(psoc, scan_priv->req_id); 1255 osif_priv->osif_scan = NULL; 1256 qdf_mem_free(scan_priv); 1257 1258 return QDF_STATUS_SUCCESS; 1259 } 1260 1261 /** 1262 * wlan_cfg80211_enqueue_for_cleanup() - Function to populate scan cleanup queue 1263 * @scan_cleanup_q: Scan cleanup queue to be populated 1264 * @scan_priv: Pointer to scan related data used by cfg80211 scan 1265 * @dev: Netdevice pointer 1266 * 1267 * The function synchrounously iterates through the global scan queue to 1268 * identify entries that have to be cleaned up, copies identified entries 1269 * to another queue(to send scan complete event to NL later) and removes the 1270 * entry from the global scan queue. 1271 * 1272 * Return: None 1273 */ 1274 static void 1275 wlan_cfg80211_enqueue_for_cleanup(qdf_list_t *scan_cleanup_q, 1276 struct osif_scan_pdev *scan_priv, 1277 struct net_device *dev) 1278 { 1279 struct scan_req *scan_req, *scan_cleanup; 1280 qdf_list_node_t *node = NULL, *next_node = NULL; 1281 1282 qdf_mutex_acquire(&scan_priv->scan_req_q_lock); 1283 if (QDF_STATUS_SUCCESS != 1284 qdf_list_peek_front(&scan_priv->scan_req_q, 1285 &node)) { 1286 qdf_mutex_release(&scan_priv->scan_req_q_lock); 1287 return; 1288 } 1289 1290 while (node) { 1291 /* 1292 * Keep track of the next node, to traverse through the list 1293 * in the event of the current node being deleted. 1294 */ 1295 qdf_list_peek_next(&scan_priv->scan_req_q, 1296 node, &next_node); 1297 scan_req = qdf_container_of(node, struct scan_req, node); 1298 if (!dev || (dev == scan_req->dev)) { 1299 scan_cleanup = qdf_mem_malloc(sizeof(struct scan_req)); 1300 if (!scan_cleanup) { 1301 qdf_mutex_release(&scan_priv->scan_req_q_lock); 1302 return; 1303 } 1304 scan_cleanup->scan_request = scan_req->scan_request; 1305 scan_cleanup->scan_id = scan_req->scan_id; 1306 scan_cleanup->source = scan_req->source; 1307 scan_cleanup->dev = scan_req->dev; 1308 qdf_list_insert_back(scan_cleanup_q, 1309 &scan_cleanup->node); 1310 if (QDF_STATUS_SUCCESS != 1311 qdf_list_remove_node(&scan_priv->scan_req_q, 1312 node)) { 1313 qdf_mutex_release(&scan_priv->scan_req_q_lock); 1314 osif_err("Failed to remove scan request"); 1315 return; 1316 } 1317 qdf_mem_free(scan_req); 1318 } 1319 node = next_node; 1320 next_node = NULL; 1321 } 1322 qdf_mutex_release(&scan_priv->scan_req_q_lock); 1323 } 1324 1325 void wlan_cfg80211_cleanup_scan_queue(struct wlan_objmgr_pdev *pdev, 1326 struct net_device *dev) 1327 { 1328 struct scan_req *scan_req; 1329 struct cfg80211_scan_request *req; 1330 uint8_t source; 1331 bool aborted = true; 1332 struct pdev_osif_priv *osif_priv; 1333 qdf_list_t scan_cleanup_q; 1334 qdf_list_node_t *node = NULL; 1335 1336 if (!pdev) { 1337 osif_err("pdev is Null"); 1338 return; 1339 } 1340 1341 osif_priv = wlan_pdev_get_ospriv(pdev); 1342 1343 /* 1344 * To avoid any race conditions, create a local list to copy all the 1345 * scan entries to be removed and then send scan complete for each of 1346 * the identified entries to NL. 1347 */ 1348 qdf_list_create(&scan_cleanup_q, WLAN_MAX_SCAN_COUNT); 1349 wlan_cfg80211_enqueue_for_cleanup(&scan_cleanup_q, 1350 osif_priv->osif_scan, dev); 1351 1352 while (!qdf_list_empty(&scan_cleanup_q)) { 1353 if (QDF_STATUS_SUCCESS != qdf_list_remove_front(&scan_cleanup_q, 1354 &node)) { 1355 osif_err("Failed to remove scan request"); 1356 return; 1357 } 1358 scan_req = container_of(node, struct scan_req, node); 1359 req = scan_req->scan_request; 1360 source = scan_req->source; 1361 if (NL_SCAN == source) 1362 wlan_cfg80211_scan_done(scan_req->dev, req, 1363 aborted, osif_priv); 1364 else 1365 wlan_vendor_scan_callback(req, aborted); 1366 1367 qdf_mem_free(scan_req); 1368 } 1369 qdf_list_destroy(&scan_cleanup_q); 1370 1371 return; 1372 } 1373 1374 /** 1375 * wlan_cfg80211_update_scan_policy_type_flags() - Set scan flags according to 1376 * scan request 1377 * @req: scan request to populate 1378 * @scan_req: Pointer to scan request params 1379 * 1380 * Return: None 1381 */ 1382 #if defined(CFG80211_SCAN_DBS_CONTROL_SUPPORT) || \ 1383 (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 16, 0)) 1384 static void wlan_cfg80211_update_scan_policy_type_flags( 1385 struct cfg80211_scan_request *req, 1386 struct scan_req_params *scan_req) 1387 { 1388 if (req->flags & NL80211_SCAN_FLAG_HIGH_ACCURACY) 1389 scan_req->scan_policy_high_accuracy = true; 1390 if (req->flags & NL80211_SCAN_FLAG_LOW_SPAN) 1391 scan_req->scan_policy_low_span = true; 1392 if (req->flags & NL80211_SCAN_FLAG_LOW_POWER) 1393 scan_req->scan_policy_low_power = true; 1394 1395 if (wlan_cfg80211_is_colocated_6ghz_scan_supported(req->flags)) 1396 scan_req->scan_policy_colocated_6ghz = true; 1397 } 1398 #else 1399 static inline void wlan_cfg80211_update_scan_policy_type_flags( 1400 struct cfg80211_scan_request *req, 1401 struct scan_req_params *scan_req) 1402 { 1403 } 1404 #endif 1405 1406 #ifdef WLAN_POLICY_MGR_ENABLE 1407 static bool 1408 wlan_cfg80211_allow_simultaneous_scan(struct wlan_objmgr_psoc *psoc) 1409 { 1410 return policy_mgr_is_scan_simultaneous_capable(psoc); 1411 } 1412 #else 1413 static bool 1414 wlan_cfg80211_allow_simultaneous_scan(struct wlan_objmgr_psoc *psoc) 1415 { 1416 return true; 1417 } 1418 #endif 1419 1420 enum scan_priority convert_nl_scan_priority_to_internal( 1421 enum qca_wlan_vendor_scan_priority nl_scan_priority) 1422 { 1423 switch (nl_scan_priority) { 1424 case QCA_WLAN_VENDOR_SCAN_PRIORITY_VERY_LOW: 1425 return SCAN_PRIORITY_VERY_LOW; 1426 1427 case QCA_WLAN_VENDOR_SCAN_PRIORITY_LOW: 1428 return SCAN_PRIORITY_LOW; 1429 1430 case QCA_WLAN_VENDOR_SCAN_PRIORITY_MEDIUM: 1431 return SCAN_PRIORITY_MEDIUM; 1432 1433 case QCA_WLAN_VENDOR_SCAN_PRIORITY_HIGH: 1434 return SCAN_PRIORITY_HIGH; 1435 1436 case QCA_WLAN_VENDOR_SCAN_PRIORITY_VERY_HIGH: 1437 return SCAN_PRIORITY_VERY_HIGH; 1438 1439 default: 1440 return SCAN_PRIORITY_COUNT; 1441 } 1442 } 1443 1444 bool wlan_is_scan_allowed(struct wlan_objmgr_vdev *vdev) 1445 { 1446 struct wlan_objmgr_pdev *pdev = wlan_vdev_get_pdev(vdev); 1447 struct pdev_osif_priv *osif_priv; 1448 struct wlan_objmgr_psoc *psoc; 1449 enum QDF_OPMODE opmode = wlan_vdev_mlme_get_opmode(vdev); 1450 1451 psoc = wlan_pdev_get_psoc(pdev); 1452 if (!psoc) { 1453 osif_err("Invalid psoc object"); 1454 return false; 1455 } 1456 1457 osif_priv = wlan_pdev_get_ospriv(pdev); 1458 if (!osif_priv) { 1459 osif_err("Invalid osif priv object"); 1460 return false; 1461 } 1462 /* 1463 * For a non-SAP vdevs, if a scan is already going on i.e the scan queue 1464 * is not empty, and the simultaneous scan is disabled, dont allow 2nd 1465 * scan. 1466 */ 1467 qdf_mutex_acquire(&osif_priv->osif_scan->scan_req_q_lock); 1468 if (!wlan_cfg80211_allow_simultaneous_scan(psoc) && 1469 !qdf_list_empty(&osif_priv->osif_scan->scan_req_q) && 1470 opmode != QDF_SAP_MODE) { 1471 qdf_mutex_release(&osif_priv->osif_scan->scan_req_q_lock); 1472 osif_err_rl("Simultaneous scan disabled, reject scan"); 1473 return false; 1474 } 1475 qdf_mutex_release(&osif_priv->osif_scan->scan_req_q_lock); 1476 1477 return true; 1478 } 1479 1480 int wlan_cfg80211_scan(struct wlan_objmgr_vdev *vdev, 1481 struct cfg80211_scan_request *request, 1482 struct scan_params *params) 1483 { 1484 struct scan_start_request *req; 1485 struct wlan_ssid *pssid; 1486 uint8_t i; 1487 int ret = 0; 1488 uint8_t num_chan = 0; 1489 uint32_t c_freq; 1490 struct wlan_objmgr_pdev *pdev = wlan_vdev_get_pdev(vdev); 1491 wlan_scan_requester req_id; 1492 struct pdev_osif_priv *osif_priv; 1493 struct wlan_objmgr_psoc *psoc; 1494 wlan_scan_id scan_id; 1495 bool is_p2p_scan = false; 1496 enum wlan_band band; 1497 QDF_STATUS qdf_status; 1498 enum QDF_OPMODE opmode; 1499 uint32_t extra_ie_len = 0; 1500 1501 psoc = wlan_pdev_get_psoc(pdev); 1502 if (!psoc) { 1503 osif_err("Invalid psoc object"); 1504 return -EINVAL; 1505 } 1506 opmode = wlan_vdev_mlme_get_opmode(vdev); 1507 1508 osif_debug("%s(vdev%d): mode %d flags 0x%x", 1509 request->wdev->netdev->name, 1510 wlan_vdev_get_id(vdev), opmode, request->flags); 1511 1512 if (!wlan_is_scan_allowed(vdev)) 1513 return -EBUSY; 1514 1515 osif_priv = wlan_pdev_get_ospriv(pdev); 1516 if (!osif_priv) { 1517 osif_err("Invalid osif priv object"); 1518 return -EINVAL; 1519 } 1520 1521 req = qdf_mem_malloc(sizeof(*req)); 1522 if (!req) 1523 return -EINVAL; 1524 1525 /* Initialize the scan global params */ 1526 ucfg_scan_init_default_params(vdev, req); 1527 1528 req_id = osif_priv->osif_scan->req_id; 1529 scan_id = ucfg_scan_get_scan_id(psoc); 1530 if (!scan_id) { 1531 osif_err("Invalid scan id"); 1532 qdf_mem_free(req); 1533 return -EINVAL; 1534 } 1535 1536 /* fill the scan request structure */ 1537 req->vdev = vdev; 1538 req->scan_req.vdev_id = wlan_vdev_get_id(vdev); 1539 req->scan_req.scan_id = scan_id; 1540 req->scan_req.scan_req_id = req_id; 1541 1542 /* Update scan policy type flags according to cfg scan request */ 1543 wlan_cfg80211_update_scan_policy_type_flags(request, 1544 &req->scan_req); 1545 /* 1546 * Even though supplicant doesn't provide any SSIDs, n_ssids is 1547 * set to 1. Because of this, driver is assuming that this is not 1548 * wildcard scan and so is not aging out the scan results. 1549 */ 1550 if ((request->ssids) && (request->n_ssids == 1) && 1551 ('\0' == request->ssids->ssid[0])) { 1552 request->n_ssids = 0; 1553 } 1554 1555 if ((request->ssids) && (0 < request->n_ssids)) { 1556 int j; 1557 req->scan_req.num_ssids = request->n_ssids; 1558 1559 if (req->scan_req.num_ssids > WLAN_SCAN_MAX_NUM_SSID) { 1560 osif_info("number of ssid %d greater than MAX %d", 1561 req->scan_req.num_ssids, 1562 WLAN_SCAN_MAX_NUM_SSID); 1563 req->scan_req.num_ssids = WLAN_SCAN_MAX_NUM_SSID; 1564 } 1565 /* copy all the ssid's and their length */ 1566 for (j = 0; j < req->scan_req.num_ssids; j++) { 1567 pssid = &req->scan_req.ssid[j]; 1568 /* get the ssid length */ 1569 pssid->length = request->ssids[j].ssid_len; 1570 if (pssid->length > WLAN_SSID_MAX_LEN) 1571 pssid->length = WLAN_SSID_MAX_LEN; 1572 qdf_mem_copy(pssid->ssid, 1573 &request->ssids[j].ssid[0], 1574 pssid->length); 1575 } 1576 } 1577 if (request->ssids || 1578 (opmode == QDF_P2P_GO_MODE) || (opmode == QDF_P2P_DEVICE_MODE)) 1579 req->scan_req.scan_f_passive = false; 1580 1581 if (params->half_rate) 1582 req->scan_req.scan_f_half_rate = true; 1583 else if (params->quarter_rate) 1584 req->scan_req.scan_f_quarter_rate = true; 1585 1586 if (params->strict_pscan) 1587 req->scan_req.scan_f_strict_passive_pch = true; 1588 1589 if ((request->n_ssids == 1) && request->ssids && 1590 !qdf_mem_cmp(&request->ssids[0], "DIRECT-", 7)) 1591 is_p2p_scan = true; 1592 1593 if (is_p2p_scan && request->no_cck) 1594 req->scan_req.scan_type = SCAN_TYPE_P2P_SEARCH; 1595 1596 if (params->dwell_time_active) 1597 req->scan_req.dwell_time_active = params->dwell_time_active; 1598 1599 if (params->dwell_time_active_2g) 1600 req->scan_req.dwell_time_active_2g = 1601 params->dwell_time_active_2g; 1602 1603 if (params->dwell_time_passive) 1604 req->scan_req.dwell_time_passive = params->dwell_time_passive; 1605 1606 if (params->dwell_time_active_6g) 1607 req->scan_req.dwell_time_active_6g = 1608 params->dwell_time_active_6g; 1609 1610 if (params->dwell_time_passive_6g) 1611 req->scan_req.dwell_time_passive_6g = 1612 params->dwell_time_passive_6g; 1613 1614 /* Set dwell time mode according to scan policy type flags */ 1615 if (ucfg_scan_cfg_honour_nl_scan_policy_flags(psoc)) { 1616 if (req->scan_req.scan_policy_high_accuracy) 1617 req->scan_req.adaptive_dwell_time_mode = 1618 SCAN_DWELL_MODE_STATIC; 1619 if (req->scan_req.scan_policy_low_power) 1620 req->scan_req.adaptive_dwell_time_mode = 1621 SCAN_DWELL_MODE_AGGRESSIVE; 1622 } 1623 1624 /* 1625 * FW require at least 1 MAC to send probe request. 1626 * If MAC is all 0 set it to BC addr as this is the address on 1627 * which fw will send probe req. 1628 */ 1629 req->scan_req.num_bssid = 1; 1630 wlan_copy_bssid_scan_request(req, request); 1631 if (qdf_is_macaddr_zero(&req->scan_req.bssid_list[0])) 1632 qdf_set_macaddr_broadcast(&req->scan_req.bssid_list[0]); 1633 1634 if (params->scan_f_2ghz && !params->scan_f_5ghz) { 1635 req->scan_req.scan_f_2ghz = true; 1636 req->scan_req.scan_f_5ghz = false; 1637 } else if (!params->scan_f_2ghz && params->scan_f_5ghz) { 1638 req->scan_req.scan_f_2ghz = false; 1639 req->scan_req.scan_f_5ghz = true; 1640 } 1641 1642 if (request->n_channels) { 1643 #ifdef WLAN_POLICY_MGR_ENABLE 1644 bool ap_or_go_present = wlan_cfg80211_is_ap_go_present(psoc); 1645 #endif 1646 for (i = 0; i < request->n_channels; i++) { 1647 c_freq = request->channels[i]->center_freq; 1648 if (wlan_reg_is_dsrc_freq(c_freq)) 1649 continue; 1650 #ifdef WLAN_POLICY_MGR_ENABLE 1651 if (ap_or_go_present) { 1652 bool ok; 1653 1654 qdf_status = policy_mgr_is_chan_ok_for_dnbs( 1655 psoc, c_freq, &ok); 1656 1657 if (QDF_IS_STATUS_ERROR(qdf_status)) { 1658 osif_err("DNBS check failed"); 1659 ret = -EINVAL; 1660 goto err; 1661 } 1662 if (!ok) 1663 continue; 1664 } 1665 #endif 1666 1667 if ((req->scan_req.scan_f_2ghz && 1668 WLAN_REG_IS_24GHZ_CH_FREQ(c_freq)) || 1669 (req->scan_req.scan_f_5ghz && 1670 (WLAN_REG_IS_5GHZ_CH_FREQ(c_freq) || 1671 WLAN_REG_IS_49GHZ_FREQ(c_freq) || 1672 WLAN_REG_IS_6GHZ_CHAN_FREQ(c_freq)))) { 1673 req->scan_req.chan_list.chan[num_chan].freq = 1674 c_freq; 1675 band = util_scan_scm_freq_to_band(c_freq); 1676 if (band == WLAN_BAND_2_4_GHZ) 1677 req->scan_req.chan_list.chan[num_chan].phymode = 1678 SCAN_PHY_MODE_11G; 1679 else 1680 req->scan_req.chan_list.chan[num_chan].phymode = 1681 SCAN_PHY_MODE_11A; 1682 num_chan++; 1683 if (num_chan >= NUM_CHANNELS) 1684 break; 1685 } 1686 } 1687 } 1688 if (!num_chan) { 1689 osif_err("Received zero non-dsrc channels"); 1690 ret = -EINVAL; 1691 goto err; 1692 } 1693 req->scan_req.chan_list.num_chan = num_chan; 1694 1695 /* P2P increase the scan priority */ 1696 if (is_p2p_scan) 1697 req->scan_req.scan_priority = SCAN_PRIORITY_HIGH; 1698 1699 if (params->priority != SCAN_PRIORITY_COUNT) 1700 req->scan_req.scan_priority = params->priority; 1701 1702 if (request->ie_len) 1703 extra_ie_len = request->ie_len; 1704 else if (params->default_ie.ptr && params->default_ie.len) 1705 extra_ie_len = params->default_ie.len; 1706 1707 if (params->vendor_ie.ptr && params->vendor_ie.len) 1708 extra_ie_len += params->vendor_ie.len; 1709 1710 if (extra_ie_len) { 1711 req->scan_req.extraie.ptr = qdf_mem_malloc(extra_ie_len); 1712 if (!req->scan_req.extraie.ptr) { 1713 ret = -ENOMEM; 1714 goto err; 1715 } 1716 } 1717 1718 if (request->ie_len) { 1719 req->scan_req.extraie.len = request->ie_len; 1720 qdf_mem_copy(req->scan_req.extraie.ptr, request->ie, 1721 request->ie_len); 1722 } else if (params->default_ie.ptr && params->default_ie.len) { 1723 req->scan_req.extraie.len = params->default_ie.len; 1724 qdf_mem_copy(req->scan_req.extraie.ptr, params->default_ie.ptr, 1725 params->default_ie.len); 1726 } 1727 1728 if (params->vendor_ie.ptr && params->vendor_ie.len) { 1729 qdf_mem_copy((req->scan_req.extraie.ptr + 1730 req->scan_req.extraie.len), 1731 params->vendor_ie.ptr, params->vendor_ie.len); 1732 1733 req->scan_req.extraie.len += params->vendor_ie.len; 1734 } 1735 1736 if (!is_p2p_scan) { 1737 if (req->scan_req.scan_random.randomize) 1738 wlan_scan_rand_attrs(vdev, request, req); 1739 if (ucfg_ie_allowlist_enabled(psoc, vdev) && 1740 ucfg_copy_ie_allowlist_attrs(psoc, 1741 &req->scan_req.ie_allowlist)) 1742 req->scan_req.scan_f_en_ie_allowlist_in_probe = true; 1743 } 1744 1745 if (request->flags & NL80211_SCAN_FLAG_FLUSH) 1746 ucfg_scan_flush_results(pdev, NULL); 1747 1748 if (params->scan_probe_unicast_ra) 1749 req->scan_req.scan_ctrl_flags_ext |= 1750 SCAN_FLAG_EXT_FORCE_UNICAST_RA; 1751 1752 osif_debug("scan_ctrl_flags_ext %0x", 1753 req->scan_req.scan_ctrl_flags_ext); 1754 1755 req->scan_req.mld_id = params->mld_id; 1756 1757 /* 1758 * Acquire wakelock to handle the case where APP's send scan to connect. 1759 * If suspend is received during scan scan will be aborted and APP will 1760 * not get scan result and not connect. eg if PNO is implemented in 1761 * framework. 1762 */ 1763 wlan_scan_acquire_wake_lock_timeout(psoc, 1764 &osif_priv->osif_scan->scan_wake_lock, 1765 SCAN_WAKE_LOCK_SCAN_DURATION); 1766 1767 qdf_runtime_pm_prevent_suspend( 1768 &osif_priv->osif_scan->runtime_pm_lock); 1769 1770 qdf_status = wlan_schedule_scan_start_request(pdev, request, 1771 params->source, req); 1772 if (QDF_IS_STATUS_ERROR(qdf_status)) { 1773 qdf_mutex_acquire(&osif_priv->osif_scan->scan_req_q_lock); 1774 if (qdf_list_empty(&osif_priv->osif_scan->scan_req_q)) { 1775 qdf_mutex_release( 1776 &osif_priv->osif_scan->scan_req_q_lock); 1777 qdf_runtime_pm_allow_suspend( 1778 &osif_priv->osif_scan->runtime_pm_lock); 1779 wlan_scan_release_wake_lock( 1780 psoc, 1781 &osif_priv->osif_scan->scan_wake_lock); 1782 } else { 1783 qdf_mutex_release( 1784 &osif_priv->osif_scan->scan_req_q_lock); 1785 } 1786 } 1787 1788 return qdf_status_to_os_return(qdf_status); 1789 1790 err: 1791 qdf_mem_free(req); 1792 return ret; 1793 } 1794 1795 /** 1796 * wlan_get_scanid() - API to get the scan id 1797 * from the scan cookie attribute. 1798 * @pdev: Pointer to pdev object 1799 * @scan_id: Pointer to scan id 1800 * @cookie : Scan cookie attribute 1801 * 1802 * API to get the scan id from the scan cookie attribute 1803 * sent from supplicant by matching scan request. 1804 * 1805 * Return: 0 for success, non zero for failure 1806 */ 1807 static int wlan_get_scanid(struct wlan_objmgr_pdev *pdev, 1808 uint32_t *scan_id, uint64_t cookie) 1809 { 1810 struct scan_req *scan_req; 1811 qdf_list_node_t *node = NULL; 1812 qdf_list_node_t *ptr_node = NULL; 1813 int ret = -EINVAL; 1814 struct pdev_osif_priv *osif_ctx; 1815 struct osif_scan_pdev *scan_priv; 1816 1817 /* Get NL global context from objmgr*/ 1818 osif_ctx = wlan_pdev_get_ospriv(pdev); 1819 if (!osif_ctx) { 1820 osif_err("Failed to retrieve osif context"); 1821 return ret; 1822 } 1823 scan_priv = osif_ctx->osif_scan; 1824 qdf_mutex_acquire(&scan_priv->scan_req_q_lock); 1825 if (qdf_list_empty(&scan_priv->scan_req_q)) { 1826 qdf_mutex_release(&scan_priv->scan_req_q_lock); 1827 osif_err("Failed to retrieve scan id"); 1828 return ret; 1829 } 1830 1831 if (QDF_STATUS_SUCCESS != 1832 qdf_list_peek_front(&scan_priv->scan_req_q, 1833 &ptr_node)) { 1834 qdf_mutex_release(&scan_priv->scan_req_q_lock); 1835 return ret; 1836 } 1837 1838 do { 1839 node = ptr_node; 1840 scan_req = qdf_container_of(node, struct scan_req, node); 1841 if (cookie == 1842 (uintptr_t)(scan_req->scan_request)) { 1843 *scan_id = scan_req->scan_id; 1844 ret = 0; 1845 break; 1846 } 1847 } while (QDF_STATUS_SUCCESS == 1848 qdf_list_peek_next(&scan_priv->scan_req_q, 1849 node, &ptr_node)); 1850 1851 qdf_mutex_release(&scan_priv->scan_req_q_lock); 1852 1853 return ret; 1854 } 1855 1856 QDF_STATUS wlan_abort_scan(struct wlan_objmgr_pdev *pdev, 1857 uint32_t pdev_id, uint32_t vdev_id, 1858 wlan_scan_id scan_id, bool sync) 1859 { 1860 struct scan_cancel_request *req; 1861 struct pdev_osif_priv *osif_ctx; 1862 struct osif_scan_pdev *scan_priv; 1863 QDF_STATUS status; 1864 struct wlan_objmgr_vdev *vdev; 1865 1866 req = qdf_mem_malloc(sizeof(*req)); 1867 if (!req) 1868 return QDF_STATUS_E_NOMEM; 1869 1870 /* Get NL global context from objmgr*/ 1871 osif_ctx = wlan_pdev_get_ospriv(pdev); 1872 if (!osif_ctx) { 1873 osif_err("Failed to retrieve osif context"); 1874 qdf_mem_free(req); 1875 return QDF_STATUS_E_FAILURE; 1876 } 1877 if (vdev_id == INVAL_VDEV_ID) 1878 vdev = wlan_objmgr_pdev_get_first_vdev(pdev, WLAN_OSIF_ID); 1879 else 1880 vdev = wlan_objmgr_get_vdev_by_id_from_pdev(pdev, 1881 vdev_id, WLAN_OSIF_ID); 1882 1883 if (!vdev) { 1884 qdf_mem_free(req); 1885 return QDF_STATUS_E_INVAL; 1886 } 1887 scan_priv = osif_ctx->osif_scan; 1888 req->cancel_req.requester = scan_priv->req_id; 1889 req->vdev = vdev; 1890 req->cancel_req.scan_id = scan_id; 1891 req->cancel_req.pdev_id = pdev_id; 1892 req->cancel_req.vdev_id = vdev_id; 1893 if (scan_id != INVAL_SCAN_ID && scan_id != CANCEL_HOST_SCAN_ID) 1894 req->cancel_req.req_type = WLAN_SCAN_CANCEL_SINGLE; 1895 else if (scan_id == CANCEL_HOST_SCAN_ID) 1896 req->cancel_req.req_type = WLAN_SCAN_CANCEL_HOST_VDEV_ALL; 1897 else if (vdev_id == INVAL_VDEV_ID) 1898 req->cancel_req.req_type = WLAN_SCAN_CANCEL_PDEV_ALL; 1899 else 1900 req->cancel_req.req_type = WLAN_SCAN_CANCEL_VDEV_ALL; 1901 1902 osif_debug("Type %d Vdev %d pdev %d scan id %d sync %d", 1903 req->cancel_req.req_type, req->cancel_req.vdev_id, 1904 req->cancel_req.pdev_id, req->cancel_req.scan_id, sync); 1905 1906 if (sync) 1907 status = ucfg_scan_cancel_sync(req); 1908 else 1909 status = ucfg_scan_cancel(req); 1910 if (QDF_IS_STATUS_ERROR(status)) 1911 osif_err("Cancel scan request failed"); 1912 1913 wlan_objmgr_vdev_release_ref(vdev, WLAN_OSIF_ID); 1914 1915 return status; 1916 } 1917 1918 qdf_export_symbol(wlan_abort_scan); 1919 1920 int wlan_cfg80211_abort_scan(struct wlan_objmgr_pdev *pdev) 1921 { 1922 uint8_t pdev_id; 1923 1924 pdev_id = wlan_objmgr_pdev_get_pdev_id(pdev); 1925 1926 if (ucfg_scan_get_pdev_status(pdev) != 1927 SCAN_NOT_IN_PROGRESS) 1928 wlan_abort_scan(pdev, pdev_id, 1929 INVAL_VDEV_ID, INVAL_SCAN_ID, true); 1930 1931 return 0; 1932 } 1933 1934 int wlan_vendor_abort_scan(struct wlan_objmgr_pdev *pdev, 1935 const void *data, int data_len) 1936 { 1937 struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_SCAN_MAX + 1]; 1938 int ret = -EINVAL; 1939 wlan_scan_id scan_id; 1940 uint64_t cookie; 1941 uint8_t pdev_id; 1942 1943 pdev_id = wlan_objmgr_pdev_get_pdev_id(pdev); 1944 if (wlan_cfg80211_nla_parse(tb, QCA_WLAN_VENDOR_ATTR_SCAN_MAX, data, 1945 data_len, cfg80211_scan_policy)) { 1946 osif_err("Invalid ATTR"); 1947 return ret; 1948 } 1949 1950 if (tb[QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE]) { 1951 cookie = nla_get_u64( 1952 tb[QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE]); 1953 ret = wlan_get_scanid(pdev, &scan_id, cookie); 1954 if (ret != 0) 1955 return ret; 1956 if (ucfg_scan_get_pdev_status(pdev) != 1957 SCAN_NOT_IN_PROGRESS) 1958 wlan_abort_scan(pdev, INVAL_PDEV_ID, 1959 INVAL_VDEV_ID, scan_id, true); 1960 } 1961 return 0; 1962 } 1963 1964 static inline struct ieee80211_channel * 1965 wlan_get_ieee80211_channel(struct wiphy *wiphy, 1966 struct wlan_objmgr_pdev *pdev, 1967 int chan_freq) 1968 { 1969 struct ieee80211_channel *chan; 1970 1971 chan = ieee80211_get_channel(wiphy, chan_freq); 1972 if (!chan) 1973 osif_err_rl("chan is NULL, freq: %d", chan_freq); 1974 1975 return chan; 1976 } 1977 1978 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 4, 0)) || \ 1979 defined(CFG80211_INFORM_BSS_FRAME_DATA) 1980 /** 1981 * wlan_fill_per_chain_rssi() - fill per chain RSSI in inform bss 1982 * @data: destination bss data 1983 * @bss: source bss data containing per chain RSSI 1984 * 1985 * Return: void 1986 */ 1987 #if defined(CFG80211_SCAN_PER_CHAIN_RSSI_SUPPORT) || \ 1988 (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 16, 0)) 1989 static void wlan_fill_per_chain_rssi(struct cfg80211_inform_bss *data, 1990 struct wlan_cfg80211_inform_bss *bss) 1991 { 1992 1993 uint32_t i; 1994 1995 if (!bss || !data) { 1996 osif_err("Received bss is NULL"); 1997 return; 1998 } 1999 for (i = 0; i < WLAN_MGMT_TXRX_HOST_MAX_ANTENNA; i++) { 2000 if (!bss->per_chain_rssi[i] || 2001 (bss->per_chain_rssi[i] == WLAN_INVALID_PER_CHAIN_RSSI)) 2002 continue; 2003 data->chain_signal[i] = bss->per_chain_rssi[i]; 2004 data->chains |= BIT(i); 2005 } 2006 } 2007 #else 2008 static inline void 2009 wlan_fill_per_chain_rssi(struct cfg80211_inform_bss *data, 2010 struct wlan_cfg80211_inform_bss *bss) 2011 { 2012 } 2013 #endif 2014 2015 struct cfg80211_bss * 2016 wlan_cfg80211_inform_bss_frame_data(struct wiphy *wiphy, 2017 struct wlan_cfg80211_inform_bss *bss) 2018 { 2019 struct cfg80211_inform_bss data = {0}; 2020 2021 if (!bss) { 2022 osif_err("bss is null"); 2023 return NULL; 2024 } 2025 wlan_fill_per_chain_rssi(&data, bss); 2026 2027 data.chan = bss->chan; 2028 data.boottime_ns = bss->boottime_ns; 2029 data.signal = bss->rssi; 2030 return cfg80211_inform_bss_frame_data(wiphy, &data, bss->mgmt, 2031 bss->frame_len, GFP_ATOMIC); 2032 } 2033 #else 2034 struct cfg80211_bss * 2035 wlan_cfg80211_inform_bss_frame_data(struct wiphy *wiphy, 2036 struct wlan_cfg80211_inform_bss *bss) 2037 2038 { 2039 return cfg80211_inform_bss_frame(wiphy, bss->chan, bss->mgmt, 2040 bss->frame_len, 2041 bss->rssi, GFP_ATOMIC); 2042 } 2043 #endif 2044 2045 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0)) 2046 static inline void wlan_cfg80211_put_bss(struct wiphy *wiphy, 2047 struct cfg80211_bss *bss) 2048 { 2049 cfg80211_put_bss(wiphy, bss); 2050 } 2051 #else 2052 static inline void wlan_cfg80211_put_bss(struct wiphy *wiphy, 2053 struct cfg80211_bss *bss) 2054 { 2055 cfg80211_put_bss(bss); 2056 } 2057 #endif 2058 2059 void wlan_cfg80211_inform_bss_frame(struct wlan_objmgr_pdev *pdev, 2060 struct scan_cache_entry *scan_params) 2061 { 2062 struct pdev_osif_priv *pdev_ospriv = wlan_pdev_get_ospriv(pdev); 2063 struct wiphy *wiphy; 2064 struct cfg80211_bss *bss = NULL; 2065 struct wlan_cfg80211_inform_bss bss_data = {0}; 2066 2067 if (!pdev_ospriv) { 2068 osif_err("os_priv is NULL"); 2069 return; 2070 } 2071 2072 wiphy = pdev_ospriv->wiphy; 2073 2074 bss_data.frame_len = ucfg_scan_get_entry_frame_len(scan_params); 2075 bss_data.mgmt = qdf_mem_malloc_atomic(bss_data.frame_len); 2076 if (!bss_data.mgmt) { 2077 osif_err("bss mem alloc failed for seq %d", 2078 scan_params->seq_num); 2079 return; 2080 } 2081 qdf_mem_copy(bss_data.mgmt, 2082 util_scan_entry_frame_ptr(scan_params), 2083 util_scan_entry_frame_len(scan_params)); 2084 /* 2085 * Android does not want the timestamp from the frame. 2086 * Instead it wants a monotonic increasing value 2087 */ 2088 bss_data.mgmt->u.probe_resp.timestamp = qdf_get_monotonic_boottime(); 2089 /* 2090 * Based on .ini configuration, raw rssi can be reported for bss. 2091 * Raw rssi is typically used for estimating power. 2092 */ 2093 bss_data.rssi = scan_params->rssi_raw; 2094 2095 bss_data.chan = wlan_get_ieee80211_channel(wiphy, pdev, 2096 scan_params->channel.chan_freq); 2097 if (!bss_data.chan) { 2098 osif_err_rl("Channel not found for bss " QDF_MAC_ADDR_FMT " seq %d chan_freq %d", 2099 QDF_MAC_ADDR_REF(bss_data.mgmt->bssid), 2100 scan_params->seq_num, 2101 scan_params->channel.chan_freq); 2102 qdf_mem_free(bss_data.mgmt); 2103 return; 2104 } 2105 2106 /* 2107 * Supplicant takes the signal strength in terms of 2108 * mBm (1 dBm = 100 mBm). 2109 */ 2110 bss_data.rssi = QDF_MIN(bss_data.rssi, 0) * 100; 2111 2112 bss_data.boottime_ns = scan_params->boottime_ns; 2113 2114 qdf_mem_copy(bss_data.per_chain_rssi, scan_params->per_chain_rssi, 2115 WLAN_MGMT_TXRX_HOST_MAX_ANTENNA); 2116 2117 bss = wlan_cfg80211_inform_bss_frame_data(wiphy, &bss_data); 2118 if (!bss) 2119 osif_err("failed to inform bss "QDF_MAC_ADDR_FMT" seq %d", 2120 QDF_MAC_ADDR_REF(bss_data.mgmt->bssid), 2121 scan_params->seq_num); 2122 else 2123 wlan_cfg80211_put_bss(wiphy, bss); 2124 2125 qdf_mem_free(bss_data.mgmt); 2126 } 2127 2128 #if (LINUX_VERSION_CODE < KERNEL_VERSION(4, 1, 0)) && \ 2129 !defined(WITH_BACKPORTS) && !defined(IEEE80211_PRIVACY) 2130 struct cfg80211_bss *wlan_cfg80211_get_bss(struct wiphy *wiphy, 2131 struct ieee80211_channel *channel, 2132 const u8 *bssid, const u8 *ssid, 2133 size_t ssid_len) 2134 { 2135 return cfg80211_get_bss(wiphy, channel, bssid, 2136 ssid, ssid_len, 2137 WLAN_CAPABILITY_ESS, 2138 WLAN_CAPABILITY_ESS); 2139 } 2140 #else 2141 struct cfg80211_bss *wlan_cfg80211_get_bss(struct wiphy *wiphy, 2142 struct ieee80211_channel *channel, 2143 const u8 *bssid, const u8 *ssid, 2144 size_t ssid_len) 2145 { 2146 return cfg80211_get_bss(wiphy, channel, bssid, 2147 ssid, ssid_len, 2148 IEEE80211_BSS_TYPE_ESS, 2149 IEEE80211_PRIVACY_ANY); 2150 } 2151 #endif 2152 2153 QDF_STATUS __wlan_cfg80211_unlink_bss_list(struct wiphy *wiphy, 2154 struct wlan_objmgr_pdev *pdev, 2155 uint8_t *bssid, uint8_t *ssid, 2156 uint8_t ssid_len) 2157 { 2158 struct cfg80211_bss *bss = NULL; 2159 uint8_t vdev_id; 2160 2161 if (bssid && wlan_get_connected_vdev_by_bssid(pdev, bssid, &vdev_id)) { 2162 osif_debug("BSS "QDF_MAC_ADDR_FMT" connected on vdev %d dont unlink", 2163 QDF_MAC_ADDR_REF(bssid), vdev_id); 2164 return QDF_STATUS_E_FAILURE; 2165 } 2166 2167 bss = wlan_cfg80211_get_bss(wiphy, NULL, bssid, 2168 ssid, ssid_len); 2169 if (!bss) { 2170 osif_info("BSS "QDF_MAC_ADDR_FMT" not found", 2171 QDF_MAC_ADDR_REF(bssid)); 2172 } else { 2173 osif_debug("unlink entry for ssid:" QDF_SSID_FMT " and BSSID " QDF_MAC_ADDR_FMT, 2174 QDF_SSID_REF(ssid_len, ssid), 2175 QDF_MAC_ADDR_REF(bssid)); 2176 cfg80211_unlink_bss(wiphy, bss); 2177 wlan_cfg80211_put_bss(wiphy, bss); 2178 } 2179 2180 /* 2181 * Kernel creates separate entries into it's bss list for probe resp 2182 * and beacon for hidden AP. Both have separate ref count and thus 2183 * deleting one will not delete other entry. 2184 * If beacon entry of the hidden AP is not deleted and AP switch to 2185 * broadcasting SSID from Hiding SSID, kernel will reject the beacon 2186 * entry. So unlink the hidden beacon entry (if present) as well from 2187 * kernel, to avoid such issue. 2188 */ 2189 bss = wlan_cfg80211_get_bss(wiphy, NULL, bssid, NULL, 0); 2190 if (!bss) { 2191 osif_debug("Hidden bss not found for ssid:" QDF_SSID_FMT " BSSID: " QDF_MAC_ADDR_FMT " sid_len %d", 2192 QDF_SSID_REF(ssid_len, ssid), 2193 QDF_MAC_ADDR_REF(bssid), ssid_len); 2194 } else { 2195 osif_debug("unlink entry for Hidden ssid:" QDF_SSID_FMT " and BSSID " QDF_MAC_ADDR_FMT, 2196 QDF_SSID_REF(ssid_len, ssid), 2197 QDF_MAC_ADDR_REF(bssid)); 2198 2199 cfg80211_unlink_bss(wiphy, bss); 2200 /* cfg80211_get_bss get bss with ref count so release it */ 2201 wlan_cfg80211_put_bss(wiphy, bss); 2202 } 2203 2204 return QDF_STATUS_SUCCESS; 2205 } 2206 void wlan_cfg80211_unlink_bss_list(struct wlan_objmgr_pdev *pdev, 2207 struct scan_cache_entry *scan_entry) 2208 { 2209 struct pdev_osif_priv *pdev_ospriv = wlan_pdev_get_ospriv(pdev); 2210 struct wiphy *wiphy; 2211 2212 if (!pdev_ospriv) { 2213 osif_err("os_priv is NULL"); 2214 return; 2215 } 2216 2217 wiphy = pdev_ospriv->wiphy; 2218 2219 __wlan_cfg80211_unlink_bss_list(wiphy, pdev, scan_entry->bssid.bytes, 2220 scan_entry->ssid.ssid, 2221 scan_entry->ssid.length); 2222 } 2223 2224 #if (LINUX_VERSION_CODE < KERNEL_VERSION(4, 12, 0)) 2225 /* 2226 * wlan_scan_wiphy_set_max_sched_scans() - set maximum number of scheduled scans 2227 * to wiphy. 2228 * @wiphy: pointer to wiphy 2229 * @max_scans: max num scans to be configured 2230 * 2231 */ 2232 static inline void 2233 wlan_scan_wiphy_set_max_sched_scans(struct wiphy *wiphy, uint8_t max_scans) 2234 { 2235 if (max_scans == 0) 2236 wiphy->flags &= ~WIPHY_FLAG_SUPPORTS_SCHED_SCAN; 2237 else 2238 wiphy->flags |= WIPHY_FLAG_SUPPORTS_SCHED_SCAN; 2239 } 2240 #else 2241 static inline void 2242 wlan_scan_wiphy_set_max_sched_scans(struct wiphy *wiphy, uint8_t max_scans) 2243 { 2244 wiphy->max_sched_scan_reqs = max_scans; 2245 } 2246 #endif /* KERNEL_VERSION(4, 12, 0) */ 2247 2248 #if defined(CFG80211_REPORT_BETTER_BSS_IN_SCHED_SCAN) || \ 2249 (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 11, 0)) 2250 void wlan_scan_cfg80211_add_connected_pno_support(struct wiphy *wiphy) 2251 { 2252 wiphy_ext_feature_set(wiphy, 2253 NL80211_EXT_FEATURE_SCHED_SCAN_RELATIVE_RSSI); 2254 } 2255 #endif 2256 2257 #if ((LINUX_VERSION_CODE > KERNEL_VERSION(4, 4, 0)) || \ 2258 defined(CFG80211_MULTI_SCAN_PLAN_BACKPORT)) && \ 2259 defined(FEATURE_WLAN_SCAN_PNO) 2260 void wlan_config_sched_scan_plans_to_wiphy(struct wiphy *wiphy, 2261 struct wlan_objmgr_psoc *psoc) 2262 { 2263 if (ucfg_scan_get_pno_scan_support(psoc)) { 2264 wlan_scan_wiphy_set_max_sched_scans(wiphy, 1); 2265 wiphy->max_sched_scan_ssids = SCAN_PNO_MAX_SUPP_NETWORKS; 2266 wiphy->max_match_sets = SCAN_PNO_MAX_SUPP_NETWORKS; 2267 wiphy->max_sched_scan_ie_len = SCAN_MAX_IE_LENGTH; 2268 wiphy->max_sched_scan_plans = SCAN_PNO_MAX_PLAN_REQUEST; 2269 2270 wiphy->max_sched_scan_plan_interval = 2271 ucfg_scan_get_max_sched_scan_plan_interval(psoc); 2272 2273 wiphy->max_sched_scan_plan_iterations = 2274 ucfg_scan_get_max_sched_scan_plan_iterations(psoc); 2275 } 2276 } 2277 #endif 2278