xref: /wlan-dirver/qca-wifi-host-cmn/umac/cmn_services/obj_mgr/src/wlan_objmgr_psoc_obj.c (revision 1f55ed1a9f5050d8da228aa8dd3fff7c0242aa71)
1 /*
2  * Copyright (c) 2016-2018 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   * DOC: Public APIs to perform operations on Global objects
20   */
21 
22 #include <wlan_objmgr_cmn.h>
23 #include <wlan_objmgr_global_obj.h>
24 #include <wlan_objmgr_psoc_obj.h>
25 #include <wlan_objmgr_pdev_obj.h>
26 #include <wlan_objmgr_vdev_obj.h>
27 #include <wlan_objmgr_peer_obj.h>
28 #include <qdf_mem.h>
29 #include <qdf_types.h>
30 #include <qdf_module.h>
31 #include "wlan_objmgr_global_obj_i.h"
32 #include "wlan_objmgr_psoc_obj_i.h"
33 #include "wlan_objmgr_pdev_obj_i.h"
34 #include "wlan_objmgr_vdev_obj_i.h"
35 
36 /**
37  ** APIs to Create/Delete Global object APIs
38  */
39 static QDF_STATUS wlan_objmgr_psoc_object_status(
40 			struct wlan_objmgr_psoc *psoc)
41 {
42 	uint8_t id;
43 	QDF_STATUS status = QDF_STATUS_SUCCESS;
44 
45 	wlan_psoc_obj_lock(psoc);
46 	/* Iterate through all components to derive the object status */
47 	for (id = 0; id < WLAN_UMAC_MAX_COMPONENTS; id++) {
48 		/* If component disabled, Ignore */
49 		if (psoc->obj_status[id] == QDF_STATUS_COMP_DISABLED)
50 			continue;
51 		/* If component operates in Async, status is Partially created,
52 		 * break
53 		 */
54 		else if (psoc->obj_status[id] == QDF_STATUS_COMP_ASYNC) {
55 			if (psoc->soc_comp_priv_obj[id] == NULL) {
56 				status = QDF_STATUS_COMP_ASYNC;
57 				break;
58 			}
59 		/*
60 		 * If component failed to allocate its object, treat it as
61 		 * failure, complete object need to be cleaned up
62 		 */
63 		} else if ((psoc->obj_status[id] == QDF_STATUS_E_NOMEM) ||
64 			(psoc->obj_status[id] == QDF_STATUS_E_FAILURE)) {
65 			status = QDF_STATUS_E_FAILURE;
66 			break;
67 		}
68 	}
69 	wlan_psoc_obj_unlock(psoc);
70 
71 	return status;
72 }
73 
74 static void wlan_objmgr_psoc_peer_list_init(struct wlan_peer_list *peer_list)
75 {
76 	uint8_t i;
77 
78 	qdf_spinlock_create(&peer_list->peer_list_lock);
79 	for (i = 0; i < WLAN_PEER_HASHSIZE; i++)
80 		qdf_list_create(&peer_list->peer_hash[i],
81 			WLAN_UMAC_PSOC_MAX_PEERS +
82 			WLAN_MAX_PSOC_TEMP_PEERS);
83 }
84 
85 static void wlan_objmgr_psoc_peer_list_deinit(struct wlan_peer_list *peer_list)
86 {
87 	uint8_t i;
88 
89 	/* deinit the lock */
90 	qdf_spinlock_destroy(&peer_list->peer_list_lock);
91 	for (i = 0; i < WLAN_PEER_HASHSIZE; i++)
92 		qdf_list_destroy(&peer_list->peer_hash[i]);
93 }
94 
95 static QDF_STATUS wlan_objmgr_psoc_obj_free(struct wlan_objmgr_psoc *psoc)
96 {
97 	/* Detach PSOC from global object's psoc list  */
98 	if (wlan_objmgr_psoc_object_detach(psoc) == QDF_STATUS_E_FAILURE) {
99 		obj_mgr_err("PSOC object detach failed");
100 		return QDF_STATUS_E_FAILURE;
101 	}
102 	wlan_objmgr_psoc_peer_list_deinit(&psoc->soc_objmgr.peer_list);
103 
104 	qdf_spinlock_destroy(&psoc->psoc_lock);
105 	qdf_mem_free(psoc);
106 
107 	return QDF_STATUS_SUCCESS;
108 }
109 
110 struct wlan_objmgr_psoc *wlan_objmgr_psoc_obj_create(uint32_t phy_version,
111 						WLAN_DEV_TYPE dev_type)
112 {
113 	uint8_t id;
114 	struct wlan_objmgr_psoc *psoc = NULL;
115 	wlan_objmgr_psoc_create_handler handler;
116 	wlan_objmgr_psoc_status_handler stat_handler;
117 	struct wlan_objmgr_psoc_objmgr *objmgr;
118 	QDF_STATUS obj_status;
119 	void *arg;
120 
121 	psoc = qdf_mem_malloc(sizeof(*psoc));
122 	if (psoc == NULL) {
123 		obj_mgr_err("PSOC allocation failed");
124 		return NULL;
125 	}
126 	psoc->obj_state = WLAN_OBJ_STATE_ALLOCATED;
127 	qdf_spinlock_create(&psoc->psoc_lock);
128 	/* Initialize with default values */
129 	objmgr = &psoc->soc_objmgr;
130 	objmgr->wlan_pdev_count = 0;
131 	objmgr->wlan_vdev_count = 0;
132 	objmgr->max_vdev_count = WLAN_UMAC_PSOC_MAX_VDEVS;
133 	objmgr->wlan_peer_count = 0;
134 	objmgr->temp_peer_count = 0;
135 	objmgr->max_peer_count = WLAN_UMAC_PSOC_MAX_PEERS;
136 	qdf_atomic_init(&objmgr->ref_cnt);
137 	objmgr->print_cnt = 0;
138 	/* set phy version, dev_type in psoc */
139 	wlan_psoc_set_nif_phy_version(psoc, phy_version);
140 	wlan_psoc_set_dev_type(psoc, dev_type);
141 	/* Initialize peer list */
142 	wlan_objmgr_psoc_peer_list_init(&objmgr->peer_list);
143 	wlan_objmgr_psoc_get_ref(psoc, WLAN_OBJMGR_ID);
144 	/* Invoke registered create handlers */
145 	for (id = 0; id < WLAN_UMAC_MAX_COMPONENTS; id++) {
146 		handler = g_umac_glb_obj->psoc_create_handler[id];
147 		arg = g_umac_glb_obj->psoc_create_handler_arg[id];
148 		if (handler != NULL)
149 			psoc->obj_status[id] = handler(psoc, arg);
150 		else
151 			psoc->obj_status[id] = QDF_STATUS_COMP_DISABLED;
152 	}
153 	/* Derive object status */
154 	obj_status = wlan_objmgr_psoc_object_status(psoc);
155 
156 	if (obj_status == QDF_STATUS_SUCCESS) {
157 		/* Object status is SUCCESS, Object is created */
158 		psoc->obj_state = WLAN_OBJ_STATE_CREATED;
159 		for (id = 0; id < WLAN_UMAC_MAX_COMPONENTS; id++) {
160 			stat_handler = g_umac_glb_obj->psoc_status_handler[id];
161 			arg = g_umac_glb_obj->psoc_status_handler_arg[id];
162 			if (stat_handler != NULL)
163 				stat_handler(psoc, arg,
164 					     QDF_STATUS_SUCCESS);
165 		}
166 	} else if (obj_status == QDF_STATUS_COMP_ASYNC) {
167 		/*
168 		 * Few components operates in Asynchrous communction
169 		 * Object state partially created
170 		 */
171 		psoc->obj_state = WLAN_OBJ_STATE_PARTIALLY_CREATED;
172 	} else if (obj_status == QDF_STATUS_E_FAILURE) {
173 		/* Component object failed to be created, clean up the object */
174 		obj_mgr_err("PSOC component objects allocation failed");
175 		/* Clean up the psoc */
176 		wlan_objmgr_psoc_obj_delete(psoc);
177 		return NULL;
178 	}
179 
180 	if (wlan_objmgr_psoc_object_attach(psoc) !=
181 				QDF_STATUS_SUCCESS) {
182 		obj_mgr_err("PSOC object attach failed");
183 		wlan_objmgr_psoc_obj_delete(psoc);
184 		return NULL;
185 	}
186 
187 	obj_mgr_info("Created psoc %d", psoc->soc_objmgr.psoc_id);
188 
189 	return psoc;
190 }
191 qdf_export_symbol(wlan_objmgr_psoc_obj_create);
192 
193 static QDF_STATUS wlan_objmgr_psoc_obj_destroy(struct wlan_objmgr_psoc *psoc)
194 {
195 	uint8_t id;
196 	wlan_objmgr_psoc_destroy_handler handler;
197 	QDF_STATUS obj_status;
198 	void *arg;
199 
200 	if (psoc == NULL) {
201 		obj_mgr_err("psoc is NULL");
202 		return QDF_STATUS_E_FAILURE;
203 	}
204 	wlan_objmgr_notify_destroy(psoc, WLAN_PSOC_OP);
205 
206 	obj_mgr_info("Physically deleting psoc %d", psoc->soc_objmgr.psoc_id);
207 
208 	if (psoc->obj_state != WLAN_OBJ_STATE_LOGICALLY_DELETED) {
209 		obj_mgr_err("PSOC object delete is not invoked obj_state:%d",
210 			    psoc->obj_state);
211 		WLAN_OBJMGR_BUG(0);
212 	}
213 
214 	/* Invoke registered create handlers */
215 	for (id = 0; id < WLAN_UMAC_MAX_COMPONENTS; id++) {
216 		handler = g_umac_glb_obj->psoc_destroy_handler[id];
217 		arg = g_umac_glb_obj->psoc_destroy_handler_arg[id];
218 		if (handler &&
219 		    (psoc->obj_status[id] == QDF_STATUS_SUCCESS ||
220 		     psoc->obj_status[id] == QDF_STATUS_COMP_ASYNC))
221 			psoc->obj_status[id] = handler(psoc, arg);
222 		else
223 			psoc->obj_status[id] = QDF_STATUS_COMP_DISABLED;
224 	}
225 	/* Derive object status */
226 	obj_status = wlan_objmgr_psoc_object_status(psoc);
227 
228 	if (obj_status == QDF_STATUS_E_FAILURE) {
229 		obj_mgr_err("PSOC component object free failed");
230 		/* Ideally should not happen
231 		 * This leads to memleak, BUG_ON to find which component
232 		 * delete notification failed and fix it.
233 		 */
234 		QDF_BUG(0);
235 		return QDF_STATUS_E_FAILURE;
236 	}
237 	/* Deletion is in progress */
238 	if (obj_status == QDF_STATUS_COMP_ASYNC) {
239 		psoc->obj_state = WLAN_OBJ_STATE_PARTIALLY_DELETED;
240 		return QDF_STATUS_COMP_ASYNC;
241 	}
242 
243 	/* Free psoc object */
244 	return wlan_objmgr_psoc_obj_free(psoc);
245 }
246 
247 
248 QDF_STATUS wlan_objmgr_psoc_obj_delete(struct wlan_objmgr_psoc *psoc)
249 {
250 	uint8_t print_idx;
251 
252 	if (psoc == NULL) {
253 		obj_mgr_err("psoc is NULL");
254 		return QDF_STATUS_E_FAILURE;
255 	}
256 
257 	obj_mgr_info("Logically deleting psoc %d", psoc->soc_objmgr.psoc_id);
258 
259 	print_idx = qdf_get_pidx();
260 	wlan_objmgr_print_ref_ids(psoc->soc_objmgr.ref_id_dbg,
261 				  QDF_TRACE_LEVEL_DEBUG);
262 	/*
263 	 * Update PSOC object state to LOGICALLY DELETED
264 	 * It prevents further access of this object
265 	 */
266 	wlan_psoc_obj_lock(psoc);
267 	psoc->obj_state = WLAN_OBJ_STATE_LOGICALLY_DELETED;
268 	wlan_psoc_obj_unlock(psoc);
269 	wlan_objmgr_notify_log_delete(psoc, WLAN_PSOC_OP);
270 	wlan_objmgr_psoc_release_ref(psoc, WLAN_OBJMGR_ID);
271 
272 	return QDF_STATUS_SUCCESS;
273 }
274 qdf_export_symbol(wlan_objmgr_psoc_obj_delete);
275 
276 QDF_STATUS wlan_objmgr_psoc_component_obj_attach(
277 		struct wlan_objmgr_psoc *psoc,
278 		enum wlan_umac_comp_id id,
279 		void *comp_priv_obj,
280 		QDF_STATUS status)
281 {
282 	wlan_objmgr_psoc_status_handler stat_handler;
283 	void *arg = NULL;
284 	QDF_STATUS obj_status;
285 	uint8_t i;
286 
287 	/* component id is invalid */
288 	if (id >= WLAN_UMAC_MAX_COMPONENTS)
289 		return QDF_STATUS_MAXCOMP_FAIL;
290 
291 	wlan_psoc_obj_lock(psoc);
292 	/* If there is a valid entry, return failure */
293 	if (psoc->soc_comp_priv_obj[id] != NULL) {
294 		wlan_psoc_obj_unlock(psoc);
295 		return QDF_STATUS_E_FAILURE;
296 	}
297 	/* Save component's pointer and status */
298 	psoc->soc_comp_priv_obj[id] = comp_priv_obj;
299 	psoc->obj_status[id] = status;
300 
301 	wlan_psoc_obj_unlock(psoc);
302 
303 	if (psoc->obj_state != WLAN_OBJ_STATE_PARTIALLY_CREATED)
304 		return QDF_STATUS_SUCCESS;
305 	/* If PSOC object status is partially created means, this API is
306 	 * invoked with differnt context, this block should be executed for
307 	 * async components only
308 	 */
309 	/* Derive status */
310 	obj_status = wlan_objmgr_psoc_object_status(psoc);
311 	/* STATUS_SUCCESS means, object is CREATED */
312 	if (obj_status == QDF_STATUS_SUCCESS)
313 		psoc->obj_state = WLAN_OBJ_STATE_CREATED;
314 	/* update state as CREATION failed, caller has to delete the
315 	 * PSOC object
316 	 */
317 	else if (obj_status == QDF_STATUS_E_FAILURE)
318 		psoc->obj_state = WLAN_OBJ_STATE_CREATION_FAILED;
319 
320 	/* Notify components about the CREATION success/failure */
321 	if ((obj_status == QDF_STATUS_SUCCESS) ||
322 	    (obj_status == QDF_STATUS_E_FAILURE)) {
323 		/* nofity object status */
324 		for (i = 0; i < WLAN_UMAC_MAX_COMPONENTS; i++) {
325 			stat_handler = g_umac_glb_obj->psoc_status_handler[i];
326 			arg = g_umac_glb_obj->psoc_status_handler_arg[i];
327 			if (stat_handler != NULL)
328 				stat_handler(psoc, arg, obj_status);
329 		}
330 	}
331 
332 	return QDF_STATUS_SUCCESS;
333 }
334 qdf_export_symbol(wlan_objmgr_psoc_component_obj_attach);
335 
336 QDF_STATUS wlan_objmgr_psoc_component_obj_detach(
337 		struct wlan_objmgr_psoc *psoc,
338 		enum wlan_umac_comp_id id,
339 		void *comp_priv_obj)
340 {
341 	QDF_STATUS obj_status;
342 
343 	/* component id is invalid */
344 	if (id >= WLAN_UMAC_MAX_COMPONENTS)
345 		return QDF_STATUS_MAXCOMP_FAIL;
346 
347 	wlan_psoc_obj_lock(psoc);
348 	/* If there is a valid entry, return failure */
349 	if (psoc->soc_comp_priv_obj[id] != comp_priv_obj) {
350 		psoc->obj_status[id] = QDF_STATUS_E_FAILURE;
351 		wlan_psoc_obj_unlock(psoc);
352 		return QDF_STATUS_E_FAILURE;
353 	}
354 	/* Reset pointers to NULL, update the status*/
355 	psoc->soc_comp_priv_obj[id] = NULL;
356 	psoc->obj_status[id] = QDF_STATUS_SUCCESS;
357 	wlan_psoc_obj_unlock(psoc);
358 
359 	/* If PSOC object status is partially created means, this API is
360 	 * invoked with differnt context, this block should be executed for
361 	 * async components only
362 	 */
363 	if ((psoc->obj_state == WLAN_OBJ_STATE_PARTIALLY_DELETED) ||
364 	    (psoc->obj_state == WLAN_OBJ_STATE_COMP_DEL_PROGRESS)) {
365 		/* Derive object status */
366 		obj_status = wlan_objmgr_psoc_object_status(psoc);
367 		if (obj_status == QDF_STATUS_SUCCESS) {
368 			/* Update the status as Deleted, if full object
369 			 * deletion is in progress
370 			 */
371 			if (psoc->obj_state == WLAN_OBJ_STATE_PARTIALLY_DELETED)
372 				psoc->obj_state = WLAN_OBJ_STATE_DELETED;
373 
374 			/* Move to creation state, since this component
375 			 * deletion alone requested
376 			 */
377 			if (psoc->obj_state == WLAN_OBJ_STATE_COMP_DEL_PROGRESS)
378 				psoc->obj_state = WLAN_OBJ_STATE_CREATED;
379 		/* Object status is failure */
380 		} else if (obj_status == QDF_STATUS_E_FAILURE) {
381 			/* Update the status as Deletion failed, if full object
382 			 * deletion is in progress
383 			 */
384 			if (psoc->obj_state == WLAN_OBJ_STATE_PARTIALLY_DELETED)
385 				psoc->obj_state =
386 					WLAN_OBJ_STATE_DELETION_FAILED;
387 
388 			/* Move to creation state, since this component
389 			 * deletion alone requested (do not block other
390 			 * components)
391 			 */
392 			if (psoc->obj_state == WLAN_OBJ_STATE_COMP_DEL_PROGRESS)
393 				psoc->obj_state = WLAN_OBJ_STATE_CREATED;
394 		}
395 
396 		/* Delete psoc object */
397 		if ((obj_status == QDF_STATUS_SUCCESS)  &&
398 		    (psoc->obj_state == WLAN_OBJ_STATE_DELETED)) {
399 			/* Free psoc object */
400 			return wlan_objmgr_psoc_obj_free(psoc);
401 		}
402 	}
403 
404 	return QDF_STATUS_SUCCESS;
405 }
406 qdf_export_symbol(wlan_objmgr_psoc_component_obj_detach);
407 
408 QDF_STATUS wlan_objmgr_iterate_obj_list(
409 		struct wlan_objmgr_psoc *psoc,
410 		enum wlan_objmgr_obj_type obj_type,
411 		wlan_objmgr_op_handler handler,
412 		void *arg, uint8_t lock_free_op,
413 		wlan_objmgr_ref_dbgid dbg_id)
414 {
415 	uint16_t obj_id;
416 	uint8_t i;
417 	struct wlan_objmgr_psoc_objmgr *objmgr = &psoc->soc_objmgr;
418 	struct wlan_peer_list *peer_list;
419 	struct wlan_objmgr_pdev *pdev;
420 	struct wlan_objmgr_vdev *vdev;
421 	struct wlan_objmgr_peer *peer;
422 	struct wlan_objmgr_peer *peer_next;
423 	uint16_t max_vdev_cnt;
424 
425 	switch (obj_type) {
426 	case WLAN_PDEV_OP:
427 		/* Iterate through PDEV list, invoke handler for each pdev */
428 		for (obj_id = 0; obj_id < WLAN_UMAC_MAX_PDEVS; obj_id++) {
429 			pdev = wlan_objmgr_get_pdev_by_id(psoc, obj_id, dbg_id);
430 			if (pdev != NULL) {
431 				handler(psoc, (void *)pdev, arg);
432 				wlan_objmgr_pdev_release_ref(pdev, dbg_id);
433 			}
434 		}
435 		break;
436 	case WLAN_VDEV_OP:
437 		/* Iterate through VDEV list, invoke handler for each vdev */
438 		max_vdev_cnt = wlan_psoc_get_max_vdev_count(psoc);
439 		for (obj_id = 0; obj_id < max_vdev_cnt; obj_id++) {
440 			vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc,
441 						obj_id, dbg_id);
442 			if (vdev != NULL) {
443 				handler(psoc, vdev, arg);
444 				wlan_objmgr_vdev_release_ref(vdev, dbg_id);
445 			}
446 		}
447 		break;
448 	case WLAN_PEER_OP:
449 		/* Iterate through PEER list, invoke handler for each peer */
450 		peer_list = &objmgr->peer_list;
451 		/* Since peer list has sublist, iterate through sublists */
452 		for (i = 0; i < WLAN_PEER_HASHSIZE; i++) {
453 			peer = wlan_psoc_peer_list_peek_active_head(peer_list,
454 					i, dbg_id);
455 			while (peer) {
456 				handler(psoc, (void *)peer, arg);
457 				/* Get next peer */
458 				peer_next =
459 					wlan_peer_get_next_active_peer_of_psoc(
460 						peer_list, i, peer, dbg_id);
461 				wlan_objmgr_peer_release_ref(peer,  dbg_id);
462 				peer = peer_next;
463 			}
464 		}
465 		break;
466 	default:
467 		break;
468 	}
469 
470 	return QDF_STATUS_SUCCESS;
471 }
472 qdf_export_symbol(wlan_objmgr_iterate_obj_list);
473 
474 QDF_STATUS wlan_objmgr_iterate_obj_list_all(
475 		struct wlan_objmgr_psoc *psoc,
476 		enum wlan_objmgr_obj_type obj_type,
477 		wlan_objmgr_op_handler handler,
478 		void *arg, uint8_t lock_free_op,
479 		wlan_objmgr_ref_dbgid dbg_id)
480 {
481 	uint16_t obj_id;
482 	uint8_t i;
483 	struct wlan_objmgr_psoc_objmgr *objmgr = &psoc->soc_objmgr;
484 	struct wlan_peer_list *peer_list;
485 	struct wlan_objmgr_pdev *pdev;
486 	struct wlan_objmgr_vdev *vdev;
487 	struct wlan_objmgr_peer *peer;
488 	struct wlan_objmgr_peer *peer_next;
489 	uint16_t max_vdev_cnt;
490 
491 	/* If caller requests for lock free opeation, do not acquire,
492 	 * handler will handle the synchronization
493 	 */
494 
495 	switch (obj_type) {
496 	case WLAN_PDEV_OP:
497 		/* Iterate through PDEV list, invoke handler for each pdev */
498 		for (obj_id = 0; obj_id < WLAN_UMAC_MAX_PDEVS; obj_id++) {
499 			pdev = wlan_objmgr_get_pdev_by_id_no_state(psoc,
500 							obj_id, dbg_id);
501 			if (pdev != NULL) {
502 				handler(psoc, (void *)pdev, arg);
503 				wlan_objmgr_pdev_release_ref(pdev, dbg_id);
504 			}
505 		}
506 		break;
507 	case WLAN_VDEV_OP:
508 		/* Iterate through VDEV list, invoke handler for each vdev */
509 		max_vdev_cnt = wlan_psoc_get_max_vdev_count(psoc);
510 		for (obj_id = 0; obj_id < max_vdev_cnt; obj_id++) {
511 			vdev = wlan_objmgr_get_vdev_by_id_from_psoc_no_state(
512 					psoc, obj_id, dbg_id);
513 			if (vdev != NULL) {
514 				handler(psoc, vdev, arg);
515 				wlan_objmgr_vdev_release_ref(vdev, dbg_id);
516 			}
517 		}
518 		break;
519 	case WLAN_PEER_OP:
520 		/* Iterate through PEER list, invoke handler for each peer */
521 		peer_list = &objmgr->peer_list;
522 		/* Since peer list has sublist, iterate through sublists */
523 		for (i = 0; i < WLAN_PEER_HASHSIZE; i++) {
524 			peer = wlan_psoc_peer_list_peek_head_ref(peer_list, i,
525 									dbg_id);
526 
527 			while (peer) {
528 				handler(psoc, (void *)peer, arg);
529 				/* Get next peer */
530 				peer_next = wlan_peer_get_next_peer_of_psoc_ref(
531 								peer_list, i,
532 								peer, dbg_id);
533 				wlan_objmgr_peer_release_ref(peer, dbg_id);
534 				peer = peer_next;
535 			}
536 		}
537 		break;
538 	default:
539 		break;
540 	}
541 
542 	return QDF_STATUS_SUCCESS;
543 }
544 qdf_export_symbol(wlan_objmgr_iterate_obj_list_all);
545 
546 /**
547  * wlan_objmgr_iterate_obj_list_all_noref() - iterate through all psoc objects
548  *                                            without taking ref
549  * @psoc: PSOC object
550  * @obj_type: PDEV_OP/VDEV_OP/PEER_OP
551  * @handler: the handler will be called for each object of requested type
552  *            the handler should be implemented to perform required operation
553  * @arg:     agruments passed by caller
554  *
555  * API to be used for performing the operations on all PDEV/VDEV/PEER objects
556  * of psoc with lock protected
557  *
558  * Return: SUCCESS/FAILURE
559  */
560 static QDF_STATUS wlan_objmgr_iterate_obj_list_all_noref(
561 		struct wlan_objmgr_psoc *psoc,
562 		enum wlan_objmgr_obj_type obj_type,
563 		wlan_objmgr_op_handler handler,
564 		void *arg)
565 {
566 	uint16_t obj_id;
567 	uint8_t i;
568 	struct wlan_objmgr_psoc_objmgr *objmgr = &psoc->soc_objmgr;
569 	struct wlan_peer_list *peer_list;
570 	qdf_list_t *obj_list;
571 	struct wlan_objmgr_pdev *pdev;
572 	struct wlan_objmgr_vdev *vdev;
573 	struct wlan_objmgr_peer *peer;
574 	struct wlan_objmgr_peer *peer_next;
575 	uint16_t max_vdev_cnt;
576 
577 	/* If caller requests for lock free opeation, do not acquire,
578 	 * handler will handle the synchronization
579 	 */
580 	wlan_psoc_obj_lock(psoc);
581 
582 	switch (obj_type) {
583 	case WLAN_PDEV_OP:
584 		/* Iterate through PDEV list, invoke handler for each pdev */
585 		for (obj_id = 0; obj_id < WLAN_UMAC_MAX_PDEVS; obj_id++) {
586 			pdev = objmgr->wlan_pdev_list[obj_id];
587 			if (pdev != NULL)
588 				handler(psoc, (void *)pdev, arg);
589 		}
590 		break;
591 	case WLAN_VDEV_OP:
592 		/* Iterate through VDEV list, invoke handler for each vdev */
593 		max_vdev_cnt = wlan_psoc_get_max_vdev_count(psoc);
594 		for (obj_id = 0; obj_id < max_vdev_cnt; obj_id++) {
595 			vdev = objmgr->wlan_vdev_list[obj_id];
596 			if (vdev != NULL)
597 				handler(psoc, vdev, arg);
598 		}
599 		break;
600 	case WLAN_PEER_OP:
601 		/* Iterate through PEER list, invoke handler for each peer */
602 		peer_list = &objmgr->peer_list;
603 		/* psoc lock should be taken before list lock */
604 		qdf_spin_lock_bh(&peer_list->peer_list_lock);
605 		/* Since peer list has sublist, iterate through sublists */
606 		for (i = 0; i < WLAN_PEER_HASHSIZE; i++) {
607 			obj_list = &peer_list->peer_hash[i];
608 			peer = wlan_psoc_peer_list_peek_head(obj_list);
609 			while (peer) {
610 				/* Get next peer */
611 				peer_next = wlan_peer_get_next_peer_of_psoc(
612 								obj_list, peer);
613 				handler(psoc, (void *)peer, arg);
614 				peer = peer_next;
615 			}
616 		}
617 		qdf_spin_unlock_bh(&peer_list->peer_list_lock);
618 		break;
619 	default:
620 		break;
621 	}
622 	wlan_psoc_obj_unlock(psoc);
623 
624 	return QDF_STATUS_SUCCESS;
625 }
626 
627 static void wlan_objmgr_psoc_peer_delete(struct wlan_objmgr_psoc *psoc,
628 					 void *obj, void *args)
629 {
630 	struct wlan_objmgr_peer *peer = (struct wlan_objmgr_peer *)obj;
631 
632 	wlan_objmgr_peer_obj_delete(peer);
633 }
634 
635 static void wlan_objmgr_psoc_vdev_delete(struct wlan_objmgr_psoc *psoc,
636 					 void *obj, void *args)
637 {
638 	struct wlan_objmgr_vdev *vdev = (struct wlan_objmgr_vdev *)obj;
639 
640 	wlan_objmgr_vdev_obj_delete(vdev);
641 }
642 
643 static void wlan_objmgr_psoc_pdev_delete(struct wlan_objmgr_psoc *psoc,
644 					 void *obj, void *args)
645 {
646 	struct wlan_objmgr_pdev *pdev = (struct wlan_objmgr_pdev *)obj;
647 
648 	wlan_objmgr_pdev_obj_delete(pdev);
649 }
650 
651 QDF_STATUS wlan_objmgr_free_all_objects_per_psoc(
652 		struct wlan_objmgr_psoc *psoc)
653 {
654 	/* Free all peers */
655 	wlan_objmgr_iterate_obj_list(psoc, WLAN_PEER_OP,
656 				     wlan_objmgr_psoc_peer_delete, NULL, 1,
657 				     WLAN_OBJMGR_ID);
658 	/* Free all vdevs */
659 	wlan_objmgr_iterate_obj_list(psoc, WLAN_VDEV_OP,
660 				     wlan_objmgr_psoc_vdev_delete, NULL, 1,
661 				     WLAN_OBJMGR_ID);
662 	/* Free all PDEVs */
663 	wlan_objmgr_iterate_obj_list(psoc, WLAN_PDEV_OP,
664 				     wlan_objmgr_psoc_pdev_delete, NULL, 1,
665 				     WLAN_OBJMGR_ID);
666 
667 	return QDF_STATUS_SUCCESS;
668 }
669 
670 QDF_STATUS wlan_objmgr_trigger_psoc_comp_priv_object_creation(
671 		struct wlan_objmgr_psoc *psoc,
672 		enum wlan_umac_comp_id id)
673 {
674 	wlan_objmgr_psoc_create_handler handler;
675 	void *arg;
676 	QDF_STATUS obj_status = QDF_STATUS_SUCCESS;
677 
678 	/* Component id is invalid */
679 	if (id >= WLAN_UMAC_MAX_COMPONENTS)
680 		return QDF_STATUS_MAXCOMP_FAIL;
681 
682 	wlan_psoc_obj_lock(psoc);
683 	/* If component object is already created, delete old
684 	 * component object, then invoke creation
685 	 */
686 	if (psoc->soc_comp_priv_obj[id] != NULL) {
687 		wlan_psoc_obj_unlock(psoc);
688 		return QDF_STATUS_E_FAILURE;
689 	}
690 	wlan_psoc_obj_unlock(psoc);
691 	/* Invoke registered create handlers */
692 	handler = g_umac_glb_obj->psoc_create_handler[id];
693 	arg = g_umac_glb_obj->psoc_create_handler_arg[id];
694 	if (handler != NULL)
695 		psoc->obj_status[id] = handler(psoc, arg);
696 	else
697 		return QDF_STATUS_E_FAILURE;
698 
699 	/* If object status is created, then only handle this object status */
700 	if (psoc->obj_state == WLAN_OBJ_STATE_CREATED) {
701 		/* Derive object status */
702 		obj_status = wlan_objmgr_psoc_object_status(psoc);
703 		/* Move PSOC object state to Partially created state */
704 		if (obj_status == QDF_STATUS_COMP_ASYNC) {
705 			/*TODO atomic */
706 			psoc->obj_state = WLAN_OBJ_STATE_PARTIALLY_CREATED;
707 		}
708 	}
709 
710 	return obj_status;
711 }
712 
713 QDF_STATUS wlan_objmgr_trigger_psoc_comp_priv_object_deletion(
714 		struct wlan_objmgr_psoc *psoc,
715 		enum wlan_umac_comp_id id)
716 {
717 	wlan_objmgr_psoc_destroy_handler handler;
718 	void *arg;
719 	QDF_STATUS obj_status = QDF_STATUS_SUCCESS;
720 
721 	/* component id is invalid */
722 	if (id >= WLAN_UMAC_MAX_COMPONENTS)
723 		return QDF_STATUS_MAXCOMP_FAIL;
724 
725 	wlan_psoc_obj_lock(psoc);
726 	/* Component object was never created, invalid operation */
727 	if (psoc->soc_comp_priv_obj[id] == NULL) {
728 		wlan_psoc_obj_unlock(psoc);
729 		return QDF_STATUS_E_FAILURE;
730 	}
731 	wlan_psoc_obj_unlock(psoc);
732 	/* Invoke registered create handlers */
733 	handler = g_umac_glb_obj->psoc_destroy_handler[id];
734 	arg = g_umac_glb_obj->psoc_destroy_handler_arg[id];
735 	if (handler != NULL)
736 		psoc->obj_status[id] = handler(psoc, arg);
737 	else
738 		return QDF_STATUS_E_FAILURE;
739 
740 	/* If object status is created, then only handle this object status */
741 	if (psoc->obj_state == WLAN_OBJ_STATE_CREATED) {
742 		obj_status = wlan_objmgr_psoc_object_status(psoc);
743 			/* move object state to DEL progress */
744 		if (obj_status == QDF_STATUS_COMP_ASYNC)
745 			psoc->obj_state = WLAN_OBJ_STATE_COMP_DEL_PROGRESS;
746 	}
747 
748 	return obj_status;
749 }
750 
751 /* Util APIs */
752 
753 QDF_STATUS wlan_objmgr_psoc_pdev_attach(struct wlan_objmgr_psoc *psoc,
754 					struct wlan_objmgr_pdev *pdev)
755 {
756 	struct wlan_objmgr_psoc_objmgr *objmgr;
757 	uint8_t id = 0;
758 	QDF_STATUS status;
759 
760 	wlan_psoc_obj_lock(psoc);
761 	objmgr = &psoc->soc_objmgr;
762 	/*
763 	 * Derive pdev id from pdev map
764 	 * First free pdev id is assigned
765 	 */
766 	while ((id < WLAN_UMAC_MAX_PDEVS) &&
767 			(objmgr->wlan_pdev_id_map & (1<<id)))
768 		id++;
769 
770 	if (id == WLAN_UMAC_MAX_PDEVS) {
771 		status = QDF_STATUS_E_FAILURE;
772 	} else {
773 		/* Update the map for reserving the id */
774 		objmgr->wlan_pdev_id_map |= (1<<id);
775 		/* store pdev in pdev list */
776 		objmgr->wlan_pdev_list[id] = pdev;
777 		/* Increment pdev count */
778 		objmgr->wlan_pdev_count++;
779 		/* save pdev id */
780 		pdev->pdev_objmgr.wlan_pdev_id = id;
781 		status = QDF_STATUS_SUCCESS;
782 		/* Inrement psoc ref count to block its free before pdev */
783 		wlan_objmgr_psoc_get_ref(psoc, WLAN_OBJMGR_ID);
784 	}
785 	wlan_psoc_obj_unlock(psoc);
786 
787 	return status;
788 }
789 
790 QDF_STATUS wlan_objmgr_psoc_pdev_detach(struct wlan_objmgr_psoc *psoc,
791 						struct wlan_objmgr_pdev *pdev)
792 {
793 	struct wlan_objmgr_psoc_objmgr *objmgr;
794 	uint8_t id;
795 
796 	id = pdev->pdev_objmgr.wlan_pdev_id;
797 	/* If id is invalid, return */
798 	if (id >= WLAN_UMAC_MAX_PDEVS)
799 		return QDF_STATUS_E_FAILURE;
800 
801 	wlan_psoc_obj_lock(psoc);
802 	objmgr = &psoc->soc_objmgr;
803 	/* Free pdev id slot */
804 	objmgr->wlan_pdev_id_map &= ~(1<<id);
805 	objmgr->wlan_pdev_list[id] = NULL;
806 	objmgr->wlan_pdev_count--;
807 	pdev->pdev_objmgr.wlan_pdev_id = 0xff;
808 	wlan_psoc_obj_unlock(psoc);
809 	/* Release ref count of psoc */
810 	wlan_objmgr_psoc_release_ref(psoc, WLAN_OBJMGR_ID);
811 
812 	return QDF_STATUS_SUCCESS;
813 }
814 
815 struct wlan_objmgr_pdev *wlan_objmgr_get_pdev_by_id(
816 		struct wlan_objmgr_psoc *psoc, uint8_t id,
817 		wlan_objmgr_ref_dbgid dbg_id)
818 {
819 	struct wlan_objmgr_psoc_objmgr *objmgr;
820 	struct wlan_objmgr_pdev *pdev = NULL;
821 
822 	/* If id is invalid, return */
823 	if (id >= WLAN_UMAC_MAX_PDEVS)
824 		return NULL;
825 
826 	wlan_psoc_obj_lock(psoc);
827 	objmgr = &psoc->soc_objmgr;
828 	/* get pdev from pdev list */
829 	pdev = objmgr->wlan_pdev_list[id];
830 	/* Do not return object, if it is not CREATED state */
831 	if (pdev != NULL) {
832 		if (wlan_objmgr_pdev_try_get_ref(pdev, dbg_id) !=
833 							QDF_STATUS_SUCCESS)
834 			pdev = NULL;
835 	}
836 
837 	wlan_psoc_obj_unlock(psoc);
838 
839 	return pdev;
840 }
841 qdf_export_symbol(wlan_objmgr_get_pdev_by_id);
842 
843 struct wlan_objmgr_pdev *wlan_objmgr_get_pdev_by_id_no_state(
844 		struct wlan_objmgr_psoc *psoc, uint8_t id,
845 		wlan_objmgr_ref_dbgid dbg_id)
846 {
847 	struct wlan_objmgr_psoc_objmgr *objmgr;
848 	struct wlan_objmgr_pdev *pdev = NULL;
849 
850 	/* If id is invalid, return */
851 	if (id >= WLAN_UMAC_MAX_PDEVS)
852 		return NULL;
853 
854 	wlan_psoc_obj_lock(psoc);
855 	objmgr = &psoc->soc_objmgr;
856 	/* get pdev from pdev list */
857 	pdev = objmgr->wlan_pdev_list[id];
858 	/* Do not return object, if it is not CREATED state */
859 	if (pdev != NULL)
860 		wlan_objmgr_pdev_get_ref(pdev, dbg_id);
861 
862 	wlan_psoc_obj_unlock(psoc);
863 
864 	return pdev;
865 }
866 QDF_STATUS wlan_objmgr_psoc_vdev_attach(struct wlan_objmgr_psoc *psoc,
867 					struct wlan_objmgr_vdev *vdev)
868 {
869 	struct wlan_objmgr_psoc_objmgr *objmgr;
870 	uint8_t id = 0;
871 	uint8_t map_index = 0;
872 	uint8_t map_entry_size = 32;
873 	uint8_t adjust_ix = 0;
874 	QDF_STATUS status;
875 
876 	wlan_psoc_obj_lock(psoc);
877 	objmgr = &psoc->soc_objmgr;
878 	/* Find first free vdev id */
879 	while ((id < objmgr->max_vdev_count) &&
880 		(objmgr->wlan_vdev_id_map[map_index] & (1<<(id - adjust_ix)))) {
881 		id++;
882 		/*
883 		 * The map is two DWORDS(32 bits), so, map_index
884 		 * adjust_ix derived based on the id value
885 		 */
886 		if (id == ((map_index + 1) * map_entry_size)) {
887 			map_index++;
888 			adjust_ix = map_index * map_entry_size;
889 		}
890 	}
891 	/* If no free slot, return failure */
892 	if (id == objmgr->max_vdev_count) {
893 		status = QDF_STATUS_E_FAILURE;
894 	} else {
895 		/* set free vdev id index */
896 		objmgr->wlan_vdev_id_map[map_index] |= (1<<(id-adjust_ix));
897 		/* store vdev pointer in vdev list */
898 		objmgr->wlan_vdev_list[id] = vdev;
899 		/* increment vdev counter */
900 		objmgr->wlan_vdev_count++;
901 		/* save vdev id */
902 		vdev->vdev_objmgr.vdev_id = id;
903 		status = QDF_STATUS_SUCCESS;
904 	}
905 	wlan_psoc_obj_unlock(psoc);
906 
907 	return status;
908 }
909 
910 QDF_STATUS wlan_objmgr_psoc_vdev_detach(struct wlan_objmgr_psoc *psoc,
911 					struct wlan_objmgr_vdev *vdev)
912 {
913 	struct wlan_objmgr_psoc_objmgr *objmgr;
914 	uint8_t id = 0;
915 	uint8_t map_index = 0;
916 	uint8_t map_entry_size = 32;
917 	uint8_t adjust_ix = 0;
918 
919 	id = vdev->vdev_objmgr.vdev_id;
920 	/* Invalid vdev id */
921 	if (id >= wlan_psoc_get_max_vdev_count(psoc))
922 		return QDF_STATUS_E_FAILURE;
923 	/*
924 	 * Derive map_index and adjust_ix to find actual DWORD
925 	 * the id map is present
926 	 */
927 	while ((id - adjust_ix) >= map_entry_size) {
928 		map_index++;
929 		adjust_ix = map_index * map_entry_size;
930 	}
931 	wlan_psoc_obj_lock(psoc);
932 	objmgr = &psoc->soc_objmgr;
933 	/* unset bit, to free the slot */
934 	objmgr->wlan_vdev_id_map[map_index] &= ~(1<<(id-adjust_ix));
935 	/* reset VDEV pointer to NULL in VDEV list array */
936 	objmgr->wlan_vdev_list[id] = NULL;
937 	/* decrement vdev count */
938 	objmgr->wlan_vdev_count--;
939 	vdev->vdev_objmgr.vdev_id = 0xff;
940 	wlan_psoc_obj_unlock(psoc);
941 
942 	return QDF_STATUS_SUCCESS;
943 }
944 
945 struct wlan_objmgr_vdev *wlan_objmgr_get_vdev_by_opmode_from_psoc(
946 			struct wlan_objmgr_psoc *psoc,
947 			enum QDF_OPMODE opmode,
948 			wlan_objmgr_ref_dbgid dbg_id)
949 {
950 	struct wlan_objmgr_vdev *vdev = NULL;
951 	int vdev_cnt = 0;
952 	uint16_t max_vdev_cnt;
953 
954 	/* if PSOC is NULL, return */
955 	if (psoc == NULL)
956 		return NULL;
957 
958 	wlan_psoc_obj_lock(psoc);
959 
960 	max_vdev_cnt = wlan_psoc_get_max_vdev_count(psoc);
961 	/* retrieve vdev pointer from vdev list */
962 	while (vdev_cnt < max_vdev_cnt) {
963 		vdev = psoc->soc_objmgr.wlan_vdev_list[vdev_cnt];
964 		vdev_cnt++;
965 		if (vdev == NULL)
966 			continue;
967 		wlan_vdev_obj_lock(vdev);
968 		if (vdev->vdev_mlme.vdev_opmode == opmode) {
969 			wlan_vdev_obj_unlock(vdev);
970 			if (wlan_objmgr_vdev_try_get_ref(vdev, dbg_id) !=
971 							QDF_STATUS_SUCCESS) {
972 				vdev = NULL;
973 				continue;
974 			}
975 			break;
976 		}
977 		wlan_vdev_obj_unlock(vdev);
978 	}
979 	wlan_psoc_obj_unlock(psoc);
980 
981 	return vdev;
982 }
983 
984 struct wlan_objmgr_vdev *wlan_objmgr_get_vdev_by_id_from_psoc(
985 			struct wlan_objmgr_psoc *psoc, uint8_t vdev_id,
986 			wlan_objmgr_ref_dbgid dbg_id)
987 {
988 	struct wlan_objmgr_vdev *vdev;
989 
990 	/* if PSOC is NULL, return */
991 	if (psoc == NULL)
992 		return NULL;
993 	/* vdev id is invalid */
994 	if (vdev_id >= wlan_psoc_get_max_vdev_count(psoc))
995 		return NULL;
996 
997 	wlan_psoc_obj_lock(psoc);
998 	/* retrieve vdev pointer from vdev list */
999 	vdev = psoc->soc_objmgr.wlan_vdev_list[vdev_id];
1000 	if (vdev != NULL) {
1001 		if (wlan_objmgr_vdev_try_get_ref(vdev, dbg_id) !=
1002 							QDF_STATUS_SUCCESS)
1003 			vdev = NULL;
1004 	}
1005 	wlan_psoc_obj_unlock(psoc);
1006 
1007 	return vdev;
1008 }
1009 qdf_export_symbol(wlan_objmgr_get_vdev_by_id_from_psoc);
1010 
1011 struct wlan_objmgr_vdev *wlan_objmgr_get_vdev_by_id_from_psoc_no_state(
1012 			struct wlan_objmgr_psoc *psoc, uint8_t vdev_id,
1013 			wlan_objmgr_ref_dbgid dbg_id)
1014 {
1015 	struct wlan_objmgr_vdev *vdev;
1016 
1017 	/* if PSOC is NULL, return */
1018 	if (psoc == NULL)
1019 		return NULL;
1020 	/* vdev id is invalid */
1021 	if (vdev_id >= wlan_psoc_get_max_vdev_count(psoc))
1022 		return NULL;
1023 
1024 	wlan_psoc_obj_lock(psoc);
1025 	/* retrieve vdev pointer from vdev list */
1026 	vdev = psoc->soc_objmgr.wlan_vdev_list[vdev_id];
1027 	if (vdev != NULL)
1028 		wlan_objmgr_vdev_get_ref(vdev, dbg_id);
1029 
1030 	wlan_psoc_obj_unlock(psoc);
1031 
1032 	return vdev;
1033 }
1034 qdf_export_symbol(wlan_objmgr_get_vdev_by_id_from_psoc_no_state);
1035 
1036 struct wlan_objmgr_vdev *wlan_objmgr_get_vdev_by_macaddr_from_psoc(
1037 		struct wlan_objmgr_psoc *psoc, uint8_t pdev_id,
1038 		uint8_t *macaddr, wlan_objmgr_ref_dbgid dbg_id)
1039 {
1040 	struct wlan_objmgr_vdev *vdev;
1041 	struct wlan_objmgr_pdev *pdev;
1042 
1043 	/* if PSOC is NULL, return */
1044 	if (psoc == NULL)
1045 		return NULL;
1046 
1047 	if (!macaddr)
1048 		return NULL;
1049 
1050 	pdev = wlan_objmgr_get_pdev_by_id(psoc, pdev_id, dbg_id);
1051 	if (!pdev) {
1052 		obj_mgr_err("pdev is null");
1053 		return NULL;
1054 	}
1055 	vdev = wlan_objmgr_get_vdev_by_macaddr_from_pdev(pdev, macaddr, dbg_id);
1056 	wlan_objmgr_pdev_release_ref(pdev, dbg_id);
1057 
1058 	return vdev;
1059 }
1060 qdf_export_symbol(wlan_objmgr_get_vdev_by_macaddr_from_psoc);
1061 
1062 struct wlan_objmgr_vdev *wlan_objmgr_get_vdev_by_macaddr_from_psoc_no_state(
1063 		struct wlan_objmgr_psoc *psoc, uint8_t pdev_id,
1064 		uint8_t *macaddr, wlan_objmgr_ref_dbgid dbg_id)
1065 {
1066 	struct wlan_objmgr_vdev *vdev;
1067 	struct wlan_objmgr_pdev *pdev;
1068 
1069 	/* if PSOC is NULL, return */
1070 	if (psoc == NULL)
1071 		return NULL;
1072 
1073 	if (!macaddr)
1074 		return NULL;
1075 
1076 	pdev = wlan_objmgr_get_pdev_by_id(psoc, pdev_id, dbg_id);
1077 	if (!pdev) {
1078 		obj_mgr_err("pdev is null");
1079 		return NULL;
1080 	}
1081 	vdev = wlan_objmgr_get_vdev_by_macaddr_from_pdev_no_state(pdev, macaddr, dbg_id);
1082 	wlan_objmgr_pdev_release_ref(pdev, dbg_id);
1083 
1084 	return vdev;
1085 }
1086 qdf_export_symbol(wlan_objmgr_get_vdev_by_macaddr_from_psoc_no_state);
1087 
1088 static void wlan_obj_psoc_peerlist_add_tail(qdf_list_t *obj_list,
1089 				struct wlan_objmgr_peer *obj)
1090 {
1091 	qdf_list_insert_back(obj_list, &obj->psoc_peer);
1092 }
1093 
1094 static QDF_STATUS wlan_obj_psoc_peerlist_remove_peer(
1095 				qdf_list_t *obj_list,
1096 				struct wlan_objmgr_peer *peer)
1097 {
1098 	qdf_list_node_t *psoc_node = NULL;
1099 
1100 	if (peer == NULL)
1101 		return QDF_STATUS_E_FAILURE;
1102 	/* get vdev list node element */
1103 	psoc_node = &peer->psoc_peer;
1104 	/* list is empty, return failure */
1105 	if (qdf_list_remove_node(obj_list, psoc_node) != QDF_STATUS_SUCCESS)
1106 		return QDF_STATUS_E_FAILURE;
1107 
1108 	return QDF_STATUS_SUCCESS;
1109 }
1110 
1111 static QDF_STATUS wlan_peer_bssid_match(struct wlan_objmgr_peer *peer,
1112 				     uint8_t *bssid)
1113 {
1114 	struct wlan_objmgr_vdev *vdev = wlan_peer_get_vdev(peer);
1115 	uint8_t *peer_bssid = wlan_vdev_mlme_get_macaddr(vdev);
1116 
1117 	if (WLAN_ADDR_EQ(peer_bssid, bssid) == QDF_STATUS_SUCCESS)
1118 		return QDF_STATUS_SUCCESS;
1119 	else
1120 		return QDF_STATUS_E_FAILURE;
1121 }
1122 
1123 /**
1124  * wlan_obj_psoc_peerlist_get_peer_logically_deleted() - get peer
1125  * from psoc peer list
1126  * @psoc: PSOC object
1127  * @macaddr: MAC address
1128  *
1129  * API to finds peer object pointer of logically deleted peer
1130  *
1131  * Return: peer pointer
1132  *         NULL on FAILURE
1133  */
1134 static struct wlan_objmgr_peer *
1135 			wlan_obj_psoc_peerlist_get_peer_logically_deleted(
1136 				qdf_list_t *obj_list, uint8_t *macaddr,
1137 				wlan_objmgr_ref_dbgid dbg_id)
1138 {
1139 	struct wlan_objmgr_peer *peer;
1140 	struct wlan_objmgr_peer *peer_temp;
1141 
1142 	/* Iterate through hash list to get the peer */
1143 	peer = wlan_psoc_peer_list_peek_head(obj_list);
1144 	while (peer != NULL) {
1145 		/* For peer, macaddr is key */
1146 		if (WLAN_ADDR_EQ(wlan_peer_get_macaddr(peer), macaddr)
1147 			== QDF_STATUS_SUCCESS) {
1148 			/* Return peer in logically deleted state */
1149 			if (peer->obj_state ==
1150 					WLAN_OBJ_STATE_LOGICALLY_DELETED) {
1151 				wlan_objmgr_peer_get_ref(peer, dbg_id);
1152 
1153 				return peer;
1154 			}
1155 
1156 		}
1157 		/* Move to next peer */
1158 		peer_temp = peer;
1159 		peer = wlan_peer_get_next_peer_of_psoc(obj_list, peer_temp);
1160 	}
1161 
1162 	/* Not found, return NULL */
1163 	return NULL;
1164 }
1165 
1166 /**
1167  * wlan_obj_psoc_peerlist_get_peer() - get peer from psoc peer list
1168  * @psoc: PSOC object
1169  * @macaddr: MAC address
1170  *
1171  * API to finds peer object pointer by MAC addr from hash list
1172  *
1173  * Return: peer pointer
1174  *         NULL on FAILURE
1175  */
1176 static struct wlan_objmgr_peer *wlan_obj_psoc_peerlist_get_peer(
1177 		qdf_list_t *obj_list, uint8_t *macaddr,
1178 		wlan_objmgr_ref_dbgid dbg_id)
1179 {
1180 	struct wlan_objmgr_peer *peer;
1181 	struct wlan_objmgr_peer *peer_temp;
1182 
1183 	/* Iterate through hash list to get the peer */
1184 	peer = wlan_psoc_peer_list_peek_head(obj_list);
1185 	while (peer != NULL) {
1186 		/* For peer, macaddr is key */
1187 		if (WLAN_ADDR_EQ(wlan_peer_get_macaddr(peer), macaddr)
1188 				== QDF_STATUS_SUCCESS) {
1189 			if (wlan_objmgr_peer_try_get_ref(peer, dbg_id) ==
1190 					QDF_STATUS_SUCCESS) {
1191 				return peer;
1192 			}
1193 		}
1194 		/* Move to next peer */
1195 		peer_temp = peer;
1196 		peer = wlan_peer_get_next_peer_of_psoc(obj_list, peer_temp);
1197 	}
1198 
1199 	/* Not found, return NULL */
1200 	return NULL;
1201 }
1202 
1203 /**
1204  * wlan_obj_psoc_peerlist_get_peer_by_pdev_id() - get peer from psoc peer list
1205  * @psoc: PSOC object
1206  * @macaddr: MAC address
1207  * #pdev_id: Pdev id
1208  *
1209  * API to finds peer object pointer by MAC addr and pdev id from hash list
1210  *
1211  * Return: peer pointer
1212  *         NULL on FAILURE
1213  */
1214 static struct wlan_objmgr_peer *wlan_obj_psoc_peerlist_get_peer_by_pdev_id(
1215 				qdf_list_t *obj_list, uint8_t *macaddr,
1216 				uint8_t pdev_id, wlan_objmgr_ref_dbgid dbg_id)
1217 {
1218 	struct wlan_objmgr_peer *peer;
1219 	struct wlan_objmgr_peer *peer_temp;
1220 
1221 	/* Iterate through hash list to get the peer */
1222 	peer = wlan_psoc_peer_list_peek_head(obj_list);
1223 	while (peer != NULL) {
1224 		/* For peer, macaddr is key */
1225 		if ((WLAN_ADDR_EQ(wlan_peer_get_macaddr(peer), macaddr)
1226 			== QDF_STATUS_SUCCESS) &&
1227 				(wlan_peer_get_pdev_id(peer) == pdev_id)) {
1228 			if (wlan_objmgr_peer_try_get_ref(peer, dbg_id) ==
1229 							QDF_STATUS_SUCCESS) {
1230 				return peer;
1231 			}
1232 		}
1233 		/* Move to next peer */
1234 		peer_temp = peer;
1235 		peer = wlan_peer_get_next_peer_of_psoc(obj_list, peer_temp);
1236 	}
1237 
1238 	/* Not found, return NULL */
1239 	return NULL;
1240 }
1241 
1242 static struct wlan_objmgr_peer *wlan_obj_psoc_peerlist_get_peer_no_state(
1243 				qdf_list_t *obj_list, uint8_t *macaddr,
1244 				uint8_t pdev_id, wlan_objmgr_ref_dbgid dbg_id)
1245 {
1246 	struct wlan_objmgr_peer *peer;
1247 	struct wlan_objmgr_peer *peer_temp;
1248 
1249 	/* Iterate through hash list to get the peer */
1250 	peer = wlan_psoc_peer_list_peek_head(obj_list);
1251 	while (peer != NULL) {
1252 		/* For peer, macaddr and pdev_id is key */
1253 		if ((WLAN_ADDR_EQ(wlan_peer_get_macaddr(peer), macaddr)
1254 			== QDF_STATUS_SUCCESS) &&
1255 				(wlan_peer_get_pdev_id(peer) == pdev_id)) {
1256 			wlan_objmgr_peer_get_ref(peer, dbg_id);
1257 
1258 			return peer;
1259 		}
1260 		/* Move to next peer */
1261 		peer_temp = peer;
1262 		peer = wlan_peer_get_next_peer_of_psoc(obj_list, peer_temp);
1263 	}
1264 
1265 	/* Not found, return NULL */
1266 	return NULL;
1267 }
1268 
1269 /**
1270  * wlan_obj_psoc_populate_logically_del_peerlist_by_mac_n_bssid() - get peer
1271  *                                           from psoc peer list using
1272  *                                           mac and vdev self mac
1273  * @obj_list: peer object list
1274  * @macaddr: MAC address
1275  * @bssid: BSSID address
1276  * @dbg_id: id of the caller
1277  *
1278  * API to finds peer object pointer by MAC addr and BSSID from
1279  * peer hash list for a node which is in logically deleted state,
1280  * bssid check is done on matching peer
1281  *
1282  * Caller to free the list allocated in this function
1283  *
1284  * Return: list of peer pointers
1285  *         NULL on FAILURE
1286  */
1287 static qdf_list_t
1288 	*wlan_obj_psoc_populate_logically_del_peerlist_by_mac_n_bssid(
1289 				qdf_list_t *obj_list, uint8_t *macaddr,
1290 				uint8_t *bssid, uint8_t pdev_id,
1291 				wlan_objmgr_ref_dbgid dbg_id)
1292 {
1293 	struct wlan_objmgr_peer *peer;
1294 	struct wlan_objmgr_peer *peer_temp;
1295 	struct wlan_logically_del_peer *peer_list = NULL;
1296 	qdf_list_t *logical_del_peer_list = NULL;
1297 	bool lock_released = false;
1298 
1299 	logical_del_peer_list = qdf_mem_malloc(sizeof(*logical_del_peer_list));
1300 	if (!logical_del_peer_list) {
1301 		obj_mgr_err("failed to allocate list");
1302 		return NULL;
1303 	}
1304 
1305 	qdf_list_create(logical_del_peer_list, WLAN_UMAC_PSOC_MAX_PEERS);
1306 
1307 	/* Iterate through hash list to get the peer */
1308 	peer = wlan_psoc_peer_list_peek_head(obj_list);
1309 	while (peer != NULL) {
1310 		wlan_peer_obj_lock(peer);
1311 		/* For peer, macaddr and pdev id are keys */
1312 		if ((WLAN_ADDR_EQ(wlan_peer_get_macaddr(peer), macaddr)
1313 			== QDF_STATUS_SUCCESS) &&
1314 				(wlan_peer_get_pdev_id(peer) == pdev_id)) {
1315 			/*
1316 			 *  if BSSID not NULL,
1317 			 *  then match is requested by caller, check BSSID
1318 			 *  (vdev mac == bssid) --  return peer
1319 			 *  (vdev mac != bssid) --  perform next iteration
1320 			 */
1321 			if ((bssid == NULL) ||
1322 				(wlan_peer_bssid_match(peer, bssid) ==
1323 				 QDF_STATUS_SUCCESS)) {
1324 				/* Return peer in logically deleted state */
1325 				if ((peer->obj_state ==
1326 					WLAN_OBJ_STATE_LOGICALLY_DELETED) &&
1327 				     qdf_atomic_read(
1328 						&peer->peer_objmgr.ref_cnt)) {
1329 
1330 					wlan_objmgr_peer_get_ref(peer, dbg_id);
1331 					wlan_peer_obj_unlock(peer);
1332 					lock_released = true;
1333 
1334 					peer_list =
1335 					qdf_mem_malloc(
1336 					sizeof(struct wlan_logically_del_peer));
1337 					if (peer_list == NULL) {
1338 						wlan_objmgr_peer_release_ref(peer, dbg_id);
1339 						/* Lock is already released */
1340 						obj_mgr_alert("Mem alloc failed");
1341 						WLAN_OBJMGR_BUG(0);
1342 						break;
1343 					}
1344 
1345 					peer_list->peer = peer;
1346 
1347 					qdf_list_insert_front(
1348 						logical_del_peer_list,
1349 							&peer_list->list);
1350 				}
1351 			}
1352 		}
1353 
1354 		if (!lock_released)
1355 			wlan_peer_obj_unlock(peer);
1356 
1357 		/* Move to next peer */
1358 		peer_temp = peer;
1359 		peer = wlan_peer_get_next_peer_of_psoc(obj_list, peer_temp);
1360 		lock_released = false;
1361 	}
1362 
1363 	/* Not found, return NULL */
1364 	if (qdf_list_empty(logical_del_peer_list)) {
1365 		qdf_mem_free(logical_del_peer_list);
1366 		return NULL;
1367 	} else {
1368 		return logical_del_peer_list;
1369 	}
1370 
1371 }
1372 
1373 /**
1374  * wlan_obj_psoc_peerlist_get_peer_by_mac_n_bssid() - get peer from psoc peer
1375  *                                                    list using mac and vdev
1376  *                                                    self mac
1377  * @psoc: PSOC object
1378  * @macaddr: MAC address
1379  * @bssid: BSSID address
1380  *
1381  * API to finds peer object pointer by MAC addr and BSSID from
1382  * peer hash list, bssid check is done on matching peer
1383  *
1384  * Return: peer pointer
1385  *         NULL on FAILURE
1386  */
1387 static struct wlan_objmgr_peer *wlan_obj_psoc_peerlist_get_peer_by_mac_n_bssid(
1388 					qdf_list_t *obj_list, uint8_t *macaddr,
1389 					uint8_t *bssid, uint8_t pdev_id,
1390 					wlan_objmgr_ref_dbgid dbg_id)
1391 {
1392 	struct wlan_objmgr_peer *peer;
1393 	struct wlan_objmgr_peer *peer_temp;
1394 
1395 	/* Iterate through hash list to get the peer */
1396 	peer = wlan_psoc_peer_list_peek_head(obj_list);
1397 	while (peer != NULL) {
1398 		/* For peer, macaddr is key */
1399 		if (WLAN_ADDR_EQ(wlan_peer_get_macaddr(peer), macaddr)
1400 			== QDF_STATUS_SUCCESS) {
1401 			/*
1402 			 *  BSSID match is requested by caller, check BSSID
1403 			 *  (vdev mac == bssid) --  return peer
1404 			 *  (vdev mac != bssid) --  perform next iteration
1405 			 */
1406 			if ((wlan_peer_bssid_match(peer, bssid) ==
1407 				QDF_STATUS_SUCCESS) &&
1408 				(wlan_peer_get_pdev_id(peer) == pdev_id)) {
1409 				if (wlan_objmgr_peer_try_get_ref(peer, dbg_id)
1410 					== QDF_STATUS_SUCCESS) {
1411 					return peer;
1412 				}
1413 			}
1414 		}
1415 		/* Move to next peer */
1416 		peer_temp = peer;
1417 		peer = wlan_peer_get_next_peer_of_psoc(obj_list, peer_temp);
1418 	}
1419 	/* Not found, return NULL */
1420 	return NULL;
1421 }
1422 
1423 static struct wlan_objmgr_peer
1424 		*wlan_obj_psoc_peerlist_get_peer_by_mac_n_bssid_no_state(
1425 					qdf_list_t *obj_list, uint8_t *macaddr,
1426 					uint8_t *bssid,
1427 					uint8_t pdev_id,
1428 					wlan_objmgr_ref_dbgid dbg_id)
1429 {
1430 	struct wlan_objmgr_peer *peer;
1431 	struct wlan_objmgr_peer *peer_temp;
1432 
1433 	/* Iterate through hash list to get the peer */
1434 	peer = wlan_psoc_peer_list_peek_head(obj_list);
1435 	while (peer != NULL) {
1436 		/* For peer, macaddr is key */
1437 		if (WLAN_ADDR_EQ(wlan_peer_get_macaddr(peer), macaddr)
1438 			== QDF_STATUS_SUCCESS) {
1439 			/*
1440 			 *  BSSID match is requested by caller, check BSSID
1441 			 *  (vdev mac == bssid) --  return peer
1442 			 *  (vdev mac != bssid) --  perform next iteration
1443 			 */
1444 			if ((wlan_peer_bssid_match(peer, bssid) ==
1445 				QDF_STATUS_SUCCESS) &&
1446 				(wlan_peer_get_pdev_id(peer) == pdev_id)) {
1447 				wlan_objmgr_peer_get_ref(peer, dbg_id);
1448 
1449 				return peer;
1450 			}
1451 		}
1452 		/* Move to next peer */
1453 		peer_temp = peer;
1454 		peer = wlan_peer_get_next_peer_of_psoc(obj_list, peer_temp);
1455 	}
1456 
1457 	/* Not found, return NULL */
1458 	return NULL;
1459 }
1460 
1461 QDF_STATUS wlan_objmgr_psoc_peer_attach(struct wlan_objmgr_psoc *psoc,
1462 					 struct wlan_objmgr_peer *peer)
1463 {
1464 	struct wlan_objmgr_psoc_objmgr *objmgr;
1465 	uint8_t hash_index;
1466 	struct wlan_peer_list *peer_list;
1467 
1468 	wlan_psoc_obj_lock(psoc);
1469 	objmgr = &psoc->soc_objmgr;
1470 	/* Max temporary peer limit is reached, return failure */
1471 	if (peer->peer_mlme.peer_type == WLAN_PEER_STA_TEMP) {
1472 		if (objmgr->temp_peer_count >= WLAN_MAX_PSOC_TEMP_PEERS) {
1473 			wlan_psoc_obj_unlock(psoc);
1474 			return QDF_STATUS_E_FAILURE;
1475 		}
1476 	} else {
1477 		/* Max peer limit is reached, return failure */
1478 		if (objmgr->wlan_peer_count
1479 			>= wlan_psoc_get_max_peer_count(psoc)) {
1480 			wlan_psoc_obj_unlock(psoc);
1481 			return QDF_STATUS_E_FAILURE;
1482 		}
1483 	}
1484 
1485 	/* Derive hash index from mac address */
1486 	hash_index = WLAN_PEER_HASH(peer->macaddr);
1487 	peer_list = &objmgr->peer_list;
1488 	/* psoc lock should be taken before list lock */
1489 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1490 	/* add peer to hash peer list */
1491 	wlan_obj_psoc_peerlist_add_tail(
1492 			&peer_list->peer_hash[hash_index],
1493 							peer);
1494 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1495 	/* Increment peer count */
1496 	if (peer->peer_mlme.peer_type == WLAN_PEER_STA_TEMP)
1497 		objmgr->temp_peer_count++;
1498 	else
1499 		objmgr->wlan_peer_count++;
1500 
1501 	wlan_psoc_obj_unlock(psoc);
1502 
1503 	return QDF_STATUS_SUCCESS;
1504 }
1505 
1506 QDF_STATUS wlan_objmgr_psoc_peer_detach(struct wlan_objmgr_psoc *psoc,
1507 						struct wlan_objmgr_peer *peer)
1508 {
1509 	struct wlan_objmgr_psoc_objmgr *objmgr;
1510 	uint8_t hash_index;
1511 	struct wlan_peer_list *peer_list;
1512 
1513 	wlan_psoc_obj_lock(psoc);
1514 	objmgr = &psoc->soc_objmgr;
1515 	/* if list is empty, return */
1516 	if (objmgr->wlan_peer_count == 0) {
1517 		wlan_psoc_obj_unlock(psoc);
1518 		return QDF_STATUS_E_FAILURE;
1519 	}
1520 	/* Get hash index, to locate the actual peer list */
1521 	hash_index = WLAN_PEER_HASH(peer->macaddr);
1522 	peer_list = &objmgr->peer_list;
1523 	/* psoc lock should be taken before list lock */
1524 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1525 	/* removes the peer from peer_list */
1526 	if (wlan_obj_psoc_peerlist_remove_peer(
1527 				&peer_list->peer_hash[hash_index],
1528 						peer) ==
1529 				QDF_STATUS_E_FAILURE) {
1530 		qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1531 		wlan_psoc_obj_unlock(psoc);
1532 		obj_mgr_err("Failed to detach peer");
1533 		return QDF_STATUS_E_FAILURE;
1534 	}
1535 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1536 	/* Decrement peer count */
1537 	if (peer->peer_mlme.peer_type == WLAN_PEER_STA_TEMP)
1538 		objmgr->temp_peer_count--;
1539 	else
1540 		objmgr->wlan_peer_count--;
1541 	wlan_psoc_obj_unlock(psoc);
1542 
1543 	return QDF_STATUS_SUCCESS;
1544 }
1545 
1546 struct wlan_objmgr_peer *wlan_objmgr_get_peer_logically_deleted(
1547 			struct wlan_objmgr_psoc *psoc, uint8_t *macaddr,
1548 			wlan_objmgr_ref_dbgid dbg_id)
1549 {
1550 	struct wlan_objmgr_psoc_objmgr *objmgr;
1551 	uint8_t hash_index;
1552 	struct wlan_objmgr_peer *peer = NULL;
1553 	struct wlan_peer_list *peer_list;
1554 
1555 	/* psoc lock should be taken before peer list lock */
1556 	wlan_psoc_obj_lock(psoc);
1557 	objmgr = &psoc->soc_objmgr;
1558 	/* List is empty, return NULL */
1559 	if (objmgr->wlan_peer_count == 0) {
1560 		wlan_psoc_obj_unlock(psoc);
1561 		return NULL;
1562 	}
1563 	/* reduce the search window, with hash key */
1564 	hash_index = WLAN_PEER_HASH(macaddr);
1565 	peer_list = &objmgr->peer_list;
1566 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1567 	/* Iterate through peer list, get peer */
1568 	peer = wlan_obj_psoc_peerlist_get_peer_logically_deleted(
1569 		&peer_list->peer_hash[hash_index], macaddr, dbg_id);
1570 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1571 	wlan_psoc_obj_unlock(psoc);
1572 
1573 	return peer;
1574 }
1575 
1576 struct wlan_objmgr_peer *wlan_objmgr_get_peer_by_mac(
1577 		struct wlan_objmgr_psoc *psoc, uint8_t *macaddr,
1578 		wlan_objmgr_ref_dbgid dbg_id)
1579 {
1580 	struct wlan_objmgr_psoc_objmgr *objmgr;
1581 	uint8_t hash_index;
1582 	struct wlan_objmgr_peer *peer = NULL;
1583 	struct wlan_peer_list *peer_list;
1584 
1585 	if (!macaddr)
1586 		return NULL;
1587 
1588 	/* psoc lock should be taken before peer list lock */
1589 	wlan_psoc_obj_lock(psoc);
1590 	objmgr = &psoc->soc_objmgr;
1591 	/* List is empty, return NULL */
1592 	if (objmgr->wlan_peer_count == 0) {
1593 		wlan_psoc_obj_unlock(psoc);
1594 		return NULL;
1595 	}
1596 	/* reduce the search window, with hash key */
1597 	hash_index = WLAN_PEER_HASH(macaddr);
1598 	peer_list = &objmgr->peer_list;
1599 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1600 	/* Iterate through peer list, get peer */
1601 	peer = wlan_obj_psoc_peerlist_get_peer(
1602 			&peer_list->peer_hash[hash_index], macaddr, dbg_id);
1603 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1604 	wlan_psoc_obj_unlock(psoc);
1605 
1606 	return peer;
1607 }
1608 qdf_export_symbol(wlan_objmgr_get_peer_by_mac);
1609 
1610 struct wlan_objmgr_peer *wlan_objmgr_get_peer(
1611 			struct wlan_objmgr_psoc *psoc, uint8_t pdev_id,
1612 			uint8_t *macaddr, wlan_objmgr_ref_dbgid dbg_id)
1613 {
1614 	struct wlan_objmgr_psoc_objmgr *objmgr;
1615 	uint8_t hash_index;
1616 	struct wlan_objmgr_peer *peer = NULL;
1617 	struct wlan_peer_list *peer_list;
1618 
1619 	if (pdev_id >= WLAN_UMAC_MAX_PDEVS)
1620 		QDF_ASSERT(0);
1621 
1622 	if (!macaddr)
1623 		return NULL;
1624 
1625 	/* psoc lock should be taken before peer list lock */
1626 	wlan_psoc_obj_lock(psoc);
1627 	objmgr = &psoc->soc_objmgr;
1628 	/* List is empty, return NULL */
1629 	if (objmgr->wlan_peer_count == 0) {
1630 		wlan_psoc_obj_unlock(psoc);
1631 		return NULL;
1632 	}
1633 	/* reduce the search window, with hash key */
1634 	hash_index = WLAN_PEER_HASH(macaddr);
1635 	peer_list = &objmgr->peer_list;
1636 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1637 	/* Iterate through peer list, get peer */
1638 	peer = wlan_obj_psoc_peerlist_get_peer_by_pdev_id(
1639 		&peer_list->peer_hash[hash_index], macaddr, pdev_id, dbg_id);
1640 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1641 	wlan_psoc_obj_unlock(psoc);
1642 
1643 	return peer;
1644 }
1645 qdf_export_symbol(wlan_objmgr_get_peer);
1646 
1647 struct wlan_objmgr_peer *wlan_objmgr_get_peer_nolock(
1648 			struct wlan_objmgr_psoc *psoc, uint8_t pdev_id,
1649 			uint8_t *macaddr, wlan_objmgr_ref_dbgid dbg_id)
1650 {
1651 	struct wlan_objmgr_psoc_objmgr *objmgr;
1652 	uint8_t hash_index;
1653 	struct wlan_objmgr_peer *peer = NULL;
1654 	struct wlan_peer_list *peer_list;
1655 
1656 	/* psoc lock should be taken before peer list lock */
1657 	objmgr = &psoc->soc_objmgr;
1658 	/* List is empty, return NULL */
1659 	if (objmgr->wlan_peer_count == 0)
1660 		return NULL;
1661 
1662 	/* reduce the search window, with hash key */
1663 	hash_index = WLAN_PEER_HASH(macaddr);
1664 	peer_list = &objmgr->peer_list;
1665 	/* Iterate through peer list, get peer */
1666 	peer = wlan_obj_psoc_peerlist_get_peer_by_pdev_id(
1667 		&peer_list->peer_hash[hash_index], macaddr, pdev_id, dbg_id);
1668 
1669 	return peer;
1670 }
1671 qdf_export_symbol(wlan_objmgr_get_peer_nolock);
1672 
1673 
1674 struct wlan_objmgr_peer *wlan_objmgr_get_peer_no_state(
1675 			struct wlan_objmgr_psoc *psoc, uint8_t pdev_id,
1676 			uint8_t *macaddr, wlan_objmgr_ref_dbgid dbg_id)
1677 {
1678 	struct wlan_objmgr_psoc_objmgr *objmgr;
1679 	uint8_t hash_index;
1680 	struct wlan_objmgr_peer *peer = NULL;
1681 	struct wlan_peer_list *peer_list;
1682 
1683 	/* psoc lock should be taken before peer list lock */
1684 	wlan_psoc_obj_lock(psoc);
1685 	objmgr = &psoc->soc_objmgr;
1686 	/* List is empty, return NULL */
1687 	if (objmgr->wlan_peer_count == 0) {
1688 		wlan_psoc_obj_unlock(psoc);
1689 		return NULL;
1690 	}
1691 	/* reduce the search window, with hash key */
1692 	hash_index = WLAN_PEER_HASH(macaddr);
1693 	peer_list = &objmgr->peer_list;
1694 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1695 	/* Iterate through peer list, get peer */
1696 	peer = wlan_obj_psoc_peerlist_get_peer_no_state(
1697 		&peer_list->peer_hash[hash_index], macaddr, pdev_id, dbg_id);
1698 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1699 	wlan_psoc_obj_unlock(psoc);
1700 
1701 	return peer;
1702 }
1703 qdf_export_symbol(wlan_objmgr_get_peer_no_state);
1704 
1705 struct wlan_objmgr_peer *wlan_objmgr_get_peer_by_mac_n_vdev(
1706 			struct wlan_objmgr_psoc *psoc, uint8_t pdev_id,
1707 			uint8_t *bssid, uint8_t *macaddr,
1708 			wlan_objmgr_ref_dbgid dbg_id)
1709 {
1710 	struct wlan_objmgr_psoc_objmgr *objmgr;
1711 	uint8_t hash_index;
1712 	struct wlan_objmgr_peer *peer = NULL;
1713 	struct wlan_peer_list *peer_list;
1714 
1715 	/* psoc lock should be taken before peer list lock */
1716 	wlan_psoc_obj_lock(psoc);
1717 	objmgr = &psoc->soc_objmgr;
1718 	/* List is empty, return NULL */
1719 	if (objmgr->wlan_peer_count == 0) {
1720 		wlan_psoc_obj_unlock(psoc);
1721 		return NULL;
1722 	}
1723 	/* reduce the search window, with hash key */
1724 	hash_index = WLAN_PEER_HASH(macaddr);
1725 	peer_list = &objmgr->peer_list;
1726 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1727 	/* Iterate through peer list, get peer */
1728 	peer = wlan_obj_psoc_peerlist_get_peer_by_mac_n_bssid(
1729 		&peer_list->peer_hash[hash_index], macaddr, bssid,
1730 		pdev_id, dbg_id);
1731 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1732 	wlan_psoc_obj_unlock(psoc);
1733 
1734 	return peer;
1735 }
1736 qdf_export_symbol(wlan_objmgr_get_peer_by_mac_n_vdev);
1737 
1738 
1739 /**
1740  * wlan_objmgr_populate_logically_deleted_peerlist_by_mac_n_vdev() - get peer from psoc
1741  *                                                           peer list using
1742  *                                                           mac and vdev
1743  *                                                           self mac
1744  * @psoc: PSOC object
1745  * @pdev_id: Pdev id
1746  * @macaddr: MAC address
1747  * @bssid: BSSID address. NULL mac means search all.
1748  * @dbg_id: id of the caller
1749  *
1750  * API to finds peer object pointer by MAC addr and BSSID from
1751  * peer hash list, bssid check is done on matching peer
1752  *
1753  * Return: list of peer pointer pointers
1754  *         NULL on FAILURE
1755  */
1756 
1757 qdf_list_t *wlan_objmgr_populate_logically_deleted_peerlist_by_mac_n_vdev(
1758 			struct wlan_objmgr_psoc *psoc, uint8_t pdev_id,
1759 			uint8_t *bssid, uint8_t *macaddr,
1760 			wlan_objmgr_ref_dbgid dbg_id)
1761 {
1762 	struct wlan_objmgr_psoc_objmgr *objmgr;
1763 	uint8_t hash_index;
1764 	struct wlan_peer_list *peer_list = NULL;
1765 	qdf_list_t *logical_del_peer_list = NULL;
1766 
1767 	/* psoc lock should be taken before peer list lock */
1768 	wlan_psoc_obj_lock(psoc);
1769 	objmgr = &psoc->soc_objmgr;
1770 	/* List is empty, return NULL */
1771 	if (objmgr->wlan_peer_count == 0) {
1772 		wlan_psoc_obj_unlock(psoc);
1773 		return NULL;
1774 	}
1775 	/* reduce the search window, with hash key */
1776 	hash_index = WLAN_PEER_HASH(macaddr);
1777 	peer_list = &objmgr->peer_list;
1778 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1779 
1780 	/* Iterate through peer list, get peer */
1781 	logical_del_peer_list =
1782 		wlan_obj_psoc_populate_logically_del_peerlist_by_mac_n_bssid(
1783 			&peer_list->peer_hash[hash_index], macaddr,
1784 			bssid, pdev_id, dbg_id);
1785 
1786 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1787 	wlan_psoc_obj_unlock(psoc);
1788 
1789 	return logical_del_peer_list;
1790 }
1791 qdf_export_symbol(wlan_objmgr_populate_logically_deleted_peerlist_by_mac_n_vdev);
1792 
1793 struct wlan_objmgr_peer *wlan_objmgr_get_peer_by_mac_n_vdev_no_state(
1794 			struct wlan_objmgr_psoc *psoc, uint8_t pdev_id,
1795 			uint8_t *bssid, uint8_t *macaddr,
1796 			wlan_objmgr_ref_dbgid dbg_id)
1797 {
1798 	struct wlan_objmgr_psoc_objmgr *objmgr;
1799 	uint8_t hash_index;
1800 	struct wlan_objmgr_peer *peer = NULL;
1801 	struct wlan_peer_list *peer_list;
1802 
1803 	/* psoc lock should be taken before peer list lock */
1804 	wlan_psoc_obj_lock(psoc);
1805 	objmgr = &psoc->soc_objmgr;
1806 	/* List is empty, return NULL */
1807 	if (objmgr->wlan_peer_count == 0) {
1808 		wlan_psoc_obj_unlock(psoc);
1809 		return NULL;
1810 	}
1811 	/* reduce the search window, with hash key */
1812 	hash_index = WLAN_PEER_HASH(macaddr);
1813 	peer_list = &objmgr->peer_list;
1814 	qdf_spin_lock_bh(&peer_list->peer_list_lock);
1815 	/* Iterate through peer list, get peer */
1816 	peer = wlan_obj_psoc_peerlist_get_peer_by_mac_n_bssid_no_state(
1817 		&peer_list->peer_hash[hash_index], macaddr, bssid,
1818 		pdev_id, dbg_id);
1819 	qdf_spin_unlock_bh(&peer_list->peer_list_lock);
1820 	wlan_psoc_obj_unlock(psoc);
1821 
1822 	return peer;
1823 }
1824 qdf_export_symbol(wlan_objmgr_get_peer_by_mac_n_vdev_no_state);
1825 
1826 void *wlan_objmgr_psoc_get_comp_private_obj(struct wlan_objmgr_psoc *psoc,
1827 					enum wlan_umac_comp_id id)
1828 {
1829 	void *comp_private_obj;
1830 
1831 	/* component id is invalid */
1832 	if (id >= WLAN_UMAC_MAX_COMPONENTS) {
1833 		QDF_BUG(0);
1834 		return NULL;
1835 	}
1836 
1837 	if (psoc == NULL) {
1838 		QDF_BUG(0);
1839 		return NULL;
1840 	}
1841 
1842 	comp_private_obj = psoc->soc_comp_priv_obj[id];
1843 
1844 	return comp_private_obj;
1845 }
1846 qdf_export_symbol(wlan_objmgr_psoc_get_comp_private_obj);
1847 
1848 void wlan_objmgr_psoc_get_ref(struct wlan_objmgr_psoc *psoc,
1849 						wlan_objmgr_ref_dbgid id)
1850 {
1851 	if (psoc == NULL) {
1852 		obj_mgr_err("psoc obj is NULL for id:%d", id);
1853 		QDF_ASSERT(0);
1854 		return;
1855 	}
1856 	/* Increment ref count */
1857 	qdf_atomic_inc(&psoc->soc_objmgr.ref_cnt);
1858 	qdf_atomic_inc(&psoc->soc_objmgr.ref_id_dbg[id]);
1859 	return;
1860 }
1861 qdf_export_symbol(wlan_objmgr_psoc_get_ref);
1862 
1863 QDF_STATUS wlan_objmgr_psoc_try_get_ref(struct wlan_objmgr_psoc *psoc,
1864 						wlan_objmgr_ref_dbgid id)
1865 {
1866 	if (psoc == NULL) {
1867 		obj_mgr_err("psoc obj is NULL for id:%d", id);
1868 		QDF_ASSERT(0);
1869 		return QDF_STATUS_E_FAILURE;
1870 	}
1871 
1872 	wlan_psoc_obj_lock(psoc);
1873 	if (psoc->obj_state != WLAN_OBJ_STATE_CREATED) {
1874 		wlan_psoc_obj_unlock(psoc);
1875 		if (psoc->soc_objmgr.print_cnt++ <=
1876 				WLAN_OBJMGR_RATELIMIT_THRESH)
1877 			obj_mgr_err(
1878 			"[Ref id: %d] psoc is not in Created state(%d)",
1879 					id, psoc->obj_state);
1880 
1881 		return QDF_STATUS_E_RESOURCES;
1882 	}
1883 
1884 	/* Increment ref count */
1885 	wlan_objmgr_psoc_get_ref(psoc, id);
1886 	wlan_psoc_obj_unlock(psoc);
1887 
1888 	return QDF_STATUS_SUCCESS;
1889 }
1890 qdf_export_symbol(wlan_objmgr_psoc_try_get_ref);
1891 
1892 void wlan_objmgr_psoc_release_ref(struct wlan_objmgr_psoc *psoc,
1893 						wlan_objmgr_ref_dbgid id)
1894 {
1895 	if (psoc == NULL) {
1896 		obj_mgr_err("psoc obj is NULL for id:%d", id);
1897 		QDF_ASSERT(0);
1898 		return;
1899 	}
1900 
1901 	if (!qdf_atomic_read(&psoc->soc_objmgr.ref_id_dbg[id])) {
1902 		obj_mgr_err("psoc ref cnt was not taken by %d", id);
1903 		wlan_objmgr_print_ref_ids(psoc->soc_objmgr.ref_id_dbg,
1904 					  QDF_TRACE_LEVEL_FATAL);
1905 		WLAN_OBJMGR_BUG(0);
1906 	}
1907 
1908 	if (!qdf_atomic_read(&psoc->soc_objmgr.ref_cnt)) {
1909 		obj_mgr_err("psoc ref cnt is 0");
1910 		WLAN_OBJMGR_BUG(0);
1911 		return;
1912 	}
1913 
1914 	qdf_atomic_dec(&psoc->soc_objmgr.ref_id_dbg[id]);
1915 	/* Decrement ref count, free psoc, if ref count == 0 */
1916 	if (qdf_atomic_dec_and_test(&psoc->soc_objmgr.ref_cnt))
1917 		wlan_objmgr_psoc_obj_destroy(psoc);
1918 
1919 	return;
1920 }
1921 qdf_export_symbol(wlan_objmgr_psoc_release_ref);
1922 
1923 static void wlan_objmgr_psoc_peer_ref_print(struct wlan_objmgr_psoc *psoc,
1924 					 void *obj, void *args)
1925 {
1926 	struct wlan_objmgr_peer *peer = (struct wlan_objmgr_peer *)obj;
1927 	WLAN_OBJ_STATE obj_state;
1928 	uint8_t vdev_id;
1929 	uint8_t *macaddr;
1930 
1931 	wlan_peer_obj_lock(peer);
1932 	macaddr = wlan_peer_get_macaddr(peer);
1933 	obj_state = peer->obj_state;
1934 	vdev_id = wlan_vdev_get_id(wlan_peer_get_vdev(peer));
1935 	wlan_peer_obj_unlock(peer);
1936 
1937 	obj_mgr_alert("Peer MAC:%02x:%02x:%02x:%02x:%02x:%02x state:%d vdev_id:%d",
1938 		  macaddr[0], macaddr[1], macaddr[2], macaddr[3],
1939 		  macaddr[4], macaddr[5], obj_state, vdev_id);
1940 	wlan_objmgr_print_peer_ref_ids(peer, QDF_TRACE_LEVEL_FATAL);
1941 }
1942 
1943 static void wlan_objmgr_psoc_vdev_ref_print(struct wlan_objmgr_psoc *psoc,
1944 					 void *obj, void *args)
1945 {
1946 	struct wlan_objmgr_vdev *vdev = (struct wlan_objmgr_vdev *)obj;
1947 	WLAN_OBJ_STATE obj_state;
1948 	uint8_t id;
1949 
1950 	wlan_vdev_obj_lock(vdev);
1951 	id = wlan_vdev_get_id(vdev);
1952 	obj_state =  vdev->obj_state;
1953 	wlan_vdev_obj_unlock(vdev);
1954 	obj_mgr_alert("Vdev ID is %d, state %d", id, obj_state);
1955 
1956 	wlan_objmgr_print_ref_ids(vdev->vdev_objmgr.ref_id_dbg,
1957 				  QDF_TRACE_LEVEL_FATAL);
1958 }
1959 
1960 static void wlan_objmgr_psoc_pdev_ref_print(struct wlan_objmgr_psoc *psoc,
1961 					 void *obj, void *args)
1962 {
1963 	struct wlan_objmgr_pdev *pdev = (struct wlan_objmgr_pdev *)obj;
1964 	uint8_t id;
1965 
1966 	wlan_pdev_obj_lock(pdev);
1967 	id = wlan_objmgr_pdev_get_pdev_id(pdev);
1968 	wlan_pdev_obj_unlock(pdev);
1969 	obj_mgr_alert("pdev ID is %d", id);
1970 
1971 	wlan_objmgr_print_ref_ids(pdev->pdev_objmgr.ref_id_dbg,
1972 				  QDF_TRACE_LEVEL_FATAL);
1973 }
1974 
1975 QDF_STATUS wlan_objmgr_print_ref_all_objects_per_psoc(
1976 		struct wlan_objmgr_psoc *psoc)
1977 {
1978 	obj_mgr_alert("Ref counts of PEER");
1979 	wlan_objmgr_iterate_obj_list_all_noref(psoc, WLAN_PEER_OP,
1980 				wlan_objmgr_psoc_peer_ref_print, NULL);
1981 	obj_mgr_alert("Ref counts of VDEV");
1982 	wlan_objmgr_iterate_obj_list_all_noref(psoc, WLAN_VDEV_OP,
1983 				wlan_objmgr_psoc_vdev_ref_print, NULL);
1984 	obj_mgr_alert("Ref counts of PDEV");
1985 	wlan_objmgr_iterate_obj_list_all_noref(psoc, WLAN_PDEV_OP,
1986 				wlan_objmgr_psoc_pdev_ref_print, NULL);
1987 
1988 	obj_mgr_alert(" Ref counts of PSOC");
1989 	wlan_objmgr_print_ref_ids(psoc->soc_objmgr.ref_id_dbg,
1990 				  QDF_TRACE_LEVEL_FATAL);
1991 
1992 	return QDF_STATUS_SUCCESS;
1993 }
1994 qdf_export_symbol(wlan_objmgr_print_ref_all_objects_per_psoc);
1995 
1996 QDF_STATUS wlan_objmgr_psoc_set_user_config(struct wlan_objmgr_psoc *psoc,
1997 		struct wlan_objmgr_psoc_user_config *user_config_data)
1998 {
1999 	if (user_config_data == NULL) {
2000 		obj_mgr_err("user_config_data is NULL");
2001 		QDF_BUG(0);
2002 		return QDF_STATUS_E_FAILURE;
2003 	}
2004 	wlan_psoc_obj_lock(psoc);
2005 	qdf_mem_copy(&psoc->soc_nif.user_config, user_config_data,
2006 		     sizeof(psoc->soc_nif.user_config));
2007 	wlan_psoc_obj_unlock(psoc);
2008 
2009 	return QDF_STATUS_SUCCESS;
2010 }
2011 
2012 void wlan_objmgr_psoc_check_for_pdev_leaks(struct wlan_objmgr_psoc *psoc)
2013 {
2014 	struct wlan_objmgr_psoc_objmgr *_psoc;
2015 	struct wlan_objmgr_pdev *pdev;
2016 	int pdev_id;
2017 	uint32_t leaks = 0;
2018 
2019 	QDF_BUG(psoc);
2020 	if (!psoc)
2021 		return;
2022 
2023 	wlan_psoc_obj_lock(psoc);
2024 	_psoc = &psoc->soc_objmgr;
2025 	if (!_psoc->wlan_pdev_count) {
2026 		wlan_psoc_obj_unlock(psoc);
2027 		return;
2028 	}
2029 
2030 	obj_mgr_alert("objmgr pdev leaks detected for psoc %u!",
2031 		      _psoc->psoc_id);
2032 	obj_mgr_alert("----------------------------------------------------");
2033 	obj_mgr_alert("Pdev Id   Refs   Module");
2034 	obj_mgr_alert("----------------------------------------------------");
2035 
2036 	wlan_objmgr_for_each_psoc_pdev(psoc, pdev_id, pdev) {
2037 		qdf_atomic_t *ref_id_dbg;
2038 		int ref_id;
2039 		int32_t refs;
2040 
2041 		wlan_pdev_obj_lock(pdev);
2042 		ref_id_dbg = pdev->pdev_objmgr.ref_id_dbg;
2043 		wlan_objmgr_for_each_refs(ref_id_dbg, ref_id, refs) {
2044 			leaks++;
2045 			obj_mgr_alert("%7u   %4u   %s",
2046 				      pdev_id, refs,
2047 				      string_from_dbgid(ref_id));
2048 		}
2049 		wlan_pdev_obj_unlock(pdev);
2050 	}
2051 
2052 	QDF_DEBUG_PANIC("%u objmgr pdev leaks detected for psoc %u!",
2053 			leaks, _psoc->psoc_id);
2054 
2055 	wlan_psoc_obj_unlock(psoc);
2056 }
2057 qdf_export_symbol(wlan_objmgr_psoc_check_for_pdev_leaks);
2058 
2059 void wlan_objmgr_psoc_check_for_vdev_leaks(struct wlan_objmgr_psoc *psoc)
2060 {
2061 	struct wlan_objmgr_psoc_objmgr *_psoc;
2062 	struct wlan_objmgr_vdev *vdev;
2063 	int vdev_id;
2064 	uint32_t leaks = 0;
2065 
2066 	QDF_BUG(psoc);
2067 	if (!psoc)
2068 		return;
2069 
2070 	wlan_psoc_obj_lock(psoc);
2071 	_psoc = &psoc->soc_objmgr;
2072 	if (!_psoc->wlan_vdev_count) {
2073 		wlan_psoc_obj_unlock(psoc);
2074 		return;
2075 	}
2076 
2077 	obj_mgr_alert("objmgr vdev leaks detected for psoc %u!",
2078 		      _psoc->psoc_id);
2079 	obj_mgr_alert("----------------------------------------------------");
2080 	obj_mgr_alert("Vdev Id   Refs   Module");
2081 	obj_mgr_alert("----------------------------------------------------");
2082 
2083 	wlan_objmgr_for_each_psoc_vdev(psoc, vdev_id, vdev) {
2084 		qdf_atomic_t *ref_id_dbg;
2085 		int ref_id;
2086 		int32_t refs;
2087 
2088 		wlan_vdev_obj_lock(vdev);
2089 		ref_id_dbg = vdev->vdev_objmgr.ref_id_dbg;
2090 		wlan_objmgr_for_each_refs(ref_id_dbg, ref_id, refs) {
2091 			leaks++;
2092 			obj_mgr_alert("%7u   %4u   %s",
2093 				      vdev_id, refs, string_from_dbgid(ref_id));
2094 		}
2095 		wlan_vdev_obj_unlock(vdev);
2096 	}
2097 
2098 	QDF_DEBUG_PANIC("%u objmgr vdev leaks detected for psoc %u!",
2099 			leaks, _psoc->psoc_id);
2100 
2101 	wlan_psoc_obj_unlock(psoc);
2102 }
2103 qdf_export_symbol(wlan_objmgr_psoc_check_for_vdev_leaks);
2104 
2105 #ifdef WLAN_OBJMGR_REF_ID_DEBUG
2106 static void
2107 wlan_objmgr_print_peer_ref_leaks(struct wlan_objmgr_peer *peer, int vdev_id)
2108 {
2109 	qdf_atomic_t *ref_id_dbg;
2110 	int32_t refs;
2111 	int ref_id;
2112 
2113 	ref_id_dbg = peer->peer_objmgr.ref_id_dbg;
2114 	wlan_objmgr_for_each_refs(ref_id_dbg, ref_id, refs) {
2115 		obj_mgr_alert(QDF_MAC_ADDR_STR " %7u   %4u   %s",
2116 			      QDF_MAC_ADDR_ARRAY(peer->macaddr),
2117 			      vdev_id,
2118 			      refs,
2119 			      string_from_dbgid(ref_id));
2120 	}
2121 }
2122 #else
2123 static inline void
2124 wlan_objmgr_print_peer_ref_leaks(struct wlan_objmgr_peer *peer, int vdev_id)
2125 {
2126 	obj_mgr_alert(QDF_MAC_ADDR_STR " %7u   %4u   %s",
2127 		      QDF_MAC_ADDR_ARRAY(peer->macaddr),
2128 		      vdev_id,
2129 		      qdf_atomic_read(&peer->peer_objmgr.ref_cnt),
2130 		      "TOTAL_REF_COUNT");
2131 }
2132 #endif
2133 
2134 void wlan_objmgr_psoc_check_for_peer_leaks(struct wlan_objmgr_psoc *psoc)
2135 {
2136 	struct wlan_objmgr_psoc_objmgr *_psoc;
2137 	struct wlan_objmgr_vdev *vdev;
2138 	int vdev_id;
2139 	uint32_t leaks = 0;
2140 
2141 	QDF_BUG(psoc);
2142 	if (!psoc)
2143 		return;
2144 
2145 	wlan_psoc_obj_lock(psoc);
2146 	_psoc = &psoc->soc_objmgr;
2147 	if (!_psoc->temp_peer_count && !_psoc->wlan_peer_count) {
2148 		wlan_psoc_obj_unlock(psoc);
2149 		return;
2150 	}
2151 
2152 	obj_mgr_alert("objmgr peer leaks detected for psoc %u!",
2153 		      _psoc->psoc_id);
2154 	obj_mgr_alert("----------------------------------------------------");
2155 	obj_mgr_alert("Peer MAC          Vdev Id   Refs   Module");
2156 	obj_mgr_alert("----------------------------------------------------");
2157 
2158 	wlan_objmgr_for_each_psoc_vdev(psoc, vdev_id, vdev) {
2159 		struct wlan_objmgr_peer *peer;
2160 
2161 		wlan_vdev_obj_lock(vdev);
2162 		wlan_objmgr_for_each_vdev_peer(vdev, peer) {
2163 			wlan_peer_obj_lock(peer);
2164 			leaks += qdf_atomic_read(&peer->peer_objmgr.ref_cnt);
2165 			wlan_objmgr_print_peer_ref_leaks(peer, vdev_id);
2166 			wlan_peer_obj_unlock(peer);
2167 		}
2168 		wlan_vdev_obj_unlock(vdev);
2169 	}
2170 
2171 	QDF_DEBUG_PANIC("%u objmgr peer leaks detected for psoc %u!",
2172 			leaks, _psoc->psoc_id);
2173 
2174 	wlan_psoc_obj_unlock(psoc);
2175 }
2176 qdf_export_symbol(wlan_objmgr_psoc_check_for_peer_leaks);
2177