wlan: Fix race conditions while configuring mc/bc filter
multicast/broadcast filter is configured when the device goes into
suspend. Fix race conditions that can occur while configuring the filter.
Change-Id: I90aa40cf67b7335222adadc1aac821427100ab42
CRs-Fixed: 540698
diff --git a/CORE/HDD/src/wlan_hdd_assoc.c b/CORE/HDD/src/wlan_hdd_assoc.c
index 54e479d..223ed4c 100644
--- a/CORE/HDD/src/wlan_hdd_assoc.c
+++ b/CORE/HDD/src/wlan_hdd_assoc.c
@@ -2490,7 +2490,14 @@
hdd_conf_mcastbcast_filter(pHddCtx, FALSE);
pHddCtx->configuredMcastBcastFilter =
pHddCtx->sus_res_mcastbcast_filter;
+ pHddCtx->sus_res_mcastbcast_filter_valid = VOS_FALSE;
+ hddLog(VOS_TRACE_LEVEL_INFO,
+ "offload: disassociation happening, restoring configuredMcastBcastFilter");
+ hddLog(VOS_TRACE_LEVEL_INFO,"McastBcastFilter = %d",
+ pHddCtx->configuredMcastBcastFilter);
+ hddLog(VOS_TRACE_LEVEL_INFO,
+ "offload: already called mcastbcast filter");
(WLAN_HDD_GET_CTX(pAdapter))->hdd_mcastbcast_filter_set = FALSE;
}
#ifdef WLAN_FEATURE_PACKET_FILTERING
diff --git a/CORE/HDD/src/wlan_hdd_cfg80211.c b/CORE/HDD/src/wlan_hdd_cfg80211.c
index aa797eb..bf7f604 100644
--- a/CORE/HDD/src/wlan_hdd_cfg80211.c
+++ b/CORE/HDD/src/wlan_hdd_cfg80211.c
@@ -7008,6 +7008,9 @@
(eConnectionState_Associated ==
(WLAN_HDD_GET_STATION_CTX_PTR(pAdapter))->conn_info.connState))
{
+
+ hddLog(VOS_TRACE_LEVEL_INFO,
+ "offload: in cfg80211_set_power_mgmt, calling arp offload");
vos_status = hdd_conf_arp_offload(pAdapter, TRUE);
if (!VOS_IS_STATUS_SUCCESS(vos_status))
{
diff --git a/CORE/HDD/src/wlan_hdd_early_suspend.c b/CORE/HDD/src/wlan_hdd_early_suspend.c
index 922b1a4..6e092f4 100644
--- a/CORE/HDD/src/wlan_hdd_early_suspend.c
+++ b/CORE/HDD/src/wlan_hdd_early_suspend.c
@@ -737,15 +737,21 @@
hddLog(VOS_TRACE_LEVEL_INFO, "%s: Enabled \n", __func__);
- if((HDD_MCASTBCASTFILTER_FILTER_ALL_BROADCAST ==
- pHddCtx->configuredMcastBcastFilter) ||
- (HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST_BROADCAST ==
- pHddCtx->configuredMcastBcastFilter))
+ if (((HDD_MCASTBCASTFILTER_FILTER_ALL_BROADCAST ==
+ pHddCtx->sus_res_mcastbcast_filter) ||
+ (HDD_MCASTBCASTFILTER_FILTER_ALL_MULTICAST_BROADCAST ==
+ pHddCtx->sus_res_mcastbcast_filter)) &&
+ (VOS_TRUE == pHddCtx->sus_res_mcastbcast_filter_valid))
{
offLoadRequest.enableOrDisable =
- SIR_OFFLOAD_ARP_AND_BCAST_FILTER_ENABLE;
+ SIR_OFFLOAD_ARP_AND_BCAST_FILTER_ENABLE;
+ hddLog(VOS_TRACE_LEVEL_INFO,
+ "offload: inside arp offload conditional check");
}
-
+
+ hddLog(VOS_TRACE_LEVEL_INFO, "offload: arp filter programmed = %d",
+ offLoadRequest.enableOrDisable);
+
//converting u32 to IPV4 address
for(i = 0 ; i < 4; i++)
{
@@ -871,8 +877,16 @@
tpSirWlanSuspendParam wlanSuspendParam =
vos_mem_malloc(sizeof(tSirWlanSuspendParam));
- pHddCtx->sus_res_mcastbcast_filter =
- pHddCtx->configuredMcastBcastFilter;
+ if (VOS_FALSE == pHddCtx->sus_res_mcastbcast_filter_valid) {
+ pHddCtx->sus_res_mcastbcast_filter =
+ pHddCtx->configuredMcastBcastFilter;
+ pHddCtx->sus_res_mcastbcast_filter_valid = VOS_TRUE;
+ hddLog(VOS_TRACE_LEVEL_INFO, "offload: hdd_conf_suspend_ind");
+ hddLog(VOS_TRACE_LEVEL_INFO, "configuredMCastBcastFilter saved = %d",
+ pHddCtx->configuredMcastBcastFilter);
+
+ }
+
if(NULL == wlanSuspendParam)
{
@@ -881,7 +895,7 @@
return;
}
- hddLog(VOS_TRACE_LEVEL_INFO,
+ hddLog(VOS_TRACE_LEVEL_INFO,
"%s: send wlan suspend indication", __func__);
if((pHddCtx->cfg_ini->nEnableSuspend == WLAN_MAP_SUSPEND_TO_MCAST_BCAST_FILTER))
@@ -941,6 +955,12 @@
pHddCtx->configuredMcastBcastFilter =
pHddCtx->sus_res_mcastbcast_filter;
+ pHddCtx->sus_res_mcastbcast_filter_valid = VOS_FALSE;
+
+ hddLog(VOS_TRACE_LEVEL_INFO,
+ "offload: in hdd_conf_resume_ind, restoring configuredMcastBcastFilter");
+ hddLog(VOS_TRACE_LEVEL_INFO, "configuredMcastBcastFilter = %d",
+ pHddCtx->configuredMcastBcastFilter);
#ifdef WLAN_FEATURE_PACKET_FILTERING
@@ -1066,7 +1086,19 @@
spin_lock(&pHddCtx->filter_lock);
if((newState == BMPS) && pHddCtx->hdd_wlan_suspended) {
spin_unlock(&pHddCtx->filter_lock);
- pHddCtx->sus_res_mcastbcast_filter = pHddCtx->configuredMcastBcastFilter;
+ if (VOS_FALSE == pHddCtx->sus_res_mcastbcast_filter_valid) {
+ pHddCtx->sus_res_mcastbcast_filter =
+ pHddCtx->configuredMcastBcastFilter;
+ pHddCtx->sus_res_mcastbcast_filter_valid = VOS_TRUE;
+
+ hddLog(VOS_TRACE_LEVEL_INFO, "offload: callback to associated");
+ hddLog(VOS_TRACE_LEVEL_INFO, "saving configuredMcastBcastFilter = %d",
+ pHddCtx->configuredMcastBcastFilter);
+ hddLog(VOS_TRACE_LEVEL_INFO,
+ "offload: calling hdd_conf_mcastbcast_filter");
+
+ }
+
hdd_conf_mcastbcast_filter(pHddCtx, TRUE);
if(pHddCtx->hdd_mcastbcast_filter_set != TRUE)
hddLog(VOS_TRACE_LEVEL_ERROR, "%s: Not able to set mcast/bcast filter ", __func__);