xref: /wlan-dirver/qcacld-3.0/core/wma/src/wma_dev_if.c (revision 8b22fbb1a3b35f27dcf9bc171053db0c548f5eb6)
1 /*
2  * Copyright (c) 2013-2021 The Linux Foundation. All rights reserved.
3  * Copyright (c) 2021-2024 Qualcomm Innovation Center, Inc. All rights reserved.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for
6  * any purpose with or without fee is hereby granted, provided that the
7  * above copyright notice and this permission notice appear in all
8  * copies.
9  *
10  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
11  * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
12  * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
13  * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
14  * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
15  * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
16  * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
17  * PERFORMANCE OF THIS SOFTWARE.
18  */
19 
20 /**
21  *  DOC:    wma_dev_if.c
22  *  This file contains vdev & peer related operations.
23  */
24 
25 /* Header files */
26 
27 #include "wma.h"
28 #include "wma_api.h"
29 #include "cds_api.h"
30 #include "wmi_unified_api.h"
31 #include "wlan_qct_sys.h"
32 #include "wni_api.h"
33 #include "ani_global.h"
34 #include "wmi_unified.h"
35 #include "wni_cfg.h"
36 
37 #include "qdf_nbuf.h"
38 #include "qdf_types.h"
39 #include "qdf_mem.h"
40 
41 #include "wma_types.h"
42 #include "lim_api.h"
43 #include "lim_session_utils.h"
44 #include "wma_pasn_peer_api.h"
45 
46 #include "cds_utils.h"
47 
48 #if !defined(REMOVE_PKT_LOG)
49 #include "pktlog_ac.h"
50 #endif /* REMOVE_PKT_LOG */
51 
52 #include "dbglog_host.h"
53 #include "csr_api.h"
54 
55 #include "wma_internal.h"
56 
57 #include "wma_ocb.h"
58 #include "cdp_txrx_cfg.h"
59 #include "cdp_txrx_flow_ctrl_legacy.h"
60 #include <cdp_txrx_peer_ops.h>
61 #include <cdp_txrx_cfg.h>
62 #include <cdp_txrx_cmn.h>
63 #include <cdp_txrx_misc.h>
64 #include <cdp_txrx_ctrl.h>
65 
66 #include "wlan_policy_mgr_api.h"
67 #include "wma_nan_datapath.h"
68 #include "wifi_pos_pasn_api.h"
69 #if defined(CONFIG_HL_SUPPORT)
70 #include "wlan_tgt_def_config_hl.h"
71 #else
72 #include "wlan_tgt_def_config.h"
73 #endif
74 #include <wlan_dfs_tgt_api.h>
75 #include <cdp_txrx_handle.h>
76 #include "wlan_pmo_ucfg_api.h"
77 #include "wlan_reg_services_api.h"
78 #include <include/wlan_vdev_mlme.h>
79 #include "wma_he.h"
80 #include "wma_eht.h"
81 #include "wlan_roam_debug.h"
82 #include "wlan_ocb_ucfg_api.h"
83 #include "init_deinit_lmac.h"
84 #include <target_if.h>
85 #include "wlan_policy_mgr_ucfg.h"
86 #include "wlan_mlme_public_struct.h"
87 #include "wlan_mlme_api.h"
88 #include "wlan_mlme_main.h"
89 #include "wlan_mlme_ucfg_api.h"
90 #include "wlan_mlme_twt_api.h"
91 #include <wlan_dfs_utils_api.h>
92 #include "../../core/src/vdev_mgr_ops.h"
93 #include "wlan_utility.h"
94 #include "wlan_coex_ucfg_api.h"
95 #include <wlan_cp_stats_mc_ucfg_api.h>
96 #include "wmi_unified_vdev_api.h"
97 #include <wlan_cm_api.h>
98 #include <../../core/src/wlan_cm_vdev_api.h>
99 #include "wlan_nan_api.h"
100 #include "wlan_mlo_mgr_peer.h"
101 #include "wifi_pos_api.h"
102 #include "wifi_pos_pasn_api.h"
103 #ifdef DCS_INTERFERENCE_DETECTION
104 #include <wlan_dcs_ucfg_api.h>
105 #endif
106 
107 #ifdef FEATURE_STA_MODE_VOTE_LINK
108 #include "wlan_ipa_ucfg_api.h"
109 #endif
110 
111 #include "son_api.h"
112 #include "wlan_vdev_mgr_tgt_if_tx_defs.h"
113 #include "wlan_mlo_mgr_roam.h"
114 #include "target_if_vdev_mgr_tx_ops.h"
115 #include "wlan_fwol_ucfg_api.h"
116 #include "wlan_vdev_mgr_utils_api.h"
117 #include "target_if.h"
118 #include <wlan_psoc_mlme_api.h>
119 
120 /*
121  * FW only supports 8 clients in SAP/GO mode for D3 WoW feature
122  * and hence host needs to hold a wake lock after 9th client connects
123  * and release the wake lock when 9th client disconnects
124  */
125 #define SAP_D3_WOW_MAX_CLIENT_HOLD_WAKE_LOCK (9)
126 #define SAP_D3_WOW_MAX_CLIENT_RELEASE_WAKE_LOCK (8)
127 
128 QDF_STATUS wma_find_vdev_id_by_addr(tp_wma_handle wma, uint8_t *addr,
129 				    uint8_t *vdev_id)
130 {
131 	uint8_t i;
132 	struct wlan_objmgr_vdev *vdev;
133 
134 	for (i = 0; i < wma->max_bssid; i++) {
135 		vdev = wma->interfaces[i].vdev;
136 		if (!vdev)
137 			continue;
138 
139 		if (qdf_is_macaddr_equal(
140 			(struct qdf_mac_addr *)wlan_vdev_mlme_get_macaddr(vdev),
141 			(struct qdf_mac_addr *)addr) == true) {
142 			*vdev_id = i;
143 			return QDF_STATUS_SUCCESS;
144 		}
145 
146 		if (qdf_is_macaddr_equal((struct qdf_mac_addr *)wlan_vdev_mlme_get_mldaddr(vdev),
147 					 (struct qdf_mac_addr *)addr) == true) {
148 				*vdev_id = i;
149 				return QDF_STATUS_SUCCESS;
150 		}
151 	}
152 
153 	return QDF_STATUS_E_FAILURE;
154 }
155 
156 
157 /**
158  * wma_is_vdev_in_ap_mode() - check that vdev is in ap mode or not
159  * @wma: wma handle
160  * @vdev_id: vdev id
161  *
162  * Helper function to know whether given vdev id
163  * is in AP mode or not.
164  *
165  * Return: True/False
166  */
167 bool wma_is_vdev_in_ap_mode(tp_wma_handle wma, uint8_t vdev_id)
168 {
169 	struct wma_txrx_node *intf = wma->interfaces;
170 
171 	if (vdev_id >= wma->max_bssid) {
172 		wma_err("Invalid vdev_id %hu", vdev_id);
173 		QDF_ASSERT(0);
174 		return false;
175 	}
176 
177 	if ((intf[vdev_id].type == WMI_VDEV_TYPE_AP) &&
178 	    ((intf[vdev_id].sub_type == WMI_UNIFIED_VDEV_SUBTYPE_P2P_GO) ||
179 	     (intf[vdev_id].sub_type == 0)))
180 		return true;
181 
182 	return false;
183 }
184 
185 uint8_t *wma_get_vdev_bssid(struct wlan_objmgr_vdev *vdev)
186 {
187 	struct vdev_mlme_obj *mlme_obj;
188 
189 	if (!vdev) {
190 		wma_err("vdev is NULL");
191 		return NULL;
192 	}
193 
194 	mlme_obj = wlan_vdev_mlme_get_cmpt_obj(vdev);
195 	if (!mlme_obj) {
196 		wma_err("Failed to get mlme_obj");
197 		return NULL;
198 	}
199 
200 	return mlme_obj->mgmt.generic.bssid;
201 }
202 
203 QDF_STATUS wma_find_vdev_id_by_bssid(tp_wma_handle wma, uint8_t *bssid,
204 				     uint8_t *vdev_id)
205 {
206 	int i;
207 	uint8_t *bssid_addr;
208 
209 	for (i = 0; i < wma->max_bssid; i++) {
210 		if (!wma->interfaces[i].vdev)
211 			continue;
212 		bssid_addr = wma_get_vdev_bssid(wma->interfaces[i].vdev);
213 		if (!bssid_addr)
214 			continue;
215 
216 		if (qdf_is_macaddr_equal(
217 			(struct qdf_mac_addr *)bssid_addr,
218 			(struct qdf_mac_addr *)bssid) == true) {
219 			*vdev_id = i;
220 			return QDF_STATUS_SUCCESS;
221 		}
222 	}
223 
224 	return QDF_STATUS_E_FAILURE;
225 }
226 
227 /**
228  * wma_find_req_on_timer_expiry() - find request by address
229  * @wma: wma handle
230  * @req: pointer to the target request
231  *
232  * On timer expiry, the pointer to the req message is received from the
233  * timer callback. Lookup the wma_hold_req_queue for the request with the
234  * same address and return success if found.
235  *
236  * Return: QDF_STATUS
237  */
238 static QDF_STATUS wma_find_req_on_timer_expiry(tp_wma_handle wma,
239 					       struct wma_target_req *req)
240 {
241 	struct wma_target_req *req_msg = NULL;
242 	bool found = false;
243 	qdf_list_node_t *cur_node = NULL, *next_node = NULL;
244 	QDF_STATUS status;
245 
246 	qdf_spin_lock_bh(&wma->wma_hold_req_q_lock);
247 	if (QDF_STATUS_SUCCESS != qdf_list_peek_front(&wma->wma_hold_req_queue,
248 						      &next_node)) {
249 		qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
250 		wma_err("unable to get msg node from request queue");
251 		return QDF_STATUS_E_FAILURE;
252 	}
253 
254 	do {
255 		cur_node = next_node;
256 		req_msg = qdf_container_of(cur_node,
257 					   struct wma_target_req, node);
258 		if (req_msg != req)
259 			continue;
260 
261 		found = true;
262 		status = qdf_list_remove_node(&wma->wma_hold_req_queue,
263 					      cur_node);
264 		if (QDF_STATUS_SUCCESS != status) {
265 			qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
266 			wma_debug("Failed to remove request for req %pK", req);
267 			return QDF_STATUS_E_FAILURE;
268 		}
269 		break;
270 	} while (QDF_STATUS_SUCCESS  ==
271 		 qdf_list_peek_next(&wma->wma_hold_req_queue,
272 				    cur_node, &next_node));
273 
274 	qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
275 	if (!found) {
276 		wma_err("target request not found for req %pK", req);
277 		return QDF_STATUS_E_INVAL;
278 	}
279 
280 	wma_debug("target request found for vdev id: %d type %d",
281 		 req_msg->vdev_id, req_msg->type);
282 
283 	return QDF_STATUS_SUCCESS;
284 }
285 
286 /**
287  * wma_find_req() - find target request for vdev id
288  * @wma: wma handle
289  * @vdev_id: vdev id
290  * @type: request type
291  * @peer_addr: Peer mac address
292  *
293  * Find target request for given vdev id & type of request.
294  * Remove that request from active list.
295  *
296  * Return: return target request if found or NULL.
297  */
298 static struct wma_target_req *wma_find_req(tp_wma_handle wma,
299 					   uint8_t vdev_id, uint8_t type,
300 					   struct qdf_mac_addr *peer_addr)
301 {
302 	struct wma_target_req *req_msg = NULL;
303 	bool found = false;
304 	qdf_list_node_t *node1 = NULL, *node2 = NULL;
305 	QDF_STATUS status;
306 
307 	qdf_spin_lock_bh(&wma->wma_hold_req_q_lock);
308 	if (QDF_STATUS_SUCCESS != qdf_list_peek_front(&wma->wma_hold_req_queue,
309 						      &node2)) {
310 		qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
311 		wma_err("unable to get msg node from request queue");
312 		return NULL;
313 	}
314 
315 	do {
316 		node1 = node2;
317 		req_msg = qdf_container_of(node1, struct wma_target_req, node);
318 		if (req_msg->vdev_id != vdev_id)
319 			continue;
320 		if (req_msg->type != type)
321 			continue;
322 
323 		found = true;
324 		if (type == WMA_PEER_CREATE_RESPONSE &&
325 		    peer_addr &&
326 		    !qdf_is_macaddr_equal(&req_msg->addr, peer_addr))
327 			found = false;
328 
329 		status = qdf_list_remove_node(&wma->wma_hold_req_queue, node1);
330 		if (QDF_STATUS_SUCCESS != status) {
331 			qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
332 			wma_debug("Failed to remove request for vdev_id %d type %d",
333 				 vdev_id, type);
334 			return NULL;
335 		}
336 		break;
337 	} while (QDF_STATUS_SUCCESS  ==
338 			qdf_list_peek_next(&wma->wma_hold_req_queue, node1,
339 					   &node2));
340 
341 	qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
342 	if (!found) {
343 		wma_err("target request not found for vdev_id %d type %d",
344 			 vdev_id, type);
345 		return NULL;
346 	}
347 
348 	wma_debug("target request found for vdev id: %d type %d",
349 		 vdev_id, type);
350 
351 	return req_msg;
352 }
353 
354 struct wma_target_req *wma_find_remove_req_msgtype(tp_wma_handle wma,
355 						   uint8_t vdev_id,
356 						   uint32_t msg_type)
357 {
358 	struct wma_target_req *req_msg = NULL;
359 	bool found = false;
360 	qdf_list_node_t *node1 = NULL, *node2 = NULL;
361 	QDF_STATUS status;
362 
363 	qdf_spin_lock_bh(&wma->wma_hold_req_q_lock);
364 	if (QDF_STATUS_SUCCESS != qdf_list_peek_front(&wma->wma_hold_req_queue,
365 						      &node2)) {
366 		qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
367 		wma_debug("unable to get msg node from request queue for vdev_id %d type %d",
368 			  vdev_id, msg_type);
369 		return NULL;
370 	}
371 
372 	do {
373 		node1 = node2;
374 		req_msg = qdf_container_of(node1, struct wma_target_req, node);
375 		if (req_msg->vdev_id != vdev_id)
376 			continue;
377 		if (req_msg->msg_type != msg_type)
378 			continue;
379 
380 		found = true;
381 		status = qdf_list_remove_node(&wma->wma_hold_req_queue, node1);
382 		if (QDF_STATUS_SUCCESS != status) {
383 			qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
384 			wma_debug("Failed to remove request. vdev_id %d type %d",
385 				  vdev_id, msg_type);
386 			return NULL;
387 		}
388 		break;
389 	} while (QDF_STATUS_SUCCESS  ==
390 			qdf_list_peek_next(&wma->wma_hold_req_queue, node1,
391 					   &node2));
392 
393 	qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
394 	if (!found) {
395 		wma_debug("target request not found for vdev_id %d type %d",
396 			  vdev_id, msg_type);
397 		return NULL;
398 	}
399 
400 	wma_debug("target request found for vdev id: %d type %d",
401 		  vdev_id, msg_type);
402 
403 	return req_msg;
404 }
405 
406 QDF_STATUS wma_vdev_detach_callback(struct vdev_delete_response *rsp)
407 {
408 	tp_wma_handle wma;
409 	struct wma_txrx_node *iface = NULL;
410 
411 	wma = cds_get_context(QDF_MODULE_ID_WMA);
412 	if (!wma)
413 		return QDF_STATUS_E_FAILURE;
414 
415 	/* Sanitize the vdev id*/
416 	if (rsp->vdev_id >= wma->max_bssid) {
417 		wma_err("vdev delete response with invalid vdev_id :%d",
418 			rsp->vdev_id);
419 		QDF_BUG(0);
420 		return QDF_STATUS_E_FAILURE;
421 	}
422 
423 	iface = &wma->interfaces[rsp->vdev_id];
424 
425 	wma_debug("vdev del response received for VDEV_%d", rsp->vdev_id);
426 	iface->del_staself_req = NULL;
427 
428 	if (iface->roam_scan_stats_req) {
429 		struct sir_roam_scan_stats *roam_scan_stats_req =
430 						iface->roam_scan_stats_req;
431 
432 		iface->roam_scan_stats_req = NULL;
433 		qdf_mem_free(roam_scan_stats_req);
434 	}
435 
436 	wma_vdev_deinit(iface);
437 	qdf_mem_zero(iface, sizeof(*iface));
438 	wma_vdev_init(iface);
439 
440 	mlme_vdev_del_resp(rsp->vdev_id);
441 
442 	return QDF_STATUS_SUCCESS;
443 }
444 
445 static void
446 wma_cdp_vdev_detach(ol_txrx_soc_handle soc, tp_wma_handle wma_handle,
447 		    uint8_t vdev_id)
448 {
449 	struct wma_txrx_node *iface = &wma_handle->interfaces[vdev_id];
450 	struct wlan_objmgr_vdev *vdev = iface->vdev;
451 
452 	if (!vdev) {
453 		wma_err("vdev is NULL");
454 		return;
455 	}
456 
457 	if (soc && wlan_vdev_get_id(vdev) != WLAN_INVALID_VDEV_ID)
458 		cdp_vdev_detach(soc, vdev_id, NULL, NULL);
459 }
460 
461 /**
462  * wma_release_vdev_ref() - Release vdev object reference count
463  * @iface: wma interface txrx node
464  *
465  * Purpose of this function is to release vdev object reference count
466  * from wma interface txrx node.
467  *
468  * Return: None
469  */
470 static void
471 wma_release_vdev_ref(struct wma_txrx_node *iface)
472 {
473 	struct wlan_objmgr_vdev *vdev;
474 
475 	vdev = iface->vdev;
476 	wma_debug("vdev state: %d", vdev->obj_state);
477 	if (vdev->obj_state != WLAN_OBJ_STATE_LOGICALLY_DELETED) {
478 		wma_debug("no vdev delete");
479 		return;
480 	}
481 	iface->vdev_active = false;
482 	iface->vdev = NULL;
483 	if (vdev)
484 		wlan_objmgr_vdev_release_ref(vdev, WLAN_LEGACY_WMA_ID);
485 }
486 
487 /**
488  * wma_handle_monitor_mode_vdev_detach() - Stop and down monitor mode vdev
489  * @wma: wma handle
490  * @vdev_id: used to get wma interface txrx node
491  *
492  * Monitor mode is unconneted mode, so do explicit vdev stop and down
493  *
494  * Return: None
495  */
496 static void wma_handle_monitor_mode_vdev_detach(tp_wma_handle wma,
497 						uint8_t vdev_id)
498 {
499 	struct wma_txrx_node *iface;
500 
501 	iface = &wma->interfaces[vdev_id];
502 	wlan_vdev_mlme_sm_deliver_evt(iface->vdev,
503 				      WLAN_VDEV_SM_EV_DOWN,
504 				      0, NULL);
505 	iface->vdev_active = false;
506 }
507 
508 /**
509  * wma_handle_vdev_detach() - wma vdev detach handler
510  * @wma_handle: pointer to wma handle
511  * @del_vdev_req_param: pointer to del req param
512  *
513  * Return: none.
514  */
515 static QDF_STATUS wma_handle_vdev_detach(tp_wma_handle wma_handle,
516 			struct del_vdev_params *del_vdev_req_param)
517 {
518 	QDF_STATUS status = QDF_STATUS_SUCCESS;
519 	uint8_t vdev_id = del_vdev_req_param->vdev_id;
520 	struct wma_txrx_node *iface = &wma_handle->interfaces[vdev_id];
521 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
522 	struct wmi_mgmt_params mgmt_params = {};
523 
524 	if (!soc) {
525 		status = QDF_STATUS_E_FAILURE;
526 		goto rel_ref;
527 	}
528 
529 	if ((cds_get_conparam() == QDF_GLOBAL_MONITOR_MODE) ||
530 	    (policy_mgr_is_sta_mon_concurrency(wma_handle->psoc) &&
531 	    wlan_vdev_mlme_get_opmode(iface->vdev) == QDF_MONITOR_MODE))
532 		wma_handle_monitor_mode_vdev_detach(wma_handle, vdev_id);
533 
534 rel_ref:
535 	wma_cdp_vdev_detach(soc, wma_handle, vdev_id);
536 	if (qdf_is_recovering())
537 		wlan_mgmt_txrx_vdev_drain(iface->vdev,
538 					  wma_mgmt_frame_fill_peer_cb,
539 					  &mgmt_params);
540 	wma_debug("Releasing wma reference for vdev:%d", vdev_id);
541 	wma_release_vdev_ref(iface);
542 	return status;
543 }
544 
545 /**
546  * wma_self_peer_remove() - Self peer remove handler
547  * @wma_handle: wma handle
548  * @del_vdev_req: vdev id
549  *
550  * Return: success if peer delete command sent to firmware, else failure.
551  */
552 static QDF_STATUS wma_self_peer_remove(tp_wma_handle wma_handle,
553 				       struct del_vdev_params *del_vdev_req)
554 {
555 	QDF_STATUS qdf_status;
556 	uint8_t vdev_id = del_vdev_req->vdev_id;
557 	struct wma_target_req *msg = NULL;
558 	struct del_sta_self_rsp_params *sta_self_wmi_rsp;
559 
560 	wma_debug("P2P Device: removing self peer "QDF_MAC_ADDR_FMT,
561 		  QDF_MAC_ADDR_REF(del_vdev_req->self_mac_addr));
562 
563 	if (wmi_service_enabled(wma_handle->wmi_handle,
564 				wmi_service_sync_delete_cmds)) {
565 		sta_self_wmi_rsp =
566 			qdf_mem_malloc(sizeof(struct del_sta_self_rsp_params));
567 		if (!sta_self_wmi_rsp) {
568 			qdf_status = QDF_STATUS_E_NOMEM;
569 			goto error;
570 		}
571 
572 		sta_self_wmi_rsp->self_sta_param = del_vdev_req;
573 		msg = wma_fill_hold_req(wma_handle, vdev_id,
574 					WMA_DELETE_STA_REQ,
575 					WMA_DEL_P2P_SELF_STA_RSP_START,
576 					sta_self_wmi_rsp,
577 					WMA_DELETE_STA_TIMEOUT);
578 		if (!msg) {
579 			wma_err("Failed to allocate request for vdev_id %d",
580 				vdev_id);
581 			wma_remove_req(wma_handle, vdev_id,
582 				       WMA_DEL_P2P_SELF_STA_RSP_START);
583 			qdf_mem_free(sta_self_wmi_rsp);
584 			qdf_status = QDF_STATUS_E_FAILURE;
585 			goto error;
586 		}
587 	}
588 
589 	 qdf_status = wma_remove_peer(wma_handle, del_vdev_req->self_mac_addr,
590 				      vdev_id, false);
591 	if (QDF_IS_STATUS_ERROR(qdf_status)) {
592 		wma_err("wma_remove_peer is failed");
593 		wma_remove_req(wma_handle, vdev_id,
594 			       WMA_DEL_P2P_SELF_STA_RSP_START);
595 		qdf_mem_free(sta_self_wmi_rsp);
596 
597 		goto error;
598 	}
599 
600 error:
601 	return qdf_status;
602 }
603 
604 #ifdef WLAN_FEATURE_DYNAMIC_MAC_ADDR_UPDATE
605 QDF_STATUS wma_p2p_self_peer_remove(struct wlan_objmgr_vdev *vdev)
606 {
607 	struct del_vdev_params *del_self_peer_req;
608 	tp_wma_handle wma_handle = cds_get_context(QDF_MODULE_ID_WMA);
609 	QDF_STATUS status;
610 
611 	if (!wma_handle)
612 		return QDF_STATUS_E_INVAL;
613 
614 	del_self_peer_req = qdf_mem_malloc(sizeof(*del_self_peer_req));
615 	if (!del_self_peer_req)
616 		return QDF_STATUS_E_NOMEM;
617 
618 	del_self_peer_req->vdev = vdev;
619 	del_self_peer_req->vdev_id = wlan_vdev_get_id(vdev);
620 	qdf_mem_copy(del_self_peer_req->self_mac_addr,
621 		     wlan_vdev_mlme_get_macaddr(vdev),
622 		     QDF_MAC_ADDR_SIZE);
623 
624 	status = wma_self_peer_remove(wma_handle, del_self_peer_req);
625 
626 	return status;
627 }
628 #endif
629 
630 void wma_remove_objmgr_peer(tp_wma_handle wma,
631 			    struct wlan_objmgr_vdev *obj_vdev,
632 			    uint8_t *peer_addr)
633 {
634 	struct wlan_objmgr_psoc *psoc;
635 	struct wlan_objmgr_peer *obj_peer;
636 	struct wlan_objmgr_pdev *obj_pdev;
637 	uint8_t pdev_id = 0;
638 
639 	psoc = wma->psoc;
640 	if (!psoc) {
641 		wma_err("PSOC is NULL");
642 		return;
643 	}
644 
645 	obj_pdev = wlan_vdev_get_pdev(obj_vdev);
646 	pdev_id = wlan_objmgr_pdev_get_pdev_id(obj_pdev);
647 	obj_peer = wlan_objmgr_get_peer(psoc, pdev_id, peer_addr,
648 					WLAN_LEGACY_WMA_ID);
649 	if (obj_peer) {
650 		wlan_objmgr_peer_obj_delete(obj_peer);
651 		/* Unref to decrement ref happened in find_peer */
652 		wlan_objmgr_peer_release_ref(obj_peer, WLAN_LEGACY_WMA_ID);
653 	} else {
654 		wma_nofl_err("Peer "QDF_MAC_ADDR_FMT" not found",
655 			 QDF_MAC_ADDR_REF(peer_addr));
656 	}
657 
658 }
659 
660 static QDF_STATUS wma_check_for_deferred_peer_delete(tp_wma_handle wma_handle,
661 						     struct del_vdev_params
662 						     *pdel_vdev_req_param)
663 {
664 	QDF_STATUS status = QDF_STATUS_SUCCESS;
665 	uint8_t vdev_id = pdel_vdev_req_param->vdev_id;
666 	struct wma_txrx_node *iface = &wma_handle->interfaces[vdev_id];
667 	uint32_t vdev_stop_type;
668 
669 	if (qdf_atomic_read(&iface->bss_status) == WMA_BSS_STATUS_STARTED) {
670 		status = mlme_get_vdev_stop_type(iface->vdev, &vdev_stop_type);
671 		if (QDF_IS_STATUS_ERROR(status)) {
672 			wma_err("Failed to get wma req msg_type for vdev_id: %d",
673 				vdev_id);
674 			status = QDF_STATUS_E_INVAL;
675 			return status;
676 		}
677 
678 		if (vdev_stop_type != WMA_DELETE_BSS_REQ) {
679 			status = QDF_STATUS_E_INVAL;
680 			return status;
681 		}
682 
683 		wma_debug("BSS is not yet stopped. Deferring vdev(vdev id %x) deletion",
684 			  vdev_id);
685 		iface->del_staself_req = pdel_vdev_req_param;
686 		iface->is_del_sta_deferred = true;
687 	}
688 
689 	return status;
690 }
691 
692 static QDF_STATUS
693 wma_vdev_self_peer_delete(tp_wma_handle wma_handle,
694 			  struct del_vdev_params *pdel_vdev_req_param)
695 {
696 	QDF_STATUS status = QDF_STATUS_SUCCESS;
697 	uint8_t vdev_id = pdel_vdev_req_param->vdev_id;
698 	struct wma_txrx_node *iface = &wma_handle->interfaces[vdev_id];
699 
700 	if (mlme_vdev_uses_self_peer(iface->type, iface->sub_type)) {
701 		status = wma_self_peer_remove(wma_handle, pdel_vdev_req_param);
702 		if (QDF_IS_STATUS_ERROR(status)) {
703 			wma_err("can't remove selfpeer, send rsp session: %d",
704 				vdev_id);
705 			wma_handle_vdev_detach(wma_handle, pdel_vdev_req_param);
706 			mlme_vdev_self_peer_delete_resp(pdel_vdev_req_param);
707 			cds_trigger_recovery(QDF_SELF_PEER_DEL_FAILED);
708 			return status;
709 		}
710 	} else if (iface->type == WMI_VDEV_TYPE_STA ||
711 		   iface->type == WMI_VDEV_TYPE_NAN) {
712 		wma_remove_objmgr_peer(wma_handle, iface->vdev,
713 				       pdel_vdev_req_param->self_mac_addr);
714 	}
715 
716 	return status;
717 }
718 
719 QDF_STATUS wma_vdev_detach(struct del_vdev_params *pdel_vdev_req_param)
720 {
721 	QDF_STATUS status = QDF_STATUS_SUCCESS;
722 	uint8_t vdev_id;
723 	struct wma_txrx_node *iface = NULL;
724 	tp_wma_handle wma_handle = cds_get_context(QDF_MODULE_ID_WMA);
725 
726 	if (!wma_handle)
727 		return QDF_STATUS_E_INVAL;
728 
729 	vdev_id = wlan_vdev_get_id(pdel_vdev_req_param->vdev);
730 	iface = &wma_handle->interfaces[vdev_id];
731 	if (!iface->vdev) {
732 		wma_err("vdev %d is NULL", vdev_id);
733 		return status;
734 	}
735 
736 	status = wma_check_for_deferred_peer_delete(wma_handle,
737 						    pdel_vdev_req_param);
738 	if (QDF_IS_STATUS_ERROR(status))
739 		goto  send_fail_rsp;
740 
741 	if (iface->is_del_sta_deferred)
742 		return status;
743 
744 	iface->is_del_sta_deferred = false;
745 	iface->del_staself_req = NULL;
746 
747 	status = wma_vdev_self_peer_delete(wma_handle, pdel_vdev_req_param);
748 	if (QDF_IS_STATUS_ERROR(status)) {
749 		wma_err("Failed to send self peer delete:%d", status);
750 		status = QDF_STATUS_E_INVAL;
751 		return status;
752 	}
753 
754 	if (iface->type != WMI_VDEV_TYPE_MONITOR)
755 		iface->vdev_active = false;
756 
757 	if (!mlme_vdev_uses_self_peer(iface->type, iface->sub_type) ||
758 	    !wmi_service_enabled(wma_handle->wmi_handle,
759 	    wmi_service_sync_delete_cmds)) {
760 		status = wma_handle_vdev_detach(wma_handle,
761 						pdel_vdev_req_param);
762 		pdel_vdev_req_param->status = status;
763 		mlme_vdev_self_peer_delete_resp(pdel_vdev_req_param);
764 	}
765 
766 	return status;
767 
768 send_fail_rsp:
769 	wma_err("rcvd del_self_sta without del_bss; vdev_id:%d", vdev_id);
770 	cds_trigger_recovery(QDF_DEL_SELF_STA_FAILED);
771 	status = QDF_STATUS_E_FAILURE;
772 	return status;
773 }
774 
775 /**
776  * wma_send_start_resp() - send vdev start response to upper layer
777  * @wma: wma handle
778  * @add_bss_rsp: add bss params
779  * @rsp: response params
780  *
781  * Return: none
782  */
783 static void wma_send_start_resp(tp_wma_handle wma,
784 				struct add_bss_rsp *add_bss_rsp,
785 				struct vdev_start_response *rsp)
786 {
787 	struct wma_txrx_node *iface = &wma->interfaces[rsp->vdev_id];
788 	QDF_STATUS status;
789 
790 	if (QDF_IS_STATUS_SUCCESS(rsp->status) &&
791 	    QDF_IS_STATUS_SUCCESS(add_bss_rsp->status)) {
792 		status =
793 		  wlan_vdev_mlme_sm_deliver_evt(iface->vdev,
794 						WLAN_VDEV_SM_EV_START_RESP,
795 						sizeof(*add_bss_rsp),
796 						add_bss_rsp);
797 		if (QDF_IS_STATUS_SUCCESS(status))
798 			return;
799 
800 		add_bss_rsp->status = status;
801 	}
802 
803 	/* Send vdev stop if vdev start was success */
804 	if (QDF_IS_STATUS_ERROR(add_bss_rsp->status) &&
805 	    QDF_IS_STATUS_SUCCESS(rsp->status)) {
806 		wlan_vdev_mlme_sm_deliver_evt(iface->vdev,
807 					      WLAN_VDEV_SM_EV_DOWN,
808 					      sizeof(*add_bss_rsp),
809 					      add_bss_rsp);
810 		return;
811 	}
812 
813 	wma_remove_bss_peer_on_failure(wma, rsp->vdev_id);
814 
815 	wma_debug("Sending add bss rsp to umac(vdev %d status %d)",
816 		 rsp->vdev_id, add_bss_rsp->status);
817 	lim_handle_add_bss_rsp(wma->mac_context, add_bss_rsp);
818 }
819 
820 /**
821  * wma_vdev_start_rsp() - send vdev start response to upper layer
822  * @wma: wma handle
823  * @vdev: vdev
824  * @rsp: response params
825  *
826  * Return: none
827  */
828 static void wma_vdev_start_rsp(tp_wma_handle wma, struct wlan_objmgr_vdev *vdev,
829 			       struct vdev_start_response *rsp)
830 {
831 	struct beacon_info *bcn;
832 	enum QDF_OPMODE opmode;
833 	struct add_bss_rsp *add_bss_rsp;
834 
835 	opmode = wlan_vdev_mlme_get_opmode(vdev);
836 
837 	add_bss_rsp = qdf_mem_malloc(sizeof(*add_bss_rsp));
838 	if (!add_bss_rsp)
839 		return;
840 
841 	add_bss_rsp->vdev_id = rsp->vdev_id;
842 	add_bss_rsp->status = rsp->status;
843 	add_bss_rsp->chain_mask = rsp->chain_mask;
844 	add_bss_rsp->smps_mode  = host_map_smps_mode(rsp->smps_mode);
845 
846 	if (rsp->status)
847 		goto send_fail_resp;
848 
849 	if (opmode == QDF_P2P_GO_MODE || opmode == QDF_SAP_MODE) {
850 		wma->interfaces[rsp->vdev_id].beacon =
851 			qdf_mem_malloc(sizeof(struct beacon_info));
852 
853 		bcn = wma->interfaces[rsp->vdev_id].beacon;
854 		if (!bcn) {
855 			add_bss_rsp->status = QDF_STATUS_E_NOMEM;
856 			goto send_fail_resp;
857 		}
858 		bcn->buf = qdf_nbuf_alloc(NULL, SIR_MAX_BEACON_SIZE, 0,
859 					  sizeof(uint32_t), 0);
860 		if (!bcn->buf) {
861 			qdf_mem_free(bcn);
862 			add_bss_rsp->status = QDF_STATUS_E_FAILURE;
863 			goto send_fail_resp;
864 		}
865 		bcn->seq_no = MIN_SW_SEQ;
866 		qdf_spinlock_create(&bcn->lock);
867 		qdf_atomic_set(&wma->interfaces[rsp->vdev_id].bss_status,
868 			       WMA_BSS_STATUS_STARTED);
869 		wma_debug("AP mode (type %d subtype %d) BSS is started",
870 			 wma->interfaces[rsp->vdev_id].type,
871 			 wma->interfaces[rsp->vdev_id].sub_type);
872 	}
873 
874 send_fail_resp:
875 	wma_send_start_resp(wma, add_bss_rsp, rsp);
876 }
877 
878 #ifdef FEATURE_AP_MCC_CH_AVOIDANCE
879 /**
880  * wma_find_mcc_ap() - finds if device is operating AP in MCC mode or not
881  * @wma: wma handle.
882  * @vdev_id: vdev ID of device for which MCC has to be checked
883  * @add: flag indicating if current device is added or deleted
884  *
885  * This function parses through all the interfaces in wma and finds if
886  * any of those devces are in MCC mode with AP. If such a vdev is found
887  * involved AP vdevs are sent WDA_UPDATE_Q2Q_IE_IND msg to update their
888  * beacon template to include Q2Q IE.
889  *
890  * Return: none
891  */
892 static void wma_find_mcc_ap(tp_wma_handle wma, uint8_t vdev_id, bool add)
893 {
894 	uint8_t i;
895 	uint16_t prev_ch_freq = 0;
896 	bool is_ap = false;
897 	bool result = false;
898 	uint8_t *ap_vdev_ids = NULL;
899 	uint8_t num_ch = 0;
900 
901 	ap_vdev_ids = qdf_mem_malloc(wma->max_bssid);
902 	if (!ap_vdev_ids)
903 		return;
904 
905 	for (i = 0; i < wma->max_bssid; i++) {
906 		ap_vdev_ids[i] = -1;
907 		if (add == false && i == vdev_id)
908 			continue;
909 
910 		if (wma_is_vdev_up(vdev_id) || (i == vdev_id && add)) {
911 			if (wma->interfaces[i].type == WMI_VDEV_TYPE_AP) {
912 				is_ap = true;
913 				ap_vdev_ids[i] = i;
914 			}
915 
916 			if (wma->interfaces[i].ch_freq != prev_ch_freq) {
917 				num_ch++;
918 				prev_ch_freq = wma->interfaces[i].ch_freq;
919 			}
920 		}
921 	}
922 
923 	if (is_ap && (num_ch > 1))
924 		result = true;
925 	else
926 		result = false;
927 
928 	wma_send_msg(wma, WMA_UPDATE_Q2Q_IE_IND, (void *)ap_vdev_ids, result);
929 }
930 #endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
931 
932 /**
933  * wma_handle_hidden_ssid_restart() - handle hidden ssid restart
934  * @wma: wma handle
935  * @iface: interface pointer
936  *
937  * Return: none
938  */
939 static void wma_handle_hidden_ssid_restart(tp_wma_handle wma,
940 					   struct wma_txrx_node *iface)
941 {
942 	wlan_vdev_mlme_sm_deliver_evt(iface->vdev,
943 				      WLAN_VDEV_SM_EV_RESTART_RESP,
944 				      0, NULL);
945 }
946 
947 #ifdef WLAN_FEATURE_11BE
948 /**
949  * wma_get_peer_phymode() - get phy mode and eht puncture
950  * @nw_type: wlan type
951  * @old_peer_phymode: old peer phy mode
952  * @vdev_chan: vdev channel
953  * @is_eht: is eht mode
954  * @puncture_bitmap: eht puncture bitmap
955  *
956  * Return: new wlan phy mode
957  */
958 static enum wlan_phymode
959 wma_get_peer_phymode(tSirNwType nw_type, enum wlan_phymode old_peer_phymode,
960 		     struct wlan_channel *vdev_chan, bool *is_eht,
961 		     uint16_t *puncture_bitmap)
962 {
963 	enum wlan_phymode new_phymode;
964 
965 	new_phymode = wma_peer_phymode(nw_type, STA_ENTRY_PEER,
966 				       IS_WLAN_PHYMODE_HT(old_peer_phymode),
967 				       vdev_chan->ch_width,
968 				       IS_WLAN_PHYMODE_VHT(old_peer_phymode),
969 				       IS_WLAN_PHYMODE_HE(old_peer_phymode),
970 				       IS_WLAN_PHYMODE_EHT(old_peer_phymode));
971 	*is_eht = IS_WLAN_PHYMODE_EHT(new_phymode);
972 	if (*is_eht)
973 		*puncture_bitmap = vdev_chan->puncture_bitmap;
974 
975 	return new_phymode;
976 }
977 #else
978 static enum wlan_phymode
979 wma_get_peer_phymode(tSirNwType nw_type, enum wlan_phymode old_peer_phymode,
980 		     struct wlan_channel *vdev_chan, bool *is_eht,
981 		     uint16_t *puncture_bitmap)
982 {
983 	enum wlan_phymode new_phymode;
984 
985 	new_phymode = wma_peer_phymode(nw_type, STA_ENTRY_PEER,
986 				       IS_WLAN_PHYMODE_HT(old_peer_phymode),
987 				       vdev_chan->ch_width,
988 				       IS_WLAN_PHYMODE_VHT(old_peer_phymode),
989 				       IS_WLAN_PHYMODE_HE(old_peer_phymode),
990 				       0);
991 
992 	return new_phymode;
993 }
994 #endif
995 
996 static void wma_peer_send_phymode(struct wlan_objmgr_vdev *vdev,
997 				  void *object, void *arg)
998 {
999 	struct wlan_objmgr_peer *peer = object;
1000 	enum wlan_phymode old_peer_phymode;
1001 	struct wlan_channel *vdev_chan;
1002 	enum wlan_phymode new_phymode;
1003 	tSirNwType nw_type;
1004 	uint32_t fw_phymode;
1005 	uint32_t max_ch_width_supported;
1006 	tp_wma_handle wma;
1007 	uint8_t *peer_mac_addr;
1008 	uint8_t vdev_id;
1009 	bool is_eht = false;
1010 	uint16_t puncture_bitmap = 0;
1011 	uint16_t new_puncture_bitmap = 0;
1012 	uint32_t bw_puncture = 0;
1013 	enum phy_ch_width new_bw;
1014 
1015 	if (wlan_peer_get_peer_type(peer) == WLAN_PEER_SELF)
1016 		return;
1017 
1018 	wma = cds_get_context(QDF_MODULE_ID_WMA);
1019 	if(!wma)
1020 		return;
1021 
1022 	old_peer_phymode = wlan_peer_get_phymode(peer);
1023 	vdev_chan = wlan_vdev_mlme_get_des_chan(vdev);
1024 
1025 	peer_mac_addr = wlan_peer_get_macaddr(peer);
1026 
1027 	if (WLAN_REG_IS_24GHZ_CH_FREQ(vdev_chan->ch_freq)) {
1028 		if (vdev_chan->ch_phymode == WLAN_PHYMODE_11B ||
1029 		    old_peer_phymode == WLAN_PHYMODE_11B)
1030 			nw_type = eSIR_11B_NW_TYPE;
1031 		else
1032 			nw_type = eSIR_11G_NW_TYPE;
1033 	} else {
1034 		nw_type = eSIR_11A_NW_TYPE;
1035 	}
1036 
1037 	new_phymode = wma_get_peer_phymode(nw_type, old_peer_phymode,
1038 					   vdev_chan, &is_eht,
1039 					   &puncture_bitmap);
1040 
1041 	if (!is_eht && new_phymode == old_peer_phymode) {
1042 		wma_debug("Ignore update as old %d and new %d phymode are same for mac "QDF_MAC_ADDR_FMT,
1043 			  old_peer_phymode, new_phymode,
1044 			  QDF_MAC_ADDR_REF(peer_mac_addr));
1045 		return;
1046 	}
1047 	wlan_peer_set_phymode(peer, new_phymode);
1048 
1049 	fw_phymode = wmi_host_to_fw_phymode(new_phymode);
1050 	vdev_id = wlan_vdev_get_id(vdev);
1051 
1052 	max_ch_width_supported =
1053 		wmi_get_ch_width_from_phy_mode(wma->wmi_handle,
1054 					       fw_phymode);
1055 	new_bw =
1056 	target_if_wmi_chan_width_to_phy_ch_width(max_ch_width_supported);
1057 
1058 	if (is_eht) {
1059 		wlan_reg_extract_puncture_by_bw(vdev_chan->ch_width,
1060 						puncture_bitmap,
1061 						vdev_chan->ch_freq,
1062 						vdev_chan->ch_freq_seg2,
1063 						new_bw,
1064 						&new_puncture_bitmap);
1065 		QDF_SET_BITS(bw_puncture, 0, 8, new_bw);
1066 		QDF_SET_BITS(bw_puncture, 8, 16, new_puncture_bitmap);
1067 		wlan_util_vdev_peer_set_param_send(vdev, peer_mac_addr,
1068 						   WLAN_MLME_PEER_BW_PUNCTURE,
1069 						   bw_puncture);
1070 	} else {
1071 		wma_set_peer_param(wma, peer_mac_addr, WMI_HOST_PEER_CHWIDTH,
1072 				   max_ch_width_supported, vdev_id);
1073 	}
1074 
1075 	wma_set_peer_param(wma, peer_mac_addr, WMI_HOST_PEER_PHYMODE,
1076 			   fw_phymode, vdev_id);
1077 	wma_debug("FW phymode %d old phymode %d new phymode %d bw %d punct: 0x%x macaddr " QDF_MAC_ADDR_FMT,
1078 		  fw_phymode, old_peer_phymode, new_phymode,
1079 		  max_ch_width_supported, new_puncture_bitmap,
1080 		  QDF_MAC_ADDR_REF(peer_mac_addr));
1081 }
1082 
1083 static
1084 void wma_update_rate_flags_after_vdev_restart(tp_wma_handle wma,
1085 						struct wma_txrx_node *iface)
1086 {
1087 	struct vdev_mlme_obj *vdev_mlme;
1088 	uint32_t rate_flags = 0;
1089 	enum wlan_phymode bss_phymode;
1090 	struct wlan_channel *des_chan;
1091 
1092 	if (iface->type != WMI_VDEV_TYPE_STA)
1093 		return;
1094 
1095 	vdev_mlme = wlan_vdev_mlme_get_cmpt_obj(iface->vdev);
1096 	if (!vdev_mlme)
1097 		return;
1098 
1099 	des_chan = wlan_vdev_mlme_get_des_chan(iface->vdev);
1100 	bss_phymode = des_chan->ch_phymode;
1101 
1102 	if (wma_is_eht_phymode_supported(bss_phymode)) {
1103 		rate_flags = wma_get_eht_rate_flags(des_chan->ch_width);
1104 	} else if (IS_WLAN_PHYMODE_HE(bss_phymode)) {
1105 		rate_flags = wma_get_he_rate_flags(des_chan->ch_width);
1106 	} else if (IS_WLAN_PHYMODE_VHT(bss_phymode)) {
1107 		rate_flags = wma_get_vht_rate_flags(des_chan->ch_width);
1108 	} else if (IS_WLAN_PHYMODE_HT(bss_phymode)) {
1109 		rate_flags = wma_get_ht_rate_flags(des_chan->ch_width);
1110 	} else {
1111 		rate_flags = TX_RATE_LEGACY;
1112 	}
1113 
1114 	vdev_mlme->mgmt.rate_info.rate_flags = rate_flags;
1115 
1116 	wma_debug("bss phymode %d rate_flags %x, ch_width %d",
1117 		  bss_phymode, rate_flags, des_chan->ch_width);
1118 
1119 	ucfg_mc_cp_stats_set_rate_flags(iface->vdev, rate_flags);
1120 }
1121 
1122 QDF_STATUS wma_handle_channel_switch_resp(tp_wma_handle wma,
1123 					  struct vdev_start_response *rsp)
1124 {
1125 	enum wlan_vdev_sm_evt  event;
1126 	struct wma_txrx_node *iface;
1127 
1128 	iface = &wma->interfaces[rsp->vdev_id];
1129 	wma_debug("Send channel switch resp vdev %d status %d",
1130 		 rsp->vdev_id, rsp->status);
1131 
1132 	/* Indicate channel switch failure to LIM */
1133 	if (QDF_IS_STATUS_ERROR(rsp->status) &&
1134 	    (iface->type == WMI_VDEV_TYPE_MONITOR ||
1135 	     wma_is_vdev_in_ap_mode(wma, rsp->vdev_id) ||
1136 	     mlme_is_chan_switch_in_progress(iface->vdev))) {
1137 		mlme_set_chan_switch_in_progress(iface->vdev, false);
1138 		lim_process_switch_channel_rsp(wma->mac_context, rsp);
1139 		return QDF_STATUS_SUCCESS;
1140 	}
1141 
1142 	if (QDF_IS_STATUS_SUCCESS(rsp->status) &&
1143 	    rsp->resp_type == WMI_VDEV_RESTART_RESP_EVENT) {
1144 		wlan_objmgr_iterate_peerobj_list(iface->vdev,
1145 					 wma_peer_send_phymode, NULL,
1146 					 WLAN_LEGACY_WMA_ID);
1147 		wma_update_rate_flags_after_vdev_restart(wma, iface);
1148 	}
1149 
1150 	if (wma_is_vdev_in_ap_mode(wma, rsp->vdev_id) ||
1151 	    mlme_is_chan_switch_in_progress(iface->vdev))
1152 		event = WLAN_VDEV_SM_EV_RESTART_RESP;
1153 	else
1154 		event = WLAN_VDEV_SM_EV_START_RESP;
1155 	wlan_vdev_mlme_sm_deliver_evt(iface->vdev, event,
1156 				      sizeof(rsp), rsp);
1157 
1158 	return QDF_STATUS_SUCCESS;
1159 }
1160 
1161 #ifdef DCS_INTERFERENCE_DETECTION
1162 /**
1163  * wma_dcs_clear_vdev_starting() - clear vdev starting within dcs information
1164  * @mac_ctx: mac context
1165  * @vdev_id: vdev id
1166  *
1167  * This function is used to clear vdev starting within dcs information
1168  *
1169  * Return: None
1170  */
1171 static void wma_dcs_clear_vdev_starting(struct mac_context *mac_ctx,
1172 					uint32_t vdev_id)
1173 {
1174 	mac_ctx->sap.dcs_info.is_vdev_starting[vdev_id] = false;
1175 }
1176 
1177 /**
1178  * wma_dcs_wlan_interference_mitigation_enable() - enable wlan
1179  * interference mitigation
1180  * @mac_ctx: mac context
1181  * @mac_id: mac id
1182  * @rsp: vdev start response
1183  *
1184  * This function is used to enable wlan interference mitigation through
1185  * send dcs command
1186  *
1187  * Return: None
1188  */
1189 static void wma_dcs_wlan_interference_mitigation_enable(
1190 					struct mac_context *mac_ctx,
1191 					uint32_t mac_id,
1192 					struct vdev_start_response *rsp)
1193 {
1194 	int vdev_index;
1195 	uint32_t list[MAX_NUMBER_OF_CONC_CONNECTIONS];
1196 	uint32_t count;
1197 	bool wlan_interference_mitigation_enable =
1198 			mac_ctx->sap.dcs_info.
1199 			wlan_interference_mitigation_enable[rsp->vdev_id];
1200 
1201 	count = policy_mgr_get_sap_go_count_on_mac(
1202 			mac_ctx->psoc, list, mac_id);
1203 
1204 	for (vdev_index = 0; vdev_index < count; vdev_index++) {
1205 		if (mac_ctx->sap.dcs_info.is_vdev_starting[list[vdev_index]]) {
1206 			wma_err("vdev %d: does not finish restart",
1207 				 list[vdev_index]);
1208 			return;
1209 		}
1210 		wlan_interference_mitigation_enable =
1211 			wlan_interference_mitigation_enable ||
1212 		mac_ctx->sap.dcs_info.
1213 			wlan_interference_mitigation_enable[list[vdev_index]];
1214 	}
1215 
1216 	if (wlan_interference_mitigation_enable)
1217 		ucfg_config_dcs_event_data(mac_ctx->psoc, mac_id, true);
1218 
1219 	if (rsp->resp_type == WMI_HOST_VDEV_START_RESP_EVENT) {
1220 		ucfg_config_dcs_enable(mac_ctx->psoc, mac_id,
1221 				       WLAN_HOST_DCS_WLANIM);
1222 		ucfg_wlan_dcs_cmd(mac_ctx->psoc, mac_id, true);
1223 	}
1224 }
1225 #else
1226 static void wma_dcs_wlan_interference_mitigation_enable(
1227 					struct mac_context *mac_ctx,
1228 					uint32_t mac_id,
1229 					struct vdev_start_response *rsp)
1230 {
1231 }
1232 
1233 
1234 static void wma_dcs_clear_vdev_starting(struct mac_context *mac_ctx,
1235 					uint32_t vdev_id)
1236 {
1237 }
1238 #endif
1239 
1240 /*
1241  * wma_get_ratemask_type() - convert user input ratemask type to FW type
1242  * @type: User input ratemask type maintained in HDD
1243  * @fwtype: Value return arg for fw ratemask type value
1244  *
1245  * Return: FW configurable ratemask type
1246  */
1247 static QDF_STATUS wma_get_ratemask_type(enum wlan_mlme_ratemask_type type,
1248 					uint8_t *fwtype)
1249 {
1250 	switch (type) {
1251 	case WLAN_MLME_RATEMASK_TYPE_CCK:
1252 		*fwtype = WMI_RATEMASK_TYPE_CCK;
1253 		break;
1254 	case WLAN_MLME_RATEMASK_TYPE_HT:
1255 		*fwtype = WMI_RATEMASK_TYPE_HT;
1256 		break;
1257 	case WLAN_MLME_RATEMASK_TYPE_VHT:
1258 		*fwtype = WMI_RATEMASK_TYPE_VHT;
1259 		break;
1260 	case WLAN_MLME_RATEMASK_TYPE_HE:
1261 		*fwtype = WMI_RATEMASK_TYPE_HE;
1262 		break;
1263 	default:
1264 		return QDF_STATUS_E_INVAL;
1265 	}
1266 
1267 	return QDF_STATUS_SUCCESS;
1268 }
1269 
1270 QDF_STATUS wma_vdev_start_resp_handler(struct vdev_mlme_obj *vdev_mlme,
1271 				       struct vdev_start_response *rsp)
1272 {
1273 	tp_wma_handle wma;
1274 	struct wma_txrx_node *iface;
1275 	target_resource_config *wlan_res_cfg;
1276 	struct wlan_objmgr_psoc *psoc;
1277 	struct mac_context *mac_ctx = cds_get_context(QDF_MODULE_ID_PE);
1278 	QDF_STATUS status;
1279 	enum vdev_assoc_type assoc_type = VDEV_ASSOC;
1280 	struct vdev_mlme_obj *mlme_obj;
1281 	struct wlan_mlme_psoc_ext_obj *mlme_psoc_obj;
1282 	const struct wlan_mlme_ratemask *ratemask_cfg;
1283 	struct config_ratemask_params rparams = {0};
1284 
1285 	wma = cds_get_context(QDF_MODULE_ID_WMA);
1286 	if (!wma)
1287 		return QDF_STATUS_E_FAILURE;
1288 
1289 	psoc = wma->psoc;
1290 	if (!psoc) {
1291 		wma_err("psoc is NULL");
1292 		return QDF_STATUS_E_FAILURE;
1293 	}
1294 
1295 	mlme_psoc_obj = mlme_get_psoc_ext_obj(psoc);
1296 	if (!mlme_psoc_obj) {
1297 		wma_err("Failed to get mlme_psoc");
1298 		return QDF_STATUS_E_FAILURE;
1299 	}
1300 
1301 	ratemask_cfg = &mlme_psoc_obj->cfg.ratemask_cfg;
1302 
1303 	if (!mac_ctx) {
1304 		wma_err("Failed to get mac_ctx");
1305 		return QDF_STATUS_E_FAILURE;
1306 	}
1307 
1308 	wlan_res_cfg = lmac_get_tgt_res_cfg(psoc);
1309 	if (!wlan_res_cfg) {
1310 		wma_err("Wlan resource config is NULL");
1311 		return QDF_STATUS_E_FAILURE;
1312 	}
1313 
1314 	if (rsp->vdev_id >= wma->max_bssid) {
1315 		wma_err("Invalid vdev id received from firmware");
1316 		return QDF_STATUS_E_FAILURE;
1317 	}
1318 
1319 	if (wma_is_vdev_in_ap_mode(wma, rsp->vdev_id))
1320 		tgt_dfs_radar_enable(wma->pdev, 0, 0, true);
1321 
1322 	iface = &wma->interfaces[rsp->vdev_id];
1323 	if (!iface->vdev) {
1324 		wma_err("Invalid vdev");
1325 		return QDF_STATUS_E_FAILURE;
1326 	}
1327 
1328 	if (rsp->status == QDF_STATUS_SUCCESS) {
1329 		wma->interfaces[rsp->vdev_id].tx_streams =
1330 			rsp->cfgd_tx_streams;
1331 
1332 		if (wlan_res_cfg->use_pdev_id) {
1333 			if (rsp->mac_id == OL_TXRX_PDEV_ID) {
1334 				wma_err("soc level id received for mac id");
1335 				return -QDF_STATUS_E_INVAL;
1336 			}
1337 			wma->interfaces[rsp->vdev_id].mac_id =
1338 				WMA_PDEV_TO_MAC_MAP(rsp->mac_id);
1339 		} else {
1340 			wma->interfaces[rsp->vdev_id].mac_id =
1341 			rsp->mac_id;
1342 		}
1343 
1344 		wma_debug("vdev:%d tx ss=%d rx ss=%d chain mask=%d mac=%d",
1345 				rsp->vdev_id,
1346 				rsp->cfgd_tx_streams,
1347 				rsp->cfgd_rx_streams,
1348 				rsp->chain_mask,
1349 				wma->interfaces[rsp->vdev_id].mac_id);
1350 
1351 		/* Fill bss_chan after vdev start */
1352 		qdf_mem_copy(iface->vdev->vdev_mlme.bss_chan,
1353 			     iface->vdev->vdev_mlme.des_chan,
1354 			     sizeof(struct wlan_channel));
1355 	}
1356 
1357 	if (wma_is_vdev_in_ap_mode(wma, rsp->vdev_id)) {
1358 		wma_dcs_clear_vdev_starting(mac_ctx, rsp->vdev_id);
1359 		wma_dcs_wlan_interference_mitigation_enable(mac_ctx,
1360 							    iface->mac_id, rsp);
1361 	}
1362 
1363 #ifdef FEATURE_AP_MCC_CH_AVOIDANCE
1364 	if (rsp->status == QDF_STATUS_SUCCESS
1365 		&& mac_ctx->sap.sap_channel_avoidance)
1366 		wma_find_mcc_ap(wma, rsp->vdev_id, true);
1367 #endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
1368 
1369 	if (wma_get_hidden_ssid_restart_in_progress(iface) &&
1370 	    wma_is_vdev_in_ap_mode(wma, rsp->vdev_id)) {
1371 		wma_handle_hidden_ssid_restart(wma, iface);
1372 		return QDF_STATUS_SUCCESS;
1373 	}
1374 
1375 	mlme_obj = wlan_vdev_mlme_get_cmpt_obj(iface->vdev);
1376 	if (!mlme_obj)
1377 		return QDF_STATUS_E_INVAL;
1378 
1379 	mlme_obj->mgmt.generic.tx_pwrlimit = rsp->max_allowed_tx_power;
1380 	wma_debug("Max allowed tx power: %d", rsp->max_allowed_tx_power);
1381 
1382 	if (iface->type == WMI_VDEV_TYPE_STA)
1383 		assoc_type = mlme_get_assoc_type(vdev_mlme->vdev);
1384 
1385 	if (mlme_is_chan_switch_in_progress(iface->vdev) ||
1386 	    iface->type == WMI_VDEV_TYPE_MONITOR ||
1387 	    (iface->type == WMI_VDEV_TYPE_STA &&
1388 	     (assoc_type == VDEV_ASSOC || assoc_type == VDEV_REASSOC))) {
1389 		status = wma_handle_channel_switch_resp(wma,
1390 							rsp);
1391 		if (QDF_IS_STATUS_ERROR(status))
1392 			return QDF_STATUS_E_FAILURE;
1393 	}  else if (iface->type == WMI_VDEV_TYPE_OCB) {
1394 		mlme_obj->proto.sta.assoc_id = iface->aid;
1395 		if (vdev_mgr_up_send(mlme_obj) != QDF_STATUS_SUCCESS) {
1396 			wma_err("failed to send vdev up");
1397 			return QDF_STATUS_E_FAILURE;
1398 		}
1399 		ucfg_ocb_config_channel(wma->pdev);
1400 	} else {
1401 		struct qdf_mac_addr bss_peer;
1402 
1403 		status =
1404 			wlan_vdev_get_bss_peer_mac(iface->vdev, &bss_peer);
1405 		if (QDF_IS_STATUS_ERROR(status)) {
1406 			wma_err("Failed to get bssid");
1407 			return QDF_STATUS_E_INVAL;
1408 		}
1409 		qdf_mem_copy(mlme_obj->mgmt.generic.bssid, bss_peer.bytes,
1410 			     QDF_MAC_ADDR_SIZE);
1411 		wma_vdev_start_rsp(wma, vdev_mlme->vdev, rsp);
1412 	}
1413 	if (iface->type == WMI_VDEV_TYPE_AP && wma_is_vdev_up(rsp->vdev_id))
1414 		wma_set_sap_keepalive(wma, rsp->vdev_id);
1415 
1416 	/* Send ratemask to firmware */
1417 	if ((ratemask_cfg->type > WLAN_MLME_RATEMASK_TYPE_NO_MASK) &&
1418 	    (ratemask_cfg->type < WLAN_MLME_RATEMASK_TYPE_MAX)) {
1419 		struct wmi_unified *wmi_handle = wma->wmi_handle;
1420 
1421 		if (wmi_validate_handle(wmi_handle))
1422 			return QDF_STATUS_E_INVAL;
1423 
1424 		rparams.vdev_id = rsp->vdev_id;
1425 		status = wma_get_ratemask_type(ratemask_cfg->type,
1426 					       &rparams.type);
1427 
1428 		if (QDF_IS_STATUS_ERROR(status)) {
1429 			wma_err(FL("unable to map ratemask"));
1430 			/* don't fail, default rates will still work */
1431 			return QDF_STATUS_SUCCESS;
1432 		}
1433 
1434 		rparams.lower32 = ratemask_cfg->lower32;
1435 		rparams.higher32 = ratemask_cfg->higher32;
1436 		rparams.lower32_2 = ratemask_cfg->lower32_2;
1437 		rparams.higher32_2 = ratemask_cfg->higher32_2;
1438 
1439 		status = wmi_unified_vdev_config_ratemask_cmd_send(wmi_handle,
1440 								   &rparams);
1441 		/* Only log failure. Do not abort */
1442 		if (QDF_IS_STATUS_ERROR(status))
1443 			wma_err(FL("failed to send ratemask"));
1444 	}
1445 
1446 	return QDF_STATUS_SUCCESS;
1447 }
1448 
1449 bool wma_is_vdev_valid(uint32_t vdev_id)
1450 {
1451 	tp_wma_handle wma_handle = cds_get_context(QDF_MODULE_ID_WMA);
1452 
1453 	if (!wma_handle)
1454 		return false;
1455 
1456 	/* No of interface are allocated based on max_bssid value */
1457 	if (vdev_id >= wma_handle->max_bssid) {
1458 		wma_debug("vdev_id: %d is invalid, max_bssid: %d",
1459 			 vdev_id, wma_handle->max_bssid);
1460 		return false;
1461 	}
1462 
1463 	return wma_handle->interfaces[vdev_id].vdev_active;
1464 }
1465 
1466 /**
1467  * wma_vdev_set_param() - set per vdev params in fw
1468  * @wmi_handle: wmi handle
1469  * @if_id: vdev id
1470  * @param_id: parameter id
1471  * @param_value: parameter value
1472  *
1473  * Return: QDF_STATUS_SUCCESS for success or error code
1474  */
1475 QDF_STATUS
1476 wma_vdev_set_param(wmi_unified_t wmi_handle, uint32_t if_id,
1477 				uint32_t param_id, uint32_t param_value)
1478 {
1479 	struct vdev_set_params param = {0};
1480 
1481 	if (!wma_is_vdev_valid(if_id)) {
1482 		wma_err("vdev_id: %d is not active reject the req: param id %d val %d",
1483 			if_id, param_id, param_value);
1484 		return QDF_STATUS_E_INVAL;
1485 	}
1486 
1487 	param.vdev_id = if_id;
1488 	param.param_id = param_id;
1489 	param.param_value = param_value;
1490 
1491 	return wmi_unified_vdev_set_param_send(wmi_handle, &param);
1492 }
1493 
1494 /**
1495  * wma_set_peer_param() - set peer parameter in fw
1496  * @wma_ctx: wma handle
1497  * @peer_addr: peer mac address
1498  * @param_id: parameter id
1499  * @param_value: parameter value
1500  * @vdev_id: vdev id
1501  *
1502  * Return: QDF_STATUS_SUCCESS for success or error code
1503  */
1504 QDF_STATUS wma_set_peer_param(void *wma_ctx, uint8_t *peer_addr,
1505 			      uint32_t param_id, uint32_t param_value,
1506 			      uint32_t vdev_id)
1507 {
1508 	tp_wma_handle wma_handle = (tp_wma_handle) wma_ctx;
1509 	struct peer_set_params param = {0};
1510 	QDF_STATUS status;
1511 
1512 	param.vdev_id = vdev_id;
1513 	param.param_value = param_value;
1514 	param.param_id = param_id;
1515 
1516 	status = wmi_set_peer_param_send(wma_handle->wmi_handle,
1517 					 peer_addr,
1518 					 &param);
1519 	if (QDF_IS_STATUS_ERROR(status))
1520 		wma_err("vdev_id: %d peer set failed, id %d, val %d",
1521 			 vdev_id, param_id, param_value);
1522 	return status;
1523 }
1524 
1525 /**
1526  * wma_peer_unmap_conf_send - send peer unmap conf cmnd to fw
1527  * @wma: wma handle
1528  * @msg: peer unmap conf params
1529  *
1530  * Return: QDF_STATUS
1531  */
1532 QDF_STATUS wma_peer_unmap_conf_send(tp_wma_handle wma,
1533 				    struct send_peer_unmap_conf_params *msg)
1534 {
1535 	QDF_STATUS qdf_status;
1536 
1537 	if (!msg) {
1538 		wma_err("null input params");
1539 		return QDF_STATUS_E_INVAL;
1540 	}
1541 
1542 	qdf_status = wmi_unified_peer_unmap_conf_send(
1543 					wma->wmi_handle,
1544 					msg->vdev_id,
1545 					msg->peer_id_cnt,
1546 					msg->peer_id_list);
1547 
1548 	if (qdf_status != QDF_STATUS_SUCCESS)
1549 		wma_err("peer_unmap_conf_send failed %d", qdf_status);
1550 
1551 	qdf_mem_free(msg->peer_id_list);
1552 	msg->peer_id_list = NULL;
1553 
1554 	return qdf_status;
1555 }
1556 
1557 /**
1558  * wma_peer_unmap_conf_cb - send peer unmap conf cmnd to fw
1559  * @vdev_id: vdev id
1560  * @peer_id_cnt: no of peer id
1561  * @peer_id_list: list of peer ids
1562  *
1563  * Return: QDF_STATUS
1564  */
1565 QDF_STATUS wma_peer_unmap_conf_cb(uint8_t vdev_id,
1566 				  uint32_t peer_id_cnt,
1567 				  uint16_t *peer_id_list)
1568 {
1569 	tp_wma_handle wma = cds_get_context(QDF_MODULE_ID_WMA);
1570 	QDF_STATUS qdf_status;
1571 
1572 	if (!wma)
1573 		return QDF_STATUS_E_INVAL;
1574 
1575 	wma_debug("peer_id_cnt: %d", peer_id_cnt);
1576 	qdf_status = wmi_unified_peer_unmap_conf_send(
1577 						wma->wmi_handle,
1578 						vdev_id, peer_id_cnt,
1579 						peer_id_list);
1580 
1581 	if (qdf_status == QDF_STATUS_E_BUSY) {
1582 		QDF_STATUS retcode;
1583 		struct scheduler_msg msg = {0};
1584 		struct send_peer_unmap_conf_params *peer_unmap_conf_req;
1585 		void *mac_ctx = cds_get_context(QDF_MODULE_ID_PE);
1586 
1587 		wma_debug("post unmap_conf cmd to MC thread");
1588 
1589 		if (!mac_ctx)
1590 			return QDF_STATUS_E_FAILURE;
1591 
1592 		peer_unmap_conf_req = qdf_mem_malloc(sizeof(
1593 					struct send_peer_unmap_conf_params));
1594 
1595 		if (!peer_unmap_conf_req)
1596 			return QDF_STATUS_E_NOMEM;
1597 
1598 		peer_unmap_conf_req->vdev_id = vdev_id;
1599 		peer_unmap_conf_req->peer_id_cnt = peer_id_cnt;
1600 		peer_unmap_conf_req->peer_id_list =  qdf_mem_malloc(
1601 					sizeof(uint16_t) * peer_id_cnt);
1602 		if (!peer_unmap_conf_req->peer_id_list) {
1603 			qdf_mem_free(peer_unmap_conf_req);
1604 			peer_unmap_conf_req = NULL;
1605 			return QDF_STATUS_E_NOMEM;
1606 		}
1607 		qdf_mem_copy(peer_unmap_conf_req->peer_id_list,
1608 			     peer_id_list, sizeof(uint16_t) * peer_id_cnt);
1609 
1610 		msg.type = WMA_SEND_PEER_UNMAP_CONF;
1611 		msg.reserved = 0;
1612 		msg.bodyptr = peer_unmap_conf_req;
1613 		msg.bodyval = 0;
1614 
1615 		retcode = wma_post_ctrl_msg(mac_ctx, &msg);
1616 		if (retcode != QDF_STATUS_SUCCESS) {
1617 			wma_err("wma_post_ctrl_msg failed");
1618 			qdf_mem_free(peer_unmap_conf_req->peer_id_list);
1619 			qdf_mem_free(peer_unmap_conf_req);
1620 			return QDF_STATUS_E_FAILURE;
1621 		}
1622 	}
1623 
1624 	return qdf_status;
1625 }
1626 
1627 bool wma_objmgr_peer_exist(tp_wma_handle wma,
1628 			   uint8_t *peer_addr, uint8_t *peer_vdev_id)
1629 {
1630 	struct wlan_objmgr_peer *peer;
1631 
1632 	if (!peer_addr ||
1633 	    qdf_is_macaddr_zero((struct qdf_mac_addr *)peer_addr))
1634 		return false;
1635 
1636 	peer = wlan_objmgr_get_peer_by_mac(wma->psoc, peer_addr,
1637 					   WLAN_LEGACY_WMA_ID);
1638 	if (!peer)
1639 		return false;
1640 
1641 	if (peer_vdev_id)
1642 		*peer_vdev_id = wlan_vdev_get_id(wlan_peer_get_vdev(peer));
1643 
1644 	wlan_objmgr_peer_release_ref(peer, WLAN_LEGACY_WMA_ID);
1645 
1646 	return true;
1647 }
1648 
1649 #ifdef WLAN_FEATURE_PEER_TRANS_HIST
1650 void wma_peer_tbl_trans_add_entry(struct wlan_objmgr_peer *peer, bool is_create,
1651 				  struct cdp_peer_setup_info *peer_info)
1652 {
1653 	QDF_STATUS status;
1654 	struct wlan_objmgr_vdev *vdev;
1655 	struct wlan_objmgr_psoc *psoc;
1656 	struct wlan_peer_tbl_trans_entry *peer_trans_entry;
1657 	uint8_t *peer_mac, *peer_mld;
1658 
1659 	vdev = wlan_peer_get_vdev(peer);
1660 	if (!vdev)
1661 		return;
1662 
1663 	psoc = wlan_vdev_get_psoc(vdev);
1664 	if (!psoc)
1665 		return;
1666 
1667 	peer_trans_entry = qdf_mem_malloc(sizeof(*peer_trans_entry));
1668 	if (!peer_trans_entry)
1669 		return;
1670 
1671 	peer_trans_entry->ts = qdf_get_log_timestamp();
1672 	peer_trans_entry->vdev_id = wlan_vdev_get_id(vdev);
1673 	peer_trans_entry->opmode = wlan_vdev_mlme_get_opmode(vdev);
1674 
1675 	peer_mac = wlan_peer_get_macaddr(peer);
1676 	peer_mld = wlan_peer_mlme_get_mldaddr(peer);
1677 	qdf_ether_addr_copy(&peer_trans_entry->peer_addr.bytes[0], peer_mac);
1678 	if (peer_mld) {
1679 		qdf_ether_addr_copy(&peer_trans_entry->peer_mld_addr.bytes[0],
1680 				    peer_mld);
1681 	}
1682 
1683 	peer_trans_entry->is_mlo = wlan_vdev_mlme_is_mlo_vdev(vdev);
1684 	peer_trans_entry->is_mlo_link = wlan_vdev_mlme_is_mlo_link_vdev(vdev);
1685 
1686 	if (wlan_cm_is_vdev_roam_sync_inprogress(vdev)) {
1687 		peer_trans_entry->peer_flags |= WLAN_PEER_TBL_TRANS_ROAM;
1688 		peer_trans_entry->auth_status =
1689 				wlan_cm_check_mlo_roam_auth_status(vdev);
1690 		peer_trans_entry->num_roam_links = mlo_mgr_num_roam_links(vdev);
1691 	} else if (wlan_vdev_mlme_is_mlo_link_switch_in_progress(vdev)) {
1692 		peer_trans_entry->peer_flags |= WLAN_PEER_TBL_TRANS_LINK_SWITCH;
1693 	} else if (is_create) {
1694 		peer_trans_entry->peer_flags |= WLAN_PEER_TBL_TRANS_CONNECT;
1695 	} else {
1696 		peer_trans_entry->peer_flags |= WLAN_PEER_TBL_TRANS_DISCONNECT;
1697 	}
1698 
1699 	if (is_create) {
1700 		peer_trans_entry->peer_flags |= WLAN_PEER_TBL_TRANS_CREATE;
1701 		peer_trans_entry->is_primary = peer_info->is_primary_link;
1702 		peer_trans_entry->is_first_link = peer_info->is_first_link;
1703 	} else {
1704 		peer_trans_entry->peer_flags |= WLAN_PEER_TBL_TRANS_DESTROY;
1705 	}
1706 
1707 	status = wlan_mlme_psoc_peer_tbl_trans_add_entry(psoc,
1708 							 peer_trans_entry);
1709 	if (QDF_IS_STATUS_ERROR(status))
1710 		qdf_mem_free(peer_trans_entry);
1711 }
1712 #endif
1713 
1714 /**
1715  * wma_remove_peer() - remove peer information from host driver and fw
1716  * @wma: wma handle
1717  * @mac_addr: peer mac address, to be removed
1718  * @vdev_id: vdev id
1719  * @no_fw_peer_delete: If true dont send peer delete to firmware
1720  *
1721  * Return: QDF_STATUS
1722  */
1723 QDF_STATUS wma_remove_peer(tp_wma_handle wma, uint8_t *mac_addr,
1724 			   uint8_t vdev_id, bool no_fw_peer_delete)
1725 {
1726 #define PEER_ALL_TID_BITMASK 0xffffffff
1727 	uint32_t peer_tid_bitmap = PEER_ALL_TID_BITMASK;
1728 	uint8_t *peer_addr = mac_addr;
1729 	uint8_t peer_mac[QDF_MAC_ADDR_SIZE] = {0};
1730 	struct peer_flush_params param = {0};
1731 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
1732 	QDF_STATUS qdf_status = QDF_STATUS_SUCCESS;
1733 	uint32_t bitmap = 1 << CDP_PEER_DELETE_NO_SPECIAL;
1734 	bool peer_unmap_conf_support_enabled;
1735 	uint8_t peer_vdev_id;
1736 	struct peer_delete_cmd_params del_param = {0};
1737 	struct wma_txrx_node *iface;
1738 	struct wlan_objmgr_peer *peer;
1739 
1740 	if (vdev_id >= WLAN_MAX_VDEVS) {
1741 		wma_err("Invalid vdev_id %d", vdev_id);
1742 		QDF_BUG(0);
1743 		return QDF_STATUS_E_INVAL;
1744 	}
1745 
1746 	iface = &wma->interfaces[vdev_id];
1747 	if (!iface->peer_count) {
1748 		wma_err("Can't remove peer with peer_addr "QDF_MAC_ADDR_FMT" vdevid %d peer_count %d",
1749 			QDF_MAC_ADDR_REF(peer_addr), vdev_id,
1750 			iface->peer_count);
1751 		QDF_ASSERT(0);
1752 		return QDF_STATUS_E_INVAL;
1753 	}
1754 
1755 	if (!soc) {
1756 		QDF_BUG(0);
1757 		return QDF_STATUS_E_INVAL;
1758 	}
1759 
1760 	peer = wlan_objmgr_get_peer_by_mac(wma->psoc, peer_addr,
1761 					   WLAN_LEGACY_WMA_ID);
1762 	if (!peer) {
1763 		wma_err("peer doesn't exist peer_addr "QDF_MAC_ADDR_FMT" vdevid %d peer_count %d",
1764 			 QDF_MAC_ADDR_REF(peer_addr), vdev_id,
1765 			 iface->peer_count);
1766 		return QDF_STATUS_E_INVAL;
1767 	}
1768 
1769 	peer_vdev_id = wlan_vdev_get_id(wlan_peer_get_vdev(peer));
1770 	if (peer_vdev_id != vdev_id) {
1771 		wma_err("peer "QDF_MAC_ADDR_FMT" is on vdev id %d but delete req on vdevid %d peer_count %d",
1772 			 QDF_MAC_ADDR_REF(peer_addr), peer_vdev_id, vdev_id,
1773 			 iface->peer_count);
1774 		wlan_objmgr_peer_release_ref(peer, WLAN_LEGACY_WMA_ID);
1775 		return QDF_STATUS_E_INVAL;
1776 	}
1777 
1778 	wma_peer_tbl_trans_add_entry(peer, false, NULL);
1779 	peer_unmap_conf_support_enabled =
1780 				cdp_cfg_get_peer_unmap_conf_support(soc);
1781 
1782 	cdp_peer_teardown(soc, vdev_id, peer_addr);
1783 
1784 	if (no_fw_peer_delete)
1785 		goto peer_detach;
1786 
1787 	/* Flush all TIDs except MGMT TID for this peer in Target */
1788 	peer_tid_bitmap &= ~(0x1 << WMI_MGMT_TID);
1789 	param.peer_tid_bitmap = peer_tid_bitmap;
1790 	param.vdev_id = vdev_id;
1791 	if (!wmi_service_enabled(wma->wmi_handle,
1792 				 wmi_service_peer_delete_no_peer_flush_tids_cmd))
1793 		wmi_unified_peer_flush_tids_send(wma->wmi_handle, mac_addr,
1794 						 &param);
1795 
1796 	/* peer->ref_cnt is not visible in WMA */
1797 	wlan_roam_debug_log(vdev_id, DEBUG_PEER_DELETE_SEND,
1798 			    DEBUG_INVALID_PEER_ID, peer_addr, NULL,
1799 			    0, 0);
1800 
1801 	del_param.vdev_id = vdev_id;
1802 	del_param.is_mlo_link_switch =
1803 		wlan_vdev_mlme_is_mlo_link_switch_in_progress(iface->vdev);
1804 	qdf_status = wmi_unified_peer_delete_send(wma->wmi_handle, peer_addr,
1805 						  &del_param);
1806 	if (QDF_IS_STATUS_ERROR(qdf_status)) {
1807 		wma_err("Peer delete could not be sent to firmware %d",
1808 			qdf_status);
1809 		/* Clear default bit and set to NOT_START_UNMAP */
1810 		bitmap = 1 << CDP_PEER_DO_NOT_START_UNMAP_TIMER;
1811 		qdf_status = QDF_STATUS_E_FAILURE;
1812 	}
1813 
1814 peer_detach:
1815 	wma_debug("vdevid %d is detaching with peer_addr "QDF_MAC_ADDR_FMT" peer_count %d",
1816 		vdev_id, QDF_MAC_ADDR_REF(peer_addr), iface->peer_count);
1817 	/* Copy peer mac to find and delete objmgr peer */
1818 	qdf_mem_copy(peer_mac, peer_addr, QDF_MAC_ADDR_SIZE);
1819 	if (no_fw_peer_delete &&
1820 	    is_cdp_peer_detach_force_delete_supported(soc)) {
1821 		if (!peer_unmap_conf_support_enabled) {
1822 			wma_debug("LFR3: trigger force delete for peer "QDF_MAC_ADDR_FMT,
1823 				 QDF_MAC_ADDR_REF(peer_addr));
1824 			cdp_peer_detach_force_delete(soc, vdev_id, peer_addr);
1825 		} else {
1826 			cdp_peer_delete_sync(soc, vdev_id, peer_addr,
1827 					     wma_peer_unmap_conf_cb,
1828 					     bitmap);
1829 		}
1830 	} else {
1831 		if (no_fw_peer_delete)
1832 			wma_debug("LFR3: Delete the peer "QDF_MAC_ADDR_FMT,
1833 				  QDF_MAC_ADDR_REF(peer_addr));
1834 
1835 		if (peer_unmap_conf_support_enabled)
1836 			cdp_peer_delete_sync(soc, vdev_id, peer_addr,
1837 					     wma_peer_unmap_conf_cb,
1838 					     bitmap);
1839 		else
1840 			cdp_peer_delete(soc, vdev_id, peer_addr, bitmap);
1841 	}
1842 
1843 	wlan_objmgr_peer_release_ref(peer, WLAN_LEGACY_WMA_ID);
1844 	wlan_release_peer_key_wakelock(wma->pdev, peer_mac);
1845 	wma_remove_objmgr_peer(wma, iface->vdev, peer_mac);
1846 
1847 	iface->peer_count--;
1848 #undef PEER_ALL_TID_BITMASK
1849 
1850 	return qdf_status;
1851 }
1852 
1853 /**
1854  * wma_get_obj_mgr_peer_type() - Determine the type of peer(eg. STA/AP)
1855  * @wma: wma handle
1856  * @vdev_id: vdev id
1857  * @peer_addr: peer mac address
1858  * @wma_peer_type: wma peer type
1859  *
1860  * Return: Peer type
1861  */
1862 static int wma_get_obj_mgr_peer_type(tp_wma_handle wma, uint8_t vdev_id,
1863 				     uint8_t *peer_addr, uint32_t wma_peer_type)
1864 
1865 {
1866 	uint32_t obj_peer_type = 0;
1867 	struct wlan_objmgr_vdev *vdev;
1868 	uint8_t *addr;
1869 	uint8_t *mld_addr;
1870 
1871 	vdev = wma->interfaces[vdev_id].vdev;
1872 	if (!vdev) {
1873 		wma_err("Couldn't find vdev for VDEV_%d", vdev_id);
1874 		return obj_peer_type;
1875 	}
1876 	addr = wlan_vdev_mlme_get_macaddr(vdev);
1877 	mld_addr = wlan_vdev_mlme_get_mldaddr(vdev);
1878 
1879 	if (wma_peer_type == WMI_PEER_TYPE_TDLS)
1880 		return WLAN_PEER_TDLS;
1881 
1882 	if (wma_peer_type == WMI_PEER_TYPE_PASN)
1883 		return WLAN_PEER_RTT_PASN;
1884 
1885 	if (!qdf_mem_cmp(addr, peer_addr, QDF_MAC_ADDR_SIZE) ||
1886 	    !qdf_mem_cmp(mld_addr, peer_addr, QDF_MAC_ADDR_SIZE)) {
1887 		obj_peer_type = WLAN_PEER_SELF;
1888 	} else if (wma->interfaces[vdev_id].type == WMI_VDEV_TYPE_STA) {
1889 		if (wma->interfaces[vdev_id].sub_type ==
1890 					WMI_UNIFIED_VDEV_SUBTYPE_P2P_CLIENT)
1891 			obj_peer_type = WLAN_PEER_P2P_GO;
1892 		else
1893 			obj_peer_type = WLAN_PEER_AP;
1894 	} else if (wma->interfaces[vdev_id].type == WMI_VDEV_TYPE_AP) {
1895 			obj_peer_type = WLAN_PEER_STA;
1896 	} else if (wma->interfaces[vdev_id].type == WMI_VDEV_TYPE_IBSS) {
1897 		obj_peer_type = WLAN_PEER_IBSS;
1898 	} else if (wma->interfaces[vdev_id].type == WMI_VDEV_TYPE_NDI) {
1899 		obj_peer_type = WLAN_PEER_NDP;
1900 	} else {
1901 		wma_err("Couldn't find peertype for type %d and sub type %d",
1902 			 wma->interfaces[vdev_id].type,
1903 			 wma->interfaces[vdev_id].sub_type);
1904 	}
1905 
1906 	return obj_peer_type;
1907 
1908 }
1909 
1910 #ifdef WLAN_FEATURE_11BE_MLO
1911 static QDF_STATUS
1912 wma_create_peer_validate_mld_address(tp_wma_handle wma,
1913 				     uint8_t *peer_mld_addr,
1914 				     struct wlan_objmgr_vdev *vdev)
1915 {
1916 	uint8_t peer_vdev_id, vdev_id;
1917 	struct wlan_objmgr_vdev *dup_vdev;
1918 	QDF_STATUS status = QDF_STATUS_SUCCESS;
1919 	struct wlan_objmgr_psoc *psoc = wma->psoc;
1920 
1921 	vdev_id = wlan_vdev_get_id(vdev);
1922 	/* Check if the @peer_mld_addr matches any other
1923 	 * peer's link address.
1924 	 * We may find a match if one of the peers added
1925 	 * has same MLD and link, in such case check if
1926 	 * both are in same ML dev context.
1927 	 */
1928 	if (wma_objmgr_peer_exist(wma, peer_mld_addr, &peer_vdev_id)) {
1929 		if (peer_vdev_id != vdev_id) {
1930 			dup_vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
1931 						psoc, peer_vdev_id,
1932 						WLAN_LEGACY_WMA_ID);
1933 			if (!dup_vdev)
1934 				return QDF_STATUS_E_INVAL;
1935 
1936 			/* If ML dev context is NULL then the matching
1937 			 * peer exist on non ML VDEV, so reject the peer.
1938 			 */
1939 			if (!dup_vdev->mlo_dev_ctx) {
1940 				wlan_objmgr_vdev_release_ref(
1941 						dup_vdev, WLAN_LEGACY_WMA_ID);
1942 				return QDF_STATUS_E_ALREADY;
1943 			} else if (dup_vdev->mlo_dev_ctx != vdev->mlo_dev_ctx) {
1944 				wma_debug("Peer " QDF_MAC_ADDR_FMT " already exists on vdev %d, current vdev %d",
1945 					  QDF_MAC_ADDR_REF(peer_mld_addr),
1946 					  peer_vdev_id, vdev_id);
1947 				wlan_objmgr_vdev_release_ref(
1948 						dup_vdev, WLAN_LEGACY_WMA_ID);
1949 				status = QDF_STATUS_E_ALREADY;
1950 			} else {
1951 				wlan_objmgr_vdev_release_ref(
1952 						dup_vdev, WLAN_LEGACY_WMA_ID);
1953 				wma_debug("Allow ML peer on same ML dev context");
1954 				status = QDF_STATUS_SUCCESS;
1955 			}
1956 		} else {
1957 			wma_debug("ML Peer exists on same VDEV %d", vdev_id);
1958 			status = QDF_STATUS_E_ALREADY;
1959 		}
1960 	} else if (mlo_mgr_ml_peer_exist_on_diff_ml_ctx(peer_mld_addr,
1961 							&vdev_id)) {
1962 		/* Reject if MLD exists on different ML dev context,
1963 		 */
1964 		wma_debug("ML Peer " QDF_MAC_ADDR_FMT " already exists on different ML dev context",
1965 			  QDF_MAC_ADDR_REF(peer_mld_addr));
1966 		status = QDF_STATUS_E_ALREADY;
1967 	}
1968 
1969 	return status;
1970 }
1971 #else
1972 static QDF_STATUS
1973 wma_create_peer_validate_mld_address(tp_wma_handle wma,
1974 				     uint8_t *peer_mld_addr,
1975 				     struct wlan_objmgr_vdev *vdev)
1976 {
1977 	return QDF_STATUS_SUCCESS;
1978 }
1979 #endif
1980 
1981 struct wlan_objmgr_peer *wma_create_objmgr_peer(tp_wma_handle wma,
1982 						uint8_t vdev_id,
1983 						uint8_t *peer_addr,
1984 						uint32_t wma_peer_type,
1985 						uint8_t *peer_mld_addr)
1986 {
1987 	QDF_STATUS status;
1988 	uint8_t peer_vdev_id;
1989 	uint32_t obj_peer_type;
1990 	struct wlan_objmgr_vdev *obj_vdev;
1991 	struct wlan_objmgr_peer *obj_peer = NULL;
1992 	struct wlan_objmgr_psoc *psoc = wma->psoc;
1993 
1994 	obj_vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
1995 							WLAN_LEGACY_WMA_ID);
1996 
1997 	if (!obj_vdev) {
1998 		wma_err("Invalid obj vdev. Unable to create peer");
1999 		return NULL;
2000 	}
2001 
2002 	/*
2003 	 * Check if peer with same MAC exist on any Vdev, If so avoid
2004 	 * adding this peer.
2005 	 */
2006 	if (wma_objmgr_peer_exist(wma, peer_addr, &peer_vdev_id)) {
2007 		wma_debug("Peer " QDF_MAC_ADDR_FMT " already exists on vdev %d, current vdev %d",
2008 			  QDF_MAC_ADDR_REF(peer_addr), peer_vdev_id, vdev_id);
2009 		goto vdev_ref;
2010 	}
2011 
2012 	/* Reject if same MAC exists on different ML dev context */
2013 	if (mlo_mgr_ml_peer_exist_on_diff_ml_ctx(peer_addr,
2014 						 &vdev_id)) {
2015 		wma_debug("Peer " QDF_MAC_ADDR_FMT " already exists on different ML dev context",
2016 			  QDF_MAC_ADDR_REF(peer_addr));
2017 		goto vdev_ref;
2018 	}
2019 
2020 	status = wma_create_peer_validate_mld_address(wma, peer_mld_addr,
2021 						      obj_vdev);
2022 	if (QDF_IS_STATUS_ERROR(status)) {
2023 		wma_debug("MLD " QDF_MAC_ADDR_FMT " matches with peer on different MLD context",
2024 			  QDF_MAC_ADDR_REF(peer_mld_addr));
2025 		goto vdev_ref;
2026 	}
2027 
2028 	obj_peer_type = wma_get_obj_mgr_peer_type(wma, vdev_id, peer_addr,
2029 						  wma_peer_type);
2030 	if (!obj_peer_type) {
2031 		wma_err("Invalid obj peer type. Unable to create peer %d",
2032 			obj_peer_type);
2033 		goto vdev_ref;
2034 	}
2035 
2036 	/* Create obj_mgr peer */
2037 	obj_peer = wlan_objmgr_peer_obj_create(obj_vdev, obj_peer_type,
2038 						peer_addr);
2039 
2040 vdev_ref:
2041 	wlan_objmgr_vdev_release_ref(obj_vdev, WLAN_LEGACY_WMA_ID);
2042 
2043 	return obj_peer;
2044 
2045 }
2046 
2047 /**
2048  * wma_increment_peer_count() - Increment the vdev peer
2049  * count
2050  * @wma: wma handle
2051  * @vdev_id: vdev id
2052  *
2053  * Return: None
2054  */
2055 static void
2056 wma_increment_peer_count(tp_wma_handle wma, uint8_t vdev_id)
2057 {
2058 	wma->interfaces[vdev_id].peer_count++;
2059 }
2060 
2061 /**
2062  * wma_update_mlo_peer_create() - update mlo parameter for peer creation
2063  * @param: peer create param
2064  * @mlo_enable: mlo enable or not
2065  *
2066  * Return: Void
2067  */
2068 #ifdef WLAN_FEATURE_11BE_MLO
2069 static void wma_update_mlo_peer_create(struct peer_create_params *param,
2070 				       bool mlo_enable)
2071 {
2072 	param->mlo_enabled = mlo_enable;
2073 }
2074 #else
2075 static void wma_update_mlo_peer_create(struct peer_create_params *param,
2076 				       bool mlo_enable)
2077 {
2078 }
2079 #endif
2080 
2081 /**
2082  * wma_add_peer() - send peer create command to fw
2083  * @wma: wma handle
2084  * @peer_addr: peer mac addr
2085  * @peer_type: peer type
2086  * @vdev_id: vdev id
2087  * @peer_mld_addr: peer mld addr
2088  * @is_assoc_peer: is assoc peer or not
2089  *
2090  * Return: QDF status
2091  */
2092 static
2093 QDF_STATUS wma_add_peer(tp_wma_handle wma,
2094 			uint8_t peer_addr[QDF_MAC_ADDR_SIZE],
2095 			uint32_t peer_type, uint8_t vdev_id,
2096 			uint8_t peer_mld_addr[QDF_MAC_ADDR_SIZE],
2097 			bool is_assoc_peer)
2098 {
2099 	struct peer_create_params param = {0};
2100 	void *dp_soc = cds_get_context(QDF_MODULE_ID_SOC);
2101 	struct wlan_objmgr_psoc *psoc = wma->psoc;
2102 	target_resource_config *wlan_res_cfg;
2103 	struct wlan_objmgr_peer *obj_peer = NULL;
2104 	QDF_STATUS status;
2105 
2106 	if (!psoc) {
2107 		wma_err("psoc is NULL");
2108 		return QDF_STATUS_E_INVAL;
2109 	}
2110 
2111 	wlan_res_cfg = lmac_get_tgt_res_cfg(psoc);
2112 	if (!wlan_res_cfg) {
2113 		wma_err("psoc target res cfg is null");
2114 		return QDF_STATUS_E_INVAL;
2115 	}
2116 
2117 	if (wma->interfaces[vdev_id].peer_count >=
2118 	    wlan_res_cfg->num_peers) {
2119 		wma_err("the peer count exceeds the limit %d",
2120 			 wma->interfaces[vdev_id].peer_count);
2121 		return QDF_STATUS_E_FAILURE;
2122 	}
2123 
2124 	if (!dp_soc)
2125 		return QDF_STATUS_E_FAILURE;
2126 
2127 	if (qdf_is_macaddr_group((struct qdf_mac_addr *)peer_addr) ||
2128 	    qdf_is_macaddr_zero((struct qdf_mac_addr *)peer_addr)) {
2129 		wma_err("Invalid peer address received reject it");
2130 		return QDF_STATUS_E_FAILURE;
2131 	}
2132 
2133 	obj_peer = wma_create_objmgr_peer(wma, vdev_id, peer_addr, peer_type,
2134 					  peer_mld_addr);
2135 	if (!obj_peer)
2136 		return QDF_STATUS_E_FAILURE;
2137 
2138 	/* The peer object should be created before sending the WMI peer
2139 	 * create command to firmware. This is to prevent a race condition
2140 	 * where the HTT peer map event is received before the peer object
2141 	 * is created in the data path
2142 	 */
2143 	if (peer_mld_addr &&
2144 	    !qdf_is_macaddr_zero((struct qdf_mac_addr *)peer_mld_addr)) {
2145 		wlan_peer_mlme_flag_ext_set(obj_peer, WLAN_PEER_FEXT_MLO);
2146 		wma_debug("peer " QDF_MAC_ADDR_FMT "is_assoc_peer%d mld mac " QDF_MAC_ADDR_FMT,
2147 			  QDF_MAC_ADDR_REF(peer_addr), is_assoc_peer,
2148 			  QDF_MAC_ADDR_REF(peer_mld_addr));
2149 		wlan_peer_mlme_set_mldaddr(obj_peer, peer_mld_addr);
2150 		wlan_peer_mlme_set_assoc_peer(obj_peer, is_assoc_peer);
2151 		wma_update_mlo_peer_create(&param, true);
2152 	}
2153 	status = cdp_peer_create(dp_soc, vdev_id, peer_addr);
2154 	if (QDF_IS_STATUS_ERROR(status)) {
2155 		wma_err("Unable to attach peer "QDF_MAC_ADDR_FMT,
2156 			QDF_MAC_ADDR_REF(peer_addr));
2157 		wlan_objmgr_peer_obj_delete(obj_peer);
2158 		return QDF_STATUS_E_FAILURE;
2159 	}
2160 
2161 	if (peer_type == WMI_PEER_TYPE_TDLS)
2162 		cdp_peer_set_peer_as_tdls(dp_soc, vdev_id, peer_addr, true);
2163 
2164 	if (wlan_cm_is_roam_sync_in_progress(wma->psoc, vdev_id) ||
2165 	    MLME_IS_MLO_ROAM_SYNCH_IN_PROGRESS(wma->psoc, vdev_id)) {
2166 		wma_debug("LFR3: Created peer "QDF_MAC_ADDR_FMT" vdev_id %d, peer_count %d",
2167 			 QDF_MAC_ADDR_REF(peer_addr), vdev_id,
2168 			 wma->interfaces[vdev_id].peer_count + 1);
2169 		return QDF_STATUS_SUCCESS;
2170 	}
2171 	param.peer_addr = peer_addr;
2172 	param.peer_type = peer_type;
2173 	param.vdev_id = vdev_id;
2174 	if (wmi_unified_peer_create_send(wma->wmi_handle,
2175 					 &param) != QDF_STATUS_SUCCESS) {
2176 		wma_err("Unable to create peer in Target");
2177 		if (cdp_cfg_get_peer_unmap_conf_support(dp_soc))
2178 			cdp_peer_delete_sync(
2179 				dp_soc, vdev_id, peer_addr,
2180 				wma_peer_unmap_conf_cb,
2181 				1 << CDP_PEER_DO_NOT_START_UNMAP_TIMER);
2182 		else
2183 			cdp_peer_delete(
2184 				dp_soc, vdev_id, peer_addr,
2185 				1 << CDP_PEER_DO_NOT_START_UNMAP_TIMER);
2186 		wlan_objmgr_peer_obj_delete(obj_peer);
2187 
2188 		return QDF_STATUS_E_FAILURE;
2189 	}
2190 
2191 	wma_debug("Created peer peer_addr "QDF_MAC_ADDR_FMT" vdev_id %d, peer_count - %d",
2192 		  QDF_MAC_ADDR_REF(peer_addr), vdev_id,
2193 		  wma->interfaces[vdev_id].peer_count + 1);
2194 
2195 	wlan_roam_debug_log(vdev_id, DEBUG_PEER_CREATE_SEND,
2196 			    DEBUG_INVALID_PEER_ID, peer_addr, NULL, 0, 0);
2197 
2198 	return QDF_STATUS_SUCCESS;
2199 }
2200 
2201 #ifdef WLAN_FEATURE_11BE_MLO
2202 static void wma_peer_setup_fill_info(struct wlan_objmgr_psoc *psoc,
2203 				     struct wlan_objmgr_peer *peer,
2204 				     struct cdp_peer_setup_info *peer_info)
2205 {
2206 	uint8_t vdev_id = wlan_vdev_get_id(wlan_peer_get_vdev(peer));
2207 
2208 	peer_info->mld_peer_mac = wlan_peer_mlme_get_mldaddr(peer);
2209 	if (MLME_IS_MLO_ROAM_SYNCH_IN_PROGRESS(psoc, vdev_id) &&
2210 	    wlan_vdev_mlme_get_is_mlo_link(psoc, vdev_id)) {
2211 		peer_info->is_first_link = true;
2212 		peer_info->is_primary_link = false;
2213 	} else if (wlan_cm_is_roam_sync_in_progress(psoc, vdev_id) &&
2214 		   wlan_vdev_mlme_get_is_mlo_vdev(psoc, vdev_id)) {
2215 		if (mlo_get_single_link_ml_roaming(psoc, vdev_id)) {
2216 			peer_info->is_first_link = true;
2217 			peer_info->is_primary_link = true;
2218 		} else {
2219 			peer_info->is_first_link = false;
2220 			peer_info->is_primary_link = true;
2221 		}
2222 	} else {
2223 		peer_info->is_first_link = wlan_peer_mlme_is_assoc_peer(peer);
2224 		peer_info->is_primary_link = peer_info->is_first_link;
2225 	}
2226 }
2227 
2228 /**
2229  * wma_cdp_peer_setup() - provide mlo information to cdp_peer_setup
2230  * @dp_soc: dp soc
2231  * @vdev_id: vdev id
2232  * @peer: Object manager peer pointer
2233  * @peer_info: Peer setup info
2234  *
2235  * Return: VOID
2236  */
2237 static void wma_cdp_peer_setup(ol_txrx_soc_handle dp_soc,
2238 			       uint8_t vdev_id, struct wlan_objmgr_peer *peer,
2239 			       struct cdp_peer_setup_info *peer_info)
2240 {
2241 	uint8_t *mld_mac, *peer_addr;
2242 
2243 	peer_addr = wlan_peer_get_macaddr(peer);
2244 	mld_mac = peer_info->mld_peer_mac;
2245 
2246 	if (!mld_mac || qdf_is_macaddr_zero((struct qdf_mac_addr *)mld_mac)) {
2247 		cdp_peer_setup(dp_soc, vdev_id, peer_addr, NULL);
2248 		return;
2249 	}
2250 
2251 	cdp_peer_setup(dp_soc, vdev_id, peer_addr, peer_info);
2252 }
2253 #else
2254 static inline void
2255 wma_peer_setup_fill_info(struct wlan_objmgr_psoc *psoc,
2256 			 struct wlan_objmgr_peer *peer,
2257 			 struct cdp_peer_setup_info *peer_info)
2258 {
2259 	peer_info->mld_peer_mac = NULL;
2260 	peer_info->is_first_link = false;
2261 	peer_info->is_primary_link = false;
2262 }
2263 
2264 static void wma_cdp_peer_setup(ol_txrx_soc_handle dp_soc,
2265 			       uint8_t vdev_id, struct wlan_objmgr_peer *peer,
2266 			       struct cdp_peer_setup_info *peer_info)
2267 {
2268 	uint8_t *peer_addr;
2269 
2270 	peer_addr = wlan_peer_get_macaddr(peer);
2271 	cdp_peer_setup(dp_soc, vdev_id, peer_addr, NULL);
2272 }
2273 #endif
2274 
2275 QDF_STATUS wma_create_peer(tp_wma_handle wma,
2276 			   uint8_t peer_addr[QDF_MAC_ADDR_SIZE],
2277 			   uint32_t peer_type, uint8_t vdev_id,
2278 			   uint8_t peer_mld_addr[QDF_MAC_ADDR_SIZE],
2279 			   bool is_assoc_peer)
2280 {
2281 	void *dp_soc = cds_get_context(QDF_MODULE_ID_SOC);
2282 	QDF_STATUS status;
2283 	struct wlan_objmgr_peer *obj_peer;
2284 	struct cdp_peer_setup_info peer_info = {0};
2285 
2286 	if (!dp_soc)
2287 		return QDF_STATUS_E_FAILURE;
2288 	status = wma_add_peer(wma, peer_addr, peer_type, vdev_id,
2289 			      peer_mld_addr, is_assoc_peer);
2290 	if (QDF_IS_STATUS_ERROR(status))
2291 		return status;
2292 
2293 	obj_peer = wlan_objmgr_get_peer_by_mac(wma->psoc, peer_addr,
2294 					       WLAN_LEGACY_WMA_ID);
2295 	if (!obj_peer)
2296 		return QDF_STATUS_E_FAILURE;
2297 
2298 	wma_increment_peer_count(wma, vdev_id);
2299 
2300 	wma_peer_setup_fill_info(wma->psoc, obj_peer, &peer_info);
2301 	wma_peer_tbl_trans_add_entry(obj_peer, true, &peer_info);
2302 	wma_cdp_peer_setup(dp_soc, vdev_id, obj_peer, &peer_info);
2303 	wlan_objmgr_peer_release_ref(obj_peer, WLAN_LEGACY_WMA_ID);
2304 
2305 	return QDF_STATUS_SUCCESS;
2306 }
2307 
2308 /**
2309  * wma_create_sta_mode_bss_peer() - send peer create command to fw
2310  * and start peer create response timer
2311  * @wma: wma handle
2312  * @peer_addr: peer mac address
2313  * @peer_type: peer type
2314  * @vdev_id: vdev id
2315  * @mld_addr: peer mld address
2316  * @is_assoc_peer: is assoc peer or not
2317  *
2318  * Return: QDF_STATUS
2319  */
2320 static QDF_STATUS
2321 wma_create_sta_mode_bss_peer(tp_wma_handle wma,
2322 			     uint8_t peer_addr[QDF_MAC_ADDR_SIZE],
2323 			     uint32_t peer_type, uint8_t vdev_id,
2324 			     uint8_t mld_addr[QDF_MAC_ADDR_SIZE],
2325 			     bool is_assoc_peer)
2326 {
2327 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
2328 	struct wma_target_req *msg = NULL;
2329 	struct peer_create_rsp_params *peer_create_rsp = NULL;
2330 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
2331 	bool is_tgt_peer_conf_supported = false;
2332 
2333 	if (!mac) {
2334 		wma_err("vdev%d: Mac context is null", vdev_id);
2335 		return status;
2336 	}
2337 
2338 	/*
2339 	 * If fw doesn't advertise peer create confirm event support,
2340 	 * use the legacy peer create API
2341 	 */
2342 	is_tgt_peer_conf_supported =
2343 		wlan_psoc_nif_fw_ext_cap_get(wma->psoc,
2344 					     WLAN_SOC_F_PEER_CREATE_RESP);
2345 	if (!is_tgt_peer_conf_supported) {
2346 		status = wma_create_peer(wma, peer_addr, peer_type, vdev_id,
2347 					 mld_addr, is_assoc_peer);
2348 		goto end;
2349 	}
2350 
2351 	peer_create_rsp = qdf_mem_malloc(sizeof(*peer_create_rsp));
2352 	if (!peer_create_rsp)
2353 		goto end;
2354 
2355 	wma_acquire_wakelock(&wma->wmi_cmd_rsp_wake_lock,
2356 			     WMA_PEER_CREATE_RESPONSE_TIMEOUT);
2357 
2358 	status = wma_add_peer(wma, peer_addr, peer_type, vdev_id,
2359 			      mld_addr, is_assoc_peer);
2360 	if (QDF_IS_STATUS_ERROR(status)) {
2361 		wma_release_wakelock(&wma->wmi_cmd_rsp_wake_lock);
2362 		goto end;
2363 	}
2364 
2365 	wma_increment_peer_count(wma, vdev_id);
2366 	qdf_mem_copy(peer_create_rsp->peer_mac.bytes, peer_addr,
2367 		     QDF_MAC_ADDR_SIZE);
2368 
2369 	msg = wma_fill_hold_req(wma, vdev_id, WMA_PEER_CREATE_REQ,
2370 				WMA_PEER_CREATE_RESPONSE,
2371 				(void *)peer_create_rsp,
2372 				WMA_PEER_CREATE_RESPONSE_TIMEOUT);
2373 	if (!msg) {
2374 		wma_err("vdev:%d failed to fill peer create req", vdev_id);
2375 		wma_remove_peer_req(wma, vdev_id, WMA_PEER_CREATE_RESPONSE,
2376 				    (struct qdf_mac_addr *)peer_addr);
2377 		wma_remove_peer(wma, peer_addr, vdev_id, false);
2378 		wma_release_wakelock(&wma->wmi_cmd_rsp_wake_lock);
2379 		status = QDF_STATUS_E_FAILURE;
2380 		goto end;
2381 	}
2382 
2383 	return status;
2384 
2385 end:
2386 	qdf_mem_free(peer_create_rsp);
2387 	lim_send_peer_create_resp(mac, vdev_id, status, peer_addr);
2388 
2389 	return status;
2390 }
2391 
2392 /**
2393  * wma_remove_bss_peer() - remove BSS peer
2394  * @wma: pointer to WMA handle
2395  * @vdev_id: vdev id on which delete BSS request was received
2396  * @vdev_stop_resp: pointer to Delete BSS response
2397  * @type: request type
2398  *
2399  * This function is called on receiving vdev stop response from FW or
2400  * vdev stop response timeout. In case of NDI, use vdev's self MAC
2401  * for removing the peer. In case of STA/SAP use bssid passed as part of
2402  * delete STA parameter.
2403  *
2404  * Return: 0 on success, ERROR code on failure
2405  */
2406 static int wma_remove_bss_peer(tp_wma_handle wma, uint32_t vdev_id,
2407 			       struct del_bss_resp *vdev_stop_resp,
2408 			       uint8_t type)
2409 {
2410 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
2411 	uint8_t *mac_addr = NULL;
2412 	struct wma_target_req *del_req;
2413 	int ret_value = 0;
2414 	QDF_STATUS qdf_status;
2415 	struct qdf_mac_addr bssid;
2416 
2417 	if (WMA_IS_VDEV_IN_NDI_MODE(wma->interfaces, vdev_id)) {
2418 		mac_addr = cdp_get_vdev_mac_addr(soc, vdev_id);
2419 		if (!mac_addr) {
2420 			wma_err("mac_addr is NULL for vdev_id = %d", vdev_id);
2421 			return -EINVAL;
2422 		}
2423 	} else {
2424 		qdf_status = wlan_vdev_get_bss_peer_mac(
2425 				wma->interfaces[vdev_id].vdev,
2426 				&bssid);
2427 		if (QDF_IS_STATUS_ERROR(qdf_status)) {
2428 			wma_err("Failed to get bssid for vdev_id: %d", vdev_id);
2429 			return -EINVAL;
2430 		}
2431 		mac_addr = bssid.bytes;
2432 	}
2433 
2434 	qdf_status = wma_remove_peer(wma, mac_addr, vdev_id, false);
2435 
2436 	if (QDF_IS_STATUS_ERROR(qdf_status)) {
2437 		wma_err("wma_remove_peer failed vdev_id:%d", vdev_id);
2438 		return -EINVAL;
2439 	}
2440 
2441 	if (cds_is_driver_recovering())
2442 		return -EINVAL;
2443 
2444 	if (wmi_service_enabled(wma->wmi_handle,
2445 				wmi_service_sync_delete_cmds)) {
2446 		wma_debug("Wait for the peer delete. vdev_id %d", vdev_id);
2447 		del_req = wma_fill_hold_req(wma, vdev_id,
2448 					    WMA_DELETE_STA_REQ,
2449 					    type,
2450 					    vdev_stop_resp,
2451 					    WMA_DELETE_STA_TIMEOUT);
2452 		if (!del_req) {
2453 			wma_err("Failed to allocate request. vdev_id %d", vdev_id);
2454 			vdev_stop_resp->status = QDF_STATUS_E_NOMEM;
2455 			ret_value = -EINVAL;
2456 		}
2457 	}
2458 
2459 	return ret_value;
2460 }
2461 
2462 #ifdef FEATURE_WLAN_APF
2463 /*
2464  * get_fw_active_apf_mode() - convert HDD APF mode to FW configurable APF
2465  * mode
2466  * @mode: APF mode maintained in HDD
2467  *
2468  * Return: FW configurable BP mode
2469  */
2470 static enum wmi_host_active_apf_mode
2471 get_fw_active_apf_mode(enum active_apf_mode mode)
2472 {
2473 	switch (mode) {
2474 	case ACTIVE_APF_DISABLED:
2475 		return WMI_HOST_ACTIVE_APF_DISABLED;
2476 	case ACTIVE_APF_ENABLED:
2477 		return WMI_HOST_ACTIVE_APF_ENABLED;
2478 	case ACTIVE_APF_ADAPTIVE:
2479 		return WMI_HOST_ACTIVE_APF_ADAPTIVE;
2480 	default:
2481 		wma_err("Invalid Active APF Mode %d; Using 'disabled'", mode);
2482 		return WMI_HOST_ACTIVE_APF_DISABLED;
2483 	}
2484 }
2485 
2486 /**
2487  * wma_config_active_apf_mode() - Config active APF mode in FW
2488  * @wma: the WMA handle
2489  * @vdev_id: the Id of the vdev for which the configuration should be applied
2490  *
2491  * Return: QDF status
2492  */
2493 static QDF_STATUS wma_config_active_apf_mode(t_wma_handle *wma, uint8_t vdev_id)
2494 {
2495 	enum wmi_host_active_apf_mode uc_mode, mcbc_mode;
2496 
2497 	uc_mode = get_fw_active_apf_mode(wma->active_uc_apf_mode);
2498 	mcbc_mode = get_fw_active_apf_mode(wma->active_mc_bc_apf_mode);
2499 
2500 	wma_debug("Configuring Active APF Mode UC:%d MC/BC:%d for vdev %u",
2501 		 uc_mode, mcbc_mode, vdev_id);
2502 
2503 	return wmi_unified_set_active_apf_mode_cmd(wma->wmi_handle, vdev_id,
2504 						   uc_mode, mcbc_mode);
2505 }
2506 #else /* FEATURE_WLAN_APF */
2507 static QDF_STATUS wma_config_active_apf_mode(t_wma_handle *wma, uint8_t vdev_id)
2508 {
2509 	return QDF_STATUS_SUCCESS;
2510 }
2511 #endif /* FEATURE_WLAN_APF */
2512 
2513 #ifdef FEATURE_AP_MCC_CH_AVOIDANCE
2514 /**
2515  * wma_check_and_find_mcc_ap() - finds if device is operating AP
2516  * in MCC mode or not
2517  * @wma: wma handle.
2518  * @vdev_id: vdev ID of device for which MCC has to be checked
2519  *
2520  * This function internally calls wma_find_mcc_ap finds if
2521  * device is operating AP in MCC mode or not
2522  *
2523  * Return: none
2524  */
2525 static void
2526 wma_check_and_find_mcc_ap(tp_wma_handle wma, uint8_t vdev_id)
2527 {
2528 	struct mac_context *mac_ctx = cds_get_context(QDF_MODULE_ID_PE);
2529 
2530 	if (!mac_ctx)
2531 		return;
2532 
2533 	if (mac_ctx->sap.sap_channel_avoidance)
2534 		wma_find_mcc_ap(wma, vdev_id, false);
2535 }
2536 #else
2537 static inline void
2538 wma_check_and_find_mcc_ap(tp_wma_handle wma, uint8_t vdev_id)
2539 {}
2540 #endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
2541 
2542 void wma_send_del_bss_response(tp_wma_handle wma, struct del_bss_resp *resp)
2543 {
2544 	struct wma_txrx_node *iface;
2545 	struct beacon_info *bcn;
2546 	uint8_t vdev_id;
2547 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
2548 
2549 	if (!resp) {
2550 		wma_err("req is NULL");
2551 		return;
2552 	}
2553 
2554 	vdev_id = resp->vdev_id;
2555 	iface = &wma->interfaces[vdev_id];
2556 
2557 	if (!iface->vdev) {
2558 		wma_err("vdev id %d iface->vdev is NULL", vdev_id);
2559 		if (resp)
2560 			qdf_mem_free(resp);
2561 		return;
2562 	}
2563 
2564 	cdp_fc_vdev_flush(soc, vdev_id);
2565 	wma_debug("vdev_id: %d, un-pausing tx_ll_queue for VDEV_STOP rsp",
2566 		 vdev_id);
2567 	cdp_fc_vdev_unpause(soc, vdev_id, OL_TXQ_PAUSE_REASON_VDEV_STOP, 0);
2568 	wma_vdev_clear_pause_bit(vdev_id, PAUSE_TYPE_HOST);
2569 	qdf_atomic_set(&iface->bss_status, WMA_BSS_STATUS_STOPPED);
2570 	wma_debug("(type %d subtype %d) BSS is stopped",
2571 		 iface->type, iface->sub_type);
2572 
2573 	bcn = wma->interfaces[vdev_id].beacon;
2574 	if (bcn) {
2575 		wma_debug("Freeing beacon struct %pK, template memory %pK",
2576 			 bcn, bcn->buf);
2577 		if (bcn->dma_mapped)
2578 			qdf_nbuf_unmap_single(wma->qdf_dev, bcn->buf,
2579 					  QDF_DMA_TO_DEVICE);
2580 		qdf_nbuf_free(bcn->buf);
2581 		qdf_mem_free(bcn);
2582 		wma->interfaces[vdev_id].beacon = NULL;
2583 	}
2584 
2585 	/* Timeout status means its WMA generated DEL BSS REQ when ADD
2586 	 * BSS REQ was timed out to stop the VDEV in this case no need
2587 	 * to send response to UMAC
2588 	 */
2589 	if (resp->status == QDF_STATUS_FW_MSG_TIMEDOUT) {
2590 		qdf_mem_free(resp);
2591 		wma_err("DEL BSS from ADD BSS timeout do not send resp to UMAC (vdev id %x)",
2592 			vdev_id);
2593 	} else {
2594 		resp->status = QDF_STATUS_SUCCESS;
2595 		wma_send_msg_high_priority(wma, WMA_DELETE_BSS_RSP,
2596 					   (void *)resp, 0);
2597 	}
2598 
2599 	if (iface->del_staself_req && iface->is_del_sta_deferred) {
2600 		iface->is_del_sta_deferred = false;
2601 		wma_nofl_alert("scheduling deferred deletion (vdev id %x)",
2602 			      vdev_id);
2603 		wma_vdev_detach(iface->del_staself_req);
2604 	}
2605 }
2606 
2607 QDF_STATUS
2608 wma_send_vdev_down(tp_wma_handle wma, struct del_bss_resp *resp)
2609 {
2610 	uint8_t vdev_id;
2611 	struct wma_txrx_node *iface = &wma->interfaces[resp->vdev_id];
2612 	uint32_t vdev_stop_type;
2613 	QDF_STATUS status;
2614 
2615 	if (!resp) {
2616 		wma_err("resp is NULL");
2617 		return QDF_STATUS_E_NULL_VALUE;
2618 	}
2619 
2620 	vdev_id = resp->vdev_id;
2621 	status = mlme_get_vdev_stop_type(iface->vdev, &vdev_stop_type);
2622 	if (QDF_IS_STATUS_ERROR(status)) {
2623 		wma_err("Failed to get vdev stop type");
2624 		qdf_mem_free(resp);
2625 		return status;
2626 	}
2627 
2628 	if (vdev_stop_type != WMA_DELETE_BSS_HO_FAIL_REQ) {
2629 		status = wma_send_vdev_down_to_fw(wma, vdev_id);
2630 		if (QDF_IS_STATUS_ERROR(status))
2631 			wma_err("Failed to send vdev down cmd: vdev %d", vdev_id);
2632 		else
2633 			wma_check_and_find_mcc_ap(wma, vdev_id);
2634 	}
2635 
2636 	wlan_vdev_mlme_sm_deliver_evt(iface->vdev,
2637 				      WLAN_VDEV_SM_EV_DOWN_COMPLETE,
2638 				      sizeof(*resp), resp);
2639 	return status;
2640 }
2641 
2642 /**
2643  * wma_send_vdev_down_req() - handle vdev down req
2644  * @wma: wma handle
2645  * @resp: pointer to vde del bss response
2646  *
2647  * Return: none
2648  */
2649 
2650 static void wma_send_vdev_down_req(tp_wma_handle wma,
2651 				   struct del_bss_resp *resp)
2652 {
2653 	struct wma_txrx_node *iface = &wma->interfaces[resp->vdev_id];
2654 	enum QDF_OPMODE mode;
2655 
2656 	mode = wlan_vdev_mlme_get_opmode(iface->vdev);
2657 	if (mode == QDF_STA_MODE || mode == QDF_P2P_CLIENT_MODE) {
2658 		/* initiate MLME Down req from CM for STA/CLI */
2659 		wlan_cm_bss_peer_delete_rsp(iface->vdev, resp->status);
2660 		qdf_mem_free(resp);
2661 		return;
2662 	}
2663 
2664 	wlan_vdev_mlme_sm_deliver_evt(iface->vdev,
2665 				      WLAN_VDEV_SM_EV_MLME_DOWN_REQ,
2666 				      sizeof(*resp), resp);
2667 }
2668 
2669 #ifdef WLAN_FEATURE_11BE_MLO
2670 void wma_delete_peer_mlo(struct wlan_objmgr_psoc *psoc, uint8_t *macaddr)
2671 {
2672 	struct wlan_objmgr_peer *peer = NULL;
2673 
2674 	peer = wlan_objmgr_get_peer_by_mac(psoc, macaddr, WLAN_LEGACY_WMA_ID);
2675 	if (peer) {
2676 		wlan_mlo_link_peer_delete(peer);
2677 		wlan_objmgr_peer_release_ref(peer, WLAN_LEGACY_WMA_ID);
2678 	}
2679 }
2680 #endif /* WLAN_FEATURE_11BE_MLO */
2681 
2682 static QDF_STATUS
2683 wma_delete_peer_on_vdev_stop(tp_wma_handle wma, uint8_t vdev_id)
2684 {
2685 	uint32_t vdev_stop_type;
2686 	struct del_bss_resp *vdev_stop_resp;
2687 	struct wma_txrx_node *iface;
2688 	QDF_STATUS status;
2689 	struct qdf_mac_addr bssid;
2690 
2691 	iface = &wma->interfaces[vdev_id];
2692 	status = wlan_vdev_get_bss_peer_mac(iface->vdev, &bssid);
2693 	if (QDF_IS_STATUS_ERROR(status)) {
2694 		wma_err("Failed to get bssid");
2695 		return QDF_STATUS_E_INVAL;
2696 	}
2697 
2698 	status = mlme_get_vdev_stop_type(iface->vdev, &vdev_stop_type);
2699 	if (QDF_IS_STATUS_ERROR(status)) {
2700 		wma_err("Failed to get wma req msg type for vdev id %d",
2701 			vdev_id);
2702 		return QDF_STATUS_E_INVAL;
2703 	}
2704 
2705 	wma_delete_peer_mlo(wma->psoc, bssid.bytes);
2706 
2707 	vdev_stop_resp = qdf_mem_malloc(sizeof(*vdev_stop_resp));
2708 	if (!vdev_stop_resp)
2709 		return QDF_STATUS_E_NOMEM;
2710 
2711 	if (vdev_stop_type == WMA_DELETE_BSS_HO_FAIL_REQ) {
2712 		status = wma_remove_peer(wma, bssid.bytes,
2713 					 vdev_id, true);
2714 		if (QDF_IS_STATUS_ERROR(status))
2715 			goto free_params;
2716 
2717 		vdev_stop_resp->status = status;
2718 		vdev_stop_resp->vdev_id = vdev_id;
2719 		wma_send_vdev_down_req(wma, vdev_stop_resp);
2720 	} else if (vdev_stop_type == WMA_DELETE_BSS_REQ ||
2721 	    vdev_stop_type == WMA_SET_LINK_STATE) {
2722 		uint8_t type;
2723 
2724 		/* CCA is required only for sta interface */
2725 		if (iface->type == WMI_VDEV_TYPE_STA)
2726 			wma_get_cca_stats(wma, vdev_id);
2727 		if (vdev_stop_type == WMA_DELETE_BSS_REQ)
2728 			type = WMA_DELETE_PEER_RSP;
2729 		else
2730 			type = WMA_SET_LINK_PEER_RSP;
2731 
2732 		vdev_stop_resp->vdev_id = vdev_id;
2733 		vdev_stop_resp->status = status;
2734 		status = wma_remove_bss_peer(wma, vdev_id,
2735 					     vdev_stop_resp, type);
2736 		if (status) {
2737 			wma_err("Del bss failed vdev:%d", vdev_id);
2738 			wma_send_vdev_down_req(wma, vdev_stop_resp);
2739 			return status;
2740 		}
2741 
2742 		if (wmi_service_enabled(wma->wmi_handle,
2743 					wmi_service_sync_delete_cmds))
2744 			return status;
2745 
2746 		wma_send_vdev_down_req(wma, vdev_stop_resp);
2747 	}
2748 
2749 	return status;
2750 
2751 free_params:
2752 	qdf_mem_free(vdev_stop_resp);
2753 	return status;
2754 }
2755 
2756 QDF_STATUS
2757 cm_send_bss_peer_delete_req(struct wlan_objmgr_vdev *vdev)
2758 {
2759 	tp_wma_handle wma = cds_get_context(QDF_MODULE_ID_WMA);
2760 	uint8_t vdev_id = wlan_vdev_get_id(vdev);
2761 
2762 	if (!wma)
2763 		return QDF_STATUS_E_INVAL;
2764 
2765 	if (wlan_vdev_mlme_is_init_state(vdev) == QDF_STATUS_SUCCESS) {
2766 		wma_remove_bss_peer_on_failure(wma, vdev_id);
2767 		return QDF_STATUS_SUCCESS;
2768 	}
2769 
2770 	return wma_delete_peer_on_vdev_stop(wma, vdev_id);
2771 }
2772 
2773 QDF_STATUS
2774 __wma_handle_vdev_stop_rsp(struct vdev_stop_response *resp_event)
2775 {
2776 	tp_wma_handle wma = cds_get_context(QDF_MODULE_ID_WMA);
2777 	struct wma_txrx_node *iface;
2778 	QDF_STATUS status;
2779 	struct qdf_mac_addr bssid;
2780 	enum QDF_OPMODE mode;
2781 
2782 	if (!wma)
2783 		return QDF_STATUS_E_INVAL;
2784 
2785 	/* Ignore stop_response in Monitor mode */
2786 	if (cds_get_conparam() == QDF_GLOBAL_MONITOR_MODE)
2787 		return  QDF_STATUS_SUCCESS;
2788 
2789 	iface = &wma->interfaces[resp_event->vdev_id];
2790 
2791 	/* vdev in stopped state, no more waiting for key */
2792 	iface->is_waiting_for_key = false;
2793 
2794 	/*
2795 	 * Reset the rmfEnabled as there might be MGMT action frames
2796 	 * sent on this vdev before the next session is established.
2797 	 */
2798 	if (iface->rmfEnabled) {
2799 		iface->rmfEnabled = 0;
2800 		wma_debug("Reset rmfEnabled for vdev %d",
2801 			 resp_event->vdev_id);
2802 	}
2803 
2804 	mode = wlan_vdev_mlme_get_opmode(iface->vdev);
2805 	if (mode == QDF_STA_MODE || mode == QDF_P2P_CLIENT_MODE) {
2806 		status = wlan_vdev_get_bss_peer_mac(iface->vdev, &bssid);
2807 		if (QDF_IS_STATUS_ERROR(status)) {
2808 			wma_debug("Failed to get bssid, peer might have got deleted already");
2809 			return wlan_cm_bss_peer_delete_rsp(iface->vdev, status);
2810 		}
2811 		/* initiate CM to delete bss peer */
2812 		return wlan_cm_bss_peer_delete_ind(iface->vdev,  &bssid);
2813 	} else if (mode == QDF_SAP_MODE) {
2814 		wlan_son_deliver_vdev_stop(iface->vdev);
2815 	}
2816 
2817 	return wma_delete_peer_on_vdev_stop(wma, resp_event->vdev_id);
2818 }
2819 
2820 /**
2821  * wma_handle_vdev_stop_rsp() - handle vdev stop resp
2822  * @wma: wma handle
2823  * @resp_event: fw resp
2824  *
2825  * Return: QDF_STATUS
2826  */
2827 static QDF_STATUS
2828 wma_handle_vdev_stop_rsp(tp_wma_handle wma,
2829 			 struct vdev_stop_response *resp_event)
2830 {
2831 	struct wma_txrx_node *iface;
2832 
2833 	iface = &wma->interfaces[resp_event->vdev_id];
2834 	return wlan_vdev_mlme_sm_deliver_evt(iface->vdev,
2835 					     WLAN_VDEV_SM_EV_STOP_RESP,
2836 					     sizeof(*resp_event), resp_event);
2837 }
2838 
2839 QDF_STATUS wma_vdev_stop_resp_handler(struct vdev_mlme_obj *vdev_mlme,
2840 				      struct vdev_stop_response *rsp)
2841 {
2842 	tp_wma_handle wma;
2843 	struct wma_txrx_node *iface = NULL;
2844 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
2845 
2846 	wma = cds_get_context(QDF_MODULE_ID_WMA);
2847 	if (!wma)
2848 		return status;
2849 
2850 	iface = &wma->interfaces[vdev_mlme->vdev->vdev_objmgr.vdev_id];
2851 
2852 	if (rsp->vdev_id >= wma->max_bssid) {
2853 		wma_err("Invalid vdev_id %d from FW", rsp->vdev_id);
2854 		return QDF_STATUS_E_INVAL;
2855 	}
2856 
2857 	status = wma_handle_vdev_stop_rsp(wma, rsp);
2858 
2859 	return status;
2860 }
2861 
2862 void wma_cleanup_vdev(struct wlan_objmgr_vdev *vdev)
2863 {
2864 	tp_wma_handle wma_handle;
2865 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
2866 	uint8_t vdev_id = wlan_vdev_get_id(vdev);
2867 	struct vdev_mlme_obj *vdev_mlme;
2868 
2869 	if (!soc)
2870 		return;
2871 
2872 	wma_handle = cds_get_context(QDF_MODULE_ID_WMA);
2873 	if (!wma_handle)
2874 		return;
2875 
2876 	if (!wma_handle->interfaces[vdev_id].vdev) {
2877 		wma_err("vdev is NULL");
2878 		return;
2879 	}
2880 
2881 	vdev_mlme = wlan_vdev_mlme_get_cmpt_obj(vdev);
2882 	if (!vdev_mlme) {
2883 		wma_err("Failed to get vdev mlme obj for vdev id %d", vdev_id);
2884 		return;
2885 	}
2886 
2887 	wma_cdp_vdev_detach(soc, wma_handle, vdev_id);
2888 	wlan_objmgr_vdev_release_ref(vdev, WLAN_LEGACY_WMA_ID);
2889 	wma_handle->interfaces[vdev_id].vdev = NULL;
2890 	wma_handle->interfaces[vdev_id].vdev_active = false;
2891 }
2892 
2893 QDF_STATUS wma_vdev_self_peer_create(struct vdev_mlme_obj *vdev_mlme)
2894 {
2895 	struct wlan_objmgr_peer *obj_peer;
2896 	QDF_STATUS status = QDF_STATUS_SUCCESS;
2897 	struct wlan_objmgr_vdev *vdev = vdev_mlme->vdev;
2898 	tp_wma_handle wma_handle;
2899 	uint8_t peer_vdev_id, *self_peer_macaddr;
2900 
2901 	wma_handle = cds_get_context(QDF_MODULE_ID_WMA);
2902 	if (!wma_handle)
2903 		return QDF_STATUS_E_FAILURE;
2904 
2905 	if (mlme_vdev_uses_self_peer(vdev_mlme->mgmt.generic.type,
2906 				     vdev_mlme->mgmt.generic.subtype)) {
2907 		status = wma_create_peer(wma_handle,
2908 					 vdev->vdev_mlme.macaddr,
2909 					 WMI_PEER_TYPE_DEFAULT,
2910 					 wlan_vdev_get_id(vdev),
2911 					 NULL, false);
2912 		if (QDF_IS_STATUS_ERROR(status))
2913 			wma_err("Failed to create peer %d", status);
2914 	} else if (vdev_mlme->mgmt.generic.type == WMI_VDEV_TYPE_STA ||
2915 		   vdev_mlme->mgmt.generic.type == WMI_VDEV_TYPE_NAN) {
2916 		if (!qdf_is_macaddr_zero(
2917 				(struct qdf_mac_addr *)vdev->vdev_mlme.mldaddr))
2918 			self_peer_macaddr = vdev->vdev_mlme.mldaddr;
2919 		else
2920 			self_peer_macaddr = vdev->vdev_mlme.macaddr;
2921 
2922 		/**
2923 		 * Self peer is used for the frames exchanged before
2924 		 * association. For ML STA, Self peer create will be triggered
2925 		 * for both the VDEVs, but one self peer is enough. So in case
2926 		 * of ML, use MLD address for the self peer and ignore self peer
2927 		 * creation for the partner link vdev.
2928 		 */
2929 		if (wma_objmgr_peer_exist(wma_handle, self_peer_macaddr,
2930 					  &peer_vdev_id))
2931 			return QDF_STATUS_SUCCESS;
2932 
2933 		obj_peer = wma_create_objmgr_peer(wma_handle,
2934 						  wlan_vdev_get_id(vdev),
2935 						  self_peer_macaddr,
2936 						  WMI_PEER_TYPE_DEFAULT,
2937 						  vdev->vdev_mlme.macaddr);
2938 		if (!obj_peer) {
2939 			wma_err("Failed to create obj mgr peer for self");
2940 			status = QDF_STATUS_E_INVAL;
2941 		}
2942 	}
2943 
2944 	return status;
2945 }
2946 
2947 #ifdef MULTI_CLIENT_LL_SUPPORT
2948 #define MAX_VDEV_LATENCY_PARAMS 10
2949 /* params being sent:
2950  * 1.wmi_vdev_param_set_multi_client_ll_feature_config
2951  * 2.wmi_vdev_param_set_normal_latency_flags_config
2952  * 3.wmi_vdev_param_set_xr_latency_flags_config
2953  * 4.wmi_vdev_param_set_low_latency_flags_config
2954  * 5.wmi_vdev_param_set_ultra_low_latency_flags_config
2955  * 6.wmi_vdev_param_set_normal_latency_ul_dl_config
2956  * 7.wmi_vdev_param_set_xr_latency_ul_dl_config
2957  * 8.wmi_vdev_param_set_low_latency_ul_dl_config
2958  * 9.wmi_vdev_param_set_ultra_low_latency_ul_dl_config
2959  * 10.wmi_vdev_param_set_default_ll_config
2960  */
2961 
2962 /**
2963  * wma_set_vdev_latency_level_param() - Set per vdev latency level params in FW
2964  * @wma_handle: wma handle
2965  * @mac: mac context
2966  * @vdev_id: vdev id
2967  *
2968  * Return: QDF_STATUS
2969  */
2970 static QDF_STATUS wma_set_vdev_latency_level_param(tp_wma_handle wma_handle,
2971 						   struct mac_context *mac,
2972 						   uint8_t vdev_id)
2973 {
2974 	QDF_STATUS status = QDF_STATUS_SUCCESS;
2975 	bool multi_client_ll_ini_support, multi_client_ll_caps;
2976 	uint32_t latency_flags;
2977 	static uint32_t ll[4] = {100, 60, 40, 20};
2978 	uint32_t ul_latency, dl_latency, ul_dl_latency;
2979 	uint8_t default_latency_level;
2980 	struct dev_set_param setparam[MAX_VDEV_LATENCY_PARAMS];
2981 	uint8_t index = 0;
2982 
2983 	multi_client_ll_ini_support =
2984 			mac->mlme_cfg->wlm_config.multi_client_ll_support;
2985 	multi_client_ll_caps =
2986 			wlan_mlme_get_wlm_multi_client_ll_caps(mac->psoc);
2987 	wma_debug("INI support: %d, fw capability:%d",
2988 		  multi_client_ll_ini_support, multi_client_ll_caps);
2989 	/*
2990 	 * Multi-Client arbiter functionality is enabled only if both INI is
2991 	 * set, and Service bit is configured.
2992 	 */
2993 	if (!(multi_client_ll_ini_support && multi_client_ll_caps))
2994 		return status;
2995 	status = mlme_check_index_setparam(
2996 			setparam,
2997 			wmi_vdev_param_set_multi_client_ll_feature_config,
2998 			multi_client_ll_ini_support, index++,
2999 			MAX_VDEV_LATENCY_PARAMS);
3000 	if (QDF_IS_STATUS_ERROR(status)) {
3001 		wma_err("failed to configure low latency feature");
3002 		return status;
3003 	}
3004 
3005 	/* wlm latency level index:0 - normal, 1 - xr, 2 - low, 3 - ultralow */
3006 	wma_debug("Setting vdev params for latency level flags");
3007 
3008 	latency_flags = mac->mlme_cfg->wlm_config.latency_flags[0];
3009 	status = mlme_check_index_setparam(
3010 				setparam,
3011 				wmi_vdev_param_set_normal_latency_flags_config,
3012 				latency_flags, index++,
3013 				MAX_VDEV_LATENCY_PARAMS);
3014 	if (QDF_IS_STATUS_ERROR(status)) {
3015 		wma_err("failed to configure normal latency feature");
3016 		return status;
3017 	}
3018 
3019 	latency_flags = mac->mlme_cfg->wlm_config.latency_flags[1];
3020 	status = mlme_check_index_setparam(
3021 				setparam,
3022 				wmi_vdev_param_set_xr_latency_flags_config,
3023 				latency_flags, index++,
3024 				MAX_VDEV_LATENCY_PARAMS);
3025 	if (QDF_IS_STATUS_ERROR(status)) {
3026 		wma_err("failed to configure xr latency feature");
3027 		return status;
3028 	}
3029 
3030 	latency_flags = mac->mlme_cfg->wlm_config.latency_flags[2];
3031 	status = mlme_check_index_setparam(
3032 				setparam,
3033 				wmi_vdev_param_set_low_latency_flags_config,
3034 				latency_flags, index++,
3035 				MAX_VDEV_LATENCY_PARAMS);
3036 	if (QDF_IS_STATUS_ERROR(status)) {
3037 		wma_err("failed to configure low latency feature");
3038 		return status;
3039 	}
3040 
3041 	latency_flags = mac->mlme_cfg->wlm_config.latency_flags[3];
3042 	status = mlme_check_index_setparam(
3043 			setparam,
3044 			wmi_vdev_param_set_ultra_low_latency_flags_config,
3045 			latency_flags, index++, MAX_VDEV_LATENCY_PARAMS);
3046 	if (QDF_IS_STATUS_ERROR(status)) {
3047 		wma_err("failed to configure ultra low latency feature");
3048 		return status;
3049 	}
3050 
3051 	wma_debug("Setting vdev params for Latency level UL/DL flags");
3052 	/*
3053 	 * Latency level UL/DL
3054 	 * 0-15 bits: UL and 16-31 bits: DL
3055 	 */
3056 	dl_latency = ll[0];
3057 	ul_latency = ll[0];
3058 	ul_dl_latency = dl_latency << 16 | ul_latency;
3059 	status = mlme_check_index_setparam(
3060 				setparam,
3061 				wmi_vdev_param_set_normal_latency_ul_dl_config,
3062 				ul_dl_latency, index++,
3063 				MAX_VDEV_LATENCY_PARAMS);
3064 	if (QDF_IS_STATUS_ERROR(status)) {
3065 		wma_err("failed to configure normal latency ul dl flag");
3066 		return status;
3067 	}
3068 
3069 	dl_latency = ll[1];
3070 	ul_latency = ll[1];
3071 	ul_dl_latency = dl_latency << 16 | ul_latency;
3072 	status = mlme_check_index_setparam(
3073 				setparam,
3074 				wmi_vdev_param_set_xr_latency_ul_dl_config,
3075 				ul_dl_latency, index++,
3076 				MAX_VDEV_LATENCY_PARAMS);
3077 	if (QDF_IS_STATUS_ERROR(status)) {
3078 		wma_err("failed to configure normal latency ul dl flag");
3079 		return status;
3080 	}
3081 
3082 	dl_latency = ll[2];
3083 	ul_latency = ll[2];
3084 	ul_dl_latency = dl_latency << 16 | ul_latency;
3085 	status = mlme_check_index_setparam(
3086 				setparam,
3087 				wmi_vdev_param_set_low_latency_ul_dl_config,
3088 				ul_dl_latency, index++,
3089 				MAX_VDEV_LATENCY_PARAMS);
3090 	if (QDF_IS_STATUS_ERROR(status)) {
3091 		wma_err("failed to configure normal latency ul dl flag");
3092 		return status;
3093 	}
3094 
3095 	dl_latency = ll[3];
3096 	ul_latency = ll[3];
3097 	ul_dl_latency = dl_latency << 16 | ul_latency;
3098 	status = mlme_check_index_setparam(
3099 			setparam,
3100 			wmi_vdev_param_set_ultra_low_latency_ul_dl_config,
3101 			ul_dl_latency, index++,
3102 			MAX_VDEV_LATENCY_PARAMS);
3103 	if (QDF_IS_STATUS_ERROR(status)) {
3104 		wma_err("failed to configure normal latency ul dl flag");
3105 		return status;
3106 	}
3107 
3108 	default_latency_level = mac->mlme_cfg->wlm_config.latency_level;
3109 	status = mlme_check_index_setparam(
3110 				      setparam,
3111 				      wmi_vdev_param_set_default_ll_config,
3112 				      default_latency_level, index++,
3113 				      MAX_VDEV_LATENCY_PARAMS);
3114 	if (QDF_IS_STATUS_ERROR(status)) {
3115 		wma_err("failed to configure low latency feature");
3116 		return status;
3117 	}
3118 
3119 	status = wma_send_multi_pdev_vdev_set_params(MLME_VDEV_SETPARAM,
3120 						     vdev_id, setparam, index);
3121 	if (QDF_IS_STATUS_ERROR(status))
3122 		wma_err("Failed to configure vdev latency level params");
3123 	return status;
3124 }
3125 #else
3126 static QDF_STATUS wma_set_vdev_latency_level_param(tp_wma_handle wma_handle,
3127 						   struct mac_context *mac,
3128 						   uint8_t vdev_id)
3129 {
3130 	return QDF_STATUS_E_FAILURE;
3131 }
3132 #endif
3133 
3134 QDF_STATUS wma_post_vdev_create_setup(struct wlan_objmgr_vdev *vdev)
3135 {
3136 	QDF_STATUS status = QDF_STATUS_SUCCESS;
3137 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
3138 	bool mcc_adapt_sch = false;
3139 	QDF_STATUS ret;
3140 	uint8_t vdev_id;
3141 	struct wlan_mlme_qos *qos_aggr;
3142 	struct vdev_mlme_obj *vdev_mlme;
3143 	tp_wma_handle wma_handle;
3144 	uint8_t enable_sifs_burst = 0;
3145 
3146 	if (!mac)
3147 		return QDF_STATUS_E_FAILURE;
3148 
3149 	wma_handle = cds_get_context(QDF_MODULE_ID_WMA);
3150 	if (!wma_handle)
3151 		return QDF_STATUS_E_FAILURE;
3152 
3153 	if (wlan_objmgr_vdev_try_get_ref(vdev, WLAN_LEGACY_WMA_ID) !=
3154 		QDF_STATUS_SUCCESS)
3155 		return QDF_STATUS_E_FAILURE;
3156 
3157 	vdev_id = wlan_vdev_get_id(vdev);
3158 	wma_handle->interfaces[vdev_id].vdev = vdev;
3159 	wma_handle->interfaces[vdev_id].vdev_active = true;
3160 
3161 	vdev_mlme = wlan_vdev_mlme_get_cmpt_obj(vdev);
3162 	if (!vdev_mlme) {
3163 		wma_err("Failed to get vdev mlme obj!");
3164 		goto end;
3165 	}
3166 
3167 	wma_vdev_update_pause_bitmap(vdev_id, 0);
3168 
3169 	wma_handle->interfaces[vdev_id].type =
3170 		vdev_mlme->mgmt.generic.type;
3171 	wma_handle->interfaces[vdev_id].sub_type =
3172 		vdev_mlme->mgmt.generic.subtype;
3173 
3174 	qos_aggr = &mac->mlme_cfg->qos_mlme_params;
3175 	if (vdev_mlme->mgmt.generic.type == WMI_VDEV_TYPE_STA) {
3176 		wma_set_sta_keep_alive(
3177 				wma_handle, vdev_id,
3178 				SIR_KEEP_ALIVE_NULL_PKT,
3179 				mac->mlme_cfg->sta.sta_keep_alive_period,
3180 				NULL, NULL, NULL);
3181 
3182 		/* offload STA SA query related params to fwr */
3183 		if (wmi_service_enabled(wma_handle->wmi_handle,
3184 					wmi_service_sta_pmf_offload)) {
3185 			wma_set_sta_sa_query_param(wma_handle, vdev_id);
3186 		}
3187 
3188 		status = wma_set_sw_retry_threshold(qos_aggr);
3189 		if (QDF_IS_STATUS_ERROR(status))
3190 			wma_err("failed to set sw retry threshold (status = %d)",
3191 				status);
3192 
3193 		status = wma_set_sw_retry_threshold_per_ac(wma_handle, vdev_id,
3194 							   qos_aggr);
3195 		if (QDF_IS_STATUS_ERROR(status))
3196 			wma_err("failed to set sw retry threshold per ac(status = %d)",
3197 				 status);
3198 	}
3199 
3200 	status = wma_vdev_create_set_param(vdev);
3201 	if (QDF_IS_STATUS_ERROR(status)) {
3202 		wma_err("Failed to setup Vdev create set param for vdev: %d",
3203 			vdev_id);
3204 		return status;
3205 	}
3206 
3207 	if (policy_mgr_get_dynamic_mcc_adaptive_sch(mac->psoc,
3208 						    &mcc_adapt_sch) ==
3209 	    QDF_STATUS_SUCCESS) {
3210 		wma_debug("setting ini value for WNI_CFG_ENABLE_MCC_ADAPTIVE_SCHED: %d",
3211 			 mcc_adapt_sch);
3212 		ret =
3213 		wma_set_enable_disable_mcc_adaptive_scheduler(mcc_adapt_sch);
3214 		if (QDF_IS_STATUS_ERROR(ret)) {
3215 			wma_err("Failed to set WNI_CFG_ENABLE_MCC_ADAPTIVE_SCHED");
3216 		}
3217 	} else {
3218 		wma_err("Failed to get value for WNI_CFG_ENABLE_MCC_ADAPTIVE_SCHED, leaving unchanged");
3219 	}
3220 
3221 	if (vdev_mlme->mgmt.generic.type == WMI_VDEV_TYPE_STA &&
3222 	    ucfg_pmo_is_apf_enabled(wma_handle->psoc)) {
3223 		ret = wma_config_active_apf_mode(wma_handle,
3224 						 vdev_id);
3225 		if (QDF_IS_STATUS_ERROR(ret))
3226 			wma_err("Failed to configure active APF mode");
3227 	}
3228 
3229 	if (vdev_mlme->mgmt.generic.type == WMI_VDEV_TYPE_STA &&
3230 	    vdev_mlme->mgmt.generic.subtype == 0)
3231 		wma_set_vdev_latency_level_param(wma_handle, mac, vdev_id);
3232 
3233 	switch (vdev_mlme->mgmt.generic.type) {
3234 	case WMI_VDEV_TYPE_AP:
3235 		if (vdev_mlme->mgmt.generic.subtype !=
3236 		    WLAN_VDEV_MLME_SUBTYPE_P2P_DEVICE)
3237 			break;
3238 
3239 		fallthrough;
3240 	case WMI_VDEV_TYPE_STA:
3241 	case WMI_VDEV_TYPE_NAN:
3242 	case WMI_VDEV_TYPE_OCB:
3243 	case WMI_VDEV_TYPE_MONITOR:
3244 		status = ucfg_get_enable_sifs_burst(wma_handle->psoc,
3245 						    &enable_sifs_burst);
3246 		if (QDF_IS_STATUS_ERROR(status))
3247 			wma_err("Failed to get sifs burst value, use default");
3248 
3249 		status = wma_vdev_set_param(wma_handle->wmi_handle, vdev_id,
3250 					    WMI_PDEV_PARAM_BURST_ENABLE,
3251 					    enable_sifs_burst);
3252 
3253 		if (QDF_IS_STATUS_ERROR(status))
3254 			wma_err("WMI_PDEV_PARAM_BURST_ENABLE set failed %d",
3255 				status);
3256 		break;
3257 	default:
3258 		break;
3259 	}
3260 
3261 	wma_vdev_set_data_tx_callback(vdev);
3262 
3263 	return QDF_STATUS_SUCCESS;
3264 
3265 end:
3266 	wma_cleanup_vdev(vdev);
3267 	return QDF_STATUS_E_FAILURE;
3268 }
3269 
3270 QDF_STATUS wma_vdev_set_data_tx_callback(struct wlan_objmgr_vdev *vdev)
3271 {
3272 	u_int8_t vdev_id;
3273 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
3274 	tp_wma_handle wma_handle = cds_get_context(QDF_MODULE_ID_WMA);
3275 
3276 	if (!vdev || !wma_handle || !soc) {
3277 		wma_err("null vdev, wma_handle or soc");
3278 		return QDF_STATUS_E_FAILURE;
3279 	}
3280 
3281 	vdev_id = wlan_vdev_get_id(vdev);
3282 	cdp_data_tx_cb_set(soc, vdev_id,
3283 			   wma_data_tx_ack_comp_hdlr,
3284 			   wma_handle);
3285 
3286 	return QDF_STATUS_SUCCESS;
3287 }
3288 
3289 enum mlme_bcn_tx_rate_code wma_get_bcn_rate_code(uint16_t rate)
3290 {
3291 	/* rate in multiples of 100 Kbps */
3292 	switch (rate) {
3293 	case WMA_BEACON_TX_RATE_1_M:
3294 		return MLME_BCN_TX_RATE_CODE_1_M;
3295 	case WMA_BEACON_TX_RATE_2_M:
3296 		return MLME_BCN_TX_RATE_CODE_2_M;
3297 	case WMA_BEACON_TX_RATE_5_5_M:
3298 		return MLME_BCN_TX_RATE_CODE_5_5_M;
3299 	case WMA_BEACON_TX_RATE_11_M:
3300 		return MLME_BCN_TX_RATE_CODE_11M;
3301 	case WMA_BEACON_TX_RATE_6_M:
3302 		return MLME_BCN_TX_RATE_CODE_6_M;
3303 	case WMA_BEACON_TX_RATE_9_M:
3304 		return MLME_BCN_TX_RATE_CODE_9_M;
3305 	case WMA_BEACON_TX_RATE_12_M:
3306 		return MLME_BCN_TX_RATE_CODE_12_M;
3307 	case WMA_BEACON_TX_RATE_18_M:
3308 		return MLME_BCN_TX_RATE_CODE_18_M;
3309 	case WMA_BEACON_TX_RATE_24_M:
3310 		return MLME_BCN_TX_RATE_CODE_24_M;
3311 	case WMA_BEACON_TX_RATE_36_M:
3312 		return MLME_BCN_TX_RATE_CODE_36_M;
3313 	case WMA_BEACON_TX_RATE_48_M:
3314 		return MLME_BCN_TX_RATE_CODE_48_M;
3315 	case WMA_BEACON_TX_RATE_54_M:
3316 		return MLME_BCN_TX_RATE_CODE_54_M;
3317 	default:
3318 		return MLME_BCN_TX_RATE_CODE_1_M;
3319 	}
3320 }
3321 
3322 #ifdef WLAN_BCN_RATECODE_ENABLE
3323 /**
3324  * wma_update_beacon_tx_rate_code() - Update bcn_tx_rate_code
3325  * @mlme_obj: pointer to mlme object
3326  *
3327  * Return: none
3328  */
3329 static void  wma_update_beacon_tx_rate_code(struct vdev_mlme_obj *mlme_obj)
3330 {
3331 	uint8_t preamble, nss, rix;
3332 	uint32_t rate_code;
3333 
3334 	rate_code = mlme_obj->mgmt.rate_info.bcn_tx_rate;
3335 
3336 	rix = rate_code & RATECODE_V1_RIX_MASK;
3337 	nss = (rate_code >> RATECODE_V1_NSS_OFFSET) & RATECODE_V1_NSS_MASK;
3338 	preamble = rate_code >> RATECODE_V1_PREAMBLE_OFFSET;
3339 
3340 	mlme_obj->mgmt.rate_info.bcn_tx_rate_code =
3341 		wlan_mlme_assemble_rate_code(preamble, nss, rix);
3342 }
3343 #else
3344 static void wma_update_beacon_tx_rate_code(struct vdev_mlme_obj *mlme_obj)
3345 {
3346 }
3347 #endif
3348 
3349 QDF_STATUS wma_vdev_pre_start(uint8_t vdev_id, bool restart)
3350 {
3351 	tp_wma_handle wma = cds_get_context(QDF_MODULE_ID_WMA);
3352 	struct wma_txrx_node *intr;
3353 	struct mac_context *mac_ctx =  cds_get_context(QDF_MODULE_ID_PE);
3354 	struct wlan_mlme_nss_chains *ini_cfg;
3355 	struct vdev_mlme_obj *mlme_obj;
3356 	struct wlan_objmgr_vdev *vdev;
3357 	struct wlan_channel *des_chan;
3358 	QDF_STATUS status;
3359 	enum coex_btc_chain_mode btc_chain_mode;
3360 	struct wlan_mlme_qos *qos_aggr;
3361 	uint8_t amsdu_val;
3362 
3363 	if (!wma || !mac_ctx)
3364 		return QDF_STATUS_E_FAILURE;
3365 
3366 	intr = wma->interfaces;
3367 	if (!intr) {
3368 		wma_err("Invalid interface");
3369 		return QDF_STATUS_E_FAILURE;
3370 	}
3371 	if (vdev_id >= WLAN_MAX_VDEVS) {
3372 		wma_err("Invalid vdev id");
3373 		return QDF_STATUS_E_INVAL;
3374 	}
3375 	vdev = intr[vdev_id].vdev;
3376 	if (!vdev) {
3377 		wma_err("Invalid vdev");
3378 		return QDF_STATUS_E_FAILURE;
3379 	}
3380 
3381 	mlme_obj = wlan_vdev_mlme_get_cmpt_obj(vdev);
3382 	if (!mlme_obj) {
3383 		wma_err("vdev component object is NULL");
3384 		return QDF_STATUS_E_FAILURE;
3385 	}
3386 	des_chan = vdev->vdev_mlme.des_chan;
3387 
3388 	ini_cfg = mlme_get_ini_vdev_config(vdev);
3389 	if (!ini_cfg) {
3390 		wma_err("nss chain ini config NULL");
3391 		return QDF_STATUS_E_FAILURE;
3392 	}
3393 
3394 	intr[vdev_id].config.gtx_info.gtxRTMask[0] =
3395 		CFG_TGT_DEFAULT_GTX_HT_MASK;
3396 	intr[vdev_id].config.gtx_info.gtxRTMask[1] =
3397 		CFG_TGT_DEFAULT_GTX_VHT_MASK;
3398 
3399 	intr[vdev_id].config.gtx_info.gtxUsrcfg =
3400 		mac_ctx->mlme_cfg->sta.tgt_gtx_usr_cfg;
3401 
3402 	intr[vdev_id].config.gtx_info.gtxPERThreshold =
3403 		CFG_TGT_DEFAULT_GTX_PER_THRESHOLD;
3404 	intr[vdev_id].config.gtx_info.gtxPERMargin =
3405 		CFG_TGT_DEFAULT_GTX_PER_MARGIN;
3406 	intr[vdev_id].config.gtx_info.gtxTPCstep =
3407 		CFG_TGT_DEFAULT_GTX_TPC_STEP;
3408 	intr[vdev_id].config.gtx_info.gtxTPCMin =
3409 		CFG_TGT_DEFAULT_GTX_TPC_MIN;
3410 	intr[vdev_id].config.gtx_info.gtxBWMask =
3411 		CFG_TGT_DEFAULT_GTX_BW_MASK;
3412 	intr[vdev_id].chan_width = des_chan->ch_width;
3413 	intr[vdev_id].ch_freq = des_chan->ch_freq;
3414 	intr[vdev_id].ch_flagext = des_chan->ch_flagext;
3415 
3416 	/*
3417 	 * If the channel has DFS set, flip on radar reporting.
3418 	 *
3419 	 * It may be that this should only be done for hostap operation
3420 	 * as this flag may be interpreted (at some point in the future)
3421 	 * by the firmware as "oh, and please do radar DETECTION."
3422 	 *
3423 	 * If that is ever the case we would insert the decision whether to
3424 	 * enable the firmware flag here.
3425 	 */
3426 	if (QDF_GLOBAL_MONITOR_MODE != cds_get_conparam() &&
3427 	    utils_is_dfs_chan_for_freq(wma->pdev, des_chan->ch_freq))
3428 		mlme_obj->mgmt.generic.disable_hw_ack = true;
3429 
3430 	if (mlme_obj->mgmt.rate_info.bcn_tx_rate) {
3431 		wma_debug("beacon tx rate [%u * 100 Kbps]",
3432 			  mlme_obj->mgmt.rate_info.bcn_tx_rate);
3433 		/*
3434 		 * beacon_tx_rate is in multiples of 100 Kbps.
3435 		 * Convert the data rate to hw rate code.
3436 		 */
3437 		mlme_obj->mgmt.rate_info.bcn_tx_rate =
3438 		wma_get_bcn_rate_code(mlme_obj->mgmt.rate_info.bcn_tx_rate);
3439 		wma_update_beacon_tx_rate_code(mlme_obj);
3440 	}
3441 
3442 	if (!restart) {
3443 		wma_debug("vdev_id: %d, unpausing tx_ll_queue at VDEV_START",
3444 			 vdev_id);
3445 
3446 		cdp_fc_vdev_unpause(cds_get_context(QDF_MODULE_ID_SOC),
3447 				    vdev_id, 0xffffffff, 0);
3448 		wma_vdev_update_pause_bitmap(vdev_id, 0);
3449 	}
3450 
3451 	/* Send the dynamic nss chain params before vdev start to fw */
3452 	if (wma->dynamic_nss_chains_support && !restart)
3453 		wma_vdev_nss_chain_params_send(vdev_id, ini_cfg);
3454 
3455 	status = ucfg_coex_psoc_get_btc_chain_mode(wma->psoc, &btc_chain_mode);
3456 	if (QDF_IS_STATUS_ERROR(status)) {
3457 		wma_err("Failed to get btc chain mode");
3458 		return QDF_STATUS_E_FAILURE;
3459 	}
3460 
3461 	if (btc_chain_mode != WLAN_COEX_BTC_CHAIN_MODE_UNSETTLED) {
3462 		status = ucfg_coex_send_btc_chain_mode(vdev, btc_chain_mode);
3463 		if (QDF_IS_STATUS_ERROR(status)) {
3464 			wma_err("Failed to send btc chain mode %d",
3465 				btc_chain_mode);
3466 			return QDF_STATUS_E_FAILURE;
3467 		}
3468 	}
3469 
3470 	qos_aggr = &mac_ctx->mlme_cfg->qos_mlme_params;
3471 	status = wma_set_tx_rx_aggr_size(vdev_id, qos_aggr->tx_aggregation_size,
3472 					 qos_aggr->rx_aggregation_size,
3473 					 WMI_VDEV_CUSTOM_AGGR_TYPE_AMPDU);
3474 	if (QDF_IS_STATUS_ERROR(status))
3475 		wma_err("failed to set aggregation sizes(status = %d)", status);
3476 
3477 	if (mac_ctx->is_usr_cfg_amsdu_enabled) {
3478 		status = wlan_mlme_get_max_amsdu_num(wma->psoc, &amsdu_val);
3479 		if (QDF_IS_STATUS_ERROR(status)) {
3480 			wma_err("failed to get amsdu aggr.size(status = %d)",
3481 				status);
3482 		} else {
3483 			status = wma_set_tx_rx_aggr_size(
3484 					vdev_id, amsdu_val, amsdu_val,
3485 					WMI_VDEV_CUSTOM_AGGR_TYPE_AMSDU);
3486 			if (QDF_IS_STATUS_ERROR(status))
3487 				wma_err("failed to set amsdu aggr.size(status = %d)",
3488 					status);
3489 		}
3490 	}
3491 
3492 	if (mlme_obj->mgmt.generic.type == WMI_VDEV_TYPE_STA) {
3493 		status = wma_set_tx_rx_aggr_size_per_ac(wma, vdev_id, qos_aggr,
3494 					WMI_VDEV_CUSTOM_AGGR_TYPE_AMPDU);
3495 
3496 		if (QDF_IS_STATUS_ERROR(status))
3497 			wma_err("failed to set aggr size per ac(status = %d)",
3498 				status);
3499 	}
3500 
3501 	return QDF_STATUS_SUCCESS;
3502 }
3503 
3504 /**
3505  * wma_peer_assoc_conf_handler() - peer assoc conf handler
3506  * @handle: wma handle
3507  * @cmd_param_info: event buffer
3508  * @len: buffer length
3509  *
3510  * Return: 0 for success or error code
3511  */
3512 int wma_peer_assoc_conf_handler(void *handle, uint8_t *cmd_param_info,
3513 				uint32_t len)
3514 {
3515 	tp_wma_handle wma = (tp_wma_handle) handle;
3516 	WMI_PEER_ASSOC_CONF_EVENTID_param_tlvs *param_buf;
3517 	wmi_peer_assoc_conf_event_fixed_param *event;
3518 	struct wma_target_req *req_msg;
3519 	uint8_t macaddr[QDF_MAC_ADDR_SIZE];
3520 	int status = 0;
3521 
3522 	param_buf = (WMI_PEER_ASSOC_CONF_EVENTID_param_tlvs *) cmd_param_info;
3523 	if (!param_buf) {
3524 		wma_err("Invalid peer assoc conf event buffer");
3525 		return -EINVAL;
3526 	}
3527 
3528 	event = param_buf->fixed_param;
3529 	if (!event) {
3530 		wma_err("Invalid peer assoc conf event buffer");
3531 		return -EINVAL;
3532 	}
3533 
3534 	WMI_MAC_ADDR_TO_CHAR_ARRAY(&event->peer_macaddr, macaddr);
3535 	wma_debug("peer assoc conf for vdev:%d mac="QDF_MAC_ADDR_FMT,
3536 		 event->vdev_id, QDF_MAC_ADDR_REF(macaddr));
3537 
3538 	req_msg = wma_find_req(wma, event->vdev_id,
3539 			       WMA_PEER_ASSOC_CNF_START, NULL);
3540 
3541 	if (!req_msg) {
3542 		wma_err("Failed to lookup request message for vdev %d",
3543 			event->vdev_id);
3544 		return -EINVAL;
3545 	}
3546 
3547 	qdf_mc_timer_stop(&req_msg->event_timeout);
3548 
3549 	if (req_msg->msg_type == WMA_ADD_STA_REQ) {
3550 		tpAddStaParams params = (tpAddStaParams)req_msg->user_data;
3551 
3552 		if (!params) {
3553 			wma_err("add STA params is NULL for vdev %d",
3554 				 event->vdev_id);
3555 			status = -EINVAL;
3556 			goto free_req_msg;
3557 		}
3558 
3559 		/* peer assoc conf event means the cmd succeeds */
3560 		params->status = event->status;
3561 		wma_debug("Send ADD_STA_RSP: statype %d vdev_id %d aid %d bssid "QDF_MAC_ADDR_FMT" status %d",
3562 			 params->staType, params->smesessionId,
3563 			 params->assocId, QDF_MAC_ADDR_REF(params->bssId),
3564 			 params->status);
3565 		wma_send_msg_high_priority(wma, WMA_ADD_STA_RSP,
3566 					   (void *)params, 0);
3567 	} else if (req_msg->msg_type == WMA_ADD_BSS_REQ) {
3568 		wma_send_add_bss_resp(wma, event->vdev_id, event->status);
3569 	} else {
3570 		wma_err("Unhandled request message type: %d", req_msg->msg_type);
3571 	}
3572 
3573 free_req_msg:
3574 	qdf_mc_timer_destroy(&req_msg->event_timeout);
3575 	qdf_mem_free(req_msg);
3576 
3577 	return status;
3578 }
3579 
3580 int wma_peer_create_confirm_handler(void *handle, uint8_t *evt_param_info,
3581 				    uint32_t len)
3582 {
3583 	tp_wma_handle wma = (tp_wma_handle)handle;
3584 	wmi_peer_create_conf_event_fixed_param *peer_create_rsp;
3585 	WMI_PEER_CREATE_CONF_EVENTID_param_tlvs *param_buf;
3586 	struct wma_target_req *req_msg = NULL;
3587 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
3588 	struct peer_create_rsp_params *rsp_data;
3589 	void *dp_soc = cds_get_context(QDF_MODULE_ID_SOC);
3590 	struct qdf_mac_addr peer_mac;
3591 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
3592 	int ret = -EINVAL;
3593 	uint8_t req_msg_type;
3594 	struct wlan_objmgr_peer *peer;
3595 	struct cdp_peer_setup_info peer_info = {0};
3596 
3597 	param_buf = (WMI_PEER_CREATE_CONF_EVENTID_param_tlvs *)evt_param_info;
3598 	if (!param_buf) {
3599 		wma_err("Invalid peer create conf evt buffer");
3600 		return -EINVAL;
3601 	}
3602 
3603 	peer_create_rsp = param_buf->fixed_param;
3604 
3605 	WMI_MAC_ADDR_TO_CHAR_ARRAY(&peer_create_rsp->peer_macaddr,
3606 				   peer_mac.bytes);
3607 	if (qdf_is_macaddr_zero(&peer_mac) ||
3608 	    qdf_is_macaddr_broadcast(&peer_mac) ||
3609 	    qdf_is_macaddr_group(&peer_mac)) {
3610 		wma_err("Invalid bssid");
3611 		return -EINVAL;
3612 	}
3613 
3614 	wma_debug("vdev:%d Peer create confirm for bssid: " QDF_MAC_ADDR_FMT,
3615 		  peer_create_rsp->vdev_id, QDF_MAC_ADDR_REF(peer_mac.bytes));
3616 	req_msg = wma_find_remove_req_msgtype(wma, peer_create_rsp->vdev_id,
3617 					      WMA_PEER_CREATE_REQ);
3618 	if (!req_msg) {
3619 		wma_debug("vdev:%d Failed to lookup peer create request msg",
3620 			  peer_create_rsp->vdev_id);
3621 		return -EINVAL;
3622 	}
3623 
3624 	rsp_data = (struct peer_create_rsp_params *)req_msg->user_data;
3625 	req_msg_type = req_msg->type;
3626 
3627 	qdf_mc_timer_stop(&req_msg->event_timeout);
3628 	qdf_mc_timer_destroy(&req_msg->event_timeout);
3629 	qdf_mem_free(rsp_data);
3630 	qdf_mem_free(req_msg);
3631 
3632 	if (req_msg_type == WMA_PASN_PEER_CREATE_RESPONSE) {
3633 		wma_pasn_handle_peer_create_conf(wma, &peer_mac,
3634 						 peer_create_rsp->status,
3635 						 peer_create_rsp->vdev_id);
3636 		wma_release_wakelock(&wma->wmi_cmd_rsp_wake_lock);
3637 		return 0;
3638 	}
3639 
3640 	wma_release_wakelock(&wma->wmi_cmd_rsp_wake_lock);
3641 	if (!peer_create_rsp->status) {
3642 		if (!dp_soc) {
3643 			wma_err("DP SOC context is NULL");
3644 			goto fail;
3645 		}
3646 
3647 		peer = wlan_objmgr_get_peer_by_mac(wma->psoc, peer_mac.bytes,
3648 						   WLAN_LEGACY_WMA_ID);
3649 		if (!peer) {
3650 			status = QDF_STATUS_E_FAILURE;
3651 			goto fail;
3652 		}
3653 
3654 		wma_peer_setup_fill_info(wma->psoc, peer, &peer_info);
3655 		wma_peer_tbl_trans_add_entry(peer, true, &peer_info);
3656 		wma_cdp_peer_setup(dp_soc, peer_create_rsp->vdev_id,
3657 				   peer, &peer_info);
3658 		wlan_objmgr_peer_release_ref(peer, WLAN_LEGACY_WMA_ID);
3659 
3660 		status = QDF_STATUS_SUCCESS;
3661 		ret = 0;
3662 	}
3663 
3664 fail:
3665 	if (QDF_IS_STATUS_ERROR(status))
3666 		wma_remove_peer(wma, peer_mac.bytes, peer_create_rsp->vdev_id,
3667 				(peer_create_rsp->status > 0) ? true : false);
3668 
3669 	if (mac)
3670 		lim_send_peer_create_resp(mac, peer_create_rsp->vdev_id, status,
3671 					  peer_mac.bytes);
3672 
3673 	return ret;
3674 }
3675 
3676 #ifdef FEATURE_WDS
3677 /*
3678  * wma_cdp_cp_peer_del_response - handle peer delete response
3679  * @psoc: psoc object pointer
3680  * @mac_addr: Mac address of the peer
3681  * @vdev_id: id of virtual device object
3682  *
3683  * when peer map v2 is enabled, cdp_peer_teardown() does not remove the AST from
3684  * hash table. Call cdp_cp_peer_del_response() when peer delete response is
3685  * received from fw to delete the AST entry from the AST hash.
3686  *
3687  * Return: None
3688  */
3689 static void
3690 wma_cdp_cp_peer_del_response(struct wlan_objmgr_psoc *psoc,
3691 			     uint8_t *peer_mac, uint8_t vdev_id)
3692 {
3693 	ol_txrx_soc_handle soc_txrx_handle;
3694 
3695 	soc_txrx_handle = wlan_psoc_get_dp_handle(psoc);
3696 	cdp_cp_peer_del_response(soc_txrx_handle, vdev_id, peer_mac);
3697 }
3698 #else
3699 static void
3700 wma_cdp_cp_peer_del_response(struct wlan_objmgr_psoc *psoc,
3701 			     uint8_t *peer_mac, uint8_t vdev_id)
3702 {
3703 }
3704 #endif
3705 
3706 /**
3707  * wma_peer_delete_handler() - peer delete response handler
3708  * @handle: wma handle
3709  * @cmd_param_info: event buffer
3710  * @len: buffer length
3711  *
3712  * Return: 0 for success or error code
3713  */
3714 int wma_peer_delete_handler(void *handle, uint8_t *cmd_param_info,
3715 				uint32_t len)
3716 {
3717 	tp_wma_handle wma = (tp_wma_handle) handle;
3718 	WMI_PEER_DELETE_RESP_EVENTID_param_tlvs *param_buf;
3719 	wmi_peer_delete_cmd_fixed_param *event;
3720 	struct wma_target_req *req_msg;
3721 	tDeleteStaParams *del_sta;
3722 	uint8_t macaddr[QDF_MAC_ADDR_SIZE];
3723 	int status = 0;
3724 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
3725 
3726 	if (!mac) {
3727 		wma_err("mac context is null");
3728 		return -EINVAL;
3729 	}
3730 	param_buf = (WMI_PEER_DELETE_RESP_EVENTID_param_tlvs *)cmd_param_info;
3731 	if (!param_buf) {
3732 		wma_err("Invalid vdev delete event buffer");
3733 		return -EINVAL;
3734 	}
3735 
3736 	event = (wmi_peer_delete_cmd_fixed_param *)param_buf->fixed_param;
3737 	if (!event) {
3738 		wma_err("Invalid vdev delete event buffer");
3739 		return -EINVAL;
3740 	}
3741 
3742 	WMI_MAC_ADDR_TO_CHAR_ARRAY(&event->peer_macaddr, macaddr);
3743 	wma_debug("Peer Delete Response, vdev %d Peer "QDF_MAC_ADDR_FMT,
3744 			event->vdev_id, QDF_MAC_ADDR_REF(macaddr));
3745 	wlan_roam_debug_log(event->vdev_id, DEBUG_PEER_DELETE_RESP,
3746 			    DEBUG_INVALID_PEER_ID, macaddr, NULL, 0, 0);
3747 	req_msg = wma_find_remove_req_msgtype(wma, event->vdev_id,
3748 					WMA_DELETE_STA_REQ);
3749 	if (!req_msg) {
3750 		wma_debug("Peer Delete response is not handled");
3751 		return -EINVAL;
3752 	}
3753 
3754 	wma_release_wakelock(&wma->wmi_cmd_rsp_wake_lock);
3755 
3756 	/* Cleanup timeout handler */
3757 	qdf_mc_timer_stop(&req_msg->event_timeout);
3758 	qdf_mc_timer_destroy(&req_msg->event_timeout);
3759 
3760 	if (req_msg->type == WMA_DELETE_STA_RSP_START) {
3761 		del_sta = req_msg->user_data;
3762 		if (del_sta->respReqd) {
3763 			wma_debug("Sending peer del rsp to umac");
3764 			wma_send_msg_high_priority(wma, WMA_DELETE_STA_RSP,
3765 				(void *)del_sta, QDF_STATUS_SUCCESS);
3766 		} else {
3767 			qdf_mem_free(del_sta);
3768 		}
3769 	} else if (req_msg->type == WMA_DEL_P2P_SELF_STA_RSP_START) {
3770 		struct del_sta_self_rsp_params *data;
3771 
3772 		data = (struct del_sta_self_rsp_params *)req_msg->user_data;
3773 		wma_debug("Calling vdev detach handler");
3774 		wma_handle_vdev_detach(wma, data->self_sta_param);
3775 		mlme_vdev_self_peer_delete_resp(data->self_sta_param);
3776 		qdf_mem_free(data);
3777 	} else if (req_msg->type == WMA_SET_LINK_PEER_RSP ||
3778 		   req_msg->type == WMA_DELETE_PEER_RSP) {
3779 		wma_send_vdev_down_req(wma, req_msg->user_data);
3780 	} else if (req_msg->type == WMA_DELETE_STA_CONNECT_RSP) {
3781 		wma_debug("wma delete peer completed vdev %d",
3782 			  req_msg->vdev_id);
3783 		lim_cm_send_connect_rsp(mac, NULL, req_msg->user_data,
3784 					CM_GENERIC_FAILURE,
3785 					QDF_STATUS_E_FAILURE, 0, false);
3786 		cm_free_join_req(req_msg->user_data);
3787 	}
3788 
3789 	wma_cdp_cp_peer_del_response(wma->psoc, macaddr, event->vdev_id);
3790 	qdf_mem_free(req_msg);
3791 
3792 	return status;
3793 }
3794 
3795 static
3796 void wma_trigger_recovery_assert_on_fw_timeout(uint16_t wma_msg,
3797 					       enum qdf_hang_reason reason)
3798 {
3799 	wma_err("%s timed out, triggering recovery",
3800 		 mac_trace_get_wma_msg_string(wma_msg));
3801 	qdf_trigger_self_recovery(NULL, reason);
3802 }
3803 
3804 static inline bool wma_crash_on_fw_timeout(bool crash_enabled)
3805 {
3806 	/* Discard FW timeouts and dont crash during SSR */
3807 	if (cds_is_driver_recovering())
3808 		return false;
3809 
3810 	/* Firmware is down send failure response */
3811 	if (cds_is_fw_down())
3812 		return false;
3813 
3814 	if (cds_is_driver_unloading())
3815 		return false;
3816 
3817 	return crash_enabled;
3818 }
3819 
3820 /**
3821  * wma_hold_req_timer() - wma hold request timeout function
3822  * @data: target request params
3823  *
3824  * Return: none
3825  */
3826 void wma_hold_req_timer(void *data)
3827 {
3828 	tp_wma_handle wma;
3829 	struct wma_target_req *tgt_req = (struct wma_target_req *)data;
3830 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
3831 	QDF_STATUS status;
3832 
3833 	wma = cds_get_context(QDF_MODULE_ID_WMA);
3834 	if (!wma)
3835 		return;
3836 
3837 	status = wma_find_req_on_timer_expiry(wma, tgt_req);
3838 
3839 	if (QDF_IS_STATUS_ERROR(status)) {
3840 		/*
3841 		 * if find request failed, then firmware rsp should have
3842 		 * consumed the buffer. Do not free.
3843 		 */
3844 		wma_debug("Failed to lookup request message - %pK", tgt_req);
3845 		return;
3846 	}
3847 	wma_alert("request %d is timed out for vdev_id - %d",
3848 		 tgt_req->msg_type, tgt_req->vdev_id);
3849 
3850 	if (tgt_req->msg_type == WMA_ADD_STA_REQ) {
3851 		tpAddStaParams params = (tpAddStaParams) tgt_req->user_data;
3852 
3853 		params->status = QDF_STATUS_E_TIMEOUT;
3854 		wma_alert("WMA_ADD_STA_REQ timed out");
3855 		wma_debug("Sending add sta rsp to umac (mac:"QDF_MAC_ADDR_FMT", status:%d)",
3856 			 QDF_MAC_ADDR_REF(params->staMac), params->status);
3857 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3858 			wma_trigger_recovery_assert_on_fw_timeout(
3859 				WMA_ADD_STA_REQ,
3860 				QDF_AP_STA_CONNECT_REQ_TIMEOUT);
3861 		wma_send_msg_high_priority(wma, WMA_ADD_STA_RSP,
3862 					   (void *)params, 0);
3863 	} else if (tgt_req->msg_type == WMA_ADD_BSS_REQ) {
3864 
3865 		wma_alert("WMA_ADD_BSS_REQ timed out");
3866 		wma_debug("Sending add bss rsp to umac (vdev %d, status:%d)",
3867 			 tgt_req->vdev_id, QDF_STATUS_E_TIMEOUT);
3868 
3869 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3870 			wma_trigger_recovery_assert_on_fw_timeout(
3871 				WMA_ADD_BSS_REQ,
3872 				QDF_STA_AP_CONNECT_REQ_TIMEOUT);
3873 
3874 		wma_send_add_bss_resp(wma, tgt_req->vdev_id,
3875 				      QDF_STATUS_E_TIMEOUT);
3876 	} else if ((tgt_req->msg_type == WMA_DELETE_STA_REQ) &&
3877 		(tgt_req->type == WMA_DELETE_STA_RSP_START)) {
3878 		tpDeleteStaParams params =
3879 				(tpDeleteStaParams) tgt_req->user_data;
3880 		params->status = QDF_STATUS_E_TIMEOUT;
3881 		wma_err("WMA_DEL_STA_REQ timed out");
3882 		wma_debug("Sending del sta rsp to umac (mac:"QDF_MAC_ADDR_FMT", status:%d)",
3883 			 QDF_MAC_ADDR_REF(params->staMac), params->status);
3884 
3885 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3886 			wma_trigger_recovery_assert_on_fw_timeout(
3887 				WMA_DELETE_STA_REQ,
3888 				QDF_PEER_DELETION_TIMEDOUT);
3889 		wma_send_msg_high_priority(wma, WMA_DELETE_STA_RSP,
3890 					   (void *)params, 0);
3891 	} else if ((tgt_req->msg_type == WMA_DELETE_STA_REQ) &&
3892 		(tgt_req->type == WMA_DEL_P2P_SELF_STA_RSP_START)) {
3893 		struct del_sta_self_rsp_params *del_sta;
3894 
3895 		del_sta = (struct del_sta_self_rsp_params *)tgt_req->user_data;
3896 
3897 		del_sta->self_sta_param->status = QDF_STATUS_E_TIMEOUT;
3898 		wma_alert("wma delete sta p2p request timed out");
3899 
3900 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3901 			wma_trigger_recovery_assert_on_fw_timeout(
3902 				WMA_DELETE_STA_REQ,
3903 				QDF_PEER_DELETION_TIMEDOUT);
3904 		wma_handle_vdev_detach(wma, del_sta->self_sta_param);
3905 		mlme_vdev_self_peer_delete_resp(del_sta->self_sta_param);
3906 		qdf_mem_free(tgt_req->user_data);
3907 	} else if ((tgt_req->msg_type == WMA_DELETE_STA_REQ) &&
3908 		   (tgt_req->type == WMA_SET_LINK_PEER_RSP ||
3909 		    tgt_req->type == WMA_DELETE_PEER_RSP)) {
3910 		struct del_bss_resp *params =
3911 			(struct del_bss_resp *)tgt_req->user_data;
3912 
3913 		params->status = QDF_STATUS_E_TIMEOUT;
3914 		wma_err("wma delete peer for del bss req timed out");
3915 
3916 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3917 			wma_trigger_recovery_assert_on_fw_timeout(
3918 				WMA_DELETE_STA_REQ,
3919 				QDF_PEER_DELETION_TIMEDOUT);
3920 		wma_send_vdev_down_req(wma, params);
3921 	} else if ((tgt_req->msg_type == WMA_DELETE_STA_REQ) &&
3922 		   (tgt_req->type == WMA_DELETE_STA_CONNECT_RSP)) {
3923 		wma_err("wma delete peer timed out vdev %d",
3924 			tgt_req->vdev_id);
3925 
3926 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3927 			wma_trigger_recovery_assert_on_fw_timeout(
3928 				WMA_DELETE_STA_REQ,
3929 				QDF_PEER_DELETION_TIMEDOUT);
3930 		if (!mac) {
3931 			wma_err("mac: Null Pointer Error");
3932 			goto timer_destroy;
3933 		}
3934 		lim_cm_send_connect_rsp(mac, NULL, tgt_req->user_data,
3935 					CM_GENERIC_FAILURE,
3936 					QDF_STATUS_E_FAILURE, 0, false);
3937 		cm_free_join_req(tgt_req->user_data);
3938 	} else if ((tgt_req->msg_type == SIR_HAL_PDEV_SET_HW_MODE) &&
3939 			(tgt_req->type == WMA_PDEV_SET_HW_MODE_RESP)) {
3940 		struct sir_set_hw_mode_resp *params =
3941 			qdf_mem_malloc(sizeof(*params));
3942 
3943 		wma_err("set hw mode req timed out");
3944 
3945 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3946 			wma_trigger_recovery_assert_on_fw_timeout(
3947 			  SIR_HAL_PDEV_SET_HW_MODE,
3948 			  QDF_MAC_HW_MODE_CHANGE_TIMEOUT);
3949 		if (!params)
3950 			goto timer_destroy;
3951 
3952 		params->status = SET_HW_MODE_STATUS_ECANCELED;
3953 		params->cfgd_hw_mode_index = 0;
3954 		params->num_vdev_mac_entries = 0;
3955 		wma_send_msg_high_priority(wma, SIR_HAL_PDEV_SET_HW_MODE_RESP,
3956 					   params, 0);
3957 	} else if ((tgt_req->msg_type == SIR_HAL_PDEV_DUAL_MAC_CFG_REQ) &&
3958 			(tgt_req->type == WMA_PDEV_MAC_CFG_RESP)) {
3959 		struct sir_dual_mac_config_resp *resp =
3960 						qdf_mem_malloc(sizeof(*resp));
3961 
3962 		wma_err("set dual mac config timeout");
3963 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3964 			wma_trigger_recovery_assert_on_fw_timeout(
3965 				SIR_HAL_PDEV_DUAL_MAC_CFG_REQ,
3966 				QDF_MAC_HW_MODE_CONFIG_TIMEOUT);
3967 		if (!resp)
3968 			goto timer_destroy;
3969 
3970 		resp->status = SET_HW_MODE_STATUS_ECANCELED;
3971 		wma_send_msg_high_priority(wma, SIR_HAL_PDEV_MAC_CFG_RESP,
3972 					   resp, 0);
3973 	} else if ((tgt_req->msg_type == WMA_PEER_CREATE_REQ) &&
3974 		   (tgt_req->type == WMA_PEER_CREATE_RESPONSE)) {
3975 		struct peer_create_rsp_params *peer_create_rsp;
3976 		struct qdf_mac_addr *peer_mac;
3977 
3978 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
3979 			wma_trigger_recovery_assert_on_fw_timeout(
3980 				WMA_PEER_CREATE_RESPONSE,
3981 				WMA_PEER_CREATE_RESPONSE_TIMEOUT);
3982 
3983 		peer_create_rsp =
3984 			(struct peer_create_rsp_params *)tgt_req->user_data;
3985 		peer_mac = &peer_create_rsp->peer_mac;
3986 		wma_remove_peer(wma, peer_mac->bytes,
3987 				tgt_req->vdev_id, false);
3988 		if (!mac) {
3989 			qdf_mem_free(tgt_req->user_data);
3990 			goto timer_destroy;
3991 		}
3992 
3993 		lim_send_peer_create_resp(mac, tgt_req->vdev_id,
3994 					  QDF_STATUS_E_TIMEOUT,
3995 					  (uint8_t *)tgt_req->user_data);
3996 		qdf_mem_free(tgt_req->user_data);
3997 	} else if ((tgt_req->msg_type == WMA_PEER_CREATE_REQ) &&
3998 		   (tgt_req->type == WMA_PASN_PEER_CREATE_RESPONSE)) {
3999 		struct peer_create_rsp_params *peer_create_rsp;
4000 		struct qdf_mac_addr *peer_mac;
4001 
4002 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
4003 			wma_trigger_recovery_assert_on_fw_timeout(
4004 				WMA_PEER_CREATE_RESPONSE,
4005 				WMA_PEER_CREATE_RESPONSE_TIMEOUT);
4006 
4007 		peer_create_rsp =
4008 			(struct peer_create_rsp_params *)tgt_req->user_data;
4009 		peer_mac = &peer_create_rsp->peer_mac;
4010 
4011 		wma_pasn_handle_peer_create_conf(
4012 				wma, peer_mac, QDF_STATUS_E_TIMEOUT,
4013 				tgt_req->vdev_id);
4014 		qdf_mem_free(tgt_req->user_data);
4015 	} else if (tgt_req->msg_type == WMA_PASN_PEER_DELETE_REQUEST &&
4016 		   tgt_req->type == WMA_PASN_PEER_DELETE_RESPONSE) {
4017 		wma_err("PASN Peer delete all resp not received. vdev:%d",
4018 			tgt_req->vdev_id);
4019 		if (wma_crash_on_fw_timeout(wma->fw_timeout_crash))
4020 			wma_trigger_recovery_assert_on_fw_timeout(
4021 				WMA_PASN_PEER_DELETE_RESPONSE,
4022 				WMA_PEER_DELETE_RESPONSE_TIMEOUT);
4023 
4024 		wma_resume_vdev_delete(wma, tgt_req->vdev_id);
4025 	} else {
4026 		wma_err("Unhandled timeout for msg_type:%d and type:%d",
4027 				tgt_req->msg_type, tgt_req->type);
4028 		QDF_BUG(0);
4029 	}
4030 
4031 timer_destroy:
4032 	qdf_mc_timer_destroy(&tgt_req->event_timeout);
4033 	qdf_mem_free(tgt_req);
4034 }
4035 
4036 /**
4037  * wma_fill_hold_req() - fill wma request
4038  * @wma: wma handle
4039  * @vdev_id: vdev id
4040  * @msg_type: message type
4041  * @type: request type
4042  * @params: request params
4043  * @timeout: timeout value
4044  *
4045  * Return: wma_target_req ptr
4046  */
4047 struct wma_target_req *wma_fill_hold_req(tp_wma_handle wma,
4048 					 uint8_t vdev_id,
4049 					 uint32_t msg_type, uint8_t type,
4050 					 void *params, uint32_t timeout)
4051 {
4052 	struct wma_target_req *req;
4053 	QDF_STATUS status;
4054 
4055 	req = qdf_mem_malloc(sizeof(*req));
4056 	if (!req)
4057 		return NULL;
4058 
4059 	wma_debug("vdev_id %d msg %d type %d", vdev_id, msg_type, type);
4060 	qdf_spin_lock_bh(&wma->wma_hold_req_q_lock);
4061 	req->vdev_id = vdev_id;
4062 	req->msg_type = msg_type;
4063 	req->type = type;
4064 	req->user_data = params;
4065 	status = qdf_list_insert_back(&wma->wma_hold_req_queue, &req->node);
4066 	if (QDF_STATUS_SUCCESS != status) {
4067 		qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
4068 		wma_err("Failed add request in queue");
4069 		qdf_mem_free(req);
4070 		return NULL;
4071 	}
4072 	qdf_spin_unlock_bh(&wma->wma_hold_req_q_lock);
4073 	qdf_mc_timer_init(&req->event_timeout, QDF_TIMER_TYPE_SW,
4074 			  wma_hold_req_timer, req);
4075 	qdf_mc_timer_start(&req->event_timeout, timeout);
4076 	return req;
4077 }
4078 
4079 void wma_remove_peer_req(tp_wma_handle wma, uint8_t vdev_id,
4080 			 uint8_t type, struct qdf_mac_addr *peer_addr)
4081 {
4082 	struct wma_target_req *req_msg;
4083 
4084 	wma_debug("Remove req for vdev: %d type: %d", vdev_id, type);
4085 	req_msg = wma_find_req(wma, vdev_id, type, peer_addr);
4086 	if (!req_msg) {
4087 		wma_err("target req not found for vdev: %d type: %d",
4088 			vdev_id, type);
4089 		return;
4090 	}
4091 
4092 	qdf_mc_timer_stop(&req_msg->event_timeout);
4093 	qdf_mc_timer_destroy(&req_msg->event_timeout);
4094 	qdf_mem_free(req_msg);
4095 }
4096 
4097 /**
4098  * wma_remove_req() - remove request
4099  * @wma: wma handle
4100  * @vdev_id: vdev id
4101  * @type: type
4102  *
4103  * Return: none
4104  */
4105 void wma_remove_req(tp_wma_handle wma, uint8_t vdev_id,
4106 		    uint8_t type)
4107 {
4108 	struct wma_target_req *req_msg;
4109 
4110 	wma_debug("Remove req for vdev: %d type: %d", vdev_id, type);
4111 	req_msg = wma_find_req(wma, vdev_id, type, NULL);
4112 	if (!req_msg) {
4113 		wma_err("target req not found for vdev: %d type: %d",
4114 			 vdev_id, type);
4115 		return;
4116 	}
4117 
4118 	qdf_mc_timer_stop(&req_msg->event_timeout);
4119 	qdf_mc_timer_destroy(&req_msg->event_timeout);
4120 	qdf_mem_free(req_msg);
4121 }
4122 
4123 #define MAX_VDEV_SET_BSS_PARAMS 5
4124 /* params being sent:
4125  * 1.wmi_vdev_param_beacon_interval
4126  * 2.wmi_vdev_param_dtim_period
4127  * 3.wmi_vdev_param_tx_pwrlimit
4128  * 4.wmi_vdev_param_slot_time
4129  * 5.wmi_vdev_param_protection_mode
4130  */
4131 
4132 /**
4133  * wma_vdev_set_bss_params() - BSS set params functions
4134  * @wma: wma handle
4135  * @vdev_id: vdev id
4136  * @beaconInterval: beacon interval
4137  * @dtimPeriod: DTIM period
4138  * @shortSlotTimeSupported: short slot time
4139  * @llbCoexist: llbCoexist
4140  * @maxTxPower: max tx power
4141  * @bss_max_idle_period: BSS max idle period
4142  *
4143  * Return: QDF_STATUS
4144  */
4145 static QDF_STATUS
4146 wma_vdev_set_bss_params(tp_wma_handle wma, int vdev_id,
4147 			tSirMacBeaconInterval beaconInterval,
4148 			uint8_t dtimPeriod, uint8_t shortSlotTimeSupported,
4149 			uint8_t llbCoexist, int8_t maxTxPower,
4150 			uint16_t bss_max_idle_period)
4151 {
4152 	uint32_t slot_time;
4153 	struct wma_txrx_node *intr = wma->interfaces;
4154 	struct dev_set_param setparam[MAX_VDEV_SET_BSS_PARAMS];
4155 	uint8_t index = 0;
4156 	enum ieee80211_protmode prot_mode;
4157 	QDF_STATUS ret;
4158 
4159 	ret = QDF_STATUS_E_FAILURE;
4160 	/* Beacon Interval setting */
4161 	ret = mlme_check_index_setparam(setparam,
4162 					wmi_vdev_param_beacon_interval,
4163 					beaconInterval, index++,
4164 					MAX_VDEV_SET_BSS_PARAMS);
4165 	if (QDF_IS_STATUS_ERROR(ret)) {
4166 		wma_debug("failed to send wmi_vdev_param_beacon_interval to fw");
4167 		goto error;
4168 	}
4169 
4170 	ret = wmi_unified_vdev_set_gtx_cfg_send(wma->wmi_handle, vdev_id,
4171 						&intr[vdev_id].config.gtx_info);
4172 	if (QDF_IS_STATUS_ERROR(ret)) {
4173 		wma_err("failed to set vdev gtx cfg");
4174 		goto error;
4175 	}
4176 	ret = mlme_check_index_setparam(setparam, wmi_vdev_param_dtim_period,
4177 					dtimPeriod, index++,
4178 					MAX_VDEV_SET_BSS_PARAMS);
4179 	if (QDF_IS_STATUS_ERROR(ret)) {
4180 		wma_debug("failed to send wmi_vdev_param_dtim_period fw");
4181 		goto error;
4182 	}
4183 	intr[vdev_id].dtimPeriod = dtimPeriod;
4184 
4185 	if (!wlan_reg_is_ext_tpc_supported(wma->psoc)) {
4186 		if (!maxTxPower)
4187 			wma_warn("Setting Tx power limit to 0");
4188 
4189 		wma_nofl_debug("TXP[W][set_bss_params]: %d", maxTxPower);
4190 
4191 		if (maxTxPower != INVALID_TXPOWER) {
4192 			ret = mlme_check_index_setparam(
4193 						setparam,
4194 						wmi_vdev_param_tx_pwrlimit,
4195 						maxTxPower, index++,
4196 						MAX_VDEV_SET_BSS_PARAMS);
4197 			if (QDF_IS_STATUS_ERROR(ret)) {
4198 				wma_debug("failed to send wmi_vdev_param_tx_pwrlimit to fw");
4199 				goto error;
4200 			}
4201 		} else {
4202 			wma_err("Invalid max Tx power");
4203 		}
4204 	}
4205 	/* Slot time */
4206 	if (shortSlotTimeSupported)
4207 		slot_time = WMI_VDEV_SLOT_TIME_SHORT;
4208 	else
4209 		slot_time = WMI_VDEV_SLOT_TIME_LONG;
4210 	ret = mlme_check_index_setparam(setparam, wmi_vdev_param_slot_time,
4211 					slot_time, index++,
4212 					MAX_VDEV_SET_BSS_PARAMS);
4213 	if (QDF_IS_STATUS_ERROR(ret)) {
4214 		wma_debug("failed to send wmi_vdev_param_slot_time to fw");
4215 		goto error;
4216 	}
4217 	/* Initialize protection mode in case of coexistence */
4218 	prot_mode = llbCoexist ? IEEE80211_PROT_CTSONLY : IEEE80211_PROT_NONE;
4219 	ret = mlme_check_index_setparam(setparam,
4220 					wmi_vdev_param_protection_mode,
4221 					prot_mode, index++,
4222 					MAX_VDEV_SET_BSS_PARAMS);
4223 	if (QDF_IS_STATUS_ERROR(ret)) {
4224 		wma_debug("failed to send wmi_vdev_param_protection_mode to fw");
4225 		goto error;
4226 	}
4227 	ret = wma_send_multi_pdev_vdev_set_params(MLME_VDEV_SETPARAM,
4228 						  vdev_id, setparam, index);
4229 	if (QDF_IS_STATUS_ERROR(ret)) {
4230 		wma_err("Failed to set BEACON/DTIM_PERIOD/PWRLIMIT/SLOTTIME/PROTECTION params");
4231 		goto error;
4232 	}
4233 	mlme_set_max_reg_power(intr[vdev_id].vdev, maxTxPower);
4234 	if (bss_max_idle_period)
4235 		wma_set_sta_keep_alive(
4236 				wma, vdev_id,
4237 				SIR_KEEP_ALIVE_NULL_PKT,
4238 				bss_max_idle_period,
4239 				NULL, NULL, NULL);
4240 error:
4241 	return ret;
4242 }
4243 
4244 static void wma_set_mgmt_frame_protection(tp_wma_handle wma)
4245 {
4246 	struct pdev_params param = {0};
4247 	QDF_STATUS ret;
4248 
4249 	/*
4250 	 * when 802.11w PMF is enabled for hw encr/decr
4251 	 * use hw MFP Qos bits 0x10
4252 	 */
4253 	param.param_id = wmi_pdev_param_pmf_qos;
4254 	param.param_value = true;
4255 	ret = wmi_unified_pdev_param_send(wma->wmi_handle,
4256 					 &param, WMA_WILDCARD_PDEV_ID);
4257 	if (QDF_IS_STATUS_ERROR(ret)) {
4258 		wma_err("Failed to set QOS MFP/PMF (%d)", ret);
4259 	} else {
4260 		wma_debug("QOS MFP/PMF set");
4261 	}
4262 }
4263 
4264 /**
4265  * wma_set_peer_pmf_status() - Get the peer and update PMF capability of it
4266  * @wma: wma handle
4267  * @peer_mac: peer mac addr
4268  * @is_pmf_enabled: Carries the status whether PMF is enabled or not
4269  *
4270  * Return: QDF_STATUS
4271  */
4272 static QDF_STATUS
4273 wma_set_peer_pmf_status(tp_wma_handle wma, uint8_t *peer_mac,
4274 			bool is_pmf_enabled)
4275 {
4276 	struct wlan_objmgr_peer *peer;
4277 
4278 	peer = wlan_objmgr_get_peer(wma->psoc,
4279 				    wlan_objmgr_pdev_get_pdev_id(wma->pdev),
4280 				    peer_mac, WLAN_LEGACY_WMA_ID);
4281 	if (!peer) {
4282 		wma_err("Peer of peer_mac "QDF_MAC_ADDR_FMT" not found",
4283 			QDF_MAC_ADDR_REF(peer_mac));
4284 		return QDF_STATUS_E_INVAL;
4285 	}
4286 	mlme_set_peer_pmf_status(peer, is_pmf_enabled);
4287 	wlan_objmgr_peer_release_ref(peer, WLAN_LEGACY_WMA_ID);
4288 	wma_debug("set is_pmf_enabled %d for "QDF_MAC_ADDR_FMT,
4289 		  is_pmf_enabled, QDF_MAC_ADDR_REF(peer_mac));
4290 
4291 	return QDF_STATUS_SUCCESS;
4292 }
4293 
4294 QDF_STATUS wma_pre_vdev_start_setup(uint8_t vdev_id,
4295 				    struct bss_params *add_bss)
4296 {
4297 	QDF_STATUS status;
4298 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
4299 	struct wma_txrx_node *iface;
4300 	tp_wma_handle wma = cds_get_context(QDF_MODULE_ID_WMA);
4301 	struct vdev_mlme_obj *mlme_obj;
4302 	uint8_t *mac_addr;
4303 
4304 	if (!soc || !wma)
4305 		return QDF_STATUS_E_FAILURE;
4306 
4307 	iface = &wma->interfaces[vdev_id];
4308 
4309 	mlme_obj = wlan_vdev_mlme_get_cmpt_obj(iface->vdev);
4310 	if (!mlme_obj) {
4311 		wma_err("vdev component object is NULL");
4312 		return QDF_STATUS_E_FAILURE;
4313 	}
4314 
4315 	wma_set_bss_rate_flags(wma, vdev_id, add_bss);
4316 	if (wlan_vdev_mlme_get_opmode(iface->vdev) == QDF_NDI_MODE ||
4317 	    wlan_vdev_mlme_get_opmode(iface->vdev) == QDF_IBSS_MODE)
4318 		mac_addr = mlme_obj->mgmt.generic.bssid;
4319 	else
4320 		mac_addr = wlan_vdev_mlme_get_macaddr(iface->vdev);
4321 
4322 	status = wma_create_peer(wma, mac_addr,
4323 				 WMI_PEER_TYPE_DEFAULT, vdev_id,
4324 				 NULL, false);
4325 	if (status != QDF_STATUS_SUCCESS) {
4326 		wma_err("Failed to create peer");
4327 		return status;
4328 	}
4329 
4330 	if (!cdp_find_peer_exist(soc, OL_TXRX_PDEV_ID, mac_addr)) {
4331 		wma_err("Failed to find peer "QDF_MAC_ADDR_FMT,
4332 			 QDF_MAC_ADDR_REF(mac_addr));
4333 		return QDF_STATUS_E_FAILURE;
4334 	}
4335 
4336 	iface->rmfEnabled = add_bss->rmfEnabled;
4337 	if (add_bss->rmfEnabled)
4338 		wma_set_mgmt_frame_protection(wma);
4339 
4340 	return status;
4341 }
4342 
4343 QDF_STATUS wma_post_vdev_start_setup(uint8_t vdev_id)
4344 {
4345 	QDF_STATUS status = QDF_STATUS_SUCCESS;
4346 	tp_wma_handle wma = cds_get_context(QDF_MODULE_ID_WMA);
4347 	struct wma_txrx_node *intr;
4348 	struct vdev_mlme_obj *mlme_obj;
4349 	struct wlan_objmgr_vdev *vdev;
4350 	uint8_t bss_power = 0;
4351 
4352 	if (!wma)
4353 		return QDF_STATUS_E_FAILURE;
4354 
4355 	intr = &wma->interfaces[vdev_id];
4356 	if (!intr) {
4357 		wma_err("Invalid interface");
4358 		return QDF_STATUS_E_FAILURE;
4359 	}
4360 	vdev = intr->vdev;
4361 	if (!vdev) {
4362 		wma_err("vdev is NULL");
4363 		return QDF_STATUS_E_FAILURE;
4364 	}
4365 	if (wlan_vdev_mlme_get_opmode(vdev) == QDF_NDI_MODE ||
4366 	    wlan_vdev_mlme_get_opmode(vdev) == QDF_IBSS_MODE) {
4367 		/* Initialize protection mode to no protection */
4368 		wma_vdev_set_param(wma->wmi_handle, vdev_id,
4369 				   wmi_vdev_param_protection_mode,
4370 				   IEEE80211_PROT_NONE);
4371 		return status;
4372 	}
4373 	mlme_obj = wlan_vdev_mlme_get_cmpt_obj(vdev);
4374 	if (!mlme_obj) {
4375 		wma_err("vdev component object is NULL");
4376 		return QDF_STATUS_E_FAILURE;
4377 	}
4378 
4379 	/* Fill bss_chan after vdev start */
4380 	qdf_mem_copy(vdev->vdev_mlme.bss_chan,
4381 		     vdev->vdev_mlme.des_chan,
4382 		     sizeof(struct wlan_channel));
4383 
4384 	if (!wlan_reg_is_ext_tpc_supported(wma->psoc))
4385 		bss_power = wlan_reg_get_channel_reg_power_for_freq(
4386 				wma->pdev, vdev->vdev_mlme.bss_chan->ch_freq);
4387 
4388 	if (wma_vdev_set_bss_params(wma, vdev_id,
4389 				    mlme_obj->proto.generic.beacon_interval,
4390 				    mlme_obj->proto.generic.dtim_period,
4391 				    mlme_obj->proto.generic.slot_time,
4392 				    mlme_obj->proto.generic.protection_mode,
4393 				    bss_power, 0)) {
4394 		wma_err("Failed to set wma_vdev_set_bss_params");
4395 	}
4396 
4397 	wma_vdev_set_he_bss_params(wma, vdev_id,
4398 				   &mlme_obj->proto.he_ops_info);
4399 #if defined(WLAN_FEATURE_11BE)
4400 	wma_vdev_set_eht_bss_params(wma, vdev_id,
4401 				    &mlme_obj->proto.eht_ops_info);
4402 #endif
4403 
4404 	return status;
4405 }
4406 
4407 static QDF_STATUS wma_update_iface_params(tp_wma_handle wma,
4408 					  struct bss_params *add_bss)
4409 {
4410 	struct wma_txrx_node *iface;
4411 	uint8_t vdev_id;
4412 
4413 	vdev_id = add_bss->staContext.smesessionId;
4414 	iface = &wma->interfaces[vdev_id];
4415 	wma_set_bss_rate_flags(wma, vdev_id, add_bss);
4416 
4417 	if (iface->addBssStaContext)
4418 		qdf_mem_free(iface->addBssStaContext);
4419 	iface->addBssStaContext = qdf_mem_malloc(sizeof(tAddStaParams));
4420 	if (!iface->addBssStaContext)
4421 		return QDF_STATUS_E_RESOURCES;
4422 
4423 	*iface->addBssStaContext = add_bss->staContext;
4424 	/* Save parameters later needed by WMA_ADD_STA_REQ */
4425 	iface->rmfEnabled = add_bss->rmfEnabled;
4426 	if (add_bss->rmfEnabled)
4427 		wma_set_peer_pmf_status(wma, add_bss->bssId, true);
4428 	iface->beaconInterval = add_bss->beaconInterval;
4429 	iface->llbCoexist = add_bss->llbCoexist;
4430 	iface->shortSlotTimeSupported = add_bss->shortSlotTimeSupported;
4431 	iface->nwType = add_bss->nwType;
4432 	iface->bss_max_idle_period = add_bss->bss_max_idle_period;
4433 
4434 	return QDF_STATUS_SUCCESS;
4435 }
4436 
4437 static inline
4438 bool wma_cdp_find_peer_by_addr(uint8_t *peer_addr)
4439 {
4440 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
4441 	uint8_t pdev_id = OL_TXRX_PDEV_ID;
4442 
4443 	if (!soc || pdev_id == OL_TXRX_INVALID_PDEV_ID) {
4444 		wma_err("Failed to get pdev/soc");
4445 		return NULL;
4446 	}
4447 
4448 	return cdp_find_peer_exist(soc, pdev_id, peer_addr);
4449 }
4450 
4451 static
4452 QDF_STATUS wma_save_bss_params(tp_wma_handle wma, struct bss_params *add_bss)
4453 {
4454 	QDF_STATUS status;
4455 
4456 	wma_vdev_set_he_config(wma, add_bss->staContext.smesessionId, add_bss);
4457 	if (!wma_cdp_find_peer_by_addr(add_bss->bssId))
4458 		status = QDF_STATUS_E_FAILURE;
4459 	else
4460 		status = QDF_STATUS_SUCCESS;
4461 	qdf_mem_copy(add_bss->staContext.staMac, add_bss->bssId,
4462 		     sizeof(add_bss->staContext.staMac));
4463 
4464 	wma_debug("update_bss %d nw_type %d bssid "QDF_MAC_ADDR_FMT" status %d",
4465 		 add_bss->updateBss, add_bss->nwType,
4466 		 QDF_MAC_ADDR_REF(add_bss->bssId),
4467 		 status);
4468 
4469 	return status;
4470 }
4471 
4472 QDF_STATUS wma_pre_assoc_req(struct bss_params *add_bss)
4473 {
4474 	QDF_STATUS status;
4475 	tp_wma_handle wma;
4476 
4477 	wma = cds_get_context(QDF_MODULE_ID_WMA);
4478 	if (!wma)
4479 		return QDF_STATUS_E_INVAL;
4480 
4481 	status = wma_update_iface_params(wma, add_bss);
4482 	if (QDF_IS_STATUS_ERROR(status))
4483 		return status;
4484 
4485 	status = wma_save_bss_params(wma, add_bss);
4486 
4487 	return status;
4488 }
4489 
4490 void wma_add_bss_lfr3(tp_wma_handle wma, struct bss_params *add_bss)
4491 {
4492 	QDF_STATUS status;
4493 
4494 	status = wma_update_iface_params(wma, add_bss);
4495 	if (QDF_IS_STATUS_ERROR(status))
4496 		return;
4497 
4498 	if (!wma_cdp_find_peer_by_addr(add_bss->bssId)) {
4499 		wma_err("Failed to find peer "QDF_MAC_ADDR_FMT,
4500 			 QDF_MAC_ADDR_REF(add_bss->bssId));
4501 		return;
4502 	}
4503 	wma_debug("LFR3: bssid "QDF_MAC_ADDR_FMT,
4504 		  QDF_MAC_ADDR_REF(add_bss->bssId));
4505 }
4506 
4507 
4508 #if defined(QCA_LL_LEGACY_TX_FLOW_CONTROL) || defined(QCA_LL_TX_FLOW_CONTROL_V2)
4509 static
4510 QDF_STATUS wma_set_cdp_vdev_pause_reason(tp_wma_handle wma, uint8_t vdev_id)
4511 {
4512 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
4513 
4514 	cdp_fc_vdev_pause(soc, vdev_id,
4515 			  OL_TXQ_PAUSE_REASON_PEER_UNAUTHORIZED, 0);
4516 
4517 	return QDF_STATUS_SUCCESS;
4518 }
4519 #else
4520 static inline
4521 QDF_STATUS wma_set_cdp_vdev_pause_reason(tp_wma_handle wma, uint8_t vdev_id)
4522 {
4523 	return QDF_STATUS_SUCCESS;
4524 }
4525 #endif
4526 
4527 void wma_send_add_bss_resp(tp_wma_handle wma, uint8_t vdev_id,
4528 			   QDF_STATUS status)
4529 {
4530 	struct add_bss_rsp *add_bss_rsp;
4531 
4532 	add_bss_rsp = qdf_mem_malloc(sizeof(*add_bss_rsp));
4533 	if (!add_bss_rsp)
4534 		return;
4535 
4536 	add_bss_rsp->vdev_id = vdev_id;
4537 	add_bss_rsp->status = status;
4538 	lim_handle_add_bss_rsp(wma->mac_context, add_bss_rsp);
4539 }
4540 
4541 #ifdef WLAN_FEATURE_HOST_ROAM
4542 QDF_STATUS wma_add_bss_lfr2_vdev_start(struct wlan_objmgr_vdev *vdev,
4543 				       struct bss_params *add_bss)
4544 {
4545 	tp_wma_handle wma;
4546 	QDF_STATUS status;
4547 	struct vdev_mlme_obj *mlme_obj;
4548 	uint8_t vdev_id;
4549 	bool peer_exist = false;
4550 
4551 	wma = cds_get_context(QDF_MODULE_ID_WMA);
4552 	if (!wma || !vdev) {
4553 		wma_err("Invalid wma or vdev");
4554 		return QDF_STATUS_E_INVAL;
4555 	}
4556 
4557 	vdev_id = vdev->vdev_objmgr.vdev_id;
4558 	mlme_obj = wlan_vdev_mlme_get_cmpt_obj(vdev);
4559 	if (!mlme_obj) {
4560 		wma_err("vdev component object is NULL");
4561 		return QDF_STATUS_E_FAILURE;
4562 	}
4563 
4564 	status = wma_update_iface_params(wma, add_bss);
4565 	if (QDF_IS_STATUS_ERROR(status))
4566 		goto send_fail_resp;
4567 
4568 	peer_exist = wma_cdp_find_peer_by_addr(mlme_obj->mgmt.generic.bssid);
4569 	if (!peer_exist) {
4570 		wma_err("Failed to find peer "QDF_MAC_ADDR_FMT,
4571 			QDF_MAC_ADDR_REF(mlme_obj->mgmt.generic.bssid));
4572 		goto send_fail_resp;
4573 	}
4574 
4575 	status = wma_vdev_pre_start(vdev_id, false);
4576 	if (QDF_IS_STATUS_ERROR(status)) {
4577 		wma_err("failed, status: %d", status);
4578 		goto peer_cleanup;
4579 	}
4580 	status = vdev_mgr_start_send(mlme_obj, false);
4581 	if (QDF_IS_STATUS_ERROR(status)) {
4582 		wma_err("failed, status: %d", status);
4583 		goto peer_cleanup;
4584 	}
4585 	status = wma_set_cdp_vdev_pause_reason(wma, vdev_id);
4586 	if (QDF_IS_STATUS_ERROR(status))
4587 		goto peer_cleanup;
4588 
4589 	/* ADD_BSS_RESP will be deferred to completion of VDEV_START */
4590 	return QDF_STATUS_SUCCESS;
4591 
4592 peer_cleanup:
4593 	if (peer_exist)
4594 		wma_remove_peer(wma, mlme_obj->mgmt.generic.bssid, vdev_id,
4595 				false);
4596 
4597 send_fail_resp:
4598 	wma_send_add_bss_resp(wma, vdev_id, QDF_STATUS_E_FAILURE);
4599 
4600 	return QDF_STATUS_SUCCESS;
4601 }
4602 #endif
4603 
4604 QDF_STATUS wma_set_vdev_bw(uint8_t vdev_id, uint8_t bw)
4605 {
4606 	QDF_STATUS status;
4607 	tp_wma_handle wma = cds_get_context(QDF_MODULE_ID_WMA);
4608 
4609 	if (!wma)
4610 		return QDF_STATUS_E_INVAL;
4611 
4612 	status = wma_vdev_set_param(wma->wmi_handle, vdev_id,
4613 				    wmi_vdev_param_chwidth, bw);
4614 	if (QDF_IS_STATUS_ERROR(status))
4615 		wma_err("failed to set vdev bw, status: %d", status);
4616 
4617 	return status;
4618 }
4619 
4620 QDF_STATUS wma_send_peer_assoc_req(struct bss_params *add_bss)
4621 {
4622 	struct wma_target_req *msg;
4623 	tp_wma_handle wma;
4624 	uint8_t vdev_id;
4625 	bool peer_exist;
4626 	QDF_STATUS status;
4627 	struct wma_txrx_node *iface;
4628 	int pps_val = 0;
4629 	struct vdev_mlme_obj *mlme_obj;
4630 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
4631 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
4632 
4633 	wma = cds_get_context(QDF_MODULE_ID_WMA);
4634 	if (!wma || !mac || !soc)
4635 		return QDF_STATUS_E_INVAL;
4636 
4637 	vdev_id = add_bss->staContext.smesessionId;
4638 
4639 	iface = &wma->interfaces[vdev_id];
4640 	status = wma_update_iface_params(wma, add_bss);
4641 	if (QDF_IS_STATUS_ERROR(status))
4642 		goto send_resp;
4643 
4644 	peer_exist = wma_cdp_find_peer_by_addr(add_bss->bssId);
4645 	if (add_bss->nonRoamReassoc && peer_exist)
4646 		goto send_resp;
4647 
4648 	if (!add_bss->updateBss)
4649 		goto send_resp;
4650 
4651 	if (!peer_exist) {
4652 		wma_err("Failed to find peer "QDF_MAC_ADDR_FMT,
4653 			QDF_MAC_ADDR_REF(add_bss->bssId));
4654 		status = QDF_STATUS_E_FAILURE;
4655 		goto send_resp;
4656 	}
4657 
4658 
4659 	if (add_bss->staContext.encryptType == eSIR_ED_NONE) {
4660 		wma_debug("Update peer("QDF_MAC_ADDR_FMT") state into auth",
4661 			 QDF_MAC_ADDR_REF(add_bss->bssId));
4662 		cdp_peer_state_update(soc, add_bss->bssId,
4663 				      OL_TXRX_PEER_STATE_AUTH);
4664 	} else {
4665 		wma_debug("Update peer("QDF_MAC_ADDR_FMT") state into conn",
4666 			 QDF_MAC_ADDR_REF(add_bss->bssId));
4667 		cdp_peer_state_update(soc, add_bss->bssId,
4668 				      OL_TXRX_PEER_STATE_CONN);
4669 		status = wma_set_cdp_vdev_pause_reason(wma, vdev_id);
4670 		if (QDF_IS_STATUS_ERROR(status))
4671 			goto send_resp;
4672 	}
4673 
4674 	wmi_unified_send_txbf(wma, &add_bss->staContext);
4675 
4676 	pps_val = ((mac->mlme_cfg->sta.enable_5g_ebt << 31) &
4677 		 0xffff0000) | (PKT_PWR_SAVE_5G_EBT & 0xffff);
4678 	status = wma_vdev_set_param(wma->wmi_handle, vdev_id,
4679 				    wmi_vdev_param_packet_powersave,
4680 				    pps_val);
4681 	if (QDF_IS_STATUS_ERROR(status))
4682 		wma_err("Failed to send wmi packet power save cmd");
4683 	else
4684 		wma_debug("Sent packet power save %x", pps_val);
4685 
4686 	add_bss->staContext.no_ptk_4_way = add_bss->no_ptk_4_way;
4687 
4688 	status = wma_send_peer_assoc(wma, add_bss->nwType,
4689 				     &add_bss->staContext);
4690 	if (QDF_IS_STATUS_ERROR(status)) {
4691 		wma_err("Failed to send peer assoc status:%d", status);
4692 		goto send_resp;
4693 	}
4694 
4695 	/* we just had peer assoc, so install key will be done later */
4696 	if (add_bss->staContext.encryptType != eSIR_ED_NONE)
4697 		iface->is_waiting_for_key = true;
4698 
4699 	if (add_bss->rmfEnabled)
4700 		wma_set_mgmt_frame_protection(wma);
4701 
4702 	if (wlan_reg_is_ext_tpc_supported(wma->psoc))
4703 		add_bss->maxTxPower = 0;
4704 
4705 	if (wma_vdev_set_bss_params(wma, add_bss->staContext.smesessionId,
4706 				    add_bss->beaconInterval,
4707 				    add_bss->dtimPeriod,
4708 				    add_bss->shortSlotTimeSupported,
4709 				    add_bss->llbCoexist,
4710 				    add_bss->maxTxPower,
4711 				    add_bss->bss_max_idle_period)) {
4712 		wma_err("Failed to set bss params");
4713 	}
4714 
4715 	mlme_obj = wlan_vdev_mlme_get_cmpt_obj(iface->vdev);
4716 	if (!mlme_obj) {
4717 		wma_err("Failed to mlme obj");
4718 		status = QDF_STATUS_E_FAILURE;
4719 		goto send_resp;
4720 	}
4721 	/*
4722 	 * Store the bssid in interface table, bssid will
4723 	 * be used during group key setting sta mode.
4724 	 */
4725 	qdf_mem_copy(mlme_obj->mgmt.generic.bssid,
4726 		     add_bss->bssId, QDF_MAC_ADDR_SIZE);
4727 
4728 	wma_save_bss_params(wma, add_bss);
4729 
4730 	if (!wmi_service_enabled(wma->wmi_handle,
4731 				 wmi_service_peer_assoc_conf)) {
4732 		wma_debug("WMI_SERVICE_PEER_ASSOC_CONF not enabled");
4733 		goto send_resp;
4734 	}
4735 
4736 	msg = wma_fill_hold_req(wma, vdev_id, WMA_ADD_BSS_REQ,
4737 				WMA_PEER_ASSOC_CNF_START, NULL,
4738 				WMA_PEER_ASSOC_TIMEOUT);
4739 	if (!msg) {
4740 		wma_err("Failed to allocate request for vdev_id %d", vdev_id);
4741 		wma_remove_req(wma, vdev_id, WMA_PEER_ASSOC_CNF_START);
4742 		status = QDF_STATUS_E_FAILURE;
4743 		goto send_resp;
4744 	}
4745 
4746 	return QDF_STATUS_SUCCESS;
4747 
4748 send_resp:
4749 	wma_send_add_bss_resp(wma, vdev_id, status);
4750 
4751 	return QDF_STATUS_SUCCESS;
4752 }
4753 
4754 #ifdef WLAN_FEATURE_11BE_MLO
4755 /**
4756  * wma_get_mld_info_ap() - get mld mac addr and assoc peer flag for ap
4757  * @add_sta: tpAddStaParams
4758  * @peer_mld_addr: peer mld mac addr
4759  * @is_assoc_peer: is assoc peer or not
4760  *
4761  * Return: void
4762  */
4763 static void wma_get_mld_info_ap(tpAddStaParams add_sta,
4764 				uint8_t **peer_mld_addr,
4765 				bool *is_assoc_peer)
4766 {
4767 	if (add_sta) {
4768 		*peer_mld_addr = add_sta->mld_mac_addr;
4769 		*is_assoc_peer = add_sta->is_assoc_peer;
4770 	} else {
4771 		peer_mld_addr = NULL;
4772 		*is_assoc_peer = false;
4773 	}
4774 }
4775 #else
4776 static void wma_get_mld_info_ap(tpAddStaParams add_sta,
4777 				uint8_t **peer_mld_addr,
4778 				bool *is_assoc_peer)
4779 {
4780 	*peer_mld_addr = NULL;
4781 	*is_assoc_peer = false;
4782 }
4783 #endif
4784 
4785 /**
4786  * wma_add_sta_req_ap_mode() - process add sta request in ap mode
4787  * @wma: wma handle
4788  * @add_sta: add sta params
4789  *
4790  * Return: none
4791  */
4792 static void wma_add_sta_req_ap_mode(tp_wma_handle wma, tpAddStaParams add_sta)
4793 {
4794 	enum ol_txrx_peer_state state = OL_TXRX_PEER_STATE_CONN;
4795 	uint8_t pdev_id = OL_TXRX_PDEV_ID;
4796 	QDF_STATUS status;
4797 	int32_t ret;
4798 	struct wma_txrx_node *iface = NULL;
4799 	struct wma_target_req *msg = NULL;
4800 	bool peer_assoc_cnf = false;
4801 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
4802 	uint32_t i, j;
4803 	uint16_t mcs_limit;
4804 	uint8_t *rate_pos;
4805 	struct mac_context *mac = wma->mac_context;
4806 	uint8_t *peer_mld_addr = NULL;
4807 	bool is_assoc_peer = false;
4808 
4809 	/* UMAC sends WMA_ADD_STA_REQ msg twice to WMA when the station
4810 	 * associates. First WMA_ADD_STA_REQ will have staType as
4811 	 * STA_ENTRY_PEER and second posting will have STA_ENTRY_SELF.
4812 	 * Peer creation is done in first WMA_ADD_STA_REQ and second
4813 	 * WMA_ADD_STA_REQ which has STA_ENTRY_SELF is ignored and
4814 	 * send fake response with success to UMAC. Otherwise UMAC
4815 	 * will get blocked.
4816 	 */
4817 	if (add_sta->staType != STA_ENTRY_PEER) {
4818 		add_sta->status = QDF_STATUS_SUCCESS;
4819 		goto send_rsp;
4820 	}
4821 
4822 	iface = &wma->interfaces[add_sta->smesessionId];
4823 
4824 	if (cdp_find_peer_exist_on_vdev(soc, add_sta->smesessionId,
4825 					add_sta->staMac)) {
4826 		wma_remove_peer(wma, add_sta->staMac, add_sta->smesessionId,
4827 				false);
4828 		wma_err("Peer already exists, Deleted peer with peer_addr "QDF_MAC_ADDR_FMT,
4829 			QDF_MAC_ADDR_REF(add_sta->staMac));
4830 	}
4831 	/* The code above only checks the peer existence on its own vdev.
4832 	 * Need to check whether the peer exists on other vDevs because firmware
4833 	 * can't create the peer if the peer with same MAC address already
4834 	 * exists on the pDev. As this peer belongs to other vDevs, just return
4835 	 * here.
4836 	 */
4837 	if (cdp_find_peer_exist(soc, pdev_id, add_sta->staMac)) {
4838 		wma_err("My vdev id %d, but Peer exists on other vdev with peer_addr "QDF_MAC_ADDR_FMT,
4839 			 add_sta->smesessionId,
4840 			 QDF_MAC_ADDR_REF(add_sta->staMac));
4841 		add_sta->status = QDF_STATUS_E_FAILURE;
4842 		goto send_rsp;
4843 	}
4844 
4845 	wma_delete_invalid_peer_entries(add_sta->smesessionId, add_sta->staMac);
4846 
4847 	wma_get_mld_info_ap(add_sta, &peer_mld_addr, &is_assoc_peer);
4848 	status = wma_create_peer(wma, add_sta->staMac, WMI_PEER_TYPE_DEFAULT,
4849 				 add_sta->smesessionId, peer_mld_addr,
4850 				 is_assoc_peer);
4851 	if (status != QDF_STATUS_SUCCESS) {
4852 		wma_err("Failed to create peer for "QDF_MAC_ADDR_FMT,
4853 			QDF_MAC_ADDR_REF(add_sta->staMac));
4854 		add_sta->status = status;
4855 		goto send_rsp;
4856 	}
4857 
4858 	if (!cdp_find_peer_exist_on_vdev(soc, add_sta->smesessionId,
4859 					 add_sta->staMac)) {
4860 		wma_err("Failed to find peer handle using peer mac "QDF_MAC_ADDR_FMT,
4861 			QDF_MAC_ADDR_REF(add_sta->staMac));
4862 		add_sta->status = QDF_STATUS_E_FAILURE;
4863 		wma_remove_peer(wma, add_sta->staMac, add_sta->smesessionId,
4864 				false);
4865 		goto send_rsp;
4866 	}
4867 
4868 	wmi_unified_send_txbf(wma, add_sta);
4869 
4870 	/*
4871 	 * Get MCS limit from ini configure, and map it to rate parameters
4872 	 * This will limit HT rate upper bound. CFG_CTRL_MASK is used to
4873 	 * check whether ini config is enabled and CFG_DATA_MASK to get the
4874 	 * MCS value.
4875 	 */
4876 #define CFG_CTRL_MASK              0xFF00
4877 #define CFG_DATA_MASK              0x00FF
4878 
4879 	mcs_limit = mac->mlme_cfg->rates.sap_max_mcs_txdata;
4880 
4881 	if (mcs_limit & CFG_CTRL_MASK) {
4882 		wma_debug("set mcs_limit %x", mcs_limit);
4883 
4884 		mcs_limit &= CFG_DATA_MASK;
4885 		rate_pos = (u_int8_t *)add_sta->supportedRates.supportedMCSSet;
4886 		for (i = 0, j = 0; i < MAX_SUPPORTED_RATES;) {
4887 			if (j < mcs_limit / 8) {
4888 				rate_pos[j] = 0xff;
4889 				j++;
4890 				i += 8;
4891 			} else if (j < mcs_limit / 8 + 1) {
4892 				if (i <= mcs_limit)
4893 					rate_pos[i / 8] |= 1 << (i % 8);
4894 				else
4895 					rate_pos[i / 8] &= ~(1 << (i % 8));
4896 				i++;
4897 
4898 				if (i >= (j + 1) * 8)
4899 					j++;
4900 			} else {
4901 				rate_pos[j++] = 0;
4902 				i += 8;
4903 			}
4904 		}
4905 	}
4906 
4907 	if (wmi_service_enabled(wma->wmi_handle,
4908 				    wmi_service_peer_assoc_conf)) {
4909 		peer_assoc_cnf = true;
4910 		msg = wma_fill_hold_req(wma, add_sta->smesessionId,
4911 				   WMA_ADD_STA_REQ, WMA_PEER_ASSOC_CNF_START,
4912 				   add_sta, WMA_PEER_ASSOC_TIMEOUT);
4913 		if (!msg) {
4914 			wma_err("Failed to alloc request for vdev_id %d",
4915 				add_sta->smesessionId);
4916 			add_sta->status = QDF_STATUS_E_FAILURE;
4917 			wma_remove_req(wma, add_sta->smesessionId,
4918 				       WMA_PEER_ASSOC_CNF_START);
4919 			wma_remove_peer(wma, add_sta->staMac,
4920 					add_sta->smesessionId, false);
4921 			peer_assoc_cnf = false;
4922 			goto send_rsp;
4923 		}
4924 	} else {
4925 		wma_err("WMI_SERVICE_PEER_ASSOC_CONF not enabled");
4926 	}
4927 
4928 	ret = wma_send_peer_assoc(wma, add_sta->nwType, add_sta);
4929 	if (ret) {
4930 		add_sta->status = QDF_STATUS_E_FAILURE;
4931 		if (msg) {
4932 			wma_remove_req(wma, add_sta->smesessionId,
4933 				       WMA_PEER_ASSOC_CNF_START);
4934 			peer_assoc_cnf = false;
4935 		}
4936 		wma_remove_peer(wma, add_sta->staMac, add_sta->smesessionId,
4937 				false);
4938 		goto send_rsp;
4939 	}
4940 
4941 	if (add_sta->rmfEnabled)
4942 		wma_set_peer_pmf_status(wma, add_sta->staMac, true);
4943 
4944 	if (add_sta->uAPSD) {
4945 		status = wma_set_ap_peer_uapsd(wma, add_sta->smesessionId,
4946 					    add_sta->staMac,
4947 					    add_sta->uAPSD, add_sta->maxSPLen);
4948 		if (QDF_IS_STATUS_ERROR(status)) {
4949 			wma_err("Failed to set peer uapsd param for "QDF_MAC_ADDR_FMT,
4950 				QDF_MAC_ADDR_REF(add_sta->staMac));
4951 			add_sta->status = QDF_STATUS_E_FAILURE;
4952 			wma_remove_peer(wma, add_sta->staMac,
4953 					add_sta->smesessionId, false);
4954 			goto send_rsp;
4955 		}
4956 	}
4957 
4958 	wma_debug("Moving peer "QDF_MAC_ADDR_FMT" to state %d",
4959 		  QDF_MAC_ADDR_REF(add_sta->staMac), state);
4960 	cdp_peer_state_update(soc, add_sta->staMac, state);
4961 
4962 	add_sta->nss    = wma_objmgr_get_peer_mlme_nss(wma, add_sta->staMac);
4963 	add_sta->status = QDF_STATUS_SUCCESS;
4964 send_rsp:
4965 	/* Do not send add stat resp when peer assoc cnf is enabled */
4966 	if (peer_assoc_cnf) {
4967 		wma_debug("WMI_SERVICE_PEER_ASSOC_CONF is enabled");
4968 		return;
4969 	}
4970 
4971 	wma_debug("statype %d vdev_id %d aid %d bssid "QDF_MAC_ADDR_FMT" status %d",
4972 		 add_sta->staType, add_sta->smesessionId,
4973 		 add_sta->assocId, QDF_MAC_ADDR_REF(add_sta->bssId),
4974 		 add_sta->status);
4975 	wma_send_msg_high_priority(wma, WMA_ADD_STA_RSP, (void *)add_sta, 0);
4976 }
4977 
4978 #ifdef FEATURE_WLAN_TDLS
4979 
4980 /**
4981  * wma_add_tdls_sta() - process add sta request in TDLS mode
4982  * @wma: wma handle
4983  * @add_sta: add sta params
4984  *
4985  * Return: none
4986  */
4987 static void wma_add_tdls_sta(tp_wma_handle wma, tpAddStaParams add_sta)
4988 {
4989 	QDF_STATUS status;
4990 	int32_t ret;
4991 	struct tdls_peer_update_state *peer_state;
4992 	struct wma_target_req *msg;
4993 	bool peer_assoc_cnf = false;
4994 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
4995 	uint8_t pdev_id = OL_TXRX_PDEV_ID;
4996 	struct wma_txrx_node *iface = &wma->interfaces[add_sta->smesessionId];
4997 
4998 	wma_debug("staType: %d, updateSta: %d, bssId: "QDF_MAC_ADDR_FMT", staMac: "QDF_MAC_ADDR_FMT,
4999 		 add_sta->staType,
5000 		 add_sta->updateSta, QDF_MAC_ADDR_REF(add_sta->bssId),
5001 		 QDF_MAC_ADDR_REF(add_sta->staMac));
5002 
5003 	if (iface->vdev && wlan_cm_is_vdev_roaming(iface->vdev)) {
5004 		wma_err("Vdev %d roaming in progress, reject add sta!",
5005 			add_sta->smesessionId);
5006 		add_sta->status = QDF_STATUS_E_PERM;
5007 		goto send_rsp;
5008 	}
5009 
5010 	if (0 == add_sta->updateSta) {
5011 		/* its a add sta request * */
5012 
5013 		cdp_peer_copy_mac_addr_raw(soc, add_sta->smesessionId,
5014 					   add_sta->bssId);
5015 
5016 		wma_debug("addSta, calling wma_create_peer for "QDF_MAC_ADDR_FMT", vdev_id %hu",
5017 			  QDF_MAC_ADDR_REF(add_sta->staMac),
5018 			  add_sta->smesessionId);
5019 
5020 		status = wma_create_peer(wma, add_sta->staMac,
5021 					 WMI_PEER_TYPE_TDLS,
5022 					 add_sta->smesessionId, NULL, false);
5023 		if (status != QDF_STATUS_SUCCESS) {
5024 			wma_err("Failed to create peer for "QDF_MAC_ADDR_FMT,
5025 				QDF_MAC_ADDR_REF(add_sta->staMac));
5026 			add_sta->status = status;
5027 			goto send_rsp;
5028 		}
5029 
5030 		wma_debug("addSta, after calling cdp_local_peer_id, staMac: "QDF_MAC_ADDR_FMT,
5031 			  QDF_MAC_ADDR_REF(add_sta->staMac));
5032 
5033 		peer_state = qdf_mem_malloc(sizeof(*peer_state));
5034 		if (!peer_state) {
5035 			add_sta->status = QDF_STATUS_E_NOMEM;
5036 			goto send_rsp;
5037 		}
5038 
5039 		peer_state->peer_state = WMI_TDLS_PEER_STATE_PEERING;
5040 		peer_state->vdev_id = add_sta->smesessionId;
5041 		qdf_mem_copy(&peer_state->peer_macaddr,
5042 			     &add_sta->staMac, sizeof(tSirMacAddr));
5043 		wma_update_tdls_peer_state(wma, peer_state);
5044 	} else {
5045 		if (wmi_service_enabled(wma->wmi_handle,
5046 					    wmi_service_peer_assoc_conf)) {
5047 			wma_err("WMI_SERVICE_PEER_ASSOC_CONF is enabled");
5048 			peer_assoc_cnf = true;
5049 			msg = wma_fill_hold_req(wma, add_sta->smesessionId,
5050 				WMA_ADD_STA_REQ, WMA_PEER_ASSOC_CNF_START,
5051 				add_sta, WMA_PEER_ASSOC_TIMEOUT);
5052 			if (!msg) {
5053 				wma_err("Failed to alloc request for vdev_id %d",
5054 					add_sta->smesessionId);
5055 				add_sta->status = QDF_STATUS_E_FAILURE;
5056 				wma_remove_req(wma, add_sta->smesessionId,
5057 					       WMA_PEER_ASSOC_CNF_START);
5058 				wma_remove_peer(wma, add_sta->staMac,
5059 						add_sta->smesessionId, false);
5060 				peer_assoc_cnf = false;
5061 				goto send_rsp;
5062 			}
5063 		} else {
5064 			wma_err("WMI_SERVICE_PEER_ASSOC_CONF not enabled");
5065 		}
5066 
5067 		wma_debug("changeSta, calling wma_send_peer_assoc");
5068 		if (add_sta->rmfEnabled)
5069 			wma_set_peer_pmf_status(wma, add_sta->staMac, true);
5070 
5071 		ret =
5072 			wma_send_peer_assoc(wma, add_sta->nwType, add_sta);
5073 		if (ret) {
5074 			add_sta->status = QDF_STATUS_E_FAILURE;
5075 			wma_remove_peer(wma, add_sta->staMac,
5076 					add_sta->smesessionId, false);
5077 			cdp_peer_add_last_real_peer(soc, pdev_id,
5078 						    add_sta->smesessionId);
5079 			wma_remove_req(wma, add_sta->smesessionId,
5080 				       WMA_PEER_ASSOC_CNF_START);
5081 			peer_assoc_cnf = false;
5082 
5083 			goto send_rsp;
5084 		}
5085 	}
5086 
5087 send_rsp:
5088 	/* Do not send add stat resp when peer assoc cnf is enabled */
5089 	if (peer_assoc_cnf)
5090 		return;
5091 
5092 	wma_debug("statype %d vdev_id %d aid %d bssid "QDF_MAC_ADDR_FMT" status %d",
5093 		 add_sta->staType, add_sta->smesessionId,
5094 		 add_sta->assocId, QDF_MAC_ADDR_REF(add_sta->bssId),
5095 		 add_sta->status);
5096 	wma_send_msg_high_priority(wma, WMA_ADD_STA_RSP, (void *)add_sta, 0);
5097 }
5098 #endif
5099 
5100 /**
5101  * wma_send_bss_color_change_enable() - send bss color change enable cmd.
5102  * @wma: wma handle
5103  * @params: add sta params
5104  *
5105  * Send bss color change command to firmware, to enable firmware to update
5106  * internally if any change in bss color in advertised by associated AP.
5107  *
5108  * Return: none
5109  */
5110 #ifdef WLAN_FEATURE_11AX
5111 static void wma_send_bss_color_change_enable(tp_wma_handle wma,
5112 					     tpAddStaParams params)
5113 {
5114 	QDF_STATUS status;
5115 	uint32_t vdev_id = params->smesessionId;
5116 
5117 	if (!params->he_capable) {
5118 		wma_debug("he_capable is not set for vdev_id:%d", vdev_id);
5119 		return;
5120 	}
5121 
5122 	status = wmi_unified_send_bss_color_change_enable_cmd(wma->wmi_handle,
5123 							      vdev_id,
5124 							      true);
5125 	if (QDF_IS_STATUS_ERROR(status)) {
5126 		wma_err("Failed to enable bss color change offload, vdev:%d",
5127 			vdev_id);
5128 	}
5129 
5130 	return;
5131 }
5132 #else
5133 static void wma_send_bss_color_change_enable(tp_wma_handle wma,
5134 					     tpAddStaParams params)
5135 {
5136 }
5137 #endif
5138 
5139 #define MAX_VDEV_STA_REQ_PARAMS 5
5140 /* params being sent:
5141  * 1.wmi_vdev_param_max_li_of_moddtim
5142  * 2.wmi_vdev_param_max_li_of_moddtim_ms
5143  * 3.wmi_vdev_param_dyndtim_cnt
5144  * 4.wmi_vdev_param_moddtim_cnt
5145  * 5.wmi_vdev_param_moddtim_cnt
5146  */
5147 
5148 /**
5149  * wma_add_sta_req_sta_mode() - process add sta request in sta mode
5150  * @wma: wma handle
5151  * @params: add sta params
5152  *
5153  * Return: none
5154  */
5155 static void wma_add_sta_req_sta_mode(tp_wma_handle wma, tpAddStaParams params)
5156 {
5157 	QDF_STATUS status = QDF_STATUS_SUCCESS;
5158 	struct wma_txrx_node *iface;
5159 	int8_t maxTxPower = 0;
5160 	int ret = 0;
5161 	struct wma_target_req *msg;
5162 	bool peer_assoc_cnf = false;
5163 	int smps_param;
5164 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
5165 	struct dev_set_param setparam[MAX_VDEV_STA_REQ_PARAMS];
5166 	uint8_t index = 0;
5167 
5168 #ifdef FEATURE_WLAN_TDLS
5169 	if (STA_ENTRY_TDLS_PEER == params->staType) {
5170 		wma_add_tdls_sta(wma, params);
5171 		return;
5172 	}
5173 #endif
5174 
5175 	iface = &wma->interfaces[params->smesessionId];
5176 	if (params->staType != STA_ENTRY_SELF) {
5177 		wma_err("unsupported station type %d", params->staType);
5178 		goto out;
5179 	}
5180 	if (params->nonRoamReassoc) {
5181 		cdp_peer_state_update(soc, params->bssId,
5182 				      OL_TXRX_PEER_STATE_AUTH);
5183 		qdf_atomic_set(&iface->bss_status, WMA_BSS_STATUS_STARTED);
5184 		iface->aid = params->assocId;
5185 		goto out;
5186 	}
5187 
5188 	if (wma_is_vdev_up(params->smesessionId)) {
5189 		wma_debug("vdev id %d is already UP for "QDF_MAC_ADDR_FMT,
5190 			 params->smesessionId,
5191 			 QDF_MAC_ADDR_REF(params->bssId));
5192 		status = QDF_STATUS_E_FAILURE;
5193 		goto out;
5194 	}
5195 
5196 	if (cdp_peer_state_get(soc, params->smesessionId,
5197 			       params->bssId, true) == OL_TXRX_PEER_STATE_DISC) {
5198 		/*
5199 		 * This is the case for reassociation.
5200 		 * peer state update and peer_assoc is required since it
5201 		 * was not done by WMA_ADD_BSS_REQ.
5202 		 */
5203 
5204 		/* Update peer state */
5205 		if (params->encryptType == eSIR_ED_NONE) {
5206 			wma_debug("Update peer("QDF_MAC_ADDR_FMT") state into auth",
5207 				  QDF_MAC_ADDR_REF(params->bssId));
5208 			cdp_peer_state_update(soc, params->bssId,
5209 					      OL_TXRX_PEER_STATE_AUTH);
5210 		} else {
5211 			wma_debug("Update peer("QDF_MAC_ADDR_FMT") state into conn",
5212 				  QDF_MAC_ADDR_REF(params->bssId));
5213 			cdp_peer_state_update(soc, params->bssId,
5214 					      OL_TXRX_PEER_STATE_CONN);
5215 		}
5216 
5217 		if (wlan_cm_is_roam_sync_in_progress(wma->psoc,
5218 						     params->smesessionId) ||
5219 		    MLME_IS_MLO_ROAM_SYNCH_IN_PROGRESS(wma->psoc,
5220 						       params->smesessionId)) {
5221 			/* iface->nss = params->nss; */
5222 			/*In LFR2.0, the following operations are performed as
5223 			 * part of wma_send_peer_assoc. As we are
5224 			 * skipping this operation, we are just executing the
5225 			 * following which are useful for LFR3.0
5226 			 */
5227 			cdp_peer_state_update(soc, params->bssId,
5228 					      OL_TXRX_PEER_STATE_AUTH);
5229 			qdf_atomic_set(&iface->bss_status,
5230 				       WMA_BSS_STATUS_STARTED);
5231 			iface->aid = params->assocId;
5232 			wma_debug("LFR3:statype %d vdev %d aid %d bssid "QDF_MAC_ADDR_FMT,
5233 					params->staType, params->smesessionId,
5234 					params->assocId,
5235 					QDF_MAC_ADDR_REF(params->bssId));
5236 			return;
5237 		}
5238 		wmi_unified_send_txbf(wma, params);
5239 
5240 		if (wmi_service_enabled(wma->wmi_handle,
5241 					    wmi_service_peer_assoc_conf)) {
5242 			peer_assoc_cnf = true;
5243 			msg = wma_fill_hold_req(wma, params->smesessionId,
5244 				WMA_ADD_STA_REQ, WMA_PEER_ASSOC_CNF_START,
5245 				params, WMA_PEER_ASSOC_TIMEOUT);
5246 			if (!msg) {
5247 				wma_debug("Failed to alloc request for vdev_id %d",
5248 					 params->smesessionId);
5249 				params->status = QDF_STATUS_E_FAILURE;
5250 				wma_remove_req(wma, params->smesessionId,
5251 					       WMA_PEER_ASSOC_CNF_START);
5252 				wma_remove_peer(wma, params->bssId,
5253 						params->smesessionId, false);
5254 				peer_assoc_cnf = false;
5255 				goto out;
5256 			}
5257 		} else {
5258 			wma_debug("WMI_SERVICE_PEER_ASSOC_CONF not enabled");
5259 		}
5260 
5261 		((tAddStaParams *)iface->addBssStaContext)->no_ptk_4_way =
5262 						params->no_ptk_4_way;
5263 
5264 		qdf_mem_copy(((tAddStaParams *)iface->addBssStaContext)->
5265 			     supportedRates.supportedMCSSet,
5266 			     params->supportedRates.supportedMCSSet,
5267 			     SIR_MAC_MAX_SUPPORTED_MCS_SET);
5268 
5269 
5270 		ret = wma_send_peer_assoc(wma,
5271 				iface->nwType,
5272 				(tAddStaParams *) iface->addBssStaContext);
5273 		if (ret) {
5274 			status = QDF_STATUS_E_FAILURE;
5275 			wma_remove_peer(wma, params->bssId,
5276 					params->smesessionId, false);
5277 			goto out;
5278 		}
5279 
5280 		if (params->rmfEnabled) {
5281 			wma_set_mgmt_frame_protection(wma);
5282 			wma_set_peer_pmf_status(wma, params->bssId, true);
5283 		}
5284 	}
5285 
5286 	if (!wlan_reg_is_ext_tpc_supported(wma->psoc))
5287 		maxTxPower = params->maxTxPower;
5288 
5289 	if (wma_vdev_set_bss_params(wma, params->smesessionId,
5290 				    iface->beaconInterval, iface->dtimPeriod,
5291 				    iface->shortSlotTimeSupported,
5292 				    iface->llbCoexist, maxTxPower,
5293 				    iface->bss_max_idle_period)) {
5294 		wma_err("Failed to bss params");
5295 	}
5296 
5297 	params->csaOffloadEnable = 0;
5298 	if (wmi_service_enabled(wma->wmi_handle,
5299 				   wmi_service_csa_offload)) {
5300 		params->csaOffloadEnable = 1;
5301 		if (wma_unified_csa_offload_enable(wma, params->smesessionId) <
5302 		    0) {
5303 			wma_err("Unable to enable CSA offload for vdev_id:%d",
5304 				params->smesessionId);
5305 		}
5306 	}
5307 
5308 	if (wmi_service_enabled(wma->wmi_handle,
5309 				wmi_service_filter_ipsec_natkeepalive)) {
5310 		if (wmi_unified_nat_keepalive_en_cmd(wma->wmi_handle,
5311 						     params->smesessionId)) {
5312 			wma_err("Unable to enable NAT keepalive for vdev_id:%d",
5313 				params->smesessionId);
5314 		}
5315 	}
5316 	qdf_atomic_set(&iface->bss_status, WMA_BSS_STATUS_STARTED);
5317 	/* Sta is now associated, configure various params */
5318 
5319 	/* Send SMPS force command to FW to send the required
5320 	 * action frame only when SM power save is enabled in
5321 	 * from INI. In case dynamic antenna selection, the
5322 	 * action frames are sent by the chain mask manager
5323 	 * In addition to the action frames, The SM power save is
5324 	 * published in the assoc request HT SMPS IE for both cases.
5325 	 */
5326 	if ((params->enableHtSmps) && (params->send_smps_action)) {
5327 		smps_param = wma_smps_mode_to_force_mode_param(
5328 			params->htSmpsconfig);
5329 		if (smps_param >= 0) {
5330 			wma_debug("Send SMPS force mode: %d",
5331 				 params->htSmpsconfig);
5332 			wma_set_mimops(wma, params->smesessionId,
5333 				smps_param);
5334 		}
5335 	}
5336 
5337 	wma_send_bss_color_change_enable(wma, params);
5338 
5339 	/* Partial AID match power save, enable when SU bformee */
5340 	if (params->enableVhtpAid && params->vhtTxBFCapable)
5341 		wma_set_ppsconfig(params->smesessionId,
5342 				  WMA_VHT_PPS_PAID_MATCH, 1);
5343 
5344 	/* Enable AMPDU power save, if htCapable/vhtCapable */
5345 	if (params->enableAmpduPs && (params->htCapable || params->vhtCapable))
5346 		wma_set_ppsconfig(params->smesessionId,
5347 				  WMA_VHT_PPS_DELIM_CRC_FAIL, 1);
5348 	if (wmi_service_enabled(wma->wmi_handle,
5349 				wmi_service_listen_interval_offload_support)) {
5350 		struct wlan_objmgr_vdev *vdev;
5351 		uint32_t moddtim;
5352 		bool is_connection_roaming_cfg_set = 0;
5353 
5354 		wma_debug("listen interval offload enabled, setting params");
5355 		status = mlme_check_index_setparam(
5356 					setparam,
5357 					wmi_vdev_param_max_li_of_moddtim,
5358 					wma->staMaxLIModDtim, index++,
5359 					MAX_VDEV_STA_REQ_PARAMS);
5360 		if (QDF_IS_STATUS_ERROR(status)) {
5361 			wma_debug("failed to send wmi_vdev_param_max_li_of_moddtim");
5362 			goto out;
5363 		}
5364 
5365 		ucfg_mlme_get_connection_roaming_ini_present(
5366 						wma->psoc,
5367 						&is_connection_roaming_cfg_set);
5368 		if (is_connection_roaming_cfg_set) {
5369 			status = mlme_check_index_setparam(
5370 					setparam,
5371 					wmi_vdev_param_max_li_of_moddtim_ms,
5372 					wma->sta_max_li_mod_dtim_ms, index++,
5373 					MAX_VDEV_STA_REQ_PARAMS);
5374 			if (QDF_IS_STATUS_ERROR(status)) {
5375 				wma_debug("failed to send wmi_vdev_param_max_li_of_moddtim_ms");
5376 				goto out;
5377 			}
5378 		}
5379 		status = mlme_check_index_setparam(
5380 						setparam,
5381 						wmi_vdev_param_dyndtim_cnt,
5382 						wma->staDynamicDtim, index++,
5383 						MAX_VDEV_STA_REQ_PARAMS);
5384 		if (QDF_IS_STATUS_ERROR(status)) {
5385 			wma_debug("failed to send wmi_vdev_param_dyndtim_cnt");
5386 			goto out;
5387 		}
5388 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(wma->psoc,
5389 							params->smesessionId,
5390 							WLAN_LEGACY_WMA_ID);
5391 		if (!vdev || !ucfg_pmo_get_moddtim_user_enable(vdev)) {
5392 			moddtim = wma->staModDtim;
5393 			status = mlme_check_index_setparam(
5394 						setparam,
5395 						wmi_vdev_param_moddtim_cnt,
5396 						moddtim, index++,
5397 						MAX_VDEV_STA_REQ_PARAMS);
5398 			if (QDF_IS_STATUS_ERROR(status)) {
5399 				wma_debug("failed to send wmi_vdev_param_moddtim_cnt");
5400 				if (vdev)
5401 					wlan_objmgr_vdev_release_ref(vdev,
5402 							WLAN_LEGACY_WMA_ID);
5403 				goto out;
5404 			}
5405 			if (vdev)
5406 				wlan_objmgr_vdev_release_ref(vdev,
5407 							    WLAN_LEGACY_WMA_ID);
5408 		} else if (vdev && ucfg_pmo_get_moddtim_user_enable(vdev) &&
5409 			   !ucfg_pmo_get_moddtim_user_active(vdev)) {
5410 			moddtim = ucfg_pmo_get_moddtim_user(vdev);
5411 			status = mlme_check_index_setparam(
5412 						setparam,
5413 						wmi_vdev_param_moddtim_cnt,
5414 						moddtim, index++,
5415 						MAX_VDEV_STA_REQ_PARAMS);
5416 			if (QDF_IS_STATUS_ERROR(status)) {
5417 				wma_debug("failed to send wmi_vdev_param_moddtim_cnt");
5418 				wlan_objmgr_vdev_release_ref(vdev,
5419 							WLAN_LEGACY_WMA_ID);
5420 				goto out;
5421 			}
5422 			wlan_objmgr_vdev_release_ref(vdev, WLAN_LEGACY_WMA_ID);
5423 		}
5424 		status = wma_send_multi_pdev_vdev_set_params(MLME_VDEV_SETPARAM,
5425 							params->smesessionId,
5426 							setparam, index);
5427 		if (QDF_IS_STATUS_ERROR(status)) {
5428 			wma_err("failed to send DTIM vdev setparams");
5429 			goto out;
5430 		}
5431 
5432 	} else {
5433 		wma_debug("listen interval offload is not set");
5434 	}
5435 	params->nss = iface->nss;
5436 out:
5437 	iface->aid = params->assocId;
5438 
5439 	/* Do not send add stat resp when peer assoc cnf is enabled */
5440 	if (peer_assoc_cnf)
5441 		return;
5442 
5443 	params->status = status;
5444 	wma_debug("vdev_id %d aid %d sta mac " QDF_MAC_ADDR_FMT " status %d",
5445 		  params->smesessionId, iface->aid,
5446 		  QDF_MAC_ADDR_REF(params->bssId), params->status);
5447 
5448 	/* Don't send a response during roam sync operation */
5449 	if (!wlan_cm_is_roam_sync_in_progress(wma->psoc,
5450 					      params->smesessionId) &&
5451 	    !MLME_IS_MLO_ROAM_SYNCH_IN_PROGRESS(wma->psoc,
5452 						params->smesessionId))
5453 		wma_send_msg_high_priority(wma, WMA_ADD_STA_RSP,
5454 					   (void *)params, 0);
5455 }
5456 
5457 /**
5458  * wma_delete_sta_req_ap_mode() - process delete sta request from UMAC in AP mode
5459  * @wma: wma handle
5460  * @del_sta: delete sta params
5461  *
5462  * Return: none
5463  */
5464 static void wma_delete_sta_req_ap_mode(tp_wma_handle wma,
5465 				       tpDeleteStaParams del_sta)
5466 {
5467 	struct wma_target_req *msg;
5468 	QDF_STATUS qdf_status;
5469 
5470 	qdf_status = wma_remove_peer(wma, del_sta->staMac,
5471 				     del_sta->smesessionId, false);
5472 	if (QDF_IS_STATUS_ERROR(qdf_status)) {
5473 		wma_err("wma_remove_peer failed");
5474 		del_sta->status = QDF_STATUS_E_FAILURE;
5475 		goto send_del_rsp;
5476 	}
5477 	del_sta->status = QDF_STATUS_SUCCESS;
5478 
5479 	if (wmi_service_enabled(wma->wmi_handle,
5480 				    wmi_service_sync_delete_cmds)) {
5481 		msg = wma_fill_hold_req(wma, del_sta->smesessionId,
5482 				   WMA_DELETE_STA_REQ,
5483 				   WMA_DELETE_STA_RSP_START, del_sta,
5484 				   WMA_DELETE_STA_TIMEOUT);
5485 		if (!msg) {
5486 			wma_err("Failed to allocate request. vdev_id %d",
5487 				 del_sta->smesessionId);
5488 			wma_remove_req(wma, del_sta->smesessionId,
5489 				       WMA_DELETE_STA_RSP_START);
5490 			del_sta->status = QDF_STATUS_E_NOMEM;
5491 			goto send_del_rsp;
5492 		}
5493 
5494 		wma_acquire_wakelock(&wma->wmi_cmd_rsp_wake_lock,
5495 				     WMA_FW_RSP_EVENT_WAKE_LOCK_DURATION);
5496 
5497 		return;
5498 	}
5499 
5500 send_del_rsp:
5501 	if (del_sta->respReqd) {
5502 		wma_debug("Sending del rsp to umac (status: %d)",
5503 			 del_sta->status);
5504 		wma_send_msg_high_priority(wma, WMA_DELETE_STA_RSP,
5505 					   (void *)del_sta, 0);
5506 	}
5507 }
5508 
5509 #ifdef FEATURE_WLAN_TDLS
5510 /**
5511  * wma_del_tdls_sta() - process delete sta request from UMAC in TDLS
5512  * @wma: wma handle
5513  * @del_sta: delete sta params
5514  *
5515  * Return: none
5516  */
5517 static void wma_del_tdls_sta(tp_wma_handle wma, tpDeleteStaParams del_sta)
5518 {
5519 	struct tdls_peer_update_state *peer_state;
5520 	struct wma_target_req *msg;
5521 	int status;
5522 
5523 	peer_state = qdf_mem_malloc(sizeof(*peer_state));
5524 	if (!peer_state) {
5525 		del_sta->status = QDF_STATUS_E_NOMEM;
5526 		goto send_del_rsp;
5527 	}
5528 
5529 	peer_state->peer_state = TDLS_PEER_STATE_TEARDOWN;
5530 	peer_state->vdev_id = del_sta->smesessionId;
5531 	peer_state->resp_reqd = del_sta->respReqd;
5532 	qdf_mem_copy(&peer_state->peer_macaddr,
5533 		     &del_sta->staMac, sizeof(tSirMacAddr));
5534 
5535 	wma_debug("sending tdls_peer_state for peer mac: "QDF_MAC_ADDR_FMT", peerState: %d",
5536 		  QDF_MAC_ADDR_REF(peer_state->peer_macaddr),
5537 		 peer_state->peer_state);
5538 
5539 	status = wma_update_tdls_peer_state(wma, peer_state);
5540 
5541 	if (status < 0) {
5542 		wma_err("wma_update_tdls_peer_state returned failure");
5543 		del_sta->status = QDF_STATUS_E_FAILURE;
5544 		goto send_del_rsp;
5545 	}
5546 
5547 	if (del_sta->respReqd &&
5548 			wmi_service_enabled(wma->wmi_handle,
5549 				wmi_service_sync_delete_cmds)) {
5550 		del_sta->status = QDF_STATUS_SUCCESS;
5551 		msg = wma_fill_hold_req(wma,
5552 				del_sta->smesessionId,
5553 				WMA_DELETE_STA_REQ,
5554 				WMA_DELETE_STA_RSP_START, del_sta,
5555 				WMA_DELETE_STA_TIMEOUT);
5556 		if (!msg) {
5557 			wma_err("Failed to allocate vdev_id %d",
5558 				del_sta->smesessionId);
5559 			wma_remove_req(wma,
5560 					del_sta->smesessionId,
5561 					WMA_DELETE_STA_RSP_START);
5562 			del_sta->status = QDF_STATUS_E_NOMEM;
5563 			goto send_del_rsp;
5564 		}
5565 
5566 		wma_acquire_wakelock(&wma->wmi_cmd_rsp_wake_lock,
5567 				WMA_FW_RSP_EVENT_WAKE_LOCK_DURATION);
5568 	}
5569 
5570 	return;
5571 
5572 send_del_rsp:
5573 	if (del_sta->respReqd) {
5574 		wma_debug("Sending del rsp to umac (status: %d)",
5575 			 del_sta->status);
5576 		wma_send_msg_high_priority(wma, WMA_DELETE_STA_RSP,
5577 					   (void *)del_sta, 0);
5578 	}
5579 }
5580 #endif
5581 
5582 /**
5583  * wma_delete_sta_req_sta_mode() - process delete sta request from UMAC
5584  * @wma: wma handle
5585  * @params: delete sta params
5586  *
5587  * Return: none
5588  */
5589 static void wma_delete_sta_req_sta_mode(tp_wma_handle wma,
5590 					tpDeleteStaParams params)
5591 {
5592 	QDF_STATUS status = QDF_STATUS_SUCCESS;
5593 	struct wma_txrx_node *iface;
5594 
5595 	if (wmi_service_enabled(wma->wmi_handle,
5596 		wmi_service_listen_interval_offload_support)) {
5597 		struct wlan_objmgr_vdev *vdev;
5598 
5599 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(wma->psoc,
5600 							params->smesessionId,
5601 							WLAN_LEGACY_WMA_ID);
5602 		if (vdev) {
5603 			if (ucfg_pmo_get_moddtim_user_enable(vdev))
5604 				ucfg_pmo_set_moddtim_user_enable(vdev, false);
5605 			wlan_objmgr_vdev_release_ref(vdev, WLAN_LEGACY_WMA_ID);
5606 		}
5607 	}
5608 
5609 	iface = &wma->interfaces[params->smesessionId];
5610 	iface->uapsd_cached_val = 0;
5611 #ifdef FEATURE_WLAN_TDLS
5612 	if (STA_ENTRY_TDLS_PEER == params->staType) {
5613 		wma_del_tdls_sta(wma, params);
5614 		return;
5615 	}
5616 #endif
5617 	params->status = status;
5618 	if (params->respReqd) {
5619 		wma_debug("vdev_id %d status %d",
5620 			 params->smesessionId, status);
5621 		wma_send_msg_high_priority(wma, WMA_DELETE_STA_RSP,
5622 					   (void *)params, 0);
5623 	}
5624 }
5625 
5626 static void wma_sap_prevent_runtime_pm(tp_wma_handle wma)
5627 {
5628 	qdf_runtime_pm_prevent_suspend(&wma->sap_prevent_runtime_pm_lock);
5629 }
5630 
5631 static void wma_sap_allow_runtime_pm(tp_wma_handle wma)
5632 {
5633 	qdf_runtime_pm_allow_suspend(&wma->sap_prevent_runtime_pm_lock);
5634 }
5635 
5636 static void wma_ndp_prevent_runtime_pm(tp_wma_handle wma)
5637 {
5638 	qdf_runtime_pm_prevent_suspend(&wma->ndp_prevent_runtime_pm_lock);
5639 }
5640 
5641 static void wma_ndp_allow_runtime_pm(tp_wma_handle wma)
5642 {
5643 	qdf_runtime_pm_allow_suspend(&wma->ndp_prevent_runtime_pm_lock);
5644 }
5645 #ifdef FEATURE_STA_MODE_VOTE_LINK
5646 static bool wma_add_sta_allow_sta_mode_vote_link(uint8_t oper_mode)
5647 {
5648 	if (oper_mode == BSS_OPERATIONAL_MODE_STA && ucfg_ipa_is_enabled())
5649 		return true;
5650 
5651 	return false;
5652 }
5653 #else /* !FEATURE_STA_MODE_VOTE_LINK */
5654 static bool wma_add_sta_allow_sta_mode_vote_link(uint8_t oper_mode)
5655 {
5656 	return false;
5657 }
5658 #endif /* FEATURE_STA_MODE_VOTE_LINK */
5659 
5660 static bool wma_is_vdev_in_sap_mode(tp_wma_handle wma, uint8_t vdev_id)
5661 {
5662 	struct wma_txrx_node *intf = wma->interfaces;
5663 
5664 	if (vdev_id >= wma->max_bssid) {
5665 		wma_err("Invalid vdev_id %hu", vdev_id);
5666 		QDF_ASSERT(0);
5667 		return false;
5668 	}
5669 
5670 	if ((intf[vdev_id].type == WMI_VDEV_TYPE_AP) &&
5671 	    (intf[vdev_id].sub_type == 0))
5672 		return true;
5673 
5674 	return false;
5675 }
5676 
5677 static bool wma_is_vdev_in_go_mode(tp_wma_handle wma, uint8_t vdev_id)
5678 {
5679 	struct wma_txrx_node *intf = wma->interfaces;
5680 
5681 	if (vdev_id >= wma->max_bssid) {
5682 		wma_err("Invalid vdev_id %hu", vdev_id);
5683 		QDF_ASSERT(0);
5684 		return false;
5685 	}
5686 
5687 	if ((intf[vdev_id].type == WMI_VDEV_TYPE_AP) &&
5688 	    (intf[vdev_id].sub_type == WMI_UNIFIED_VDEV_SUBTYPE_P2P_GO))
5689 		return true;
5690 
5691 	return false;
5692 }
5693 
5694 static void wma_sap_d3_wow_client_connect(tp_wma_handle wma)
5695 {
5696 	uint32_t num_clients;
5697 
5698 	num_clients = qdf_atomic_inc_return(&wma->sap_num_clients_connected);
5699 	wmi_debug("sap d3 wow %d client connected", num_clients);
5700 	if (num_clients == SAP_D3_WOW_MAX_CLIENT_HOLD_WAKE_LOCK) {
5701 		wmi_info("max clients connected acquire sap d3 wow wake lock");
5702 		qdf_wake_lock_acquire(&wma->sap_d3_wow_wake_lock,
5703 				      WIFI_POWER_EVENT_WAKELOCK_SAP_D3_WOW);
5704 	}
5705 }
5706 
5707 static void wma_sap_d3_wow_client_disconnect(tp_wma_handle wma)
5708 {
5709 	uint32_t num_clients;
5710 
5711 	num_clients = qdf_atomic_dec_return(&wma->sap_num_clients_connected);
5712 	wmi_debug("sap d3 wow %d client connected", num_clients);
5713 	if (num_clients == SAP_D3_WOW_MAX_CLIENT_RELEASE_WAKE_LOCK) {
5714 		wmi_info("max clients disconnected release sap d3 wow wake lock");
5715 		qdf_wake_lock_release(&wma->sap_d3_wow_wake_lock,
5716 				      WIFI_POWER_EVENT_WAKELOCK_SAP_D3_WOW);
5717 	}
5718 }
5719 
5720 static void wma_go_d3_wow_client_connect(tp_wma_handle wma)
5721 {
5722 	uint32_t num_clients;
5723 
5724 	num_clients = qdf_atomic_inc_return(&wma->go_num_clients_connected);
5725 	wmi_debug("go d3 wow %d client connected", num_clients);
5726 	if (num_clients == SAP_D3_WOW_MAX_CLIENT_HOLD_WAKE_LOCK) {
5727 		wmi_info("max clients connected acquire go d3 wow wake lock");
5728 		qdf_wake_lock_acquire(&wma->go_d3_wow_wake_lock,
5729 				      WIFI_POWER_EVENT_WAKELOCK_GO_D3_WOW);
5730 	}
5731 }
5732 
5733 static void wma_go_d3_wow_client_disconnect(tp_wma_handle wma)
5734 {
5735 	uint32_t num_clients;
5736 
5737 	num_clients = qdf_atomic_dec_return(&wma->go_num_clients_connected);
5738 	wmi_debug("go d3 wow %d client connected", num_clients);
5739 	if (num_clients == SAP_D3_WOW_MAX_CLIENT_RELEASE_WAKE_LOCK) {
5740 		wmi_info("max clients disconnected release go d3 wow wake lock");
5741 		qdf_wake_lock_release(&wma->go_d3_wow_wake_lock,
5742 				      WIFI_POWER_EVENT_WAKELOCK_GO_D3_WOW);
5743 	}
5744 }
5745 
5746 void wma_add_sta(tp_wma_handle wma, tpAddStaParams add_sta)
5747 {
5748 	uint8_t oper_mode = BSS_OPERATIONAL_MODE_STA;
5749 	void *htc_handle;
5750 	QDF_STATUS status = QDF_STATUS_SUCCESS;
5751 	uint8_t vdev_id = add_sta->smesessionId;
5752 
5753 	htc_handle = lmac_get_htc_hdl(wma->psoc);
5754 	if (!htc_handle) {
5755 		wma_err("HTC handle is NULL");
5756 		return;
5757 	}
5758 
5759 	wma_debug("Vdev %d BSSID "QDF_MAC_ADDR_FMT, vdev_id,
5760 		  QDF_MAC_ADDR_REF(add_sta->bssId));
5761 
5762 	if (wma_is_vdev_in_ap_mode(wma, vdev_id))
5763 		oper_mode = BSS_OPERATIONAL_MODE_AP;
5764 
5765 	if (WMA_IS_VDEV_IN_NDI_MODE(wma->interfaces, vdev_id))
5766 		oper_mode = BSS_OPERATIONAL_MODE_NDI;
5767 	switch (oper_mode) {
5768 	case BSS_OPERATIONAL_MODE_STA:
5769 		wma_add_sta_req_sta_mode(wma, add_sta);
5770 		break;
5771 
5772 	case BSS_OPERATIONAL_MODE_AP:
5773 		wma_add_sta_req_ap_mode(wma, add_sta);
5774 		break;
5775 	case BSS_OPERATIONAL_MODE_NDI:
5776 		status = wma_add_sta_ndi_mode(wma, add_sta);
5777 		break;
5778 	}
5779 
5780 	/*
5781 	 * not use add_sta after this to avoid use after free
5782 	 * as it maybe freed.
5783 	 */
5784 
5785 	/* handle wow for sap with 1 or more peer in same way */
5786 	if (wma_is_vdev_in_sap_mode(wma, vdev_id)) {
5787 		bool is_bus_suspend_allowed_in_sap_mode =
5788 			(wlan_pmo_get_sap_mode_bus_suspend(wma->psoc) &&
5789 				wmi_service_enabled(wma->wmi_handle,
5790 					wmi_service_sap_connected_d3_wow));
5791 		if (!is_bus_suspend_allowed_in_sap_mode) {
5792 			htc_vote_link_up(htc_handle, HTC_LINK_VOTE_SAP_USER_ID);
5793 			wmi_info("sap d0 wow");
5794 		} else {
5795 			wmi_debug("sap d3 wow");
5796 			wma_sap_d3_wow_client_connect(wma);
5797 		}
5798 		wma_sap_prevent_runtime_pm(wma);
5799 
5800 		return;
5801 	}
5802 
5803 	/* handle wow for p2pgo with 1 or more peer in same way */
5804 	if (wma_is_vdev_in_go_mode(wma, vdev_id)) {
5805 		bool is_bus_suspend_allowed_in_go_mode =
5806 			(wlan_pmo_get_go_mode_bus_suspend(wma->psoc) &&
5807 				wmi_service_enabled(wma->wmi_handle,
5808 					wmi_service_go_connected_d3_wow));
5809 		if (!is_bus_suspend_allowed_in_go_mode) {
5810 			htc_vote_link_up(htc_handle, HTC_LINK_VOTE_GO_USER_ID);
5811 			wmi_info("p2p go d0 wow");
5812 		} else {
5813 			wmi_info("p2p go d3 wow");
5814 			wma_go_d3_wow_client_connect(wma);
5815 		}
5816 		wma_sap_prevent_runtime_pm(wma);
5817 
5818 		return;
5819 	}
5820 
5821 	/* handle wow for nan with 1 or more peer in same way */
5822 	if (BSS_OPERATIONAL_MODE_NDI == oper_mode &&
5823 	    QDF_IS_STATUS_SUCCESS(status)) {
5824 		wma_debug("disable runtime pm and vote for link up");
5825 		htc_vote_link_up(htc_handle, HTC_LINK_VOTE_NDP_USER_ID);
5826 		wma_ndp_prevent_runtime_pm(wma);
5827 	} else if (wma_add_sta_allow_sta_mode_vote_link(oper_mode)) {
5828 		wma_debug("vote for link up");
5829 		htc_vote_link_up(htc_handle, HTC_LINK_VOTE_STA_USER_ID);
5830 	}
5831 }
5832 
5833 void wma_delete_sta(tp_wma_handle wma, tpDeleteStaParams del_sta)
5834 {
5835 	uint8_t oper_mode = BSS_OPERATIONAL_MODE_STA;
5836 	uint8_t vdev_id = del_sta->smesessionId;
5837 	bool rsp_requested = del_sta->respReqd;
5838 	void *htc_handle;
5839 	QDF_STATUS status = QDF_STATUS_SUCCESS;
5840 
5841 	htc_handle = lmac_get_htc_hdl(wma->psoc);
5842 	if (!htc_handle) {
5843 		wma_err("HTC handle is NULL");
5844 		return;
5845 	}
5846 
5847 	if (wma_is_vdev_in_ap_mode(wma, vdev_id))
5848 		oper_mode = BSS_OPERATIONAL_MODE_AP;
5849 	if (del_sta->staType == STA_ENTRY_NDI_PEER)
5850 		oper_mode = BSS_OPERATIONAL_MODE_NDI;
5851 
5852 	wma_debug("vdev %d oper_mode %d", vdev_id, oper_mode);
5853 
5854 	switch (oper_mode) {
5855 	case BSS_OPERATIONAL_MODE_STA:
5856 		if (wlan_cm_is_roam_sync_in_progress(wma->psoc, vdev_id) ||
5857 		    MLME_IS_MLO_ROAM_SYNCH_IN_PROGRESS(wma->psoc, vdev_id) ||
5858 		    mlo_is_roaming_in_progress(wma->psoc, vdev_id)) {
5859 			wma_debug("LFR3: Del STA on vdev_id %d", vdev_id);
5860 			qdf_mem_free(del_sta);
5861 			return;
5862 		}
5863 		wma_delete_sta_req_sta_mode(wma, del_sta);
5864 		if (!rsp_requested)
5865 			qdf_mem_free(del_sta);
5866 
5867 		break;
5868 
5869 	case BSS_OPERATIONAL_MODE_AP:
5870 		wma_delete_sta_req_ap_mode(wma, del_sta);
5871 		/* free the memory here only if sync feature is not enabled */
5872 		if (!rsp_requested &&
5873 		    !wmi_service_enabled(wma->wmi_handle,
5874 					 wmi_service_sync_delete_cmds))
5875 			qdf_mem_free(del_sta);
5876 		else if (!rsp_requested &&
5877 			 (del_sta->status != QDF_STATUS_SUCCESS))
5878 			qdf_mem_free(del_sta);
5879 		break;
5880 	case BSS_OPERATIONAL_MODE_NDI:
5881 		status = wma_delete_sta_req_ndi_mode(wma, del_sta);
5882 		break;
5883 	default:
5884 		wma_err("Incorrect oper mode %d", oper_mode);
5885 		qdf_mem_free(del_sta);
5886 	}
5887 
5888 	if (wma_is_vdev_in_sap_mode(wma, vdev_id)) {
5889 		bool is_bus_suspend_allowed_in_sap_mode =
5890 			(wlan_pmo_get_sap_mode_bus_suspend(wma->psoc) &&
5891 				wmi_service_enabled(wma->wmi_handle,
5892 					wmi_service_sap_connected_d3_wow));
5893 		if (!is_bus_suspend_allowed_in_sap_mode) {
5894 			htc_vote_link_down(htc_handle,
5895 					   HTC_LINK_VOTE_SAP_USER_ID);
5896 			wmi_info("sap d0 wow");
5897 		} else {
5898 			wmi_debug("sap d3 wow");
5899 			wma_sap_d3_wow_client_disconnect(wma);
5900 		}
5901 		wma_sap_allow_runtime_pm(wma);
5902 
5903 		return;
5904 	}
5905 
5906 	if (wma_is_vdev_in_go_mode(wma, vdev_id)) {
5907 		bool is_bus_suspend_allowed_in_go_mode =
5908 			(wlan_pmo_get_go_mode_bus_suspend(wma->psoc) &&
5909 				wmi_service_enabled(wma->wmi_handle,
5910 					wmi_service_go_connected_d3_wow));
5911 		if (!is_bus_suspend_allowed_in_go_mode) {
5912 			htc_vote_link_down(htc_handle,
5913 					   HTC_LINK_VOTE_GO_USER_ID);
5914 			wmi_info("p2p go d0 wow");
5915 		} else {
5916 			wmi_info("p2p go d3 wow");
5917 			wma_go_d3_wow_client_disconnect(wma);
5918 		}
5919 		wma_sap_allow_runtime_pm(wma);
5920 
5921 		return;
5922 	}
5923 
5924 	if (BSS_OPERATIONAL_MODE_NDI == oper_mode &&
5925 	    QDF_IS_STATUS_SUCCESS(status)) {
5926 		wma_debug("allow runtime pm and vote for link down");
5927 		htc_vote_link_down(htc_handle, HTC_LINK_VOTE_NDP_USER_ID);
5928 		wma_ndp_allow_runtime_pm(wma);
5929 	} else if (wma_add_sta_allow_sta_mode_vote_link(oper_mode)) {
5930 		wma_debug("vote for link down");
5931 		htc_vote_link_down(htc_handle, HTC_LINK_VOTE_STA_USER_ID);
5932 	}
5933 }
5934 
5935 void wma_delete_bss_ho_fail(tp_wma_handle wma, uint8_t vdev_id)
5936 {
5937 	QDF_STATUS status = QDF_STATUS_SUCCESS;
5938 	struct wma_txrx_node *iface;
5939 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
5940 	struct vdev_stop_response resp_event;
5941 	struct del_bss_resp *vdev_stop_resp;
5942 	uint8_t *bssid;
5943 
5944 	iface = &wma->interfaces[vdev_id];
5945 	if (!iface) {
5946 		wma_err("iface for vdev_id %d is already deleted", vdev_id);
5947 		goto fail_del_bss_ho_fail;
5948 	}
5949 	bssid = wma_get_vdev_bssid(iface->vdev);
5950 	if (!bssid) {
5951 		wma_err("Invalid bssid");
5952 		status = QDF_STATUS_E_FAILURE;
5953 		goto fail_del_bss_ho_fail;
5954 	}
5955 	qdf_mem_zero(bssid, QDF_MAC_ADDR_SIZE);
5956 
5957 	if (iface->psnr_req) {
5958 		qdf_mem_free(iface->psnr_req);
5959 		iface->psnr_req = NULL;
5960 	}
5961 
5962 	if (iface->rcpi_req) {
5963 		struct sme_rcpi_req *rcpi_req = iface->rcpi_req;
5964 
5965 		iface->rcpi_req = NULL;
5966 		qdf_mem_free(rcpi_req);
5967 	}
5968 
5969 	if (iface->roam_scan_stats_req) {
5970 		struct sir_roam_scan_stats *roam_scan_stats_req =
5971 						iface->roam_scan_stats_req;
5972 
5973 		iface->roam_scan_stats_req = NULL;
5974 		qdf_mem_free(roam_scan_stats_req);
5975 	}
5976 
5977 	wma_debug("vdev_id: %d, pausing tx_ll_queue for VDEV_STOP (del_bss)",
5978 		 vdev_id);
5979 	cdp_fc_vdev_pause(soc, vdev_id, OL_TXQ_PAUSE_REASON_VDEV_STOP, 0);
5980 	wma_vdev_set_pause_bit(vdev_id, PAUSE_TYPE_HOST);
5981 	cdp_fc_vdev_flush(soc, vdev_id);
5982 	wma_debug("vdev_id: %d, un-pausing tx_ll_queue for VDEV_STOP rsp",
5983 		 vdev_id);
5984 	cdp_fc_vdev_unpause(soc, vdev_id, OL_TXQ_PAUSE_REASON_VDEV_STOP, 0);
5985 	wma_vdev_clear_pause_bit(vdev_id, PAUSE_TYPE_HOST);
5986 	qdf_atomic_set(&iface->bss_status, WMA_BSS_STATUS_STOPPED);
5987 	wma_debug("(type %d subtype %d) BSS is stopped",
5988 			iface->type, iface->sub_type);
5989 
5990 	status = mlme_set_vdev_stop_type(iface->vdev,
5991 					 WMA_DELETE_BSS_HO_FAIL_REQ);
5992 	if (QDF_IS_STATUS_ERROR(status)) {
5993 		wma_err("Failed to set wma req msg_type for vdev_id: %d",
5994 			vdev_id);
5995 		goto fail_del_bss_ho_fail;
5996 	}
5997 
5998 	/* Try to use the vdev stop response path */
5999 	resp_event.vdev_id = vdev_id;
6000 	status = wma_handle_vdev_stop_rsp(wma, &resp_event);
6001 	if (QDF_IS_STATUS_ERROR(status)) {
6002 		wma_err("Failed to handle vdev stop rsp for vdev_id %d",
6003 			vdev_id);
6004 		goto fail_del_bss_ho_fail;
6005 	}
6006 
6007 	return;
6008 
6009 fail_del_bss_ho_fail:
6010 	vdev_stop_resp = qdf_mem_malloc(sizeof(*vdev_stop_resp));
6011 	if (!vdev_stop_resp)
6012 		return;
6013 
6014 	vdev_stop_resp->vdev_id = vdev_id;
6015 	vdev_stop_resp->status = status;
6016 	wma_send_msg_high_priority(wma, WMA_DELETE_BSS_HO_FAIL_RSP,
6017 				   (void *)vdev_stop_resp, 0);
6018 }
6019 
6020 /**
6021  * wma_wait_tx_complete() - Wait till tx packets are drained
6022  * @wma: wma handle
6023  * @session_id: vdev id
6024  *
6025  * Return: none
6026  */
6027 static void wma_wait_tx_complete(tp_wma_handle wma,
6028 				uint32_t session_id)
6029 {
6030 	uint8_t max_wait_iterations = 0, delay = 0;
6031 	cdp_config_param_type val;
6032 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
6033 	QDF_STATUS status;
6034 
6035 	if (!wma_is_vdev_valid(session_id)) {
6036 		wma_err("Vdev is not valid: %d", session_id);
6037 		return;
6038 	}
6039 
6040 	status = ucfg_mlme_get_delay_before_vdev_stop(wma->psoc, &delay);
6041 	if (QDF_IS_STATUS_ERROR(status))
6042 		wma_err("Failed to get delay before vdev stop");
6043 
6044 	max_wait_iterations = delay / WMA_TX_Q_RECHECK_TIMER_WAIT;
6045 	if (cdp_txrx_get_pdev_param(soc,
6046 				    wlan_objmgr_pdev_get_pdev_id(wma->pdev),
6047 				    CDP_TX_PENDING, &val))
6048 		return;
6049 	while (val.cdp_pdev_param_tx_pending && max_wait_iterations) {
6050 		wma_warn("Waiting for outstanding packet to drain");
6051 		qdf_wait_for_event_completion(&wma->tx_queue_empty_event,
6052 				      WMA_TX_Q_RECHECK_TIMER_WAIT);
6053 		if (cdp_txrx_get_pdev_param(
6054 					soc,
6055 					wlan_objmgr_pdev_get_pdev_id(wma->pdev),
6056 					CDP_TX_PENDING, &val))
6057 			return;
6058 		max_wait_iterations--;
6059 	}
6060 }
6061 
6062 void wma_delete_bss(tp_wma_handle wma, uint8_t vdev_id)
6063 {
6064 	bool peer_exist = false;
6065 	QDF_STATUS status = QDF_STATUS_SUCCESS;
6066 	uint32_t tx_pending = 0;
6067 	cdp_config_param_type val;
6068 	bool roam_synch_in_progress = false;
6069 	struct wma_txrx_node *iface;
6070 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
6071 	struct qdf_mac_addr bssid;
6072 	struct del_bss_resp *params;
6073 	uint8_t *addr, *bssid_addr;
6074 
6075 	iface = &wma->interfaces[vdev_id];
6076 	if (!iface || !iface->vdev) {
6077 		wma_err("vdev id %d is already deleted", vdev_id);
6078 		goto out;
6079 	}
6080 
6081 	status = wlan_vdev_get_bss_peer_mac(iface->vdev, &bssid);
6082 	if (QDF_IS_STATUS_ERROR(status)) {
6083 		wma_err("vdev id %d : failed to get bssid", vdev_id);
6084 		goto out;
6085 	}
6086 
6087 	addr = wlan_vdev_mlme_get_macaddr(iface->vdev);
6088 	if (!addr) {
6089 		wma_err("vdev id %d : failed to get macaddr", vdev_id);
6090 		goto out;
6091 	}
6092 
6093 	if (WMA_IS_VDEV_IN_NDI_MODE(wma->interfaces,
6094 			vdev_id))
6095 		/* In ndi case, self mac is used to create the self peer */
6096 		peer_exist = wma_cdp_find_peer_by_addr(addr);
6097 	else
6098 		peer_exist = wma_cdp_find_peer_by_addr(bssid.bytes);
6099 	if (!peer_exist) {
6100 		wma_err("Failed to find peer "QDF_MAC_ADDR_FMT,
6101 			 QDF_MAC_ADDR_REF(bssid.bytes));
6102 		status = QDF_STATUS_E_FAILURE;
6103 		goto out;
6104 	}
6105 	bssid_addr = wma_get_vdev_bssid(wma->interfaces[vdev_id].vdev);
6106 	if (!bssid_addr) {
6107 		wma_err("Failed to bssid for vdev_%d", vdev_id);
6108 		status = QDF_STATUS_E_FAILURE;
6109 		goto out;
6110 	}
6111 	qdf_mem_zero(bssid_addr,
6112 		     QDF_MAC_ADDR_SIZE);
6113 
6114 	wma_delete_invalid_peer_entries(vdev_id, NULL);
6115 
6116 	if (iface->psnr_req) {
6117 		qdf_mem_free(iface->psnr_req);
6118 		iface->psnr_req = NULL;
6119 	}
6120 
6121 	if (iface->rcpi_req) {
6122 		struct sme_rcpi_req *rcpi_req = iface->rcpi_req;
6123 
6124 		iface->rcpi_req = NULL;
6125 		qdf_mem_free(rcpi_req);
6126 	}
6127 
6128 	if (iface->roam_scan_stats_req) {
6129 		struct sir_roam_scan_stats *roam_scan_stats_req =
6130 						iface->roam_scan_stats_req;
6131 
6132 		iface->roam_scan_stats_req = NULL;
6133 		qdf_mem_free(roam_scan_stats_req);
6134 	}
6135 
6136 	if (wlan_cm_is_roam_sync_in_progress(wma->psoc, vdev_id) ||
6137 	    MLME_IS_MLO_ROAM_SYNCH_IN_PROGRESS(wma->psoc, vdev_id) ||
6138 	    mlo_is_roaming_in_progress(wma->psoc, vdev_id)) {
6139 		roam_synch_in_progress = true;
6140 		wma_debug("LFR3: Setting vdev_up to FALSE for vdev:%d",
6141 			  vdev_id);
6142 
6143 		goto detach_peer;
6144 	}
6145 
6146 	status = mlme_set_vdev_stop_type(iface->vdev,
6147 					 WMA_DELETE_BSS_REQ);
6148 	if (QDF_IS_STATUS_ERROR(status)) {
6149 		wma_err("Failed to set wma req msg_type for vdev_id: %d",
6150 			vdev_id);
6151 		goto out;
6152 	}
6153 
6154 	cdp_txrx_get_pdev_param(soc, wlan_objmgr_pdev_get_pdev_id(wma->pdev),
6155 				CDP_TX_PENDING, &val);
6156 	tx_pending = val.cdp_pdev_param_tx_pending;
6157 	wma_debug("Outstanding msdu packets: %u", tx_pending);
6158 	wma_wait_tx_complete(wma, vdev_id);
6159 
6160 	cdp_txrx_get_pdev_param(soc, wlan_objmgr_pdev_get_pdev_id(wma->pdev),
6161 				CDP_TX_PENDING, &val);
6162 	if (tx_pending) {
6163 		wma_debug("Outstanding msdu packets before VDEV_STOP : %u",
6164 			 tx_pending);
6165 	}
6166 
6167 	wma_debug("vdev_id: %d, pausing tx_ll_queue for VDEV_STOP (del_bss)",
6168 		 vdev_id);
6169 	wma_vdev_set_pause_bit(vdev_id, PAUSE_TYPE_HOST);
6170 	cdp_fc_vdev_pause(soc, vdev_id,
6171 			  OL_TXQ_PAUSE_REASON_VDEV_STOP, 0);
6172 
6173 	if (wma_send_vdev_stop_to_fw(wma, vdev_id)) {
6174 		struct vdev_stop_response vdev_stop_rsp = {0};
6175 
6176 		wma_err("Failed to send vdev stop to FW, explicitly invoke vdev stop rsp");
6177 		vdev_stop_rsp.vdev_id = vdev_id;
6178 		wma_handle_vdev_stop_rsp(wma, &vdev_stop_rsp);
6179 		qdf_atomic_set(&iface->bss_status, WMA_BSS_STATUS_STOPPED);
6180 	}
6181 	wma_debug("bssid "QDF_MAC_ADDR_FMT" vdev_id %d",
6182 		  QDF_MAC_ADDR_REF(bssid.bytes), vdev_id);
6183 
6184 	return;
6185 
6186 detach_peer:
6187 	wma_remove_peer(wma, bssid.bytes, vdev_id, roam_synch_in_progress);
6188 	if (roam_synch_in_progress)
6189 		return;
6190 
6191 out:
6192 	/* skip when legacy to mlo roam sync ongoing */
6193 	if (MLME_IS_MLO_ROAM_SYNCH_IN_PROGRESS(wma->psoc, vdev_id))
6194 		return;
6195 
6196 	params = qdf_mem_malloc(sizeof(*params));
6197 	if (!params)
6198 		return;
6199 
6200 	params->vdev_id = vdev_id;
6201 	params->status = status;
6202 	wma_send_msg_high_priority(wma, WMA_DELETE_BSS_RSP, params, 0);
6203 }
6204 
6205 /**
6206  * wma_find_vdev_by_type() - This function finds vdev_id based on input type
6207  * @wma: wma handle
6208  * @type: vdev type
6209  *
6210  * Return: vdev id
6211  */
6212 int32_t wma_find_vdev_by_type(tp_wma_handle wma, int32_t type)
6213 {
6214 	int32_t vdev_id = 0;
6215 	struct wma_txrx_node *intf = wma->interfaces;
6216 
6217 	for (vdev_id = 0; vdev_id < wma->max_bssid; vdev_id++) {
6218 		if (intf) {
6219 			if (intf[vdev_id].type == type)
6220 				return vdev_id;
6221 		}
6222 	}
6223 
6224 	return -EFAULT;
6225 }
6226 
6227 void wma_set_vdev_intrabss_fwd(tp_wma_handle wma_handle,
6228 				      tpDisableIntraBssFwd pdis_intra_fwd)
6229 {
6230 	struct wlan_objmgr_vdev *vdev;
6231 
6232 	wma_debug("intra_fwd:vdev(%d) intrabss_dis=%s",
6233 		 pdis_intra_fwd->sessionId,
6234 		 (pdis_intra_fwd->disableintrabssfwd ? "true" : "false"));
6235 
6236 	vdev = wma_handle->interfaces[pdis_intra_fwd->sessionId].vdev;
6237 	cdp_cfg_vdev_rx_set_intrabss_fwd(cds_get_context(QDF_MODULE_ID_SOC),
6238 					 pdis_intra_fwd->sessionId,
6239 					 pdis_intra_fwd->disableintrabssfwd);
6240 }
6241 
6242 /**
6243  * wma_get_pdev_from_scn_handle() - API to get pdev from scn handle
6244  * @scn_handle: opaque wma handle
6245  *
6246  * API to get pdev from scn handle
6247  *
6248  * Return: None
6249  */
6250 static struct wlan_objmgr_pdev *wma_get_pdev_from_scn_handle(void *scn_handle)
6251 {
6252 	tp_wma_handle wma_handle;
6253 
6254 	if (!scn_handle) {
6255 		wma_err("invalid scn handle");
6256 		return NULL;
6257 	}
6258 	wma_handle = (tp_wma_handle)scn_handle;
6259 
6260 	return wma_handle->pdev;
6261 }
6262 
6263 void wma_store_pdev(void *wma_ctx, struct wlan_objmgr_pdev *pdev)
6264 {
6265 	tp_wma_handle wma = (tp_wma_handle)wma_ctx;
6266 	QDF_STATUS status;
6267 
6268 	status = wlan_objmgr_pdev_try_get_ref(pdev, WLAN_LEGACY_WMA_ID);
6269 	if (QDF_STATUS_SUCCESS != status) {
6270 		wma->pdev = NULL;
6271 		return;
6272 	}
6273 
6274 	wma->pdev = pdev;
6275 
6276 	target_if_store_pdev_target_if_ctx(wma_get_pdev_from_scn_handle);
6277 	target_pdev_set_wmi_handle(wma->pdev->tgt_if_handle,
6278 				   wma->wmi_handle);
6279 }
6280 
6281 /**
6282  * wma_vdev_reset_beacon_interval_timer() - reset beacon interval back
6283  * to its original value after the channel switch.
6284  *
6285  * @data: data
6286  *
6287  * Return: void
6288  */
6289 static void wma_vdev_reset_beacon_interval_timer(void *data)
6290 {
6291 	tp_wma_handle wma;
6292 	struct wma_beacon_interval_reset_req *req =
6293 		(struct wma_beacon_interval_reset_req *)data;
6294 	uint16_t beacon_interval = req->interval;
6295 	uint8_t vdev_id = req->vdev_id;
6296 
6297 	wma = (tp_wma_handle)cds_get_context(QDF_MODULE_ID_WMA);
6298 	if (!wma)
6299 		goto end;
6300 
6301 	/* Change the beacon interval back to its original value */
6302 	wma_debug("Change beacon interval back to %d", beacon_interval);
6303 	wma_update_beacon_interval(wma, vdev_id, beacon_interval);
6304 
6305 end:
6306 	qdf_timer_stop(&req->event_timeout);
6307 	qdf_timer_free(&req->event_timeout);
6308 	qdf_mem_free(req);
6309 }
6310 
6311 int wma_fill_beacon_interval_reset_req(tp_wma_handle wma, uint8_t vdev_id,
6312 				uint16_t beacon_interval, uint32_t timeout)
6313 {
6314 	struct wma_beacon_interval_reset_req *req;
6315 
6316 	req = qdf_mem_malloc(sizeof(*req));
6317 	if (!req)
6318 		return -ENOMEM;
6319 
6320 	wma_debug("vdev_id %d ", vdev_id);
6321 	req->vdev_id = vdev_id;
6322 	req->interval = beacon_interval;
6323 	qdf_timer_init(NULL, &req->event_timeout,
6324 		wma_vdev_reset_beacon_interval_timer, req, QDF_TIMER_TYPE_SW);
6325 	qdf_timer_start(&req->event_timeout, timeout);
6326 
6327 	return 0;
6328 }
6329 
6330 QDF_STATUS wma_set_wlm_latency_level(void *wma_ptr,
6331 			struct wlm_latency_level_param *latency_params)
6332 {
6333 	QDF_STATUS ret;
6334 	tp_wma_handle wma = (tp_wma_handle)wma_ptr;
6335 
6336 	wma_debug("set latency level %d, fw wlm_latency_flags 0x%x",
6337 		 latency_params->wlm_latency_level,
6338 		 latency_params->wlm_latency_flags);
6339 
6340 	ret = wmi_unified_wlm_latency_level_cmd(wma->wmi_handle,
6341 						latency_params);
6342 	if (QDF_IS_STATUS_ERROR(ret))
6343 		wma_warn("Failed to set latency level");
6344 
6345 	return ret;
6346 }
6347 
6348 QDF_STATUS wma_add_bss_peer_sta(uint8_t vdev_id, uint8_t *bssid,
6349 				bool is_resp_required,
6350 				uint8_t *mld_mac, bool is_assoc_peer)
6351 {
6352 	tp_wma_handle wma;
6353 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
6354 
6355 	wma = cds_get_context(QDF_MODULE_ID_WMA);
6356 	if (!wma)
6357 		goto err;
6358 
6359 	if (is_resp_required)
6360 		status = wma_create_sta_mode_bss_peer(wma, bssid,
6361 						      WMI_PEER_TYPE_DEFAULT,
6362 						      vdev_id, mld_mac,
6363 						      is_assoc_peer);
6364 	else
6365 		status = wma_create_peer(wma, bssid, WMI_PEER_TYPE_DEFAULT,
6366 					 vdev_id, mld_mac, is_assoc_peer);
6367 err:
6368 	return status;
6369 }
6370 
6371 QDF_STATUS wma_send_vdev_stop(uint8_t vdev_id)
6372 {
6373 	tp_wma_handle wma;
6374 	void *soc = cds_get_context(QDF_MODULE_ID_SOC);
6375 	QDF_STATUS status;
6376 
6377 	wma = cds_get_context(QDF_MODULE_ID_WMA);
6378 	if (!wma)
6379 		return QDF_STATUS_E_FAILURE;
6380 
6381 	wma_debug("vdev_id: %d, pausing tx_ll_queue for VDEV_STOP", vdev_id);
6382 	cdp_fc_vdev_pause(soc, vdev_id,
6383 			  OL_TXQ_PAUSE_REASON_VDEV_STOP, 0);
6384 
6385 	status = mlme_set_vdev_stop_type(
6386 				wma->interfaces[vdev_id].vdev,
6387 				WMA_SET_LINK_STATE);
6388 	if (QDF_IS_STATUS_ERROR(status)) {
6389 		wma_alert("Failed to set wma req msg_type for vdev_id %d",
6390 			 vdev_id);
6391 		return QDF_STATUS_E_FAILURE;
6392 	}
6393 
6394 	wma_vdev_set_pause_bit(vdev_id, PAUSE_TYPE_HOST);
6395 
6396 	status = wma_send_vdev_stop_to_fw(wma, vdev_id);
6397 	if (QDF_IS_STATUS_ERROR(status)) {
6398 		struct vdev_stop_response resp_event;
6399 
6400 		wma_info("vdev %d Failed to send vdev stop", vdev_id);
6401 		resp_event.vdev_id = vdev_id;
6402 		mlme_set_connection_fail(wma->interfaces[vdev_id].vdev, false);
6403 		wma_handle_vdev_stop_rsp(wma, &resp_event);
6404 	}
6405 
6406 	/*
6407 	 * Remove peer, Vdev down and sending set link
6408 	 * response will be handled in vdev stop response
6409 	 * handler
6410 	 */
6411 
6412 	return QDF_STATUS_SUCCESS;
6413 }
6414 
6415 #define TX_MGMT_RATE_2G_ENABLE_OFFSET 30
6416 #define TX_MGMT_RATE_5G_ENABLE_OFFSET 31
6417 #define TX_MGMT_RATE_2G_OFFSET 0
6418 #define TX_MGMT_RATE_5G_OFFSET 12
6419 
6420 /**
6421  * wma_verify_rate_code() - verify if rate code is valid.
6422  * @rate_code: rate code
6423  * @band: band information
6424  *
6425  * Return: verify result
6426  */
6427 static bool wma_verify_rate_code(uint32_t rate_code, enum cds_band_type band)
6428 {
6429 	uint8_t preamble, nss, rate;
6430 	bool valid = true;
6431 
6432 	preamble = (rate_code & 0xc0) >> 6;
6433 	nss = (rate_code & 0x30) >> 4;
6434 	rate = rate_code & 0xf;
6435 
6436 	switch (preamble) {
6437 	case WMI_RATE_PREAMBLE_CCK:
6438 		if (nss != 0 || rate > 3 || band == CDS_BAND_5GHZ)
6439 			valid = false;
6440 		break;
6441 	case WMI_RATE_PREAMBLE_OFDM:
6442 		if (nss != 0 || rate > 7)
6443 			valid = false;
6444 		break;
6445 	case WMI_RATE_PREAMBLE_HT:
6446 		if (nss != 0 || rate > 7)
6447 			valid = false;
6448 		break;
6449 	case WMI_RATE_PREAMBLE_VHT:
6450 		if (nss != 0 || rate > 9)
6451 			valid = false;
6452 		break;
6453 	default:
6454 		break;
6455 	}
6456 	return valid;
6457 }
6458 
6459 /**
6460  * wma_vdev_mgmt_tx_rate() - set vdev mgmt rate.
6461  * @info: pointer to vdev set param.
6462  *
6463  * Return: return status
6464  */
6465 static QDF_STATUS wma_vdev_mgmt_tx_rate(struct dev_set_param *info)
6466 {
6467 	uint32_t cfg_val;
6468 	enum cds_band_type band = 0;
6469 	QDF_STATUS status;
6470 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
6471 
6472 	if (!mac) {
6473 		wma_err("Failed to get mac");
6474 		return QDF_STATUS_E_FAILURE;
6475 	}
6476 
6477 	cfg_val = mac->mlme_cfg->sap_cfg.rate_tx_mgmt;
6478 	band = CDS_BAND_ALL;
6479 	if (cfg_val == MLME_CFG_TX_MGMT_RATE_DEF ||
6480 	    !wma_verify_rate_code(cfg_val, band)) {
6481 		wma_nofl_debug("default WNI_CFG_RATE_FOR_TX_MGMT, ignore");
6482 		status = QDF_STATUS_E_FAILURE;
6483 	} else {
6484 		info->param_id = wmi_vdev_param_mgmt_tx_rate;
6485 		info->param_value = cfg_val;
6486 		status = QDF_STATUS_SUCCESS;
6487 	}
6488 	return status;
6489 }
6490 
6491 /**
6492  * wma_vdev_mgmt_perband_tx_rate() - set vdev mgmt perband tx rate.
6493  * @info: pointer to vdev set param
6494  *
6495  * Return: returns status
6496  */
6497 static QDF_STATUS wma_vdev_mgmt_perband_tx_rate(struct dev_set_param *info)
6498 {
6499 	uint32_t cfg_val;
6500 	uint32_t per_band_mgmt_tx_rate = 0;
6501 	enum cds_band_type band = 0;
6502 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
6503 
6504 	if (!mac) {
6505 		wma_err("failed to get mac");
6506 		return QDF_STATUS_E_FAILURE;
6507 	}
6508 
6509 	cfg_val = mac->mlme_cfg->sap_cfg.rate_tx_mgmt_2g;
6510 	band = CDS_BAND_2GHZ;
6511 	if (cfg_val == MLME_CFG_TX_MGMT_2G_RATE_DEF ||
6512 	    !wma_verify_rate_code(cfg_val, band)) {
6513 		wma_nofl_debug("use default 2G MGMT rate.");
6514 		per_band_mgmt_tx_rate &=
6515 		    ~(1 << TX_MGMT_RATE_2G_ENABLE_OFFSET);
6516 	} else {
6517 		per_band_mgmt_tx_rate |=
6518 		    (1 << TX_MGMT_RATE_2G_ENABLE_OFFSET);
6519 		per_band_mgmt_tx_rate |=
6520 		    ((cfg_val & 0x7FF) << TX_MGMT_RATE_2G_OFFSET);
6521 	}
6522 
6523 	cfg_val = mac->mlme_cfg->sap_cfg.rate_tx_mgmt;
6524 	band = CDS_BAND_5GHZ;
6525 	if (cfg_val == MLME_CFG_TX_MGMT_5G_RATE_DEF ||
6526 	    !wma_verify_rate_code(cfg_val, band)) {
6527 		wma_nofl_debug("use default 5G MGMT rate.");
6528 		per_band_mgmt_tx_rate &=
6529 		    ~(1 << TX_MGMT_RATE_5G_ENABLE_OFFSET);
6530 	} else {
6531 		per_band_mgmt_tx_rate |=
6532 		    (1 << TX_MGMT_RATE_5G_ENABLE_OFFSET);
6533 		per_band_mgmt_tx_rate |=
6534 		    ((cfg_val & 0x7FF) << TX_MGMT_RATE_5G_OFFSET);
6535 	}
6536 
6537 	info->param_id = wmi_vdev_param_per_band_mgmt_tx_rate;
6538 	info->param_value = per_band_mgmt_tx_rate;
6539 	return QDF_STATUS_SUCCESS;
6540 }
6541 
6542 #define MAX_VDEV_CREATE_PARAMS 22
6543 /* params being sent:
6544  * 1.wmi_vdev_param_wmm_txop_enable
6545  * 2.wmi_vdev_param_disconnect_th
6546  * 3.wmi_vdev_param_mcc_rtscts_protection_enable
6547  * 4.wmi_vdev_param_mcc_broadcast_probe_enable
6548  * 5.wmi_vdev_param_rts_threshold
6549  * 6.wmi_vdev_param_fragmentation_threshold
6550  * 7.wmi_vdev_param_tx_stbc
6551  * 8.wmi_vdev_param_mgmt_tx_rate
6552  * 9.wmi_vdev_param_per_band_mgmt_tx_rate
6553  * 10.wmi_vdev_param_set_eht_mu_mode
6554  * 11.wmi_vdev_param_set_hemu_mode
6555  * 12.wmi_vdev_param_txbf
6556  * 13.wmi_vdev_param_enable_bcast_probe_response
6557  * 14.wmi_vdev_param_fils_max_channel_guard_time
6558  * 15.wmi_vdev_param_probe_delay
6559  * 16.wmi_vdev_param_repeat_probe_time
6560  * 17.wmi_vdev_param_enable_disable_oce_features
6561  * 18.wmi_vdev_param_bmiss_first_bcnt
6562  * 19.wmi_vdev_param_bmiss_final_bcnt
6563  * 20.wmi_vdev_param_set_sap_ps_with_twt
6564  * 21.wmi_vdev_param_disable_2g_twt
6565  * 22.wmi_vdev_param_disable_twt_info_frame
6566  */
6567 
6568 QDF_STATUS wma_vdev_create_set_param(struct wlan_objmgr_vdev *vdev)
6569 {
6570 	QDF_STATUS status;
6571 	struct mlme_ht_capabilities_info *ht_cap_info;
6572 	uint32_t cfg_val;
6573 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
6574 	struct dev_set_param ext_val;
6575 	wmi_vdev_txbf_en txbf_en = {0};
6576 	struct vdev_mlme_obj *vdev_mlme;
6577 	uint8_t vdev_id;
6578 	uint32_t hemu_mode;
6579 	struct dev_set_param setparam[MAX_VDEV_CREATE_PARAMS];
6580 	uint8_t index = 0;
6581 	bool is_24ghz_twt_enabled;
6582 	bool disable_twt_info_frame;
6583 	enum QDF_OPMODE opmode;
6584 
6585 	if (!mac)
6586 		return QDF_STATUS_E_FAILURE;
6587 
6588 	vdev_id = wlan_vdev_get_id(vdev);
6589 
6590 	vdev_mlme = wlan_vdev_mlme_get_cmpt_obj(vdev);
6591 	if (!vdev_mlme) {
6592 		wma_err("Failed to get vdev mlme obj!");
6593 		return QDF_STATUS_E_FAILURE;
6594 	}
6595 
6596 	status = mlme_check_index_setparam(
6597 				setparam, wmi_vdev_param_wmm_txop_enable,
6598 				mac->mlme_cfg->edca_params.enable_wmm_txop,
6599 				index++, MAX_VDEV_CREATE_PARAMS);
6600 	if (QDF_IS_STATUS_ERROR(status)) {
6601 		wma_debug("failed to set wmi_vdev_param_wmm_txop_enable");
6602 		goto error;
6603 	}
6604 	wma_debug("Setting wmi_vdev_param_disconnect_th: %d",
6605 		  mac->mlme_cfg->gen.dropped_pkt_disconnect_thresh);
6606 	status = mlme_check_index_setparam(
6607 			setparam, wmi_vdev_param_disconnect_th,
6608 			mac->mlme_cfg->gen.dropped_pkt_disconnect_thresh,
6609 			index++, MAX_VDEV_CREATE_PARAMS);
6610 	if (QDF_IS_STATUS_ERROR(status)) {
6611 		wma_debug("failed to set wmi_vdev_param_disconnect_th");
6612 		goto error;
6613 	}
6614 	status = mlme_check_index_setparam(
6615 				 setparam,
6616 				 wmi_vdev_param_mcc_rtscts_protection_enable,
6617 				 mac->roam.configParam.mcc_rts_cts_prot_enable,
6618 				 index++, MAX_VDEV_CREATE_PARAMS);
6619 	if (QDF_IS_STATUS_ERROR(status)) {
6620 		wma_debug("failed to set wmi_vdev_param_mcc_rtscts_protection_enable");
6621 		goto error;
6622 	}
6623 	status = mlme_check_index_setparam(
6624 			setparam,
6625 			wmi_vdev_param_mcc_broadcast_probe_enable,
6626 			mac->roam.configParam.mcc_bcast_prob_resp_enable,
6627 			index++, MAX_VDEV_CREATE_PARAMS);
6628 	if (QDF_IS_STATUS_ERROR(status)) {
6629 		wma_debug("failed to set wmi_vdev_param_mcc_broadcast_probe_enable");
6630 		goto error;
6631 	}
6632 	if (wlan_mlme_get_rts_threshold(mac->psoc, &cfg_val) ==
6633 							QDF_STATUS_SUCCESS) {
6634 		status = mlme_check_index_setparam(
6635 					      setparam,
6636 					      wmi_vdev_param_rts_threshold,
6637 					      cfg_val, index++,
6638 					      MAX_VDEV_CREATE_PARAMS);
6639 		if (QDF_IS_STATUS_ERROR(status)) {
6640 			wma_debug("failed to set wmi_vdev_param_rts_threshold");
6641 			goto error;
6642 		}
6643 	} else {
6644 		wma_err("Fail to get val for rts threshold, leave unchanged");
6645 	}
6646 	if (wlan_mlme_get_frag_threshold(mac->psoc, &cfg_val) ==
6647 		 QDF_STATUS_SUCCESS) {
6648 		status = mlme_check_index_setparam(
6649 					setparam,
6650 					wmi_vdev_param_fragmentation_threshold,
6651 					cfg_val, index++,
6652 					MAX_VDEV_CREATE_PARAMS);
6653 		if (QDF_IS_STATUS_ERROR(status)) {
6654 			wma_debug("failed to set wmi_vdev_param_fragmentation_threshold");
6655 			goto error;
6656 		}
6657 	} else {
6658 		wma_err("Fail to get val for frag threshold, leave unchanged");
6659 	}
6660 
6661 	ht_cap_info = &mac->mlme_cfg->ht_caps.ht_cap_info;
6662 	status = mlme_check_index_setparam(setparam,
6663 					   wmi_vdev_param_tx_stbc,
6664 					   ht_cap_info->tx_stbc, index++,
6665 					   MAX_VDEV_CREATE_PARAMS);
6666 	if (QDF_IS_STATUS_ERROR(status)) {
6667 		wma_debug("failed to set wmi_vdev_param_tx_stbc");
6668 		goto error;
6669 	}
6670 	if (!wma_vdev_mgmt_tx_rate(&ext_val)) {
6671 		status = mlme_check_index_setparam(setparam, ext_val.param_id,
6672 						   ext_val.param_value, index++,
6673 						   MAX_VDEV_CREATE_PARAMS);
6674 		if (QDF_IS_STATUS_ERROR(status)) {
6675 			wma_debug("failed to set param for MGMT RATE");
6676 			goto error;
6677 		}
6678 	}
6679 	if (!wma_vdev_mgmt_perband_tx_rate(&ext_val)) {
6680 		status = mlme_check_index_setparam(setparam, ext_val.param_id,
6681 						   ext_val.param_value, index++,
6682 						   MAX_VDEV_CREATE_PARAMS);
6683 		if (QDF_IS_STATUS_ERROR(status)) {
6684 			wma_debug("failed to set PERBAND_MGMT RATE");
6685 			goto error;
6686 		}
6687 	}
6688 	if (IS_FEATURE_11BE_SUPPORTED_BY_FW) {
6689 		uint32_t mode;
6690 
6691 		status = wma_set_eht_txbf_vdev_params(mac, &mode);
6692 		if (status == QDF_STATUS_SUCCESS) {
6693 			wma_debug("set EHTMU_MODE (ehtmu_mode = 0x%x)", mode);
6694 			status = mlme_check_index_setparam(
6695 						setparam,
6696 						wmi_vdev_param_set_eht_mu_mode,
6697 						mode, index++,
6698 						MAX_VDEV_CREATE_PARAMS);
6699 			if (QDF_IS_STATUS_ERROR(status)) {
6700 				wma_debug("failed to set wmi_vdev_param_set_eht_mu_mode");
6701 				goto error;
6702 			}
6703 		}
6704 	}
6705 	if (IS_FEATURE_SUPPORTED_BY_FW(DOT11AX)) {
6706 		if (!wma_get_hemu_mode(&hemu_mode, mac)) {
6707 			wma_debug("set HEMU_MODE (hemu_mode = 0x%x)",
6708 			  hemu_mode);
6709 			status = mlme_check_index_setparam(
6710 						setparam,
6711 						wmi_vdev_param_set_hemu_mode,
6712 						hemu_mode, index++,
6713 						MAX_VDEV_CREATE_PARAMS);
6714 			if (QDF_IS_STATUS_ERROR(status)) {
6715 				wma_debug("failed to set wmi_vdev_param_set_hemu_mode");
6716 				goto error;
6717 			}
6718 		}
6719 	}
6720 	if (wlan_nan_is_beamforming_supported(mac->psoc)) {
6721 		txbf_en.sutxbfee =
6722 			mac->mlme_cfg->vht_caps.vht_cap_info.su_bformee;
6723 		txbf_en.mutxbfee =
6724 		mac->mlme_cfg->vht_caps.vht_cap_info.enable_mu_bformee;
6725 		txbf_en.sutxbfer =
6726 			mac->mlme_cfg->vht_caps.vht_cap_info.su_bformer;
6727 		status = mlme_check_index_setparam(setparam,
6728 					      wmi_vdev_param_txbf,
6729 					      *((A_UINT8 *)&txbf_en), index++,
6730 					      MAX_VDEV_CREATE_PARAMS);
6731 		if (QDF_IS_STATUS_ERROR(status)) {
6732 			wma_debug("failed to set wmi_vdev_param_txbf");
6733 			goto error;
6734 		}
6735 	}
6736 	/* Initialize roaming offload state */
6737 	if (vdev_mlme->mgmt.generic.type == WMI_VDEV_TYPE_STA &&
6738 	    vdev_mlme->mgmt.generic.subtype == 0) {
6739 		/* Pass down enable/disable bcast probe rsp to FW */
6740 		status = mlme_check_index_setparam(
6741 				setparam,
6742 				wmi_vdev_param_enable_bcast_probe_response,
6743 				mac->mlme_cfg->oce.enable_bcast_probe_rsp,
6744 				index++, MAX_VDEV_CREATE_PARAMS);
6745 		if (QDF_IS_STATUS_ERROR(status)) {
6746 			wma_debug("failed to set wmi_vdev_param_enable_bcast_probe_response");
6747 			goto error;
6748 		}
6749 		/* Pass down the FILS max channel guard time to FW */
6750 		status = mlme_check_index_setparam(
6751 				setparam,
6752 				wmi_vdev_param_fils_max_channel_guard_time,
6753 				mac->mlme_cfg->sta.fils_max_chan_guard_time,
6754 				index++, MAX_VDEV_CREATE_PARAMS);
6755 		if (QDF_IS_STATUS_ERROR(status)) {
6756 			wma_debug("failed to set wmi_vdev_param_fils_max_channel_guard_time");
6757 			goto error;
6758 		}
6759 		/* Pass down the Probe Request tx delay(in ms) to FW */
6760 		status = mlme_check_index_setparam(setparam,
6761 						   wmi_vdev_param_probe_delay,
6762 						   PROBE_REQ_TX_DELAY, index++,
6763 						   MAX_VDEV_CREATE_PARAMS);
6764 		if (QDF_IS_STATUS_ERROR(status)) {
6765 			wma_debug("failed to set wmi_vdev_param_probe_delay");
6766 			goto error;
6767 		}
6768 		/* Pass down the probe request tx time gap_ms to FW */
6769 		status = mlme_check_index_setparam(
6770 					      setparam,
6771 					      wmi_vdev_param_repeat_probe_time,
6772 					      PROBE_REQ_TX_TIME_GAP, index++,
6773 					      MAX_VDEV_CREATE_PARAMS);
6774 		if (QDF_IS_STATUS_ERROR(status)) {
6775 			wma_debug("failed to set wmi_vdev_param_repeat_probe_time");
6776 			goto error;
6777 		}
6778 		status = mlme_check_index_setparam(
6779 				setparam,
6780 				wmi_vdev_param_enable_disable_oce_features,
6781 				mac->mlme_cfg->oce.feature_bitmap, index++,
6782 				MAX_VDEV_CREATE_PARAMS);
6783 		if (QDF_IS_STATUS_ERROR(status)) {
6784 			wma_debug("failed to set wmi_vdev_param_enable_disable_oce_features");
6785 			goto error;
6786 		}
6787 		/* Initialize BMISS parameters */
6788 		wma_debug("first_bcnt: %d, final_bcnt: %d",
6789 			  mac->mlme_cfg->lfr.roam_bmiss_first_bcnt,
6790 			  mac->mlme_cfg->lfr.roam_bmiss_final_bcnt);
6791 		status = mlme_check_index_setparam(
6792 				setparam,
6793 				wmi_vdev_param_bmiss_first_bcnt,
6794 				mac->mlme_cfg->lfr.roam_bmiss_first_bcnt,
6795 				index++, MAX_VDEV_CREATE_PARAMS);
6796 		if (QDF_IS_STATUS_ERROR(status)) {
6797 			wma_debug("failed to set wmi_vdev_param_bmiss_first_bcnt");
6798 			goto error;
6799 		}
6800 		status = mlme_check_index_setparam(setparam,
6801 				wmi_vdev_param_bmiss_final_bcnt,
6802 				mac->mlme_cfg->lfr.roam_bmiss_final_bcnt,
6803 				index++, MAX_VDEV_CREATE_PARAMS);
6804 		if (QDF_IS_STATUS_ERROR(status)) {
6805 			wma_debug("failed to set wmi_vdev_param_bmiss_final_bcnt");
6806 			goto error;
6807 		}
6808 	}
6809 	if (vdev_mlme->mgmt.generic.type == WMI_VDEV_TYPE_AP &&
6810 	    vdev_mlme->mgmt.generic.subtype == 0) {
6811 		status = mlme_check_index_setparam(setparam,
6812 				wmi_vdev_param_enable_disable_oce_features,
6813 				mac->mlme_cfg->oce.feature_bitmap, index++,
6814 				MAX_VDEV_CREATE_PARAMS);
6815 		if (QDF_IS_STATUS_ERROR(status)) {
6816 			wma_debug("failed to set wmi_vdev_param_enable_disable_oce_features");
6817 			goto error;
6818 		}
6819 	}
6820 
6821 	opmode = wlan_vdev_mlme_get_opmode(vdev);
6822 	if (opmode == QDF_SAP_MODE) {
6823 		status = mlme_check_index_setparam(
6824 				setparam,
6825 				wmi_vdev_param_set_sap_ps_with_twt,
6826 				wlan_mlme_get_sap_ps_with_twt(mac->psoc),
6827 				index++, MAX_VDEV_CREATE_PARAMS);
6828 		if (QDF_IS_STATUS_ERROR(status)) {
6829 			wma_debug("failed to set wmi_vdev_param_set_sap_ps_with_twt");
6830 			goto error;
6831 		}
6832 	}
6833 
6834 	is_24ghz_twt_enabled = mlme_is_24ghz_twt_enabled(mac->psoc);
6835 	status = mlme_check_index_setparam(setparam,
6836 					   wmi_vdev_param_disable_2g_twt,
6837 					   !is_24ghz_twt_enabled,
6838 					   index++, MAX_VDEV_CREATE_PARAMS);
6839 	if (QDF_IS_STATUS_ERROR(status)) {
6840 		wma_debug("failed to set wmi_vdev_param_disable_2g_twt");
6841 		goto error;
6842 	}
6843 
6844 	disable_twt_info_frame = mlme_is_twt_disable_info_frame(mac->psoc);
6845 	status = mlme_check_index_setparam(
6846 					setparam,
6847 					wmi_vdev_param_disable_twt_info_frame,
6848 					disable_twt_info_frame,
6849 					index++, MAX_VDEV_CREATE_PARAMS);
6850 	if (QDF_IS_STATUS_ERROR(status)) {
6851 		wma_debug("failed to set wmi_vdev_param_disable_twt_info_frame");
6852 		goto error;
6853 	}
6854 
6855 	status = wma_send_multi_pdev_vdev_set_params(MLME_VDEV_SETPARAM,
6856 						     vdev_id, setparam, index);
6857 	if (QDF_IS_STATUS_ERROR(status)) {
6858 		wma_err("failed to update vdev set all params");
6859 		status = QDF_STATUS_E_FAILURE;
6860 		goto error;
6861 	}
6862 error:
6863 	return status;
6864 }
6865 
6866 static inline bool wma_tx_is_chainmask_valid(int value,
6867 					     struct target_psoc_info *tgt_hdl)
6868 {
6869 	struct wlan_psoc_host_mac_phy_caps *mac_phy_cap;
6870 	uint8_t total_mac_phy_cnt, i;
6871 
6872 	mac_phy_cap = target_psoc_get_mac_phy_cap(tgt_hdl);
6873 	if (!mac_phy_cap) {
6874 		wma_err("Invalid MAC PHY capabilities handle");
6875 		return false;
6876 	}
6877 	total_mac_phy_cnt = target_psoc_get_total_mac_phy_cnt(tgt_hdl);
6878 	for (i = 0; i < total_mac_phy_cnt; i++) {
6879 		if (((mac_phy_cap[i].tx_chain_mask_5G) & (value)))
6880 			return true;
6881 	}
6882 	return false;
6883 }
6884 
6885 QDF_STATUS
6886 wma_validate_txrx_chain_mask(uint32_t id, uint32_t value)
6887 {
6888 	tp_wma_handle wma_handle =
6889 			cds_get_context(QDF_MODULE_ID_WMA);
6890 	struct target_psoc_info *tgt_hdl;
6891 
6892 	if (!wma_handle)
6893 		return QDF_STATUS_E_FAILURE;
6894 
6895 	tgt_hdl = wlan_psoc_get_tgt_if_handle(wma_handle->psoc);
6896 	if (!tgt_hdl)
6897 		return QDF_STATUS_E_FAILURE;
6898 
6899 	wma_debug("pdev pid %d pval %d", id, value);
6900 	if (id == wmi_pdev_param_tx_chain_mask) {
6901 		if (wma_check_txrx_chainmask(target_if_get_num_rf_chains(
6902 		    tgt_hdl), value) || !wma_tx_is_chainmask_valid(value,
6903 								   tgt_hdl)) {
6904 			wma_err("failed in validating tx chainmask");
6905 			return QDF_STATUS_E_FAILURE;
6906 		}
6907 	}
6908 	if (id == wmi_pdev_param_rx_chain_mask) {
6909 		if (wma_check_txrx_chainmask(target_if_get_num_rf_chains(
6910 					     tgt_hdl), value)) {
6911 			wma_err("failed in validating rtx chainmask");
6912 			return QDF_STATUS_SUCCESS;
6913 		}
6914 	}
6915 	return QDF_STATUS_SUCCESS;
6916 }
6917 
6918 QDF_STATUS wma_send_multi_pdev_vdev_set_params(enum mlme_dev_setparam param_type,
6919 					       uint8_t dev_id,
6920 					       struct dev_set_param *param,
6921 					       uint8_t n_params)
6922 {
6923 	struct mac_context *mac = cds_get_context(QDF_MODULE_ID_PE);
6924 	struct set_multiple_pdev_vdev_param params = {};
6925 	QDF_STATUS status;
6926 	wmi_unified_t wmi_handle;
6927 
6928 	if (!mac)
6929 		return QDF_STATUS_E_FAILURE;
6930 
6931 	wmi_handle = get_wmi_unified_hdl_from_psoc(mac->psoc);
6932 	if (!wmi_handle)
6933 		return QDF_STATUS_E_FAILURE;
6934 
6935 	params.param_type = param_type;
6936 	params.dev_id = dev_id;
6937 	params.is_host_pdev_id = false;
6938 	params.params = param;
6939 	params.n_params = n_params;
6940 
6941 	if (param_type == MLME_VDEV_SETPARAM) {
6942 		status = wmi_unified_multiple_vdev_param_send(wmi_handle,
6943 							      &params);
6944 		if (QDF_IS_STATUS_ERROR(status))
6945 			wma_err("failed to send multi vdev set params");
6946 	} else if (param_type == MLME_PDEV_SETPARAM) {
6947 		status = wmi_unified_multiple_pdev_param_send(wmi_handle,
6948 							      &params);
6949 		if (QDF_IS_STATUS_ERROR(status))
6950 			wma_err("failed to send multi pdev set params");
6951 	} else {
6952 		status = QDF_STATUS_E_FAILURE;
6953 		wma_err("Invalid param type");
6954 	}
6955 	return status;
6956 }
6957