From 89029e4d9e91fa7729515940bc0915cd0968cea5 Mon Sep 17 00:00:00 2001 From: Ashish Kumar Dhanotiya Date: Wed, 25 Sep 2019 11:55:03 +0530 Subject: [PATCH] qcacmn: Send CTL info to firmware In regulatory non-offloads feature, send conformance_test_limit_2G, conformance_test_limit_5G, reg_domain, reg_domain_2G and reg_domain_5G information to firmware using WMI_PDEV_SET_REGDOMAIN_CMDID. If all these attributes are not populated then CTL power limit is not applied by the firmware. Change-Id: I1523ab447aec64ec0af42da32318136f90fd17ca CRs-Fixed: 2518246 --- target_if/regulatory/src/target_if_reg.c | 35 +++++++++ .../lmac_if/inc/wlan_lmac_if_def.h | 3 + .../regulatory/core/src/reg_build_chan_list.c | 77 +++++++++++++++++++ umac/regulatory/core/src/reg_db.c | 65 ++++++++++++++++ umac/regulatory/core/src/reg_db_parser.h | 5 ++ .../inc/reg_services_public_struct.h | 16 ++++ wmi/src/wmi_unified_tlv.c | 5 ++ 7 files changed, 206 insertions(+) diff --git a/target_if/regulatory/src/target_if_reg.c b/target_if/regulatory/src/target_if_reg.c index 59cbe146e4..fdb9e56286 100644 --- a/target_if/regulatory/src/target_if_reg.c +++ b/target_if/regulatory/src/target_if_reg.c @@ -345,6 +345,39 @@ QDF_STATUS tgt_if_regulatory_modify_freq_range(struct wlan_objmgr_psoc *psoc) return QDF_STATUS_SUCCESS; } +#ifdef CONFIG_REG_CLIENT +/** + * tgt_if_regulatory_send_ctl_info() - Send CTL info to firmware + * @psoc: Pointer to psoc + * @params: Pointer to reg control params + * + * Return: QDF_STATUS + */ +static QDF_STATUS +tgt_if_regulatory_send_ctl_info(struct wlan_objmgr_psoc *psoc, + struct reg_ctl_params *params) +{ + wmi_unified_t wmi_handle = get_wmi_unified_hdl_from_psoc(psoc); + + if (!wmi_handle) + return QDF_STATUS_E_FAILURE; + + return wmi_unified_send_regdomain_info_to_fw_cmd(wmi_handle, + params->regd, + params->regd_2g, + params->regd_5g, + params->ctl_2g, + params->ctl_5g); +} +#else +static QDF_STATUS +tgt_if_regulatory_send_ctl_info(struct wlan_objmgr_psoc *psoc, + struct reg_ctl_params *params) +{ + return QDF_STATUS_SUCCESS; +} +#endif + QDF_STATUS target_if_register_regulatory_tx_ops( struct wlan_lmac_if_tx_ops *tx_ops) { @@ -384,5 +417,7 @@ QDF_STATUS target_if_register_regulatory_tx_ops( reg_ops->unregister_ch_avoid_event_handler = tgt_if_regulatory_unregister_ch_avoid_event_handler; + reg_ops->send_ctl_info = tgt_if_regulatory_send_ctl_info; + return QDF_STATUS_SUCCESS; } diff --git a/umac/global_umac_dispatcher/lmac_if/inc/wlan_lmac_if_def.h b/umac/global_umac_dispatcher/lmac_if/inc/wlan_lmac_if_def.h index c1462e1a6c..a9b895ee3a 100644 --- a/umac/global_umac_dispatcher/lmac_if/inc/wlan_lmac_if_def.h +++ b/umac/global_umac_dispatcher/lmac_if/inc/wlan_lmac_if_def.h @@ -725,6 +725,7 @@ struct wlan_lmac_if_ftm_rx_ops { * @unregister_master_handler: pointer to unregister event handler * @register_11d_new_cc_handler: pointer to register 11d cc event handler * @unregister_11d_new_cc_handler: pointer to unregister 11d cc event handler + * @send_ctl_info: call-back function to send CTL info to firmware */ struct wlan_lmac_if_reg_tx_ops { QDF_STATUS (*register_master_handler)(struct wlan_objmgr_psoc *psoc, @@ -753,6 +754,8 @@ struct wlan_lmac_if_reg_tx_ops { struct wlan_objmgr_psoc *psoc, void *arg); QDF_STATUS (*unregister_ch_avoid_event_handler)( struct wlan_objmgr_psoc *psoc, void *arg); + QDF_STATUS (*send_ctl_info)(struct wlan_objmgr_psoc *psoc, + struct reg_ctl_params *params); }; /** diff --git a/umac/regulatory/core/src/reg_build_chan_list.c b/umac/regulatory/core/src/reg_build_chan_list.c index cd0623bd68..bff886602f 100644 --- a/umac/regulatory/core/src/reg_build_chan_list.c +++ b/umac/regulatory/core/src/reg_build_chan_list.c @@ -899,6 +899,77 @@ reg_populate_6g_band_channels(struct cur_reg_rule *reg_rule_5g, } #endif /* CONFIG_BAND_6GHZ */ +#ifdef CONFIG_REG_CLIENT +/** + * reg_send_ctl_info() - Send CTL info to firmware when regdb is not offloaded + * @soc_reg: soc private object for regulatory + * @regulatory_info: regulatory info + * @tx_ops: send operations for regulatory component + * + * Return: QDF_STATUS + */ +static QDF_STATUS +reg_send_ctl_info(struct wlan_regulatory_psoc_priv_obj *soc_reg, + struct cur_regulatory_info *regulatory_info, + struct wlan_lmac_if_reg_tx_ops *tx_ops) +{ + struct wlan_objmgr_psoc *psoc = regulatory_info->psoc; + struct reg_ctl_params params = {0}; + QDF_STATUS status; + uint16_t regd_index; + uint32_t index_2g, index_5g; + + if (soc_reg->offload_enabled) + return QDF_STATUS_SUCCESS; + + if (!tx_ops || !tx_ops->send_ctl_info) { + reg_err("No regulatory tx_ops for send_ctl_info"); + return QDF_STATUS_E_FAULT; + } + + status = reg_get_rdpair_from_regdmn_id(regulatory_info->reg_dmn_pair, + ®d_index); + if (QDF_IS_STATUS_ERROR(status)) { + reg_err("Failed to get regdomain index for regdomain pair: %x", + regulatory_info->reg_dmn_pair); + return status; + } + + index_2g = g_reg_dmn_pairs[regd_index].dmn_id_2g; + index_5g = g_reg_dmn_pairs[regd_index].dmn_id_5g; + params.ctl_2g = regdomains_2g[index_2g].ctl_val; + params.ctl_5g = regdomains_5g[index_5g].ctl_val; + params.regd_2g = reg_2g_sub_dmn_code[index_2g]; + params.regd_5g = reg_5g_sub_dmn_code[index_5g]; + + if (reg_is_world_ctry_code(regulatory_info->reg_dmn_pair)) + params.regd = regulatory_info->reg_dmn_pair; + else + params.regd = regulatory_info->ctry_code | COUNTRY_ERD_FLAG; + + reg_debug("regdomain pair = %u, regdomain index = %u", + regulatory_info->reg_dmn_pair, regd_index); + reg_debug("index_2g = %u, index_5g = %u, ctl_2g = %x, ctl_5g = %x", + index_2g, index_5g, params.ctl_2g, params.ctl_5g); + reg_debug("regd_2g = %x, regd_5g = %x, regd = %x", + params.regd_2g, params.regd_5g, params.regd); + + status = tx_ops->send_ctl_info(psoc, ¶ms); + if (QDF_IS_STATUS_ERROR(status)) + reg_err("Failed to send CTL info to firmware"); + + return status; +} +#else +static QDF_STATUS +reg_send_ctl_info(struct wlan_regulatory_psoc_priv_obj *soc_reg, + struct cur_regulatory_info *regulatory_info, + struct wlan_lmac_if_reg_tx_ops *tx_ops) +{ + return QDF_STATUS_SUCCESS; +} +#endif + QDF_STATUS reg_process_master_chan_list( struct cur_regulatory_info *regulat_info) { @@ -1063,6 +1134,12 @@ QDF_STATUS reg_process_master_chan_list( } soc_reg->chan_list_recvd[phy_id] = true; + status = reg_send_ctl_info(soc_reg, regulat_info, tx_ops); + if (!QDF_IS_STATUS_SUCCESS(status)) { + reg_err("Failed to send ctl info to fw"); + return status; + } + if (soc_reg->new_user_ctry_pending[phy_id]) { soc_reg->new_user_ctry_pending[phy_id] = false; soc_reg->cc_src = SOURCE_USERSPACE; diff --git a/umac/regulatory/core/src/reg_db.c b/umac/regulatory/core/src/reg_db.c index f81e5408b3..f175aac96c 100644 --- a/umac/regulatory/core/src/reg_db.c +++ b/umac/regulatory/core/src/reg_db.c @@ -943,6 +943,8 @@ enum reg_domains_2g { WORLD_2G_1, WORLD_2G_2, WORLD_2G_3, + + REG_DOMAINS_2G_MAX, }; enum reg_domains_5g { @@ -1002,6 +1004,8 @@ enum reg_domains_5g { MKK17, WORLD_5G_1, WORLD_5G_2, + + REG_DOMAINS_5G_MAX, }; const struct reg_domain_pair g_reg_dmn_pairs[] = { @@ -1556,6 +1560,67 @@ const struct regdomain regdomains_5g[] = { CHAN_5735_5835_5} }, }; +#ifdef CONFIG_REG_CLIENT +const uint32_t reg_2g_sub_dmn_code[REG_DOMAINS_2G_MAX] = { + [FCCA] = 0x0A10, + [FCCB] = 0x0B90, + [WORLD] = 0x0199, + [MKKA] = 0x0A40, + [MKKC] = 0x0A50, + [ETSIC] = 0x0C30, + [ETSID] = 0x0F30, + [KRRA] = 0x0A60, +}; + +const uint32_t reg_5g_sub_dmn_code[REG_DOMAINS_5G_MAX] = { + [NULL1] = 0x0198, + [FCC1] = 0x0110, + [FCC2] = 0x0120, + [FCC3] = 0x0160, + [FCC4] = 0x0165, + [FCC5] = 0x0510, + [FCC6] = 0x0610, + [FCC8] = 0x0810, + [FCC10] = 0x0B10, + [FCC11] = 0x0B20, + [FCC13] = 0x0B60, + [FCC14] = 0x0B70, + [ETSI1] = 0x0130, + [ETSI3] = 0x0330, + [ETSI4] = 0x0430, + [ETSI8] = 0x0830, + [ETSI9] = 0x0930, + [ETSI10] = 0x0D30, + [ETSI11] = 0x0E30, + [ETSI12] = 0x0E38, + [ETSI13] = 0x0E39, + [ETSI14] = 0x0E40, + [ETSI15] = 0x0E41, + [APL1] = 0x0150, + [APL2] = 0x0250, + [APL4] = 0x0450, + [APL6] = 0x0650, + [APL8] = 0x0850, + [APL9] = 0x0950, + [APL10] = 0x1050, + [APL11] = 0x1150, + [APL12] = 0x1160, + [APL13] = 0x1170, + [APL14] = 0x1180, + [APL15] = 0x1190, + [APL16] = 0x1200, + [APL17] = 0x1210, + [APL23] = 0x1280, + [APL20] = 0x1250, + [APL23] = 0x1280, + [MKK3] = 0x0340, + [MKK5] = 0x0540, + [MKK11] = 0x1140, + [MKK16] = 0x1640, + [MKK17] = 0x1650, +}; +#endif + QDF_STATUS reg_get_num_countries(int *num_countries) { *num_countries = QDF_ARRAY_SIZE(g_all_countries); diff --git a/umac/regulatory/core/src/reg_db_parser.h b/umac/regulatory/core/src/reg_db_parser.h index 4d945e17fe..cc9cd021ad 100644 --- a/umac/regulatory/core/src/reg_db_parser.h +++ b/umac/regulatory/core/src/reg_db_parser.h @@ -32,6 +32,11 @@ extern const struct regdomain regdomains_2g[]; extern const struct regulatory_rule reg_rules_5g[]; extern const struct regdomain regdomains_5g[]; +#ifdef CONFIG_REG_CLIENT +extern const uint32_t reg_2g_sub_dmn_code[]; +extern const uint32_t reg_5g_sub_dmn_code[]; +#endif + /** * reg_is_country_code_valid() - Check if the given country code is valid * @alpha2: Country string diff --git a/umac/regulatory/dispatcher/inc/reg_services_public_struct.h b/umac/regulatory/dispatcher/inc/reg_services_public_struct.h index a95c1e400d..2617cd8484 100644 --- a/umac/regulatory/dispatcher/inc/reg_services_public_struct.h +++ b/umac/regulatory/dispatcher/inc/reg_services_public_struct.h @@ -1076,4 +1076,20 @@ struct avoid_freq_ind_data { #define TWOG_CHAN_6_IN_MHZ 2437 #define TWOG_CHAN_13_IN_MHZ 2472 +/** + * struct reg_ctl_params - reg ctl and regd info + * @regd: regdomain pair + * @regd_2g: 2g sub domain code + * @regd_5g: 5g sub domain code + * @ctl_2g: 2g ctl info + * @ctl_5g: 5g ctl info + */ +struct reg_ctl_params { + uint32_t regd; + uint16_t regd_2g; + uint16_t regd_5g; + uint8_t ctl_2g; + uint8_t ctl_5g; +}; + #endif diff --git a/wmi/src/wmi_unified_tlv.c b/wmi/src/wmi_unified_tlv.c index 4f0ffa9a8e..d052e3f905 100644 --- a/wmi/src/wmi_unified_tlv.c +++ b/wmi/src/wmi_unified_tlv.c @@ -5947,6 +5947,11 @@ static QDF_STATUS send_regdomain_info_to_fw_cmd_tlv(wmi_unified_t wmi_handle, cmd->conformance_test_limit_2G = ctl2G; cmd->conformance_test_limit_5G = ctl5G; + wmi_debug("regd = %x, regd_2g = %x, regd_5g = %x, ctl_2g = %x, ctl_5g = %x", + cmd->reg_domain, cmd->reg_domain_2G, cmd->reg_domain_5G, + cmd->conformance_test_limit_2G, + cmd->conformance_test_limit_5G); + wmi_mtrace(WMI_PDEV_SET_REGDOMAIN_CMDID, NO_SESSION, 0); if (wmi_unified_cmd_send(wmi_handle, buf, len, WMI_PDEV_SET_REGDOMAIN_CMDID)) {