diff --git a/components/cmn_services/policy_mgr/inc/wlan_policy_mgr_public_struct.h b/components/cmn_services/policy_mgr/inc/wlan_policy_mgr_public_struct.h index c5ad6f3749a7..fb135528999e 100644 --- a/components/cmn_services/policy_mgr/inc/wlan_policy_mgr_public_struct.h +++ b/components/cmn_services/policy_mgr/inc/wlan_policy_mgr_public_struct.h @@ -988,6 +988,7 @@ enum dbs_support { * @original_nss: nss negotiated at connection time * @vdev_id: vdev id of the connection * @in_use: if the table entry is active + * @ch_flagext: Channel extension flags. */ struct policy_mgr_conc_connection_info { enum policy_mgr_con_mode mode; @@ -998,6 +999,7 @@ struct policy_mgr_conc_connection_info { uint32_t original_nss; uint32_t vdev_id; bool in_use; + uint16_t ch_flagext; }; /** @@ -1109,6 +1111,7 @@ struct policy_mgr_pcl_chan_weights { * @mhz: channel frequency in MHz * @chan_width: channel bandwidth * @mac_id: the mac on which vdev is on + * @ch_flagext: Channel extension flags. */ struct policy_mgr_vdev_entry_info { uint32_t type; @@ -1116,6 +1119,7 @@ struct policy_mgr_vdev_entry_info { uint32_t mhz; uint32_t chan_width; uint32_t mac_id; + uint16_t ch_flagext; }; /** diff --git a/components/cmn_services/policy_mgr/src/wlan_policy_mgr_action.c b/components/cmn_services/policy_mgr/src/wlan_policy_mgr_action.c index 1db071680924..5acbf1fadd79 100644 --- a/components/cmn_services/policy_mgr/src/wlan_policy_mgr_action.c +++ b/components/cmn_services/policy_mgr/src/wlan_policy_mgr_action.c @@ -372,7 +372,7 @@ QDF_STATUS policy_mgr_update_connection_info(struct wlan_objmgr_psoc *psoc, psoc, conn_index, mode, ch_freq, policy_mgr_get_bw(conn_table_entry.chan_width), conn_table_entry.mac_id, chain_mask, - nss, vdev_id, true, true); + nss, vdev_id, true, true, conn_table_entry.ch_flagext); /* do we need to change the HW mode */ policy_mgr_check_n_start_opportunistic_timer(psoc); @@ -2575,6 +2575,7 @@ QDF_STATUS policy_mgr_update_connection_info_utfw( QDF_STATUS status = QDF_STATUS_E_FAILURE; uint32_t conn_index = 0, found = 0; struct policy_mgr_psoc_priv_obj *pm_ctx; + uint16_t ch_flagext = 0; pm_ctx = policy_mgr_get_context(psoc); if (!pm_ctx) { @@ -2600,10 +2601,14 @@ QDF_STATUS policy_mgr_update_connection_info_utfw( } policy_mgr_debug("--> updating entry at index[%d]", conn_index); + if (wlan_reg_is_dfs_for_freq(pm_ctx->pdev, ch_freq)) + ch_flagext |= IEEE80211_CHAN_DFS; + policy_mgr_update_conc_list(psoc, conn_index, policy_mgr_get_mode(type, sub_type), ch_freq, HW_MODE_20_MHZ, - mac_id, chain_mask, 0, vdev_id, true, true); + mac_id, chain_mask, 0, vdev_id, true, true, + ch_flagext); return QDF_STATUS_SUCCESS; } @@ -2618,6 +2623,8 @@ QDF_STATUS policy_mgr_incr_connection_count_utfw( uint32_t conn_index = 0; bool update_conn = true; enum policy_mgr_con_mode mode; + uint16_t ch_flagext = 0; + struct policy_mgr_psoc_priv_obj *pm_ctx; conn_index = policy_mgr_get_connection_count(psoc); if (MAX_NUMBER_OF_CONC_CONNECTIONS <= conn_index) { @@ -2632,11 +2639,17 @@ QDF_STATUS policy_mgr_incr_connection_count_utfw( if (mode == PM_STA_MODE || mode == PM_P2P_CLIENT_MODE) update_conn = false; - policy_mgr_update_conc_list(psoc, conn_index, - mode, - ch_freq, HW_MODE_20_MHZ, - mac_id, chain_mask, 0, vdev_id, true, - update_conn); + pm_ctx = policy_mgr_get_context(psoc); + if (!pm_ctx) { + policy_mgr_err("Invalid pm context"); + return false; + } + if (wlan_reg_is_dfs_for_freq(pm_ctx->pdev, ch_freq)) + ch_flagext |= IEEE80211_CHAN_DFS; + + policy_mgr_update_conc_list(psoc, conn_index, mode, ch_freq, + HW_MODE_20_MHZ, mac_id, chain_mask, + 0, vdev_id, true, update_conn, ch_flagext); return QDF_STATUS_SUCCESS; } diff --git a/components/cmn_services/policy_mgr/src/wlan_policy_mgr_core.c b/components/cmn_services/policy_mgr/src/wlan_policy_mgr_core.c index bd4922e2d27c..b161203bc292 100644 --- a/components/cmn_services/policy_mgr/src/wlan_policy_mgr_core.c +++ b/components/cmn_services/policy_mgr/src/wlan_policy_mgr_core.c @@ -566,23 +566,6 @@ QDF_STATUS policy_mgr_get_old_and_new_hw_index( return QDF_STATUS_SUCCESS; } -/** - * policy_mgr_update_conc_list() - Update the concurrent connection list - * @conn_index: Connection index - * @mode: Mode - * @ch_freq: channel frequency - * @bw: Bandwidth - * @mac: Mac id - * @chain_mask: Chain mask - * @vdev_id: vdev id - * @in_use: Flag to indicate if the index is in use or not - * @update_conn: Flag to indicate if mode change event should - * be sent or not - * - * Updates the index value of the concurrent connection list - * - * Return: None - */ void policy_mgr_update_conc_list(struct wlan_objmgr_psoc *psoc, uint32_t conn_index, enum policy_mgr_con_mode mode, @@ -593,7 +576,8 @@ void policy_mgr_update_conc_list(struct wlan_objmgr_psoc *psoc, uint32_t original_nss, uint32_t vdev_id, bool in_use, - bool update_conn) + bool update_conn, + uint16_t ch_flagext) { struct policy_mgr_psoc_priv_obj *pm_ctx; bool mcc_mode; @@ -619,6 +603,7 @@ void policy_mgr_update_conc_list(struct wlan_objmgr_psoc *psoc, pm_conc_connection_list[conn_index].original_nss = original_nss; pm_conc_connection_list[conn_index].vdev_id = vdev_id; pm_conc_connection_list[conn_index].in_use = in_use; + pm_conc_connection_list[conn_index].ch_flagext = ch_flagext; qdf_mutex_release(&pm_ctx->qdf_conc_list_lock); /* @@ -2539,6 +2524,7 @@ static bool policy_mgr_is_multi_ap_plus_sta_3vif_conc( * @mode: policy_mgr_con_mode of new connection, * @channel: channel on which new connection is coming up * @num_connections: number of current connections + * @is_dfs_ch: DFS channel or not * * When a new connection is about to come up check if current * concurrency combination including the new connection is @@ -2548,7 +2534,7 @@ static bool policy_mgr_is_multi_ap_plus_sta_3vif_conc( */ bool policy_mgr_allow_new_home_channel( struct wlan_objmgr_psoc *psoc, enum policy_mgr_con_mode mode, - uint32_t ch_freq, uint32_t num_connections) + uint32_t ch_freq, uint32_t num_connections, bool is_dfs_ch) { bool status = true; struct policy_mgr_psoc_priv_obj *pm_ctx; @@ -2567,11 +2553,11 @@ bool policy_mgr_allow_new_home_channel( /* No SCC or MCC combination is allowed with / on DFS channel */ if ((mcc_to_scc_switch == QDF_MCC_TO_SCC_SWITCH_FORCE_PREFERRED_WITHOUT_DISCONNECTION) && - wlan_reg_is_dfs_for_freq(pm_ctx->pdev, ch_freq) && - (wlan_reg_is_dfs_for_freq(pm_ctx->pdev, - pm_conc_connection_list[0].freq) || - wlan_reg_is_dfs_for_freq(pm_ctx->pdev, - pm_conc_connection_list[1].freq))) { + is_dfs_ch && + ((pm_conc_connection_list[0].ch_flagext & + (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) || + (pm_conc_connection_list[1].ch_flagext & + (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)))) { policy_mgr_err("Existing DFS connection, new 3-port DFS connection is not allowed"); status = false; @@ -2651,9 +2637,9 @@ bool policy_mgr_allow_new_home_channel( } else if ((num_connections == 1) && (mcc_to_scc_switch == QDF_MCC_TO_SCC_SWITCH_FORCE_PREFERRED_WITHOUT_DISCONNECTION) && - wlan_reg_is_dfs_for_freq(pm_ctx->pdev, ch_freq) && - wlan_reg_is_dfs_for_freq(pm_ctx->pdev, - pm_conc_connection_list[0].freq)) { + is_dfs_ch && + (pm_conc_connection_list[0].ch_flagext & + (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2))) { policy_mgr_err("Existing DFS connection, new 2-port DFS connection is not allowed"); status = false; @@ -2679,9 +2665,8 @@ bool policy_mgr_is_5g_channel_allowed(struct wlan_objmgr_psoc *psoc, count = policy_mgr_mode_specific_connection_count(psoc, mode, list); qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock); while (index < count) { - if (wlan_reg_is_dfs_for_freq( - pm_ctx->pdev, - pm_conc_connection_list[list[index]].freq) && + if ((pm_conc_connection_list[list[index]].ch_flagext & + (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) && WLAN_REG_IS_5GHZ_CH_FREQ(ch_freq) && (ch_freq != pm_conc_connection_list[list[index]].freq)) { qdf_mutex_release(&pm_ctx->qdf_conc_list_lock); diff --git a/components/cmn_services/policy_mgr/src/wlan_policy_mgr_get_set_utils.c b/components/cmn_services/policy_mgr/src/wlan_policy_mgr_get_set_utils.c index d272b22a96fc..f7af65a4d7e7 100644 --- a/components/cmn_services/policy_mgr/src/wlan_policy_mgr_get_set_utils.c +++ b/components/cmn_services/policy_mgr/src/wlan_policy_mgr_get_set_utils.c @@ -1507,9 +1507,8 @@ bool policy_mgr_is_sap_p2pgo_on_dfs(struct wlan_objmgr_psoc *psoc) PM_SAP_MODE, list); while (index < count) { - if (wlan_reg_is_dfs_for_freq( - pm_ctx->pdev, - pm_conc_connection_list[list[index]].freq)){ + if (pm_conc_connection_list[list[index]].ch_flagext & + (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) { qdf_mutex_release(&pm_ctx->qdf_conc_list_lock); return true; } @@ -1520,9 +1519,8 @@ bool policy_mgr_is_sap_p2pgo_on_dfs(struct wlan_objmgr_psoc *psoc) list); index = 0; while (index < count) { - if (wlan_reg_is_dfs_for_freq( - pm_ctx->pdev, - pm_conc_connection_list[list[index]].freq)){ + if (pm_conc_connection_list[list[index]].ch_flagext & + (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) { qdf_mutex_release(&pm_ctx->qdf_conc_list_lock); return true; } @@ -1850,7 +1848,8 @@ QDF_STATUS policy_mgr_incr_connection_count( policy_mgr_get_bw(conn_table_entry.chan_width), conn_table_entry.mac_id, chain_mask, - nss, vdev_id, true, update_conn); + nss, vdev_id, true, update_conn, + conn_table_entry.ch_flagext); policy_mgr_debug("Add at idx:%d vdev %d mac=%d", conn_index, vdev_id, conn_table_entry.mac_id); @@ -1905,6 +1904,8 @@ QDF_STATUS policy_mgr_decr_connection_count(struct wlan_objmgr_psoc *psoc, pm_conc_connection_list[next_conn_index].original_nss; pm_conc_connection_list[conn_index].in_use = pm_conc_connection_list[next_conn_index].in_use; + pm_conc_connection_list[conn_index].ch_flagext = + pm_conc_connection_list[next_conn_index].ch_flagext; conn_index++; next_conn_index++; } @@ -2176,6 +2177,8 @@ bool policy_mgr_is_concurrency_allowed(struct wlan_objmgr_psoc *psoc, struct policy_mgr_psoc_priv_obj *pm_ctx; bool sta_sap_scc_on_dfs_chan; uint32_t sta_freq; + enum channel_state chan_state; + bool is_dfs_ch = false; pm_ctx = policy_mgr_get_context(psoc); if (!pm_ctx) { @@ -2198,9 +2201,15 @@ bool policy_mgr_is_concurrency_allowed(struct wlan_objmgr_psoc *psoc, } if (ch_freq) { + chan_state = wlan_reg_get_5g_bonded_channel_state_for_freq( + pm_ctx->pdev, ch_freq, + policy_mgr_get_ch_width(bw)); + if (chan_state == CHANNEL_STATE_DFS) + is_dfs_ch = true; /* don't allow 3rd home channel on same MAC */ if (!policy_mgr_allow_new_home_channel(psoc, mode, ch_freq, - num_connections)) + num_connections, + is_dfs_ch)) goto done; /* @@ -2230,7 +2239,7 @@ bool policy_mgr_is_concurrency_allowed(struct wlan_objmgr_psoc *psoc, if (!sta_sap_scc_on_dfs_chan && ((mode == PM_P2P_GO_MODE) || (mode == PM_SAP_MODE))) { - if (wlan_reg_is_dfs_for_freq(pm_ctx->pdev, ch_freq)) + if (is_dfs_ch) match = policy_mgr_disallow_mcc(psoc, ch_freq); } @@ -3188,7 +3197,7 @@ void policy_mgr_dump_connection_status_info(struct wlan_objmgr_psoc *psoc) qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock); for (i = 0; i < MAX_NUMBER_OF_CONC_CONNECTIONS; i++) { - policy_mgr_debug("%d: use:%d vdev:%d mode:%d mac:%d freq:%d orig chainmask:%d orig nss:%d bw:%d", + 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", i, pm_conc_connection_list[i].in_use, pm_conc_connection_list[i].vdev_id, pm_conc_connection_list[i].mode, @@ -3196,7 +3205,8 @@ void policy_mgr_dump_connection_status_info(struct wlan_objmgr_psoc *psoc) pm_conc_connection_list[i].freq, pm_conc_connection_list[i].chain_mask, pm_conc_connection_list[i].original_nss, - pm_conc_connection_list[i].bw); + pm_conc_connection_list[i].bw, + pm_conc_connection_list[i].ch_flagext); } qdf_mutex_release(&pm_ctx->qdf_conc_list_lock); } diff --git a/components/cmn_services/policy_mgr/src/wlan_policy_mgr_i.h b/components/cmn_services/policy_mgr/src/wlan_policy_mgr_i.h index 85ef6c1fc21c..f22ba692f28c 100644 --- a/components/cmn_services/policy_mgr/src/wlan_policy_mgr_i.h +++ b/components/cmn_services/policy_mgr/src/wlan_policy_mgr_i.h @@ -25,6 +25,7 @@ #include "qdf_lock.h" #include "qdf_defer.h" #include "wlan_reg_services_api.h" +#include "cds_ieee80211_common_i.h" #define DBS_OPPORTUNISTIC_TIME 5 @@ -446,6 +447,25 @@ QDF_STATUS policy_mgr_get_old_and_new_hw_index( struct wlan_objmgr_psoc *psoc, uint32_t *old_hw_mode_index, uint32_t *new_hw_mode_index); + +/** + * policy_mgr_update_conc_list() - Update the concurrent connection list + * @conn_index: Connection index + * @mode: Mode + * @ch_freq: channel frequency + * @bw: Bandwidth + * @mac: Mac id + * @chain_mask: Chain mask + * @vdev_id: vdev id + * @in_use: Flag to indicate if the index is in use or not + * @update_conn: Flag to indicate if mode change event should + * be sent or not + * @ch_flagext: channel state flags + * + * Updates the index value of the concurrent connection list + * + * Return: None + */ void policy_mgr_update_conc_list(struct wlan_objmgr_psoc *psoc, uint32_t conn_index, enum policy_mgr_con_mode mode, @@ -456,7 +476,9 @@ void policy_mgr_update_conc_list(struct wlan_objmgr_psoc *psoc, uint32_t original_nss, uint32_t vdev_id, bool in_use, - bool update_conn); + bool update_conn, + uint16_t ch_flagext); + void policy_mgr_store_and_del_conn_info(struct wlan_objmgr_psoc *psoc, enum policy_mgr_con_mode mode, bool all_matching_cxn_to_del, @@ -559,6 +581,7 @@ QDF_STATUS policy_mgr_get_channel_list(struct wlan_objmgr_psoc *psoc, * @mode: Connection mode * @ch_freq: channel frequency on which new connection is coming up * @num_connections: number of current connections + * @is_dfs_ch: DFS channel or not * * When a new connection is about to come up check if current * concurrency combination including the new connection is @@ -568,7 +591,7 @@ QDF_STATUS policy_mgr_get_channel_list(struct wlan_objmgr_psoc *psoc, */ bool policy_mgr_allow_new_home_channel( struct wlan_objmgr_psoc *psoc, enum policy_mgr_con_mode mode, - uint32_t ch_freq, uint32_t num_connections); + uint32_t ch_freq, uint32_t num_connections, bool is_dfs_ch); /** * policy_mgr_is_5g_channel_allowed() - check if 5g channel is allowed diff --git a/core/mac/src/pe/lim/lim_utils.c b/core/mac/src/pe/lim/lim_utils.c index 121c27a247da..3fac2d37ec78 100644 --- a/core/mac/src/pe/lim/lim_utils.c +++ b/core/mac/src/pe/lim/lim_utils.c @@ -8397,6 +8397,8 @@ QDF_STATUS lim_set_ch_phy_mode(struct wlan_objmgr_vdev *vdev, uint8_t dot11mode) uint16_t bw_val; enum reg_wifi_band band; uint8_t band_mask; + enum channel_state ch_state; + uint32_t start_ch_freq; mlme_obj = wlan_vdev_mlme_get_cmpt_obj(vdev); if (!mlme_obj) { @@ -8484,9 +8486,18 @@ QDF_STATUS lim_set_ch_phy_mode(struct wlan_objmgr_vdev *vdev, uint8_t dot11mode) des_chan->ch_flagext = 0; if (wlan_reg_is_dfs_for_freq(mac_ctx->pdev, des_chan->ch_freq)) des_chan->ch_flagext |= IEEE80211_CHAN_DFS; - if (des_chan->ch_cfreq2 && - wlan_reg_is_dfs_for_freq(mac_ctx->pdev, des_chan->ch_cfreq2)) - des_chan->ch_flagext |= IEEE80211_CHAN_DFS_CFREQ2; + if (des_chan->ch_cfreq2) { + if (CH_WIDTH_80P80MHZ == des_chan->ch_width) + start_ch_freq = des_chan->ch_cfreq2 - 30; + else + start_ch_freq = des_chan->ch_freq; + + ch_state = wlan_reg_get_5g_bonded_channel_state_for_freq( + mac_ctx->pdev, start_ch_freq, + des_chan->ch_width); + if (CHANNEL_STATE_DFS == ch_state) + des_chan->ch_flagext |= IEEE80211_CHAN_DFS_CFREQ2; + } chan_mode = wma_chan_phy_mode(des_chan->ch_freq, ch_width, dot11mode); diff --git a/core/wma/inc/wma.h b/core/wma/inc/wma.h index 2dd012ecebcf..91758a36fb1c 100644 --- a/core/wma/inc/wma.h +++ b/core/wma/inc/wma.h @@ -793,6 +793,7 @@ struct wma_txrx_node { struct roam_synch_frame_ind roam_synch_frame_ind; bool is_waiting_for_key; uint32_t ch_freq; + uint16_t ch_flagext; struct sir_roam_scan_stats *roam_scan_stats_req; struct wma_invalid_peer_params invalid_peers[INVALID_PEER_MAX_NUM]; uint8_t invalid_peer_idx; diff --git a/core/wma/src/wma_dev_if.c b/core/wma/src/wma_dev_if.c index 3aa66fd7eac2..39546ca35905 100644 --- a/core/wma/src/wma_dev_if.c +++ b/core/wma/src/wma_dev_if.c @@ -2895,6 +2895,7 @@ QDF_STATUS wma_vdev_pre_start(uint8_t vdev_id, bool restart) intr[vdev_id].mhz = des_chan->ch_freq; intr[vdev_id].chan_width = des_chan->ch_width; intr[vdev_id].ch_freq = des_chan->ch_freq; + intr[vdev_id].ch_flagext = des_chan->ch_flagext; /* * If the channel has DFS set, flip on radar reporting. diff --git a/core/wma/src/wma_utils.c b/core/wma/src/wma_utils.c index d26c98e63c7d..5aadf61a48c7 100644 --- a/core/wma/src/wma_utils.c +++ b/core/wma/src/wma_utils.c @@ -3415,6 +3415,7 @@ QDF_STATUS wma_get_connection_info(uint8_t vdev_id, conn_table_entry->mhz = wma_conn_table_entry->mhz; conn_table_entry->sub_type = wma_conn_table_entry->sub_type; conn_table_entry->type = wma_conn_table_entry->type; + conn_table_entry->ch_flagext = wma_conn_table_entry->ch_flagext; return QDF_STATUS_SUCCESS; }