xref: /wlan-dirver/qcacld-3.0/components/cmn_services/policy_mgr/src/wlan_policy_mgr_get_set_utils.c (revision 663120a0f77ecf0340b3ac51e334fe65218a2b86)
1 /*
2  * Copyright (c) 2012-2021 The Linux Foundation. All rights reserved.
3  * Copyright (c) 2021-2023 Qualcomm Innovation Center, Inc. All rights reserved.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for
6  * any purpose with or without fee is hereby granted, provided that the
7  * above copyright notice and this permission notice appear in all
8  * copies.
9  *
10  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
11  * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
12  * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
13  * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
14  * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
15  * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
16  * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
17  * PERFORMANCE OF THIS SOFTWARE.
18  */
19 
20 /**
21  * DOC: wlan_policy_mgr_get_set_utils.c
22  *
23  * WLAN Concurrenct Connection Management APIs
24  *
25  */
26 
27 /* Include files */
28 #include "target_if.h"
29 #include "wlan_policy_mgr_api.h"
30 #include "wlan_policy_mgr_i.h"
31 #include "qdf_types.h"
32 #include "qdf_trace.h"
33 #include "wlan_objmgr_global_obj.h"
34 #include "wlan_objmgr_pdev_obj.h"
35 #include "wlan_objmgr_vdev_obj.h"
36 #include "wlan_nan_api.h"
37 #include "nan_public_structs.h"
38 #include "wlan_reg_services_api.h"
39 #include "wlan_cm_roam_public_struct.h"
40 #include "wlan_mlme_api.h"
41 #include "wlan_mlme_main.h"
42 #include "wlan_mlme_vdev_mgr_interface.h"
43 #include "wlan_mlo_mgr_sta.h"
44 #include "wlan_cm_ucfg_api.h"
45 #include "wlan_cm_roam_api.h"
46 #include "wlan_mlme_ucfg_api.h"
47 #include "wlan_p2p_ucfg_api.h"
48 #include "wlan_mlo_link_force.h"
49 
50 /* invalid channel id. */
51 #define INVALID_CHANNEL_ID 0
52 
53 #define IS_FREQ_ON_MAC_ID(freq_range, freq, mac_id) \
54 	((freq >= freq_range[mac_id].low_2ghz_freq && \
55 	  freq <= freq_range[mac_id].high_2ghz_freq) || \
56 	(freq >= freq_range[mac_id].low_5ghz_freq && \
57 	 freq <= freq_range[mac_id].high_5ghz_freq))
58 
59 /**
60  * policy_mgr_debug_alert() - fatal error alert
61  *
62  * This function will flush host drv log and
63  * disable all level logs.
64  * It can be called in fatal error detected in policy
65  * manager.
66  * This is to avoid host log overwritten in stress
67  * test to help issue debug.
68  *
69  * Return: none
70  */
71 static void
72 policy_mgr_debug_alert(void)
73 {
74 	int module_id;
75 	int qdf_print_idx;
76 
77 	policy_mgr_err("fatal error detected to flush and pause host log");
78 	qdf_logging_flush_logs();
79 	qdf_print_idx = qdf_get_pidx();
80 	for (module_id = 0; module_id < QDF_MODULE_ID_MAX; module_id++)
81 		qdf_print_set_category_verbose(
82 					qdf_print_idx,
83 					module_id, QDF_TRACE_LEVEL_NONE,
84 					0);
85 }
86 
87 QDF_STATUS
88 policy_mgr_get_allow_mcc_go_diff_bi(struct wlan_objmgr_psoc *psoc,
89 				    uint8_t *allow_mcc_go_diff_bi)
90 {
91 	struct policy_mgr_psoc_priv_obj *pm_ctx;
92 
93 	pm_ctx = policy_mgr_get_context(psoc);
94 	if (!pm_ctx) {
95 		policy_mgr_err("pm_ctx is NULL");
96 		return QDF_STATUS_E_FAILURE;
97 	}
98 	*allow_mcc_go_diff_bi = pm_ctx->cfg.allow_mcc_go_diff_bi;
99 
100 	return QDF_STATUS_SUCCESS;
101 }
102 
103 QDF_STATUS policy_mgr_set_dual_mac_feature(struct wlan_objmgr_psoc *psoc,
104 					   uint8_t dual_mac_feature)
105 {
106 	struct policy_mgr_psoc_priv_obj *pm_ctx;
107 
108 	pm_ctx = policy_mgr_get_context(psoc);
109 	if (!pm_ctx) {
110 		policy_mgr_err("pm_ctx is NULL");
111 		return QDF_STATUS_E_FAILURE;
112 	}
113 
114 	pm_ctx->cfg.dual_mac_feature = dual_mac_feature;
115 
116 	return QDF_STATUS_SUCCESS;
117 }
118 
119 QDF_STATUS policy_mgr_get_dual_mac_feature(struct wlan_objmgr_psoc *psoc,
120 					   uint8_t *dual_mac_feature)
121 {
122 	struct policy_mgr_psoc_priv_obj *pm_ctx;
123 
124 	pm_ctx = policy_mgr_get_context(psoc);
125 	if (!pm_ctx) {
126 		policy_mgr_err("pm_ctx is NULL");
127 		return QDF_STATUS_E_FAILURE;
128 	}
129 	*dual_mac_feature = pm_ctx->cfg.dual_mac_feature;
130 
131 	return QDF_STATUS_SUCCESS;
132 }
133 
134 QDF_STATUS policy_mgr_get_force_1x1(struct wlan_objmgr_psoc *psoc,
135 				    uint8_t *force_1x1)
136 {
137 	struct policy_mgr_psoc_priv_obj *pm_ctx;
138 
139 	pm_ctx = policy_mgr_get_context(psoc);
140 	if (!pm_ctx) {
141 		policy_mgr_err("pm_ctx is NULL");
142 		return QDF_STATUS_E_FAILURE;
143 	}
144 	*force_1x1 = pm_ctx->cfg.is_force_1x1_enable;
145 
146 	return QDF_STATUS_SUCCESS;
147 }
148 
149 uint32_t policy_mgr_get_max_conc_cxns(struct wlan_objmgr_psoc *psoc)
150 {
151 	struct policy_mgr_psoc_priv_obj *pm_ctx;
152 
153 	pm_ctx = policy_mgr_get_context(psoc);
154 	if (!pm_ctx) {
155 		policy_mgr_err("pm_ctx is NULL");
156 		return 0;
157 	}
158 
159 	return pm_ctx->cfg.max_conc_cxns;
160 }
161 
162 QDF_STATUS policy_mgr_set_max_conc_cxns(struct wlan_objmgr_psoc *psoc,
163 					uint32_t max_conc_cxns)
164 {
165 	struct policy_mgr_psoc_priv_obj *pm_ctx;
166 
167 	pm_ctx = policy_mgr_get_context(psoc);
168 	if (!pm_ctx) {
169 		policy_mgr_err("pm_ctx is NULL");
170 		return QDF_STATUS_E_FAILURE;
171 	}
172 
173 	policy_mgr_debug("set max_conc_cxns %d old %d", max_conc_cxns,
174 			 pm_ctx->cfg.max_conc_cxns);
175 	pm_ctx->cfg.max_conc_cxns = max_conc_cxns;
176 
177 	return QDF_STATUS_SUCCESS;
178 }
179 
180 QDF_STATUS
181 policy_mgr_set_sta_sap_scc_on_dfs_chnl(struct wlan_objmgr_psoc *psoc,
182 				       uint8_t sta_sap_scc_on_dfs_chnl)
183 {
184 	struct policy_mgr_psoc_priv_obj *pm_ctx;
185 
186 	pm_ctx = policy_mgr_get_context(psoc);
187 	if (!pm_ctx) {
188 		policy_mgr_err("pm_ctx is NULL");
189 		return QDF_STATUS_E_FAILURE;
190 	}
191 	pm_ctx->cfg.sta_sap_scc_on_dfs_chnl = sta_sap_scc_on_dfs_chnl;
192 
193 	return QDF_STATUS_SUCCESS;
194 }
195 
196 QDF_STATUS
197 policy_mgr_get_sta_sap_scc_on_dfs_chnl(struct wlan_objmgr_psoc *psoc,
198 				       uint8_t *sta_sap_scc_on_dfs_chnl)
199 {
200 	struct policy_mgr_psoc_priv_obj *pm_ctx;
201 
202 	pm_ctx = policy_mgr_get_context(psoc);
203 	if (!pm_ctx) {
204 		policy_mgr_err("pm_ctx is NULL");
205 		return QDF_STATUS_E_FAILURE;
206 	}
207 	*sta_sap_scc_on_dfs_chnl = pm_ctx->cfg.sta_sap_scc_on_dfs_chnl;
208 
209 	return QDF_STATUS_SUCCESS;
210 }
211 
212 bool
213 policy_mgr_get_sta_sap_scc_allowed_on_indoor_chnl(struct wlan_objmgr_psoc *psoc)
214 {
215 	struct policy_mgr_psoc_priv_obj *pm_ctx;
216 
217 	pm_ctx = policy_mgr_get_context(psoc);
218 	if (!pm_ctx) {
219 		policy_mgr_err("pm_ctx is NULL");
220 		return false;
221 	}
222 
223 	return pm_ctx->cfg.sta_sap_scc_on_indoor_channel;
224 }
225 
226 QDF_STATUS
227 policy_mgr_set_multi_sap_allowed_on_same_band(struct wlan_objmgr_psoc *psoc,
228 					bool multi_sap_allowed_on_same_band)
229 {
230 	struct policy_mgr_psoc_priv_obj *pm_ctx;
231 
232 	pm_ctx = policy_mgr_get_context(psoc);
233 	if (!pm_ctx) {
234 		policy_mgr_err("pm_ctx is NULL");
235 		return QDF_STATUS_E_FAILURE;
236 	}
237 	pm_ctx->cfg.multi_sap_allowed_on_same_band =
238 				multi_sap_allowed_on_same_band;
239 
240 	return QDF_STATUS_SUCCESS;
241 }
242 
243 QDF_STATUS
244 policy_mgr_get_multi_sap_allowed_on_same_band(struct wlan_objmgr_psoc *psoc,
245 					bool *multi_sap_allowed_on_same_band)
246 {
247 	struct policy_mgr_psoc_priv_obj *pm_ctx;
248 
249 	pm_ctx = policy_mgr_get_context(psoc);
250 	if (!pm_ctx) {
251 		policy_mgr_err("pm_ctx is NULL");
252 		return QDF_STATUS_E_FAILURE;
253 	}
254 	*multi_sap_allowed_on_same_band =
255 				pm_ctx->cfg.multi_sap_allowed_on_same_band;
256 
257 	return QDF_STATUS_SUCCESS;
258 }
259 
260 QDF_STATUS
261 policy_mgr_set_original_bw_for_sap_restart(struct wlan_objmgr_psoc *psoc,
262 					   bool use_sap_original_bw)
263 {
264 	struct policy_mgr_psoc_priv_obj *pm_ctx;
265 
266 	pm_ctx = policy_mgr_get_context(psoc);
267 	if (!pm_ctx) {
268 		policy_mgr_err("pm_ctx is NULL");
269 		return QDF_STATUS_E_FAILURE;
270 	}
271 	pm_ctx->cfg.use_sap_original_bw = use_sap_original_bw;
272 
273 	return QDF_STATUS_SUCCESS;
274 }
275 
276 QDF_STATUS
277 policy_mgr_get_original_bw_for_sap_restart(struct wlan_objmgr_psoc *psoc,
278 					   bool *use_sap_original_bw)
279 {
280 	struct policy_mgr_psoc_priv_obj *pm_ctx;
281 
282 	pm_ctx = policy_mgr_get_context(psoc);
283 	if (!pm_ctx) {
284 		policy_mgr_err("pm_ctx is NULL");
285 		return QDF_STATUS_E_FAILURE;
286 	}
287 	*use_sap_original_bw = pm_ctx->cfg.use_sap_original_bw;
288 
289 	return QDF_STATUS_SUCCESS;
290 }
291 
292 QDF_STATUS
293 policy_mgr_get_dfs_sta_sap_go_scc_movement(struct wlan_objmgr_psoc *psoc,
294 					   bool *move_sap_go_first)
295 {
296 	struct policy_mgr_psoc_priv_obj *pm_ctx;
297 
298 	pm_ctx = policy_mgr_get_context(psoc);
299 	if (!pm_ctx) {
300 		policy_mgr_err("pm_ctx is NULL");
301 		return QDF_STATUS_E_FAILURE;
302 	}
303 	*move_sap_go_first = pm_ctx->cfg.move_sap_go_1st_on_dfs_sta_csa;
304 
305 	return QDF_STATUS_SUCCESS;
306 }
307 
308 static bool
309 policy_mgr_update_dfs_master_dynamic_enabled(
310 	struct wlan_objmgr_psoc *psoc, uint8_t vdev_id)
311 {
312 	struct policy_mgr_psoc_priv_obj *pm_ctx;
313 	bool sta_on_5g = false;
314 	bool sta_on_2g = false;
315 	uint32_t i;
316 	bool enable = true;
317 
318 	pm_ctx = policy_mgr_get_context(psoc);
319 	if (!pm_ctx) {
320 		policy_mgr_err("pm_ctx is NULL");
321 		return true;
322 	}
323 
324 	if (!pm_ctx->cfg.sta_sap_scc_on_dfs_chnl) {
325 		enable = true;
326 		goto end;
327 	}
328 	if (pm_ctx->cfg.sta_sap_scc_on_dfs_chnl ==
329 	    PM_STA_SAP_ON_DFS_MASTER_MODE_DISABLED) {
330 		enable = false;
331 		goto end;
332 	}
333 	if (pm_ctx->cfg.sta_sap_scc_on_dfs_chnl !=
334 	    PM_STA_SAP_ON_DFS_MASTER_MODE_FLEX) {
335 		policy_mgr_debug("sta_sap_scc_on_dfs_chnl %d unknown",
336 				 pm_ctx->cfg.sta_sap_scc_on_dfs_chnl);
337 		enable = true;
338 		goto end;
339 	}
340 
341 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
342 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
343 		if (!((pm_conc_connection_list[i].vdev_id != vdev_id) &&
344 		      pm_conc_connection_list[i].in_use &&
345 		      (pm_conc_connection_list[i].mode == PM_STA_MODE ||
346 		       pm_conc_connection_list[i].mode == PM_P2P_CLIENT_MODE)))
347 			continue;
348 		if (WLAN_REG_IS_5GHZ_CH_FREQ(pm_conc_connection_list[i].freq))
349 			sta_on_5g = true;
350 		else
351 			sta_on_2g = true;
352 	}
353 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
354 
355 	if (policy_mgr_is_hw_dbs_capable(psoc) && !sta_on_5g)
356 		enable = true;
357 	else if (!sta_on_5g && !sta_on_2g)
358 		enable = true;
359 	else
360 		enable = false;
361 end:
362 	pm_ctx->dynamic_dfs_master_disabled = !enable;
363 	if (!enable)
364 		policy_mgr_debug("sta_sap_scc_on_dfs_chnl %d sta_on_2g %d sta_on_5g %d enable %d",
365 				 pm_ctx->cfg.sta_sap_scc_on_dfs_chnl, sta_on_2g,
366 				 sta_on_5g, enable);
367 
368 	return enable;
369 }
370 
371 bool
372 policy_mgr_get_dfs_master_dynamic_enabled(
373 	struct wlan_objmgr_psoc *psoc, uint8_t vdev_id)
374 {
375 	struct policy_mgr_psoc_priv_obj *pm_ctx;
376 
377 	pm_ctx = policy_mgr_get_context(psoc);
378 	if (!pm_ctx) {
379 		policy_mgr_err("pm_ctx is NULL");
380 		return true;
381 	}
382 
383 	return policy_mgr_update_dfs_master_dynamic_enabled(psoc, vdev_id);
384 }
385 
386 bool
387 policy_mgr_get_can_skip_radar_event(struct wlan_objmgr_psoc *psoc,
388 				    uint8_t vdev_id)
389 {
390 	struct policy_mgr_psoc_priv_obj *pm_ctx;
391 
392 	pm_ctx = policy_mgr_get_context(psoc);
393 	if (!pm_ctx) {
394 		policy_mgr_err("pm_ctx is NULL");
395 		return false;
396 	}
397 
398 	return pm_ctx->dynamic_dfs_master_disabled;
399 }
400 
401 QDF_STATUS
402 policy_mgr_get_sta_sap_scc_lte_coex_chnl(struct wlan_objmgr_psoc *psoc,
403 					 uint8_t *sta_sap_scc_lte_coex)
404 {
405 	struct policy_mgr_psoc_priv_obj *pm_ctx;
406 
407 	pm_ctx = policy_mgr_get_context(psoc);
408 	if (!pm_ctx) {
409 		policy_mgr_err("pm_ctx is NULL");
410 		return QDF_STATUS_E_FAILURE;
411 	}
412 	*sta_sap_scc_lte_coex = pm_ctx->cfg.sta_sap_scc_on_lte_coex_chnl;
413 
414 	return QDF_STATUS_SUCCESS;
415 }
416 
417 QDF_STATUS policy_mgr_get_sap_mandt_chnl(struct wlan_objmgr_psoc *psoc,
418 					 uint8_t *sap_mandt_chnl)
419 {
420 	struct policy_mgr_psoc_priv_obj *pm_ctx;
421 
422 	pm_ctx = policy_mgr_get_context(psoc);
423 	if (!pm_ctx) {
424 		policy_mgr_err("pm_ctx is NULL");
425 		return QDF_STATUS_E_FAILURE;
426 	}
427 	*sap_mandt_chnl = pm_ctx->cfg.sap_mandatory_chnl_enable;
428 
429 	return QDF_STATUS_SUCCESS;
430 }
431 
432 QDF_STATUS
433 policy_mgr_get_indoor_chnl_marking(struct wlan_objmgr_psoc *psoc,
434 				   uint8_t *indoor_chnl_marking)
435 {
436 	struct policy_mgr_psoc_priv_obj *pm_ctx;
437 
438 	pm_ctx = policy_mgr_get_context(psoc);
439 	if (!pm_ctx) {
440 		policy_mgr_err("pm_ctx is NULL");
441 		return QDF_STATUS_E_FAILURE;
442 	}
443 	*indoor_chnl_marking = pm_ctx->cfg.mark_indoor_chnl_disable;
444 
445 	return QDF_STATUS_SUCCESS;
446 }
447 
448 QDF_STATUS policy_mgr_get_mcc_scc_switch(struct wlan_objmgr_psoc *psoc,
449 					      uint8_t *mcc_scc_switch)
450 {
451 	struct policy_mgr_psoc_priv_obj *pm_ctx;
452 
453 	pm_ctx = policy_mgr_get_context(psoc);
454 	if (!pm_ctx) {
455 		policy_mgr_err("pm_ctx is NULL");
456 		return QDF_STATUS_E_FAILURE;
457 	}
458 	*mcc_scc_switch = pm_ctx->cfg.mcc_to_scc_switch;
459 
460 	return QDF_STATUS_SUCCESS;
461 }
462 
463 QDF_STATUS policy_mgr_get_sys_pref(struct wlan_objmgr_psoc *psoc,
464 					uint8_t *sys_pref)
465 {
466 	struct policy_mgr_psoc_priv_obj *pm_ctx;
467 
468 	pm_ctx = policy_mgr_get_context(psoc);
469 	if (!pm_ctx) {
470 		policy_mgr_err("pm_ctx is NULL");
471 		return QDF_STATUS_E_FAILURE;
472 	}
473 	*sys_pref = pm_ctx->cfg.sys_pref;
474 
475 	return QDF_STATUS_SUCCESS;
476 }
477 
478 QDF_STATUS policy_mgr_set_sys_pref(struct wlan_objmgr_psoc *psoc,
479 				   uint8_t sys_pref)
480 {
481 	struct policy_mgr_psoc_priv_obj *pm_ctx;
482 
483 	pm_ctx = policy_mgr_get_context(psoc);
484 	if (!pm_ctx) {
485 		policy_mgr_err("pm_ctx is NULL");
486 		return QDF_STATUS_E_FAILURE;
487 	}
488 	pm_ctx->cfg.sys_pref = sys_pref;
489 
490 	return QDF_STATUS_SUCCESS;
491 }
492 
493 QDF_STATUS policy_mgr_get_conc_rule1(struct wlan_objmgr_psoc *psoc,
494 						uint8_t *conc_rule1)
495 {
496 	struct policy_mgr_psoc_priv_obj *pm_ctx;
497 
498 	pm_ctx = policy_mgr_get_context(psoc);
499 	if (!pm_ctx) {
500 		policy_mgr_err("pm_ctx is NULL");
501 		return QDF_STATUS_E_FAILURE;
502 	}
503 	*conc_rule1 = pm_ctx->cfg.conc_rule1;
504 
505 	return QDF_STATUS_SUCCESS;
506 }
507 
508 QDF_STATUS policy_mgr_get_conc_rule2(struct wlan_objmgr_psoc *psoc,
509 						uint8_t *conc_rule2)
510 {
511 	struct policy_mgr_psoc_priv_obj *pm_ctx;
512 
513 	pm_ctx = policy_mgr_get_context(psoc);
514 	if (!pm_ctx) {
515 		policy_mgr_err("pm_ctx is NULL");
516 		return QDF_STATUS_E_FAILURE;
517 	}
518 	*conc_rule2 = pm_ctx->cfg.conc_rule2;
519 
520 	return QDF_STATUS_SUCCESS;
521 }
522 
523 QDF_STATUS policy_mgr_get_chnl_select_plcy(struct wlan_objmgr_psoc *psoc,
524 					   uint32_t *chnl_select_plcy)
525 {
526 	struct policy_mgr_psoc_priv_obj *pm_ctx;
527 
528 	pm_ctx = policy_mgr_get_context(psoc);
529 	if (!pm_ctx) {
530 		policy_mgr_err("pm_ctx is NULL");
531 		return QDF_STATUS_E_FAILURE;
532 	}
533 	*chnl_select_plcy = pm_ctx->cfg.chnl_select_plcy;
534 
535 	return QDF_STATUS_SUCCESS;
536 }
537 
538 QDF_STATUS policy_mgr_set_ch_select_plcy(struct wlan_objmgr_psoc *psoc,
539 					 uint32_t ch_select_policy)
540 {
541 	struct policy_mgr_psoc_priv_obj *pm_ctx;
542 
543 	pm_ctx = policy_mgr_get_context(psoc);
544 	if (!pm_ctx) {
545 		policy_mgr_err("pm_ctx is NULL");
546 		return QDF_STATUS_E_FAILURE;
547 	}
548 	pm_ctx->cfg.chnl_select_plcy = ch_select_policy;
549 
550 	return QDF_STATUS_SUCCESS;
551 }
552 
553 QDF_STATUS policy_mgr_set_dynamic_mcc_adaptive_sch(
554 				struct wlan_objmgr_psoc *psoc,
555 				bool dynamic_mcc_adaptive_sched)
556 {
557 	struct policy_mgr_psoc_priv_obj *pm_ctx;
558 
559 	pm_ctx = policy_mgr_get_context(psoc);
560 	if (!pm_ctx) {
561 		policy_mgr_err("pm_ctx is NULL");
562 		return QDF_STATUS_E_FAILURE;
563 	}
564 	pm_ctx->dynamic_mcc_adaptive_sched = dynamic_mcc_adaptive_sched;
565 
566 	return QDF_STATUS_SUCCESS;
567 }
568 
569 QDF_STATUS policy_mgr_get_dynamic_mcc_adaptive_sch(
570 				struct wlan_objmgr_psoc *psoc,
571 				bool *dynamic_mcc_adaptive_sched)
572 {
573 	struct policy_mgr_psoc_priv_obj *pm_ctx;
574 
575 	pm_ctx = policy_mgr_get_context(psoc);
576 	if (!pm_ctx) {
577 		policy_mgr_err("pm_ctx is NULL");
578 		return QDF_STATUS_E_FAILURE;
579 	}
580 	*dynamic_mcc_adaptive_sched = pm_ctx->dynamic_mcc_adaptive_sched;
581 
582 	return QDF_STATUS_SUCCESS;
583 }
584 
585 QDF_STATUS policy_mgr_get_mcc_adaptive_sch(struct wlan_objmgr_psoc *psoc,
586 					   bool *enable_mcc_adaptive_sch)
587 {
588 	struct policy_mgr_psoc_priv_obj *pm_ctx;
589 
590 	pm_ctx = policy_mgr_get_context(psoc);
591 	if (!pm_ctx) {
592 		policy_mgr_err("pm_ctx is NULL");
593 		return QDF_STATUS_E_FAILURE;
594 	}
595 	*enable_mcc_adaptive_sch = pm_ctx->cfg.enable_mcc_adaptive_sch;
596 
597 	return QDF_STATUS_SUCCESS;
598 }
599 
600 QDF_STATUS policy_mgr_get_sta_cxn_5g_band(struct wlan_objmgr_psoc *psoc,
601 					  uint8_t *enable_sta_cxn_5g_band)
602 {
603 	struct policy_mgr_psoc_priv_obj *pm_ctx;
604 
605 	pm_ctx = policy_mgr_get_context(psoc);
606 	if (!pm_ctx) {
607 		policy_mgr_err("pm_ctx is NULL");
608 		return QDF_STATUS_E_FAILURE;
609 	}
610 	*enable_sta_cxn_5g_band = pm_ctx->cfg.enable_sta_cxn_5g_band;
611 
612 	return QDF_STATUS_SUCCESS;
613 }
614 
615 void policy_mgr_update_new_hw_mode_index(struct wlan_objmgr_psoc *psoc,
616 		uint32_t new_hw_mode_index)
617 {
618 	struct policy_mgr_psoc_priv_obj *pm_ctx;
619 
620 	pm_ctx = policy_mgr_get_context(psoc);
621 	if (!pm_ctx) {
622 		policy_mgr_err("Invalid Context");
623 		return;
624 	}
625 	pm_ctx->new_hw_mode_index = new_hw_mode_index;
626 }
627 
628 void policy_mgr_update_old_hw_mode_index(struct wlan_objmgr_psoc *psoc,
629 		uint32_t old_hw_mode_index)
630 {
631 	struct policy_mgr_psoc_priv_obj *pm_ctx;
632 
633 	pm_ctx = policy_mgr_get_context(psoc);
634 	if (!pm_ctx) {
635 		policy_mgr_err("Invalid Context");
636 		return;
637 	}
638 	pm_ctx->old_hw_mode_index = old_hw_mode_index;
639 }
640 
641 void policy_mgr_update_hw_mode_index(struct wlan_objmgr_psoc *psoc,
642 		uint32_t new_hw_mode_index)
643 {
644 	struct policy_mgr_psoc_priv_obj *pm_ctx;
645 
646 	pm_ctx = policy_mgr_get_context(psoc);
647 	if (!pm_ctx) {
648 		policy_mgr_err("Invalid Context");
649 		return;
650 	}
651 	if (POLICY_MGR_DEFAULT_HW_MODE_INDEX == pm_ctx->new_hw_mode_index) {
652 		pm_ctx->new_hw_mode_index = new_hw_mode_index;
653 	} else {
654 		pm_ctx->old_hw_mode_index = pm_ctx->new_hw_mode_index;
655 		pm_ctx->new_hw_mode_index = new_hw_mode_index;
656 	}
657 	policy_mgr_debug("Updated: old_hw_mode_index:%d new_hw_mode_index:%d",
658 		pm_ctx->old_hw_mode_index, pm_ctx->new_hw_mode_index);
659 }
660 
661 /**
662  * policy_mgr_get_num_of_setbits_from_bitmask() - to get num of
663  * setbits from bitmask
664  * @mask: given bitmask
665  *
666  * This helper function should return number of setbits from bitmask
667  *
668  * Return: number of setbits from bitmask
669  */
670 static uint32_t policy_mgr_get_num_of_setbits_from_bitmask(uint32_t mask)
671 {
672 	uint32_t num_of_setbits = 0;
673 
674 	while (mask) {
675 		mask &= (mask - 1);
676 		num_of_setbits++;
677 	}
678 	return num_of_setbits;
679 }
680 
681 /**
682  * policy_mgr_map_wmi_channel_width_to_hw_mode_bw() - returns
683  * bandwidth in terms of hw_mode_bandwidth
684  * @width: bandwidth in terms of wmi_channel_width
685  *
686  * This function returns the bandwidth in terms of hw_mode_bandwidth.
687  *
688  * Return: BW in terms of hw_mode_bandwidth.
689  */
690 static enum hw_mode_bandwidth policy_mgr_map_wmi_channel_width_to_hw_mode_bw(
691 		wmi_channel_width width)
692 {
693 	switch (width) {
694 	case WMI_CHAN_WIDTH_20:
695 		return HW_MODE_20_MHZ;
696 	case WMI_CHAN_WIDTH_40:
697 		return HW_MODE_40_MHZ;
698 	case WMI_CHAN_WIDTH_80:
699 		return HW_MODE_80_MHZ;
700 	case WMI_CHAN_WIDTH_160:
701 		return HW_MODE_160_MHZ;
702 	case WMI_CHAN_WIDTH_80P80:
703 		return HW_MODE_80_PLUS_80_MHZ;
704 	case WMI_CHAN_WIDTH_5:
705 		return HW_MODE_5_MHZ;
706 	case WMI_CHAN_WIDTH_10:
707 		return HW_MODE_10_MHZ;
708 #ifdef WLAN_FEATURE_11BE
709 	case WMI_CHAN_WIDTH_320:
710 		return HW_MODE_320_MHZ;
711 #endif
712 	default:
713 		return HW_MODE_BW_NONE;
714 	}
715 
716 	return HW_MODE_BW_NONE;
717 }
718 
719 static void policy_mgr_get_hw_mode_params(
720 		struct wlan_psoc_host_mac_phy_caps *caps,
721 		struct policy_mgr_mac_ss_bw_info *info)
722 {
723 	qdf_freq_t max_5g_freq;
724 
725 	if (!caps) {
726 		policy_mgr_err("Invalid capabilities");
727 		return;
728 	}
729 
730 	info->mac_tx_stream = policy_mgr_get_num_of_setbits_from_bitmask(
731 		QDF_MAX(caps->tx_chain_mask_2G,
732 		caps->tx_chain_mask_5G));
733 	info->mac_rx_stream = policy_mgr_get_num_of_setbits_from_bitmask(
734 		QDF_MAX(caps->rx_chain_mask_2G,
735 		caps->rx_chain_mask_5G));
736 	info->mac_bw = policy_mgr_map_wmi_channel_width_to_hw_mode_bw(
737 		QDF_MAX(caps->max_bw_supported_2G,
738 		caps->max_bw_supported_5G));
739 	info->mac_band_cap = caps->supported_bands;
740 
741 	if (caps->supported_bands & WMI_HOST_WLAN_5G_CAPABILITY) {
742 		max_5g_freq = wlan_reg_max_6ghz_chan_freq() ?
743 				wlan_reg_max_6ghz_chan_freq() :
744 				wlan_reg_max_5ghz_chan_freq();
745 		max_5g_freq = caps->reg_cap_ext.high_5ghz_chan ?
746 				QDF_MIN(caps->reg_cap_ext.high_5ghz_chan,
747 					max_5g_freq) : max_5g_freq;
748 		info->support_6ghz_band =
749 			max_5g_freq > wlan_reg_min_6ghz_chan_freq();
750 	}
751 }
752 
753 /**
754  * policy_mgr_set_hw_mode_params() - sets TX-RX stream,
755  * bandwidth and DBS in hw_mode_list
756  * @psoc: PSOC object information
757  * @mac0_ss_bw_info: TX-RX streams, BW for MAC0
758  * @mac1_ss_bw_info: TX-RX streams, BW for MAC1
759  * @pos: refers to hw_mode_list array index
760  * @hw_mode_id: hw mode id value used by firmware
761  * @dbs_mode: dbs_mode for the dbs_hw_mode
762  * @sbs_mode: sbs_mode for the sbs_hw_mode
763  * @emlsr_mode: emlsr_mode for the emlsr_hw_mode
764  *
765  * This function sets TX-RX stream, bandwidth and DBS mode in
766  * hw_mode_list.
767  *
768  * Return: none
769  */
770 static void policy_mgr_set_hw_mode_params(struct wlan_objmgr_psoc *psoc,
771 			struct policy_mgr_mac_ss_bw_info mac0_ss_bw_info,
772 			struct policy_mgr_mac_ss_bw_info mac1_ss_bw_info,
773 			uint32_t pos, uint32_t hw_mode_id, uint32_t dbs_mode,
774 			uint32_t sbs_mode, uint64_t emlsr_mode)
775 {
776 	struct policy_mgr_psoc_priv_obj *pm_ctx;
777 	uint64_t legacy_hwmode_lst;
778 
779 	pm_ctx = policy_mgr_get_context(psoc);
780 	if (!pm_ctx) {
781 		policy_mgr_err("Invalid Context");
782 		return;
783 	}
784 
785 	POLICY_MGR_HW_MODE_MAC0_TX_STREAMS_SET(
786 		pm_ctx->hw_mode.hw_mode_list[pos],
787 		mac0_ss_bw_info.mac_tx_stream);
788 	POLICY_MGR_HW_MODE_MAC0_RX_STREAMS_SET(
789 		pm_ctx->hw_mode.hw_mode_list[pos],
790 		mac0_ss_bw_info.mac_rx_stream);
791 	POLICY_MGR_HW_MODE_MAC0_BANDWIDTH_SET(
792 		pm_ctx->hw_mode.hw_mode_list[pos],
793 		mac0_ss_bw_info.mac_bw);
794 	POLICY_MGR_HW_MODE_MAC1_TX_STREAMS_SET(
795 		pm_ctx->hw_mode.hw_mode_list[pos],
796 		mac1_ss_bw_info.mac_tx_stream);
797 	POLICY_MGR_HW_MODE_MAC1_RX_STREAMS_SET(
798 		pm_ctx->hw_mode.hw_mode_list[pos],
799 		mac1_ss_bw_info.mac_rx_stream);
800 	POLICY_MGR_HW_MODE_MAC1_BANDWIDTH_SET(
801 		pm_ctx->hw_mode.hw_mode_list[pos],
802 		mac1_ss_bw_info.mac_bw);
803 	POLICY_MGR_HW_MODE_DBS_MODE_SET(
804 		pm_ctx->hw_mode.hw_mode_list[pos],
805 		dbs_mode);
806 	POLICY_MGR_HW_MODE_AGILE_DFS_SET(
807 		pm_ctx->hw_mode.hw_mode_list[pos],
808 		HW_MODE_AGILE_DFS_NONE);
809 	POLICY_MGR_HW_MODE_SBS_MODE_SET(
810 		pm_ctx->hw_mode.hw_mode_list[pos],
811 		sbs_mode);
812 	POLICY_MGR_HW_MODE_MAC0_BAND_SET(
813 		pm_ctx->hw_mode.hw_mode_list[pos],
814 		mac0_ss_bw_info.mac_band_cap);
815 	POLICY_MGR_HW_MODE_ID_SET(
816 		pm_ctx->hw_mode.hw_mode_list[pos],
817 		hw_mode_id);
818 
819 	legacy_hwmode_lst = pm_ctx->hw_mode.hw_mode_list[pos];
820 	POLICY_MGR_HW_MODE_EMLSR_MODE_SET(
821 	    pm_ctx->hw_mode.hw_mode_list[pos],
822 	    legacy_hwmode_lst, emlsr_mode);
823 }
824 
825 QDF_STATUS policy_mgr_get_radio_combinations(struct wlan_objmgr_psoc *psoc,
826 					     struct radio_combination *comb,
827 					     uint32_t comb_max,
828 					     uint32_t *comb_num)
829 {
830 	struct policy_mgr_psoc_priv_obj *pm_ctx;
831 	struct radio_combination *radio_comb;
832 	uint32_t i;
833 	bool dbs_or_sbs_enabled = false;
834 
835 	pm_ctx = policy_mgr_get_context(psoc);
836 	if (!pm_ctx) {
837 		policy_mgr_err("Invalid Context");
838 		return QDF_STATUS_E_FAILURE;
839 	}
840 
841 	*comb_num = 0;
842 	if (policy_mgr_is_hw_dbs_capable(psoc) ||
843 	    policy_mgr_is_hw_sbs_capable(psoc))
844 		dbs_or_sbs_enabled = true;
845 
846 	for (i = 0; i < pm_ctx->radio_comb_num; i++) {
847 		radio_comb = &pm_ctx->radio_combinations[i];
848 		if (!dbs_or_sbs_enabled && radio_comb->hw_mode != MODE_SMM)
849 			continue;
850 		if (*comb_num >= comb_max) {
851 			policy_mgr_err("out of buffer %d max %d",
852 				       pm_ctx->radio_comb_num,
853 				       comb_max);
854 			return QDF_STATUS_E_FAILURE;
855 		}
856 		policy_mgr_debug("radio %d: mode %d mac0 (0x%x, 0x%x), mac1 (0x%x 0x%x)",
857 				 *comb_num,
858 				 radio_comb->hw_mode,
859 				 radio_comb->band_mask[0],
860 				 radio_comb->antenna[0],
861 				 radio_comb->band_mask[1],
862 				 radio_comb->antenna[1]);
863 		qdf_mem_copy(&comb[*comb_num], radio_comb,
864 			     sizeof(*radio_comb));
865 		(*comb_num)++;
866 	}
867 
868 	return QDF_STATUS_SUCCESS;
869 }
870 
871 /**
872  * policy_mgr_add_radio_comb() - Add radio combination
873  * @pm_ctx: bandwidth in terms of wmi_channel_width
874  * @radio: radio combination
875  *
876  * This function adds one radio combination to list
877  *
878  * Return: void
879  */
880 static void policy_mgr_add_radio_comb(struct policy_mgr_psoc_priv_obj *pm_ctx,
881 				      struct radio_combination *radio)
882 {
883 	uint32_t i;
884 	struct radio_combination *comb;
885 
886 	/* don't add duplicated item */
887 	for (i = 0; i < pm_ctx->radio_comb_num; i++) {
888 		comb = &pm_ctx->radio_combinations[i];
889 		if (radio->hw_mode == comb->hw_mode &&
890 		    radio->band_mask[0] == comb->band_mask[0] &&
891 		    radio->band_mask[1] == comb->band_mask[1] &&
892 		    radio->antenna[0] == comb->antenna[0] &&
893 		    radio->antenna[1] == comb->antenna[1])
894 			return;
895 	}
896 	if (pm_ctx->radio_comb_num == MAX_RADIO_COMBINATION) {
897 		policy_mgr_err("radio combination overflow %d",
898 			       pm_ctx->radio_comb_num);
899 		return;
900 	}
901 	policy_mgr_debug("radio %d: mode %d mac0 (0x%x, 0x%x), mac1 (0x%x 0x%x)",
902 			 pm_ctx->radio_comb_num,
903 			 radio->hw_mode,
904 			 radio->band_mask[0],
905 			 radio->antenna[0],
906 			 radio->band_mask[1],
907 			 radio->antenna[1]);
908 
909 	qdf_mem_copy(&pm_ctx->radio_combinations[pm_ctx->radio_comb_num],
910 		     radio, sizeof(*radio));
911 	pm_ctx->radio_comb_num++;
912 }
913 
914 #define SET_RADIO(_radio, _mode, _mac0_band, _mac1_band,\
915 		  _mac0_antenna, _mac1_antenna) \
916 do { \
917 	(_radio)->hw_mode = _mode; \
918 	(_radio)->band_mask[0] = _mac0_band; \
919 	(_radio)->band_mask[1] = _mac1_band; \
920 	(_radio)->antenna[0] = _mac0_antenna; \
921 	(_radio)->antenna[1] = _mac1_antenna; \
922 } while (0)
923 
924 /**
925  * policy_mgr_update_radio_combination_matrix() - Update radio combination
926  * list
927  * @psoc: psoc object
928  * @mac0_ss_bw_info: mac 0 band/bw info
929  * @mac1_ss_bw_info: mac 1 band/bw info
930  * @dbs_mode: dbs mode
931  * @sbs_mode: sbs mode
932  *
933  * This function updates radio combination list based on hw mode information.
934  *
935  * Return: void
936  */
937 static void
938 policy_mgr_update_radio_combination_matrix(
939 			struct wlan_objmgr_psoc *psoc,
940 			struct policy_mgr_mac_ss_bw_info mac0_ss_bw_info,
941 			struct policy_mgr_mac_ss_bw_info mac1_ss_bw_info,
942 			uint32_t dbs_mode, uint32_t sbs_mode)
943 {
944 	struct policy_mgr_psoc_priv_obj *pm_ctx;
945 	struct radio_combination radio;
946 
947 	pm_ctx = policy_mgr_get_context(psoc);
948 	if (!pm_ctx) {
949 		policy_mgr_err("Invalid Context");
950 		return;
951 	}
952 
953 	if (!dbs_mode && !sbs_mode) {
954 		if (mac0_ss_bw_info.mac_band_cap &
955 					WMI_HOST_WLAN_2G_CAPABILITY) {
956 			SET_RADIO(&radio, MODE_SMM, BIT(REG_BAND_2G), 0,
957 				  mac0_ss_bw_info.mac_tx_stream, 0);
958 			policy_mgr_add_radio_comb(pm_ctx, &radio);
959 		}
960 		if (mac0_ss_bw_info.mac_band_cap &
961 					WMI_HOST_WLAN_5G_CAPABILITY) {
962 			SET_RADIO(&radio, MODE_SMM, BIT(REG_BAND_5G), 0,
963 				  mac0_ss_bw_info.mac_tx_stream, 0);
964 			policy_mgr_add_radio_comb(pm_ctx, &radio);
965 			if (mac0_ss_bw_info.support_6ghz_band) {
966 				SET_RADIO(&radio, MODE_SMM, BIT(REG_BAND_6G),
967 					  0, mac0_ss_bw_info.mac_tx_stream, 0);
968 				policy_mgr_add_radio_comb(pm_ctx, &radio);
969 			}
970 		}
971 		return;
972 	}
973 	if ((mac0_ss_bw_info.mac_band_cap & WMI_HOST_WLAN_2G_CAPABILITY) &&
974 	    (mac1_ss_bw_info.mac_band_cap & WMI_HOST_WLAN_5G_CAPABILITY)) {
975 		SET_RADIO(&radio, MODE_DBS, BIT(REG_BAND_2G), BIT(REG_BAND_5G),
976 			  mac0_ss_bw_info.mac_tx_stream,
977 			  mac1_ss_bw_info.mac_tx_stream);
978 		policy_mgr_add_radio_comb(pm_ctx, &radio);
979 		if (mac1_ss_bw_info.support_6ghz_band) {
980 			SET_RADIO(&radio, MODE_DBS, BIT(REG_BAND_2G),
981 				  BIT(REG_BAND_6G),
982 				  mac0_ss_bw_info.mac_tx_stream,
983 				  mac1_ss_bw_info.mac_tx_stream);
984 			policy_mgr_add_radio_comb(pm_ctx, &radio);
985 		}
986 	}
987 	if ((mac0_ss_bw_info.mac_band_cap & WMI_HOST_WLAN_5G_CAPABILITY) &&
988 	    (mac1_ss_bw_info.mac_band_cap & WMI_HOST_WLAN_2G_CAPABILITY)) {
989 		SET_RADIO(&radio, MODE_DBS, BIT(REG_BAND_2G), BIT(REG_BAND_5G),
990 			  mac1_ss_bw_info.mac_tx_stream,
991 			  mac0_ss_bw_info.mac_tx_stream);
992 		policy_mgr_add_radio_comb(pm_ctx, &radio);
993 		if (mac0_ss_bw_info.support_6ghz_band) {
994 			SET_RADIO(&radio, MODE_DBS, BIT(REG_BAND_2G),
995 				  BIT(REG_BAND_6G),
996 				  mac1_ss_bw_info.mac_tx_stream,
997 				  mac0_ss_bw_info.mac_tx_stream);
998 			policy_mgr_add_radio_comb(pm_ctx, &radio);
999 		}
1000 	}
1001 	if ((mac0_ss_bw_info.mac_band_cap & WMI_HOST_WLAN_5G_CAPABILITY) &&
1002 	    (mac1_ss_bw_info.mac_band_cap & WMI_HOST_WLAN_5G_CAPABILITY)) {
1003 		if (mac0_ss_bw_info.support_6ghz_band) {
1004 			SET_RADIO(&radio, MODE_SBS, BIT(REG_BAND_5G),
1005 				  BIT(REG_BAND_6G),
1006 				  mac1_ss_bw_info.mac_tx_stream,
1007 				  mac0_ss_bw_info.mac_tx_stream);
1008 			policy_mgr_add_radio_comb(pm_ctx, &radio);
1009 		} else if (mac1_ss_bw_info.support_6ghz_band) {
1010 			SET_RADIO(&radio, MODE_SBS, BIT(REG_BAND_5G),
1011 				  BIT(REG_BAND_6G),
1012 				  mac0_ss_bw_info.mac_tx_stream,
1013 				  mac1_ss_bw_info.mac_tx_stream);
1014 			policy_mgr_add_radio_comb(pm_ctx, &radio);
1015 		}
1016 	}
1017 }
1018 
1019 static void
1020 policy_mgr_update_24Ghz_freq_info(struct policy_mgr_freq_range *mac_range,
1021 				  struct wlan_psoc_host_mac_phy_caps *mac_cap)
1022 {
1023 	mac_range->low_2ghz_freq = QDF_MAX(mac_cap->reg_cap_ext.low_2ghz_chan,
1024 					   wlan_reg_min_24ghz_chan_freq());
1025 	mac_range->high_2ghz_freq = mac_cap->reg_cap_ext.high_2ghz_chan ?
1026 				    QDF_MIN(mac_cap->reg_cap_ext.high_2ghz_chan,
1027 					    wlan_reg_max_24ghz_chan_freq()) :
1028 				    wlan_reg_max_24ghz_chan_freq();
1029 }
1030 
1031 static void
1032 policy_mgr_update_5Ghz_freq_info(struct policy_mgr_freq_range *mac_range,
1033 				  struct wlan_psoc_host_mac_phy_caps *mac_cap)
1034 {
1035 	qdf_freq_t max_5g_freq;
1036 
1037 	max_5g_freq = wlan_reg_max_6ghz_chan_freq() ?
1038 			wlan_reg_max_6ghz_chan_freq() :
1039 			wlan_reg_max_5ghz_chan_freq();
1040 
1041 	mac_range->low_5ghz_freq = QDF_MAX(mac_cap->reg_cap_ext.low_5ghz_chan,
1042 					   wlan_reg_min_5ghz_chan_freq());
1043 	mac_range->high_5ghz_freq = mac_cap->reg_cap_ext.high_5ghz_chan ?
1044 				    QDF_MIN(mac_cap->reg_cap_ext.high_5ghz_chan,
1045 					    max_5g_freq) :
1046 				    max_5g_freq;
1047 
1048 }
1049 
1050 static void
1051 policy_mgr_update_freq_info(struct policy_mgr_psoc_priv_obj *pm_ctx,
1052 			    struct wlan_psoc_host_mac_phy_caps *mac_cap,
1053 			    enum policy_mgr_mode mode,
1054 			    uint32_t phy_id)
1055 {
1056 	struct policy_mgr_freq_range *mac_range;
1057 
1058 	mac_range = &pm_ctx->hw_mode.freq_range_caps[mode][phy_id];
1059 	if (mac_cap->supported_bands & WMI_HOST_WLAN_2G_CAPABILITY)
1060 		policy_mgr_update_24Ghz_freq_info(mac_range, mac_cap);
1061 
1062 	if (mac_cap->supported_bands & WMI_HOST_WLAN_5G_CAPABILITY)
1063 		policy_mgr_update_5Ghz_freq_info(mac_range, mac_cap);
1064 }
1065 
1066 static QDF_STATUS
1067 policy_mgr_modify_sbs_freq(struct policy_mgr_psoc_priv_obj *pm_ctx,
1068 			   uint8_t phy_id)
1069 {
1070 	uint8_t shared_phy_id;
1071 	struct policy_mgr_freq_range *sbs_mac_range, *shared_mac_range;
1072 	struct policy_mgr_freq_range *non_shared_range;
1073 
1074 	sbs_mac_range = &pm_ctx->hw_mode.freq_range_caps[MODE_SBS][phy_id];
1075 
1076 	/*
1077 	 * if SBS mac range has both 2.4 and 5 Ghz range, i e shared phy_id
1078 	 * keep the range as it is in SBS
1079 	 */
1080 	if (sbs_mac_range->low_2ghz_freq && sbs_mac_range->low_5ghz_freq)
1081 		return QDF_STATUS_SUCCESS;
1082 	if (sbs_mac_range->low_2ghz_freq && !sbs_mac_range->low_5ghz_freq) {
1083 		policy_mgr_err("Invalid DBS/SBS mode with only 2.4Ghz");
1084 		policy_mgr_dump_freq_range_per_mac(sbs_mac_range, MODE_SBS);
1085 		return QDF_STATUS_E_INVAL;
1086 	}
1087 
1088 	non_shared_range = sbs_mac_range;
1089 	/*
1090 	 * if SBS mac range has only 5Ghz then its the non shared phy, so
1091 	 * modify the range as per the shared mac.
1092 	 */
1093 	shared_phy_id = phy_id ? 0 : 1;
1094 	shared_mac_range =
1095 		&pm_ctx->hw_mode.freq_range_caps[MODE_SBS][shared_phy_id];
1096 
1097 	if (shared_mac_range->low_5ghz_freq > non_shared_range->low_5ghz_freq) {
1098 		policy_mgr_debug("High 5Ghz shared");
1099 		/*
1100 		 * If the shared mac lower 5Ghz frequency is greater than
1101 		 * non-shared mac lower 5Ghz frequency then the shared mac has
1102 		 * HIGH 5Ghz shared with 2.4Ghz. So non-shared mac's 5Ghz high
1103 		 * freq should be less than the shared mac's low 5Ghz freq.
1104 		 */
1105 		if (non_shared_range->high_5ghz_freq >=
1106 		    shared_mac_range->low_5ghz_freq)
1107 			non_shared_range->high_5ghz_freq =
1108 				QDF_MAX(shared_mac_range->low_5ghz_freq - 10,
1109 					non_shared_range->low_5ghz_freq);
1110 	} else if (shared_mac_range->high_5ghz_freq <
1111 		   non_shared_range->high_5ghz_freq) {
1112 		policy_mgr_debug("LOW 5Ghz shared");
1113 		/*
1114 		 * If the shared mac high 5Ghz frequency is less than
1115 		 * non-shared mac high 5Ghz frequency then the shared mac has
1116 		 * LOW 5Ghz shared with 2.4Ghz So non-shared mac's 5Ghz low
1117 		 * freq should be greater than the shared mac's high 5Ghz freq.
1118 		 */
1119 		if (shared_mac_range->high_5ghz_freq >=
1120 		    non_shared_range->low_5ghz_freq)
1121 			non_shared_range->low_5ghz_freq =
1122 				QDF_MIN(shared_mac_range->high_5ghz_freq + 10,
1123 					non_shared_range->high_5ghz_freq);
1124 	} else {
1125 		policy_mgr_info("Invalid SBS range with all 5Ghz shared");
1126 		return QDF_STATUS_E_INVAL;
1127 	}
1128 
1129 	return QDF_STATUS_SUCCESS;
1130 }
1131 
1132 static qdf_freq_t
1133 policy_mgr_get_highest_5ghz_freq_frm_range(struct policy_mgr_freq_range *range)
1134 {
1135 	uint8_t phy_id;
1136 	qdf_freq_t highest_freq = 0;
1137 	qdf_freq_t max_5g_freq = wlan_reg_max_6ghz_chan_freq() ?
1138 			wlan_reg_max_6ghz_chan_freq() :
1139 			wlan_reg_max_5ghz_chan_freq();
1140 
1141 	for (phy_id = 0; phy_id < MAX_MAC; phy_id++) {
1142 		if (range[phy_id].high_5ghz_freq > highest_freq)
1143 			highest_freq = range[phy_id].high_5ghz_freq;
1144 	}
1145 
1146 	return highest_freq ? highest_freq : max_5g_freq;
1147 }
1148 
1149 static qdf_freq_t
1150 policy_mgr_get_lowest_5ghz_freq_frm_range(struct policy_mgr_freq_range *range)
1151 {
1152 	uint8_t phy_id;
1153 	qdf_freq_t lowest_freq = 0;
1154 
1155 	for (phy_id = 0; phy_id < MAX_MAC; phy_id++) {
1156 		if ((!lowest_freq && range[phy_id].low_5ghz_freq) ||
1157 		    (range[phy_id].low_5ghz_freq < lowest_freq))
1158 			lowest_freq = range[phy_id].low_5ghz_freq;
1159 	}
1160 
1161 	return lowest_freq ? lowest_freq : wlan_reg_min_5ghz_chan_freq();
1162 }
1163 
1164 static void
1165 policy_mgr_fill_lower_share_sbs_freq(struct policy_mgr_psoc_priv_obj *pm_ctx,
1166 				     uint16_t sbs_range_sep,
1167 				     struct policy_mgr_freq_range *ref_freq)
1168 {
1169 	struct policy_mgr_freq_range *lower_sbs_freq_range;
1170 	uint8_t phy_id;
1171 
1172 	lower_sbs_freq_range =
1173 		pm_ctx->hw_mode.freq_range_caps[MODE_SBS_LOWER_SHARE];
1174 
1175 	for (phy_id = 0; phy_id < MAX_MAC; phy_id++) {
1176 		lower_sbs_freq_range[phy_id].low_2ghz_freq =
1177 						ref_freq[phy_id].low_2ghz_freq;
1178 		lower_sbs_freq_range[phy_id].high_2ghz_freq =
1179 						ref_freq[phy_id].high_2ghz_freq;
1180 
1181 		/* update for shared mac */
1182 		if (lower_sbs_freq_range[phy_id].low_2ghz_freq) {
1183 			lower_sbs_freq_range[phy_id].low_5ghz_freq =
1184 			    policy_mgr_get_lowest_5ghz_freq_frm_range(ref_freq);
1185 			lower_sbs_freq_range[phy_id].high_5ghz_freq =
1186 				sbs_range_sep;
1187 		} else {
1188 			lower_sbs_freq_range[phy_id].low_5ghz_freq =
1189 				sbs_range_sep + 10;
1190 			lower_sbs_freq_range[phy_id].high_5ghz_freq =
1191 			   policy_mgr_get_highest_5ghz_freq_frm_range(ref_freq);
1192 		}
1193 	}
1194 }
1195 
1196 static void
1197 policy_mgr_fill_upper_share_sbs_freq(struct policy_mgr_psoc_priv_obj *pm_ctx,
1198 				     uint16_t sbs_range_sep,
1199 				     struct policy_mgr_freq_range *ref_freq)
1200 {
1201 	struct policy_mgr_freq_range *upper_sbs_freq_range;
1202 	uint8_t phy_id;
1203 
1204 	upper_sbs_freq_range =
1205 		pm_ctx->hw_mode.freq_range_caps[MODE_SBS_UPPER_SHARE];
1206 
1207 	for (phy_id = 0; phy_id < MAX_MAC; phy_id++) {
1208 		upper_sbs_freq_range[phy_id].low_2ghz_freq =
1209 						ref_freq[phy_id].low_2ghz_freq;
1210 		upper_sbs_freq_range[phy_id].high_2ghz_freq =
1211 						ref_freq[phy_id].high_2ghz_freq;
1212 
1213 		/* update for shared mac */
1214 		if (upper_sbs_freq_range[phy_id].low_2ghz_freq) {
1215 			upper_sbs_freq_range[phy_id].low_5ghz_freq =
1216 				sbs_range_sep + 10;
1217 			upper_sbs_freq_range[phy_id].high_5ghz_freq =
1218 			   policy_mgr_get_highest_5ghz_freq_frm_range(ref_freq);
1219 		} else {
1220 			upper_sbs_freq_range[phy_id].low_5ghz_freq =
1221 			    policy_mgr_get_lowest_5ghz_freq_frm_range(ref_freq);
1222 			upper_sbs_freq_range[phy_id].high_5ghz_freq =
1223 				sbs_range_sep;
1224 		}
1225 	}
1226 }
1227 
1228 static bool
1229 policy_mgr_both_phy_range_updated(struct policy_mgr_psoc_priv_obj *pm_ctx,
1230 				  enum policy_mgr_mode hwmode)
1231 {
1232 	struct policy_mgr_freq_range *mac_range;
1233 	uint8_t phy_id;
1234 
1235 	for (phy_id = 0; phy_id < MAX_MAC; phy_id++) {
1236 		mac_range =
1237 			&pm_ctx->hw_mode.freq_range_caps[hwmode][phy_id];
1238 		/* modify SBS/DBS range only when both phy for DBS are filled */
1239 		if (!mac_range->low_2ghz_freq && !mac_range->low_5ghz_freq)
1240 			return false;
1241 	}
1242 
1243 	return true;
1244 }
1245 
1246 static void
1247 policy_mgr_update_sbs_freq_info(struct policy_mgr_psoc_priv_obj *pm_ctx)
1248 {
1249 	uint16_t sbs_range_sep;
1250 	struct policy_mgr_freq_range *mac_range;
1251 	uint8_t phy_id;
1252 	QDF_STATUS status;
1253 
1254 	mac_range = pm_ctx->hw_mode.freq_range_caps[MODE_SBS];
1255 
1256 	/*
1257 	 * If sbs_lower_band_end_freq has a value Z, then the frequency range
1258 	 * will be split using that value.
1259 	 */
1260 	sbs_range_sep = pm_ctx->hw_mode.sbs_lower_band_end_freq;
1261 	if (sbs_range_sep) {
1262 		policy_mgr_fill_upper_share_sbs_freq(pm_ctx, sbs_range_sep,
1263 						     mac_range);
1264 		policy_mgr_fill_lower_share_sbs_freq(pm_ctx, sbs_range_sep,
1265 						     mac_range);
1266 		/* Reset the SBS range */
1267 		qdf_mem_zero(mac_range, sizeof(*mac_range) * MAX_MAC);
1268 		return;
1269 	}
1270 
1271 	/*
1272 	 * If sbs_lower_band_end_freq is not set that means FW will send one
1273 	 * shared mac range and one non-shared mac range. so update that freq.
1274 	 */
1275 	for (phy_id = 0; phy_id < MAX_MAC; phy_id++) {
1276 		status = policy_mgr_modify_sbs_freq(pm_ctx, phy_id);
1277 		if (QDF_IS_STATUS_ERROR(status)) {
1278 			/* Reset the SBS range */
1279 			qdf_mem_zero(mac_range, sizeof(*mac_range) * MAX_MAC);
1280 			break;
1281 		}
1282 	}
1283 }
1284 
1285 static void
1286 policy_mgr_update_dbs_freq_info(struct policy_mgr_psoc_priv_obj *pm_ctx)
1287 {
1288 	struct policy_mgr_freq_range *mac_range;
1289 	uint8_t phy_id;
1290 
1291 	mac_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
1292 	/* Reset 5Ghz range for shared mac for DBS */
1293 	for (phy_id = 0; phy_id < MAX_MAC; phy_id++) {
1294 		if (mac_range[phy_id].low_2ghz_freq &&
1295 		    mac_range[phy_id].low_5ghz_freq) {
1296 			mac_range[phy_id].low_5ghz_freq = 0;
1297 			mac_range[phy_id].high_5ghz_freq = 0;
1298 		}
1299 	}
1300 }
1301 
1302 static void
1303 policy_mgr_update_mac_freq_info(struct wlan_objmgr_psoc *psoc,
1304 				struct policy_mgr_psoc_priv_obj *pm_ctx,
1305 				enum wmi_hw_mode_config_type hw_config_type,
1306 				uint32_t phy_id,
1307 				struct wlan_psoc_host_mac_phy_caps *mac_cap)
1308 {
1309 	if (phy_id >= MAX_MAC) {
1310 		policy_mgr_err("mac more than two not supported: %d",
1311 			       phy_id);
1312 		return;
1313 	}
1314 
1315 	policy_mgr_debug("hw_mode_cfg: %d mac: %d band: 0x%x, SBS cutoff freq %d, 2Ghz: %d -> %d 5Ghz: %d -> %d",
1316 			 hw_config_type, phy_id, mac_cap->supported_bands,
1317 			 pm_ctx->hw_mode.sbs_lower_band_end_freq,
1318 			 mac_cap->reg_cap_ext.low_2ghz_chan,
1319 			 mac_cap->reg_cap_ext.high_2ghz_chan,
1320 			 mac_cap->reg_cap_ext.low_5ghz_chan,
1321 			 mac_cap->reg_cap_ext.high_5ghz_chan);
1322 
1323 	switch (hw_config_type) {
1324 	case WMI_HW_MODE_SINGLE:
1325 		if (phy_id) {
1326 			policy_mgr_debug("MAC Phy 1 is not supported");
1327 			break;
1328 		}
1329 		policy_mgr_update_freq_info(pm_ctx, mac_cap, MODE_SMM, phy_id);
1330 		break;
1331 
1332 	case WMI_HW_MODE_DBS:
1333 	case WMI_HW_MODE_DBS_2G_5G:
1334 		if (!policy_mgr_both_phy_range_updated(pm_ctx, MODE_DBS))
1335 			policy_mgr_update_freq_info(pm_ctx, mac_cap,
1336 						    MODE_DBS, phy_id);
1337 		break;
1338 	case WMI_HW_MODE_DBS_SBS:
1339 	case WMI_HW_MODE_DBS_OR_SBS:
1340 		policy_mgr_update_freq_info(pm_ctx, mac_cap, MODE_DBS, phy_id);
1341 		/*
1342 		 * fill SBS only if freq is provided by FW or
1343 		 * pm_ctx->hw_mode.sbs_lower_band_end_freq is set
1344 		 */
1345 		if (pm_ctx->hw_mode.sbs_lower_band_end_freq ||
1346 		    mac_cap->reg_cap_ext.low_5ghz_chan ||
1347 		    mac_cap->reg_cap_ext.low_2ghz_chan)
1348 			policy_mgr_update_freq_info(pm_ctx, mac_cap, MODE_SBS,
1349 						    phy_id);
1350 
1351 		/* Modify the DBS list once both phy info are filled */
1352 		if (policy_mgr_both_phy_range_updated(pm_ctx, MODE_DBS))
1353 			policy_mgr_update_dbs_freq_info(pm_ctx);
1354 		/* Modify the SBS list once both phy info are filled */
1355 		if (policy_mgr_both_phy_range_updated(pm_ctx, MODE_SBS))
1356 			policy_mgr_update_sbs_freq_info(pm_ctx);
1357 		break;
1358 	case WMI_HW_MODE_2G_PHYB:
1359 		if (phy_id)
1360 			policy_mgr_update_freq_info(pm_ctx, mac_cap, MODE_SMM,
1361 						    phy_id);
1362 		break;
1363 	case WMI_HW_MODE_SBS:
1364 	case WMI_HW_MODE_SBS_PASSIVE:
1365 		policy_mgr_update_freq_info(pm_ctx, mac_cap, MODE_SBS, phy_id);
1366 		/* Modify the SBS Upper Lower list once both phy are filled */
1367 		if (policy_mgr_both_phy_range_updated(pm_ctx, MODE_SBS))
1368 			policy_mgr_update_sbs_freq_info(pm_ctx);
1369 
1370 		break;
1371 	case WMI_HW_MODE_EMLSR:
1372 	case WMI_HW_MODE_AUX_EMLSR_SINGLE:
1373 	case WMI_HW_MODE_AUX_EMLSR_SPLIT:
1374 		policy_mgr_update_freq_info(pm_ctx, mac_cap, MODE_EMLSR,
1375 					    phy_id);
1376 		break;
1377 	default:
1378 		policy_mgr_err("HW mode not defined %d",
1379 			       hw_config_type);
1380 		break;
1381 	}
1382 }
1383 
1384 void
1385 policy_mgr_dump_curr_freq_range(struct policy_mgr_psoc_priv_obj *pm_ctx)
1386 {
1387 	uint32_t i;
1388 	struct policy_mgr_freq_range *freq_range;
1389 
1390 	freq_range = pm_ctx->hw_mode.cur_mac_freq_range;
1391 	for (i = 0; i < MAX_MAC; i++)
1392 		if (freq_range[i].low_2ghz_freq || freq_range[i].low_5ghz_freq)
1393 			policymgr_nofl_debug("PLCY_MGR_FREQ_RANGE_CUR: mac %d: 2Ghz: %d -> %d, 5Ghz: %d -> %d",
1394 					     i, freq_range[i].low_2ghz_freq,
1395 					     freq_range[i].high_2ghz_freq,
1396 					     freq_range[i].low_5ghz_freq,
1397 					     freq_range[i].high_5ghz_freq);
1398 }
1399 
1400 static const char *policy_mgr_hw_mode_to_str(enum policy_mgr_mode hw_mode)
1401 {
1402 	if (hw_mode >= MODE_HW_MAX)
1403 		return "Unknown";
1404 
1405 	switch (hw_mode) {
1406 	CASE_RETURN_STRING(MODE_SMM);
1407 	CASE_RETURN_STRING(MODE_DBS);
1408 	CASE_RETURN_STRING(MODE_SBS);
1409 	CASE_RETURN_STRING(MODE_SBS_UPPER_SHARE);
1410 	CASE_RETURN_STRING(MODE_SBS_LOWER_SHARE);
1411 	CASE_RETURN_STRING(MODE_EMLSR);
1412 	default:
1413 		return "Unknown";
1414 	}
1415 }
1416 
1417 void
1418 policy_mgr_dump_freq_range_per_mac(struct policy_mgr_freq_range *freq_range,
1419 				   enum policy_mgr_mode hw_mode)
1420 {
1421 	uint32_t i;
1422 
1423 	for (i = 0; i < MAX_MAC; i++)
1424 		if (freq_range[i].low_2ghz_freq || freq_range[i].low_5ghz_freq)
1425 			policymgr_nofl_debug("PLCY_MGR_FREQ_RANGE: %s(%d): mac %d: 2Ghz: %d -> %d, 5Ghz: %d -> %d",
1426 					     policy_mgr_hw_mode_to_str(hw_mode),
1427 					     hw_mode, i,
1428 					     freq_range[i].low_2ghz_freq,
1429 					     freq_range[i].high_2ghz_freq,
1430 					     freq_range[i].low_5ghz_freq,
1431 					     freq_range[i].high_5ghz_freq);
1432 }
1433 
1434 static void
1435 policy_mgr_dump_hw_modes_freq_range(struct policy_mgr_psoc_priv_obj *pm_ctx)
1436 {
1437 	uint32_t i;
1438 	struct policy_mgr_freq_range *freq_range;
1439 
1440 	for (i = MODE_SMM; i < MODE_HW_MAX; i++) {
1441 		freq_range = pm_ctx->hw_mode.freq_range_caps[i];
1442 		policy_mgr_dump_freq_range_per_mac(freq_range, i);
1443 	}
1444 }
1445 
1446 void policy_mgr_dump_sbs_freq_range(struct policy_mgr_psoc_priv_obj *pm_ctx)
1447 {
1448 	uint32_t i;
1449 	struct policy_mgr_freq_range *freq_range;
1450 
1451 	for (i = MODE_SMM; i < MODE_HW_MAX; i++) {
1452 		if ((i == MODE_SBS) ||
1453 		    (pm_ctx->hw_mode.sbs_lower_band_end_freq &&
1454 		    (i == MODE_SBS_LOWER_SHARE || i == MODE_SBS_UPPER_SHARE))) {
1455 			freq_range = pm_ctx->hw_mode.freq_range_caps[i];
1456 			policy_mgr_dump_freq_range_per_mac(freq_range, i);
1457 		}
1458 	}
1459 }
1460 
1461 static bool
1462 policy_mgr_sbs_range_present(struct policy_mgr_psoc_priv_obj *pm_ctx)
1463 {
1464 	if (policy_mgr_both_phy_range_updated(pm_ctx, MODE_SBS) ||
1465 	    (pm_ctx->hw_mode.sbs_lower_band_end_freq &&
1466 	     policy_mgr_both_phy_range_updated(pm_ctx, MODE_SBS_LOWER_SHARE) &&
1467 	     policy_mgr_both_phy_range_updated(pm_ctx, MODE_SBS_UPPER_SHARE)))
1468 		return true;
1469 
1470 	return false;
1471 }
1472 
1473 void
1474 policy_mgr_dump_freq_range(struct policy_mgr_psoc_priv_obj *pm_ctx)
1475 {
1476 	policy_mgr_dump_hw_modes_freq_range(pm_ctx);
1477 	policy_mgr_dump_curr_freq_range(pm_ctx);
1478 }
1479 
1480 static void
1481 policy_mgr_update_sbs_lowr_band_end_frq(struct policy_mgr_psoc_priv_obj *pm_ctx,
1482 					struct tgt_info *info)
1483 {
1484 	if (wlan_reg_is_5ghz_ch_freq(info->sbs_lower_band_end_freq) ||
1485 	    wlan_reg_is_6ghz_chan_freq(info->sbs_lower_band_end_freq))
1486 		pm_ctx->hw_mode.sbs_lower_band_end_freq =
1487 						info->sbs_lower_band_end_freq;
1488 }
1489 
1490 QDF_STATUS policy_mgr_update_hw_mode_list(struct wlan_objmgr_psoc *psoc,
1491 					  struct target_psoc_info *tgt_hdl)
1492 {
1493 	struct wlan_psoc_host_mac_phy_caps *tmp;
1494 	struct wlan_psoc_host_mac_phy_caps_ext2 *cap;
1495 	uint32_t i, j = 0;
1496 	enum wmi_hw_mode_config_type hw_config_type;
1497 	uint32_t dbs_mode, sbs_mode;
1498 	uint64_t emlsr_mode;
1499 	struct policy_mgr_mac_ss_bw_info mac0_ss_bw_info = {0};
1500 	struct policy_mgr_mac_ss_bw_info mac1_ss_bw_info = {0};
1501 	struct policy_mgr_psoc_priv_obj *pm_ctx;
1502 	struct tgt_info *info;
1503 
1504 	pm_ctx = policy_mgr_get_context(psoc);
1505 	if (!pm_ctx) {
1506 		policy_mgr_err("Invalid Context");
1507 		return QDF_STATUS_E_FAILURE;
1508 	}
1509 
1510 	info = &tgt_hdl->info;
1511 	if (!info->service_ext_param.num_hw_modes) {
1512 		policy_mgr_err("Number of HW modes: %d",
1513 			       info->service_ext_param.num_hw_modes);
1514 		return QDF_STATUS_E_FAILURE;
1515 	}
1516 
1517 	/*
1518 	 * This list was updated as part of service ready event. Re-populate
1519 	 * HW mode list from the device capabilities.
1520 	 */
1521 	if (pm_ctx->hw_mode.hw_mode_list) {
1522 		qdf_mem_free(pm_ctx->hw_mode.hw_mode_list);
1523 		pm_ctx->hw_mode.hw_mode_list = NULL;
1524 		policy_mgr_debug("DBS list is freed");
1525 	}
1526 
1527 	/* Reset old freq ranges */
1528 	qdf_mem_zero(pm_ctx->hw_mode.freq_range_caps,
1529 		     sizeof(pm_ctx->hw_mode.freq_range_caps));
1530 	qdf_mem_zero(pm_ctx->hw_mode.cur_mac_freq_range,
1531 		     sizeof(pm_ctx->hw_mode.cur_mac_freq_range));
1532 	pm_ctx->num_dbs_hw_modes = info->service_ext_param.num_hw_modes;
1533 	pm_ctx->hw_mode.hw_mode_list =
1534 		qdf_mem_malloc(sizeof(*pm_ctx->hw_mode.hw_mode_list) *
1535 		pm_ctx->num_dbs_hw_modes);
1536 	if (!pm_ctx->hw_mode.hw_mode_list) {
1537 		pm_ctx->num_dbs_hw_modes = 0;
1538 		return QDF_STATUS_E_NOMEM;
1539 	}
1540 	pm_ctx->radio_comb_num = 0;
1541 	qdf_mem_zero(pm_ctx->radio_combinations,
1542 		     sizeof(pm_ctx->radio_combinations));
1543 
1544 	policy_mgr_debug("Updated HW mode list: Num modes:%d",
1545 		pm_ctx->num_dbs_hw_modes);
1546 
1547 	for (i = 0; i < pm_ctx->num_dbs_hw_modes; i++) {
1548 		/* Update for MAC0 */
1549 		tmp = &info->mac_phy_cap[j++];
1550 		policy_mgr_get_hw_mode_params(tmp, &mac0_ss_bw_info);
1551 		dbs_mode = HW_MODE_DBS_NONE;
1552 		sbs_mode = HW_MODE_SBS_NONE;
1553 		emlsr_mode = HW_MODE_EMLSR_NONE;
1554 		mac1_ss_bw_info.mac_tx_stream = 0;
1555 		mac1_ss_bw_info.mac_rx_stream = 0;
1556 		mac1_ss_bw_info.mac_bw = 0;
1557 
1558 		hw_config_type = tmp->hw_mode_config_type;
1559 		if (WMI_BECAP_PHY_GET_HW_MODE_CFG(hw_config_type) ==
1560 		    WMI_HW_MODE_EMLSR)
1561 			hw_config_type = WMI_HW_MODE_EMLSR;
1562 
1563 		policy_mgr_update_mac_freq_info(psoc, pm_ctx,
1564 						hw_config_type,
1565 						tmp->phy_id, tmp);
1566 
1567 		/* SBS and DBS have dual MAC. Upto 2 MACs are considered. */
1568 		if ((hw_config_type == WMI_HW_MODE_DBS) ||
1569 		    (hw_config_type == WMI_HW_MODE_SBS_PASSIVE) ||
1570 		    (hw_config_type == WMI_HW_MODE_SBS) ||
1571 		    (hw_config_type == WMI_HW_MODE_DBS_OR_SBS)) {
1572 			/* Update for MAC1 */
1573 			tmp = &info->mac_phy_cap[j++];
1574 			policy_mgr_get_hw_mode_params(tmp, &mac1_ss_bw_info);
1575 			policy_mgr_update_mac_freq_info(psoc, pm_ctx,
1576 							hw_config_type,
1577 							tmp->phy_id, tmp);
1578 			if (hw_config_type == WMI_HW_MODE_DBS ||
1579 			    hw_config_type == WMI_HW_MODE_DBS_OR_SBS)
1580 				dbs_mode = HW_MODE_DBS;
1581 			if (policy_mgr_sbs_range_present(pm_ctx) &&
1582 			    ((hw_config_type == WMI_HW_MODE_SBS_PASSIVE) ||
1583 			    (hw_config_type == WMI_HW_MODE_SBS) ||
1584 			    (hw_config_type == WMI_HW_MODE_DBS_OR_SBS)))
1585 				sbs_mode = HW_MODE_SBS;
1586 		} else if (hw_config_type == WMI_HW_MODE_EMLSR) {
1587 			/* eMLSR mode */
1588 			tmp = &info->mac_phy_cap[j++];
1589 			cap = &info->mac_phy_caps_ext2[i];
1590 			wlan_mlme_set_eml_params(psoc, cap);
1591 			policy_mgr_get_hw_mode_params(tmp, &mac1_ss_bw_info);
1592 			policy_mgr_update_mac_freq_info(psoc, pm_ctx,
1593 							hw_config_type,
1594 							tmp->phy_id, tmp);
1595 			emlsr_mode = HW_MODE_EMLSR;
1596 		}
1597 
1598 		/* Updating HW mode list */
1599 		policy_mgr_set_hw_mode_params(psoc, mac0_ss_bw_info,
1600 			mac1_ss_bw_info, i, tmp->hw_mode_id, dbs_mode,
1601 			sbs_mode, emlsr_mode);
1602 		/* Update radio combination info */
1603 		policy_mgr_update_radio_combination_matrix(
1604 			psoc, mac0_ss_bw_info, mac1_ss_bw_info,
1605 			dbs_mode, sbs_mode);
1606 	}
1607 
1608 	/*
1609 	 * Initializing Current frequency with SMM frequency.
1610 	 */
1611 	policy_mgr_fill_curr_mac_freq_by_hwmode(pm_ctx, MODE_SMM);
1612 	policy_mgr_dump_freq_range(pm_ctx);
1613 
1614 	return QDF_STATUS_SUCCESS;
1615 }
1616 
1617 QDF_STATUS policy_mgr_update_sbs_freq(struct wlan_objmgr_psoc *psoc,
1618 				      struct target_psoc_info *tgt_hdl)
1619 {
1620 	struct policy_mgr_psoc_priv_obj *pm_ctx;
1621 	struct tgt_info *info;
1622 
1623 	pm_ctx = policy_mgr_get_context(psoc);
1624 	if (!pm_ctx) {
1625 		policy_mgr_err("Invalid Context");
1626 		return QDF_STATUS_E_FAILURE;
1627 	}
1628 
1629 	info = &tgt_hdl->info;
1630 	policy_mgr_debug("sbs_lower_band_end_freq %d",
1631 			 info->sbs_lower_band_end_freq);
1632 	policy_mgr_update_sbs_lowr_band_end_frq(pm_ctx, info);
1633 
1634 	policy_mgr_update_hw_mode_list(psoc, tgt_hdl);
1635 
1636 	return QDF_STATUS_SUCCESS;
1637 }
1638 
1639 qdf_freq_t policy_mgr_get_sbs_cut_off_freq(struct wlan_objmgr_psoc *psoc)
1640 {
1641 	struct policy_mgr_psoc_priv_obj *pm_ctx;
1642 	struct policy_mgr_freq_range *first_mac_range, *second_mac_range;
1643 	qdf_freq_t sbs_cut_off_freq = 0;
1644 
1645 	pm_ctx = policy_mgr_get_context(psoc);
1646 	if (!pm_ctx) {
1647 		policy_mgr_err("Invalid Context");
1648 		return 0;
1649 	}
1650 
1651 	if (pm_ctx->hw_mode.sbs_lower_band_end_freq)
1652 		return pm_ctx->hw_mode.sbs_lower_band_end_freq;
1653 	/*
1654 	 * if cutoff freq is not available from FW (i.e SBS is not dynamic)
1655 	 * get it from SBS freq range
1656 	 */
1657 	first_mac_range = &pm_ctx->hw_mode.freq_range_caps[MODE_SBS][0];
1658 
1659 	second_mac_range =
1660 		&pm_ctx->hw_mode.freq_range_caps[MODE_SBS][1];
1661 
1662 	/*
1663 	 * SBS range is low 5Ghz shared with 2.4Ghz: The low_5Ghz of shared
1664 	 * mac will be starting of 5Ghz and low_5Ghz of non-shared mac will be
1665 	 * the cutoff freq
1666 	 *
1667 	 * SBS range is high 5Ghz shared with 2.4Ghz: The low_5Ghz of shared
1668 	 * mac will be cutoff freq and low_5Ghz of non-shared mac will be
1669 	 * the starting of 5Ghz
1670 	 *
1671 	 * so, maximum of low_5Ghz will be cutoff freq
1672 	 */
1673 	sbs_cut_off_freq = QDF_MAX(second_mac_range->low_5ghz_freq,
1674 				   first_mac_range->low_5ghz_freq) - 1;
1675 	policy_mgr_debug("sbs cutoff freq %d", sbs_cut_off_freq);
1676 
1677 	return sbs_cut_off_freq;
1678 }
1679 
1680 static bool
1681 policy_mgr_2_freq_same_mac_in_freq_range(
1682 				struct policy_mgr_psoc_priv_obj *pm_ctx,
1683 				struct policy_mgr_freq_range *freq_range,
1684 				qdf_freq_t freq_1, qdf_freq_t freq_2)
1685 {
1686 	uint8_t i;
1687 
1688 	for (i = 0; i < MAX_MAC; i++) {
1689 		if (IS_FREQ_ON_MAC_ID(freq_range, freq_1, i) &&
1690 		    IS_FREQ_ON_MAC_ID(freq_range, freq_2, i))
1691 			return true;
1692 	}
1693 
1694 	return false;
1695 }
1696 
1697 bool policy_mgr_can_2ghz_share_low_high_5ghz_sbs(
1698 			struct policy_mgr_psoc_priv_obj *pm_ctx)
1699 {
1700 	if (pm_ctx->hw_mode.sbs_lower_band_end_freq)
1701 		return true;
1702 
1703 	return false;
1704 }
1705 
1706 bool
1707 policy_mgr_sbs_24_shared_with_high_5(struct policy_mgr_psoc_priv_obj *pm_ctx)
1708 {
1709 	qdf_freq_t sbs_cut_off_freq;
1710 	struct policy_mgr_freq_range freq_range;
1711 	uint8_t i = 0;
1712 
1713 	if (policy_mgr_can_2ghz_share_low_high_5ghz_sbs(pm_ctx))
1714 		return true;
1715 
1716 	sbs_cut_off_freq = policy_mgr_get_sbs_cut_off_freq(pm_ctx->psoc);
1717 	if (!sbs_cut_off_freq) {
1718 		policy_mgr_err("Invalid cut off freq");
1719 		return false;
1720 	}
1721 
1722 	for (i = 0; i < MAX_MAC; i++) {
1723 		freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_SBS][i];
1724 		/*
1725 		 * if 5 GHZ start freq of this mac is greater than cutoff
1726 		 * return true
1727 		 */
1728 		if (freq_range.low_2ghz_freq && freq_range.low_5ghz_freq) {
1729 			if  (sbs_cut_off_freq < freq_range.low_5ghz_freq)
1730 				return true;
1731 		}
1732 	}
1733 
1734 	return false;
1735 }
1736 
1737 bool
1738 policy_mgr_sbs_24_shared_with_low_5(struct policy_mgr_psoc_priv_obj *pm_ctx)
1739 {
1740 	qdf_freq_t sbs_cut_off_freq;
1741 	struct policy_mgr_freq_range freq_range;
1742 	uint8_t i = 0;
1743 
1744 	if (policy_mgr_can_2ghz_share_low_high_5ghz_sbs(pm_ctx))
1745 		return true;
1746 
1747 	sbs_cut_off_freq = policy_mgr_get_sbs_cut_off_freq(pm_ctx->psoc);
1748 	if (!sbs_cut_off_freq) {
1749 		policy_mgr_err("Invalid cut off freq");
1750 		return false;
1751 	}
1752 
1753 	for (i = 0; i < MAX_MAC; i++) {
1754 		freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_SBS][i];
1755 		if (freq_range.low_2ghz_freq && freq_range.high_5ghz_freq) {
1756 			/*
1757 			 * if 5 GHZ end freq of this mac is less than cutoff
1758 			 * return true
1759 			 */
1760 			if  (sbs_cut_off_freq > freq_range.high_5ghz_freq)
1761 				return true;
1762 		}
1763 	}
1764 
1765 	return false;
1766 }
1767 
1768 bool
1769 policy_mgr_2_freq_same_mac_in_dbs(struct policy_mgr_psoc_priv_obj *pm_ctx,
1770 				  qdf_freq_t freq_1, qdf_freq_t freq_2)
1771 {
1772 	struct policy_mgr_freq_range *freq_range;
1773 
1774 	/* Return true if non DBS capable HW */
1775 	if (!policy_mgr_is_hw_dbs_capable(pm_ctx->psoc))
1776 		return true;
1777 
1778 	freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
1779 	return policy_mgr_2_freq_same_mac_in_freq_range(pm_ctx, freq_range,
1780 							 freq_1, freq_2);
1781 }
1782 
1783 bool
1784 policy_mgr_2_freq_same_mac_in_sbs(struct policy_mgr_psoc_priv_obj *pm_ctx,
1785 				  qdf_freq_t freq_1, qdf_freq_t freq_2)
1786 {
1787 	struct policy_mgr_freq_range *sbs_low_share;
1788 	struct policy_mgr_freq_range *sbs_uppr_share;
1789 	struct policy_mgr_freq_range *sbs_range;
1790 
1791 	/* Return true if non SBS capable HW */
1792 	if (!policy_mgr_is_hw_sbs_capable(pm_ctx->psoc))
1793 		return true;
1794 
1795 	if (policy_mgr_can_2ghz_share_low_high_5ghz_sbs(pm_ctx)) {
1796 		sbs_uppr_share =
1797 			pm_ctx->hw_mode.freq_range_caps[MODE_SBS_UPPER_SHARE];
1798 		sbs_low_share =
1799 			pm_ctx->hw_mode.freq_range_caps[MODE_SBS_LOWER_SHARE];
1800 		if (policy_mgr_2_freq_same_mac_in_freq_range(pm_ctx,
1801 							     sbs_low_share,
1802 							     freq_1, freq_2) ||
1803 		    policy_mgr_2_freq_same_mac_in_freq_range(pm_ctx,
1804 							     sbs_uppr_share,
1805 							     freq_1, freq_2))
1806 				return true;
1807 
1808 		return false;
1809 	}
1810 
1811 	sbs_range = pm_ctx->hw_mode.freq_range_caps[MODE_SBS];
1812 
1813 	return policy_mgr_2_freq_same_mac_in_freq_range(pm_ctx, sbs_range,
1814 							freq_1, freq_2);
1815 }
1816 
1817 static bool
1818 policy_mgr_is_cur_freq_range_sbs(struct wlan_objmgr_psoc *psoc)
1819 {
1820 	struct policy_mgr_psoc_priv_obj *pm_ctx;
1821 	struct policy_mgr_freq_range *freq_range;
1822 	uint8_t i;
1823 
1824 	pm_ctx = policy_mgr_get_context(psoc);
1825 	if (!pm_ctx)
1826 		return false;
1827 
1828 	/* Check if any of the mac is shared */
1829 	for (i = 0 ; i < MAX_MAC; i++) {
1830 		freq_range = &pm_ctx->hw_mode.cur_mac_freq_range[i];
1831 		if (freq_range->low_2ghz_freq && freq_range->low_5ghz_freq)
1832 			return true;
1833 	}
1834 
1835 	return false;
1836 }
1837 
1838 bool policy_mgr_2_freq_always_on_same_mac(struct wlan_objmgr_psoc *psoc,
1839 					  qdf_freq_t freq_1, qdf_freq_t freq_2)
1840 {
1841 	struct policy_mgr_psoc_priv_obj *pm_ctx;
1842 	bool is_dbs_mode_same_mac = true;
1843 	bool is_sbs_mode_same_mac = true;
1844 
1845 	pm_ctx = policy_mgr_get_context(psoc);
1846 	if (!pm_ctx)
1847 		return false;
1848 
1849 	is_dbs_mode_same_mac =
1850 		policy_mgr_2_freq_same_mac_in_dbs(pm_ctx, freq_1, freq_2);
1851 
1852 	/* if DBS mode leading to same mac, check for SBS mode */
1853 	if (is_dbs_mode_same_mac)
1854 		is_sbs_mode_same_mac =
1855 			policy_mgr_2_freq_same_mac_in_sbs(pm_ctx, freq_1,
1856 							  freq_2);
1857 
1858 	policy_mgr_rl_debug("freq1 %d freq2 %d: Same mac:: DBS:%d SBS:%d",
1859 			    freq_1, freq_2, is_dbs_mode_same_mac,
1860 			    is_sbs_mode_same_mac);
1861 	/*
1862 	 * if in SBS and DBS mode, both is leading to freqs on same mac,
1863 	 * return true else return false.
1864 	 */
1865 	if (is_dbs_mode_same_mac && is_sbs_mode_same_mac)
1866 		return true;
1867 
1868 	return false;
1869 }
1870 
1871 bool policy_mgr_are_2_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
1872 				       qdf_freq_t freq_1,
1873 				       qdf_freq_t  freq_2)
1874 {
1875 	struct policy_mgr_psoc_priv_obj *pm_ctx;
1876 	struct policy_mgr_freq_range *freq_range;
1877 	struct policy_mgr_hw_mode_params hw_mode;
1878 	QDF_STATUS status;
1879 	bool cur_range_sbs = false;
1880 
1881 	pm_ctx = policy_mgr_get_context(psoc);
1882 	if (!pm_ctx)
1883 		return false;
1884 
1885 	/* if HW is not DBS return true*/
1886 	if (!policy_mgr_is_hw_dbs_capable(psoc))
1887 		return true;
1888 
1889 	policy_mgr_rl_debug("freq_1 %d freq_2 %d old_hw_mode_index=%d, new_hw_mode_index=%d",
1890 			    freq_1, freq_2, pm_ctx->old_hw_mode_index,
1891 			    pm_ctx->new_hw_mode_index);
1892 
1893 	/* HW is DBS/SBS capable */
1894 	status = policy_mgr_get_current_hw_mode(psoc, &hw_mode);
1895 	if (!QDF_IS_STATUS_SUCCESS(status)) {
1896 		policy_mgr_err("policy_mgr_get_current_hw_mode failed");
1897 		return false;
1898 	}
1899 
1900 	if (hw_mode.dbs_cap || hw_mode.sbs_cap)
1901 		cur_range_sbs = policy_mgr_is_cur_freq_range_sbs(psoc);
1902 
1903 	policy_mgr_rl_debug("dbs_cap %d sbs_cap %d, cur range is sbs %d",
1904 			    hw_mode.dbs_cap, hw_mode.sbs_cap, cur_range_sbs);
1905 	freq_range = pm_ctx->hw_mode.cur_mac_freq_range;
1906 	/* current HW is DBS OR SBS check current DBS/SBS freq range */
1907 	if (hw_mode.dbs_cap || hw_mode.sbs_cap)
1908 		return policy_mgr_2_freq_same_mac_in_freq_range(pm_ctx,
1909 								freq_range,
1910 								freq_1, freq_2);
1911 
1912 	/*
1913 	 * If current HW mode is not DBS/SBS, check if in all supported mode
1914 	 * it they will be on same mac
1915 	 */
1916 	return policy_mgr_2_freq_always_on_same_mac(psoc, freq_1, freq_2);
1917 }
1918 
1919 static bool
1920 policy_mgr_3_freq_same_mac_in_freq_range(
1921 				struct policy_mgr_psoc_priv_obj *pm_ctx,
1922 				struct policy_mgr_freq_range *freq_range,
1923 				qdf_freq_t freq_1, qdf_freq_t freq_2,
1924 				qdf_freq_t freq_3)
1925 {
1926 	uint8_t i;
1927 
1928 	for (i = 0 ; i < MAX_MAC; i++) {
1929 		if (IS_FREQ_ON_MAC_ID(freq_range, freq_1, i) &&
1930 		    IS_FREQ_ON_MAC_ID(freq_range, freq_2, i) &&
1931 		    IS_FREQ_ON_MAC_ID(freq_range, freq_3, i))
1932 			return true;
1933 	}
1934 
1935 	return false;
1936 }
1937 
1938 static bool
1939 policy_mgr_3_freq_same_mac_in_sbs(struct policy_mgr_psoc_priv_obj *pm_ctx,
1940 				  qdf_freq_t freq_1, qdf_freq_t freq_2,
1941 				  qdf_freq_t freq_3)
1942 {
1943 	struct policy_mgr_freq_range *sbs_low_share;
1944 	struct policy_mgr_freq_range *sbs_uppr_share;
1945 	struct policy_mgr_freq_range *sbs_range;
1946 
1947 	/* Return true if non SBS capable HW */
1948 	if (!policy_mgr_is_hw_sbs_capable(pm_ctx->psoc))
1949 		return true;
1950 
1951 	if (pm_ctx->hw_mode.sbs_lower_band_end_freq) {
1952 		sbs_uppr_share =
1953 			pm_ctx->hw_mode.freq_range_caps[MODE_SBS_UPPER_SHARE];
1954 		sbs_low_share =
1955 			pm_ctx->hw_mode.freq_range_caps[MODE_SBS_LOWER_SHARE];
1956 		if (policy_mgr_3_freq_same_mac_in_freq_range(pm_ctx,
1957 							     sbs_low_share,
1958 							     freq_1, freq_2,
1959 							     freq_3) ||
1960 		    policy_mgr_3_freq_same_mac_in_freq_range(pm_ctx,
1961 							     sbs_uppr_share,
1962 							     freq_1, freq_2,
1963 							     freq_3))
1964 			return true;
1965 
1966 		return false;
1967 	}
1968 
1969 	sbs_range = pm_ctx->hw_mode.freq_range_caps[MODE_SBS];
1970 	return policy_mgr_3_freq_same_mac_in_freq_range(pm_ctx, sbs_range,
1971 							freq_1, freq_2, freq_3);
1972 }
1973 
1974 bool
1975 policy_mgr_3_freq_always_on_same_mac(struct wlan_objmgr_psoc *psoc,
1976 				     qdf_freq_t freq_1, qdf_freq_t freq_2,
1977 				     qdf_freq_t freq_3)
1978 {
1979 	struct policy_mgr_psoc_priv_obj *pm_ctx;
1980 	struct policy_mgr_freq_range *freq_range;
1981 	bool is_dbs_mode_same_mac = true;
1982 	bool is_sbs_mode_same_mac = true;
1983 
1984 	pm_ctx = policy_mgr_get_context(psoc);
1985 	if (!pm_ctx)
1986 		return false;
1987 
1988 	/* if HW is not DBS return true*/
1989 	if (!policy_mgr_is_hw_dbs_capable(psoc))
1990 		return true;
1991 
1992 	/* Check for DBS mode first */
1993 	freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
1994 	is_dbs_mode_same_mac =
1995 		policy_mgr_3_freq_same_mac_in_freq_range(pm_ctx, freq_range,
1996 							 freq_1, freq_2,
1997 							 freq_3);
1998 
1999 	/* if DBS mode leading to same mac, check for SBS mode */
2000 	if (is_dbs_mode_same_mac)
2001 		is_sbs_mode_same_mac =
2002 			policy_mgr_3_freq_same_mac_in_sbs(pm_ctx, freq_1,
2003 							  freq_2, freq_3);
2004 
2005 	policy_mgr_rl_debug("freq1 %d freq2 %d freq3 %d: Same mac:: DBS:%d SBS:%d",
2006 			    freq_1, freq_2, freq_3, is_dbs_mode_same_mac,
2007 			    is_sbs_mode_same_mac);
2008 	/*
2009 	 * if in SBS and DBS mode, both is leading to freqs on same mac,
2010 	 * return true else return false.
2011 	 */
2012 	if (is_dbs_mode_same_mac && is_sbs_mode_same_mac)
2013 		return true;
2014 
2015 	return false;
2016 }
2017 
2018 bool
2019 policy_mgr_are_3_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
2020 				  qdf_freq_t freq_1, qdf_freq_t freq_2,
2021 				  qdf_freq_t freq_3)
2022 {
2023 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2024 	struct policy_mgr_freq_range *freq_range;
2025 	QDF_STATUS status;
2026 	struct policy_mgr_hw_mode_params hw_mode;
2027 	bool cur_range_sbs = false;
2028 
2029 	pm_ctx = policy_mgr_get_context(psoc);
2030 	if (!pm_ctx)
2031 		return false;
2032 
2033 	/* if HW is not DBS return true*/
2034 	if (!policy_mgr_is_hw_dbs_capable(psoc))
2035 		return true;
2036 
2037 	policy_mgr_rl_debug("freq_1 %d freq_2 %d freq_3 %d", freq_1, freq_2,
2038 			    freq_3);
2039 
2040 	/* HW is DBS/SBS capable, get current HW mode */
2041 	status = policy_mgr_get_current_hw_mode(psoc, &hw_mode);
2042 	if (!QDF_IS_STATUS_SUCCESS(status)) {
2043 		policy_mgr_err("policy_mgr_get_current_hw_mode failed");
2044 		return false;
2045 	}
2046 	if (hw_mode.dbs_cap || hw_mode.sbs_cap)
2047 		cur_range_sbs = policy_mgr_is_cur_freq_range_sbs(psoc);
2048 
2049 	policy_mgr_rl_debug("dbs_cap %d sbs_cap %d, cur range is sbs %d",
2050 			    hw_mode.dbs_cap, hw_mode.sbs_cap, cur_range_sbs);
2051 	freq_range = pm_ctx->hw_mode.cur_mac_freq_range;
2052 
2053 	/* current HW is DBS OR SBS check current DBS/SBS freq range */
2054 	if (hw_mode.dbs_cap || hw_mode.sbs_cap)
2055 		return policy_mgr_3_freq_same_mac_in_freq_range(pm_ctx,
2056 							freq_range,
2057 							freq_1, freq_2, freq_3);
2058 	/*
2059 	 * If current HW mode is not DBS/SBS, check if in all supported mode
2060 	 * it they will be on same mac
2061 	 */
2062 	return policy_mgr_3_freq_always_on_same_mac(psoc, freq_1, freq_2,
2063 						    freq_3);
2064 }
2065 
2066 #ifdef FEATURE_FOURTH_CONNECTION
2067 static void
2068 policy_mgr_get_mac_freq_list(struct policy_mgr_freq_range *freq_range,
2069 			     uint8_t mac_id,
2070 			     uint8_t mac_freq_list[MAX_NUMBER_OF_CONC_CONNECTIONS],
2071 			     uint8_t mac_mode_list[MAX_NUMBER_OF_CONC_CONNECTIONS],
2072 			     uint8_t *mac_freq_num,
2073 			     qdf_freq_t freq_1, enum policy_mgr_con_mode mode_1,
2074 			     qdf_freq_t freq_2, enum policy_mgr_con_mode mode_2,
2075 			     qdf_freq_t freq_3, enum policy_mgr_con_mode mode_3,
2076 			     qdf_freq_t freq_4, enum policy_mgr_con_mode mode_4)
2077 {
2078 	uint8_t j = 0;
2079 
2080 	if (freq_1 && IS_FREQ_ON_MAC_ID(freq_range, freq_1, mac_id)) {
2081 		mac_freq_list[j] = freq_1;
2082 		mac_mode_list[j++] = mode_1;
2083 	}
2084 	if (freq_2 && IS_FREQ_ON_MAC_ID(freq_range, freq_2, mac_id)) {
2085 		mac_freq_list[j] = freq_2;
2086 		mac_mode_list[j++] = mode_2;
2087 	}
2088 	if (freq_3 && IS_FREQ_ON_MAC_ID(freq_range, freq_3, mac_id)) {
2089 		mac_freq_list[j] = freq_3;
2090 		mac_mode_list[j++] = mode_3;
2091 	}
2092 	if (freq_4 && IS_FREQ_ON_MAC_ID(freq_range, freq_4, mac_id)) {
2093 		mac_freq_list[j] = freq_4;
2094 		mac_mode_list[j++] = mode_4;
2095 	}
2096 
2097 	*mac_freq_num = j;
2098 }
2099 
2100 static bool
2101 policy_mgr_is_supported_hw_mode(struct wlan_objmgr_psoc *psoc,
2102 				struct policy_mgr_psoc_priv_obj *pm_ctx,
2103 				enum policy_mgr_mode hw_mode)
2104 {
2105 	if (hw_mode == MODE_SMM)
2106 		return true;
2107 
2108 	if (hw_mode == MODE_DBS)
2109 		return policy_mgr_is_hw_dbs_capable(psoc);
2110 
2111 	if (hw_mode == MODE_SBS_UPPER_SHARE ||
2112 	    hw_mode == MODE_SBS_LOWER_SHARE)
2113 		return policy_mgr_is_hw_sbs_capable(psoc) &&
2114 			pm_ctx->hw_mode.sbs_lower_band_end_freq;
2115 
2116 	if (hw_mode == MODE_SBS)
2117 		return policy_mgr_is_hw_sbs_capable(psoc);
2118 
2119 	return false;
2120 }
2121 
2122 static bool
2123 policy_mgr_mac_freq_list_allow(uint8_t mac_freq_list[MAX_NUMBER_OF_CONC_CONNECTIONS],
2124 			       uint8_t mac_mode_list[MAX_NUMBER_OF_CONC_CONNECTIONS],
2125 			       uint8_t mac_freq_num)
2126 {
2127 	uint8_t sta = 0, ap = 0, i;
2128 
2129 	switch (mac_freq_num) {
2130 	case 1:
2131 	case 2:
2132 		return true;
2133 	case 3:
2134 		/* If 3 vifs are active in same mac, target only support:
2135 		 * 3 vifs are in SCC and 3 vifs are :
2136 		 * 1 STA + 2 APs, or 3 APs
2137 		 */
2138 		if (mac_freq_list[0] != mac_freq_list[1] ||
2139 		    mac_freq_list[0] != mac_freq_list[2])
2140 			return false;
2141 		for (i = 0; i < mac_freq_num; i++) {
2142 			if (mac_mode_list[i] == PM_STA_MODE ||
2143 			    mac_mode_list[i] == PM_P2P_CLIENT_MODE)
2144 				sta++;
2145 			else
2146 				ap++;
2147 		}
2148 
2149 		if (sta == 1 && ap == 2)
2150 			return true;
2151 		if (ap == 3)
2152 			return true;
2153 		return false;
2154 	default:
2155 		return false;
2156 	}
2157 }
2158 
2159 #ifdef WLAN_FEATURE_11BE_MLO
2160 static void
2161 policy_mgr_ml_sta_active_freq(struct wlan_objmgr_psoc *psoc,
2162 			      qdf_freq_t ch_freq,
2163 			      enum policy_mgr_con_mode mode,
2164 			      uint32_t ext_flags,
2165 			      qdf_freq_t *ml_sta_link0_freq,
2166 			      qdf_freq_t *ml_sta_link1_freq)
2167 {
2168 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0;
2169 	uint8_t num_active_ml_sta;
2170 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
2171 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
2172 	union conc_ext_flag conc_ext_flags;
2173 
2174 	conc_ext_flags.value = ext_flags;
2175 	/* find the two active ml sta home channels */
2176 	policy_mgr_get_ml_sta_info_psoc(psoc, &num_ml_sta,
2177 					&num_disabled_ml_sta,
2178 					ml_sta_vdev_lst, ml_freq_lst,
2179 					NULL, NULL, NULL);
2180 	if (num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
2181 	    num_disabled_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
2182 	    num_ml_sta <= num_disabled_ml_sta) {
2183 		if (num_ml_sta || num_disabled_ml_sta)
2184 			policy_mgr_rl_debug("unexpected ml sta num %d %d",
2185 					    num_ml_sta, num_disabled_ml_sta);
2186 		return;
2187 	}
2188 	num_active_ml_sta = num_ml_sta;
2189 	if (num_ml_sta >= num_disabled_ml_sta)
2190 		num_active_ml_sta = num_ml_sta - num_disabled_ml_sta;
2191 	if (num_active_ml_sta > 1) {
2192 		*ml_sta_link0_freq = ml_freq_lst[0];
2193 		*ml_sta_link1_freq = ml_freq_lst[1];
2194 	} else if (num_active_ml_sta > 0 && conc_ext_flags.mlo &&
2195 		   mode == PM_STA_MODE) {
2196 		*ml_sta_link0_freq = ml_freq_lst[0];
2197 		*ml_sta_link1_freq = ch_freq;
2198 	}
2199 }
2200 #else
2201 static void
2202 policy_mgr_ml_sta_active_freq(struct wlan_objmgr_psoc *psoc,
2203 			      qdf_freq_t ch_freq,
2204 			      enum policy_mgr_con_mode mode,
2205 			      uint32_t ext_flags,
2206 			      qdf_freq_t *ml_sta_link0_freq,
2207 			      qdf_freq_t *ml_sta_link1_freq)
2208 {
2209 }
2210 #endif
2211 
2212 bool
2213 policy_mgr_allow_4th_new_freq(struct wlan_objmgr_psoc *psoc,
2214 			      qdf_freq_t ch_freq,
2215 			      enum policy_mgr_con_mode mode,
2216 			      uint32_t ext_flags)
2217 {
2218 	struct policy_mgr_conc_connection_info *conn = pm_conc_connection_list;
2219 	uint8_t mac_freq_list[MAX_NUMBER_OF_CONC_CONNECTIONS];
2220 	uint8_t mac_mode_list[MAX_NUMBER_OF_CONC_CONNECTIONS];
2221 	uint8_t mac_freq_num;
2222 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2223 	qdf_freq_t ml_sta_link0_freq = 0;
2224 	qdf_freq_t ml_sta_link1_freq = 0;
2225 	uint8_t i, j;
2226 	struct policy_mgr_freq_range *freq_range;
2227 
2228 	pm_ctx = policy_mgr_get_context(psoc);
2229 	if (!pm_ctx) {
2230 		policy_mgr_err("Invalid Context");
2231 		return false;
2232 	}
2233 
2234 	/* if HW is not DBS return false */
2235 	if (!policy_mgr_is_hw_dbs_capable(psoc))
2236 		return false;
2237 
2238 	/* Find the two active ml sta home channels */
2239 	policy_mgr_ml_sta_active_freq(psoc, ch_freq, mode, ext_flags,
2240 				      &ml_sta_link0_freq,
2241 				      &ml_sta_link1_freq);
2242 
2243 	/* Check if any hw mode can support the 4th channel frequency
2244 	 * and device mode.
2245 	 */
2246 	for (j = 0; j < MODE_HW_MAX; j++) {
2247 		if (!policy_mgr_is_supported_hw_mode(psoc, pm_ctx, j))
2248 			continue;
2249 		freq_range = pm_ctx->hw_mode.freq_range_caps[j];
2250 
2251 		/* If ml sta present, the two links should be in
2252 		 * different mac always. Skip the hw mode which
2253 		 * causes they in same mac.
2254 		 */
2255 		if (ml_sta_link0_freq && ml_sta_link1_freq &&
2256 		    policy_mgr_2_freq_same_mac_in_freq_range(pm_ctx,
2257 							     freq_range,
2258 							     ml_sta_link0_freq,
2259 							     ml_sta_link1_freq))
2260 			continue;
2261 		for (i = 0; i < MAX_MAC; i++) {
2262 			/* Get the freq list which are in the MAC
2263 			 * supported freq range.
2264 			 */
2265 			policy_mgr_get_mac_freq_list(
2266 				freq_range,
2267 				i,
2268 				mac_freq_list, mac_mode_list, &mac_freq_num,
2269 				conn[0].freq, conn[0].mode,
2270 				conn[1].freq, conn[1].mode,
2271 				conn[2].freq, conn[2].mode,
2272 				ch_freq, mode);
2273 
2274 			/* Check the freq & mode list support or not in the
2275 			 * MAC.
2276 			 */
2277 			if (!policy_mgr_mac_freq_list_allow(
2278 				mac_freq_list, mac_mode_list, mac_freq_num))
2279 				break;
2280 		}
2281 
2282 		/* If the frequency/mode combination meet requirement in the
2283 		 * hw mode, then the 4th new ch_freq/mode are allowed to start
2284 		 * in this hw mode.
2285 		 */
2286 		if (i == MAX_MAC) {
2287 			policy_mgr_rl_debug("new freq %d mode %s is allowed in hw mode %s",
2288 					    ch_freq,
2289 					    device_mode_to_string(mode),
2290 					    policy_mgr_hw_mode_to_str(j));
2291 			return true;
2292 		}
2293 	}
2294 	policy_mgr_debug("the 4th new freq %d mode %s is not allowed in any hw mode",
2295 			 ch_freq, device_mode_to_string(mode));
2296 
2297 	return false;
2298 }
2299 #endif
2300 
2301 bool policy_mgr_are_sbs_chan(struct wlan_objmgr_psoc *psoc, qdf_freq_t freq_1,
2302 			     qdf_freq_t freq_2)
2303 {
2304 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2305 
2306 	pm_ctx = policy_mgr_get_context(psoc);
2307 	if (!pm_ctx)
2308 		return false;
2309 
2310 	if (!policy_mgr_is_hw_sbs_capable(psoc))
2311 		return false;
2312 
2313 	if (WLAN_REG_IS_24GHZ_CH_FREQ(freq_1) ||
2314 	    WLAN_REG_IS_24GHZ_CH_FREQ(freq_2))
2315 		return false;
2316 
2317 	return !policy_mgr_2_freq_same_mac_in_sbs(pm_ctx, freq_1, freq_2);
2318 }
2319 
2320 bool policy_mgr_is_current_hwmode_sbs(struct wlan_objmgr_psoc *psoc)
2321 {
2322 	struct policy_mgr_hw_mode_params hw_mode;
2323 
2324 	if (!policy_mgr_is_hw_sbs_capable(psoc))
2325 		return false;
2326 
2327 	if (QDF_STATUS_SUCCESS !=
2328 	    policy_mgr_get_current_hw_mode(psoc, &hw_mode))
2329 		return false;
2330 
2331 	if (hw_mode.sbs_cap && policy_mgr_is_cur_freq_range_sbs(psoc))
2332 		return true;
2333 
2334 	return false;
2335 }
2336 
2337 void policy_mgr_init_dbs_hw_mode(struct wlan_objmgr_psoc *psoc,
2338 		uint32_t num_dbs_hw_modes,
2339 		uint32_t *ev_wlan_dbs_hw_mode_list)
2340 {
2341 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2342 
2343 	pm_ctx = policy_mgr_get_context(psoc);
2344 	if (!pm_ctx) {
2345 		policy_mgr_err("Invalid Context");
2346 		return;
2347 	}
2348 
2349 	pm_ctx->num_dbs_hw_modes = num_dbs_hw_modes;
2350 	pm_ctx->hw_mode.hw_mode_list =
2351 		qdf_mem_malloc(sizeof(*pm_ctx->hw_mode.hw_mode_list) *
2352 		pm_ctx->num_dbs_hw_modes);
2353 	if (!pm_ctx->hw_mode.hw_mode_list) {
2354 		pm_ctx->num_dbs_hw_modes = 0;
2355 		return;
2356 	}
2357 
2358 	qdf_mem_copy(pm_ctx->hw_mode.hw_mode_list,
2359 		ev_wlan_dbs_hw_mode_list,
2360 		(sizeof(*pm_ctx->hw_mode.hw_mode_list) *
2361 		pm_ctx->num_dbs_hw_modes));
2362 
2363 	policy_mgr_dump_dbs_hw_mode(psoc);
2364 }
2365 
2366 void policy_mgr_dump_dbs_hw_mode(struct wlan_objmgr_psoc *psoc)
2367 {
2368 	uint32_t i;
2369 	uint32_t param;
2370 	uint32_t param1;
2371 
2372 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2373 
2374 	pm_ctx = policy_mgr_get_context(psoc);
2375 	if (!pm_ctx) {
2376 		policy_mgr_err("Invalid Context");
2377 		return;
2378 	}
2379 	policy_mgr_debug("old_hw_mode_index=%d, new_hw_mode_index=%d",
2380 			 pm_ctx->old_hw_mode_index, pm_ctx->new_hw_mode_index);
2381 
2382 	for (i = 0; i < pm_ctx->num_dbs_hw_modes; i++) {
2383 		param = pm_ctx->hw_mode.hw_mode_list[i];
2384 		param1 = pm_ctx->hw_mode.hw_mode_list[i] >> 32;
2385 		policy_mgr_debug("[%d] 0x%x 0x%x", i, param, param1);
2386 		policy_mgr_debug("[%d]-MAC0: tx_ss:%d rx_ss:%d bw_idx:%d band_cap:%d",
2387 				 i,
2388 				 POLICY_MGR_HW_MODE_MAC0_TX_STREAMS_GET(param),
2389 				 POLICY_MGR_HW_MODE_MAC0_RX_STREAMS_GET(param),
2390 				 POLICY_MGR_HW_MODE_MAC0_BANDWIDTH_GET(param),
2391 				 POLICY_MGR_HW_MODE_MAC0_BAND_GET(param));
2392 		policy_mgr_debug("[%d]-MAC1: tx_ss:%d rx_ss:%d bw_idx:%d",
2393 				 i,
2394 				 POLICY_MGR_HW_MODE_MAC1_TX_STREAMS_GET(param),
2395 				 POLICY_MGR_HW_MODE_MAC1_RX_STREAMS_GET(param),
2396 				 POLICY_MGR_HW_MODE_MAC1_BANDWIDTH_GET(param));
2397 		policy_mgr_debug("[%d] DBS:%d SBS:%d hw_mode_id:%d", i,
2398 				 POLICY_MGR_HW_MODE_DBS_MODE_GET(param),
2399 				 POLICY_MGR_HW_MODE_SBS_MODE_GET(param),
2400 				 POLICY_MGR_HW_MODE_ID_GET(param));
2401 	}
2402 }
2403 
2404 void policy_mgr_init_dbs_config(struct wlan_objmgr_psoc *psoc,
2405 		uint32_t scan_config, uint32_t fw_config)
2406 {
2407 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2408 	uint8_t dual_mac_feature;
2409 
2410 	pm_ctx = policy_mgr_get_context(psoc);
2411 	if (!pm_ctx) {
2412 		policy_mgr_err("Invalid Context");
2413 		return;
2414 	}
2415 	pm_ctx->dual_mac_cfg.cur_scan_config = 0;
2416 	pm_ctx->dual_mac_cfg.cur_fw_mode_config = 0;
2417 
2418 	dual_mac_feature = pm_ctx->cfg.dual_mac_feature;
2419 	/* If dual mac features are disabled in the INI, we
2420 	 * need not proceed further
2421 	 */
2422 	if (dual_mac_feature == DISABLE_DBS_CXN_AND_SCAN) {
2423 		policy_mgr_err("Disabling dual mac capabilities");
2424 		/* All capabilities are initialized to 0. We can return */
2425 		goto done;
2426 	}
2427 
2428 	/* Initialize concurrent_scan_config_bits with default FW value */
2429 	WMI_DBS_CONC_SCAN_CFG_ASYNC_DBS_SCAN_SET(
2430 		pm_ctx->dual_mac_cfg.cur_scan_config,
2431 		WMI_DBS_CONC_SCAN_CFG_ASYNC_DBS_SCAN_GET(scan_config));
2432 	WMI_DBS_CONC_SCAN_CFG_SYNC_DBS_SCAN_SET(
2433 		pm_ctx->dual_mac_cfg.cur_scan_config,
2434 		WMI_DBS_CONC_SCAN_CFG_SYNC_DBS_SCAN_GET(scan_config));
2435 	WMI_DBS_CONC_SCAN_CFG_DBS_SCAN_SET(
2436 		pm_ctx->dual_mac_cfg.cur_scan_config,
2437 		WMI_DBS_CONC_SCAN_CFG_DBS_SCAN_GET(scan_config));
2438 	WMI_DBS_CONC_SCAN_CFG_AGILE_SCAN_SET(
2439 		pm_ctx->dual_mac_cfg.cur_scan_config,
2440 		WMI_DBS_CONC_SCAN_CFG_AGILE_SCAN_GET(scan_config));
2441 	WMI_DBS_CONC_SCAN_CFG_AGILE_DFS_SCAN_SET(
2442 		pm_ctx->dual_mac_cfg.cur_scan_config,
2443 		WMI_DBS_CONC_SCAN_CFG_AGILE_DFS_SCAN_GET(scan_config));
2444 
2445 	/* Initialize fw_mode_config_bits with default FW value */
2446 	WMI_DBS_FW_MODE_CFG_DBS_SET(
2447 		pm_ctx->dual_mac_cfg.cur_fw_mode_config,
2448 		WMI_DBS_FW_MODE_CFG_DBS_GET(fw_config));
2449 	WMI_DBS_FW_MODE_CFG_AGILE_DFS_SET(
2450 		pm_ctx->dual_mac_cfg.cur_fw_mode_config,
2451 		WMI_DBS_FW_MODE_CFG_AGILE_DFS_GET(fw_config));
2452 	WMI_DBS_FW_MODE_CFG_DBS_FOR_CXN_SET(
2453 		pm_ctx->dual_mac_cfg.cur_fw_mode_config,
2454 		WMI_DBS_FW_MODE_CFG_DBS_FOR_CXN_GET(fw_config));
2455 done:
2456 	/* Initialize the previous scan/fw mode config */
2457 	pm_ctx->dual_mac_cfg.prev_scan_config =
2458 		pm_ctx->dual_mac_cfg.cur_scan_config;
2459 	pm_ctx->dual_mac_cfg.prev_fw_mode_config =
2460 		pm_ctx->dual_mac_cfg.cur_fw_mode_config;
2461 
2462 	policy_mgr_debug("cur_scan_config:%x cur_fw_mode_config:%x",
2463 		pm_ctx->dual_mac_cfg.cur_scan_config,
2464 		pm_ctx->dual_mac_cfg.cur_fw_mode_config);
2465 }
2466 
2467 void policy_mgr_init_sbs_fw_config(struct wlan_objmgr_psoc *psoc,
2468 				   uint32_t fw_config)
2469 {
2470 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2471 	bool sbs_enabled;
2472 
2473 	pm_ctx = policy_mgr_get_context(psoc);
2474 	if (!pm_ctx) {
2475 		policy_mgr_err("Invalid Context");
2476 		return;
2477 	}
2478 
2479 	/*
2480 	 * If SBS is not enabled from ini, no need to set SBS bits in fw config
2481 	 */
2482 	sbs_enabled = pm_ctx->cfg.sbs_enable;
2483 	if (!sbs_enabled) {
2484 		policy_mgr_debug("SBS not enabled from ini");
2485 		return;
2486 	}
2487 
2488 	/* Initialize fw_mode_config_bits with default FW value */
2489 	WMI_DBS_FW_MODE_CFG_ASYNC_SBS_SET(
2490 			pm_ctx->dual_mac_cfg.cur_fw_mode_config,
2491 			WMI_DBS_FW_MODE_CFG_ASYNC_SBS_GET(fw_config));
2492 
2493 	policy_mgr_debug("fw_mode config updated from %x to %x",
2494 			 pm_ctx->dual_mac_cfg.prev_fw_mode_config,
2495 			 pm_ctx->dual_mac_cfg.cur_fw_mode_config);
2496 	/* Initialize the previous scan/fw mode config */
2497 	pm_ctx->dual_mac_cfg.prev_fw_mode_config =
2498 		pm_ctx->dual_mac_cfg.cur_fw_mode_config;
2499 }
2500 
2501 void policy_mgr_update_dbs_scan_config(struct wlan_objmgr_psoc *psoc)
2502 {
2503 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2504 
2505 	pm_ctx = policy_mgr_get_context(psoc);
2506 	if (!pm_ctx) {
2507 		policy_mgr_err("Invalid Context");
2508 		return;
2509 	}
2510 
2511 	pm_ctx->dual_mac_cfg.prev_scan_config =
2512 		pm_ctx->dual_mac_cfg.cur_scan_config;
2513 	pm_ctx->dual_mac_cfg.cur_scan_config =
2514 		pm_ctx->dual_mac_cfg.req_scan_config;
2515 }
2516 
2517 void policy_mgr_update_dbs_fw_config(struct wlan_objmgr_psoc *psoc)
2518 {
2519 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2520 
2521 	pm_ctx = policy_mgr_get_context(psoc);
2522 	if (!pm_ctx) {
2523 		policy_mgr_err("Invalid Context");
2524 		return;
2525 	}
2526 
2527 	pm_ctx->dual_mac_cfg.prev_fw_mode_config =
2528 		pm_ctx->dual_mac_cfg.cur_fw_mode_config;
2529 	pm_ctx->dual_mac_cfg.cur_fw_mode_config =
2530 		pm_ctx->dual_mac_cfg.req_fw_mode_config;
2531 }
2532 
2533 void policy_mgr_update_dbs_req_config(struct wlan_objmgr_psoc *psoc,
2534 		uint32_t scan_config, uint32_t fw_mode_config)
2535 {
2536 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2537 
2538 	pm_ctx = policy_mgr_get_context(psoc);
2539 	if (!pm_ctx) {
2540 		policy_mgr_err("Invalid Context");
2541 		return;
2542 	}
2543 	pm_ctx->dual_mac_cfg.req_scan_config = scan_config;
2544 	pm_ctx->dual_mac_cfg.req_fw_mode_config = fw_mode_config;
2545 }
2546 
2547 bool policy_mgr_get_dbs_plus_agile_scan_config(struct wlan_objmgr_psoc *psoc)
2548 {
2549 	uint32_t scan_config;
2550 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2551 
2552 	if (policy_mgr_is_dual_mac_disabled_in_ini(psoc))
2553 		return false;
2554 
2555 
2556 	pm_ctx = policy_mgr_get_context(psoc);
2557 	if (!pm_ctx) {
2558 		policy_mgr_err("Invalid Context");
2559 		/* We take that it is disabled and proceed */
2560 		return false;
2561 	}
2562 	scan_config = pm_ctx->dual_mac_cfg.cur_scan_config;
2563 
2564 	return WMI_DBS_CONC_SCAN_CFG_AGILE_SCAN_GET(scan_config);
2565 }
2566 
2567 bool policy_mgr_get_single_mac_scan_with_dfs_config(
2568 		struct wlan_objmgr_psoc *psoc)
2569 {
2570 	uint32_t scan_config;
2571 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2572 
2573 	if (policy_mgr_is_dual_mac_disabled_in_ini(psoc))
2574 		return false;
2575 
2576 
2577 	pm_ctx = policy_mgr_get_context(psoc);
2578 	if (!pm_ctx) {
2579 		policy_mgr_err("Invalid Context");
2580 		/* We take that it is disabled and proceed */
2581 		return false;
2582 	}
2583 	scan_config = pm_ctx->dual_mac_cfg.cur_scan_config;
2584 
2585 	return WMI_DBS_CONC_SCAN_CFG_AGILE_DFS_SCAN_GET(scan_config);
2586 }
2587 
2588 int8_t policy_mgr_get_num_dbs_hw_modes(struct wlan_objmgr_psoc *psoc)
2589 {
2590 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2591 
2592 	pm_ctx = policy_mgr_get_context(psoc);
2593 	if (!pm_ctx) {
2594 		policy_mgr_err("Invalid Context");
2595 		return -EINVAL;
2596 	}
2597 	return pm_ctx->num_dbs_hw_modes;
2598 }
2599 
2600 bool policy_mgr_find_if_fw_supports_dbs(struct wlan_objmgr_psoc *psoc)
2601 {
2602 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2603 	struct wmi_unified *wmi_handle;
2604 	bool dbs_support;
2605 
2606 	pm_ctx = policy_mgr_get_context(psoc);
2607 
2608 	if (!pm_ctx) {
2609 		policy_mgr_err("Invalid Context");
2610 		return false;
2611 	}
2612 	wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
2613 	if (!wmi_handle) {
2614 		policy_mgr_debug("Invalid WMI handle");
2615 		return false;
2616 	}
2617 	dbs_support =
2618 	wmi_service_enabled(wmi_handle,
2619 			    wmi_service_dual_band_simultaneous_support);
2620 
2621 	/* The agreement with FW is that: To know if the target is DBS
2622 	 * capable, DBS needs to be supported both in the HW mode list
2623 	 * and in the service ready event
2624 	 */
2625 	if (!dbs_support)
2626 		return false;
2627 
2628 	return true;
2629 }
2630 
2631 bool policy_mgr_find_if_hwlist_has_dbs(struct wlan_objmgr_psoc *psoc)
2632 {
2633 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2634 	uint32_t param, i, found = 0;
2635 
2636 	pm_ctx = policy_mgr_get_context(psoc);
2637 
2638 	if (!pm_ctx) {
2639 		policy_mgr_err("Invalid Context");
2640 		return false;
2641 	}
2642 	for (i = 0; i < pm_ctx->num_dbs_hw_modes; i++) {
2643 		param = pm_ctx->hw_mode.hw_mode_list[i];
2644 		if (POLICY_MGR_HW_MODE_DBS_MODE_GET(param)) {
2645 			found = 1;
2646 			break;
2647 		}
2648 	}
2649 	if (found)
2650 		return true;
2651 
2652 	return false;
2653 }
2654 
2655 static bool policy_mgr_find_if_hwlist_has_sbs(struct wlan_objmgr_psoc *psoc)
2656 {
2657 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2658 	uint32_t param, i;
2659 
2660 	pm_ctx = policy_mgr_get_context(psoc);
2661 
2662 	if (!pm_ctx) {
2663 		policy_mgr_err("Invalid Context");
2664 		return false;
2665 	}
2666 	for (i = 0; i < pm_ctx->num_dbs_hw_modes; i++) {
2667 		param = pm_ctx->hw_mode.hw_mode_list[i];
2668 		if (POLICY_MGR_HW_MODE_SBS_MODE_GET(param)) {
2669 			return true;
2670 		}
2671 	}
2672 
2673 	return false;
2674 }
2675 
2676 bool policy_mgr_is_dbs_scan_allowed(struct wlan_objmgr_psoc *psoc)
2677 {
2678 	uint8_t dbs_type = DISABLE_DBS_CXN_AND_SCAN;
2679 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2680 
2681 	pm_ctx = policy_mgr_get_context(psoc);
2682 	if (!pm_ctx) {
2683 		policy_mgr_err("Invalid Context");
2684 		return false;
2685 	}
2686 
2687 	if (!policy_mgr_find_if_fw_supports_dbs(psoc) ||
2688 	    !policy_mgr_find_if_hwlist_has_dbs(psoc))
2689 		return false;
2690 
2691 	policy_mgr_get_dual_mac_feature(psoc, &dbs_type);
2692 	/*
2693 	 * If DBS support for scan is disabled through INI then DBS is not
2694 	 * supported for scan.
2695 	 *
2696 	 * For DBS scan check the INI value explicitly
2697 	 */
2698 	switch (dbs_type) {
2699 	case DISABLE_DBS_CXN_AND_SCAN:
2700 	case ENABLE_DBS_CXN_AND_DISABLE_DBS_SCAN:
2701 		return false;
2702 	default:
2703 		return true;
2704 	}
2705 }
2706 
2707 bool policy_mgr_is_hw_dbs_capable(struct wlan_objmgr_psoc *psoc)
2708 {
2709 	if (!policy_mgr_is_dbs_enable(psoc))
2710 		return false;
2711 
2712 	if (!policy_mgr_find_if_fw_supports_dbs(psoc))
2713 		return false;
2714 
2715 	if (!policy_mgr_find_if_hwlist_has_dbs(psoc)) {
2716 		policymgr_nofl_debug("HW mode list has no DBS");
2717 		return false;
2718 	}
2719 
2720 	return true;
2721 }
2722 
2723 bool policy_mgr_is_hw_emlsr_capable(struct wlan_objmgr_psoc *psoc)
2724 {
2725 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2726 	uint64_t param, i;
2727 
2728 	pm_ctx = policy_mgr_get_context(psoc);
2729 
2730 	if (!pm_ctx) {
2731 		policy_mgr_err("Invalid Context");
2732 		return false;
2733 	}
2734 	for (i = 0; i < pm_ctx->num_dbs_hw_modes; i++) {
2735 		param = pm_ctx->hw_mode.hw_mode_list[i];
2736 		if (POLICY_MGR_HW_MODE_EMLSR_MODE_GET(param))
2737 			return true;
2738 	}
2739 
2740 	return false;
2741 }
2742 
2743 bool policy_mgr_is_current_hwmode_dbs(struct wlan_objmgr_psoc *psoc)
2744 {
2745 	struct policy_mgr_hw_mode_params hw_mode;
2746 
2747 	if (!policy_mgr_is_hw_dbs_capable(psoc))
2748 		return false;
2749 
2750 	if (QDF_STATUS_SUCCESS != policy_mgr_get_current_hw_mode(psoc,
2751 								 &hw_mode))
2752 		return false;
2753 
2754 	if (!hw_mode.dbs_cap)
2755 		return false;
2756 
2757 	/* sbs is not enabled and dbs_cap is set return true */
2758 	if (!policy_mgr_is_hw_sbs_capable(psoc))
2759 		return true;
2760 
2761 	/* sbs is enabled and dbs_cap is set then check the freq range */
2762 	if (!policy_mgr_is_cur_freq_range_sbs(psoc))
2763 		return true;
2764 
2765 	return false;
2766 }
2767 
2768 bool policy_mgr_is_pcl_weightage_required(struct wlan_objmgr_psoc *psoc)
2769 {
2770 	struct wlan_mlme_psoc_ext_obj *mlme_obj;
2771 	struct dual_sta_policy *dual_sta_policy;
2772 
2773 	mlme_obj = mlme_get_psoc_ext_obj(psoc);
2774 	if (!mlme_obj)
2775 		return true;
2776 
2777 	dual_sta_policy = &mlme_obj->cfg.gen.dual_sta_policy;
2778 
2779 	if (dual_sta_policy->concurrent_sta_policy  ==
2780 		QCA_WLAN_CONCURRENT_STA_POLICY_PREFER_PRIMARY &&
2781 		dual_sta_policy->primary_vdev_id != WLAN_UMAC_VDEV_ID_MAX) {
2782 		policy_mgr_debug("dual_sta_policy : %d, primary_vdev_id:%d",
2783 			dual_sta_policy->concurrent_sta_policy,
2784 			dual_sta_policy->primary_vdev_id);
2785 		return false;
2786 	}
2787 
2788 	return true;
2789 }
2790 
2791 bool policy_mgr_is_interband_mcc_supported(struct wlan_objmgr_psoc *psoc)
2792 {
2793 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2794 	struct wmi_unified *wmi_handle;
2795 
2796 	pm_ctx = policy_mgr_get_context(psoc);
2797 
2798 	if (!pm_ctx) {
2799 		policy_mgr_err("Invalid Context");
2800 		return false;
2801 	}
2802 	wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
2803 	if (!wmi_handle) {
2804 		policy_mgr_debug("Invalid WMI handle");
2805 		return false;
2806 	}
2807 
2808 	return !wmi_service_enabled(wmi_handle,
2809 				    wmi_service_no_interband_mcc_support);
2810 }
2811 
2812 static bool policy_mgr_is_sbs_enable(struct wlan_objmgr_psoc *psoc)
2813 {
2814 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2815 
2816 	pm_ctx = policy_mgr_get_context(psoc);
2817 	if (!pm_ctx) {
2818 		policy_mgr_err("Invalid Context");
2819 		return false;
2820 	}
2821 
2822 	/*
2823 	 * if gEnableSBS is not set then policy_mgr_init_sbs_fw_config won't
2824 	 * enable Async SBS fw config bit
2825 	 */
2826 	if (WMI_DBS_FW_MODE_CFG_ASYNC_SBS_GET(
2827 			pm_ctx->dual_mac_cfg.cur_fw_mode_config))
2828 		return true;
2829 
2830 	return false;
2831 }
2832 
2833 bool policy_mgr_is_hw_sbs_capable(struct wlan_objmgr_psoc *psoc)
2834 {
2835 	if (!policy_mgr_is_sbs_enable(psoc)) {
2836 		policy_mgr_rl_debug("SBS INI is disabled");
2837 		return false;
2838 	}
2839 
2840 	if (!policy_mgr_find_if_fw_supports_dbs(psoc)) {
2841 		policy_mgr_rl_debug("fw doesn't support dual band");
2842 		return false;
2843 	}
2844 
2845 	if (!policy_mgr_find_if_hwlist_has_sbs(psoc)) {
2846 		policy_mgr_rl_debug("HW mode list has no SBS");
2847 		return false;
2848 	}
2849 
2850 	return true;
2851 }
2852 
2853 QDF_STATUS policy_mgr_get_dbs_hw_modes(struct wlan_objmgr_psoc *psoc,
2854 		bool *one_by_one_dbs, bool *two_by_two_dbs)
2855 {
2856 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2857 	uint32_t i;
2858 	int8_t found_one_by_one = -EINVAL, found_two_by_two = -EINVAL;
2859 	uint32_t conf1_tx_ss, conf1_rx_ss;
2860 	uint32_t conf2_tx_ss, conf2_rx_ss;
2861 
2862 	*one_by_one_dbs = false;
2863 	*two_by_two_dbs = false;
2864 
2865 	if (policy_mgr_is_hw_dbs_capable(psoc) == false) {
2866 		policy_mgr_rl_debug("HW is not DBS capable");
2867 		/* Caller will understand that DBS is disabled */
2868 		return QDF_STATUS_SUCCESS;
2869 
2870 	}
2871 
2872 	pm_ctx = policy_mgr_get_context(psoc);
2873 	if (!pm_ctx) {
2874 		policy_mgr_err("Invalid Context");
2875 		return QDF_STATUS_E_FAILURE;
2876 	}
2877 
2878 	/* To check 1x1 capability */
2879 	policy_mgr_get_tx_rx_ss_from_config(HW_MODE_SS_1x1,
2880 			&conf1_tx_ss, &conf1_rx_ss);
2881 	/* To check 2x2 capability */
2882 	policy_mgr_get_tx_rx_ss_from_config(HW_MODE_SS_2x2,
2883 			&conf2_tx_ss, &conf2_rx_ss);
2884 
2885 	for (i = 0; i < pm_ctx->num_dbs_hw_modes; i++) {
2886 		uint32_t t_conf0_tx_ss, t_conf0_rx_ss;
2887 		uint32_t t_conf1_tx_ss, t_conf1_rx_ss;
2888 		uint32_t dbs_mode;
2889 
2890 		t_conf0_tx_ss = POLICY_MGR_HW_MODE_MAC0_TX_STREAMS_GET(
2891 				pm_ctx->hw_mode.hw_mode_list[i]);
2892 		t_conf0_rx_ss = POLICY_MGR_HW_MODE_MAC0_RX_STREAMS_GET(
2893 				pm_ctx->hw_mode.hw_mode_list[i]);
2894 		t_conf1_tx_ss = POLICY_MGR_HW_MODE_MAC1_TX_STREAMS_GET(
2895 				pm_ctx->hw_mode.hw_mode_list[i]);
2896 		t_conf1_rx_ss = POLICY_MGR_HW_MODE_MAC1_RX_STREAMS_GET(
2897 				pm_ctx->hw_mode.hw_mode_list[i]);
2898 		dbs_mode = POLICY_MGR_HW_MODE_DBS_MODE_GET(
2899 				pm_ctx->hw_mode.hw_mode_list[i]);
2900 
2901 		if (((((t_conf0_tx_ss == conf1_tx_ss) &&
2902 		    (t_conf0_rx_ss == conf1_rx_ss)) ||
2903 		    ((t_conf1_tx_ss == conf1_tx_ss) &&
2904 		    (t_conf1_rx_ss == conf1_rx_ss))) &&
2905 		    (dbs_mode == HW_MODE_DBS)) &&
2906 		    (found_one_by_one < 0)) {
2907 			found_one_by_one = i;
2908 			policy_mgr_debug("1x1 hw_mode index %d found", i);
2909 			/* Once an entry is found, need not check for 1x1
2910 			 * again
2911 			 */
2912 			continue;
2913 		}
2914 
2915 		if (((((t_conf0_tx_ss == conf2_tx_ss) &&
2916 		    (t_conf0_rx_ss == conf2_rx_ss)) ||
2917 		    ((t_conf1_tx_ss == conf2_tx_ss) &&
2918 		    (t_conf1_rx_ss == conf2_rx_ss))) &&
2919 		    (dbs_mode == HW_MODE_DBS)) &&
2920 		    (found_two_by_two < 0)) {
2921 			found_two_by_two = i;
2922 			policy_mgr_debug("2x2 hw_mode index %d found", i);
2923 			/* Once an entry is found, need not check for 2x2
2924 			 * again
2925 			 */
2926 			continue;
2927 		}
2928 	}
2929 
2930 	if (found_one_by_one >= 0)
2931 		*one_by_one_dbs = true;
2932 	if (found_two_by_two >= 0)
2933 		*two_by_two_dbs = true;
2934 
2935 	return QDF_STATUS_SUCCESS;
2936 }
2937 
2938 QDF_STATUS policy_mgr_get_current_hw_mode(struct wlan_objmgr_psoc *psoc,
2939 		struct policy_mgr_hw_mode_params *hw_mode)
2940 {
2941 	QDF_STATUS status;
2942 	uint32_t old_hw_index = 0, new_hw_index = 0;
2943 
2944 	status = policy_mgr_get_old_and_new_hw_index(psoc, &old_hw_index,
2945 			&new_hw_index);
2946 	if (QDF_STATUS_SUCCESS != status) {
2947 		policy_mgr_err("Failed to get HW mode index");
2948 		return QDF_STATUS_E_FAILURE;
2949 	}
2950 
2951 	if (new_hw_index == POLICY_MGR_DEFAULT_HW_MODE_INDEX) {
2952 		policy_mgr_err("HW mode is not yet initialized");
2953 		return QDF_STATUS_E_FAILURE;
2954 	}
2955 
2956 	status = policy_mgr_get_hw_mode_from_idx(psoc, new_hw_index, hw_mode);
2957 	if (QDF_STATUS_SUCCESS != status) {
2958 		policy_mgr_err("Failed to get HW mode index");
2959 		return QDF_STATUS_E_FAILURE;
2960 	}
2961 	return QDF_STATUS_SUCCESS;
2962 }
2963 
2964 bool policy_mgr_is_dbs_enable(struct wlan_objmgr_psoc *psoc)
2965 {
2966 	struct policy_mgr_psoc_priv_obj *pm_ctx;
2967 
2968 	if (policy_mgr_is_dual_mac_disabled_in_ini(psoc)) {
2969 		policy_mgr_rl_debug("DBS is disabled from ini");
2970 		return false;
2971 	}
2972 
2973 	pm_ctx = policy_mgr_get_context(psoc);
2974 	if (!pm_ctx) {
2975 		policy_mgr_err("Invalid Context");
2976 		return false;
2977 	}
2978 
2979 	if (WMI_DBS_FW_MODE_CFG_DBS_GET(
2980 			pm_ctx->dual_mac_cfg.cur_fw_mode_config))
2981 		return true;
2982 
2983 	return false;
2984 }
2985 
2986 bool policy_mgr_is_hw_dbs_2x2_capable(struct wlan_objmgr_psoc *psoc)
2987 {
2988 	struct dbs_nss nss_dbs = {0};
2989 	uint32_t nss;
2990 
2991 	nss = policy_mgr_get_hw_dbs_nss(psoc, &nss_dbs);
2992 	if (nss >= HW_MODE_SS_2x2 && (nss_dbs.mac0_ss == nss_dbs.mac1_ss))
2993 		return true;
2994 	else
2995 		return false;
2996 }
2997 
2998 bool policy_mgr_is_hw_dbs_required_for_band(struct wlan_objmgr_psoc *psoc,
2999 					    enum hw_mode_mac_band_cap band)
3000 {
3001 	struct dbs_nss nss_dbs = {0};
3002 	uint32_t nss;
3003 
3004 	nss = policy_mgr_get_hw_dbs_nss(psoc, &nss_dbs);
3005 	if (nss >= HW_MODE_SS_1x1 && nss_dbs.mac0_ss >= nss_dbs.mac1_ss &&
3006 	    !(nss_dbs.single_mac0_band_cap & band))
3007 		return true;
3008 	else
3009 		return false;
3010 }
3011 
3012 bool policy_mgr_is_dp_hw_dbs_capable(struct wlan_objmgr_psoc *psoc)
3013 {
3014 	return policy_mgr_find_if_hwlist_has_dbs(psoc);
3015 }
3016 
3017 /*
3018  * policy_mgr_is_2x2_1x1_dbs_capable() - check 2x2+1x1 DBS supported or not
3019  * @psoc: PSOC object data
3020  *
3021  * This routine is called to check 2x2 5G + 1x1 2G (DBS1) or
3022  * 2x2 2G + 1x1 5G (DBS2) support or not.
3023  * Either DBS1 or DBS2 supported
3024  *
3025  * Return: true/false
3026  */
3027 bool policy_mgr_is_2x2_1x1_dbs_capable(struct wlan_objmgr_psoc *psoc)
3028 {
3029 	struct dbs_nss nss_dbs;
3030 	uint32_t nss;
3031 
3032 	nss = policy_mgr_get_hw_dbs_nss(psoc, &nss_dbs);
3033 	if (nss >= HW_MODE_SS_2x2 && (nss_dbs.mac0_ss > nss_dbs.mac1_ss))
3034 		return true;
3035 	else
3036 		return false;
3037 }
3038 
3039 /*
3040  * policy_mgr_is_2x2_5G_1x1_2G_dbs_capable() - check Genoa DBS1 enabled or not
3041  * @psoc: PSOC object data
3042  *
3043  * This routine is called to check support DBS1 or not.
3044  * Notes: DBS1: 2x2 5G + 1x1 2G.
3045  * This function will call policy_mgr_get_hw_mode_idx_from_dbs_hw_list to match
3046  * the HW mode from hw mode list. The parameters will also be matched to
3047  * 2x2 5G +2x2 2G HW mode. But firmware will not report 2x2 5G + 2x2 2G alone
3048  * with 2x2 5G + 1x1 2G at same time. So, it is safe to find DBS1 with
3049  * policy_mgr_get_hw_mode_idx_from_dbs_hw_list.
3050  *
3051  * Return: true/false
3052  */
3053 bool policy_mgr_is_2x2_5G_1x1_2G_dbs_capable(struct wlan_objmgr_psoc *psoc)
3054 {
3055 	return policy_mgr_is_2x2_1x1_dbs_capable(psoc) &&
3056 		(policy_mgr_get_hw_mode_idx_from_dbs_hw_list(
3057 					psoc,
3058 					HW_MODE_SS_2x2,
3059 					HW_MODE_80_MHZ,
3060 					HW_MODE_SS_1x1, HW_MODE_40_MHZ,
3061 					HW_MODE_MAC_BAND_5G,
3062 					HW_MODE_DBS,
3063 					HW_MODE_AGILE_DFS_NONE,
3064 					HW_MODE_SBS_NONE) >= 0);
3065 }
3066 
3067 /*
3068  * policy_mgr_is_2x2_2G_1x1_5G_dbs_capable() - check Genoa DBS2 enabled or not
3069  * @psoc: PSOC object data
3070  *
3071  * This routine is called to check support DBS2 or not.
3072  * Notes: DBS2: 2x2 2G + 1x1 5G
3073  *
3074  * Return: true/false
3075  */
3076 bool policy_mgr_is_2x2_2G_1x1_5G_dbs_capable(struct wlan_objmgr_psoc *psoc)
3077 {
3078 	return policy_mgr_is_2x2_1x1_dbs_capable(psoc) &&
3079 		(policy_mgr_get_hw_mode_idx_from_dbs_hw_list(
3080 					psoc,
3081 					HW_MODE_SS_2x2,
3082 					HW_MODE_40_MHZ,
3083 					HW_MODE_SS_1x1, HW_MODE_40_MHZ,
3084 					HW_MODE_MAC_BAND_2G,
3085 					HW_MODE_DBS,
3086 					HW_MODE_AGILE_DFS_NONE,
3087 					HW_MODE_SBS_NONE) >= 0);
3088 }
3089 
3090 uint32_t policy_mgr_get_connection_count(struct wlan_objmgr_psoc *psoc)
3091 {
3092 	uint32_t conn_index, count = 0;
3093 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3094 
3095 	pm_ctx = policy_mgr_get_context(psoc);
3096 	if (!pm_ctx) {
3097 		policy_mgr_err("Invalid Context");
3098 		return count;
3099 	}
3100 
3101 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3102 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
3103 		conn_index++) {
3104 		if (pm_conc_connection_list[conn_index].in_use)
3105 			count++;
3106 	}
3107 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3108 
3109 	return count;
3110 }
3111 
3112 uint32_t
3113 policy_mgr_get_connection_count_with_mlo(struct wlan_objmgr_psoc *psoc)
3114 {
3115 	uint32_t conn_index, count = 0;
3116 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3117 	enum policy_mgr_con_mode mode;
3118 	bool is_mlo = false, count_mlo = false;
3119 
3120 	pm_ctx = policy_mgr_get_context(psoc);
3121 	if (!pm_ctx) {
3122 		policy_mgr_err("Invalid Context");
3123 		return count;
3124 	}
3125 
3126 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3127 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
3128 		conn_index++) {
3129 		if (pm_conc_connection_list[conn_index].in_use) {
3130 			is_mlo = policy_mgr_is_ml_vdev_id(psoc,
3131 				   pm_conc_connection_list[conn_index].vdev_id);
3132 			mode = pm_conc_connection_list[conn_index].mode;
3133 			if (is_mlo && (mode == PM_STA_MODE)) {
3134 				if (!count_mlo) {
3135 					count_mlo = true;
3136 					count++;
3137 				}
3138 			} else {
3139 				count++;
3140 			}
3141 		}
3142 	}
3143 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3144 
3145 	return count;
3146 }
3147 
3148 uint32_t policy_mgr_mode_specific_vdev_id(struct wlan_objmgr_psoc *psoc,
3149 					  enum policy_mgr_con_mode mode)
3150 {
3151 	uint32_t conn_index = 0;
3152 	uint32_t vdev_id = WLAN_INVALID_VDEV_ID;
3153 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3154 
3155 	pm_ctx = policy_mgr_get_context(psoc);
3156 	if (!pm_ctx) {
3157 		policy_mgr_err("Invalid Context");
3158 		return vdev_id;
3159 	}
3160 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3161 	/*
3162 	 * Note: This gives you the first vdev id of the mode type in a
3163 	 * sta+sta or sap+sap or p2p + p2p case
3164 	 */
3165 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
3166 		conn_index++) {
3167 		if ((pm_conc_connection_list[conn_index].mode == mode) &&
3168 			pm_conc_connection_list[conn_index].in_use) {
3169 			vdev_id = pm_conc_connection_list[conn_index].vdev_id;
3170 			break;
3171 		}
3172 	}
3173 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3174 
3175 	return vdev_id;
3176 }
3177 
3178 uint32_t policy_mgr_mode_get_macid_by_vdev_id(struct wlan_objmgr_psoc *psoc,
3179 					      uint32_t vdev_id)
3180 {
3181 	uint32_t conn_index = 0;
3182 	uint32_t mac_id = 0xFF;
3183 	enum policy_mgr_con_mode mode;
3184 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3185 
3186 	pm_ctx = policy_mgr_get_context(psoc);
3187 	if (!pm_ctx) {
3188 		policy_mgr_err("Invalid Context");
3189 		return vdev_id;
3190 	}
3191 	mode = policy_mgr_con_mode_by_vdev_id(psoc, vdev_id);
3192 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3193 
3194 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
3195 		conn_index++) {
3196 		if ((pm_conc_connection_list[conn_index].mode == mode) &&
3197 		    pm_conc_connection_list[conn_index].in_use &&
3198 		    vdev_id == pm_conc_connection_list[conn_index].vdev_id) {
3199 			mac_id = pm_conc_connection_list[conn_index].mac;
3200 			break;
3201 		}
3202 	}
3203 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3204 
3205 	return mac_id;
3206 }
3207 
3208 uint32_t policy_mgr_mode_specific_connection_count(
3209 		struct wlan_objmgr_psoc *psoc,
3210 		enum policy_mgr_con_mode mode,
3211 		uint32_t *list)
3212 {
3213 	uint32_t conn_index = 0, count = 0;
3214 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3215 
3216 	pm_ctx = policy_mgr_get_context(psoc);
3217 	if (!pm_ctx) {
3218 		policy_mgr_err("Invalid Context");
3219 		return count;
3220 	}
3221 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3222 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
3223 		conn_index++) {
3224 		if ((pm_conc_connection_list[conn_index].mode == mode) &&
3225 			pm_conc_connection_list[conn_index].in_use) {
3226 			if (list)
3227 				list[count] = conn_index;
3228 			 count++;
3229 		}
3230 	}
3231 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3232 
3233 	return count;
3234 }
3235 
3236 uint32_t policy_mgr_get_sap_mode_count(struct wlan_objmgr_psoc *psoc,
3237 				       uint32_t *list)
3238 {
3239 	uint32_t count;
3240 
3241 	count = policy_mgr_mode_specific_connection_count(psoc, PM_SAP_MODE,
3242 							  list);
3243 
3244 	count += policy_mgr_mode_specific_connection_count(
3245 						psoc,
3246 						PM_LL_LT_SAP_MODE,
3247 						list ? &list[count] : NULL);
3248 	return count;
3249 }
3250 
3251 uint32_t policy_mgr_get_beaconing_mode_count(struct wlan_objmgr_psoc *psoc,
3252 					     uint32_t *list)
3253 {
3254 	uint32_t count;
3255 
3256 	count = policy_mgr_get_sap_mode_count(psoc, list);
3257 
3258 	count += policy_mgr_mode_specific_connection_count(
3259 						psoc,
3260 						PM_P2P_GO_MODE,
3261 						list ? &list[count] : NULL);
3262 	return count;
3263 }
3264 
3265 QDF_STATUS policy_mgr_check_conn_with_mode_and_vdev_id(
3266 		struct wlan_objmgr_psoc *psoc, enum policy_mgr_con_mode mode,
3267 		uint32_t vdev_id)
3268 {
3269 	QDF_STATUS qdf_status = QDF_STATUS_E_FAILURE;
3270 	uint32_t conn_index = 0;
3271 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3272 
3273 	pm_ctx = policy_mgr_get_context(psoc);
3274 	if (!pm_ctx) {
3275 		policy_mgr_err("Invalid Context");
3276 		return qdf_status;
3277 	}
3278 
3279 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3280 	while (PM_CONC_CONNECTION_LIST_VALID_INDEX(conn_index)) {
3281 		if ((pm_conc_connection_list[conn_index].mode == mode) &&
3282 		    (pm_conc_connection_list[conn_index].vdev_id == vdev_id)) {
3283 			qdf_status = QDF_STATUS_SUCCESS;
3284 			break;
3285 		}
3286 		conn_index++;
3287 	}
3288 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3289 	return qdf_status;
3290 }
3291 
3292 void policy_mgr_soc_set_dual_mac_cfg_cb(enum set_hw_mode_status status,
3293 		uint32_t scan_config,
3294 		uint32_t fw_mode_config)
3295 {
3296 	policy_mgr_debug("Status:%d for scan_config:%x fw_mode_config:%x",
3297 			 status, scan_config, fw_mode_config);
3298 }
3299 
3300 void policy_mgr_set_dual_mac_scan_config(struct wlan_objmgr_psoc *psoc,
3301 		uint8_t dbs_val,
3302 		uint8_t dbs_plus_agile_scan_val,
3303 		uint8_t single_mac_scan_with_dbs_val)
3304 {
3305 	struct policy_mgr_dual_mac_config cfg;
3306 	QDF_STATUS status;
3307 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3308 
3309 	pm_ctx = policy_mgr_get_context(psoc);
3310 	if (!pm_ctx) {
3311 		policy_mgr_err("Invalid Context");
3312 		return;
3313 	}
3314 
3315 	/* Any non-zero positive value is treated as 1 */
3316 	if (dbs_val != 0)
3317 		dbs_val = 1;
3318 	if (dbs_plus_agile_scan_val != 0)
3319 		dbs_plus_agile_scan_val = 1;
3320 	if (single_mac_scan_with_dbs_val != 0)
3321 		single_mac_scan_with_dbs_val = 1;
3322 
3323 	status = policy_mgr_get_updated_scan_config(psoc, &cfg.scan_config,
3324 			dbs_val,
3325 			dbs_plus_agile_scan_val,
3326 			single_mac_scan_with_dbs_val);
3327 	if (status != QDF_STATUS_SUCCESS) {
3328 		policy_mgr_err("policy_mgr_get_updated_scan_config failed %d",
3329 			status);
3330 		return;
3331 	}
3332 
3333 	status = policy_mgr_get_updated_fw_mode_config(psoc,
3334 			&cfg.fw_mode_config,
3335 			policy_mgr_get_dbs_config(psoc),
3336 			policy_mgr_get_agile_dfs_config(psoc));
3337 	if (status != QDF_STATUS_SUCCESS) {
3338 		policy_mgr_err("policy_mgr_get_updated_fw_mode_config failed %d",
3339 			status);
3340 		return;
3341 	}
3342 
3343 	cfg.set_dual_mac_cb = policy_mgr_soc_set_dual_mac_cfg_cb;
3344 
3345 	policy_mgr_debug("scan_config:%x fw_mode_config:%x",
3346 			cfg.scan_config, cfg.fw_mode_config);
3347 
3348 	status = pm_ctx->sme_cbacks.sme_soc_set_dual_mac_config(cfg);
3349 	if (status != QDF_STATUS_SUCCESS)
3350 		policy_mgr_err("sme_soc_set_dual_mac_config failed %d", status);
3351 }
3352 
3353 void policy_mgr_set_dual_mac_fw_mode_config(struct wlan_objmgr_psoc *psoc,
3354 			uint8_t dbs, uint8_t dfs)
3355 {
3356 	struct policy_mgr_dual_mac_config cfg;
3357 	QDF_STATUS status;
3358 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3359 
3360 	pm_ctx = policy_mgr_get_context(psoc);
3361 	if (!pm_ctx) {
3362 		policy_mgr_err("Invalid Context");
3363 		return;
3364 	}
3365 
3366 	/* Any non-zero positive value is treated as 1 */
3367 	if (dbs != 0)
3368 		dbs = 1;
3369 	if (dfs != 0)
3370 		dfs = 1;
3371 
3372 	status = policy_mgr_get_updated_scan_config(psoc, &cfg.scan_config,
3373 			policy_mgr_get_dbs_scan_config(psoc),
3374 			policy_mgr_get_dbs_plus_agile_scan_config(psoc),
3375 			policy_mgr_get_single_mac_scan_with_dfs_config(psoc));
3376 	if (status != QDF_STATUS_SUCCESS) {
3377 		policy_mgr_err("policy_mgr_get_updated_scan_config failed %d",
3378 			status);
3379 		return;
3380 	}
3381 
3382 	status = policy_mgr_get_updated_fw_mode_config(psoc,
3383 				&cfg.fw_mode_config, dbs, dfs);
3384 	if (status != QDF_STATUS_SUCCESS) {
3385 		policy_mgr_err("policy_mgr_get_updated_fw_mode_config failed %d",
3386 			status);
3387 		return;
3388 	}
3389 
3390 	cfg.set_dual_mac_cb = policy_mgr_soc_set_dual_mac_cfg_cb;
3391 
3392 	policy_mgr_debug("scan_config:%x fw_mode_config:%x",
3393 			cfg.scan_config, cfg.fw_mode_config);
3394 
3395 	status = pm_ctx->sme_cbacks.sme_soc_set_dual_mac_config(cfg);
3396 	if (status != QDF_STATUS_SUCCESS)
3397 		policy_mgr_err("sme_soc_set_dual_mac_config failed %d", status);
3398 }
3399 
3400 bool policy_mgr_is_scc_with_this_vdev_id(struct wlan_objmgr_psoc *psoc,
3401 					 uint8_t vdev_id)
3402 {
3403 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3404 	uint32_t i, ch_freq;
3405 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
3406 
3407 	pm_ctx = policy_mgr_get_context(psoc);
3408 	if (!pm_ctx) {
3409 		policy_mgr_err("Invalid Context");
3410 		return false;
3411 	}
3412 
3413 	/* Get the channel freq for a given vdev_id */
3414 	status = policy_mgr_get_chan_by_session_id(psoc, vdev_id,
3415 						   &ch_freq);
3416 	if (QDF_IS_STATUS_ERROR(status)) {
3417 		policy_mgr_err("Failed to get channel for vdev:%d", vdev_id);
3418 		return false;
3419 	}
3420 
3421 	/* Compare given vdev_id freq against other vdev_id's */
3422 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3423 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
3424 		if ((pm_conc_connection_list[i].vdev_id != vdev_id) &&
3425 		    (pm_conc_connection_list[i].in_use) &&
3426 		    (pm_conc_connection_list[i].freq == ch_freq)) {
3427 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3428 			return true;
3429 		}
3430 	}
3431 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3432 
3433 	return false;
3434 }
3435 
3436 bool policy_mgr_is_mcc_with_this_vdev_id(struct wlan_objmgr_psoc *psoc,
3437 					 uint8_t vdev_id, uint8_t *mcc_vdev_id)
3438 {
3439 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3440 	uint32_t i, ch_freq;
3441 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
3442 
3443 	if (mcc_vdev_id)
3444 		*mcc_vdev_id = WLAN_INVALID_VDEV_ID;
3445 
3446 	pm_ctx = policy_mgr_get_context(psoc);
3447 	if (!pm_ctx) {
3448 		policy_mgr_err("Invalid Context");
3449 		return false;
3450 	}
3451 
3452 	/* Get the channel freq for a given vdev_id */
3453 	status = policy_mgr_get_chan_by_session_id(psoc, vdev_id, &ch_freq);
3454 	if (QDF_IS_STATUS_ERROR(status)) {
3455 		policy_mgr_err("Failed to get channel for vdev:%d", vdev_id);
3456 		return false;
3457 	}
3458 
3459 	/* Compare given vdev_id freq against other vdev_id's */
3460 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3461 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
3462 		if (pm_conc_connection_list[i].vdev_id == vdev_id)
3463 			continue;
3464 
3465 		if (!pm_conc_connection_list[i].in_use)
3466 			continue;
3467 
3468 		if (pm_conc_connection_list[i].freq != ch_freq &&
3469 		    policy_mgr_are_2_freq_on_same_mac(psoc,
3470 						      pm_conc_connection_list[i].freq,
3471 						      ch_freq)) {
3472 			if (mcc_vdev_id)
3473 				*mcc_vdev_id = pm_conc_connection_list[i].vdev_id;
3474 
3475 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3476 			return true;
3477 		}
3478 	}
3479 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3480 
3481 	return false;
3482 }
3483 
3484 bool policy_mgr_is_mcc_on_any_sta_vdev(struct wlan_objmgr_psoc *psoc)
3485 {
3486 	uint8_t connection_count, i;
3487 	uint8_t vdev_id_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
3488 
3489 	connection_count =
3490 		policy_mgr_get_mode_specific_conn_info(psoc, NULL, vdev_id_list,
3491 						       PM_STA_MODE);
3492 	if (!connection_count)
3493 		return false;
3494 
3495 	for (i = 0; i < connection_count; i++)
3496 		if (policy_mgr_is_mcc_with_this_vdev_id(psoc, vdev_id_list[i],
3497 							NULL))
3498 			return true;
3499 
3500 	return false;
3501 }
3502 
3503 bool policy_mgr_current_concurrency_is_scc(struct wlan_objmgr_psoc *psoc)
3504 {
3505 	uint32_t num_connections = 0;
3506 	bool is_scc = false;
3507 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3508 
3509 	pm_ctx = policy_mgr_get_context(psoc);
3510 	if (!pm_ctx) {
3511 		policy_mgr_err("Invalid Context");
3512 		return is_scc;
3513 	}
3514 
3515 	num_connections = policy_mgr_get_connection_count(psoc);
3516 
3517 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3518 	switch (num_connections) {
3519 	case 1:
3520 		break;
3521 	case 2:
3522 		if (pm_conc_connection_list[0].freq ==
3523 		    pm_conc_connection_list[1].freq &&
3524 		    policy_mgr_are_2_freq_on_same_mac(psoc,
3525 			pm_conc_connection_list[0].freq,
3526 			pm_conc_connection_list[1].freq))
3527 			is_scc = true;
3528 		break;
3529 	case 3:
3530 		/*
3531 		 * In DBS/SBS mode 2 freq are different and on different mac.
3532 		 * Thus if any of 2 freq are same that mean one of the MAC is
3533 		 * in SCC.
3534 		 * For non DBS/SBS, if all 3 freq are same then its SCC
3535 		 */
3536 		if ((policy_mgr_is_current_hwmode_dbs(psoc) ||
3537 		     policy_mgr_is_current_hwmode_sbs(psoc)) &&
3538 		    (pm_conc_connection_list[0].freq ==
3539 		     pm_conc_connection_list[1].freq ||
3540 		     pm_conc_connection_list[0].freq ==
3541 		     pm_conc_connection_list[2].freq ||
3542 		     pm_conc_connection_list[1].freq ==
3543 		     pm_conc_connection_list[2].freq))
3544 			is_scc = true;
3545 		else if ((pm_conc_connection_list[0].freq ==
3546 			  pm_conc_connection_list[1].freq) &&
3547 			 (pm_conc_connection_list[0].freq ==
3548 			  pm_conc_connection_list[2].freq))
3549 			is_scc = true;
3550 
3551 		break;
3552 	default:
3553 		policy_mgr_debug("unexpected num_connections value %d",
3554 				 num_connections);
3555 		break;
3556 	}
3557 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3558 
3559 	return is_scc;
3560 }
3561 
3562 bool policy_mgr_current_concurrency_is_mcc(struct wlan_objmgr_psoc *psoc)
3563 {
3564 	uint32_t num_connections = 0;
3565 	bool is_mcc = false;
3566 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3567 
3568 	pm_ctx = policy_mgr_get_context(psoc);
3569 	if (!pm_ctx) {
3570 		policy_mgr_err("Invalid Context");
3571 		return is_mcc;
3572 	}
3573 
3574 	num_connections = policy_mgr_get_connection_count(psoc);
3575 
3576 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3577 	switch (num_connections) {
3578 	case 1:
3579 		break;
3580 	case 2:
3581 		if (pm_conc_connection_list[0].freq !=
3582 		    pm_conc_connection_list[1].freq &&
3583 		    policy_mgr_are_2_freq_on_same_mac(psoc,
3584 			pm_conc_connection_list[0].freq,
3585 			pm_conc_connection_list[1].freq))
3586 			is_mcc = true;
3587 		break;
3588 	case 3:
3589 		/*
3590 		 * Check if any 2 different freq is on same MAC.
3591 		 * Return true if any of the different freq is on same MAC.
3592 		 */
3593 		if ((pm_conc_connection_list[0].freq !=
3594 		     pm_conc_connection_list[1].freq &&
3595 		     policy_mgr_are_2_freq_on_same_mac(psoc,
3596 			pm_conc_connection_list[0].freq,
3597 			pm_conc_connection_list[1].freq)) ||
3598 		    (pm_conc_connection_list[0].freq !=
3599 		     pm_conc_connection_list[2].freq &&
3600 		     policy_mgr_are_2_freq_on_same_mac(psoc,
3601 			pm_conc_connection_list[0].freq,
3602 			pm_conc_connection_list[2].freq)) ||
3603 		    (pm_conc_connection_list[1].freq !=
3604 		     pm_conc_connection_list[2].freq &&
3605 		     policy_mgr_are_2_freq_on_same_mac(psoc,
3606 			pm_conc_connection_list[1].freq,
3607 			pm_conc_connection_list[2].freq)))
3608 			is_mcc = true;
3609 		break;
3610 	default:
3611 		policy_mgr_debug("unexpected num_connections value %d",
3612 				 num_connections);
3613 		break;
3614 	}
3615 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3616 
3617 	return is_mcc;
3618 }
3619 
3620 bool policy_mgr_is_sap_p2pgo_on_dfs(struct wlan_objmgr_psoc *psoc)
3621 {
3622 	int index, count;
3623 	uint32_t list[MAX_NUMBER_OF_CONC_CONNECTIONS];
3624 	struct policy_mgr_psoc_priv_obj *pm_ctx = NULL;
3625 
3626 	if (psoc)
3627 		pm_ctx = policy_mgr_get_context(psoc);
3628 
3629 	if (!pm_ctx) {
3630 		policy_mgr_err("Invalid Context");
3631 		return false;
3632 	}
3633 
3634 	index = 0;
3635 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3636 	count = policy_mgr_mode_specific_connection_count(psoc,
3637 							  PM_SAP_MODE,
3638 							  list);
3639 	while (index < count) {
3640 		if (pm_conc_connection_list[list[index]].ch_flagext &
3641 		    (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) {
3642 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3643 			return true;
3644 		}
3645 		index++;
3646 	}
3647 	count = policy_mgr_mode_specific_connection_count(psoc,
3648 							  PM_P2P_GO_MODE,
3649 							  list);
3650 	index = 0;
3651 	while (index < count) {
3652 		if (pm_conc_connection_list[list[index]].ch_flagext &
3653 		    (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) {
3654 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3655 			return true;
3656 		}
3657 		index++;
3658 	}
3659 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3660 	return false;
3661 }
3662 
3663 /**
3664  * policy_mgr_set_concurrency_mode() - To set concurrency mode
3665  * @psoc: PSOC object data
3666  * @mode: device mode
3667  *
3668  * This routine is called to set the concurrency mode
3669  *
3670  * Return: NONE
3671  */
3672 void policy_mgr_set_concurrency_mode(struct wlan_objmgr_psoc *psoc,
3673 				     enum QDF_OPMODE mode)
3674 {
3675 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3676 
3677 	pm_ctx = policy_mgr_get_context(psoc);
3678 	if (!pm_ctx) {
3679 		policy_mgr_err("Invalid context");
3680 		return;
3681 	}
3682 
3683 	switch (mode) {
3684 	case QDF_STA_MODE:
3685 	case QDF_P2P_CLIENT_MODE:
3686 	case QDF_P2P_GO_MODE:
3687 	case QDF_SAP_MODE:
3688 	case QDF_MONITOR_MODE:
3689 		pm_ctx->concurrency_mode |= (1 << mode);
3690 		pm_ctx->no_of_open_sessions[mode]++;
3691 		break;
3692 	default:
3693 		break;
3694 	}
3695 
3696 	policy_mgr_debug("concurrency_mode = 0x%x Number of open sessions for mode %d = %d",
3697 			 pm_ctx->concurrency_mode, mode,
3698 		pm_ctx->no_of_open_sessions[mode]);
3699 }
3700 
3701 /**
3702  * policy_mgr_clear_concurrency_mode() - To clear concurrency mode
3703  * @psoc: PSOC object data
3704  * @mode: device mode
3705  *
3706  * This routine is called to clear the concurrency mode
3707  *
3708  * Return: NONE
3709  */
3710 void policy_mgr_clear_concurrency_mode(struct wlan_objmgr_psoc *psoc,
3711 				       enum QDF_OPMODE mode)
3712 {
3713 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3714 
3715 	pm_ctx = policy_mgr_get_context(psoc);
3716 	if (!pm_ctx) {
3717 		policy_mgr_err("Invalid context");
3718 		return;
3719 	}
3720 
3721 	switch (mode) {
3722 	case QDF_STA_MODE:
3723 	case QDF_P2P_CLIENT_MODE:
3724 	case QDF_P2P_GO_MODE:
3725 	case QDF_SAP_MODE:
3726 	case QDF_MONITOR_MODE:
3727 		pm_ctx->no_of_open_sessions[mode]--;
3728 		if (!(pm_ctx->no_of_open_sessions[mode]))
3729 			pm_ctx->concurrency_mode &= (~(1 << mode));
3730 		break;
3731 	default:
3732 		break;
3733 	}
3734 
3735 	policy_mgr_debug("concurrency_mode = 0x%x Number of open sessions for mode %d = %d",
3736 			 pm_ctx->concurrency_mode, mode,
3737 			 pm_ctx->no_of_open_sessions[mode]);
3738 }
3739 
3740 /**
3741  * policy_mgr_validate_conn_info() - validate conn info list
3742  * @psoc: PSOC object data
3743  *
3744  * This function will check connection list to see duplicated
3745  * vdev entry existing or not.
3746  *
3747  * Return: true if conn list is in abnormal state.
3748  */
3749 static bool
3750 policy_mgr_validate_conn_info(struct wlan_objmgr_psoc *psoc)
3751 {
3752 	uint32_t i, j, conn_num = 0;
3753 	bool panic = false;
3754 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3755 
3756 	pm_ctx = policy_mgr_get_context(psoc);
3757 	if (!pm_ctx) {
3758 		policy_mgr_err("Invalid Context");
3759 		return true;
3760 	}
3761 
3762 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3763 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
3764 		if (pm_conc_connection_list[i].in_use) {
3765 			for (j = i + 1; j < MAX_NUMBER_OF_CONC_CONNECTIONS;
3766 									j++) {
3767 				if (pm_conc_connection_list[j].in_use &&
3768 				    pm_conc_connection_list[i].vdev_id ==
3769 				    pm_conc_connection_list[j].vdev_id) {
3770 					policy_mgr_debug(
3771 					"dup entry %d",
3772 					pm_conc_connection_list[i].vdev_id);
3773 					panic = true;
3774 				}
3775 			}
3776 			conn_num++;
3777 		}
3778 	}
3779 	if (panic)
3780 		policy_mgr_err("dup entry");
3781 
3782 	for (i = 0, j = 0; i < QDF_MAX_NO_OF_MODE; i++)
3783 		j += pm_ctx->no_of_active_sessions[i];
3784 
3785 	if (j != conn_num) {
3786 		policy_mgr_err("active session/conn count mismatch %d %d",
3787 			       j, conn_num);
3788 		panic = true;
3789 	}
3790 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3791 
3792 	if (panic)
3793 		policy_mgr_debug_alert();
3794 
3795 	return panic;
3796 }
3797 
3798 #ifdef WLAN_FEATURE_11BE_MLO
3799 bool policy_mgr_is_ml_vdev_id(struct wlan_objmgr_psoc *psoc, uint8_t vdev_id)
3800 {
3801 	struct wlan_objmgr_vdev *vdev;
3802 	bool is_mlo = false;
3803 
3804 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
3805 						    WLAN_POLICY_MGR_ID);
3806 	if (!vdev)
3807 		return is_mlo;
3808 
3809 	if (wlan_vdev_mlme_is_mlo_vdev(vdev))
3810 		is_mlo = true;
3811 
3812 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
3813 
3814 	return is_mlo;
3815 }
3816 
3817 /*
3818  * policy_mgr_get_ml_sta_info() - Get number of ML STA vdev ids and freq list
3819  * @pm_ctx: pm_ctx ctx
3820  * @num_ml_sta: Return number of ML STA present
3821  * @num_disabled_ml_sta: Return number of disabled ML STA links
3822  * @ml_vdev_lst: Return ML STA vdev id list
3823  * @ml_freq_lst: Return ML STA freq list
3824  * @num_non_ml: Return number of non-ML STA present
3825  * @non_ml_vdev_lst: Return non-ML STA vdev id list
3826  * @non_ml_freq_lst: Return non-ML STA freq list
3827  *
3828  * Return: void
3829  */
3830 static void
3831 policy_mgr_get_ml_sta_info(struct policy_mgr_psoc_priv_obj *pm_ctx,
3832 			   uint8_t *num_ml_sta,
3833 			   uint8_t *num_disabled_ml_sta,
3834 			   uint8_t *ml_vdev_lst,
3835 			   qdf_freq_t *ml_freq_lst,
3836 			   uint8_t *num_non_ml,
3837 			   uint8_t *non_ml_vdev_lst,
3838 			   qdf_freq_t *non_ml_freq_lst)
3839 {
3840 	struct wlan_objmgr_vdev *vdev;
3841 	uint8_t vdev_id, conn_index;
3842 	qdf_freq_t freq;
3843 
3844 	*num_ml_sta = 0;
3845 	*num_disabled_ml_sta = 0;
3846 	if (num_non_ml)
3847 		*num_non_ml = 0;
3848 
3849 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3850 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
3851 	     conn_index++) {
3852 		if (!pm_conc_connection_list[conn_index].in_use)
3853 			continue;
3854 		if (pm_conc_connection_list[conn_index].mode != PM_STA_MODE)
3855 			continue;
3856 		vdev_id = pm_conc_connection_list[conn_index].vdev_id;
3857 		freq = pm_conc_connection_list[conn_index].freq;
3858 
3859 		/* add ml sta vdev and freq list */
3860 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(pm_ctx->psoc,
3861 							    vdev_id,
3862 							    WLAN_POLICY_MGR_ID);
3863 		if (!vdev) {
3864 			policy_mgr_err("invalid vdev for id %d", vdev_id);
3865 			continue;
3866 		}
3867 
3868 		if (wlan_vdev_mlme_is_mlo_vdev(vdev)) {
3869 			ml_vdev_lst[*num_ml_sta] = vdev_id;
3870 			ml_freq_lst[(*num_ml_sta)++] = freq;
3871 		} else if (num_non_ml) {
3872 			if (non_ml_vdev_lst)
3873 				non_ml_vdev_lst[*num_non_ml] = vdev_id;
3874 			if (non_ml_freq_lst)
3875 				non_ml_freq_lst[*num_non_ml] = freq;
3876 			(*num_non_ml)++;
3877 		}
3878 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
3879 	}
3880 	/* Get disabled link info as well and keep it at last */
3881 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_DISABLE_LINK;
3882 	     conn_index++) {
3883 		if (!pm_disabled_ml_links[conn_index].in_use)
3884 			continue;
3885 		if (pm_disabled_ml_links[conn_index].mode != PM_STA_MODE)
3886 			continue;
3887 		ml_vdev_lst[*num_ml_sta] =
3888 				pm_disabled_ml_links[conn_index].vdev_id;
3889 		ml_freq_lst[(*num_ml_sta)++] =
3890 			pm_disabled_ml_links[conn_index].freq;
3891 		(*num_disabled_ml_sta)++;
3892 	}
3893 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3894 }
3895 
3896 void
3897 policy_mgr_get_ml_sta_info_psoc(struct wlan_objmgr_psoc *psoc,
3898 				uint8_t *num_ml_sta,
3899 				uint8_t *num_disabled_ml_sta,
3900 				uint8_t *ml_vdev_lst,
3901 				qdf_freq_t *ml_freq_lst,
3902 				uint8_t *num_non_ml,
3903 				uint8_t *non_ml_vdev_lst,
3904 				qdf_freq_t *non_ml_freq_lst)
3905 {
3906 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3907 
3908 	pm_ctx = policy_mgr_get_context(psoc);
3909 	if (!pm_ctx) {
3910 		policy_mgr_err("Invalid pm_ctx");
3911 		return;
3912 	}
3913 
3914 	return policy_mgr_get_ml_sta_info(pm_ctx,
3915 					  num_ml_sta,
3916 					  num_disabled_ml_sta,
3917 					  ml_vdev_lst,
3918 					  ml_freq_lst,
3919 					  num_non_ml,
3920 					  non_ml_vdev_lst,
3921 					  non_ml_freq_lst);
3922 }
3923 
3924 uint32_t policy_mgr_get_disabled_ml_links_count(struct wlan_objmgr_psoc *psoc)
3925 {
3926 	uint32_t i, count = 0;
3927 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3928 
3929 	pm_ctx = policy_mgr_get_context(psoc);
3930 	if (!pm_ctx) {
3931 		policy_mgr_err("Invalid pm_ctx");
3932 		return count;
3933 	}
3934 
3935 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3936 	for (i = 0; i < MAX_NUMBER_OF_DISABLE_LINK; i++) {
3937 		if (pm_disabled_ml_links[i].in_use)
3938 			count++;
3939 	}
3940 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3941 
3942 	return count;
3943 }
3944 
3945 static QDF_STATUS
3946 policy_mgr_delete_from_disabled_links(struct policy_mgr_psoc_priv_obj *pm_ctx,
3947 				      uint8_t vdev_id)
3948 {
3949 	int i;
3950 
3951 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
3952 	for (i = 0; i < MAX_NUMBER_OF_DISABLE_LINK; i++) {
3953 		if (pm_disabled_ml_links[i].in_use &&
3954 		    pm_disabled_ml_links[i].vdev_id == vdev_id) {
3955 			pm_disabled_ml_links[i].in_use = false;
3956 			policy_mgr_debug("Disabled link removed for vdev %d",
3957 					 vdev_id);
3958 			break;
3959 		}
3960 	}
3961 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
3962 	/* Return failure if not found */
3963 	if (i >= MAX_NUMBER_OF_DISABLE_LINK)
3964 		return QDF_STATUS_E_EXISTS;
3965 
3966 	return QDF_STATUS_SUCCESS;
3967 }
3968 
3969 void policy_mgr_move_vdev_from_disabled_to_connection_tbl(
3970 						struct wlan_objmgr_psoc *psoc,
3971 						uint8_t vdev_id)
3972 {
3973 	struct policy_mgr_psoc_priv_obj *pm_ctx;
3974 	QDF_STATUS status;
3975 	enum QDF_OPMODE mode;
3976 
3977 	pm_ctx = policy_mgr_get_context(psoc);
3978 	if (!pm_ctx) {
3979 		policy_mgr_err("Invalid pm_ctx");
3980 		return;
3981 	}
3982 	mode = wlan_get_opmode_from_vdev_id(pm_ctx->pdev, vdev_id);
3983 	if (mode != QDF_STA_MODE) {
3984 		policy_mgr_err("vdev %d opmode %d is not STA", vdev_id, mode);
3985 		return;
3986 	}
3987 
3988 	if (!policy_mgr_is_ml_vdev_id(psoc, vdev_id)) {
3989 		policy_mgr_err("vdev %d is not ML", vdev_id);
3990 		return;
3991 	}
3992 
3993 	status = policy_mgr_delete_from_disabled_links(pm_ctx, vdev_id);
3994 	if (QDF_IS_STATUS_ERROR(status)) {
3995 		policy_mgr_debug("Disabled link not found for vdev %d",
3996 				 vdev_id);
3997 		return;
3998 	}
3999 
4000 	/*
4001 	 * Add entry to pm_conc_connection_list if remove from disabled links
4002 	 * was success
4003 	 */
4004 	policy_mgr_incr_active_session(psoc, mode, vdev_id);
4005 }
4006 
4007 static QDF_STATUS
4008 policy_mgr_add_to_disabled_links(struct policy_mgr_psoc_priv_obj *pm_ctx,
4009 				 qdf_freq_t freq, enum QDF_OPMODE mode,
4010 				 uint8_t vdev_id)
4011 {
4012 	int i;
4013 	enum policy_mgr_con_mode pm_mode;
4014 
4015 	pm_mode = policy_mgr_qdf_opmode_to_pm_con_mode(pm_ctx->psoc, mode,
4016 						       vdev_id);
4017 
4018 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
4019 	for (i = 0; i < MAX_NUMBER_OF_DISABLE_LINK; i++) {
4020 		if (pm_disabled_ml_links[i].in_use &&
4021 		    pm_disabled_ml_links[i].vdev_id == vdev_id)
4022 			break;
4023 	}
4024 
4025 	if (i < MAX_NUMBER_OF_DISABLE_LINK) {
4026 		pm_disabled_ml_links[i].freq = freq;
4027 		qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
4028 		policy_mgr_debug("Disabled link already present vdev %d, pm_mode %d, update freq %d",
4029 				 vdev_id, pm_mode, freq);
4030 
4031 		return QDF_STATUS_E_EXISTS;
4032 	}
4033 
4034 	for (i = 0; i < MAX_NUMBER_OF_DISABLE_LINK; i++) {
4035 		if (!pm_disabled_ml_links[i].in_use) {
4036 			/* add in empty place */
4037 			pm_disabled_ml_links[i].vdev_id = vdev_id;
4038 			pm_disabled_ml_links[i].mode = pm_mode;
4039 			pm_disabled_ml_links[i].in_use = true;
4040 			pm_disabled_ml_links[i].freq = freq;
4041 			policy_mgr_debug("Disabled link added vdev id: %d freq: %d pm_mode %d",
4042 					 vdev_id, freq, pm_mode);
4043 			break;
4044 		}
4045 	}
4046 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
4047 	if (i >= MAX_NUMBER_OF_DISABLE_LINK) {
4048 		policy_mgr_err("No empty entry found to disable link for vdev %d",
4049 			       vdev_id);
4050 		return QDF_STATUS_E_RESOURCES;
4051 	}
4052 
4053 	return QDF_STATUS_SUCCESS;
4054 }
4055 
4056 void policy_mgr_move_vdev_from_connection_to_disabled_tbl(
4057 						struct wlan_objmgr_psoc *psoc,
4058 						uint8_t vdev_id)
4059 {
4060 	struct policy_mgr_psoc_priv_obj *pm_ctx;
4061 	qdf_freq_t freq;
4062 	enum QDF_OPMODE mode;
4063 	QDF_STATUS status;
4064 
4065 	pm_ctx = policy_mgr_get_context(psoc);
4066 	if (!pm_ctx) {
4067 		policy_mgr_err("Invalid pm_ctx");
4068 		return;
4069 	}
4070 
4071 	mode = wlan_get_opmode_from_vdev_id(pm_ctx->pdev, vdev_id);
4072 	if (mode != QDF_STA_MODE) {
4073 		policy_mgr_err("vdev %d opmode %d is not STA", vdev_id, mode);
4074 		return;
4075 	}
4076 
4077 	if (!policy_mgr_is_ml_vdev_id(psoc, vdev_id)) {
4078 		policy_mgr_err("vdev %d is not ML", vdev_id);
4079 		return;
4080 	}
4081 	freq = wlan_get_operation_chan_freq_vdev_id(pm_ctx->pdev, vdev_id);
4082 	status = policy_mgr_check_conn_with_mode_and_vdev_id(psoc, PM_STA_MODE,
4083 							     vdev_id);
4084 	/*
4085 	 * Remove entry if present in pm_conc_connection_list, if not just add
4086 	 * it in disabled table.
4087 	 */
4088 	if (QDF_IS_STATUS_SUCCESS(status))
4089 		policy_mgr_decr_session_set_pcl(psoc, mode, vdev_id);
4090 	else
4091 		policy_mgr_debug("Connection tbl dont have vdev %d in STA mode, Add it in disabled tbl",
4092 				 vdev_id);
4093 
4094 	policy_mgr_add_to_disabled_links(pm_ctx, freq, mode, vdev_id);
4095 	policy_mgr_dump_current_concurrency(psoc);
4096 }
4097 
4098 static bool
4099 policy_mgr_vdev_disabled_by_link_force(struct wlan_objmgr_psoc *psoc,
4100 				       struct wlan_objmgr_vdev *vdev,
4101 				       bool peer_assoc)
4102 {
4103 	uint16_t dynamic_inactive = 0, forced_inactive = 0;
4104 	uint16_t link_id;
4105 
4106 	if (ml_is_nlink_service_supported(psoc) &&
4107 	    !peer_assoc) {
4108 		ml_nlink_get_dynamic_inactive_links(psoc, vdev,
4109 						    &dynamic_inactive,
4110 						    &forced_inactive);
4111 		link_id = wlan_vdev_get_link_id(vdev);
4112 		if ((forced_inactive | dynamic_inactive) &
4113 		    (1 << link_id)) {
4114 			policy_mgr_debug("vdev %d linkid %d is forced inactived 0x%0x dyn 0x%x",
4115 					 wlan_vdev_get_id(vdev),
4116 					 link_id, forced_inactive,
4117 					 dynamic_inactive);
4118 			return true;
4119 		}
4120 	}
4121 
4122 	return false;
4123 }
4124 
4125 bool
4126 policy_mgr_ml_link_vdev_need_to_be_disabled(struct wlan_objmgr_psoc *psoc,
4127 					    struct wlan_objmgr_vdev *vdev,
4128 					    bool peer_assoc)
4129 {
4130 	union conc_ext_flag conc_ext_flags;
4131 
4132 	if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE)
4133 		return false;
4134 
4135 	/* Check only for link vdev */
4136 	if (!wlan_vdev_mlme_is_mlo_vdev(vdev) ||
4137 	    !wlan_vdev_mlme_is_mlo_link_vdev(vdev))
4138 		return false;
4139 
4140 	/* Check vdev is disabled by link force command */
4141 	if (policy_mgr_vdev_disabled_by_link_force(psoc, vdev,
4142 						   peer_assoc))
4143 		return true;
4144 
4145 	conc_ext_flags.value = policy_mgr_get_conc_ext_flags(vdev, false);
4146 	/*
4147 	 * For non-assoc link vdev set link as disabled if concurrency is
4148 	 * not allowed
4149 	 */
4150 	return !policy_mgr_is_concurrency_allowed(psoc, PM_STA_MODE,
4151 					wlan_get_operation_chan_freq(vdev),
4152 					HW_MODE_20_MHZ,
4153 					conc_ext_flags.value, NULL);
4154 }
4155 
4156 static void
4157 policy_mgr_enable_disable_link_from_vdev_bitmask(struct wlan_objmgr_psoc *psoc,
4158 						 unsigned long enable_vdev_mask,
4159 						 unsigned long disable_vdev_mask,
4160 						 uint8_t start_vdev_id)
4161 {
4162 	uint8_t i;
4163 
4164 	/* Enable required link if enable_vdev_mask preset */
4165 	for (i = 0; enable_vdev_mask && i < WLAN_MAX_VDEVS; i++) {
4166 		if (qdf_test_and_clear_bit(i, &enable_vdev_mask))
4167 			policy_mgr_move_vdev_from_disabled_to_connection_tbl(
4168 							psoc,
4169 							i + start_vdev_id);
4170 	}
4171 
4172 	/* Disable required link if disable_mask preset */
4173 	for (i = 0; disable_vdev_mask && i < WLAN_MAX_VDEVS; i++) {
4174 		if (qdf_test_and_clear_bit(i, &disable_vdev_mask))
4175 			policy_mgr_move_vdev_from_connection_to_disabled_tbl(
4176 							psoc,
4177 							i + start_vdev_id);
4178 	}
4179 }
4180 
4181 static void
4182 policy_mgr_set_link_in_progress(struct policy_mgr_psoc_priv_obj *pm_ctx,
4183 				bool value)
4184 {
4185 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
4186 	pm_ctx->set_link_in_progress = value;
4187 	/* if set link has started reset the event, else complete the event */
4188 	if (pm_ctx->set_link_in_progress)
4189 		qdf_event_reset(&pm_ctx->set_link_update_done_evt);
4190 	else
4191 		qdf_event_set(&pm_ctx->set_link_update_done_evt);
4192 	policy_mgr_debug("set_link_in_progress %d",
4193 			 pm_ctx->set_link_in_progress);
4194 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
4195 }
4196 
4197 static bool
4198 policy_mgr_get_link_in_progress(struct policy_mgr_psoc_priv_obj *pm_ctx)
4199 {
4200 	bool value;
4201 
4202 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
4203 	value = pm_ctx->set_link_in_progress;
4204 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
4205 	if (value)
4206 		policy_mgr_debug("set_link_in_progress %d", value);
4207 
4208 	return value;
4209 }
4210 
4211 bool policy_mgr_is_set_link_in_progress(struct wlan_objmgr_psoc *psoc)
4212 {
4213 	struct policy_mgr_psoc_priv_obj *pm_ctx;
4214 
4215 	pm_ctx = policy_mgr_get_context(psoc);
4216 	if (!pm_ctx) {
4217 		policy_mgr_err("Invalid Context");
4218 		return false;
4219 	}
4220 
4221 	return policy_mgr_get_link_in_progress(pm_ctx);
4222 }
4223 
4224 /*
4225  * policy_mgr_trigger_roam_on_link_removal() - Trigger roam on link removal
4226  * @vdev: vdev object
4227  *
4228  * In multilink ML STA, if one link is removed by AP, and no other active
4229  * link, trigger roam by roaming invoke command.
4230  *
4231  * Return: void
4232  */
4233 static void
4234 policy_mgr_trigger_roam_on_link_removal(struct wlan_objmgr_vdev *vdev)
4235 {
4236 	struct wlan_objmgr_psoc *psoc;
4237 	struct wlan_objmgr_pdev *pdev;
4238 	struct wlan_objmgr_vdev *ml_vdev;
4239 	struct policy_mgr_psoc_priv_obj *pm_ctx;
4240 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0;
4241 	uint8_t num_active_ml_sta;
4242 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
4243 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
4244 	uint8_t vdev_id = wlan_vdev_get_id(vdev);
4245 	uint8_t assoc_vdev_id = WLAN_INVALID_VDEV_ID;
4246 	uint8_t removed_vdev_id = WLAN_INVALID_VDEV_ID;
4247 	struct qdf_mac_addr bssid;
4248 	QDF_STATUS status;
4249 	bool ml_sta_is_not_connected = false;
4250 	uint32_t i;
4251 
4252 	psoc = wlan_vdev_get_psoc(vdev);
4253 	if (!psoc) {
4254 		policy_mgr_err("Failed to get psoc");
4255 		return;
4256 	}
4257 	pdev = wlan_vdev_get_pdev(vdev);
4258 	if (!pdev) {
4259 		policy_mgr_err("Failed to get pdev");
4260 		return;
4261 	}
4262 	pm_ctx = policy_mgr_get_context(psoc);
4263 	if (!pm_ctx) {
4264 		policy_mgr_err("Invalid Context");
4265 		return;
4266 	}
4267 
4268 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
4269 				   ml_sta_vdev_lst, ml_freq_lst,
4270 				   NULL, NULL, NULL);
4271 	if (!num_ml_sta) {
4272 		policy_mgr_debug("unexpected event, no ml sta");
4273 		return;
4274 	}
4275 	if (num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
4276 	    num_disabled_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
4277 	    num_ml_sta <= num_disabled_ml_sta) {
4278 		policy_mgr_debug("unexpected ml sta num %d %d",
4279 				 num_ml_sta, num_disabled_ml_sta);
4280 		return;
4281 	}
4282 	num_active_ml_sta = num_ml_sta;
4283 	if (num_ml_sta >= num_disabled_ml_sta)
4284 		num_active_ml_sta = num_ml_sta - num_disabled_ml_sta;
4285 
4286 	for (i = 0; i < num_active_ml_sta; i++) {
4287 		if (!wlan_get_vdev_link_removed_flag_by_vdev_id(
4288 					psoc, ml_sta_vdev_lst[i]))
4289 			break;
4290 	}
4291 
4292 	/* After link removal, one link is still active, no need invoke
4293 	 * roaming.
4294 	 * For Single link MLO, FW will do roaming automatically.
4295 	 */
4296 	if (i < num_active_ml_sta || num_ml_sta < 2)
4297 		return;
4298 
4299 	/* For multi-link MLO STA, if one link is removed and no other active
4300 	 * link, then trigger roaming. the other link may have concurrency
4301 	 * limitation and can't be active.
4302 	 */
4303 	for (i = 0; i < num_ml_sta; i++) {
4304 		if (removed_vdev_id == WLAN_INVALID_VDEV_ID &&
4305 		    wlan_get_vdev_link_removed_flag_by_vdev_id(
4306 			psoc, ml_sta_vdev_lst[i])) {
4307 			policy_mgr_debug("removal link vdev %d is removed ",
4308 					 vdev_id);
4309 			removed_vdev_id = ml_sta_vdev_lst[i];
4310 		}
4311 		ml_vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
4312 						pm_ctx->psoc,
4313 						ml_sta_vdev_lst[i],
4314 						WLAN_POLICY_MGR_ID);
4315 		if (!ml_vdev) {
4316 			policy_mgr_err("invalid vdev for id %d",
4317 				       ml_sta_vdev_lst[i]);
4318 			continue;
4319 		}
4320 		if (!wlan_cm_is_vdev_connected(ml_vdev)) {
4321 			policy_mgr_debug("ml sta vdev %d is not connected state",
4322 					 ml_sta_vdev_lst[i]);
4323 			ml_sta_is_not_connected = true;
4324 		}
4325 
4326 		wlan_objmgr_vdev_release_ref(ml_vdev, WLAN_POLICY_MGR_ID);
4327 
4328 		if (assoc_vdev_id == WLAN_INVALID_VDEV_ID &&
4329 		    !wlan_vdev_mlme_get_is_mlo_link(psoc,
4330 						    ml_sta_vdev_lst[i]))
4331 			assoc_vdev_id = ml_sta_vdev_lst[i];
4332 	}
4333 	if (removed_vdev_id == WLAN_INVALID_VDEV_ID) {
4334 		policy_mgr_debug("no link removed, unexpected");
4335 		return;
4336 	}
4337 	if (assoc_vdev_id == WLAN_INVALID_VDEV_ID) {
4338 		policy_mgr_debug("no find assoc vdev, unexpected");
4339 		return;
4340 	}
4341 	if (ml_sta_is_not_connected) {
4342 		policy_mgr_debug("ml sta is non-connected state, don't trigger roam");
4343 		return;
4344 	}
4345 	/* trigger roaming */
4346 	policy_mgr_debug("link removal detected, try roaming on vdev id: %d",
4347 			 assoc_vdev_id);
4348 	qdf_zero_macaddr(&bssid);
4349 	status = wlan_cm_roam_invoke(pdev, assoc_vdev_id, &bssid, 0,
4350 				     CM_ROAMING_LINK_REMOVAL);
4351 	if (QDF_IS_STATUS_ERROR(status))
4352 		policy_mgr_err("roam invoke failed");
4353 }
4354 
4355 static void
4356 policy_mgr_update_dynamic_inactive_bitmap(
4357 			struct wlan_objmgr_psoc *psoc,
4358 			struct wlan_objmgr_vdev *vdev,
4359 			struct mlo_link_set_active_req *req,
4360 			struct mlo_link_set_active_resp *resp)
4361 {
4362 	uint32_t candidate_inactive_links;
4363 	uint32_t dyn_inactive_links = 0;
4364 	uint8_t dyn_num = 0, num = 0, i;
4365 	uint8_t link_ids[MAX_MLO_LINK_ID * 2];
4366 
4367 	if (req->param.force_mode != MLO_LINK_FORCE_MODE_INACTIVE_NUM ||
4368 	    !req->param.control_flags.dynamic_force_link_num)
4369 		return;
4370 
4371 	/* force inactive num "clear" case, return 0 - no
4372 	 * dynamic inactive links.
4373 	 */
4374 	if (!req->param.force_cmd.link_num) {
4375 		dyn_inactive_links = 0;
4376 		dyn_num = 0;
4377 		goto update;
4378 	}
4379 	/* 1. If force inactive overlap with force num bitmap,
4380 	 * select the inactive link from overlapped links firstly.
4381 	 * 2. If selected inactive link num <
4382 	 * req->param.force_cmd.link_num, then select the inactive
4383 	 * links from current inactive links reported from FW.
4384 	 */
4385 	candidate_inactive_links =
4386 		req->param.force_cmd.ieee_link_id_bitmap &
4387 		resp->inactive_linkid_bitmap;
4388 
4389 	num = ml_nlink_convert_link_bitmap_to_ids(candidate_inactive_links,
4390 						  QDF_ARRAY_SIZE(link_ids),
4391 						  link_ids);
4392 	if (num < req->param.force_cmd.link_num &&
4393 	    num < QDF_ARRAY_SIZE(link_ids)) {
4394 		candidate_inactive_links =
4395 			req->param.force_cmd.ieee_link_id_bitmap &
4396 			resp->curr_inactive_linkid_bitmap &
4397 			~candidate_inactive_links;
4398 		num += ml_nlink_convert_link_bitmap_to_ids(
4399 				candidate_inactive_links,
4400 				QDF_ARRAY_SIZE(link_ids) - num,
4401 				&link_ids[num]);
4402 	}
4403 	for (i = 0; i < num; i++) {
4404 		if (dyn_num >= req->param.force_cmd.link_num)
4405 			break;
4406 		dyn_inactive_links |= 1 << link_ids[i];
4407 		dyn_num++;
4408 	}
4409 
4410 update:
4411 	policy_mgr_debug("inactive link num %d bitmap 0x%x force inactive 0x%x dyn links 0x%x num %d",
4412 			 req->param.force_cmd.link_num,
4413 			 req->param.force_cmd.ieee_link_id_bitmap,
4414 			 resp->inactive_linkid_bitmap,
4415 			 dyn_inactive_links, dyn_num);
4416 	if (dyn_num < req->param.force_cmd.link_num)
4417 		policy_mgr_debug("unexpected selected dynamic inactive link num %d",
4418 				 dyn_num);
4419 	ml_nlink_set_dynamic_inactive_links(psoc, vdev, dyn_inactive_links);
4420 }
4421 
4422 static void
4423 policy_mgr_handle_vdev_active_inactive_resp(
4424 					struct wlan_objmgr_psoc *psoc,
4425 					struct wlan_objmgr_vdev *vdev,
4426 					struct mlo_link_set_active_req *req,
4427 					struct mlo_link_set_active_resp *resp)
4428 {
4429 	uint8_t i;
4430 	uint8_t vdev_id_num = 0;
4431 	uint8_t vdev_ids[WLAN_MLO_MAX_VDEVS] = {0};
4432 	uint32_t assoc_bitmap = 0;
4433 	uint16_t dynamic_inactive_bitmap = 0;
4434 	uint16_t forced_inactive_bitmap = 0;
4435 
4436 	/* convert link id to vdev id and update vdev status based
4437 	 * on both inactive and active bitmap.
4438 	 * In link bitmap based WMI event (use_ieee_link_id = true),
4439 	 * target will always indicate current force inactive and
4440 	 * active bitmaps to host. For links in inactive_linkid_bitmap,
4441 	 * they will be moved to policy mgr disable connection table.
4442 	 * for other links, they will be in active tables.
4443 	 */
4444 	ml_nlink_get_dynamic_inactive_links(psoc, vdev,
4445 					    &dynamic_inactive_bitmap,
4446 					    &forced_inactive_bitmap);
4447 	resp->inactive_linkid_bitmap |= dynamic_inactive_bitmap;
4448 	ml_nlink_convert_linkid_bitmap_to_vdev_bitmap(
4449 		psoc, vdev, resp->inactive_linkid_bitmap,
4450 		&assoc_bitmap,
4451 		&resp->inactive_sz, resp->inactive,
4452 		&vdev_id_num, vdev_ids);
4453 
4454 	ml_nlink_convert_linkid_bitmap_to_vdev_bitmap(
4455 		psoc, vdev,
4456 		(~resp->inactive_linkid_bitmap) & assoc_bitmap,
4457 		NULL,
4458 		&resp->active_sz, resp->active,
4459 		&vdev_id_num, vdev_ids);
4460 	for (i = 0; i < resp->inactive_sz; i++)
4461 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4462 				psoc, 0, resp->inactive[i], i * 32);
4463 	for (i = 0; i < resp->active_sz; i++)
4464 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4465 				psoc, resp->active[i], 0, i * 32);
4466 }
4467 
4468 static void
4469 policy_mgr_handle_force_active_resp(struct wlan_objmgr_psoc *psoc,
4470 				    struct wlan_objmgr_vdev *vdev,
4471 				    struct mlo_link_set_active_req *req,
4472 				    struct mlo_link_set_active_resp *resp)
4473 {
4474 	uint8_t i;
4475 	uint32_t assoc_bitmap = 0;
4476 
4477 	if (resp->use_ieee_link_id) {
4478 		/* save link force active bitmap */
4479 		ml_nlink_set_curr_force_active_state(
4480 			psoc, vdev, req->param.force_cmd.ieee_link_id_bitmap,
4481 			req->param.control_flags.overwrite_force_active_bitmap ?
4482 			LINK_OVERWRITE : LINK_ADD);
4483 
4484 		/* update vdev active inactive status */
4485 		policy_mgr_handle_vdev_active_inactive_resp(psoc, vdev, req,
4486 							    resp);
4487 		return;
4488 	}
4489 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
4490 		psoc, vdev, req->param.num_vdev_bitmap,
4491 		req->param.vdev_bitmap, &resp->active_linkid_bitmap,
4492 		&assoc_bitmap);
4493 	ml_nlink_set_curr_force_active_state(
4494 		psoc, vdev, resp->active_linkid_bitmap, LINK_ADD);
4495 
4496 	for (i = 0; i < resp->active_sz; i++)
4497 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4498 				psoc, resp->active[i], 0, i * 32);
4499 }
4500 
4501 static void
4502 policy_mgr_handle_force_inactive_resp(struct wlan_objmgr_psoc *psoc,
4503 				      struct wlan_objmgr_vdev *vdev,
4504 				      struct mlo_link_set_active_req *req,
4505 				      struct mlo_link_set_active_resp *resp)
4506 {
4507 	uint8_t i;
4508 	uint32_t assoc_bitmap = 0;
4509 
4510 	if (resp->use_ieee_link_id) {
4511 		/* save link force inactive bitmap */
4512 		ml_nlink_set_curr_force_inactive_state(
4513 			psoc, vdev, req->param.force_cmd.ieee_link_id_bitmap,
4514 			req->param.control_flags.overwrite_force_inactive_bitmap ?
4515 			LINK_OVERWRITE : LINK_ADD);
4516 
4517 		/* update vdev active inactive status */
4518 		policy_mgr_handle_vdev_active_inactive_resp(psoc, vdev, req,
4519 							    resp);
4520 		return;
4521 	}
4522 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
4523 		psoc, vdev, req->param.num_vdev_bitmap,
4524 		req->param.vdev_bitmap, &resp->inactive_linkid_bitmap,
4525 		&assoc_bitmap);
4526 	ml_nlink_set_curr_force_inactive_state(
4527 		psoc, vdev, resp->inactive_linkid_bitmap, LINK_ADD);
4528 
4529 	for (i = 0; i < resp->inactive_sz; i++)
4530 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4531 				psoc, 0, resp->inactive[i], i * 32);
4532 }
4533 
4534 static void
4535 policy_mgr_handle_force_active_num_resp(struct wlan_objmgr_psoc *psoc,
4536 					struct wlan_objmgr_vdev *vdev,
4537 					struct mlo_link_set_active_req *req,
4538 					struct mlo_link_set_active_resp *resp)
4539 {
4540 	uint8_t i;
4541 	uint32_t assoc_bitmap = 0;
4542 	uint32_t link_bitmap = 0;
4543 
4544 	if (resp->use_ieee_link_id) {
4545 		/* save force num and force num bitmap */
4546 		ml_nlink_set_curr_force_active_num_state(
4547 			psoc, vdev, req->param.force_cmd.link_num,
4548 			req->param.force_cmd.ieee_link_id_bitmap);
4549 
4550 		/* update vdev active inactive status */
4551 		policy_mgr_handle_vdev_active_inactive_resp(psoc, vdev, req,
4552 							    resp);
4553 		return;
4554 	}
4555 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
4556 		psoc, vdev, req->param.num_vdev_bitmap,
4557 		req->param.vdev_bitmap,
4558 		&link_bitmap,
4559 		&assoc_bitmap);
4560 	ml_nlink_set_curr_force_active_num_state(
4561 		psoc, vdev, req->param.link_num[0].num_of_link,
4562 		link_bitmap);
4563 	/*
4564 	 * When the host sends a set link command with force link num
4565 	 * and dynamic flag set, FW may not process it immediately.
4566 	 * In this case FW buffer the request and sends a response as
4567 	 * success to the host with VDEV bitmap as zero.
4568 	 * FW ensures that the number of active links will be equal to
4569 	 * the link num sent via WMI_MLO_LINK_SET_ACTIVE_CMDID command.
4570 	 * So the host should also fill the mlo policy_mgr table as per
4571 	 * request.
4572 	 */
4573 	if (req->param.control_flags.dynamic_force_link_num) {
4574 		policy_mgr_debug("Enable ML vdev(s) as sent in req");
4575 		for (i = 0; i < req->param.num_vdev_bitmap; i++)
4576 			policy_mgr_enable_disable_link_from_vdev_bitmask(
4577 				psoc,
4578 				req->param.vdev_bitmap[i], 0, i * 32);
4579 		return;
4580 	}
4581 
4582 	/*
4583 	 * MLO_LINK_FORCE_MODE_ACTIVE_NUM return which vdev is active
4584 	 * So XOR of the requested ML vdev and active vdev bit will give
4585 	 * the vdev bits to disable
4586 	 */
4587 	for (i = 0; i < resp->active_sz; i++)
4588 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4589 			psoc, resp->active[i],
4590 			resp->active[i] ^ req->param.vdev_bitmap[i],
4591 			i * 32);
4592 }
4593 
4594 static void
4595 policy_mgr_handle_force_inactive_num_resp(
4596 				struct wlan_objmgr_psoc *psoc,
4597 				struct wlan_objmgr_vdev *vdev,
4598 				struct mlo_link_set_active_req *req,
4599 				struct mlo_link_set_active_resp *resp)
4600 {
4601 	uint8_t i;
4602 	uint32_t assoc_bitmap = 0;
4603 	uint32_t link_bitmap = 0;
4604 
4605 	if (resp->use_ieee_link_id) {
4606 		/* save force num and force num bitmap */
4607 		ml_nlink_set_curr_force_inactive_num_state(
4608 			psoc, vdev, req->param.force_cmd.link_num,
4609 			req->param.force_cmd.ieee_link_id_bitmap);
4610 		policy_mgr_update_dynamic_inactive_bitmap(psoc, vdev, req,
4611 							  resp);
4612 
4613 		/* update vdev active inactive status */
4614 		policy_mgr_handle_vdev_active_inactive_resp(psoc, vdev, req,
4615 							    resp);
4616 		return;
4617 	}
4618 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
4619 		psoc, vdev, req->param.num_vdev_bitmap,
4620 		req->param.vdev_bitmap,
4621 		&link_bitmap,
4622 		&assoc_bitmap);
4623 	ml_nlink_set_curr_force_inactive_num_state(
4624 		psoc, vdev, req->param.link_num[0].num_of_link,
4625 		link_bitmap);
4626 
4627 	/*
4628 	 * MLO_LINK_FORCE_MODE_INACTIVE_NUM return which vdev is
4629 	 * inactive So XOR of the requested ML vdev and inactive vdev
4630 	 * bit will give the vdev bits to be enable.
4631 	 */
4632 	for (i = 0; i < resp->inactive_sz; i++)
4633 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4634 			psoc,
4635 			resp->inactive[i] ^ req->param.vdev_bitmap[i],
4636 			resp->inactive[i], i * 32);
4637 }
4638 
4639 static void
4640 policy_mgr_handle_force_active_inactive_resp(
4641 				struct wlan_objmgr_psoc *psoc,
4642 				struct wlan_objmgr_vdev *vdev,
4643 				struct mlo_link_set_active_req *req,
4644 				struct mlo_link_set_active_resp *resp)
4645 {
4646 	uint8_t i;
4647 	uint32_t assoc_bitmap = 0;
4648 
4649 	if (resp->use_ieee_link_id) {
4650 		/* save link active/inactive bitmap */
4651 		ml_nlink_set_curr_force_active_state(
4652 			psoc, vdev, req->param.force_cmd.ieee_link_id_bitmap,
4653 			req->param.control_flags.overwrite_force_active_bitmap ?
4654 			LINK_OVERWRITE : LINK_ADD);
4655 		ml_nlink_set_curr_force_inactive_state(
4656 			psoc, vdev, req->param.force_cmd.ieee_link_id_bitmap2,
4657 			req->param.control_flags.overwrite_force_inactive_bitmap ?
4658 			LINK_OVERWRITE : LINK_ADD);
4659 
4660 		/* update vdev active inactive status */
4661 		policy_mgr_handle_vdev_active_inactive_resp(psoc, vdev, req,
4662 							    resp);
4663 		return;
4664 	}
4665 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
4666 		psoc, vdev, req->param.num_inactive_vdev_bitmap,
4667 		req->param.inactive_vdev_bitmap,
4668 		&resp->inactive_linkid_bitmap,
4669 		&assoc_bitmap);
4670 	ml_nlink_set_curr_force_inactive_state(
4671 		psoc, vdev, resp->inactive_linkid_bitmap, LINK_ADD);
4672 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
4673 		psoc, vdev, req->param.num_vdev_bitmap,
4674 		req->param.vdev_bitmap,
4675 		&resp->active_linkid_bitmap,
4676 		&assoc_bitmap);
4677 	ml_nlink_set_curr_force_active_state(
4678 		psoc, vdev, resp->active_linkid_bitmap, LINK_ADD);
4679 
4680 	for (i = 0; i < resp->inactive_sz; i++)
4681 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4682 				psoc, 0, resp->inactive[i], i * 32);
4683 	for (i = 0; i < resp->active_sz; i++)
4684 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4685 				psoc, resp->active[i], 0, i * 32);
4686 }
4687 
4688 static void
4689 policy_mgr_handle_no_force_resp(struct wlan_objmgr_psoc *psoc,
4690 				struct wlan_objmgr_vdev *vdev,
4691 				struct mlo_link_set_active_req *req,
4692 				struct mlo_link_set_active_resp *resp)
4693 {
4694 	uint8_t i;
4695 	uint32_t assoc_bitmap = 0;
4696 	uint32_t link_bitmap = 0;
4697 
4698 	if (resp->use_ieee_link_id) {
4699 		/* update link inactive/active bitmap */
4700 		if (req->param.force_cmd.ieee_link_id_bitmap) {
4701 			ml_nlink_set_curr_force_inactive_state(
4702 				psoc, vdev,
4703 				req->param.force_cmd.ieee_link_id_bitmap,
4704 				LINK_CLR);
4705 			ml_nlink_set_curr_force_active_state(
4706 				psoc, vdev,
4707 				req->param.force_cmd.ieee_link_id_bitmap,
4708 				LINK_CLR);
4709 		} else {
4710 			/* special handling for no force to clear all */
4711 			ml_nlink_clr_force_state(psoc, vdev);
4712 		}
4713 
4714 		/* update vdev active inactive status */
4715 		policy_mgr_handle_vdev_active_inactive_resp(psoc, vdev, req,
4716 							    resp);
4717 		return;
4718 	}
4719 
4720 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
4721 		psoc, vdev, req->param.num_vdev_bitmap,
4722 		req->param.vdev_bitmap,
4723 		&link_bitmap, &assoc_bitmap);
4724 
4725 	ml_nlink_set_curr_force_inactive_state(
4726 		psoc, vdev, link_bitmap, LINK_CLR);
4727 	ml_nlink_set_curr_force_active_state(
4728 		psoc, vdev, link_bitmap, LINK_CLR);
4729 	ml_nlink_set_curr_force_active_num_state(
4730 		psoc, vdev, 0, 0);
4731 	ml_nlink_set_curr_force_inactive_num_state(
4732 		psoc, vdev, 0, 0);
4733 
4734 	/* Enable all the ML vdev id sent in request */
4735 	for (i = 0; i < req->param.num_vdev_bitmap; i++)
4736 		policy_mgr_enable_disable_link_from_vdev_bitmask(
4737 			psoc, req->param.vdev_bitmap[i], 0, i * 32);
4738 }
4739 
4740 static void
4741 policy_mgr_handle_link_enable_disable_resp(struct wlan_objmgr_vdev *vdev,
4742 					  void *arg,
4743 					  struct mlo_link_set_active_resp *resp)
4744 {
4745 	struct mlo_link_set_active_req *req = arg;
4746 	struct wlan_objmgr_psoc *psoc;
4747 	struct policy_mgr_psoc_priv_obj *pm_ctx;
4748 	QDF_STATUS status = QDF_STATUS_SUCCESS;
4749 
4750 	psoc = wlan_vdev_get_psoc(vdev);
4751 	if (!psoc) {
4752 		policy_mgr_err("Psoc is Null");
4753 		return;
4754 	}
4755 	pm_ctx = policy_mgr_get_context(psoc);
4756 	if (!pm_ctx) {
4757 		policy_mgr_err("Invalid Context");
4758 		return;
4759 	}
4760 
4761 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
4762 	if (!req || !resp) {
4763 		policy_mgr_err("arguments or event empty for vdev %d",
4764 			       wlan_vdev_get_id(vdev));
4765 		goto complete_evnt;
4766 	}
4767 
4768 	if (resp->status) {
4769 		policy_mgr_err("Set link status %d, for mode %d reason %d vdev bitmask 0x%x",
4770 			       resp->status, req->param.force_mode,
4771 			       req->param.reason, req->param.vdev_bitmap[0]);
4772 		goto complete_evnt;
4773 	}
4774 
4775 	policy_mgr_debug("Req mode %d reason %d, bitmask[0] = 0x%x, resp: active %d inactive %d, active[0] 0x%x inactive[0] 0x%x",
4776 			 req->param.force_mode, req->param.reason,
4777 			 req->param.vdev_bitmap[0],
4778 			 resp->active_sz, resp->inactive_sz,
4779 			 resp->active[0], resp->inactive[0]);
4780 	switch (req->param.force_mode) {
4781 	case MLO_LINK_FORCE_MODE_ACTIVE:
4782 		policy_mgr_handle_force_active_resp(psoc, vdev, req, resp);
4783 		break;
4784 	case MLO_LINK_FORCE_MODE_INACTIVE:
4785 		policy_mgr_handle_force_inactive_resp(psoc, vdev, req, resp);
4786 		break;
4787 	case MLO_LINK_FORCE_MODE_ACTIVE_NUM:
4788 		policy_mgr_handle_force_active_num_resp(psoc, vdev, req, resp);
4789 		break;
4790 	case MLO_LINK_FORCE_MODE_INACTIVE_NUM:
4791 		policy_mgr_handle_force_inactive_num_resp(psoc, vdev, req,
4792 							  resp);
4793 		break;
4794 	case MLO_LINK_FORCE_MODE_NO_FORCE:
4795 		policy_mgr_handle_no_force_resp(psoc, vdev, req, resp);
4796 		break;
4797 	case MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE:
4798 		policy_mgr_handle_force_active_inactive_resp(psoc, vdev, req,
4799 							     resp);
4800 		break;
4801 	default:
4802 		policy_mgr_err("Invalid request req mode %d",
4803 			       req->param.force_mode);
4804 		break;
4805 	}
4806 	if (req->param.reason == MLO_LINK_FORCE_REASON_LINK_REMOVAL)
4807 		policy_mgr_trigger_roam_on_link_removal(vdev);
4808 
4809 complete_evnt:
4810 	policy_mgr_set_link_in_progress(pm_ctx, false);
4811 	if (ml_is_nlink_service_supported(psoc) &&
4812 	    req && resp && !resp->status &&
4813 	    req->param.control_flags.post_re_evaluate)
4814 		status = ml_nlink_conn_change_notify(
4815 			psoc, wlan_vdev_get_id(vdev),
4816 			ml_nlink_connection_updated_evt, NULL);
4817 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
4818 
4819 	/* reschedule force scc workqueue after link state changes */
4820 	if (req && resp && !resp->status &&
4821 	    status == QDF_STATUS_SUCCESS)
4822 		policy_mgr_check_concurrent_intf_and_restart_sap(psoc, false);
4823 }
4824 #else
4825 static inline QDF_STATUS
4826 policy_mgr_delete_from_disabled_links(struct policy_mgr_psoc_priv_obj *pm_ctx,
4827 				      uint8_t vdev_id)
4828 {
4829 	return QDF_STATUS_SUCCESS;
4830 }
4831 #endif
4832 
4833 bool policy_mgr_is_mlo_sta_disconnected(struct wlan_objmgr_psoc *psoc,
4834 					 uint8_t vdev_id)
4835 {
4836 	struct wlan_objmgr_vdev *vdev;
4837 	bool disconnected;
4838 
4839 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
4840 						    WLAN_POLICY_MGR_ID);
4841 	if (!vdev)
4842 		return true;
4843 	/* mlo mgr has no corresponding protocol api used in non-osif/hdd
4844 	 * component. Todo: clean up to use internal API
4845 	 */
4846 	disconnected = ucfg_mlo_is_mld_disconnected(vdev);
4847 
4848 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
4849 
4850 	return disconnected;
4851 }
4852 
4853 void policy_mgr_incr_active_session(struct wlan_objmgr_psoc *psoc,
4854 				enum QDF_OPMODE mode,
4855 				uint8_t session_id)
4856 {
4857 	struct policy_mgr_psoc_priv_obj *pm_ctx;
4858 	uint32_t conn_6ghz_flag = 0;
4859 
4860 	pm_ctx = policy_mgr_get_context(psoc);
4861 	if (!pm_ctx) {
4862 		policy_mgr_err("Invalid Context");
4863 		return;
4864 	}
4865 
4866 	/*
4867 	 * Need to acquire mutex as entire functionality in this function
4868 	 * is in critical section
4869 	 */
4870 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
4871 	switch (mode) {
4872 	case QDF_STA_MODE:
4873 	case QDF_P2P_CLIENT_MODE:
4874 	case QDF_P2P_GO_MODE:
4875 	case QDF_SAP_MODE:
4876 	case QDF_NAN_DISC_MODE:
4877 	case QDF_NDI_MODE:
4878 		pm_ctx->no_of_active_sessions[mode]++;
4879 		break;
4880 	default:
4881 		break;
4882 	}
4883 
4884 	if (mode == QDF_NDI_MODE &&
4885 	    pm_ctx->hdd_cbacks.wlan_hdd_indicate_active_ndp_cnt)
4886 		pm_ctx->hdd_cbacks.wlan_hdd_indicate_active_ndp_cnt(
4887 				psoc, session_id,
4888 				pm_ctx->no_of_active_sessions[mode]);
4889 
4890 	if (mode != QDF_NAN_DISC_MODE && pm_ctx->dp_cbacks.hdd_v2_flow_pool_map)
4891 		pm_ctx->dp_cbacks.hdd_v2_flow_pool_map(session_id);
4892 	if (mode == QDF_SAP_MODE || mode == QDF_P2P_GO_MODE)
4893 		policy_mgr_get_ap_6ghz_capable(psoc, session_id,
4894 					       &conn_6ghz_flag);
4895 
4896 	policy_mgr_debug("No.# of active sessions for mode %d = %d",
4897 		mode, pm_ctx->no_of_active_sessions[mode]);
4898 	policy_mgr_incr_connection_count(psoc, session_id, mode);
4899 
4900 	if ((policy_mgr_mode_specific_connection_count(
4901 		psoc, PM_STA_MODE, NULL) > 0) && (mode != QDF_STA_MODE)) {
4902 		/* Send set pcl for all the connected STA vdev */
4903 		qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
4904 		polic_mgr_send_pcl_to_fw(psoc, mode);
4905 		qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
4906 	}
4907 
4908 	/* Notify tdls */
4909 	if (pm_ctx->tdls_cbacks.tdls_notify_increment_session)
4910 		pm_ctx->tdls_cbacks.tdls_notify_increment_session(psoc);
4911 
4912 	/*
4913 	 * Disable LRO/GRO if P2P or SAP connection has come up or
4914 	 * there are more than one STA connections
4915 	 */
4916 	if ((policy_mgr_mode_specific_connection_count(psoc, PM_STA_MODE, NULL) > 1) ||
4917 	    (policy_mgr_get_beaconing_mode_count(psoc, NULL) > 0) ||
4918 	    (policy_mgr_mode_specific_connection_count(psoc, PM_P2P_CLIENT_MODE, NULL) >
4919 									0) ||
4920 	    (policy_mgr_mode_specific_connection_count(psoc,
4921 						       PM_NDI_MODE,
4922 						       NULL) > 0)) {
4923 		if (pm_ctx->dp_cbacks.hdd_disable_rx_ol_in_concurrency)
4924 			pm_ctx->dp_cbacks.hdd_disable_rx_ol_in_concurrency(true);
4925 	};
4926 
4927 	/* Enable RPS if SAP interface has come up */
4928 	if (policy_mgr_get_sap_mode_count(psoc, NULL) == 1) {
4929 		if (pm_ctx->dp_cbacks.hdd_set_rx_mode_rps_cb)
4930 			pm_ctx->dp_cbacks.hdd_set_rx_mode_rps_cb(true);
4931 	}
4932 	if (mode == QDF_SAP_MODE || mode == QDF_P2P_GO_MODE)
4933 		policy_mgr_init_ap_6ghz_capable(psoc, session_id,
4934 						conn_6ghz_flag);
4935 	if (mode == QDF_SAP_MODE || mode == QDF_P2P_GO_MODE ||
4936 	    mode == QDF_STA_MODE || mode == QDF_P2P_CLIENT_MODE)
4937 		policy_mgr_update_dfs_master_dynamic_enabled(psoc, session_id);
4938 
4939 	policy_mgr_dump_current_concurrency(psoc);
4940 
4941 	if (policy_mgr_update_indoor_concurrency(psoc, session_id, 0, CONNECT))
4942 		wlan_reg_recompute_current_chan_list(psoc, pm_ctx->pdev);
4943 
4944 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
4945 	if (mode == QDF_SAP_MODE || mode == QDF_P2P_GO_MODE)
4946 		ml_nlink_conn_change_notify(
4947 			psoc, session_id, ml_nlink_ap_started_evt, NULL);
4948 }
4949 
4950 /**
4951  * policy_mgr_update_sta_scc_info_for_later_check() - function to update sta/sap
4952  * scc channel frequency and later check flag.
4953  * @pm_ctx: policy manager context pointer
4954  * @mode: operation mode
4955  * @vdev_id: vdev id
4956  *
4957  * Return: None
4958  */
4959 static void policy_mgr_update_sta_scc_info_for_later_check(
4960 		struct policy_mgr_psoc_priv_obj *pm_ctx,
4961 		enum QDF_OPMODE mode,
4962 		uint8_t vdev_id)
4963 {
4964 	uint32_t conn_index = 0;
4965 	qdf_freq_t sta_freq = 0;
4966 
4967 	if (mode != QDF_STA_MODE && mode != QDF_P2P_CLIENT_MODE)
4968 		return;
4969 
4970 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
4971 	while (PM_CONC_CONNECTION_LIST_VALID_INDEX(conn_index)) {
4972 		if (vdev_id == pm_conc_connection_list[conn_index].vdev_id) {
4973 			sta_freq = pm_conc_connection_list[conn_index].freq;
4974 			break;
4975 		}
4976 		conn_index++;
4977 	}
4978 
4979 	if (!sta_freq)
4980 		goto release_mutex;
4981 
4982 	/*
4983 	 * When STA disconnected, we need to move DFS SAP
4984 	 * to Non-DFS if g_sta_sap_scc_on_dfs_chan enabled.
4985 	 * The same if g_sta_sap_scc_on_lte_coex_chan enabled,
4986 	 * need to move SAP on unsafe channel to safe channel.
4987 	 * The flag will be checked by
4988 	 * policy_mgr_is_sap_restart_required_after_sta_disconnect.
4989 	 */
4990 	conn_index = 0;
4991 	while (PM_CONC_CONNECTION_LIST_VALID_INDEX(conn_index)) {
4992 		if (pm_conc_connection_list[conn_index].freq == sta_freq &&
4993 		    (pm_conc_connection_list[conn_index].mode == PM_SAP_MODE ||
4994 		    pm_conc_connection_list[conn_index].mode ==
4995 		    PM_P2P_GO_MODE)) {
4996 			pm_ctx->last_disconn_sta_freq = sta_freq;
4997 			break;
4998 		}
4999 		conn_index++;
5000 	}
5001 
5002 release_mutex:
5003 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5004 }
5005 
5006 QDF_STATUS policy_mgr_decr_active_session(struct wlan_objmgr_psoc *psoc,
5007 				enum QDF_OPMODE mode,
5008 				uint8_t session_id)
5009 {
5010 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5011 	QDF_STATUS qdf_status;
5012 	bool mcc_mode;
5013 	uint32_t session_count, cur_freq;
5014 
5015 	pm_ctx = policy_mgr_get_context(psoc);
5016 	if (!pm_ctx) {
5017 		policy_mgr_err("context is NULL");
5018 		return QDF_STATUS_E_EMPTY;
5019 	}
5020 
5021 	qdf_status = policy_mgr_check_conn_with_mode_and_vdev_id(psoc,
5022 			policy_mgr_qdf_opmode_to_pm_con_mode(psoc, mode,
5023 							     session_id),
5024 			session_id);
5025 	if (QDF_IS_STATUS_ERROR(qdf_status)) {
5026 		policy_mgr_debug("No connection with mode:%d vdev_id:%d",
5027 			policy_mgr_qdf_opmode_to_pm_con_mode(psoc, mode,
5028 							     session_id),
5029 			session_id);
5030 		/*
5031 		 * In case of disconnect try delete the link from disabled link
5032 		 * as well, if its not present in pm_conc_connection_list,
5033 		 * it can be present in pm_disabled_ml_links.
5034 		 */
5035 		policy_mgr_delete_from_disabled_links(pm_ctx, session_id);
5036 		policy_mgr_dump_current_concurrency(psoc);
5037 		return qdf_status;
5038 	}
5039 	policy_mgr_update_sta_scc_info_for_later_check(pm_ctx,
5040 						       mode,
5041 						       session_id);
5042 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
5043 	switch (mode) {
5044 	case QDF_STA_MODE:
5045 	case QDF_P2P_CLIENT_MODE:
5046 	case QDF_P2P_GO_MODE:
5047 	case QDF_SAP_MODE:
5048 	case QDF_NAN_DISC_MODE:
5049 	case QDF_NDI_MODE:
5050 		if (pm_ctx->no_of_active_sessions[mode])
5051 			pm_ctx->no_of_active_sessions[mode]--;
5052 		break;
5053 	default:
5054 		break;
5055 	}
5056 
5057 	policy_mgr_get_chan_by_session_id(psoc, session_id, &cur_freq);
5058 
5059 	policy_mgr_decr_connection_count(psoc, session_id);
5060 	session_count = pm_ctx->no_of_active_sessions[mode];
5061 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5062 
5063 	if (mode != QDF_NAN_DISC_MODE &&
5064 	    pm_ctx->dp_cbacks.hdd_v2_flow_pool_unmap)
5065 		pm_ctx->dp_cbacks.hdd_v2_flow_pool_unmap(session_id);
5066 
5067 	if (mode == QDF_NDI_MODE &&
5068 	    pm_ctx->hdd_cbacks.wlan_hdd_indicate_active_ndp_cnt)
5069 		pm_ctx->hdd_cbacks.wlan_hdd_indicate_active_ndp_cnt(
5070 				psoc, session_id, session_count);
5071 
5072 	policy_mgr_debug("No.# of active sessions for mode %d = %d",
5073 			 mode, session_count);
5074 
5075 	/* Notify tdls */
5076 	if (pm_ctx->tdls_cbacks.tdls_notify_decrement_session)
5077 		pm_ctx->tdls_cbacks.tdls_notify_decrement_session(psoc);
5078 	/* Enable LRO/GRO if there no concurrency */
5079 	if ((policy_mgr_get_connection_count(psoc) == 0) ||
5080 	    ((policy_mgr_mode_specific_connection_count(psoc,
5081 							PM_STA_MODE,
5082 							NULL) == 1) &&
5083 	     (policy_mgr_get_beaconing_mode_count(psoc, NULL) == 0) &&
5084 	     (policy_mgr_mode_specific_connection_count(psoc,
5085 							PM_P2P_CLIENT_MODE,
5086 							NULL) == 0) &&
5087 	     (policy_mgr_mode_specific_connection_count(psoc,
5088 							PM_NDI_MODE,
5089 							NULL) == 0))) {
5090 		if (pm_ctx->dp_cbacks.hdd_disable_rx_ol_in_concurrency)
5091 			pm_ctx->dp_cbacks.hdd_disable_rx_ol_in_concurrency(false);
5092 	};
5093 
5094 	/* Disable RPS if SAP interface has come up */
5095 	if (policy_mgr_get_sap_mode_count(psoc, NULL) == 0) {
5096 		if (pm_ctx->dp_cbacks.hdd_set_rx_mode_rps_cb)
5097 			pm_ctx->dp_cbacks.hdd_set_rx_mode_rps_cb(false);
5098 	}
5099 
5100 	policy_mgr_dump_current_concurrency(psoc);
5101 
5102 	/*
5103 	 * Check mode of entry being removed. Update mcc_mode only when STA
5104 	 * or SAP since IPA only cares about these two
5105 	 */
5106 	if (mode == QDF_STA_MODE || mode == QDF_SAP_MODE) {
5107 		mcc_mode = policy_mgr_current_concurrency_is_mcc(psoc);
5108 
5109 		if (pm_ctx->dp_cbacks.hdd_ipa_set_mcc_mode_cb)
5110 			pm_ctx->dp_cbacks.hdd_ipa_set_mcc_mode_cb(mcc_mode);
5111 	}
5112 
5113 	if (mode == QDF_SAP_MODE || mode == QDF_P2P_GO_MODE ||
5114 	    mode == QDF_STA_MODE || mode == QDF_P2P_CLIENT_MODE)
5115 		policy_mgr_update_dfs_master_dynamic_enabled(psoc, session_id);
5116 
5117 	if (!pm_ctx->last_disconn_sta_freq) {
5118 		if (policy_mgr_update_indoor_concurrency(psoc, session_id,
5119 		    cur_freq, DISCONNECT_WITHOUT_CONCURRENCY))
5120 			wlan_reg_recompute_current_chan_list(psoc,
5121 							     pm_ctx->pdev);
5122 	}
5123 
5124 	if (wlan_reg_get_keep_6ghz_sta_cli_connection(pm_ctx->pdev) &&
5125 	    (mode == QDF_STA_MODE || mode == QDF_P2P_CLIENT_MODE))
5126 		wlan_reg_recompute_current_chan_list(psoc, pm_ctx->pdev);
5127 
5128 	return qdf_status;
5129 }
5130 
5131 QDF_STATUS policy_mgr_incr_connection_count(struct wlan_objmgr_psoc *psoc,
5132 					    uint32_t vdev_id,
5133 					    enum QDF_OPMODE op_mode)
5134 {
5135 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
5136 	uint32_t conn_index;
5137 	struct policy_mgr_vdev_entry_info conn_table_entry = {0};
5138 	enum policy_mgr_chain_mode chain_mask = POLICY_MGR_ONE_ONE;
5139 	uint8_t nss_2g = 0, nss_5g = 0;
5140 	enum policy_mgr_con_mode mode;
5141 	uint32_t ch_freq;
5142 	uint32_t nss = 0;
5143 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5144 	bool update_conn = true;
5145 
5146 	pm_ctx = policy_mgr_get_context(psoc);
5147 	if (!pm_ctx) {
5148 		policy_mgr_err("context is NULL");
5149 		return status;
5150 	}
5151 
5152 	conn_index = policy_mgr_get_connection_count(psoc);
5153 	if (pm_ctx->cfg.max_conc_cxns < conn_index) {
5154 		policy_mgr_err("exceeded max connection limit %d",
5155 			pm_ctx->cfg.max_conc_cxns);
5156 		return status;
5157 	}
5158 
5159 	if (op_mode == QDF_NAN_DISC_MODE) {
5160 		status = wlan_nan_get_connection_info(psoc, &conn_table_entry);
5161 		if (QDF_IS_STATUS_ERROR(status)) {
5162 			policy_mgr_err("Can't get NAN Connection info");
5163 			return status;
5164 		}
5165 	} else if (pm_ctx->wma_cbacks.wma_get_connection_info) {
5166 		status = pm_ctx->wma_cbacks.wma_get_connection_info(
5167 				vdev_id, &conn_table_entry);
5168 		if (QDF_STATUS_SUCCESS != status) {
5169 			policy_mgr_err("can't find vdev_id %d in connection table",
5170 			vdev_id);
5171 			return status;
5172 		}
5173 	} else {
5174 		policy_mgr_err("wma_get_connection_info is NULL");
5175 		return QDF_STATUS_E_FAILURE;
5176 	}
5177 
5178 	mode =  policy_mgr_qdf_opmode_to_pm_con_mode(psoc, op_mode, vdev_id);
5179 
5180 	ch_freq = conn_table_entry.mhz;
5181 	status = policy_mgr_get_nss_for_vdev(psoc, mode, &nss_2g, &nss_5g);
5182 	if (QDF_IS_STATUS_SUCCESS(status)) {
5183 		if ((WLAN_REG_IS_24GHZ_CH_FREQ(ch_freq) && nss_2g > 1) ||
5184 		    (WLAN_REG_IS_5GHZ_CH_FREQ(ch_freq) && nss_5g > 1))
5185 			chain_mask = POLICY_MGR_TWO_TWO;
5186 		else
5187 			chain_mask = POLICY_MGR_ONE_ONE;
5188 		nss = (WLAN_REG_IS_24GHZ_CH_FREQ(ch_freq)) ? nss_2g : nss_5g;
5189 	} else {
5190 		policy_mgr_err("Error in getting nss");
5191 	}
5192 
5193 	if (mode == PM_STA_MODE || mode == PM_P2P_CLIENT_MODE)
5194 		update_conn = false;
5195 
5196 	/* add the entry */
5197 	policy_mgr_update_conc_list(psoc, conn_index,
5198 			mode,
5199 			ch_freq,
5200 			policy_mgr_get_bw(conn_table_entry.chan_width),
5201 			conn_table_entry.mac_id,
5202 			chain_mask,
5203 			nss, vdev_id, true, update_conn,
5204 			conn_table_entry.ch_flagext);
5205 	policy_mgr_debug("Add at idx:%d vdev %d mac=%d",
5206 		conn_index, vdev_id,
5207 		conn_table_entry.mac_id);
5208 
5209 	return QDF_STATUS_SUCCESS;
5210 }
5211 
5212 QDF_STATUS policy_mgr_decr_connection_count(struct wlan_objmgr_psoc *psoc,
5213 					uint32_t vdev_id)
5214 {
5215 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
5216 	uint32_t conn_index = 0, next_conn_index = 0;
5217 	bool found = false;
5218 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5219 	bool panic = false;
5220 
5221 	pm_ctx = policy_mgr_get_context(psoc);
5222 	if (!pm_ctx) {
5223 		policy_mgr_err("Invalid Context");
5224 		return status;
5225 	}
5226 
5227 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
5228 	while (PM_CONC_CONNECTION_LIST_VALID_INDEX(conn_index)) {
5229 		if (vdev_id == pm_conc_connection_list[conn_index].vdev_id) {
5230 			/* debug msg */
5231 			found = true;
5232 			break;
5233 		}
5234 		conn_index++;
5235 	}
5236 	if (!found) {
5237 		policy_mgr_err("can't find vdev_id %d in pm_conc_connection_list",
5238 			vdev_id);
5239 		qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5240 		return status;
5241 	}
5242 	next_conn_index = conn_index + 1;
5243 	while (PM_CONC_CONNECTION_LIST_VALID_INDEX(next_conn_index)) {
5244 		pm_conc_connection_list[conn_index].vdev_id =
5245 			pm_conc_connection_list[next_conn_index].vdev_id;
5246 		pm_conc_connection_list[conn_index].mode =
5247 			pm_conc_connection_list[next_conn_index].mode;
5248 		pm_conc_connection_list[conn_index].mac =
5249 			pm_conc_connection_list[next_conn_index].mac;
5250 		pm_conc_connection_list[conn_index].freq =
5251 			pm_conc_connection_list[next_conn_index].freq;
5252 		pm_conc_connection_list[conn_index].bw =
5253 			pm_conc_connection_list[next_conn_index].bw;
5254 		pm_conc_connection_list[conn_index].chain_mask =
5255 			pm_conc_connection_list[next_conn_index].chain_mask;
5256 		pm_conc_connection_list[conn_index].original_nss =
5257 			pm_conc_connection_list[next_conn_index].original_nss;
5258 		pm_conc_connection_list[conn_index].in_use =
5259 			pm_conc_connection_list[next_conn_index].in_use;
5260 		pm_conc_connection_list[conn_index].ch_flagext =
5261 			pm_conc_connection_list[next_conn_index].ch_flagext;
5262 		conn_index++;
5263 		next_conn_index++;
5264 	}
5265 
5266 	/* clean up the entry */
5267 	qdf_mem_zero(&pm_conc_connection_list[next_conn_index - 1],
5268 		sizeof(*pm_conc_connection_list));
5269 
5270 	conn_index = 0;
5271 	while (PM_CONC_CONNECTION_LIST_VALID_INDEX(conn_index)) {
5272 		if (vdev_id == pm_conc_connection_list[conn_index].vdev_id) {
5273 			panic = true;
5274 			break;
5275 		}
5276 		conn_index++;
5277 	}
5278 
5279 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5280 	if (panic) {
5281 		policy_mgr_err("dup entry occur");
5282 		policy_mgr_debug_alert();
5283 	}
5284 	if (pm_ctx->conc_cbacks.connection_info_update)
5285 		pm_ctx->conc_cbacks.connection_info_update();
5286 
5287 	return QDF_STATUS_SUCCESS;
5288 }
5289 
5290 uint32_t policy_mgr_get_mode_specific_conn_info(
5291 		struct wlan_objmgr_psoc *psoc,
5292 		uint32_t *ch_freq_list, uint8_t *vdev_id,
5293 		enum policy_mgr_con_mode mode)
5294 {
5295 
5296 	uint32_t count = 0, index = 0;
5297 	uint32_t list[MAX_NUMBER_OF_CONC_CONNECTIONS];
5298 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5299 
5300 	pm_ctx = policy_mgr_get_context(psoc);
5301 	if (!pm_ctx) {
5302 		policy_mgr_err("Invalid Context");
5303 		return count;
5304 	}
5305 	if (!vdev_id) {
5306 		policy_mgr_err("Null pointer error");
5307 		return count;
5308 	}
5309 
5310 	count = policy_mgr_mode_specific_connection_count(
5311 				psoc, mode, list);
5312 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
5313 	if (count == 1) {
5314 		if (ch_freq_list)
5315 			*ch_freq_list =
5316 				pm_conc_connection_list[list[index]].freq;
5317 		*vdev_id =
5318 			pm_conc_connection_list[list[index]].vdev_id;
5319 	} else {
5320 		for (index = 0; index < count; index++) {
5321 			if (ch_freq_list)
5322 				ch_freq_list[index] =
5323 			pm_conc_connection_list[list[index]].freq;
5324 
5325 			vdev_id[index] =
5326 			pm_conc_connection_list[list[index]].vdev_id;
5327 		}
5328 	}
5329 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5330 
5331 	return count;
5332 }
5333 
5334 uint32_t policy_mgr_get_sap_mode_info(struct wlan_objmgr_psoc *psoc,
5335 				      uint32_t *ch_freq_list, uint8_t *vdev_id)
5336 {
5337 	uint32_t count;
5338 
5339 	count = policy_mgr_get_mode_specific_conn_info(psoc, ch_freq_list,
5340 						       vdev_id, PM_SAP_MODE);
5341 
5342 	count += policy_mgr_get_mode_specific_conn_info(
5343 				psoc,
5344 				ch_freq_list ? &ch_freq_list[count] : NULL,
5345 				vdev_id ? &vdev_id[count] : NULL,
5346 				PM_LL_LT_SAP_MODE);
5347 	return count;
5348 }
5349 
5350 uint32_t policy_mgr_get_beaconing_mode_info(struct wlan_objmgr_psoc *psoc,
5351 					    uint32_t *ch_freq_list,
5352 					    uint8_t *vdev_id)
5353 {
5354 	uint32_t count;
5355 
5356 	count = policy_mgr_get_sap_mode_info(psoc, ch_freq_list, vdev_id);
5357 
5358 	count += policy_mgr_get_mode_specific_conn_info(
5359 				psoc,
5360 				ch_freq_list ? &ch_freq_list[count] : NULL,
5361 				vdev_id ? &vdev_id[count] : NULL,
5362 				PM_P2P_GO_MODE);
5363 	return count;
5364 }
5365 
5366 void policy_mgr_get_ml_and_non_ml_sta_count(struct wlan_objmgr_psoc *psoc,
5367 					    uint8_t *num_ml, uint8_t *ml_idx,
5368 					    uint8_t *num_non_ml,
5369 					    uint8_t *non_ml_idx,
5370 					    qdf_freq_t *freq_list,
5371 					    uint8_t *vdev_id_list)
5372 {
5373 	uint32_t sta_num = 0;
5374 	uint8_t i;
5375 	struct wlan_objmgr_vdev *temp_vdev;
5376 
5377 	*num_ml = 0;
5378 	*num_non_ml = 0;
5379 
5380 	sta_num = policy_mgr_get_mode_specific_conn_info(psoc, freq_list,
5381 							 vdev_id_list,
5382 							 PM_STA_MODE);
5383 	if (!sta_num)
5384 		return;
5385 
5386 	for (i = 0; i < sta_num; i++) {
5387 		temp_vdev =
5388 			wlan_objmgr_get_vdev_by_id_from_psoc(psoc,
5389 							    vdev_id_list[i],
5390 							    WLAN_POLICY_MGR_ID);
5391 		if (!temp_vdev) {
5392 			policy_mgr_err("invalid vdev for id %d",
5393 				       vdev_id_list[i]);
5394 			*num_ml = 0;
5395 			*num_non_ml = 0;
5396 			return;
5397 		}
5398 
5399 		if (wlan_vdev_mlme_is_mlo_vdev(temp_vdev)) {
5400 			if (ml_idx)
5401 				ml_idx[*num_ml] = i;
5402 			(*num_ml)++;
5403 		} else {
5404 			if (non_ml_idx)
5405 				non_ml_idx[*num_non_ml] = i;
5406 			(*num_non_ml)++;
5407 		}
5408 
5409 		wlan_objmgr_vdev_release_ref(temp_vdev, WLAN_POLICY_MGR_ID);
5410 	}
5411 }
5412 
5413 bool policy_mgr_concurrent_sta_on_different_mac(struct wlan_objmgr_psoc *psoc)
5414 {
5415 	uint8_t num_ml = 0, num_non_ml = 0;
5416 	uint8_t ml_idx[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
5417 	uint8_t non_ml_idx[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
5418 	qdf_freq_t freq_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
5419 	uint8_t vdev_id_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
5420 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5421 	bool is_different_mac = false;
5422 	int i;
5423 
5424 	if (!policy_mgr_is_hw_dbs_capable(psoc))
5425 		return false;
5426 
5427 	pm_ctx = policy_mgr_get_context(psoc);
5428 	if (!pm_ctx) {
5429 		policy_mgr_err("Invalid Context");
5430 		return false;
5431 	}
5432 
5433 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
5434 	policy_mgr_get_ml_and_non_ml_sta_count(psoc, &num_ml, ml_idx,
5435 					       &num_non_ml, non_ml_idx,
5436 					       freq_list, vdev_id_list);
5437 	if (num_ml + num_non_ml < 2 || !num_non_ml)
5438 		goto out;
5439 
5440 	/*
5441 	 * If more than 1 Non-ML STA is present, check whether they are
5442 	 * within the same band.
5443 	 */
5444 	for (i = 1; i < num_non_ml; i++) {
5445 		if (!policy_mgr_2_freq_always_on_same_mac(psoc,
5446 							  freq_list[non_ml_idx[i]],
5447 							  freq_list[non_ml_idx[0]])) {
5448 			is_different_mac = true;
5449 			goto out;
5450 		}
5451 	}
5452 
5453 	if (num_non_ml >= 2)
5454 		goto out;
5455 
5456 	/* ML STA + Non-ML STA */
5457 	for (i = 0; i < num_ml; i++) {
5458 		if (!policy_mgr_2_freq_always_on_same_mac(psoc,
5459 							  freq_list[ml_idx[i]],
5460 							  freq_list[non_ml_idx[0]])) {
5461 			is_different_mac = true;
5462 			goto out;
5463 		}
5464 	}
5465 
5466 out:
5467 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5468 	policy_mgr_debug("Non-ML STA count %d, ML STA count %d, sta concurrency on different mac %d",
5469 			 num_non_ml, num_ml, is_different_mac);
5470 
5471 	return is_different_mac;
5472 }
5473 
5474 bool policy_mgr_max_concurrent_connections_reached(
5475 		struct wlan_objmgr_psoc *psoc)
5476 {
5477 	uint8_t i = 0, j = 0;
5478 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5479 
5480 	pm_ctx = policy_mgr_get_context(psoc);
5481 	if (pm_ctx) {
5482 		for (i = 0; i < QDF_MAX_NO_OF_MODE; i++)
5483 			j += pm_ctx->no_of_active_sessions[i];
5484 		return j >
5485 			(pm_ctx->cfg.max_conc_cxns - 1);
5486 	}
5487 
5488 	return false;
5489 }
5490 
5491 static bool policy_mgr_is_sub_20_mhz_enabled(struct wlan_objmgr_psoc *psoc)
5492 {
5493 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5494 
5495 	pm_ctx = policy_mgr_get_context(psoc);
5496 	if (!pm_ctx) {
5497 		policy_mgr_err("Invalid Context");
5498 		return false;
5499 	}
5500 
5501 	return pm_ctx->user_cfg.sub_20_mhz_enabled;
5502 }
5503 
5504 /**
5505  * policy_mgr_allow_wapi_concurrency() - Check if WAPI concurrency is allowed
5506  * @pm_ctx: policy_mgr_psoc_priv_obj policy mgr context
5507  *
5508  * This routine is called to check vdev security mode allowed in concurrency.
5509  * At present, WAPI security mode is not allowed to run concurrency with any
5510  * other vdev if the hardware doesn't support WAPI concurrency.
5511  *
5512  * Return: true - allow
5513  */
5514 static bool
5515 policy_mgr_allow_wapi_concurrency(struct policy_mgr_psoc_priv_obj *pm_ctx)
5516 {
5517 	struct wlan_objmgr_pdev *pdev = pm_ctx->pdev;
5518 	struct wmi_unified *wmi_handle;
5519 	struct wlan_objmgr_psoc *psoc;
5520 
5521 	if (!pdev) {
5522 		policy_mgr_debug("pdev is Null");
5523 		return false;
5524 	}
5525 
5526 	psoc = wlan_pdev_get_psoc(pdev);
5527 	if (!psoc)
5528 		return false;
5529 
5530 	wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
5531 	if (!wmi_handle) {
5532 		policy_mgr_debug("Invalid WMI handle");
5533 		return false;
5534 	}
5535 
5536 	if (!wmi_service_enabled(wmi_handle,
5537 				 wmi_service_wapi_concurrency_supported) &&
5538 	    mlme_is_wapi_sta_active(pdev) &&
5539 	    policy_mgr_get_connection_count(pm_ctx->psoc) > 0)
5540 		return false;
5541 
5542 	return true;
5543 }
5544 
5545 #ifdef FEATURE_FOURTH_CONNECTION
5546 static bool policy_mgr_is_concurrency_allowed_4_port(
5547 					struct wlan_objmgr_psoc *psoc,
5548 					enum policy_mgr_con_mode mode,
5549 					uint32_t ch_freq,
5550 					struct policy_mgr_pcl_list pcl)
5551 {
5552 	uint32_t i;
5553 	struct policy_mgr_psoc_priv_obj *pm_ctx = NULL;
5554 	uint8_t sap_cnt, go_cnt;
5555 
5556 	/* new STA may just have ssid, no channel until bssid assigned */
5557 	if (ch_freq == 0 && mode == PM_STA_MODE)
5558 		return true;
5559 
5560 	sap_cnt = policy_mgr_mode_specific_connection_count(psoc,
5561 							    PM_SAP_MODE, NULL);
5562 
5563 	go_cnt = policy_mgr_mode_specific_connection_count(psoc,
5564 							   PM_P2P_GO_MODE, NULL);
5565 	if (sap_cnt || go_cnt) {
5566 		pm_ctx = policy_mgr_get_context(psoc);
5567 		if (!pm_ctx) {
5568 			policy_mgr_err("context is NULL");
5569 			return false;
5570 		}
5571 
5572 		if (!policy_mgr_is_force_scc(psoc)) {
5573 			policy_mgr_err("couldn't start 4th port for bad force scc cfg");
5574 			return false;
5575 		}
5576 
5577 		if (!policy_mgr_is_dbs_enable(psoc) ||
5578 		    !pm_ctx->cfg.sta_sap_scc_on_dfs_chnl  ||
5579 		    !pm_ctx->cfg.sta_sap_scc_on_lte_coex_chnl) {
5580 			policy_mgr_err(
5581 				"Couldn't start 4th port for bad cfg of dual mac, dfs scc, lte coex scc");
5582 			return false;
5583 		}
5584 		for (i = 0; i < pcl.pcl_len; i++)
5585 			if (ch_freq == pcl.pcl_list[i])
5586 				return true;
5587 
5588 		policy_mgr_err("4th port failed on ch freq %d with mode %d",
5589 			       ch_freq, mode);
5590 
5591 		return false;
5592 	}
5593 
5594 	return true;
5595 }
5596 #else
5597 static inline bool policy_mgr_is_concurrency_allowed_4_port(
5598 				struct wlan_objmgr_psoc *psoc,
5599 				enum policy_mgr_con_mode mode,
5600 				uint32_t ch_freq,
5601 				struct policy_mgr_pcl_list pcl)
5602 {return false; }
5603 #endif
5604 
5605 bool
5606 policy_mgr_allow_multiple_sta_connections(struct wlan_objmgr_psoc *psoc)
5607 {
5608 	struct wmi_unified *wmi_handle;
5609 
5610 	wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
5611 	if (!wmi_handle) {
5612 		policy_mgr_debug("Invalid WMI handle");
5613 		return false;
5614 	}
5615 	if (!wmi_service_enabled(wmi_handle,
5616 				 wmi_service_sta_plus_sta_support)) {
5617 		policy_mgr_rl_debug("STA+STA is not supported");
5618 		return false;
5619 	}
5620 
5621 	return true;
5622 }
5623 
5624 #if defined(CONFIG_BAND_6GHZ) && defined(WLAN_FEATURE_11AX)
5625 bool policy_mgr_is_6ghz_conc_mode_supported(
5626 	struct wlan_objmgr_psoc *psoc, enum policy_mgr_con_mode mode)
5627 {
5628 	if (mode == PM_STA_MODE || mode == PM_SAP_MODE ||
5629 	    mode == PM_P2P_CLIENT_MODE || mode == PM_P2P_GO_MODE)
5630 		return true;
5631 	else
5632 		return false;
5633 }
5634 #endif
5635 
5636 /**
5637  * policy_mgr_is_6g_channel_allowed() - Check new 6Ghz connection
5638  * allowed or not
5639  * @psoc: Pointer to soc
5640  * @mode: new connection mode
5641  * @ch_freq: channel freq
5642  *
5643  * 1. Only STA/SAP are allowed on 6Ghz.
5644  * 2. If there is DFS beacon entity existing on 5G band, 5G+6G MCC is not
5645  * allowed.
5646  *
5647  *  Return: true if supports else false.
5648  */
5649 static bool policy_mgr_is_6g_channel_allowed(
5650 	struct wlan_objmgr_psoc *psoc, enum policy_mgr_con_mode mode,
5651 	uint32_t ch_freq)
5652 {
5653 	uint32_t conn_index = 0;
5654 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5655 	struct policy_mgr_conc_connection_info *conn;
5656 	bool is_dfs;
5657 
5658 	pm_ctx = policy_mgr_get_context(psoc);
5659 	if (!pm_ctx) {
5660 		policy_mgr_err("Invalid Context");
5661 		return false;
5662 	}
5663 	if (!WLAN_REG_IS_6GHZ_CHAN_FREQ(ch_freq)) {
5664 		policy_mgr_rl_debug("Not a 6Ghz channel Freq");
5665 		return true;
5666 	}
5667 	/* Only STA/SAP is supported on 6Ghz currently */
5668 	if (!policy_mgr_is_6ghz_conc_mode_supported(psoc, mode)) {
5669 		policy_mgr_rl_debug("mode %d for 6ghz not supported", mode);
5670 		return false;
5671 	}
5672 
5673 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
5674 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
5675 				conn_index++) {
5676 		conn = &pm_conc_connection_list[conn_index];
5677 		if (!conn->in_use)
5678 			continue;
5679 		is_dfs = (conn->ch_flagext &
5680 			(IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) &&
5681 			WLAN_REG_IS_5GHZ_CH_FREQ(conn->freq);
5682 		if (policy_mgr_is_beaconing_mode(conn->mode) &&
5683 		    is_dfs && (ch_freq != conn->freq &&
5684 			       !policy_mgr_are_sbs_chan(psoc, ch_freq,
5685 							conn->freq))) {
5686 			policy_mgr_rl_debug("don't allow MCC if SAP/GO on DFS channel");
5687 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5688 			return false;
5689 		}
5690 	}
5691 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5692 
5693 	return true;
5694 }
5695 
5696 #ifdef WLAN_FEATURE_11BE_MLO
5697 static bool policy_mgr_is_acs_2ghz_only_sap(struct wlan_objmgr_psoc *psoc,
5698 					    uint8_t sap_vdev_id)
5699 {
5700 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5701 	uint32_t acs_band = QCA_ACS_MODE_IEEE80211ANY;
5702 
5703 	pm_ctx = policy_mgr_get_context(psoc);
5704 	if (!pm_ctx) {
5705 		policy_mgr_err("Invalid Context");
5706 		return false;
5707 	}
5708 
5709 	if (pm_ctx->hdd_cbacks.wlan_get_sap_acs_band)
5710 		pm_ctx->hdd_cbacks.wlan_get_sap_acs_band(psoc,
5711 							 sap_vdev_id,
5712 							 &acs_band);
5713 
5714 	if (acs_band == QCA_ACS_MODE_IEEE80211B ||
5715 	    acs_band == QCA_ACS_MODE_IEEE80211G)
5716 		return true;
5717 
5718 	return false;
5719 }
5720 
5721 bool policy_mgr_vdev_is_force_inactive(struct wlan_objmgr_psoc *psoc,
5722 				       uint8_t vdev_id)
5723 {
5724 	bool force_inactive = false;
5725 	uint8_t conn_index;
5726 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5727 
5728 	pm_ctx = policy_mgr_get_context(psoc);
5729 	if (!pm_ctx) {
5730 		policy_mgr_err("Invalid Context");
5731 		return false;
5732 	}
5733 
5734 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
5735 	/* Get disabled link info as well and keep it at last */
5736 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_DISABLE_LINK;
5737 	     conn_index++) {
5738 		if (pm_disabled_ml_links[conn_index].in_use &&
5739 		    pm_disabled_ml_links[conn_index].mode == PM_STA_MODE &&
5740 		    pm_disabled_ml_links[conn_index].vdev_id == vdev_id) {
5741 			force_inactive = true;
5742 			break;
5743 		}
5744 	}
5745 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5746 
5747 	return force_inactive;
5748 }
5749 
5750 /* MCC avoidance priority value for different legacy connection type.
5751  * Internal macro, not expected used other code.
5752  * Bigger value have higher priority.
5753  */
5754 #define PRIORITY_STA	3
5755 #define PRIORITY_SAP	2
5756 #define PRIORITY_P2P	1
5757 #define PRIORITY_OTHER	0
5758 
5759 uint8_t
5760 policy_mgr_get_legacy_conn_info(struct wlan_objmgr_psoc *psoc,
5761 				uint8_t *vdev_lst,
5762 				qdf_freq_t *freq_lst,
5763 				enum policy_mgr_con_mode *mode_lst,
5764 				uint8_t lst_sz)
5765 {
5766 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5767 	uint8_t conn_index, j = 0, i, k, n;
5768 	struct wlan_objmgr_vdev *vdev;
5769 	uint8_t vdev_id;
5770 	uint8_t has_priority[MAX_NUMBER_OF_CONC_CONNECTIONS];
5771 
5772 	pm_ctx = policy_mgr_get_context(psoc);
5773 	if (!pm_ctx) {
5774 		policy_mgr_err("Invalid Context");
5775 		return 0;
5776 	}
5777 
5778 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
5779 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
5780 	     conn_index++) {
5781 		if (j >= lst_sz)
5782 			break;
5783 		if (!pm_conc_connection_list[conn_index].in_use)
5784 			continue;
5785 		vdev_id = pm_conc_connection_list[conn_index].vdev_id;
5786 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
5787 				pm_ctx->psoc, vdev_id, WLAN_POLICY_MGR_ID);
5788 		if (!vdev) {
5789 			policy_mgr_err("invalid vdev for id %d", vdev_id);
5790 			continue;
5791 		}
5792 
5793 		if (wlan_vdev_mlme_is_mlo_vdev(vdev) &&
5794 		    pm_conc_connection_list[conn_index].mode ==
5795 							PM_STA_MODE) {
5796 			wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
5797 			continue;
5798 		}
5799 		if (pm_conc_connection_list[conn_index].mode !=
5800 							PM_STA_MODE &&
5801 		    pm_conc_connection_list[conn_index].mode !=
5802 							PM_SAP_MODE &&
5803 		    pm_conc_connection_list[conn_index].mode !=
5804 							PM_P2P_CLIENT_MODE &&
5805 		    pm_conc_connection_list[conn_index].mode !=
5806 							PM_P2P_GO_MODE) {
5807 			wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
5808 			continue;
5809 		}
5810 
5811 		/* Set mcc avoidance priority value. The bigger value
5812 		 * have higher priority to avoid MCC. In 3 Port concurrency
5813 		 * case, usually we can only meet the higher priority intf's
5814 		 * MCC avoidance by force inactive link.
5815 		 */
5816 		if (pm_conc_connection_list[conn_index].mode == PM_STA_MODE)
5817 			has_priority[j] = PRIORITY_STA;
5818 		else if (pm_conc_connection_list[conn_index].mode ==
5819 							PM_SAP_MODE &&
5820 			 policy_mgr_is_acs_2ghz_only_sap(psoc, vdev_id))
5821 			has_priority[j] = PRIORITY_SAP;
5822 		else if ((pm_conc_connection_list[conn_index].mode ==
5823 							PM_P2P_CLIENT_MODE ||
5824 			  pm_conc_connection_list[conn_index].mode ==
5825 							PM_P2P_GO_MODE) &&
5826 			 policy_mgr_is_vdev_high_tput_or_low_latency(
5827 							psoc, vdev_id))
5828 			has_priority[j] = PRIORITY_P2P;
5829 		else
5830 			has_priority[j] = PRIORITY_OTHER;
5831 
5832 		vdev_lst[j] = vdev_id;
5833 		freq_lst[j] = pm_conc_connection_list[conn_index].freq;
5834 		mode_lst[j] = pm_conc_connection_list[conn_index].mode;
5835 		policy_mgr_debug("vdev %d freq %d mode %s pri %d",
5836 				 vdev_id, freq_lst[j],
5837 				 device_mode_to_string(mode_lst[j]),
5838 				 has_priority[j]);
5839 		j++;
5840 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
5841 	}
5842 	/* sort the list based on priority */
5843 	for (i = 0; i < j; i++) {
5844 		uint8_t tmp_vdev_lst;
5845 		qdf_freq_t tmp_freq_lst;
5846 		enum policy_mgr_con_mode tmp_mode_lst;
5847 
5848 		n = i;
5849 		for (k = i + 1; k < j; k++) {
5850 			if (has_priority[n] < has_priority[k])
5851 				n = k;
5852 			else if ((has_priority[n] == has_priority[k]) &&
5853 				 (vdev_lst[n] > vdev_lst[k]))
5854 				n = k;
5855 		}
5856 		if (n == i)
5857 			continue;
5858 		tmp_vdev_lst = vdev_lst[i];
5859 		tmp_freq_lst = freq_lst[i];
5860 		tmp_mode_lst = mode_lst[i];
5861 
5862 		vdev_lst[i] = vdev_lst[n];
5863 		freq_lst[i] = freq_lst[n];
5864 		mode_lst[i] = mode_lst[n];
5865 
5866 		vdev_lst[n] = tmp_vdev_lst;
5867 		freq_lst[n] = tmp_freq_lst;
5868 		mode_lst[n] = tmp_mode_lst;
5869 	}
5870 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
5871 
5872 	return j;
5873 }
5874 
5875 static void
5876 policy_mgr_fill_ml_active_link_vdev_bitmap(struct mlo_link_set_active_req *req,
5877 					   uint8_t *mlo_vdev_lst,
5878 					   uint32_t num_mlo_vdev)
5879 {
5880 	uint32_t entry_idx, entry_offset, vdev_idx;
5881 	uint8_t vdev_id;
5882 
5883 	for (vdev_idx = 0; vdev_idx < num_mlo_vdev; vdev_idx++) {
5884 		vdev_id = mlo_vdev_lst[vdev_idx];
5885 		entry_idx = vdev_id / 32;
5886 		entry_offset = vdev_id % 32;
5887 		if (entry_idx >= MLO_LINK_NUM_SZ) {
5888 			policy_mgr_err("Invalid entry_idx %d num_mlo_vdev %d vdev %d",
5889 				       entry_idx, num_mlo_vdev, vdev_id);
5890 			continue;
5891 		}
5892 		req->param.vdev_bitmap[entry_idx] |= (1 << entry_offset);
5893 		/* update entry number if entry index changed */
5894 		if (req->param.num_vdev_bitmap < entry_idx + 1)
5895 			req->param.num_vdev_bitmap = entry_idx + 1;
5896 	}
5897 
5898 	policy_mgr_debug("num_vdev_bitmap %d vdev_bitmap[0] = 0x%x, vdev_bitmap[1] = 0x%x",
5899 			 req->param.num_vdev_bitmap, req->param.vdev_bitmap[0],
5900 			 req->param.vdev_bitmap[1]);
5901 }
5902 
5903 static void
5904 policy_mgr_fill_ml_inactive_link_vdev_bitmap(
5905 				struct mlo_link_set_active_req *req,
5906 				uint8_t *mlo_inactive_vdev_lst,
5907 				uint32_t num_mlo_inactive_vdev)
5908 {
5909 	uint32_t entry_idx, entry_offset, vdev_idx;
5910 	uint8_t vdev_id;
5911 
5912 	for (vdev_idx = 0; vdev_idx < num_mlo_inactive_vdev; vdev_idx++) {
5913 		vdev_id = mlo_inactive_vdev_lst[vdev_idx];
5914 		entry_idx = vdev_id / 32;
5915 		entry_offset = vdev_id % 32;
5916 		if (entry_idx >= MLO_LINK_NUM_SZ) {
5917 			policy_mgr_err("Invalid entry_idx %d num_mlo_vdev %d vdev %d",
5918 				       entry_idx, num_mlo_inactive_vdev,
5919 				       vdev_id);
5920 			continue;
5921 		}
5922 		req->param.inactive_vdev_bitmap[entry_idx] |=
5923 							(1 << entry_offset);
5924 		/* update entry number if entry index changed */
5925 		if (req->param.num_inactive_vdev_bitmap < entry_idx + 1)
5926 			req->param.num_inactive_vdev_bitmap = entry_idx + 1;
5927 	}
5928 
5929 	policy_mgr_debug("num_vdev_bitmap %d inactive_vdev_bitmap[0] = 0x%x, inactive_vdev_bitmap[1] = 0x%x",
5930 			 req->param.num_inactive_vdev_bitmap,
5931 			 req->param.inactive_vdev_bitmap[0],
5932 			 req->param.inactive_vdev_bitmap[1]);
5933 }
5934 
5935 /*
5936  * policy_mgr_handle_ml_sta_link_state_allowed() - Check ml sta connection to
5937  * allow link state change.
5938  * @psoc: psoc object
5939  * @reason: set link state reason
5940  *
5941  * If ml sta is not "connected" state, no need to do link state handling.
5942  * After disconnected, target will clear the force active/inactive state
5943  * and host will remove the connection entry finally.
5944  * After roaming done, active/inactive will be re-calculated.
5945  *
5946  * Return: QDF_STATUS_SUCCESS if link state is allowed to change
5947  */
5948 static QDF_STATUS
5949 policy_mgr_handle_ml_sta_link_state_allowed(struct wlan_objmgr_psoc *psoc,
5950 					    enum mlo_link_force_reason reason)
5951 {
5952 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0, num_non_ml = 0;
5953 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
5954 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
5955 	struct policy_mgr_psoc_priv_obj *pm_ctx;
5956 	struct wlan_objmgr_vdev *vdev;
5957 	bool ml_sta_is_not_connected = false;
5958 	bool ml_sta_is_link_removal = false;
5959 	uint8_t i;
5960 	QDF_STATUS status = QDF_STATUS_SUCCESS;
5961 
5962 	pm_ctx = policy_mgr_get_context(psoc);
5963 	if (!pm_ctx) {
5964 		policy_mgr_err("Invalid Context");
5965 		return QDF_STATUS_E_INVAL;
5966 	}
5967 
5968 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
5969 				   ml_sta_vdev_lst, ml_freq_lst, &num_non_ml,
5970 				   NULL, NULL);
5971 	if (!num_ml_sta || num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS) {
5972 		policy_mgr_debug("ml sta num is %d", num_ml_sta);
5973 		return QDF_STATUS_E_INVAL;
5974 	}
5975 
5976 	for (i = 0; i < num_ml_sta; i++) {
5977 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(pm_ctx->psoc,
5978 							    ml_sta_vdev_lst[i],
5979 							    WLAN_POLICY_MGR_ID);
5980 		if (!vdev) {
5981 			policy_mgr_err("invalid vdev for id %d",
5982 				       ml_sta_vdev_lst[i]);
5983 			continue;
5984 		}
5985 		if (!wlan_cm_is_vdev_connected(vdev)) {
5986 			policy_mgr_debug("ml sta vdev %d is not connected state",
5987 					 ml_sta_vdev_lst[i]);
5988 			ml_sta_is_not_connected = true;
5989 		}
5990 		if (wlan_get_vdev_link_removed_flag_by_vdev_id(
5991 						psoc, ml_sta_vdev_lst[i])) {
5992 			policy_mgr_debug("ml sta vdev %d link removed",
5993 					 ml_sta_vdev_lst[i]);
5994 			ml_sta_is_link_removal = true;
5995 		}
5996 
5997 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
5998 	}
5999 
6000 	if (ml_sta_is_not_connected)
6001 		status = QDF_STATUS_E_FAILURE;
6002 	else if (reason == MLO_LINK_FORCE_REASON_LINK_REMOVAL) {
6003 		if (!ml_sta_is_link_removal)
6004 			status = QDF_STATUS_E_FAILURE;
6005 	} else {
6006 		if (ml_sta_is_link_removal)
6007 			status = QDF_STATUS_E_FAILURE;
6008 	}
6009 	policy_mgr_debug("set link reason %d status %d", reason, status);
6010 
6011 	return status;
6012 }
6013 
6014 /*
6015  * policy_mgr_validate_set_mlo_link_cb() - Callback to check whether
6016  * it is allowed to set mlo sta link state.
6017  * @psoc: psoc object
6018  * @param: set mlo link parameter
6019  *
6020  * This api will be used as callback to be called by mlo_link_set_active
6021  * in serialization context.
6022  *
6023  * Return: QDF_STATUS_SUCCESS if set mlo link is allowed
6024  */
6025 static QDF_STATUS
6026 policy_mgr_validate_set_mlo_link_cb(struct wlan_objmgr_psoc *psoc,
6027 				    struct mlo_link_set_active_param *param)
6028 {
6029 	return policy_mgr_handle_ml_sta_link_state_allowed(psoc,
6030 							   param->reason);
6031 }
6032 
6033 uint32_t
6034 policy_mgr_get_active_vdev_bitmap(struct wlan_objmgr_psoc *psoc)
6035 {
6036 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6037 
6038 	pm_ctx = policy_mgr_get_context(psoc);
6039 	if (!pm_ctx) {
6040 		policy_mgr_err("Invalid Context");
6041 		return QDF_STATUS_E_INVAL;
6042 	}
6043 
6044 	policy_mgr_debug("active link bitmap value: %d",
6045 			 pm_ctx->active_vdev_bitmap);
6046 
6047 	return pm_ctx->active_vdev_bitmap;
6048 }
6049 
6050 /**
6051  * policy_mgr_mlo_sta_set_link_by_linkid() - wrapper API to call set link
6052  * by link id bitmap API
6053  * @psoc: psoc object
6054  * @vdev: vdev object
6055  * @reason: Reason for which link is forced
6056  * @mode: Force reason
6057  * @link_num: valid for MLO_LINK_FORCE_MODE_ACTIVE_NUM and
6058  *  MLO_LINK_FORCE_MODE_INACTIVE_NUM.
6059  * @num_mlo_vdev: number of mlo vdev in array mlo_vdev_lst
6060  * @mlo_vdev_lst: MLO STA vdev list
6061  * @num_mlo_inactive_vdev: number of mlo vdev in array mlo_inactive_vdev_lst
6062  * @mlo_inactive_vdev_lst: MLO STA vdev list
6063  *
6064  * This is internal wrapper of policy_mgr_mlo_sta_set_nlink to convert
6065  * vdev based set link to link id based API for being compatible with old code.
6066  * New code to use policy_mgr_mlo_sta_set_nlink directly as much as possible.
6067  *
6068  * Return: QDF_STATUS
6069  */
6070 static QDF_STATUS
6071 policy_mgr_mlo_sta_set_link_by_linkid(struct wlan_objmgr_psoc *psoc,
6072 				      struct wlan_objmgr_vdev *vdev,
6073 				      enum mlo_link_force_reason reason,
6074 				      enum mlo_link_force_mode mode,
6075 				      uint8_t link_num,
6076 				      uint8_t num_mlo_vdev,
6077 				      uint8_t *mlo_vdev_lst,
6078 				      uint8_t num_mlo_inactive_vdev,
6079 				      uint8_t *mlo_inactive_vdev_lst)
6080 {
6081 	uint32_t link_bitmap = 0;
6082 	uint32_t link_bitmap2 = 0;
6083 	uint32_t assoc_bitmap = 0;
6084 	uint32_t vdev_bitmap[MLO_VDEV_BITMAP_SZ];
6085 	uint32_t vdev_bitmap2[MLO_VDEV_BITMAP_SZ];
6086 	uint8_t i, idx;
6087 	uint32_t link_control_flags = 0;
6088 
6089 	qdf_mem_zero(vdev_bitmap, sizeof(vdev_bitmap));
6090 	qdf_mem_zero(vdev_bitmap2, sizeof(vdev_bitmap2));
6091 
6092 	for (i = 0; i < num_mlo_vdev; i++) {
6093 		idx = mlo_vdev_lst[i] / 32;
6094 		if (idx >= MLO_VDEV_BITMAP_SZ)
6095 			return QDF_STATUS_E_INVAL;
6096 		vdev_bitmap[idx] |= 1 << (mlo_vdev_lst[i] % 32);
6097 	}
6098 
6099 	for (i = 0; i < num_mlo_inactive_vdev; i++) {
6100 		idx = mlo_inactive_vdev_lst[i] / 32;
6101 		if (idx >= MLO_VDEV_BITMAP_SZ)
6102 			return QDF_STATUS_E_INVAL;
6103 		vdev_bitmap2[idx] |= 1 << (mlo_inactive_vdev_lst[i] % 32);
6104 	}
6105 
6106 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
6107 		psoc, vdev, MLO_VDEV_BITMAP_SZ, vdev_bitmap,
6108 		&link_bitmap, &assoc_bitmap);
6109 
6110 	ml_nlink_convert_vdev_bitmap_to_linkid_bitmap(
6111 		psoc, vdev, MLO_VDEV_BITMAP_SZ, vdev_bitmap2,
6112 		&link_bitmap2, &assoc_bitmap);
6113 
6114 	switch (mode) {
6115 	case MLO_LINK_FORCE_MODE_ACTIVE:
6116 		link_control_flags = link_ctrl_f_overwrite_active_bitmap;
6117 		break;
6118 	case MLO_LINK_FORCE_MODE_INACTIVE:
6119 		if (reason != MLO_LINK_FORCE_REASON_LINK_REMOVAL)
6120 			link_control_flags =
6121 				link_ctrl_f_overwrite_inactive_bitmap;
6122 		break;
6123 	case MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE:
6124 		if (reason != MLO_LINK_FORCE_REASON_LINK_REMOVAL)
6125 			link_control_flags =
6126 				link_ctrl_f_overwrite_active_bitmap |
6127 				link_ctrl_f_overwrite_inactive_bitmap;
6128 		break;
6129 	case MLO_LINK_FORCE_MODE_ACTIVE_NUM:
6130 		link_control_flags = link_ctrl_f_dynamic_force_link_num;
6131 		break;
6132 	case MLO_LINK_FORCE_MODE_INACTIVE_NUM:
6133 		link_control_flags = link_ctrl_f_dynamic_force_link_num;
6134 		break;
6135 	case MLO_LINK_FORCE_MODE_NO_FORCE:
6136 		link_control_flags = 0;
6137 		break;
6138 	default:
6139 		policy_mgr_err("Invalid force mode: %d", mode);
6140 		return QDF_STATUS_E_INVAL;
6141 	}
6142 
6143 	return policy_mgr_mlo_sta_set_nlink(psoc, vdev, reason, mode,
6144 					    link_num, link_bitmap,
6145 					    link_bitmap2, link_control_flags);
6146 }
6147 
6148 /**
6149  * policy_mgr_mlo_sta_set_link_ext() - Set links for MLO STA
6150  * @psoc: psoc object
6151  * @reason: Reason for which link is forced
6152  * @mode: Force reason
6153  * @num_mlo_vdev: number of mlo vdev
6154  * @mlo_vdev_lst: MLO STA vdev list
6155  * @num_mlo_inactive_vdev: number of mlo vdev
6156  * @mlo_inactive_vdev_lst: MLO STA vdev list
6157  *
6158  * Interface manager Set links for MLO STA. And it supports to
6159  * add inactive vdev list.
6160  *
6161  * Return: QDF_STATUS
6162  */
6163 static QDF_STATUS
6164 policy_mgr_mlo_sta_set_link_ext(struct wlan_objmgr_psoc *psoc,
6165 				enum mlo_link_force_reason reason,
6166 				enum mlo_link_force_mode mode,
6167 				uint8_t num_mlo_vdev, uint8_t *mlo_vdev_lst,
6168 				uint8_t num_mlo_inactive_vdev,
6169 				uint8_t *mlo_inactive_vdev_lst)
6170 {
6171 	struct mlo_link_set_active_req *req;
6172 	QDF_STATUS status;
6173 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6174 	struct wlan_objmgr_vdev *vdev;
6175 
6176 	if (!num_mlo_vdev) {
6177 		policy_mgr_err("invalid 0 num_mlo_vdev");
6178 		return QDF_STATUS_E_INVAL;
6179 	}
6180 
6181 	pm_ctx = policy_mgr_get_context(psoc);
6182 	if (!pm_ctx) {
6183 		policy_mgr_err("Invalid Context");
6184 		return QDF_STATUS_E_INVAL;
6185 	}
6186 
6187 	req = qdf_mem_malloc(sizeof(*req));
6188 	if (!req)
6189 		return QDF_STATUS_E_NOMEM;
6190 
6191 	/*
6192 	 * Use one of the ML vdev as, if called from disconnect the caller vdev
6193 	 * may get deleted, and thus flush serialization command.
6194 	 */
6195 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, mlo_vdev_lst[0],
6196 						    WLAN_POLICY_MGR_ID);
6197 	if (!vdev) {
6198 		policy_mgr_err("vdev %d: invalid vdev", mlo_vdev_lst[0]);
6199 		qdf_mem_free(req);
6200 		return QDF_STATUS_E_FAILURE;
6201 	}
6202 
6203 	policy_mgr_debug("vdev %d: mode %d num_mlo_vdev %d reason %d",
6204 			 wlan_vdev_get_id(vdev), mode, num_mlo_vdev, reason);
6205 
6206 	req->ctx.vdev = vdev;
6207 	req->param.reason = reason;
6208 	req->param.force_mode = mode;
6209 	req->ctx.set_mlo_link_cb = policy_mgr_handle_link_enable_disable_resp;
6210 	req->ctx.validate_set_mlo_link_cb =
6211 		policy_mgr_validate_set_mlo_link_cb;
6212 	req->ctx.cb_arg = req;
6213 
6214 	/* set MLO vdev bit mask for all case */
6215 	policy_mgr_fill_ml_active_link_vdev_bitmap(req, mlo_vdev_lst,
6216 						   num_mlo_vdev);
6217 
6218 	pm_ctx->active_vdev_bitmap = req->param.vdev_bitmap[0];
6219 	pm_ctx->inactive_vdev_bitmap = req->param.vdev_bitmap[1];
6220 
6221 	if (mode == MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE)
6222 		policy_mgr_fill_ml_inactive_link_vdev_bitmap(
6223 			req, mlo_inactive_vdev_lst, num_mlo_inactive_vdev);
6224 
6225 	/*
6226 	 * Fill number of links for MLO_LINK_FORCE_MODE_ACTIVE_NUM or
6227 	 * MLO_LINK_FORCE_MODE_INACTIVE_NUM mode.
6228 	 */
6229 	if (mode == MLO_LINK_FORCE_MODE_ACTIVE_NUM ||
6230 	    mode == MLO_LINK_FORCE_MODE_INACTIVE_NUM) {
6231 		req->param.num_link_entry = 1;
6232 		req->param.link_num[0].num_of_link = num_mlo_vdev - 1;
6233 	}
6234 
6235 	if (ml_is_nlink_service_supported(psoc) &&
6236 	    reason != MLO_LINK_FORCE_REASON_TDLS) {
6237 		status =
6238 		policy_mgr_mlo_sta_set_link_by_linkid(psoc, vdev, reason,
6239 						      mode,
6240 						      req->param.link_num[0].
6241 						      num_of_link,
6242 						      num_mlo_vdev,
6243 						      mlo_vdev_lst,
6244 						      num_mlo_inactive_vdev,
6245 						      mlo_inactive_vdev_lst);
6246 		qdf_mem_free(req);
6247 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6248 
6249 		if (status != QDF_STATUS_E_PENDING) {
6250 			policy_mgr_err("set_link_by_linkid status %d", status);
6251 			return status;
6252 		}
6253 		return QDF_STATUS_SUCCESS;
6254 	}
6255 
6256 	policy_mgr_set_link_in_progress(pm_ctx, true);
6257 
6258 	status = mlo_ser_set_link_req(req);
6259 	if (QDF_IS_STATUS_ERROR(status)) {
6260 		policy_mgr_err("vdev %d: Failed to set link mode %d num_mlo_vdev %d reason %d",
6261 			       wlan_vdev_get_id(vdev), mode, num_mlo_vdev,
6262 			       reason);
6263 		qdf_mem_free(req);
6264 		policy_mgr_set_link_in_progress(pm_ctx, false);
6265 	}
6266 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6267 	return status;
6268 }
6269 
6270 QDF_STATUS
6271 policy_mgr_mlo_sta_set_link(struct wlan_objmgr_psoc *psoc,
6272 			    enum mlo_link_force_reason reason,
6273 			    enum mlo_link_force_mode mode,
6274 			    uint8_t num_mlo_vdev, uint8_t *mlo_vdev_lst)
6275 {
6276 	return policy_mgr_mlo_sta_set_link_ext(psoc, reason, mode, num_mlo_vdev,
6277 					       mlo_vdev_lst, 0, NULL);
6278 }
6279 
6280 QDF_STATUS
6281 policy_mgr_mlo_sta_set_nlink(struct wlan_objmgr_psoc *psoc,
6282 			     struct wlan_objmgr_vdev *vdev,
6283 			     enum mlo_link_force_reason reason,
6284 			     enum mlo_link_force_mode mode,
6285 			     uint8_t link_num,
6286 			     uint16_t link_bitmap,
6287 			     uint16_t link_bitmap2,
6288 			     uint32_t link_control_flags)
6289 {
6290 	struct mlo_link_set_active_req *req;
6291 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
6292 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6293 
6294 	pm_ctx = policy_mgr_get_context(psoc);
6295 	if (!pm_ctx) {
6296 		policy_mgr_err("Invalid Context");
6297 		return QDF_STATUS_E_INVAL;
6298 	}
6299 
6300 	req = qdf_mem_malloc(sizeof(*req));
6301 	if (!req)
6302 		return QDF_STATUS_E_NOMEM;
6303 
6304 	status = wlan_objmgr_vdev_try_get_ref(vdev, WLAN_POLICY_MGR_ID);
6305 	if (QDF_IS_STATUS_ERROR(status)) {
6306 		qdf_mem_free(req);
6307 		return QDF_STATUS_E_FAILURE;
6308 	}
6309 
6310 	policy_mgr_set_link_in_progress(pm_ctx, true);
6311 
6312 	policy_mgr_debug("vdev %d: mode %d %s reason %d bitmap 0x%x 0x%x ctrl 0x%x",
6313 			 wlan_vdev_get_id(vdev), mode,
6314 			 force_mode_to_string(mode), reason,
6315 			 link_bitmap, link_bitmap2,
6316 			 link_control_flags);
6317 
6318 	req->ctx.vdev = vdev;
6319 	req->param.reason = reason;
6320 	req->param.force_mode = mode;
6321 	req->param.use_ieee_link_id = true;
6322 	req->param.force_cmd.ieee_link_id_bitmap = link_bitmap;
6323 	req->param.force_cmd.ieee_link_id_bitmap2 = link_bitmap2;
6324 	req->param.force_cmd.link_num = link_num;
6325 	if (link_control_flags & link_ctrl_f_overwrite_active_bitmap)
6326 		req->param.control_flags.overwrite_force_active_bitmap = true;
6327 	if (link_control_flags & link_ctrl_f_overwrite_inactive_bitmap)
6328 		req->param.control_flags.overwrite_force_inactive_bitmap =
6329 									true;
6330 	if (link_control_flags & link_ctrl_f_dynamic_force_link_num)
6331 		req->param.control_flags.dynamic_force_link_num = true;
6332 	if (link_control_flags & link_ctrl_f_post_re_evaluate)
6333 		req->param.control_flags.post_re_evaluate = true;
6334 
6335 	status =
6336 	wlan_vdev_get_bss_peer_mld_mac(vdev,
6337 				       &req->param.force_cmd.ap_mld_mac_addr);
6338 	if (QDF_IS_STATUS_ERROR(status)) {
6339 		policy_mgr_err("fail to get ap mld addr for vdev %d",
6340 			       wlan_vdev_get_id(vdev));
6341 		goto end;
6342 	}
6343 	if (qdf_is_macaddr_zero(&req->param.force_cmd.ap_mld_mac_addr)) {
6344 		policy_mgr_err("get ap zero mld addr for vdev %d",
6345 			       wlan_vdev_get_id(vdev));
6346 		goto end;
6347 	}
6348 
6349 	req->ctx.set_mlo_link_cb = policy_mgr_handle_link_enable_disable_resp;
6350 	req->ctx.validate_set_mlo_link_cb =
6351 		policy_mgr_validate_set_mlo_link_cb;
6352 	req->ctx.cb_arg = req;
6353 	status = mlo_ser_set_link_req(req);
6354 end:
6355 	if (QDF_IS_STATUS_ERROR(status)) {
6356 		policy_mgr_err("vdev %d: Failed to set link mode %d num_mlo_vdev %d reason %d",
6357 			       wlan_vdev_get_id(vdev), mode, link_num,
6358 			       reason);
6359 		qdf_mem_free(req);
6360 		policy_mgr_set_link_in_progress(pm_ctx, false);
6361 	} else {
6362 		status = QDF_STATUS_E_PENDING;
6363 	}
6364 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6365 
6366 	return status;
6367 }
6368 
6369 uint32_t
6370 policy_mgr_get_conc_ext_flags(struct wlan_objmgr_vdev *vdev, bool force_mlo)
6371 {
6372 	struct wlan_objmgr_vdev *assoc_vdev;
6373 	union conc_ext_flag conc_ext_flags;
6374 
6375 	conc_ext_flags.value = 0;
6376 	if (!vdev || wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE)
6377 		return conc_ext_flags.value;
6378 
6379 	if (!force_mlo && !wlan_vdev_mlme_is_mlo_vdev(vdev))
6380 		return conc_ext_flags.value;
6381 
6382 	conc_ext_flags.mlo = 1;
6383 	if (wlan_vdev_mlme_is_mlo_link_vdev(vdev)) {
6384 		assoc_vdev = ucfg_mlo_get_assoc_link_vdev(vdev);
6385 		if (assoc_vdev && ucfg_cm_is_vdev_active(assoc_vdev))
6386 			conc_ext_flags.mlo_link_assoc_connected = 1;
6387 	}
6388 
6389 	return conc_ext_flags.value;
6390 }
6391 
6392 /**
6393  * policy_mgr_allow_sta_concurrency() - check whether STA concurrency is allowed
6394  * @psoc: Pointer to soc
6395  * @freq: frequency to be checked
6396  * @ext_flags: extended flags for concurrency check
6397  *
6398  *  Return: true if supports else false.
6399  */
6400 static bool
6401 policy_mgr_allow_sta_concurrency(struct wlan_objmgr_psoc *psoc,
6402 				 qdf_freq_t freq,
6403 				 uint32_t ext_flags)
6404 {
6405 	uint32_t conn_index = 0;
6406 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6407 	struct wlan_objmgr_vdev *vdev;
6408 	bool is_mlo, mlo_sta_present = false;
6409 	uint8_t vdev_id, sta_cnt = 0;
6410 	enum policy_mgr_con_mode mode;
6411 	union conc_ext_flag conc_ext_flags;
6412 
6413 	pm_ctx = policy_mgr_get_context(psoc);
6414 	if (!pm_ctx) {
6415 		policy_mgr_err("Invalid Context");
6416 		return false;
6417 	}
6418 
6419 	conc_ext_flags.value = ext_flags;
6420 
6421 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
6422 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
6423 	     conn_index++) {
6424 		mode = pm_conc_connection_list[conn_index].mode;
6425 		if (mode != PM_STA_MODE ||
6426 		    !pm_conc_connection_list[conn_index].in_use)
6427 			continue;
6428 
6429 		vdev_id = pm_conc_connection_list[conn_index].vdev_id;
6430 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
6431 							    WLAN_POLICY_MGR_ID);
6432 		if (!vdev)
6433 			continue;
6434 
6435 		is_mlo = wlan_vdev_mlme_is_mlo_vdev(vdev);
6436 
6437 		/* Skip the link vdev for MLO STA */
6438 		if (wlan_vdev_mlme_is_mlo_link_vdev(vdev))
6439 			goto next;
6440 
6441 		sta_cnt++;
6442 		if (!is_mlo)
6443 			goto next;
6444 
6445 		mlo_sta_present = true;
6446 next:
6447 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6448 	}
6449 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
6450 
6451 	/* Reject if multiple STA connections are not allowed */
6452 	if (sta_cnt &&
6453 	    !policy_mgr_allow_multiple_sta_connections(psoc)) {
6454 		policy_mgr_rl_debug("Disallow Multiple STA connections");
6455 		return false;
6456 	}
6457 
6458 	if (mlo_sta_present && conc_ext_flags.mlo_link_assoc_connected) {
6459 		policy_mgr_rl_debug("Allow secondary MLO link");
6460 		return true;
6461 	}
6462 
6463 	if (conc_ext_flags.mlo && mlo_sta_present) {
6464 		policy_mgr_rl_debug("Disallow ML STA when ML STA is present");
6465 		return false;
6466 	}
6467 
6468 	/*
6469 	 * Reject a 3rd STA.
6470 	 * Treat a MLO STA(including the primary and secondary link vdevs)
6471 	 * as 1 STA here.
6472 	 */
6473 	if (sta_cnt >= 2) {
6474 		policy_mgr_rl_debug("Disallow 3rd STA");
6475 		return false;
6476 	}
6477 
6478 	return true;
6479 }
6480 
6481 bool
6482 policy_mgr_is_mlo_sap_concurrency_allowed(struct wlan_objmgr_psoc *psoc,
6483 					  bool is_new_vdev_mlo,
6484 					  uint8_t new_vdev_id)
6485 {
6486 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6487 	uint32_t conn_index;
6488 	bool ret = false, mlo_sap_present = false;
6489 	struct wlan_objmgr_vdev *vdev;
6490 	uint32_t vdev_id;
6491 
6492 	pm_ctx = policy_mgr_get_context(psoc);
6493 	if (!pm_ctx) {
6494 		policy_mgr_err("Invalid Context");
6495 		return ret;
6496 	}
6497 
6498 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
6499 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
6500 		 conn_index++) {
6501 		if (!pm_conc_connection_list[conn_index].in_use ||
6502 		    (pm_conc_connection_list[conn_index].mode != PM_SAP_MODE))
6503 			continue;
6504 
6505 		vdev_id = pm_conc_connection_list[conn_index].vdev_id;
6506 		if (vdev_id == new_vdev_id)
6507 			continue;
6508 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
6509 							    WLAN_POLICY_MGR_ID);
6510 		if (!vdev) {
6511 			policy_mgr_err("vdev for vdev_id:%d is NULL", vdev_id);
6512 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
6513 			return ret;
6514 		}
6515 
6516 		/* As only one ML SAP is allowed, break after one ML SAP
6517 		 * instance found in the policy manager list.
6518 		 */
6519 		if (wlan_vdev_mlme_is_mlo_vdev(vdev)) {
6520 			mlo_sap_present = true;
6521 			wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6522 			break;
6523 		}
6524 
6525 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6526 	}
6527 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
6528 
6529 	if (is_new_vdev_mlo && mlo_sap_present)
6530 		ret = false;
6531 	else
6532 		ret = true;
6533 
6534 	return ret;
6535 }
6536 
6537 QDF_STATUS
6538 policy_mgr_link_switch_notifier_cb(struct wlan_objmgr_vdev *vdev,
6539 				   struct wlan_mlo_link_switch_req *req)
6540 {
6541 	struct wlan_objmgr_psoc *psoc = wlan_vdev_get_psoc(vdev);
6542 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6543 	uint8_t vdev_id = req->vdev_id;
6544 	uint8_t curr_ieee_link_id = req->curr_ieee_link_id;
6545 	uint8_t new_ieee_link_id = req->new_ieee_link_id;
6546 	uint32_t new_primary_freq = req->new_primary_freq;
6547 	QDF_STATUS status;
6548 	union conc_ext_flag conc_ext_flags;
6549 	struct policy_mgr_conc_connection_info
6550 			info[MAX_NUMBER_OF_CONC_CONNECTIONS] = { {0} };
6551 	uint8_t num_del = 0;
6552 	struct ml_nlink_change_event data;
6553 
6554 	pm_ctx = policy_mgr_get_context(psoc);
6555 	if (!pm_ctx) {
6556 		policy_mgr_err("Invalid Context");
6557 		return QDF_STATUS_E_INVAL;
6558 	}
6559 
6560 	policy_mgr_debug("target link %d freq %d curr link %d vdev %d",
6561 			 new_ieee_link_id, new_primary_freq,
6562 			 curr_ieee_link_id, vdev_id);
6563 	qdf_mem_zero(&data, sizeof(data));
6564 	data.evt.link_switch.curr_ieee_link_id = curr_ieee_link_id;
6565 	data.evt.link_switch.new_ieee_link_id = new_ieee_link_id;
6566 	data.evt.link_switch.new_primary_freq = new_primary_freq;
6567 	status = ml_nlink_conn_change_notify(psoc, vdev_id,
6568 					     ml_nlink_link_switch_start_evt,
6569 					     &data);
6570 	if (QDF_IS_STATUS_ERROR(status))
6571 		return status;
6572 
6573 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
6574 
6575 	policy_mgr_store_and_del_conn_info_by_vdev_id(
6576 		psoc, vdev_id, info, &num_del);
6577 	conc_ext_flags.value =
6578 	policy_mgr_get_conc_ext_flags(vdev, true);
6579 	if (!policy_mgr_is_concurrency_allowed(psoc, PM_STA_MODE,
6580 					       new_primary_freq,
6581 					       HW_MODE_20_MHZ,
6582 					       conc_ext_flags.value,
6583 					       NULL)) {
6584 		status = QDF_STATUS_E_INVAL;
6585 		policy_mgr_debug("target link %d freq %d not allowed by conc rule",
6586 				 new_ieee_link_id, new_primary_freq);
6587 	}
6588 
6589 	if (num_del > 0)
6590 		policy_mgr_restore_deleted_conn_info(psoc, info, num_del);
6591 
6592 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
6593 
6594 	return status;
6595 }
6596 
6597 bool policy_mgr_is_non_ml_sta_present(struct wlan_objmgr_psoc *psoc)
6598 {
6599 	uint32_t conn_index = 0;
6600 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6601 	struct wlan_objmgr_vdev *vdev;
6602 	bool non_ml_sta_present = false;
6603 	uint8_t vdev_id;
6604 
6605 	pm_ctx = policy_mgr_get_context(psoc);
6606 	if (!pm_ctx) {
6607 		policy_mgr_err("Invalid Context");
6608 		return false;
6609 	}
6610 
6611 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
6612 	for (conn_index = 0;
6613 	     conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
6614 	     conn_index++) {
6615 		if (pm_conc_connection_list[conn_index].mode != PM_STA_MODE ||
6616 		    !pm_conc_connection_list[conn_index].in_use)
6617 			continue;
6618 
6619 		vdev_id = pm_conc_connection_list[conn_index].vdev_id;
6620 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
6621 							    WLAN_POLICY_MGR_ID);
6622 		if (!vdev)
6623 			continue;
6624 
6625 		if (!wlan_vdev_mlme_is_mlo_vdev(vdev)) {
6626 			non_ml_sta_present = true;
6627 			wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6628 			break;
6629 		}
6630 
6631 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6632 	}
6633 
6634 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
6635 	return non_ml_sta_present;
6636 }
6637 
6638 bool policy_mgr_is_mlo_sta_present(struct wlan_objmgr_psoc *psoc)
6639 {
6640 	uint32_t conn_index = 0;
6641 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6642 	struct wlan_objmgr_vdev *vdev;
6643 	bool mlo_sta_present = false;
6644 	uint8_t vdev_id;
6645 
6646 	pm_ctx = policy_mgr_get_context(psoc);
6647 	if (!pm_ctx) {
6648 		policy_mgr_err("Invalid Context");
6649 		return false;
6650 	}
6651 
6652 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
6653 	for (conn_index = 0;
6654 	     conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS && !mlo_sta_present;
6655 	     conn_index++) {
6656 		if (pm_conc_connection_list[conn_index].mode != PM_STA_MODE ||
6657 		    !pm_conc_connection_list[conn_index].in_use)
6658 			continue;
6659 
6660 		vdev_id = pm_conc_connection_list[conn_index].vdev_id;
6661 		vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
6662 							    WLAN_POLICY_MGR_ID);
6663 		if (!vdev)
6664 			continue;
6665 
6666 		mlo_sta_present = wlan_vdev_mlme_is_mlo_vdev(vdev);
6667 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
6668 	}
6669 
6670 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
6671 	return mlo_sta_present;
6672 }
6673 
6674 bool policy_mgr_is_mlo_in_mode_sbs(struct wlan_objmgr_psoc *psoc,
6675 				   enum policy_mgr_con_mode mode,
6676 				   uint8_t *mlo_vdev_lst, uint8_t *num_mlo)
6677 {
6678 	uint32_t mode_num = 0;
6679 	uint8_t i, mlo_idx = 0;
6680 	struct wlan_objmgr_vdev *temp_vdev;
6681 	qdf_freq_t mlo_freq_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
6682 	uint8_t vdev_id_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
6683 	bool is_sbs_link = true;
6684 
6685 	mode_num = policy_mgr_get_mode_specific_conn_info(psoc, NULL,
6686 							 vdev_id_list, mode);
6687 	if (!mode_num || mode_num < 2)
6688 		return false;
6689 
6690 	for (i = 0; i < mode_num; i++) {
6691 		temp_vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc,
6692 							vdev_id_list[i],
6693 							WLAN_POLICY_MGR_ID);
6694 		if (!temp_vdev) {
6695 			policy_mgr_err("invalid vdev for id %d",
6696 				       vdev_id_list[i]);
6697 			return false;
6698 		}
6699 
6700 		if (wlan_vdev_mlme_is_mlo_vdev(temp_vdev)) {
6701 			if (mlo_vdev_lst)
6702 				mlo_vdev_lst[mlo_idx] = vdev_id_list[i];
6703 			mlo_freq_list[mlo_idx] =
6704 				wlan_get_operation_chan_freq(temp_vdev);
6705 			if (wlan_reg_is_24ghz_ch_freq(mlo_freq_list[mlo_idx]))
6706 				is_sbs_link = false;
6707 			mlo_idx++;
6708 		}
6709 		wlan_objmgr_vdev_release_ref(temp_vdev, WLAN_POLICY_MGR_ID);
6710 	}
6711 
6712 	if (num_mlo)
6713 		*num_mlo = mlo_idx;
6714 	if (mlo_idx < 2)
6715 		is_sbs_link = false;
6716 	if (is_sbs_link &&
6717 	    !policy_mgr_are_sbs_chan(psoc, mlo_freq_list[0],
6718 				     mlo_freq_list[1])) {
6719 		policy_mgr_debug("Freq %d and %d are not SBS, set SBS false",
6720 				 mlo_freq_list[0],
6721 				 mlo_freq_list[1]);
6722 		is_sbs_link = false;
6723 	}
6724 
6725 	return is_sbs_link;
6726 }
6727 
6728 bool policy_mgr_is_mlo_in_mode_dbs(struct wlan_objmgr_psoc *psoc,
6729 				   enum policy_mgr_con_mode mode,
6730 				   uint8_t *mlo_vdev_lst, uint8_t *num_mlo)
6731 {
6732 	uint32_t mode_num = 0;
6733 	uint8_t i, mlo_idx = 0;
6734 	struct wlan_objmgr_vdev *temp_vdev;
6735 	uint8_t vdev_id_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
6736 	bool has_2g_link = false;
6737 	bool has_5g_link = false;
6738 	qdf_freq_t mlo_freq;
6739 
6740 	mode_num = policy_mgr_get_mode_specific_conn_info(psoc, NULL,
6741 							  vdev_id_list, mode);
6742 	if (!mode_num || mode_num < 2)
6743 		return false;
6744 
6745 	for (i = 0; i < mode_num; i++) {
6746 		temp_vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
6747 							psoc,
6748 							vdev_id_list[i],
6749 							WLAN_POLICY_MGR_ID);
6750 		if (!temp_vdev) {
6751 			policy_mgr_err("invalid vdev for id %d",
6752 				       vdev_id_list[i]);
6753 			return false;
6754 		}
6755 
6756 		if (wlan_vdev_mlme_is_mlo_vdev(temp_vdev)) {
6757 			if (mlo_vdev_lst)
6758 				mlo_vdev_lst[mlo_idx] = vdev_id_list[i];
6759 			mlo_freq =
6760 				wlan_get_operation_chan_freq(temp_vdev);
6761 			if (wlan_reg_is_24ghz_ch_freq(mlo_freq))
6762 				has_2g_link = true;
6763 			else
6764 				has_5g_link = true;
6765 			mlo_idx++;
6766 		}
6767 		wlan_objmgr_vdev_release_ref(temp_vdev, WLAN_POLICY_MGR_ID);
6768 	}
6769 
6770 	if (num_mlo)
6771 		*num_mlo = mlo_idx;
6772 
6773 	return has_2g_link && has_5g_link;
6774 }
6775 
6776 bool policy_mgr_is_curr_hwmode_emlsr(struct wlan_objmgr_psoc *psoc)
6777 {
6778 	struct policy_mgr_hw_mode_params hw_mode;
6779 
6780 	if (!policy_mgr_is_hw_emlsr_capable(psoc))
6781 		return false;
6782 
6783 	if (QDF_STATUS_SUCCESS != policy_mgr_get_current_hw_mode(psoc,
6784 								 &hw_mode))
6785 		return false;
6786 
6787 	if (!hw_mode.emlsr_cap)
6788 		return false;
6789 
6790 	return true;
6791 }
6792 
6793 bool policy_mgr_is_mlo_in_mode_emlsr(struct wlan_objmgr_psoc *psoc,
6794 				     uint8_t *mlo_vdev_lst, uint8_t *num_mlo)
6795 {
6796 	bool emlsr_connection = false;
6797 	uint32_t mode_num = 0;
6798 	uint8_t i, mlo_idx = 0;
6799 	struct wlan_objmgr_vdev *temp_vdev;
6800 	uint8_t vdev_id_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
6801 
6802 	mode_num = policy_mgr_get_mode_specific_conn_info(psoc, NULL,
6803 							  vdev_id_list,
6804 							  PM_STA_MODE);
6805 
6806 	for (i = 0; i < mode_num; i++) {
6807 		temp_vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
6808 							psoc, vdev_id_list[i],
6809 							WLAN_POLICY_MGR_ID);
6810 		if (!temp_vdev) {
6811 			policy_mgr_err("invalid vdev for id %d",
6812 				       vdev_id_list[i]);
6813 			goto end;
6814 		}
6815 
6816 		if (wlan_vdev_mlme_is_mlo_vdev(temp_vdev)) {
6817 			if (mlo_vdev_lst)
6818 				mlo_vdev_lst[mlo_idx] = vdev_id_list[i];
6819 			mlo_idx++;
6820 		}
6821 		/* Check if existing vdev is eMLSR STA */
6822 		if (wlan_vdev_mlme_cap_get(temp_vdev, WLAN_VDEV_C_EMLSR_CAP))
6823 			emlsr_connection = true;
6824 
6825 		wlan_objmgr_vdev_release_ref(temp_vdev, WLAN_POLICY_MGR_ID);
6826 	}
6827 end:
6828 	if (num_mlo)
6829 		*num_mlo = mlo_idx;
6830 
6831 	return emlsr_connection;
6832 }
6833 
6834 void policy_mgr_handle_emlsr_sta_concurrency(struct wlan_objmgr_psoc *psoc,
6835 					     bool conc_con_coming_up,
6836 					     bool emlsr_sta_coming_up)
6837 {
6838 	uint8_t num_mlo = 0;
6839 	uint8_t mlo_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
6840 	bool is_mlo_emlsr = false;
6841 	uint8_t num_disabled_ml_sta = 0;
6842 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
6843 	struct policy_mgr_psoc_priv_obj *pm_ctx;
6844 
6845 	pm_ctx = policy_mgr_get_context(psoc);
6846 	if (!pm_ctx) {
6847 		policy_mgr_err("Invalid Context");
6848 		return;
6849 	}
6850 
6851 	is_mlo_emlsr = policy_mgr_is_mlo_in_mode_emlsr(psoc, mlo_vdev_lst,
6852 						       &num_mlo);
6853 	policy_mgr_debug("num_mlo %d is_mlo_emlsr %d conc_con_coming_up: %d",
6854 			 num_mlo, is_mlo_emlsr, conc_con_coming_up);
6855 
6856 	if (!is_mlo_emlsr)
6857 		return;
6858 
6859 	if (num_mlo < 2) {
6860 		policy_mgr_debug("conc_con_coming_up %d num mlo sta links %d",
6861 				 conc_con_coming_up, num_mlo);
6862 		policy_mgr_get_ml_sta_info(pm_ctx, &num_mlo,
6863 					   &num_disabled_ml_sta,
6864 					   mlo_vdev_lst, ml_freq_lst,
6865 					   NULL, NULL, NULL);
6866 		if (policy_mgr_get_connection_count(psoc) != 1 ||
6867 		    !num_disabled_ml_sta)
6868 			return;
6869 	}
6870 
6871 	if (conc_con_coming_up ||
6872 	    (emlsr_sta_coming_up &&
6873 	     policy_mgr_get_connection_count(psoc) > 2)) {
6874 		/*
6875 		 * Force disable one of the links (FW will decide which link) if
6876 		 * 1) EMLSR STA is present and SAP/STA/NAN connection comes up.
6877 		 * 2) There is a legacy connection (SAP/P2P/NAN) and a STA comes
6878 		 * up in EMLSR mode.
6879 		 */
6880 		policy_mgr_mlo_sta_set_link(psoc, MLO_LINK_FORCE_REASON_CONNECT,
6881 					    MLO_LINK_FORCE_MODE_INACTIVE_NUM,
6882 					    num_mlo, mlo_vdev_lst);
6883 		return;
6884 	}
6885 
6886 	if (!conc_con_coming_up && emlsr_sta_coming_up)
6887 		/*
6888 		 * No force i.e. Re-enable the disabled link if-
6889 		 * 1) EMLSR STA is present and new SAP/STA/NAN connection goes
6890 		 *    down. One of the links was disabled while a new connection
6891 		 *    came up.
6892 		 * 2) Legacy connection (SAP/P2P/NAN) goes down and if STA is
6893 		 *    EMLSR capable. One of the links was disabled after EMLSR
6894 		 *    association.
6895 		 */
6896 		policy_mgr_mlo_sta_set_link(psoc,
6897 					    MLO_LINK_FORCE_REASON_DISCONNECT,
6898 					    MLO_LINK_FORCE_MODE_NO_FORCE,
6899 					    num_mlo, mlo_vdev_lst);
6900 }
6901 
6902 bool
6903 policy_mgr_is_emlsr_sta_concurrency_present(struct wlan_objmgr_psoc *psoc)
6904 {
6905 	uint8_t num_mlo = 0;
6906 
6907 	if (policy_mgr_is_mlo_in_mode_emlsr(psoc, NULL, &num_mlo) &&
6908 	    num_mlo < policy_mgr_get_connection_count(psoc))
6909 		return true;
6910 
6911 	return false;
6912 }
6913 
6914 static uint8_t
6915 policy_mgr_get_affected_links_for_sta_sta(struct wlan_objmgr_psoc *psoc,
6916 					  uint8_t num_ml, qdf_freq_t *freq_list,
6917 					  uint8_t *vdev_id_list,
6918 					  uint8_t *ml_vdev_lst,
6919 					  uint8_t *ml_idx, qdf_freq_t freq)
6920 {
6921 	uint8_t i = 0;
6922 	bool same_band_sta_allowed;
6923 
6924 	/*
6925 	 * STA freq:      ML STA combo:  SBS Action
6926 	 * ---------------------------------------------------
6927 	 * 2Ghz           2Ghz+5/6Ghz    Disable 2Ghz(Same MAC)
6928 	 * 5Ghz           2Ghz+5/6Ghz    Disable 2.4Ghz if 5Ghz lead to SBS
6929 	 *                               (SBS, same MAC) and same band STA
6930 	 *                               allowed, else disable 5/6Ghz
6931 	 *                               (NON SBS, same MAC)
6932 	 * 5Ghz(lower)    5Ghz+6Ghz      Disable 5Ghz (NON SBS, same MAC)
6933 	 * 5Ghz(higher)   5Ghz+6Ghz      Disable 6Ghz (NON SBS, Same MAC)
6934 	 * 2Ghz           5Ghz+6Ghz      Disable Any
6935 	 */
6936 
6937 	/* If non-ML STA is 2.4Ghz disable 2.4Ghz if present OR disable any */
6938 	if (wlan_reg_is_24ghz_ch_freq(freq)) {
6939 		while (i < num_ml) {
6940 			if (wlan_reg_is_24ghz_ch_freq(freq_list[ml_idx[i]])) {
6941 				/* Affected ML STA link on 2.4Ghz */
6942 				ml_vdev_lst[0] = vdev_id_list[ml_idx[i]];
6943 				return 1;
6944 			}
6945 			/* Fill non effected vdev in list */
6946 			ml_vdev_lst[i] = vdev_id_list[ml_idx[i]];
6947 			i++;
6948 		}
6949 		/* No link affected return num_ml to disable any */
6950 		return i;
6951 	}
6952 
6953 	/* This mean non-ML STA is 5Ghz */
6954 
6955 	/* check if ML STA is DBS */
6956 	i = 0;
6957 	while (i < num_ml &&
6958 	       !wlan_reg_is_24ghz_ch_freq(freq_list[ml_idx[i]]))
6959 		i++;
6960 
6961 	same_band_sta_allowed = wlan_cm_same_band_sta_allowed(psoc);
6962 
6963 	/*
6964 	 * if ML STA is DBS ie 2.4Ghz link present and if same_band_sta_allowed
6965 	 * is false, disable 5/6Ghz link to make sure we dont have all link
6966 	 * on 5Ghz
6967 	 */
6968 	if (i < num_ml && !same_band_sta_allowed)
6969 		goto check_dbs_ml;
6970 
6971 	/* check if any link lead to SBS, so that we can disable the other*/
6972 	i = 0;
6973 	while (i < num_ml &&
6974 	       !policy_mgr_are_sbs_chan(psoc, freq, freq_list[ml_idx[i]]))
6975 		i++;
6976 
6977 	/*
6978 	 * if i < num_ml then i is the SBS link, in this case disable the other
6979 	 * non SBS link, this mean ML STA is 5+6 or 2+5/6.
6980 	 */
6981 	if (i < num_ml) {
6982 		i = 0;
6983 		while (i < num_ml) {
6984 			if (!policy_mgr_are_sbs_chan(psoc, freq,
6985 						     freq_list[ml_idx[i]])) {
6986 				/* Affected non SBS ML STA link */
6987 				ml_vdev_lst[0] = vdev_id_list[ml_idx[i]];
6988 				return 1;
6989 			}
6990 			/* Fill non effected vdev in list */
6991 			ml_vdev_lst[i] = vdev_id_list[ml_idx[i]];
6992 			i++;
6993 		}
6994 		/* All link lead to SBS, disable any, This should not happen */
6995 		return i;
6996 	}
6997 
6998 check_dbs_ml:
6999 	/*
7000 	 * None of the link can lead to SBS, i.e. its 2+ 5/6 ML STA in this case
7001 	 * disable 5Ghz link.
7002 	 */
7003 	i = 0;
7004 	while (i < num_ml) {
7005 		if (!wlan_reg_is_24ghz_ch_freq(freq_list[ml_idx[i]])) {
7006 			/* Affected 5/6Ghz ML STA link */
7007 			ml_vdev_lst[0] = vdev_id_list[ml_idx[i]];
7008 			return 1;
7009 		}
7010 		/* Fill non effected vdev in list */
7011 		ml_vdev_lst[i] = vdev_id_list[ml_idx[i]];
7012 		i++;
7013 	}
7014 
7015 	/* No link affected, This should not happen */
7016 	return i;
7017 }
7018 
7019 /*
7020  * policy_mgr_get_concurrent_num_links() - get links which are affected
7021  * if no affected then return num ml. Also fills the ml_vdev_lst to send.
7022  * @num_ml: number of ML vdev
7023  * @freq_list: freq list of all vdev
7024  * @vdev_id_list: vdev id list
7025  * @ml_vdev_lst: ML vdev list
7026  * @ml_idx: ML index
7027  * @freq: non ML STA freq
7028  *
7029  * Return: number of the affected links, else total link and ml_vdev_lst list.
7030  */
7031 static uint8_t
7032 policy_mgr_get_concurrent_num_links(struct wlan_objmgr_vdev *vdev,
7033 				    uint8_t num_ml, qdf_freq_t *freq_list,
7034 				    uint8_t *vdev_id_list,
7035 				    uint8_t *ml_vdev_lst,
7036 				    uint8_t *ml_idx, qdf_freq_t freq)
7037 {
7038 	uint8_t i = 0;
7039 	struct wlan_objmgr_psoc *psoc = wlan_vdev_get_psoc(vdev);
7040 
7041 	if (!psoc)
7042 		return 0;
7043 
7044 	while (i < num_ml && (freq_list[ml_idx[i]] != freq))
7045 		i++;
7046 
7047 	if (i < num_ml) {
7048 		/* if one link is SCC then no need to disable any link */
7049 		policy_mgr_debug("vdev %d: ML vdev %d lead to SCC, STA freq %d ML freq %d, no need to disable link",
7050 				 wlan_vdev_get_id(vdev),
7051 				 vdev_id_list[ml_idx[i]],
7052 				 freq, freq_list[ml_idx[i]]);
7053 		return 0;
7054 	}
7055 
7056 
7057 	return policy_mgr_get_affected_links_for_sta_sta(psoc, num_ml,
7058 							 freq_list,
7059 							 vdev_id_list,
7060 							 ml_vdev_lst,
7061 							 ml_idx, freq);
7062 }
7063 
7064 static void
7065 policy_mgr_ml_sta_concurrency_on_connect(struct wlan_objmgr_psoc *psoc,
7066 				    struct wlan_objmgr_vdev *vdev,
7067 				    uint8_t num_ml, uint8_t *ml_idx,
7068 				    uint8_t num_non_ml, uint8_t *non_ml_idx,
7069 				    qdf_freq_t *freq_list,
7070 				    uint8_t *vdev_id_list)
7071 {
7072 	qdf_freq_t freq = 0;
7073 	struct wlan_channel *bss_chan;
7074 	uint8_t vdev_id = wlan_vdev_get_id(vdev);
7075 	uint8_t ml_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7076 	uint8_t affected_links = 0;
7077 	enum mlo_link_force_mode mode = MLO_LINK_FORCE_MODE_ACTIVE_NUM;
7078 
7079 	/* non ML STA doesn't exist, no need to change to link.*/
7080 	if (!num_non_ml)
7081 		return;
7082 
7083 	if (wlan_vdev_mlme_is_mlo_vdev(vdev)) {
7084 		freq = freq_list[non_ml_idx[0]];
7085 	} else {
7086 		bss_chan = wlan_vdev_mlme_get_bss_chan(vdev);
7087 		if (bss_chan)
7088 			freq = bss_chan->ch_freq;
7089 	}
7090 	policy_mgr_debug("vdev %d: Freq %d (non ML vdev id %d), is ML STA %d",
7091 			 vdev_id, freq, vdev_id_list[non_ml_idx[0]],
7092 			 wlan_vdev_mlme_is_mlo_vdev(vdev));
7093 	if (!freq)
7094 		return;
7095 
7096 	affected_links =
7097 		policy_mgr_get_concurrent_num_links(vdev, num_ml, freq_list,
7098 						    vdev_id_list, ml_vdev_lst,
7099 						    ml_idx, freq);
7100 
7101 	if (!affected_links) {
7102 		policy_mgr_debug("vdev %d: no affected link found", vdev_id);
7103 		return;
7104 	}
7105 	policy_mgr_debug("affected link found: %u vdev_id: %u",
7106 			 affected_links, ml_vdev_lst[0]);
7107 
7108 	/*
7109 	 * If affected link is less than num_ml, ie not all link are affected,
7110 	 * send MLO_LINK_FORCE_MODE_INACTIVE.
7111 	 */
7112 	if (affected_links < num_ml &&
7113 	    affected_links <= MAX_NUMBER_OF_CONC_CONNECTIONS) {
7114 		if (mlo_is_sta_inactivity_allowed_with_quiet(psoc, vdev_id_list,
7115 							     num_ml, ml_idx,
7116 							     affected_links,
7117 							     ml_vdev_lst)) {
7118 			mode = MLO_LINK_FORCE_MODE_INACTIVE;
7119 		} else {
7120 			policy_mgr_debug("vdev %d: force inactivity is not allowed",
7121 					 ml_vdev_lst[0]);
7122 			return;
7123 		}
7124 	}
7125 
7126 	policy_mgr_mlo_sta_set_link(psoc, MLO_LINK_FORCE_REASON_CONNECT,
7127 				    mode, affected_links, ml_vdev_lst);
7128 }
7129 
7130 static void
7131 policy_mgr_get_disabled_ml_sta_idx(struct wlan_objmgr_psoc *psoc,
7132 				   uint8_t *ml_sta,
7133 				   uint8_t *ml_idx,
7134 				   qdf_freq_t *freq_list,
7135 				   uint8_t *vdev_id_list, uint8_t next_idx)
7136 {
7137 	uint8_t conn_index, fill_index = next_idx;
7138 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7139 
7140 	pm_ctx = policy_mgr_get_context(psoc);
7141 	if (!pm_ctx) {
7142 		policy_mgr_err("Invalid Context");
7143 		return;
7144 	}
7145 
7146 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
7147 	/* Get disabled link info as well and keep it at last */
7148 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_DISABLE_LINK;
7149 	     conn_index++) {
7150 		if (!pm_disabled_ml_links[conn_index].in_use)
7151 			continue;
7152 		if (pm_disabled_ml_links[conn_index].mode != PM_STA_MODE)
7153 			continue;
7154 		if ((fill_index >= MAX_NUMBER_OF_CONC_CONNECTIONS) ||
7155 		    (*ml_sta >= MAX_NUMBER_OF_CONC_CONNECTIONS)) {
7156 			policy_mgr_err("Invalid fill_index: %d or ml_sta: %d",
7157 				       fill_index, *ml_sta);
7158 			break;
7159 		}
7160 		vdev_id_list[fill_index] =
7161 				pm_disabled_ml_links[conn_index].vdev_id;
7162 		freq_list[fill_index] = pm_disabled_ml_links[conn_index].freq;
7163 		ml_idx[(*ml_sta)++] = fill_index++;
7164 	}
7165 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
7166 }
7167 
7168 /**
7169  * policy_mgr_handle_ml_sta_link_concurrency() - Handle STA+ML_STA concurrency
7170  * @psoc: PSOC object information
7171  * @vdev: vdev of the changed interface caller
7172  *
7173  * Return: void
7174  */
7175 static QDF_STATUS
7176 policy_mgr_handle_ml_sta_link_concurrency(struct wlan_objmgr_psoc *psoc,
7177 					  struct wlan_objmgr_vdev *vdev)
7178 {
7179 	uint8_t num_ml = 0, num_non_ml = 0, next_idx, disabled_links;
7180 	uint8_t ml_idx[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7181 	uint8_t non_ml_idx[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7182 	qdf_freq_t freq_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7183 	uint8_t vdev_id_list[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7184 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7185 
7186 	pm_ctx = policy_mgr_get_context(psoc);
7187 	if (!pm_ctx) {
7188 		policy_mgr_err("Invalid Context");
7189 		return QDF_STATUS_E_INVAL;
7190 	}
7191 
7192 	/* Skip non STA connection handling */
7193 	if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE)
7194 		return QDF_STATUS_E_INVAL;
7195 
7196 	/*
7197 	 * Skip this in case of SAP/P2P Concurrencies, to avoid renable of
7198 	 * the link, disabled by SAP/P2P logic, as this API only consider
7199 	 * STA specific counts and ignore other counts.
7200 	 */
7201 	if (policy_mgr_get_beaconing_mode_count(psoc, NULL) ||
7202 	    policy_mgr_mode_specific_connection_count(psoc,
7203 						      PM_P2P_CLIENT_MODE,
7204 						      NULL)) {
7205 		policy_mgr_debug("SAP/GO/CLI exist ignore this check");
7206 		return QDF_STATUS_E_INVAL;
7207 	}
7208 
7209 	policy_mgr_get_ml_and_non_ml_sta_count(psoc, &num_ml, ml_idx,
7210 					       &num_non_ml, non_ml_idx,
7211 					       freq_list, vdev_id_list);
7212 	/* Skip non STA+STA cases */
7213 	if (!num_ml || !num_non_ml)
7214 		return QDF_STATUS_E_INVAL;
7215 
7216 	next_idx = num_ml + num_non_ml;
7217 	policy_mgr_get_disabled_ml_sta_idx(psoc, &num_ml, ml_idx,
7218 					   freq_list, vdev_id_list, next_idx);
7219 
7220 	disabled_links = num_ml - (next_idx - num_non_ml);
7221 	policy_mgr_debug("vdev %d: num_ml %d num_non_ml %d disabled_links: %d",
7222 			 wlan_vdev_get_id(vdev), num_ml, num_non_ml,
7223 			 disabled_links);
7224 
7225 	/* ML STA is not up or not sufficient links to disable */
7226 	if (num_ml < 2 || num_ml > MAX_NUMBER_OF_CONC_CONNECTIONS ||
7227 	    num_ml - disabled_links < 2) {
7228 		policy_mgr_debug("ML STA is not up or not sufficient links to disable");
7229 		return QDF_STATUS_E_INVAL;
7230 	}
7231 	/*
7232 	 * TODO: Check if both link enable/ link switch is possible when
7233 	 * secondary STA switch happens to a new channel due to CSA
7234 	 */
7235 
7236 	policy_mgr_ml_sta_concurrency_on_connect(psoc, vdev, num_ml,
7237 						 ml_idx, num_non_ml,
7238 						 non_ml_idx, freq_list,
7239 						 vdev_id_list);
7240 	return QDF_STATUS_SUCCESS;
7241 }
7242 
7243 static bool
7244 policy_mgr_is_mode_p2p_sap(enum policy_mgr_con_mode mode)
7245 {
7246 	return (policy_mgr_is_beaconing_mode(mode) ||
7247 		(mode == PM_P2P_CLIENT_MODE));
7248 }
7249 
7250 bool
7251 policy_mgr_is_vdev_high_tput_or_low_latency(struct wlan_objmgr_psoc *psoc,
7252 					    uint8_t vdev_id)
7253 {
7254 	struct wlan_objmgr_vdev *vdev;
7255 	bool is_vdev_ll_ht;
7256 
7257 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
7258 						    WLAN_POLICY_MGR_ID);
7259 	if (!vdev) {
7260 		policy_mgr_err("invalid vdev for id %d", vdev_id);
7261 		return false;
7262 	}
7263 	is_vdev_ll_ht = wlan_is_vdev_traffic_ll_ht(vdev);
7264 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
7265 
7266 	return is_vdev_ll_ht;
7267 }
7268 
7269 bool
7270 policy_mgr_check_2ghz_only_sap_affected_link(
7271 			struct wlan_objmgr_psoc *psoc,
7272 			uint8_t sap_vdev_id,
7273 			qdf_freq_t sap_ch_freq,
7274 			uint8_t ml_ch_freq_num,
7275 			qdf_freq_t *ml_freq_lst)
7276 {
7277 	uint8_t i;
7278 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7279 	struct wlan_objmgr_vdev *vdev;
7280 	enum QDF_OPMODE op_mode;
7281 
7282 	pm_ctx = policy_mgr_get_context(psoc);
7283 	if (!pm_ctx) {
7284 		policy_mgr_err("Invalid Context");
7285 		return false;
7286 	}
7287 
7288 	if (!WLAN_REG_IS_24GHZ_CH_FREQ(sap_ch_freq))
7289 		return false;
7290 
7291 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
7292 				psoc, sap_vdev_id,
7293 				WLAN_POLICY_MGR_ID);
7294 	if (!vdev) {
7295 		policy_mgr_debug("vdev is null %d", sap_vdev_id);
7296 		return false;
7297 	}
7298 	op_mode = wlan_vdev_mlme_get_opmode(vdev);
7299 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
7300 	if (op_mode != QDF_SAP_MODE)
7301 		return false;
7302 
7303 	if (!policy_mgr_is_acs_2ghz_only_sap(psoc, sap_vdev_id))
7304 		return false;
7305 
7306 	/* If 2G ml STA exist, force scc will happen, no link
7307 	 * to get affected.
7308 	 */
7309 	for (i = 0; i < ml_ch_freq_num; i++)
7310 		if (WLAN_REG_IS_24GHZ_CH_FREQ(ml_freq_lst[i]))
7311 			return false;
7312 
7313 	/* If All ml STA are 5/6 band, force SCC will not happen
7314 	 * for 2G only SAP, so return true to indicate one
7315 	 * link get affected.
7316 	 */
7317 	return true;
7318 }
7319 
7320 /*
7321  * policy_mgr_get_affected_links_for_go_sap_cli() - Check if any of the P2P OR
7322  * SAP is causing MCC with a ML link and also is configured high tput or low
7323  * latency
7324  * @psoc: psoc ctx
7325  * @num_ml_sta: Number of ML STA present
7326  * @ml_vdev_lst: ML STA vdev id list
7327  * @ml_freq_lst: ML STA freq list
7328  * @num_p2p_sap: Number of P2P and SAP present
7329  * @p2p_sap_vdev_lst: P2P and SAP vdev id list
7330  * @p2p_sap_freq_lst: P2P and SAP freq list
7331  *
7332  * Return: Number of links causing MCC with any of the P2P or SAP which is
7333  * configured high tput or low latency
7334  */
7335 static uint8_t
7336 policy_mgr_get_affected_links_for_go_sap_cli(struct wlan_objmgr_psoc *psoc,
7337 					     uint8_t num_ml_sta,
7338 					     uint8_t *ml_vdev_lst,
7339 					     qdf_freq_t *ml_freq_lst,
7340 					     uint8_t num_p2p_sap,
7341 					     uint8_t *p2p_sap_vdev_lst,
7342 					     qdf_freq_t *p2p_sap_freq_lst)
7343 {
7344 	uint8_t i = 0, k = 0, num_affected_links = 0;
7345 
7346 	if (!num_p2p_sap || num_ml_sta < 2)
7347 		return num_affected_links;
7348 
7349 	while (i < num_ml_sta) {
7350 		/* if any link is causing MCC with GO/GC/AP, set mcc as true.*/
7351 		for (k = 0; k < num_p2p_sap; k++) {
7352 			/* Continue if SCC */
7353 			if (ml_freq_lst[i] == p2p_sap_freq_lst[k])
7354 				continue;
7355 
7356 			/* SAP MCC with MLO STA link is not preferred.
7357 			 * If SAP is 2Ghz only by ACS and two ML link are
7358 			 * 5/6 band, then force SCC may not happen. In such
7359 			 * case inactive one link.
7360 			 */
7361 			if (policy_mgr_check_2ghz_only_sap_affected_link(
7362 					psoc, p2p_sap_vdev_lst[k],
7363 					p2p_sap_freq_lst[k],
7364 					num_ml_sta, ml_freq_lst)) {
7365 				policy_mgr_debug("2G only SAP vdev %d ch freq %d is not SCC with any MLO STA link",
7366 						 p2p_sap_vdev_lst[k],
7367 						 p2p_sap_freq_lst[k]);
7368 				num_affected_links++;
7369 				continue;
7370 			}
7371 
7372 			/* Continue if high tput or low latency is not set */
7373 			if (!policy_mgr_is_vdev_high_tput_or_low_latency(
7374 						psoc, p2p_sap_vdev_lst[k]))
7375 				continue;
7376 
7377 			/* If both freq are on same mac then its MCC */
7378 			if (policy_mgr_are_2_freq_on_same_mac(psoc,
7379 							ml_freq_lst[i],
7380 							p2p_sap_freq_lst[k])) {
7381 				policy_mgr_debug("ml sta vdev %d (freq %d) and p2p/sap vdev %d (freq %d) are MCC",
7382 						 ml_vdev_lst[i], ml_freq_lst[i],
7383 						 p2p_sap_vdev_lst[k],
7384 						 p2p_sap_freq_lst[k]);
7385 				num_affected_links++;
7386 			}
7387 		}
7388 		i++;
7389 	}
7390 
7391 	return num_affected_links;
7392 }
7393 
7394 /*
7395  * policy_mgr_get_ml_sta_and_p2p_cli_go_sap_info() - Get number of ML STA,
7396  * P2P and SAP interfaces and their vdev ids and freq list
7397  * @pm_ctx: pm_ctx ctx
7398  * @num_ml_sta: Return number of ML STA present
7399  * @num_disabled_ml_sta: Return number of disabled ML STA links
7400  * @ml_vdev_lst: Return ML STA vdev id list
7401  * @ml_freq_lst: Return ML STA freq list
7402  * @num_p2p_sap: Return number of P2P and SAP present
7403  * @p2p_sap_vdev_lst: Return P2P and SAP vdev id list
7404  * @p2p_sap_freq_lst: Return P2P and SAP freq list
7405  *
7406  * Return: void
7407  */
7408 static void
7409 policy_mgr_get_ml_sta_and_p2p_cli_go_sap_info(
7410 					struct policy_mgr_psoc_priv_obj *pm_ctx,
7411 					uint8_t *num_ml_sta,
7412 					uint8_t *num_disabled_ml_sta,
7413 					uint8_t *ml_vdev_lst,
7414 					qdf_freq_t *ml_freq_lst,
7415 					uint8_t *num_p2p_sap,
7416 					uint8_t *p2p_sap_vdev_lst,
7417 					qdf_freq_t *p2p_sap_freq_lst)
7418 {
7419 	enum policy_mgr_con_mode mode;
7420 	uint8_t vdev_id, conn_index;
7421 	qdf_freq_t freq;
7422 
7423 	*num_p2p_sap = 0;
7424 
7425 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
7426 	policy_mgr_get_ml_sta_info(pm_ctx, num_ml_sta, num_disabled_ml_sta,
7427 				   ml_vdev_lst, ml_freq_lst, NULL, NULL, NULL);
7428 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
7429 	     conn_index++) {
7430 		if (!pm_conc_connection_list[conn_index].in_use)
7431 			continue;
7432 		mode = pm_conc_connection_list[conn_index].mode;
7433 		if (!policy_mgr_is_mode_p2p_sap(mode))
7434 			continue;
7435 		vdev_id = pm_conc_connection_list[conn_index].vdev_id;
7436 		freq = pm_conc_connection_list[conn_index].freq;
7437 
7438 		/* add p2p and sap vdev and freq list */
7439 		p2p_sap_vdev_lst[*num_p2p_sap] = vdev_id;
7440 		p2p_sap_freq_lst[(*num_p2p_sap)++] = freq;
7441 	}
7442 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
7443 }
7444 
7445 /*
7446  * policy_mgr_is_ml_sta_links_in_mcc() - Check ML links are in MCC or not
7447  * @psoc: psoc ctx
7448  * @ml_freq_lst: ML STA freq list
7449  * @ml_vdev_lst: ML STA vdev id list
7450  * @ml_linkid_lst: ML STA link id list
7451  * @num_ml_sta: Number of total ML STA links
7452  * @affected_linkid_bitmap: link id bitmap which home channels are in MCC
7453  * with each other
7454  *
7455  * Return: true if ML link in MCC else false
7456  */
7457 bool
7458 policy_mgr_is_ml_sta_links_in_mcc(struct wlan_objmgr_psoc *psoc,
7459 				  qdf_freq_t *ml_freq_lst,
7460 				  uint8_t *ml_vdev_lst,
7461 				  uint8_t *ml_linkid_lst,
7462 				  uint8_t num_ml_sta,
7463 				  uint32_t *affected_linkid_bitmap)
7464 {
7465 	uint8_t i, j;
7466 	uint32_t link_id_bitmap;
7467 
7468 	for (i = 0; i < num_ml_sta; i++) {
7469 		link_id_bitmap = 0;
7470 		if (ml_linkid_lst)
7471 			link_id_bitmap = 1 << ml_linkid_lst[i];
7472 		for (j = i + 1; j < num_ml_sta; j++) {
7473 			if (ml_freq_lst[i] != ml_freq_lst[j] &&
7474 			    policy_mgr_2_freq_always_on_same_mac(
7475 					psoc, ml_freq_lst[i], ml_freq_lst[j])) {
7476 				if (ml_vdev_lst)
7477 					policy_mgr_debug("vdev %d and %d are in MCC with freq %d and freq %d",
7478 							 ml_vdev_lst[i],
7479 							 ml_vdev_lst[j],
7480 							 ml_freq_lst[i],
7481 							 ml_freq_lst[j]);
7482 				if (ml_linkid_lst) {
7483 					link_id_bitmap |= 1 << ml_linkid_lst[j];
7484 					policy_mgr_debug("link %d and %d are in MCC with freq %d and freq %d",
7485 							 ml_linkid_lst[i],
7486 							 ml_linkid_lst[j],
7487 							 ml_freq_lst[i],
7488 							 ml_freq_lst[j]);
7489 					if (affected_linkid_bitmap)
7490 						*affected_linkid_bitmap =
7491 							link_id_bitmap;
7492 				}
7493 				return true;
7494 			}
7495 		}
7496 	}
7497 
7498 	return false;
7499 }
7500 
7501 /*
7502  * policy_mgr_handle_mcc_ml_sta() - disables one ML STA link if causing MCC
7503  * DBS - if ML STA links on 5 GHz + 6 GHz
7504  * SBS - if both ML STA links on 5 GHz high/5 GHz low
7505  * non-SBS - any combo (5/6 GHz + 5/6 GHz OR 2 GHz + 5/6 GHz)
7506  * @psoc: psoc ctx
7507  *
7508  * Return: Success if MCC link is disabled else failure
7509  */
7510 static QDF_STATUS
7511 policy_mgr_handle_mcc_ml_sta(struct wlan_objmgr_psoc *psoc,
7512 			     struct wlan_objmgr_vdev *vdev)
7513 {
7514 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0;
7515 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7516 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7517 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7518 
7519 	if ((wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE))
7520 		return QDF_STATUS_E_FAILURE;
7521 
7522 	pm_ctx = policy_mgr_get_context(psoc);
7523 	if (!pm_ctx) {
7524 		policy_mgr_err("Invalid Context");
7525 		return QDF_STATUS_E_FAILURE;
7526 	}
7527 
7528 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
7529 				   ml_sta_vdev_lst, ml_freq_lst,
7530 				   NULL, NULL, NULL);
7531 	if (num_ml_sta < 2 || num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
7532 	    num_disabled_ml_sta) {
7533 		policy_mgr_debug("num_ml_sta invalid %d or link already disabled%d",
7534 				 num_ml_sta, num_disabled_ml_sta);
7535 		return QDF_STATUS_E_FAILURE;
7536 	}
7537 
7538 	if (!policy_mgr_is_ml_sta_links_in_mcc(psoc, ml_freq_lst,
7539 					       ml_sta_vdev_lst, NULL,
7540 					       num_ml_sta,
7541 					       NULL))
7542 		return QDF_STATUS_E_FAILURE;
7543 
7544 	/*
7545 	 * eMLSR is allowed in MCC mode also. So, don't disable any links
7546 	 * if current connection happens in eMLSR mode.
7547 	 */
7548 	if (policy_mgr_is_mlo_in_mode_emlsr(psoc, NULL, NULL)) {
7549 		policy_mgr_debug("Don't disable eMLSR links");
7550 		return QDF_STATUS_E_FAILURE;
7551 	}
7552 
7553 	policy_mgr_mlo_sta_set_link(psoc, MLO_LINK_FORCE_REASON_CONNECT,
7554 				    MLO_LINK_FORCE_MODE_ACTIVE_NUM,
7555 				    num_ml_sta, ml_sta_vdev_lst);
7556 	return QDF_STATUS_SUCCESS;
7557 }
7558 
7559 /*
7560  * policy_mgr_sta_ml_link_enable_allowed() - Check with given ML links and
7561  * existing concurrencies, a disabled ml link can be enabled back.
7562  * @psoc: psoc ctx
7563  * @num_disabled_ml_sta: Number of existing disabled links
7564  * @num_ml_sta: Number of total ML STA links
7565  * @ml_freq_lst: ML STA freq list
7566  * @ml_vdev_lst: ML STA vdev id list
7567  *
7568  * Return: if link can be enabled or not
7569  */
7570 static bool
7571 policy_mgr_sta_ml_link_enable_allowed(struct wlan_objmgr_psoc *psoc,
7572 				      uint8_t num_disabled_ml_sta,
7573 				      uint8_t num_ml_sta,
7574 				      qdf_freq_t *ml_freq_lst,
7575 				      uint8_t *ml_vdev_lst)
7576 {
7577 	union conc_ext_flag conc_ext_flags;
7578 	uint8_t disabled_link_vdev_id;
7579 	qdf_freq_t disabled_link_freq;
7580 	struct wlan_objmgr_vdev *vdev;
7581 
7582 	/* If no link is disabled nothing to do */
7583 	if (!num_disabled_ml_sta || num_ml_sta < 2)
7584 		return false;
7585 	if (policy_mgr_is_ml_sta_links_in_mcc(psoc, ml_freq_lst, ml_vdev_lst,
7586 					      NULL, num_ml_sta,
7587 					      NULL))
7588 		return false;
7589 	/* Disabled link is at the last index */
7590 	disabled_link_vdev_id = ml_vdev_lst[num_ml_sta - 1];
7591 	disabled_link_freq = ml_freq_lst[num_ml_sta - 1];
7592 	policy_mgr_debug("disabled_link_vdev_id %d disabled_link_freq %d",
7593 			 disabled_link_vdev_id, disabled_link_freq);
7594 	if (!disabled_link_freq)
7595 		return false;
7596 
7597 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, disabled_link_vdev_id,
7598 						    WLAN_POLICY_MGR_ID);
7599 	if (!vdev) {
7600 		policy_mgr_err("invalid vdev for id %d", disabled_link_vdev_id);
7601 		return false;
7602 	}
7603 	conc_ext_flags.value = policy_mgr_get_conc_ext_flags(vdev, false);
7604 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
7605 
7606 	return policy_mgr_is_concurrency_allowed(psoc, PM_STA_MODE,
7607 					disabled_link_freq, HW_MODE_20_MHZ,
7608 					conc_ext_flags.value, NULL);
7609 }
7610 
7611 /*
7612  * policy_mgr_re_enable_ml_sta_on_p2p_sap_down() - Handle enable
7613  * link on P2P/SAP/ML_STA vdev UP or channel change
7614  * @psoc: objmgr psoc
7615  * @vdev: vdev which went UP or changed chan
7616  *
7617  * Return: void
7618  */
7619 static void
7620 policy_mgr_handle_sap_cli_go_ml_sta_up_csa(struct wlan_objmgr_psoc *psoc,
7621 					   struct wlan_objmgr_vdev *vdev)
7622 {
7623 	uint8_t num_ml_sta = 0, num_p2p_sap = 0, num_disabled_ml_sta = 0;
7624 	uint8_t num_affected_link;
7625 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7626 	uint8_t p2p_sap_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7627 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7628 	qdf_freq_t p2p_sap_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7629 	uint8_t vdev_id = wlan_vdev_get_id(vdev);
7630 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7631 	QDF_STATUS status;
7632 
7633 	pm_ctx = policy_mgr_get_context(psoc);
7634 	if (!pm_ctx) {
7635 		policy_mgr_err("Invalid Context");
7636 		return;
7637 	}
7638 
7639 	status = policy_mgr_handle_ml_sta_link_state_allowed(
7640 				psoc, MLO_LINK_FORCE_REASON_CONNECT);
7641 	if (QDF_IS_STATUS_ERROR(status))
7642 		return;
7643 
7644 	/*
7645 	 * eMLSR API policy_mgr_handle_emlsr_sta_concurrency() takes care of
7646 	 * eMLSR concurrencies. Currently, eMLSR STA can't operate with any
7647 	 * cocurrent mode, i.e. one link gets force-disabled when a new
7648 	 * concurrecy is coming up.
7649 	 */
7650 	if (policy_mgr_is_mlo_in_mode_emlsr(psoc, NULL, NULL)) {
7651 		policy_mgr_debug("STA connected in eMLSR mode, don't enable/disable links");
7652 		return;
7653 	}
7654 
7655 	if (QDF_IS_STATUS_SUCCESS(policy_mgr_handle_mcc_ml_sta(psoc, vdev)))
7656 		return;
7657 
7658 	status = policy_mgr_handle_ml_sta_link_concurrency(psoc, vdev);
7659 	if (QDF_IS_STATUS_SUCCESS(status))
7660 		return;
7661 
7662 	policy_mgr_get_ml_sta_and_p2p_cli_go_sap_info(pm_ctx, &num_ml_sta,
7663 						      &num_disabled_ml_sta,
7664 						      ml_sta_vdev_lst,
7665 						      ml_freq_lst, &num_p2p_sap,
7666 						      p2p_sap_vdev_lst,
7667 						      p2p_sap_freq_lst);
7668 
7669 	policy_mgr_debug("vdev %d: num_ml_sta %d disabled %d num_p2p_sap %d",
7670 			 vdev_id, num_ml_sta, num_disabled_ml_sta, num_p2p_sap);
7671 	if (num_ml_sta < 2 || num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
7672 	    num_p2p_sap > MAX_NUMBER_OF_CONC_CONNECTIONS)
7673 		return;
7674 
7675 	num_affected_link = policy_mgr_get_affected_links_for_go_sap_cli(psoc,
7676 						num_ml_sta, ml_sta_vdev_lst,
7677 						ml_freq_lst, num_p2p_sap,
7678 						p2p_sap_vdev_lst,
7679 						p2p_sap_freq_lst);
7680 
7681 	if (!num_affected_link) {
7682 		policy_mgr_debug("vdev %d: no affected link found", vdev_id);
7683 		goto enable_link;
7684 	}
7685 
7686 	if (num_disabled_ml_sta) {
7687 		policy_mgr_debug("As a link is already disabled and affected link present (%d), No action required",
7688 				 num_affected_link);
7689 		return;
7690 	}
7691 
7692 	policy_mgr_mlo_sta_set_link(psoc, MLO_LINK_FORCE_REASON_CONNECT,
7693 				    MLO_LINK_FORCE_MODE_ACTIVE_NUM,
7694 				    num_ml_sta, ml_sta_vdev_lst);
7695 
7696 	return;
7697 enable_link:
7698 
7699 	/*
7700 	 * if no affected link and link can be allowed to enable then renable
7701 	 * the disabled link.
7702 	 */
7703 	if (policy_mgr_sta_ml_link_enable_allowed(psoc, num_disabled_ml_sta,
7704 						  num_ml_sta, ml_freq_lst,
7705 						  ml_sta_vdev_lst))
7706 		policy_mgr_mlo_sta_set_link(psoc,
7707 					    MLO_LINK_FORCE_REASON_DISCONNECT,
7708 					    MLO_LINK_FORCE_MODE_NO_FORCE,
7709 					    num_ml_sta, ml_sta_vdev_lst);
7710 }
7711 
7712 void
7713 policy_mgr_handle_ml_sta_links_on_vdev_up_csa(struct wlan_objmgr_psoc *psoc,
7714 					      enum QDF_OPMODE mode,
7715 					      uint8_t vdev_id)
7716 {
7717 	struct wlan_objmgr_vdev *vdev;
7718 
7719 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
7720 						    WLAN_POLICY_MGR_ID);
7721 	if (!vdev) {
7722 		policy_mgr_err("vdev %d: invalid vdev", vdev_id);
7723 		return;
7724 	}
7725 
7726 	if (mode == QDF_STA_MODE || mode == QDF_SAP_MODE ||
7727 	    mode == QDF_P2P_CLIENT_MODE || mode == QDF_P2P_GO_MODE)
7728 		policy_mgr_handle_sap_cli_go_ml_sta_up_csa(psoc, vdev);
7729 
7730 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
7731 }
7732 
7733 #define SET_LINK_TIMEOUT 6000
7734 QDF_STATUS policy_mgr_wait_for_set_link_update(struct wlan_objmgr_psoc *psoc)
7735 {
7736 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7737 	QDF_STATUS status;
7738 
7739 	pm_ctx = policy_mgr_get_context(psoc);
7740 	if (!pm_ctx) {
7741 		policy_mgr_err("Invalid Context");
7742 		return QDF_STATUS_E_INVAL;
7743 	}
7744 
7745 	if (!policy_mgr_get_link_in_progress(pm_ctx)) {
7746 		policy_mgr_err("link is not in progress");
7747 		return QDF_STATUS_E_FAILURE;
7748 	}
7749 
7750 	status =
7751 		qdf_wait_for_event_completion(&pm_ctx->set_link_update_done_evt,
7752 					      SET_LINK_TIMEOUT);
7753 
7754 	if (QDF_IS_STATUS_ERROR(status)) {
7755 		policy_mgr_set_link_in_progress(pm_ctx, false);
7756 		policy_mgr_err("wait for set_link_in_progress failed");
7757 	}
7758 
7759 	return status;
7760 }
7761 
7762 void policy_mgr_handle_ml_sta_link_on_traffic_type_change(
7763 						struct wlan_objmgr_psoc *psoc,
7764 						struct wlan_objmgr_vdev *vdev)
7765 {
7766 	/* Check if any set link is already progress and thus wait */
7767 	policy_mgr_wait_for_set_link_update(psoc);
7768 
7769 	ml_nlink_conn_change_notify(
7770 		psoc, wlan_vdev_get_id(vdev),
7771 		ml_nlink_connection_updated_evt, NULL);
7772 
7773 	/*
7774 	 * Check if traffic type change lead to set link is progress and
7775 	 * thus wait for it to complete.
7776 	 */
7777 	policy_mgr_wait_for_set_link_update(psoc);
7778 }
7779 
7780 static QDF_STATUS
7781 policy_mgr_handle_ml_sta_link_enable_on_sta_down(struct wlan_objmgr_psoc *psoc,
7782 						 struct wlan_objmgr_vdev *vdev)
7783 {
7784 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0, num_non_ml = 0;
7785 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7786 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7787 	uint8_t vdev_id = wlan_vdev_get_id(vdev);
7788 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7789 
7790 	if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE)
7791 		return QDF_STATUS_E_INVAL;
7792 
7793 	pm_ctx = policy_mgr_get_context(psoc);
7794 	if (!pm_ctx) {
7795 		policy_mgr_err("Invalid Context");
7796 		return QDF_STATUS_E_INVAL;
7797 	}
7798 
7799 	/* Handle only when non-ML STA is going down and ML STA is active */
7800 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
7801 				   ml_sta_vdev_lst, ml_freq_lst, &num_non_ml,
7802 				   NULL, NULL);
7803 	policy_mgr_debug("vdev %d: num_ml_sta %d disabled %d num_non_ml: %d",
7804 			 vdev_id, num_ml_sta, num_disabled_ml_sta, num_non_ml);
7805 
7806 	/*
7807 	 * No ML STA is present or sinle link ML is present or
7808 	 * more no.of links are active than supported concurrent connections
7809 	 */
7810 	if (num_ml_sta < 2 || num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS)
7811 		return QDF_STATUS_E_INVAL;
7812 
7813 	/* STA+STA cases */
7814 
7815 	/* One ML/non-ML STA is going down and another non ML STA is present */
7816 	if (num_non_ml) {
7817 		policy_mgr_debug("non-ML STA is present");
7818 		return QDF_STATUS_SUCCESS;
7819 	}
7820 
7821 	/*
7822 	 * If no links are disabled or
7823 	 * link can not be allowed to enable then skip checking further.
7824 	 */
7825 	if (!num_disabled_ml_sta ||
7826 	    !policy_mgr_sta_ml_link_enable_allowed(psoc, num_disabled_ml_sta,
7827 						  num_ml_sta, ml_freq_lst,
7828 						  ml_sta_vdev_lst)) {
7829 		if (num_disabled_ml_sta)
7830 			policy_mgr_debug("Not re-enabled due to disallowed concurrency");
7831 		goto done;
7832 	}
7833 
7834 	policy_mgr_mlo_sta_set_link(psoc,
7835 				    MLO_LINK_FORCE_REASON_DISCONNECT,
7836 				    MLO_LINK_FORCE_MODE_NO_FORCE,
7837 				    num_ml_sta, ml_sta_vdev_lst);
7838 
7839 done:
7840 	return QDF_STATUS_SUCCESS;
7841 }
7842 
7843 /*
7844  * policy_mgr_re_enable_ml_sta_on_p2p_sap_sta_down() - Handle enable
7845  * link on P2P/SAP/ML_STA vdev down
7846  * @psoc: objmgr psoc
7847  * @vdev: vdev which went down
7848  *
7849  * Return: void
7850  */
7851 static void
7852 policy_mgr_re_enable_ml_sta_on_p2p_sap_sta_down(struct wlan_objmgr_psoc *psoc,
7853 						struct wlan_objmgr_vdev *vdev)
7854 {
7855 	uint8_t num_ml_sta = 0, num_p2p_sap = 0, num_disabled_ml_sta = 0;
7856 	uint8_t num_affected_link = 0;
7857 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7858 	uint8_t p2p_sap_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7859 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7860 	qdf_freq_t p2p_sap_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
7861 	uint8_t vdev_id = wlan_vdev_get_id(vdev);
7862 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7863 	QDF_STATUS status;
7864 
7865 	status = policy_mgr_handle_ml_sta_link_state_allowed(
7866 				psoc, MLO_LINK_FORCE_REASON_DISCONNECT);
7867 	if (QDF_IS_STATUS_ERROR(status))
7868 		return;
7869 
7870 	status = policy_mgr_handle_ml_sta_link_enable_on_sta_down(psoc, vdev);
7871 	if (QDF_IS_STATUS_SUCCESS(status))
7872 		return;
7873 
7874 	pm_ctx = policy_mgr_get_context(psoc);
7875 	if (!pm_ctx) {
7876 		policy_mgr_err("Invalid Context");
7877 		return;
7878 	}
7879 
7880 	policy_mgr_get_ml_sta_and_p2p_cli_go_sap_info(pm_ctx, &num_ml_sta,
7881 						      &num_disabled_ml_sta,
7882 						      ml_sta_vdev_lst,
7883 						      ml_freq_lst, &num_p2p_sap,
7884 						      p2p_sap_vdev_lst,
7885 						      p2p_sap_freq_lst);
7886 
7887 	policy_mgr_debug("vdev %d: num_ml_sta %d disabled %d num_p2p_sap %d",
7888 			 vdev_id, num_ml_sta, num_disabled_ml_sta, num_p2p_sap);
7889 
7890 	if (num_ml_sta < 2 || num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
7891 	    num_p2p_sap > MAX_NUMBER_OF_CONC_CONNECTIONS)
7892 		return;
7893 
7894 	/* If link can not be allowed to enable then skip checking further. */
7895 	if (!policy_mgr_sta_ml_link_enable_allowed(psoc, num_disabled_ml_sta,
7896 						   num_ml_sta, ml_freq_lst,
7897 						   ml_sta_vdev_lst))
7898 		return;
7899 
7900 	/*
7901 	 * If num_p2p_sap is non zero, ie p2p or sap still present check if
7902 	 * disable link is still required, if not enable the link.
7903 	 *
7904 	 * If num_p2p_sap is 0, ie only ml sta is present, enable the link.
7905 	 */
7906 	if (num_p2p_sap)
7907 		num_affected_link =
7908 			policy_mgr_get_affected_links_for_go_sap_cli(psoc,
7909 						num_ml_sta, ml_sta_vdev_lst,
7910 						ml_freq_lst, num_p2p_sap,
7911 						p2p_sap_vdev_lst,
7912 						p2p_sap_freq_lst);
7913 
7914 	if (num_affected_link)
7915 		policy_mgr_debug("vdev %d: Affected link present, dont reanabe ML link",
7916 				 vdev_id);
7917 	else
7918 		policy_mgr_mlo_sta_set_link(psoc,
7919 					    MLO_LINK_FORCE_REASON_DISCONNECT,
7920 					    MLO_LINK_FORCE_MODE_NO_FORCE,
7921 					    num_ml_sta, ml_sta_vdev_lst);
7922 }
7923 
7924 void policy_mgr_handle_ml_sta_links_on_vdev_down(struct wlan_objmgr_psoc *psoc,
7925 						 enum QDF_OPMODE mode,
7926 						 uint8_t vdev_id)
7927 {
7928 	struct wlan_objmgr_vdev *vdev;
7929 
7930 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
7931 						    WLAN_POLICY_MGR_ID);
7932 	if (!vdev) {
7933 		policy_mgr_err("vdev %d: invalid vdev", vdev_id);
7934 		return;
7935 	}
7936 
7937 	if (mode == QDF_STA_MODE || mode == QDF_SAP_MODE ||
7938 	    mode == QDF_P2P_CLIENT_MODE || mode == QDF_P2P_GO_MODE)
7939 		policy_mgr_re_enable_ml_sta_on_p2p_sap_sta_down(psoc, vdev);
7940 
7941 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
7942 }
7943 
7944 /**
7945  * policy_mgr_pick_link_vdev_from_inactive_list() - Get inactive vdev
7946  * which can be activated
7947  * @psoc: PSOC object information
7948  * @vdev: vdev object
7949  * @inactive_vdev_num: inactive vdev num in list
7950  * @inactive_vdev_lst: inactive vdev list
7951  * @inactive_freq_lst: inactive vdev frequency list
7952  * @picked_vdev_id: Picked vdev id
7953  * @non_removed_vdev_id: not removed inactive vdev id
7954  *
7955  * If one link is removed and inactivated, pick one of existing inactive
7956  * vdev which can be activated by checking concurrency API.
7957  *
7958  * Return: void
7959  */
7960 static void
7961 policy_mgr_pick_link_vdev_from_inactive_list(
7962 	struct wlan_objmgr_psoc *psoc, struct wlan_objmgr_vdev *vdev,
7963 	uint8_t inactive_vdev_num, uint8_t *inactive_vdev_lst,
7964 	qdf_freq_t *inactive_freq_lst, uint8_t *picked_vdev_id,
7965 	uint8_t *non_removed_vdev_id)
7966 {
7967 	struct policy_mgr_psoc_priv_obj *pm_ctx;
7968 	struct policy_mgr_conc_connection_info
7969 			info[MAX_NUMBER_OF_CONC_CONNECTIONS] = { {0} };
7970 	uint8_t num_del = 0;
7971 	union conc_ext_flag conc_ext_flags = {0};
7972 	uint8_t i;
7973 
7974 	pm_ctx = policy_mgr_get_context(psoc);
7975 	if (!pm_ctx) {
7976 		policy_mgr_err("Invalid Context");
7977 		return;
7978 	}
7979 
7980 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
7981 	policy_mgr_store_and_del_conn_info_by_vdev_id(
7982 			psoc, wlan_vdev_get_id(vdev),
7983 			info, &num_del);
7984 	/* pick one inactive parnter link and make it active */
7985 	for (i = 0; i < inactive_vdev_num; i++) {
7986 		struct wlan_objmgr_vdev *partner_vdev;
7987 
7988 		if (wlan_get_vdev_link_removed_flag_by_vdev_id(
7989 				psoc, inactive_vdev_lst[i])) {
7990 			policy_mgr_debug("skip removed link vdev %d",
7991 					 inactive_vdev_lst[i]);
7992 			continue;
7993 		}
7994 
7995 		partner_vdev =
7996 		wlan_objmgr_get_vdev_by_id_from_psoc(psoc,
7997 						     inactive_vdev_lst[i],
7998 						     WLAN_POLICY_MGR_ID);
7999 		if (!partner_vdev) {
8000 			policy_mgr_err("invalid partner_vdev %d ",
8001 				       inactive_vdev_lst[i]);
8002 			continue;
8003 		}
8004 		*non_removed_vdev_id = inactive_vdev_lst[i];
8005 
8006 		conc_ext_flags.value =
8007 		policy_mgr_get_conc_ext_flags(partner_vdev, false);
8008 
8009 		if (policy_mgr_is_concurrency_allowed(psoc, PM_STA_MODE,
8010 						      inactive_freq_lst[i],
8011 						      HW_MODE_20_MHZ,
8012 						      conc_ext_flags.value,
8013 						      NULL)) {
8014 			*picked_vdev_id = inactive_vdev_lst[i];
8015 			wlan_objmgr_vdev_release_ref(partner_vdev,
8016 						     WLAN_POLICY_MGR_ID);
8017 			break;
8018 		}
8019 		wlan_objmgr_vdev_release_ref(partner_vdev, WLAN_POLICY_MGR_ID);
8020 	}
8021 	/* Restore the connection info */
8022 	policy_mgr_restore_deleted_conn_info(psoc, info, num_del);
8023 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
8024 }
8025 
8026 void policy_mgr_handle_link_removal_on_vdev(struct wlan_objmgr_vdev *vdev)
8027 {
8028 	struct wlan_objmgr_psoc *psoc;
8029 	struct policy_mgr_psoc_priv_obj *pm_ctx;
8030 	uint32_t i;
8031 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0;
8032 	uint8_t num_active_ml_sta;
8033 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8034 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8035 	uint8_t vdev_id = wlan_vdev_get_id(vdev);
8036 	uint8_t non_removal_link_vdev_id = WLAN_INVALID_VDEV_ID;
8037 	uint8_t picked_vdev_id = WLAN_INVALID_VDEV_ID;
8038 	QDF_STATUS status;
8039 
8040 	psoc = wlan_vdev_get_psoc(vdev);
8041 	if (!psoc) {
8042 		policy_mgr_err("Failed to get psoc");
8043 		return;
8044 	}
8045 	pm_ctx = policy_mgr_get_context(psoc);
8046 	if (!pm_ctx) {
8047 		policy_mgr_err("Invalid Context");
8048 		return;
8049 	}
8050 	if (wlan_get_vdev_link_removed_flag_by_vdev_id(psoc, vdev_id)) {
8051 		policy_mgr_debug("removal link vdev %d is removed already",
8052 				 vdev_id);
8053 		return;
8054 	}
8055 	/* mark link removed for vdev */
8056 	wlan_set_vdev_link_removed_flag_by_vdev_id(psoc, vdev_id,
8057 						   true);
8058 	status = policy_mgr_handle_ml_sta_link_state_allowed(
8059 			psoc, MLO_LINK_FORCE_REASON_LINK_REMOVAL);
8060 	if (QDF_IS_STATUS_ERROR(status)) {
8061 		wlan_set_vdev_link_removed_flag_by_vdev_id(psoc, vdev_id,
8062 							   false);
8063 		return;
8064 	}
8065 
8066 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
8067 				   ml_sta_vdev_lst, ml_freq_lst,
8068 				   NULL, NULL, NULL);
8069 	if (!num_ml_sta) {
8070 		policy_mgr_debug("unexpected event, no ml sta");
8071 		return;
8072 	}
8073 	if (num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
8074 	    num_disabled_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
8075 	    num_ml_sta <= num_disabled_ml_sta) {
8076 		policy_mgr_debug("unexpected ml sta num %d %d",
8077 				 num_ml_sta, num_disabled_ml_sta);
8078 		return;
8079 	}
8080 	/* Single link FW should handle BTM/disassoc and do roaming.
8081 	 * Host will not send inactive command to FW.
8082 	 */
8083 	if (num_ml_sta < 2) {
8084 		policy_mgr_debug("no op for single link mlo, num_ml_sta %d",
8085 				 num_ml_sta);
8086 		return;
8087 	}
8088 
8089 	policy_mgr_debug("removal link vdev %d num_ml_sta %d num_disabled_ml_sta %d",
8090 			 vdev_id, num_ml_sta, num_disabled_ml_sta);
8091 
8092 	num_active_ml_sta = num_ml_sta;
8093 	if (num_ml_sta >= num_disabled_ml_sta)
8094 		num_active_ml_sta = num_ml_sta - num_disabled_ml_sta;
8095 
8096 	for (i = 0; i < num_active_ml_sta; i++)
8097 		if (ml_sta_vdev_lst[i] == vdev_id)
8098 			break;
8099 
8100 	if (i == num_active_ml_sta) {
8101 		/* no found in active ml list, it must be in inactive list */
8102 		policy_mgr_debug("removal link vdev %d is inactive already",
8103 				 vdev_id);
8104 
8105 		/* send inactive command to fw again with "link removal
8106 		 * reason"
8107 		 */
8108 		policy_mgr_mlo_sta_set_link(
8109 			psoc, MLO_LINK_FORCE_REASON_LINK_REMOVAL,
8110 			MLO_LINK_FORCE_MODE_INACTIVE,
8111 			1, &vdev_id);
8112 		return;
8113 	}
8114 
8115 	/* pick one inactive parnter link and make it active */
8116 	if (num_active_ml_sta < num_ml_sta)
8117 		policy_mgr_pick_link_vdev_from_inactive_list(
8118 				psoc, vdev, num_disabled_ml_sta,
8119 				&ml_sta_vdev_lst[num_active_ml_sta],
8120 				&ml_freq_lst[num_active_ml_sta],
8121 				&picked_vdev_id,
8122 				&non_removal_link_vdev_id);
8123 	if (picked_vdev_id != WLAN_INVALID_VDEV_ID) {
8124 		/* find one inactive link can be active, send it to fw with
8125 		 * the removed link together.
8126 		 */
8127 		policy_mgr_debug("active parnter vdev %d, inactive removal vdev %d",
8128 				 picked_vdev_id, vdev_id);
8129 		policy_mgr_mlo_sta_set_link_ext(
8130 				psoc, MLO_LINK_FORCE_REASON_LINK_REMOVAL,
8131 				MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE,
8132 				1, &picked_vdev_id,
8133 				1, &vdev_id);
8134 		return;
8135 	}
8136 	if (num_active_ml_sta < 2) {
8137 		/* For multi-link MLO, one link is removed and
8138 		 * no find one inactive link can be active:
8139 		 * 1. If at least one left link is not link removed state,
8140 		 * host will trigger roaming.
8141 		 * 2. If all left links are link removed state,
8142 		 * FW will trigger roaming based on BTM or disassoc frame
8143 		 */
8144 		if (non_removal_link_vdev_id != WLAN_INVALID_VDEV_ID) {
8145 			policy_mgr_debug("trigger roaming, non_removal_link_vdev_id %d",
8146 					 non_removal_link_vdev_id);
8147 			policy_mgr_trigger_roam_on_link_removal(vdev);
8148 		}
8149 		return;
8150 	}
8151 	/* If active link number >= 2 and one link is removed, then at least
8152 	 * one link is still active, just send inactived command to fw.
8153 	 */
8154 	policy_mgr_mlo_sta_set_link(psoc, MLO_LINK_FORCE_REASON_LINK_REMOVAL,
8155 				    MLO_LINK_FORCE_MODE_INACTIVE,
8156 				    1, &vdev_id);
8157 }
8158 
8159 /**
8160  * policy_mgr_is_restart_sap_required_with_mlo_sta() - Check SAP required to
8161  * restart for force SCC with MLO STA
8162  * @psoc: PSOC object information
8163  * @sap_vdev_id: sap vdev id
8164  * @sap_ch_freq: sap channel frequency
8165  *
8166  * For MLO STA+SAP case, mlo link maybe in inactive state after connected
8167  * and the hw mode maybe not updated, check MCC/SCC by
8168  * policy_mgr_are_2_freq_on_same_mac may not match MCC/SCC state
8169  * after the link is activated by target later. So to check frequency match
8170  * or not to decide SAP do force SCC or not if MLO STA 2 links are present.
8171  *
8172  * Return: true if SAP is required to force SCC with MLO STA
8173  */
8174 static bool
8175 policy_mgr_is_restart_sap_required_with_mlo_sta(struct wlan_objmgr_psoc *psoc,
8176 						uint8_t sap_vdev_id,
8177 						qdf_freq_t sap_ch_freq)
8178 {
8179 	struct policy_mgr_psoc_priv_obj *pm_ctx;
8180 	uint32_t i;
8181 	bool same_freq_with_mlo_sta = false;
8182 	bool restart_required = false;
8183 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0, num_ml_active_sta = 0;
8184 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8185 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8186 
8187 	pm_ctx = policy_mgr_get_context(psoc);
8188 	if (!pm_ctx) {
8189 		policy_mgr_err("Invalid Context");
8190 		return false;
8191 	}
8192 
8193 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
8194 				   ml_sta_vdev_lst, ml_freq_lst,
8195 				   NULL, NULL, NULL);
8196 	if (num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS) {
8197 		policy_mgr_debug("unexpected num_ml_sta %d ", num_ml_sta);
8198 		return false;
8199 	}
8200 
8201 	num_ml_active_sta = num_ml_sta;
8202 	if (num_ml_sta >= num_disabled_ml_sta)
8203 		num_ml_active_sta = num_ml_sta - num_disabled_ml_sta;
8204 	for (i = 0; i < num_ml_active_sta; i++) {
8205 		if (ml_freq_lst[i] == sap_ch_freq) {
8206 			same_freq_with_mlo_sta = true;
8207 			break;
8208 		}
8209 	}
8210 
8211 	if (num_ml_active_sta >= 2 && !same_freq_with_mlo_sta) {
8212 		policy_mgr_debug("SAP is not SCC with any of active MLO STA link, restart SAP");
8213 		restart_required = true;
8214 	}
8215 
8216 	return restart_required;
8217 }
8218 
8219 void policy_mgr_activate_mlo_links(struct wlan_objmgr_psoc *psoc,
8220 				   uint8_t session_id, uint8_t num_links,
8221 				   struct qdf_mac_addr active_link_addr[2])
8222 {
8223 	uint8_t idx, link, active_vdev_cnt = 0, inactive_vdev_cnt = 0;
8224 	uint16_t ml_vdev_cnt = 0;
8225 	struct wlan_objmgr_vdev *tmp_vdev_lst[WLAN_UMAC_MLO_MAX_VDEVS] = {0};
8226 	uint8_t active_vdev_lst[WLAN_UMAC_MLO_MAX_VDEVS] = {0};
8227 	uint8_t inactive_vdev_lst[WLAN_UMAC_MLO_MAX_VDEVS] = {0};
8228 	struct wlan_objmgr_vdev *vdev;
8229 	uint8_t *link_mac_addr;
8230 	bool active_vdev_present = false;
8231 
8232 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, session_id,
8233 						    WLAN_POLICY_MGR_ID);
8234 	if (!vdev) {
8235 		policy_mgr_err("vdev_id: %d vdev not found", session_id);
8236 		return;
8237 	}
8238 
8239 	if (!wlan_cm_is_vdev_connected(vdev)) {
8240 		policy_mgr_err("vdev is not in connected state");
8241 		goto done;
8242 	}
8243 
8244 	if (!wlan_vdev_mlme_is_mlo_vdev(vdev)) {
8245 		policy_mgr_err("vdev is not mlo vdev");
8246 		goto done;
8247 	}
8248 
8249 	mlo_get_ml_vdev_list(vdev, &ml_vdev_cnt, tmp_vdev_lst);
8250 	policy_mgr_debug("Num active links: %d, ML vdev cnt: %d", num_links,
8251 			 ml_vdev_cnt);
8252 	for (idx = 0; idx < ml_vdev_cnt; idx++) {
8253 		link_mac_addr = wlan_vdev_mlme_get_macaddr(tmp_vdev_lst[idx]);
8254 		policy_mgr_debug("link addr: " QDF_MAC_ADDR_FMT,
8255 				 QDF_MAC_ADDR_REF(link_mac_addr));
8256 		for (link = 0; link < num_links; link++) {
8257 			policy_mgr_debug("active addr: " QDF_MAC_ADDR_FMT,
8258 			   QDF_MAC_ADDR_REF(&active_link_addr[link].bytes[0]));
8259 			if (!qdf_mem_cmp(link_mac_addr,
8260 					 &active_link_addr[link].bytes[0],
8261 					 QDF_MAC_ADDR_SIZE)) {
8262 				active_vdev_lst[active_vdev_cnt] =
8263 					wlan_vdev_get_id(tmp_vdev_lst[idx]);
8264 				active_vdev_cnt++;
8265 				active_vdev_present = true;
8266 				policy_mgr_debug("Link address match");
8267 			}
8268 		}
8269 		if (!active_vdev_present) {
8270 			inactive_vdev_lst[inactive_vdev_cnt] =
8271 					wlan_vdev_get_id(tmp_vdev_lst[idx]);
8272 			inactive_vdev_cnt++;
8273 			policy_mgr_err("No link address match");
8274 		}
8275 		active_vdev_present = false;
8276 	}
8277 
8278 	policy_mgr_debug("active vdev cnt: %d, inactive vdev cnt: %d",
8279 			 active_vdev_cnt, inactive_vdev_cnt);
8280 
8281 	if (active_vdev_cnt &&
8282 	    policy_mgr_is_emlsr_sta_concurrency_present(psoc)) {
8283 		policy_mgr_debug("Concurrency exists, cannot enter EMLSR mode");
8284 		goto ref_release;
8285 	}
8286 
8287 	/*
8288 	 * If there are both active and inactive vdev count, then issue a
8289 	 * single WMI with force mode MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE,
8290 	 * else if there is only active vdev count, send single WMI for
8291 	 * all active vdevs with force mode MLO_LINK_FORCE_MODE_ACTIVE.
8292 	 */
8293 	if (active_vdev_cnt && inactive_vdev_cnt)
8294 		policy_mgr_mlo_sta_set_link_ext(
8295 					psoc, MLO_LINK_FORCE_REASON_CONNECT,
8296 					MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE,
8297 					active_vdev_cnt, active_vdev_lst,
8298 					inactive_vdev_cnt, inactive_vdev_lst);
8299 	else if (active_vdev_cnt && !inactive_vdev_cnt)
8300 		policy_mgr_mlo_sta_set_link(psoc,
8301 					    MLO_LINK_FORCE_REASON_DISCONNECT,
8302 					    MLO_LINK_FORCE_MODE_ACTIVE,
8303 					    active_vdev_cnt, active_vdev_lst);
8304 ref_release:
8305 	for (idx = 0; idx < ml_vdev_cnt; idx++)
8306 		mlo_release_vdev_ref(tmp_vdev_lst[idx]);
8307 done:
8308 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
8309 }
8310 
8311 QDF_STATUS
8312 policy_mgr_update_mlo_links_based_on_linkid(struct wlan_objmgr_psoc *psoc,
8313 					    uint8_t vdev_id,
8314 					    uint8_t num_links,
8315 					    uint8_t *link_id_list,
8316 					    uint32_t *config_state_list)
8317 {
8318 	uint8_t idx, link, active_vdev_cnt = 0, inactive_vdev_cnt = 0;
8319 	uint16_t ml_vdev_cnt = 0;
8320 	struct wlan_objmgr_vdev *vdev_lst[WLAN_UMAC_MLO_MAX_VDEVS] = {0};
8321 	uint8_t active_vdev_lst[WLAN_UMAC_MLO_MAX_VDEVS] = {0};
8322 	uint8_t inactive_vdev_lst[WLAN_UMAC_MLO_MAX_VDEVS] = {0};
8323 	struct wlan_objmgr_vdev *vdev;
8324 	uint8_t link_id, num_links_to_disable = 0, num_matched_linkid = 0;
8325 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
8326 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0, num_non_ml = 0;
8327 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8328 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8329 	struct policy_mgr_psoc_priv_obj *pm_ctx;
8330 
8331 	for (idx = 0; idx < num_links; idx++) {
8332 		if (config_state_list[idx] == 0)
8333 			num_links_to_disable++;
8334 	}
8335 
8336 	if (num_links_to_disable == num_links) {
8337 		policy_mgr_debug("vdev: %d num_links_to_disable: %d", vdev_id,
8338 				 num_links_to_disable);
8339 		return QDF_STATUS_E_FAILURE;
8340 	}
8341 
8342 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
8343 						    WLAN_POLICY_MGR_ID);
8344 	if (!vdev) {
8345 		policy_mgr_err("vdev: %d vdev not found", vdev_id);
8346 		return QDF_STATUS_E_FAILURE;
8347 	}
8348 
8349 	if (!wlan_cm_is_vdev_connected(vdev)) {
8350 		policy_mgr_err("vdev: %d is not in connected state", vdev_id);
8351 		goto release_vdev_ref;
8352 	}
8353 
8354 	if (!wlan_vdev_mlme_is_mlo_vdev(vdev)) {
8355 		policy_mgr_err("vdev:%d is not mlo vdev", vdev_id);
8356 		goto release_vdev_ref;
8357 	}
8358 
8359 	pm_ctx = policy_mgr_get_context(psoc);
8360 	if (!pm_ctx) {
8361 		policy_mgr_err("Invalid pm context");
8362 		goto release_vdev_ref;
8363 	}
8364 
8365 	mlo_get_ml_vdev_list(vdev, &ml_vdev_cnt, vdev_lst);
8366 	for (idx = 0; idx < ml_vdev_cnt; idx++) {
8367 		link_id = wlan_vdev_get_link_id(vdev_lst[idx]);
8368 		for (link = 0; link < num_links; link++) {
8369 			if (link_id_list[link] == link_id) {
8370 				num_matched_linkid++;
8371 				policy_mgr_debug("link id:%d match", link_id);
8372 				if (config_state_list[link]) {
8373 					active_vdev_lst[active_vdev_cnt] =
8374 						wlan_vdev_get_id(vdev_lst[idx]);
8375 					active_vdev_cnt++;
8376 				} else {
8377 					inactive_vdev_lst[inactive_vdev_cnt] =
8378 						wlan_vdev_get_id(vdev_lst[idx]);
8379 					inactive_vdev_cnt++;
8380 				}
8381 			}
8382 		}
8383 	}
8384 
8385 	policy_mgr_debug("vdev: %d, active links: %d, ml count: %d, active count: %d, inactive count: %d",
8386 			 vdev_id, num_links, ml_vdev_cnt, active_vdev_cnt,
8387 			 inactive_vdev_cnt);
8388 
8389 	if (num_links != num_matched_linkid) {
8390 		policy_mgr_debug("invalid link id(s), num_matched_linkid: %d",
8391 				 num_matched_linkid);
8392 		goto release_ml_vdev_ref;
8393 	}
8394 
8395 	if (active_vdev_cnt &&
8396 	    policy_mgr_is_emlsr_sta_concurrency_present(psoc)) {
8397 		policy_mgr_debug("vdev: %d emlsr sta conn present", vdev_id);
8398 		if (active_vdev_cnt == 1)
8399 			status = QDF_STATUS_SUCCESS;
8400 		goto release_ml_vdev_ref;
8401 	}
8402 
8403 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
8404 				   ml_sta_vdev_lst, ml_freq_lst, &num_non_ml,
8405 				   NULL, NULL);
8406 	policy_mgr_debug("vdev %d: num_ml_sta %d disabled %d num_non_ml: %d",
8407 			 vdev_id, num_ml_sta, num_disabled_ml_sta, num_non_ml);
8408 
8409 	/*
8410 	 * No ML STA is present or sinle link ML is present or
8411 	 * more no.of links are active than supported concurrent connections
8412 	 */
8413 	if (!num_ml_sta || num_ml_sta < 2 ||
8414 	    num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS)
8415 		goto release_ml_vdev_ref;
8416 
8417 	if (!num_disabled_ml_sta) {
8418 		/*
8419 		 * both link are already enabled and received set link req to
8420 		 * enable both again
8421 		 */
8422 		if (active_vdev_cnt && !inactive_vdev_cnt) {
8423 			status = QDF_STATUS_SUCCESS;
8424 			goto release_ml_vdev_ref;
8425 		}
8426 
8427 		/*
8428 		 * both link are already enabled and received set link req
8429 		 * disable one link, disable any
8430 		 */
8431 		if (active_vdev_cnt && inactive_vdev_cnt) {
8432 			status = policy_mgr_mlo_sta_set_link_ext(psoc,
8433 					MLO_LINK_FORCE_REASON_CONNECT,
8434 					MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE,
8435 					active_vdev_cnt, active_vdev_lst,
8436 					inactive_vdev_cnt, inactive_vdev_lst);
8437 			goto release_ml_vdev_ref;
8438 		}
8439 	} else {
8440 		/*
8441 		 * one link is enable and one link is disabled, If disabled
8442 		 * link can not be allowed to enable then send status failure
8443 		 * to upper layer.
8444 		 */
8445 		if (active_vdev_cnt &&
8446 		    !policy_mgr_sta_ml_link_enable_allowed(psoc,
8447 							   num_disabled_ml_sta,
8448 							   num_ml_sta,
8449 							   ml_freq_lst,
8450 							   ml_sta_vdev_lst)) {
8451 			policy_mgr_debug("vdev %d: link enable not allowed",
8452 					 vdev_id);
8453 			goto release_ml_vdev_ref;
8454 		}
8455 
8456 		/*
8457 		 * If there are both active and inactive vdev count, then
8458 		 * issue a single WMI with force mode
8459 		 * MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE, else if there is only
8460 		 * active vdev count, send single WMI for all active vdevs
8461 		 * with force mode MLO_LINK_FORCE_MODE_ACTIVE.
8462 		 */
8463 		if (active_vdev_cnt && inactive_vdev_cnt)
8464 			status = policy_mgr_mlo_sta_set_link_ext(psoc,
8465 					MLO_LINK_FORCE_REASON_CONNECT,
8466 					MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE,
8467 					active_vdev_cnt, active_vdev_lst,
8468 					inactive_vdev_cnt, inactive_vdev_lst);
8469 		else if (active_vdev_cnt && !inactive_vdev_cnt)
8470 			status = policy_mgr_mlo_sta_set_link(psoc,
8471 					MLO_LINK_FORCE_REASON_DISCONNECT,
8472 					MLO_LINK_FORCE_MODE_ACTIVE,
8473 					active_vdev_cnt, active_vdev_lst);
8474 	}
8475 
8476 release_ml_vdev_ref:
8477 	for (idx = 0; idx < ml_vdev_cnt; idx++)
8478 		mlo_release_vdev_ref(vdev_lst[idx]);
8479 release_vdev_ref:
8480 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
8481 
8482 	return status;
8483 }
8484 
8485 /**
8486  * policy_mgr_process_mlo_sta_dynamic_force_num_link() - Set links for MLO STA
8487  * @psoc: psoc object
8488  * @reason: Reason for which link is forced
8489  * @mode: Force reason
8490  * @num_mlo_vdev: number of mlo vdev
8491  * @mlo_vdev_lst: MLO STA vdev list
8492  * @force_active_cnt: number of MLO links to operate in active state as per
8493  * user req
8494  *
8495  * User space provides the desired number of MLO links to operate in active
8496  * state at any given time. Host validate request as per current concurrency
8497  * and send SET LINK requests to FW. FW will choose which MLO links should
8498  * operate in the active state.
8499  *
8500  * Return: QDF_STATUS
8501  */
8502 static QDF_STATUS
8503 policy_mgr_process_mlo_sta_dynamic_force_num_link(struct wlan_objmgr_psoc *psoc,
8504 				enum mlo_link_force_reason reason,
8505 				enum mlo_link_force_mode mode,
8506 				uint8_t num_mlo_vdev, uint8_t *mlo_vdev_lst,
8507 				uint8_t force_active_cnt)
8508 {
8509 	struct mlo_link_set_active_req *req;
8510 	QDF_STATUS status;
8511 	struct policy_mgr_psoc_priv_obj *pm_ctx;
8512 	struct wlan_objmgr_vdev *vdev;
8513 
8514 	if (!num_mlo_vdev) {
8515 		policy_mgr_err("invalid 0 num_mlo_vdev");
8516 		return QDF_STATUS_E_INVAL;
8517 	}
8518 
8519 	pm_ctx = policy_mgr_get_context(psoc);
8520 	if (!pm_ctx) {
8521 		policy_mgr_err("Invalid Context");
8522 		return QDF_STATUS_E_INVAL;
8523 	}
8524 
8525 	req = qdf_mem_malloc(sizeof(*req));
8526 	if (!req)
8527 		return QDF_STATUS_E_NOMEM;
8528 
8529 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, mlo_vdev_lst[0],
8530 						    WLAN_POLICY_MGR_ID);
8531 	if (!vdev) {
8532 		policy_mgr_err("vdev %d: invalid vdev", mlo_vdev_lst[0]);
8533 		qdf_mem_free(req);
8534 		return QDF_STATUS_E_FAILURE;
8535 	}
8536 
8537 	policy_mgr_debug("vdev %d: mode %d num_mlo_vdev %d reason %d",
8538 			 wlan_vdev_get_id(vdev), mode, num_mlo_vdev, reason);
8539 
8540 	/*
8541 	 * TODO: this API has to be merged with policy_mgr_mlo_sta_set_link_ext
8542 	 * as part of 3 link FR change as in caller only we have to decide how
8543 	 * many links to disable/enable for MLO_LINK_FORCE_MODE_ACTIVE_NUM or
8544 	 * MLO_LINK_FORCE_MODE_INACTIVE_NUM scenario
8545 	 */
8546 	req->ctx.vdev = vdev;
8547 	req->param.reason = reason;
8548 	req->param.force_mode = mode;
8549 	req->ctx.set_mlo_link_cb = policy_mgr_handle_link_enable_disable_resp;
8550 	req->ctx.validate_set_mlo_link_cb =
8551 		policy_mgr_validate_set_mlo_link_cb;
8552 	req->ctx.cb_arg = req;
8553 
8554 	/* set MLO vdev bit mask */
8555 	policy_mgr_fill_ml_active_link_vdev_bitmap(req, mlo_vdev_lst,
8556 						   num_mlo_vdev);
8557 
8558 	pm_ctx->active_vdev_bitmap = req->param.vdev_bitmap[0];
8559 	pm_ctx->inactive_vdev_bitmap = req->param.vdev_bitmap[1];
8560 
8561 	req->param.num_link_entry = 1;
8562 	req->param.link_num[0].num_of_link = force_active_cnt;
8563 	req->param.control_flags.dynamic_force_link_num = 1;
8564 
8565 	if (ml_is_nlink_service_supported(psoc)) {
8566 		status =
8567 		policy_mgr_mlo_sta_set_link_by_linkid(psoc, vdev, reason,
8568 						      mode,
8569 						      req->param.link_num[0].
8570 						      num_of_link,
8571 						      num_mlo_vdev,
8572 						      mlo_vdev_lst,
8573 						      0,
8574 						      NULL);
8575 		qdf_mem_free(req);
8576 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
8577 
8578 		if (status != QDF_STATUS_E_PENDING) {
8579 			policy_mgr_err("set_link_by_linkid status %d", status);
8580 			return status;
8581 		}
8582 		return QDF_STATUS_SUCCESS;
8583 	}
8584 
8585 	policy_mgr_set_link_in_progress(pm_ctx, true);
8586 
8587 	status = mlo_ser_set_link_req(req);
8588 	if (QDF_IS_STATUS_ERROR(status)) {
8589 		policy_mgr_err("vdev %d: Failed to set link mode %d num_mlo_vdev %d force_active_cnt: %d, reason %d",
8590 			       wlan_vdev_get_id(vdev), mode, num_mlo_vdev,
8591 			       force_active_cnt,
8592 			       reason);
8593 		qdf_mem_free(req);
8594 		policy_mgr_set_link_in_progress(pm_ctx, false);
8595 	}
8596 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
8597 	return status;
8598 }
8599 
8600 QDF_STATUS policy_mgr_update_active_mlo_num_links(struct wlan_objmgr_psoc *psoc,
8601 						  uint8_t vdev_id,
8602 						  uint8_t force_active_cnt)
8603 {
8604 	struct wlan_objmgr_vdev *vdev;
8605 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0, num_non_ml = 0;
8606 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8607 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8608 	struct policy_mgr_psoc_priv_obj *pm_ctx;
8609 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
8610 
8611 	if (policy_mgr_is_emlsr_sta_concurrency_present(psoc)) {
8612 		policy_mgr_debug("Concurrency exists, cannot enter EMLSR mode");
8613 		return QDF_STATUS_E_FAILURE;
8614 	}
8615 
8616 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
8617 						    WLAN_POLICY_MGR_ID);
8618 	if (!vdev) {
8619 		policy_mgr_err("vdev_id: %d vdev not found", vdev_id);
8620 		return QDF_STATUS_E_FAILURE;
8621 	}
8622 
8623 	if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE)
8624 		goto release_vdev_ref;
8625 
8626 	if (!wlan_cm_is_vdev_connected(vdev)) {
8627 		policy_mgr_err("vdev is not in connected state");
8628 		goto release_vdev_ref;
8629 	}
8630 
8631 	if (!wlan_vdev_mlme_is_mlo_vdev(vdev)) {
8632 		policy_mgr_err("vdev is not mlo vdev");
8633 		goto release_vdev_ref;
8634 	}
8635 
8636 	pm_ctx = policy_mgr_get_context(psoc);
8637 	if (!pm_ctx) {
8638 		policy_mgr_err("Invalid Context");
8639 		goto release_vdev_ref;
8640 	}
8641 
8642 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
8643 				   ml_sta_vdev_lst, ml_freq_lst, &num_non_ml,
8644 				   NULL, NULL);
8645 	policy_mgr_debug("vdev %d: num_ml_sta %d disabled %d num_non_ml: %d",
8646 			 vdev_id, num_ml_sta, num_disabled_ml_sta, num_non_ml);
8647 
8648 	/*
8649 	 * No ML STA is present or more no.of links are active than supported
8650 	 * concurrent connections
8651 	 */
8652 	if (!num_ml_sta || num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS)
8653 		goto release_vdev_ref;
8654 
8655 	/*
8656 	 * DUT connected with MLO AP, one link is always active, So if
8657 	 * request comes to make one link is active, host sends set link command
8658 	 * with mode MLO_LINK_FORCE_MODE_ACTIVE_NUM, so that FW should restrict
8659 	 * to only one link and avoid switch from MLSR to MLMR.
8660 	 */
8661 	if (force_active_cnt == 1)
8662 		goto set_link;
8663 
8664 	/*
8665 	 * num_disabled_ml_sta == 0, means 2 link is already active,
8666 	 * In this case send set link command with num link 2 and mode
8667 	 * MLO_LINK_FORCE_MODE_ACTIVE_NUM, so that FW should restrict to only
8668 	 * in MLMR mode (2 link should be active).
8669 	 */
8670 	if (force_active_cnt == 2 && num_disabled_ml_sta == 0)
8671 		goto set_link;
8672 
8673 	/* Link can not be allowed to enable then skip checking further */
8674 	if (!policy_mgr_sta_ml_link_enable_allowed(psoc, num_disabled_ml_sta,
8675 						   num_ml_sta, ml_freq_lst,
8676 						   ml_sta_vdev_lst)) {
8677 		policy_mgr_debug("vdev %d: link enable not allowed", vdev_id);
8678 		goto release_vdev_ref;
8679 	}
8680 
8681 set_link:
8682 	status = policy_mgr_process_mlo_sta_dynamic_force_num_link(psoc,
8683 					     MLO_LINK_FORCE_REASON_CONNECT,
8684 					     MLO_LINK_FORCE_MODE_ACTIVE_NUM,
8685 					     num_ml_sta, ml_sta_vdev_lst,
8686 					     force_active_cnt);
8687 	if (QDF_IS_STATUS_SUCCESS(status))
8688 		policy_mgr_debug("vdev %d: link enable allowed", vdev_id);
8689 
8690 release_vdev_ref:
8691 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
8692 	return status;
8693 }
8694 
8695 QDF_STATUS
8696 policy_mgr_clear_ml_links_settings_in_fw(struct wlan_objmgr_psoc *psoc,
8697 					 uint8_t vdev_id)
8698 {
8699 	struct wlan_objmgr_vdev *vdev;
8700 	uint8_t num_ml_sta = 0, num_disabled_ml_sta = 0, num_non_ml = 0;
8701 	uint8_t ml_sta_vdev_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8702 	qdf_freq_t ml_freq_lst[MAX_NUMBER_OF_CONC_CONNECTIONS] = {0};
8703 	struct policy_mgr_psoc_priv_obj *pm_ctx;
8704 	uint8_t num_link_to_no_force = 0, num_active_ml_sta = 0;
8705 	QDF_STATUS status = QDF_STATUS_E_FAILURE;
8706 
8707 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
8708 						    WLAN_POLICY_MGR_ID);
8709 	if (!vdev) {
8710 		policy_mgr_err("vdev: %d vdev not found", vdev_id);
8711 		return QDF_STATUS_E_FAILURE;
8712 	}
8713 
8714 	if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE)
8715 		goto release_vdev_ref;
8716 
8717 	if (!wlan_cm_is_vdev_connected(vdev)) {
8718 		policy_mgr_err("vdev: %d is not in connected state", vdev_id);
8719 		goto release_vdev_ref;
8720 	}
8721 
8722 	if (!wlan_vdev_mlme_is_mlo_vdev(vdev)) {
8723 		policy_mgr_err("vdev: %d is not mlo vdev", vdev_id);
8724 		goto release_vdev_ref;
8725 	}
8726 
8727 	pm_ctx = policy_mgr_get_context(psoc);
8728 	if (!pm_ctx) {
8729 		policy_mgr_err("vdev: %d Invalid Context", vdev_id);
8730 		goto release_vdev_ref;
8731 	}
8732 
8733 	policy_mgr_get_ml_sta_info(pm_ctx, &num_ml_sta, &num_disabled_ml_sta,
8734 				   ml_sta_vdev_lst, ml_freq_lst, &num_non_ml,
8735 				   NULL, NULL);
8736 	policy_mgr_debug("vdev %d: num_ml_sta %d disabled %d num_non_ml: %d",
8737 			 vdev_id, num_ml_sta, num_disabled_ml_sta, num_non_ml);
8738 
8739 	if (!num_ml_sta || num_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS ||
8740 	    num_disabled_ml_sta > MAX_NUMBER_OF_CONC_CONNECTIONS)
8741 		goto release_vdev_ref;
8742 
8743 	num_active_ml_sta = num_ml_sta;
8744 	if (num_ml_sta >= num_disabled_ml_sta)
8745 		num_active_ml_sta = num_ml_sta - num_disabled_ml_sta;
8746 
8747 	num_link_to_no_force += num_active_ml_sta;
8748 
8749 	/* Link can not be allowed to enable then skip checking further */
8750 	if (policy_mgr_sta_ml_link_enable_allowed(psoc, num_disabled_ml_sta,
8751 						  num_ml_sta, ml_freq_lst,
8752 						  ml_sta_vdev_lst)) {
8753 		num_link_to_no_force += num_disabled_ml_sta;
8754 		policy_mgr_debug("Link enable allowed, total num_links: %d",
8755 				 num_link_to_no_force);
8756 	}
8757 
8758 	if (num_link_to_no_force < 1 ||
8759 	    num_link_to_no_force > MAX_NUMBER_OF_CONC_CONNECTIONS) {
8760 		policy_mgr_debug("vdev %d: invalid num_link_to_no_force: %d",
8761 				 vdev_id, num_link_to_no_force);
8762 		goto release_vdev_ref;
8763 	}
8764 
8765 	/*
8766 	 * send WMI_MLO_LINK_SET_ACTIVE_CMDID to clear user mode setting
8767 	 * configured via QCA_WLAN_VENDOR_ATTR_LINK_STATE_CONTROL_MODE in FW
8768 	 */
8769 	status = policy_mgr_mlo_sta_set_link(psoc,
8770 					MLO_LINK_FORCE_REASON_CONNECT,
8771 					MLO_LINK_FORCE_MODE_NO_FORCE,
8772 					num_link_to_no_force,
8773 					ml_sta_vdev_lst);
8774 	if (QDF_IS_STATUS_ERROR(status))
8775 		goto release_vdev_ref;
8776 	else
8777 		policy_mgr_debug("clear user mode setting for num_links:%d",
8778 				 num_link_to_no_force);
8779 
8780 	/*
8781 	 * send WMI_MLO_LINK_SET_ACTIVE_CMDID with value of
8782 	 * num_link as 0 to clear dynamic mode setting configured
8783 	 * via vendor attr LINK_STATE_MIXED_MODE_ACTIVE_NUM_LINKS in FW
8784 	 */
8785 	status = policy_mgr_process_mlo_sta_dynamic_force_num_link(psoc,
8786 				MLO_LINK_FORCE_REASON_CONNECT,
8787 				MLO_LINK_FORCE_MODE_ACTIVE_NUM,
8788 				num_link_to_no_force, ml_sta_vdev_lst, 0);
8789 	if (QDF_IS_STATUS_SUCCESS(status))
8790 		policy_mgr_debug("clear mixed mode setting for num_links:%d",
8791 				 num_link_to_no_force);
8792 release_vdev_ref:
8793 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
8794 	return status;
8795 }
8796 
8797 #else
8798 static bool
8799 policy_mgr_allow_sta_concurrency(struct wlan_objmgr_psoc *psoc,
8800 				 qdf_freq_t freq,
8801 				 uint32_t ext_flags)
8802 {
8803 	uint32_t count;
8804 
8805 	count = policy_mgr_mode_specific_connection_count(psoc, PM_STA_MODE,
8806 							  NULL);
8807 	if (!count)
8808 		return true;
8809 
8810 	if (count >= 2) {
8811 		policy_mgr_rl_debug("Disallow 3rd STA");
8812 		return false;
8813 	}
8814 
8815 	if (!policy_mgr_allow_multiple_sta_connections(psoc)) {
8816 		policy_mgr_rl_debug("Multiple STA connections is not allowed");
8817 		return false;
8818 	}
8819 
8820 	return true;
8821 }
8822 
8823 static bool
8824 policy_mgr_is_restart_sap_required_with_mlo_sta(struct wlan_objmgr_psoc *psoc,
8825 						uint8_t sap_vdev_id,
8826 						qdf_freq_t sap_ch_freq)
8827 {
8828 	return false;
8829 }
8830 #endif
8831 
8832 #ifdef WLAN_FEATURE_P2P_P2P_STA
8833 bool policy_mgr_is_p2p_p2p_conc_supported(struct wlan_objmgr_psoc *psoc)
8834 {
8835 	return wlan_mlme_get_p2p_p2p_conc_support(psoc);
8836 }
8837 #endif
8838 
8839 /**
8840  * policy_mgr_is_third_conn_sta_p2p_p2p_valid: This API checks the firmware
8841  * capability and allows STA + P2P + P2P combination. It can be in SCC/MCC/DBS
8842  * @psoc: psoc pointer
8843  * @new_conn_mode: third connection mode
8844  *
8845  * Return: true if support else false
8846  */
8847 static bool policy_mgr_is_third_conn_sta_p2p_p2p_valid(
8848 					struct wlan_objmgr_psoc *psoc,
8849 					enum policy_mgr_con_mode new_conn_mode)
8850 {
8851 	int num_sta, num_go, num_cli;
8852 
8853 	num_sta = policy_mgr_mode_specific_connection_count(psoc,
8854 							    PM_STA_MODE,
8855 							    NULL);
8856 
8857 	num_go = policy_mgr_mode_specific_connection_count(psoc,
8858 							   PM_P2P_GO_MODE,
8859 							   NULL);
8860 
8861 	num_cli = policy_mgr_mode_specific_connection_count(psoc,
8862 							    PM_P2P_CLIENT_MODE,
8863 							    NULL);
8864 
8865 	if (num_sta + num_go + num_cli != 2)
8866 		return true;
8867 
8868 	/* If STA + P2P + another STA comes up then return true
8869 	 * as this API is only for two port P2P + single STA combo
8870 	 * checks
8871 	 */
8872 	if (num_sta == 1 && new_conn_mode == PM_STA_MODE)
8873 		return true;
8874 
8875 	if ((((PM_STA_MODE == pm_conc_connection_list[0].mode &&
8876 	       PM_P2P_GO_MODE == pm_conc_connection_list[1].mode) ||
8877 	      (PM_P2P_GO_MODE == pm_conc_connection_list[0].mode &&
8878 	       PM_STA_MODE == pm_conc_connection_list[1].mode))
8879 	      ||
8880 	      (PM_P2P_GO_MODE == pm_conc_connection_list[0].mode &&
8881 	       PM_P2P_GO_MODE == pm_conc_connection_list[1].mode)
8882 	      ||
8883 	      ((PM_STA_MODE == pm_conc_connection_list[0].mode &&
8884 		PM_P2P_CLIENT_MODE == pm_conc_connection_list[1].mode) ||
8885 	       (PM_P2P_CLIENT_MODE == pm_conc_connection_list[0].mode &&
8886 		PM_STA_MODE == pm_conc_connection_list[1].mode))
8887 	      ||
8888 	      (PM_P2P_CLIENT_MODE == pm_conc_connection_list[0].mode &&
8889 	       PM_P2P_CLIENT_MODE == pm_conc_connection_list[1].mode)
8890 	      ||
8891 	      ((PM_P2P_GO_MODE == pm_conc_connection_list[0].mode &&
8892 		PM_P2P_CLIENT_MODE == pm_conc_connection_list[1].mode) ||
8893 	       (PM_P2P_CLIENT_MODE == pm_conc_connection_list[0].mode &&
8894 		PM_P2P_GO_MODE == pm_conc_connection_list[1].mode))) &&
8895 	      num_sta <= 1) {
8896 		if ((new_conn_mode == PM_STA_MODE ||
8897 		     new_conn_mode == PM_P2P_CLIENT_MODE ||
8898 		     new_conn_mode == PM_P2P_GO_MODE) &&
8899 		    !policy_mgr_is_p2p_p2p_conc_supported(psoc))
8900 			return false;
8901 	}
8902 
8903 	return true;
8904 }
8905 
8906 static bool policy_mgr_is_sap_go_allowed_with_ll_sap(
8907 					struct wlan_objmgr_psoc *psoc,
8908 					qdf_freq_t freq,
8909 					enum policy_mgr_con_mode mode)
8910 {
8911 	/**
8912 	 * Scenario: When ll SAP(whose profile is set as gaming or
8913 	 * lossless audio) is present on 5GHz channel and SAP/GO
8914 	 * is trying to come up.
8915 	 * Validate the ch_freq of SAP/GO for both DBS and SBS case
8916 	 */
8917 	if ((mode == PM_SAP_MODE || mode == PM_P2P_GO_MODE) &&
8918 	    !policy_mgr_is_ll_sap_concurrency_valid(psoc, freq, mode))
8919 		return false;
8920 
8921 	return true;
8922 }
8923 
8924 bool policy_mgr_is_concurrency_allowed(struct wlan_objmgr_psoc *psoc,
8925 				       enum policy_mgr_con_mode mode,
8926 				       uint32_t ch_freq,
8927 				       enum hw_mode_bandwidth bw,
8928 				       uint32_t ext_flags,
8929 				       struct policy_mgr_pcl_list *pcl)
8930 {
8931 	uint32_t num_connections = 0, count = 0, index = 0, i;
8932 	bool status = false, match = false;
8933 	uint32_t list[MAX_NUMBER_OF_CONC_CONNECTIONS];
8934 	struct policy_mgr_psoc_priv_obj *pm_ctx;
8935 	bool sta_sap_scc_on_dfs_chan;
8936 	bool go_force_scc;
8937 	enum channel_state chan_state;
8938 	bool is_dfs_ch = false;
8939 	struct ch_params ch_params;
8940 
8941 	pm_ctx = policy_mgr_get_context(psoc);
8942 	if (!pm_ctx) {
8943 		policy_mgr_err("Invalid Context");
8944 		return status;
8945 	}
8946 	/* find the current connection state from pm_conc_connection_list*/
8947 	num_connections = policy_mgr_get_connection_count(psoc);
8948 
8949 	if (num_connections && policy_mgr_is_sub_20_mhz_enabled(psoc)) {
8950 		policy_mgr_rl_debug("dont allow concurrency if Sub 20 MHz is enabled");
8951 		return status;
8952 	}
8953 
8954 	if (policy_mgr_max_concurrent_connections_reached(psoc)) {
8955 		policy_mgr_rl_debug("Reached max concurrent connections: %d",
8956 				    pm_ctx->cfg.max_conc_cxns);
8957 		policy_mgr_validate_conn_info(psoc);
8958 		return status;
8959 	}
8960 
8961 	if (ch_freq) {
8962 		if (wlan_reg_is_5ghz_ch_freq(ch_freq)) {
8963 			qdf_mem_zero(&ch_params, sizeof(ch_params));
8964 			ch_params.ch_width = policy_mgr_get_ch_width(bw);
8965 			chan_state =
8966 			wlan_reg_get_5g_bonded_channel_state_for_pwrmode(
8967 					pm_ctx->pdev, ch_freq,
8968 					&ch_params, REG_CURRENT_PWR_MODE);
8969 			if (chan_state == CHANNEL_STATE_DFS)
8970 				is_dfs_ch = true;
8971 		}
8972 		/* don't allow 3rd home channel on same MAC
8973 		 * also check for single mac target which doesn't
8974 		 * support interbad MCC as well
8975 		 */
8976 		if (!policy_mgr_allow_new_home_channel(psoc, mode, ch_freq,
8977 						       num_connections,
8978 						       is_dfs_ch,
8979 						       ext_flags))
8980 			return status;
8981 
8982 		/*
8983 		 * 1) DFS MCC is not yet supported
8984 		 * 2) If you already have STA connection on 5G channel then
8985 		 *    don't allow any other persona to make connection on DFS
8986 		 *    channel because STA 5G + DFS MCC is not allowed.
8987 		 * 3) If STA is on 2G channel and SAP is coming up on
8988 		 *    DFS channel then allow concurrency but make sure it is
8989 		 *    going to DBS and send PCL to firmware indicating that
8990 		 *    don't allow STA to roam to 5G channels.
8991 		 * 4) On a single MAC device, if a SAP/P2PGO is already on a DFS
8992 		 *    channel, don't allow a 2 channel as it will result
8993 		 *    in MCC which is not allowed.
8994 		 */
8995 		if (!policy_mgr_is_5g_channel_allowed(psoc,
8996 			ch_freq, list, PM_P2P_GO_MODE))
8997 			return status;
8998 		if (!policy_mgr_is_5g_channel_allowed(psoc,
8999 			ch_freq, list, PM_SAP_MODE))
9000 			return status;
9001 		if (!policy_mgr_is_6g_channel_allowed(psoc, mode,
9002 						      ch_freq))
9003 			return status;
9004 
9005 		sta_sap_scc_on_dfs_chan =
9006 			policy_mgr_is_sta_sap_scc_allowed_on_dfs_chan(psoc);
9007 		go_force_scc = policy_mgr_go_scc_enforced(psoc);
9008 		if ((mode == PM_SAP_MODE || mode == PM_P2P_GO_MODE) &&
9009 		    (!sta_sap_scc_on_dfs_chan ||
9010 		     !policy_mgr_is_sta_sap_scc(psoc, ch_freq) ||
9011 		     (!go_force_scc && mode == PM_P2P_GO_MODE))) {
9012 			if (is_dfs_ch)
9013 				match = policy_mgr_disallow_mcc(psoc,
9014 								ch_freq);
9015 		}
9016 		if (true == match) {
9017 			policy_mgr_rl_debug("No MCC, SAP/GO about to come up on DFS channel");
9018 			return status;
9019 		}
9020 		if ((policy_mgr_is_hw_dbs_capable(psoc) != true) &&
9021 		    num_connections) {
9022 			if (WLAN_REG_IS_24GHZ_CH_FREQ(ch_freq)) {
9023 				if (policy_mgr_is_sap_p2pgo_on_dfs(psoc)) {
9024 					policy_mgr_rl_debug("MCC not allowed: SAP/P2PGO on DFS");
9025 					return status;
9026 				}
9027 			}
9028 		}
9029 	}
9030 
9031 	if (mode == PM_STA_MODE &&
9032 	    !policy_mgr_allow_sta_concurrency(psoc, ch_freq, ext_flags))
9033 		return status;
9034 
9035 	if (!policy_mgr_allow_sap_go_concurrency(psoc, mode, ch_freq,
9036 						 WLAN_INVALID_VDEV_ID)) {
9037 		policy_mgr_rl_debug("This concurrency combination is not allowed");
9038 		return status;
9039 	}
9040 
9041 	/*
9042 	 * don't allow two P2P GO on same band, if fw doesn't
9043 	 * support p2p +p2p concurrency
9044 	 */
9045 	if (ch_freq && mode == PM_P2P_GO_MODE && num_connections &&
9046 	    !policy_mgr_is_p2p_p2p_conc_supported(psoc)) {
9047 		index = 0;
9048 		count = policy_mgr_mode_specific_connection_count(
9049 				psoc, PM_P2P_GO_MODE, list);
9050 		qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9051 		while (index < count) {
9052 			if (WLAN_REG_IS_SAME_BAND_FREQS(
9053 			    ch_freq,
9054 			    pm_conc_connection_list[list[index]].freq)) {
9055 				policy_mgr_rl_debug("Don't allow P2P GO on same band");
9056 				qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9057 				return status;
9058 			}
9059 			index++;
9060 		}
9061 		qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9062 	}
9063 
9064 	if (!policy_mgr_allow_wapi_concurrency(pm_ctx)) {
9065 		policy_mgr_rl_debug("Don't allow new conn when wapi security conn existing");
9066 		return status;
9067 	}
9068 
9069 	/* Allow sta+p2p+p2p only if firmware supports the capability */
9070 	if (!policy_mgr_is_third_conn_sta_p2p_p2p_valid(psoc, mode)) {
9071 		policy_mgr_err("Don't allow third connection as GO or GC or STA with old fw");
9072 		return status;
9073 	}
9074 
9075 	/* Validate ll sap + sap/go concurrency */
9076 	if (!policy_mgr_is_sap_go_allowed_with_ll_sap(psoc, ch_freq, mode)) {
9077 		policy_mgr_err("LL SAP concurrency is not valid");
9078 		return status;
9079 	}
9080 
9081 	/*
9082 	 * Don't allow DFS SAP on non-SCC channels if an ML-STA is already
9083 	 * present. PCL list returns the SCC channels and all channels from
9084 	 * other MAC in case of non-ML/single link STA.
9085 	 */
9086 	if (mode == PM_SAP_MODE && pcl &&
9087 	    wlan_reg_is_dfs_for_freq(pm_ctx->pdev, ch_freq)) {
9088 		for (i = 0; i < pcl->pcl_len; i++)
9089 			if (pcl->pcl_list[i] == ch_freq) {
9090 				status = true;
9091 				break;
9092 			}
9093 		if (!status) {
9094 			policy_mgr_err("SAP channel %d Not present in PCL",
9095 				       ch_freq);
9096 			return status;
9097 		}
9098 	}
9099 	status = true;
9100 
9101 	return status;
9102 }
9103 
9104 bool policy_mgr_allow_concurrency(struct wlan_objmgr_psoc *psoc,
9105 				  enum policy_mgr_con_mode mode,
9106 				  uint32_t ch_freq,
9107 				  enum hw_mode_bandwidth bw,
9108 				  uint32_t ext_flags, uint8_t vdev_id)
9109 {
9110 	QDF_STATUS status;
9111 	struct policy_mgr_pcl_list pcl;
9112 	bool allowed;
9113 
9114 	qdf_mem_zero(&pcl, sizeof(pcl));
9115 	status = policy_mgr_get_pcl(psoc, mode, pcl.pcl_list, &pcl.pcl_len,
9116 				    pcl.weight_list,
9117 				    QDF_ARRAY_SIZE(pcl.weight_list), vdev_id);
9118 	if (QDF_IS_STATUS_ERROR(status)) {
9119 		policy_mgr_err("disallow connection:%d", status);
9120 		return false;
9121 	}
9122 
9123 	allowed = policy_mgr_is_concurrency_allowed(psoc, mode, ch_freq,
9124 						    bw, ext_flags, &pcl);
9125 
9126 	/* Fourth connection concurrency check */
9127 	if (allowed && policy_mgr_get_connection_count(psoc) == 3)
9128 		allowed = policy_mgr_is_concurrency_allowed_4_port(
9129 				psoc,
9130 				mode,
9131 				ch_freq,
9132 				pcl);
9133 	return allowed;
9134 }
9135 
9136 bool
9137 policy_mgr_allow_concurrency_csa(struct wlan_objmgr_psoc *psoc,
9138 				 enum policy_mgr_con_mode mode,
9139 				 uint32_t ch_freq, enum hw_mode_bandwidth bw,
9140 				 uint32_t vdev_id, bool forced,
9141 				 enum sap_csa_reason_code reason)
9142 {
9143 	bool allow = false;
9144 	struct policy_mgr_conc_connection_info
9145 			info[MAX_NUMBER_OF_CONC_CONNECTIONS];
9146 	uint8_t num_cxn_del = 0;
9147 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9148 	uint32_t old_ch_freq, conc_ext_flags;
9149 	QDF_STATUS status;
9150 	struct wlan_objmgr_vdev *vdev;
9151 
9152 	pm_ctx = policy_mgr_get_context(psoc);
9153 	if (!pm_ctx) {
9154 		policy_mgr_err("Invalid Context");
9155 		return allow;
9156 	}
9157 	policy_mgr_debug("check concurrency_csa vdev:%d ch %d bw %d, forced %d, reason %d",
9158 			 vdev_id, ch_freq, bw, forced, reason);
9159 
9160 	status = policy_mgr_get_chan_by_session_id(psoc, vdev_id,
9161 						   &old_ch_freq);
9162 	if (QDF_IS_STATUS_ERROR(status)) {
9163 		policy_mgr_err("Failed to get channel for vdev:%d",
9164 			       vdev_id);
9165 		return allow;
9166 	}
9167 	qdf_mem_zero(info, sizeof(info));
9168 
9169 	/*
9170 	 * Store the connection's parameter and temporarily delete it
9171 	 * from the concurrency table. This way the allow concurrency
9172 	 * check can be used as though a new connection is coming up,
9173 	 * after check, restore the connection to concurrency table.
9174 	 *
9175 	 * In SAP+SAP SCC case, when LTE unsafe event processing,
9176 	 * we should remove the all SAP conn entry on the same ch before
9177 	 * do the concurrency check. Otherwise the left SAP on old channel
9178 	 * will cause the concurrency check failure because of dual beacon
9179 	 * MCC not supported. for the CSA request reason code,
9180 	 * PM_CSA_REASON_UNSAFE_CHANNEL, we remove all the SAP
9181 	 * entry on old channel before do concurrency check.
9182 	 *
9183 	 * The assumption is both SAP should move to the new channel later for
9184 	 * the reason code.
9185 	 */
9186 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9187 
9188 	if (forced && (reason == CSA_REASON_UNSAFE_CHANNEL ||
9189 		       reason == CSA_REASON_DCS))
9190 		policy_mgr_store_and_del_conn_info_by_chan_and_mode(
9191 			psoc, old_ch_freq, mode, info, &num_cxn_del);
9192 	else
9193 		policy_mgr_store_and_del_conn_info_by_vdev_id(
9194 			psoc, vdev_id, info, &num_cxn_del);
9195 
9196 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
9197 						    WLAN_POLICY_MGR_ID);
9198 	conc_ext_flags = policy_mgr_get_conc_ext_flags(vdev, false);
9199 	allow = policy_mgr_allow_concurrency(psoc, mode, ch_freq,
9200 					     bw, conc_ext_flags, vdev_id);
9201 	if (vdev)
9202 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
9203 
9204 	/* Restore the connection entry */
9205 	if (num_cxn_del > 0)
9206 		policy_mgr_restore_deleted_conn_info(psoc, info, num_cxn_del);
9207 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9208 
9209 	if (!allow)
9210 		policy_mgr_err("CSA concurrency check failed");
9211 
9212 	return allow;
9213 }
9214 
9215 /**
9216  * policy_mgr_get_concurrency_mode() - return concurrency mode
9217  * @psoc: PSOC object information
9218  *
9219  * This routine is used to retrieve concurrency mode
9220  *
9221  * Return: uint32_t value of concurrency mask
9222  */
9223 uint32_t policy_mgr_get_concurrency_mode(struct wlan_objmgr_psoc *psoc)
9224 {
9225 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9226 
9227 	pm_ctx = policy_mgr_get_context(psoc);
9228 	if (!pm_ctx) {
9229 		policy_mgr_err("Invalid context");
9230 		return QDF_STA_MASK;
9231 	}
9232 
9233 	policy_mgr_debug("concurrency_mode: 0x%x",
9234 			 pm_ctx->concurrency_mode);
9235 
9236 	return pm_ctx->concurrency_mode;
9237 }
9238 
9239 QDF_STATUS policy_mgr_set_user_cfg(struct wlan_objmgr_psoc *psoc,
9240 				struct policy_mgr_user_cfg *user_cfg)
9241 {
9242 
9243 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9244 
9245 	pm_ctx = policy_mgr_get_context(psoc);
9246 	if (!pm_ctx) {
9247 		policy_mgr_err("Invalid context");
9248 		return QDF_STATUS_E_FAILURE;
9249 	}
9250 	if (!user_cfg) {
9251 		policy_mgr_err("Invalid User Config");
9252 		return QDF_STATUS_E_FAILURE;
9253 	}
9254 
9255 	pm_ctx->user_cfg = *user_cfg;
9256 	policy_mgr_debug("dbs_selection_plcy 0x%x",
9257 			 pm_ctx->cfg.dbs_selection_plcy);
9258 	policy_mgr_debug("vdev_priority_list 0x%x",
9259 			 pm_ctx->cfg.vdev_priority_list);
9260 	pm_ctx->cur_conc_system_pref = pm_ctx->cfg.sys_pref;
9261 
9262 	return QDF_STATUS_SUCCESS;
9263 }
9264 
9265 bool policy_mgr_will_freq_lead_to_mcc(struct wlan_objmgr_psoc *psoc,
9266 				      qdf_freq_t freq)
9267 {
9268 	bool is_mcc = false;
9269 	uint32_t conn_index;
9270 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9271 
9272 	pm_ctx = policy_mgr_get_context(psoc);
9273 	if (!pm_ctx) {
9274 		policy_mgr_err("Invalid Context");
9275 		return is_mcc;
9276 	}
9277 
9278 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9279 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
9280 	     conn_index++) {
9281 		if (pm_conc_connection_list[conn_index].in_use &&
9282 		    policy_mgr_2_freq_always_on_same_mac(psoc, freq,
9283 		     pm_conc_connection_list[conn_index].freq)) {
9284 			is_mcc = true;
9285 			break;
9286 		}
9287 	}
9288 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9289 
9290 	return is_mcc;
9291 }
9292 
9293 /**
9294  * policy_mgr_is_two_connection_mcc() - Check if MCC scenario
9295  * when there are two connections
9296  * @psoc: PSOC object information
9297  *
9298  * If if MCC scenario when there are two connections
9299  *
9300  * Return: true or false
9301  */
9302 static bool policy_mgr_is_two_connection_mcc(struct wlan_objmgr_psoc *psoc)
9303 {
9304 	return ((pm_conc_connection_list[0].freq !=
9305 		 pm_conc_connection_list[1].freq) &&
9306 		(policy_mgr_are_2_freq_on_same_mac(psoc,
9307 			pm_conc_connection_list[0].freq,
9308 			pm_conc_connection_list[1].freq)) &&
9309 		(pm_conc_connection_list[0].freq <=
9310 		 WLAN_REG_MAX_24GHZ_CHAN_FREQ) &&
9311 		(pm_conc_connection_list[1].freq <=
9312 		 WLAN_REG_MAX_24GHZ_CHAN_FREQ)) ? true : false;
9313 }
9314 
9315 /**
9316  * policy_mgr_is_three_connection_mcc() - Check if MCC scenario
9317  * when there are three connections
9318  *
9319  * If if MCC scenario when there are three connections
9320  *
9321  * Return: true or false
9322  */
9323 static bool policy_mgr_is_three_connection_mcc(void)
9324 {
9325 	return (((pm_conc_connection_list[0].freq !=
9326 		  pm_conc_connection_list[1].freq) ||
9327 		 (pm_conc_connection_list[0].freq !=
9328 		  pm_conc_connection_list[2].freq) ||
9329 		 (pm_conc_connection_list[1].freq !=
9330 		  pm_conc_connection_list[2].freq)) &&
9331 		(pm_conc_connection_list[0].freq <=
9332 		 WLAN_REG_MAX_24GHZ_CHAN_FREQ) &&
9333 		(pm_conc_connection_list[1].freq <=
9334 		 WLAN_REG_MAX_24GHZ_CHAN_FREQ) &&
9335 		(pm_conc_connection_list[2].freq <=
9336 		 WLAN_REG_MAX_24GHZ_CHAN_FREQ)) ? true : false;
9337 }
9338 
9339 uint32_t policy_mgr_get_conc_vdev_on_same_mac(struct wlan_objmgr_psoc *psoc,
9340 					      uint32_t vdev_id, uint8_t mac_id)
9341 {
9342 	uint32_t id = WLAN_INVALID_VDEV_ID;
9343 	uint32_t conn_index;
9344 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9345 
9346 	pm_ctx = policy_mgr_get_context(psoc);
9347 	if (!pm_ctx) {
9348 		policy_mgr_err("Invalid Context");
9349 		return id;
9350 	}
9351 
9352 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9353 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
9354 	     conn_index++) {
9355 		if ((pm_conc_connection_list[conn_index].in_use) &&
9356 		    (pm_conc_connection_list[conn_index].vdev_id != vdev_id) &&
9357 		    (pm_conc_connection_list[conn_index].mac == mac_id)) {
9358 			id = pm_conc_connection_list[conn_index].vdev_id;
9359 			break;
9360 		}
9361 	}
9362 
9363 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9364 
9365 	return id;
9366 }
9367 
9368 bool policy_mgr_is_mcc_in_24G(struct wlan_objmgr_psoc *psoc)
9369 {
9370 	uint32_t num_connections = 0;
9371 	bool is_24G_mcc = false;
9372 
9373 	num_connections = policy_mgr_get_connection_count(psoc);
9374 
9375 	switch (num_connections) {
9376 	case 1:
9377 		break;
9378 	case 2:
9379 		if (policy_mgr_is_two_connection_mcc(psoc))
9380 			is_24G_mcc = true;
9381 		break;
9382 	case 3:
9383 		if (policy_mgr_is_three_connection_mcc())
9384 			is_24G_mcc = true;
9385 		break;
9386 	default:
9387 		policy_mgr_err("unexpected num_connections value %d",
9388 			num_connections);
9389 		break;
9390 	}
9391 
9392 	return is_24G_mcc;
9393 }
9394 
9395 bool policy_mgr_check_for_session_conc(struct wlan_objmgr_psoc *psoc,
9396 				       uint8_t vdev_id, uint32_t ch_freq)
9397 {
9398 	enum policy_mgr_con_mode mode;
9399 	bool ret;
9400 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9401 	struct wlan_objmgr_vdev *vdev;
9402 	uint32_t conc_ext_flags;
9403 
9404 	pm_ctx = policy_mgr_get_context(psoc);
9405 	if (!pm_ctx) {
9406 		policy_mgr_err("Invalid Context");
9407 		return false;
9408 	}
9409 
9410 	if (pm_ctx->hdd_cbacks.get_mode_for_non_connected_vdev) {
9411 		mode = pm_ctx->hdd_cbacks.get_mode_for_non_connected_vdev(
9412 			psoc, vdev_id);
9413 		if (PM_MAX_NUM_OF_MODE == mode) {
9414 			policy_mgr_err("Invalid mode");
9415 			return false;
9416 		}
9417 	} else
9418 		return false;
9419 
9420 	if (ch_freq == 0) {
9421 		policy_mgr_err("Invalid channel number 0");
9422 		return false;
9423 	}
9424 
9425 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
9426 						    WLAN_POLICY_MGR_ID);
9427 
9428 	/* Take care of 160MHz and 80+80Mhz later */
9429 	conc_ext_flags = policy_mgr_get_conc_ext_flags(vdev, false);
9430 	ret = policy_mgr_allow_concurrency(psoc, mode, ch_freq, HW_MODE_20_MHZ,
9431 					   conc_ext_flags, vdev_id);
9432 	if (vdev)
9433 		wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
9434 
9435 	if (false == ret) {
9436 		policy_mgr_err("Connection failed due to conc check fail");
9437 		return 0;
9438 	}
9439 
9440 	return true;
9441 }
9442 
9443 /**
9444  * policy_mgr_change_mcc_go_beacon_interval() - Change MCC beacon interval
9445  * @psoc: PSOC object information
9446  * @vdev_id: vdev id
9447  * @dev_mode: device mode
9448  *
9449  * Updates the beacon parameters of the GO in MCC scenario
9450  *
9451  * Return: Success or Failure depending on the overall function behavior
9452  */
9453 QDF_STATUS policy_mgr_change_mcc_go_beacon_interval(
9454 		struct wlan_objmgr_psoc *psoc,
9455 		uint8_t vdev_id, enum QDF_OPMODE dev_mode)
9456 {
9457 	QDF_STATUS status;
9458 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9459 
9460 	pm_ctx = policy_mgr_get_context(psoc);
9461 	if (!pm_ctx) {
9462 		policy_mgr_err("Invalid context");
9463 		return QDF_STATUS_E_FAILURE;
9464 	}
9465 
9466 	policy_mgr_debug("UPDATE Beacon Params");
9467 
9468 	if (QDF_SAP_MODE == dev_mode) {
9469 		if (pm_ctx->sme_cbacks.sme_change_mcc_beacon_interval
9470 		    ) {
9471 			status = pm_ctx->sme_cbacks.
9472 				sme_change_mcc_beacon_interval(vdev_id);
9473 			if (status == QDF_STATUS_E_FAILURE) {
9474 				policy_mgr_err("Failed to update Beacon Params");
9475 				return QDF_STATUS_E_FAILURE;
9476 			}
9477 		} else {
9478 			policy_mgr_err("sme_change_mcc_beacon_interval callback is NULL");
9479 			return QDF_STATUS_E_FAILURE;
9480 		}
9481 	}
9482 
9483 	return QDF_STATUS_SUCCESS;
9484 }
9485 
9486 struct policy_mgr_conc_connection_info *policy_mgr_get_conn_info(uint32_t *len)
9487 {
9488 	struct policy_mgr_conc_connection_info *conn_ptr =
9489 		&pm_conc_connection_list[0];
9490 	*len = MAX_NUMBER_OF_CONC_CONNECTIONS;
9491 
9492 	return conn_ptr;
9493 }
9494 
9495 enum policy_mgr_con_mode
9496 policy_mgr_qdf_opmode_to_pm_con_mode(struct wlan_objmgr_psoc *psoc,
9497 				     enum QDF_OPMODE device_mode,
9498 				     uint8_t vdev_id)
9499 {
9500 	enum policy_mgr_con_mode mode = PM_MAX_NUM_OF_MODE;
9501 
9502 	switch (device_mode) {
9503 	case QDF_STA_MODE:
9504 		mode = PM_STA_MODE;
9505 		break;
9506 	case QDF_P2P_CLIENT_MODE:
9507 		mode = PM_P2P_CLIENT_MODE;
9508 		break;
9509 	case QDF_P2P_GO_MODE:
9510 		mode = PM_P2P_GO_MODE;
9511 		break;
9512 	case QDF_SAP_MODE:
9513 #ifdef WLAN_FEATURE_LL_LT_SAP
9514 		if (policy_mgr_is_vdev_ll_lt_sap(psoc, vdev_id))
9515 			mode = PM_LL_LT_SAP_MODE;
9516 		else
9517 #endif
9518 			mode = PM_SAP_MODE;
9519 		break;
9520 	case QDF_NAN_DISC_MODE:
9521 		mode = PM_NAN_DISC_MODE;
9522 		break;
9523 	case QDF_NDI_MODE:
9524 		mode = PM_NDI_MODE;
9525 		break;
9526 	default:
9527 		policy_mgr_debug("Unsupported mode (%d)",
9528 				 device_mode);
9529 	}
9530 
9531 	return mode;
9532 }
9533 
9534 enum QDF_OPMODE policy_mgr_get_qdf_mode_from_pm(
9535 			enum policy_mgr_con_mode device_mode)
9536 {
9537 	enum QDF_OPMODE mode = QDF_MAX_NO_OF_MODE;
9538 
9539 	switch (device_mode) {
9540 	case PM_STA_MODE:
9541 		mode = QDF_STA_MODE;
9542 		break;
9543 	case PM_SAP_MODE:
9544 	case PM_LL_LT_SAP_MODE:
9545 		mode = QDF_SAP_MODE;
9546 		break;
9547 	case PM_P2P_CLIENT_MODE:
9548 		mode = QDF_P2P_CLIENT_MODE;
9549 		break;
9550 	case PM_P2P_GO_MODE:
9551 		mode = QDF_P2P_GO_MODE;
9552 		break;
9553 	case PM_NAN_DISC_MODE:
9554 		mode = QDF_NAN_DISC_MODE;
9555 		break;
9556 	case PM_NDI_MODE:
9557 		mode = QDF_NDI_MODE;
9558 		break;
9559 	default:
9560 		policy_mgr_debug("Unsupported policy mgr mode (%d)",
9561 				 device_mode);
9562 	}
9563 	return mode;
9564 }
9565 
9566 QDF_STATUS policy_mgr_mode_specific_num_open_sessions(
9567 		struct wlan_objmgr_psoc *psoc, enum QDF_OPMODE mode,
9568 		uint8_t *num_sessions)
9569 {
9570 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9571 
9572 	pm_ctx = policy_mgr_get_context(psoc);
9573 	if (!pm_ctx) {
9574 		policy_mgr_err("Invalid context");
9575 		return QDF_STATUS_E_FAILURE;
9576 	}
9577 
9578 	*num_sessions = pm_ctx->no_of_open_sessions[mode];
9579 	return QDF_STATUS_SUCCESS;
9580 }
9581 
9582 QDF_STATUS policy_mgr_mode_specific_num_active_sessions(
9583 		struct wlan_objmgr_psoc *psoc, enum QDF_OPMODE mode,
9584 		uint8_t *num_sessions)
9585 {
9586 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9587 
9588 	pm_ctx = policy_mgr_get_context(psoc);
9589 	if (!pm_ctx) {
9590 		policy_mgr_err("Invalid context");
9591 		return QDF_STATUS_E_FAILURE;
9592 	}
9593 
9594 	*num_sessions = pm_ctx->no_of_active_sessions[mode];
9595 	return QDF_STATUS_SUCCESS;
9596 }
9597 
9598 /**
9599  * policy_mgr_concurrent_open_sessions_running() - Checks for
9600  * concurrent open session
9601  * @psoc: PSOC object information
9602  *
9603  * Checks if more than one open session is running for all the allowed modes
9604  * in the driver
9605  *
9606  * Return: True if more than one open session exists, False otherwise
9607  */
9608 bool policy_mgr_concurrent_open_sessions_running(
9609 	struct wlan_objmgr_psoc *psoc)
9610 {
9611 	uint8_t i = 0;
9612 	uint8_t j = 0;
9613 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9614 
9615 	pm_ctx = policy_mgr_get_context(psoc);
9616 	if (!pm_ctx) {
9617 		policy_mgr_err("Invalid context");
9618 		return false;
9619 	}
9620 
9621 	for (i = 0; i < QDF_MAX_NO_OF_MODE; i++)
9622 		j += pm_ctx->no_of_open_sessions[i];
9623 
9624 	return j > 1;
9625 }
9626 
9627 /**
9628  * policy_mgr_concurrent_beaconing_sessions_running() - Checks
9629  * for concurrent beaconing entities
9630  * @psoc: PSOC object information
9631  *
9632  * Checks if multiple beaconing sessions are running i.e., if SAP or GO
9633  * are beaconing together
9634  *
9635  * Return: True if multiple entities are beaconing together, False otherwise
9636  */
9637 bool policy_mgr_concurrent_beaconing_sessions_running(
9638 	struct wlan_objmgr_psoc *psoc)
9639 {
9640 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9641 
9642 	pm_ctx = policy_mgr_get_context(psoc);
9643 	if (!pm_ctx) {
9644 		policy_mgr_err("Invalid context");
9645 		return false;
9646 	}
9647 
9648 	return (pm_ctx->no_of_open_sessions[QDF_SAP_MODE] +
9649 		pm_ctx->no_of_open_sessions[QDF_P2P_GO_MODE]
9650 		> 1) ? true : false;
9651 }
9652 
9653 
9654 void policy_mgr_clear_concurrent_session_count(struct wlan_objmgr_psoc *psoc)
9655 {
9656 	uint8_t i = 0;
9657 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9658 
9659 	pm_ctx = policy_mgr_get_context(psoc);
9660 	if (pm_ctx) {
9661 		for (i = 0; i < QDF_MAX_NO_OF_MODE; i++)
9662 			pm_ctx->no_of_active_sessions[i] = 0;
9663 	}
9664 }
9665 
9666 bool policy_mgr_is_multiple_active_sta_sessions(struct wlan_objmgr_psoc *psoc)
9667 {
9668 	return policy_mgr_mode_specific_connection_count(
9669 		psoc, PM_STA_MODE, NULL) > 1;
9670 }
9671 
9672 bool policy_mgr_is_sta_present_on_dfs_channel(struct wlan_objmgr_psoc *psoc,
9673 					      uint8_t *vdev_id,
9674 					      qdf_freq_t *ch_freq,
9675 					      enum hw_mode_bandwidth *ch_width)
9676 {
9677 	struct policy_mgr_conc_connection_info *conn_info;
9678 	bool status = false;
9679 	uint32_t conn_index = 0;
9680 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9681 
9682 	pm_ctx = policy_mgr_get_context(psoc);
9683 	if (!pm_ctx) {
9684 		policy_mgr_err("Invalid Context");
9685 		return false;
9686 	}
9687 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9688 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
9689 	     conn_index++) {
9690 		conn_info = &pm_conc_connection_list[conn_index];
9691 		if (conn_info->in_use &&
9692 		    (conn_info->mode == PM_STA_MODE ||
9693 		     conn_info->mode == PM_P2P_CLIENT_MODE) &&
9694 		    (wlan_reg_is_dfs_for_freq(pm_ctx->pdev, conn_info->freq) ||
9695 		     (wlan_reg_is_5ghz_ch_freq(conn_info->freq) &&
9696 		      conn_info->bw == HW_MODE_160_MHZ))) {
9697 			*vdev_id = conn_info->vdev_id;
9698 			*ch_freq = pm_conc_connection_list[conn_index].freq;
9699 			*ch_width = conn_info->bw;
9700 			status = true;
9701 			break;
9702 		}
9703 	}
9704 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9705 
9706 	return status;
9707 }
9708 
9709 bool policy_mgr_is_sta_present_on_freq(struct wlan_objmgr_psoc *psoc,
9710 				       uint8_t *vdev_id,
9711 				       qdf_freq_t ch_freq,
9712 				       enum hw_mode_bandwidth *ch_width)
9713 {
9714 	struct policy_mgr_conc_connection_info *conn_info;
9715 	bool status = false;
9716 	uint32_t conn_index = 0;
9717 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9718 
9719 	pm_ctx = policy_mgr_get_context(psoc);
9720 	if (!pm_ctx) {
9721 		policy_mgr_err("Invalid Context");
9722 		return false;
9723 	}
9724 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9725 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
9726 	     conn_index++) {
9727 		conn_info = &pm_conc_connection_list[conn_index];
9728 		if (conn_info->in_use &&
9729 		    (conn_info->mode == PM_STA_MODE ||
9730 		     conn_info->mode == PM_P2P_CLIENT_MODE) &&
9731 		    ch_freq == conn_info->freq) {
9732 			*vdev_id = conn_info->vdev_id;
9733 			*ch_width = conn_info->bw;
9734 			status = true;
9735 			break;
9736 		}
9737 	}
9738 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9739 
9740 	return status;
9741 }
9742 
9743 bool policy_mgr_is_sta_gc_active_on_mac(struct wlan_objmgr_psoc *psoc,
9744 					uint8_t mac_id)
9745 {
9746 	uint32_t list[MAX_NUMBER_OF_CONC_CONNECTIONS];
9747 	uint32_t index, count;
9748 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9749 
9750 	pm_ctx = policy_mgr_get_context(psoc);
9751 	if (!pm_ctx) {
9752 		policy_mgr_err("Invalid Context");
9753 		return false;
9754 	}
9755 
9756 	count = policy_mgr_mode_specific_connection_count(
9757 		psoc, PM_STA_MODE, list);
9758 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9759 	for (index = 0; index < count; index++) {
9760 		if (mac_id == pm_conc_connection_list[list[index]].mac) {
9761 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9762 			return true;
9763 		}
9764 	}
9765 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9766 
9767 	count = policy_mgr_mode_specific_connection_count(
9768 		psoc, PM_P2P_CLIENT_MODE, list);
9769 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9770 	for (index = 0; index < count; index++) {
9771 		if (mac_id == pm_conc_connection_list[list[index]].mac) {
9772 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9773 			return true;
9774 		}
9775 	}
9776 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9777 
9778 	return false;
9779 }
9780 
9781 /**
9782  * policy_mgr_is_sta_active_connection_exists() - Check if a STA
9783  * connection is active
9784  * @psoc: PSOC object information
9785  *
9786  * Checks if there is atleast one active STA connection in the driver
9787  *
9788  * Return: True if an active STA session is present, False otherwise
9789  */
9790 bool policy_mgr_is_sta_active_connection_exists(
9791 	struct wlan_objmgr_psoc *psoc)
9792 {
9793 	return (!policy_mgr_mode_specific_connection_count(
9794 		psoc, PM_STA_MODE, NULL)) ? false : true;
9795 }
9796 
9797 bool policy_mgr_is_any_nondfs_chnl_present(struct wlan_objmgr_psoc *psoc,
9798 					   uint32_t *ch_freq)
9799 {
9800 	bool status = false;
9801 	uint32_t conn_index = 0;
9802 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9803 
9804 	pm_ctx = policy_mgr_get_context(psoc);
9805 	if (!pm_ctx) {
9806 		policy_mgr_err("Invalid Context");
9807 		return false;
9808 	}
9809 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9810 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
9811 			conn_index++) {
9812 		if (pm_conc_connection_list[conn_index].in_use &&
9813 		    !wlan_reg_is_dfs_for_freq(pm_ctx->pdev,
9814 		    pm_conc_connection_list[conn_index].freq)) {
9815 			*ch_freq = pm_conc_connection_list[conn_index].freq;
9816 			status = true;
9817 		}
9818 	}
9819 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9820 
9821 	return status;
9822 }
9823 
9824 uint32_t policy_mgr_get_dfs_beaconing_session_id(
9825 		struct wlan_objmgr_psoc *psoc)
9826 {
9827 	uint32_t session_id = WLAN_UMAC_VDEV_ID_MAX;
9828 	struct policy_mgr_conc_connection_info *conn_info;
9829 	uint32_t conn_index = 0;
9830 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9831 
9832 	pm_ctx = policy_mgr_get_context(psoc);
9833 	if (!pm_ctx) {
9834 		policy_mgr_err("Invalid Context");
9835 		return session_id;
9836 	}
9837 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9838 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
9839 	     conn_index++) {
9840 		conn_info = &pm_conc_connection_list[conn_index];
9841 		if (conn_info->in_use &&
9842 		    WLAN_REG_IS_5GHZ_CH_FREQ(conn_info->freq) &&
9843 		    (conn_info->ch_flagext & (IEEE80211_CHAN_DFS |
9844 					      IEEE80211_CHAN_DFS_CFREQ2)) &&
9845 		    (conn_info->mode == PM_SAP_MODE ||
9846 		     conn_info->mode == PM_P2P_GO_MODE)) {
9847 			session_id =
9848 				pm_conc_connection_list[conn_index].vdev_id;
9849 			break;
9850 		}
9851 	}
9852 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9853 
9854 	return session_id;
9855 }
9856 
9857 bool policy_mgr_is_any_dfs_beaconing_session_present(
9858 		struct wlan_objmgr_psoc *psoc, qdf_freq_t *ch_freq,
9859 		enum hw_mode_bandwidth *ch_width)
9860 {
9861 	struct policy_mgr_conc_connection_info *conn_info;
9862 	bool status = false;
9863 	uint32_t conn_index = 0;
9864 	struct policy_mgr_psoc_priv_obj *pm_ctx;
9865 
9866 	pm_ctx = policy_mgr_get_context(psoc);
9867 	if (!pm_ctx) {
9868 		policy_mgr_err("Invalid Context");
9869 		return false;
9870 	}
9871 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
9872 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
9873 			conn_index++) {
9874 		conn_info = &pm_conc_connection_list[conn_index];
9875 		if (conn_info->in_use &&
9876 		    (conn_info->mode == PM_SAP_MODE ||
9877 		     conn_info->mode == PM_P2P_GO_MODE) &&
9878 		     (wlan_reg_is_dfs_for_freq(pm_ctx->pdev, conn_info->freq) ||
9879 		      (wlan_reg_is_5ghz_ch_freq(conn_info->freq) &&
9880 		      conn_info->bw == HW_MODE_160_MHZ))) {
9881 			*ch_freq = pm_conc_connection_list[conn_index].freq;
9882 			*ch_width = conn_info->bw;
9883 			status = true;
9884 		}
9885 	}
9886 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
9887 
9888 	return status;
9889 }
9890 
9891 bool policy_mgr_scan_trim_5g_chnls_for_dfs_ap(struct wlan_objmgr_psoc *psoc,
9892 					      qdf_freq_t *freq)
9893 {
9894 	qdf_freq_t dfs_ch_frq = 0;
9895 	qdf_freq_t dfs_sta_frq = 0;
9896 	uint8_t vdev_id;
9897 	enum hw_mode_bandwidth ch_width;
9898 	enum hw_mode_bandwidth ch_sta_width;
9899 	QDF_STATUS status;
9900 	uint8_t  sta_sap_scc_on_dfs_chnl;
9901 
9902 	policy_mgr_is_any_dfs_beaconing_session_present(psoc, &dfs_ch_frq,
9903 							&ch_width);
9904 	if (!dfs_ch_frq)
9905 		return false;
9906 
9907 	*freq = dfs_ch_frq;
9908 
9909 	status = policy_mgr_get_sta_sap_scc_on_dfs_chnl(psoc,
9910 						&sta_sap_scc_on_dfs_chnl);
9911 	if (QDF_IS_STATUS_ERROR(status))
9912 		return false;
9913 
9914 	if (policy_mgr_is_sta_present_on_dfs_channel(psoc, &vdev_id,
9915 						     &dfs_sta_frq,
9916 						     &ch_sta_width) &&
9917 	    !policy_mgr_is_hw_dbs_capable(psoc) &&
9918 	    sta_sap_scc_on_dfs_chnl != PM_STA_SAP_ON_DFS_DEFAULT) {
9919 		policymgr_nofl_err("DFS STA present vdev_id %d ch_feq %d ch_width %d",
9920 				   vdev_id, dfs_sta_frq, ch_sta_width);
9921 		return false;
9922 	}
9923 
9924 	/*
9925 	 * 1) if agile & DFS scans are supported
9926 	 * 2) if hardware is DBS capable
9927 	 * 3) if current hw mode is non-dbs
9928 	 * if all above 3 conditions are true then don't skip any
9929 	 * channel from scan list
9930 	 */
9931 	if (policy_mgr_is_hw_dbs_capable(psoc) &&
9932 	    !policy_mgr_is_current_hwmode_dbs(psoc) &&
9933 	    policy_mgr_get_dbs_plus_agile_scan_config(psoc) &&
9934 	    policy_mgr_get_single_mac_scan_with_dfs_config(psoc))
9935 		return false;
9936 
9937 	policy_mgr_debug("scan skip 5g chan due to dfs ap(ch %d / ch_width %d) present",
9938 			 dfs_ch_frq, ch_width);
9939 
9940 	return true;
9941 }
9942 
9943 static void
9944 policy_mgr_fill_trim_chan(struct wlan_objmgr_pdev *pdev,
9945 			  void *object, void *arg)
9946 {
9947 	struct wlan_objmgr_vdev *vdev = object;
9948 	struct trim_chan_info *trim_info = arg;
9949 	uint16_t sap_peer_count = 0;
9950 	qdf_freq_t chan_freq;
9951 
9952 	if (wlan_vdev_mlme_get_opmode(vdev) != QDF_SAP_MODE)
9953 		return;
9954 
9955 	if (wlan_vdev_is_up(vdev) != QDF_STATUS_SUCCESS)
9956 		return;
9957 
9958 	sap_peer_count = wlan_vdev_get_peer_count(vdev);
9959 	policy_mgr_debug("vdev %d - peer count %d",
9960 			 wlan_vdev_get_id(vdev), sap_peer_count);
9961 	if (sap_peer_count <= 1)
9962 		return;
9963 
9964 	chan_freq = wlan_get_operation_chan_freq(vdev);
9965 	if (!chan_freq)
9966 		return;
9967 
9968 	if (WLAN_REG_IS_5GHZ_CH_FREQ(chan_freq)) {
9969 		trim_info->trim |= TRIM_CHANNEL_LIST_5G;
9970 	} else if (WLAN_REG_IS_24GHZ_CH_FREQ(chan_freq)) {
9971 		if (trim_info->sap_count != 1)
9972 			return;
9973 
9974 		if ((trim_info->band_capability & BIT(REG_BAND_5G)) ==
9975 		     BIT(REG_BAND_5G))
9976 			return;
9977 
9978 		trim_info->trim |= TRIM_CHANNEL_LIST_24G;
9979 	}
9980 }
9981 
9982 uint16_t
9983 policy_mgr_scan_trim_chnls_for_connected_ap(struct wlan_objmgr_pdev *pdev)
9984 {
9985 	struct trim_chan_info trim_info;
9986 	struct wlan_objmgr_psoc *psoc;
9987 	QDF_STATUS status;
9988 
9989 	psoc = wlan_pdev_get_psoc(pdev);
9990 	if (!psoc)
9991 		return TRIM_CHANNEL_LIST_NONE;
9992 
9993 	status = wlan_mlme_get_band_capability(psoc,
9994 					       &trim_info.band_capability);
9995 	if (QDF_IS_STATUS_ERROR(status)) {
9996 		policy_mgr_err("Could not get band capability");
9997 		return TRIM_CHANNEL_LIST_NONE;
9998 	}
9999 
10000 	trim_info.sap_count = policy_mgr_mode_specific_connection_count(psoc,
10001 							PM_SAP_MODE, NULL);
10002 	if (!trim_info.sap_count)
10003 		return TRIM_CHANNEL_LIST_NONE;
10004 
10005 	trim_info.trim = TRIM_CHANNEL_LIST_NONE;
10006 
10007 	wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_VDEV_OP,
10008 					  policy_mgr_fill_trim_chan, &trim_info,
10009 					  0, WLAN_POLICY_MGR_ID);
10010 	policy_mgr_debug("band_capability %d, sap_count %d, trim %d",
10011 			 trim_info.band_capability, trim_info.sap_count,
10012 			 trim_info.trim);
10013 
10014 	return trim_info.trim;
10015 }
10016 
10017 QDF_STATUS policy_mgr_get_nss_for_vdev(struct wlan_objmgr_psoc *psoc,
10018 				enum policy_mgr_con_mode mode,
10019 				uint8_t *nss_2g, uint8_t *nss_5g)
10020 {
10021 	enum QDF_OPMODE dev_mode;
10022 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10023 
10024 	dev_mode = policy_mgr_get_qdf_mode_from_pm(mode);
10025 	if (dev_mode == QDF_MAX_NO_OF_MODE)
10026 		return  QDF_STATUS_E_FAILURE;
10027 	pm_ctx = policy_mgr_get_context(psoc);
10028 	if (!pm_ctx) {
10029 		policy_mgr_err("Invalid Context");
10030 		return QDF_STATUS_E_FAILURE;
10031 	}
10032 
10033 	if (pm_ctx->sme_cbacks.sme_get_nss_for_vdev) {
10034 		pm_ctx->sme_cbacks.sme_get_nss_for_vdev(
10035 			dev_mode, nss_2g, nss_5g);
10036 
10037 	} else {
10038 		policy_mgr_err("sme_get_nss_for_vdev callback is NULL");
10039 		return QDF_STATUS_E_FAILURE;
10040 	}
10041 
10042 	return QDF_STATUS_SUCCESS;
10043 }
10044 
10045 void policy_mgr_dump_connection_status_info(struct wlan_objmgr_psoc *psoc)
10046 {
10047 	uint32_t i;
10048 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10049 
10050 	pm_ctx = policy_mgr_get_context(psoc);
10051 	if (!pm_ctx) {
10052 		policy_mgr_err("Invalid Context");
10053 		return;
10054 	}
10055 
10056 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10057 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
10058 		if (!pm_conc_connection_list[i].in_use)
10059 			continue;
10060 		policy_mgr_debug("%d: use:%d vdev:%d mode:%d mac:%d freq:%d orig chainmask:%d orig nss:%d bw:%d, ch_flags %0X",
10061 				 i, pm_conc_connection_list[i].in_use,
10062 				 pm_conc_connection_list[i].vdev_id,
10063 				 pm_conc_connection_list[i].mode,
10064 				 pm_conc_connection_list[i].mac,
10065 				 pm_conc_connection_list[i].freq,
10066 				 pm_conc_connection_list[i].chain_mask,
10067 				 pm_conc_connection_list[i].original_nss,
10068 				 pm_conc_connection_list[i].bw,
10069 				 pm_conc_connection_list[i].ch_flagext);
10070 	}
10071 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10072 
10073 	policy_mgr_dump_freq_range(pm_ctx);
10074 	policy_mgr_validate_conn_info(psoc);
10075 }
10076 
10077 bool policy_mgr_is_any_mode_active_on_band_along_with_session(
10078 						struct wlan_objmgr_psoc *psoc,
10079 						uint8_t session_id,
10080 						enum policy_mgr_band band)
10081 {
10082 	uint32_t i;
10083 	bool status = false;
10084 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10085 
10086 	pm_ctx = policy_mgr_get_context(psoc);
10087 	if (!pm_ctx) {
10088 		policy_mgr_err("Invalid Context");
10089 		status = false;
10090 		goto send_status;
10091 	}
10092 
10093 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10094 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
10095 		switch (band) {
10096 		case POLICY_MGR_BAND_24:
10097 			if ((pm_conc_connection_list[i].vdev_id != session_id)
10098 			&& (pm_conc_connection_list[i].in_use) &&
10099 			(WLAN_REG_IS_24GHZ_CH_FREQ(
10100 			pm_conc_connection_list[i].freq))) {
10101 				status = true;
10102 				goto release_mutex_and_send_status;
10103 			}
10104 			break;
10105 		case POLICY_MGR_BAND_5:
10106 			if ((pm_conc_connection_list[i].vdev_id != session_id)
10107 			&& (pm_conc_connection_list[i].in_use) &&
10108 			(WLAN_REG_IS_5GHZ_CH_FREQ(
10109 			pm_conc_connection_list[i].freq))) {
10110 				status = true;
10111 				goto release_mutex_and_send_status;
10112 			}
10113 			break;
10114 		default:
10115 			policy_mgr_err("Invalidband option:%d", band);
10116 			status = false;
10117 			goto release_mutex_and_send_status;
10118 		}
10119 	}
10120 release_mutex_and_send_status:
10121 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10122 send_status:
10123 	return status;
10124 }
10125 
10126 enum phy_ch_width
10127 policy_mgr_get_bw_by_session_id(struct wlan_objmgr_psoc *psoc,
10128 				uint8_t session_id)
10129 {
10130 	uint32_t i;
10131 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10132 	enum hw_mode_bandwidth bw = HW_MODE_BW_NONE;
10133 
10134 	pm_ctx = policy_mgr_get_context(psoc);
10135 	if (!pm_ctx) {
10136 		policy_mgr_err("Invalid Context");
10137 		return CH_WIDTH_INVALID;
10138 	}
10139 
10140 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10141 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
10142 		if (pm_conc_connection_list[i].vdev_id == session_id &&
10143 		    pm_conc_connection_list[i].in_use) {
10144 			bw = pm_conc_connection_list[i].bw;
10145 			break;
10146 		}
10147 	}
10148 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10149 	return policy_mgr_get_ch_width(bw);
10150 }
10151 
10152 QDF_STATUS policy_mgr_get_chan_by_session_id(struct wlan_objmgr_psoc *psoc,
10153 					     uint8_t session_id,
10154 					     uint32_t *ch_freq)
10155 {
10156 	uint32_t i;
10157 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10158 
10159 	pm_ctx = policy_mgr_get_context(psoc);
10160 	if (!pm_ctx) {
10161 		policy_mgr_err("Invalid Context");
10162 		return QDF_STATUS_E_FAILURE;
10163 	}
10164 
10165 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10166 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
10167 		if ((pm_conc_connection_list[i].vdev_id == session_id) &&
10168 		    (pm_conc_connection_list[i].in_use)) {
10169 			*ch_freq = pm_conc_connection_list[i].freq;
10170 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10171 			return QDF_STATUS_SUCCESS;
10172 		}
10173 	}
10174 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10175 
10176 	return QDF_STATUS_E_FAILURE;
10177 }
10178 
10179 QDF_STATUS policy_mgr_get_mac_id_by_session_id(struct wlan_objmgr_psoc *psoc,
10180 					       uint8_t session_id,
10181 					       uint8_t *mac_id)
10182 {
10183 	uint32_t i;
10184 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10185 
10186 	pm_ctx = policy_mgr_get_context(psoc);
10187 	if (!pm_ctx) {
10188 		policy_mgr_err("Invalid Context");
10189 		return QDF_STATUS_E_FAILURE;
10190 	}
10191 
10192 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10193 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
10194 		if ((pm_conc_connection_list[i].vdev_id == session_id) &&
10195 		    (pm_conc_connection_list[i].in_use)) {
10196 			*mac_id = pm_conc_connection_list[i].mac;
10197 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10198 			return QDF_STATUS_SUCCESS;
10199 		}
10200 	}
10201 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10202 
10203 	return QDF_STATUS_E_FAILURE;
10204 }
10205 
10206 uint32_t policy_mgr_get_sap_go_count_on_mac(struct wlan_objmgr_psoc *psoc,
10207 					    uint32_t *list, uint8_t mac_id)
10208 {
10209 	uint32_t conn_index;
10210 	uint32_t count = 0;
10211 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10212 
10213 	pm_ctx = policy_mgr_get_context(psoc);
10214 	if (!pm_ctx) {
10215 		policy_mgr_err("Invalid Context");
10216 		return count;
10217 	}
10218 
10219 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10220 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
10221 	     conn_index++) {
10222 		if (pm_conc_connection_list[conn_index].mac == mac_id &&
10223 		    pm_conc_connection_list[conn_index].in_use &&
10224 		    policy_mgr_is_beaconing_mode(
10225 				pm_conc_connection_list[conn_index].mode)) {
10226 			if (list)
10227 				list[count] =
10228 				    pm_conc_connection_list[conn_index].vdev_id;
10229 			count++;
10230 		}
10231 	}
10232 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10233 
10234 	return count;
10235 }
10236 
10237 uint32_t policy_mgr_get_mcc_operating_channel(struct wlan_objmgr_psoc *psoc,
10238 					      uint8_t vdev_id)
10239 {
10240 	uint8_t mcc_vdev_id;
10241 	QDF_STATUS status;
10242 	uint32_t ch_freq;
10243 
10244 	if (!policy_mgr_is_mcc_with_this_vdev_id(psoc, vdev_id, &mcc_vdev_id)) {
10245 		policy_mgr_debug("No concurrent MCC vdev for id:%d", vdev_id);
10246 		return INVALID_CHANNEL_ID;
10247 	}
10248 
10249 	status = policy_mgr_get_chan_by_session_id(psoc, mcc_vdev_id, &ch_freq);
10250 	if (QDF_IS_STATUS_ERROR(status)) {
10251 		policy_mgr_err("Failed to get channel for MCC vdev:%d",
10252 			       mcc_vdev_id);
10253 		return INVALID_CHANNEL_ID;
10254 	}
10255 
10256 	return ch_freq;
10257 }
10258 
10259 bool policy_mgr_is_dnsc_set(struct wlan_objmgr_vdev *vdev)
10260 {
10261 	bool roffchan;
10262 
10263 	if (!vdev) {
10264 		policy_mgr_err("Invalid parameter");
10265 		return false;
10266 	}
10267 
10268 	roffchan = wlan_vdev_mlme_cap_get(vdev, WLAN_VDEV_C_RESTRICT_OFFCHAN);
10269 
10270 	if (roffchan)
10271 		policy_mgr_debug("Restrict offchannel is set");
10272 
10273 	return roffchan;
10274 }
10275 
10276 QDF_STATUS policy_mgr_is_chan_ok_for_dnbs(struct wlan_objmgr_psoc *psoc,
10277 					  uint32_t ch_freq, bool *ok)
10278 {
10279 	uint32_t cc_count = 0, i;
10280 	uint32_t op_ch_freq_list[MAX_NUMBER_OF_CONC_CONNECTIONS];
10281 	uint8_t vdev_id[MAX_NUMBER_OF_CONC_CONNECTIONS];
10282 	struct wlan_objmgr_vdev *vdev;
10283 
10284 	if (!ok) {
10285 		policy_mgr_err("Invalid parameter");
10286 		return QDF_STATUS_E_INVAL;
10287 	}
10288 
10289 	cc_count = policy_mgr_get_sap_mode_info(psoc,
10290 						&op_ch_freq_list[cc_count],
10291 						&vdev_id[cc_count]);
10292 
10293 	if (cc_count < MAX_NUMBER_OF_CONC_CONNECTIONS)
10294 		cc_count = cc_count +
10295 			   policy_mgr_get_mode_specific_conn_info(
10296 					psoc, &op_ch_freq_list[cc_count],
10297 					&vdev_id[cc_count], PM_P2P_GO_MODE);
10298 
10299 	if (!cc_count) {
10300 		*ok = true;
10301 		return QDF_STATUS_SUCCESS;
10302 	}
10303 
10304 	if (!ch_freq) {
10305 		policy_mgr_err("channel is 0, cc count %d", cc_count);
10306 		return QDF_STATUS_E_INVAL;
10307 	}
10308 
10309 	if (cc_count <= MAX_NUMBER_OF_CONC_CONNECTIONS) {
10310 		for (i = 0; i < cc_count; i++) {
10311 			vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
10312 					psoc, vdev_id[i], WLAN_POLICY_MGR_ID);
10313 			if (!vdev) {
10314 				policy_mgr_err("vdev for vdev_id:%d is NULL",
10315 					       vdev_id[i]);
10316 				return QDF_STATUS_E_INVAL;
10317 			}
10318 
10319 			/**
10320 			 * If channel passed is same as AP/GO operating
10321 			 * channel, return true.
10322 			 *
10323 			 * If channel is different from operating channel but
10324 			 * in same band, return false.
10325 			 *
10326 			 * If operating channel in different band
10327 			 * (DBS capable), return true.
10328 			 *
10329 			 * If operating channel in different band
10330 			 * (not DBS capable), return false.
10331 			 */
10332 			/* TODO: To be enhanced for SBS */
10333 			if (policy_mgr_is_dnsc_set(vdev)) {
10334 				if (op_ch_freq_list[i] == ch_freq) {
10335 					*ok = true;
10336 					wlan_objmgr_vdev_release_ref(
10337 							vdev,
10338 							WLAN_POLICY_MGR_ID);
10339 					break;
10340 				} else if (WLAN_REG_IS_SAME_BAND_FREQS(
10341 					op_ch_freq_list[i], ch_freq)) {
10342 					*ok = false;
10343 					wlan_objmgr_vdev_release_ref(
10344 							vdev,
10345 							WLAN_POLICY_MGR_ID);
10346 					break;
10347 				} else if (policy_mgr_is_hw_dbs_capable(psoc)) {
10348 					*ok = true;
10349 					wlan_objmgr_vdev_release_ref(
10350 							vdev,
10351 							WLAN_POLICY_MGR_ID);
10352 					break;
10353 				} else {
10354 					*ok = false;
10355 					wlan_objmgr_vdev_release_ref(
10356 							vdev,
10357 							WLAN_POLICY_MGR_ID);
10358 					break;
10359 				}
10360 			} else {
10361 				*ok = true;
10362 			}
10363 			wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
10364 		}
10365 	}
10366 
10367 	return QDF_STATUS_SUCCESS;
10368 }
10369 
10370 void policy_mgr_get_hw_dbs_max_bw(struct wlan_objmgr_psoc *psoc,
10371 				  struct dbs_bw *bw_dbs)
10372 {
10373 	uint32_t dbs, sbs, i, param;
10374 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10375 
10376 	pm_ctx = policy_mgr_get_context(psoc);
10377 	if (!pm_ctx) {
10378 		policy_mgr_err("Invalid Context");
10379 		return;
10380 	}
10381 
10382 	for (i = 0; i < pm_ctx->num_dbs_hw_modes; i++) {
10383 		param = pm_ctx->hw_mode.hw_mode_list[i];
10384 		dbs = POLICY_MGR_HW_MODE_DBS_MODE_GET(param);
10385 		sbs = POLICY_MGR_HW_MODE_SBS_MODE_GET(param);
10386 
10387 		if (!dbs && !sbs)
10388 			bw_dbs->mac0_bw =
10389 				POLICY_MGR_HW_MODE_MAC0_BANDWIDTH_GET(param);
10390 
10391 		if (dbs) {
10392 			bw_dbs->mac0_bw =
10393 				POLICY_MGR_HW_MODE_MAC0_BANDWIDTH_GET(param);
10394 			bw_dbs->mac1_bw =
10395 				POLICY_MGR_HW_MODE_MAC1_BANDWIDTH_GET(param);
10396 		} else {
10397 			continue;
10398 		}
10399 	}
10400 }
10401 
10402 uint32_t policy_mgr_get_hw_dbs_nss(struct wlan_objmgr_psoc *psoc,
10403 				   struct dbs_nss *nss_dbs)
10404 {
10405 	int i, param;
10406 	uint32_t dbs, sbs, tx_chain0, rx_chain0, tx_chain1, rx_chain1;
10407 	uint32_t min_mac0_rf_chains, min_mac1_rf_chains;
10408 	uint32_t max_rf_chains, final_max_rf_chains = HW_MODE_SS_0x0;
10409 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10410 
10411 	pm_ctx = policy_mgr_get_context(psoc);
10412 	if (!pm_ctx) {
10413 		policy_mgr_err("Invalid Context");
10414 		return final_max_rf_chains;
10415 	}
10416 
10417 	nss_dbs->single_mac0_band_cap = 0;
10418 	for (i = 0; i < pm_ctx->num_dbs_hw_modes; i++) {
10419 		param = pm_ctx->hw_mode.hw_mode_list[i];
10420 		dbs = POLICY_MGR_HW_MODE_DBS_MODE_GET(param);
10421 		sbs = POLICY_MGR_HW_MODE_SBS_MODE_GET(param);
10422 
10423 		if (!dbs && !sbs && !nss_dbs->single_mac0_band_cap)
10424 			nss_dbs->single_mac0_band_cap =
10425 				POLICY_MGR_HW_MODE_MAC0_BAND_GET(param);
10426 
10427 		if (dbs) {
10428 			tx_chain0
10429 				= POLICY_MGR_HW_MODE_MAC0_TX_STREAMS_GET(param);
10430 			rx_chain0
10431 				= POLICY_MGR_HW_MODE_MAC0_RX_STREAMS_GET(param);
10432 
10433 			tx_chain1
10434 				= POLICY_MGR_HW_MODE_MAC1_TX_STREAMS_GET(param);
10435 			rx_chain1
10436 				= POLICY_MGR_HW_MODE_MAC1_RX_STREAMS_GET(param);
10437 
10438 			min_mac0_rf_chains = QDF_MIN(tx_chain0, rx_chain0);
10439 			min_mac1_rf_chains = QDF_MIN(tx_chain1, rx_chain1);
10440 
10441 			max_rf_chains
10442 			= QDF_MAX(min_mac0_rf_chains, min_mac1_rf_chains);
10443 
10444 			if (final_max_rf_chains < max_rf_chains) {
10445 				final_max_rf_chains
10446 					= (max_rf_chains == 2)
10447 					? HW_MODE_SS_2x2 : HW_MODE_SS_1x1;
10448 
10449 				nss_dbs->mac0_ss
10450 					= (min_mac0_rf_chains == 2)
10451 					? HW_MODE_SS_2x2 : HW_MODE_SS_1x1;
10452 
10453 				nss_dbs->mac1_ss
10454 					= (min_mac1_rf_chains == 2)
10455 					? HW_MODE_SS_2x2 : HW_MODE_SS_1x1;
10456 			}
10457 		} else {
10458 			continue;
10459 		}
10460 	}
10461 
10462 	return final_max_rf_chains;
10463 }
10464 
10465 bool policy_mgr_is_scan_simultaneous_capable(struct wlan_objmgr_psoc *psoc)
10466 {
10467 	uint8_t dual_mac_feature = DISABLE_DBS_CXN_AND_SCAN;
10468 
10469 	policy_mgr_get_dual_mac_feature(psoc, &dual_mac_feature);
10470 	if ((dual_mac_feature == DISABLE_DBS_CXN_AND_SCAN) ||
10471 	    (dual_mac_feature == ENABLE_DBS_CXN_AND_DISABLE_DBS_SCAN) ||
10472 	    (dual_mac_feature ==
10473 	     ENABLE_DBS_CXN_AND_DISABLE_SIMULTANEOUS_SCAN) ||
10474 	     !policy_mgr_is_hw_dbs_capable(psoc))
10475 		return false;
10476 
10477 	return true;
10478 }
10479 
10480 void policy_mgr_set_cur_conc_system_pref(struct wlan_objmgr_psoc *psoc,
10481 		uint8_t conc_system_pref)
10482 {
10483 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10484 
10485 	pm_ctx = policy_mgr_get_context(psoc);
10486 
10487 	if (!pm_ctx) {
10488 		policy_mgr_err("Invalid Context");
10489 		return;
10490 	}
10491 
10492 	policy_mgr_debug("conc_system_pref %hu", conc_system_pref);
10493 	pm_ctx->cur_conc_system_pref = conc_system_pref;
10494 }
10495 
10496 uint8_t policy_mgr_get_cur_conc_system_pref(struct wlan_objmgr_psoc *psoc)
10497 {
10498 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10499 
10500 	pm_ctx = policy_mgr_get_context(psoc);
10501 	if (!pm_ctx) {
10502 		policy_mgr_err("Invalid Context");
10503 		return PM_THROUGHPUT;
10504 	}
10505 
10506 	policy_mgr_debug("conc_system_pref %hu", pm_ctx->cur_conc_system_pref);
10507 	return pm_ctx->cur_conc_system_pref;
10508 }
10509 
10510 QDF_STATUS policy_mgr_get_updated_scan_and_fw_mode_config(
10511 		struct wlan_objmgr_psoc *psoc, uint32_t *scan_config,
10512 		uint32_t *fw_mode_config, uint32_t dual_mac_disable_ini,
10513 		uint32_t channel_select_logic_conc)
10514 {
10515 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10516 
10517 	pm_ctx = policy_mgr_get_context(psoc);
10518 	if (!pm_ctx) {
10519 		policy_mgr_err("Invalid Context");
10520 		return QDF_STATUS_E_FAILURE;
10521 	}
10522 
10523 	*scan_config = pm_ctx->dual_mac_cfg.cur_scan_config;
10524 	*fw_mode_config = pm_ctx->dual_mac_cfg.cur_fw_mode_config;
10525 	switch (dual_mac_disable_ini) {
10526 	case DISABLE_DBS_CXN_AND_ENABLE_DBS_SCAN_WITH_ASYNC_SCAN_OFF:
10527 		policy_mgr_debug("dual_mac_disable_ini:%d async/dbs off",
10528 			dual_mac_disable_ini);
10529 		WMI_DBS_CONC_SCAN_CFG_ASYNC_DBS_SCAN_SET(*scan_config, 0);
10530 		WMI_DBS_FW_MODE_CFG_DBS_FOR_CXN_SET(*fw_mode_config, 0);
10531 		break;
10532 	case DISABLE_DBS_CXN_AND_ENABLE_DBS_SCAN:
10533 		policy_mgr_debug("dual_mac_disable_ini:%d dbs_cxn off",
10534 			dual_mac_disable_ini);
10535 		WMI_DBS_FW_MODE_CFG_DBS_FOR_CXN_SET(*fw_mode_config, 0);
10536 		break;
10537 	case ENABLE_DBS_CXN_AND_ENABLE_SCAN_WITH_ASYNC_SCAN_OFF:
10538 		policy_mgr_debug("dual_mac_disable_ini:%d async off",
10539 			dual_mac_disable_ini);
10540 		WMI_DBS_CONC_SCAN_CFG_ASYNC_DBS_SCAN_SET(*scan_config, 0);
10541 		break;
10542 	case ENABLE_DBS_CXN_AND_DISABLE_DBS_SCAN:
10543 		policy_mgr_debug("dual_mac_disable_ini:%d ",
10544 				 dual_mac_disable_ini);
10545 		WMI_DBS_CONC_SCAN_CFG_DBS_SCAN_SET(*scan_config, 0);
10546 		break;
10547 	default:
10548 		break;
10549 	}
10550 
10551 	WMI_DBS_FW_MODE_CFG_DBS_FOR_STA_PLUS_STA_SET(*fw_mode_config,
10552 		PM_CHANNEL_SELECT_LOGIC_STA_STA_GET(channel_select_logic_conc));
10553 	WMI_DBS_FW_MODE_CFG_DBS_FOR_STA_PLUS_P2P_SET(*fw_mode_config,
10554 		PM_CHANNEL_SELECT_LOGIC_STA_P2P_GET(channel_select_logic_conc));
10555 
10556 	policy_mgr_debug("*scan_config:%x ", *scan_config);
10557 	policy_mgr_debug("*fw_mode_config:%x ", *fw_mode_config);
10558 
10559 	return QDF_STATUS_SUCCESS;
10560 }
10561 
10562 bool policy_mgr_is_force_scc(struct wlan_objmgr_psoc *psoc)
10563 {
10564 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10565 
10566 	pm_ctx = policy_mgr_get_context(psoc);
10567 	if (!pm_ctx) {
10568 		policy_mgr_err("Invalid Context");
10569 		return 0;
10570 	}
10571 
10572 	return ((pm_ctx->cfg.mcc_to_scc_switch ==
10573 		QDF_MCC_TO_SCC_SWITCH_FORCE_WITHOUT_DISCONNECTION) ||
10574 		(pm_ctx->cfg.mcc_to_scc_switch ==
10575 		QDF_MCC_TO_SCC_SWITCH_WITH_FAVORITE_CHANNEL) ||
10576 		(pm_ctx->cfg.mcc_to_scc_switch ==
10577 		QDF_MCC_TO_SCC_SWITCH_FORCE_PREFERRED_WITHOUT_DISCONNECTION) ||
10578 		(pm_ctx->cfg.mcc_to_scc_switch ==
10579 		QDF_MCC_TO_SCC_WITH_PREFERRED_BAND));
10580 }
10581 
10582 bool policy_mgr_is_sap_allowed_on_dfs_freq(struct wlan_objmgr_pdev *pdev,
10583 					   uint8_t vdev_id, qdf_freq_t ch_freq)
10584 {
10585 	struct wlan_objmgr_psoc *psoc;
10586 	uint32_t sta_sap_scc_on_dfs_chan;
10587 	uint32_t sta_cnt, gc_cnt;
10588 
10589 	psoc = wlan_pdev_get_psoc(pdev);
10590 	if (!psoc)
10591 		return false;
10592 
10593 	sta_sap_scc_on_dfs_chan =
10594 		policy_mgr_is_sta_sap_scc_allowed_on_dfs_chan(psoc);
10595 	sta_cnt = policy_mgr_mode_specific_connection_count(psoc,
10596 							    PM_STA_MODE, NULL);
10597 	gc_cnt = policy_mgr_mode_specific_connection_count(psoc,
10598 						PM_P2P_CLIENT_MODE, NULL);
10599 
10600 	policy_mgr_debug("sta_sap_scc_on_dfs_chan %u, sta_cnt %u, gc_cnt %u",
10601 			 sta_sap_scc_on_dfs_chan, sta_cnt, gc_cnt);
10602 
10603 	/* if sta_sap_scc_on_dfs_chan ini is set, DFS master capability is
10604 	 * assumed disabled in the driver.
10605 	 */
10606 	if ((wlan_reg_get_channel_state_for_pwrmode(
10607 		pdev, ch_freq, REG_CURRENT_PWR_MODE) == CHANNEL_STATE_DFS) &&
10608 	    !sta_cnt && !gc_cnt && sta_sap_scc_on_dfs_chan &&
10609 	    !policy_mgr_get_dfs_master_dynamic_enabled(psoc, vdev_id)) {
10610 		policy_mgr_err("SAP not allowed on DFS channel if no dfs master capability!!");
10611 		return false;
10612 	}
10613 
10614 	return true;
10615 }
10616 
10617 bool
10618 policy_mgr_is_sap_go_interface_allowed_on_indoor(struct wlan_objmgr_pdev *pdev,
10619 						 uint8_t vdev_id,
10620 						 qdf_freq_t ch_freq)
10621 {
10622 	struct wlan_objmgr_psoc *psoc;
10623 	bool is_scc = false, indoor_support = false;
10624 	enum QDF_OPMODE mode;
10625 
10626 	psoc = wlan_pdev_get_psoc(pdev);
10627 	if (!psoc)
10628 		return true;
10629 
10630 	if (!wlan_reg_is_freq_indoor(pdev, ch_freq))
10631 		return true;
10632 
10633 	is_scc = policy_mgr_is_sta_sap_scc(psoc, ch_freq);
10634 	mode = wlan_get_opmode_from_vdev_id(pdev, vdev_id);
10635 	ucfg_mlme_get_indoor_channel_support(psoc, &indoor_support);
10636 
10637 	/*
10638 	 * Rules for indoor operation:
10639 	 * If gindoor_channel_support is enabled - Allow SAP/GO
10640 	 * If gindoor_channel_support is disabled
10641 	 *      a) Restrict 6 GHz SAP
10642 	 *      b) Restrict standalone 5 GHz SAP
10643 	 *
10644 	 * If p2p_go_on_5ghz_indoor_chan is enabled - Allow GO
10645 	 * with or without concurrency
10646 	 *
10647 	 * If sta_sap_scc_on_indoor_chan is enabled - Allow
10648 	 * SAP/GO with concurrent STA in indoor SCC
10649 	 *
10650 	 * Restrict all other operations on indoor
10651 	 */
10652 
10653 	if (indoor_support)
10654 		return true;
10655 
10656 	if (WLAN_REG_IS_6GHZ_CHAN_FREQ(ch_freq)) {
10657 		policy_mgr_rl_debug("SAP operation is not allowed on 6 GHz indoor channel");
10658 		return false;
10659 	}
10660 
10661 	if (mode == QDF_SAP_MODE) {
10662 		if (is_scc &&
10663 		    policy_mgr_get_sta_sap_scc_allowed_on_indoor_chnl(psoc))
10664 			return true;
10665 		policy_mgr_rl_debug("SAP operation is not allowed on indoor channel");
10666 		return false;
10667 	}
10668 
10669 	if (mode == QDF_P2P_GO_MODE) {
10670 		if (ucfg_p2p_get_indoor_ch_support(psoc) ||
10671 		    (is_scc &&
10672 		    policy_mgr_get_sta_sap_scc_allowed_on_indoor_chnl(psoc)))
10673 			return true;
10674 		policy_mgr_rl_debug("GO operation is not allowed on indoor channel");
10675 		return false;
10676 	}
10677 
10678 	policy_mgr_rl_debug("SAP operation is not allowed on indoor channel");
10679 	return false;
10680 }
10681 
10682 bool policy_mgr_is_sta_sap_scc_allowed_on_dfs_chan(
10683 		struct wlan_objmgr_psoc *psoc)
10684 {
10685 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10686 	uint8_t sta_sap_scc_on_dfs_chnl = 0;
10687 	bool status = false;
10688 
10689 	pm_ctx = policy_mgr_get_context(psoc);
10690 	if (!pm_ctx) {
10691 		policy_mgr_err("Invalid Context");
10692 		return status;
10693 	}
10694 
10695 	policy_mgr_get_sta_sap_scc_on_dfs_chnl(psoc,
10696 					       &sta_sap_scc_on_dfs_chnl);
10697 	if (policy_mgr_is_force_scc(psoc) && sta_sap_scc_on_dfs_chnl)
10698 		status = true;
10699 
10700 	return status;
10701 }
10702 
10703 bool policy_mgr_is_multi_sap_allowed_on_same_band(
10704 					struct wlan_objmgr_pdev *pdev,
10705 					enum policy_mgr_con_mode mode,
10706 					qdf_freq_t ch_freq)
10707 {
10708 	struct wlan_objmgr_psoc *psoc;
10709 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10710 	bool multi_sap_allowed_on_same_band;
10711 	QDF_STATUS status;
10712 
10713 	psoc = wlan_pdev_get_psoc(pdev);
10714 	if (!psoc)
10715 		return false;
10716 
10717 	pm_ctx = policy_mgr_get_context(psoc);
10718 	if (!pm_ctx) {
10719 		policy_mgr_err("Invalid Context");
10720 		return false;
10721 	}
10722 
10723 	if (!ch_freq || !policy_mgr_is_sap_mode(mode))
10724 		return true;
10725 
10726 	status = policy_mgr_get_multi_sap_allowed_on_same_band(psoc,
10727 					&multi_sap_allowed_on_same_band);
10728 	if (!QDF_IS_STATUS_SUCCESS(status)) {
10729 		policy_mgr_err("Failed to get multi_sap_allowed_on_same_band");
10730 		/* Allow multi SAPs started on same band by default. */
10731 		multi_sap_allowed_on_same_band = true;
10732 	}
10733 	if (!multi_sap_allowed_on_same_band) {
10734 		uint32_t ap_cnt, index = 0;
10735 		uint32_t list[MAX_NUMBER_OF_CONC_CONNECTIONS];
10736 		struct policy_mgr_conc_connection_info *ap_info;
10737 
10738 		ap_cnt = policy_mgr_get_sap_mode_count(psoc, list);
10739 		if (!ap_cnt)
10740 			return true;
10741 
10742 		qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10743 		while (index < ap_cnt) {
10744 			ap_info = &pm_conc_connection_list[list[index]];
10745 			if (WLAN_REG_IS_SAME_BAND_FREQS(ch_freq,
10746 							ap_info->freq)) {
10747 				policy_mgr_rl_debug("Don't allow SAP on same band");
10748 				qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10749 				return false;
10750 			}
10751 			index++;
10752 		}
10753 		qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10754 	}
10755 
10756 	return true;
10757 }
10758 
10759 bool policy_mgr_is_special_mode_active_5g(struct wlan_objmgr_psoc *psoc,
10760 					  enum policy_mgr_con_mode mode)
10761 {
10762 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10763 	uint32_t conn_index;
10764 	bool ret = false;
10765 
10766 	pm_ctx = policy_mgr_get_context(psoc);
10767 	if (!pm_ctx) {
10768 		policy_mgr_err("Invalid Context");
10769 		return ret;
10770 	}
10771 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10772 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
10773 	     conn_index++) {
10774 		if (pm_conc_connection_list[conn_index].mode == mode &&
10775 		    pm_conc_connection_list[conn_index].freq >=
10776 					WLAN_REG_MIN_5GHZ_CHAN_FREQ &&
10777 		    pm_conc_connection_list[conn_index].in_use)
10778 			ret = true;
10779 	}
10780 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10781 
10782 	return ret;
10783 }
10784 
10785 bool policy_mgr_is_sta_connected_2g(struct wlan_objmgr_psoc *psoc)
10786 {
10787 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10788 	uint32_t conn_index;
10789 	bool ret = false;
10790 
10791 	pm_ctx = policy_mgr_get_context(psoc);
10792 	if (!pm_ctx) {
10793 		policy_mgr_err("Invalid Context");
10794 		return ret;
10795 	}
10796 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10797 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
10798 	     conn_index++) {
10799 		if (pm_conc_connection_list[conn_index].mode == PM_STA_MODE &&
10800 		    pm_conc_connection_list[conn_index].freq <=
10801 				WLAN_REG_MAX_24GHZ_CHAN_FREQ &&
10802 		    pm_conc_connection_list[conn_index].in_use)
10803 			ret = true;
10804 	}
10805 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10806 
10807 	return ret;
10808 }
10809 
10810 bool
10811 policy_mgr_is_connected_sta_5g(struct wlan_objmgr_psoc *psoc, qdf_freq_t *freq)
10812 {
10813 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10814 	uint32_t conn_index;
10815 	bool ret = false;
10816 
10817 	pm_ctx = policy_mgr_get_context(psoc);
10818 	if (!pm_ctx) {
10819 		policy_mgr_err("Invalid Context");
10820 		return ret;
10821 	}
10822 
10823 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10824 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
10825 	     conn_index++) {
10826 		*freq = pm_conc_connection_list[conn_index].freq;
10827 		if (pm_conc_connection_list[conn_index].mode == PM_STA_MODE &&
10828 		    WLAN_REG_IS_5GHZ_CH_FREQ(*freq) &&
10829 		    pm_conc_connection_list[conn_index].in_use) {
10830 			ret = true;
10831 			break;
10832 		}
10833 	}
10834 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10835 
10836 	return ret;
10837 }
10838 
10839 uint32_t policy_mgr_get_connection_info(struct wlan_objmgr_psoc *psoc,
10840 					struct connection_info *info)
10841 {
10842 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10843 	uint32_t conn_index, count = 0;
10844 
10845 	pm_ctx = policy_mgr_get_context(psoc);
10846 	if (!pm_ctx) {
10847 		policy_mgr_err("Invalid Context");
10848 		return count;
10849 	}
10850 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
10851 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
10852 	     conn_index++) {
10853 		if (PM_CONC_CONNECTION_LIST_VALID_INDEX(conn_index)) {
10854 			info[count].vdev_id =
10855 				pm_conc_connection_list[conn_index].vdev_id;
10856 			info[count].mac_id =
10857 				pm_conc_connection_list[conn_index].mac;
10858 			info[count].channel = wlan_reg_freq_to_chan(
10859 				pm_ctx->pdev,
10860 				pm_conc_connection_list[conn_index].freq);
10861 			info[count].ch_freq =
10862 				pm_conc_connection_list[conn_index].freq;
10863 			count++;
10864 		}
10865 	}
10866 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
10867 
10868 	return count;
10869 }
10870 
10871 bool policy_mgr_allow_sap_go_concurrency(struct wlan_objmgr_psoc *psoc,
10872 					 enum policy_mgr_con_mode mode,
10873 					 uint32_t ch_freq,
10874 					 uint32_t vdev_id)
10875 {
10876 	enum policy_mgr_con_mode con_mode;
10877 	int id;
10878 	uint32_t vdev, con_freq;
10879 	bool dbs;
10880 
10881 	if (mode != PM_SAP_MODE && mode != PM_P2P_GO_MODE)
10882 		return true;
10883 	dbs = policy_mgr_is_hw_dbs_capable(psoc);
10884 	for (id = 0; id < MAX_NUMBER_OF_CONC_CONNECTIONS; id++) {
10885 		if (!pm_conc_connection_list[id].in_use)
10886 			continue;
10887 		vdev = pm_conc_connection_list[id].vdev_id;
10888 		if (vdev_id == vdev)
10889 			continue;
10890 		con_mode = pm_conc_connection_list[id].mode;
10891 		if (con_mode != PM_SAP_MODE && con_mode != PM_P2P_GO_MODE)
10892 			continue;
10893 		con_freq = pm_conc_connection_list[id].freq;
10894 
10895 		if (policy_mgr_is_p2p_p2p_conc_supported(psoc) &&
10896 		    (mode == PM_P2P_GO_MODE) && (con_mode == PM_P2P_GO_MODE)) {
10897 			policy_mgr_debug("GO+GO scc is allowed freq = %d ",
10898 					 ch_freq);
10899 			return true;
10900 		}
10901 
10902 		if (policy_mgr_dual_beacon_on_single_mac_mcc_capable(psoc) &&
10903 		    (mode == PM_SAP_MODE || mode == PM_P2P_GO_MODE) &&
10904 		    (con_mode == PM_SAP_MODE || con_mode == PM_P2P_GO_MODE))
10905 			return true;
10906 
10907 		if (policy_mgr_dual_beacon_on_single_mac_scc_capable(psoc) &&
10908 		    (ch_freq == con_freq)) {
10909 			policy_mgr_debug("SCC enabled, 2 AP on same channel, allow 2nd AP");
10910 			return true;
10911 		}
10912 		if (!dbs) {
10913 			policy_mgr_debug("DBS unsupported, mcc and scc unsupported too, don't allow 2nd AP");
10914 			return false;
10915 		}
10916 
10917 		if (policy_mgr_are_2_freq_on_same_mac(psoc, ch_freq,
10918 						      con_freq)) {
10919 			policy_mgr_debug("DBS supported, 2 SAP on same band, reject 2nd AP");
10920 			return false;
10921 		}
10922 	}
10923 
10924 	/* Don't block the second interface */
10925 	return true;
10926 }
10927 
10928 bool policy_mgr_dual_beacon_on_single_mac_scc_capable(
10929 		struct wlan_objmgr_psoc *psoc)
10930 {
10931 	struct wmi_unified *wmi_handle;
10932 
10933 	wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
10934 	if (!wmi_handle) {
10935 		policy_mgr_debug("Invalid WMI handle");
10936 		return false;
10937 	}
10938 
10939 	if (wmi_service_enabled(
10940 			wmi_handle,
10941 			wmi_service_dual_beacon_on_single_mac_scc_support)) {
10942 		policy_mgr_debug("Dual beaconing on same channel on single MAC supported");
10943 		return true;
10944 	}
10945 	policy_mgr_debug("Dual beaconing on same channel on single MAC is not supported");
10946 	return false;
10947 }
10948 
10949 bool policy_mgr_dual_beacon_on_single_mac_mcc_capable(
10950 		struct wlan_objmgr_psoc *psoc)
10951 {
10952 	struct wmi_unified *wmi_handle;
10953 
10954 	wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
10955 	if (!wmi_handle) {
10956 		policy_mgr_debug("Invalid WMI handle");
10957 		return false;
10958 	}
10959 
10960 	if (wmi_service_enabled(
10961 			wmi_handle,
10962 			wmi_service_dual_beacon_on_single_mac_mcc_support)) {
10963 		policy_mgr_debug("Dual beaconing on different channel on single MAC supported");
10964 		return true;
10965 	}
10966 	policy_mgr_debug("Dual beaconing on different channel on single MAC is not supported");
10967 	return false;
10968 }
10969 
10970 bool policy_mgr_sta_sap_scc_on_lte_coex_chan(
10971 	struct wlan_objmgr_psoc *psoc)
10972 {
10973 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10974 	uint8_t scc_lte_coex = 0;
10975 
10976 	pm_ctx = policy_mgr_get_context(psoc);
10977 	if (!pm_ctx) {
10978 		policy_mgr_err("Invalid Context");
10979 		return false;
10980 	}
10981 	policy_mgr_get_sta_sap_scc_lte_coex_chnl(psoc, &scc_lte_coex);
10982 
10983 	return scc_lte_coex;
10984 }
10985 
10986 #if defined(CONFIG_BAND_6GHZ) && defined(WLAN_FEATURE_11AX)
10987 void policy_mgr_init_ap_6ghz_capable(struct wlan_objmgr_psoc *psoc,
10988 				     uint8_t vdev_id,
10989 				     enum conn_6ghz_flag ap_6ghz_capable)
10990 {
10991 	struct policy_mgr_conc_connection_info *conn_info;
10992 	uint32_t conn_index;
10993 	struct policy_mgr_psoc_priv_obj *pm_ctx;
10994 	enum conn_6ghz_flag conn_6ghz_flag = 0;
10995 
10996 	pm_ctx = policy_mgr_get_context(psoc);
10997 	if (!pm_ctx) {
10998 		policy_mgr_err("Invalid Context");
10999 		return;
11000 	}
11001 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11002 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
11003 			conn_index++) {
11004 		conn_info = &pm_conc_connection_list[conn_index];
11005 		if (conn_info->in_use &&
11006 		    policy_mgr_is_sap_mode(conn_info->mode) &&
11007 		    vdev_id == conn_info->vdev_id) {
11008 			conn_info->conn_6ghz_flag = ap_6ghz_capable;
11009 			conn_info->conn_6ghz_flag |= CONN_6GHZ_FLAG_VALID;
11010 			conn_6ghz_flag = conn_info->conn_6ghz_flag;
11011 			break;
11012 		}
11013 	}
11014 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11015 	policy_mgr_debug("vdev %d init conn_6ghz_flag %x new %x",
11016 			 vdev_id, ap_6ghz_capable, conn_6ghz_flag);
11017 }
11018 
11019 void policy_mgr_set_ap_6ghz_capable(struct wlan_objmgr_psoc *psoc,
11020 				    uint8_t vdev_id,
11021 				    bool set,
11022 				    enum conn_6ghz_flag ap_6ghz_capable)
11023 {
11024 	struct policy_mgr_conc_connection_info *conn_info;
11025 	uint32_t conn_index;
11026 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11027 	enum conn_6ghz_flag conn_6ghz_flag = 0;
11028 
11029 	pm_ctx = policy_mgr_get_context(psoc);
11030 	if (!pm_ctx) {
11031 		policy_mgr_err("Invalid Context");
11032 		return;
11033 	}
11034 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11035 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
11036 			conn_index++) {
11037 		conn_info = &pm_conc_connection_list[conn_index];
11038 		if (conn_info->in_use &&
11039 		    policy_mgr_is_beaconing_mode(conn_info->mode) &&
11040 		    policy_mgr_is_6ghz_conc_mode_supported(
11041 						psoc, conn_info->mode) &&
11042 		    vdev_id == conn_info->vdev_id) {
11043 			if (set)
11044 				conn_info->conn_6ghz_flag |= ap_6ghz_capable;
11045 			else
11046 				conn_info->conn_6ghz_flag &= ~ap_6ghz_capable;
11047 			conn_info->conn_6ghz_flag |= CONN_6GHZ_FLAG_VALID;
11048 			conn_6ghz_flag = conn_info->conn_6ghz_flag;
11049 			break;
11050 		}
11051 	}
11052 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11053 	policy_mgr_debug("vdev %d %s conn_6ghz_flag %x new %x",
11054 			 vdev_id, set ? "set" : "clr",
11055 			 ap_6ghz_capable, conn_6ghz_flag);
11056 }
11057 
11058 bool policy_mgr_get_ap_6ghz_capable(struct wlan_objmgr_psoc *psoc,
11059 				    uint8_t vdev_id,
11060 				    uint32_t *conn_flag)
11061 {
11062 	struct policy_mgr_conc_connection_info *conn_info;
11063 	uint32_t conn_index;
11064 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11065 	enum conn_6ghz_flag conn_6ghz_flag = 0;
11066 	bool is_6g_allowed = false;
11067 
11068 	if (conn_flag)
11069 		*conn_flag = 0;
11070 	pm_ctx = policy_mgr_get_context(psoc);
11071 	if (!pm_ctx) {
11072 		policy_mgr_err("Invalid Context");
11073 		return false;
11074 	}
11075 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11076 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
11077 			conn_index++) {
11078 		conn_info = &pm_conc_connection_list[conn_index];
11079 		if (conn_info->in_use &&
11080 		    policy_mgr_is_beaconing_mode(conn_info->mode) &&
11081 		    policy_mgr_is_6ghz_conc_mode_supported(
11082 						psoc, conn_info->mode) &&
11083 		    vdev_id == conn_info->vdev_id) {
11084 			conn_6ghz_flag = conn_info->conn_6ghz_flag;
11085 			break;
11086 		}
11087 	}
11088 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11089 
11090 	/* If the vdev connection is not active, policy mgr will query legacy
11091 	 * hdd to get sap acs and security information.
11092 	 * The assumption is no legacy client connected for non active
11093 	 * connection.
11094 	 */
11095 	if (!(conn_6ghz_flag & CONN_6GHZ_FLAG_VALID) &&
11096 	    pm_ctx->hdd_cbacks.hdd_get_ap_6ghz_capable)
11097 		conn_6ghz_flag = pm_ctx->hdd_cbacks.hdd_get_ap_6ghz_capable(
11098 					psoc, vdev_id) |
11099 					CONN_6GHZ_FLAG_NO_LEGACY_CLIENT;
11100 
11101 	if ((conn_6ghz_flag & CONN_6GHZ_CAPABLE) == CONN_6GHZ_CAPABLE)
11102 		is_6g_allowed = true;
11103 	policy_mgr_debug("vdev %d conn_6ghz_flag %x 6ghz %s", vdev_id,
11104 			 conn_6ghz_flag, is_6g_allowed ? "allowed" : "deny");
11105 	if (conn_flag)
11106 		*conn_flag = conn_6ghz_flag;
11107 
11108 	return is_6g_allowed;
11109 }
11110 #endif
11111 
11112 bool policy_mgr_is_valid_for_channel_switch(struct wlan_objmgr_psoc *psoc,
11113 					    uint32_t ch_freq)
11114 {
11115 	uint32_t sta_sap_scc_on_dfs_chan, sta_sap_scc_allowed_on_indoor_chan;
11116 	uint32_t sap_count;
11117 	enum channel_state state;
11118 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11119 
11120 	pm_ctx = policy_mgr_get_context(psoc);
11121 	if (!pm_ctx) {
11122 		policy_mgr_err("Invalid Context");
11123 		return false;
11124 	}
11125 
11126 	sta_sap_scc_on_dfs_chan =
11127 			policy_mgr_is_sta_sap_scc_allowed_on_dfs_chan(psoc);
11128 	sta_sap_scc_allowed_on_indoor_chan =
11129 			policy_mgr_get_sta_sap_scc_allowed_on_indoor_chnl(psoc);
11130 
11131 	sap_count = policy_mgr_mode_specific_connection_count(psoc,
11132 							      PM_SAP_MODE,
11133 							      NULL);
11134 	state = wlan_reg_get_channel_state_for_pwrmode(pm_ctx->pdev, ch_freq,
11135 						       REG_CURRENT_PWR_MODE);
11136 
11137 	policy_mgr_debug("sta_sap_scc_on_dfs_chan %u, sap_count %u, ch freq %u, state %u",
11138 			 sta_sap_scc_on_dfs_chan, sap_count, ch_freq, state);
11139 
11140 	if ((state == CHANNEL_STATE_ENABLE) || (sap_count == 0) ||
11141 	    (wlan_reg_is_dfs_for_freq(pm_ctx->pdev, ch_freq) &&
11142 	     sta_sap_scc_on_dfs_chan) ||
11143 	    (sta_sap_scc_allowed_on_indoor_chan &&
11144 	     wlan_reg_is_freq_indoor(pm_ctx->pdev, ch_freq))) {
11145 		policy_mgr_debug("Valid channel for channel switch");
11146 		return true;
11147 	}
11148 
11149 	policy_mgr_debug("Invalid channel for channel switch");
11150 	return false;
11151 }
11152 
11153 bool policy_mgr_is_sta_sap_scc(struct wlan_objmgr_psoc *psoc,
11154 			       uint32_t sap_freq)
11155 {
11156 	uint32_t conn_index;
11157 	bool is_scc = false;
11158 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11159 
11160 	pm_ctx = policy_mgr_get_context(psoc);
11161 	if (!pm_ctx) {
11162 		policy_mgr_err("Invalid Context");
11163 		return is_scc;
11164 	}
11165 
11166 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11167 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
11168 		conn_index++) {
11169 		if (pm_conc_connection_list[conn_index].in_use &&
11170 				(pm_conc_connection_list[conn_index].mode ==
11171 				PM_STA_MODE ||
11172 				pm_conc_connection_list[conn_index].mode ==
11173 				PM_P2P_CLIENT_MODE) && (sap_freq ==
11174 				pm_conc_connection_list[conn_index].freq)) {
11175 			is_scc = true;
11176 			break;
11177 		}
11178 	}
11179 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11180 
11181 	return is_scc;
11182 }
11183 
11184 bool policy_mgr_go_scc_enforced(struct wlan_objmgr_psoc *psoc)
11185 {
11186 	uint32_t mcc_to_scc_switch;
11187 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11188 
11189 	pm_ctx = policy_mgr_get_context(psoc);
11190 	if (!pm_ctx) {
11191 		policy_mgr_err("Invalid Context");
11192 		return false;
11193 	}
11194 	mcc_to_scc_switch = policy_mgr_get_mcc_to_scc_switch_mode(psoc);
11195 	if (mcc_to_scc_switch ==
11196 	    QDF_MCC_TO_SCC_SWITCH_FORCE_PREFERRED_WITHOUT_DISCONNECTION)
11197 		return true;
11198 
11199 	if (pm_ctx->cfg.go_force_scc && policy_mgr_is_force_scc(psoc))
11200 		return true;
11201 
11202 	return false;
11203 }
11204 
11205 uint8_t
11206 policy_mgr_fetch_existing_con_info(struct wlan_objmgr_psoc *psoc,
11207 				   uint8_t vdev_id, uint32_t freq,
11208 				   enum policy_mgr_con_mode *mode,
11209 				   uint32_t *existing_con_freq,
11210 				   enum phy_ch_width *existing_ch_width)
11211 {
11212 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11213 	uint32_t conn_index;
11214 
11215 	pm_ctx = policy_mgr_get_context(psoc);
11216 	if (!pm_ctx) {
11217 		policy_mgr_err("Invalid Context");
11218 		return WLAN_UMAC_VDEV_ID_MAX;
11219 	}
11220 
11221 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11222 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
11223 	     conn_index++) {
11224 		if ((policy_mgr_is_beaconing_mode(
11225 				pm_conc_connection_list[conn_index].mode) ||
11226 		    pm_conc_connection_list[conn_index].mode ==
11227 		    PM_P2P_CLIENT_MODE ||
11228 		    pm_conc_connection_list[conn_index].mode ==
11229 		    PM_STA_MODE) &&
11230 		    pm_conc_connection_list[conn_index].in_use &&
11231 		    policy_mgr_are_2_freq_on_same_mac(
11232 			psoc, freq, pm_conc_connection_list[conn_index].freq) &&
11233 		    freq != pm_conc_connection_list[conn_index].freq &&
11234 		    vdev_id != pm_conc_connection_list[conn_index].vdev_id) {
11235 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11236 			policy_mgr_debug(
11237 				"Existing vdev_id for mode %d is %d",
11238 				pm_conc_connection_list[conn_index].mode,
11239 				pm_conc_connection_list[conn_index].vdev_id);
11240 			*mode = pm_conc_connection_list[conn_index].mode;
11241 			*existing_con_freq =
11242 				pm_conc_connection_list[conn_index].freq;
11243 			*existing_ch_width = policy_mgr_get_ch_width(
11244 					pm_conc_connection_list[conn_index].bw);
11245 			return pm_conc_connection_list[conn_index].vdev_id;
11246 		}
11247 	}
11248 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11249 
11250 	return WLAN_UMAC_VDEV_ID_MAX;
11251 }
11252 
11253 #ifdef WLAN_FEATURE_P2P_P2P_STA
11254 bool policy_mgr_is_go_scc_strict(struct wlan_objmgr_psoc *psoc)
11255 {
11256 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11257 	bool ret = false;
11258 
11259 	pm_ctx = policy_mgr_get_context(psoc);
11260 	if (!pm_ctx) {
11261 		ret = false;
11262 		goto return_val;
11263 	}
11264 	if (pm_ctx->cfg.go_force_scc & GO_FORCE_SCC_STRICT) {
11265 		ret = true;
11266 		goto return_val;
11267 	}
11268 	ret = false;
11269 return_val:
11270 	policy_mgr_debug("ret val is %d", ret);
11271 	return ret;
11272 }
11273 #endif
11274 
11275 QDF_STATUS policy_mgr_update_nan_vdev_mac_info(struct wlan_objmgr_psoc *psoc,
11276 					       uint8_t nan_vdev_id,
11277 					       uint8_t mac_id)
11278 {
11279 	struct policy_mgr_hw_mode_params hw_mode = {0};
11280 	struct policy_mgr_vdev_mac_map vdev_mac_map = {0};
11281 	QDF_STATUS status;
11282 
11283 	vdev_mac_map.vdev_id = nan_vdev_id;
11284 	vdev_mac_map.mac_id = mac_id;
11285 
11286 	status = policy_mgr_get_current_hw_mode(psoc, &hw_mode);
11287 
11288 	if (QDF_IS_STATUS_SUCCESS(status))
11289 		policy_mgr_update_hw_mode_conn_info(psoc, 1, &vdev_mac_map,
11290 						    hw_mode, 0, NULL);
11291 
11292 	return status;
11293 }
11294 
11295 bool policy_mgr_is_sap_go_on_2g(struct wlan_objmgr_psoc *psoc)
11296 {
11297 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11298 	uint32_t conn_index;
11299 	bool ret = false;
11300 
11301 	pm_ctx = policy_mgr_get_context(psoc);
11302 	if (!pm_ctx) {
11303 		policy_mgr_err("Invalid Context");
11304 		return ret;
11305 	}
11306 
11307 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11308 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
11309 		 conn_index++) {
11310 		if ((pm_conc_connection_list[conn_index].mode == PM_SAP_MODE ||
11311 		     pm_conc_connection_list[conn_index].mode == PM_P2P_GO_MODE) &&
11312 			 pm_conc_connection_list[conn_index].freq <=
11313 				WLAN_REG_MAX_24GHZ_CHAN_FREQ &&
11314 			 pm_conc_connection_list[conn_index].in_use)
11315 			ret = true;
11316 	}
11317 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11318 
11319 	return ret;
11320 }
11321 
11322 bool policy_mgr_is_restart_sap_required(struct wlan_objmgr_psoc *psoc,
11323 					uint8_t vdev_id,
11324 					qdf_freq_t freq,
11325 					tQDF_MCC_TO_SCC_SWITCH_MODE scc_mode)
11326 {
11327 	uint8_t i;
11328 	bool restart_required = false;
11329 	bool is_sta_p2p_cli;
11330 	bool sap_on_dfs = false;
11331 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11332 	struct policy_mgr_conc_connection_info *connection;
11333 	bool sta_sap_scc_on_dfs_chan, sta_sap_scc_allowed_on_indoor_ch;
11334 	qdf_freq_t user_config_freq;
11335 	bool sap_found = false;
11336 	uint8_t num_mcc_conn = 0;
11337 	uint8_t num_scc_conn = 0;
11338 
11339 	pm_ctx = policy_mgr_get_context(psoc);
11340 	if (!pm_ctx) {
11341 		policy_mgr_err("Invalid psoc");
11342 		return false;
11343 	}
11344 	if (scc_mode == QDF_MCC_TO_SCC_SWITCH_DISABLE) {
11345 		policy_mgr_debug("No scc required");
11346 		return false;
11347 	}
11348 
11349 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11350 	connection = pm_conc_connection_list;
11351 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
11352 		if (!connection[i].in_use)
11353 			continue;
11354 		if (connection[i].vdev_id == vdev_id) {
11355 			if (WLAN_REG_IS_5GHZ_CH_FREQ(connection[i].freq) &&
11356 			    (connection[i].ch_flagext & (IEEE80211_CHAN_DFS |
11357 					      IEEE80211_CHAN_DFS_CFREQ2)))
11358 				sap_on_dfs = true;
11359 			sap_found = true;
11360 		} else if (connection[i].freq == freq) {
11361 			num_scc_conn++;
11362 		} else {
11363 			num_mcc_conn++;
11364 		}
11365 	}
11366 	if (!sap_found) {
11367 		policy_mgr_err("Invalid vdev id: %d", vdev_id);
11368 		qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11369 		return false;
11370 	}
11371 	/* Current hw mode is SBS low share. STA 5180, SAP 1 2412,
11372 	 * SAP 2 5745, but SAP 1 is 2G only, can't move to STA 5180,
11373 	 * SAP 2 is SBS with STA, policy_mgr_are_2_freq_on_same_mac
11374 	 * return false for 5745 and 5180 and finally this function
11375 	 * return false, no force SCC on SAP2.
11376 	 * Add mcc conntion count check for SAP2, if SAP 2 channel
11377 	 * is different from all of exsting 2 or more connections, then
11378 	 * try to force SCC on SAP 2.
11379 	 */
11380 	if (num_mcc_conn > 1 && !num_scc_conn) {
11381 		policy_mgr_debug("sap vdev %d has chan %d diff with %d exsting conn",
11382 				 vdev_id, freq, num_mcc_conn);
11383 		qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11384 		return true;
11385 	}
11386 	sta_sap_scc_on_dfs_chan =
11387 		policy_mgr_is_sta_sap_scc_allowed_on_dfs_chan(psoc);
11388 
11389 	sta_sap_scc_allowed_on_indoor_ch =
11390 		policy_mgr_get_sta_sap_scc_allowed_on_indoor_chnl(psoc);
11391 
11392 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
11393 		is_sta_p2p_cli =
11394 			connection[i].in_use &&
11395 			(connection[i].mode == PM_STA_MODE ||
11396 			connection[i].mode == PM_P2P_CLIENT_MODE);
11397 		if (!is_sta_p2p_cli)
11398 			continue;
11399 
11400 		if (connection[i].freq != freq &&
11401 		    policy_mgr_are_2_freq_on_same_mac(psoc, freq,
11402 						      connection[i].freq)) {
11403 			policy_mgr_debug("SAP:%d and STA:%d on same mac. Restart SAP ",
11404 					 freq, connection[i].freq);
11405 			restart_required = true;
11406 			break;
11407 		}
11408 		if (connection[i].freq == freq &&
11409 		    !sta_sap_scc_on_dfs_chan && sap_on_dfs) {
11410 			policy_mgr_debug("Move SAP out of DFS ch:%d", freq);
11411 			restart_required = true;
11412 			break;
11413 		}
11414 
11415 		if (connection[i].freq == freq &&
11416 		    !sta_sap_scc_allowed_on_indoor_ch &&
11417 		    wlan_reg_is_freq_indoor(pm_ctx->pdev, connection[i].freq)) {
11418 			policy_mgr_debug("Move SAP out of indoor ch:%d", freq);
11419 			restart_required = true;
11420 			break;
11421 		}
11422 
11423 		/*
11424 		 * Existing connection:
11425 		 * 1. "STA in DFS ch and SoftAP in 2.4 GHz channel, and then
11426 		 * STA moves to 5 GHz non-DFS channel
11427 		 *
11428 		 * 2. "STA in indoor channel and sta_sap_scc_on_indoor_ch
11429 		 * ini is false & SAP has moved to 2.4 GHz channel"
11430 		 * STA moves back to 5 GHZ non indoor/non DFS channel
11431 		 *
11432 		 * Now SAP has to move to STA 5 GHz channel if SAP
11433 		 * was started on 5 GHz channel initially.
11434 		 */
11435 		user_config_freq =
11436 			policy_mgr_get_user_config_sap_freq(psoc, vdev_id);
11437 
11438 		if (connection[i].freq != freq &&
11439 		    WLAN_REG_IS_24GHZ_CH_FREQ(freq) &&
11440 		    WLAN_REG_IS_5GHZ_CH_FREQ(connection[i].freq) &&
11441 		    !wlan_reg_is_dfs_for_freq(pm_ctx->pdev,
11442 					      connection[i].freq) &&
11443 		    WLAN_REG_IS_5GHZ_CH_FREQ(user_config_freq)) {
11444 			policy_mgr_debug("Move SAP from:%d to STA ch:%d  (sap start freq:%d)",
11445 					 freq, connection[i].freq,
11446 					 user_config_freq);
11447 			restart_required = true;
11448 
11449 			if (wlan_reg_is_freq_indoor(pm_ctx->pdev,
11450 						    connection[i].freq) &&
11451 			    !sta_sap_scc_allowed_on_indoor_ch)
11452 				restart_required = false;
11453 			break;
11454 		}
11455 
11456 		/*
11457 		 * SAP has to move away from indoor only channel
11458 		 * when STA moves out of indoor only channel and
11459 		 * SAP standalone support on indoor only
11460 		 * channel ini is disabled
11461 		 **/
11462 		if (connection[i].freq != freq &&
11463 		    WLAN_REG_IS_24GHZ_CH_FREQ(connection[i].freq) &&
11464 		    WLAN_REG_IS_5GHZ_CH_FREQ(freq) &&
11465 		    !policy_mgr_is_sap_go_interface_allowed_on_indoor(
11466 							pm_ctx->pdev,
11467 							vdev_id, freq)) {
11468 			policy_mgr_debug("SAP in indoor freq: sta:%d sap:%d",
11469 					 connection[i].freq, freq);
11470 			restart_required = true;
11471 		}
11472 	}
11473 
11474 	if (!restart_required &&
11475 	    policy_mgr_is_restart_sap_required_with_mlo_sta(
11476 					psoc, vdev_id, freq))
11477 		restart_required = true;
11478 
11479 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11480 
11481 	return restart_required;
11482 }
11483 
11484 uint8_t policy_mgr_get_roam_enabled_sta_session_id(
11485 					struct wlan_objmgr_psoc *psoc,
11486 					uint8_t vdev_id)
11487 {
11488 	uint32_t list[MAX_NUMBER_OF_CONC_CONNECTIONS];
11489 	uint32_t index, count;
11490 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11491 	struct wlan_objmgr_vdev *vdev, *assoc_vdev;
11492 
11493 	pm_ctx = policy_mgr_get_context(psoc);
11494 	if (!pm_ctx) {
11495 		policy_mgr_err("Invalid Context");
11496 		return WLAN_UMAC_VDEV_ID_MAX;
11497 	}
11498 
11499 	vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
11500 						    WLAN_POLICY_MGR_ID);
11501 	if (!vdev) {
11502 		policy_mgr_err("Invalid vdev");
11503 		return WLAN_UMAC_VDEV_ID_MAX;
11504 	}
11505 
11506 	if (wlan_vdev_mlme_is_link_sta_vdev(vdev)) {
11507 		assoc_vdev = ucfg_mlo_get_assoc_link_vdev(vdev);
11508 		if (assoc_vdev && ucfg_cm_is_vdev_active(assoc_vdev)) {
11509 			policy_mgr_debug("replace link vdev %d with assoc vdev %d",
11510 					 vdev_id, wlan_vdev_get_id(assoc_vdev));
11511 			vdev_id = wlan_vdev_get_id(assoc_vdev);
11512 		}
11513 	}
11514 	wlan_objmgr_vdev_release_ref(vdev, WLAN_POLICY_MGR_ID);
11515 
11516 	count = policy_mgr_mode_specific_connection_count(
11517 		psoc, PM_STA_MODE, list);
11518 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11519 
11520 	for (index = 0; index < count; index++) {
11521 		if (vdev_id == pm_conc_connection_list[list[index]].vdev_id)
11522 			continue;
11523 		if (MLME_IS_ROAM_INITIALIZED(
11524 			psoc, pm_conc_connection_list[list[index]].vdev_id)) {
11525 			qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11526 			return pm_conc_connection_list[list[index]].vdev_id;
11527 		}
11528 	}
11529 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11530 
11531 	return WLAN_UMAC_VDEV_ID_MAX;
11532 }
11533 
11534 bool policy_mgr_is_sta_mon_concurrency(struct wlan_objmgr_psoc *psoc)
11535 {
11536 	uint32_t conc_mode;
11537 
11538 	if (wlan_mlme_is_sta_mon_conc_supported(psoc)) {
11539 		conc_mode = policy_mgr_get_concurrency_mode(psoc);
11540 		if (conc_mode & QDF_STA_MASK &&
11541 		    conc_mode & QDF_MONITOR_MASK) {
11542 			policy_mgr_err("STA + MON mode is UP");
11543 			return true;
11544 		}
11545 	}
11546 	return false;
11547 }
11548 
11549 QDF_STATUS policy_mgr_check_mon_concurrency(struct wlan_objmgr_psoc *psoc)
11550 {
11551 	uint8_t num_open_session = 0;
11552 
11553 	if (policy_mgr_mode_specific_num_open_sessions(
11554 				psoc,
11555 				QDF_MONITOR_MODE,
11556 				&num_open_session) != QDF_STATUS_SUCCESS)
11557 		return QDF_STATUS_E_INVAL;
11558 
11559 	if (num_open_session) {
11560 		policy_mgr_err("monitor mode already exists, only one is possible");
11561 		return QDF_STATUS_E_BUSY;
11562 	}
11563 
11564 	num_open_session = policy_mgr_get_sap_mode_count(psoc, NULL);
11565 
11566 	if (num_open_session) {
11567 		policy_mgr_err("cannot add monitor mode, due to SAP concurrency");
11568 		return QDF_STATUS_E_INVAL;
11569 	}
11570 
11571 	num_open_session = policy_mgr_mode_specific_connection_count(
11572 					psoc,
11573 					PM_P2P_CLIENT_MODE,
11574 					NULL);
11575 
11576 	if (num_open_session) {
11577 		policy_mgr_err("cannot add monitor mode, due to P2P CLIENT concurrency");
11578 		return QDF_STATUS_E_INVAL;
11579 	}
11580 
11581 	num_open_session = policy_mgr_mode_specific_connection_count(
11582 					psoc,
11583 					PM_P2P_GO_MODE,
11584 					NULL);
11585 
11586 	if (num_open_session) {
11587 		policy_mgr_err("cannot add monitor mode, due to P2P GO concurrency");
11588 		return QDF_STATUS_E_INVAL;
11589 	}
11590 
11591 	num_open_session = policy_mgr_mode_specific_connection_count(
11592 					psoc,
11593 					PM_NAN_DISC_MODE,
11594 					NULL);
11595 
11596 	if (num_open_session) {
11597 		policy_mgr_err("cannot add monitor mode, due to NAN concurrency");
11598 		return QDF_STATUS_E_INVAL;
11599 	}
11600 
11601 	return QDF_STATUS_SUCCESS;
11602 }
11603 
11604 bool policy_mgr_is_hwmode_offload_enabled(struct wlan_objmgr_psoc *psoc)
11605 {
11606 	struct wmi_unified *wmi_handle;
11607 
11608 	wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
11609 	if (!wmi_handle) {
11610 		policy_mgr_err("Invalid WMI handle");
11611 		return false;
11612 	}
11613 
11614 	return wmi_service_enabled(wmi_handle,
11615 				   wmi_service_hw_mode_policy_offload_support);
11616 }
11617 
11618 bool policy_mgr_is_ap_ap_mcc_allow(struct wlan_objmgr_psoc *psoc,
11619 				   struct wlan_objmgr_pdev *pdev,
11620 				   struct wlan_objmgr_vdev *vdev,
11621 				   uint32_t ch_freq,
11622 				   enum phy_ch_width ch_width,
11623 				   uint8_t *con_vdev_id,
11624 				   uint32_t *con_freq)
11625 {
11626 	enum QDF_OPMODE mode;
11627 	enum policy_mgr_con_mode con_mode;
11628 	union conc_ext_flag conc_ext_flags;
11629 	uint32_t cc_count, i, j, ap_index;
11630 	uint32_t op_freq[MAX_NUMBER_OF_CONC_CONNECTIONS * 2];
11631 	uint8_t vdev_id[MAX_NUMBER_OF_CONC_CONNECTIONS * 2];
11632 	QDF_STATUS status;
11633 	struct policy_mgr_pcl_list pcl;
11634 
11635 	if (!psoc || !vdev || !pdev) {
11636 		policy_mgr_debug("psoc or vdev or pdev is NULL");
11637 		return false;
11638 	}
11639 
11640 	cc_count = policy_mgr_get_mode_specific_conn_info(psoc,
11641 							  &op_freq[0],
11642 							  &vdev_id[0],
11643 							  PM_SAP_MODE);
11644 	if (cc_count < MAX_NUMBER_OF_CONC_CONNECTIONS)
11645 		cc_count = cc_count +
11646 				policy_mgr_get_mode_specific_conn_info(
11647 					psoc,
11648 					&op_freq[cc_count],
11649 					&vdev_id[cc_count],
11650 					PM_P2P_GO_MODE);
11651 	if (!cc_count)
11652 		return true;
11653 
11654 	mode = wlan_vdev_mlme_get_opmode(vdev);
11655 	con_mode = policy_mgr_qdf_opmode_to_pm_con_mode(
11656 				psoc, mode, wlan_vdev_get_id(vdev));
11657 	qdf_mem_zero(&pcl, sizeof(pcl));
11658 	status = policy_mgr_get_pcl(psoc, con_mode, pcl.pcl_list, &pcl.pcl_len,
11659 				    pcl.weight_list,
11660 				    QDF_ARRAY_SIZE(pcl.weight_list),
11661 				    wlan_vdev_get_id(vdev));
11662 	if (!pcl.pcl_len)
11663 		return true;
11664 	ap_index = cc_count;
11665 	for (i = 0 ; i < pcl.pcl_len; i++) {
11666 		for (j = 0; j < cc_count; j++) {
11667 			if (op_freq[j] == pcl.pcl_list[i])
11668 				break;
11669 		}
11670 		if (j >= cc_count)
11671 			continue;
11672 		if (ch_freq == op_freq[j]) {
11673 			ap_index = j;
11674 			break;
11675 		}
11676 		if (!policy_mgr_is_hw_dbs_capable(psoc)) {
11677 			ap_index = j;
11678 			break;
11679 		}
11680 		if (wlan_reg_is_same_band_freqs(ch_freq, op_freq[j]) &&
11681 		    !policy_mgr_are_sbs_chan(psoc, ch_freq, op_freq[j])) {
11682 			ap_index = j;
11683 			break;
11684 		}
11685 		if (wlan_reg_is_same_band_freqs(ch_freq, op_freq[j]) &&
11686 		    policy_mgr_get_connection_count(psoc) > 2) {
11687 			ap_index = j;
11688 			break;
11689 		}
11690 	}
11691 	/* If same band MCC SAP/GO not present, return true,
11692 	 * no AP to AP channel override
11693 	 */
11694 	if (ap_index >= cc_count)
11695 		return true;
11696 
11697 	*con_freq = op_freq[ap_index];
11698 	*con_vdev_id = vdev_id[ap_index];
11699 	/*
11700 	 * For 3Vif concurrency we only support SCC in same MAC
11701 	 * in below combination:
11702 	 * 2 beaconing entities with STA in SCC.
11703 	 * 3 beaconing entities in SCC.
11704 	 */
11705 	conc_ext_flags.value = policy_mgr_get_conc_ext_flags(vdev, false);
11706 	if (!policy_mgr_allow_concurrency(
11707 			psoc, con_mode, ch_freq,
11708 			policy_mgr_get_bw(ch_width),
11709 			conc_ext_flags.value,
11710 			wlan_vdev_get_id(vdev))) {
11711 		policy_mgr_debug("AP AP mcc not allowed, try to override 2nd SAP/GO chan");
11712 		return false;
11713 	}
11714 	/* For SCC case & bandwdith > 20, the center frequency have to be
11715 	 * same to avoid target MCC on different center frequency even though
11716 	 * primary channel are same.
11717 	 */
11718 	if (*con_freq == ch_freq && wlan_reg_get_bw_value(ch_width) > 20)
11719 		return false;
11720 
11721 	return true;
11722 }
11723 
11724 bool policy_mgr_any_other_vdev_on_same_mac_as_freq(
11725 				struct wlan_objmgr_psoc *psoc,
11726 				uint32_t freq, uint8_t vdev_id)
11727 {
11728 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11729 	uint32_t conn_index = 0;
11730 	bool same_mac = false;
11731 
11732 	pm_ctx = policy_mgr_get_context(psoc);
11733 	if (!pm_ctx) {
11734 		policy_mgr_err("Invalid Context");
11735 		return false;
11736 	}
11737 
11738 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11739 	for (conn_index = 0; conn_index < MAX_NUMBER_OF_CONC_CONNECTIONS;
11740 	     conn_index++) {
11741 		if (!pm_conc_connection_list[conn_index].in_use)
11742 			continue;
11743 
11744 		if (pm_conc_connection_list[conn_index].vdev_id == vdev_id)
11745 			continue;
11746 
11747 		if (policy_mgr_are_2_freq_on_same_mac(
11748 				psoc,
11749 				pm_conc_connection_list[conn_index].freq,
11750 				freq)) {
11751 			same_mac = true;
11752 			break;
11753 		}
11754 	}
11755 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11756 
11757 	return same_mac;
11758 }
11759 
11760 QDF_STATUS policy_mgr_get_sbs_cfg(struct wlan_objmgr_psoc *psoc, bool *sbs)
11761 {
11762 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11763 
11764 	pm_ctx = policy_mgr_get_context(psoc);
11765 	if (!pm_ctx) {
11766 		policy_mgr_err("pm_ctx is NULL");
11767 		return QDF_STATUS_E_FAILURE;
11768 	}
11769 	*sbs = pm_ctx->cfg.sbs_enable;
11770 
11771 	return QDF_STATUS_SUCCESS;
11772 }
11773 
11774 #ifdef WLAN_FEATURE_SR
11775 bool policy_mgr_sr_same_mac_conc_enabled(struct wlan_objmgr_psoc *psoc)
11776 {
11777 	struct wmi_unified *wmi_handle;
11778 	bool sr_conc_enabled;
11779 
11780 	if (!psoc) {
11781 		mlme_err("PSOC is NULL");
11782 		return false;
11783 	}
11784 
11785 	wmi_handle = get_wmi_unified_hdl_from_psoc(psoc);
11786 	if (!wmi_handle) {
11787 		mlme_err("wmi_handle is null");
11788 		return false;
11789 	}
11790 
11791 	sr_conc_enabled = policy_mgr_get_same_mac_conc_sr_status(psoc);
11792 
11793 	return (sr_conc_enabled &&
11794 		wmi_service_enabled(wmi_handle,
11795 				    wmi_service_obss_per_packet_sr_support));
11796 }
11797 #endif
11798 
11799 /**
11800  * _policy_mgr_get_ll_sap_freq()- Function to get LL sap freq if it's present
11801  * for provided type
11802  * @psoc: PSOC object
11803  * @ap_type: low latency ap type
11804  *
11805  * Return: freq if LL SAP otherwise return 0
11806  *
11807  */
11808 static qdf_freq_t _policy_mgr_get_ll_sap_freq(struct wlan_objmgr_psoc *psoc,
11809 					      enum ll_ap_type ap_type)
11810 {
11811 	struct wlan_objmgr_vdev *sap_vdev;
11812 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11813 	uint32_t conn_idx = 0, vdev_id;
11814 	bool is_ll_sap_present = false;
11815 	qdf_freq_t freq = 0;
11816 	enum host_concurrent_ap_policy profile =
11817 					HOST_CONCURRENT_AP_POLICY_UNSPECIFIED;
11818 
11819 	pm_ctx = policy_mgr_get_context(psoc);
11820 	if (!pm_ctx) {
11821 		policy_mgr_err("pm_ctx is NULL");
11822 		return 0;
11823 	}
11824 
11825 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
11826 	for (conn_idx = 0; conn_idx < MAX_NUMBER_OF_CONC_CONNECTIONS;
11827 	     conn_idx++) {
11828 		if (!(policy_mgr_is_sap_mode(
11829 				pm_conc_connection_list[conn_idx].mode) &&
11830 		      pm_conc_connection_list[conn_idx].in_use))
11831 			continue;
11832 
11833 		vdev_id = pm_conc_connection_list[conn_idx].vdev_id;
11834 		freq = pm_conc_connection_list[conn_idx].freq;
11835 
11836 		sap_vdev = wlan_objmgr_get_vdev_by_id_from_psoc(
11837 				psoc,
11838 				vdev_id,
11839 				WLAN_POLICY_MGR_ID);
11840 
11841 		if (!sap_vdev) {
11842 			policy_mgr_err("vdev %d: not a sap vdev", vdev_id);
11843 			continue;
11844 		}
11845 
11846 		profile = wlan_mlme_get_ap_policy(sap_vdev);
11847 		wlan_objmgr_vdev_release_ref(sap_vdev,
11848 					     WLAN_POLICY_MGR_ID);
11849 		switch (ap_type) {
11850 		case LL_AP_TYPE_HT:
11851 			if (profile == HOST_CONCURRENT_AP_POLICY_XR)
11852 				is_ll_sap_present = true;
11853 		break;
11854 		case LL_AP_TYPE_LT:
11855 			if (profile == HOST_CONCURRENT_AP_POLICY_GAMING_AUDIO ||
11856 			    profile ==
11857 			    HOST_CONCURRENT_AP_POLICY_LOSSLESS_AUDIO_STREAMING)
11858 				is_ll_sap_present = true;
11859 		break;
11860 		case LL_AP_TYPE_ANY:
11861 			if (profile == HOST_CONCURRENT_AP_POLICY_GAMING_AUDIO ||
11862 			    profile == HOST_CONCURRENT_AP_POLICY_XR ||
11863 			    profile ==
11864 			    HOST_CONCURRENT_AP_POLICY_LOSSLESS_AUDIO_STREAMING)
11865 				is_ll_sap_present = true;
11866 		break;
11867 		default:
11868 		break;
11869 		}
11870 		if (!is_ll_sap_present)
11871 			continue;
11872 
11873 	       policy_mgr_debug("LL SAP %d present with vdev_id %d and freq %d",
11874 				ap_type, vdev_id, freq);
11875 
11876 		qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11877 		return freq;
11878 	}
11879 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
11880 	return 0;
11881 }
11882 
11883 qdf_freq_t policy_mgr_get_ll_sap_freq(struct wlan_objmgr_psoc *psoc)
11884 {
11885 	return _policy_mgr_get_ll_sap_freq(psoc, LL_AP_TYPE_ANY);
11886 }
11887 
11888 qdf_freq_t policy_mgr_get_ht_ll_sap_freq(struct wlan_objmgr_psoc *psoc)
11889 {
11890 	return _policy_mgr_get_ll_sap_freq(psoc, LL_AP_TYPE_HT);
11891 }
11892 
11893 qdf_freq_t policy_mgr_get_lt_ll_sap_freq(struct wlan_objmgr_psoc *psoc)
11894 {
11895 	return _policy_mgr_get_ll_sap_freq(psoc, LL_AP_TYPE_LT);
11896 }
11897 
11898 bool policy_mgr_is_ll_sap_concurrency_valid(struct wlan_objmgr_psoc *psoc,
11899 					    qdf_freq_t freq,
11900 					    enum policy_mgr_con_mode mode)
11901 {
11902 	qdf_freq_t ll_sap_freq;
11903 
11904 	ll_sap_freq = policy_mgr_get_ll_sap_freq(psoc);
11905 	if (!ll_sap_freq)
11906 		return true;
11907 
11908 	/*
11909 	 * Scenario: When low latency SAP with 5GHz channel(whose
11910 	 * profile is set as gaming or lossless audio or XR) is present
11911 	 * on SBS/DBS hardware and the other interface like
11912 	 * STA/SAP/GC/GO trying to form connection.
11913 	 * Allow connection on those freq which are mutually exclusive
11914 	 * to LL SAP mac
11915 	 */
11916 
11917 	if (policy_mgr_2_freq_always_on_same_mac(psoc, ll_sap_freq,
11918 						 freq)) {
11919 		policy_mgr_debug("Invalid LL-SAP concurrency for SBS/DBS hw, ll-sap freq %d, conc_freq %d, conc_mode %d",
11920 				 ll_sap_freq, freq, mode);
11921 		return false;
11922 	}
11923 
11924 	return true;
11925 }
11926 
11927 bool
11928 policy_mgr_update_indoor_concurrency(struct wlan_objmgr_psoc *psoc,
11929 				     uint8_t vdev_id,
11930 				     uint32_t discon_freq,
11931 				     enum indoor_conc_update_type type)
11932 {
11933 	uint32_t ch_freq;
11934 	enum QDF_OPMODE mode;
11935 	struct policy_mgr_psoc_priv_obj *pm_ctx;
11936 	enum phy_ch_width ch_width = CH_WIDTH_INVALID;
11937 	bool indoor_support = false;
11938 
11939 	pm_ctx = policy_mgr_get_context(psoc);
11940 	if (!pm_ctx) {
11941 		policy_mgr_err("Invalid pm context");
11942 		return false;
11943 	}
11944 
11945 	ucfg_mlme_get_indoor_channel_support(psoc, &indoor_support);
11946 	if (indoor_support ||
11947 	    !policy_mgr_get_sta_sap_scc_allowed_on_indoor_chnl(psoc))
11948 		return false;
11949 
11950 	mode = wlan_get_opmode_from_vdev_id(pm_ctx->pdev, vdev_id);
11951 
11952 	/**
11953 	 * DISCONNECT_WITH_CONCURRENCY update comes after SAP/GO CSA.
11954 	 * Whereas, all other updates come from STA/GC operation.
11955 	 */
11956 	if (type != DISCONNECT_WITH_CONCURRENCY &&
11957 	    (mode != QDF_STA_MODE && mode != QDF_P2P_CLIENT_MODE)) {
11958 		return false;
11959 	} else if (type == DISCONNECT_WITH_CONCURRENCY &&
11960 		 (mode != QDF_SAP_MODE && mode != QDF_P2P_GO_MODE)) {
11961 		return false;
11962 	}
11963 
11964 	switch (type) {
11965 	case CONNECT:
11966 	case SWITCH_WITHOUT_CONCURRENCY:
11967 	case SWITCH_WITH_CONCURRENCY:
11968 		policy_mgr_get_chan_by_session_id(psoc, vdev_id, &ch_freq);
11969 		ch_width = policy_mgr_get_bw_by_session_id(psoc, vdev_id);
11970 		break;
11971 	case DISCONNECT_WITHOUT_CONCURRENCY:
11972 	case DISCONNECT_WITH_CONCURRENCY:
11973 		ch_freq = discon_freq;
11974 		break;
11975 	default:
11976 		return false;
11977 	}
11978 
11979 	if (type != SWITCH_WITHOUT_CONCURRENCY &&
11980 	    !(WLAN_REG_IS_5GHZ_CH_FREQ(ch_freq) &&
11981 	    wlan_reg_is_freq_indoor(pm_ctx->pdev, ch_freq))) {
11982 		return false;
11983 	} else if (type == SWITCH_WITHOUT_CONCURRENCY) {
11984 		/* Either the previous frequency or the current
11985 		 * frequency can be indoor. Or both can be indoor.
11986 		 * Therefore, atleast one of the frequency must be
11987 		 * indoor in order to proceed for the update.
11988 		 */
11989 		if (!((WLAN_REG_IS_5GHZ_CH_FREQ(ch_freq) &&
11990 		       wlan_reg_is_freq_indoor(pm_ctx->pdev, ch_freq)) ||
11991 		      (WLAN_REG_IS_5GHZ_CH_FREQ(discon_freq) &&
11992 		       wlan_reg_is_freq_indoor(pm_ctx->pdev, discon_freq))))
11993 			return false;
11994 	}
11995 
11996 	switch (type) {
11997 	case CONNECT:
11998 		wlan_reg_modify_indoor_concurrency(pm_ctx->pdev, vdev_id,
11999 						   ch_freq, ch_width, true);
12000 		break;
12001 	case DISCONNECT_WITHOUT_CONCURRENCY:
12002 		wlan_reg_modify_indoor_concurrency(pm_ctx->pdev, vdev_id,
12003 						   0, CH_WIDTH_INVALID, false);
12004 		break;
12005 	case SWITCH_WITHOUT_CONCURRENCY:
12006 		wlan_reg_modify_indoor_concurrency(pm_ctx->pdev, vdev_id, 0,
12007 						   CH_WIDTH_INVALID, false);
12008 		if (wlan_reg_is_freq_indoor(pm_ctx->pdev, ch_freq))
12009 			wlan_reg_modify_indoor_concurrency(pm_ctx->pdev,
12010 							   vdev_id, ch_freq,
12011 							   ch_width, true);
12012 		break;
12013 	case DISCONNECT_WITH_CONCURRENCY:
12014 		/*If there are other sessions, do not change current chan list*/
12015 		if (policy_mgr_get_connection_count_with_ch_freq(ch_freq) > 1)
12016 			return false;
12017 		wlan_reg_modify_indoor_concurrency(pm_ctx->pdev,
12018 						   INVALID_VDEV_ID, ch_freq,
12019 						   CH_WIDTH_INVALID, false);
12020 		break;
12021 	case SWITCH_WITH_CONCURRENCY:
12022 		wlan_reg_modify_indoor_concurrency(pm_ctx->pdev, vdev_id,
12023 						   ch_freq, ch_width, true);
12024 		/*
12025 		 * The previous frequency removal and current channel list
12026 		 * recomputation will happen after SAP CSA
12027 		 */
12028 		return false;
12029 	}
12030 	return true;
12031 }
12032 
12033 bool policy_mgr_is_conc_sap_present_on_sta_freq(struct wlan_objmgr_psoc *psoc,
12034 						enum policy_mgr_con_mode mode,
12035 						uint32_t ch_freq)
12036 {
12037 	struct policy_mgr_psoc_priv_obj *pm_ctx;
12038 	uint8_t i;
12039 	bool sap_go_exists = false;
12040 	enum policy_mgr_con_mode cmode;
12041 
12042 	pm_ctx = policy_mgr_get_context(psoc);
12043 	if (!pm_ctx) {
12044 		policy_mgr_err("Invalid pm context");
12045 		return false;
12046 	}
12047 
12048 	if (mode != PM_STA_MODE && mode != PM_P2P_CLIENT_MODE)
12049 		return false;
12050 
12051 	qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
12052 	for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) {
12053 		cmode = pm_conc_connection_list[i].mode;
12054 		if (pm_conc_connection_list[i].in_use &&
12055 		    ch_freq == pm_conc_connection_list[i].freq &&
12056 		    (cmode == PM_SAP_MODE || cmode == PM_P2P_GO_MODE)) {
12057 			sap_go_exists = true;
12058 			break;
12059 		}
12060 	}
12061 	qdf_mutex_release(&pm_ctx->qdf_conc_list_lock);
12062 
12063 	return sap_go_exists;
12064 }
12065 
12066 bool policy_mgr_is_sap_mode(enum policy_mgr_con_mode mode)
12067 {
12068 	if (mode == PM_SAP_MODE || mode == PM_LL_LT_SAP_MODE)
12069 		return true;
12070 
12071 	return false;
12072 }
12073 
12074 bool policy_mgr_is_beaconing_mode(enum policy_mgr_con_mode mode)
12075 {
12076 	if (mode == PM_SAP_MODE || mode == PM_LL_LT_SAP_MODE ||
12077 	    mode == PM_P2P_GO_MODE)
12078 		return true;
12079 
12080 	return false;
12081 }
12082 
12083 bool policy_mgr_get_nan_sap_scc_on_lte_coex_chnl(struct wlan_objmgr_psoc *psoc)
12084 {
12085 	struct policy_mgr_psoc_priv_obj *pm_ctx;
12086 
12087 	pm_ctx = policy_mgr_get_context(psoc);
12088 	if (!pm_ctx) {
12089 		policy_mgr_err("pm_ctx is NULL");
12090 		return 0;
12091 	}
12092 	return pm_ctx->cfg.nan_sap_scc_on_lte_coex_chnl;
12093 }
12094 
12095 QDF_STATUS
12096 policy_mgr_reset_sap_mandatory_channels(struct wlan_objmgr_psoc *psoc)
12097 {
12098 	struct policy_mgr_psoc_priv_obj *pm_ctx;
12099 
12100 	pm_ctx = policy_mgr_get_context(psoc);
12101 	if (!pm_ctx) {
12102 		policy_mgr_err("Invalid Context");
12103 		return QDF_STATUS_E_FAILURE;
12104 	}
12105 
12106 	pm_ctx->sap_mandatory_channels_len = 0;
12107 	qdf_mem_zero(pm_ctx->sap_mandatory_channels,
12108 		     QDF_ARRAY_SIZE(pm_ctx->sap_mandatory_channels) *
12109 		     sizeof(*pm_ctx->sap_mandatory_channels));
12110 
12111 	return QDF_STATUS_SUCCESS;
12112 }
12113 
12114 bool policy_mgr_is_freq_on_mac_id(struct policy_mgr_freq_range *freq_range,
12115 				  qdf_freq_t freq, uint8_t mac_id)
12116 {
12117 	return IS_FREQ_ON_MAC_ID(freq_range, freq, mac_id);
12118 }
12119