summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAgrawal Ashish <ashishka@codeaurora.org>2016-08-18 13:24:32 +0530
committerGerrit - the friendly Code Review server <code-review@localhost>2016-09-28 10:14:15 -0700
commit6563461fa71120d7bf4d40baaa3228f2396fd3d3 (patch)
treecb769c5244e6f7c0333266b8c2617a735e0679e5
parent727ffac40b6f71d4393f9c73934ebcf1f4d0542e (diff)
qcacld-3.0: Implement vendor command for ACS policy
qcacld-2.0 to qcacld-3.0 propagation Add support for vendor command which informs the driver about the ACS policy. QCA_NL80211_VENDOR_SUBCMD_ACS_POLICY is used to inform driver about ACS policies. QCA_WLAN_VENDOR_ATTR_ACS_DFS_MODE attribute tells if DFS channel should be enabled or disabled in ACS. QCA_WLAN_VENDOR_ATTR_ACS_CHANNEL attribute provides channel number to SAP module to skip ACS and use this channel as operating channel. Change-Id: I1ba69ed8fdf1c56a90e857054c725b830293d6bf CRs-Fixed: 997433
-rw-r--r--core/hdd/inc/wlan_hdd_main.h12
-rw-r--r--core/hdd/src/wlan_hdd_cfg80211.c129
-rw-r--r--core/hdd/src/wlan_hdd_cfg80211.h34
-rw-r--r--core/hdd/src/wlan_hdd_hostapd.c12
-rw-r--r--core/hdd/src/wlan_hdd_main.c25
-rw-r--r--core/sap/inc/sap_api.h15
-rw-r--r--core/sap/src/sap_ch_select.c7
-rw-r--r--core/sap/src/sap_internal.h1
-rw-r--r--core/sap/src/sap_module.c2
9 files changed, 234 insertions, 3 deletions
diff --git a/core/hdd/inc/wlan_hdd_main.h b/core/hdd/inc/wlan_hdd_main.h
index e0dfae71a240..3c3954f69764 100644
--- a/core/hdd/inc/wlan_hdd_main.h
+++ b/core/hdd/inc/wlan_hdd_main.h
@@ -1224,6 +1224,16 @@ enum driver_modules_status {
DRIVER_MODULES_CLOSED
};
+/**
+ * struct acs_dfs_policy - Define ACS policies
+ * @acs_dfs_mode: Dfs mode enabled/disabled.
+ * @acs_channel: pre defined channel to avoid ACS.
+ */
+struct acs_dfs_policy {
+ enum dfs_mode acs_dfs_mode;
+ uint8_t acs_channel;
+};
+
/** Adapter structure definition */
struct hdd_context_s {
@@ -1495,6 +1505,7 @@ struct hdd_context_s {
bool stop_modules_in_progress;
bool start_modules_in_progress;
bool update_mac_addr_to_fw;
+ struct acs_dfs_policy acs_policy;
};
/*---------------------------------------------------------------------------
@@ -1848,4 +1859,5 @@ static inline void hdd_enable_fastpath(struct hdd_config *hdd_cfg,
#endif
void hdd_wlan_update_target_info(hdd_context_t *hdd_ctx, void *context);
+enum sap_acs_dfs_mode wlan_hdd_get_dfs_mode(enum dfs_mode mode);
#endif /* end #if !defined(WLAN_HDD_MAIN_H) */
diff --git a/core/hdd/src/wlan_hdd_cfg80211.c b/core/hdd/src/wlan_hdd_cfg80211.c
index 837b9a090427..d45d371a37bd 100644
--- a/core/hdd/src/wlan_hdd_cfg80211.c
+++ b/core/hdd/src/wlan_hdd_cfg80211.c
@@ -74,6 +74,8 @@
#include "wlan_hdd_nan.h"
#include <wlan_hdd_ipa.h>
#include "wlan_logging_sock_svc.h"
+#include "sap_api.h"
+
#ifdef FEATURE_WLAN_EXTSCAN
#include "wlan_hdd_ext_scan.h"
@@ -142,6 +144,11 @@
#define HDD_CHANNEL_14 14
+#define IS_DFS_MODE_VALID(mode) ((mode >= DFS_MODE_NONE && \
+ mode <= DFS_MODE_DEPRIORITIZE))
+#define IS_CHANNEL_VALID(channel) ((channel >= 0 && channel < 15) \
+ || (channel >= 36 && channel <= 184))
+
#define MAX_TXPOWER_SCALE 4
#define CDS_MAX_FEATURE_SET 8
@@ -1330,7 +1337,10 @@ static int wlan_hdd_cfg80211_start_acs(hdd_adapter_t *adapter)
int status;
sap_config = &adapter->sessionCtx.ap.sapConfig;
- sap_config->channel = AUTO_CHANNEL_SELECT;
+ if (hdd_ctx->acs_policy.acs_channel)
+ sap_config->channel = hdd_ctx->acs_policy.acs_channel;
+ else
+ sap_config->channel = AUTO_CHANNEL_SELECT;
status = wlan_hdd_sap_cfg_dfs_override(adapter);
if (status < 0) {
@@ -6790,6 +6800,115 @@ wlan_hdd_sap_config_policy[QCA_WLAN_VENDOR_ATTR_SAP_CONFIG_MAX + 1] = {
[QCA_WLAN_VENDOR_ATTR_SAP_CONFIG_CHANNEL] = {.type = NLA_U8 },
};
+static const struct nla_policy
+wlan_hdd_set_acs_dfs_config_policy[QCA_WLAN_VENDOR_ATTR_ACS_DFS_MAX + 1] = {
+ [QCA_WLAN_VENDOR_ATTR_ACS_DFS_MODE] = {.type = NLA_U8 },
+ [QCA_WLAN_VENDOR_ATTR_ACS_CHANNEL_HINT] = {.type = NLA_U8 },
+};
+
+/**
+ * __wlan_hdd_cfg80211_acs_dfs_mode() - set ACS DFS mode and channel
+ * @wiphy: Pointer to wireless phy
+ * @wdev: Pointer to wireless device
+ * @data: Pointer to data
+ * @data_len: Length of @data
+ *
+ * This function parses the incoming NL vendor command data attributes and
+ * updates the SAP context about channel_hint and DFS mode.
+ * If channel_hint is set, SAP will choose that channel
+ * as operating channel.
+ *
+ * If DFS mode is enabled, driver will include DFS channels
+ * in ACS else driver will skip DFS channels.
+ *
+ * Return: 0 on success, negative errno on failure
+ */
+static int
+__wlan_hdd_cfg80211_acs_dfs_mode(struct wiphy *wiphy,
+ struct wireless_dev *wdev,
+ const void *data, int data_len)
+{
+ hdd_context_t *hdd_ctx = wiphy_priv(wiphy);
+ struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_ACS_DFS_MAX + 1];
+ int ret;
+ struct acs_dfs_policy *acs_policy;
+ int mode = DFS_MODE_NONE;
+ int channel_hint = 0;
+
+ ENTER_DEV(wdev->netdev);
+
+ if (QDF_GLOBAL_FTM_MODE == hdd_get_conparam()) {
+ hdd_err("Command not allowed in FTM mode");
+ return -EINVAL;
+ }
+
+ ret = wlan_hdd_validate_context(hdd_ctx);
+ if (0 != ret)
+ return ret;
+
+ if (nla_parse(tb, QCA_WLAN_VENDOR_ATTR_ACS_DFS_MAX,
+ data, data_len,
+ wlan_hdd_set_acs_dfs_config_policy)) {
+ hdd_err("invalid attr");
+ return -EINVAL;
+ }
+
+ acs_policy = &hdd_ctx->acs_policy;
+ /*
+ * SCM sends this attribute to restrict SAP from choosing
+ * DFS channels from ACS.
+ */
+ if (tb[QCA_WLAN_VENDOR_ATTR_ACS_DFS_MODE])
+ mode = nla_get_u8(tb[QCA_WLAN_VENDOR_ATTR_ACS_DFS_MODE]);
+
+ if (!IS_DFS_MODE_VALID(mode)) {
+ hdd_err("attr acs dfs mode is not valid");
+ return -EINVAL;
+ }
+ acs_policy->acs_dfs_mode = mode;
+
+ /*
+ * SCM sends this attribute to provide an active channel,
+ * to skip redundant ACS between drivers, and save driver start up time
+ */
+ if (tb[QCA_WLAN_VENDOR_ATTR_ACS_CHANNEL_HINT])
+ channel_hint = nla_get_u8(
+ tb[QCA_WLAN_VENDOR_ATTR_ACS_CHANNEL_HINT]);
+
+ if (!IS_CHANNEL_VALID(channel_hint)) {
+ hdd_err("acs channel is not valid");
+ return -EINVAL;
+ }
+ acs_policy->acs_channel = channel_hint;
+
+ return 0;
+}
+
+/**
+ * wlan_hdd_cfg80211_acs_dfs_mode() - Wrapper to set ACS DFS mode
+ * @wiphy: wiphy structure pointer
+ * @wdev: Wireless device structure pointer
+ * @data: Pointer to the data received
+ * @data_len: Length of @data
+ *
+ * This function parses the incoming NL vendor command data attributes and
+ * updates the SAP context about channel_hint and DFS mode.
+ *
+ * Return: 0 on success; errno on failure
+ */
+static int wlan_hdd_cfg80211_acs_dfs_mode(struct wiphy *wiphy,
+ struct wireless_dev *wdev,
+ const void *data, int data_len)
+{
+ int ret;
+
+ cds_ssr_protect(__func__);
+ ret = __wlan_hdd_cfg80211_acs_dfs_mode(wiphy, wdev, data, data_len);
+ cds_ssr_unprotect(__func__);
+
+ return ret;
+}
+
/**
* __wlan_hdd_cfg80211_sap_configuration_set() - ask driver to restart SAP if
* SAP is on unsafe channel.
@@ -7818,6 +7937,14 @@ const struct wiphy_vendor_command hdd_wiphy_vendor_commands[] = {
},
{
.info.vendor_id = QCA_NL80211_VENDOR_ID,
+ .info.subcmd = QCA_NL80211_VENDOR_SUBCMD_ACS_POLICY,
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV |
+ WIPHY_VENDOR_CMD_NEED_NETDEV |
+ WIPHY_VENDOR_CMD_NEED_RUNNING,
+ .doit = wlan_hdd_cfg80211_acs_dfs_mode
+ },
+ {
+ .info.vendor_id = QCA_NL80211_VENDOR_ID,
.info.subcmd = QCA_NL80211_VENDOR_SUBCMD_SET_SAP_CONFIG,
.flags = WIPHY_VENDOR_CMD_NEED_WDEV |
WIPHY_VENDOR_CMD_NEED_NETDEV |
diff --git a/core/hdd/src/wlan_hdd_cfg80211.h b/core/hdd/src/wlan_hdd_cfg80211.h
index 8910c89ff5e5..d7a08553be80 100644
--- a/core/hdd/src/wlan_hdd_cfg80211.h
+++ b/core/hdd/src/wlan_hdd_cfg80211.h
@@ -419,6 +419,7 @@ enum qca_nl80211_vendor_subcmds {
QCA_NL80211_VENDOR_SUBCMD_SET_TXPOWER_SCALE = 109,
/* Tx power scaling in db subcommands */
QCA_NL80211_VENDOR_SUBCMD_SET_TXPOWER_SCALE_DECR_DB = 115,
+ QCA_NL80211_VENDOR_SUBCMD_ACS_POLICY = 116,
QCA_NL80211_VENDOR_SUBCMD_SET_SAP_CONFIG = 118,
QCA_NL80211_VENDOR_SUBCMD_TSF = 119,
QCA_NL80211_VENDOR_SUBCMD_WISA = 120,
@@ -2755,6 +2756,39 @@ enum qca_vendor_attr_txpower_scale_decr_db {
};
/**
+ * enum dfs_mode - state of DFS mode
+ * @DFS_MODE_NONE: DFS mode attribute is none
+ * @DFS_MODE_ENABLE: DFS mode is enabled
+ * @DFS_MODE_DISABLE: DFS mode is disabled
+ * @DFS_MODE_DEPRIORITIZE: Deprioritize DFS channels in scanning
+ */
+enum dfs_mode {
+ DFS_MODE_NONE,
+ DFS_MODE_ENABLE,
+ DFS_MODE_DISABLE,
+ DFS_MODE_DEPRIORITIZE
+};
+
+/**
+ * enum qca_wlan_vendor_attr_acs_config - Config params for ACS
+ * @QCA_WLAN_VENDOR_ATTR_ACS_MODE_INVALID: Invalid
+ * @QCA_WLAN_VENDOR_ATTR_ACS_DFS_MODE: Dfs mode for ACS
+ * QCA_WLAN_VENDOR_ATTR_ACS_CHANNEL_HINT: channel_hint for ACS
+ * QCA_WLAN_VENDOR_ATTR_ACS_DFS_AFTER_LAST: after_last
+ * QCA_WLAN_VENDOR_ATTR_ACS_DFS_MAX: max attribute
+ */
+enum qca_wlan_vendor_attr_acs_config {
+ QCA_WLAN_VENDOR_ATTR_ACS_MODE_INVALID = 0,
+ QCA_WLAN_VENDOR_ATTR_ACS_DFS_MODE,
+ QCA_WLAN_VENDOR_ATTR_ACS_CHANNEL_HINT,
+
+ QCA_WLAN_VENDOR_ATTR_ACS_DFS_AFTER_LAST,
+ QCA_WLAN_VENDOR_ATTR_ACS_DFS_MAX =
+ QCA_WLAN_VENDOR_ATTR_ACS_DFS_AFTER_LAST - 1,
+
+};
+
+/**
* enum qca_wlan_vendor_attr_sap_config - config params for sap configuration
* @QCA_WLAN_VENDOR_ATTR_SAP_CONFIG_INVALID: invalid
* @QCA_WLAN_VENDOR_ATTR_SAP_CONFIG_CHANNEL: Channel on which SAP should start
diff --git a/core/hdd/src/wlan_hdd_hostapd.c b/core/hdd/src/wlan_hdd_hostapd.c
index 40403ff3d8c8..2d427064e918 100644
--- a/core/hdd/src/wlan_hdd_hostapd.c
+++ b/core/hdd/src/wlan_hdd_hostapd.c
@@ -5595,6 +5595,7 @@ QDF_STATUS hdd_init_ap_mode(hdd_adapter_t *pAdapter)
int ret;
enum tQDF_ADAPTER_MODE mode;
uint32_t session_id = CSR_SESSION_ID_INVALID;
+ enum dfs_mode acs_dfs_mode;
ENTER();
@@ -5605,6 +5606,11 @@ QDF_STATUS hdd_init_ap_mode(hdd_adapter_t *pAdapter)
}
pAdapter->sessionCtx.ap.sapContext = sapContext;
+ pAdapter->sessionCtx.ap.sapConfig.channel =
+ pHddCtx->acs_policy.acs_channel;
+ acs_dfs_mode = pHddCtx->acs_policy.acs_dfs_mode;
+ pAdapter->sessionCtx.ap.sapConfig.acs_dfs_mode =
+ wlan_hdd_get_dfs_mode(acs_dfs_mode);
if (pAdapter->device_mode == QDF_P2P_GO_MODE) {
mode = QDF_P2P_GO_MODE;
@@ -6921,6 +6927,8 @@ int wlan_hdd_cfg80211_start_bss(hdd_adapter_t *pHostapdAdapter,
bool MFPCapable = false;
bool MFPRequired = false;
uint16_t prev_rsn_length = 0;
+ enum dfs_mode mode;
+
ENTER();
if (cds_is_connection_in_progress()) {
@@ -6952,6 +6960,10 @@ int wlan_hdd_cfg80211_start_bss(hdd_adapter_t *pHostapdAdapter,
pConfig->enOverLapCh = iniConfig->gEnableOverLapCh;
pConfig->dtim_period = pBeacon->dtim_period;
+ if (pHddCtx->acs_policy.acs_channel)
+ pConfig->channel = pHddCtx->acs_policy.acs_channel;
+ mode = pHddCtx->acs_policy.acs_dfs_mode;
+ pConfig->acs_dfs_mode = wlan_hdd_get_dfs_mode(mode);
hdd_info("****pConfig->dtim_period=%d***",
pConfig->dtim_period);
diff --git a/core/hdd/src/wlan_hdd_main.c b/core/hdd/src/wlan_hdd_main.c
index d7e2dd46a402..d51d9a44bcdb 100644
--- a/core/hdd/src/wlan_hdd_main.c
+++ b/core/hdd/src/wlan_hdd_main.c
@@ -9194,6 +9194,31 @@ int hdd_update_config(hdd_context_t *hdd_ctx)
return ret;
}
+/**
+ * wlan_hdd_get_dfs_mode() - get ACS DFS mode
+ * @mode : cfg80211 DFS mode
+ *
+ * Return: return SAP ACS DFS mode else return ACS_DFS_MODE_NONE
+ */
+enum sap_acs_dfs_mode wlan_hdd_get_dfs_mode(enum dfs_mode mode)
+{
+ switch (mode) {
+ case DFS_MODE_ENABLE:
+ return ACS_DFS_MODE_ENABLE;
+ break;
+ case DFS_MODE_DISABLE:
+ return ACS_DFS_MODE_DISABLE;
+ break;
+ case DFS_MODE_DEPRIORITIZE:
+ return ACS_DFS_MODE_DEPRIORITIZE;
+ break;
+ default:
+ hdd_err("ACS dfs mode is NONE");
+ return ACS_DFS_MODE_NONE;
+ }
+}
+
+
/* Register the module init/exit functions */
module_init(hdd_module_init);
module_exit(hdd_module_exit);
diff --git a/core/sap/inc/sap_api.h b/core/sap/inc/sap_api.h
index 60b97cca6da2..d9f06b8bf7c3 100644
--- a/core/sap/inc/sap_api.h
+++ b/core/sap/inc/sap_api.h
@@ -508,6 +508,20 @@ enum vendor_ie_access_policy {
ACCESS_POLICY_DONOT_RESPOND_IF_IE_IS_PRESENT,
};
+/*
+ * enum sap_acs_dfs_mode- state of DFS mode
+ * @ACS_DFS_MODE_NONE: DFS mode attribute is not valid
+ * @ACS_DFS_MODE_ENABLE: DFS mode is enabled
+ * @ACS_DFS_MODE_DISABLE: DFS mode is disabled
+ * @ACS_DFS_MODE_DEPRIORITIZE: Deprioritize DFS channels in scanning
+ */
+enum sap_acs_dfs_mode {
+ ACS_DFS_MODE_NONE,
+ ACS_DFS_MODE_ENABLE,
+ ACS_DFS_MODE_DISABLE,
+ ACS_DFS_MODE_DEPRIORITIZE
+};
+
typedef struct sap_Config {
tSap_SSIDInfo_t SSIDinfo;
eCsrPhyMode SapHw_mode; /* Wireless Mode */
@@ -577,6 +591,7 @@ typedef struct sap_Config {
uint8_t ampdu_size;
tSirMacRateSet supp_rate_set;
tSirMacRateSet extended_rate_set;
+ enum sap_acs_dfs_mode acs_dfs_mode;
} tsap_Config_t;
#ifdef FEATURE_WLAN_AP_AP_ACS_OPTIMIZE
diff --git a/core/sap/src/sap_ch_select.c b/core/sap/src/sap_ch_select.c
index 0f488b99bdfa..b4a54dd5adab 100644
--- a/core/sap/src/sap_ch_select.c
+++ b/core/sap/src/sap_ch_select.c
@@ -586,7 +586,8 @@ bool sap_chan_sel_init(tHalHandle halHandle,
#endif
sme_cfg_get_int(halHandle, WNI_CFG_DFS_MASTER_ENABLED,
&dfs_master_cap_enabled);
- if (dfs_master_cap_enabled == 0)
+ if (dfs_master_cap_enabled == 0 ||
+ ACS_DFS_MODE_DISABLE == pSapCtx->dfs_mode)
include_dfs_ch = false;
/* Fill the channel number in the spectrum in the operating freq band */
@@ -1949,7 +1950,6 @@ static uint8_t sap_select_channel_no_scan_result(tHalHandle hal,
if ((ch_type == CHANNEL_STATE_DISABLE) ||
(ch_type == CHANNEL_STATE_INVALID))
continue;
-
if ((!dfs_master_cap_enabled) &&
(CHANNEL_STATE_DFS == ch_type)) {
QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
@@ -1957,6 +1957,9 @@ static uint8_t sap_select_channel_no_scan_result(tHalHandle hal,
__func__, safe_channels[i].channelNumber);
continue;
}
+ if ((sap_ctx->dfs_mode == ACS_DFS_MODE_DISABLE) &&
+ (CHANNEL_STATE_DFS == ch_type))
+ continue;
if (safe_channels[i].isSafe == true) {
QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
diff --git a/core/sap/src/sap_internal.h b/core/sap/src/sap_internal.h
index dc52e2fe304c..22608eff91cc 100644
--- a/core/sap/src/sap_internal.h
+++ b/core/sap/src/sap_internal.h
@@ -270,6 +270,7 @@ typedef struct sSapContext {
uint8_t beacon_tx_rate;
tSirMacRateSet supp_rate_set;
tSirMacRateSet extended_rate_set;
+ enum sap_acs_dfs_mode dfs_mode;
} *ptSapContext;
/*----------------------------------------------------------------------------
diff --git a/core/sap/src/sap_module.c b/core/sap/src/sap_module.c
index 653871ecacf8..457fcf9ecf47 100644
--- a/core/sap/src/sap_module.c
+++ b/core/sap/src/sap_module.c
@@ -647,6 +647,7 @@ wlansap_set_scan_acs_channel_params(tsap_Config_t *pconfig,
/* Channel selection is auto or configured */
psap_ctx->channel = pconfig->channel;
+ psap_ctx->dfs_mode = pconfig->acs_dfs_mode;
#ifdef FEATURE_WLAN_MCC_TO_SCC_SWITCH
psap_ctx->cc_switch_mode = pconfig->cc_switch_mode;
#endif
@@ -810,6 +811,7 @@ QDF_STATUS wlansap_start_bss(void *pCtx, /* pwextCtx */
/* Channel selection is auto or configured */
pSapCtx->channel = pConfig->channel;
+ pSapCtx->dfs_mode = pConfig->acs_dfs_mode;
pSapCtx->ch_params.ch_width = pConfig->ch_params.ch_width;
pSapCtx->ch_params.center_freq_seg0 =
pConfig->ch_params.center_freq_seg0;