xref: /wlan-dirver/qca-wifi-host-cmn/umac/cmn_services/utils/src/wlan_utility.c (revision 97f44cd39e4ff816eaa1710279d28cf6b9e65ad9)
1 /*
2  * Copyright (c) 2017-2020 The Linux Foundation. All rights reserved.
3  *
4  * Permission to use, copy, modify, and/or distribute this software for any
5  * purpose with or without fee is hereby granted, provided that the above
6  * copyright notice and this permission notice appear in all copies.
7  *
8  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15  */
16 
17 /**
18  * DOC: This file contains definition for mandatory legacy API
19  */
20 
21 #include "qdf_str.h"
22 #include "wlan_utility.h"
23 #include <wlan_cmn.h>
24 #include "wlan_osif_priv.h"
25 #include <net/cfg80211.h>
26 #include <qdf_module.h>
27 #include <wlan_vdev_mlme_api.h>
28 #include "cfg_ucfg_api.h"
29 
30 uint32_t wlan_chan_to_freq(uint8_t chan)
31 {
32 	if (chan == 0 )
33 		return 0;
34 
35 	if (chan < WLAN_24_GHZ_CHANNEL_14)
36 		return WLAN_24_GHZ_BASE_FREQ + chan * WLAN_CHAN_SPACING_5MHZ;
37 	else if (chan == WLAN_24_GHZ_CHANNEL_14)
38 		return WLAN_CHAN_14_FREQ;
39 	else if (chan < WLAN_24_GHZ_CHANNEL_27)
40 		/* ch 15 - ch 26 */
41 		return WLAN_CHAN_15_FREQ +
42 		  (chan - WLAN_24_GHZ_CHANNEL_15) * WLAN_CHAN_SPACING_20MHZ;
43 	else if (chan == WLAN_5_GHZ_CHANNEL_170)
44 		return WLAN_CHAN_170_FREQ;
45 	else
46 		return WLAN_5_GHZ_BASE_FREQ + chan * WLAN_CHAN_SPACING_5MHZ;
47 }
48 
49 uint8_t wlan_freq_to_chan(uint32_t freq)
50 {
51 	uint8_t chan;
52 
53 	if (freq == 0)
54 		return 0;
55 
56 	if (freq > WLAN_24_GHZ_BASE_FREQ && freq < WLAN_CHAN_14_FREQ)
57 		chan = ((freq - WLAN_24_GHZ_BASE_FREQ) /
58 			WLAN_CHAN_SPACING_5MHZ);
59 	else if (freq == WLAN_CHAN_14_FREQ)
60 		chan = WLAN_24_GHZ_CHANNEL_14;
61 	else if ((freq > WLAN_24_GHZ_BASE_FREQ) &&
62 		(freq < WLAN_5_GHZ_BASE_FREQ))
63 		chan = (((freq - WLAN_CHAN_15_FREQ) /
64 			WLAN_CHAN_SPACING_20MHZ) +
65 			WLAN_24_GHZ_CHANNEL_15);
66 	else
67 		chan = (freq - WLAN_5_GHZ_BASE_FREQ) /
68 			WLAN_CHAN_SPACING_5MHZ;
69 
70 	return chan;
71 }
72 
73 bool wlan_is_ie_valid(const uint8_t *ie, size_t ie_len)
74 {
75 	uint8_t elen;
76 
77 	while (ie_len) {
78 		if (ie_len < 2)
79 			return false;
80 
81 		elen = ie[1];
82 		ie_len -= 2;
83 		ie += 2;
84 		if (elen > ie_len)
85 			return false;
86 
87 		ie_len -= elen;
88 		ie += elen;
89 	}
90 
91 	return true;
92 }
93 
94 static const uint8_t *wlan_get_ie_ptr_from_eid_n_oui(uint8_t eid,
95 						     const uint8_t *oui,
96 						     uint8_t oui_size,
97 						     const uint8_t *ie,
98 						     uint16_t ie_len)
99 {
100 	int32_t left = ie_len;
101 	const uint8_t *ptr = ie;
102 	uint8_t elem_id, elem_len;
103 
104 	while (left >= 2) {
105 		elem_id  = ptr[0];
106 		elem_len = ptr[1];
107 		left -= 2;
108 
109 		if (elem_len > left)
110 			return NULL;
111 
112 		if (eid == elem_id) {
113 			/* if oui is not provide eid match is enough */
114 			if (!oui)
115 				return ptr;
116 
117 			/*
118 			 * if oui is provided and oui_size is more than left
119 			 * bytes, then we cannot have match
120 			 */
121 			if (oui_size > left)
122 				return NULL;
123 
124 			if (qdf_mem_cmp(&ptr[2], oui, oui_size) == 0)
125 				return ptr;
126 		}
127 
128 		left -= elem_len;
129 		ptr += (elem_len + 2);
130 	}
131 
132 	return NULL;
133 }
134 
135 const uint8_t *wlan_get_ie_ptr_from_eid(uint8_t eid,
136 					const uint8_t *ie,
137 					int ie_len)
138 {
139 	return wlan_get_ie_ptr_from_eid_n_oui(eid, NULL, 0, ie, ie_len);
140 }
141 
142 const uint8_t *wlan_get_vendor_ie_ptr_from_oui(const uint8_t *oui,
143 					       uint8_t oui_size,
144 					       const uint8_t *ie,
145 					       uint16_t ie_len)
146 {
147 	return wlan_get_ie_ptr_from_eid_n_oui(WLAN_MAC_EID_VENDOR,
148 					      oui, oui_size, ie, ie_len);
149 }
150 
151 const uint8_t *wlan_get_ext_ie_ptr_from_ext_id(const uint8_t *oui,
152 					       uint8_t oui_size,
153 					       const uint8_t *ie,
154 					       uint16_t ie_len)
155 {
156 	return wlan_get_ie_ptr_from_eid_n_oui(WLAN_MAC_EID_EXT,
157 					      oui, oui_size, ie, ie_len);
158 }
159 
160 bool wlan_is_emulation_platform(uint32_t phy_version)
161 {
162 	if ((phy_version == 0xABC0) || (phy_version == 0xABC1) ||
163 		(phy_version == 0xABC2) || (phy_version == 0xABC3) ||
164 		(phy_version == 0xFFFF) || (phy_version == 0xABCD))
165 		return true;
166 
167 	return false;
168 }
169 
170 uint32_t wlan_get_pdev_id_from_vdev_id(struct wlan_objmgr_psoc *psoc,
171 				      uint8_t vdev_id,
172 				      wlan_objmgr_ref_dbgid dbg_id)
173 {
174 	struct wlan_objmgr_vdev *vdev;
175 	struct wlan_objmgr_pdev *pdev = NULL;
176 	uint32_t pdev_id = WLAN_INVALID_PDEV_ID;
177 
178 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc,
179 						    vdev_id, dbg_id);
180 
181 	if (vdev) {
182 		pdev = wlan_vdev_get_pdev(vdev);
183 		if (pdev)
184 			pdev_id = wlan_objmgr_pdev_get_pdev_id(pdev);
185 		wlan_objmgr_vdev_release_ref(vdev, dbg_id);
186 	}
187 
188 	return pdev_id;
189 }
190 qdf_export_symbol(wlan_get_pdev_id_from_vdev_id);
191 
192 static void wlan_vdev_active(struct wlan_objmgr_pdev *pdev, void *object,
193 			     void *arg)
194 {
195 	struct wlan_objmgr_vdev *vdev = (struct wlan_objmgr_vdev *)object;
196 	uint8_t *flag = (uint8_t *)arg;
197 
198 	wlan_vdev_obj_lock(vdev);
199 	if (wlan_vdev_mlme_is_active(vdev) == QDF_STATUS_SUCCESS)
200 		*flag = 1;
201 
202 	wlan_vdev_obj_unlock(vdev);
203 }
204 
205 QDF_STATUS wlan_vdev_is_up(struct wlan_objmgr_vdev *vdev)
206 {
207 	return wlan_vdev_allow_connect_n_tx(vdev);
208 }
209 qdf_export_symbol(wlan_vdev_is_up);
210 
211 QDF_STATUS wlan_util_is_vdev_active(struct wlan_objmgr_pdev *pdev,
212 				    wlan_objmgr_ref_dbgid dbg_id)
213 {
214 	uint8_t flag = 0;
215 
216 	if (!pdev)
217 		return QDF_STATUS_E_INVAL;
218 
219 	wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP, wlan_vdev_active,
220 					  &flag, 0, dbg_id);
221 
222 	if (flag == 1)
223 		return QDF_STATUS_SUCCESS;
224 
225 	return QDF_STATUS_E_INVAL;
226 }
227 
228 qdf_export_symbol(wlan_util_is_vdev_active);
229 
230 void wlan_util_change_map_index(unsigned long *map, uint8_t id, uint8_t set)
231 {
232 	if (set)
233 		qdf_set_bit(id, map);
234 	else
235 		qdf_clear_bit(id, map);
236 }
237 
238 bool wlan_util_map_index_is_set(unsigned long *map, uint8_t id)
239 {
240 	return qdf_test_bit(id, map);
241 }
242 
243 bool wlan_util_map_is_any_index_set(unsigned long *map, unsigned long nbytes)
244 {
245 	return !qdf_bitmap_empty(map, QDF_CHAR_BIT * nbytes);
246 }
247 
248 static void wlan_vdev_chan_change_pending(struct wlan_objmgr_pdev *pdev,
249 					  void *object, void *arg)
250 {
251 	struct wlan_objmgr_vdev *vdev = (struct wlan_objmgr_vdev *)object;
252 	unsigned long *vdev_id_map = (unsigned long *)arg;
253 	uint8_t id = 0;
254 	struct wlan_objmgr_psoc *psoc;
255 
256 	psoc = wlan_pdev_get_psoc(pdev);
257 	if (!psoc)
258 		return;
259 
260 	wlan_vdev_obj_lock(vdev);
261 	if (wlan_vdev_chan_config_valid(vdev) == QDF_STATUS_SUCCESS) {
262 		id = wlan_vdev_get_id(vdev);
263 		/* Invalid vdev id */
264 		if (id >= wlan_psoc_get_max_vdev_count(psoc)) {
265 			wlan_vdev_obj_unlock(vdev);
266 			return;
267 		}
268 
269 		wlan_util_change_map_index(vdev_id_map, id, 1);
270 	}
271 
272 	wlan_vdev_obj_unlock(vdev);
273 }
274 
275 QDF_STATUS wlan_pdev_chan_change_pending_vdevs(struct wlan_objmgr_pdev *pdev,
276 					       unsigned long *vdev_id_map,
277 					       wlan_objmgr_ref_dbgid dbg_id)
278 {
279 	if (!pdev)
280 		return QDF_STATUS_E_INVAL;
281 
282 	wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP,
283 					  wlan_vdev_chan_change_pending,
284 					  vdev_id_map, 0, dbg_id);
285 
286 	return QDF_STATUS_SUCCESS;
287 }
288 
289 static void wlan_vdev_down_pending(struct wlan_objmgr_pdev *pdev,
290 				   void *object, void *arg)
291 {
292 	struct wlan_objmgr_vdev *vdev = (struct wlan_objmgr_vdev *)object;
293 	unsigned long *vdev_id_map = (unsigned long *)arg;
294 	uint8_t id = 0;
295 	struct wlan_objmgr_psoc *psoc;
296 
297 	psoc = wlan_pdev_get_psoc(pdev);
298 	if (!psoc)
299 		return;
300 
301 	wlan_vdev_obj_lock(vdev);
302 	if (wlan_vdev_mlme_is_init_state(vdev) != QDF_STATUS_SUCCESS) {
303 		id = wlan_vdev_get_id(vdev);
304 		/* Invalid vdev id */
305 		if (id >= wlan_psoc_get_max_vdev_count(psoc)) {
306 			wlan_vdev_obj_unlock(vdev);
307 			return;
308 		}
309 		wlan_util_change_map_index(vdev_id_map, id, 1);
310 	}
311 
312 	wlan_vdev_obj_unlock(vdev);
313 }
314 
315 static void wlan_vdev_ap_down_pending(struct wlan_objmgr_pdev *pdev,
316 				      void *object, void *arg)
317 {
318 	struct wlan_objmgr_vdev *vdev = (struct wlan_objmgr_vdev *)object;
319 	unsigned long *vdev_id_map = (unsigned long *)arg;
320 	uint8_t id = 0;
321 	struct wlan_objmgr_psoc *psoc;
322 
323 	psoc = wlan_pdev_get_psoc(pdev);
324 	if (!psoc)
325 		return;
326 
327 	if (wlan_vdev_mlme_get_opmode(vdev) != QDF_SAP_MODE)
328 		return;
329 
330 	wlan_vdev_obj_lock(vdev);
331 	if (wlan_vdev_mlme_is_init_state(vdev) != QDF_STATUS_SUCCESS) {
332 		id = wlan_vdev_get_id(vdev);
333 		/* Invalid vdev id */
334 		if (id >= wlan_psoc_get_max_vdev_count(psoc)) {
335 			wlan_vdev_obj_unlock(vdev);
336 			return;
337 		}
338 		wlan_util_change_map_index(vdev_id_map, id, 1);
339 	}
340 
341 	wlan_vdev_obj_unlock(vdev);
342 }
343 
344 QDF_STATUS wlan_pdev_chan_change_pending_vdevs_down(
345 					struct wlan_objmgr_pdev *pdev,
346 					unsigned long *vdev_id_map,
347 					wlan_objmgr_ref_dbgid dbg_id)
348 {
349 	if (!pdev)
350 		return QDF_STATUS_E_INVAL;
351 
352 	wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP,
353 					  wlan_vdev_down_pending,
354 					  vdev_id_map, 0, dbg_id);
355 
356 	return QDF_STATUS_SUCCESS;
357 }
358 
359 QDF_STATUS wlan_pdev_chan_change_pending_ap_vdevs_down(
360 						struct wlan_objmgr_pdev *pdev,
361 						unsigned long *vdev_id_map,
362 						wlan_objmgr_ref_dbgid dbg_id)
363 {
364 	if (!pdev)
365 		return QDF_STATUS_E_INVAL;
366 
367 	wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP,
368 					  wlan_vdev_ap_down_pending,
369 					  vdev_id_map, 0, dbg_id);
370 
371 	return QDF_STATUS_SUCCESS;
372 }
373 
374 QDF_STATUS wlan_chan_eq(struct wlan_channel *chan1, struct wlan_channel *chan2)
375 {
376 	if ((chan1->ch_ieee == chan2->ch_ieee) &&
377 	    (chan1->ch_freq_seg2 == chan2->ch_freq_seg2))
378 		return QDF_STATUS_SUCCESS;
379 
380 	return QDF_STATUS_E_FAILURE;
381 }
382 
383 void wlan_chan_copy(struct wlan_channel *tgt, struct wlan_channel *src)
384 {
385 	qdf_mem_copy(tgt, src, sizeof(struct wlan_channel));
386 }
387 
388 struct wlan_channel *wlan_vdev_get_active_channel(struct wlan_objmgr_vdev *vdev)
389 {
390 	struct wlan_channel *comp_vdev_chan = NULL;
391 
392 	if (wlan_vdev_chan_config_valid(vdev) == QDF_STATUS_SUCCESS) {
393 		/* compare with BSS channel, when vdev is active, since desired
394 		 * channel gets update, if channel is triggered in another path
395 		 */
396 		if (wlan_vdev_mlme_is_active(vdev) == QDF_STATUS_SUCCESS)
397 			comp_vdev_chan = wlan_vdev_mlme_get_bss_chan(vdev);
398 		else
399 			comp_vdev_chan = wlan_vdev_mlme_get_des_chan(vdev);
400 	}
401 
402 	return comp_vdev_chan;
403 }
404 
405 static void wlan_pdev_chan_match(struct wlan_objmgr_pdev *pdev, void *object,
406 				 void *arg)
407 {
408 	struct wlan_objmgr_vdev *comp_vdev = (struct wlan_objmgr_vdev *)object;
409 	struct wlan_vdev_ch_check_filter *ch_filter = arg;
410 	struct wlan_channel vdev_chan, *chan;
411 	struct wlan_channel *iter_vdev_chan;
412 
413 	if (ch_filter->flag)
414 		return;
415 
416 	if (comp_vdev == ch_filter->vdev)
417 		return;
418 
419 	wlan_vdev_obj_lock(comp_vdev);
420 	chan = wlan_vdev_get_active_channel(comp_vdev);
421 	if (!chan) {
422 		wlan_vdev_obj_unlock(comp_vdev);
423 		return;
424 	}
425 	wlan_chan_copy(&vdev_chan, chan);
426 	wlan_vdev_obj_unlock(comp_vdev);
427 
428 	wlan_vdev_obj_lock(ch_filter->vdev);
429 	iter_vdev_chan = wlan_vdev_mlme_get_des_chan(ch_filter->vdev);
430 	if (wlan_chan_eq(&vdev_chan, iter_vdev_chan)
431 		!= QDF_STATUS_SUCCESS) {
432 		ch_filter->flag = 1;
433 		qdf_nofl_err("==> iter vdev id: %d: ieee %d, mode %d",
434 			     wlan_vdev_get_id(comp_vdev),
435 			     vdev_chan.ch_ieee,
436 			     vdev_chan.ch_phymode);
437 		qdf_nofl_err("fl %016llx, fl-ext %08x, s1 %d, s2 %d ",
438 			     vdev_chan.ch_flags, vdev_chan.ch_flagext,
439 			     vdev_chan.ch_freq_seg1,
440 			     vdev_chan.ch_freq_seg2);
441 		qdf_nofl_err("==> base vdev id: %d: ieee %d mode %d",
442 			     wlan_vdev_get_id(ch_filter->vdev),
443 			     iter_vdev_chan->ch_ieee,
444 			     iter_vdev_chan->ch_phymode);
445 		qdf_nofl_err("fl %016llx, fl-ext %08x s1 %d, s2 %d",
446 			     iter_vdev_chan->ch_flags,
447 			     iter_vdev_chan->ch_flagext,
448 			     iter_vdev_chan->ch_freq_seg1,
449 			     iter_vdev_chan->ch_freq_seg2);
450 	}
451 	wlan_vdev_obj_unlock(ch_filter->vdev);
452 }
453 
454 QDF_STATUS wlan_util_pdev_vdevs_deschan_match(struct wlan_objmgr_pdev *pdev,
455 					      struct wlan_objmgr_vdev *vdev,
456 					      wlan_objmgr_ref_dbgid dbg_id)
457 {
458 	struct wlan_vdev_ch_check_filter ch_filter;
459 
460 	if (!pdev)
461 		return QDF_STATUS_E_INVAL;
462 
463 	if (wlan_pdev_nif_feat_cap_get(pdev, WLAN_PDEV_F_CHAN_CONCURRENCY))
464 		return QDF_STATUS_SUCCESS;
465 
466 	if (wlan_objmgr_vdev_try_get_ref(vdev, dbg_id) == QDF_STATUS_SUCCESS) {
467 		ch_filter.flag = 0;
468 		ch_filter.vdev = vdev;
469 
470 		wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP,
471 						  wlan_pdev_chan_match,
472 						  &ch_filter, 0, dbg_id);
473 
474 		wlan_objmgr_vdev_release_ref(vdev, dbg_id);
475 
476 		if (ch_filter.flag == 0)
477 			return QDF_STATUS_SUCCESS;
478 	}
479 
480 	return QDF_STATUS_E_FAILURE;
481 }
482 
483 static void wlan_vdev_restart_progress(struct wlan_objmgr_pdev *pdev,
484 				       void *object, void *arg)
485 {
486 	struct wlan_objmgr_vdev *vdev = (struct wlan_objmgr_vdev *)object;
487 	uint8_t *flag = (uint8_t *)arg;
488 
489 	wlan_vdev_obj_lock(vdev);
490 	if (wlan_vdev_is_restart_progress(vdev) == QDF_STATUS_SUCCESS)
491 		*flag = 1;
492 
493 	wlan_vdev_obj_unlock(vdev);
494 }
495 
496 QDF_STATUS wlan_util_is_pdev_restart_progress(struct wlan_objmgr_pdev *pdev,
497 					      wlan_objmgr_ref_dbgid dbg_id)
498 {
499 	uint8_t flag = 0;
500 
501 	if (!pdev)
502 		return QDF_STATUS_E_INVAL;
503 
504 	wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP,
505 					  wlan_vdev_restart_progress,
506 					  &flag, 0, dbg_id);
507 
508 	if (flag == 1)
509 		return QDF_STATUS_SUCCESS;
510 
511 	return QDF_STATUS_E_INVAL;
512 }
513 
514 static void wlan_vdev_scan_allowed(struct wlan_objmgr_pdev *pdev, void *object,
515 				   void *arg)
516 {
517 	struct wlan_objmgr_vdev *vdev = (struct wlan_objmgr_vdev *)object;
518 	uint8_t *flag = (uint8_t *)arg;
519 
520 	wlan_vdev_obj_lock(vdev);
521 	if (wlan_vdev_mlme_is_scan_allowed(vdev) != QDF_STATUS_SUCCESS)
522 		*flag = 1;
523 
524 	wlan_vdev_obj_unlock(vdev);
525 }
526 
527 QDF_STATUS wlan_util_is_pdev_scan_allowed(struct wlan_objmgr_pdev *pdev,
528 					  wlan_objmgr_ref_dbgid dbg_id)
529 {
530 	uint8_t flag = 0;
531 
532 	if (!pdev)
533 		return QDF_STATUS_E_INVAL;
534 
535 	wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP,
536 					  wlan_vdev_scan_allowed,
537 					  &flag, 0, dbg_id);
538 
539 	if (flag == 1)
540 		return QDF_STATUS_E_FAILURE;
541 
542 	return QDF_STATUS_SUCCESS;
543 }
544 
545 void
546 wlan_util_stats_get_rssi(bool db2dbm_enabled, int32_t bcn_snr, int32_t dat_snr,
547 			 int8_t *rssi)
548 {
549 	uint32_t snr;
550 
551 	if (db2dbm_enabled) {
552 		if (TGT_IS_VALID_RSSI(bcn_snr))
553 			*rssi = bcn_snr;
554 		else if (TGT_IS_VALID_RSSI(dat_snr))
555 			*rssi = dat_snr;
556 		else
557 			*rssi = TGT_NOISE_FLOOR_DBM;
558 	} else {
559 		if (TGT_IS_VALID_SNR(bcn_snr))
560 			snr = bcn_snr;
561 		else if (TGT_IS_VALID_SNR(dat_snr))
562 			snr = dat_snr;
563 		else
564 			snr = TGT_INVALID_SNR;
565 
566 		/* Get the absolute rssi value from the current rssi value */
567 		*rssi = snr + TGT_NOISE_FLOOR_DBM;
568 	}
569 }
570 
571 /**
572  * wlan_util_get_mode_specific_peer_count - This api gives vdev mode specific
573  * peer count`
574  * @pdev: PDEV object
575  * @object: vdev object
576  * @arg: argument passed by caller
577  *
578  * Return: void
579  */
580 static void
581 wlan_util_get_mode_specific_peer_count(struct wlan_objmgr_pdev *pdev,
582 				       void *object, void *arg)
583 {
584 	struct wlan_objmgr_vdev *vdev = object;
585 	uint16_t temp_count = 0;
586 	struct wlan_op_mode_peer_count *count = arg;
587 
588 	wlan_vdev_obj_lock(vdev);
589 	if (wlan_vdev_mlme_get_opmode(vdev) == count->opmode) {
590 		temp_count = wlan_vdev_get_peer_count(vdev);
591 		/* Decrement the self peer count */
592 		if (temp_count > 1)
593 			count->peer_count += (temp_count - 1);
594 	}
595 	wlan_vdev_obj_unlock(vdev);
596 }
597 
598 uint16_t wlan_util_get_peer_count_for_mode(struct wlan_objmgr_pdev *pdev,
599 					   enum QDF_OPMODE mode)
600 {
601 	struct wlan_op_mode_peer_count count;
602 
603 	count.opmode = mode;
604 	count.peer_count = 0;
605 	wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP,
606 				wlan_util_get_mode_specific_peer_count, &count,
607 				0, WLAN_OBJMGR_ID);
608 
609 	return count.peer_count;
610 }
611 
612 #ifdef CONFIG_QCA_MINIDUMP
613 void wlan_minidump_log(void *start_addr, size_t size,
614 		       void *psoc_obj,
615 		       enum wlan_minidump_host_data type,
616 		       const char *name)
617 {
618 	int setval = 0;
619 
620 	struct wlan_objmgr_psoc *psoc;
621 
622 	if (!psoc_obj) {
623 		qdf_debug("Minidump: Psoc is NULL");
624 		return;
625 	}
626 
627 	psoc = (struct wlan_objmgr_psoc *)psoc_obj;
628 
629 	switch (type) {
630 	case WLAN_MD_CP_EXT_PDEV:
631 		if (cfg_get(psoc, CFG_OL_MD_CP_EXT_PDEV))
632 			setval = 1;
633 		break;
634 	case WLAN_MD_CP_EXT_PSOC:
635 		if (cfg_get(psoc, CFG_OL_MD_CP_EXT_PSOC))
636 			setval = 1;
637 		break;
638 	case WLAN_MD_CP_EXT_VDEV:
639 		if (cfg_get(psoc, CFG_OL_MD_CP_EXT_VDEV))
640 			setval = 1;
641 		break;
642 	case WLAN_MD_CP_EXT_PEER:
643 		if (cfg_get(psoc, CFG_OL_MD_CP_EXT_PEER))
644 			setval = 1;
645 		break;
646 	case WLAN_MD_DP_SOC:
647 		if (cfg_get(psoc, CFG_OL_MD_DP_SOC))
648 			setval = 1;
649 		break;
650 	case WLAN_MD_DP_PDEV:
651 		if (cfg_get(psoc, CFG_OL_MD_DP_PDEV))
652 			setval = 1;
653 		break;
654 	case WLAN_MD_DP_PEER:
655 		if (cfg_get(psoc, CFG_OL_MD_DP_PEER))
656 			setval = 1;
657 		break;
658 	case WLAN_MD_DP_SRNG_REO_DEST:
659 	case WLAN_MD_DP_SRNG_REO_EXCEPTION:
660 	case WLAN_MD_DP_SRNG_RX_REL:
661 	case WLAN_MD_DP_SRNG_REO_REINJECT:
662 	case WLAN_MD_DP_SRNG_REO_CMD:
663 	case WLAN_MD_DP_SRNG_REO_STATUS:
664 		if (cfg_get(psoc, CFG_OL_MD_DP_SRNG_REO))
665 			setval = 1;
666 		break;
667 	case WLAN_MD_DP_SRNG_TCL_DATA:
668 	case WLAN_MD_DP_SRNG_TCL_CMD:
669 	case WLAN_MD_DP_SRNG_TCL_STATUS:
670 	case WLAN_MD_DP_SRNG_TX_COMP:
671 		if (cfg_get(psoc, CFG_OL_MD_DP_SRNG_TCL))
672 			setval = 1;
673 		break;
674 	case WLAN_MD_DP_SRNG_WBM_DESC_REL:
675 	case WLAN_MD_DP_SRNG_WBM_IDLE_LINK:
676 		if (cfg_get(psoc, CFG_OL_MD_DP_SRNG_WBM))
677 			setval = 1;
678 		break;
679 	case WLAN_MD_DP_LINK_DESC_BANK:
680 		if (cfg_get(psoc, CFG_OL_MD_DP_LINK_DESC_BANK))
681 			setval = 1;
682 		break;
683 	case WLAN_MD_DP_SRNG_RXDMA_MON_BUF:
684 	case WLAN_MD_DP_SRNG_RXDMA_MON_DST:
685 	case WLAN_MD_DP_SRNG_RXDMA_MON_DESC:
686 	case WLAN_MD_DP_SRNG_RXDMA_ERR_DST:
687 	case WLAN_MD_DP_SRNG_RXDMA_MON_STATUS:
688 		if (cfg_get(psoc, CFG_OL_MD_DP_SRNG_RXDMA))
689 			setval = 1;
690 		break;
691 	case WLAN_MD_DP_HAL_SOC:
692 		if (cfg_get(psoc, CFG_OL_MD_DP_HAL_SOC))
693 			setval = 1;
694 		break;
695 	case WLAN_MD_OBJMGR_PSOC:
696 	case WLAN_MD_OBJMGR_PSOC_TGT_INFO:
697 		if (cfg_get(psoc, CFG_OL_MD_OBJMGR_PSOC))
698 			setval = 1;
699 		break;
700 	case WLAN_MD_OBJMGR_PDEV:
701 	case WLAN_MD_OBJMGR_PDEV_MLME:
702 		if (cfg_get(psoc, CFG_OL_MD_OBJMGR_PDEV))
703 			setval = 1;
704 		break;
705 	case WLAN_MD_OBJMGR_VDEV_MLME:
706 	case WLAN_MD_OBJMGR_VDEV_SM:
707 	case WLAN_MD_OBJMGR_VDEV:
708 		if (cfg_get(psoc, CFG_OL_MD_OBJMGR_VDEV))
709 			setval = 1;
710 		break;
711 	default:
712 		qdf_debug("Minidump: Type not implemented");
713 	}
714 	if (setval)
715 		qdf_minidump_log(start_addr, size, name);
716 }
717 qdf_export_symbol(wlan_minidump_log);
718 
719 void wlan_minidump_remove(void *addr)
720 {
721 	qdf_minidump_remove(addr);
722 }
723 qdf_export_symbol(wlan_minidump_remove);
724 #else
725 void wlan_minidump_log(void *start_addr, size_t size,
726 		       void *psoc_obj,
727 		       enum wlan_minidump_host_data type,
728 		       const char *name) {}
729 qdf_export_symbol(wlan_minidump_log);
730 
731 void wlan_minidump_remove(void *addr) {}
732 qdf_export_symbol(wlan_minidump_remove);
733 #endif /* CONFIG_QCA_MINIDUMP */
734