qcacld-3.0: Update subband CCA busy info to HDD
In case of wide band scan request, FW sends subband CCA busy info to host via a new tlv wmi_cca_busy_subband_info added in existing event WMI_CHAN_INFO_EVENTID. Fix is to store CCA busy info coming from FW to HDD context. Change-Id: Ic4b439ed1c270badbe265dc8543dc6d6a1612fab CRs-Fixed: 3469467
This commit is contained in:

committato da
Madan Koyyalamudi

parent
62b5a049d6
commit
076551fd20
@@ -726,6 +726,16 @@ static inline QDF_STATUS wlan_cm_host_roam_start(struct scheduler_msg *msg)
|
||||
}
|
||||
#endif
|
||||
|
||||
/**
|
||||
* wlan_cm_get_associated_ch_width() - get associated channel width
|
||||
* @psoc: psoc pointer
|
||||
* @vdev_id: vdev id
|
||||
*
|
||||
* Return: enum phy_ch_width
|
||||
*/
|
||||
enum phy_ch_width
|
||||
wlan_cm_get_associated_ch_width(struct wlan_objmgr_psoc *psoc, uint8_t vdev_id);
|
||||
|
||||
#ifdef WLAN_FEATURE_ROAM_OFFLOAD
|
||||
/**
|
||||
* wlan_cm_fw_roam_abort_req() - roam abort request handling
|
||||
|
@@ -123,6 +123,12 @@ ucfg_cm_update_session_assoc_ie(struct wlan_objmgr_psoc *psoc,
|
||||
cm_update_session_assoc_ie(psoc, vdev_id, assoc_ie);
|
||||
}
|
||||
|
||||
static inline enum phy_ch_width
|
||||
ucfg_cm_get_associated_ch_width(struct wlan_objmgr_psoc *psoc, uint8_t vdev_id)
|
||||
{
|
||||
return wlan_cm_get_associated_ch_width(psoc, vdev_id);
|
||||
}
|
||||
|
||||
#ifdef WLAN_FEATURE_ROAM_OFFLOAD
|
||||
#ifdef FEATURE_RX_LINKSPEED_ROAM_TRIGGER
|
||||
/**
|
||||
|
@@ -2118,6 +2118,32 @@ QDF_STATUS wlan_cm_update_fils_ft(struct wlan_objmgr_psoc *psoc,
|
||||
}
|
||||
#endif
|
||||
|
||||
enum phy_ch_width
|
||||
wlan_cm_get_associated_ch_width(struct wlan_objmgr_psoc *psoc, uint8_t vdev_id)
|
||||
{
|
||||
struct wlan_objmgr_vdev *vdev;
|
||||
struct mlme_legacy_priv *mlme_priv;
|
||||
enum phy_ch_width ch_width = CH_WIDTH_INVALID;
|
||||
|
||||
vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id,
|
||||
WLAN_MLME_NB_ID);
|
||||
|
||||
if (!vdev) {
|
||||
mlme_err("vdev%d: vdev object is NULL", vdev_id);
|
||||
goto release;
|
||||
}
|
||||
|
||||
mlme_priv = wlan_vdev_mlme_get_ext_hdl(vdev);
|
||||
if (!mlme_priv)
|
||||
goto release;
|
||||
|
||||
ch_width = mlme_priv->connect_info.ch_width_orig;
|
||||
mlme_debug("vdev %d: associated_ch_width:%d", vdev_id, ch_width);
|
||||
release:
|
||||
wlan_objmgr_vdev_release_ref(vdev, WLAN_MLME_NB_ID);
|
||||
return ch_width;
|
||||
}
|
||||
|
||||
#ifdef WLAN_FEATURE_ROAM_OFFLOAD
|
||||
QDF_STATUS
|
||||
wlan_cm_update_roam_scan_scheme_bitmap(struct wlan_objmgr_psoc *psoc,
|
||||
|
@@ -25508,6 +25508,81 @@ static int wlan_hdd_cfg80211_nan_change_conf(struct wiphy *wiphy,
|
||||
}
|
||||
#endif
|
||||
|
||||
/**
|
||||
* wlan_hdd_fill_subband_scan_info - Fill subband channel info
|
||||
* @hdd_ctx: hdd context
|
||||
* @info: struct scan_chan_info
|
||||
* @chan: scan channel info
|
||||
*
|
||||
* update channel info into HDD context on scan done
|
||||
*
|
||||
* Return: None.
|
||||
*/
|
||||
static void wlan_hdd_fill_subband_scan_info(struct hdd_context *hdd_ctx,
|
||||
struct scan_chan_info *info,
|
||||
struct scan_chan_info *chan)
|
||||
{
|
||||
uint8_t idx, info_index, freq_info_num;
|
||||
enum phy_ch_width ch_width;
|
||||
const struct bonded_channel_freq *range = NULL;
|
||||
uint32_t start_freq, end_freq;
|
||||
|
||||
ch_width = ucfg_cm_get_associated_ch_width(hdd_ctx->psoc,
|
||||
info->subband_info.vdev_id);
|
||||
if (ch_width == CH_WIDTH_INVALID) {
|
||||
hdd_debug("vdev %d: Invalid ch width",
|
||||
info->subband_info.vdev_id);
|
||||
return;
|
||||
}
|
||||
|
||||
if (ch_width == CH_WIDTH_20MHZ) {
|
||||
start_freq = info->freq;
|
||||
end_freq = info->freq;
|
||||
} else {
|
||||
range = wlan_reg_get_bonded_chan_entry(info->freq, ch_width, 0);
|
||||
if (!range) {
|
||||
hdd_err("vdev %d: bonded_chan_array is NULL for freq %d, ch_width %d",
|
||||
info->subband_info.vdev_id, info->freq,
|
||||
ch_width);
|
||||
return;
|
||||
}
|
||||
start_freq = range->start_freq;
|
||||
end_freq = range->end_freq;
|
||||
}
|
||||
|
||||
freq_info_num = info->subband_info.num_chan;
|
||||
info_index = 0;
|
||||
|
||||
hdd_debug("vdev %d: freq :%d bw %d, range [%d-%d], num_freq:%d",
|
||||
info->subband_info.vdev_id, info->freq, ch_width, start_freq,
|
||||
end_freq, freq_info_num);
|
||||
|
||||
for (idx = 0; idx < SIR_MAX_NUM_CHANNELS; idx++) {
|
||||
if (chan[idx].freq == 0)
|
||||
continue;
|
||||
|
||||
if (start_freq > end_freq || info_index >= freq_info_num ||
|
||||
info_index >= MAX_WIDE_BAND_SCAN_CHAN)
|
||||
break;
|
||||
|
||||
if (chan[idx].freq == start_freq) {
|
||||
/*update channel info as per cca busy info */
|
||||
info->freq = start_freq;
|
||||
info->rx_clear_count =
|
||||
info->subband_info.cca_busy_subband_info[info_index];
|
||||
|
||||
hdd_update_chan_info(hdd_ctx, &chan[idx], info,
|
||||
info->cmd_flag);
|
||||
|
||||
hdd_debug("updated info for freq:%u rcc:%d at index:%d",
|
||||
chan[idx].freq, chan[idx].rx_clear_count,
|
||||
idx);
|
||||
start_freq += BW_20_MHZ;
|
||||
info_index++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* wlan_hdd_chan_info_cb() - channel info callback
|
||||
* @info: struct scan_chan_info
|
||||
@@ -25532,6 +25607,12 @@ static void wlan_hdd_chan_info_cb(struct scan_chan_info *info)
|
||||
}
|
||||
|
||||
chan = hdd_ctx->chan_info;
|
||||
|
||||
if (info->subband_info.is_wide_band_scan) {
|
||||
wlan_hdd_fill_subband_scan_info(hdd_ctx, info, chan);
|
||||
return;
|
||||
}
|
||||
|
||||
for (idx = 0; idx < SIR_MAX_NUM_CHANNELS; idx++) {
|
||||
if (chan[idx].freq == info->freq) {
|
||||
hdd_update_chan_info(hdd_ctx, &chan[idx], info,
|
||||
|
@@ -4349,6 +4349,24 @@ struct wow_pulse_mode {
|
||||
*/
|
||||
QDF_STATUS umac_send_mb_message_to_mac(void *msg);
|
||||
|
||||
/* Max supported bandwidth is 320Mhz, so max 16 subbands fo 20Mhz */
|
||||
#define MAX_WIDE_BAND_SCAN_CHAN 16
|
||||
|
||||
/**
|
||||
* struct wide_band_scan_chan_info - wide band scan channel info
|
||||
* @vdev_id: vdev id
|
||||
* @num_chan: number of channels (for each subbands fo 20Mhz)
|
||||
* @is_wide_band_scan: wide band scan or not
|
||||
* @cca_busy_subband_info: CCA busy for each possible 20Mhz subbands
|
||||
* of the wideband scan channel
|
||||
*/
|
||||
struct wide_band_scan_chan_info {
|
||||
uint32_t vdev_id;
|
||||
uint8_t num_chan;
|
||||
bool is_wide_band_scan;
|
||||
uint32_t cca_busy_subband_info[MAX_WIDE_BAND_SCAN_CHAN];
|
||||
};
|
||||
|
||||
/**
|
||||
* struct scan_chan_info - channel info
|
||||
* @freq: radio frequence
|
||||
@@ -4358,6 +4376,8 @@ QDF_STATUS umac_send_mb_message_to_mac(void *msg);
|
||||
* @rx_clear_count: rx clear count
|
||||
* @tx_frame_count: TX frame count
|
||||
* @clock_freq: clock frequence MHZ
|
||||
* @cca_busy_subband_info: CCA busy for each possible 20Mhz subbands
|
||||
* of the wideband scan channel
|
||||
*/
|
||||
struct scan_chan_info {
|
||||
uint32_t freq;
|
||||
@@ -4367,6 +4387,7 @@ struct scan_chan_info {
|
||||
uint32_t rx_clear_count;
|
||||
uint32_t tx_frame_count;
|
||||
uint32_t clock_freq;
|
||||
struct wide_band_scan_chan_info subband_info;
|
||||
};
|
||||
|
||||
/**
|
||||
|
@@ -5343,6 +5343,49 @@ wma_vdev_bcn_latency_event_handler(void *handle,
|
||||
}
|
||||
#endif
|
||||
|
||||
static void
|
||||
wma_update_sacn_channel_info_buf(wmi_unified_t wmi_handle,
|
||||
wmi_chan_info_event_fixed_param *event,
|
||||
struct scan_chan_info *buf,
|
||||
wmi_cca_busy_subband_info *cca_info,
|
||||
uint32_t num_tlvs)
|
||||
{
|
||||
uint32_t i;
|
||||
bool is_cca_busy_info;
|
||||
|
||||
buf->tx_frame_count = event->tx_frame_cnt;
|
||||
buf->clock_freq = event->mac_clk_mhz;
|
||||
buf->cmd_flag = event->cmd_flags;
|
||||
buf->freq = event->freq;
|
||||
buf->noise_floor = event->noise_floor;
|
||||
buf->cycle_count = event->cycle_count;
|
||||
buf->rx_clear_count = event->rx_clear_count;
|
||||
|
||||
is_cca_busy_info = wmi_service_enabled(wmi_handle,
|
||||
wmi_service_cca_busy_info_for_each_20mhz);
|
||||
|
||||
if (!is_cca_busy_info || num_tlvs == 0)
|
||||
return;
|
||||
|
||||
wma_debug("is_cca_busy_info: %d, num_tlvs:%d", is_cca_busy_info,
|
||||
num_tlvs);
|
||||
|
||||
if (cca_info && num_tlvs > 0) {
|
||||
buf->subband_info.num_chan = 0;
|
||||
for (i = 0; i < num_tlvs && i < MAX_WIDE_BAND_SCAN_CHAN; i++) {
|
||||
buf->subband_info.cca_busy_subband_info[i] =
|
||||
cca_info->rx_clear_count;
|
||||
wma_debug("cca_info->rx_clear_count:%d",
|
||||
cca_info->rx_clear_count);
|
||||
buf->subband_info.num_chan++;
|
||||
cca_info++;
|
||||
}
|
||||
|
||||
buf->subband_info.is_wide_band_scan = true;
|
||||
buf->subband_info.vdev_id = event->vdev_id;
|
||||
}
|
||||
}
|
||||
|
||||
int wma_chan_info_event_handler(void *handle, uint8_t *event_buf,
|
||||
uint32_t len)
|
||||
{
|
||||
@@ -5356,6 +5399,8 @@ int wma_chan_info_event_handler(void *handle, uint8_t *event_buf,
|
||||
struct wlan_objmgr_vdev *vdev;
|
||||
enum QDF_OPMODE mode;
|
||||
struct scheduler_msg sme_msg = {0};
|
||||
wmi_cca_busy_subband_info *cca_info = NULL;
|
||||
uint32_t num_tlvs = 0;
|
||||
|
||||
if (wma && wma->cds_context)
|
||||
mac = (struct mac_context *)cds_get_context(QDF_MODULE_ID_PE);
|
||||
@@ -5374,18 +5419,6 @@ int wma_chan_info_event_handler(void *handle, uint8_t *event_buf,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
snr_monitor_enabled = wlan_scan_is_snr_monitor_enabled(mac->psoc);
|
||||
if (snr_monitor_enabled && mac->chan_info_cb) {
|
||||
buf.tx_frame_count = event->tx_frame_cnt;
|
||||
buf.clock_freq = event->mac_clk_mhz;
|
||||
buf.cmd_flag = event->cmd_flags;
|
||||
buf.freq = event->freq;
|
||||
buf.noise_floor = event->noise_floor;
|
||||
buf.cycle_count = event->cycle_count;
|
||||
buf.rx_clear_count = event->rx_clear_count;
|
||||
mac->chan_info_cb(&buf);
|
||||
}
|
||||
|
||||
/* Ignore the last channel event data whose command flag is set to 1.
|
||||
* It’s basically an event with empty data only to indicate scan event
|
||||
* completion.
|
||||
@@ -5393,6 +5426,15 @@ int wma_chan_info_event_handler(void *handle, uint8_t *event_buf,
|
||||
if (event->cmd_flags == WMI_CHAN_INFO_END_RESP)
|
||||
return 0;
|
||||
|
||||
snr_monitor_enabled = wlan_scan_is_snr_monitor_enabled(mac->psoc);
|
||||
if (snr_monitor_enabled && mac->chan_info_cb) {
|
||||
cca_info = param_buf->cca_busy_subband_info;
|
||||
num_tlvs = param_buf->num_cca_busy_subband_info;
|
||||
wma_update_sacn_channel_info_buf(wma->wmi_handle, event,
|
||||
&buf, cca_info, num_tlvs);
|
||||
mac->chan_info_cb(&buf);
|
||||
}
|
||||
|
||||
vdev = wlan_objmgr_get_vdev_by_id_from_psoc(wma->psoc, event->vdev_id,
|
||||
WLAN_LEGACY_WMA_ID);
|
||||
|
||||
|
Fai riferimento in un nuovo problema
Block a user