diff --git a/components/action_oui/core/src/wlan_action_oui_parse.c b/components/action_oui/core/src/wlan_action_oui_parse.c index a8f16c84d1..13e007a714 100644 --- a/components/action_oui/core/src/wlan_action_oui_parse.c +++ b/components/action_oui/core/src/wlan_action_oui_parse.c @@ -747,6 +747,9 @@ check_for_vendor_oui_data(struct action_oui_extension *extension, uint8_t i, j, elem_len, data_len; uint8_t data_mask = 0x80; + if (!oui_ptr) + return false; + elem_len = oui_ptr[1]; if (elem_len < extension->oui_length) return false; @@ -857,6 +860,19 @@ check_for_vendor_ap_capabilities(struct action_oui_extension *extension, return true; } +static const uint8_t * +action_oui_get_oui_ptr(struct action_oui_extension *extension, + struct action_oui_search_attr *attr) +{ + if (!attr->ie_data || !attr->ie_length) + return NULL; + + return wlan_get_vendor_ie_ptr_from_oui(extension->oui, + extension->oui_length, + attr->ie_data, + attr->ie_length); +} + bool action_oui_search(struct action_oui_psoc_priv *psoc_priv, struct action_oui_search_attr *attr, @@ -904,10 +920,8 @@ action_oui_search(struct action_oui_psoc_priv *psoc_priv, wildcard_oui = true; } - oui_ptr = wlan_get_vendor_ie_ptr_from_oui(extension->oui, - extension->oui_length, - attr->ie_data, - attr->ie_length); + oui_ptr = action_oui_get_oui_ptr(extension, attr); + if (!oui_ptr && !wildcard_oui) { action_oui_debug("No matching IE found for OUI"); QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_PE, @@ -940,7 +954,7 @@ action_oui_search(struct action_oui_psoc_priv *psoc_priv, goto next; } - action_oui_debug("Vendor AP found for OUI"); + action_oui_debug("Vendor AP/STA found for OUI"); QDF_TRACE_HEX_DUMP(QDF_MODULE_ID_PE, QDF_TRACE_LEVEL_DEBUG, extension->oui, extension->oui_length); qdf_mutex_release(&oui_priv->extension_lock); diff --git a/components/action_oui/dispatcher/inc/wlan_action_oui_public_struct.h b/components/action_oui/dispatcher/inc/wlan_action_oui_public_struct.h index 6056b765c6..817c1836e0 100644 --- a/components/action_oui/dispatcher/inc/wlan_action_oui_public_struct.h +++ b/components/action_oui/dispatcher/inc/wlan_action_oui_public_struct.h @@ -84,6 +84,10 @@ * @ACTION_OUI_CONNECT_1X1: for 1x1 connection only * @ACTION_OUI_ITO_EXTENSION: for extending inactivity time of station * @ACTION_OUI_CCKM_1X1: for TX with CCKM 1x1 only + * @ACTION_OUI_ITO_ALTERNATE: alternate ITO extensions used by firmware + * @ACTION_OUI_SWITCH_TO_11N_MODE: connect in 11n + * @ACTION_OUI_CONNECT_1X1_WITH_1_CHAIN: connect in 1x1 & disable diversity gain + * @ACTION_OUI_DISABLE_AGGRESSIVE_TX: disable aggressive TX in firmware * @ACTION_OUI_MAXIMUM_ID: maximun number of action oui types */ enum action_oui_id { @@ -93,6 +97,7 @@ enum action_oui_id { ACTION_OUI_ITO_ALTERNATE = 3, ACTION_OUI_SWITCH_TO_11N_MODE = 4, ACTION_OUI_CONNECT_1X1_WITH_1_CHAIN = 5, + ACTION_OUI_DISABLE_AGGRESSIVE_TX = 6, ACTION_OUI_MAXIMUM_ID }; diff --git a/components/action_oui/dispatcher/src/wlan_action_oui_ucfg_api.c b/components/action_oui/dispatcher/src/wlan_action_oui_ucfg_api.c index 7a3e38b5f9..f6d31f9191 100644 --- a/components/action_oui/dispatcher/src/wlan_action_oui_ucfg_api.c +++ b/components/action_oui/dispatcher/src/wlan_action_oui_ucfg_api.c @@ -179,8 +179,7 @@ bool ucfg_action_oui_search(struct wlan_objmgr_psoc *psoc, goto exit; } - if (action_id >= ACTION_OUI_MAXIMUM_ID || - !attr->ie_data || !attr->ie_length) { + if (action_id >= ACTION_OUI_MAXIMUM_ID) { action_oui_err("Invalid action_oui id: %u", action_id); goto exit; } diff --git a/core/hdd/inc/hdd_config.h b/core/hdd/inc/hdd_config.h index ce61536e9c..58140b4987 100644 --- a/core/hdd/inc/hdd_config.h +++ b/core/hdd/inc/hdd_config.h @@ -975,6 +975,54 @@ enum hdd_wext_control { "001018 06 02FFF0040000 BC 21 40 001018 06 02FFF0050000 BC 21 40 001018 06 02FFF4050000 BC 21 40", \ "Used to specify action OUIs for 1x1 connection with one Tx/Rx Chain") +/* + * + * gActionOUIDisableAggressiveTX - Used to specify action OUIs to disable + * Aggressive TX feature when operating in softap. + * + * @Default: + * Note: User should strictly add new action OUIs at the end of this + * default value. + * + * Default OUIs: + * + * OUI 1 : FFFFFF + * OUI data Len : 00 + * OUI Data: No data + * OUI data Mask: No data mask + * Info Mask: 2A - Check for mac-addr, HT capability and Band + * Mac-addr: F8:59:71:00:00:00 - first 3 bytes + * Mac-mask: E0 - Match only first 3 bytes of peer mac-addr + * Capabilities: 50 – HT should be enabled, and band should be 2.4GHz + * + * OUI 2 : FFFFFF + * OUI data Len : 00 + * OUI Data: No data + * OUI data Mask: No data mask + * Info Mask: 2A - Check for mac-addr, HT capability and Band + * Mac-addr: 14:AB:C5:00:00:00 - first 3 bytes + * Mac-mask: E0 - Match only first 3 bytes of peer mac-addr + * Capabilities: 50 – HT should be enabled, and band should be 2.4GHz + * + * When operating in Softap mode, this ini is used to specify + * STA (peer) OUIs/mac-addr for which aggressive tx is disabled after + * association is successful. + * + * Related: gEnableActionOUI + * + * Supported Feature: Action OUIs + * + * Usage: External + * + * + */ +#define CFG_ACTION_OUI_DISABLE_AGGRESSIVE_TX CFG_INI_STRING( \ + "gActionOUIDisableAggressiveTX", \ + 0, \ + ACTION_OUI_MAX_STR_LEN, \ + "FFFFFF 00 2A F85971000000 E0 50 FFFFFF 00 2A 14ABC5000000 E0 50", \ + "Used to specify action OUIs to disable aggressive TX") + /* End of action oui inis */ #define CFG_HDD_ALL \ @@ -988,6 +1036,7 @@ enum hdd_wext_control { CFG(CFG_ACTION_OUI_CONNECT_1X1_WITH_1_CHAIN) \ CFG(CFG_ACTION_OUI_ITO_ALTERNATE) \ CFG(CFG_ACTION_OUI_ITO_EXTENSION) \ + CFG(CFG_ACTION_OUI_DISABLE_AGGRESSIVE_TX) \ CFG(CFG_ACTION_OUI_SWITCH_TO_11N_MODE) \ CFG(CFG_BUG_ON_REINIT_FAILURE) \ CFG(CFG_DBS_SCAN_SELECTION) \ diff --git a/core/hdd/src/wlan_hdd_hostapd.c b/core/hdd/src/wlan_hdd_hostapd.c index b8d22d1487..77d785c3b7 100644 --- a/core/hdd/src/wlan_hdd_hostapd.c +++ b/core/hdd/src/wlan_hdd_hostapd.c @@ -85,6 +85,7 @@ #include "wlan_mlme_ucfg_api.h" #include "cfg_ucfg_api.h" #include "wlan_crypto_global_api.h" +#include "wlan_action_oui_ucfg_api.h" #define ACS_SCAN_EXPIRY_TIMEOUT_S 4 @@ -1574,6 +1575,63 @@ hdd_stop_sap_due_to_invalid_channel(struct work_struct *work) cds_ssr_unprotect(__func__); } +/** + * hdd_hostapd_apply_action_oui() - Check for action_ouis to be applied on peers + * @hdd_ctx: pointer to hdd context + * @adapter: pointer to adapter + * @event: assoc complete params + * + * This function is used to check whether aggressive tx should be disabled + * based on the soft-ap configuration and action_oui ini + * gActionOUIDisableAggressiveTX + * + * Return: None + */ +static void +hdd_hostapd_apply_action_oui(struct hdd_context *hdd_ctx, + struct hdd_adapter *adapter, + tSap_StationAssocReassocCompleteEvent *event) +{ + bool found; + uint32_t freq; + tSirMacHTChannelWidth ch_width; + enum sir_sme_phy_mode mode; + struct action_oui_search_attr attr = {0}; + QDF_STATUS status; + + ch_width = event->ch_width; + if (ch_width != eHT_CHANNEL_WIDTH_20MHZ) + return; + + freq = cds_chan_to_freq(event->chan_info.chan_id); + if (WLAN_REG_IS_24GHZ_CH_FREQ(freq)) + attr.enable_2g = true; + else if (WLAN_REG_IS_5GHZ_CH_FREQ(freq)) + attr.enable_5g = true; + else + return; + + mode = event->mode; + if (event->vht_caps.present && mode == SIR_SME_PHY_MODE_VHT) + attr.vht_cap = true; + else if (event->ht_caps.present && mode == SIR_SME_PHY_MODE_HT) + attr.ht_cap = true; + + attr.mac_addr = (uint8_t *)(&event->staMac); + + found = ucfg_action_oui_search(hdd_ctx->psoc, + &attr, + ACTION_OUI_DISABLE_AGGRESSIVE_TX); + if (!found) + return; + + status = sme_set_peer_param(attr.mac_addr, + WMI_PEER_PARAM_DISABLE_AGGRESSIVE_TX, + true, adapter->session_id); + if (QDF_IS_STATUS_ERROR(status)) + hdd_err("Failed to disable aggregation for peer"); +} + QDF_STATUS hdd_hostapd_sap_event_cb(tpSap_Event pSapEvent, void *context) { @@ -2053,6 +2111,8 @@ QDF_STATUS hdd_hostapd_sap_event_cb(tpSap_Event pSapEvent, break; } + hdd_hostapd_apply_action_oui(hdd_ctx, adapter, event); + wrqu.addr.sa_family = ARPHRD_ETHER; memcpy(wrqu.addr.sa_data, &event->staMac, QDF_MAC_ADDR_SIZE); diff --git a/core/hdd/src/wlan_hdd_main.c b/core/hdd/src/wlan_hdd_main.c index d087fc5a81..7d6410e462 100644 --- a/core/hdd/src/wlan_hdd_main.c +++ b/core/hdd/src/wlan_hdd_main.c @@ -9405,6 +9405,10 @@ static void hdd_cfg_params_init(struct hdd_context *hdd_ctx) cfg_get(psoc, CFG_ACTION_OUI_CONNECT_1X1_WITH_1_CHAIN), ACTION_OUI_MAX_STR_LEN); + qdf_str_lcopy(config->action_oui_str[6], + cfg_get(psoc, + CFG_ACTION_OUI_DISABLE_AGGRESSIVE_TX), + ACTION_OUI_MAX_STR_LEN); hdd_init_vc_mode_cfg_bitmap(config, psoc); hdd_init_runtime_pm(config, psoc);