summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHanumantha Reddy Pothula <c_hpothu@qti.qualcomm.com>2016-05-12 18:54:57 +0530
committerAnjaneedevi Kapparapu <akappa@codeaurora.org>2016-05-24 19:10:17 +0530
commitaafc3b94ac8bf65a490b86fd85b7546fe58752bf (patch)
treeb08cbd2386cefceaac8b65161b96b2c47afe71f0
parentb82a62373995a33255b1029d109d87d581ff423c (diff)
qcacld-2.0: Restart SAP on receiving channel avoidance indication
Previously, when Host receives channel avoidance indication it calls netif_carrier_off() and as part of carrier clear framework used to receive an indication and thereby it performs SAP restart, so that SAP comes in safe channel. But in latest code, framework doesn't receive any indication as part of carrier clear, causing SAP not to restart and thereby operate on unsafe channel. Hence, when Host receives channel avoidance indication, do STOP/START BSS, so that SAP comes in safe channel. Change-Id: I05a57d7f64c9f775afb7f591f1b6e08ae7cfdfaa CRs-Fixed: 1015265
-rw-r--r--CORE/HDD/inc/wlan_hdd_cfg.h6
-rw-r--r--CORE/HDD/inc/wlan_hdd_hostapd.h27
-rw-r--r--CORE/HDD/inc/wlan_hdd_main.h5
-rw-r--r--CORE/HDD/src/wlan_hdd_assoc.c22
-rw-r--r--CORE/HDD/src/wlan_hdd_cfg.c10
-rw-r--r--CORE/HDD/src/wlan_hdd_cfg80211.c1
-rw-r--r--CORE/HDD/src/wlan_hdd_main.c33
7 files changed, 84 insertions, 20 deletions
diff --git a/CORE/HDD/inc/wlan_hdd_cfg.h b/CORE/HDD/inc/wlan_hdd_cfg.h
index 168c907f0760..77bcc2bd4733 100644
--- a/CORE/HDD/inc/wlan_hdd_cfg.h
+++ b/CORE/HDD/inc/wlan_hdd_cfg.h
@@ -3825,6 +3825,11 @@ enum dot11p_mode {
#define CFG_TGT_GTX_USR_CFG_MAX (32)
#define CFG_TGT_GTX_USR_CFG_DEFAULT (32)
+#define CFG_CH_AVOID_SAP_RESTART_NAME "sap_ch_avoid_restart"
+#define CFG_CH_AVOID_SAP_RESTART_MIN (0)
+#define CFG_CH_AVOID_SAP_RESTART_MAX (1)
+#define CFG_CH_AVOID_SAP_RESTART_DEFAULT (0)
+
/*---------------------------------------------------------------------------
Type declarations
-------------------------------------------------------------------------*/
@@ -4583,6 +4588,7 @@ struct hdd_config {
/* parameter to control GTX */
uint32_t tgt_gtx_usr_cfg;
+ bool sap_restrt_ch_avoid;
};
typedef struct hdd_config hdd_config_t;
diff --git a/CORE/HDD/inc/wlan_hdd_hostapd.h b/CORE/HDD/inc/wlan_hdd_hostapd.h
index 8fe456aadf52..1e18dbf533bc 100644
--- a/CORE/HDD/inc/wlan_hdd_hostapd.h
+++ b/CORE/HDD/inc/wlan_hdd_hostapd.h
@@ -173,16 +173,18 @@ hdd_change_sta_conn_pending_status(hdd_context_t *hdd_ctx,
static inline bool
hdd_is_sap_restart_required(hdd_context_t *hdd_ctx)
{
- bool status;
+ bool status = false;
spin_lock(&hdd_ctx->sap_update_info_lock);
- status = hdd_ctx->is_sap_restart_required;
+ if (!hdd_ctx->is_ch_avoid_in_progress)
+ status = hdd_ctx->is_sap_restart_required;
spin_unlock(&hdd_ctx->sap_update_info_lock);
return status;
}
/**
* hdd_change_sap_restart_required_status() - This function will change the
- * value of is_sap_restart_required
+ * value of is_sap_restart_required
+ *
* @hdd_ctx: pointer to hdd context
* @value: value to set
*
@@ -199,4 +201,23 @@ hdd_change_sap_restart_required_status(hdd_context_t *hdd_ctx,
spin_unlock(&hdd_ctx->sap_update_info_lock);
}
+/**
+ * hdd_change_ch_avoidance_status() - update is_ch_avoid_in_progress flag
+ *
+ * @hdd_ctx: pointer to hdd context
+ * @value: value to set
+ *
+ * This function will change the value of is_ch_avoid_in_progress
+ *
+ * Return: none
+ */
+static inline void
+hdd_change_ch_avoidance_status(hdd_context_t *hdd_ctx,
+ bool value)
+{
+ spin_lock(&hdd_ctx->sap_update_info_lock);
+ hdd_ctx->is_ch_avoid_in_progress = value;
+ spin_unlock(&hdd_ctx->sap_update_info_lock);
+}
+
#endif // end #if !defined( WLAN_HDD_HOSTAPD_H )
diff --git a/CORE/HDD/inc/wlan_hdd_main.h b/CORE/HDD/inc/wlan_hdd_main.h
index 73dd9f1f8463..700b5caa2668 100644
--- a/CORE/HDD/inc/wlan_hdd_main.h
+++ b/CORE/HDD/inc/wlan_hdd_main.h
@@ -1720,6 +1720,8 @@ struct hdd_context_s
struct work_struct sap_start_work;
bool is_sap_restart_required;
+ bool is_ch_avoid_in_progress;
+
bool is_sta_connection_pending;
spinlock_t sap_update_info_lock;
spinlock_t sta_update_info_lock;
@@ -2221,4 +2223,7 @@ static inline void wlan_hdd_restart_sap(hdd_adapter_t *ap_adapter)
int hdd_reassoc(hdd_adapter_t *pAdapter, const tANI_U8 *bssid,
const tANI_U8 channel, const handoff_src src);
+
+void hdd_sap_restart_handle(struct work_struct *work);
+
#endif // end #if !defined( WLAN_HDD_MAIN_H )
diff --git a/CORE/HDD/src/wlan_hdd_assoc.c b/CORE/HDD/src/wlan_hdd_assoc.c
index bcdf5cb8c195..76b5ac7ff83c 100644
--- a/CORE/HDD/src/wlan_hdd_assoc.c
+++ b/CORE/HDD/src/wlan_hdd_assoc.c
@@ -1609,7 +1609,7 @@ void hdd_PerformRoamSetKeyComplete(hdd_adapter_t *pAdapter)
*
* Return: void.
*/
-static void hdd_sap_restart_handle(struct work_struct *work)
+void hdd_sap_restart_handle(struct work_struct *work)
{
hdd_adapter_t *sap_adapter;
hdd_context_t *hdd_ctx = container_of(work,
@@ -1628,9 +1628,15 @@ static void hdd_sap_restart_handle(struct work_struct *work)
vos_ssr_unprotect(__func__);
return;
}
- wlan_hdd_start_sap(sap_adapter);
- hdd_change_sap_restart_required_status(hdd_ctx, false);
+ if (hdd_ctx->is_ch_avoid_in_progress) {
+ sap_adapter->sessionCtx.ap.sapConfig.channel = AUTO_CHANNEL_SELECT;
+ wlan_hdd_restart_sap(sap_adapter);
+ hdd_change_ch_avoidance_status(hdd_ctx, false);
+ } else {
+ wlan_hdd_start_sap(sap_adapter);
+ hdd_change_sap_restart_required_status(hdd_ctx, false);
+ }
vos_ssr_unprotect(__func__);
}
@@ -2242,9 +2248,13 @@ static eHalStatus hdd_AssociationCompletionHandler( hdd_adapter_t *pAdapter, tCs
* creating workqueue then our main thread might go to sleep which
* is not acceptable.
*/
- vos_init_work(&pHddCtx->sap_start_work,
- hdd_sap_restart_handle);
- schedule_work(&pHddCtx->sap_start_work);
+
+ /*
+ * If channel avoidance is intiated, don't schedule the work.
+ * Channel avoidance takes care restarting SAP.
+ */
+ if (true == hdd_is_sap_restart_required(pHddCtx))
+ schedule_work(&pHddCtx->sap_start_work);
}
diff --git a/CORE/HDD/src/wlan_hdd_cfg.c b/CORE/HDD/src/wlan_hdd_cfg.c
index 6130a7f54faa..a4ae6863208a 100644
--- a/CORE/HDD/src/wlan_hdd_cfg.c
+++ b/CORE/HDD/src/wlan_hdd_cfg.c
@@ -4575,6 +4575,13 @@ REG_TABLE_ENTRY g_registry_table[] =
CFG_TGT_GTX_USR_CFG_DEFAULT,
CFG_TGT_GTX_USR_CFG_MIN,
CFG_TGT_GTX_USR_CFG_MAX),
+
+ REG_VARIABLE(CFG_CH_AVOID_SAP_RESTART_NAME, WLAN_PARAM_Integer,
+ hdd_config_t, sap_restrt_ch_avoid,
+ VAR_FLAGS_OPTIONAL | VAR_FLAGS_RANGE_CHECK_ASSUME_DEFAULT,
+ CFG_CH_AVOID_SAP_RESTART_DEFAULT,
+ CFG_CH_AVOID_SAP_RESTART_MIN,
+ CFG_CH_AVOID_SAP_RESTART_MAX)
};
@@ -5389,6 +5396,9 @@ void print_hdd_cfg(hdd_context_t *pHddCtx)
CFG_TGT_GTX_USR_CFG_NAME,
pHddCtx->cfg_ini->tgt_gtx_usr_cfg);
+ hddLog(LOG2, "Name = [%s] Value = [%u]",
+ CFG_CH_AVOID_SAP_RESTART_NAME,
+ pHddCtx->cfg_ini->sap_restrt_ch_avoid);
hdd_ndp_print_ini_config(pHddCtx);
}
diff --git a/CORE/HDD/src/wlan_hdd_cfg80211.c b/CORE/HDD/src/wlan_hdd_cfg80211.c
index 65d0d9a08164..d003774ef817 100644
--- a/CORE/HDD/src/wlan_hdd_cfg80211.c
+++ b/CORE/HDD/src/wlan_hdd_cfg80211.c
@@ -14347,6 +14347,7 @@ static int __wlan_hdd_cfg80211_stop_ap (struct wiphy *wiphy,
vos_flush_work(&pHddCtx->sap_start_work);
VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_WARN,
FL("Canceled the pending restart work"));
+ hdd_change_ch_avoidance_status(pHddCtx, false);
hdd_change_sap_restart_required_status(pHddCtx, false);
}
diff --git a/CORE/HDD/src/wlan_hdd_main.c b/CORE/HDD/src/wlan_hdd_main.c
index 0ceb47f54faf..b732458e2f78 100644
--- a/CORE/HDD/src/wlan_hdd_main.c
+++ b/CORE/HDD/src/wlan_hdd_main.c
@@ -865,7 +865,7 @@ static void hdd_smps_force_mode_cb(void *context,
}
-#if defined (FEATURE_WLAN_MCC_TO_SCC_SWITCH) || defined (FEATURE_WLAN_STA_AP_MODE_DFS_DISABLE)
+#if defined (FEATURE_WLAN_MCC_TO_SCC_SWITCH) || defined (FEATURE_WLAN_STA_AP_MODE_DFS_DISABLE) || defined (FEATURE_WLAN_CH_AVOID)
/**
* wlan_hdd_restart_sap() - This function is used to restart SAP in driver internally
* @ap_adapter: - Pointer to SAP hdd_adapter_t structure
@@ -11529,6 +11529,7 @@ VOS_STATUS hdd_stop_adapter( hdd_context_t *pHddCtx, hdd_adapter_t *pAdapter,
vos_flush_work(&pHddCtx->sap_start_work);
VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO_HIGH,
FL("Canceled the pending SAP restart work"));
+ hdd_change_ch_avoidance_status(pHddCtx, false);
hdd_change_sap_restart_required_status(pHddCtx, false);
}
//Any softap specific cleanup here...
@@ -14977,6 +14978,7 @@ int hdd_wlan_startup(struct device *dev, v_VOID_t *hif_sc)
/* Initialize the RoC Request queue and work. */
hdd_list_init((&pHddCtx->hdd_roc_req_q), MAX_ROC_REQ_QUEUE_ENTRY);
vos_init_delayed_work(&pHddCtx->rocReqWork, wlan_hdd_roc_request_dequeue);
+ vos_init_work(&pHddCtx->sap_start_work, hdd_sap_restart_handle);
if (pHddCtx->cfg_ini->dot11p_mode == WLAN_HDD_11P_STANDALONE) {
/* Create only 802.11p interface */
@@ -16549,8 +16551,6 @@ void hdd_unsafe_channel_restart_sap(hdd_context_t *hdd_ctx)
hdd_adapter_t *adapter;
VOS_STATUS status;
- static bool restart_sap_in_progress = false;
-
status = hdd_get_front_adapter(hdd_ctx, &adapter_node);
while (NULL != adapter_node && VOS_STATUS_SUCCESS == status) {
adapter = adapter_node->pAdapter;
@@ -16583,22 +16583,33 @@ void hdd_unsafe_channel_restart_sap(hdd_context_t *hdd_ctx)
channel_loop++) {
if (((hdd_ctx->unsafe_channel_list[channel_loop] ==
adapter->sessionCtx.ap.operatingChannel)) &&
+ (false == hdd_ctx->is_ch_avoid_in_progress) &&
(adapter->sessionCtx.ap.sapConfig.acs_cfg.
- acs_mode == true) &&
- !restart_sap_in_progress) {
+ acs_mode == true)) {
+ hdd_change_ch_avoidance_status(hdd_ctx, true);
+
+ vos_flush_work(
+ &hdd_ctx->sap_start_work);
+
+ /*
+ * current operating channel
+ * is un-safe channel, restart driver
+ */
hddLog(LOGE,
- FL("Restarting SAP due to unsafe channel"));
+ FL("Restarting SAP due to unsafe channel"));
+
wlan_hdd_send_svc_nlink_msg(
hdd_ctx->radio_index,
WLAN_SVC_LTE_COEX_IND,
NULL,
0);
- restart_sap_in_progress = true;
- /*
- * current operating channel
- * is un-safe channel, restart driver
- */
+
hdd_hostapd_stop(adapter->dev);
+
+ if (hdd_ctx->cfg_ini->sap_restrt_ch_avoid)
+ schedule_work(
+ &hdd_ctx->sap_start_work);
+
return;
}
}