qcacld-3.0: Add 3 home channel check for 4th active vdev

Add 3 home channel check for 4th active vdev. Do not allow
if in DBS and SBS modes 4th freq can lead to 3 home channel.

And optimize 3rd active vdev APIs.

Change-Id: I2d1ef437fc5c69b1255863c85a2b9f4efa24fa58
CRs-Fixed: 3172212
This commit is contained in:
Abhishek Singh
2022-04-08 10:40:07 +05:30
committed by Madan Koyyalamudi
parent 8a7ddd5f40
commit 1ae6c6e85b
3 changed files with 269 additions and 62 deletions

View File

@@ -2816,9 +2816,27 @@ bool policy_mgr_is_dbs_scan_allowed(struct wlan_objmgr_psoc *psoc);
*/ */
bool policy_mgr_is_hw_sbs_capable(struct wlan_objmgr_psoc *psoc); bool policy_mgr_is_hw_sbs_capable(struct wlan_objmgr_psoc *psoc);
/**
* policy_mgr_2_freq_always_on_same_mac() - Function to check whether both the
* input frequencies are on same mac in all supported mode/freq range
*
* @psoc: Pointer to Psoc
* @freq_1: Frequency 1 to check
* @freq_2: Frequency 2 to check
*
* This Function check whether both the input frequency exist in the same mac
* in all supported mode/freq range
*
* Return:True if both the frequency exist on the same mac in all supported
* mode/freq range.
*
*/
bool policy_mgr_2_freq_always_on_same_mac(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq_1, qdf_freq_t freq_2);
/** /**
* policy_mgr_are_2_freq_on_same_mac() - Function to check whether both the * policy_mgr_are_2_freq_on_same_mac() - Function to check whether both the
* input frequencies are on same mac * input frequencies are on same mac in current freq range
* *
* @psoc: Pointer to Psoc * @psoc: Pointer to Psoc
* @freq_1: Frequency 1 to check * @freq_1: Frequency 1 to check
@@ -2834,9 +2852,30 @@ policy_mgr_are_2_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq_1, qdf_freq_t freq_1,
qdf_freq_t freq_2); qdf_freq_t freq_2);
/**
* policy_mgr_3_freq_always_on_same_mac() - Function to check whether all three
* input frequencies will always in same mac in all supported mode/freq range
*
* @psoc: Pointer to Psoc
* @freq_1: Frequency 1 to check
* @freq_2: Frequency 2 to check
* @freq_3: Frequency 3 to check
*
* This Function check whether all three input frequencies exist in the same
* mac in all supported mode/freq range.
*
* Return:True if all three frequency exist on the same mac in all supported
* mode/freq range
*
*/
bool
policy_mgr_3_freq_always_on_same_mac(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq_1, qdf_freq_t freq_2,
qdf_freq_t freq_3);
/** /**
* policy_mgr_are_3_freq_on_same_mac() - Function to check whether all three * policy_mgr_are_3_freq_on_same_mac() - Function to check whether all three
* input frequencies are in same mac * input frequencies are in same mac in current freq range
* *
* @psoc: Pointer to Psoc * @psoc: Pointer to Psoc
* @freq_1: Frequency 1 to check * @freq_1: Frequency 1 to check
@@ -2854,6 +2893,34 @@ policy_mgr_are_3_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq_1, qdf_freq_t freq_2, qdf_freq_t freq_1, qdf_freq_t freq_2,
qdf_freq_t freq_3); qdf_freq_t freq_3);
/**
* policy_mgr_allow_4th_new_freq() - Function to check whether 4th freq can
* be allowed wthout leading to 3 home freq on same mac
*
* @psoc: Pointer to Psoc
* @freq1: Frequency 1
* @freq2: Frequency 2
* @freq3: Frequency 3
* @new_ch_freq: freq to check with reference to freq1 freq2 and freq3
*
* Return:True if all 4 freq doesnt cause 3 home frequency on same mac
*
*/
#ifdef FEATURE_FOURTH_CONNECTION
bool
policy_mgr_allow_4th_new_freq(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq1, qdf_freq_t freq2,
qdf_freq_t freq3, qdf_freq_t new_ch_freq);
#else
static inline bool
policy_mgr_allow_4th_new_freq(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq1, qdf_freq_t freq2,
qdf_freq_t freq3, qdf_freq_t new_ch_freq)
{
return false;
}
#endif
/** /**
* policy_mgr_are_sbs_chan() - Function to check whether both the * policy_mgr_are_sbs_chan() - Function to check whether both the
* input frequency are in SBS frequency range * input frequency are in SBS frequency range

View File

@@ -3411,7 +3411,7 @@ bool policy_mgr_allow_same_mac_diff_freq(struct wlan_objmgr_psoc *psoc,
policy_mgr_rl_debug("don't allow 3rd home channel on same MAC"); policy_mgr_rl_debug("don't allow 3rd home channel on same MAC");
allow = false; allow = false;
} }
} else if (policy_mgr_are_3_freq_on_same_mac(psoc, ch_freq, } else if (policy_mgr_3_freq_always_on_same_mac(psoc, ch_freq,
pm_conc_connection_list[0].freq, pm_conc_connection_list[0].freq,
pm_conc_connection_list[1].freq)) { pm_conc_connection_list[1].freq)) {
policy_mgr_rl_debug("don't allow 3rd home channel on same MAC"); policy_mgr_rl_debug("don't allow 3rd home channel on same MAC");
@@ -3454,7 +3454,7 @@ bool policy_mgr_allow_same_mac_same_freq(struct wlan_objmgr_psoc *psoc,
* and therefore a 3rd connection with the * and therefore a 3rd connection with the
* same MAC is possible. * same MAC is possible.
*/ */
} else if (policy_mgr_are_2_freq_on_same_mac(psoc, ch_freq, } else if (policy_mgr_2_freq_always_on_same_mac(psoc, ch_freq,
pm_conc_connection_list[0].freq) && pm_conc_connection_list[0].freq) &&
!policy_mgr_is_3rd_conn_on_same_band_allowed(psoc, mode)) { !policy_mgr_is_3rd_conn_on_same_band_allowed(psoc, mode)) {
policy_mgr_rl_debug("don't allow 3rd home channel on same MAC for sta+multi-AP"); policy_mgr_rl_debug("don't allow 3rd home channel on same MAC for sta+multi-AP");
@@ -3464,23 +3464,9 @@ bool policy_mgr_allow_same_mac_same_freq(struct wlan_objmgr_psoc *psoc,
return allow; return allow;
} }
/**
* policy_mgr_allow_new_home_channel() - Check for allowed number of
* home channels
* @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
* allowed or not based on the HW capability
*
* Return: True/False
*/
bool policy_mgr_allow_new_home_channel( bool policy_mgr_allow_new_home_channel(
struct wlan_objmgr_psoc *psoc, enum policy_mgr_con_mode mode, struct wlan_objmgr_psoc *psoc, enum policy_mgr_con_mode mode,
uint32_t ch_freq, uint32_t num_connections, bool is_dfs_ch) qdf_freq_t ch_freq, uint32_t num_connections, bool is_dfs_ch)
{ {
bool status = true; bool status = true;
struct policy_mgr_psoc_priv_obj *pm_ctx; struct policy_mgr_psoc_priv_obj *pm_ctx;
@@ -3497,11 +3483,17 @@ bool policy_mgr_allow_new_home_channel(
QDF_MCC_TO_SCC_SWITCH_FORCE_PREFERRED_WITHOUT_DISCONNECTION; QDF_MCC_TO_SCC_SWITCH_FORCE_PREFERRED_WITHOUT_DISCONNECTION;
qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock); qdf_mutex_acquire(&pm_ctx->qdf_conc_list_lock);
if (num_connections == 2) { if (num_connections == 3) {
status = policy_mgr_allow_4th_new_freq(psoc,
pm_conc_connection_list[0].freq,
pm_conc_connection_list[1].freq,
pm_conc_connection_list[2].freq,
ch_freq);
} else if (num_connections == 2) {
/* No SCC or MCC combination is allowed with / on DFS channel */ /* No SCC or MCC combination is allowed with / on DFS channel */
on_same_mac = policy_mgr_are_2_freq_on_same_mac(psoc, on_same_mac = policy_mgr_2_freq_always_on_same_mac(psoc,
pm_conc_connection_list[0].freq, pm_conc_connection_list[0].freq,
pm_conc_connection_list[1].freq); pm_conc_connection_list[1].freq);
if (force_switch_without_dis && is_dfs_ch && if (force_switch_without_dis && is_dfs_ch &&
((pm_conc_connection_list[0].ch_flagext & ((pm_conc_connection_list[0].ch_flagext &
(IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) || (IEEE80211_CHAN_DFS | IEEE80211_CHAN_DFS_CFREQ2)) ||
@@ -3533,7 +3525,7 @@ bool policy_mgr_allow_new_home_channel(
*/ */
if ((pm_conc_connection_list[0].mode != PM_NAN_DISC_MODE) && if ((pm_conc_connection_list[0].mode != PM_NAN_DISC_MODE) &&
(mode != PM_NAN_DISC_MODE)) (mode != PM_NAN_DISC_MODE))
status = policy_mgr_are_2_freq_on_same_mac(psoc, status = policy_mgr_2_freq_always_on_same_mac(psoc,
ch_freq, ch_freq,
pm_conc_connection_list[0].freq); pm_conc_connection_list[0].freq);
} }
@@ -3742,7 +3734,7 @@ policy_mgr_check_force_scc_two_connection(struct wlan_objmgr_psoc *psoc,
return; return;
} }
if (!policy_mgr_are_3_freq_on_same_mac(psoc, sap_ch_freq, if (!policy_mgr_3_freq_always_on_same_mac(psoc, sap_ch_freq,
pm_conc_connection_list[0].freq, pm_conc_connection_list[0].freq,
pm_conc_connection_list[1].freq)) { pm_conc_connection_list[1].freq)) {
/* /*

View File

@@ -1361,6 +1361,54 @@ policy_mgr_is_cur_freq_range_sbs(struct wlan_objmgr_psoc *psoc)
return false; return false;
} }
bool policy_mgr_2_freq_always_on_same_mac(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq_1, qdf_freq_t freq_2)
{
struct policy_mgr_psoc_priv_obj *pm_ctx;
struct policy_mgr_freq_range *freq_range;
bool is_dbs_mode_same_mac = true;
bool is_sbs_mode_same_mac = true;
pm_ctx = policy_mgr_get_context(psoc);
if (!pm_ctx)
return false;
/* if HW is not DBS return true*/
if (!policy_mgr_is_hw_dbs_capable(psoc))
return true;
/* Check for DBS mode first */
freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
is_dbs_mode_same_mac =
policy_mgr_are_2_freq_in_freq_range(pm_ctx, freq_range,
freq_1, freq_2);
/*
* if not leading to same mac in dbs mode or SBS not supported no need
* to check further
*/
if (!is_dbs_mode_same_mac ||
!policy_mgr_is_hw_sbs_capable(psoc))
goto skip_sbs;
/* Check for SBS mode */
is_sbs_mode_same_mac =
policy_mgr_are_2_freq_in_sbs_freq_range(pm_ctx, freq_1, freq_2);
skip_sbs:
policy_mgr_debug("freq1 %d freq2 %d: Same mac:: DBS:%d SBS:%d",
freq_1, freq_2, is_dbs_mode_same_mac,
is_sbs_mode_same_mac);
/*
* if in SBS and DBS mode, both is leading to freqs on same mac,
* return true else return false.
*/
if (is_dbs_mode_same_mac && is_sbs_mode_same_mac)
return true;
return false;
}
bool policy_mgr_are_2_freq_on_same_mac(struct wlan_objmgr_psoc *psoc, bool policy_mgr_are_2_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq_1, qdf_freq_t freq_1,
qdf_freq_t freq_2) qdf_freq_t freq_2)
@@ -1380,12 +1428,6 @@ bool policy_mgr_are_2_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
return true; return true;
policy_mgr_rl_debug("freq_1 %d freq_2 %d", freq_1, freq_2); policy_mgr_rl_debug("freq_1 %d freq_2 %d", freq_1, freq_2);
if (!policy_mgr_is_hw_sbs_capable(psoc)) {
/* If not SBS capable but DBS capable */
freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
return policy_mgr_are_2_freq_in_freq_range(pm_ctx, freq_range,
freq_1, freq_2);
}
/* HW is DBS/SBS capable */ /* HW is DBS/SBS capable */
status = policy_mgr_get_current_hw_mode(psoc, &hw_mode); status = policy_mgr_get_current_hw_mode(psoc, &hw_mode);
@@ -1406,19 +1448,10 @@ bool policy_mgr_are_2_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
freq_1, freq_2); freq_1, freq_2);
/* /*
* Current HW is SMM check, if they can lead to SBS or DBS without being * If current HW mode is not DBS/SBS, check if in all supported mode
* in same mac, return true only if Both will lead to same mac * it they will be on same mac
*/ */
if (!policy_mgr_are_2_freq_in_sbs_freq_range(pm_ctx, freq_1, freq_2)) return policy_mgr_2_freq_always_on_same_mac(psoc, freq_1, freq_2);
return false;
/*
* If SBS lead to same mac, check if DBS mode will also lead to same
* mac
*/
freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
return policy_mgr_are_2_freq_in_freq_range(pm_ctx, freq_range,
freq_1, freq_2);
} }
static bool static bool
@@ -1468,6 +1501,57 @@ policy_mgr_are_3_freq_in_sbs_freq_range(struct policy_mgr_psoc_priv_obj *pm_ctx,
freq_1, freq_2, freq_3); freq_1, freq_2, freq_3);
} }
bool
policy_mgr_3_freq_always_on_same_mac(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq_1, qdf_freq_t freq_2,
qdf_freq_t freq_3)
{
struct policy_mgr_psoc_priv_obj *pm_ctx;
struct policy_mgr_freq_range *freq_range;
bool is_dbs_mode_same_mac = true;
bool is_sbs_mode_same_mac = true;
pm_ctx = policy_mgr_get_context(psoc);
if (!pm_ctx)
return false;
/* if HW is not DBS return true*/
if (!policy_mgr_is_hw_dbs_capable(psoc))
return true;
/* Check for DBS mode first */
freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
is_dbs_mode_same_mac =
policy_mgr_are_3_freq_in_freq_range(pm_ctx, freq_range,
freq_1, freq_2, freq_3);
/*
* if not leading to same mac in dbs mode or SBS not supported no need
* to check further
*/
if (!is_dbs_mode_same_mac ||
!policy_mgr_is_hw_sbs_capable(psoc))
goto skip_sbs;
/* Check for SBS mode */
is_sbs_mode_same_mac =
policy_mgr_are_3_freq_in_sbs_freq_range(pm_ctx, freq_1, freq_2,
freq_3);
skip_sbs:
policy_mgr_debug("freq1 %d freq2 %d freq3 %d: Same mac:: DBS:%d SBS:%d",
freq_1, freq_2, freq_3, is_dbs_mode_same_mac,
is_sbs_mode_same_mac);
/*
* if in SBS and DBS mode, both is leading to freqs on same mac,
* return true else return false.
*/
if (is_dbs_mode_same_mac && is_sbs_mode_same_mac)
return true;
return false;
}
bool bool
policy_mgr_are_3_freq_on_same_mac(struct wlan_objmgr_psoc *psoc, policy_mgr_are_3_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq_1, qdf_freq_t freq_2, qdf_freq_t freq_1, qdf_freq_t freq_2,
@@ -1489,13 +1573,6 @@ policy_mgr_are_3_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
policy_mgr_rl_debug("freq_1 %d freq_2 %d freq_3 %d", freq_1, freq_2, policy_mgr_rl_debug("freq_1 %d freq_2 %d freq_3 %d", freq_1, freq_2,
freq_3); freq_3);
if (!policy_mgr_is_hw_sbs_capable(psoc)) {
/* If not SBS capable but DBS capable */
freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
return policy_mgr_are_3_freq_in_freq_range(pm_ctx, freq_range,
freq_1, freq_2,
freq_3);
}
/* HW is DBS/SBS capable, get current HW mode */ /* HW is DBS/SBS capable, get current HW mode */
status = policy_mgr_get_current_hw_mode(psoc, &hw_mode); status = policy_mgr_get_current_hw_mode(psoc, &hw_mode);
@@ -1516,21 +1593,92 @@ policy_mgr_are_3_freq_on_same_mac(struct wlan_objmgr_psoc *psoc,
freq_1, freq_2, freq_1, freq_2,
freq_3); freq_3);
/* /*
* Current HW is SMM check, if they can lead to SBS or DBS without being * If current HW mode is not DBS/SBS, check if in all supported mode
* in same mac, return true only if both will lead to same mac * it they will be on same mac
*/ */
if (!policy_mgr_are_3_freq_in_sbs_freq_range(pm_ctx, freq_1, freq_2, return policy_mgr_3_freq_always_on_same_mac(psoc, freq_1, freq_2,
freq_3)) freq_3);
return false;
/*
* If SBS lead to same mac, check if DBS mode will also lead to same mac
*/
freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
return policy_mgr_are_3_freq_in_freq_range(pm_ctx, freq_range, freq_1,
freq_2, freq_3);
} }
#ifdef FEATURE_FOURTH_CONNECTION
bool
policy_mgr_allow_4th_new_freq(struct wlan_objmgr_psoc *psoc,
qdf_freq_t freq1, qdf_freq_t freq2,
qdf_freq_t freq3, qdf_freq_t new_ch_freq)
{
struct policy_mgr_freq_range *dbs_freq_range;
bool is_dbs_mode_3_home_freq = false;
bool is_sbs_mode_3_home_freq = false;
struct policy_mgr_psoc_priv_obj *pm_ctx;
pm_ctx = policy_mgr_get_context(psoc);
if (!pm_ctx)
return false;
if (!freq1 || !freq2 || !freq3 || !new_ch_freq) {
policy_mgr_info("one or more freq are 0: freq1 %d freq2 %d freq3 %d new_freq %d",
freq1, freq2, freq3, new_ch_freq);
return false;
}
/* Check for DBS mode first */
dbs_freq_range = pm_ctx->hw_mode.freq_range_caps[MODE_DBS];
/*
* If existing freq leading to 3 home channel in DBS mode, check SBS.
* Else check if new_ch_freq can cause 3 home freq with existing 2 home
* freq on same mac.
*/
if (policy_mgr_are_3_freq_in_freq_range(pm_ctx, dbs_freq_range, freq1,
freq2, freq3) ||
policy_mgr_are_3_freq_in_freq_range(pm_ctx, dbs_freq_range, freq1,
freq2, new_ch_freq) ||
policy_mgr_are_3_freq_in_freq_range(pm_ctx, dbs_freq_range, freq1,
freq3, new_ch_freq) ||
policy_mgr_are_3_freq_in_freq_range(pm_ctx, dbs_freq_range, freq2,
freq3, new_ch_freq))
is_dbs_mode_3_home_freq = true;
/*
* if allowed in dbs mode or SBS not supported no need
* to check further
*/
if (!is_dbs_mode_3_home_freq ||
!policy_mgr_is_hw_sbs_capable(psoc))
goto skip_sbs_check;
/* Check for SBS mode */
/*
* If existing freq leading to 3 home channel in SBS mode, skip the
* check. Else check if new_ch_freq can cause 3 home freq with
* existing 2 home home freq on same mac
*/
if (policy_mgr_are_3_freq_in_sbs_freq_range(pm_ctx, freq1,
freq2, freq3) ||
policy_mgr_are_3_freq_in_sbs_freq_range(pm_ctx, freq1, freq2,
new_ch_freq) ||
policy_mgr_are_3_freq_in_sbs_freq_range(pm_ctx, freq1, freq3,
new_ch_freq) ||
policy_mgr_are_3_freq_in_sbs_freq_range(pm_ctx, freq2, freq3,
new_ch_freq))
is_sbs_mode_3_home_freq = true;
skip_sbs_check:
policy_mgr_debug("freq1 %d freq2 %d freq3 %d new_freq %d: leads to 3 home freq:: DBS:%d SBS:%d",
freq1, freq2, freq3, new_ch_freq,
is_dbs_mode_3_home_freq, is_sbs_mode_3_home_freq);
/*
* if in SBS or DBS mode, it can be allowed without leading to 3 home
* freq on same mac, return true.
* Return false only if in both mode it will lead to 3 home freq on same
* mac.
*/
if (!is_dbs_mode_3_home_freq || !is_sbs_mode_3_home_freq)
return true;
return false;
}
#endif
bool policy_mgr_are_sbs_chan(struct wlan_objmgr_psoc *psoc, qdf_freq_t freq_1, bool policy_mgr_are_sbs_chan(struct wlan_objmgr_psoc *psoc, qdf_freq_t freq_1,
qdf_freq_t freq_2) qdf_freq_t freq_2)
{ {