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