1 /* 2 * Copyright (c) 2016-2021 The Linux Foundation. All rights reserved. 3 * Copyright (c) 2021-2022 Qualcomm Innovation Center, Inc. All rights reserved. 4 * 5 * Permission to use, copy, modify, and/or distribute this software for 6 * any purpose with or without fee is hereby granted, provided that the 7 * above copyright notice and this permission notice appear in all 8 * copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL 11 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED 12 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE 13 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL 14 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR 15 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER 16 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 17 * PERFORMANCE OF THIS SOFTWARE. 18 */ 19 20 #include "wmi_unified_api.h" 21 #include "wmi.h" 22 #include "wmi_version.h" 23 #include "wmi_unified_priv.h" 24 #include "wmi_version_allowlist.h" 25 #include "wifi_pos_public_struct.h" 26 #include <qdf_module.h> 27 #include <wlan_defs.h> 28 #include <wlan_cmn.h> 29 #include <htc_services.h> 30 #ifdef FEATURE_WLAN_APF 31 #include "wmi_unified_apf_tlv.h" 32 #endif 33 #ifdef WLAN_FEATURE_ACTION_OUI 34 #include "wmi_unified_action_oui_tlv.h" 35 #endif 36 #ifdef WLAN_POWER_MANAGEMENT_OFFLOAD 37 #include "wlan_pmo_hw_filter_public_struct.h" 38 #endif 39 #include <wlan_utility.h> 40 #ifdef WLAN_SUPPORT_GREEN_AP 41 #include "wlan_green_ap_api.h" 42 #endif 43 44 #include "wmi_unified_twt_api.h" 45 #include "wmi_unified_wds_api.h" 46 47 #ifdef WLAN_POLICY_MGR_ENABLE 48 #include "wlan_policy_mgr_public_struct.h" 49 #endif 50 51 #ifdef WMI_SMART_ANT_SUPPORT 52 #include "wmi_unified_smart_ant_api.h" 53 #endif 54 55 #ifdef WMI_DBR_SUPPORT 56 #include "wmi_unified_dbr_api.h" 57 #endif 58 59 #ifdef WMI_ATF_SUPPORT 60 #include "wmi_unified_atf_api.h" 61 #endif 62 63 #ifdef WMI_AP_SUPPORT 64 #include "wmi_unified_ap_api.h" 65 #endif 66 67 #include <wmi_unified_vdev_api.h> 68 #include <wmi_unified_vdev_tlv.h> 69 #include <wmi_unified_11be_tlv.h> 70 71 /* 72 * If FW supports WMI_SERVICE_SCAN_CONFIG_PER_CHANNEL, 73 * then channel_list may fill the upper 12 bits with channel flags, 74 * while using only the lower 20 bits for channel frequency. 75 * If FW doesn't support WMI_SERVICE_SCAN_CONFIG_PER_CHANNEL, 76 * then channel_list only holds the frequency value. 77 */ 78 #define CHAN_LIST_FLAG_MASK_POS 20 79 #define TARGET_SET_FREQ_IN_CHAN_LIST_TLV(buf, freq) \ 80 ((buf) |= ((freq) & WMI_SCAN_CHANNEL_FREQ_MASK)) 81 #define TARGET_SET_FLAGS_IN_CHAN_LIST_TLV(buf, flags) \ 82 ((buf) |= ((flags) << CHAN_LIST_FLAG_MASK_POS)) 83 84 /* HTC service ids for WMI for multi-radio */ 85 static const uint32_t multi_svc_ids[] = {WMI_CONTROL_SVC, 86 WMI_CONTROL_SVC_WMAC1, 87 WMI_CONTROL_SVC_WMAC2}; 88 89 #ifdef ENABLE_HOST_TO_TARGET_CONVERSION 90 /*Populate peer_param array whose index as host id and 91 *value as target id 92 */ 93 static const uint32_t peer_param_tlv[] = { 94 [WMI_HOST_PEER_MIMO_PS_STATE] = WMI_PEER_MIMO_PS_STATE, 95 [WMI_HOST_PEER_AMPDU] = WMI_PEER_AMPDU, 96 [WMI_HOST_PEER_AUTHORIZE] = WMI_PEER_AUTHORIZE, 97 [WMI_HOST_PEER_CHWIDTH] = WMI_PEER_CHWIDTH, 98 [WMI_HOST_PEER_NSS] = WMI_PEER_NSS, 99 [WMI_HOST_PEER_USE_4ADDR] = WMI_PEER_USE_4ADDR, 100 [WMI_HOST_PEER_MEMBERSHIP] = WMI_PEER_MEMBERSHIP, 101 [WMI_HOST_PEER_USERPOS] = WMI_PEER_USERPOS, 102 [WMI_HOST_PEER_CRIT_PROTO_HINT_ENABLED] = 103 WMI_PEER_CRIT_PROTO_HINT_ENABLED, 104 [WMI_HOST_PEER_TX_FAIL_CNT_THR] = WMI_PEER_TX_FAIL_CNT_THR, 105 [WMI_HOST_PEER_SET_HW_RETRY_CTS2S] = WMI_PEER_SET_HW_RETRY_CTS2S, 106 [WMI_HOST_PEER_IBSS_ATIM_WINDOW_LENGTH] = 107 WMI_PEER_IBSS_ATIM_WINDOW_LENGTH, 108 [WMI_HOST_PEER_PHYMODE] = WMI_PEER_PHYMODE, 109 [WMI_HOST_PEER_USE_FIXED_PWR] = WMI_PEER_USE_FIXED_PWR, 110 [WMI_HOST_PEER_PARAM_FIXED_RATE] = WMI_PEER_PARAM_FIXED_RATE, 111 [WMI_HOST_PEER_SET_MU_ALLOWLIST] = WMI_PEER_SET_MU_ALLOWLIST, 112 [WMI_HOST_PEER_SET_MAX_TX_RATE] = WMI_PEER_SET_MAX_TX_RATE, 113 [WMI_HOST_PEER_SET_MIN_TX_RATE] = WMI_PEER_SET_MIN_TX_RATE, 114 [WMI_HOST_PEER_SET_DEFAULT_ROUTING] = WMI_PEER_SET_DEFAULT_ROUTING, 115 [WMI_HOST_PEER_NSS_VHT160] = WMI_PEER_NSS_VHT160, 116 [WMI_HOST_PEER_NSS_VHT80_80] = WMI_PEER_NSS_VHT80_80, 117 [WMI_HOST_PEER_PARAM_SU_TXBF_SOUNDING_INTERVAL] = 118 WMI_PEER_PARAM_SU_TXBF_SOUNDING_INTERVAL, 119 [WMI_HOST_PEER_PARAM_MU_TXBF_SOUNDING_INTERVAL] = 120 WMI_PEER_PARAM_MU_TXBF_SOUNDING_INTERVAL, 121 [WMI_HOST_PEER_PARAM_TXBF_SOUNDING_ENABLE] = 122 WMI_PEER_PARAM_TXBF_SOUNDING_ENABLE, 123 [WMI_HOST_PEER_PARAM_MU_ENABLE] = WMI_PEER_PARAM_MU_ENABLE, 124 [WMI_HOST_PEER_PARAM_OFDMA_ENABLE] = WMI_PEER_PARAM_OFDMA_ENABLE, 125 [WMI_HOST_PEER_PARAM_ENABLE_FT] = WMI_PEER_PARAM_ENABLE_FT, 126 [WMI_HOST_PEER_CHWIDTH_PUNCTURE_20MHZ_BITMAP] = 127 WMI_PEER_CHWIDTH_PUNCTURE_20MHZ_BITMAP, 128 }; 129 130 /** 131 * Populate pdev_param_value whose index is host param and value is target 132 * param 133 */ 134 static const uint32_t pdev_param_tlv[] = { 135 [wmi_pdev_param_tx_chain_mask] = WMI_PDEV_PARAM_TX_CHAIN_MASK, 136 [wmi_pdev_param_rx_chain_mask] = WMI_PDEV_PARAM_RX_CHAIN_MASK, 137 [wmi_pdev_param_txpower_limit2g] = WMI_PDEV_PARAM_TXPOWER_LIMIT2G, 138 [wmi_pdev_param_txpower_limit5g] = WMI_PDEV_PARAM_TXPOWER_LIMIT5G, 139 [wmi_pdev_param_txpower_scale] = WMI_PDEV_PARAM_TXPOWER_SCALE, 140 [wmi_pdev_param_beacon_gen_mode] = WMI_PDEV_PARAM_BEACON_GEN_MODE, 141 [wmi_pdev_param_beacon_tx_mode] = WMI_PDEV_PARAM_BEACON_TX_MODE, 142 [wmi_pdev_param_resmgr_offchan_mode] = 143 WMI_PDEV_PARAM_RESMGR_OFFCHAN_MODE, 144 [wmi_pdev_param_protection_mode] = WMI_PDEV_PARAM_PROTECTION_MODE, 145 [wmi_pdev_param_dynamic_bw] = WMI_PDEV_PARAM_DYNAMIC_BW, 146 [wmi_pdev_param_non_agg_sw_retry_th] = 147 WMI_PDEV_PARAM_NON_AGG_SW_RETRY_TH, 148 [wmi_pdev_param_agg_sw_retry_th] = WMI_PDEV_PARAM_AGG_SW_RETRY_TH, 149 [wmi_pdev_param_sta_kickout_th] = WMI_PDEV_PARAM_STA_KICKOUT_TH, 150 [wmi_pdev_param_ac_aggrsize_scaling] = 151 WMI_PDEV_PARAM_AC_AGGRSIZE_SCALING, 152 [wmi_pdev_param_ltr_enable] = WMI_PDEV_PARAM_LTR_ENABLE, 153 [wmi_pdev_param_ltr_ac_latency_be] = 154 WMI_PDEV_PARAM_LTR_AC_LATENCY_BE, 155 [wmi_pdev_param_ltr_ac_latency_bk] = WMI_PDEV_PARAM_LTR_AC_LATENCY_BK, 156 [wmi_pdev_param_ltr_ac_latency_vi] = WMI_PDEV_PARAM_LTR_AC_LATENCY_VI, 157 [wmi_pdev_param_ltr_ac_latency_vo] = WMI_PDEV_PARAM_LTR_AC_LATENCY_VO, 158 [wmi_pdev_param_ltr_ac_latency_timeout] = 159 WMI_PDEV_PARAM_LTR_AC_LATENCY_TIMEOUT, 160 [wmi_pdev_param_ltr_sleep_override] = WMI_PDEV_PARAM_LTR_SLEEP_OVERRIDE, 161 [wmi_pdev_param_ltr_rx_override] = WMI_PDEV_PARAM_LTR_RX_OVERRIDE, 162 [wmi_pdev_param_ltr_tx_activity_timeout] = 163 WMI_PDEV_PARAM_LTR_TX_ACTIVITY_TIMEOUT, 164 [wmi_pdev_param_l1ss_enable] = WMI_PDEV_PARAM_L1SS_ENABLE, 165 [wmi_pdev_param_dsleep_enable] = WMI_PDEV_PARAM_DSLEEP_ENABLE, 166 [wmi_pdev_param_pcielp_txbuf_flush] = WMI_PDEV_PARAM_PCIELP_TXBUF_FLUSH, 167 [wmi_pdev_param_pcielp_txbuf_watermark] = 168 WMI_PDEV_PARAM_PCIELP_TXBUF_WATERMARK, 169 [wmi_pdev_param_pcielp_txbuf_tmo_en] = 170 WMI_PDEV_PARAM_PCIELP_TXBUF_TMO_EN, 171 [wmi_pdev_param_pcielp_txbuf_tmo_value] = 172 WMI_PDEV_PARAM_PCIELP_TXBUF_TMO_VALUE, 173 [wmi_pdev_param_pdev_stats_update_period] = 174 WMI_PDEV_PARAM_PDEV_STATS_UPDATE_PERIOD, 175 [wmi_pdev_param_vdev_stats_update_period] = 176 WMI_PDEV_PARAM_VDEV_STATS_UPDATE_PERIOD, 177 [wmi_pdev_param_peer_stats_update_period] = 178 WMI_PDEV_PARAM_PEER_STATS_UPDATE_PERIOD, 179 [wmi_pdev_param_bcnflt_stats_update_period] = 180 WMI_PDEV_PARAM_BCNFLT_STATS_UPDATE_PERIOD, 181 [wmi_pdev_param_pmf_qos] = WMI_PDEV_PARAM_PMF_QOS, 182 [wmi_pdev_param_arp_ac_override] = WMI_PDEV_PARAM_ARP_AC_OVERRIDE, 183 [wmi_pdev_param_dcs] = WMI_PDEV_PARAM_DCS, 184 [wmi_pdev_param_ani_enable] = WMI_PDEV_PARAM_ANI_ENABLE, 185 [wmi_pdev_param_ani_poll_period] = WMI_PDEV_PARAM_ANI_POLL_PERIOD, 186 [wmi_pdev_param_ani_listen_period] = WMI_PDEV_PARAM_ANI_LISTEN_PERIOD, 187 [wmi_pdev_param_ani_ofdm_level] = WMI_PDEV_PARAM_ANI_OFDM_LEVEL, 188 [wmi_pdev_param_ani_cck_level] = WMI_PDEV_PARAM_ANI_CCK_LEVEL, 189 [wmi_pdev_param_dyntxchain] = WMI_PDEV_PARAM_DYNTXCHAIN, 190 [wmi_pdev_param_proxy_sta] = WMI_PDEV_PARAM_PROXY_STA, 191 [wmi_pdev_param_idle_ps_config] = WMI_PDEV_PARAM_IDLE_PS_CONFIG, 192 [wmi_pdev_param_power_gating_sleep] = WMI_PDEV_PARAM_POWER_GATING_SLEEP, 193 [wmi_pdev_param_rfkill_enable] = WMI_PDEV_PARAM_RFKILL_ENABLE, 194 [wmi_pdev_param_burst_dur] = WMI_PDEV_PARAM_BURST_DUR, 195 [wmi_pdev_param_burst_enable] = WMI_PDEV_PARAM_BURST_ENABLE, 196 [wmi_pdev_param_hw_rfkill_config] = WMI_PDEV_PARAM_HW_RFKILL_CONFIG, 197 [wmi_pdev_param_low_power_rf_enable] = 198 WMI_PDEV_PARAM_LOW_POWER_RF_ENABLE, 199 [wmi_pdev_param_l1ss_track] = WMI_PDEV_PARAM_L1SS_TRACK, 200 [wmi_pdev_param_hyst_en] = WMI_PDEV_PARAM_HYST_EN, 201 [wmi_pdev_param_power_collapse_enable] = 202 WMI_PDEV_PARAM_POWER_COLLAPSE_ENABLE, 203 [wmi_pdev_param_led_sys_state] = WMI_PDEV_PARAM_LED_SYS_STATE, 204 [wmi_pdev_param_led_enable] = WMI_PDEV_PARAM_LED_ENABLE, 205 [wmi_pdev_param_audio_over_wlan_latency] = 206 WMI_PDEV_PARAM_AUDIO_OVER_WLAN_LATENCY, 207 [wmi_pdev_param_audio_over_wlan_enable] = 208 WMI_PDEV_PARAM_AUDIO_OVER_WLAN_ENABLE, 209 [wmi_pdev_param_whal_mib_stats_update_enable] = 210 WMI_PDEV_PARAM_WHAL_MIB_STATS_UPDATE_ENABLE, 211 [wmi_pdev_param_vdev_rate_stats_update_period] = 212 WMI_PDEV_PARAM_VDEV_RATE_STATS_UPDATE_PERIOD, 213 [wmi_pdev_param_cts_cbw] = WMI_PDEV_PARAM_CTS_CBW, 214 [wmi_pdev_param_wnts_config] = WMI_PDEV_PARAM_WNTS_CONFIG, 215 [wmi_pdev_param_adaptive_early_rx_enable] = 216 WMI_PDEV_PARAM_ADAPTIVE_EARLY_RX_ENABLE, 217 [wmi_pdev_param_adaptive_early_rx_min_sleep_slop] = 218 WMI_PDEV_PARAM_ADAPTIVE_EARLY_RX_MIN_SLEEP_SLOP, 219 [wmi_pdev_param_adaptive_early_rx_inc_dec_step] = 220 WMI_PDEV_PARAM_ADAPTIVE_EARLY_RX_INC_DEC_STEP, 221 [wmi_pdev_param_early_rx_fix_sleep_slop] = 222 WMI_PDEV_PARAM_EARLY_RX_FIX_SLEEP_SLOP, 223 [wmi_pdev_param_bmiss_based_adaptive_bto_enable] = 224 WMI_PDEV_PARAM_BMISS_BASED_ADAPTIVE_BTO_ENABLE, 225 [wmi_pdev_param_bmiss_bto_min_bcn_timeout] = 226 WMI_PDEV_PARAM_BMISS_BTO_MIN_BCN_TIMEOUT, 227 [wmi_pdev_param_bmiss_bto_inc_dec_step] = 228 WMI_PDEV_PARAM_BMISS_BTO_INC_DEC_STEP, 229 [wmi_pdev_param_bto_fix_bcn_timeout] = 230 WMI_PDEV_PARAM_BTO_FIX_BCN_TIMEOUT, 231 [wmi_pdev_param_ce_based_adaptive_bto_enable] = 232 WMI_PDEV_PARAM_CE_BASED_ADAPTIVE_BTO_ENABLE, 233 [wmi_pdev_param_ce_bto_combo_ce_value] = 234 WMI_PDEV_PARAM_CE_BTO_COMBO_CE_VALUE, 235 [wmi_pdev_param_tx_chain_mask_2g] = WMI_PDEV_PARAM_TX_CHAIN_MASK_2G, 236 [wmi_pdev_param_rx_chain_mask_2g] = WMI_PDEV_PARAM_RX_CHAIN_MASK_2G, 237 [wmi_pdev_param_tx_chain_mask_5g] = WMI_PDEV_PARAM_TX_CHAIN_MASK_5G, 238 [wmi_pdev_param_rx_chain_mask_5g] = WMI_PDEV_PARAM_RX_CHAIN_MASK_5G, 239 [wmi_pdev_param_tx_chain_mask_cck] = WMI_PDEV_PARAM_TX_CHAIN_MASK_CCK, 240 [wmi_pdev_param_tx_chain_mask_1ss] = WMI_PDEV_PARAM_TX_CHAIN_MASK_1SS, 241 [wmi_pdev_param_soft_tx_chain_mask] = WMI_PDEV_PARAM_TX_CHAIN_MASK, 242 [wmi_pdev_param_rx_filter] = WMI_PDEV_PARAM_RX_FILTER, 243 [wmi_pdev_set_mcast_to_ucast_tid] = WMI_PDEV_SET_MCAST_TO_UCAST_TID, 244 [wmi_pdev_param_mgmt_retry_limit] = WMI_PDEV_PARAM_MGMT_RETRY_LIMIT, 245 [wmi_pdev_param_aggr_burst] = WMI_PDEV_PARAM_AGGR_BURST, 246 [wmi_pdev_peer_sta_ps_statechg_enable] = 247 WMI_PDEV_PEER_STA_PS_STATECHG_ENABLE, 248 [wmi_pdev_param_proxy_sta_mode] = WMI_PDEV_PARAM_PROXY_STA_MODE, 249 [wmi_pdev_param_mu_group_policy] = WMI_PDEV_PARAM_MU_GROUP_POLICY, 250 [wmi_pdev_param_noise_detection] = WMI_PDEV_PARAM_NOISE_DETECTION, 251 [wmi_pdev_param_noise_threshold] = WMI_PDEV_PARAM_NOISE_THRESHOLD, 252 [wmi_pdev_param_dpd_enable] = WMI_PDEV_PARAM_DPD_ENABLE, 253 [wmi_pdev_param_set_mcast_bcast_echo] = 254 WMI_PDEV_PARAM_SET_MCAST_BCAST_ECHO, 255 [wmi_pdev_param_atf_strict_sch] = WMI_PDEV_PARAM_ATF_STRICT_SCH, 256 [wmi_pdev_param_atf_sched_duration] = WMI_PDEV_PARAM_ATF_SCHED_DURATION, 257 [wmi_pdev_param_ant_plzn] = WMI_PDEV_PARAM_ANT_PLZN, 258 [wmi_pdev_param_sensitivity_level] = WMI_PDEV_PARAM_SENSITIVITY_LEVEL, 259 [wmi_pdev_param_signed_txpower_2g] = WMI_PDEV_PARAM_SIGNED_TXPOWER_2G, 260 [wmi_pdev_param_signed_txpower_5g] = WMI_PDEV_PARAM_SIGNED_TXPOWER_5G, 261 [wmi_pdev_param_enable_per_tid_amsdu] = 262 WMI_PDEV_PARAM_ENABLE_PER_TID_AMSDU, 263 [wmi_pdev_param_enable_per_tid_ampdu] = 264 WMI_PDEV_PARAM_ENABLE_PER_TID_AMPDU, 265 [wmi_pdev_param_cca_threshold] = WMI_PDEV_PARAM_CCA_THRESHOLD, 266 [wmi_pdev_param_rts_fixed_rate] = WMI_PDEV_PARAM_RTS_FIXED_RATE, 267 [wmi_pdev_param_cal_period] = WMI_UNAVAILABLE_PARAM, 268 [wmi_pdev_param_pdev_reset] = WMI_PDEV_PARAM_PDEV_RESET, 269 [wmi_pdev_param_wapi_mbssid_offset] = WMI_PDEV_PARAM_WAPI_MBSSID_OFFSET, 270 [wmi_pdev_param_arp_srcaddr] = WMI_PDEV_PARAM_ARP_DBG_SRCADDR, 271 [wmi_pdev_param_arp_dstaddr] = WMI_PDEV_PARAM_ARP_DBG_DSTADDR, 272 [wmi_pdev_param_txpower_decr_db] = WMI_PDEV_PARAM_TXPOWER_DECR_DB, 273 [wmi_pdev_param_rx_batchmode] = WMI_UNAVAILABLE_PARAM, 274 [wmi_pdev_param_packet_aggr_delay] = WMI_UNAVAILABLE_PARAM, 275 [wmi_pdev_param_atf_obss_noise_sch] = 276 WMI_PDEV_PARAM_ATF_OBSS_NOISE_SCH, 277 [wmi_pdev_param_atf_obss_noise_scaling_factor] = 278 WMI_PDEV_PARAM_ATF_OBSS_NOISE_SCALING_FACTOR, 279 [wmi_pdev_param_cust_txpower_scale] = WMI_PDEV_PARAM_CUST_TXPOWER_SCALE, 280 [wmi_pdev_param_atf_dynamic_enable] = WMI_PDEV_PARAM_ATF_DYNAMIC_ENABLE, 281 [wmi_pdev_param_atf_ssid_group_policy] = WMI_UNAVAILABLE_PARAM, 282 [wmi_pdev_param_igmpmld_override] = WMI_PDEV_PARAM_IGMPMLD_AC_OVERRIDE, 283 [wmi_pdev_param_igmpmld_tid] = WMI_PDEV_PARAM_IGMPMLD_AC_OVERRIDE, 284 [wmi_pdev_param_antenna_gain] = WMI_PDEV_PARAM_ANTENNA_GAIN, 285 [wmi_pdev_param_block_interbss] = WMI_PDEV_PARAM_BLOCK_INTERBSS, 286 [wmi_pdev_param_set_disable_reset_cmdid] = 287 WMI_PDEV_PARAM_SET_DISABLE_RESET_CMDID, 288 [wmi_pdev_param_set_msdu_ttl_cmdid] = WMI_PDEV_PARAM_SET_MSDU_TTL_CMDID, 289 [wmi_pdev_param_txbf_sound_period_cmdid] = 290 WMI_PDEV_PARAM_TXBF_SOUND_PERIOD_CMDID, 291 [wmi_pdev_param_set_burst_mode_cmdid] = 292 WMI_PDEV_PARAM_SET_BURST_MODE_CMDID, 293 [wmi_pdev_param_en_stats] = WMI_PDEV_PARAM_EN_STATS, 294 [wmi_pdev_param_mesh_mcast_enable] = WMI_PDEV_PARAM_MESH_MCAST_ENABLE, 295 [wmi_pdev_param_set_promisc_mode_cmdid] = 296 WMI_PDEV_PARAM_SET_PROMISC_MODE_CMDID, 297 [wmi_pdev_param_set_ppdu_duration_cmdid] = 298 WMI_PDEV_PARAM_SET_PPDU_DURATION_CMDID, 299 [wmi_pdev_param_remove_mcast2ucast_buffer] = 300 WMI_PDEV_PARAM_REMOVE_MCAST2UCAST_BUFFER, 301 [wmi_pdev_param_set_mcast2ucast_buffer] = 302 WMI_PDEV_PARAM_SET_MCAST2UCAST_BUFFER, 303 [wmi_pdev_param_set_mcast2ucast_mode] = 304 WMI_PDEV_PARAM_SET_MCAST2UCAST_MODE, 305 [wmi_pdev_param_smart_antenna_default_antenna] = 306 WMI_PDEV_PARAM_SMART_ANTENNA_DEFAULT_ANTENNA, 307 [wmi_pdev_param_fast_channel_reset] = 308 WMI_PDEV_PARAM_FAST_CHANNEL_RESET, 309 [wmi_pdev_param_rx_decap_mode] = WMI_PDEV_PARAM_RX_DECAP_MODE, 310 [wmi_pdev_param_tx_ack_timeout] = WMI_PDEV_PARAM_ACK_TIMEOUT, 311 [wmi_pdev_param_cck_tx_enable] = WMI_PDEV_PARAM_CCK_TX_ENABLE, 312 [wmi_pdev_param_antenna_gain_half_db] = 313 WMI_PDEV_PARAM_ANTENNA_GAIN_HALF_DB, 314 [wmi_pdev_param_esp_indication_period] = 315 WMI_PDEV_PARAM_ESP_INDICATION_PERIOD, 316 [wmi_pdev_param_esp_ba_window] = WMI_PDEV_PARAM_ESP_BA_WINDOW, 317 [wmi_pdev_param_esp_airtime_fraction] = 318 WMI_PDEV_PARAM_ESP_AIRTIME_FRACTION, 319 [wmi_pdev_param_esp_ppdu_duration] = WMI_PDEV_PARAM_ESP_PPDU_DURATION, 320 [wmi_pdev_param_ru26_allowed] = WMI_PDEV_PARAM_UL_RU26_ALLOWED, 321 [wmi_pdev_param_use_nol] = WMI_PDEV_PARAM_USE_NOL, 322 /* Trigger interval for all trigger types. */ 323 [wmi_pdev_param_ul_trig_int] = WMI_PDEV_PARAM_SET_UL_BSR_TRIG_INTERVAL, 324 [wmi_pdev_param_sub_channel_marking] = 325 WMI_PDEV_PARAM_SUB_CHANNEL_MARKING, 326 [wmi_pdev_param_ul_ppdu_duration] = WMI_PDEV_PARAM_SET_UL_PPDU_DURATION, 327 [wmi_pdev_param_equal_ru_allocation_enable] = 328 WMI_PDEV_PARAM_EQUAL_RU_ALLOCATION_ENABLE, 329 [wmi_pdev_param_per_peer_prd_cfr_enable] = 330 WMI_PDEV_PARAM_PER_PEER_PERIODIC_CFR_ENABLE, 331 [wmi_pdev_param_nav_override_config] = 332 WMI_PDEV_PARAM_NAV_OVERRIDE_CONFIG, 333 [wmi_pdev_param_set_mgmt_ttl] = WMI_PDEV_PARAM_SET_MGMT_TTL, 334 [wmi_pdev_param_set_prb_rsp_ttl] = 335 WMI_PDEV_PARAM_SET_PROBE_RESP_TTL, 336 [wmi_pdev_param_set_mu_ppdu_duration] = 337 WMI_PDEV_PARAM_SET_MU_PPDU_DURATION, 338 [wmi_pdev_param_set_tbtt_ctrl] = 339 WMI_PDEV_PARAM_SET_TBTT_CTRL, 340 [wmi_pdev_param_set_cmd_obss_pd_threshold] = 341 WMI_PDEV_PARAM_SET_CMD_OBSS_PD_THRESHOLD, 342 [wmi_pdev_param_set_cmd_obss_pd_per_ac] = 343 WMI_PDEV_PARAM_SET_CMD_OBSS_PD_PER_AC, 344 [wmi_pdev_param_set_cong_ctrl_max_msdus] = 345 WMI_PDEV_PARAM_SET_CONG_CTRL_MAX_MSDUS, 346 [wmi_pdev_param_enable_fw_dynamic_he_edca] = 347 WMI_PDEV_PARAM_ENABLE_FW_DYNAMIC_HE_EDCA, 348 [wmi_pdev_param_enable_srp] = WMI_PDEV_PARAM_ENABLE_SRP, 349 [wmi_pdev_param_enable_sr_prohibit] = WMI_PDEV_PARAM_ENABLE_SR_PROHIBIT, 350 [wmi_pdev_param_sr_trigger_margin] = WMI_PDEV_PARAM_SR_TRIGGER_MARGIN, 351 [wmi_pdev_param_pream_punct_bw] = WMI_PDEV_PARAM_SET_PREAM_PUNCT_BW, 352 [wmi_pdev_param_enable_mbssid_ctrl_frame] = WMI_PDEV_PARAM_ENABLE_MBSSID_CTRL_FRAME, 353 [wmi_pdev_param_set_mesh_params] = WMI_PDEV_PARAM_SET_MESH_PARAMS, 354 [wmi_pdev_param_mpd_userpd_ssr] = WMI_PDEV_PARAM_MPD_USERPD_SSR, 355 [wmi_pdev_param_low_latency_mode] = 356 WMI_PDEV_PARAM_LOW_LATENCY_SCHED_MODE, 357 [wmi_pdev_param_scan_radio_tx_on_dfs] = 358 WMI_PDEV_PARAM_SCAN_RADIO_TX_ON_DFS, 359 [wmi_pdev_param_en_probe_all_bw] = 360 WMI_PDEV_PARAM_EN_PROBE_ALL_BW, 361 [wmi_pdev_param_obss_min_duration_check_for_sr] = 362 WMI_PDEV_PARAM_OBSS_MIN_DURATION_CHECK_FOR_SR, 363 [wmi_pdev_param_truncate_sr] = WMI_PDEV_PARAM_TRUNCATE_SR, 364 [wmi_pdev_param_ctrl_frame_obss_pd_threshold] = 365 WMI_PDEV_PARAM_CTRL_FRAME_OBSS_PD_THRESHOLD, 366 [wmi_pdev_param_rate_upper_cap] = WMI_PDEV_PARAM_RATE_UPPER_CAP, 367 [wmi_pdev_param_rate_retry_mcs_drop] = 368 WMI_PDEV_PARAM_SET_RATE_DROP_DOWN_RETRY_THRESH, 369 [wmi_pdev_param_mcs_probe_intvl] = 370 WMI_PDEV_PARAM_MIN_MAX_MCS_PROBE_INTERVAL, 371 [wmi_pdev_param_nss_probe_intvl] = 372 WMI_PDEV_PARAM_MIN_MAX_NSS_PROBE_INTERVAL, 373 [wmi_pdev_param_dtim_synth] = WMI_PDEV_PARAM_DTIM_SYNTH, 374 [wmi_pdev_param_1ch_dtim_optimized_chain_selection] = 375 WMI_PDEV_PARAM_1CH_DTIM_OPTIMIZED_CHAIN_SELECTION, 376 [wmi_pdev_param_tx_sch_delay] = WMI_PDEV_PARAM_TX_SCH_DELAY, 377 [wmi_pdev_param_en_update_scram_seed] = 378 WMI_PDEV_PARAM_EN_UPDATE_SCRAM_SEED, 379 [wmi_pdev_param_secondary_retry_enable] = 380 WMI_PDEV_PARAM_SECONDARY_RETRY_ENABLE, 381 [wmi_pdev_param_set_sap_xlna_bypass] = 382 WMI_PDEV_PARAM_SET_SAP_XLNA_BYPASS, 383 [wmi_pdev_param_set_dfs_chan_ageout_time] = 384 WMI_PDEV_PARAM_SET_DFS_CHAN_AGEOUT_TIME, 385 [wmi_pdev_param_pdev_stats_tx_xretry_ext] = 386 WMI_PDEV_PARAM_PDEV_STATS_TX_XRETRY_EXT, 387 [wmi_pdev_param_smart_chainmask_scheme] = 388 WMI_PDEV_PARAM_SMART_CHAINMASK_SCHEME, 389 [wmi_pdev_param_alternative_chainmask_scheme] = 390 WMI_PDEV_PARAM_ALTERNATIVE_CHAINMASK_SCHEME, 391 [wmi_pdev_param_enable_rts_sifs_bursting] = 392 WMI_PDEV_PARAM_ENABLE_RTS_SIFS_BURSTING, 393 [wmi_pdev_param_max_mpdus_in_ampdu] = WMI_PDEV_PARAM_MAX_MPDUS_IN_AMPDU, 394 [wmi_pdev_param_set_iot_pattern] = WMI_PDEV_PARAM_SET_IOT_PATTERN, 395 [wmi_pdev_param_mwscoex_scc_chavd_delay] = 396 WMI_PDEV_PARAM_MWSCOEX_SCC_CHAVD_DELAY, 397 [wmi_pdev_param_mwscoex_pcc_chavd_delay] = 398 WMI_PDEV_PARAM_MWSCOEX_PCC_CHAVD_DELAY, 399 [wmi_pdev_param_mwscoex_set_5gnr_pwr_limit] = 400 WMI_PDEV_PARAM_MWSCOEX_SET_5GNR_PWR_LIMIT, 401 [wmi_pdev_param_mwscoex_4g_allow_quick_ftdm] = 402 WMI_PDEV_PARAM_MWSCOEX_4G_ALLOW_QUICK_FTDM, 403 [wmi_pdev_param_fast_pwr_transition] = 404 WMI_PDEV_PARAM_FAST_PWR_TRANSITION, 405 [wmi_pdev_auto_detect_power_failure] = 406 WMI_PDEV_AUTO_DETECT_POWER_FAILURE, 407 [wmi_pdev_param_gcmp_support_enable] = 408 WMI_PDEV_PARAM_GCMP_SUPPORT_ENABLE, 409 [wmi_pdev_param_abg_mode_tx_chain_num] = 410 WMI_PDEV_PARAM_ABG_MODE_TX_CHAIN_NUM, 411 [wmi_pdev_param_peer_stats_info_enable] = 412 WMI_PDEV_PARAM_PEER_STATS_INFO_ENABLE, 413 [wmi_pdev_param_enable_cck_txfir_override] = 414 WMI_PDEV_PARAM_ENABLE_CCK_TXFIR_OVERRIDE, 415 [wmi_pdev_param_twt_ac_config] = WMI_PDEV_PARAM_TWT_AC_CONFIG, 416 [wmi_pdev_param_pcie_hw_ilp] = WMI_PDEV_PARAM_PCIE_HW_ILP, 417 [wmi_pdev_param_disable_hw_assist] = WMI_PDEV_PARAM_DISABLE_HW_ASSIST, 418 [wmi_pdev_param_ant_div_usrcfg] = WMI_PDEV_PARAM_ANT_DIV_USRCFG, 419 [wmi_pdev_param_ctrl_retry_limit] = WMI_PDEV_PARAM_CTRL_RETRY_LIMIT, 420 [wmi_pdev_param_propagation_delay] = WMI_PDEV_PARAM_PROPAGATION_DELAY, 421 [wmi_pdev_param_ena_ant_div] = WMI_PDEV_PARAM_ENA_ANT_DIV, 422 [wmi_pdev_param_force_chain_ant] = WMI_PDEV_PARAM_FORCE_CHAIN_ANT, 423 [wmi_pdev_param_ant_div_selftest] = WMI_PDEV_PARAM_ANT_DIV_SELFTEST, 424 [wmi_pdev_param_ant_div_selftest_intvl] = 425 WMI_PDEV_PARAM_ANT_DIV_SELFTEST_INTVL, 426 [wmi_pdev_param_1ch_dtim_optimized_chain_selection] = 427 WMI_PDEV_PARAM_1CH_DTIM_OPTIMIZED_CHAIN_SELECTION, 428 [wmi_pdev_param_data_stall_detect_enable] = 429 WMI_PDEV_PARAM_DATA_STALL_DETECT_ENABLE, 430 [wmi_pdev_param_max_mpdus_in_ampdu] = 431 WMI_PDEV_PARAM_MAX_MPDUS_IN_AMPDU, 432 [wmi_pdev_param_stats_observation_period] = 433 WMI_PDEV_PARAM_STATS_OBSERVATION_PERIOD, 434 [wmi_pdev_param_cts2self_for_p2p_go_config] = 435 WMI_PDEV_PARAM_CTS2SELF_FOR_P2P_GO_CONFIG, 436 [wmi_pdev_param_txpower_reason_sar] = WMI_PDEV_PARAM_TXPOWER_REASON_SAR, 437 }; 438 439 /** 440 * Populate vdev_param_value_tlv array whose index is host param 441 * and value is target param 442 */ 443 static const uint32_t vdev_param_tlv[] = { 444 [wmi_vdev_param_rts_threshold] = WMI_VDEV_PARAM_RTS_THRESHOLD, 445 [wmi_vdev_param_fragmentation_threshold] = 446 WMI_VDEV_PARAM_FRAGMENTATION_THRESHOLD, 447 [wmi_vdev_param_beacon_interval] = WMI_VDEV_PARAM_BEACON_INTERVAL, 448 [wmi_vdev_param_listen_interval] = WMI_VDEV_PARAM_LISTEN_INTERVAL, 449 [wmi_vdev_param_multicast_rate] = WMI_VDEV_PARAM_MULTICAST_RATE, 450 [wmi_vdev_param_mgmt_tx_rate] = WMI_VDEV_PARAM_MGMT_TX_RATE, 451 [wmi_vdev_param_slot_time] = WMI_VDEV_PARAM_SLOT_TIME, 452 [wmi_vdev_param_preamble] = WMI_VDEV_PARAM_PREAMBLE, 453 [wmi_vdev_param_swba_time] = WMI_VDEV_PARAM_SWBA_TIME, 454 [wmi_vdev_stats_update_period] = WMI_VDEV_STATS_UPDATE_PERIOD, 455 [wmi_vdev_pwrsave_ageout_time] = WMI_VDEV_PWRSAVE_AGEOUT_TIME, 456 [wmi_vdev_host_swba_interval] = WMI_VDEV_HOST_SWBA_INTERVAL, 457 [wmi_vdev_param_dtim_period] = WMI_VDEV_PARAM_DTIM_PERIOD, 458 [wmi_vdev_oc_scheduler_air_time_limit] = 459 WMI_VDEV_OC_SCHEDULER_AIR_TIME_LIMIT, 460 [wmi_vdev_param_wds] = WMI_VDEV_PARAM_WDS, 461 [wmi_vdev_param_atim_window] = WMI_VDEV_PARAM_ATIM_WINDOW, 462 [wmi_vdev_param_bmiss_count_max] = WMI_VDEV_PARAM_BMISS_COUNT_MAX, 463 [wmi_vdev_param_bmiss_first_bcnt] = WMI_VDEV_PARAM_BMISS_FIRST_BCNT, 464 [wmi_vdev_param_bmiss_final_bcnt] = WMI_VDEV_PARAM_BMISS_FINAL_BCNT, 465 [wmi_vdev_param_feature_wmm] = WMI_VDEV_PARAM_FEATURE_WMM, 466 [wmi_vdev_param_chwidth] = WMI_VDEV_PARAM_CHWIDTH, 467 [wmi_vdev_param_chextoffset] = WMI_VDEV_PARAM_CHEXTOFFSET, 468 [wmi_vdev_param_disable_htprotection] = 469 WMI_VDEV_PARAM_DISABLE_HTPROTECTION, 470 [wmi_vdev_param_sta_quickkickout] = WMI_VDEV_PARAM_STA_QUICKKICKOUT, 471 [wmi_vdev_param_mgmt_rate] = WMI_VDEV_PARAM_MGMT_RATE, 472 [wmi_vdev_param_protection_mode] = WMI_VDEV_PARAM_PROTECTION_MODE, 473 [wmi_vdev_param_fixed_rate] = WMI_VDEV_PARAM_FIXED_RATE, 474 [wmi_vdev_param_sgi] = WMI_VDEV_PARAM_SGI, 475 [wmi_vdev_param_ldpc] = WMI_VDEV_PARAM_LDPC, 476 [wmi_vdev_param_tx_stbc] = WMI_VDEV_PARAM_TX_STBC, 477 [wmi_vdev_param_rx_stbc] = WMI_VDEV_PARAM_RX_STBC, 478 [wmi_vdev_param_intra_bss_fwd] = WMI_VDEV_PARAM_INTRA_BSS_FWD, 479 [wmi_vdev_param_def_keyid] = WMI_VDEV_PARAM_DEF_KEYID, 480 [wmi_vdev_param_nss] = WMI_VDEV_PARAM_NSS, 481 [wmi_vdev_param_bcast_data_rate] = WMI_VDEV_PARAM_BCAST_DATA_RATE, 482 [wmi_vdev_param_mcast_data_rate] = WMI_VDEV_PARAM_MCAST_DATA_RATE, 483 [wmi_vdev_param_mcast_indicate] = WMI_VDEV_PARAM_MCAST_INDICATE, 484 [wmi_vdev_param_dhcp_indicate] = WMI_VDEV_PARAM_DHCP_INDICATE, 485 [wmi_vdev_param_unknown_dest_indicate] = 486 WMI_VDEV_PARAM_UNKNOWN_DEST_INDICATE, 487 [wmi_vdev_param_ap_keepalive_min_idle_inactive_time_secs] = 488 WMI_VDEV_PARAM_AP_KEEPALIVE_MIN_IDLE_INACTIVE_TIME_SECS, 489 [wmi_vdev_param_ap_keepalive_max_idle_inactive_time_secs] = 490 WMI_VDEV_PARAM_AP_KEEPALIVE_MAX_IDLE_INACTIVE_TIME_SECS, 491 [wmi_vdev_param_ap_keepalive_max_unresponsive_time_secs] = 492 WMI_VDEV_PARAM_AP_KEEPALIVE_MAX_UNRESPONSIVE_TIME_SECS, 493 [wmi_vdev_param_ap_enable_nawds] = WMI_VDEV_PARAM_AP_ENABLE_NAWDS, 494 [wmi_vdev_param_enable_rtscts] = WMI_VDEV_PARAM_ENABLE_RTSCTS, 495 [wmi_vdev_param_txbf] = WMI_VDEV_PARAM_TXBF, 496 [wmi_vdev_param_packet_powersave] = WMI_VDEV_PARAM_PACKET_POWERSAVE, 497 [wmi_vdev_param_drop_unencry] = WMI_VDEV_PARAM_DROP_UNENCRY, 498 [wmi_vdev_param_tx_encap_type] = WMI_VDEV_PARAM_TX_ENCAP_TYPE, 499 [wmi_vdev_param_ap_detect_out_of_sync_sleeping_sta_time_secs] = 500 WMI_VDEV_PARAM_AP_DETECT_OUT_OF_SYNC_SLEEPING_STA_TIME_SECS, 501 [wmi_vdev_param_early_rx_adjust_enable] = 502 WMI_VDEV_PARAM_EARLY_RX_ADJUST_ENABLE, 503 [wmi_vdev_param_early_rx_tgt_bmiss_num] = 504 WMI_VDEV_PARAM_EARLY_RX_TGT_BMISS_NUM, 505 [wmi_vdev_param_early_rx_bmiss_sample_cycle] = 506 WMI_VDEV_PARAM_EARLY_RX_BMISS_SAMPLE_CYCLE, 507 [wmi_vdev_param_early_rx_slop_step] = WMI_VDEV_PARAM_EARLY_RX_SLOP_STEP, 508 [wmi_vdev_param_early_rx_init_slop] = WMI_VDEV_PARAM_EARLY_RX_INIT_SLOP, 509 [wmi_vdev_param_early_rx_adjust_pause] = 510 WMI_VDEV_PARAM_EARLY_RX_ADJUST_PAUSE, 511 [wmi_vdev_param_tx_pwrlimit] = WMI_VDEV_PARAM_TX_PWRLIMIT, 512 [wmi_vdev_param_snr_num_for_cal] = WMI_VDEV_PARAM_SNR_NUM_FOR_CAL, 513 [wmi_vdev_param_roam_fw_offload] = WMI_VDEV_PARAM_ROAM_FW_OFFLOAD, 514 [wmi_vdev_param_enable_rmc] = WMI_VDEV_PARAM_ENABLE_RMC, 515 [wmi_vdev_param_ibss_max_bcn_lost_ms] = 516 WMI_VDEV_PARAM_IBSS_MAX_BCN_LOST_MS, 517 [wmi_vdev_param_max_rate] = WMI_VDEV_PARAM_MAX_RATE, 518 [wmi_vdev_param_early_rx_drift_sample] = 519 WMI_VDEV_PARAM_EARLY_RX_DRIFT_SAMPLE, 520 [wmi_vdev_param_set_ibss_tx_fail_cnt_thr] = 521 WMI_VDEV_PARAM_SET_IBSS_TX_FAIL_CNT_THR, 522 [wmi_vdev_param_ebt_resync_timeout] = 523 WMI_VDEV_PARAM_EBT_RESYNC_TIMEOUT, 524 [wmi_vdev_param_aggr_trig_event_enable] = 525 WMI_VDEV_PARAM_AGGR_TRIG_EVENT_ENABLE, 526 [wmi_vdev_param_is_ibss_power_save_allowed] = 527 WMI_VDEV_PARAM_IS_IBSS_POWER_SAVE_ALLOWED, 528 [wmi_vdev_param_is_power_collapse_allowed] = 529 WMI_VDEV_PARAM_IS_POWER_COLLAPSE_ALLOWED, 530 [wmi_vdev_param_is_awake_on_txrx_enabled] = 531 WMI_VDEV_PARAM_IS_AWAKE_ON_TXRX_ENABLED, 532 [wmi_vdev_param_inactivity_cnt] = WMI_VDEV_PARAM_INACTIVITY_CNT, 533 [wmi_vdev_param_txsp_end_inactivity_time_ms] = 534 WMI_VDEV_PARAM_TXSP_END_INACTIVITY_TIME_MS, 535 [wmi_vdev_param_dtim_policy] = WMI_VDEV_PARAM_DTIM_POLICY, 536 [wmi_vdev_param_ibss_ps_warmup_time_secs] = 537 WMI_VDEV_PARAM_IBSS_PS_WARMUP_TIME_SECS, 538 [wmi_vdev_param_ibss_ps_1rx_chain_in_atim_window_enable] = 539 WMI_VDEV_PARAM_IBSS_PS_1RX_CHAIN_IN_ATIM_WINDOW_ENABLE, 540 [wmi_vdev_param_rx_leak_window] = WMI_VDEV_PARAM_RX_LEAK_WINDOW, 541 [wmi_vdev_param_stats_avg_factor] = 542 WMI_VDEV_PARAM_STATS_AVG_FACTOR, 543 [wmi_vdev_param_disconnect_th] = WMI_VDEV_PARAM_DISCONNECT_TH, 544 [wmi_vdev_param_rtscts_rate] = WMI_VDEV_PARAM_RTSCTS_RATE, 545 [wmi_vdev_param_mcc_rtscts_protection_enable] = 546 WMI_VDEV_PARAM_MCC_RTSCTS_PROTECTION_ENABLE, 547 [wmi_vdev_param_mcc_broadcast_probe_enable] = 548 WMI_VDEV_PARAM_MCC_BROADCAST_PROBE_ENABLE, 549 [wmi_vdev_param_mgmt_tx_power] = WMI_VDEV_PARAM_MGMT_TX_POWER, 550 [wmi_vdev_param_beacon_rate] = WMI_VDEV_PARAM_BEACON_RATE, 551 [wmi_vdev_param_rx_decap_type] = WMI_VDEV_PARAM_RX_DECAP_TYPE, 552 [wmi_vdev_param_he_dcm_enable] = WMI_VDEV_PARAM_HE_DCM, 553 [wmi_vdev_param_he_range_ext_enable] = WMI_VDEV_PARAM_HE_RANGE_EXT, 554 [wmi_vdev_param_he_bss_color] = WMI_VDEV_PARAM_BSS_COLOR, 555 [wmi_vdev_param_set_hemu_mode] = WMI_VDEV_PARAM_SET_HEMU_MODE, 556 [wmi_vdev_param_set_he_sounding_mode] = 557 WMI_VDEV_PARAM_SET_HE_SOUNDING_MODE, 558 [wmi_vdev_param_set_heop] = WMI_VDEV_PARAM_HEOPS_0_31, 559 #ifdef WLAN_FEATURE_11BE 560 [wmi_vdev_param_set_ehtop] = WMI_VDEV_PARAM_EHTOPS_0_31, 561 [wmi_vdev_param_set_eht_mu_mode] = WMI_VDEV_PARAM_SET_EHT_MU_MODE, 562 [wmi_vdev_param_set_eht_puncturing_mode] = 563 WMI_VDEV_PARAM_SET_EHT_PUNCTURING_MODE, 564 [wmi_vdev_param_set_eht_ltf] = WMI_VDEV_PARAM_EHT_LTF, 565 [wmi_vdev_param_set_ul_eht_ltf] = WMI_VDEV_PARAM_UL_EHT_LTF, 566 [wmi_vdev_param_set_eht_dcm] = WMI_VDEV_PARAM_EHT_DCM, 567 [wmi_vdev_param_set_eht_range_ext] = WMI_VDEV_PARAM_EHT_RANGE_EXT, 568 [wmi_vdev_param_set_non_data_eht_range_ext] = 569 WMI_VDEV_PARAM_NON_DATA_EHT_RANGE_EXT, 570 #endif 571 [wmi_vdev_param_sensor_ap] = WMI_VDEV_PARAM_SENSOR_AP, 572 [wmi_vdev_param_dtim_enable_cts] = WMI_VDEV_PARAM_DTIM_ENABLE_CTS, 573 [wmi_vdev_param_atf_ssid_sched_policy] = 574 WMI_VDEV_PARAM_ATF_SSID_SCHED_POLICY, 575 [wmi_vdev_param_disable_dyn_bw_rts] = WMI_VDEV_PARAM_DISABLE_DYN_BW_RTS, 576 [wmi_vdev_param_mcast2ucast_set] = WMI_VDEV_PARAM_MCAST2UCAST_SET, 577 [wmi_vdev_param_rc_num_retries] = WMI_VDEV_PARAM_RC_NUM_RETRIES, 578 [wmi_vdev_param_cabq_maxdur] = WMI_VDEV_PARAM_CABQ_MAXDUR, 579 [wmi_vdev_param_mfptest_set] = WMI_VDEV_PARAM_MFPTEST_SET, 580 [wmi_vdev_param_rts_fixed_rate] = WMI_VDEV_PARAM_RTS_FIXED_RATE, 581 [wmi_vdev_param_vht_sgimask] = WMI_VDEV_PARAM_VHT_SGIMASK, 582 [wmi_vdev_param_vht80_ratemask] = WMI_VDEV_PARAM_VHT80_RATEMASK, 583 [wmi_vdev_param_proxy_sta] = WMI_VDEV_PARAM_PROXY_STA, 584 [wmi_vdev_param_bw_nss_ratemask] = WMI_VDEV_PARAM_BW_NSS_RATEMASK, 585 [wmi_vdev_param_set_he_ltf] = WMI_VDEV_PARAM_HE_LTF, 586 [wmi_vdev_param_disable_cabq] = WMI_VDEV_PARAM_DISABLE_CABQ, 587 [wmi_vdev_param_rate_dropdown_bmap] = WMI_VDEV_PARAM_RATE_DROPDOWN_BMAP, 588 [wmi_vdev_param_set_ba_mode] = WMI_VDEV_PARAM_BA_MODE, 589 [wmi_vdev_param_capabilities] = WMI_VDEV_PARAM_CAPABILITIES, 590 [wmi_vdev_param_autorate_misc_cfg] = WMI_VDEV_PARAM_AUTORATE_MISC_CFG, 591 [wmi_vdev_param_ul_shortgi] = WMI_VDEV_PARAM_UL_GI, 592 [wmi_vdev_param_ul_he_ltf] = WMI_VDEV_PARAM_UL_HE_LTF, 593 [wmi_vdev_param_ul_nss] = WMI_VDEV_PARAM_UL_NSS, 594 [wmi_vdev_param_ul_ppdu_bw] = WMI_VDEV_PARAM_UL_PPDU_BW, 595 [wmi_vdev_param_ul_ldpc] = WMI_VDEV_PARAM_UL_LDPC, 596 [wmi_vdev_param_ul_stbc] = WMI_VDEV_PARAM_UL_STBC, 597 [wmi_vdev_param_ul_fixed_rate] = WMI_VDEV_PARAM_UL_FIXED_RATE, 598 [wmi_vdev_param_rawmode_open_war] = WMI_VDEV_PARAM_RAW_IS_ENCRYPTED, 599 [wmi_vdev_param_max_mtu_size] = WMI_VDEV_PARAM_MAX_MTU_SIZE, 600 [wmi_vdev_param_mcast_rc_stale_period] = 601 WMI_VDEV_PARAM_MCAST_RC_STALE_PERIOD, 602 [wmi_vdev_param_enable_multi_group_key] = 603 WMI_VDEV_PARAM_ENABLE_MULTI_GROUP_KEY, 604 [wmi_vdev_param_max_group_keys] = WMI_VDEV_PARAM_NUM_GROUP_KEYS, 605 [wmi_vdev_param_enable_mcast_rc] = WMI_VDEV_PARAM_ENABLE_MCAST_RC, 606 [wmi_vdev_param_6ghz_params] = WMI_VDEV_PARAM_6GHZ_PARAMS, 607 [wmi_vdev_param_enable_disable_roam_reason_vsie] = 608 WMI_VDEV_PARAM_ENABLE_DISABLE_ROAM_REASON_VSIE, 609 [wmi_vdev_param_set_cmd_obss_pd_threshold] = 610 WMI_VDEV_PARAM_SET_CMD_OBSS_PD_THRESHOLD, 611 [wmi_vdev_param_set_cmd_obss_pd_per_ac] = 612 WMI_VDEV_PARAM_SET_CMD_OBSS_PD_PER_AC, 613 [wmi_vdev_param_enable_srp] = WMI_VDEV_PARAM_ENABLE_SRP, 614 [wmi_vdev_param_nan_config_features] = 615 WMI_VDEV_PARAM_ENABLE_DISABLE_NAN_CONFIG_FEATURES, 616 [wmi_vdev_param_enable_disable_rtt_responder_role] = 617 WMI_VDEV_PARAM_ENABLE_DISABLE_RTT_RESPONDER_ROLE, 618 [wmi_vdev_param_enable_disable_rtt_initiator_role] = 619 WMI_VDEV_PARAM_ENABLE_DISABLE_RTT_INITIATOR_ROLE, 620 [wmi_vdev_param_mcast_steer] = WMI_VDEV_PARAM_MCAST_STEERING, 621 #ifdef MULTI_CLIENT_LL_SUPPORT 622 [wmi_vdev_param_set_normal_latency_flags_config] = 623 WMI_VDEV_PARAM_NORMAL_LATENCY_FLAGS_CONFIGURATION, 624 [wmi_vdev_param_set_xr_latency_flags_config] = 625 WMI_VDEV_PARAM_XR_LATENCY_FLAGS_CONFIGURATION, 626 [wmi_vdev_param_set_low_latency_flags_config] = 627 WMI_VDEV_PARAM_LOW_LATENCY_FLAGS_CONFIGURATION, 628 [wmi_vdev_param_set_ultra_low_latency_flags_config] = 629 WMI_VDEV_PARAM_ULTRA_LOW_LATENCY_FLAGS_CONFIGURATION, 630 [wmi_vdev_param_set_normal_latency_ul_dl_config] = 631 WMI_VDEV_PARAM_NORMAL_LATENCY_UL_DL_CONFIGURATION, 632 [wmi_vdev_param_set_xr_latency_ul_dl_config] = 633 WMI_VDEV_PARAM_XR_LATENCY_UL_DL_CONFIGURATION, 634 [wmi_vdev_param_set_low_latency_ul_dl_config] = 635 WMI_VDEV_PARAM_LOW_LATENCY_UL_DL_CONFIGURATION, 636 [wmi_vdev_param_set_ultra_low_latency_ul_dl_config] = 637 WMI_VDEV_PARAM_ULTRA_LOW_LATENCY_UL_DL_CONFIGURATION, 638 [wmi_vdev_param_set_default_ll_config] = 639 WMI_VDEV_PARAM_DEFAULT_LATENCY_LEVEL_CONFIGURATION, 640 [wmi_vdev_param_set_multi_client_ll_feature_config] = 641 WMI_VDEV_PARAM_MULTI_CLIENT_LL_FEATURE_CONFIGURATION, 642 #endif 643 [wmi_vdev_param_set_traffic_config] = 644 WMI_VDEV_PARAM_VDEV_TRAFFIC_CONFIG, 645 [wmi_vdev_param_he_range_ext] = WMI_VDEV_PARAM_HE_RANGE_EXT, 646 [wmi_vdev_param_non_data_he_range_ext] = 647 WMI_VDEV_PARAM_NON_DATA_HE_RANGE_EXT, 648 [wmi_vdev_param_ndp_inactivity_timeout] = 649 WMI_VDEV_PARAM_NDP_INACTIVITY_TIMEOUT, 650 [wmi_vdev_param_ndp_keepalive_timeout] = 651 WMI_VDEV_PARAM_NDP_KEEPALIVE_TIMEOUT, 652 [wmi_vdev_param_final_bmiss_time_sec] = 653 WMI_VDEV_PARAM_FINAL_BMISS_TIME_SEC, 654 [wmi_vdev_param_final_bmiss_time_wow_sec] = 655 WMI_VDEV_PARAM_FINAL_BMISS_TIME_WOW_SEC, 656 [wmi_vdev_param_ap_keepalive_max_idle_inactive_secs] = 657 WMI_VDEV_PARAM_AP_KEEPALIVE_MAX_IDLE_INACTIVE_TIME_SECS, 658 [wmi_vdev_param_per_band_mgmt_tx_rate] = 659 WMI_VDEV_PARAM_PER_BAND_MGMT_TX_RATE, 660 [wmi_vdev_param_max_li_of_moddtim] = 661 WMI_VDEV_PARAM_MAX_LI_OF_MODDTIM, 662 [wmi_vdev_param_moddtim_cnt] = WMI_VDEV_PARAM_MODDTIM_CNT, 663 [wmi_vdev_param_max_li_of_moddtim_ms] = 664 WMI_VDEV_PARAM_MAX_LI_OF_MODDTIM_MS, 665 [wmi_vdev_param_dyndtim_cnt] = WMI_VDEV_PARAM_DYNDTIM_CNT, 666 [wmi_vdev_param_wmm_txop_enable] = WMI_VDEV_PARAM_WMM_TXOP_ENABLE, 667 [wmi_vdev_param_enable_bcast_probe_response] = 668 WMI_VDEV_PARAM_ENABLE_BCAST_PROBE_RESPONSE, 669 [wmi_vdev_param_fils_max_channel_guard_time] = 670 WMI_VDEV_PARAM_FILS_MAX_CHANNEL_GUARD_TIME, 671 [wmi_vdev_param_probe_delay] = WMI_VDEV_PARAM_PROBE_DELAY, 672 [wmi_vdev_param_repeat_probe_time] = WMI_VDEV_PARAM_REPEAT_PROBE_TIME, 673 [wmi_vdev_param_enable_disable_oce_features] = 674 WMI_VDEV_PARAM_ENABLE_DISABLE_OCE_FEATURES, 675 [wmi_vdev_param_enable_disable_nan_config_features] = 676 WMI_VDEV_PARAM_ENABLE_DISABLE_NAN_CONFIG_FEATURES, 677 [wmi_vdev_param_rsn_capability] = WMI_VDEV_PARAM_RSN_CAPABILITY, 678 [wmi_vdev_param_smps_intolerant] = WMI_VDEV_PARAM_SMPS_INTOLERANT, 679 [wmi_vdev_param_abg_mode_tx_chain_num] = WMI_VDEV_PARAM_ABG_MODE_TX_CHAIN_NUM, 680 [wmi_vdev_param_nth_beacon_to_host] = WMI_VDEV_PARAM_NTH_BEACON_TO_HOST, 681 [wmi_vdev_param_prohibit_data_mgmt] = WMI_VDEV_PARAM_PROHIBIT_DATA_MGMT, 682 [wmi_vdev_param_skip_roam_eapol_4way_handshake] = WMI_VDEV_PARAM_SKIP_ROAM_EAPOL_4WAY_HANDSHAKE, 683 [wmi_vdev_param_skip_sae_roam_4way_handshake] = WMI_VDEV_PARAM_SKIP_SAE_ROAM_4WAY_HANDSHAKE, 684 [wmi_vdev_param_roam_11kv_ctrl] = WMI_VDEV_PARAM_ROAM_11KV_CTRL, 685 [wmi_vdev_param_disable_noa_p2p_go] = WMI_VDEV_PARAM_DISABLE_NOA_P2P_GO, 686 [wmi_vdev_param_packet_capture_mode] = WMI_VDEV_PARAM_PACKET_CAPTURE_MODE, 687 [wmi_vdev_param_smart_monitor_config] = WMI_VDEV_PARAM_SMART_MONITOR_CONFIG, 688 [wmi_vdev_param_force_dtim_cnt] = WMI_VDEV_PARAM_FORCE_DTIM_CNT, 689 [wmi_vdev_param_sho_config] = WMI_VDEV_PARAM_SHO_CONFIG, 690 [wmi_vdev_param_gtx_enable] = WMI_VDEV_PARAM_GTX_ENABLE, 691 [wmi_vdev_param_mu_edca_fw_update_en] = WMI_VDEV_PARAM_MU_EDCA_FW_UPDATE_EN, 692 [wmi_vdev_param_enable_disable_rtt_initiator_random_mac] = 693 WMI_VDEV_PARAM_ENABLE_DISABLE_RTT_INITIATOR_RANDOM_MAC, 694 [wmi_vdev_param_allow_nan_initial_discovery_of_mp0_cluster] = 695 WMI_VDEV_PARAM_ALLOW_NAN_INITIAL_DISCOVERY_OF_MP0_CLUSTER, 696 [wmi_vdev_param_txpower_scale_decr_db] = WMI_VDEV_PARAM_TXPOWER_SCALE_DECR_DB, 697 [wmi_vdev_param_txpower_scale] = WMI_VDEV_PARAM_TXPOWER_SCALE, 698 [wmi_vdev_param_agg_sw_retry_th] = WMI_VDEV_PARAM_AGG_SW_RETRY_TH, 699 [wmi_vdev_param_obsspd] = WMI_VDEV_PARAM_OBSSPD, 700 [wmi_vdev_param_multi_client_ll_feature_configuration] = 701 WMI_VDEV_PARAM_NORMAL_LATENCY_FLAGS_CONFIGURATION, 702 [wmi_vdev_param_normal_latency_flags_configuration] = 703 WMI_VDEV_PARAM_NORMAL_LATENCY_FLAGS_CONFIGURATION, 704 [wmi_vdev_param_xr_latency_flags_configuration] = 705 WMI_VDEV_PARAM_XR_LATENCY_FLAGS_CONFIGURATION, 706 [wmi_vdev_param_low_latency_flags_configuration] = 707 WMI_VDEV_PARAM_LOW_LATENCY_FLAGS_CONFIGURATION, 708 [wmi_vdev_param_ultra_low_latency_flags_configuration] = 709 WMI_VDEV_PARAM_ULTRA_LOW_LATENCY_FLAGS_CONFIGURATION, 710 [wmi_vdev_param_normal_latency_ul_dl_configuration] = 711 WMI_VDEV_PARAM_NORMAL_LATENCY_UL_DL_CONFIGURATION, 712 [wmi_vdev_param_xr_latency_ul_dl_configuration] = 713 WMI_VDEV_PARAM_XR_LATENCY_UL_DL_CONFIGURATION, 714 [wmi_vdev_param_low_latency_ul_dl_configuration] = 715 WMI_VDEV_PARAM_LOW_LATENCY_UL_DL_CONFIGURATION, 716 [wmi_vdev_param_ultra_low_latency_ul_dl_configuration] = 717 WMI_VDEV_PARAM_ULTRA_LOW_LATENCY_UL_DL_CONFIGURATION, 718 [wmi_vdev_param_default_latency_level_configuration] = 719 WMI_VDEV_PARAM_DEFAULT_LATENCY_LEVEL_CONFIGURATION, 720 [wmi_vdev_param_amsdu_aggregation_size_optimization] = 721 WMI_VDEV_PARAM_AMSDU_AGGREGATION_SIZE_OPTIMIZATION, 722 [wmi_vdev_param_non_agg_sw_retry_th] = 723 WMI_VDEV_PARAM_NON_AGG_SW_RETRY_TH, 724 }; 725 #endif 726 727 #ifndef WMI_PKTLOG_EVENT_CBF 728 #define WMI_PKTLOG_EVENT_CBF 0x100 729 #endif 730 731 /** 732 * Populate the pktlog event tlv array, where 733 * the values are the FW WMI events, which host 734 * uses to communicate with FW for pktlog 735 */ 736 737 static const uint32_t pktlog_event_tlv[] = { 738 [WMI_HOST_PKTLOG_EVENT_RX_BIT] = WMI_PKTLOG_EVENT_RX, 739 [WMI_HOST_PKTLOG_EVENT_TX_BIT] = WMI_PKTLOG_EVENT_TX, 740 [WMI_HOST_PKTLOG_EVENT_RCF_BIT] = WMI_PKTLOG_EVENT_RCF, 741 [WMI_HOST_PKTLOG_EVENT_RCU_BIT] = WMI_PKTLOG_EVENT_RCU, 742 [WMI_HOST_PKTLOG_EVENT_DBG_PRINT_BIT] = 0, 743 [WMI_HOST_PKTLOG_EVENT_SMART_ANTENNA_BIT] = 744 WMI_PKTLOG_EVENT_SMART_ANTENNA, 745 [WMI_HOST_PKTLOG_EVENT_H_INFO_BIT] = 0, 746 [WMI_HOST_PKTLOG_EVENT_STEERING_BIT] = 0, 747 [WMI_HOST_PKTLOG_EVENT_TX_DATA_CAPTURE_BIT] = 0, 748 [WMI_HOST_PKTLOG_EVENT_PHY_LOGGING_BIT] = WMI_PKTLOG_EVENT_PHY, 749 [WMI_HOST_PKTLOG_EVENT_CBF_BIT] = WMI_PKTLOG_EVENT_CBF, 750 #ifdef BE_PKTLOG_SUPPORT 751 [WMI_HOST_PKTLOG_EVENT_HYBRID_TX_BIT] = WMI_PKTLOG_EVENT_HYBRID_TX, 752 #endif 753 }; 754 755 /** 756 * convert_host_pdev_id_to_target_pdev_id() - Convert pdev_id from 757 * host to target defines. 758 * @wmi_handle: pointer to wmi_handle 759 * @param pdev_id: host pdev_id to be converted. 760 * Return: target pdev_id after conversion. 761 */ 762 static uint32_t convert_host_pdev_id_to_target_pdev_id(wmi_unified_t wmi_handle, 763 uint32_t pdev_id) 764 { 765 if (pdev_id <= WMI_HOST_PDEV_ID_2 && pdev_id >= WMI_HOST_PDEV_ID_0) { 766 if (!wmi_handle->soc->is_pdev_is_map_enable) { 767 switch (pdev_id) { 768 case WMI_HOST_PDEV_ID_0: 769 return WMI_PDEV_ID_1ST; 770 case WMI_HOST_PDEV_ID_1: 771 return WMI_PDEV_ID_2ND; 772 case WMI_HOST_PDEV_ID_2: 773 return WMI_PDEV_ID_3RD; 774 } 775 } else { 776 return wmi_handle->cmd_pdev_id_map[pdev_id]; 777 } 778 } else { 779 return WMI_PDEV_ID_SOC; 780 } 781 782 QDF_ASSERT(0); 783 784 return WMI_PDEV_ID_SOC; 785 } 786 787 /** 788 * convert_target_pdev_id_to_host_pdev_id() - Convert pdev_id from 789 * target to host defines. 790 * @wmi_handle: pointer to wmi_handle 791 * @param pdev_id: target pdev_id to be converted. 792 * Return: host pdev_id after conversion. 793 */ 794 static uint32_t convert_target_pdev_id_to_host_pdev_id(wmi_unified_t wmi_handle, 795 uint32_t pdev_id) 796 { 797 798 if (pdev_id <= WMI_PDEV_ID_3RD && pdev_id >= WMI_PDEV_ID_1ST) { 799 if (!wmi_handle->soc->is_pdev_is_map_enable) { 800 switch (pdev_id) { 801 case WMI_PDEV_ID_1ST: 802 return WMI_HOST_PDEV_ID_0; 803 case WMI_PDEV_ID_2ND: 804 return WMI_HOST_PDEV_ID_1; 805 case WMI_PDEV_ID_3RD: 806 return WMI_HOST_PDEV_ID_2; 807 } 808 } else { 809 return wmi_handle->evt_pdev_id_map[pdev_id - 1]; 810 } 811 } else if (pdev_id == WMI_PDEV_ID_SOC) { 812 return WMI_HOST_PDEV_ID_SOC; 813 } else { 814 wmi_err("Invalid pdev_id"); 815 } 816 817 return WMI_HOST_PDEV_ID_INVALID; 818 } 819 820 /** 821 * convert_host_phy_id_to_target_phy_id() - Convert phy_id from 822 * host to target defines. 823 * @wmi_handle: pointer to wmi_handle 824 * @param phy_id: host pdev_id to be converted. 825 * Return: target phy_id after conversion. 826 */ 827 static uint32_t convert_host_phy_id_to_target_phy_id(wmi_unified_t wmi_handle, 828 uint32_t phy_id) 829 { 830 if (!wmi_handle->soc->is_phy_id_map_enable || 831 phy_id >= WMI_MAX_RADIOS) { 832 return phy_id; 833 } 834 835 return wmi_handle->cmd_phy_id_map[phy_id]; 836 } 837 838 /** 839 * convert_target_phy_id_to_host_phy_id() - Convert phy_id from 840 * target to host defines. 841 * @wmi_handle: pointer to wmi_handle 842 * @param phy_id: target phy_id to be converted. 843 * Return: host phy_id after conversion. 844 */ 845 static uint32_t convert_target_phy_id_to_host_phy_id(wmi_unified_t wmi_handle, 846 uint32_t phy_id) 847 { 848 if (!wmi_handle->soc->is_phy_id_map_enable || 849 phy_id >= WMI_MAX_RADIOS) { 850 return phy_id; 851 } 852 853 return wmi_handle->evt_phy_id_map[phy_id]; 854 } 855 856 /** 857 * wmi_tlv_pdev_id_conversion_enable() - Enable pdev_id conversion 858 * 859 * Return None. 860 */ 861 static void wmi_tlv_pdev_id_conversion_enable(wmi_unified_t wmi_handle, 862 uint32_t *pdev_id_map, 863 uint8_t size) 864 { 865 int i = 0; 866 867 if (pdev_id_map && (size <= WMI_MAX_RADIOS)) { 868 for (i = 0; i < size; i++) { 869 wmi_handle->cmd_pdev_id_map[i] = pdev_id_map[i]; 870 wmi_handle->evt_pdev_id_map[i] = 871 WMI_HOST_PDEV_ID_INVALID; 872 wmi_handle->cmd_phy_id_map[i] = pdev_id_map[i] - 1; 873 wmi_handle->evt_phy_id_map[i] = 874 WMI_HOST_PDEV_ID_INVALID; 875 } 876 877 for (i = 0; i < size; i++) { 878 if (wmi_handle->cmd_pdev_id_map[i] != 879 WMI_HOST_PDEV_ID_INVALID) { 880 wmi_handle->evt_pdev_id_map 881 [wmi_handle->cmd_pdev_id_map[i] - 1] = i; 882 } 883 if (wmi_handle->cmd_phy_id_map[i] != 884 WMI_HOST_PDEV_ID_INVALID) { 885 wmi_handle->evt_phy_id_map 886 [wmi_handle->cmd_phy_id_map[i]] = i; 887 } 888 } 889 wmi_handle->soc->is_pdev_is_map_enable = true; 890 wmi_handle->soc->is_phy_id_map_enable = true; 891 } else { 892 wmi_handle->soc->is_pdev_is_map_enable = false; 893 wmi_handle->soc->is_phy_id_map_enable = false; 894 } 895 896 wmi_handle->ops->convert_pdev_id_host_to_target = 897 convert_host_pdev_id_to_target_pdev_id; 898 wmi_handle->ops->convert_pdev_id_target_to_host = 899 convert_target_pdev_id_to_host_pdev_id; 900 901 /* phy_id convert function assignments */ 902 wmi_handle->ops->convert_phy_id_host_to_target = 903 convert_host_phy_id_to_target_phy_id; 904 wmi_handle->ops->convert_phy_id_target_to_host = 905 convert_target_phy_id_to_host_phy_id; 906 } 907 908 /* copy_vdev_create_pdev_id() - copy pdev from host params to target command 909 * buffer. 910 * @wmi_handle: pointer to wmi_handle 911 * @cmd: pointer target vdev create command buffer 912 * @param: pointer host params for vdev create 913 * 914 * Return: None 915 */ 916 static inline void copy_vdev_create_pdev_id( 917 struct wmi_unified *wmi_handle, 918 wmi_vdev_create_cmd_fixed_param * cmd, 919 struct vdev_create_params *param) 920 { 921 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 922 wmi_handle, 923 param->pdev_id); 924 } 925 926 void wmi_mtrace(uint32_t message_id, uint16_t vdev_id, uint32_t data) 927 { 928 uint16_t mtrace_message_id; 929 930 mtrace_message_id = QDF_WMI_MTRACE_CMD_ID(message_id) | 931 (QDF_WMI_MTRACE_GRP_ID(message_id) << 932 QDF_WMI_MTRACE_CMD_NUM_BITS); 933 qdf_mtrace(QDF_MODULE_ID_WMI, QDF_MODULE_ID_TARGET, 934 mtrace_message_id, vdev_id, data); 935 } 936 qdf_export_symbol(wmi_mtrace); 937 938 QDF_STATUS wmi_unified_cmd_send_pm_chk(struct wmi_unified *wmi_handle, 939 wmi_buf_t buf, 940 uint32_t buflen, uint32_t cmd_id, 941 bool is_qmi_send_support) 942 { 943 if (!is_qmi_send_support) 944 goto send_over_wmi; 945 946 if (!wmi_is_qmi_stats_enabled(wmi_handle)) 947 goto send_over_wmi; 948 949 if (wmi_is_target_suspend_acked(wmi_handle)) { 950 if (QDF_IS_STATUS_SUCCESS( 951 wmi_unified_cmd_send_over_qmi(wmi_handle, buf, 952 buflen, cmd_id))) 953 return QDF_STATUS_SUCCESS; 954 } 955 956 send_over_wmi: 957 qdf_atomic_set(&wmi_handle->num_stats_over_qmi, 0); 958 959 return wmi_unified_cmd_send(wmi_handle, buf, buflen, cmd_id); 960 } 961 962 /** 963 * send_vdev_create_cmd_tlv() - send VDEV create command to fw 964 * @wmi_handle: wmi handle 965 * @param: pointer to hold vdev create parameter 966 * @macaddr: vdev mac address 967 * 968 * Return: QDF_STATUS_SUCCESS for success or error code 969 */ 970 static QDF_STATUS send_vdev_create_cmd_tlv(wmi_unified_t wmi_handle, 971 uint8_t macaddr[QDF_MAC_ADDR_SIZE], 972 struct vdev_create_params *param) 973 { 974 wmi_vdev_create_cmd_fixed_param *cmd; 975 wmi_buf_t buf; 976 int32_t len = sizeof(*cmd); 977 QDF_STATUS ret; 978 int num_bands = 2; 979 uint8_t *buf_ptr; 980 wmi_vdev_txrx_streams *txrx_streams; 981 982 len += (num_bands * sizeof(*txrx_streams) + WMI_TLV_HDR_SIZE); 983 len += vdev_create_mlo_params_size(param); 984 985 buf = wmi_buf_alloc(wmi_handle, len); 986 if (!buf) 987 return QDF_STATUS_E_NOMEM; 988 989 cmd = (wmi_vdev_create_cmd_fixed_param *) wmi_buf_data(buf); 990 WMITLV_SET_HDR(&cmd->tlv_header, 991 WMITLV_TAG_STRUC_wmi_vdev_create_cmd_fixed_param, 992 WMITLV_GET_STRUCT_TLVLEN 993 (wmi_vdev_create_cmd_fixed_param)); 994 cmd->vdev_id = param->vdev_id; 995 cmd->vdev_type = param->type; 996 cmd->vdev_subtype = param->subtype; 997 cmd->flags = param->mbssid_flags; 998 cmd->flags |= (param->special_vdev_mode ? VDEV_FLAGS_SCAN_MODE_VAP : 0); 999 cmd->vdevid_trans = param->vdevid_trans; 1000 cmd->num_cfg_txrx_streams = num_bands; 1001 #ifdef QCA_VDEV_STATS_HW_OFFLOAD_SUPPORT 1002 cmd->vdev_stats_id_valid = param->vdev_stats_id_valid; 1003 cmd->vdev_stats_id = param->vdev_stats_id; 1004 #endif 1005 copy_vdev_create_pdev_id(wmi_handle, cmd, param); 1006 WMI_CHAR_ARRAY_TO_MAC_ADDR(macaddr, &cmd->vdev_macaddr); 1007 wmi_debug("ID = %d[pdev:%d] VAP Addr = "QDF_MAC_ADDR_FMT, 1008 param->vdev_id, cmd->pdev_id, 1009 QDF_MAC_ADDR_REF(macaddr)); 1010 buf_ptr = (uint8_t *)cmd + sizeof(*cmd); 1011 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 1012 (num_bands * sizeof(wmi_vdev_txrx_streams))); 1013 buf_ptr += WMI_TLV_HDR_SIZE; 1014 1015 wmi_debug("type %d, subtype %d, nss_2g %d, nss_5g %d", 1016 param->type, param->subtype, 1017 param->nss_2g, param->nss_5g); 1018 txrx_streams = (wmi_vdev_txrx_streams *)buf_ptr; 1019 txrx_streams->band = WMI_TPC_CHAINMASK_CONFIG_BAND_2G; 1020 txrx_streams->supported_tx_streams = param->nss_2g; 1021 txrx_streams->supported_rx_streams = param->nss_2g; 1022 WMITLV_SET_HDR(&txrx_streams->tlv_header, 1023 WMITLV_TAG_STRUC_wmi_vdev_txrx_streams, 1024 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_txrx_streams)); 1025 1026 txrx_streams++; 1027 txrx_streams->band = WMI_TPC_CHAINMASK_CONFIG_BAND_5G; 1028 txrx_streams->supported_tx_streams = param->nss_5g; 1029 txrx_streams->supported_rx_streams = param->nss_5g; 1030 WMITLV_SET_HDR(&txrx_streams->tlv_header, 1031 WMITLV_TAG_STRUC_wmi_vdev_txrx_streams, 1032 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_txrx_streams)); 1033 1034 buf_ptr += (num_bands * sizeof(wmi_vdev_txrx_streams)); 1035 buf_ptr = vdev_create_add_mlo_params(buf_ptr, param); 1036 1037 wmi_mtrace(WMI_VDEV_CREATE_CMDID, cmd->vdev_id, 0); 1038 ret = wmi_unified_cmd_send(wmi_handle, buf, len, WMI_VDEV_CREATE_CMDID); 1039 if (QDF_IS_STATUS_ERROR(ret)) { 1040 wmi_err("Failed to send WMI_VDEV_CREATE_CMDID"); 1041 wmi_buf_free(buf); 1042 } 1043 1044 return ret; 1045 } 1046 1047 /** 1048 * send_vdev_delete_cmd_tlv() - send VDEV delete command to fw 1049 * @wmi_handle: wmi handle 1050 * @if_id: vdev id 1051 * 1052 * Return: QDF_STATUS_SUCCESS for success or error code 1053 */ 1054 static QDF_STATUS send_vdev_delete_cmd_tlv(wmi_unified_t wmi_handle, 1055 uint8_t if_id) 1056 { 1057 wmi_vdev_delete_cmd_fixed_param *cmd; 1058 wmi_buf_t buf; 1059 QDF_STATUS ret; 1060 1061 buf = wmi_buf_alloc(wmi_handle, sizeof(*cmd)); 1062 if (!buf) 1063 return QDF_STATUS_E_NOMEM; 1064 1065 cmd = (wmi_vdev_delete_cmd_fixed_param *) wmi_buf_data(buf); 1066 WMITLV_SET_HDR(&cmd->tlv_header, 1067 WMITLV_TAG_STRUC_wmi_vdev_delete_cmd_fixed_param, 1068 WMITLV_GET_STRUCT_TLVLEN 1069 (wmi_vdev_delete_cmd_fixed_param)); 1070 cmd->vdev_id = if_id; 1071 wmi_mtrace(WMI_VDEV_DELETE_CMDID, cmd->vdev_id, 0); 1072 ret = wmi_unified_cmd_send(wmi_handle, buf, 1073 sizeof(wmi_vdev_delete_cmd_fixed_param), 1074 WMI_VDEV_DELETE_CMDID); 1075 if (QDF_IS_STATUS_ERROR(ret)) { 1076 wmi_err("Failed to send WMI_VDEV_DELETE_CMDID"); 1077 wmi_buf_free(buf); 1078 } 1079 wmi_debug("vdev id = %d", if_id); 1080 1081 return ret; 1082 } 1083 1084 /** 1085 * send_vdev_nss_chain_params_cmd_tlv() - send VDEV nss chain params to fw 1086 * @wmi_handle: wmi handle 1087 * @vdev_id: vdev id 1088 * @nss_chains_user_cfg: user configured nss chain params 1089 * 1090 * Return: QDF_STATUS_SUCCESS for success or error code 1091 */ 1092 static QDF_STATUS 1093 send_vdev_nss_chain_params_cmd_tlv(wmi_unified_t wmi_handle, 1094 uint8_t vdev_id, 1095 struct vdev_nss_chains *user_cfg) 1096 { 1097 wmi_vdev_chainmask_config_cmd_fixed_param *cmd; 1098 wmi_buf_t buf; 1099 QDF_STATUS ret; 1100 1101 buf = wmi_buf_alloc(wmi_handle, sizeof(*cmd)); 1102 if (!buf) 1103 return QDF_STATUS_E_NOMEM; 1104 1105 cmd = (wmi_vdev_chainmask_config_cmd_fixed_param *)wmi_buf_data(buf); 1106 WMITLV_SET_HDR(&cmd->tlv_header, 1107 WMITLV_TAG_STRUC_wmi_vdev_chainmask_config_cmd_fixed_param, 1108 WMITLV_GET_STRUCT_TLVLEN 1109 (wmi_vdev_chainmask_config_cmd_fixed_param)); 1110 cmd->vdev_id = vdev_id; 1111 cmd->disable_rx_mrc_2g = user_cfg->disable_rx_mrc[NSS_CHAINS_BAND_2GHZ]; 1112 cmd->disable_tx_mrc_2g = user_cfg->disable_tx_mrc[NSS_CHAINS_BAND_2GHZ]; 1113 cmd->disable_rx_mrc_5g = user_cfg->disable_rx_mrc[NSS_CHAINS_BAND_5GHZ]; 1114 cmd->disable_tx_mrc_5g = user_cfg->disable_tx_mrc[NSS_CHAINS_BAND_5GHZ]; 1115 cmd->num_rx_chains_2g = user_cfg->num_rx_chains[NSS_CHAINS_BAND_2GHZ]; 1116 cmd->num_tx_chains_2g = user_cfg->num_tx_chains[NSS_CHAINS_BAND_2GHZ]; 1117 cmd->num_rx_chains_5g = user_cfg->num_rx_chains[NSS_CHAINS_BAND_5GHZ]; 1118 cmd->num_tx_chains_5g = user_cfg->num_tx_chains[NSS_CHAINS_BAND_5GHZ]; 1119 cmd->rx_nss_2g = user_cfg->rx_nss[NSS_CHAINS_BAND_2GHZ]; 1120 cmd->tx_nss_2g = user_cfg->tx_nss[NSS_CHAINS_BAND_2GHZ]; 1121 cmd->rx_nss_5g = user_cfg->rx_nss[NSS_CHAINS_BAND_5GHZ]; 1122 cmd->tx_nss_5g = user_cfg->tx_nss[NSS_CHAINS_BAND_5GHZ]; 1123 cmd->num_tx_chains_a = user_cfg->num_tx_chains_11a; 1124 cmd->num_tx_chains_b = user_cfg->num_tx_chains_11b; 1125 cmd->num_tx_chains_g = user_cfg->num_tx_chains_11g; 1126 1127 wmi_mtrace(WMI_VDEV_CHAINMASK_CONFIG_CMDID, cmd->vdev_id, 0); 1128 ret = wmi_unified_cmd_send(wmi_handle, buf, 1129 sizeof(wmi_vdev_chainmask_config_cmd_fixed_param), 1130 WMI_VDEV_CHAINMASK_CONFIG_CMDID); 1131 if (QDF_IS_STATUS_ERROR(ret)) { 1132 wmi_err("Failed to send WMI_VDEV_CHAINMASK_CONFIG_CMDID"); 1133 wmi_buf_free(buf); 1134 } 1135 wmi_debug("vdev_id %d", vdev_id); 1136 1137 return ret; 1138 } 1139 1140 /** 1141 * send_vdev_stop_cmd_tlv() - send vdev stop command to fw 1142 * @wmi: wmi handle 1143 * @vdev_id: vdev id 1144 * 1145 * Return: QDF_STATUS_SUCCESS for success or erro code 1146 */ 1147 static QDF_STATUS send_vdev_stop_cmd_tlv(wmi_unified_t wmi, 1148 uint8_t vdev_id) 1149 { 1150 wmi_vdev_stop_cmd_fixed_param *cmd; 1151 wmi_buf_t buf; 1152 int32_t len = sizeof(*cmd); 1153 1154 buf = wmi_buf_alloc(wmi, len); 1155 if (!buf) 1156 return QDF_STATUS_E_NOMEM; 1157 1158 cmd = (wmi_vdev_stop_cmd_fixed_param *) wmi_buf_data(buf); 1159 WMITLV_SET_HDR(&cmd->tlv_header, 1160 WMITLV_TAG_STRUC_wmi_vdev_stop_cmd_fixed_param, 1161 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_stop_cmd_fixed_param)); 1162 cmd->vdev_id = vdev_id; 1163 wmi_mtrace(WMI_VDEV_STOP_CMDID, cmd->vdev_id, 0); 1164 if (wmi_unified_cmd_send(wmi, buf, len, WMI_VDEV_STOP_CMDID)) { 1165 wmi_err("Failed to send vdev stop command"); 1166 wmi_buf_free(buf); 1167 return QDF_STATUS_E_FAILURE; 1168 } 1169 wmi_debug("vdev id = %d", vdev_id); 1170 1171 return 0; 1172 } 1173 1174 /** 1175 * send_vdev_down_cmd_tlv() - send vdev down command to fw 1176 * @wmi: wmi handle 1177 * @vdev_id: vdev id 1178 * 1179 * Return: QDF_STATUS_SUCCESS for success or error code 1180 */ 1181 static QDF_STATUS send_vdev_down_cmd_tlv(wmi_unified_t wmi, uint8_t vdev_id) 1182 { 1183 wmi_vdev_down_cmd_fixed_param *cmd; 1184 wmi_buf_t buf; 1185 int32_t len = sizeof(*cmd); 1186 1187 buf = wmi_buf_alloc(wmi, len); 1188 if (!buf) 1189 return QDF_STATUS_E_NOMEM; 1190 1191 cmd = (wmi_vdev_down_cmd_fixed_param *) wmi_buf_data(buf); 1192 WMITLV_SET_HDR(&cmd->tlv_header, 1193 WMITLV_TAG_STRUC_wmi_vdev_down_cmd_fixed_param, 1194 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_down_cmd_fixed_param)); 1195 cmd->vdev_id = vdev_id; 1196 wmi_mtrace(WMI_VDEV_DOWN_CMDID, cmd->vdev_id, 0); 1197 if (wmi_unified_cmd_send(wmi, buf, len, WMI_VDEV_DOWN_CMDID)) { 1198 wmi_err("Failed to send vdev down"); 1199 wmi_buf_free(buf); 1200 return QDF_STATUS_E_FAILURE; 1201 } 1202 wmi_debug("vdev_id %d", vdev_id); 1203 1204 return 0; 1205 } 1206 1207 static inline void copy_channel_info( 1208 wmi_vdev_start_request_cmd_fixed_param * cmd, 1209 wmi_channel *chan, 1210 struct vdev_start_params *req) 1211 { 1212 chan->mhz = req->channel.mhz; 1213 1214 WMI_SET_CHANNEL_MODE(chan, req->channel.phy_mode); 1215 1216 chan->band_center_freq1 = req->channel.cfreq1; 1217 chan->band_center_freq2 = req->channel.cfreq2; 1218 1219 if (req->channel.half_rate) 1220 WMI_SET_CHANNEL_FLAG(chan, WMI_CHAN_FLAG_HALF_RATE); 1221 else if (req->channel.quarter_rate) 1222 WMI_SET_CHANNEL_FLAG(chan, WMI_CHAN_FLAG_QUARTER_RATE); 1223 1224 if (req->channel.dfs_set) { 1225 WMI_SET_CHANNEL_FLAG(chan, WMI_CHAN_FLAG_DFS); 1226 cmd->disable_hw_ack = req->disable_hw_ack; 1227 } 1228 1229 if (req->channel.dfs_set_cfreq2) 1230 WMI_SET_CHANNEL_FLAG(chan, WMI_CHAN_FLAG_DFS_CFREQ2); 1231 1232 if (req->channel.is_stadfs_en) 1233 WMI_SET_CHANNEL_FLAG(chan, WMI_CHAN_FLAG_STA_DFS); 1234 1235 /* According to firmware both reg power and max tx power 1236 * on set channel power is used and set it to max reg 1237 * power from regulatory. 1238 */ 1239 WMI_SET_CHANNEL_MIN_POWER(chan, req->channel.minpower); 1240 WMI_SET_CHANNEL_MAX_POWER(chan, req->channel.maxpower); 1241 WMI_SET_CHANNEL_REG_POWER(chan, req->channel.maxregpower); 1242 WMI_SET_CHANNEL_ANTENNA_MAX(chan, req->channel.antennamax); 1243 WMI_SET_CHANNEL_REG_CLASSID(chan, req->channel.reg_class_id); 1244 WMI_SET_CHANNEL_MAX_TX_POWER(chan, req->channel.maxregpower); 1245 1246 } 1247 1248 /** 1249 * vdev_start_cmd_fill_11be() - 11be information fiiling in vdev_ststart 1250 * @cmd: wmi cmd 1251 * @req: vdev start params 1252 * 1253 * Return: QDF status 1254 */ 1255 #ifdef WLAN_FEATURE_11BE 1256 static void 1257 vdev_start_cmd_fill_11be(wmi_vdev_start_request_cmd_fixed_param *cmd, 1258 struct vdev_start_params *req) 1259 { 1260 cmd->eht_ops = req->eht_ops; 1261 cmd->puncture_20mhz_bitmap = ~req->channel.puncture_bitmap; 1262 wmi_info("EHT ops: %x puncture_bitmap %x wmi cmd puncture bitmap %x", 1263 req->eht_ops, req->channel.puncture_bitmap, 1264 cmd->puncture_20mhz_bitmap); 1265 } 1266 #else 1267 static void 1268 vdev_start_cmd_fill_11be(wmi_vdev_start_request_cmd_fixed_param *cmd, 1269 struct vdev_start_params *req) 1270 { 1271 } 1272 #endif 1273 1274 /** 1275 * send_vdev_start_cmd_tlv() - send vdev start request to fw 1276 * @wmi_handle: wmi handle 1277 * @req: vdev start params 1278 * 1279 * Return: QDF status 1280 */ 1281 static QDF_STATUS send_vdev_start_cmd_tlv(wmi_unified_t wmi_handle, 1282 struct vdev_start_params *req) 1283 { 1284 wmi_vdev_start_request_cmd_fixed_param *cmd; 1285 wmi_buf_t buf; 1286 wmi_channel *chan; 1287 int32_t len, ret; 1288 uint8_t *buf_ptr; 1289 1290 len = sizeof(*cmd) + sizeof(wmi_channel) + WMI_TLV_HDR_SIZE; 1291 if (!req->is_restart) 1292 len += vdev_start_mlo_params_size(req); 1293 buf = wmi_buf_alloc(wmi_handle, len); 1294 if (!buf) 1295 return QDF_STATUS_E_NOMEM; 1296 1297 buf_ptr = (uint8_t *) wmi_buf_data(buf); 1298 cmd = (wmi_vdev_start_request_cmd_fixed_param *) buf_ptr; 1299 chan = (wmi_channel *) (buf_ptr + sizeof(*cmd)); 1300 WMITLV_SET_HDR(&cmd->tlv_header, 1301 WMITLV_TAG_STRUC_wmi_vdev_start_request_cmd_fixed_param, 1302 WMITLV_GET_STRUCT_TLVLEN 1303 (wmi_vdev_start_request_cmd_fixed_param)); 1304 WMITLV_SET_HDR(&chan->tlv_header, WMITLV_TAG_STRUC_wmi_channel, 1305 WMITLV_GET_STRUCT_TLVLEN(wmi_channel)); 1306 cmd->vdev_id = req->vdev_id; 1307 1308 /* Fill channel info */ 1309 copy_channel_info(cmd, chan, req); 1310 cmd->beacon_interval = req->beacon_interval; 1311 cmd->dtim_period = req->dtim_period; 1312 1313 cmd->bcn_tx_rate = req->bcn_tx_rate_code; 1314 if (req->bcn_tx_rate_code) 1315 wmi_enable_bcn_ratecode(&cmd->flags); 1316 1317 if (!req->is_restart) { 1318 if (req->pmf_enabled) 1319 cmd->flags |= WMI_UNIFIED_VDEV_START_PMF_ENABLED; 1320 1321 cmd->mbss_capability_flags = req->mbssid_flags; 1322 cmd->vdevid_trans = req->vdevid_trans; 1323 } 1324 1325 /* Copy the SSID */ 1326 if (req->ssid.length) { 1327 if (req->ssid.length < sizeof(cmd->ssid.ssid)) 1328 cmd->ssid.ssid_len = req->ssid.length; 1329 else 1330 cmd->ssid.ssid_len = sizeof(cmd->ssid.ssid); 1331 qdf_mem_copy(cmd->ssid.ssid, req->ssid.ssid, 1332 cmd->ssid.ssid_len); 1333 } 1334 1335 if (req->hidden_ssid) 1336 cmd->flags |= WMI_UNIFIED_VDEV_START_HIDDEN_SSID; 1337 1338 cmd->flags |= WMI_UNIFIED_VDEV_START_LDPC_RX_ENABLED; 1339 cmd->num_noa_descriptors = req->num_noa_descriptors; 1340 cmd->preferred_rx_streams = req->preferred_rx_streams; 1341 cmd->preferred_tx_streams = req->preferred_tx_streams; 1342 cmd->cac_duration_ms = req->cac_duration_ms; 1343 cmd->regdomain = req->regdomain; 1344 cmd->he_ops = req->he_ops; 1345 1346 buf_ptr = (uint8_t *) (((uintptr_t) cmd) + sizeof(*cmd) + 1347 sizeof(wmi_channel)); 1348 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 1349 cmd->num_noa_descriptors * 1350 sizeof(wmi_p2p_noa_descriptor)); 1351 if (!req->is_restart) { 1352 buf_ptr += WMI_TLV_HDR_SIZE + 1353 (cmd->num_noa_descriptors * sizeof(wmi_p2p_noa_descriptor)); 1354 1355 buf_ptr = vdev_start_add_mlo_params(buf_ptr, req); 1356 buf_ptr = vdev_start_add_ml_partner_links(buf_ptr, req); 1357 } 1358 wmi_info("vdev_id %d freq %d chanmode %d ch_info: 0x%x is_dfs %d " 1359 "beacon interval %d dtim %d center_chan %d center_freq2 %d " 1360 "reg_info_1: 0x%x reg_info_2: 0x%x, req->max_txpow: 0x%x " 1361 "Tx SS %d, Rx SS %d, ldpc_rx: %d, cac %d, regd %d, HE ops: %d" 1362 "req->dis_hw_ack: %d ", req->vdev_id, 1363 chan->mhz, req->channel.phy_mode, chan->info, 1364 req->channel.dfs_set, req->beacon_interval, cmd->dtim_period, 1365 chan->band_center_freq1, chan->band_center_freq2, 1366 chan->reg_info_1, chan->reg_info_2, req->channel.maxregpower, 1367 req->preferred_tx_streams, req->preferred_rx_streams, 1368 req->ldpc_rx_enabled, req->cac_duration_ms, 1369 req->regdomain, req->he_ops, 1370 req->disable_hw_ack); 1371 1372 vdev_start_cmd_fill_11be(cmd, req); 1373 1374 if (req->is_restart) { 1375 wmi_mtrace(WMI_VDEV_RESTART_REQUEST_CMDID, cmd->vdev_id, 0); 1376 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 1377 WMI_VDEV_RESTART_REQUEST_CMDID); 1378 } else { 1379 wmi_mtrace(WMI_VDEV_START_REQUEST_CMDID, cmd->vdev_id, 0); 1380 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 1381 WMI_VDEV_START_REQUEST_CMDID); 1382 } 1383 if (ret) { 1384 wmi_err("Failed to send vdev start command"); 1385 wmi_buf_free(buf); 1386 return QDF_STATUS_E_FAILURE; 1387 } 1388 1389 return QDF_STATUS_SUCCESS; 1390 } 1391 1392 /** 1393 * send_peer_flush_tids_cmd_tlv() - flush peer tids packets in fw 1394 * @wmi: wmi handle 1395 * @peer_addr: peer mac address 1396 * @param: pointer to hold peer flush tid parameter 1397 * 1398 * Return: 0 for success or error code 1399 */ 1400 static QDF_STATUS send_peer_flush_tids_cmd_tlv(wmi_unified_t wmi, 1401 uint8_t peer_addr[QDF_MAC_ADDR_SIZE], 1402 struct peer_flush_params *param) 1403 { 1404 wmi_peer_flush_tids_cmd_fixed_param *cmd; 1405 wmi_buf_t buf; 1406 int32_t len = sizeof(*cmd); 1407 1408 buf = wmi_buf_alloc(wmi, len); 1409 if (!buf) 1410 return QDF_STATUS_E_NOMEM; 1411 1412 cmd = (wmi_peer_flush_tids_cmd_fixed_param *) wmi_buf_data(buf); 1413 WMITLV_SET_HDR(&cmd->tlv_header, 1414 WMITLV_TAG_STRUC_wmi_peer_flush_tids_cmd_fixed_param, 1415 WMITLV_GET_STRUCT_TLVLEN 1416 (wmi_peer_flush_tids_cmd_fixed_param)); 1417 WMI_CHAR_ARRAY_TO_MAC_ADDR(peer_addr, &cmd->peer_macaddr); 1418 cmd->peer_tid_bitmap = param->peer_tid_bitmap; 1419 cmd->vdev_id = param->vdev_id; 1420 wmi_debug("peer_addr "QDF_MAC_ADDR_FMT" vdev_id %d and peer bitmap %d", 1421 QDF_MAC_ADDR_REF(peer_addr), param->vdev_id, 1422 param->peer_tid_bitmap); 1423 wmi_mtrace(WMI_PEER_FLUSH_TIDS_CMDID, cmd->vdev_id, 0); 1424 if (wmi_unified_cmd_send(wmi, buf, len, WMI_PEER_FLUSH_TIDS_CMDID)) { 1425 wmi_err("Failed to send flush tid command"); 1426 wmi_buf_free(buf); 1427 return QDF_STATUS_E_FAILURE; 1428 } 1429 1430 return 0; 1431 } 1432 1433 #ifdef WLAN_FEATURE_PEER_TXQ_FLUSH_CONF 1434 /** 1435 * map_to_wmi_flush_policy() - Map flush policy to firmware defined values 1436 * @policy: The target i/f flush policy value 1437 * 1438 * Return: WMI layer flush policy 1439 */ 1440 static wmi_peer_flush_policy 1441 map_to_wmi_flush_policy(enum peer_txq_flush_policy policy) 1442 { 1443 switch (policy) { 1444 case PEER_TXQ_FLUSH_POLICY_NONE: 1445 return WMI_NO_FLUSH; 1446 case PEER_TXQ_FLUSH_POLICY_TWT_SP_END: 1447 return WMI_TWT_FLUSH; 1448 default: 1449 return WMI_MAX_FLUSH_POLICY; 1450 } 1451 } 1452 1453 /** 1454 * send_peer_txq_flush_config_cmd_tlv() - Send peer TID queue flush config 1455 * @wmi: wmi handle 1456 * @para: Peer txq flush configuration 1457 * 1458 * Return: QDF status 1459 */ 1460 static QDF_STATUS 1461 send_peer_txq_flush_config_cmd_tlv(wmi_unified_t wmi, 1462 struct peer_txq_flush_config_params *param) 1463 { 1464 wmi_peer_flush_policy_cmd_fixed_param *cmd; 1465 wmi_buf_t buf; 1466 int32_t len = sizeof(*cmd); 1467 1468 buf = wmi_buf_alloc(wmi, len); 1469 if (!buf) 1470 return QDF_STATUS_E_NOMEM; 1471 1472 cmd = (wmi_peer_flush_policy_cmd_fixed_param *)wmi_buf_data(buf); 1473 1474 WMITLV_SET_HDR(&cmd->tlv_header, 1475 WMITLV_TAG_STRUC_wmi_peer_flush_policy_cmd_fixed_param, 1476 WMITLV_GET_STRUCT_TLVLEN 1477 (wmi_peer_flush_policy_cmd_fixed_param)); 1478 1479 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->peer, &cmd->peer_macaddr); 1480 cmd->peer_tid_bitmap = param->tid_mask; 1481 cmd->vdev_id = param->vdev_id; 1482 cmd->flush_policy = map_to_wmi_flush_policy(param->policy); 1483 if (cmd->flush_policy == WMI_MAX_FLUSH_POLICY) { 1484 wmi_buf_free(buf); 1485 wmi_err("Invalid policy"); 1486 return QDF_STATUS_E_INVAL; 1487 } 1488 wmi_debug("peer_addr " QDF_MAC_ADDR_FMT "vdev %d tid %x policy %d", 1489 QDF_MAC_ADDR_REF(param->peer), param->vdev_id, 1490 param->tid_mask, param->policy); 1491 wmi_mtrace(WMI_PEER_FLUSH_POLICY_CMDID, cmd->vdev_id, 0); 1492 if (wmi_unified_cmd_send(wmi, buf, len, WMI_PEER_FLUSH_POLICY_CMDID)) { 1493 wmi_err("Failed to send flush policy command"); 1494 wmi_buf_free(buf); 1495 return QDF_STATUS_E_FAILURE; 1496 } 1497 1498 return QDF_STATUS_SUCCESS; 1499 } 1500 #endif 1501 /** 1502 * send_peer_delete_cmd_tlv() - send PEER delete command to fw 1503 * @wmi: wmi handle 1504 * @peer_addr: peer mac addr 1505 * @param: peer delete parameters 1506 * 1507 * Return: QDF_STATUS_SUCCESS for success or error code 1508 */ 1509 static QDF_STATUS send_peer_delete_cmd_tlv(wmi_unified_t wmi, 1510 uint8_t peer_addr[QDF_MAC_ADDR_SIZE], 1511 struct peer_delete_cmd_params *param) 1512 { 1513 wmi_peer_delete_cmd_fixed_param *cmd; 1514 wmi_buf_t buf; 1515 int32_t len = sizeof(*cmd); 1516 uint8_t *buf_ptr; 1517 1518 len += peer_delete_mlo_params_size(param); 1519 buf = wmi_buf_alloc(wmi, len); 1520 if (!buf) 1521 return QDF_STATUS_E_NOMEM; 1522 1523 buf_ptr = (uint8_t *)wmi_buf_data(buf); 1524 cmd = (wmi_peer_delete_cmd_fixed_param *)buf_ptr; 1525 WMITLV_SET_HDR(&cmd->tlv_header, 1526 WMITLV_TAG_STRUC_wmi_peer_delete_cmd_fixed_param, 1527 WMITLV_GET_STRUCT_TLVLEN 1528 (wmi_peer_delete_cmd_fixed_param)); 1529 WMI_CHAR_ARRAY_TO_MAC_ADDR(peer_addr, &cmd->peer_macaddr); 1530 cmd->vdev_id = param->vdev_id; 1531 buf_ptr = (uint8_t *)(((uintptr_t) cmd) + sizeof(*cmd)); 1532 buf_ptr = peer_delete_add_mlo_params(buf_ptr, param); 1533 wmi_debug("peer_addr "QDF_MAC_ADDR_FMT" vdev_id %d", 1534 QDF_MAC_ADDR_REF(peer_addr), param->vdev_id); 1535 wmi_mtrace(WMI_PEER_DELETE_CMDID, cmd->vdev_id, 0); 1536 if (wmi_unified_cmd_send(wmi, buf, len, WMI_PEER_DELETE_CMDID)) { 1537 wmi_err("Failed to send peer delete command"); 1538 wmi_buf_free(buf); 1539 return QDF_STATUS_E_FAILURE; 1540 } 1541 return 0; 1542 } 1543 1544 static void 1545 wmi_get_converted_peer_bitmap(uint32_t src_peer_bitmap, uint32_t *dst_bitmap) 1546 { 1547 if (QDF_HAS_PARAM(src_peer_bitmap, WLAN_PEER_SELF)) 1548 WMI_VDEV_DELETE_ALL_PEER_BITMAP_SET(dst_bitmap, 1549 WMI_PEER_TYPE_DEFAULT); 1550 1551 if (QDF_HAS_PARAM(src_peer_bitmap, WLAN_PEER_AP)) 1552 WMI_VDEV_DELETE_ALL_PEER_BITMAP_SET(dst_bitmap, 1553 WMI_PEER_TYPE_BSS); 1554 1555 if (QDF_HAS_PARAM(src_peer_bitmap, WLAN_PEER_TDLS)) 1556 WMI_VDEV_DELETE_ALL_PEER_BITMAP_SET(dst_bitmap, 1557 WMI_PEER_TYPE_TDLS); 1558 1559 if (QDF_HAS_PARAM(src_peer_bitmap, WLAN_PEER_NDP)) 1560 WMI_VDEV_DELETE_ALL_PEER_BITMAP_SET(dst_bitmap, 1561 WMI_PEER_TYPE_NAN_DATA); 1562 1563 if (QDF_HAS_PARAM(src_peer_bitmap, WLAN_PEER_RTT_PASN)) 1564 WMI_VDEV_DELETE_ALL_PEER_BITMAP_SET(dst_bitmap, 1565 WMI_PEER_TYPE_PASN); 1566 } 1567 1568 /** 1569 * send_peer_delete_all_cmd_tlv() - send PEER delete all command to fw 1570 * @wmi: wmi handle 1571 * @param: pointer to hold peer delete all parameter 1572 * 1573 * Return: QDF_STATUS_SUCCESS for success or error code 1574 */ 1575 static QDF_STATUS send_peer_delete_all_cmd_tlv( 1576 wmi_unified_t wmi, 1577 struct peer_delete_all_params *param) 1578 { 1579 wmi_vdev_delete_all_peer_cmd_fixed_param *cmd; 1580 wmi_buf_t buf; 1581 int32_t len = sizeof(*cmd); 1582 1583 buf = wmi_buf_alloc(wmi, len); 1584 if (!buf) 1585 return QDF_STATUS_E_NOMEM; 1586 1587 cmd = (wmi_vdev_delete_all_peer_cmd_fixed_param *)wmi_buf_data(buf); 1588 WMITLV_SET_HDR( 1589 &cmd->tlv_header, 1590 WMITLV_TAG_STRUC_wmi_vdev_delete_all_peer_cmd_fixed_param, 1591 WMITLV_GET_STRUCT_TLVLEN 1592 (wmi_vdev_delete_all_peer_cmd_fixed_param)); 1593 cmd->vdev_id = param->vdev_id; 1594 wmi_get_converted_peer_bitmap(param->peer_type_bitmap, 1595 cmd->peer_type_bitmap); 1596 1597 wmi_debug("vdev_id %d peer_type_bitmap:%d", cmd->vdev_id, 1598 param->peer_type_bitmap); 1599 wmi_mtrace(WMI_VDEV_DELETE_ALL_PEER_CMDID, cmd->vdev_id, 0); 1600 if (wmi_unified_cmd_send(wmi, buf, len, 1601 WMI_VDEV_DELETE_ALL_PEER_CMDID)) { 1602 wmi_err("Failed to send peer del all command"); 1603 wmi_buf_free(buf); 1604 return QDF_STATUS_E_FAILURE; 1605 } 1606 1607 return QDF_STATUS_SUCCESS; 1608 } 1609 1610 /** 1611 * convert_host_peer_param_id_to_target_id_tlv - convert host peer param_id 1612 * to target id. 1613 * @peer_param_id: host param id. 1614 * 1615 * Return: Target param id. 1616 */ 1617 #ifdef ENABLE_HOST_TO_TARGET_CONVERSION 1618 static inline uint32_t convert_host_peer_param_id_to_target_id_tlv( 1619 uint32_t peer_param_id) 1620 { 1621 if (peer_param_id < QDF_ARRAY_SIZE(peer_param_tlv)) 1622 return peer_param_tlv[peer_param_id]; 1623 return WMI_UNAVAILABLE_PARAM; 1624 } 1625 #else 1626 static inline uint32_t convert_host_peer_param_id_to_target_id_tlv( 1627 uint32_t peer_param_id) 1628 { 1629 return peer_param_id; 1630 } 1631 #endif 1632 1633 /** 1634 * wmi_host_chan_bw_to_target_chan_bw - convert wmi_host_channel_width to 1635 * wmi_channel_width 1636 * @bw: wmi_host_channel_width channel width 1637 * 1638 * Return: wmi_channel_width 1639 */ 1640 static wmi_channel_width wmi_host_chan_bw_to_target_chan_bw( 1641 wmi_host_channel_width bw) 1642 { 1643 wmi_channel_width target_bw = WMI_CHAN_WIDTH_20; 1644 1645 switch (bw) { 1646 case WMI_HOST_CHAN_WIDTH_20: 1647 target_bw = WMI_CHAN_WIDTH_20; 1648 break; 1649 case WMI_HOST_CHAN_WIDTH_40: 1650 target_bw = WMI_CHAN_WIDTH_40; 1651 break; 1652 case WMI_HOST_CHAN_WIDTH_80: 1653 target_bw = WMI_CHAN_WIDTH_80; 1654 break; 1655 case WMI_HOST_CHAN_WIDTH_160: 1656 target_bw = WMI_CHAN_WIDTH_160; 1657 break; 1658 case WMI_HOST_CHAN_WIDTH_80P80: 1659 target_bw = WMI_CHAN_WIDTH_80P80; 1660 break; 1661 case WMI_HOST_CHAN_WIDTH_5: 1662 target_bw = WMI_CHAN_WIDTH_5; 1663 break; 1664 case WMI_HOST_CHAN_WIDTH_10: 1665 target_bw = WMI_CHAN_WIDTH_10; 1666 break; 1667 case WMI_HOST_CHAN_WIDTH_165: 1668 target_bw = WMI_CHAN_WIDTH_165; 1669 break; 1670 case WMI_HOST_CHAN_WIDTH_160P160: 1671 target_bw = WMI_CHAN_WIDTH_160P160; 1672 break; 1673 case WMI_HOST_CHAN_WIDTH_320: 1674 target_bw = WMI_CHAN_WIDTH_320; 1675 break; 1676 default: 1677 break; 1678 } 1679 1680 return target_bw; 1681 } 1682 1683 /** 1684 * convert_host_peer_param_value_to_target_value_tlv() - convert host peer 1685 * param value to target 1686 * @param_id: target param id 1687 * @param_value: host param value 1688 * 1689 * @Return: target param value 1690 */ 1691 static uint32_t convert_host_peer_param_value_to_target_value_tlv( 1692 uint32_t param_id, uint32_t param_value) 1693 { 1694 uint32_t fw_param_value = 0; 1695 wmi_host_channel_width bw; 1696 uint16_t punc; 1697 1698 switch (param_id) { 1699 case WMI_PEER_CHWIDTH_PUNCTURE_20MHZ_BITMAP: 1700 bw = QDF_GET_BITS(param_value, 0, 8); 1701 punc = QDF_GET_BITS(param_value, 8, 16); 1702 QDF_SET_BITS(fw_param_value, 0, 8, 1703 wmi_host_chan_bw_to_target_chan_bw(bw)); 1704 QDF_SET_BITS(fw_param_value, 8, 16, ~punc); 1705 break; 1706 default: 1707 fw_param_value = param_value; 1708 break; 1709 } 1710 1711 return fw_param_value; 1712 } 1713 1714 #ifdef WLAN_SUPPORT_PPEDS 1715 /** 1716 * peer_ppe_ds_param_send_tlv() - Set peer PPE DS config 1717 * @wmi: wmi handle 1718 * @param: pointer to hold PPE DS config 1719 * 1720 * Return: QDF_STATUS_SUCCESS for success or error code 1721 */ 1722 static QDF_STATUS peer_ppe_ds_param_send_tlv(wmi_unified_t wmi, 1723 struct peer_ppe_ds_param *param) 1724 { 1725 wmi_peer_config_ppe_ds_cmd_fixed_param *cmd; 1726 wmi_buf_t buf; 1727 int32_t err; 1728 uint32_t len = sizeof(wmi_peer_config_ppe_ds_cmd_fixed_param); 1729 1730 buf = wmi_buf_alloc(wmi, sizeof(*cmd)); 1731 if (!buf) 1732 return QDF_STATUS_E_NOMEM; 1733 1734 cmd = (wmi_peer_config_ppe_ds_cmd_fixed_param *)wmi_buf_data(buf); 1735 WMITLV_SET_HDR(&cmd->tlv_header, 1736 WMITLV_TAG_STRUC_wmi_peer_config_ppe_ds_cmd_fixed_param, 1737 WMITLV_GET_STRUCT_TLVLEN 1738 (wmi_peer_config_ppe_ds_cmd_fixed_param)); 1739 1740 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->peer_macaddr, &cmd->peer_macaddr); 1741 1742 if (param->ppe_routing_enabled) 1743 cmd->ppe_routing_enable = param->use_ppe ? 1744 WMI_AST_USE_PPE_ENABLED : WMI_AST_USE_PPE_DISABLED; 1745 else 1746 cmd->ppe_routing_enable = WMI_PPE_ROUTING_DISABLED; 1747 1748 cmd->service_code = param->service_code; 1749 cmd->priority_valid = param->priority_valid; 1750 cmd->src_info = param->src_info; 1751 cmd->vdev_id = param->vdev_id; 1752 1753 wmi_debug("vdev_id %d peer_mac: QDF_MAC_ADDR_FMT\n" 1754 "ppe_routing_enable: %u service_code: %u\n" 1755 "priority_valid:%d src_info:%u", 1756 param->vdev_id, 1757 QDF_MAC_ADDR_REF(param->peer_macaddr), 1758 param->ppe_routing_enabled, 1759 param->service_code, 1760 param->priority_valid, 1761 param->src_info); 1762 1763 wmi_mtrace(WMI_PEER_CONFIG_PPE_DS_CMDID, cmd->vdev_id, 0); 1764 err = wmi_unified_cmd_send(wmi, buf, 1765 len, 1766 WMI_PEER_CONFIG_PPE_DS_CMDID); 1767 if (err) { 1768 wmi_err("Failed to send ppeds config cmd"); 1769 wmi_buf_free(buf); 1770 return QDF_STATUS_E_FAILURE; 1771 } 1772 1773 return 0; 1774 } 1775 #endif /* WLAN_SUPPORT_PPEDS */ 1776 1777 /** 1778 * send_peer_param_cmd_tlv() - set peer parameter in fw 1779 * @wmi: wmi handle 1780 * @peer_addr: peer mac address 1781 * @param : pointer to hold peer set parameter 1782 * 1783 * Return: QDF_STATUS_SUCCESS for success or error code 1784 */ 1785 static QDF_STATUS send_peer_param_cmd_tlv(wmi_unified_t wmi, 1786 uint8_t peer_addr[QDF_MAC_ADDR_SIZE], 1787 struct peer_set_params *param) 1788 { 1789 wmi_peer_set_param_cmd_fixed_param *cmd; 1790 wmi_buf_t buf; 1791 int32_t err; 1792 uint32_t param_id; 1793 uint32_t param_value; 1794 1795 param_id = convert_host_peer_param_id_to_target_id_tlv(param->param_id); 1796 if (param_id == WMI_UNAVAILABLE_PARAM) { 1797 wmi_err("Unavailable param %d", param->param_id); 1798 return QDF_STATUS_E_NOSUPPORT; 1799 } 1800 param_value = convert_host_peer_param_value_to_target_value_tlv( 1801 param_id, param->param_value); 1802 buf = wmi_buf_alloc(wmi, sizeof(*cmd)); 1803 if (!buf) 1804 return QDF_STATUS_E_NOMEM; 1805 1806 cmd = (wmi_peer_set_param_cmd_fixed_param *) wmi_buf_data(buf); 1807 WMITLV_SET_HDR(&cmd->tlv_header, 1808 WMITLV_TAG_STRUC_wmi_peer_set_param_cmd_fixed_param, 1809 WMITLV_GET_STRUCT_TLVLEN 1810 (wmi_peer_set_param_cmd_fixed_param)); 1811 cmd->vdev_id = param->vdev_id; 1812 WMI_CHAR_ARRAY_TO_MAC_ADDR(peer_addr, &cmd->peer_macaddr); 1813 cmd->param_id = param_id; 1814 cmd->param_value = param_value; 1815 1816 wmi_debug("vdev_id %d peer_mac: "QDF_MAC_ADDR_FMT" param_id: %u param_value: %x", 1817 cmd->vdev_id, 1818 QDF_MAC_ADDR_REF(peer_addr), param->param_id, 1819 cmd->param_value); 1820 1821 wmi_mtrace(WMI_PEER_SET_PARAM_CMDID, cmd->vdev_id, 0); 1822 err = wmi_unified_cmd_send(wmi, buf, 1823 sizeof(wmi_peer_set_param_cmd_fixed_param), 1824 WMI_PEER_SET_PARAM_CMDID); 1825 if (err) { 1826 wmi_err("Failed to send set_param cmd"); 1827 wmi_buf_free(buf); 1828 return QDF_STATUS_E_FAILURE; 1829 } 1830 1831 return 0; 1832 } 1833 1834 /** 1835 * send_vdev_up_cmd_tlv() - send vdev up command in fw 1836 * @wmi: wmi handle 1837 * @bssid: bssid 1838 * @vdev_up_params: pointer to hold vdev up parameter 1839 * 1840 * Return: QDF_STATUS_SUCCESS for success or error code 1841 */ 1842 static QDF_STATUS send_vdev_up_cmd_tlv(wmi_unified_t wmi, 1843 uint8_t bssid[QDF_MAC_ADDR_SIZE], 1844 struct vdev_up_params *params) 1845 { 1846 wmi_vdev_up_cmd_fixed_param *cmd; 1847 wmi_buf_t buf; 1848 int32_t len = sizeof(*cmd); 1849 1850 wmi_debug("VDEV_UP"); 1851 wmi_debug("vdev_id %d aid %d bssid "QDF_MAC_ADDR_FMT, 1852 params->vdev_id, params->assoc_id, QDF_MAC_ADDR_REF(bssid)); 1853 buf = wmi_buf_alloc(wmi, len); 1854 if (!buf) 1855 return QDF_STATUS_E_NOMEM; 1856 1857 cmd = (wmi_vdev_up_cmd_fixed_param *) wmi_buf_data(buf); 1858 WMITLV_SET_HDR(&cmd->tlv_header, 1859 WMITLV_TAG_STRUC_wmi_vdev_up_cmd_fixed_param, 1860 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_up_cmd_fixed_param)); 1861 cmd->vdev_id = params->vdev_id; 1862 cmd->vdev_assoc_id = params->assoc_id; 1863 cmd->profile_idx = params->profile_idx; 1864 cmd->profile_num = params->profile_num; 1865 WMI_CHAR_ARRAY_TO_MAC_ADDR(params->trans_bssid, &cmd->trans_bssid); 1866 WMI_CHAR_ARRAY_TO_MAC_ADDR(bssid, &cmd->vdev_bssid); 1867 wmi_mtrace(WMI_VDEV_UP_CMDID, cmd->vdev_id, 0); 1868 if (wmi_unified_cmd_send(wmi, buf, len, WMI_VDEV_UP_CMDID)) { 1869 wmi_err("Failed to send vdev up command"); 1870 wmi_buf_free(buf); 1871 return QDF_STATUS_E_FAILURE; 1872 } 1873 1874 return 0; 1875 } 1876 1877 #ifdef ENABLE_HOST_TO_TARGET_CONVERSION 1878 static uint32_t convert_peer_type_host_to_target(uint32_t peer_type) 1879 { 1880 /* Host sets the peer_type as 0 for the peer create command sent to FW 1881 * other than PASN peer create command. 1882 */ 1883 if (peer_type == WLAN_PEER_RTT_PASN) 1884 return WMI_PEER_TYPE_PASN; 1885 1886 return peer_type; 1887 } 1888 #else 1889 static uint32_t convert_peer_type_host_to_target(uint32_t peer_type) 1890 { 1891 return peer_type; 1892 } 1893 #endif 1894 /** 1895 * send_peer_create_cmd_tlv() - send peer create command to fw 1896 * @wmi: wmi handle 1897 * @peer_addr: peer mac address 1898 * @peer_type: peer type 1899 * @vdev_id: vdev id 1900 * 1901 * Return: QDF_STATUS_SUCCESS for success or error code 1902 */ 1903 static QDF_STATUS send_peer_create_cmd_tlv(wmi_unified_t wmi, 1904 struct peer_create_params *param) 1905 { 1906 wmi_peer_create_cmd_fixed_param *cmd; 1907 wmi_buf_t buf; 1908 uint8_t *buf_ptr; 1909 int32_t len = sizeof(*cmd); 1910 1911 len += peer_create_mlo_params_size(param); 1912 buf = wmi_buf_alloc(wmi, len); 1913 if (!buf) 1914 return QDF_STATUS_E_NOMEM; 1915 1916 cmd = (wmi_peer_create_cmd_fixed_param *) wmi_buf_data(buf); 1917 WMITLV_SET_HDR(&cmd->tlv_header, 1918 WMITLV_TAG_STRUC_wmi_peer_create_cmd_fixed_param, 1919 WMITLV_GET_STRUCT_TLVLEN 1920 (wmi_peer_create_cmd_fixed_param)); 1921 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->peer_addr, &cmd->peer_macaddr); 1922 cmd->peer_type = convert_peer_type_host_to_target(param->peer_type); 1923 cmd->vdev_id = param->vdev_id; 1924 1925 buf_ptr = (uint8_t *)wmi_buf_data(buf); 1926 buf_ptr += sizeof(*cmd); 1927 buf_ptr = peer_create_add_mlo_params(buf_ptr, param); 1928 wmi_mtrace(WMI_PEER_CREATE_CMDID, cmd->vdev_id, 0); 1929 if (wmi_unified_cmd_send(wmi, buf, len, WMI_PEER_CREATE_CMDID)) { 1930 wmi_err("Failed to send WMI_PEER_CREATE_CMDID"); 1931 wmi_buf_free(buf); 1932 return QDF_STATUS_E_FAILURE; 1933 } 1934 wmi_debug("peer_addr "QDF_MAC_ADDR_FMT" vdev_id %d", 1935 QDF_MAC_ADDR_REF(param->peer_addr), 1936 param->vdev_id); 1937 1938 return 0; 1939 } 1940 1941 /** 1942 * send_peer_rx_reorder_queue_setup_cmd_tlv() - send rx reorder setup 1943 * command to fw 1944 * @wmi: wmi handle 1945 * @rx_reorder_queue_setup_params: Rx reorder queue setup parameters 1946 * 1947 * Return: 0 for success or error code 1948 */ 1949 static 1950 QDF_STATUS send_peer_rx_reorder_queue_setup_cmd_tlv(wmi_unified_t wmi, 1951 struct rx_reorder_queue_setup_params *param) 1952 { 1953 wmi_peer_reorder_queue_setup_cmd_fixed_param *cmd; 1954 wmi_buf_t buf; 1955 int32_t len = sizeof(*cmd); 1956 1957 buf = wmi_buf_alloc(wmi, len); 1958 if (!buf) 1959 return QDF_STATUS_E_NOMEM; 1960 1961 cmd = (wmi_peer_reorder_queue_setup_cmd_fixed_param *)wmi_buf_data(buf); 1962 WMITLV_SET_HDR(&cmd->tlv_header, 1963 WMITLV_TAG_STRUC_wmi_peer_reorder_queue_setup_cmd_fixed_param, 1964 WMITLV_GET_STRUCT_TLVLEN 1965 (wmi_peer_reorder_queue_setup_cmd_fixed_param)); 1966 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->peer_macaddr, &cmd->peer_macaddr); 1967 cmd->vdev_id = param->vdev_id; 1968 cmd->tid = param->tid; 1969 cmd->queue_ptr_lo = param->hw_qdesc_paddr_lo; 1970 cmd->queue_ptr_hi = param->hw_qdesc_paddr_hi; 1971 cmd->queue_no = param->queue_no; 1972 cmd->ba_window_size_valid = param->ba_window_size_valid; 1973 cmd->ba_window_size = param->ba_window_size; 1974 1975 1976 wmi_mtrace(WMI_PEER_REORDER_QUEUE_SETUP_CMDID, cmd->vdev_id, 0); 1977 if (wmi_unified_cmd_send(wmi, buf, len, 1978 WMI_PEER_REORDER_QUEUE_SETUP_CMDID)) { 1979 wmi_err("Fail to send WMI_PEER_REORDER_QUEUE_SETUP_CMDID"); 1980 wmi_buf_free(buf); 1981 return QDF_STATUS_E_FAILURE; 1982 } 1983 wmi_debug("peer_macaddr "QDF_MAC_ADDR_FMT" vdev_id %d, tid %d", 1984 QDF_MAC_ADDR_REF(param->peer_macaddr), 1985 param->vdev_id, param->tid); 1986 1987 return QDF_STATUS_SUCCESS; 1988 } 1989 1990 /** 1991 * send_peer_rx_reorder_queue_remove_cmd_tlv() - send rx reorder remove 1992 * command to fw 1993 * @wmi: wmi handle 1994 * @rx_reorder_queue_remove_params: Rx reorder queue remove parameters 1995 * 1996 * Return: 0 for success or error code 1997 */ 1998 static 1999 QDF_STATUS send_peer_rx_reorder_queue_remove_cmd_tlv(wmi_unified_t wmi, 2000 struct rx_reorder_queue_remove_params *param) 2001 { 2002 wmi_peer_reorder_queue_remove_cmd_fixed_param *cmd; 2003 wmi_buf_t buf; 2004 int32_t len = sizeof(*cmd); 2005 2006 buf = wmi_buf_alloc(wmi, len); 2007 if (!buf) 2008 return QDF_STATUS_E_NOMEM; 2009 2010 cmd = (wmi_peer_reorder_queue_remove_cmd_fixed_param *) 2011 wmi_buf_data(buf); 2012 WMITLV_SET_HDR(&cmd->tlv_header, 2013 WMITLV_TAG_STRUC_wmi_peer_reorder_queue_remove_cmd_fixed_param, 2014 WMITLV_GET_STRUCT_TLVLEN 2015 (wmi_peer_reorder_queue_remove_cmd_fixed_param)); 2016 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->peer_macaddr, &cmd->peer_macaddr); 2017 cmd->vdev_id = param->vdev_id; 2018 cmd->tid_mask = param->peer_tid_bitmap; 2019 2020 wmi_mtrace(WMI_PEER_REORDER_QUEUE_REMOVE_CMDID, cmd->vdev_id, 0); 2021 if (wmi_unified_cmd_send(wmi, buf, len, 2022 WMI_PEER_REORDER_QUEUE_REMOVE_CMDID)) { 2023 wmi_err("Fail to send WMI_PEER_REORDER_QUEUE_REMOVE_CMDID"); 2024 wmi_buf_free(buf); 2025 return QDF_STATUS_E_FAILURE; 2026 } 2027 wmi_debug("peer_macaddr "QDF_MAC_ADDR_FMT" vdev_id %d, tid_map %d", 2028 QDF_MAC_ADDR_REF(param->peer_macaddr), 2029 param->vdev_id, param->peer_tid_bitmap); 2030 2031 return QDF_STATUS_SUCCESS; 2032 } 2033 2034 #ifdef WLAN_SUPPORT_GREEN_AP 2035 /** 2036 * send_green_ap_ps_cmd_tlv() - enable green ap powersave command 2037 * @wmi_handle: wmi handle 2038 * @value: value 2039 * @pdev_id: pdev id to have radio context 2040 * 2041 * Return: QDF_STATUS_SUCCESS for success or error code 2042 */ 2043 static QDF_STATUS send_green_ap_ps_cmd_tlv(wmi_unified_t wmi_handle, 2044 uint32_t value, uint8_t pdev_id) 2045 { 2046 wmi_pdev_green_ap_ps_enable_cmd_fixed_param *cmd; 2047 wmi_buf_t buf; 2048 int32_t len = sizeof(*cmd); 2049 2050 wmi_debug("Set Green AP PS val %d", value); 2051 2052 buf = wmi_buf_alloc(wmi_handle, len); 2053 if (!buf) 2054 return QDF_STATUS_E_NOMEM; 2055 2056 cmd = (wmi_pdev_green_ap_ps_enable_cmd_fixed_param *) wmi_buf_data(buf); 2057 WMITLV_SET_HDR(&cmd->tlv_header, 2058 WMITLV_TAG_STRUC_wmi_pdev_green_ap_ps_enable_cmd_fixed_param, 2059 WMITLV_GET_STRUCT_TLVLEN 2060 (wmi_pdev_green_ap_ps_enable_cmd_fixed_param)); 2061 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 2062 wmi_handle, 2063 pdev_id); 2064 cmd->enable = value; 2065 2066 wmi_mtrace(WMI_PDEV_GREEN_AP_PS_ENABLE_CMDID, NO_SESSION, 0); 2067 if (wmi_unified_cmd_send(wmi_handle, buf, len, 2068 WMI_PDEV_GREEN_AP_PS_ENABLE_CMDID)) { 2069 wmi_err("Set Green AP PS param Failed val %d", value); 2070 wmi_buf_free(buf); 2071 return QDF_STATUS_E_FAILURE; 2072 } 2073 2074 return 0; 2075 } 2076 #endif 2077 2078 /** 2079 * send_pdev_utf_cmd_tlv() - send utf command to fw 2080 * @wmi_handle: wmi handle 2081 * @param: pointer to pdev_utf_params 2082 * @mac_id: mac id to have radio context 2083 * 2084 * Return: QDF_STATUS_SUCCESS for success or error code 2085 */ 2086 static QDF_STATUS 2087 send_pdev_utf_cmd_tlv(wmi_unified_t wmi_handle, 2088 struct pdev_utf_params *param, 2089 uint8_t mac_id) 2090 { 2091 wmi_buf_t buf; 2092 uint8_t *cmd; 2093 /* if param->len is 0 no data is sent, return error */ 2094 QDF_STATUS ret = QDF_STATUS_E_INVAL; 2095 static uint8_t msgref = 1; 2096 uint8_t segNumber = 0, segInfo, numSegments; 2097 uint16_t chunk_len, total_bytes; 2098 uint8_t *bufpos; 2099 struct seg_hdr_info segHdrInfo; 2100 2101 bufpos = param->utf_payload; 2102 total_bytes = param->len; 2103 ASSERT(total_bytes / MAX_WMI_UTF_LEN == 2104 (uint8_t) (total_bytes / MAX_WMI_UTF_LEN)); 2105 numSegments = (uint8_t) (total_bytes / MAX_WMI_UTF_LEN); 2106 2107 if (param->len - (numSegments * MAX_WMI_UTF_LEN)) 2108 numSegments++; 2109 2110 while (param->len) { 2111 if (param->len > MAX_WMI_UTF_LEN) 2112 chunk_len = MAX_WMI_UTF_LEN; /* MAX message */ 2113 else 2114 chunk_len = param->len; 2115 2116 buf = wmi_buf_alloc(wmi_handle, 2117 (chunk_len + sizeof(segHdrInfo) + 2118 WMI_TLV_HDR_SIZE)); 2119 if (!buf) 2120 return QDF_STATUS_E_NOMEM; 2121 2122 cmd = (uint8_t *) wmi_buf_data(buf); 2123 2124 segHdrInfo.len = total_bytes; 2125 segHdrInfo.msgref = msgref; 2126 segInfo = ((numSegments << 4) & 0xF0) | (segNumber & 0xF); 2127 segHdrInfo.segmentInfo = segInfo; 2128 segHdrInfo.pad = 0; 2129 2130 wmi_debug("segHdrInfo.len = %d, segHdrInfo.msgref = %d," 2131 " segHdrInfo.segmentInfo = %d", 2132 segHdrInfo.len, segHdrInfo.msgref, 2133 segHdrInfo.segmentInfo); 2134 2135 wmi_debug("total_bytes %d segNumber %d totalSegments %d" 2136 " chunk len %d", total_bytes, segNumber, 2137 numSegments, chunk_len); 2138 2139 segNumber++; 2140 2141 WMITLV_SET_HDR(cmd, WMITLV_TAG_ARRAY_BYTE, 2142 (chunk_len + sizeof(segHdrInfo))); 2143 cmd += WMI_TLV_HDR_SIZE; 2144 memcpy(cmd, &segHdrInfo, sizeof(segHdrInfo)); /* 4 bytes */ 2145 WMI_HOST_IF_MSG_COPY_CHAR_ARRAY(&cmd[sizeof(segHdrInfo)], 2146 bufpos, chunk_len); 2147 2148 wmi_mtrace(WMI_PDEV_UTF_CMDID, NO_SESSION, 0); 2149 ret = wmi_unified_cmd_send(wmi_handle, buf, 2150 (chunk_len + sizeof(segHdrInfo) + 2151 WMI_TLV_HDR_SIZE), 2152 WMI_PDEV_UTF_CMDID); 2153 2154 if (QDF_IS_STATUS_ERROR(ret)) { 2155 wmi_err("Failed to send WMI_PDEV_UTF_CMDID command"); 2156 wmi_buf_free(buf); 2157 break; 2158 } 2159 2160 param->len -= chunk_len; 2161 bufpos += chunk_len; 2162 } 2163 2164 msgref++; 2165 2166 return ret; 2167 } 2168 2169 #ifdef ENABLE_HOST_TO_TARGET_CONVERSION 2170 static inline uint32_t convert_host_pdev_param_tlv(uint32_t host_param) 2171 { 2172 if (host_param < QDF_ARRAY_SIZE(pdev_param_tlv)) 2173 return pdev_param_tlv[host_param]; 2174 return WMI_UNAVAILABLE_PARAM; 2175 } 2176 2177 static inline uint32_t convert_host_vdev_param_tlv(uint32_t host_param) 2178 { 2179 if (host_param < QDF_ARRAY_SIZE(vdev_param_tlv)) 2180 return vdev_param_tlv[host_param]; 2181 return WMI_UNAVAILABLE_PARAM; 2182 } 2183 #else 2184 static inline uint32_t convert_host_pdev_param_tlv(uint32_t host_param) 2185 { 2186 return host_param; 2187 } 2188 2189 static inline uint32_t convert_host_vdev_param_tlv(uint32_t host_param) 2190 { 2191 return host_param; 2192 } 2193 #endif /* end of ENABLE_HOST_TO_TARGET_CONVERSION */ 2194 2195 /** 2196 * send_pdev_param_cmd_tlv() - set pdev parameters 2197 * @wmi_handle: wmi handle 2198 * @param: pointer to pdev parameter 2199 * @mac_id: radio context 2200 * 2201 * Return: 0 on success, errno on failure 2202 */ 2203 static QDF_STATUS 2204 send_pdev_param_cmd_tlv(wmi_unified_t wmi_handle, 2205 struct pdev_params *param, 2206 uint8_t mac_id) 2207 { 2208 QDF_STATUS ret; 2209 wmi_pdev_set_param_cmd_fixed_param *cmd; 2210 wmi_buf_t buf; 2211 uint16_t len = sizeof(*cmd); 2212 uint32_t pdev_param; 2213 2214 pdev_param = convert_host_pdev_param_tlv(param->param_id); 2215 if (pdev_param == WMI_UNAVAILABLE_PARAM) { 2216 wmi_err("Unavailable param %d", param->param_id); 2217 return QDF_STATUS_E_INVAL; 2218 } 2219 2220 buf = wmi_buf_alloc(wmi_handle, len); 2221 if (!buf) 2222 return QDF_STATUS_E_NOMEM; 2223 2224 cmd = (wmi_pdev_set_param_cmd_fixed_param *) wmi_buf_data(buf); 2225 WMITLV_SET_HDR(&cmd->tlv_header, 2226 WMITLV_TAG_STRUC_wmi_pdev_set_param_cmd_fixed_param, 2227 WMITLV_GET_STRUCT_TLVLEN 2228 (wmi_pdev_set_param_cmd_fixed_param)); 2229 if (param->is_host_pdev_id) 2230 cmd->pdev_id = wmi_handle->ops->convert_host_pdev_id_to_target( 2231 wmi_handle, 2232 mac_id); 2233 else 2234 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 2235 wmi_handle, 2236 mac_id); 2237 cmd->param_id = pdev_param; 2238 cmd->param_value = param->param_value; 2239 wmi_debug("Setting pdev %d param = %x, value = %u", cmd->pdev_id, 2240 cmd->param_id, cmd->param_value); 2241 wmi_mtrace(WMI_PDEV_SET_PARAM_CMDID, NO_SESSION, 0); 2242 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 2243 WMI_PDEV_SET_PARAM_CMDID); 2244 if (QDF_IS_STATUS_ERROR(ret)) { 2245 wmi_err("Failed to send set param command ret = %d", ret); 2246 wmi_buf_free(buf); 2247 } 2248 return ret; 2249 } 2250 2251 /** 2252 * send_multi_param_cmd_using_pdev_set_param_tlv() - set pdev parameters 2253 * @wmi_handle: wmi handle 2254 * @params: pointer to hold set_multiple_pdev_vdev_param info 2255 * 2256 * Return: 0 on success, errno on failure 2257 */ 2258 static QDF_STATUS 2259 send_multi_param_cmd_using_pdev_set_param_tlv(wmi_unified_t wmi_handle, 2260 struct set_multiple_pdev_vdev_param *params) 2261 { 2262 uint8_t index; 2263 struct pdev_params pdevparam; 2264 uint8_t n_params = params->n_params; 2265 2266 pdevparam.is_host_pdev_id = params->is_host_pdev_id; 2267 for (index = 0; index < n_params; index++) { 2268 pdevparam.param_id = params->params[index].param_id; 2269 pdevparam.param_value = params->params[index].param_value; 2270 if (QDF_IS_STATUS_ERROR(send_pdev_param_cmd_tlv(wmi_handle, 2271 &pdevparam, 2272 params->dev_id))) { 2273 wmi_err("failed to send pdev setparam:%d", 2274 pdevparam.param_id); 2275 return QDF_STATUS_E_FAILURE; 2276 } 2277 } 2278 return QDF_STATUS_SUCCESS; 2279 } 2280 2281 #ifdef WLAN_PDEV_VDEV_SEND_MULTI_PARAM 2282 2283 /** 2284 * convert_host_pdev_vdev_param_id_to_target()- convert host params to target params 2285 * @params: pointer to point set_multiple_pdev_vdev_param info 2286 * 2287 * Return: returns QDF_STATUS 2288 */ 2289 static QDF_STATUS 2290 convert_host_pdev_vdev_param_id_to_target(struct set_multiple_pdev_vdev_param *params) 2291 { 2292 uint8_t index; 2293 uint32_t dev_paramid; 2294 uint8_t num = params->n_params; 2295 2296 if (params->param_type == MLME_PDEV_SETPARAM) { 2297 for (index = 0; index < num; index++) { 2298 dev_paramid = convert_host_pdev_param_tlv(params->params[index].param_id); 2299 if (dev_paramid == WMI_UNAVAILABLE_PARAM) { 2300 wmi_err("pdev param %d not available", 2301 params->params[index].param_id); 2302 return QDF_STATUS_E_INVAL; 2303 } 2304 params->params[index].param_id = dev_paramid; 2305 } 2306 } else if (params->param_type == MLME_VDEV_SETPARAM) { 2307 for (index = 0; index < num; index++) { 2308 dev_paramid = convert_host_vdev_param_tlv(params->params[index].param_id); 2309 if (dev_paramid == WMI_UNAVAILABLE_PARAM) { 2310 wmi_err("vdev param %d not available", 2311 params->params[index].param_id); 2312 return QDF_STATUS_E_INVAL; 2313 } 2314 params->params[index].param_id = dev_paramid; 2315 } 2316 } else { 2317 wmi_err("invalid param type"); 2318 return QDF_STATUS_E_INVAL; 2319 } 2320 return QDF_STATUS_SUCCESS; 2321 } 2322 2323 /** 2324 * send_dev_multi_setparam_cmd_tlv()-to print the paramid and param value 2325 * @setparam: buffer pointer where host is filling paramsid and value 2326 * @params: pointer to hold set_multiple_pdev_vdev_param info 2327 * 2328 */ 2329 static void send_dev_multi_setparam_cmd_tlv(wmi_set_param_info *setparam, 2330 struct set_multiple_pdev_vdev_param *params) 2331 { 2332 if (params->param_type == MLME_VDEV_SETPARAM) { 2333 wmi_debug("Setting vdev %d param = %x value = %u", params->dev_id, 2334 setparam->param_id, setparam->param_value); 2335 } else { 2336 wmi_debug("Setting pdev %d param = %x value = %u", 2337 params->dev_id, setparam->param_id, setparam->param_value); 2338 } 2339 } 2340 2341 /** 2342 * send_multi_pdev_vdev_set_param_cmd_tlv()-set pdev/vdev params 2343 * @wmi_handle: wmi handle 2344 * @params: pointer to hold set_multiple_pdev_vdev_param info 2345 * 2346 * Return: returns QDF_STATUS 2347 */ 2348 static QDF_STATUS 2349 send_multi_pdev_vdev_set_param_cmd_tlv( 2350 wmi_unified_t wmi_handle, 2351 struct set_multiple_pdev_vdev_param *params) 2352 { 2353 uint8_t *buf_ptr; 2354 QDF_STATUS ret; 2355 wmi_buf_t buf; 2356 wmi_set_param_info *setparam; 2357 wmi_set_multiple_pdev_vdev_param_cmd_fixed_param *cmd; 2358 uint8_t num = params->n_params; 2359 uint16_t len; 2360 uint8_t index = 0; 2361 2362 if (convert_host_pdev_vdev_param_id_to_target(params)) 2363 return QDF_STATUS_E_INVAL; 2364 2365 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE + (num * sizeof(*setparam)); 2366 buf = wmi_buf_alloc(wmi_handle, len); 2367 if (!buf) 2368 return QDF_STATUS_E_NOMEM; 2369 2370 buf_ptr = (uint8_t *)wmi_buf_data(buf); 2371 cmd = (wmi_set_multiple_pdev_vdev_param_cmd_fixed_param *)buf_ptr; 2372 2373 WMITLV_SET_HDR(&cmd->tlv_header, 2374 WMITLV_TAG_STRUC_wmi_set_multiple_pdev_vdev_param_cmd_fixed_param, 2375 WMITLV_GET_STRUCT_TLVLEN(wmi_set_multiple_pdev_vdev_param_cmd_fixed_param)); 2376 2377 cmd->is_vdev = params->param_type; 2378 if (params->param_type == MLME_PDEV_SETPARAM) { 2379 if (params->is_host_pdev_id) 2380 params->dev_id = wmi_handle->ops->convert_host_pdev_id_to_target(wmi_handle, 2381 params->dev_id); 2382 else 2383 params->dev_id = wmi_handle->ops->convert_pdev_id_host_to_target(wmi_handle, 2384 params->dev_id); 2385 } 2386 cmd->dev_id = params->dev_id; 2387 buf_ptr += sizeof(wmi_set_multiple_pdev_vdev_param_cmd_fixed_param); 2388 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, (num * sizeof(*setparam))); 2389 buf_ptr += WMI_TLV_HDR_SIZE; 2390 for (index = 0; index < num; index++) { 2391 setparam = (wmi_set_param_info *)buf_ptr; 2392 WMITLV_SET_HDR(&setparam->tlv_header, 2393 WMITLV_TAG_STRUC_wmi_set_param_info, 2394 WMITLV_GET_STRUCT_TLVLEN(*setparam)); 2395 setparam->param_id = params->params[index].param_id; 2396 setparam->param_value = params->params[index].param_value; 2397 send_dev_multi_setparam_cmd_tlv(setparam, params); 2398 buf_ptr += sizeof(*setparam); 2399 } 2400 wmi_mtrace(WMI_SET_MULTIPLE_PDEV_VDEV_PARAM_CMDID, 2401 cmd->dev_id, 0); 2402 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 2403 WMI_SET_MULTIPLE_PDEV_VDEV_PARAM_CMDID); 2404 if (QDF_IS_STATUS_ERROR(ret)) { 2405 wmi_err("failed to send WMI_SET_MULTIPLE_PDEV_VDEV_PARAM_CMDID"); 2406 wmi_buf_free(buf); 2407 } 2408 return ret; 2409 } 2410 2411 /** 2412 * send_multiple_pdev_param_cmd_tlv() - set pdev parameters 2413 * @wmi_handle: wmi handle 2414 * @params: pointer to set_multiple_pdev_vdev_param structure 2415 * 2416 * Return: 0 on success, errno on failure 2417 */ 2418 static QDF_STATUS 2419 send_multiple_pdev_param_cmd_tlv(wmi_unified_t wmi_handle, 2420 struct set_multiple_pdev_vdev_param *params) 2421 { 2422 if (!wmi_service_enabled(wmi_handle, 2423 wmi_service_combined_set_param_support)) 2424 return send_multi_param_cmd_using_pdev_set_param_tlv(wmi_handle, 2425 params); 2426 return send_multi_pdev_vdev_set_param_cmd_tlv(wmi_handle, params); 2427 } 2428 2429 #else /* WLAN_PDEV_VDEV_SEND_MULTI_PARAM */ 2430 /** 2431 * send_multiple_pdev_param_cmd_tlv() - set pdev parameters 2432 * @wmi_handle: wmi handle 2433 * @params: pointer to set_multiple_pdev_vdev_param structure 2434 * 2435 * Return: 0 on success, errno on failure 2436 */ 2437 static QDF_STATUS 2438 send_multiple_pdev_param_cmd_tlv(wmi_unified_t wmi_handle, 2439 struct set_multiple_pdev_vdev_param *params) 2440 { 2441 return send_multi_param_cmd_using_pdev_set_param_tlv(wmi_handle, params); 2442 } 2443 #endif /* end of WLAN_PDEV_VDEV_SEND_MULTI_PARAM */ 2444 2445 /** 2446 * send_pdev_set_hw_mode_cmd_tlv() - Send WMI_PDEV_SET_HW_MODE_CMDID to FW 2447 * @wmi_handle: wmi handle 2448 * @msg: Structure containing the following parameters 2449 * @hw_mode_index: The HW_Mode field is a enumerated type that is selected 2450 * from the HW_Mode table, which is returned in the WMI_SERVICE_READY_EVENTID. 2451 * 2452 * Provides notification to the WLAN firmware that host driver is requesting a 2453 * HardWare (HW) Mode change. This command is needed to support iHelium in the 2454 * configurations that include the Dual Band Simultaneous (DBS) feature. 2455 * 2456 * Return: Success if the cmd is sent successfully to the firmware 2457 */ 2458 static QDF_STATUS send_pdev_set_hw_mode_cmd_tlv(wmi_unified_t wmi_handle, 2459 uint32_t hw_mode_index) 2460 { 2461 wmi_pdev_set_hw_mode_cmd_fixed_param *cmd; 2462 wmi_buf_t buf; 2463 uint32_t len; 2464 2465 len = sizeof(*cmd); 2466 2467 buf = wmi_buf_alloc(wmi_handle, len); 2468 if (!buf) 2469 return QDF_STATUS_E_NOMEM; 2470 2471 cmd = (wmi_pdev_set_hw_mode_cmd_fixed_param *)wmi_buf_data(buf); 2472 WMITLV_SET_HDR(&cmd->tlv_header, 2473 WMITLV_TAG_STRUC_wmi_pdev_set_hw_mode_cmd_fixed_param, 2474 WMITLV_GET_STRUCT_TLVLEN( 2475 wmi_pdev_set_hw_mode_cmd_fixed_param)); 2476 2477 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 2478 wmi_handle, 2479 WMI_HOST_PDEV_ID_SOC); 2480 cmd->hw_mode_index = hw_mode_index; 2481 wmi_debug("HW mode index:%d", cmd->hw_mode_index); 2482 2483 wmi_mtrace(WMI_PDEV_SET_HW_MODE_CMDID, NO_SESSION, 0); 2484 if (wmi_unified_cmd_send(wmi_handle, buf, len, 2485 WMI_PDEV_SET_HW_MODE_CMDID)) { 2486 wmi_err("Failed to send WMI_PDEV_SET_HW_MODE_CMDID"); 2487 wmi_buf_free(buf); 2488 return QDF_STATUS_E_FAILURE; 2489 } 2490 2491 return QDF_STATUS_SUCCESS; 2492 } 2493 2494 /** 2495 * send_suspend_cmd_tlv() - WMI suspend function 2496 * @param wmi_handle : handle to WMI. 2497 * @param param : pointer to hold suspend parameter 2498 * @mac_id: radio context 2499 * 2500 * Return 0 on success and -ve on failure. 2501 */ 2502 static QDF_STATUS send_suspend_cmd_tlv(wmi_unified_t wmi_handle, 2503 struct suspend_params *param, 2504 uint8_t mac_id) 2505 { 2506 wmi_pdev_suspend_cmd_fixed_param *cmd; 2507 wmi_buf_t wmibuf; 2508 uint32_t len = sizeof(*cmd); 2509 int32_t ret; 2510 2511 /* 2512 * send the command to Target to ignore the 2513 * PCIE reset so as to ensure that Host and target 2514 * states are in sync 2515 */ 2516 wmibuf = wmi_buf_alloc(wmi_handle, len); 2517 if (!wmibuf) 2518 return QDF_STATUS_E_NOMEM; 2519 2520 cmd = (wmi_pdev_suspend_cmd_fixed_param *) wmi_buf_data(wmibuf); 2521 WMITLV_SET_HDR(&cmd->tlv_header, 2522 WMITLV_TAG_STRUC_wmi_pdev_suspend_cmd_fixed_param, 2523 WMITLV_GET_STRUCT_TLVLEN 2524 (wmi_pdev_suspend_cmd_fixed_param)); 2525 if (param->disable_target_intr) 2526 cmd->suspend_opt = WMI_PDEV_SUSPEND_AND_DISABLE_INTR; 2527 else 2528 cmd->suspend_opt = WMI_PDEV_SUSPEND; 2529 2530 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 2531 wmi_handle, 2532 mac_id); 2533 2534 wmi_mtrace(WMI_PDEV_SUSPEND_CMDID, NO_SESSION, 0); 2535 ret = wmi_unified_cmd_send(wmi_handle, wmibuf, len, 2536 WMI_PDEV_SUSPEND_CMDID); 2537 if (ret) { 2538 wmi_buf_free(wmibuf); 2539 wmi_err("Failed to send WMI_PDEV_SUSPEND_CMDID command"); 2540 } 2541 2542 return ret; 2543 } 2544 2545 /** 2546 * send_resume_cmd_tlv() - WMI resume function 2547 * @param wmi_handle : handle to WMI. 2548 * @mac_id: radio context 2549 * 2550 * Return: 0 on success and -ve on failure. 2551 */ 2552 static QDF_STATUS send_resume_cmd_tlv(wmi_unified_t wmi_handle, 2553 uint8_t mac_id) 2554 { 2555 wmi_buf_t wmibuf; 2556 wmi_pdev_resume_cmd_fixed_param *cmd; 2557 QDF_STATUS ret; 2558 2559 wmibuf = wmi_buf_alloc(wmi_handle, sizeof(*cmd)); 2560 if (!wmibuf) 2561 return QDF_STATUS_E_NOMEM; 2562 cmd = (wmi_pdev_resume_cmd_fixed_param *) wmi_buf_data(wmibuf); 2563 WMITLV_SET_HDR(&cmd->tlv_header, 2564 WMITLV_TAG_STRUC_wmi_pdev_resume_cmd_fixed_param, 2565 WMITLV_GET_STRUCT_TLVLEN 2566 (wmi_pdev_resume_cmd_fixed_param)); 2567 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 2568 wmi_handle, 2569 mac_id); 2570 wmi_mtrace(WMI_PDEV_RESUME_CMDID, NO_SESSION, 0); 2571 ret = wmi_unified_cmd_send(wmi_handle, wmibuf, sizeof(*cmd), 2572 WMI_PDEV_RESUME_CMDID); 2573 if (QDF_IS_STATUS_ERROR(ret)) { 2574 wmi_err("Failed to send WMI_PDEV_RESUME_CMDID command"); 2575 wmi_buf_free(wmibuf); 2576 } 2577 2578 return ret; 2579 } 2580 2581 /** 2582 * send_wow_enable_cmd_tlv() - WMI wow enable function 2583 * @param wmi_handle : handle to WMI. 2584 * @param param : pointer to hold wow enable parameter 2585 * @mac_id: radio context 2586 * 2587 * Return: 0 on success and -ve on failure. 2588 */ 2589 static QDF_STATUS send_wow_enable_cmd_tlv(wmi_unified_t wmi_handle, 2590 struct wow_cmd_params *param, 2591 uint8_t mac_id) 2592 { 2593 wmi_wow_enable_cmd_fixed_param *cmd; 2594 wmi_buf_t buf; 2595 int32_t len; 2596 int32_t ret; 2597 2598 len = sizeof(wmi_wow_enable_cmd_fixed_param); 2599 2600 buf = wmi_buf_alloc(wmi_handle, len); 2601 if (!buf) 2602 return QDF_STATUS_E_NOMEM; 2603 2604 cmd = (wmi_wow_enable_cmd_fixed_param *) wmi_buf_data(buf); 2605 WMITLV_SET_HDR(&cmd->tlv_header, 2606 WMITLV_TAG_STRUC_wmi_wow_enable_cmd_fixed_param, 2607 WMITLV_GET_STRUCT_TLVLEN 2608 (wmi_wow_enable_cmd_fixed_param)); 2609 cmd->enable = param->enable; 2610 if (param->can_suspend_link) 2611 cmd->pause_iface_config = WOW_IFACE_PAUSE_ENABLED; 2612 else 2613 cmd->pause_iface_config = WOW_IFACE_PAUSE_DISABLED; 2614 cmd->flags = param->flags; 2615 2616 wmi_debug("suspend type: %s flag is 0x%x", 2617 cmd->pause_iface_config == WOW_IFACE_PAUSE_ENABLED ? 2618 "WOW_IFACE_PAUSE_ENABLED" : "WOW_IFACE_PAUSE_DISABLED", 2619 cmd->flags); 2620 2621 wmi_mtrace(WMI_WOW_ENABLE_CMDID, NO_SESSION, 0); 2622 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 2623 WMI_WOW_ENABLE_CMDID); 2624 if (ret) 2625 wmi_buf_free(buf); 2626 2627 return ret; 2628 } 2629 2630 /** 2631 * send_set_ap_ps_param_cmd_tlv() - set ap powersave parameters 2632 * @wmi_handle: wmi handle 2633 * @peer_addr: peer mac address 2634 * @param: pointer to ap_ps parameter structure 2635 * 2636 * Return: QDF_STATUS_SUCCESS for success or error code 2637 */ 2638 static QDF_STATUS send_set_ap_ps_param_cmd_tlv(wmi_unified_t wmi_handle, 2639 uint8_t *peer_addr, 2640 struct ap_ps_params *param) 2641 { 2642 wmi_ap_ps_peer_cmd_fixed_param *cmd; 2643 wmi_buf_t buf; 2644 int32_t err; 2645 2646 buf = wmi_buf_alloc(wmi_handle, sizeof(*cmd)); 2647 if (!buf) 2648 return QDF_STATUS_E_NOMEM; 2649 2650 cmd = (wmi_ap_ps_peer_cmd_fixed_param *) wmi_buf_data(buf); 2651 WMITLV_SET_HDR(&cmd->tlv_header, 2652 WMITLV_TAG_STRUC_wmi_ap_ps_peer_cmd_fixed_param, 2653 WMITLV_GET_STRUCT_TLVLEN 2654 (wmi_ap_ps_peer_cmd_fixed_param)); 2655 cmd->vdev_id = param->vdev_id; 2656 WMI_CHAR_ARRAY_TO_MAC_ADDR(peer_addr, &cmd->peer_macaddr); 2657 cmd->param = param->param; 2658 cmd->value = param->value; 2659 wmi_mtrace(WMI_AP_PS_PEER_PARAM_CMDID, cmd->vdev_id, 0); 2660 err = wmi_unified_cmd_send(wmi_handle, buf, 2661 sizeof(*cmd), WMI_AP_PS_PEER_PARAM_CMDID); 2662 if (err) { 2663 wmi_err("Failed to send set_ap_ps_param cmd"); 2664 wmi_buf_free(buf); 2665 return QDF_STATUS_E_FAILURE; 2666 } 2667 2668 return 0; 2669 } 2670 2671 /** 2672 * send_set_sta_ps_param_cmd_tlv() - set sta powersave parameters 2673 * @wmi_handle: wmi handle 2674 * @peer_addr: peer mac address 2675 * @param: pointer to sta_ps parameter structure 2676 * 2677 * Return: QDF_STATUS_SUCCESS for success or error code 2678 */ 2679 static QDF_STATUS send_set_sta_ps_param_cmd_tlv(wmi_unified_t wmi_handle, 2680 struct sta_ps_params *param) 2681 { 2682 wmi_sta_powersave_param_cmd_fixed_param *cmd; 2683 wmi_buf_t buf; 2684 int32_t len = sizeof(*cmd); 2685 2686 buf = wmi_buf_alloc(wmi_handle, len); 2687 if (!buf) 2688 return QDF_STATUS_E_NOMEM; 2689 2690 cmd = (wmi_sta_powersave_param_cmd_fixed_param *) wmi_buf_data(buf); 2691 WMITLV_SET_HDR(&cmd->tlv_header, 2692 WMITLV_TAG_STRUC_wmi_sta_powersave_param_cmd_fixed_param, 2693 WMITLV_GET_STRUCT_TLVLEN 2694 (wmi_sta_powersave_param_cmd_fixed_param)); 2695 cmd->vdev_id = param->vdev_id; 2696 cmd->param = param->param_id; 2697 cmd->value = param->value; 2698 2699 wmi_mtrace(WMI_STA_POWERSAVE_PARAM_CMDID, cmd->vdev_id, 0); 2700 if (wmi_unified_cmd_send(wmi_handle, buf, len, 2701 WMI_STA_POWERSAVE_PARAM_CMDID)) { 2702 wmi_err("Set Sta Ps param Failed vdevId %d Param %d val %d", 2703 param->vdev_id, param->param_id, param->value); 2704 wmi_buf_free(buf); 2705 return QDF_STATUS_E_FAILURE; 2706 } 2707 2708 return 0; 2709 } 2710 2711 /** 2712 * send_crash_inject_cmd_tlv() - inject fw crash 2713 * @wmi_handle: wmi handle 2714 * @param: ponirt to crash inject parameter structure 2715 * 2716 * Return: QDF_STATUS_SUCCESS for success or return error 2717 */ 2718 static QDF_STATUS send_crash_inject_cmd_tlv(wmi_unified_t wmi_handle, 2719 struct crash_inject *param) 2720 { 2721 int32_t ret = 0; 2722 WMI_FORCE_FW_HANG_CMD_fixed_param *cmd; 2723 uint16_t len = sizeof(*cmd); 2724 wmi_buf_t buf; 2725 2726 buf = wmi_buf_alloc(wmi_handle, len); 2727 if (!buf) 2728 return QDF_STATUS_E_NOMEM; 2729 2730 cmd = (WMI_FORCE_FW_HANG_CMD_fixed_param *) wmi_buf_data(buf); 2731 WMITLV_SET_HDR(&cmd->tlv_header, 2732 WMITLV_TAG_STRUC_WMI_FORCE_FW_HANG_CMD_fixed_param, 2733 WMITLV_GET_STRUCT_TLVLEN 2734 (WMI_FORCE_FW_HANG_CMD_fixed_param)); 2735 cmd->type = param->type; 2736 cmd->delay_time_ms = param->delay_time_ms; 2737 2738 wmi_mtrace(WMI_FORCE_FW_HANG_CMDID, NO_SESSION, 0); 2739 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 2740 WMI_FORCE_FW_HANG_CMDID); 2741 if (ret) { 2742 wmi_err("Failed to send set param command, ret = %d", ret); 2743 wmi_buf_free(buf); 2744 } 2745 2746 return ret; 2747 } 2748 2749 /** 2750 * send_dbglog_cmd_tlv() - set debug log level 2751 * @param wmi_handle : handle to WMI. 2752 * @param param : pointer to hold dbglog level parameter 2753 * 2754 * Return: 0 on success and -ve on failure. 2755 */ 2756 static QDF_STATUS 2757 send_dbglog_cmd_tlv(wmi_unified_t wmi_handle, 2758 struct dbglog_params *dbglog_param) 2759 { 2760 wmi_buf_t buf; 2761 wmi_debug_log_config_cmd_fixed_param *configmsg; 2762 QDF_STATUS status; 2763 int32_t i; 2764 int32_t len; 2765 int8_t *buf_ptr; 2766 int32_t *module_id_bitmap_array; /* Used to fomr the second tlv */ 2767 2768 ASSERT(dbglog_param->bitmap_len < MAX_MODULE_ID_BITMAP_WORDS); 2769 2770 /* Allocate size for 2 tlvs - including tlv hdr space for second tlv */ 2771 len = sizeof(wmi_debug_log_config_cmd_fixed_param) + WMI_TLV_HDR_SIZE + 2772 (sizeof(int32_t) * MAX_MODULE_ID_BITMAP_WORDS); 2773 buf = wmi_buf_alloc(wmi_handle, len); 2774 if (!buf) 2775 return QDF_STATUS_E_NOMEM; 2776 2777 configmsg = 2778 (wmi_debug_log_config_cmd_fixed_param *) (wmi_buf_data(buf)); 2779 buf_ptr = (int8_t *) configmsg; 2780 WMITLV_SET_HDR(&configmsg->tlv_header, 2781 WMITLV_TAG_STRUC_wmi_debug_log_config_cmd_fixed_param, 2782 WMITLV_GET_STRUCT_TLVLEN 2783 (wmi_debug_log_config_cmd_fixed_param)); 2784 configmsg->dbg_log_param = dbglog_param->param; 2785 configmsg->value = dbglog_param->val; 2786 /* Filling in the data part of second tlv -- should 2787 * follow first tlv _ WMI_TLV_HDR_SIZE */ 2788 module_id_bitmap_array = (uint32_t *) (buf_ptr + 2789 sizeof 2790 (wmi_debug_log_config_cmd_fixed_param) 2791 + WMI_TLV_HDR_SIZE); 2792 WMITLV_SET_HDR(buf_ptr + sizeof(wmi_debug_log_config_cmd_fixed_param), 2793 WMITLV_TAG_ARRAY_UINT32, 2794 sizeof(uint32_t) * MAX_MODULE_ID_BITMAP_WORDS); 2795 if (dbglog_param->module_id_bitmap) { 2796 for (i = 0; i < dbglog_param->bitmap_len; ++i) { 2797 module_id_bitmap_array[i] = 2798 dbglog_param->module_id_bitmap[i]; 2799 } 2800 } 2801 2802 wmi_mtrace(WMI_DBGLOG_CFG_CMDID, NO_SESSION, 0); 2803 status = wmi_unified_cmd_send(wmi_handle, buf, 2804 len, WMI_DBGLOG_CFG_CMDID); 2805 2806 if (status != QDF_STATUS_SUCCESS) 2807 wmi_buf_free(buf); 2808 2809 return status; 2810 } 2811 2812 /** 2813 * send_vdev_set_param_cmd_tlv() - WMI vdev set parameter function 2814 * @param wmi_handle : handle to WMI. 2815 * @param macaddr : MAC address 2816 * @param param : pointer to hold vdev set parameter 2817 * 2818 * Return: 0 on success and -ve on failure. 2819 */ 2820 static QDF_STATUS send_vdev_set_param_cmd_tlv(wmi_unified_t wmi_handle, 2821 struct vdev_set_params *param) 2822 { 2823 QDF_STATUS ret; 2824 wmi_vdev_set_param_cmd_fixed_param *cmd; 2825 wmi_buf_t buf; 2826 uint16_t len = sizeof(*cmd); 2827 uint32_t vdev_param; 2828 2829 vdev_param = convert_host_vdev_param_tlv(param->param_id); 2830 if (vdev_param == WMI_UNAVAILABLE_PARAM) { 2831 wmi_err("Vdev param %d not available", param->param_id); 2832 return QDF_STATUS_E_INVAL; 2833 2834 } 2835 2836 buf = wmi_buf_alloc(wmi_handle, len); 2837 if (!buf) 2838 return QDF_STATUS_E_NOMEM; 2839 2840 cmd = (wmi_vdev_set_param_cmd_fixed_param *) wmi_buf_data(buf); 2841 WMITLV_SET_HDR(&cmd->tlv_header, 2842 WMITLV_TAG_STRUC_wmi_vdev_set_param_cmd_fixed_param, 2843 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_set_param_cmd_fixed_param)); 2844 cmd->vdev_id = param->vdev_id; 2845 cmd->param_id = vdev_param; 2846 cmd->param_value = param->param_value; 2847 wmi_debug("Setting vdev %d param = %x, value = %u", 2848 cmd->vdev_id, cmd->param_id, cmd->param_value); 2849 wmi_mtrace(WMI_VDEV_SET_PARAM_CMDID, cmd->vdev_id, 0); 2850 ret = wmi_unified_cmd_send(wmi_handle, buf, len, WMI_VDEV_SET_PARAM_CMDID); 2851 if (QDF_IS_STATUS_ERROR(ret)) { 2852 wmi_err("Failed to send set param command ret = %d", ret); 2853 wmi_buf_free(buf); 2854 } 2855 2856 return ret; 2857 } 2858 2859 /** 2860 * send_multi_param_cmd_using_vdev_param_tlv() - vdev set parameter function 2861 * @wmi_handle : handle to WMI. 2862 * @dev_id: device id of pdev/vdev 2863 * @params: pointer to point array of structure dev_set_param with @n_params 2864 * @n_params: total number of set params that are combined with @params 2865 * 2866 * Return: returns QDF_STATUS. 2867 */ 2868 static QDF_STATUS 2869 send_multi_param_cmd_using_vdev_param_tlv(wmi_unified_t wmi_handle, 2870 struct set_multiple_pdev_vdev_param *params) 2871 { 2872 uint8_t index; 2873 struct vdev_set_params vdevparam; 2874 2875 for (index = 0; index < params->n_params; index++) { 2876 vdevparam.param_id = params->params[index].param_id; 2877 vdevparam.param_value = params->params[index].param_value; 2878 vdevparam.vdev_id = params->dev_id; 2879 if (QDF_IS_STATUS_ERROR(send_vdev_set_param_cmd_tlv(wmi_handle, &vdevparam))) { 2880 wmi_err("failed to send param:%d", vdevparam.param_id); 2881 return QDF_STATUS_E_FAILURE; 2882 } 2883 } 2884 return QDF_STATUS_SUCCESS; 2885 } 2886 2887 #ifdef WLAN_PDEV_VDEV_SEND_MULTI_PARAM 2888 /** 2889 * send_multiple_vdev_param_cmd_tlv() - WMI vdev set parameter function 2890 * @wmi_handle : handle to WMI. 2891 * @params: pointer to hold set_multiple_pdev_vdev_param info 2892 * 2893 * Return: 0 on success and errorcode on failure. 2894 */ 2895 static QDF_STATUS 2896 send_multiple_vdev_param_cmd_tlv(wmi_unified_t wmi_handle, 2897 struct set_multiple_pdev_vdev_param *params) 2898 { 2899 if (!wmi_service_enabled(wmi_handle, 2900 wmi_service_combined_set_param_support)) 2901 return send_multi_param_cmd_using_vdev_param_tlv(wmi_handle, 2902 params); 2903 return send_multi_pdev_vdev_set_param_cmd_tlv(wmi_handle, params); 2904 } 2905 2906 #else /* WLAN_PDEV_VDEV_SEND_MULTI_PARAM */ 2907 2908 /** 2909 * send_multiple_vdev_param_cmd_tlv() - WMI vdev set parameter function 2910 * @wmi_handle : handle to WMI. 2911 * @params: pointer to hold set_multiple_pdev_vdev_param info 2912 * 2913 * Return: 0 on success and errorcode on failure. 2914 */ 2915 static QDF_STATUS 2916 send_multiple_vdev_param_cmd_tlv(wmi_unified_t wmi_handle, 2917 struct set_multiple_pdev_vdev_param *params) 2918 { 2919 return send_multi_param_cmd_using_vdev_param_tlv(wmi_handle, params); 2920 } 2921 #endif /*end of WLAN_PDEV_VDEV_SEND_MULTI_PARAM */ 2922 2923 /** 2924 * send_vdev_set_mu_snif_cmd_tlv() - WMI vdev set mu snif function 2925 * @param wmi_handle : handle to WMI. 2926 * @param param : pointer to hold mu sniffer parameter 2927 * 2928 * Return: 0 on success and -ve on failure. 2929 */ 2930 static 2931 QDF_STATUS send_vdev_set_mu_snif_cmd_tlv(wmi_unified_t wmi_handle, 2932 struct vdev_set_mu_snif_param *param) 2933 { 2934 QDF_STATUS ret; 2935 wmi_vdev_set_mu_snif_cmd_param *cmd; 2936 wmi_buf_t buf; 2937 uint32_t *tmp_ptr; 2938 uint16_t len = sizeof(*cmd); 2939 uint8_t *buf_ptr; 2940 uint32_t i; 2941 2942 /* Length TLV placeholder for array of uint32_t */ 2943 len += WMI_TLV_HDR_SIZE; 2944 2945 if (param->num_aid) 2946 len += param->num_aid * sizeof(uint32_t); 2947 2948 buf = wmi_buf_alloc(wmi_handle, len); 2949 if (!buf) 2950 return QDF_STATUS_E_NOMEM; 2951 2952 buf_ptr = (uint8_t *)wmi_buf_data(buf); 2953 cmd = (wmi_vdev_set_mu_snif_cmd_param *)buf_ptr; 2954 2955 WMITLV_SET_HDR(&cmd->tlv_header, 2956 WMITLV_TAG_STRUC_wmi_vdev_set_mu_snif_cmd_param, 2957 WMITLV_GET_STRUCT_TLVLEN 2958 (wmi_vdev_set_mu_snif_cmd_param)); 2959 2960 cmd->vdev_id = param->vdev_id; 2961 cmd->mode = param->mode; 2962 cmd->max_num_user = param->num_user; 2963 2964 buf_ptr += sizeof(*cmd); 2965 2966 tmp_ptr = (uint32_t *)(buf_ptr + WMI_TLV_HDR_SIZE); 2967 2968 for (i = 0; i < param->num_aid; ++i) 2969 tmp_ptr[i] = param->aid[i]; 2970 2971 WMITLV_SET_HDR(buf_ptr, 2972 WMITLV_TAG_ARRAY_UINT32, 2973 (param->num_aid * sizeof(uint32_t))); 2974 2975 wmi_debug("Setting vdev %d mode = %x, max user = %u aids= %u", 2976 cmd->vdev_id, cmd->mode, cmd->max_num_user, param->num_aid); 2977 wmi_mtrace(WMI_VDEV_SET_PARAM_CMDID, cmd->vdev_id, 0); 2978 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 2979 WMI_VDEV_SET_MU_SNIF_CMDID); 2980 if (QDF_IS_STATUS_ERROR(ret)) { 2981 wmi_err("Failed to send set param command ret = %d", ret); 2982 wmi_buf_free(buf); 2983 } 2984 2985 return ret; 2986 } 2987 2988 /** 2989 * send_peer_based_pktlog_cmd() - Send WMI command to enable packet-log 2990 * @wmi_handle: handle to WMI. 2991 * @macaddr: Peer mac address to be filter 2992 * @mac_id: mac id to have radio context 2993 * @enb_dsb: Enable MAC based filtering or Disable 2994 * 2995 * Return: QDF_STATUS 2996 */ 2997 static QDF_STATUS send_peer_based_pktlog_cmd(wmi_unified_t wmi_handle, 2998 uint8_t *macaddr, 2999 uint8_t mac_id, 3000 uint8_t enb_dsb) 3001 { 3002 int32_t ret; 3003 wmi_pdev_pktlog_filter_cmd_fixed_param *cmd; 3004 wmi_pdev_pktlog_filter_info *mac_info; 3005 wmi_buf_t buf; 3006 uint8_t *buf_ptr; 3007 uint16_t len = sizeof(wmi_pdev_pktlog_filter_cmd_fixed_param) + 3008 sizeof(wmi_pdev_pktlog_filter_info) + WMI_TLV_HDR_SIZE; 3009 3010 buf = wmi_buf_alloc(wmi_handle, len); 3011 if (!buf) 3012 return QDF_STATUS_E_NOMEM; 3013 3014 buf_ptr = (uint8_t *)wmi_buf_data(buf); 3015 cmd = (wmi_pdev_pktlog_filter_cmd_fixed_param *)buf_ptr; 3016 WMITLV_SET_HDR(&cmd->tlv_header, 3017 WMITLV_TAG_STRUC_wmi_pdev_pktlog_filter_cmd_fixed_param, 3018 WMITLV_GET_STRUCT_TLVLEN 3019 (wmi_pdev_pktlog_filter_cmd_fixed_param)); 3020 cmd->pdev_id = mac_id; 3021 cmd->enable = enb_dsb; 3022 cmd->num_of_mac_addresses = 1; 3023 wmi_mtrace(WMI_PDEV_PKTLOG_FILTER_CMDID, cmd->pdev_id, 0); 3024 3025 buf_ptr += sizeof(*cmd); 3026 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 3027 sizeof(wmi_pdev_pktlog_filter_info)); 3028 buf_ptr += WMI_TLV_HDR_SIZE; 3029 3030 mac_info = (wmi_pdev_pktlog_filter_info *)(buf_ptr); 3031 3032 WMITLV_SET_HDR(&mac_info->tlv_header, 3033 WMITLV_TAG_STRUC_wmi_pdev_pktlog_filter_info, 3034 WMITLV_GET_STRUCT_TLVLEN 3035 (wmi_pdev_pktlog_filter_info)); 3036 3037 WMI_CHAR_ARRAY_TO_MAC_ADDR(macaddr, &mac_info->peer_mac_address); 3038 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 3039 WMI_PDEV_PKTLOG_FILTER_CMDID); 3040 if (ret) { 3041 wmi_err("Failed to send peer based pktlog command to FW =%d" 3042 , ret); 3043 wmi_buf_free(buf); 3044 } 3045 3046 return ret; 3047 } 3048 3049 /** 3050 * send_packet_log_enable_cmd_tlv() - Send WMI command to enable packet-log 3051 * @param wmi_handle : handle to WMI. 3052 * @param PKTLOG_EVENT : packet log event 3053 * @mac_id: mac id to have radio context 3054 * 3055 * Return: 0 on success and -ve on failure. 3056 */ 3057 static QDF_STATUS send_packet_log_enable_cmd_tlv(wmi_unified_t wmi_handle, 3058 WMI_HOST_PKTLOG_EVENT PKTLOG_EVENT, uint8_t mac_id) 3059 { 3060 int32_t ret, idx, max_idx; 3061 wmi_pdev_pktlog_enable_cmd_fixed_param *cmd; 3062 wmi_buf_t buf; 3063 uint16_t len = sizeof(wmi_pdev_pktlog_enable_cmd_fixed_param); 3064 3065 buf = wmi_buf_alloc(wmi_handle, len); 3066 if (!buf) 3067 return -QDF_STATUS_E_NOMEM; 3068 3069 cmd = (wmi_pdev_pktlog_enable_cmd_fixed_param *) wmi_buf_data(buf); 3070 WMITLV_SET_HDR(&cmd->tlv_header, 3071 WMITLV_TAG_STRUC_wmi_pdev_pktlog_enable_cmd_fixed_param, 3072 WMITLV_GET_STRUCT_TLVLEN 3073 (wmi_pdev_pktlog_enable_cmd_fixed_param)); 3074 max_idx = sizeof(pktlog_event_tlv) / (sizeof(pktlog_event_tlv[0])); 3075 cmd->evlist = 0; 3076 for (idx = 0; idx < max_idx; idx++) { 3077 if (PKTLOG_EVENT & (1 << idx)) 3078 cmd->evlist |= pktlog_event_tlv[idx]; 3079 } 3080 cmd->pdev_id = mac_id; 3081 wmi_mtrace(WMI_PDEV_PKTLOG_ENABLE_CMDID, cmd->pdev_id, 0); 3082 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 3083 WMI_PDEV_PKTLOG_ENABLE_CMDID); 3084 if (ret) { 3085 wmi_err("Failed to send pktlog enable cmd to FW =%d", ret); 3086 wmi_buf_free(buf); 3087 } 3088 3089 return ret; 3090 } 3091 3092 /** 3093 * send_packet_log_disable_cmd_tlv() - Send WMI command to disable packet-log 3094 * @param wmi_handle : handle to WMI. 3095 * @mac_id: mac id to have radio context 3096 * 3097 * Return: 0 on success and -ve on failure. 3098 */ 3099 static QDF_STATUS send_packet_log_disable_cmd_tlv(wmi_unified_t wmi_handle, 3100 uint8_t mac_id) 3101 { 3102 int32_t ret; 3103 wmi_pdev_pktlog_disable_cmd_fixed_param *cmd; 3104 wmi_buf_t buf; 3105 uint16_t len = sizeof(wmi_pdev_pktlog_disable_cmd_fixed_param); 3106 3107 buf = wmi_buf_alloc(wmi_handle, len); 3108 if (!buf) 3109 return -QDF_STATUS_E_NOMEM; 3110 3111 cmd = (wmi_pdev_pktlog_disable_cmd_fixed_param *) wmi_buf_data(buf); 3112 WMITLV_SET_HDR(&cmd->tlv_header, 3113 WMITLV_TAG_STRUC_wmi_pdev_pktlog_disable_cmd_fixed_param, 3114 WMITLV_GET_STRUCT_TLVLEN 3115 (wmi_pdev_pktlog_disable_cmd_fixed_param)); 3116 cmd->pdev_id = mac_id; 3117 wmi_mtrace(WMI_PDEV_PKTLOG_DISABLE_CMDID, cmd->pdev_id, 0); 3118 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 3119 WMI_PDEV_PKTLOG_DISABLE_CMDID); 3120 if (ret) { 3121 wmi_err("Failed to send pktlog disable cmd to FW =%d", ret); 3122 wmi_buf_free(buf); 3123 } 3124 3125 return ret; 3126 } 3127 3128 #define WMI_FW_TIME_STAMP_LOW_MASK 0xffffffff 3129 /** 3130 * send_time_stamp_sync_cmd_tlv() - Send WMI command to 3131 * sync time between bwtween host and firmware 3132 * @param wmi_handle : handle to WMI. 3133 * 3134 * Return: None 3135 */ 3136 static void send_time_stamp_sync_cmd_tlv(wmi_unified_t wmi_handle) 3137 { 3138 wmi_buf_t buf; 3139 QDF_STATUS status = QDF_STATUS_SUCCESS; 3140 WMI_DBGLOG_TIME_STAMP_SYNC_CMD_fixed_param *time_stamp; 3141 int32_t len; 3142 qdf_time_t time_ms; 3143 3144 len = sizeof(*time_stamp); 3145 buf = wmi_buf_alloc(wmi_handle, len); 3146 3147 if (!buf) 3148 return; 3149 3150 time_stamp = 3151 (WMI_DBGLOG_TIME_STAMP_SYNC_CMD_fixed_param *) 3152 (wmi_buf_data(buf)); 3153 WMITLV_SET_HDR(&time_stamp->tlv_header, 3154 WMITLV_TAG_STRUC_wmi_dbglog_time_stamp_sync_cmd_fixed_param, 3155 WMITLV_GET_STRUCT_TLVLEN( 3156 WMI_DBGLOG_TIME_STAMP_SYNC_CMD_fixed_param)); 3157 3158 time_ms = qdf_get_time_of_the_day_ms(); 3159 time_stamp->mode = WMI_TIME_STAMP_SYNC_MODE_MS; 3160 time_stamp->time_stamp_low = time_ms & 3161 WMI_FW_TIME_STAMP_LOW_MASK; 3162 /* 3163 * Send time_stamp_high 0 as the time converted from HR:MIN:SEC:MS to ms 3164 * wont exceed 27 bit 3165 */ 3166 time_stamp->time_stamp_high = 0; 3167 wmi_debug("WMA --> DBGLOG_TIME_STAMP_SYNC_CMDID mode %d time_stamp low %d high %d", 3168 time_stamp->mode, time_stamp->time_stamp_low, 3169 time_stamp->time_stamp_high); 3170 3171 wmi_mtrace(WMI_DBGLOG_TIME_STAMP_SYNC_CMDID, NO_SESSION, 0); 3172 status = wmi_unified_cmd_send(wmi_handle, buf, 3173 len, WMI_DBGLOG_TIME_STAMP_SYNC_CMDID); 3174 if (status) { 3175 wmi_err("Failed to send WMI_DBGLOG_TIME_STAMP_SYNC_CMDID command"); 3176 wmi_buf_free(buf); 3177 } 3178 3179 } 3180 3181 /** 3182 * send_fd_tmpl_cmd_tlv() - WMI FILS Discovery send function 3183 * @param wmi_handle : handle to WMI. 3184 * @param param : pointer to hold FILS Discovery send cmd parameter 3185 * 3186 * Return: 0 on success and -ve on failure. 3187 */ 3188 static QDF_STATUS send_fd_tmpl_cmd_tlv(wmi_unified_t wmi_handle, 3189 struct fils_discovery_tmpl_params *param) 3190 { 3191 int32_t ret; 3192 wmi_fd_tmpl_cmd_fixed_param *cmd; 3193 wmi_buf_t wmi_buf; 3194 uint8_t *buf_ptr; 3195 uint32_t wmi_buf_len; 3196 3197 wmi_buf_len = sizeof(wmi_fd_tmpl_cmd_fixed_param) + 3198 WMI_TLV_HDR_SIZE + param->tmpl_len_aligned; 3199 wmi_buf = wmi_buf_alloc(wmi_handle, wmi_buf_len); 3200 if (!wmi_buf) 3201 return QDF_STATUS_E_NOMEM; 3202 3203 buf_ptr = (uint8_t *) wmi_buf_data(wmi_buf); 3204 cmd = (wmi_fd_tmpl_cmd_fixed_param *) buf_ptr; 3205 WMITLV_SET_HDR(&cmd->tlv_header, 3206 WMITLV_TAG_STRUC_wmi_fd_tmpl_cmd_fixed_param, 3207 WMITLV_GET_STRUCT_TLVLEN(wmi_fd_tmpl_cmd_fixed_param)); 3208 cmd->vdev_id = param->vdev_id; 3209 cmd->buf_len = param->tmpl_len; 3210 buf_ptr += sizeof(wmi_fd_tmpl_cmd_fixed_param); 3211 3212 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, param->tmpl_len_aligned); 3213 buf_ptr += WMI_TLV_HDR_SIZE; 3214 qdf_mem_copy(buf_ptr, param->frm, param->tmpl_len); 3215 3216 wmi_mtrace(WMI_FD_TMPL_CMDID, cmd->vdev_id, 0); 3217 ret = wmi_unified_cmd_send(wmi_handle, 3218 wmi_buf, wmi_buf_len, WMI_FD_TMPL_CMDID); 3219 3220 if (ret) { 3221 wmi_err("Failed to send fd tmpl: %d", ret); 3222 wmi_buf_free(wmi_buf); 3223 return ret; 3224 } 3225 3226 return 0; 3227 } 3228 3229 /** 3230 * send_beacon_send_tmpl_cmd_tlv() - WMI beacon send function 3231 * @param wmi_handle : handle to WMI. 3232 * @param param : pointer to hold beacon send cmd parameter 3233 * 3234 * Return: 0 on success and -ve on failure. 3235 */ 3236 static QDF_STATUS send_beacon_tmpl_send_cmd_tlv(wmi_unified_t wmi_handle, 3237 struct beacon_tmpl_params *param) 3238 { 3239 int32_t ret; 3240 wmi_bcn_tmpl_cmd_fixed_param *cmd; 3241 wmi_bcn_prb_info *bcn_prb_info; 3242 wmi_buf_t wmi_buf; 3243 uint8_t *buf_ptr; 3244 uint32_t wmi_buf_len; 3245 3246 wmi_buf_len = sizeof(wmi_bcn_tmpl_cmd_fixed_param) + 3247 sizeof(wmi_bcn_prb_info) + WMI_TLV_HDR_SIZE + 3248 param->tmpl_len_aligned + 3249 bcn_tmpl_mlo_param_size(param) + 3250 bcn_tmpl_ml_info_size(param); 3251 3252 wmi_buf = wmi_buf_alloc(wmi_handle, wmi_buf_len); 3253 if (!wmi_buf) 3254 return QDF_STATUS_E_NOMEM; 3255 3256 buf_ptr = (uint8_t *) wmi_buf_data(wmi_buf); 3257 cmd = (wmi_bcn_tmpl_cmd_fixed_param *) buf_ptr; 3258 WMITLV_SET_HDR(&cmd->tlv_header, 3259 WMITLV_TAG_STRUC_wmi_bcn_tmpl_cmd_fixed_param, 3260 WMITLV_GET_STRUCT_TLVLEN(wmi_bcn_tmpl_cmd_fixed_param)); 3261 cmd->vdev_id = param->vdev_id; 3262 cmd->tim_ie_offset = param->tim_ie_offset; 3263 cmd->mbssid_ie_offset = param->mbssid_ie_offset; 3264 cmd->csa_switch_count_offset = param->csa_switch_count_offset; 3265 cmd->ext_csa_switch_count_offset = param->ext_csa_switch_count_offset; 3266 cmd->esp_ie_offset = param->esp_ie_offset; 3267 cmd->mu_edca_ie_offset = param->mu_edca_ie_offset; 3268 cmd->ema_params = param->ema_params; 3269 cmd->buf_len = param->tmpl_len; 3270 cmd->csa_event_bitmap = param->csa_event_bitmap; 3271 3272 WMI_BEACON_PROTECTION_EN_SET(cmd->feature_enable_bitmap, 3273 param->enable_bigtk); 3274 buf_ptr += sizeof(wmi_bcn_tmpl_cmd_fixed_param); 3275 3276 bcn_prb_info = (wmi_bcn_prb_info *) buf_ptr; 3277 WMITLV_SET_HDR(&bcn_prb_info->tlv_header, 3278 WMITLV_TAG_STRUC_wmi_bcn_prb_info, 3279 WMITLV_GET_STRUCT_TLVLEN(wmi_bcn_prb_info)); 3280 bcn_prb_info->caps = 0; 3281 bcn_prb_info->erp = 0; 3282 buf_ptr += sizeof(wmi_bcn_prb_info); 3283 3284 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, param->tmpl_len_aligned); 3285 buf_ptr += WMI_TLV_HDR_SIZE; 3286 3287 /* for big endian host, copy engine byte_swap is enabled 3288 * But the frame content is in network byte order 3289 * Need to byte swap the frame content - so when copy engine 3290 * does byte_swap - target gets frame content in the correct order 3291 */ 3292 WMI_HOST_IF_MSG_COPY_CHAR_ARRAY(buf_ptr, param->frm, 3293 param->tmpl_len); 3294 3295 buf_ptr += roundup(param->tmpl_len, sizeof(uint32_t)); 3296 buf_ptr = bcn_tmpl_add_ml_partner_links(buf_ptr, param); 3297 3298 buf_ptr = bcn_tmpl_add_ml_info(buf_ptr, param); 3299 3300 wmi_mtrace(WMI_BCN_TMPL_CMDID, cmd->vdev_id, 0); 3301 ret = wmi_unified_cmd_send(wmi_handle, 3302 wmi_buf, wmi_buf_len, WMI_BCN_TMPL_CMDID); 3303 if (ret) { 3304 wmi_err("Failed to send bcn tmpl: %d", ret); 3305 wmi_buf_free(wmi_buf); 3306 } 3307 3308 return 0; 3309 } 3310 3311 #ifdef WLAN_FEATURE_11BE 3312 static inline void copy_peer_flags_tlv_11be( 3313 wmi_peer_assoc_complete_cmd_fixed_param * cmd, 3314 struct peer_assoc_params *param) 3315 { 3316 if (param->bw_320) 3317 cmd->peer_flags_ext |= WMI_PEER_EXT_320MHZ; 3318 if (param->eht_flag) 3319 cmd->peer_flags_ext |= WMI_PEER_EXT_EHT; 3320 3321 wmi_debug("peer_flags_ext 0x%x", cmd->peer_flags_ext); 3322 } 3323 #else 3324 static inline void copy_peer_flags_tlv_11be( 3325 wmi_peer_assoc_complete_cmd_fixed_param * cmd, 3326 struct peer_assoc_params *param) 3327 { 3328 } 3329 #endif 3330 3331 static inline void copy_peer_flags_tlv( 3332 wmi_peer_assoc_complete_cmd_fixed_param * cmd, 3333 struct peer_assoc_params *param) 3334 { 3335 /* 3336 * The target only needs a subset of the flags maintained in the host. 3337 * Just populate those flags and send it down 3338 */ 3339 cmd->peer_flags = 0; 3340 if (param->peer_dms_capable) 3341 cmd->peer_flags_ext |= WMI_PEER_EXT_DMS_CAPABLE; 3342 /* 3343 * Do not enable HT/VHT if WMM/wme is disabled for vap. 3344 */ 3345 if (param->is_wme_set) { 3346 3347 if (param->qos_flag) 3348 cmd->peer_flags |= WMI_PEER_QOS; 3349 if (param->apsd_flag) 3350 cmd->peer_flags |= WMI_PEER_APSD; 3351 if (param->ht_flag) 3352 cmd->peer_flags |= WMI_PEER_HT; 3353 if (param->bw_40) 3354 cmd->peer_flags |= WMI_PEER_40MHZ; 3355 if (param->bw_80) 3356 cmd->peer_flags |= WMI_PEER_80MHZ; 3357 if (param->bw_160) 3358 cmd->peer_flags |= WMI_PEER_160MHZ; 3359 3360 copy_peer_flags_tlv_11be(cmd, param); 3361 3362 /* Typically if STBC is enabled for VHT it should be enabled 3363 * for HT as well 3364 **/ 3365 if (param->stbc_flag) 3366 cmd->peer_flags |= WMI_PEER_STBC; 3367 3368 /* Typically if LDPC is enabled for VHT it should be enabled 3369 * for HT as well 3370 **/ 3371 if (param->ldpc_flag) 3372 cmd->peer_flags |= WMI_PEER_LDPC; 3373 3374 if (param->static_mimops_flag) 3375 cmd->peer_flags |= WMI_PEER_STATIC_MIMOPS; 3376 if (param->dynamic_mimops_flag) 3377 cmd->peer_flags |= WMI_PEER_DYN_MIMOPS; 3378 if (param->spatial_mux_flag) 3379 cmd->peer_flags |= WMI_PEER_SPATIAL_MUX; 3380 if (param->vht_flag) 3381 cmd->peer_flags |= WMI_PEER_VHT; 3382 if (param->he_flag) 3383 cmd->peer_flags |= WMI_PEER_HE; 3384 if (param->p2p_capable_sta) 3385 cmd->peer_flags |= WMI_PEER_IS_P2P_CAPABLE; 3386 } 3387 3388 if (param->is_pmf_enabled) 3389 cmd->peer_flags |= WMI_PEER_PMF; 3390 /* 3391 * Suppress authorization for all AUTH modes that need 4-way handshake 3392 * (during re-association). 3393 * Authorization will be done for these modes on key installation. 3394 */ 3395 if (param->auth_flag) 3396 cmd->peer_flags |= WMI_PEER_AUTH; 3397 if (param->need_ptk_4_way) 3398 cmd->peer_flags |= WMI_PEER_NEED_PTK_4_WAY; 3399 else 3400 cmd->peer_flags &= ~WMI_PEER_NEED_PTK_4_WAY; 3401 if (param->need_gtk_2_way) 3402 cmd->peer_flags |= WMI_PEER_NEED_GTK_2_WAY; 3403 /* safe mode bypass the 4-way handshake */ 3404 if (param->safe_mode_enabled) 3405 cmd->peer_flags &= 3406 ~(WMI_PEER_NEED_PTK_4_WAY | WMI_PEER_NEED_GTK_2_WAY); 3407 /* inter BSS peer */ 3408 if (param->inter_bss_peer) 3409 cmd->peer_flags |= WMI_PEER_INTER_BSS_PEER; 3410 /* Disable AMSDU for station transmit, if user configures it */ 3411 /* Disable AMSDU for AP transmit to 11n Stations, if user configures 3412 * it 3413 * if (param->amsdu_disable) Add after FW support 3414 **/ 3415 3416 /* Target asserts if node is marked HT and all MCS is set to 0. 3417 * Mark the node as non-HT if all the mcs rates are disabled through 3418 * iwpriv 3419 **/ 3420 if (param->peer_ht_rates.num_rates == 0) 3421 cmd->peer_flags &= ~WMI_PEER_HT; 3422 3423 if (param->twt_requester) 3424 cmd->peer_flags |= WMI_PEER_TWT_REQ; 3425 3426 if (param->twt_responder) 3427 cmd->peer_flags |= WMI_PEER_TWT_RESP; 3428 } 3429 3430 static inline void copy_peer_mac_addr_tlv( 3431 wmi_peer_assoc_complete_cmd_fixed_param * cmd, 3432 struct peer_assoc_params *param) 3433 { 3434 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->peer_mac, &cmd->peer_macaddr); 3435 } 3436 3437 #ifdef WLAN_FEATURE_11BE 3438 static uint8_t *update_peer_flags_tlv_ehtinfo( 3439 wmi_peer_assoc_complete_cmd_fixed_param * cmd, 3440 struct peer_assoc_params *param, uint8_t *buf_ptr) 3441 { 3442 wmi_eht_rate_set *eht_mcs; 3443 int i; 3444 3445 cmd->peer_eht_ops = param->peer_eht_ops; 3446 cmd->puncture_20mhz_bitmap = ~param->puncture_bitmap; 3447 3448 qdf_mem_copy(&cmd->peer_eht_cap_mac, ¶m->peer_eht_cap_macinfo, 3449 sizeof(param->peer_eht_cap_macinfo)); 3450 qdf_mem_copy(&cmd->peer_eht_cap_phy, ¶m->peer_eht_cap_phyinfo, 3451 sizeof(param->peer_eht_cap_phyinfo)); 3452 qdf_mem_copy(&cmd->peer_eht_ppet, ¶m->peer_eht_ppet, 3453 sizeof(param->peer_eht_ppet)); 3454 3455 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 3456 (param->peer_eht_mcs_count * sizeof(wmi_eht_rate_set))); 3457 buf_ptr += WMI_TLV_HDR_SIZE; 3458 3459 /* Loop through the EHT rate set */ 3460 for (i = 0; i < param->peer_eht_mcs_count; i++) { 3461 eht_mcs = (wmi_eht_rate_set *)buf_ptr; 3462 WMITLV_SET_HDR(eht_mcs, WMITLV_TAG_STRUC_wmi_eht_rate_set, 3463 WMITLV_GET_STRUCT_TLVLEN(wmi_eht_rate_set)); 3464 3465 eht_mcs->rx_mcs_set = param->peer_eht_rx_mcs_set[i]; 3466 eht_mcs->tx_mcs_set = param->peer_eht_tx_mcs_set[i]; 3467 wmi_debug("EHT idx %d RxMCSmap %x TxMCSmap %x ", 3468 i, eht_mcs->rx_mcs_set, eht_mcs->tx_mcs_set); 3469 buf_ptr += sizeof(wmi_eht_rate_set); 3470 } 3471 3472 wmi_debug("nss %d ru mask 0x%x", 3473 cmd->peer_eht_ppet.numss_m1, cmd->peer_eht_ppet.ru_mask); 3474 for (i = 0; i < WMI_MAX_NUM_SS; i++) { 3475 wmi_debug("ppet idx %d ppet %x ", 3476 i, cmd->peer_eht_ppet.ppet16_ppet8_ru3_ru0[i]); 3477 } 3478 3479 if ((param->eht_flag) && (param->peer_eht_mcs_count > 1) && 3480 (param->peer_eht_rx_mcs_set[WMI_HOST_EHT_TXRX_MCS_NSS_IDX_160] 3481 == WMI_HOST_EHT_INVALID_MCSNSSMAP || 3482 param->peer_eht_tx_mcs_set[WMI_HOST_EHT_TXRX_MCS_NSS_IDX_160] 3483 == WMI_HOST_HE_INVALID_MCSNSSMAP)) { 3484 wmi_debug("param->peer_eht_tx_mcs_set[160MHz]=%x", 3485 param->peer_eht_tx_mcs_set 3486 [WMI_HOST_HE_TXRX_MCS_NSS_IDX_160]); 3487 wmi_debug("param->peer_eht_rx_mcs_set[160MHz]=%x", 3488 param->peer_eht_rx_mcs_set 3489 [WMI_HOST_HE_TXRX_MCS_NSS_IDX_160]); 3490 wmi_debug("peer_mac="QDF_MAC_ADDR_FMT, 3491 QDF_MAC_ADDR_REF(param->peer_mac)); 3492 } 3493 3494 wmi_debug("EHT cap_mac %x %x ehtops %x EHT phy %x %x %x pp %x", 3495 cmd->peer_eht_cap_mac[0], 3496 cmd->peer_eht_cap_mac[1], cmd->peer_eht_ops, 3497 cmd->peer_eht_cap_phy[0], cmd->peer_he_cap_phy[1], 3498 cmd->peer_eht_cap_phy[2], cmd->puncture_20mhz_bitmap); 3499 3500 return buf_ptr; 3501 } 3502 #else 3503 static uint8_t *update_peer_flags_tlv_ehtinfo( 3504 wmi_peer_assoc_complete_cmd_fixed_param * cmd, 3505 struct peer_assoc_params *param, uint8_t *buf_ptr) 3506 { 3507 return buf_ptr; 3508 } 3509 #endif 3510 3511 #ifdef WLAN_FEATURE_11BE 3512 static 3513 uint32_t wmi_eht_peer_assoc_params_len(struct peer_assoc_params *param) 3514 { 3515 return (sizeof(wmi_he_rate_set) * param->peer_eht_mcs_count 3516 + WMI_TLV_HDR_SIZE); 3517 } 3518 3519 static void wmi_populate_service_11be(uint32_t *wmi_service) 3520 { 3521 wmi_service[wmi_service_11be] = WMI_SERVICE_11BE; 3522 } 3523 3524 #else 3525 static 3526 uint32_t wmi_eht_peer_assoc_params_len(struct peer_assoc_params *param) 3527 { 3528 return 0; 3529 } 3530 3531 static void wmi_populate_service_11be(uint32_t *wmi_service) 3532 { 3533 } 3534 3535 #endif 3536 3537 /** 3538 * send_peer_assoc_cmd_tlv() - WMI peer assoc function 3539 * @param wmi_handle : handle to WMI. 3540 * @param param : pointer to peer assoc parameter 3541 * 3542 * Return: 0 on success and -ve on failure. 3543 */ 3544 static QDF_STATUS send_peer_assoc_cmd_tlv(wmi_unified_t wmi_handle, 3545 struct peer_assoc_params *param) 3546 { 3547 wmi_peer_assoc_complete_cmd_fixed_param *cmd; 3548 wmi_vht_rate_set *mcs; 3549 wmi_he_rate_set *he_mcs; 3550 wmi_buf_t buf; 3551 int32_t len; 3552 uint8_t *buf_ptr; 3553 QDF_STATUS ret; 3554 uint32_t peer_legacy_rates_align; 3555 uint32_t peer_ht_rates_align; 3556 int32_t i; 3557 3558 3559 peer_legacy_rates_align = wmi_align(param->peer_legacy_rates.num_rates); 3560 peer_ht_rates_align = wmi_align(param->peer_ht_rates.num_rates); 3561 3562 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE + 3563 (peer_legacy_rates_align * sizeof(uint8_t)) + 3564 WMI_TLV_HDR_SIZE + 3565 (peer_ht_rates_align * sizeof(uint8_t)) + 3566 sizeof(wmi_vht_rate_set) + 3567 (sizeof(wmi_he_rate_set) * param->peer_he_mcs_count 3568 + WMI_TLV_HDR_SIZE) 3569 + wmi_eht_peer_assoc_params_len(param) + 3570 peer_assoc_mlo_params_size(param) + 3571 peer_assoc_t2lm_params_size(param); 3572 3573 buf = wmi_buf_alloc(wmi_handle, len); 3574 if (!buf) 3575 return QDF_STATUS_E_NOMEM; 3576 3577 buf_ptr = (uint8_t *) wmi_buf_data(buf); 3578 cmd = (wmi_peer_assoc_complete_cmd_fixed_param *) buf_ptr; 3579 WMITLV_SET_HDR(&cmd->tlv_header, 3580 WMITLV_TAG_STRUC_wmi_peer_assoc_complete_cmd_fixed_param, 3581 WMITLV_GET_STRUCT_TLVLEN 3582 (wmi_peer_assoc_complete_cmd_fixed_param)); 3583 3584 cmd->vdev_id = param->vdev_id; 3585 3586 cmd->peer_new_assoc = param->peer_new_assoc; 3587 cmd->peer_associd = param->peer_associd; 3588 3589 copy_peer_flags_tlv(cmd, param); 3590 copy_peer_mac_addr_tlv(cmd, param); 3591 3592 cmd->peer_rate_caps = param->peer_rate_caps; 3593 cmd->peer_caps = param->peer_caps; 3594 cmd->peer_listen_intval = param->peer_listen_intval; 3595 cmd->peer_ht_caps = param->peer_ht_caps; 3596 cmd->peer_max_mpdu = param->peer_max_mpdu; 3597 cmd->peer_mpdu_density = param->peer_mpdu_density; 3598 cmd->peer_vht_caps = param->peer_vht_caps; 3599 cmd->peer_phymode = param->peer_phymode; 3600 cmd->bss_max_idle_option = param->peer_bss_max_idle_option; 3601 3602 /* Update 11ax capabilities */ 3603 cmd->peer_he_cap_info = 3604 param->peer_he_cap_macinfo[WMI_HOST_HECAP_MAC_WORD1]; 3605 cmd->peer_he_cap_info_ext = 3606 param->peer_he_cap_macinfo[WMI_HOST_HECAP_MAC_WORD2]; 3607 cmd->peer_he_cap_info_internal = param->peer_he_cap_info_internal; 3608 cmd->peer_he_ops = param->peer_he_ops; 3609 qdf_mem_copy(&cmd->peer_he_cap_phy, ¶m->peer_he_cap_phyinfo, 3610 sizeof(param->peer_he_cap_phyinfo)); 3611 qdf_mem_copy(&cmd->peer_ppet, ¶m->peer_ppet, 3612 sizeof(param->peer_ppet)); 3613 cmd->peer_he_caps_6ghz = param->peer_he_caps_6ghz; 3614 3615 /* Update peer legacy rate information */ 3616 buf_ptr += sizeof(*cmd); 3617 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, 3618 peer_legacy_rates_align); 3619 buf_ptr += WMI_TLV_HDR_SIZE; 3620 cmd->num_peer_legacy_rates = param->peer_legacy_rates.num_rates; 3621 qdf_mem_copy(buf_ptr, param->peer_legacy_rates.rates, 3622 param->peer_legacy_rates.num_rates); 3623 3624 /* Update peer HT rate information */ 3625 buf_ptr += peer_legacy_rates_align; 3626 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, 3627 peer_ht_rates_align); 3628 buf_ptr += WMI_TLV_HDR_SIZE; 3629 cmd->num_peer_ht_rates = param->peer_ht_rates.num_rates; 3630 qdf_mem_copy(buf_ptr, param->peer_ht_rates.rates, 3631 param->peer_ht_rates.num_rates); 3632 3633 /* VHT Rates */ 3634 buf_ptr += peer_ht_rates_align; 3635 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_STRUC_wmi_vht_rate_set, 3636 WMITLV_GET_STRUCT_TLVLEN(wmi_vht_rate_set)); 3637 3638 cmd->auth_mode = param->akm; 3639 cmd->peer_nss = param->peer_nss; 3640 3641 /* Update bandwidth-NSS mapping */ 3642 cmd->peer_bw_rxnss_override = 0; 3643 cmd->peer_bw_rxnss_override |= param->peer_bw_rxnss_override; 3644 3645 mcs = (wmi_vht_rate_set *) buf_ptr; 3646 if (param->vht_capable) { 3647 mcs->rx_max_rate = param->rx_max_rate; 3648 mcs->rx_mcs_set = param->rx_mcs_set; 3649 mcs->tx_max_rate = param->tx_max_rate; 3650 mcs->tx_mcs_set = param->tx_mcs_set; 3651 mcs->tx_max_mcs_nss = param->tx_max_mcs_nss; 3652 } 3653 3654 /* HE Rates */ 3655 cmd->min_data_rate = param->min_data_rate; 3656 cmd->peer_he_mcs = param->peer_he_mcs_count; 3657 buf_ptr += sizeof(wmi_vht_rate_set); 3658 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 3659 (param->peer_he_mcs_count * sizeof(wmi_he_rate_set))); 3660 buf_ptr += WMI_TLV_HDR_SIZE; 3661 3662 WMI_PEER_STA_TYPE_SET(cmd->sta_type, param->peer_bsscolor_rept_info); 3663 /* Loop through the HE rate set */ 3664 for (i = 0; i < param->peer_he_mcs_count; i++) { 3665 he_mcs = (wmi_he_rate_set *) buf_ptr; 3666 WMITLV_SET_HDR(he_mcs, WMITLV_TAG_STRUC_wmi_he_rate_set, 3667 WMITLV_GET_STRUCT_TLVLEN(wmi_he_rate_set)); 3668 3669 he_mcs->rx_mcs_set = param->peer_he_rx_mcs_set[i]; 3670 he_mcs->tx_mcs_set = param->peer_he_tx_mcs_set[i]; 3671 wmi_debug("HE idx %d RxMCSmap %x TxMCSmap %x ", 3672 i, he_mcs->rx_mcs_set, he_mcs->tx_mcs_set); 3673 buf_ptr += sizeof(wmi_he_rate_set); 3674 } 3675 3676 if ((param->he_flag) && (param->peer_he_mcs_count > 1) && 3677 (param->peer_he_rx_mcs_set[WMI_HOST_HE_TXRX_MCS_NSS_IDX_160] 3678 == WMI_HOST_HE_INVALID_MCSNSSMAP || 3679 param->peer_he_tx_mcs_set[WMI_HOST_HE_TXRX_MCS_NSS_IDX_160] 3680 == WMI_HOST_HE_INVALID_MCSNSSMAP)) { 3681 wmi_debug("param->peer_he_tx_mcs_set[160MHz]=%x", 3682 param->peer_he_tx_mcs_set[WMI_HOST_HE_TXRX_MCS_NSS_IDX_160]); 3683 wmi_debug("param->peer_he_rx_mcs_set[160MHz]=%x", 3684 param->peer_he_rx_mcs_set[WMI_HOST_HE_TXRX_MCS_NSS_IDX_160]); 3685 wmi_debug("peer_mac="QDF_MAC_ADDR_FMT, 3686 QDF_MAC_ADDR_REF(param->peer_mac)); 3687 } 3688 3689 wmi_debug("vdev_id %d associd %d peer_flags %x rate_caps %x " 3690 "peer_caps %x listen_intval %d ht_caps %x max_mpdu %d " 3691 "nss %d phymode %d peer_mpdu_density %d " 3692 "cmd->peer_vht_caps %x " 3693 "HE cap_info %x ops %x " 3694 "HE cap_info_ext %x " 3695 "HE phy %x %x %x " 3696 "peer_bw_rxnss_override %x", 3697 cmd->vdev_id, cmd->peer_associd, cmd->peer_flags, 3698 cmd->peer_rate_caps, cmd->peer_caps, 3699 cmd->peer_listen_intval, cmd->peer_ht_caps, 3700 cmd->peer_max_mpdu, cmd->peer_nss, cmd->peer_phymode, 3701 cmd->peer_mpdu_density, 3702 cmd->peer_vht_caps, cmd->peer_he_cap_info, 3703 cmd->peer_he_ops, cmd->peer_he_cap_info_ext, 3704 cmd->peer_he_cap_phy[0], cmd->peer_he_cap_phy[1], 3705 cmd->peer_he_cap_phy[2], 3706 cmd->peer_bw_rxnss_override); 3707 3708 buf_ptr = peer_assoc_add_mlo_params(buf_ptr, param); 3709 3710 buf_ptr = update_peer_flags_tlv_ehtinfo(cmd, param, buf_ptr); 3711 3712 buf_ptr = peer_assoc_add_ml_partner_links(buf_ptr, param); 3713 3714 buf_ptr = peer_assoc_add_tid_to_link_map(buf_ptr, param); 3715 3716 wmi_mtrace(WMI_PEER_ASSOC_CMDID, cmd->vdev_id, 0); 3717 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 3718 WMI_PEER_ASSOC_CMDID); 3719 if (QDF_IS_STATUS_ERROR(ret)) { 3720 wmi_err("Failed to send peer assoc command ret = %d", ret); 3721 wmi_buf_free(buf); 3722 } 3723 3724 return ret; 3725 } 3726 3727 /* copy_scan_notify_events() - Helper routine to copy scan notify events 3728 */ 3729 static inline void copy_scan_event_cntrl_flags( 3730 wmi_start_scan_cmd_fixed_param * cmd, 3731 struct scan_req_params *param) 3732 { 3733 3734 /* Scan events subscription */ 3735 if (param->scan_ev_started) 3736 cmd->notify_scan_events |= WMI_SCAN_EVENT_STARTED; 3737 if (param->scan_ev_completed) 3738 cmd->notify_scan_events |= WMI_SCAN_EVENT_COMPLETED; 3739 if (param->scan_ev_bss_chan) 3740 cmd->notify_scan_events |= WMI_SCAN_EVENT_BSS_CHANNEL; 3741 if (param->scan_ev_foreign_chan) 3742 cmd->notify_scan_events |= WMI_SCAN_EVENT_FOREIGN_CHANNEL; 3743 if (param->scan_ev_dequeued) 3744 cmd->notify_scan_events |= WMI_SCAN_EVENT_DEQUEUED; 3745 if (param->scan_ev_preempted) 3746 cmd->notify_scan_events |= WMI_SCAN_EVENT_PREEMPTED; 3747 if (param->scan_ev_start_failed) 3748 cmd->notify_scan_events |= WMI_SCAN_EVENT_START_FAILED; 3749 if (param->scan_ev_restarted) 3750 cmd->notify_scan_events |= WMI_SCAN_EVENT_RESTARTED; 3751 if (param->scan_ev_foreign_chn_exit) 3752 cmd->notify_scan_events |= WMI_SCAN_EVENT_FOREIGN_CHANNEL_EXIT; 3753 if (param->scan_ev_suspended) 3754 cmd->notify_scan_events |= WMI_SCAN_EVENT_SUSPENDED; 3755 if (param->scan_ev_resumed) 3756 cmd->notify_scan_events |= WMI_SCAN_EVENT_RESUMED; 3757 3758 /** Set scan control flags */ 3759 cmd->scan_ctrl_flags = 0; 3760 if (param->scan_f_passive) 3761 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_PASSIVE; 3762 if (param->scan_f_strict_passive_pch) 3763 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_STRICT_PASSIVE_ON_PCHN; 3764 if (param->scan_f_promisc_mode) 3765 cmd->scan_ctrl_flags |= WMI_SCAN_FILTER_PROMISCOUS; 3766 if (param->scan_f_capture_phy_err) 3767 cmd->scan_ctrl_flags |= WMI_SCAN_CAPTURE_PHY_ERROR; 3768 if (param->scan_f_half_rate) 3769 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_HALF_RATE_SUPPORT; 3770 if (param->scan_f_quarter_rate) 3771 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_QUARTER_RATE_SUPPORT; 3772 if (param->scan_f_cck_rates) 3773 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_CCK_RATES; 3774 if (param->scan_f_ofdm_rates) 3775 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_OFDM_RATES; 3776 if (param->scan_f_chan_stat_evnt) 3777 cmd->scan_ctrl_flags |= WMI_SCAN_CHAN_STAT_EVENT; 3778 if (param->scan_f_filter_prb_req) 3779 cmd->scan_ctrl_flags |= WMI_SCAN_FILTER_PROBE_REQ; 3780 if (param->scan_f_bcast_probe) 3781 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_BCAST_PROBE_REQ; 3782 if (param->scan_f_offchan_mgmt_tx) 3783 cmd->scan_ctrl_flags |= WMI_SCAN_OFFCHAN_MGMT_TX; 3784 if (param->scan_f_offchan_data_tx) 3785 cmd->scan_ctrl_flags |= WMI_SCAN_OFFCHAN_DATA_TX; 3786 if (param->scan_f_force_active_dfs_chn) 3787 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_FORCE_ACTIVE_ON_DFS; 3788 if (param->scan_f_add_tpc_ie_in_probe) 3789 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_TPC_IE_IN_PROBE_REQ; 3790 if (param->scan_f_add_ds_ie_in_probe) 3791 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_DS_IE_IN_PROBE_REQ; 3792 if (param->scan_f_add_spoofed_mac_in_probe) 3793 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_SPOOFED_MAC_IN_PROBE_REQ; 3794 if (param->scan_f_add_rand_seq_in_probe) 3795 cmd->scan_ctrl_flags |= WMI_SCAN_RANDOM_SEQ_NO_IN_PROBE_REQ; 3796 if (param->scan_f_en_ie_allowlist_in_probe) 3797 cmd->scan_ctrl_flags |= 3798 WMI_SCAN_ENABLE_IE_WHTELIST_IN_PROBE_REQ; 3799 3800 /* for adaptive scan mode using 3 bits (21 - 23 bits) */ 3801 WMI_SCAN_SET_DWELL_MODE(cmd->scan_ctrl_flags, 3802 param->adaptive_dwell_time_mode); 3803 } 3804 3805 /* scan_copy_ie_buffer() - Copy scan ie_data */ 3806 static inline void scan_copy_ie_buffer(uint8_t *buf_ptr, 3807 struct scan_req_params *params) 3808 { 3809 qdf_mem_copy(buf_ptr, params->extraie.ptr, params->extraie.len); 3810 } 3811 3812 /** 3813 * wmi_copy_scan_random_mac() - To copy scan randomization attrs to wmi buffer 3814 * @mac: random mac addr 3815 * @mask: random mac mask 3816 * @mac_addr: wmi random mac 3817 * @mac_mask: wmi random mac mask 3818 * 3819 * Return None. 3820 */ 3821 static inline 3822 void wmi_copy_scan_random_mac(uint8_t *mac, uint8_t *mask, 3823 wmi_mac_addr *mac_addr, wmi_mac_addr *mac_mask) 3824 { 3825 WMI_CHAR_ARRAY_TO_MAC_ADDR(mac, mac_addr); 3826 WMI_CHAR_ARRAY_TO_MAC_ADDR(mask, mac_mask); 3827 } 3828 3829 /* 3830 * wmi_fill_vendor_oui() - fill vendor OUIs 3831 * @buf_ptr: pointer to wmi tlv buffer 3832 * @num_vendor_oui: number of vendor OUIs to be filled 3833 * @param_voui: pointer to OUI buffer 3834 * 3835 * This function populates the wmi tlv buffer when vendor specific OUIs are 3836 * present. 3837 * 3838 * Return: None 3839 */ 3840 static inline 3841 void wmi_fill_vendor_oui(uint8_t *buf_ptr, uint32_t num_vendor_oui, 3842 uint32_t *pvoui) 3843 { 3844 wmi_vendor_oui *voui = NULL; 3845 uint32_t i; 3846 3847 voui = (wmi_vendor_oui *)buf_ptr; 3848 3849 for (i = 0; i < num_vendor_oui; i++) { 3850 WMITLV_SET_HDR(&voui[i].tlv_header, 3851 WMITLV_TAG_STRUC_wmi_vendor_oui, 3852 WMITLV_GET_STRUCT_TLVLEN(wmi_vendor_oui)); 3853 voui[i].oui_type_subtype = pvoui[i]; 3854 } 3855 } 3856 3857 /* 3858 * wmi_fill_ie_allowlist_attrs() - fill IE allowlist attrs 3859 * @ie_bitmap: output pointer to ie bit map in cmd 3860 * @num_vendor_oui: output pointer to num vendor OUIs 3861 * @ie_allowlist: input parameter 3862 * 3863 * This function populates the IE allowlist attrs of scan, pno and 3864 * scan oui commands for ie_allowlist parameter. 3865 * 3866 * Return: None 3867 */ 3868 static inline 3869 void wmi_fill_ie_allowlist_attrs(uint32_t *ie_bitmap, 3870 uint32_t *num_vendor_oui, 3871 struct probe_req_allowlist_attr *ie_allowlist) 3872 { 3873 uint32_t i = 0; 3874 3875 for (i = 0; i < PROBE_REQ_BITMAP_LEN; i++) 3876 ie_bitmap[i] = ie_allowlist->ie_bitmap[i]; 3877 3878 *num_vendor_oui = ie_allowlist->num_vendor_oui; 3879 } 3880 3881 /** 3882 * send_scan_start_cmd_tlv() - WMI scan start function 3883 * @param wmi_handle : handle to WMI. 3884 * @param param : pointer to hold scan start cmd parameter 3885 * 3886 * Return: 0 on success and -ve on failure. 3887 */ 3888 static QDF_STATUS send_scan_start_cmd_tlv(wmi_unified_t wmi_handle, 3889 struct scan_req_params *params) 3890 { 3891 int32_t ret = 0; 3892 int32_t i; 3893 wmi_buf_t wmi_buf; 3894 wmi_start_scan_cmd_fixed_param *cmd; 3895 uint8_t *buf_ptr; 3896 uint32_t *tmp_ptr; 3897 wmi_ssid *ssid = NULL; 3898 wmi_mac_addr *bssid; 3899 size_t len = sizeof(*cmd); 3900 uint16_t extraie_len_with_pad = 0; 3901 uint8_t phymode_roundup = 0; 3902 struct probe_req_allowlist_attr *ie_allowlist = ¶ms->ie_allowlist; 3903 wmi_hint_freq_short_ssid *s_ssid = NULL; 3904 wmi_hint_freq_bssid *hint_bssid = NULL; 3905 3906 /* Length TLV placeholder for array of uint32_t */ 3907 len += WMI_TLV_HDR_SIZE; 3908 /* calculate the length of buffer required */ 3909 if (params->chan_list.num_chan) 3910 len += params->chan_list.num_chan * sizeof(uint32_t); 3911 3912 /* Length TLV placeholder for array of wmi_ssid structures */ 3913 len += WMI_TLV_HDR_SIZE; 3914 if (params->num_ssids) 3915 len += params->num_ssids * sizeof(wmi_ssid); 3916 3917 /* Length TLV placeholder for array of wmi_mac_addr structures */ 3918 len += WMI_TLV_HDR_SIZE; 3919 if (params->num_bssid) 3920 len += sizeof(wmi_mac_addr) * params->num_bssid; 3921 3922 /* Length TLV placeholder for array of bytes */ 3923 len += WMI_TLV_HDR_SIZE; 3924 if (params->extraie.len) 3925 extraie_len_with_pad = 3926 roundup(params->extraie.len, sizeof(uint32_t)); 3927 len += extraie_len_with_pad; 3928 3929 len += WMI_TLV_HDR_SIZE; /* Length of TLV for array of wmi_vendor_oui */ 3930 if (ie_allowlist->num_vendor_oui) 3931 len += ie_allowlist->num_vendor_oui * sizeof(wmi_vendor_oui); 3932 3933 len += WMI_TLV_HDR_SIZE; /* Length of TLV for array of scan phymode */ 3934 if (params->scan_f_wide_band) 3935 phymode_roundup = 3936 qdf_roundup(params->chan_list.num_chan * sizeof(uint8_t), 3937 sizeof(uint32_t)); 3938 len += phymode_roundup; 3939 3940 len += WMI_TLV_HDR_SIZE; 3941 if (params->num_hint_bssid) 3942 len += params->num_hint_bssid * sizeof(wmi_hint_freq_bssid); 3943 3944 len += WMI_TLV_HDR_SIZE; 3945 if (params->num_hint_s_ssid) 3946 len += params->num_hint_s_ssid * sizeof(wmi_hint_freq_short_ssid); 3947 3948 /* Allocate the memory */ 3949 wmi_buf = wmi_buf_alloc(wmi_handle, len); 3950 if (!wmi_buf) 3951 return QDF_STATUS_E_FAILURE; 3952 3953 buf_ptr = (uint8_t *) wmi_buf_data(wmi_buf); 3954 cmd = (wmi_start_scan_cmd_fixed_param *) buf_ptr; 3955 WMITLV_SET_HDR(&cmd->tlv_header, 3956 WMITLV_TAG_STRUC_wmi_start_scan_cmd_fixed_param, 3957 WMITLV_GET_STRUCT_TLVLEN 3958 (wmi_start_scan_cmd_fixed_param)); 3959 3960 cmd->scan_id = params->scan_id; 3961 cmd->scan_req_id = params->scan_req_id; 3962 cmd->vdev_id = params->vdev_id; 3963 cmd->scan_priority = params->scan_priority; 3964 3965 copy_scan_event_cntrl_flags(cmd, params); 3966 3967 cmd->dwell_time_active = params->dwell_time_active; 3968 cmd->dwell_time_active_2g = params->dwell_time_active_2g; 3969 cmd->dwell_time_passive = params->dwell_time_passive; 3970 cmd->min_dwell_time_6ghz = params->min_dwell_time_6g; 3971 cmd->dwell_time_active_6ghz = params->dwell_time_active_6g; 3972 cmd->dwell_time_passive_6ghz = params->dwell_time_passive_6g; 3973 cmd->scan_start_offset = params->scan_offset_time; 3974 cmd->min_rest_time = params->min_rest_time; 3975 cmd->max_rest_time = params->max_rest_time; 3976 cmd->repeat_probe_time = params->repeat_probe_time; 3977 cmd->probe_spacing_time = params->probe_spacing_time; 3978 cmd->idle_time = params->idle_time; 3979 cmd->max_scan_time = params->max_scan_time; 3980 cmd->probe_delay = params->probe_delay; 3981 cmd->burst_duration = params->burst_duration; 3982 cmd->num_chan = params->chan_list.num_chan; 3983 cmd->num_bssid = params->num_bssid; 3984 cmd->num_ssids = params->num_ssids; 3985 cmd->ie_len = params->extraie.len; 3986 cmd->n_probes = params->n_probes; 3987 cmd->scan_ctrl_flags_ext = params->scan_ctrl_flags_ext; 3988 3989 if (params->scan_random.randomize) 3990 wmi_copy_scan_random_mac(params->scan_random.mac_addr, 3991 params->scan_random.mac_mask, 3992 &cmd->mac_addr, 3993 &cmd->mac_mask); 3994 3995 if (ie_allowlist->allow_list) 3996 wmi_fill_ie_allowlist_attrs(cmd->ie_bitmap, 3997 &cmd->num_vendor_oui, 3998 ie_allowlist); 3999 4000 buf_ptr += sizeof(*cmd); 4001 tmp_ptr = (uint32_t *) (buf_ptr + WMI_TLV_HDR_SIZE); 4002 for (i = 0; i < params->chan_list.num_chan; ++i) { 4003 TARGET_SET_FREQ_IN_CHAN_LIST_TLV(tmp_ptr[i], 4004 params->chan_list.chan[i].freq); 4005 TARGET_SET_FLAGS_IN_CHAN_LIST_TLV(tmp_ptr[i], 4006 params->chan_list.chan[i].flags); 4007 } 4008 4009 WMITLV_SET_HDR(buf_ptr, 4010 WMITLV_TAG_ARRAY_UINT32, 4011 (params->chan_list.num_chan * sizeof(uint32_t))); 4012 buf_ptr += WMI_TLV_HDR_SIZE + 4013 (params->chan_list.num_chan * sizeof(uint32_t)); 4014 4015 if (params->num_ssids > WLAN_SCAN_MAX_NUM_SSID) { 4016 wmi_err("Invalid value for num_ssids %d", params->num_ssids); 4017 goto error; 4018 } 4019 4020 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_FIXED_STRUC, 4021 (params->num_ssids * sizeof(wmi_ssid))); 4022 4023 if (params->num_ssids) { 4024 ssid = (wmi_ssid *) (buf_ptr + WMI_TLV_HDR_SIZE); 4025 for (i = 0; i < params->num_ssids; ++i) { 4026 ssid->ssid_len = params->ssid[i].length; 4027 qdf_mem_copy(ssid->ssid, params->ssid[i].ssid, 4028 params->ssid[i].length); 4029 ssid++; 4030 } 4031 } 4032 buf_ptr += WMI_TLV_HDR_SIZE + (params->num_ssids * sizeof(wmi_ssid)); 4033 4034 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_FIXED_STRUC, 4035 (params->num_bssid * sizeof(wmi_mac_addr))); 4036 bssid = (wmi_mac_addr *) (buf_ptr + WMI_TLV_HDR_SIZE); 4037 4038 if (params->num_bssid) { 4039 for (i = 0; i < params->num_bssid; ++i) { 4040 WMI_CHAR_ARRAY_TO_MAC_ADDR( 4041 ¶ms->bssid_list[i].bytes[0], bssid); 4042 bssid++; 4043 } 4044 } 4045 4046 buf_ptr += WMI_TLV_HDR_SIZE + 4047 (params->num_bssid * sizeof(wmi_mac_addr)); 4048 4049 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, extraie_len_with_pad); 4050 if (params->extraie.len) 4051 scan_copy_ie_buffer(buf_ptr + WMI_TLV_HDR_SIZE, 4052 params); 4053 4054 buf_ptr += WMI_TLV_HDR_SIZE + extraie_len_with_pad; 4055 4056 /* probe req ie allowlisting */ 4057 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 4058 ie_allowlist->num_vendor_oui * sizeof(wmi_vendor_oui)); 4059 4060 buf_ptr += WMI_TLV_HDR_SIZE; 4061 4062 if (cmd->num_vendor_oui) { 4063 wmi_fill_vendor_oui(buf_ptr, cmd->num_vendor_oui, 4064 ie_allowlist->voui); 4065 buf_ptr += cmd->num_vendor_oui * sizeof(wmi_vendor_oui); 4066 } 4067 4068 /* Add phy mode TLV if it's a wide band scan */ 4069 if (params->scan_f_wide_band) { 4070 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, phymode_roundup); 4071 buf_ptr = (uint8_t *) (buf_ptr + WMI_TLV_HDR_SIZE); 4072 for (i = 0; i < params->chan_list.num_chan; ++i) 4073 buf_ptr[i] = 4074 WMI_SCAN_CHAN_SET_MODE(params->chan_list.chan[i].phymode); 4075 buf_ptr += phymode_roundup; 4076 } else { 4077 /* Add ZERO legth phy mode TLV */ 4078 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, 0); 4079 buf_ptr += WMI_TLV_HDR_SIZE; 4080 } 4081 4082 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_FIXED_STRUC, 4083 (params->num_hint_s_ssid * sizeof(wmi_hint_freq_short_ssid))); 4084 if (params->num_hint_s_ssid) { 4085 s_ssid = (wmi_hint_freq_short_ssid *)(buf_ptr + WMI_TLV_HDR_SIZE); 4086 for (i = 0; i < params->num_hint_s_ssid; ++i) { 4087 s_ssid->freq_flags = params->hint_s_ssid[i].freq_flags; 4088 s_ssid->short_ssid = params->hint_s_ssid[i].short_ssid; 4089 s_ssid++; 4090 } 4091 } 4092 buf_ptr += WMI_TLV_HDR_SIZE + 4093 (params->num_hint_s_ssid * sizeof(wmi_hint_freq_short_ssid)); 4094 4095 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_FIXED_STRUC, 4096 (params->num_hint_bssid * sizeof(wmi_hint_freq_bssid))); 4097 if (params->num_hint_bssid) { 4098 hint_bssid = (wmi_hint_freq_bssid *)(buf_ptr + WMI_TLV_HDR_SIZE); 4099 for (i = 0; i < params->num_hint_bssid; ++i) { 4100 hint_bssid->freq_flags = 4101 params->hint_bssid[i].freq_flags; 4102 WMI_CHAR_ARRAY_TO_MAC_ADDR(¶ms->hint_bssid[i].bssid.bytes[0], 4103 &hint_bssid->bssid); 4104 hint_bssid++; 4105 } 4106 } 4107 4108 wmi_mtrace(WMI_START_SCAN_CMDID, cmd->vdev_id, 0); 4109 ret = wmi_unified_cmd_send(wmi_handle, wmi_buf, 4110 len, WMI_START_SCAN_CMDID); 4111 if (ret) { 4112 wmi_err("Failed to start scan: %d", ret); 4113 wmi_buf_free(wmi_buf); 4114 } 4115 return ret; 4116 error: 4117 wmi_buf_free(wmi_buf); 4118 return QDF_STATUS_E_FAILURE; 4119 } 4120 4121 /** 4122 * send_scan_stop_cmd_tlv() - WMI scan start function 4123 * @param wmi_handle : handle to WMI. 4124 * @param param : pointer to hold scan cancel cmd parameter 4125 * 4126 * Return: 0 on success and -ve on failure. 4127 */ 4128 static QDF_STATUS send_scan_stop_cmd_tlv(wmi_unified_t wmi_handle, 4129 struct scan_cancel_param *param) 4130 { 4131 wmi_stop_scan_cmd_fixed_param *cmd; 4132 int ret; 4133 int len = sizeof(*cmd); 4134 wmi_buf_t wmi_buf; 4135 4136 /* Allocate the memory */ 4137 wmi_buf = wmi_buf_alloc(wmi_handle, len); 4138 if (!wmi_buf) { 4139 ret = QDF_STATUS_E_NOMEM; 4140 goto error; 4141 } 4142 4143 cmd = (wmi_stop_scan_cmd_fixed_param *) wmi_buf_data(wmi_buf); 4144 WMITLV_SET_HDR(&cmd->tlv_header, 4145 WMITLV_TAG_STRUC_wmi_stop_scan_cmd_fixed_param, 4146 WMITLV_GET_STRUCT_TLVLEN(wmi_stop_scan_cmd_fixed_param)); 4147 cmd->vdev_id = param->vdev_id; 4148 cmd->requestor = param->requester; 4149 cmd->scan_id = param->scan_id; 4150 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 4151 wmi_handle, 4152 param->pdev_id); 4153 /* stop the scan with the corresponding scan_id */ 4154 if (param->req_type == WLAN_SCAN_CANCEL_PDEV_ALL) { 4155 /* Cancelling all scans */ 4156 cmd->req_type = WMI_SCAN_STOP_ALL; 4157 } else if (param->req_type == WLAN_SCAN_CANCEL_VDEV_ALL) { 4158 /* Cancelling VAP scans */ 4159 cmd->req_type = WMI_SCN_STOP_VAP_ALL; 4160 } else if (param->req_type == WLAN_SCAN_CANCEL_SINGLE) { 4161 /* Cancelling specific scan */ 4162 cmd->req_type = WMI_SCAN_STOP_ONE; 4163 } else if (param->req_type == WLAN_SCAN_CANCEL_HOST_VDEV_ALL) { 4164 cmd->req_type = WMI_SCN_STOP_HOST_VAP_ALL; 4165 } else { 4166 wmi_err("Invalid Scan cancel req type: %d", param->req_type); 4167 wmi_buf_free(wmi_buf); 4168 return QDF_STATUS_E_INVAL; 4169 } 4170 4171 wmi_mtrace(WMI_STOP_SCAN_CMDID, cmd->vdev_id, 0); 4172 ret = wmi_unified_cmd_send(wmi_handle, wmi_buf, 4173 len, WMI_STOP_SCAN_CMDID); 4174 if (ret) { 4175 wmi_err("Failed to send stop scan: %d", ret); 4176 wmi_buf_free(wmi_buf); 4177 } 4178 4179 error: 4180 return ret; 4181 } 4182 4183 #define WMI_MAX_CHAN_INFO_LOG 192 4184 4185 /** 4186 * wmi_scan_chanlist_dump() - Dump scan channel list info 4187 * @scan_chan_list: scan channel list 4188 * 4189 * Return: void 4190 */ 4191 static void wmi_scan_chanlist_dump(struct scan_chan_list_params *scan_chan_list) 4192 { 4193 uint32_t i; 4194 uint8_t info[WMI_MAX_CHAN_INFO_LOG]; 4195 uint32_t len = 0; 4196 struct channel_param *chan; 4197 int ret; 4198 4199 wmi_debug("Total chan %d", scan_chan_list->nallchans); 4200 for (i = 0; i < scan_chan_list->nallchans; i++) { 4201 chan = &scan_chan_list->ch_param[i]; 4202 ret = qdf_scnprintf(info + len, sizeof(info) - len, 4203 " %d[%d][%d][%d]", chan->mhz, 4204 chan->maxregpower, 4205 chan->dfs_set, chan->nan_disabled); 4206 if (ret <= 0) 4207 break; 4208 len += ret; 4209 if (len >= (sizeof(info) - 20)) { 4210 wmi_nofl_debug("Chan[TXPwr][DFS][nan_disabled]:%s", 4211 info); 4212 len = 0; 4213 } 4214 } 4215 if (len) 4216 wmi_nofl_debug("Chan[TXPwr][DFS]:%s", info); 4217 } 4218 4219 static QDF_STATUS send_scan_chan_list_cmd_tlv(wmi_unified_t wmi_handle, 4220 struct scan_chan_list_params *chan_list) 4221 { 4222 wmi_buf_t buf; 4223 QDF_STATUS qdf_status = QDF_STATUS_SUCCESS; 4224 wmi_scan_chan_list_cmd_fixed_param *cmd; 4225 int i; 4226 uint8_t *buf_ptr; 4227 wmi_channel *chan_info; 4228 struct channel_param *tchan_info; 4229 uint16_t len; 4230 uint16_t num_send_chans, num_sends = 0; 4231 4232 wmi_scan_chanlist_dump(chan_list); 4233 tchan_info = &chan_list->ch_param[0]; 4234 while (chan_list->nallchans) { 4235 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE; 4236 if (chan_list->nallchans > MAX_NUM_CHAN_PER_WMI_CMD) 4237 num_send_chans = MAX_NUM_CHAN_PER_WMI_CMD; 4238 else 4239 num_send_chans = chan_list->nallchans; 4240 4241 chan_list->nallchans -= num_send_chans; 4242 len += sizeof(wmi_channel) * num_send_chans; 4243 buf = wmi_buf_alloc(wmi_handle, len); 4244 if (!buf) { 4245 qdf_status = QDF_STATUS_E_NOMEM; 4246 goto end; 4247 } 4248 4249 buf_ptr = (uint8_t *)wmi_buf_data(buf); 4250 cmd = (wmi_scan_chan_list_cmd_fixed_param *)buf_ptr; 4251 WMITLV_SET_HDR(&cmd->tlv_header, 4252 WMITLV_TAG_STRUC_wmi_scan_chan_list_cmd_fixed_param, 4253 WMITLV_GET_STRUCT_TLVLEN 4254 (wmi_scan_chan_list_cmd_fixed_param)); 4255 4256 wmi_debug("no of channels = %d, len = %d", num_send_chans, len); 4257 4258 if (num_sends) 4259 cmd->flags |= APPEND_TO_EXISTING_CHAN_LIST; 4260 4261 if (chan_list->max_bw_support_present) 4262 cmd->flags |= CHANNEL_MAX_BANDWIDTH_VALID; 4263 4264 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 4265 wmi_handle, 4266 chan_list->pdev_id); 4267 4268 wmi_mtrace(WMI_SCAN_CHAN_LIST_CMDID, cmd->pdev_id, 0); 4269 4270 cmd->num_scan_chans = num_send_chans; 4271 WMITLV_SET_HDR((buf_ptr + 4272 sizeof(wmi_scan_chan_list_cmd_fixed_param)), 4273 WMITLV_TAG_ARRAY_STRUC, 4274 sizeof(wmi_channel) * num_send_chans); 4275 chan_info = (wmi_channel *)(buf_ptr + sizeof(*cmd) + 4276 WMI_TLV_HDR_SIZE); 4277 4278 for (i = 0; i < num_send_chans; ++i) { 4279 WMITLV_SET_HDR(&chan_info->tlv_header, 4280 WMITLV_TAG_STRUC_wmi_channel, 4281 WMITLV_GET_STRUCT_TLVLEN(wmi_channel)); 4282 chan_info->mhz = tchan_info->mhz; 4283 chan_info->band_center_freq1 = 4284 tchan_info->cfreq1; 4285 chan_info->band_center_freq2 = 4286 tchan_info->cfreq2; 4287 4288 if (tchan_info->is_chan_passive) 4289 WMI_SET_CHANNEL_FLAG(chan_info, 4290 WMI_CHAN_FLAG_PASSIVE); 4291 if (tchan_info->dfs_set) 4292 WMI_SET_CHANNEL_FLAG(chan_info, 4293 WMI_CHAN_FLAG_DFS); 4294 4295 if (tchan_info->dfs_set_cfreq2) 4296 WMI_SET_CHANNEL_FLAG(chan_info, 4297 WMI_CHAN_FLAG_DFS_CFREQ2); 4298 4299 if (tchan_info->allow_he) 4300 WMI_SET_CHANNEL_FLAG(chan_info, 4301 WMI_CHAN_FLAG_ALLOW_HE); 4302 4303 if (tchan_info->allow_eht) 4304 WMI_SET_CHANNEL_FLAG(chan_info, 4305 WMI_CHAN_FLAG_ALLOW_EHT); 4306 4307 if (tchan_info->allow_vht) 4308 WMI_SET_CHANNEL_FLAG(chan_info, 4309 WMI_CHAN_FLAG_ALLOW_VHT); 4310 4311 if (tchan_info->allow_ht) 4312 WMI_SET_CHANNEL_FLAG(chan_info, 4313 WMI_CHAN_FLAG_ALLOW_HT); 4314 WMI_SET_CHANNEL_MODE(chan_info, 4315 tchan_info->phy_mode); 4316 4317 if (tchan_info->half_rate) 4318 WMI_SET_CHANNEL_FLAG(chan_info, 4319 WMI_CHAN_FLAG_HALF_RATE); 4320 4321 if (tchan_info->quarter_rate) 4322 WMI_SET_CHANNEL_FLAG(chan_info, 4323 WMI_CHAN_FLAG_QUARTER_RATE); 4324 4325 if (tchan_info->psc_channel) 4326 WMI_SET_CHANNEL_FLAG(chan_info, 4327 WMI_CHAN_FLAG_PSC); 4328 4329 if (tchan_info->nan_disabled) 4330 WMI_SET_CHANNEL_FLAG(chan_info, 4331 WMI_CHAN_FLAG_NAN_DISABLED); 4332 4333 /* also fill in power information */ 4334 WMI_SET_CHANNEL_MIN_POWER(chan_info, 4335 tchan_info->minpower); 4336 WMI_SET_CHANNEL_MAX_POWER(chan_info, 4337 tchan_info->maxpower); 4338 WMI_SET_CHANNEL_REG_POWER(chan_info, 4339 tchan_info->maxregpower); 4340 WMI_SET_CHANNEL_ANTENNA_MAX(chan_info, 4341 tchan_info->antennamax); 4342 WMI_SET_CHANNEL_REG_CLASSID(chan_info, 4343 tchan_info->reg_class_id); 4344 WMI_SET_CHANNEL_MAX_TX_POWER(chan_info, 4345 tchan_info->maxregpower); 4346 WMI_SET_CHANNEL_MAX_BANDWIDTH(chan_info, 4347 tchan_info->max_bw_supported); 4348 4349 tchan_info++; 4350 chan_info++; 4351 } 4352 4353 qdf_status = wmi_unified_cmd_send( 4354 wmi_handle, 4355 buf, len, WMI_SCAN_CHAN_LIST_CMDID); 4356 4357 if (QDF_IS_STATUS_ERROR(qdf_status)) { 4358 wmi_err("Failed to send WMI_SCAN_CHAN_LIST_CMDID"); 4359 wmi_buf_free(buf); 4360 goto end; 4361 } 4362 num_sends++; 4363 } 4364 4365 end: 4366 return qdf_status; 4367 } 4368 4369 /** 4370 * populate_tx_send_params - Populate TX param TLV for mgmt and offchan tx 4371 * 4372 * @bufp: Pointer to buffer 4373 * @param: Pointer to tx param 4374 * 4375 * Return: QDF_STATUS_SUCCESS for success and QDF_STATUS_E_FAILURE for failure 4376 */ 4377 static inline QDF_STATUS populate_tx_send_params(uint8_t *bufp, 4378 struct tx_send_params param) 4379 { 4380 wmi_tx_send_params *tx_param; 4381 QDF_STATUS status = QDF_STATUS_SUCCESS; 4382 4383 if (!bufp) { 4384 status = QDF_STATUS_E_FAILURE; 4385 return status; 4386 } 4387 tx_param = (wmi_tx_send_params *)bufp; 4388 WMITLV_SET_HDR(&tx_param->tlv_header, 4389 WMITLV_TAG_STRUC_wmi_tx_send_params, 4390 WMITLV_GET_STRUCT_TLVLEN(wmi_tx_send_params)); 4391 WMI_TX_SEND_PARAM_PWR_SET(tx_param->tx_param_dword0, param.pwr); 4392 WMI_TX_SEND_PARAM_MCS_MASK_SET(tx_param->tx_param_dword0, 4393 param.mcs_mask); 4394 WMI_TX_SEND_PARAM_NSS_MASK_SET(tx_param->tx_param_dword0, 4395 param.nss_mask); 4396 WMI_TX_SEND_PARAM_RETRY_LIMIT_SET(tx_param->tx_param_dword0, 4397 param.retry_limit); 4398 WMI_TX_SEND_PARAM_CHAIN_MASK_SET(tx_param->tx_param_dword1, 4399 param.chain_mask); 4400 WMI_TX_SEND_PARAM_BW_MASK_SET(tx_param->tx_param_dword1, 4401 param.bw_mask); 4402 WMI_TX_SEND_PARAM_PREAMBLE_SET(tx_param->tx_param_dword1, 4403 param.preamble_type); 4404 WMI_TX_SEND_PARAM_FRAME_TYPE_SET(tx_param->tx_param_dword1, 4405 param.frame_type); 4406 WMI_TX_SEND_PARAM_CFR_CAPTURE_SET(tx_param->tx_param_dword1, 4407 param.cfr_enable); 4408 WMI_TX_SEND_PARAM_BEAMFORM_SET(tx_param->tx_param_dword1, 4409 param.en_beamforming); 4410 WMI_TX_SEND_PARAM_RETRY_LIMIT_EXT_SET(tx_param->tx_param_dword1, 4411 param.retry_limit_ext); 4412 4413 return status; 4414 } 4415 4416 #ifdef CONFIG_HL_SUPPORT 4417 /** 4418 * send_mgmt_cmd_tlv() - WMI scan start function 4419 * @wmi_handle : handle to WMI. 4420 * @param : pointer to hold mgmt cmd parameter 4421 * 4422 * Return: 0 on success and -ve on failure. 4423 */ 4424 static QDF_STATUS send_mgmt_cmd_tlv(wmi_unified_t wmi_handle, 4425 struct wmi_mgmt_params *param) 4426 { 4427 wmi_buf_t buf; 4428 uint8_t *bufp; 4429 int32_t cmd_len; 4430 wmi_mgmt_tx_send_cmd_fixed_param *cmd; 4431 int32_t bufp_len = (param->frm_len < mgmt_tx_dl_frm_len) ? param->frm_len : 4432 mgmt_tx_dl_frm_len; 4433 4434 if (param->frm_len > mgmt_tx_dl_frm_len) { 4435 wmi_err("mgmt frame len %u exceeds %u", 4436 param->frm_len, mgmt_tx_dl_frm_len); 4437 return QDF_STATUS_E_INVAL; 4438 } 4439 4440 cmd_len = sizeof(wmi_mgmt_tx_send_cmd_fixed_param) + 4441 WMI_TLV_HDR_SIZE + 4442 roundup(bufp_len, sizeof(uint32_t)); 4443 4444 buf = wmi_buf_alloc(wmi_handle, sizeof(wmi_tx_send_params) + cmd_len); 4445 if (!buf) 4446 return QDF_STATUS_E_NOMEM; 4447 4448 cmd = (wmi_mgmt_tx_send_cmd_fixed_param *)wmi_buf_data(buf); 4449 bufp = (uint8_t *) cmd; 4450 WMITLV_SET_HDR(&cmd->tlv_header, 4451 WMITLV_TAG_STRUC_wmi_mgmt_tx_send_cmd_fixed_param, 4452 WMITLV_GET_STRUCT_TLVLEN 4453 (wmi_mgmt_tx_send_cmd_fixed_param)); 4454 4455 cmd->vdev_id = param->vdev_id; 4456 4457 cmd->desc_id = param->desc_id; 4458 cmd->chanfreq = param->chanfreq; 4459 bufp += sizeof(wmi_mgmt_tx_send_cmd_fixed_param); 4460 WMITLV_SET_HDR(bufp, WMITLV_TAG_ARRAY_BYTE, roundup(bufp_len, 4461 sizeof(uint32_t))); 4462 bufp += WMI_TLV_HDR_SIZE; 4463 qdf_mem_copy(bufp, param->pdata, bufp_len); 4464 4465 cmd->frame_len = param->frm_len; 4466 cmd->buf_len = bufp_len; 4467 cmd->tx_params_valid = param->tx_params_valid; 4468 cmd->tx_flags = param->tx_flags; 4469 cmd->peer_rssi = param->peer_rssi; 4470 4471 wmi_mgmt_cmd_record(wmi_handle, WMI_MGMT_TX_SEND_CMDID, 4472 bufp, cmd->vdev_id, cmd->chanfreq); 4473 4474 bufp += roundup(bufp_len, sizeof(uint32_t)); 4475 if (param->tx_params_valid) { 4476 if (populate_tx_send_params(bufp, param->tx_param) != 4477 QDF_STATUS_SUCCESS) { 4478 wmi_err("Populate TX send params failed"); 4479 goto free_buf; 4480 } 4481 cmd_len += sizeof(wmi_tx_send_params); 4482 } 4483 4484 wmi_mtrace(WMI_MGMT_TX_SEND_CMDID, cmd->vdev_id, 0); 4485 if (wmi_unified_cmd_send(wmi_handle, buf, cmd_len, 4486 WMI_MGMT_TX_SEND_CMDID)) { 4487 wmi_err("Failed to send mgmt Tx"); 4488 goto free_buf; 4489 } 4490 return QDF_STATUS_SUCCESS; 4491 4492 free_buf: 4493 wmi_buf_free(buf); 4494 return QDF_STATUS_E_FAILURE; 4495 } 4496 #else 4497 /** 4498 * send_mgmt_cmd_tlv() - WMI scan start function 4499 * @wmi_handle : handle to WMI. 4500 * @param : pointer to hold mgmt cmd parameter 4501 * 4502 * Return: 0 on success and -ve on failure. 4503 */ 4504 static QDF_STATUS send_mgmt_cmd_tlv(wmi_unified_t wmi_handle, 4505 struct wmi_mgmt_params *param) 4506 { 4507 wmi_buf_t buf; 4508 wmi_mgmt_tx_send_cmd_fixed_param *cmd; 4509 int32_t cmd_len; 4510 uint64_t dma_addr; 4511 void *qdf_ctx = param->qdf_ctx; 4512 uint8_t *bufp; 4513 QDF_STATUS status = QDF_STATUS_SUCCESS; 4514 wmi_mlo_tx_send_params *mlo_params; 4515 int32_t bufp_len = (param->frm_len < mgmt_tx_dl_frm_len) ? param->frm_len : 4516 mgmt_tx_dl_frm_len; 4517 4518 cmd_len = sizeof(wmi_mgmt_tx_send_cmd_fixed_param) + 4519 WMI_TLV_HDR_SIZE + 4520 roundup(bufp_len, sizeof(uint32_t)); 4521 4522 buf = wmi_buf_alloc(wmi_handle, sizeof(wmi_tx_send_params) + cmd_len + 4523 WMI_TLV_HDR_SIZE + sizeof(wmi_mlo_tx_send_params)); 4524 if (!buf) 4525 return QDF_STATUS_E_NOMEM; 4526 4527 cmd = (wmi_mgmt_tx_send_cmd_fixed_param *)wmi_buf_data(buf); 4528 bufp = (uint8_t *) cmd; 4529 WMITLV_SET_HDR(&cmd->tlv_header, 4530 WMITLV_TAG_STRUC_wmi_mgmt_tx_send_cmd_fixed_param, 4531 WMITLV_GET_STRUCT_TLVLEN 4532 (wmi_mgmt_tx_send_cmd_fixed_param)); 4533 4534 cmd->vdev_id = param->vdev_id; 4535 4536 cmd->desc_id = param->desc_id; 4537 cmd->chanfreq = param->chanfreq; 4538 cmd->peer_rssi = param->peer_rssi; 4539 bufp += sizeof(wmi_mgmt_tx_send_cmd_fixed_param); 4540 WMITLV_SET_HDR(bufp, WMITLV_TAG_ARRAY_BYTE, roundup(bufp_len, 4541 sizeof(uint32_t))); 4542 bufp += WMI_TLV_HDR_SIZE; 4543 4544 /* for big endian host, copy engine byte_swap is enabled 4545 * But the frame content is in network byte order 4546 * Need to byte swap the frame content - so when copy engine 4547 * does byte_swap - target gets frame content in the correct order 4548 */ 4549 WMI_HOST_IF_MSG_COPY_CHAR_ARRAY(bufp, param->pdata, bufp_len); 4550 4551 status = qdf_nbuf_map_single(qdf_ctx, param->tx_frame, 4552 QDF_DMA_TO_DEVICE); 4553 if (status != QDF_STATUS_SUCCESS) { 4554 wmi_err("wmi buf map failed"); 4555 goto free_buf; 4556 } 4557 4558 dma_addr = qdf_nbuf_get_frag_paddr(param->tx_frame, 0); 4559 cmd->paddr_lo = (uint32_t)(dma_addr & 0xffffffff); 4560 #if defined(HTT_PADDR64) 4561 cmd->paddr_hi = (uint32_t)((dma_addr >> 32) & 0x1F); 4562 #endif 4563 cmd->frame_len = param->frm_len; 4564 cmd->buf_len = bufp_len; 4565 cmd->tx_params_valid = param->tx_params_valid; 4566 cmd->tx_flags = param->tx_flags; 4567 4568 wmi_mgmt_cmd_record(wmi_handle, WMI_MGMT_TX_SEND_CMDID, 4569 bufp, cmd->vdev_id, cmd->chanfreq); 4570 4571 bufp += roundup(bufp_len, sizeof(uint32_t)); 4572 if (param->tx_params_valid) { 4573 status = populate_tx_send_params(bufp, param->tx_param); 4574 if (status != QDF_STATUS_SUCCESS) { 4575 wmi_err("Populate TX send params failed"); 4576 goto unmap_tx_frame; 4577 } 4578 } else { 4579 WMITLV_SET_HDR(&((wmi_tx_send_params *)bufp)->tlv_header, 4580 WMITLV_TAG_STRUC_wmi_tx_send_params, 4581 WMITLV_GET_STRUCT_TLVLEN(wmi_tx_send_params)); 4582 } 4583 4584 /* Even tx_params_valid is false, still need reserve space to pass wmi 4585 * tag check */ 4586 cmd_len += sizeof(wmi_tx_send_params); 4587 bufp += sizeof(wmi_tx_send_params); 4588 /* wmi_mlo_tx_send_params */ 4589 if (param->mlo_link_agnostic) { 4590 wmi_debug("Set mlo mgmt tid"); 4591 WMITLV_SET_HDR(bufp, WMITLV_TAG_ARRAY_STRUC, 4592 sizeof(wmi_mlo_tx_send_params)); 4593 bufp += WMI_TLV_HDR_SIZE; 4594 mlo_params = (wmi_mlo_tx_send_params *)bufp; 4595 WMITLV_SET_HDR(&mlo_params->tlv_header, 4596 WMITLV_TAG_STRUC_wmi_mlo_tx_send_params, 4597 WMITLV_GET_STRUCT_TLVLEN(wmi_mlo_tx_send_params)); 4598 mlo_params->hw_link_id = WMI_MLO_MGMT_TID; 4599 cmd_len += WMI_TLV_HDR_SIZE + sizeof(wmi_mlo_tx_send_params); 4600 } 4601 4602 wmi_mtrace(WMI_MGMT_TX_SEND_CMDID, cmd->vdev_id, 0); 4603 if (wmi_unified_cmd_send(wmi_handle, buf, cmd_len, 4604 WMI_MGMT_TX_SEND_CMDID)) { 4605 wmi_err("Failed to send mgmt Tx"); 4606 goto unmap_tx_frame; 4607 } 4608 return QDF_STATUS_SUCCESS; 4609 4610 unmap_tx_frame: 4611 qdf_nbuf_unmap_single(qdf_ctx, param->tx_frame, 4612 QDF_DMA_TO_DEVICE); 4613 free_buf: 4614 wmi_buf_free(buf); 4615 return QDF_STATUS_E_FAILURE; 4616 } 4617 #endif /* CONFIG_HL_SUPPORT */ 4618 4619 /** 4620 * send_offchan_data_tx_send_cmd_tlv() - Send off-chan tx data 4621 * @wmi_handle : handle to WMI. 4622 * @param : pointer to offchan data tx cmd parameter 4623 * 4624 * Return: QDF_STATUS_SUCCESS on success and error on failure. 4625 */ 4626 static QDF_STATUS send_offchan_data_tx_cmd_tlv(wmi_unified_t wmi_handle, 4627 struct wmi_offchan_data_tx_params *param) 4628 { 4629 wmi_buf_t buf; 4630 wmi_offchan_data_tx_send_cmd_fixed_param *cmd; 4631 int32_t cmd_len; 4632 uint64_t dma_addr; 4633 void *qdf_ctx = param->qdf_ctx; 4634 uint8_t *bufp; 4635 int32_t bufp_len = (param->frm_len < mgmt_tx_dl_frm_len) ? 4636 param->frm_len : mgmt_tx_dl_frm_len; 4637 QDF_STATUS status = QDF_STATUS_SUCCESS; 4638 4639 cmd_len = sizeof(wmi_offchan_data_tx_send_cmd_fixed_param) + 4640 WMI_TLV_HDR_SIZE + 4641 roundup(bufp_len, sizeof(uint32_t)); 4642 4643 buf = wmi_buf_alloc(wmi_handle, sizeof(wmi_tx_send_params) + cmd_len); 4644 if (!buf) 4645 return QDF_STATUS_E_NOMEM; 4646 4647 cmd = (wmi_offchan_data_tx_send_cmd_fixed_param *) wmi_buf_data(buf); 4648 bufp = (uint8_t *) cmd; 4649 WMITLV_SET_HDR(&cmd->tlv_header, 4650 WMITLV_TAG_STRUC_wmi_offchan_data_tx_send_cmd_fixed_param, 4651 WMITLV_GET_STRUCT_TLVLEN 4652 (wmi_offchan_data_tx_send_cmd_fixed_param)); 4653 4654 cmd->vdev_id = param->vdev_id; 4655 4656 cmd->desc_id = param->desc_id; 4657 cmd->chanfreq = param->chanfreq; 4658 bufp += sizeof(wmi_offchan_data_tx_send_cmd_fixed_param); 4659 WMITLV_SET_HDR(bufp, WMITLV_TAG_ARRAY_BYTE, roundup(bufp_len, 4660 sizeof(uint32_t))); 4661 bufp += WMI_TLV_HDR_SIZE; 4662 qdf_mem_copy(bufp, param->pdata, bufp_len); 4663 qdf_nbuf_map_single(qdf_ctx, param->tx_frame, QDF_DMA_TO_DEVICE); 4664 dma_addr = qdf_nbuf_get_frag_paddr(param->tx_frame, 0); 4665 cmd->paddr_lo = (uint32_t)(dma_addr & 0xffffffff); 4666 #if defined(HTT_PADDR64) 4667 cmd->paddr_hi = (uint32_t)((dma_addr >> 32) & 0x1F); 4668 #endif 4669 cmd->frame_len = param->frm_len; 4670 cmd->buf_len = bufp_len; 4671 cmd->tx_params_valid = param->tx_params_valid; 4672 4673 wmi_mgmt_cmd_record(wmi_handle, WMI_OFFCHAN_DATA_TX_SEND_CMDID, 4674 bufp, cmd->vdev_id, cmd->chanfreq); 4675 4676 bufp += roundup(bufp_len, sizeof(uint32_t)); 4677 if (param->tx_params_valid) { 4678 status = populate_tx_send_params(bufp, param->tx_param); 4679 if (status != QDF_STATUS_SUCCESS) { 4680 wmi_err("Populate TX send params failed"); 4681 goto err1; 4682 } 4683 cmd_len += sizeof(wmi_tx_send_params); 4684 } 4685 4686 wmi_mtrace(WMI_OFFCHAN_DATA_TX_SEND_CMDID, cmd->vdev_id, 0); 4687 if (wmi_unified_cmd_send(wmi_handle, buf, cmd_len, 4688 WMI_OFFCHAN_DATA_TX_SEND_CMDID)) { 4689 wmi_err("Failed to offchan data Tx"); 4690 goto err1; 4691 } 4692 4693 return QDF_STATUS_SUCCESS; 4694 4695 err1: 4696 wmi_buf_free(buf); 4697 return QDF_STATUS_E_FAILURE; 4698 } 4699 4700 /** 4701 * send_modem_power_state_cmd_tlv() - set modem power state to fw 4702 * @wmi_handle: wmi handle 4703 * @param_value: parameter value 4704 * 4705 * Return: QDF_STATUS_SUCCESS for success or error code 4706 */ 4707 static QDF_STATUS send_modem_power_state_cmd_tlv(wmi_unified_t wmi_handle, 4708 uint32_t param_value) 4709 { 4710 QDF_STATUS ret; 4711 wmi_modem_power_state_cmd_param *cmd; 4712 wmi_buf_t buf; 4713 uint16_t len = sizeof(*cmd); 4714 4715 buf = wmi_buf_alloc(wmi_handle, len); 4716 if (!buf) 4717 return QDF_STATUS_E_NOMEM; 4718 4719 cmd = (wmi_modem_power_state_cmd_param *) wmi_buf_data(buf); 4720 WMITLV_SET_HDR(&cmd->tlv_header, 4721 WMITLV_TAG_STRUC_wmi_modem_power_state_cmd_param, 4722 WMITLV_GET_STRUCT_TLVLEN 4723 (wmi_modem_power_state_cmd_param)); 4724 cmd->modem_power_state = param_value; 4725 wmi_debug("Setting cmd->modem_power_state = %u", param_value); 4726 wmi_mtrace(WMI_MODEM_POWER_STATE_CMDID, NO_SESSION, 0); 4727 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 4728 WMI_MODEM_POWER_STATE_CMDID); 4729 if (QDF_IS_STATUS_ERROR(ret)) { 4730 wmi_err("Failed to send notify cmd ret = %d", ret); 4731 wmi_buf_free(buf); 4732 } 4733 4734 return ret; 4735 } 4736 4737 /** 4738 * send_set_sta_ps_mode_cmd_tlv() - set sta powersave mode in fw 4739 * @wmi_handle: wmi handle 4740 * @vdev_id: vdev id 4741 * @val: value 4742 * 4743 * Return: QDF_STATUS_SUCCESS for success or error code. 4744 */ 4745 static QDF_STATUS send_set_sta_ps_mode_cmd_tlv(wmi_unified_t wmi_handle, 4746 uint32_t vdev_id, uint8_t val) 4747 { 4748 wmi_sta_powersave_mode_cmd_fixed_param *cmd; 4749 wmi_buf_t buf; 4750 int32_t len = sizeof(*cmd); 4751 4752 wmi_debug("Set Sta Mode Ps vdevId %d val %d", vdev_id, val); 4753 4754 buf = wmi_buf_alloc(wmi_handle, len); 4755 if (!buf) 4756 return QDF_STATUS_E_NOMEM; 4757 4758 cmd = (wmi_sta_powersave_mode_cmd_fixed_param *) wmi_buf_data(buf); 4759 WMITLV_SET_HDR(&cmd->tlv_header, 4760 WMITLV_TAG_STRUC_wmi_sta_powersave_mode_cmd_fixed_param, 4761 WMITLV_GET_STRUCT_TLVLEN 4762 (wmi_sta_powersave_mode_cmd_fixed_param)); 4763 cmd->vdev_id = vdev_id; 4764 if (val) 4765 cmd->sta_ps_mode = WMI_STA_PS_MODE_ENABLED; 4766 else 4767 cmd->sta_ps_mode = WMI_STA_PS_MODE_DISABLED; 4768 4769 wmi_mtrace(WMI_STA_POWERSAVE_MODE_CMDID, cmd->vdev_id, 0); 4770 if (wmi_unified_cmd_send(wmi_handle, buf, len, 4771 WMI_STA_POWERSAVE_MODE_CMDID)) { 4772 wmi_err("Set Sta Mode Ps Failed vdevId %d val %d", 4773 vdev_id, val); 4774 wmi_buf_free(buf); 4775 return QDF_STATUS_E_FAILURE; 4776 } 4777 return QDF_STATUS_SUCCESS; 4778 } 4779 4780 /** 4781 * send_idle_roam_monitor_cmd_tlv() - send idle monitor command to fw 4782 * @wmi_handle: wmi handle 4783 * @vdev_id: vdev id 4784 * 4785 * Return: QDF_STATUS_SUCCESS for success or error code. 4786 */ 4787 static QDF_STATUS send_idle_roam_monitor_cmd_tlv(wmi_unified_t wmi_handle, 4788 uint8_t val) 4789 { 4790 wmi_idle_trigger_monitor_cmd_fixed_param *cmd; 4791 wmi_buf_t buf; 4792 size_t len = sizeof(*cmd); 4793 4794 buf = wmi_buf_alloc(wmi_handle, len); 4795 if (!buf) 4796 return QDF_STATUS_E_NOMEM; 4797 4798 cmd = (wmi_idle_trigger_monitor_cmd_fixed_param *)wmi_buf_data(buf); 4799 WMITLV_SET_HDR(&cmd->tlv_header, 4800 WMITLV_TAG_STRUC_wmi_idle_trigger_monitor_cmd_fixed_param, 4801 WMITLV_GET_STRUCT_TLVLEN(wmi_idle_trigger_monitor_cmd_fixed_param)); 4802 4803 cmd->idle_trigger_monitor = (val ? WMI_IDLE_TRIGGER_MONITOR_ON : 4804 WMI_IDLE_TRIGGER_MONITOR_OFF); 4805 4806 wmi_debug("val: %d", cmd->idle_trigger_monitor); 4807 4808 if (wmi_unified_cmd_send(wmi_handle, buf, len, 4809 WMI_IDLE_TRIGGER_MONITOR_CMDID)) { 4810 wmi_buf_free(buf); 4811 return QDF_STATUS_E_FAILURE; 4812 } 4813 return QDF_STATUS_SUCCESS; 4814 } 4815 4816 /** 4817 * send_set_mimops_cmd_tlv() - set MIMO powersave 4818 * @wmi_handle: wmi handle 4819 * @vdev_id: vdev id 4820 * @value: value 4821 * 4822 * Return: QDF_STATUS_SUCCESS for success or error code. 4823 */ 4824 static QDF_STATUS send_set_mimops_cmd_tlv(wmi_unified_t wmi_handle, 4825 uint8_t vdev_id, int value) 4826 { 4827 QDF_STATUS ret; 4828 wmi_sta_smps_force_mode_cmd_fixed_param *cmd; 4829 wmi_buf_t buf; 4830 uint16_t len = sizeof(*cmd); 4831 4832 buf = wmi_buf_alloc(wmi_handle, len); 4833 if (!buf) 4834 return QDF_STATUS_E_NOMEM; 4835 4836 cmd = (wmi_sta_smps_force_mode_cmd_fixed_param *) wmi_buf_data(buf); 4837 WMITLV_SET_HDR(&cmd->tlv_header, 4838 WMITLV_TAG_STRUC_wmi_sta_smps_force_mode_cmd_fixed_param, 4839 WMITLV_GET_STRUCT_TLVLEN 4840 (wmi_sta_smps_force_mode_cmd_fixed_param)); 4841 4842 cmd->vdev_id = vdev_id; 4843 4844 /* WMI_SMPS_FORCED_MODE values do not directly map 4845 * to SM power save values defined in the specification. 4846 * Make sure to send the right mapping. 4847 */ 4848 switch (value) { 4849 case 0: 4850 cmd->forced_mode = WMI_SMPS_FORCED_MODE_NONE; 4851 break; 4852 case 1: 4853 cmd->forced_mode = WMI_SMPS_FORCED_MODE_DISABLED; 4854 break; 4855 case 2: 4856 cmd->forced_mode = WMI_SMPS_FORCED_MODE_STATIC; 4857 break; 4858 case 3: 4859 cmd->forced_mode = WMI_SMPS_FORCED_MODE_DYNAMIC; 4860 break; 4861 default: 4862 wmi_err("INVALID MIMO PS CONFIG: %d", value); 4863 wmi_buf_free(buf); 4864 return QDF_STATUS_E_FAILURE; 4865 } 4866 4867 wmi_debug("Setting vdev %d value = %u", vdev_id, value); 4868 4869 wmi_mtrace(WMI_STA_SMPS_FORCE_MODE_CMDID, cmd->vdev_id, 0); 4870 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 4871 WMI_STA_SMPS_FORCE_MODE_CMDID); 4872 if (QDF_IS_STATUS_ERROR(ret)) { 4873 wmi_err("Failed to send set Mimo PS ret = %d", ret); 4874 wmi_buf_free(buf); 4875 } 4876 4877 return ret; 4878 } 4879 4880 /** 4881 * send_set_smps_params_cmd_tlv() - set smps params 4882 * @wmi_handle: wmi handle 4883 * @vdev_id: vdev id 4884 * @value: value 4885 * 4886 * Return: QDF_STATUS_SUCCESS for success or error code. 4887 */ 4888 static QDF_STATUS send_set_smps_params_cmd_tlv(wmi_unified_t wmi_handle, uint8_t vdev_id, 4889 int value) 4890 { 4891 QDF_STATUS ret; 4892 wmi_sta_smps_param_cmd_fixed_param *cmd; 4893 wmi_buf_t buf; 4894 uint16_t len = sizeof(*cmd); 4895 4896 buf = wmi_buf_alloc(wmi_handle, len); 4897 if (!buf) 4898 return QDF_STATUS_E_NOMEM; 4899 4900 cmd = (wmi_sta_smps_param_cmd_fixed_param *) wmi_buf_data(buf); 4901 WMITLV_SET_HDR(&cmd->tlv_header, 4902 WMITLV_TAG_STRUC_wmi_sta_smps_param_cmd_fixed_param, 4903 WMITLV_GET_STRUCT_TLVLEN 4904 (wmi_sta_smps_param_cmd_fixed_param)); 4905 4906 cmd->vdev_id = vdev_id; 4907 cmd->value = value & WMI_SMPS_MASK_LOWER_16BITS; 4908 cmd->param = 4909 (value >> WMI_SMPS_PARAM_VALUE_S) & WMI_SMPS_MASK_UPPER_3BITS; 4910 4911 wmi_debug("Setting vdev %d value = %x param %x", vdev_id, cmd->value, 4912 cmd->param); 4913 4914 wmi_mtrace(WMI_STA_SMPS_PARAM_CMDID, cmd->vdev_id, 0); 4915 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 4916 WMI_STA_SMPS_PARAM_CMDID); 4917 if (QDF_IS_STATUS_ERROR(ret)) { 4918 wmi_err("Failed to send set Mimo PS ret = %d", ret); 4919 wmi_buf_free(buf); 4920 } 4921 4922 return ret; 4923 } 4924 4925 /** 4926 * send_get_temperature_cmd_tlv() - get pdev temperature req 4927 * @wmi_handle: wmi handle 4928 * 4929 * Return: QDF_STATUS_SUCCESS for success or error code. 4930 */ 4931 static QDF_STATUS send_get_temperature_cmd_tlv(wmi_unified_t wmi_handle) 4932 { 4933 wmi_pdev_get_temperature_cmd_fixed_param *cmd; 4934 wmi_buf_t wmi_buf; 4935 uint32_t len = sizeof(wmi_pdev_get_temperature_cmd_fixed_param); 4936 uint8_t *buf_ptr; 4937 4938 if (!wmi_handle) { 4939 wmi_err("WMI is closed, can not issue cmd"); 4940 return QDF_STATUS_E_INVAL; 4941 } 4942 4943 wmi_buf = wmi_buf_alloc(wmi_handle, len); 4944 if (!wmi_buf) 4945 return QDF_STATUS_E_NOMEM; 4946 4947 buf_ptr = (uint8_t *) wmi_buf_data(wmi_buf); 4948 4949 cmd = (wmi_pdev_get_temperature_cmd_fixed_param *) buf_ptr; 4950 WMITLV_SET_HDR(&cmd->tlv_header, 4951 WMITLV_TAG_STRUC_wmi_pdev_get_temperature_cmd_fixed_param, 4952 WMITLV_GET_STRUCT_TLVLEN 4953 (wmi_pdev_get_temperature_cmd_fixed_param)); 4954 4955 wmi_mtrace(WMI_PDEV_GET_TEMPERATURE_CMDID, NO_SESSION, 0); 4956 if (wmi_unified_cmd_send(wmi_handle, wmi_buf, len, 4957 WMI_PDEV_GET_TEMPERATURE_CMDID)) { 4958 wmi_err("Failed to send get temperature command"); 4959 wmi_buf_free(wmi_buf); 4960 return QDF_STATUS_E_FAILURE; 4961 } 4962 4963 return QDF_STATUS_SUCCESS; 4964 } 4965 4966 /** 4967 * send_set_sta_uapsd_auto_trig_cmd_tlv() - set uapsd auto trigger command 4968 * @wmi_handle: wmi handle 4969 * @vdevid: vdev id 4970 * @peer_addr: peer mac address 4971 * @auto_triggerparam: auto trigger parameters 4972 * @num_ac: number of access category 4973 * 4974 * This function sets the trigger 4975 * uapsd params such as service interval, delay interval 4976 * and suspend interval which will be used by the firmware 4977 * to send trigger frames periodically when there is no 4978 * traffic on the transmit side. 4979 * 4980 * Return: QDF_STATUS_SUCCESS for success or error code. 4981 */ 4982 static QDF_STATUS send_set_sta_uapsd_auto_trig_cmd_tlv(wmi_unified_t wmi_handle, 4983 struct sta_uapsd_trig_params *param) 4984 { 4985 wmi_sta_uapsd_auto_trig_cmd_fixed_param *cmd; 4986 QDF_STATUS ret; 4987 uint32_t param_len = param->num_ac * sizeof(wmi_sta_uapsd_auto_trig_param); 4988 uint32_t cmd_len = sizeof(*cmd) + param_len + WMI_TLV_HDR_SIZE; 4989 uint32_t i; 4990 wmi_buf_t buf; 4991 uint8_t *buf_ptr; 4992 struct sta_uapsd_params *uapsd_param; 4993 wmi_sta_uapsd_auto_trig_param *trig_param; 4994 4995 buf = wmi_buf_alloc(wmi_handle, cmd_len); 4996 if (!buf) 4997 return QDF_STATUS_E_NOMEM; 4998 4999 buf_ptr = (uint8_t *) wmi_buf_data(buf); 5000 cmd = (wmi_sta_uapsd_auto_trig_cmd_fixed_param *) buf_ptr; 5001 WMITLV_SET_HDR(&cmd->tlv_header, 5002 WMITLV_TAG_STRUC_wmi_sta_uapsd_auto_trig_cmd_fixed_param, 5003 WMITLV_GET_STRUCT_TLVLEN 5004 (wmi_sta_uapsd_auto_trig_cmd_fixed_param)); 5005 cmd->vdev_id = param->vdevid; 5006 cmd->num_ac = param->num_ac; 5007 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->peer_addr, &cmd->peer_macaddr); 5008 5009 /* TLV indicating array of structures to follow */ 5010 buf_ptr += sizeof(*cmd); 5011 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, param_len); 5012 5013 buf_ptr += WMI_TLV_HDR_SIZE; 5014 5015 /* 5016 * Update tag and length for uapsd auto trigger params (this will take 5017 * care of updating tag and length if it is not pre-filled by caller). 5018 */ 5019 uapsd_param = (struct sta_uapsd_params *)param->auto_triggerparam; 5020 trig_param = (wmi_sta_uapsd_auto_trig_param *)buf_ptr; 5021 for (i = 0; i < param->num_ac; i++) { 5022 WMITLV_SET_HDR((buf_ptr + 5023 (i * sizeof(wmi_sta_uapsd_auto_trig_param))), 5024 WMITLV_TAG_STRUC_wmi_sta_uapsd_auto_trig_param, 5025 WMITLV_GET_STRUCT_TLVLEN 5026 (wmi_sta_uapsd_auto_trig_param)); 5027 trig_param->wmm_ac = uapsd_param->wmm_ac; 5028 trig_param->user_priority = uapsd_param->user_priority; 5029 trig_param->service_interval = uapsd_param->service_interval; 5030 trig_param->suspend_interval = uapsd_param->suspend_interval; 5031 trig_param->delay_interval = uapsd_param->delay_interval; 5032 trig_param++; 5033 uapsd_param++; 5034 } 5035 5036 wmi_mtrace(WMI_STA_UAPSD_AUTO_TRIG_CMDID, cmd->vdev_id, 0); 5037 ret = wmi_unified_cmd_send(wmi_handle, buf, cmd_len, 5038 WMI_STA_UAPSD_AUTO_TRIG_CMDID); 5039 if (QDF_IS_STATUS_ERROR(ret)) { 5040 wmi_err("Failed to send set uapsd param ret = %d", ret); 5041 wmi_buf_free(buf); 5042 } 5043 5044 return ret; 5045 } 5046 5047 /** 5048 * send_set_thermal_mgmt_cmd_tlv() - set thermal mgmt command to fw 5049 * @wmi_handle: Pointer to wmi handle 5050 * @thermal_info: Thermal command information 5051 * 5052 * This function sends the thermal management command 5053 * to the firmware 5054 * 5055 * Return: QDF_STATUS_SUCCESS for success otherwise failure 5056 */ 5057 static QDF_STATUS send_set_thermal_mgmt_cmd_tlv(wmi_unified_t wmi_handle, 5058 struct thermal_cmd_params *thermal_info) 5059 { 5060 wmi_thermal_mgmt_cmd_fixed_param *cmd = NULL; 5061 wmi_buf_t buf = NULL; 5062 QDF_STATUS status; 5063 uint32_t len = 0; 5064 uint8_t action; 5065 5066 switch (thermal_info->thermal_action) { 5067 case THERMAL_MGMT_ACTION_DEFAULT: 5068 action = WMI_THERMAL_MGMT_ACTION_DEFAULT; 5069 break; 5070 5071 case THERMAL_MGMT_ACTION_HALT_TRAFFIC: 5072 action = WMI_THERMAL_MGMT_ACTION_HALT_TRAFFIC; 5073 break; 5074 5075 case THERMAL_MGMT_ACTION_NOTIFY_HOST: 5076 action = WMI_THERMAL_MGMT_ACTION_NOTIFY_HOST; 5077 break; 5078 5079 case THERMAL_MGMT_ACTION_CHAINSCALING: 5080 action = WMI_THERMAL_MGMT_ACTION_CHAINSCALING; 5081 break; 5082 5083 default: 5084 wmi_err("Invalid thermal_action code %d", 5085 thermal_info->thermal_action); 5086 return QDF_STATUS_E_FAILURE; 5087 } 5088 5089 len = sizeof(*cmd); 5090 5091 buf = wmi_buf_alloc(wmi_handle, len); 5092 if (!buf) 5093 return QDF_STATUS_E_FAILURE; 5094 5095 cmd = (wmi_thermal_mgmt_cmd_fixed_param *) wmi_buf_data(buf); 5096 5097 WMITLV_SET_HDR(&cmd->tlv_header, 5098 WMITLV_TAG_STRUC_wmi_thermal_mgmt_cmd_fixed_param, 5099 WMITLV_GET_STRUCT_TLVLEN 5100 (wmi_thermal_mgmt_cmd_fixed_param)); 5101 5102 cmd->lower_thresh_degreeC = thermal_info->min_temp; 5103 cmd->upper_thresh_degreeC = thermal_info->max_temp; 5104 cmd->enable = thermal_info->thermal_enable; 5105 cmd->action = action; 5106 5107 wmi_debug("TM Sending thermal mgmt cmd: low temp %d, upper temp %d, enabled %d action %d", 5108 cmd->lower_thresh_degreeC, cmd->upper_thresh_degreeC, 5109 cmd->enable, cmd->action); 5110 5111 wmi_mtrace(WMI_THERMAL_MGMT_CMDID, NO_SESSION, 0); 5112 status = wmi_unified_cmd_send(wmi_handle, buf, len, 5113 WMI_THERMAL_MGMT_CMDID); 5114 if (QDF_IS_STATUS_ERROR(status)) { 5115 wmi_buf_free(buf); 5116 wmi_err("Failed to send thermal mgmt command"); 5117 } 5118 5119 return status; 5120 } 5121 5122 /** 5123 * send_lro_config_cmd_tlv() - process the LRO config command 5124 * @wmi_handle: Pointer to WMI handle 5125 * @wmi_lro_cmd: Pointer to LRO configuration parameters 5126 * 5127 * This function sends down the LRO configuration parameters to 5128 * the firmware to enable LRO, sets the TCP flags and sets the 5129 * seed values for the toeplitz hash generation 5130 * 5131 * Return: QDF_STATUS_SUCCESS for success otherwise failure 5132 */ 5133 static QDF_STATUS send_lro_config_cmd_tlv(wmi_unified_t wmi_handle, 5134 struct wmi_lro_config_cmd_t *wmi_lro_cmd) 5135 { 5136 wmi_lro_info_cmd_fixed_param *cmd; 5137 wmi_buf_t buf; 5138 QDF_STATUS status; 5139 uint8_t pdev_id = wmi_lro_cmd->pdev_id; 5140 5141 buf = wmi_buf_alloc(wmi_handle, sizeof(*cmd)); 5142 if (!buf) 5143 return QDF_STATUS_E_FAILURE; 5144 5145 cmd = (wmi_lro_info_cmd_fixed_param *) wmi_buf_data(buf); 5146 5147 WMITLV_SET_HDR(&cmd->tlv_header, 5148 WMITLV_TAG_STRUC_wmi_lro_info_cmd_fixed_param, 5149 WMITLV_GET_STRUCT_TLVLEN(wmi_lro_info_cmd_fixed_param)); 5150 5151 cmd->lro_enable = wmi_lro_cmd->lro_enable; 5152 WMI_LRO_INFO_TCP_FLAG_VALS_SET(cmd->tcp_flag_u32, 5153 wmi_lro_cmd->tcp_flag); 5154 WMI_LRO_INFO_TCP_FLAGS_MASK_SET(cmd->tcp_flag_u32, 5155 wmi_lro_cmd->tcp_flag_mask); 5156 cmd->toeplitz_hash_ipv4_0_3 = 5157 wmi_lro_cmd->toeplitz_hash_ipv4[0]; 5158 cmd->toeplitz_hash_ipv4_4_7 = 5159 wmi_lro_cmd->toeplitz_hash_ipv4[1]; 5160 cmd->toeplitz_hash_ipv4_8_11 = 5161 wmi_lro_cmd->toeplitz_hash_ipv4[2]; 5162 cmd->toeplitz_hash_ipv4_12_15 = 5163 wmi_lro_cmd->toeplitz_hash_ipv4[3]; 5164 cmd->toeplitz_hash_ipv4_16 = 5165 wmi_lro_cmd->toeplitz_hash_ipv4[4]; 5166 5167 cmd->toeplitz_hash_ipv6_0_3 = 5168 wmi_lro_cmd->toeplitz_hash_ipv6[0]; 5169 cmd->toeplitz_hash_ipv6_4_7 = 5170 wmi_lro_cmd->toeplitz_hash_ipv6[1]; 5171 cmd->toeplitz_hash_ipv6_8_11 = 5172 wmi_lro_cmd->toeplitz_hash_ipv6[2]; 5173 cmd->toeplitz_hash_ipv6_12_15 = 5174 wmi_lro_cmd->toeplitz_hash_ipv6[3]; 5175 cmd->toeplitz_hash_ipv6_16_19 = 5176 wmi_lro_cmd->toeplitz_hash_ipv6[4]; 5177 cmd->toeplitz_hash_ipv6_20_23 = 5178 wmi_lro_cmd->toeplitz_hash_ipv6[5]; 5179 cmd->toeplitz_hash_ipv6_24_27 = 5180 wmi_lro_cmd->toeplitz_hash_ipv6[6]; 5181 cmd->toeplitz_hash_ipv6_28_31 = 5182 wmi_lro_cmd->toeplitz_hash_ipv6[7]; 5183 cmd->toeplitz_hash_ipv6_32_35 = 5184 wmi_lro_cmd->toeplitz_hash_ipv6[8]; 5185 cmd->toeplitz_hash_ipv6_36_39 = 5186 wmi_lro_cmd->toeplitz_hash_ipv6[9]; 5187 cmd->toeplitz_hash_ipv6_40 = 5188 wmi_lro_cmd->toeplitz_hash_ipv6[10]; 5189 5190 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 5191 wmi_handle, 5192 pdev_id); 5193 wmi_debug("WMI_LRO_CONFIG: lro_enable %d, tcp_flag 0x%x, pdev_id: %d", 5194 cmd->lro_enable, cmd->tcp_flag_u32, cmd->pdev_id); 5195 5196 wmi_mtrace(WMI_LRO_CONFIG_CMDID, NO_SESSION, 0); 5197 status = wmi_unified_cmd_send(wmi_handle, buf, 5198 sizeof(*cmd), WMI_LRO_CONFIG_CMDID); 5199 if (QDF_IS_STATUS_ERROR(status)) { 5200 wmi_buf_free(buf); 5201 wmi_err("Failed to send WMI_LRO_CONFIG_CMDID"); 5202 } 5203 5204 return status; 5205 } 5206 5207 /** 5208 * send_peer_rate_report_cmd_tlv() - process the peer rate report command 5209 * @wmi_handle: Pointer to wmi handle 5210 * @rate_report_params: Pointer to peer rate report parameters 5211 * 5212 * 5213 * Return: QDF_STATUS_SUCCESS for success otherwise failure 5214 */ 5215 static QDF_STATUS send_peer_rate_report_cmd_tlv(wmi_unified_t wmi_handle, 5216 struct wmi_peer_rate_report_params *rate_report_params) 5217 { 5218 wmi_peer_set_rate_report_condition_fixed_param *cmd = NULL; 5219 wmi_buf_t buf = NULL; 5220 QDF_STATUS status = 0; 5221 uint32_t len = 0; 5222 uint32_t i, j; 5223 5224 len = sizeof(*cmd); 5225 5226 buf = wmi_buf_alloc(wmi_handle, len); 5227 if (!buf) 5228 return QDF_STATUS_E_FAILURE; 5229 5230 cmd = (wmi_peer_set_rate_report_condition_fixed_param *) 5231 wmi_buf_data(buf); 5232 5233 WMITLV_SET_HDR( 5234 &cmd->tlv_header, 5235 WMITLV_TAG_STRUC_wmi_peer_set_rate_report_condition_fixed_param, 5236 WMITLV_GET_STRUCT_TLVLEN( 5237 wmi_peer_set_rate_report_condition_fixed_param)); 5238 5239 cmd->enable_rate_report = rate_report_params->rate_report_enable; 5240 cmd->report_backoff_time = rate_report_params->backoff_time; 5241 cmd->report_timer_period = rate_report_params->timer_period; 5242 for (i = 0; i < PEER_RATE_REPORT_COND_MAX_NUM; i++) { 5243 cmd->cond_per_phy[i].val_cond_flags = 5244 rate_report_params->report_per_phy[i].cond_flags; 5245 cmd->cond_per_phy[i].rate_delta.min_delta = 5246 rate_report_params->report_per_phy[i].delta.delta_min; 5247 cmd->cond_per_phy[i].rate_delta.percentage = 5248 rate_report_params->report_per_phy[i].delta.percent; 5249 for (j = 0; j < MAX_NUM_OF_RATE_THRESH; j++) { 5250 cmd->cond_per_phy[i].rate_threshold[j] = 5251 rate_report_params->report_per_phy[i]. 5252 report_rate_threshold[j]; 5253 } 5254 } 5255 5256 wmi_debug("enable %d backoff_time %d period %d", 5257 cmd->enable_rate_report, 5258 cmd->report_backoff_time, cmd->report_timer_period); 5259 5260 wmi_mtrace(WMI_PEER_SET_RATE_REPORT_CONDITION_CMDID, NO_SESSION, 0); 5261 status = wmi_unified_cmd_send(wmi_handle, buf, len, 5262 WMI_PEER_SET_RATE_REPORT_CONDITION_CMDID); 5263 if (QDF_IS_STATUS_ERROR(status)) { 5264 wmi_buf_free(buf); 5265 wmi_err("Failed to send peer_set_report_cond command"); 5266 } 5267 return status; 5268 } 5269 5270 /** 5271 * send_process_update_edca_param_cmd_tlv() - update EDCA params 5272 * @wmi_handle: wmi handle 5273 * @vdev_id: vdev id. 5274 * @wmm_vparams: edca parameters 5275 * 5276 * This function updates EDCA parameters to the target 5277 * 5278 * Return: CDF Status 5279 */ 5280 static QDF_STATUS send_process_update_edca_param_cmd_tlv(wmi_unified_t wmi_handle, 5281 uint8_t vdev_id, bool mu_edca_param, 5282 struct wmi_host_wme_vparams wmm_vparams[WMI_MAX_NUM_AC]) 5283 { 5284 uint8_t *buf_ptr; 5285 wmi_buf_t buf; 5286 wmi_vdev_set_wmm_params_cmd_fixed_param *cmd; 5287 wmi_wmm_vparams *wmm_param; 5288 struct wmi_host_wme_vparams *twmm_param; 5289 int len = sizeof(*cmd); 5290 int ac; 5291 5292 buf = wmi_buf_alloc(wmi_handle, len); 5293 5294 if (!buf) 5295 return QDF_STATUS_E_NOMEM; 5296 5297 buf_ptr = (uint8_t *) wmi_buf_data(buf); 5298 cmd = (wmi_vdev_set_wmm_params_cmd_fixed_param *) buf_ptr; 5299 WMITLV_SET_HDR(&cmd->tlv_header, 5300 WMITLV_TAG_STRUC_wmi_vdev_set_wmm_params_cmd_fixed_param, 5301 WMITLV_GET_STRUCT_TLVLEN 5302 (wmi_vdev_set_wmm_params_cmd_fixed_param)); 5303 cmd->vdev_id = vdev_id; 5304 cmd->wmm_param_type = mu_edca_param; 5305 5306 for (ac = 0; ac < WMI_MAX_NUM_AC; ac++) { 5307 wmm_param = (wmi_wmm_vparams *) (&cmd->wmm_params[ac]); 5308 twmm_param = (struct wmi_host_wme_vparams *) (&wmm_vparams[ac]); 5309 WMITLV_SET_HDR(&wmm_param->tlv_header, 5310 WMITLV_TAG_STRUC_wmi_vdev_set_wmm_params_cmd_fixed_param, 5311 WMITLV_GET_STRUCT_TLVLEN(wmi_wmm_vparams)); 5312 wmm_param->cwmin = twmm_param->cwmin; 5313 wmm_param->cwmax = twmm_param->cwmax; 5314 wmm_param->aifs = twmm_param->aifs; 5315 if (mu_edca_param) 5316 wmm_param->mu_edca_timer = twmm_param->mu_edca_timer; 5317 else 5318 wmm_param->txoplimit = twmm_param->txoplimit; 5319 wmm_param->acm = twmm_param->acm; 5320 wmm_param->no_ack = twmm_param->noackpolicy; 5321 } 5322 5323 wmi_mtrace(WMI_VDEV_SET_WMM_PARAMS_CMDID, cmd->vdev_id, 0); 5324 if (wmi_unified_cmd_send(wmi_handle, buf, len, 5325 WMI_VDEV_SET_WMM_PARAMS_CMDID)) 5326 goto fail; 5327 5328 return QDF_STATUS_SUCCESS; 5329 5330 fail: 5331 wmi_buf_free(buf); 5332 wmi_err("Failed to set WMM Parameters"); 5333 return QDF_STATUS_E_FAILURE; 5334 } 5335 5336 /** 5337 * send_probe_rsp_tmpl_send_cmd_tlv() - send probe response template to fw 5338 * @wmi_handle: wmi handle 5339 * @vdev_id: vdev id 5340 * @probe_rsp_info: probe response info 5341 * 5342 * Return: QDF_STATUS_SUCCESS for success or error code 5343 */ 5344 static QDF_STATUS send_probe_rsp_tmpl_send_cmd_tlv(wmi_unified_t wmi_handle, 5345 uint8_t vdev_id, 5346 struct wmi_probe_resp_params *probe_rsp_info) 5347 { 5348 wmi_prb_tmpl_cmd_fixed_param *cmd; 5349 wmi_bcn_prb_info *bcn_prb_info; 5350 wmi_buf_t wmi_buf; 5351 uint32_t tmpl_len, tmpl_len_aligned, wmi_buf_len; 5352 uint8_t *buf_ptr; 5353 QDF_STATUS ret; 5354 5355 wmi_debug("Send probe response template for vdev %d", vdev_id); 5356 5357 tmpl_len = probe_rsp_info->prb_rsp_template_len; 5358 tmpl_len_aligned = roundup(tmpl_len, sizeof(uint32_t)); 5359 5360 wmi_buf_len = sizeof(wmi_prb_tmpl_cmd_fixed_param) + 5361 sizeof(wmi_bcn_prb_info) + WMI_TLV_HDR_SIZE + 5362 tmpl_len_aligned; 5363 5364 if (wmi_buf_len > WMI_BEACON_TX_BUFFER_SIZE) { 5365 wmi_err("wmi_buf_len: %d > %d. Can't send wmi cmd", 5366 wmi_buf_len, WMI_BEACON_TX_BUFFER_SIZE); 5367 return QDF_STATUS_E_INVAL; 5368 } 5369 5370 wmi_buf = wmi_buf_alloc(wmi_handle, wmi_buf_len); 5371 if (!wmi_buf) 5372 return QDF_STATUS_E_NOMEM; 5373 5374 buf_ptr = (uint8_t *) wmi_buf_data(wmi_buf); 5375 5376 cmd = (wmi_prb_tmpl_cmd_fixed_param *) buf_ptr; 5377 WMITLV_SET_HDR(&cmd->tlv_header, 5378 WMITLV_TAG_STRUC_wmi_prb_tmpl_cmd_fixed_param, 5379 WMITLV_GET_STRUCT_TLVLEN(wmi_prb_tmpl_cmd_fixed_param)); 5380 cmd->vdev_id = vdev_id; 5381 cmd->buf_len = tmpl_len; 5382 buf_ptr += sizeof(wmi_prb_tmpl_cmd_fixed_param); 5383 5384 bcn_prb_info = (wmi_bcn_prb_info *) buf_ptr; 5385 WMITLV_SET_HDR(&bcn_prb_info->tlv_header, 5386 WMITLV_TAG_STRUC_wmi_bcn_prb_info, 5387 WMITLV_GET_STRUCT_TLVLEN(wmi_bcn_prb_info)); 5388 bcn_prb_info->caps = 0; 5389 bcn_prb_info->erp = 0; 5390 buf_ptr += sizeof(wmi_bcn_prb_info); 5391 5392 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, tmpl_len_aligned); 5393 buf_ptr += WMI_TLV_HDR_SIZE; 5394 qdf_mem_copy(buf_ptr, probe_rsp_info->prb_rsp_template_frm, tmpl_len); 5395 5396 wmi_mtrace(WMI_PRB_TMPL_CMDID, cmd->vdev_id, 0); 5397 ret = wmi_unified_cmd_send(wmi_handle, 5398 wmi_buf, wmi_buf_len, WMI_PRB_TMPL_CMDID); 5399 if (QDF_IS_STATUS_ERROR(ret)) { 5400 wmi_err("Failed to send PRB RSP tmpl: %d", ret); 5401 wmi_buf_free(wmi_buf); 5402 } 5403 5404 return ret; 5405 } 5406 5407 #if defined(ATH_SUPPORT_WAPI) || defined(FEATURE_WLAN_WAPI) 5408 #define WPI_IV_LEN 16 5409 5410 /** 5411 * wmi_update_wpi_key_counter() - update WAPI tsc and rsc key counters 5412 * 5413 * @dest_tx: destination address of tsc key counter 5414 * @src_tx: source address of tsc key counter 5415 * @dest_rx: destination address of rsc key counter 5416 * @src_rx: source address of rsc key counter 5417 * 5418 * This function copies WAPI tsc and rsc key counters in the wmi buffer. 5419 * 5420 * Return: None 5421 * 5422 */ 5423 static void wmi_update_wpi_key_counter(uint8_t *dest_tx, uint8_t *src_tx, 5424 uint8_t *dest_rx, uint8_t *src_rx) 5425 { 5426 qdf_mem_copy(dest_tx, src_tx, WPI_IV_LEN); 5427 qdf_mem_copy(dest_rx, src_rx, WPI_IV_LEN); 5428 } 5429 #else 5430 static void wmi_update_wpi_key_counter(uint8_t *dest_tx, uint8_t *src_tx, 5431 uint8_t *dest_rx, uint8_t *src_rx) 5432 { 5433 return; 5434 } 5435 #endif 5436 5437 /** 5438 * send_setup_install_key_cmd_tlv() - set key parameters 5439 * @wmi_handle: wmi handle 5440 * @key_params: key parameters 5441 * 5442 * This function fills structure from information 5443 * passed in key_params. 5444 * 5445 * Return: QDF_STATUS_SUCCESS - success 5446 * QDF_STATUS_E_FAILURE - failure 5447 * QDF_STATUS_E_NOMEM - not able to allocate buffer 5448 */ 5449 static QDF_STATUS send_setup_install_key_cmd_tlv(wmi_unified_t wmi_handle, 5450 struct set_key_params *key_params) 5451 { 5452 wmi_vdev_install_key_cmd_fixed_param *cmd; 5453 wmi_buf_t buf; 5454 uint8_t *buf_ptr; 5455 uint32_t len; 5456 uint8_t *key_data; 5457 QDF_STATUS status; 5458 5459 len = sizeof(*cmd) + roundup(key_params->key_len, sizeof(uint32_t)) + 5460 WMI_TLV_HDR_SIZE; 5461 5462 buf = wmi_buf_alloc(wmi_handle, len); 5463 if (!buf) 5464 return QDF_STATUS_E_NOMEM; 5465 5466 buf_ptr = (uint8_t *) wmi_buf_data(buf); 5467 cmd = (wmi_vdev_install_key_cmd_fixed_param *) buf_ptr; 5468 WMITLV_SET_HDR(&cmd->tlv_header, 5469 WMITLV_TAG_STRUC_wmi_vdev_install_key_cmd_fixed_param, 5470 WMITLV_GET_STRUCT_TLVLEN 5471 (wmi_vdev_install_key_cmd_fixed_param)); 5472 cmd->vdev_id = key_params->vdev_id; 5473 cmd->key_ix = key_params->key_idx; 5474 if (key_params->group_key_idx) { 5475 cmd->is_group_key_ix_valid = 1; 5476 cmd->group_key_ix = key_params->group_key_idx; 5477 } 5478 5479 WMI_CHAR_ARRAY_TO_MAC_ADDR(key_params->peer_mac, &cmd->peer_macaddr); 5480 cmd->key_flags |= key_params->key_flags; 5481 cmd->key_cipher = key_params->key_cipher; 5482 if ((key_params->key_txmic_len) && 5483 (key_params->key_rxmic_len)) { 5484 cmd->key_txmic_len = key_params->key_txmic_len; 5485 cmd->key_rxmic_len = key_params->key_rxmic_len; 5486 } 5487 #if defined(ATH_SUPPORT_WAPI) || defined(FEATURE_WLAN_WAPI) 5488 wmi_update_wpi_key_counter(cmd->wpi_key_tsc_counter, 5489 key_params->tx_iv, 5490 cmd->wpi_key_rsc_counter, 5491 key_params->rx_iv); 5492 #endif 5493 buf_ptr += sizeof(wmi_vdev_install_key_cmd_fixed_param); 5494 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, 5495 roundup(key_params->key_len, sizeof(uint32_t))); 5496 key_data = (uint8_t *) (buf_ptr + WMI_TLV_HDR_SIZE); 5497 5498 /* for big endian host, copy engine byte_swap is enabled 5499 * But key_data is in network byte order 5500 * Need to byte swap the key_data - so when copy engine 5501 * does byte_swap - target gets key_data in the correct order 5502 */ 5503 WMI_HOST_IF_MSG_COPY_CHAR_ARRAY((void *)key_data, 5504 (const void *)key_params->key_data, 5505 key_params->key_len); 5506 qdf_mem_copy(&cmd->key_rsc_counter, &key_params->key_rsc_counter, 5507 sizeof(wmi_key_seq_counter)); 5508 cmd->key_len = key_params->key_len; 5509 5510 qdf_mem_copy(&cmd->key_tsc_counter, &key_params->key_tsc_counter, 5511 sizeof(wmi_key_seq_counter)); 5512 wmi_mtrace(WMI_VDEV_INSTALL_KEY_CMDID, cmd->vdev_id, 0); 5513 status = wmi_unified_cmd_send(wmi_handle, buf, len, 5514 WMI_VDEV_INSTALL_KEY_CMDID); 5515 if (QDF_IS_STATUS_ERROR(status)) { 5516 qdf_mem_zero(wmi_buf_data(buf), len); 5517 wmi_buf_free(buf); 5518 } 5519 return status; 5520 } 5521 5522 /** 5523 * send_p2p_go_set_beacon_ie_cmd_tlv() - set beacon IE for p2p go 5524 * @wmi_handle: wmi handle 5525 * @vdev_id: vdev id 5526 * @p2p_ie: p2p IE 5527 * 5528 * Return: QDF_STATUS_SUCCESS for success or error code 5529 */ 5530 static QDF_STATUS send_p2p_go_set_beacon_ie_cmd_tlv(wmi_unified_t wmi_handle, 5531 uint32_t vdev_id, uint8_t *p2p_ie) 5532 { 5533 QDF_STATUS ret; 5534 wmi_p2p_go_set_beacon_ie_fixed_param *cmd; 5535 wmi_buf_t wmi_buf; 5536 uint32_t ie_len, ie_len_aligned, wmi_buf_len; 5537 uint8_t *buf_ptr; 5538 5539 ie_len = (uint32_t) (p2p_ie[1] + 2); 5540 5541 /* More than one P2P IE may be included in a single frame. 5542 If multiple P2P IEs are present, the complete P2P attribute 5543 data consists of the concatenation of the P2P Attribute 5544 fields of the P2P IEs. The P2P Attributes field of each 5545 P2P IE may be any length up to the maximum (251 octets). 5546 In this case host sends one P2P IE to firmware so the length 5547 should not exceed more than 251 bytes 5548 */ 5549 if (ie_len > 251) { 5550 wmi_err("Invalid p2p ie length %u", ie_len); 5551 return QDF_STATUS_E_INVAL; 5552 } 5553 5554 ie_len_aligned = roundup(ie_len, sizeof(uint32_t)); 5555 5556 wmi_buf_len = 5557 sizeof(wmi_p2p_go_set_beacon_ie_fixed_param) + ie_len_aligned + 5558 WMI_TLV_HDR_SIZE; 5559 5560 wmi_buf = wmi_buf_alloc(wmi_handle, wmi_buf_len); 5561 if (!wmi_buf) 5562 return QDF_STATUS_E_NOMEM; 5563 5564 buf_ptr = (uint8_t *) wmi_buf_data(wmi_buf); 5565 5566 cmd = (wmi_p2p_go_set_beacon_ie_fixed_param *) buf_ptr; 5567 WMITLV_SET_HDR(&cmd->tlv_header, 5568 WMITLV_TAG_STRUC_wmi_p2p_go_set_beacon_ie_fixed_param, 5569 WMITLV_GET_STRUCT_TLVLEN 5570 (wmi_p2p_go_set_beacon_ie_fixed_param)); 5571 cmd->vdev_id = vdev_id; 5572 cmd->ie_buf_len = ie_len; 5573 5574 buf_ptr += sizeof(wmi_p2p_go_set_beacon_ie_fixed_param); 5575 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, ie_len_aligned); 5576 buf_ptr += WMI_TLV_HDR_SIZE; 5577 qdf_mem_copy(buf_ptr, p2p_ie, ie_len); 5578 5579 wmi_debug("Sending WMI_P2P_GO_SET_BEACON_IE"); 5580 5581 wmi_mtrace(WMI_P2P_GO_SET_BEACON_IE, cmd->vdev_id, 0); 5582 ret = wmi_unified_cmd_send(wmi_handle, 5583 wmi_buf, wmi_buf_len, 5584 WMI_P2P_GO_SET_BEACON_IE); 5585 if (QDF_IS_STATUS_ERROR(ret)) { 5586 wmi_err("Failed to send bcn tmpl: %d", ret); 5587 wmi_buf_free(wmi_buf); 5588 } 5589 5590 wmi_debug("Successfully sent WMI_P2P_GO_SET_BEACON_IE"); 5591 return ret; 5592 } 5593 5594 /** 5595 * send_scan_probe_setoui_cmd_tlv() - set scan probe OUI 5596 * @wmi_handle: wmi handle 5597 * @psetoui: OUI parameters 5598 * 5599 * set scan probe OUI parameters in firmware 5600 * 5601 * Return: CDF status 5602 */ 5603 static QDF_STATUS send_scan_probe_setoui_cmd_tlv(wmi_unified_t wmi_handle, 5604 struct scan_mac_oui *psetoui) 5605 { 5606 wmi_scan_prob_req_oui_cmd_fixed_param *cmd; 5607 wmi_buf_t wmi_buf; 5608 uint32_t len; 5609 uint8_t *buf_ptr; 5610 uint32_t *oui_buf; 5611 struct probe_req_allowlist_attr *ie_allowlist = &psetoui->ie_allowlist; 5612 5613 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE + 5614 ie_allowlist->num_vendor_oui * sizeof(wmi_vendor_oui); 5615 5616 wmi_buf = wmi_buf_alloc(wmi_handle, len); 5617 if (!wmi_buf) 5618 return QDF_STATUS_E_NOMEM; 5619 5620 buf_ptr = (uint8_t *) wmi_buf_data(wmi_buf); 5621 cmd = (wmi_scan_prob_req_oui_cmd_fixed_param *) buf_ptr; 5622 WMITLV_SET_HDR(&cmd->tlv_header, 5623 WMITLV_TAG_STRUC_wmi_scan_prob_req_oui_cmd_fixed_param, 5624 WMITLV_GET_STRUCT_TLVLEN 5625 (wmi_scan_prob_req_oui_cmd_fixed_param)); 5626 5627 oui_buf = &cmd->prob_req_oui; 5628 qdf_mem_zero(oui_buf, sizeof(cmd->prob_req_oui)); 5629 *oui_buf = psetoui->oui[0] << 16 | psetoui->oui[1] << 8 5630 | psetoui->oui[2]; 5631 wmi_debug("wmi:oui received from hdd %08x", cmd->prob_req_oui); 5632 5633 cmd->vdev_id = psetoui->vdev_id; 5634 cmd->flags = WMI_SCAN_PROBE_OUI_SPOOFED_MAC_IN_PROBE_REQ; 5635 if (psetoui->enb_probe_req_sno_randomization) 5636 cmd->flags |= WMI_SCAN_PROBE_OUI_RANDOM_SEQ_NO_IN_PROBE_REQ; 5637 5638 if (ie_allowlist->allow_list) { 5639 wmi_fill_ie_allowlist_attrs(cmd->ie_bitmap, 5640 &cmd->num_vendor_oui, 5641 ie_allowlist); 5642 cmd->flags |= 5643 WMI_SCAN_PROBE_OUI_ENABLE_IE_WHITELIST_IN_PROBE_REQ; 5644 } 5645 5646 buf_ptr += sizeof(*cmd); 5647 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 5648 ie_allowlist->num_vendor_oui * sizeof(wmi_vendor_oui)); 5649 buf_ptr += WMI_TLV_HDR_SIZE; 5650 5651 if (cmd->num_vendor_oui != 0) { 5652 wmi_fill_vendor_oui(buf_ptr, cmd->num_vendor_oui, 5653 ie_allowlist->voui); 5654 buf_ptr += cmd->num_vendor_oui * sizeof(wmi_vendor_oui); 5655 } 5656 5657 wmi_mtrace(WMI_SCAN_PROB_REQ_OUI_CMDID, cmd->vdev_id, 0); 5658 if (wmi_unified_cmd_send(wmi_handle, wmi_buf, len, 5659 WMI_SCAN_PROB_REQ_OUI_CMDID)) { 5660 wmi_err("Failed to send command WMI_SCAN_PROB_REQ_OUI_CMDID"); 5661 wmi_buf_free(wmi_buf); 5662 return QDF_STATUS_E_FAILURE; 5663 } 5664 return QDF_STATUS_SUCCESS; 5665 } 5666 5667 #ifdef IPA_OFFLOAD 5668 /** send_ipa_offload_control_cmd_tlv() - ipa offload control parameter 5669 * @wmi_handle: wmi handle 5670 * @ipa_offload: ipa offload control parameter 5671 * 5672 * Returns: 0 on success, error number otherwise 5673 */ 5674 static QDF_STATUS send_ipa_offload_control_cmd_tlv(wmi_unified_t wmi_handle, 5675 struct ipa_uc_offload_control_params *ipa_offload) 5676 { 5677 wmi_ipa_offload_enable_disable_cmd_fixed_param *cmd; 5678 wmi_buf_t wmi_buf; 5679 uint32_t len; 5680 u_int8_t *buf_ptr; 5681 5682 len = sizeof(*cmd); 5683 wmi_buf = wmi_buf_alloc(wmi_handle, len); 5684 if (!wmi_buf) 5685 return QDF_STATUS_E_NOMEM; 5686 5687 wmi_debug("offload_type=%d, enable=%d", 5688 ipa_offload->offload_type, ipa_offload->enable); 5689 5690 buf_ptr = (u_int8_t *)wmi_buf_data(wmi_buf); 5691 5692 cmd = (wmi_ipa_offload_enable_disable_cmd_fixed_param *)buf_ptr; 5693 WMITLV_SET_HDR(&cmd->tlv_header, 5694 WMITLV_TAG_STRUCT_wmi_ipa_offload_enable_disable_cmd_fixed_param, 5695 WMITLV_GET_STRUCT_TLVLEN( 5696 wmi_ipa_offload_enable_disable_cmd_fixed_param)); 5697 5698 cmd->offload_type = ipa_offload->offload_type; 5699 cmd->vdev_id = ipa_offload->vdev_id; 5700 cmd->enable = ipa_offload->enable; 5701 5702 wmi_mtrace(WMI_IPA_OFFLOAD_ENABLE_DISABLE_CMDID, cmd->vdev_id, 0); 5703 if (wmi_unified_cmd_send(wmi_handle, wmi_buf, len, 5704 WMI_IPA_OFFLOAD_ENABLE_DISABLE_CMDID)) { 5705 wmi_err("Failed to send WMI_IPA_OFFLOAD_ENABLE_DISABLE_CMDID"); 5706 wmi_buf_free(wmi_buf); 5707 return QDF_STATUS_E_FAILURE; 5708 } 5709 5710 return QDF_STATUS_SUCCESS; 5711 } 5712 #endif 5713 5714 /** 5715 * send_pno_stop_cmd_tlv() - PNO stop request 5716 * @wmi_handle: wmi handle 5717 * @vdev_id: vdev id 5718 * 5719 * This function request FW to stop ongoing PNO operation. 5720 * 5721 * Return: CDF status 5722 */ 5723 static QDF_STATUS send_pno_stop_cmd_tlv(wmi_unified_t wmi_handle, uint8_t vdev_id) 5724 { 5725 wmi_nlo_config_cmd_fixed_param *cmd; 5726 int32_t len = sizeof(*cmd); 5727 wmi_buf_t buf; 5728 uint8_t *buf_ptr; 5729 int ret; 5730 5731 /* 5732 * TLV place holder for array of structures nlo_configured_parameters 5733 * TLV place holder for array of uint32_t channel_list 5734 * TLV place holder for chnl prediction cfg 5735 */ 5736 len += WMI_TLV_HDR_SIZE + WMI_TLV_HDR_SIZE + WMI_TLV_HDR_SIZE; 5737 buf = wmi_buf_alloc(wmi_handle, len); 5738 if (!buf) 5739 return QDF_STATUS_E_NOMEM; 5740 5741 cmd = (wmi_nlo_config_cmd_fixed_param *) wmi_buf_data(buf); 5742 buf_ptr = (uint8_t *) cmd; 5743 5744 WMITLV_SET_HDR(&cmd->tlv_header, 5745 WMITLV_TAG_STRUC_wmi_nlo_config_cmd_fixed_param, 5746 WMITLV_GET_STRUCT_TLVLEN 5747 (wmi_nlo_config_cmd_fixed_param)); 5748 5749 cmd->vdev_id = vdev_id; 5750 cmd->flags = WMI_NLO_CONFIG_STOP; 5751 buf_ptr += sizeof(*cmd); 5752 5753 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 0); 5754 buf_ptr += WMI_TLV_HDR_SIZE; 5755 5756 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, 0); 5757 buf_ptr += WMI_TLV_HDR_SIZE; 5758 5759 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 0); 5760 buf_ptr += WMI_TLV_HDR_SIZE; 5761 5762 wmi_mtrace(WMI_NETWORK_LIST_OFFLOAD_CONFIG_CMDID, cmd->vdev_id, 0); 5763 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 5764 WMI_NETWORK_LIST_OFFLOAD_CONFIG_CMDID); 5765 if (ret) { 5766 wmi_err("Failed to send nlo wmi cmd"); 5767 wmi_buf_free(buf); 5768 return QDF_STATUS_E_FAILURE; 5769 } 5770 5771 return QDF_STATUS_SUCCESS; 5772 } 5773 5774 /** 5775 * send_obss_disable_cmd_tlv() - disable obss scan request 5776 * @wmi_handle: wmi handle 5777 * @vdev_id: vdev id 5778 * 5779 * This function request FW to disable ongoing obss scan operation. 5780 * 5781 * Return: QDF status 5782 */ 5783 static QDF_STATUS send_obss_disable_cmd_tlv(wmi_unified_t wmi_handle, 5784 uint8_t vdev_id) 5785 { 5786 QDF_STATUS status; 5787 wmi_buf_t buf; 5788 wmi_obss_scan_disable_cmd_fixed_param *cmd; 5789 int len = sizeof(*cmd); 5790 5791 buf = wmi_buf_alloc(wmi_handle, len); 5792 if (!buf) 5793 return QDF_STATUS_E_NOMEM; 5794 5795 wmi_debug("cmd %x vdev_id %d", WMI_OBSS_SCAN_DISABLE_CMDID, vdev_id); 5796 5797 cmd = (wmi_obss_scan_disable_cmd_fixed_param *)wmi_buf_data(buf); 5798 WMITLV_SET_HDR(&cmd->tlv_header, 5799 WMITLV_TAG_STRUC_wmi_obss_scan_disable_cmd_fixed_param, 5800 WMITLV_GET_STRUCT_TLVLEN( 5801 wmi_obss_scan_disable_cmd_fixed_param)); 5802 5803 cmd->vdev_id = vdev_id; 5804 status = wmi_unified_cmd_send(wmi_handle, buf, len, 5805 WMI_OBSS_SCAN_DISABLE_CMDID); 5806 if (QDF_IS_STATUS_ERROR(status)) 5807 wmi_buf_free(buf); 5808 5809 return status; 5810 } 5811 5812 /** 5813 * wmi_set_pno_channel_prediction() - Set PNO channel prediction 5814 * @buf_ptr: Buffer passed by upper layers 5815 * @pno: Buffer to be sent to the firmware 5816 * 5817 * Copy the PNO Channel prediction configuration parameters 5818 * passed by the upper layers to a WMI format TLV and send it 5819 * down to the firmware. 5820 * 5821 * Return: None 5822 */ 5823 static void wmi_set_pno_channel_prediction(uint8_t *buf_ptr, 5824 struct pno_scan_req_params *pno) 5825 { 5826 nlo_channel_prediction_cfg *channel_prediction_cfg = 5827 (nlo_channel_prediction_cfg *) buf_ptr; 5828 WMITLV_SET_HDR(&channel_prediction_cfg->tlv_header, 5829 WMITLV_TAG_ARRAY_BYTE, 5830 WMITLV_GET_STRUCT_TLVLEN(nlo_channel_prediction_cfg)); 5831 #ifdef FEATURE_WLAN_SCAN_PNO 5832 channel_prediction_cfg->enable = pno->pno_channel_prediction; 5833 channel_prediction_cfg->top_k_num = pno->top_k_num_of_channels; 5834 channel_prediction_cfg->stationary_threshold = pno->stationary_thresh; 5835 channel_prediction_cfg->full_scan_period_ms = 5836 pno->channel_prediction_full_scan; 5837 #endif 5838 buf_ptr += sizeof(nlo_channel_prediction_cfg); 5839 wmi_debug("enable: %d, top_k_num: %d, stat_thresh: %d, full_scan: %d", 5840 channel_prediction_cfg->enable, 5841 channel_prediction_cfg->top_k_num, 5842 channel_prediction_cfg->stationary_threshold, 5843 channel_prediction_cfg->full_scan_period_ms); 5844 } 5845 5846 /** 5847 * send_cp_stats_cmd_tlv() - Send cp stats wmi command 5848 * @wmi_handle: wmi handle 5849 * @buf_ptr: Buffer passed by upper layers 5850 * @buf_len: Length of passed buffer by upper layer 5851 * 5852 * Copy the buffer passed by the upper layers and send it 5853 * down to the firmware. 5854 * 5855 * Return: None 5856 */ 5857 static QDF_STATUS send_cp_stats_cmd_tlv(wmi_unified_t wmi_handle, 5858 void *buf_ptr, uint32_t buf_len) 5859 { 5860 wmi_buf_t buf = NULL; 5861 QDF_STATUS status; 5862 int len; 5863 uint8_t *data_ptr; 5864 5865 len = buf_len; 5866 buf = wmi_buf_alloc(wmi_handle, len); 5867 if (!buf) 5868 return QDF_STATUS_E_NOMEM; 5869 5870 data_ptr = (uint8_t *)wmi_buf_data(buf); 5871 qdf_mem_copy(data_ptr, buf_ptr, len); 5872 5873 wmi_mtrace(WMI_REQUEST_CTRL_PATH_STATS_CMDID, NO_SESSION, 0); 5874 status = wmi_unified_cmd_send(wmi_handle, buf, 5875 len, WMI_REQUEST_CTRL_PATH_STATS_CMDID); 5876 5877 if (QDF_IS_STATUS_ERROR(status)) { 5878 wmi_buf_free(buf); 5879 return QDF_STATUS_E_FAILURE; 5880 } 5881 return QDF_STATUS_SUCCESS; 5882 } 5883 5884 /** 5885 * send_halphy_stats_cmd_tlv() - Send halphy stats wmi command 5886 * @wmi_handle: wmi handle 5887 * @buf_ptr: Buffer passed by upper layers 5888 * @buf_len: Length of passed buffer by upper layer 5889 * 5890 * Copy the buffer passed by the upper layers and send it 5891 * down to the firmware. 5892 * 5893 * Return: None 5894 */ 5895 static QDF_STATUS send_halphy_stats_cmd_tlv(wmi_unified_t wmi_handle, 5896 void *buf_ptr, uint32_t buf_len) 5897 { 5898 wmi_buf_t buf = NULL; 5899 QDF_STATUS status; 5900 int len; 5901 uint8_t *data_ptr; 5902 5903 len = buf_len; 5904 buf = wmi_buf_alloc(wmi_handle, len); 5905 if (!buf) 5906 return QDF_STATUS_E_NOMEM; 5907 5908 data_ptr = (uint8_t *)wmi_buf_data(buf); 5909 qdf_mem_copy(data_ptr, buf_ptr, len); 5910 5911 wmi_mtrace(WMI_REQUEST_HALPHY_CTRL_PATH_STATS_CMDID, NO_SESSION, 0); 5912 status = wmi_unified_cmd_send(wmi_handle, buf, 5913 len, 5914 WMI_REQUEST_HALPHY_CTRL_PATH_STATS_CMDID); 5915 5916 if (QDF_IS_STATUS_ERROR(status)) { 5917 wmi_buf_free(buf); 5918 return QDF_STATUS_E_FAILURE; 5919 } 5920 return QDF_STATUS_SUCCESS; 5921 } 5922 5923 /** 5924 * extract_cp_stats_more_pending_tlv - api to extract more flag from event data 5925 * @wmi_handle: wmi handle 5926 * @evt_buf: event buffer 5927 * @more_flag: buffer to populate more flag 5928 * 5929 * Return: status of operation 5930 */ 5931 static QDF_STATUS 5932 extract_cp_stats_more_pending_tlv(wmi_unified_t wmi, void *evt_buf, 5933 uint32_t *more_flag) 5934 { 5935 WMI_CTRL_PATH_STATS_EVENTID_param_tlvs *param_buf; 5936 wmi_ctrl_path_stats_event_fixed_param *ev; 5937 5938 param_buf = (WMI_CTRL_PATH_STATS_EVENTID_param_tlvs *)evt_buf; 5939 if (!param_buf) { 5940 wmi_err_rl("param_buf is NULL"); 5941 return QDF_STATUS_E_FAILURE; 5942 } 5943 ev = (wmi_ctrl_path_stats_event_fixed_param *)param_buf->fixed_param; 5944 5945 *more_flag = ev->more; 5946 return QDF_STATUS_SUCCESS; 5947 } 5948 5949 /** 5950 * extract_halphy_stats_end_of_event_tlv - api to extract end_of_event flag 5951 * from event data 5952 * @wmi_handle: wmi handle 5953 * @evt_buf: event buffer 5954 * @end_of_event_flag: buffer to populate end_of_event flag 5955 * 5956 * Return: status of operation 5957 */ 5958 static QDF_STATUS 5959 extract_halphy_stats_end_of_event_tlv(wmi_unified_t wmi, void *evt_buf, 5960 uint32_t *end_of_event_flag) 5961 { 5962 WMI_HALPHY_CTRL_PATH_STATS_EVENTID_param_tlvs *param_buf; 5963 wmi_halphy_ctrl_path_stats_event_fixed_param *ev; 5964 5965 param_buf = (WMI_HALPHY_CTRL_PATH_STATS_EVENTID_param_tlvs *)evt_buf; 5966 if (!param_buf) { 5967 wmi_err_rl("param_buf is NULL"); 5968 return QDF_STATUS_E_FAILURE; 5969 } 5970 ev = (wmi_halphy_ctrl_path_stats_event_fixed_param *) 5971 param_buf->fixed_param; 5972 5973 *end_of_event_flag = ev->end_of_event; 5974 return QDF_STATUS_SUCCESS; 5975 } 5976 5977 /** 5978 * extract_halphy_stats_event_count - api to extract event count flag from 5979 * event data 5980 * @wmi_handle: wmi handle 5981 * @evt_buf: event buffer 5982 * @event_count_flag: buffer to populate event_count flag 5983 * 5984 * Return: status of operation 5985 */ 5986 static QDF_STATUS 5987 extract_halphy_stats_event_count_tlv(wmi_unified_t wmi, void *evt_buf, 5988 uint32_t *event_count_flag) 5989 { 5990 WMI_HALPHY_CTRL_PATH_STATS_EVENTID_param_tlvs *param_buf; 5991 wmi_halphy_ctrl_path_stats_event_fixed_param *ev; 5992 5993 param_buf = (WMI_HALPHY_CTRL_PATH_STATS_EVENTID_param_tlvs *)evt_buf; 5994 if (!param_buf) { 5995 wmi_err_rl("param_buf is NULL"); 5996 return QDF_STATUS_E_FAILURE; 5997 } 5998 ev = (wmi_halphy_ctrl_path_stats_event_fixed_param *) 5999 param_buf->fixed_param; 6000 6001 *event_count_flag = ev->event_count; 6002 return QDF_STATUS_SUCCESS; 6003 } 6004 6005 /** 6006 * send_nlo_mawc_cmd_tlv() - Send MAWC NLO configuration 6007 * @wmi_handle: wmi handle 6008 * @params: configuration parameters 6009 * 6010 * Return: QDF_STATUS 6011 */ 6012 static QDF_STATUS send_nlo_mawc_cmd_tlv(wmi_unified_t wmi_handle, 6013 struct nlo_mawc_params *params) 6014 { 6015 wmi_buf_t buf = NULL; 6016 QDF_STATUS status; 6017 int len; 6018 uint8_t *buf_ptr; 6019 wmi_nlo_configure_mawc_cmd_fixed_param *wmi_nlo_mawc_params; 6020 6021 len = sizeof(*wmi_nlo_mawc_params); 6022 buf = wmi_buf_alloc(wmi_handle, len); 6023 if (!buf) 6024 return QDF_STATUS_E_NOMEM; 6025 6026 buf_ptr = (uint8_t *) wmi_buf_data(buf); 6027 wmi_nlo_mawc_params = 6028 (wmi_nlo_configure_mawc_cmd_fixed_param *) buf_ptr; 6029 WMITLV_SET_HDR(&wmi_nlo_mawc_params->tlv_header, 6030 WMITLV_TAG_STRUC_wmi_nlo_configure_mawc_cmd_fixed_param, 6031 WMITLV_GET_STRUCT_TLVLEN 6032 (wmi_nlo_configure_mawc_cmd_fixed_param)); 6033 wmi_nlo_mawc_params->vdev_id = params->vdev_id; 6034 if (params->enable) 6035 wmi_nlo_mawc_params->enable = 1; 6036 else 6037 wmi_nlo_mawc_params->enable = 0; 6038 wmi_nlo_mawc_params->exp_backoff_ratio = params->exp_backoff_ratio; 6039 wmi_nlo_mawc_params->init_scan_interval = params->init_scan_interval; 6040 wmi_nlo_mawc_params->max_scan_interval = params->max_scan_interval; 6041 wmi_debug("MAWC NLO en=%d, vdev=%d, ratio=%d, SCAN init=%d, max=%d", 6042 wmi_nlo_mawc_params->enable, wmi_nlo_mawc_params->vdev_id, 6043 wmi_nlo_mawc_params->exp_backoff_ratio, 6044 wmi_nlo_mawc_params->init_scan_interval, 6045 wmi_nlo_mawc_params->max_scan_interval); 6046 6047 wmi_mtrace(WMI_NLO_CONFIGURE_MAWC_CMDID, NO_SESSION, 0); 6048 status = wmi_unified_cmd_send(wmi_handle, buf, 6049 len, WMI_NLO_CONFIGURE_MAWC_CMDID); 6050 if (QDF_IS_STATUS_ERROR(status)) { 6051 wmi_err("WMI_NLO_CONFIGURE_MAWC_CMDID failed, Error %d", 6052 status); 6053 wmi_buf_free(buf); 6054 return QDF_STATUS_E_FAILURE; 6055 } 6056 6057 return QDF_STATUS_SUCCESS; 6058 } 6059 6060 /** 6061 * wmi_dump_pno_scan_freq_list() - dump frequency list associated with pno 6062 * scan 6063 * @scan_freq_list: frequency list for pno scan 6064 * 6065 * Return: void 6066 */ 6067 static void wmi_dump_pno_scan_freq_list(struct chan_list *scan_freq_list) 6068 { 6069 uint32_t i; 6070 uint8_t info[WMI_MAX_CHAN_INFO_LOG]; 6071 uint32_t len = 0; 6072 struct chan_info *chan_info; 6073 int ret; 6074 6075 wmi_debug("[PNO_SCAN] Total freq %d", scan_freq_list->num_chan); 6076 for (i = 0; i < scan_freq_list->num_chan; i++) { 6077 chan_info = &scan_freq_list->chan[i]; 6078 ret = qdf_scnprintf(info + len, sizeof(info) - len, 6079 " %d[%d]", chan_info->freq, 6080 chan_info->flags); 6081 if (ret <= 0) 6082 break; 6083 len += ret; 6084 if (len >= (sizeof(info) - 20)) { 6085 wmi_nofl_debug("Freq[flag]:%s", 6086 info); 6087 len = 0; 6088 } 6089 } 6090 if (len) 6091 wmi_nofl_debug("Freq[flag]:%s", info); 6092 } 6093 6094 /** 6095 * send_pno_start_cmd_tlv() - PNO start request 6096 * @wmi_handle: wmi handle 6097 * @pno: PNO request 6098 * 6099 * This function request FW to start PNO request. 6100 * Request: CDF status 6101 */ 6102 static QDF_STATUS send_pno_start_cmd_tlv(wmi_unified_t wmi_handle, 6103 struct pno_scan_req_params *pno) 6104 { 6105 wmi_nlo_config_cmd_fixed_param *cmd; 6106 nlo_configured_parameters *nlo_list; 6107 uint32_t *channel_list; 6108 int32_t len; 6109 qdf_freq_t freq; 6110 wmi_buf_t buf; 6111 uint8_t *buf_ptr; 6112 uint8_t i; 6113 int ret; 6114 struct probe_req_allowlist_attr *ie_allowlist = &pno->ie_allowlist; 6115 connected_nlo_rssi_params *nlo_relative_rssi; 6116 connected_nlo_bss_band_rssi_pref *nlo_band_rssi; 6117 6118 /* 6119 * TLV place holder for array nlo_configured_parameters(nlo_list) 6120 * TLV place holder for array of uint32_t channel_list 6121 * TLV place holder for chnnl prediction cfg 6122 * TLV place holder for array of wmi_vendor_oui 6123 * TLV place holder for array of connected_nlo_bss_band_rssi_pref 6124 */ 6125 len = sizeof(*cmd) + 6126 WMI_TLV_HDR_SIZE + WMI_TLV_HDR_SIZE + WMI_TLV_HDR_SIZE + 6127 WMI_TLV_HDR_SIZE + WMI_TLV_HDR_SIZE; 6128 6129 len += sizeof(uint32_t) * pno->networks_list[0].pno_chan_list.num_chan; 6130 len += sizeof(nlo_configured_parameters) * 6131 QDF_MIN(pno->networks_cnt, WMI_NLO_MAX_SSIDS); 6132 len += sizeof(nlo_channel_prediction_cfg); 6133 len += sizeof(enlo_candidate_score_params); 6134 len += sizeof(wmi_vendor_oui) * ie_allowlist->num_vendor_oui; 6135 len += sizeof(connected_nlo_rssi_params); 6136 len += sizeof(connected_nlo_bss_band_rssi_pref); 6137 6138 buf = wmi_buf_alloc(wmi_handle, len); 6139 if (!buf) 6140 return QDF_STATUS_E_NOMEM; 6141 6142 cmd = (wmi_nlo_config_cmd_fixed_param *) wmi_buf_data(buf); 6143 6144 buf_ptr = (uint8_t *) cmd; 6145 WMITLV_SET_HDR(&cmd->tlv_header, 6146 WMITLV_TAG_STRUC_wmi_nlo_config_cmd_fixed_param, 6147 WMITLV_GET_STRUCT_TLVLEN 6148 (wmi_nlo_config_cmd_fixed_param)); 6149 cmd->vdev_id = pno->vdev_id; 6150 cmd->flags = WMI_NLO_CONFIG_START | WMI_NLO_CONFIG_SSID_HIDE_EN; 6151 6152 #ifdef FEATURE_WLAN_SCAN_PNO 6153 WMI_SCAN_SET_DWELL_MODE(cmd->flags, 6154 pno->adaptive_dwell_mode); 6155 #endif 6156 /* Current FW does not support min-max range for dwell time */ 6157 cmd->active_dwell_time = pno->active_dwell_time; 6158 cmd->passive_dwell_time = pno->passive_dwell_time; 6159 6160 if (pno->do_passive_scan) 6161 cmd->flags |= WMI_NLO_CONFIG_SCAN_PASSIVE; 6162 /* Copy scan interval */ 6163 cmd->fast_scan_period = pno->fast_scan_period; 6164 cmd->slow_scan_period = pno->slow_scan_period; 6165 cmd->delay_start_time = WMI_SEC_TO_MSEC(pno->delay_start_time); 6166 cmd->fast_scan_max_cycles = pno->fast_scan_max_cycles; 6167 cmd->scan_backoff_multiplier = pno->scan_backoff_multiplier; 6168 6169 /* mac randomization attributes */ 6170 if (pno->scan_random.randomize) { 6171 cmd->flags |= WMI_NLO_CONFIG_SPOOFED_MAC_IN_PROBE_REQ | 6172 WMI_NLO_CONFIG_RANDOM_SEQ_NO_IN_PROBE_REQ; 6173 wmi_copy_scan_random_mac(pno->scan_random.mac_addr, 6174 pno->scan_random.mac_mask, 6175 &cmd->mac_addr, 6176 &cmd->mac_mask); 6177 } 6178 6179 buf_ptr += sizeof(wmi_nlo_config_cmd_fixed_param); 6180 6181 cmd->no_of_ssids = QDF_MIN(pno->networks_cnt, WMI_NLO_MAX_SSIDS); 6182 6183 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 6184 cmd->no_of_ssids * sizeof(nlo_configured_parameters)); 6185 buf_ptr += WMI_TLV_HDR_SIZE; 6186 6187 nlo_list = (nlo_configured_parameters *) buf_ptr; 6188 for (i = 0; i < cmd->no_of_ssids; i++) { 6189 WMITLV_SET_HDR(&nlo_list[i].tlv_header, 6190 WMITLV_TAG_ARRAY_BYTE, 6191 WMITLV_GET_STRUCT_TLVLEN 6192 (nlo_configured_parameters)); 6193 /* Copy ssid and it's length */ 6194 nlo_list[i].ssid.valid = true; 6195 nlo_list[i].ssid.ssid.ssid_len = 6196 pno->networks_list[i].ssid.length; 6197 qdf_mem_copy(nlo_list[i].ssid.ssid.ssid, 6198 pno->networks_list[i].ssid.ssid, 6199 nlo_list[i].ssid.ssid.ssid_len); 6200 6201 /* Copy rssi threshold */ 6202 if (pno->networks_list[i].rssi_thresh && 6203 pno->networks_list[i].rssi_thresh > 6204 WMI_RSSI_THOLD_DEFAULT) { 6205 nlo_list[i].rssi_cond.valid = true; 6206 nlo_list[i].rssi_cond.rssi = 6207 pno->networks_list[i].rssi_thresh; 6208 } 6209 nlo_list[i].bcast_nw_type.valid = true; 6210 nlo_list[i].bcast_nw_type.bcast_nw_type = 6211 pno->networks_list[i].bc_new_type; 6212 } 6213 buf_ptr += cmd->no_of_ssids * sizeof(nlo_configured_parameters); 6214 6215 /* Copy channel info */ 6216 cmd->num_of_channels = pno->networks_list[0].pno_chan_list.num_chan; 6217 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, 6218 (cmd->num_of_channels * sizeof(uint32_t))); 6219 buf_ptr += WMI_TLV_HDR_SIZE; 6220 6221 channel_list = (uint32_t *) buf_ptr; 6222 for (i = 0; i < cmd->num_of_channels; i++) { 6223 TARGET_SET_FREQ_IN_CHAN_LIST_TLV(channel_list[i], 6224 pno->networks_list[0].pno_chan_list.chan[i].freq); 6225 6226 if (channel_list[i] < WMI_NLO_FREQ_THRESH) { 6227 freq = pno->networks_list[0].pno_chan_list.chan[i].freq; 6228 TARGET_SET_FREQ_IN_CHAN_LIST_TLV(channel_list[i], 6229 wlan_chan_to_freq(freq)); 6230 } 6231 6232 TARGET_SET_FLAGS_IN_CHAN_LIST_TLV(channel_list[i], 6233 pno->networks_list[0].pno_chan_list.chan[i].flags); 6234 } 6235 6236 wmi_dump_pno_scan_freq_list(&pno->networks_list[0].pno_chan_list); 6237 6238 buf_ptr += cmd->num_of_channels * sizeof(uint32_t); 6239 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 6240 sizeof(nlo_channel_prediction_cfg)); 6241 buf_ptr += WMI_TLV_HDR_SIZE; 6242 wmi_set_pno_channel_prediction(buf_ptr, pno); 6243 buf_ptr += sizeof(nlo_channel_prediction_cfg); 6244 /** TODO: Discrete firmware doesn't have command/option to configure 6245 * App IE which comes from wpa_supplicant as of part PNO start request. 6246 */ 6247 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_STRUC_enlo_candidate_score_param, 6248 WMITLV_GET_STRUCT_TLVLEN(enlo_candidate_score_params)); 6249 buf_ptr += sizeof(enlo_candidate_score_params); 6250 6251 if (ie_allowlist->allow_list) { 6252 cmd->flags |= WMI_NLO_CONFIG_ENABLE_IE_WHITELIST_IN_PROBE_REQ; 6253 wmi_fill_ie_allowlist_attrs(cmd->ie_bitmap, 6254 &cmd->num_vendor_oui, 6255 ie_allowlist); 6256 } 6257 6258 /* ie allow list */ 6259 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 6260 ie_allowlist->num_vendor_oui * sizeof(wmi_vendor_oui)); 6261 buf_ptr += WMI_TLV_HDR_SIZE; 6262 if (cmd->num_vendor_oui != 0) { 6263 wmi_fill_vendor_oui(buf_ptr, cmd->num_vendor_oui, 6264 ie_allowlist->voui); 6265 buf_ptr += cmd->num_vendor_oui * sizeof(wmi_vendor_oui); 6266 } 6267 6268 if (pno->relative_rssi_set) 6269 cmd->flags |= WMI_NLO_CONFIG_ENABLE_CNLO_RSSI_CONFIG; 6270 6271 /* 6272 * Firmware calculation using connected PNO params: 6273 * New AP's RSSI >= (Connected AP's RSSI + relative_rssi +/- rssi_pref) 6274 * deduction of rssi_pref for chosen band_pref and 6275 * addition of rssi_pref for remaining bands (other than chosen band). 6276 */ 6277 nlo_relative_rssi = (connected_nlo_rssi_params *) buf_ptr; 6278 WMITLV_SET_HDR(&nlo_relative_rssi->tlv_header, 6279 WMITLV_TAG_STRUC_wmi_connected_nlo_rssi_params, 6280 WMITLV_GET_STRUCT_TLVLEN(connected_nlo_rssi_params)); 6281 nlo_relative_rssi->relative_rssi = pno->relative_rssi; 6282 buf_ptr += sizeof(*nlo_relative_rssi); 6283 6284 /* 6285 * As of now Kernel and Host supports one band and rssi preference. 6286 * Firmware supports array of band and rssi preferences 6287 */ 6288 cmd->num_cnlo_band_pref = 1; 6289 WMITLV_SET_HDR(buf_ptr, 6290 WMITLV_TAG_ARRAY_STRUC, 6291 cmd->num_cnlo_band_pref * 6292 sizeof(connected_nlo_bss_band_rssi_pref)); 6293 buf_ptr += WMI_TLV_HDR_SIZE; 6294 6295 nlo_band_rssi = (connected_nlo_bss_band_rssi_pref *) buf_ptr; 6296 for (i = 0; i < cmd->num_cnlo_band_pref; i++) { 6297 WMITLV_SET_HDR(&nlo_band_rssi[i].tlv_header, 6298 WMITLV_TAG_STRUC_wmi_connected_nlo_bss_band_rssi_pref, 6299 WMITLV_GET_STRUCT_TLVLEN( 6300 connected_nlo_bss_band_rssi_pref)); 6301 nlo_band_rssi[i].band = pno->band_rssi_pref.band; 6302 nlo_band_rssi[i].rssi_pref = pno->band_rssi_pref.rssi; 6303 } 6304 buf_ptr += cmd->num_cnlo_band_pref * sizeof(*nlo_band_rssi); 6305 6306 wmi_mtrace(WMI_NETWORK_LIST_OFFLOAD_CONFIG_CMDID, cmd->vdev_id, 0); 6307 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 6308 WMI_NETWORK_LIST_OFFLOAD_CONFIG_CMDID); 6309 if (ret) { 6310 wmi_err("Failed to send nlo wmi cmd"); 6311 wmi_buf_free(buf); 6312 return QDF_STATUS_E_FAILURE; 6313 } 6314 6315 return QDF_STATUS_SUCCESS; 6316 } 6317 6318 /** 6319 * is_service_enabled_tlv() - Check if service enabled 6320 * @param wmi_handle: wmi handle 6321 * @param service_id: service identifier 6322 * 6323 * Return: 1 enabled, 0 disabled 6324 */ 6325 static bool is_service_enabled_tlv(wmi_unified_t wmi_handle, 6326 uint32_t service_id) 6327 { 6328 struct wmi_soc *soc = wmi_handle->soc; 6329 6330 if (!soc->wmi_service_bitmap) { 6331 wmi_err("WMI service bit map is not saved yet"); 6332 return false; 6333 } 6334 6335 /* if wmi_service_enabled was received with extended2 bitmap, 6336 * use WMI_SERVICE_EXT2_IS_ENABLED to check the services. 6337 */ 6338 if (soc->wmi_ext2_service_bitmap) { 6339 if (!soc->wmi_ext_service_bitmap) { 6340 wmi_err("WMI service ext bit map is not saved yet"); 6341 return false; 6342 } 6343 6344 return WMI_SERVICE_EXT2_IS_ENABLED(soc->wmi_service_bitmap, 6345 soc->wmi_ext_service_bitmap, 6346 soc->wmi_ext2_service_bitmap, 6347 service_id); 6348 } 6349 6350 if (service_id >= WMI_MAX_EXT_SERVICE) { 6351 wmi_err_rl("Service id %d but WMI ext2 service bitmap is NULL", 6352 service_id); 6353 return false; 6354 } 6355 /* if wmi_service_enabled was received with extended bitmap, 6356 * use WMI_SERVICE_EXT_IS_ENABLED to check the services. 6357 */ 6358 if (soc->wmi_ext_service_bitmap) 6359 return WMI_SERVICE_EXT_IS_ENABLED(soc->wmi_service_bitmap, 6360 soc->wmi_ext_service_bitmap, 6361 service_id); 6362 6363 if (service_id >= WMI_MAX_SERVICE) { 6364 wmi_err("Service id %d but WMI ext service bitmap is NULL", 6365 service_id); 6366 return false; 6367 } 6368 6369 return WMI_SERVICE_IS_ENABLED(soc->wmi_service_bitmap, 6370 service_id); 6371 } 6372 6373 #ifdef WLAN_FEATURE_LINK_LAYER_STATS 6374 /** 6375 * send_process_ll_stats_clear_cmd_tlv() - clear link layer stats 6376 * @wmi_handle: wmi handle 6377 * @clear_req: ll stats clear request command params 6378 * 6379 * Return: QDF_STATUS_SUCCESS for success or error code 6380 */ 6381 static QDF_STATUS send_process_ll_stats_clear_cmd_tlv(wmi_unified_t wmi_handle, 6382 const struct ll_stats_clear_params *clear_req) 6383 { 6384 wmi_clear_link_stats_cmd_fixed_param *cmd; 6385 int32_t len; 6386 wmi_buf_t buf; 6387 uint8_t *buf_ptr; 6388 int ret; 6389 6390 len = sizeof(*cmd); 6391 buf = wmi_buf_alloc(wmi_handle, len); 6392 6393 if (!buf) 6394 return QDF_STATUS_E_NOMEM; 6395 6396 buf_ptr = (uint8_t *) wmi_buf_data(buf); 6397 qdf_mem_zero(buf_ptr, len); 6398 cmd = (wmi_clear_link_stats_cmd_fixed_param *) buf_ptr; 6399 6400 WMITLV_SET_HDR(&cmd->tlv_header, 6401 WMITLV_TAG_STRUC_wmi_clear_link_stats_cmd_fixed_param, 6402 WMITLV_GET_STRUCT_TLVLEN 6403 (wmi_clear_link_stats_cmd_fixed_param)); 6404 6405 cmd->stop_stats_collection_req = clear_req->stop_req; 6406 cmd->vdev_id = clear_req->vdev_id; 6407 cmd->stats_clear_req_mask = clear_req->stats_clear_mask; 6408 6409 WMI_CHAR_ARRAY_TO_MAC_ADDR(clear_req->peer_macaddr.bytes, 6410 &cmd->peer_macaddr); 6411 6412 wmi_debug("LINK_LAYER_STATS - Clear Request Params"); 6413 wmi_debug("StopReq: %d Vdev Id: %d Clear Stat Mask: %d" 6414 " Peer MAC Addr: "QDF_MAC_ADDR_FMT, 6415 cmd->stop_stats_collection_req, 6416 cmd->vdev_id, cmd->stats_clear_req_mask, 6417 QDF_MAC_ADDR_REF(clear_req->peer_macaddr.bytes)); 6418 6419 wmi_mtrace(WMI_CLEAR_LINK_STATS_CMDID, cmd->vdev_id, 0); 6420 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 6421 WMI_CLEAR_LINK_STATS_CMDID); 6422 if (ret) { 6423 wmi_err("Failed to send clear link stats req"); 6424 wmi_buf_free(buf); 6425 return QDF_STATUS_E_FAILURE; 6426 } 6427 6428 wmi_debug("Clear Link Layer Stats request sent successfully"); 6429 return QDF_STATUS_SUCCESS; 6430 } 6431 6432 /** 6433 * send_process_ll_stats_set_cmd_tlv() - link layer stats set request 6434 * @wmi_handle: wmi handle 6435 * @set_req: ll stats set request command params 6436 * 6437 * Return: QDF_STATUS_SUCCESS for success or error code 6438 */ 6439 static QDF_STATUS send_process_ll_stats_set_cmd_tlv(wmi_unified_t wmi_handle, 6440 const struct ll_stats_set_params *set_req) 6441 { 6442 wmi_start_link_stats_cmd_fixed_param *cmd; 6443 int32_t len; 6444 wmi_buf_t buf; 6445 uint8_t *buf_ptr; 6446 int ret; 6447 6448 len = sizeof(*cmd); 6449 buf = wmi_buf_alloc(wmi_handle, len); 6450 6451 if (!buf) 6452 return QDF_STATUS_E_NOMEM; 6453 6454 buf_ptr = (uint8_t *) wmi_buf_data(buf); 6455 qdf_mem_zero(buf_ptr, len); 6456 cmd = (wmi_start_link_stats_cmd_fixed_param *) buf_ptr; 6457 6458 WMITLV_SET_HDR(&cmd->tlv_header, 6459 WMITLV_TAG_STRUC_wmi_start_link_stats_cmd_fixed_param, 6460 WMITLV_GET_STRUCT_TLVLEN 6461 (wmi_start_link_stats_cmd_fixed_param)); 6462 6463 cmd->mpdu_size_threshold = set_req->mpdu_size_threshold; 6464 cmd->aggressive_statistics_gathering = 6465 set_req->aggressive_statistics_gathering; 6466 6467 wmi_debug("LINK_LAYER_STATS - Start/Set Params MPDU Size Thresh : %d Aggressive Gather: %d", 6468 cmd->mpdu_size_threshold, 6469 cmd->aggressive_statistics_gathering); 6470 6471 wmi_mtrace(WMI_START_LINK_STATS_CMDID, NO_SESSION, 0); 6472 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 6473 WMI_START_LINK_STATS_CMDID); 6474 if (ret) { 6475 wmi_err("Failed to send set link stats request"); 6476 wmi_buf_free(buf); 6477 return QDF_STATUS_E_FAILURE; 6478 } 6479 6480 return QDF_STATUS_SUCCESS; 6481 } 6482 6483 /** 6484 * send_process_ll_stats_get_cmd_tlv() - link layer stats get request 6485 * @wmi_handle: wmi handle 6486 * @get_req: ll stats get request command params 6487 * 6488 * Return: QDF_STATUS_SUCCESS for success or error code 6489 */ 6490 static QDF_STATUS send_process_ll_stats_get_cmd_tlv(wmi_unified_t wmi_handle, 6491 const struct ll_stats_get_params *get_req) 6492 { 6493 wmi_request_link_stats_cmd_fixed_param *cmd; 6494 int32_t len; 6495 wmi_buf_t buf; 6496 uint8_t *buf_ptr; 6497 int ret; 6498 6499 len = sizeof(*cmd); 6500 buf = wmi_buf_alloc(wmi_handle, len); 6501 6502 if (!buf) 6503 return QDF_STATUS_E_NOMEM; 6504 6505 buf_ptr = (uint8_t *) wmi_buf_data(buf); 6506 qdf_mem_zero(buf_ptr, len); 6507 cmd = (wmi_request_link_stats_cmd_fixed_param *) buf_ptr; 6508 6509 WMITLV_SET_HDR(&cmd->tlv_header, 6510 WMITLV_TAG_STRUC_wmi_request_link_stats_cmd_fixed_param, 6511 WMITLV_GET_STRUCT_TLVLEN 6512 (wmi_request_link_stats_cmd_fixed_param)); 6513 6514 cmd->request_id = get_req->req_id; 6515 cmd->stats_type = get_req->param_id_mask; 6516 cmd->vdev_id = get_req->vdev_id; 6517 6518 WMI_CHAR_ARRAY_TO_MAC_ADDR(get_req->peer_macaddr.bytes, 6519 &cmd->peer_macaddr); 6520 6521 wmi_debug("LINK_LAYER_STATS - Get Request Params Request ID: %u Stats Type: %0x Vdev ID: %d Peer MAC Addr: "QDF_MAC_ADDR_FMT, 6522 cmd->request_id, cmd->stats_type, cmd->vdev_id, 6523 QDF_MAC_ADDR_REF(get_req->peer_macaddr.bytes)); 6524 6525 wmi_mtrace(WMI_REQUEST_LINK_STATS_CMDID, cmd->vdev_id, 0); 6526 ret = wmi_unified_cmd_send_pm_chk(wmi_handle, buf, len, 6527 WMI_REQUEST_LINK_STATS_CMDID, true); 6528 if (ret) { 6529 wmi_buf_free(buf); 6530 return QDF_STATUS_E_FAILURE; 6531 } 6532 6533 return QDF_STATUS_SUCCESS; 6534 } 6535 6536 #ifdef WLAN_FEATURE_11BE_MLO 6537 static int 6538 wmi_get_tlv_length_for_mlo_stats(const struct ll_stats_get_params *get_req) 6539 { 6540 int32_t len = 0; 6541 6542 /* In case of MLO connection, update the length of the buffer. 6543 * The wmi_inst_rssi_stats_params structure is not needed for MLO stats, 6544 * hence just update the TLV header, but allocate no memory for it. 6545 */ 6546 if (!get_req->is_mlo_req) 6547 return len; 6548 6549 len += WMI_TLV_HDR_SIZE + 0 * sizeof(wmi_inst_rssi_stats_params) + 6550 WMI_TLV_HDR_SIZE + 1 * sizeof(uint32_t) + 6551 WMI_TLV_HDR_SIZE + 1 * sizeof(wmi_mac_addr); 6552 6553 return len; 6554 } 6555 6556 static void 6557 wmi_update_tlv_headers_for_mlo_stats(const struct ll_stats_get_params *get_req, 6558 void *buf_ptr) 6559 { 6560 wmi_request_unified_ll_get_sta_cmd_fixed_param *unified_cmd; 6561 uint32_t *vdev_id_bitmap; 6562 wmi_mac_addr *mld_mac; 6563 6564 /* In case of MLO connection, update the TLV Headers */ 6565 if (!get_req->is_mlo_req) 6566 return; 6567 6568 buf_ptr += sizeof(*unified_cmd); 6569 6570 /* Fill TLV but no data for wmi_inst_rssi_stats_params */ 6571 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 0); 6572 buf_ptr += WMI_TLV_HDR_SIZE; 6573 6574 /* Adding vdev_bitmap_id array TLV */ 6575 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, 6576 sizeof(*vdev_id_bitmap)); 6577 buf_ptr += WMI_TLV_HDR_SIZE; 6578 vdev_id_bitmap = buf_ptr; 6579 *(vdev_id_bitmap) = get_req->vdev_id_bitmap; 6580 buf_ptr += sizeof(*vdev_id_bitmap); 6581 6582 /* Adding mld_macaddr array TLV */ 6583 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_FIXED_STRUC, 6584 sizeof(*mld_mac)); 6585 buf_ptr += WMI_TLV_HDR_SIZE; 6586 mld_mac = buf_ptr; 6587 WMI_CHAR_ARRAY_TO_MAC_ADDR(get_req->mld_macaddr.bytes, mld_mac); 6588 6589 wmi_debug("MLO vdev_id_bitmap: 0x%x MLD MAC Addr: " 6590 QDF_MAC_ADDR_FMT, get_req->vdev_id_bitmap, 6591 QDF_MAC_ADDR_REF(get_req->mld_macaddr.bytes)); 6592 } 6593 #else 6594 static inline int 6595 wmi_get_tlv_length_for_mlo_stats(const struct ll_stats_get_params *get_req) 6596 { 6597 return 0; 6598 } 6599 6600 static inline void 6601 wmi_update_tlv_headers_for_mlo_stats(const struct ll_stats_get_params *get_req, 6602 void *buf_ptr) 6603 { 6604 } 6605 #endif 6606 6607 #ifdef FEATURE_CLUB_LL_STATS_AND_GET_STATION 6608 /** 6609 * send_unified_ll_stats_get_sta_cmd_tlv() - unified link layer stats and get 6610 * station request 6611 * @wmi_handle: wmi handle 6612 * @get_req: ll stats get request command params 6613 * 6614 * Return: QDF_STATUS_SUCCESS for success or error code 6615 */ 6616 static QDF_STATUS send_unified_ll_stats_get_sta_cmd_tlv( 6617 wmi_unified_t wmi_handle, 6618 const struct ll_stats_get_params *get_req) 6619 { 6620 wmi_request_unified_ll_get_sta_cmd_fixed_param *unified_cmd; 6621 int32_t len; 6622 wmi_buf_t buf; 6623 void *buf_ptr; 6624 QDF_STATUS ret; 6625 bool is_ll_get_sta_stats_over_qmi; 6626 6627 len = sizeof(*unified_cmd); 6628 len += wmi_get_tlv_length_for_mlo_stats(get_req); 6629 6630 buf = wmi_buf_alloc(wmi_handle, len); 6631 if (!buf) 6632 return QDF_STATUS_E_NOMEM; 6633 6634 buf_ptr = wmi_buf_data(buf); 6635 6636 unified_cmd = buf_ptr; 6637 WMITLV_SET_HDR( 6638 &unified_cmd->tlv_header, 6639 WMITLV_TAG_STRUC_wmi_request_unified_ll_get_sta_cmd_fixed_param, 6640 WMITLV_GET_STRUCT_TLVLEN 6641 (wmi_request_unified_ll_get_sta_cmd_fixed_param)); 6642 6643 unified_cmd->link_stats_type = get_req->param_id_mask; 6644 unified_cmd->get_sta_stats_id = (WMI_REQUEST_AP_STAT | 6645 WMI_REQUEST_PEER_STAT | 6646 WMI_REQUEST_VDEV_STAT | 6647 WMI_REQUEST_PDEV_STAT | 6648 WMI_REQUEST_PEER_EXTD2_STAT | 6649 WMI_REQUEST_RSSI_PER_CHAIN_STAT); 6650 unified_cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 6651 wmi_handle, 6652 WMI_HOST_PDEV_ID_SOC); 6653 6654 unified_cmd->vdev_id = get_req->vdev_id; 6655 unified_cmd->request_id = get_req->req_id; 6656 WMI_CHAR_ARRAY_TO_MAC_ADDR(get_req->peer_macaddr.bytes, 6657 &unified_cmd->peer_macaddr); 6658 6659 wmi_debug("UNIFIED_LINK_STATS_GET_STA - Get Request Params Request ID: %u Stats Type: %0x Vdev ID: %d Peer MAC Addr: " 6660 QDF_MAC_ADDR_FMT, 6661 get_req->req_id, get_req->param_id_mask, get_req->vdev_id, 6662 QDF_MAC_ADDR_REF(get_req->peer_macaddr.bytes)); 6663 6664 wmi_update_tlv_headers_for_mlo_stats(get_req, buf_ptr); 6665 wmi_mtrace(WMI_REQUEST_UNIFIED_LL_GET_STA_CMDID, get_req->vdev_id, 0); 6666 6667 /** 6668 * FW support for LL_get_sta command. True represents the unified 6669 * ll_get_sta command should be sent over QMI always irrespective of 6670 * WOW state. 6671 */ 6672 is_ll_get_sta_stats_over_qmi = is_service_enabled_tlv( 6673 wmi_handle, 6674 WMI_SERVICE_UNIFIED_LL_GET_STA_OVER_QMI_SUPPORT); 6675 6676 if (is_ll_get_sta_stats_over_qmi) { 6677 ret = wmi_unified_cmd_send_over_qmi( 6678 wmi_handle, buf, len, 6679 WMI_REQUEST_UNIFIED_LL_GET_STA_CMDID); 6680 } else { 6681 ret = wmi_unified_cmd_send_pm_chk( 6682 wmi_handle, buf, len, 6683 WMI_REQUEST_UNIFIED_LL_GET_STA_CMDID, 6684 true); 6685 } 6686 6687 if (QDF_IS_STATUS_ERROR(ret)) { 6688 wmi_buf_free(buf); 6689 return QDF_STATUS_E_FAILURE; 6690 } 6691 6692 return ret; 6693 } 6694 #endif 6695 #endif /* WLAN_FEATURE_LINK_LAYER_STATS */ 6696 6697 /** 6698 * send_congestion_cmd_tlv() - send request to fw to get CCA 6699 * @wmi_handle: wmi handle 6700 * @vdev_id: vdev id 6701 * 6702 * Return: CDF status 6703 */ 6704 static QDF_STATUS send_congestion_cmd_tlv(wmi_unified_t wmi_handle, 6705 uint8_t vdev_id) 6706 { 6707 wmi_buf_t buf; 6708 wmi_request_stats_cmd_fixed_param *cmd; 6709 uint8_t len; 6710 uint8_t *buf_ptr; 6711 6712 len = sizeof(*cmd); 6713 buf = wmi_buf_alloc(wmi_handle, len); 6714 if (!buf) 6715 return QDF_STATUS_E_FAILURE; 6716 6717 buf_ptr = wmi_buf_data(buf); 6718 cmd = (wmi_request_stats_cmd_fixed_param *)buf_ptr; 6719 WMITLV_SET_HDR(&cmd->tlv_header, 6720 WMITLV_TAG_STRUC_wmi_request_stats_cmd_fixed_param, 6721 WMITLV_GET_STRUCT_TLVLEN 6722 (wmi_request_stats_cmd_fixed_param)); 6723 6724 cmd->stats_id = WMI_REQUEST_CONGESTION_STAT; 6725 cmd->vdev_id = vdev_id; 6726 wmi_debug("STATS REQ VDEV_ID:%d stats_id %d -->", 6727 cmd->vdev_id, cmd->stats_id); 6728 6729 wmi_mtrace(WMI_REQUEST_STATS_CMDID, cmd->vdev_id, 0); 6730 if (wmi_unified_cmd_send(wmi_handle, buf, len, 6731 WMI_REQUEST_STATS_CMDID)) { 6732 wmi_err("Failed to send WMI_REQUEST_STATS_CMDID"); 6733 wmi_buf_free(buf); 6734 return QDF_STATUS_E_FAILURE; 6735 } 6736 6737 return QDF_STATUS_SUCCESS; 6738 } 6739 6740 /** 6741 * send_snr_request_cmd_tlv() - send request to fw to get RSSI stats 6742 * @wmi_handle: wmi handle 6743 * @rssi_req: get RSSI request 6744 * 6745 * Return: CDF status 6746 */ 6747 static QDF_STATUS send_snr_request_cmd_tlv(wmi_unified_t wmi_handle) 6748 { 6749 wmi_buf_t buf; 6750 wmi_request_stats_cmd_fixed_param *cmd; 6751 uint8_t len = sizeof(wmi_request_stats_cmd_fixed_param); 6752 6753 buf = wmi_buf_alloc(wmi_handle, len); 6754 if (!buf) 6755 return QDF_STATUS_E_FAILURE; 6756 6757 cmd = (wmi_request_stats_cmd_fixed_param *) wmi_buf_data(buf); 6758 WMITLV_SET_HDR(&cmd->tlv_header, 6759 WMITLV_TAG_STRUC_wmi_request_stats_cmd_fixed_param, 6760 WMITLV_GET_STRUCT_TLVLEN 6761 (wmi_request_stats_cmd_fixed_param)); 6762 cmd->stats_id = WMI_REQUEST_VDEV_STAT; 6763 wmi_mtrace(WMI_REQUEST_STATS_CMDID, cmd->vdev_id, 0); 6764 if (wmi_unified_cmd_send(wmi_handle, buf, len, 6765 WMI_REQUEST_STATS_CMDID)) { 6766 wmi_err("Failed to send host stats request to fw"); 6767 wmi_buf_free(buf); 6768 return QDF_STATUS_E_FAILURE; 6769 } 6770 6771 return QDF_STATUS_SUCCESS; 6772 } 6773 6774 /** 6775 * send_snr_cmd_tlv() - get RSSI from fw 6776 * @wmi_handle: wmi handle 6777 * @vdev_id: vdev id 6778 * 6779 * Return: CDF status 6780 */ 6781 static QDF_STATUS send_snr_cmd_tlv(wmi_unified_t wmi_handle, uint8_t vdev_id) 6782 { 6783 wmi_buf_t buf; 6784 wmi_request_stats_cmd_fixed_param *cmd; 6785 uint8_t len = sizeof(wmi_request_stats_cmd_fixed_param); 6786 6787 buf = wmi_buf_alloc(wmi_handle, len); 6788 if (!buf) 6789 return QDF_STATUS_E_FAILURE; 6790 6791 cmd = (wmi_request_stats_cmd_fixed_param *) wmi_buf_data(buf); 6792 cmd->vdev_id = vdev_id; 6793 6794 WMITLV_SET_HDR(&cmd->tlv_header, 6795 WMITLV_TAG_STRUC_wmi_request_stats_cmd_fixed_param, 6796 WMITLV_GET_STRUCT_TLVLEN 6797 (wmi_request_stats_cmd_fixed_param)); 6798 cmd->stats_id = WMI_REQUEST_VDEV_STAT; 6799 wmi_mtrace(WMI_REQUEST_STATS_CMDID, cmd->vdev_id, 0); 6800 if (wmi_unified_cmd_send(wmi_handle, buf, len, 6801 WMI_REQUEST_STATS_CMDID)) { 6802 wmi_err("Failed to send host stats request to fw"); 6803 wmi_buf_free(buf); 6804 return QDF_STATUS_E_FAILURE; 6805 } 6806 6807 return QDF_STATUS_SUCCESS; 6808 } 6809 6810 /** 6811 * send_link_status_req_cmd_tlv() - process link status request from UMAC 6812 * @wmi_handle: wmi handle 6813 * @link_status: get link params 6814 * 6815 * Return: CDF status 6816 */ 6817 static QDF_STATUS send_link_status_req_cmd_tlv(wmi_unified_t wmi_handle, 6818 struct link_status_params *link_status) 6819 { 6820 wmi_buf_t buf; 6821 wmi_request_stats_cmd_fixed_param *cmd; 6822 uint8_t len = sizeof(wmi_request_stats_cmd_fixed_param); 6823 6824 buf = wmi_buf_alloc(wmi_handle, len); 6825 if (!buf) 6826 return QDF_STATUS_E_FAILURE; 6827 6828 cmd = (wmi_request_stats_cmd_fixed_param *) wmi_buf_data(buf); 6829 WMITLV_SET_HDR(&cmd->tlv_header, 6830 WMITLV_TAG_STRUC_wmi_request_stats_cmd_fixed_param, 6831 WMITLV_GET_STRUCT_TLVLEN 6832 (wmi_request_stats_cmd_fixed_param)); 6833 cmd->stats_id = WMI_REQUEST_VDEV_RATE_STAT; 6834 cmd->vdev_id = link_status->vdev_id; 6835 wmi_mtrace(WMI_REQUEST_STATS_CMDID, cmd->vdev_id, 0); 6836 if (wmi_unified_cmd_send(wmi_handle, buf, len, 6837 WMI_REQUEST_STATS_CMDID)) { 6838 wmi_err("Failed to send WMI link status request to fw"); 6839 wmi_buf_free(buf); 6840 return QDF_STATUS_E_FAILURE; 6841 } 6842 6843 return QDF_STATUS_SUCCESS; 6844 } 6845 6846 #ifdef WLAN_SUPPORT_GREEN_AP 6847 /** 6848 * send_egap_conf_params_cmd_tlv() - send wmi cmd of egap configuration params 6849 * @wmi_handle: wmi handler 6850 * @egap_params: pointer to egap_params 6851 * 6852 * Return: 0 for success, otherwise appropriate error code 6853 */ 6854 static QDF_STATUS send_egap_conf_params_cmd_tlv(wmi_unified_t wmi_handle, 6855 struct wlan_green_ap_egap_params *egap_params) 6856 { 6857 wmi_ap_ps_egap_param_cmd_fixed_param *cmd; 6858 wmi_buf_t buf; 6859 int32_t err; 6860 6861 buf = wmi_buf_alloc(wmi_handle, sizeof(*cmd)); 6862 if (!buf) 6863 return QDF_STATUS_E_NOMEM; 6864 6865 cmd = (wmi_ap_ps_egap_param_cmd_fixed_param *) wmi_buf_data(buf); 6866 WMITLV_SET_HDR(&cmd->tlv_header, 6867 WMITLV_TAG_STRUC_wmi_ap_ps_egap_param_cmd_fixed_param, 6868 WMITLV_GET_STRUCT_TLVLEN( 6869 wmi_ap_ps_egap_param_cmd_fixed_param)); 6870 6871 cmd->enable = egap_params->host_enable_egap; 6872 cmd->inactivity_time = egap_params->egap_inactivity_time; 6873 cmd->wait_time = egap_params->egap_wait_time; 6874 cmd->flags = egap_params->egap_feature_flags; 6875 wmi_mtrace(WMI_AP_PS_EGAP_PARAM_CMDID, NO_SESSION, 0); 6876 err = wmi_unified_cmd_send(wmi_handle, buf, 6877 sizeof(*cmd), WMI_AP_PS_EGAP_PARAM_CMDID); 6878 if (err) { 6879 wmi_err("Failed to send ap_ps_egap cmd"); 6880 wmi_buf_free(buf); 6881 return QDF_STATUS_E_FAILURE; 6882 } 6883 6884 return QDF_STATUS_SUCCESS; 6885 } 6886 #endif 6887 6888 /** 6889 * wmi_unified_csa_offload_enable() - sen CSA offload enable command 6890 * @wmi_handle: wmi handle 6891 * @vdev_id: vdev id 6892 * 6893 * Return: QDF_STATUS_SUCCESS for success or error code 6894 */ 6895 static QDF_STATUS send_csa_offload_enable_cmd_tlv(wmi_unified_t wmi_handle, 6896 uint8_t vdev_id) 6897 { 6898 wmi_csa_offload_enable_cmd_fixed_param *cmd; 6899 wmi_buf_t buf; 6900 int32_t len = sizeof(*cmd); 6901 6902 wmi_debug("vdev_id %d", vdev_id); 6903 buf = wmi_buf_alloc(wmi_handle, len); 6904 if (!buf) 6905 return QDF_STATUS_E_NOMEM; 6906 6907 cmd = (wmi_csa_offload_enable_cmd_fixed_param *) wmi_buf_data(buf); 6908 WMITLV_SET_HDR(&cmd->tlv_header, 6909 WMITLV_TAG_STRUC_wmi_csa_offload_enable_cmd_fixed_param, 6910 WMITLV_GET_STRUCT_TLVLEN 6911 (wmi_csa_offload_enable_cmd_fixed_param)); 6912 cmd->vdev_id = vdev_id; 6913 cmd->csa_offload_enable = WMI_CSA_OFFLOAD_ENABLE; 6914 wmi_mtrace(WMI_CSA_OFFLOAD_ENABLE_CMDID, cmd->vdev_id, 0); 6915 if (wmi_unified_cmd_send(wmi_handle, buf, len, 6916 WMI_CSA_OFFLOAD_ENABLE_CMDID)) { 6917 wmi_err("Failed to send CSA offload enable command"); 6918 wmi_buf_free(buf); 6919 return QDF_STATUS_E_FAILURE; 6920 } 6921 6922 return 0; 6923 } 6924 6925 #ifdef WLAN_FEATURE_CIF_CFR 6926 /** 6927 * send_oem_dma_cfg_cmd_tlv() - configure OEM DMA rings 6928 * @wmi_handle: wmi handle 6929 * @data_len: len of dma cfg req 6930 * @data: dma cfg req 6931 * 6932 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_FAILURE for failure 6933 */ 6934 static QDF_STATUS send_oem_dma_cfg_cmd_tlv(wmi_unified_t wmi_handle, 6935 wmi_oem_dma_ring_cfg_req_fixed_param *cfg) 6936 { 6937 wmi_buf_t buf; 6938 uint8_t *cmd; 6939 QDF_STATUS ret; 6940 6941 WMITLV_SET_HDR(cfg, 6942 WMITLV_TAG_STRUC_wmi_oem_dma_ring_cfg_req_fixed_param, 6943 (sizeof(*cfg) - WMI_TLV_HDR_SIZE)); 6944 6945 buf = wmi_buf_alloc(wmi_handle, sizeof(*cfg)); 6946 if (!buf) 6947 return QDF_STATUS_E_FAILURE; 6948 6949 cmd = (uint8_t *) wmi_buf_data(buf); 6950 qdf_mem_copy(cmd, cfg, sizeof(*cfg)); 6951 wmi_debug("Sending OEM Data Request to target, data len %lu", 6952 sizeof(*cfg)); 6953 wmi_mtrace(WMI_OEM_DMA_RING_CFG_REQ_CMDID, NO_SESSION, 0); 6954 ret = wmi_unified_cmd_send(wmi_handle, buf, sizeof(*cfg), 6955 WMI_OEM_DMA_RING_CFG_REQ_CMDID); 6956 if (QDF_IS_STATUS_ERROR(ret)) { 6957 wmi_err("Failed to send WMI_OEM_DMA_RING_CFG_REQ_CMDID"); 6958 wmi_buf_free(buf); 6959 } 6960 6961 return ret; 6962 } 6963 #endif 6964 6965 /** 6966 * send_start_11d_scan_cmd_tlv() - start 11d scan request 6967 * @wmi_handle: wmi handle 6968 * @start_11d_scan: 11d scan start request parameters 6969 * 6970 * This function request FW to start 11d scan. 6971 * 6972 * Return: QDF status 6973 */ 6974 static QDF_STATUS send_start_11d_scan_cmd_tlv(wmi_unified_t wmi_handle, 6975 struct reg_start_11d_scan_req *start_11d_scan) 6976 { 6977 wmi_11d_scan_start_cmd_fixed_param *cmd; 6978 int32_t len; 6979 wmi_buf_t buf; 6980 int ret; 6981 6982 len = sizeof(*cmd); 6983 buf = wmi_buf_alloc(wmi_handle, len); 6984 if (!buf) 6985 return QDF_STATUS_E_NOMEM; 6986 6987 cmd = (wmi_11d_scan_start_cmd_fixed_param *)wmi_buf_data(buf); 6988 6989 WMITLV_SET_HDR(&cmd->tlv_header, 6990 WMITLV_TAG_STRUC_wmi_11d_scan_start_cmd_fixed_param, 6991 WMITLV_GET_STRUCT_TLVLEN 6992 (wmi_11d_scan_start_cmd_fixed_param)); 6993 6994 cmd->vdev_id = start_11d_scan->vdev_id; 6995 cmd->scan_period_msec = start_11d_scan->scan_period_msec; 6996 cmd->start_interval_msec = start_11d_scan->start_interval_msec; 6997 6998 wmi_debug("vdev %d sending 11D scan start req", cmd->vdev_id); 6999 7000 wmi_mtrace(WMI_11D_SCAN_START_CMDID, cmd->vdev_id, 0); 7001 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 7002 WMI_11D_SCAN_START_CMDID); 7003 if (ret) { 7004 wmi_err("Failed to send start 11d scan wmi cmd"); 7005 wmi_buf_free(buf); 7006 return QDF_STATUS_E_FAILURE; 7007 } 7008 7009 return QDF_STATUS_SUCCESS; 7010 } 7011 7012 /** 7013 * send_stop_11d_scan_cmd_tlv() - stop 11d scan request 7014 * @wmi_handle: wmi handle 7015 * @start_11d_scan: 11d scan stop request parameters 7016 * 7017 * This function request FW to stop 11d scan. 7018 * 7019 * Return: QDF status 7020 */ 7021 static QDF_STATUS send_stop_11d_scan_cmd_tlv(wmi_unified_t wmi_handle, 7022 struct reg_stop_11d_scan_req *stop_11d_scan) 7023 { 7024 wmi_11d_scan_stop_cmd_fixed_param *cmd; 7025 int32_t len; 7026 wmi_buf_t buf; 7027 int ret; 7028 7029 len = sizeof(*cmd); 7030 buf = wmi_buf_alloc(wmi_handle, len); 7031 if (!buf) 7032 return QDF_STATUS_E_NOMEM; 7033 7034 cmd = (wmi_11d_scan_stop_cmd_fixed_param *)wmi_buf_data(buf); 7035 7036 WMITLV_SET_HDR(&cmd->tlv_header, 7037 WMITLV_TAG_STRUC_wmi_11d_scan_stop_cmd_fixed_param, 7038 WMITLV_GET_STRUCT_TLVLEN 7039 (wmi_11d_scan_stop_cmd_fixed_param)); 7040 7041 cmd->vdev_id = stop_11d_scan->vdev_id; 7042 7043 wmi_debug("vdev %d sending 11D scan stop req", cmd->vdev_id); 7044 7045 wmi_mtrace(WMI_11D_SCAN_STOP_CMDID, cmd->vdev_id, 0); 7046 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 7047 WMI_11D_SCAN_STOP_CMDID); 7048 if (ret) { 7049 wmi_err("Failed to send stop 11d scan wmi cmd"); 7050 wmi_buf_free(buf); 7051 return QDF_STATUS_E_FAILURE; 7052 } 7053 7054 return QDF_STATUS_SUCCESS; 7055 } 7056 7057 /** 7058 * send_start_oem_data_cmd_tlv() - start OEM data request to target 7059 * @wmi_handle: wmi handle 7060 * @data_len: the length of @data 7061 * @data: the pointer to data buf 7062 * 7063 * Return: CDF status 7064 */ 7065 static QDF_STATUS send_start_oem_data_cmd_tlv(wmi_unified_t wmi_handle, 7066 uint32_t data_len, 7067 uint8_t *data) 7068 { 7069 wmi_buf_t buf; 7070 uint8_t *cmd; 7071 QDF_STATUS ret; 7072 7073 buf = wmi_buf_alloc(wmi_handle, 7074 (data_len + WMI_TLV_HDR_SIZE)); 7075 if (!buf) 7076 return QDF_STATUS_E_FAILURE; 7077 7078 cmd = (uint8_t *) wmi_buf_data(buf); 7079 7080 WMITLV_SET_HDR(cmd, WMITLV_TAG_ARRAY_BYTE, data_len); 7081 cmd += WMI_TLV_HDR_SIZE; 7082 qdf_mem_copy(cmd, data, 7083 data_len); 7084 7085 wmi_debug("Sending OEM Data Request to target, data len %d", data_len); 7086 7087 wmi_mtrace(WMI_OEM_REQ_CMDID, NO_SESSION, 0); 7088 ret = wmi_unified_cmd_send(wmi_handle, buf, 7089 (data_len + 7090 WMI_TLV_HDR_SIZE), WMI_OEM_REQ_CMDID); 7091 7092 if (QDF_IS_STATUS_ERROR(ret)) { 7093 wmi_err("Failed to send WMI_OEM_REQ_CMDID"); 7094 wmi_buf_free(buf); 7095 } 7096 7097 return ret; 7098 } 7099 7100 #ifdef FEATURE_OEM_DATA 7101 /** 7102 * send_start_oemv2_data_cmd_tlv() - start OEM data to target 7103 * @wmi_handle: wmi handle 7104 * @oem_data: the pointer to oem data 7105 * 7106 * Return: QDF status 7107 */ 7108 static QDF_STATUS send_start_oemv2_data_cmd_tlv(wmi_unified_t wmi_handle, 7109 struct oem_data *oem_data) 7110 { 7111 QDF_STATUS ret; 7112 wmi_oem_data_cmd_fixed_param *cmd; 7113 struct wmi_ops *ops; 7114 wmi_buf_t buf; 7115 uint16_t len = sizeof(*cmd); 7116 uint16_t oem_data_len_aligned; 7117 uint8_t *buf_ptr; 7118 uint32_t pdev_id; 7119 7120 if (!oem_data || !oem_data->data) { 7121 wmi_err_rl("oem data is not valid"); 7122 return QDF_STATUS_E_FAILURE; 7123 } 7124 7125 oem_data_len_aligned = roundup(oem_data->data_len, sizeof(uint32_t)); 7126 if (oem_data_len_aligned < oem_data->data_len) { 7127 wmi_err_rl("integer overflow while rounding up data_len"); 7128 return QDF_STATUS_E_FAILURE; 7129 } 7130 7131 if (oem_data_len_aligned > WMI_SVC_MSG_MAX_SIZE - WMI_TLV_HDR_SIZE) { 7132 wmi_err_rl("wmi_max_msg_size overflow for given data_len"); 7133 return QDF_STATUS_E_FAILURE; 7134 } 7135 7136 len += WMI_TLV_HDR_SIZE + oem_data_len_aligned; 7137 buf = wmi_buf_alloc(wmi_handle, len); 7138 if (!buf) 7139 return QDF_STATUS_E_NOMEM; 7140 7141 buf_ptr = (uint8_t *)wmi_buf_data(buf); 7142 cmd = (wmi_oem_data_cmd_fixed_param *)buf_ptr; 7143 WMITLV_SET_HDR(&cmd->tlv_header, 7144 WMITLV_TAG_STRUC_wmi_oem_data_cmd_fixed_param, 7145 WMITLV_GET_STRUCT_TLVLEN(wmi_oem_data_cmd_fixed_param)); 7146 7147 pdev_id = oem_data->pdev_id; 7148 if (oem_data->pdev_vdev_flag) { 7149 ops = wmi_handle->ops; 7150 if (oem_data->is_host_pdev_id) 7151 pdev_id = 7152 ops->convert_host_pdev_id_to_target(wmi_handle, 7153 pdev_id); 7154 else 7155 pdev_id = 7156 ops->convert_pdev_id_host_to_target(wmi_handle, 7157 pdev_id); 7158 } 7159 7160 cmd->vdev_id = oem_data->vdev_id; 7161 cmd->data_len = oem_data->data_len; 7162 cmd->pdev_vdev_flag = oem_data->pdev_vdev_flag; 7163 cmd->pdev_id = pdev_id; 7164 7165 buf_ptr += sizeof(*cmd); 7166 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, oem_data_len_aligned); 7167 buf_ptr += WMI_TLV_HDR_SIZE; 7168 qdf_mem_copy(buf_ptr, oem_data->data, oem_data->data_len); 7169 7170 wmi_mtrace(WMI_OEM_DATA_CMDID, NO_SESSION, 0); 7171 ret = wmi_unified_cmd_send(wmi_handle, buf, len, WMI_OEM_DATA_CMDID); 7172 if (QDF_IS_STATUS_ERROR(ret)) { 7173 wmi_err_rl("Failed with ret = %d", ret); 7174 wmi_buf_free(buf); 7175 } 7176 7177 return ret; 7178 } 7179 #endif 7180 7181 /** 7182 * send_dfs_phyerr_filter_offload_en_cmd_tlv() - enable dfs phyerr filter 7183 * @wmi_handle: wmi handle 7184 * @dfs_phyerr_filter_offload: is dfs phyerr filter offload 7185 * 7186 * Send WMI_DFS_PHYERR_FILTER_ENA_CMDID or 7187 * WMI_DFS_PHYERR_FILTER_DIS_CMDID command 7188 * to firmware based on phyerr filtering 7189 * offload status. 7190 * 7191 * Return: 1 success, 0 failure 7192 */ 7193 static QDF_STATUS 7194 send_dfs_phyerr_filter_offload_en_cmd_tlv(wmi_unified_t wmi_handle, 7195 bool dfs_phyerr_filter_offload) 7196 { 7197 wmi_dfs_phyerr_filter_ena_cmd_fixed_param *enable_phyerr_offload_cmd; 7198 wmi_dfs_phyerr_filter_dis_cmd_fixed_param *disable_phyerr_offload_cmd; 7199 wmi_buf_t buf; 7200 uint16_t len; 7201 QDF_STATUS ret; 7202 7203 7204 if (false == dfs_phyerr_filter_offload) { 7205 wmi_debug("Phyerror Filtering offload is Disabled in ini"); 7206 len = sizeof(*disable_phyerr_offload_cmd); 7207 buf = wmi_buf_alloc(wmi_handle, len); 7208 if (!buf) 7209 return 0; 7210 7211 disable_phyerr_offload_cmd = 7212 (wmi_dfs_phyerr_filter_dis_cmd_fixed_param *) 7213 wmi_buf_data(buf); 7214 7215 WMITLV_SET_HDR(&disable_phyerr_offload_cmd->tlv_header, 7216 WMITLV_TAG_STRUC_wmi_dfs_phyerr_filter_dis_cmd_fixed_param, 7217 WMITLV_GET_STRUCT_TLVLEN 7218 (wmi_dfs_phyerr_filter_dis_cmd_fixed_param)); 7219 7220 /* 7221 * Send WMI_DFS_PHYERR_FILTER_DIS_CMDID 7222 * to the firmware to disable the phyerror 7223 * filtering offload. 7224 */ 7225 wmi_mtrace(WMI_DFS_PHYERR_FILTER_DIS_CMDID, NO_SESSION, 0); 7226 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 7227 WMI_DFS_PHYERR_FILTER_DIS_CMDID); 7228 if (QDF_IS_STATUS_ERROR(ret)) { 7229 wmi_err("Failed to send WMI_DFS_PHYERR_FILTER_DIS_CMDID ret=%d", 7230 ret); 7231 wmi_buf_free(buf); 7232 return QDF_STATUS_E_FAILURE; 7233 } 7234 wmi_debug("WMI_DFS_PHYERR_FILTER_DIS_CMDID Send Success"); 7235 } else { 7236 wmi_debug("Phyerror Filtering offload is Enabled in ini"); 7237 7238 len = sizeof(*enable_phyerr_offload_cmd); 7239 buf = wmi_buf_alloc(wmi_handle, len); 7240 if (!buf) 7241 return QDF_STATUS_E_FAILURE; 7242 7243 enable_phyerr_offload_cmd = 7244 (wmi_dfs_phyerr_filter_ena_cmd_fixed_param *) 7245 wmi_buf_data(buf); 7246 7247 WMITLV_SET_HDR(&enable_phyerr_offload_cmd->tlv_header, 7248 WMITLV_TAG_STRUC_wmi_dfs_phyerr_filter_ena_cmd_fixed_param, 7249 WMITLV_GET_STRUCT_TLVLEN 7250 (wmi_dfs_phyerr_filter_ena_cmd_fixed_param)); 7251 7252 /* 7253 * Send a WMI_DFS_PHYERR_FILTER_ENA_CMDID 7254 * to the firmware to enable the phyerror 7255 * filtering offload. 7256 */ 7257 wmi_mtrace(WMI_DFS_PHYERR_FILTER_ENA_CMDID, NO_SESSION, 0); 7258 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 7259 WMI_DFS_PHYERR_FILTER_ENA_CMDID); 7260 7261 if (QDF_IS_STATUS_ERROR(ret)) { 7262 wmi_err("Failed to send DFS PHYERR CMD ret=%d", ret); 7263 wmi_buf_free(buf); 7264 return QDF_STATUS_E_FAILURE; 7265 } 7266 wmi_debug("WMI_DFS_PHYERR_FILTER_ENA_CMDID Send Success"); 7267 } 7268 7269 return QDF_STATUS_SUCCESS; 7270 } 7271 7272 #if !defined(REMOVE_PKT_LOG) && defined(FEATURE_PKTLOG) 7273 /** 7274 * send_pktlog_wmi_send_cmd_tlv() - send pktlog enable/disable command to target 7275 * @wmi_handle: wmi handle 7276 * @pktlog_event: pktlog event 7277 * @cmd_id: pktlog cmd id 7278 * @user_triggered: user triggered input for PKTLOG enable mode 7279 * 7280 * Return: CDF status 7281 */ 7282 static QDF_STATUS send_pktlog_wmi_send_cmd_tlv(wmi_unified_t wmi_handle, 7283 WMI_PKTLOG_EVENT pktlog_event, 7284 WMI_CMD_ID cmd_id, uint8_t user_triggered) 7285 { 7286 WMI_PKTLOG_EVENT PKTLOG_EVENT; 7287 WMI_CMD_ID CMD_ID; 7288 wmi_pdev_pktlog_enable_cmd_fixed_param *cmd; 7289 wmi_pdev_pktlog_disable_cmd_fixed_param *disable_cmd; 7290 int len = 0; 7291 wmi_buf_t buf; 7292 int32_t idx, max_idx; 7293 7294 PKTLOG_EVENT = pktlog_event; 7295 CMD_ID = cmd_id; 7296 7297 max_idx = sizeof(pktlog_event_tlv) / (sizeof(pktlog_event_tlv[0])); 7298 switch (CMD_ID) { 7299 case WMI_PDEV_PKTLOG_ENABLE_CMDID: 7300 len = sizeof(*cmd); 7301 buf = wmi_buf_alloc(wmi_handle, len); 7302 if (!buf) 7303 return QDF_STATUS_E_NOMEM; 7304 7305 cmd = (wmi_pdev_pktlog_enable_cmd_fixed_param *) 7306 wmi_buf_data(buf); 7307 WMITLV_SET_HDR(&cmd->tlv_header, 7308 WMITLV_TAG_STRUC_wmi_pdev_pktlog_enable_cmd_fixed_param, 7309 WMITLV_GET_STRUCT_TLVLEN 7310 (wmi_pdev_pktlog_enable_cmd_fixed_param)); 7311 cmd->evlist = 0; 7312 for (idx = 0; idx < max_idx; idx++) { 7313 if (PKTLOG_EVENT & (1 << idx)) 7314 cmd->evlist |= pktlog_event_tlv[idx]; 7315 } 7316 cmd->enable = user_triggered ? WMI_PKTLOG_ENABLE_FORCE 7317 : WMI_PKTLOG_ENABLE_AUTO; 7318 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 7319 wmi_handle, 7320 WMI_HOST_PDEV_ID_SOC); 7321 wmi_mtrace(WMI_PDEV_PKTLOG_ENABLE_CMDID, NO_SESSION, 0); 7322 if (wmi_unified_cmd_send(wmi_handle, buf, len, 7323 WMI_PDEV_PKTLOG_ENABLE_CMDID)) { 7324 wmi_err("Failed to send pktlog enable cmdid"); 7325 goto wmi_send_failed; 7326 } 7327 break; 7328 case WMI_PDEV_PKTLOG_DISABLE_CMDID: 7329 len = sizeof(*disable_cmd); 7330 buf = wmi_buf_alloc(wmi_handle, len); 7331 if (!buf) 7332 return QDF_STATUS_E_NOMEM; 7333 7334 disable_cmd = (wmi_pdev_pktlog_disable_cmd_fixed_param *) 7335 wmi_buf_data(buf); 7336 WMITLV_SET_HDR(&disable_cmd->tlv_header, 7337 WMITLV_TAG_STRUC_wmi_pdev_pktlog_disable_cmd_fixed_param, 7338 WMITLV_GET_STRUCT_TLVLEN 7339 (wmi_pdev_pktlog_disable_cmd_fixed_param)); 7340 disable_cmd->pdev_id = 7341 wmi_handle->ops->convert_pdev_id_host_to_target( 7342 wmi_handle, 7343 WMI_HOST_PDEV_ID_SOC); 7344 wmi_mtrace(WMI_PDEV_PKTLOG_DISABLE_CMDID, NO_SESSION, 0); 7345 if (wmi_unified_cmd_send(wmi_handle, buf, len, 7346 WMI_PDEV_PKTLOG_DISABLE_CMDID)) { 7347 wmi_err("failed to send pktlog disable cmdid"); 7348 goto wmi_send_failed; 7349 } 7350 break; 7351 default: 7352 wmi_debug("Invalid PKTLOG command: %d", CMD_ID); 7353 break; 7354 } 7355 7356 return QDF_STATUS_SUCCESS; 7357 7358 wmi_send_failed: 7359 wmi_buf_free(buf); 7360 return QDF_STATUS_E_FAILURE; 7361 } 7362 #endif /* !REMOVE_PKT_LOG && FEATURE_PKTLOG */ 7363 7364 /** 7365 * send_stats_ext_req_cmd_tlv() - request ext stats from fw 7366 * @wmi_handle: wmi handle 7367 * @preq: stats ext params 7368 * 7369 * Return: CDF status 7370 */ 7371 static QDF_STATUS send_stats_ext_req_cmd_tlv(wmi_unified_t wmi_handle, 7372 struct stats_ext_params *preq) 7373 { 7374 QDF_STATUS ret; 7375 wmi_req_stats_ext_cmd_fixed_param *cmd; 7376 wmi_buf_t buf; 7377 size_t len; 7378 uint8_t *buf_ptr; 7379 uint16_t max_wmi_msg_size = wmi_get_max_msg_len(wmi_handle); 7380 uint32_t *vdev_bitmap; 7381 7382 if (preq->request_data_len > (max_wmi_msg_size - WMI_TLV_HDR_SIZE - 7383 sizeof(*cmd))) { 7384 wmi_err("Data length=%d is greater than max wmi msg size", 7385 preq->request_data_len); 7386 return QDF_STATUS_E_FAILURE; 7387 } 7388 7389 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE + preq->request_data_len + 7390 WMI_TLV_HDR_SIZE + sizeof(uint32_t); 7391 7392 buf = wmi_buf_alloc(wmi_handle, len); 7393 if (!buf) 7394 return QDF_STATUS_E_NOMEM; 7395 7396 buf_ptr = (uint8_t *) wmi_buf_data(buf); 7397 cmd = (wmi_req_stats_ext_cmd_fixed_param *) buf_ptr; 7398 7399 WMITLV_SET_HDR(&cmd->tlv_header, 7400 WMITLV_TAG_STRUC_wmi_req_stats_ext_cmd_fixed_param, 7401 WMITLV_GET_STRUCT_TLVLEN 7402 (wmi_req_stats_ext_cmd_fixed_param)); 7403 cmd->vdev_id = preq->vdev_id; 7404 cmd->data_len = preq->request_data_len; 7405 7406 wmi_debug("The data len value is %u and vdev id set is %u", 7407 preq->request_data_len, preq->vdev_id); 7408 7409 buf_ptr += sizeof(wmi_req_stats_ext_cmd_fixed_param); 7410 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, cmd->data_len); 7411 7412 buf_ptr += WMI_TLV_HDR_SIZE; 7413 qdf_mem_copy(buf_ptr, preq->request_data, cmd->data_len); 7414 7415 buf_ptr += cmd->data_len; 7416 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, sizeof(uint32_t)); 7417 7418 buf_ptr += WMI_TLV_HDR_SIZE; 7419 7420 vdev_bitmap = (A_UINT32 *)buf_ptr; 7421 7422 vdev_bitmap[0] = preq->vdev_id_bitmap; 7423 7424 wmi_debug("Sending MLO vdev_id_bitmap:%x", vdev_bitmap[0]); 7425 7426 buf_ptr += sizeof(uint32_t); 7427 7428 wmi_mtrace(WMI_REQUEST_STATS_EXT_CMDID, cmd->vdev_id, 0); 7429 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 7430 WMI_REQUEST_STATS_EXT_CMDID); 7431 if (QDF_IS_STATUS_ERROR(ret)) { 7432 wmi_err("Failed to send notify cmd ret = %d", ret); 7433 wmi_buf_free(buf); 7434 } 7435 7436 return ret; 7437 } 7438 7439 /** 7440 * send_process_dhcpserver_offload_cmd_tlv() - enable DHCP server offload 7441 * @wmi_handle: wmi handle 7442 * @params: DHCP server offload info 7443 * 7444 * Return: QDF_STATUS_SUCCESS for success or error code 7445 */ 7446 static QDF_STATUS 7447 send_process_dhcpserver_offload_cmd_tlv(wmi_unified_t wmi_handle, 7448 struct dhcp_offload_info_params *params) 7449 { 7450 wmi_set_dhcp_server_offload_cmd_fixed_param *cmd; 7451 wmi_buf_t buf; 7452 QDF_STATUS status; 7453 7454 buf = wmi_buf_alloc(wmi_handle, sizeof(*cmd)); 7455 if (!buf) 7456 return QDF_STATUS_E_NOMEM; 7457 7458 cmd = (wmi_set_dhcp_server_offload_cmd_fixed_param *) wmi_buf_data(buf); 7459 7460 WMITLV_SET_HDR(&cmd->tlv_header, 7461 WMITLV_TAG_STRUC_wmi_set_dhcp_server_offload_cmd_fixed_param, 7462 WMITLV_GET_STRUCT_TLVLEN 7463 (wmi_set_dhcp_server_offload_cmd_fixed_param)); 7464 cmd->vdev_id = params->vdev_id; 7465 cmd->enable = params->dhcp_offload_enabled; 7466 cmd->num_client = params->dhcp_client_num; 7467 cmd->srv_ipv4 = params->dhcp_srv_addr; 7468 cmd->start_lsb = 0; 7469 wmi_mtrace(WMI_SET_DHCP_SERVER_OFFLOAD_CMDID, cmd->vdev_id, 0); 7470 status = wmi_unified_cmd_send(wmi_handle, buf, 7471 sizeof(*cmd), 7472 WMI_SET_DHCP_SERVER_OFFLOAD_CMDID); 7473 if (QDF_IS_STATUS_ERROR(status)) { 7474 wmi_err("Failed to send set_dhcp_server_offload cmd"); 7475 wmi_buf_free(buf); 7476 return QDF_STATUS_E_FAILURE; 7477 } 7478 wmi_debug("Set dhcp server offload to vdevId %d", params->vdev_id); 7479 7480 return status; 7481 } 7482 7483 /** 7484 * send_pdev_set_regdomain_cmd_tlv() - send set regdomain command to fw 7485 * @wmi_handle: wmi handle 7486 * @param: pointer to pdev regdomain params 7487 * 7488 * Return: 0 for success or error code 7489 */ 7490 static QDF_STATUS 7491 send_pdev_set_regdomain_cmd_tlv(wmi_unified_t wmi_handle, 7492 struct pdev_set_regdomain_params *param) 7493 { 7494 wmi_buf_t buf; 7495 wmi_pdev_set_regdomain_cmd_fixed_param *cmd; 7496 int32_t len = sizeof(*cmd); 7497 7498 buf = wmi_buf_alloc(wmi_handle, len); 7499 if (!buf) 7500 return QDF_STATUS_E_NOMEM; 7501 7502 cmd = (wmi_pdev_set_regdomain_cmd_fixed_param *) wmi_buf_data(buf); 7503 WMITLV_SET_HDR(&cmd->tlv_header, 7504 WMITLV_TAG_STRUC_wmi_pdev_set_regdomain_cmd_fixed_param, 7505 WMITLV_GET_STRUCT_TLVLEN 7506 (wmi_pdev_set_regdomain_cmd_fixed_param)); 7507 7508 cmd->reg_domain = param->currentRDinuse; 7509 cmd->reg_domain_2G = param->currentRD2G; 7510 cmd->reg_domain_5G = param->currentRD5G; 7511 cmd->conformance_test_limit_2G = param->ctl_2G; 7512 cmd->conformance_test_limit_5G = param->ctl_5G; 7513 cmd->dfs_domain = param->dfsDomain; 7514 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 7515 wmi_handle, 7516 param->pdev_id); 7517 7518 wmi_mtrace(WMI_PDEV_SET_REGDOMAIN_CMDID, NO_SESSION, 0); 7519 if (wmi_unified_cmd_send(wmi_handle, buf, len, 7520 WMI_PDEV_SET_REGDOMAIN_CMDID)) { 7521 wmi_err("Failed to send pdev set regdomain command"); 7522 wmi_buf_free(buf); 7523 return QDF_STATUS_E_FAILURE; 7524 } 7525 7526 return QDF_STATUS_SUCCESS; 7527 } 7528 7529 /** 7530 * send_regdomain_info_to_fw_cmd_tlv() - send regdomain info to fw 7531 * @wmi_handle: wmi handle 7532 * @reg_dmn: reg domain 7533 * @regdmn2G: 2G reg domain 7534 * @regdmn5G: 5G reg domain 7535 * @ctl2G: 2G test limit 7536 * @ctl5G: 5G test limit 7537 * 7538 * Return: none 7539 */ 7540 static QDF_STATUS send_regdomain_info_to_fw_cmd_tlv(wmi_unified_t wmi_handle, 7541 uint32_t reg_dmn, uint16_t regdmn2G, 7542 uint16_t regdmn5G, uint8_t ctl2G, 7543 uint8_t ctl5G) 7544 { 7545 wmi_buf_t buf; 7546 wmi_pdev_set_regdomain_cmd_fixed_param *cmd; 7547 int32_t len = sizeof(*cmd); 7548 7549 7550 buf = wmi_buf_alloc(wmi_handle, len); 7551 if (!buf) 7552 return QDF_STATUS_E_NOMEM; 7553 7554 cmd = (wmi_pdev_set_regdomain_cmd_fixed_param *) wmi_buf_data(buf); 7555 WMITLV_SET_HDR(&cmd->tlv_header, 7556 WMITLV_TAG_STRUC_wmi_pdev_set_regdomain_cmd_fixed_param, 7557 WMITLV_GET_STRUCT_TLVLEN 7558 (wmi_pdev_set_regdomain_cmd_fixed_param)); 7559 cmd->reg_domain = reg_dmn; 7560 cmd->reg_domain_2G = regdmn2G; 7561 cmd->reg_domain_5G = regdmn5G; 7562 cmd->conformance_test_limit_2G = ctl2G; 7563 cmd->conformance_test_limit_5G = ctl5G; 7564 7565 wmi_debug("regd = %x, regd_2g = %x, regd_5g = %x, ctl_2g = %x, ctl_5g = %x", 7566 cmd->reg_domain, cmd->reg_domain_2G, cmd->reg_domain_5G, 7567 cmd->conformance_test_limit_2G, 7568 cmd->conformance_test_limit_5G); 7569 7570 wmi_mtrace(WMI_PDEV_SET_REGDOMAIN_CMDID, NO_SESSION, 0); 7571 if (wmi_unified_cmd_send(wmi_handle, buf, len, 7572 WMI_PDEV_SET_REGDOMAIN_CMDID)) { 7573 wmi_err("Failed to send pdev set regdomain command"); 7574 wmi_buf_free(buf); 7575 return QDF_STATUS_E_FAILURE; 7576 } 7577 7578 return QDF_STATUS_SUCCESS; 7579 } 7580 7581 /** 7582 * copy_custom_aggr_bitmap() - copies host side bitmap using FW APIs 7583 * @param: param sent from the host side 7584 * @cmd: param to be sent to the fw side 7585 */ 7586 static inline void copy_custom_aggr_bitmap( 7587 struct set_custom_aggr_size_params *param, 7588 wmi_vdev_set_custom_aggr_size_cmd_fixed_param *cmd) 7589 { 7590 WMI_VDEV_CUSTOM_AGGR_AC_SET(cmd->enable_bitmap, 7591 param->ac); 7592 WMI_VDEV_CUSTOM_AGGR_TYPE_SET(cmd->enable_bitmap, 7593 param->aggr_type); 7594 WMI_VDEV_CUSTOM_TX_AGGR_SZ_DIS_SET(cmd->enable_bitmap, 7595 param->tx_aggr_size_disable); 7596 WMI_VDEV_CUSTOM_RX_AGGR_SZ_DIS_SET(cmd->enable_bitmap, 7597 param->rx_aggr_size_disable); 7598 WMI_VDEV_CUSTOM_TX_AC_EN_SET(cmd->enable_bitmap, 7599 param->tx_ac_enable); 7600 WMI_VDEV_CUSTOM_AGGR_256_BA_EN_SET(cmd->enable_bitmap, 7601 param->aggr_ba_enable); 7602 } 7603 7604 /** 7605 * send_vdev_set_custom_aggr_size_cmd_tlv() - custom aggr size param in fw 7606 * @wmi_handle: wmi handle 7607 * @param: pointer to hold custom aggr size params 7608 * 7609 * @return QDF_STATUS_SUCCESS on success and -ve on failure. 7610 */ 7611 static QDF_STATUS send_vdev_set_custom_aggr_size_cmd_tlv( 7612 wmi_unified_t wmi_handle, 7613 struct set_custom_aggr_size_params *param) 7614 { 7615 wmi_vdev_set_custom_aggr_size_cmd_fixed_param *cmd; 7616 wmi_buf_t buf; 7617 int32_t len = sizeof(*cmd); 7618 7619 buf = wmi_buf_alloc(wmi_handle, len); 7620 if (!buf) 7621 return QDF_STATUS_E_FAILURE; 7622 7623 cmd = (wmi_vdev_set_custom_aggr_size_cmd_fixed_param *) 7624 wmi_buf_data(buf); 7625 WMITLV_SET_HDR(&cmd->tlv_header, 7626 WMITLV_TAG_STRUC_wmi_vdev_set_custom_aggr_size_cmd_fixed_param, 7627 WMITLV_GET_STRUCT_TLVLEN( 7628 wmi_vdev_set_custom_aggr_size_cmd_fixed_param)); 7629 cmd->vdev_id = param->vdev_id; 7630 cmd->tx_aggr_size = param->tx_aggr_size; 7631 cmd->rx_aggr_size = param->rx_aggr_size; 7632 copy_custom_aggr_bitmap(param, cmd); 7633 7634 wmi_debug("Set custom aggr: vdev id=0x%X, tx aggr size=0x%X " 7635 "rx_aggr_size=0x%X access category=0x%X, agg_type=0x%X " 7636 "tx_aggr_size_disable=0x%X, rx_aggr_size_disable=0x%X " 7637 "tx_ac_enable=0x%X", 7638 param->vdev_id, param->tx_aggr_size, param->rx_aggr_size, 7639 param->ac, param->aggr_type, param->tx_aggr_size_disable, 7640 param->rx_aggr_size_disable, param->tx_ac_enable); 7641 7642 wmi_mtrace(WMI_VDEV_SET_CUSTOM_AGGR_SIZE_CMDID, cmd->vdev_id, 0); 7643 if (wmi_unified_cmd_send(wmi_handle, buf, len, 7644 WMI_VDEV_SET_CUSTOM_AGGR_SIZE_CMDID)) { 7645 wmi_err("Setting custom aggregation size failed"); 7646 wmi_buf_free(buf); 7647 return QDF_STATUS_E_FAILURE; 7648 } 7649 7650 return QDF_STATUS_SUCCESS; 7651 } 7652 7653 /** 7654 * send_vdev_set_qdepth_thresh_cmd_tlv() - WMI set qdepth threshold 7655 * @param wmi_handle : handle to WMI. 7656 * @param param : pointer to tx antenna param 7657 * 7658 * @return QDF_STATUS_SUCCESS on success and -ve on failure. 7659 */ 7660 7661 static QDF_STATUS send_vdev_set_qdepth_thresh_cmd_tlv(wmi_unified_t wmi_handle, 7662 struct set_qdepth_thresh_params *param) 7663 { 7664 wmi_peer_tid_msduq_qdepth_thresh_update_cmd_fixed_param *cmd; 7665 wmi_msduq_qdepth_thresh_update *cmd_update; 7666 wmi_buf_t buf; 7667 int32_t len = 0; 7668 int i; 7669 uint8_t *buf_ptr; 7670 QDF_STATUS ret; 7671 7672 if (param->num_of_msduq_updates > QDEPTH_THRESH_MAX_UPDATES) { 7673 wmi_err("Invalid Update Count!"); 7674 return QDF_STATUS_E_INVAL; 7675 } 7676 7677 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE; 7678 len += (sizeof(wmi_msduq_qdepth_thresh_update) * 7679 param->num_of_msduq_updates); 7680 buf = wmi_buf_alloc(wmi_handle, len); 7681 7682 if (!buf) 7683 return QDF_STATUS_E_NOMEM; 7684 7685 buf_ptr = (uint8_t *)wmi_buf_data(buf); 7686 cmd = (wmi_peer_tid_msduq_qdepth_thresh_update_cmd_fixed_param *) 7687 buf_ptr; 7688 7689 WMITLV_SET_HDR(&cmd->tlv_header, 7690 WMITLV_TAG_STRUC_wmi_peer_tid_msduq_qdepth_thresh_update_cmd_fixed_param 7691 , WMITLV_GET_STRUCT_TLVLEN( 7692 wmi_peer_tid_msduq_qdepth_thresh_update_cmd_fixed_param)); 7693 7694 cmd->pdev_id = 7695 wmi_handle->ops->convert_pdev_id_host_to_target( 7696 wmi_handle, 7697 param->pdev_id); 7698 cmd->vdev_id = param->vdev_id; 7699 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->mac_addr, &cmd->peer_mac_address); 7700 cmd->num_of_msduq_updates = param->num_of_msduq_updates; 7701 7702 buf_ptr += sizeof( 7703 wmi_peer_tid_msduq_qdepth_thresh_update_cmd_fixed_param); 7704 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 7705 param->num_of_msduq_updates * 7706 sizeof(wmi_msduq_qdepth_thresh_update)); 7707 buf_ptr += WMI_TLV_HDR_SIZE; 7708 cmd_update = (wmi_msduq_qdepth_thresh_update *)buf_ptr; 7709 7710 for (i = 0; i < cmd->num_of_msduq_updates; i++) { 7711 WMITLV_SET_HDR(&cmd_update->tlv_header, 7712 WMITLV_TAG_STRUC_wmi_msduq_qdepth_thresh_update, 7713 WMITLV_GET_STRUCT_TLVLEN( 7714 wmi_msduq_qdepth_thresh_update)); 7715 cmd_update->tid_num = param->update_params[i].tid_num; 7716 cmd_update->msduq_update_mask = 7717 param->update_params[i].msduq_update_mask; 7718 cmd_update->qdepth_thresh_value = 7719 param->update_params[i].qdepth_thresh_value; 7720 wmi_debug("Set QDepth Threshold: vdev=0x%X pdev=0x%X, tid=0x%X " 7721 "mac_addr_upper4=%X, mac_addr_lower2:%X," 7722 " update mask=0x%X thresh val=0x%X", 7723 cmd->vdev_id, cmd->pdev_id, cmd_update->tid_num, 7724 cmd->peer_mac_address.mac_addr31to0, 7725 cmd->peer_mac_address.mac_addr47to32, 7726 cmd_update->msduq_update_mask, 7727 cmd_update->qdepth_thresh_value); 7728 cmd_update++; 7729 } 7730 7731 wmi_mtrace(WMI_PEER_TID_MSDUQ_QDEPTH_THRESH_UPDATE_CMDID, 7732 cmd->vdev_id, 0); 7733 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 7734 WMI_PEER_TID_MSDUQ_QDEPTH_THRESH_UPDATE_CMDID); 7735 7736 if (ret != 0) { 7737 wmi_err("Failed to send WMI_PEER_TID_MSDUQ_QDEPTH_THRESH_UPDATE_CMDID"); 7738 wmi_buf_free(buf); 7739 } 7740 7741 return ret; 7742 } 7743 7744 /** 7745 * send_set_vap_dscp_tid_map_cmd_tlv() - send vap dscp tid map cmd to fw 7746 * @wmi_handle: wmi handle 7747 * @param: pointer to hold vap dscp tid map param 7748 * 7749 * @return QDF_STATUS_SUCCESS on success and -ve on failure. 7750 */ 7751 static QDF_STATUS 7752 send_set_vap_dscp_tid_map_cmd_tlv(wmi_unified_t wmi_handle, 7753 struct vap_dscp_tid_map_params *param) 7754 { 7755 wmi_buf_t buf; 7756 wmi_vdev_set_dscp_tid_map_cmd_fixed_param *cmd; 7757 int32_t len = sizeof(*cmd); 7758 7759 buf = wmi_buf_alloc(wmi_handle, len); 7760 if (!buf) 7761 return QDF_STATUS_E_FAILURE; 7762 7763 cmd = (wmi_vdev_set_dscp_tid_map_cmd_fixed_param *)wmi_buf_data(buf); 7764 qdf_mem_copy(cmd->dscp_to_tid_map, param->dscp_to_tid_map, 7765 sizeof(uint32_t) * WMI_DSCP_MAP_MAX); 7766 7767 cmd->vdev_id = param->vdev_id; 7768 cmd->enable_override = 0; 7769 7770 wmi_debug("Setting dscp for vap id: %d", cmd->vdev_id); 7771 wmi_mtrace(WMI_VDEV_SET_DSCP_TID_MAP_CMDID, cmd->vdev_id, 0); 7772 if (wmi_unified_cmd_send(wmi_handle, buf, len, 7773 WMI_VDEV_SET_DSCP_TID_MAP_CMDID)) { 7774 wmi_err("Failed to set dscp cmd"); 7775 wmi_buf_free(buf); 7776 return QDF_STATUS_E_FAILURE; 7777 } 7778 7779 return QDF_STATUS_SUCCESS; 7780 } 7781 7782 /** 7783 * send_vdev_set_fwtest_param_cmd_tlv() - send fwtest param in fw 7784 * @wmi_handle: wmi handle 7785 * @param: pointer to hold fwtest param 7786 * 7787 * @return QDF_STATUS_SUCCESS on success and -ve on failure. 7788 */ 7789 static QDF_STATUS send_vdev_set_fwtest_param_cmd_tlv(wmi_unified_t wmi_handle, 7790 struct set_fwtest_params *param) 7791 { 7792 wmi_fwtest_set_param_cmd_fixed_param *cmd; 7793 wmi_buf_t buf; 7794 int32_t len = sizeof(*cmd); 7795 7796 buf = wmi_buf_alloc(wmi_handle, len); 7797 7798 if (!buf) 7799 return QDF_STATUS_E_FAILURE; 7800 7801 cmd = (wmi_fwtest_set_param_cmd_fixed_param *)wmi_buf_data(buf); 7802 WMITLV_SET_HDR(&cmd->tlv_header, 7803 WMITLV_TAG_STRUC_wmi_fwtest_set_param_cmd_fixed_param, 7804 WMITLV_GET_STRUCT_TLVLEN( 7805 wmi_fwtest_set_param_cmd_fixed_param)); 7806 cmd->param_id = param->arg; 7807 cmd->param_value = param->value; 7808 7809 wmi_mtrace(WMI_FWTEST_CMDID, NO_SESSION, 0); 7810 if (wmi_unified_cmd_send(wmi_handle, buf, len, WMI_FWTEST_CMDID)) { 7811 wmi_err("Setting FW test param failed"); 7812 wmi_buf_free(buf); 7813 return QDF_STATUS_E_FAILURE; 7814 } 7815 7816 return QDF_STATUS_SUCCESS; 7817 } 7818 7819 /** 7820 * send_phyerr_disable_cmd_tlv() - WMI phyerr disable function 7821 * 7822 * @param wmi_handle : handle to WMI. 7823 * @return QDF_STATUS_SUCCESS on success and -ve on failure. 7824 */ 7825 static QDF_STATUS send_phyerr_disable_cmd_tlv(wmi_unified_t wmi_handle) 7826 { 7827 wmi_pdev_dfs_disable_cmd_fixed_param *cmd; 7828 wmi_buf_t buf; 7829 QDF_STATUS ret; 7830 int32_t len; 7831 7832 len = sizeof(*cmd); 7833 7834 buf = wmi_buf_alloc(wmi_handle, len); 7835 if (!buf) 7836 return QDF_STATUS_E_FAILURE; 7837 7838 cmd = (wmi_pdev_dfs_disable_cmd_fixed_param *)wmi_buf_data(buf); 7839 WMITLV_SET_HDR(&cmd->tlv_header, 7840 WMITLV_TAG_STRUC_wmi_pdev_dfs_disable_cmd_fixed_param, 7841 WMITLV_GET_STRUCT_TLVLEN( 7842 wmi_pdev_dfs_disable_cmd_fixed_param)); 7843 /* Filling it with WMI_PDEV_ID_SOC for now */ 7844 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 7845 wmi_handle, 7846 WMI_HOST_PDEV_ID_SOC); 7847 7848 wmi_mtrace(WMI_PDEV_DFS_DISABLE_CMDID, NO_SESSION, 0); 7849 ret = wmi_unified_cmd_send(wmi_handle, buf, sizeof(*cmd), 7850 WMI_PDEV_DFS_DISABLE_CMDID); 7851 7852 if (ret != 0) { 7853 wmi_err("Sending PDEV DFS disable cmd failed"); 7854 wmi_buf_free(buf); 7855 } 7856 7857 return ret; 7858 } 7859 7860 /** 7861 * send_phyerr_enable_cmd_tlv() - WMI phyerr disable function 7862 * 7863 * @param wmi_handle : handle to WMI. 7864 * @return QDF_STATUS_SUCCESS on success and -ve on failure. 7865 */ 7866 static QDF_STATUS send_phyerr_enable_cmd_tlv(wmi_unified_t wmi_handle) 7867 { 7868 wmi_pdev_dfs_enable_cmd_fixed_param *cmd; 7869 wmi_buf_t buf; 7870 QDF_STATUS ret; 7871 int32_t len; 7872 7873 len = sizeof(*cmd); 7874 7875 buf = wmi_buf_alloc(wmi_handle, len); 7876 if (!buf) 7877 return QDF_STATUS_E_FAILURE; 7878 7879 cmd = (wmi_pdev_dfs_enable_cmd_fixed_param *)wmi_buf_data(buf); 7880 WMITLV_SET_HDR(&cmd->tlv_header, 7881 WMITLV_TAG_STRUC_wmi_pdev_dfs_enable_cmd_fixed_param, 7882 WMITLV_GET_STRUCT_TLVLEN( 7883 wmi_pdev_dfs_enable_cmd_fixed_param)); 7884 /* Reserved for future use */ 7885 cmd->reserved0 = 0; 7886 7887 wmi_mtrace(WMI_PDEV_DFS_ENABLE_CMDID, NO_SESSION, 0); 7888 ret = wmi_unified_cmd_send(wmi_handle, buf, sizeof(*cmd), 7889 WMI_PDEV_DFS_ENABLE_CMDID); 7890 7891 if (ret != 0) { 7892 wmi_err("Sending PDEV DFS enable cmd failed"); 7893 wmi_buf_free(buf); 7894 } 7895 7896 return ret; 7897 } 7898 7899 /** 7900 * send_periodic_chan_stats_config_cmd_tlv() - send periodic chan stats cmd 7901 * to fw 7902 * @wmi_handle: wmi handle 7903 * @param: pointer to hold periodic chan stats param 7904 * 7905 * Return: 0 for success or error code 7906 */ 7907 static QDF_STATUS 7908 send_periodic_chan_stats_config_cmd_tlv(wmi_unified_t wmi_handle, 7909 struct periodic_chan_stats_params *param) 7910 { 7911 wmi_set_periodic_channel_stats_config_fixed_param *cmd; 7912 wmi_buf_t buf; 7913 QDF_STATUS ret; 7914 int32_t len; 7915 7916 len = sizeof(*cmd); 7917 7918 buf = wmi_buf_alloc(wmi_handle, len); 7919 if (!buf) 7920 return QDF_STATUS_E_FAILURE; 7921 7922 cmd = (wmi_set_periodic_channel_stats_config_fixed_param *) 7923 wmi_buf_data(buf); 7924 WMITLV_SET_HDR(&cmd->tlv_header, 7925 WMITLV_TAG_STRUC_wmi_set_periodic_channel_stats_config_fixed_param, 7926 WMITLV_GET_STRUCT_TLVLEN( 7927 wmi_set_periodic_channel_stats_config_fixed_param)); 7928 cmd->enable = param->enable; 7929 cmd->stats_period = param->stats_period; 7930 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 7931 wmi_handle, 7932 param->pdev_id); 7933 7934 wmi_mtrace(WMI_SET_PERIODIC_CHANNEL_STATS_CONFIG_CMDID, NO_SESSION, 0); 7935 ret = wmi_unified_cmd_send(wmi_handle, buf, sizeof(*cmd), 7936 WMI_SET_PERIODIC_CHANNEL_STATS_CONFIG_CMDID); 7937 7938 if (ret != 0) { 7939 wmi_err("Sending periodic chan stats config failed"); 7940 wmi_buf_free(buf); 7941 } 7942 7943 return ret; 7944 } 7945 7946 #ifdef WLAN_IOT_SIM_SUPPORT 7947 /** 7948 * send_simulation_test_cmd_tlv() - send simulation test command to fw 7949 * 7950 * @wmi_handle: wmi handle 7951 * @param: pointer to hold simulation test parameter 7952 * 7953 * Return: 0 for success or error code 7954 */ 7955 static QDF_STATUS send_simulation_test_cmd_tlv(wmi_unified_t wmi_handle, 7956 struct simulation_test_params 7957 *param) 7958 { 7959 wmi_simulation_test_cmd_fixed_param *cmd; 7960 u32 wmi_buf_len; 7961 wmi_buf_t buf; 7962 u8 *buf_ptr; 7963 u32 aligned_len = 0; 7964 7965 wmi_buf_len = sizeof(*cmd); 7966 if (param->buf_len) { 7967 aligned_len = roundup(param->buf_len, sizeof(A_UINT32)); 7968 wmi_buf_len += WMI_TLV_HDR_SIZE + aligned_len; 7969 } 7970 7971 buf = wmi_buf_alloc(wmi_handle, wmi_buf_len); 7972 if (!buf) { 7973 wmi_err("wmi_buf_alloc failed"); 7974 return QDF_STATUS_E_NOMEM; 7975 } 7976 7977 buf_ptr = wmi_buf_data(buf); 7978 cmd = (wmi_simulation_test_cmd_fixed_param *)buf_ptr; 7979 WMITLV_SET_HDR(&cmd->tlv_header, 7980 WMITLV_TAG_STRUC_wmi_simulation_test_cmd_fixed_param, 7981 WMITLV_GET_STRUCT_TLVLEN( 7982 wmi_simulation_test_cmd_fixed_param)); 7983 cmd->pdev_id = param->pdev_id; 7984 cmd->vdev_id = param->vdev_id; 7985 WMI_CHAR_ARRAY_TO_MAC_ADDR(param->peer_mac, &cmd->peer_macaddr); 7986 cmd->test_cmd_type = param->test_cmd_type; 7987 cmd->test_subcmd_type = param->test_subcmd_type; 7988 WMI_SIM_FRAME_TYPE_SET(cmd->frame_type_subtype_seq, param->frame_type); 7989 WMI_SIM_FRAME_SUBTYPE_SET(cmd->frame_type_subtype_seq, 7990 param->frame_subtype); 7991 WMI_SIM_FRAME_SEQ_SET(cmd->frame_type_subtype_seq, param->seq); 7992 WMI_SIM_FRAME_OFFSET_SET(cmd->frame_offset_length, param->offset); 7993 WMI_SIM_FRAME_LENGTH_SET(cmd->frame_offset_length, param->frame_length); 7994 cmd->buf_len = param->buf_len; 7995 7996 if (param->buf_len) { 7997 buf_ptr += sizeof(*cmd); 7998 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, aligned_len); 7999 buf_ptr += WMI_TLV_HDR_SIZE; 8000 qdf_mem_copy(buf_ptr, param->bufp, param->buf_len); 8001 } 8002 8003 if (wmi_unified_cmd_send(wmi_handle, buf, wmi_buf_len, 8004 WMI_SIMULATION_TEST_CMDID)) { 8005 wmi_err("Failed to send test simulation cmd"); 8006 wmi_buf_free(buf); 8007 return QDF_STATUS_E_FAILURE; 8008 } 8009 8010 return QDF_STATUS_SUCCESS; 8011 } 8012 #endif 8013 8014 #ifdef WLAN_FEATURE_11BE 8015 #define WLAN_PHY_CH_WIDTH_320MHZ CH_WIDTH_320MHZ 8016 #else 8017 #define WLAN_PHY_CH_WIDTH_320MHZ CH_WIDTH_INVALID 8018 #endif 8019 enum phy_ch_width wmi_map_ch_width(A_UINT32 wmi_width) 8020 { 8021 switch (wmi_width) { 8022 case WMI_CHAN_WIDTH_20: 8023 return CH_WIDTH_20MHZ; 8024 case WMI_CHAN_WIDTH_40: 8025 return CH_WIDTH_40MHZ; 8026 case WMI_CHAN_WIDTH_80: 8027 return CH_WIDTH_80MHZ; 8028 case WMI_CHAN_WIDTH_160: 8029 return CH_WIDTH_160MHZ; 8030 case WMI_CHAN_WIDTH_80P80: 8031 return CH_WIDTH_80P80MHZ; 8032 case WMI_CHAN_WIDTH_5: 8033 return CH_WIDTH_5MHZ; 8034 case WMI_CHAN_WIDTH_10: 8035 return CH_WIDTH_10MHZ; 8036 case WMI_CHAN_WIDTH_320: 8037 return WLAN_PHY_CH_WIDTH_320MHZ; 8038 default: 8039 return CH_WIDTH_INVALID; 8040 } 8041 } 8042 8043 /** 8044 * send_vdev_spectral_configure_cmd_tlv() - send VDEV spectral configure 8045 * command to fw 8046 * @wmi_handle: wmi handle 8047 * @param: pointer to hold spectral config parameter 8048 * 8049 * Return: 0 for success or error code 8050 */ 8051 static QDF_STATUS send_vdev_spectral_configure_cmd_tlv(wmi_unified_t wmi_handle, 8052 struct vdev_spectral_configure_params *param) 8053 { 8054 wmi_vdev_spectral_configure_cmd_fixed_param *cmd; 8055 wmi_buf_t buf; 8056 QDF_STATUS ret; 8057 int32_t len; 8058 8059 len = sizeof(*cmd); 8060 buf = wmi_buf_alloc(wmi_handle, len); 8061 if (!buf) 8062 return QDF_STATUS_E_FAILURE; 8063 8064 cmd = (wmi_vdev_spectral_configure_cmd_fixed_param *)wmi_buf_data(buf); 8065 WMITLV_SET_HDR(&cmd->tlv_header, 8066 WMITLV_TAG_STRUC_wmi_vdev_spectral_configure_cmd_fixed_param, 8067 WMITLV_GET_STRUCT_TLVLEN( 8068 wmi_vdev_spectral_configure_cmd_fixed_param)); 8069 8070 cmd->vdev_id = param->vdev_id; 8071 cmd->spectral_scan_count = param->count; 8072 cmd->spectral_scan_period = param->period; 8073 cmd->spectral_scan_priority = param->spectral_pri; 8074 cmd->spectral_scan_fft_size = param->fft_size; 8075 cmd->spectral_scan_gc_ena = param->gc_enable; 8076 cmd->spectral_scan_restart_ena = param->restart_enable; 8077 cmd->spectral_scan_noise_floor_ref = param->noise_floor_ref; 8078 cmd->spectral_scan_init_delay = param->init_delay; 8079 cmd->spectral_scan_nb_tone_thr = param->nb_tone_thr; 8080 cmd->spectral_scan_str_bin_thr = param->str_bin_thr; 8081 cmd->spectral_scan_wb_rpt_mode = param->wb_rpt_mode; 8082 cmd->spectral_scan_rssi_rpt_mode = param->rssi_rpt_mode; 8083 cmd->spectral_scan_rssi_thr = param->rssi_thr; 8084 cmd->spectral_scan_pwr_format = param->pwr_format; 8085 cmd->spectral_scan_rpt_mode = param->rpt_mode; 8086 cmd->spectral_scan_bin_scale = param->bin_scale; 8087 cmd->spectral_scan_dBm_adj = param->dbm_adj; 8088 cmd->spectral_scan_chn_mask = param->chn_mask; 8089 cmd->spectral_scan_mode = param->mode; 8090 cmd->spectral_scan_center_freq1 = param->center_freq1; 8091 cmd->spectral_scan_center_freq2 = param->center_freq2; 8092 cmd->spectral_scan_chan_width = param->chan_width; 8093 cmd->recapture_sample_on_gain_change = param->fft_recap; 8094 /* Not used, fill with zeros */ 8095 cmd->spectral_scan_chan_freq = 0; 8096 8097 wmi_mtrace(WMI_VDEV_SPECTRAL_SCAN_CONFIGURE_CMDID, cmd->vdev_id, 0); 8098 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 8099 WMI_VDEV_SPECTRAL_SCAN_CONFIGURE_CMDID); 8100 8101 if (ret != 0) { 8102 wmi_err("Sending set quiet cmd failed"); 8103 wmi_buf_free(buf); 8104 } 8105 8106 wmi_debug("Sent WMI_VDEV_SPECTRAL_SCAN_CONFIGURE_CMDID"); 8107 wmi_debug("vdev_id: %u spectral_scan_count: %u", 8108 param->vdev_id, param->count); 8109 wmi_debug("spectral_scan_period: %u spectral_scan_priority: %u", 8110 param->period, param->spectral_pri); 8111 wmi_debug("spectral_fft_recapture_cap: %u", param->fft_recap); 8112 wmi_debug("spectral_scan_fft_size: %u spectral_scan_gc_ena: %u", 8113 param->fft_size, param->gc_enable); 8114 wmi_debug("spectral_scan_restart_ena: %u", param->restart_enable); 8115 wmi_debug("spectral_scan_noise_floor_ref: %u", param->noise_floor_ref); 8116 wmi_debug("spectral_scan_init_delay: %u", param->init_delay); 8117 wmi_debug("spectral_scan_nb_tone_thr: %u", param->nb_tone_thr); 8118 wmi_debug("spectral_scan_str_bin_thr: %u", param->str_bin_thr); 8119 wmi_debug("spectral_scan_wb_rpt_mode: %u", param->wb_rpt_mode); 8120 wmi_debug("spectral_scan_rssi_rpt_mode: %u", param->rssi_rpt_mode); 8121 wmi_debug("spectral_scan_rssi_thr: %u spectral_scan_pwr_format: %u", 8122 param->rssi_thr, param->pwr_format); 8123 wmi_debug("spectral_scan_rpt_mode: %u spectral_scan_bin_scale: %u", 8124 param->rpt_mode, param->bin_scale); 8125 wmi_debug("spectral_scan_dBm_adj: %u spectral_scan_chn_mask: %u", 8126 param->dbm_adj, param->chn_mask); 8127 wmi_debug("spectral_scan_mode: %u spectral_scan_center_freq1: %u", 8128 param->mode, param->center_freq1); 8129 wmi_debug("spectral_scan_center_freq2: %u spectral_scan_chan_freq: %u", 8130 param->center_freq2, param->chan_freq); 8131 wmi_debug("spectral_scan_chan_width: %u Status: %d", 8132 param->chan_width, ret); 8133 8134 return ret; 8135 } 8136 8137 /** 8138 * send_vdev_spectral_enable_cmd_tlv() - send VDEV spectral configure 8139 * command to fw 8140 * @wmi_handle: wmi handle 8141 * @param: pointer to hold spectral enable parameter 8142 * 8143 * Return: 0 for success or error code 8144 */ 8145 static QDF_STATUS send_vdev_spectral_enable_cmd_tlv(wmi_unified_t wmi_handle, 8146 struct vdev_spectral_enable_params *param) 8147 { 8148 wmi_vdev_spectral_enable_cmd_fixed_param *cmd; 8149 wmi_buf_t buf; 8150 QDF_STATUS ret; 8151 int32_t len; 8152 8153 len = sizeof(*cmd); 8154 buf = wmi_buf_alloc(wmi_handle, len); 8155 if (!buf) 8156 return QDF_STATUS_E_FAILURE; 8157 8158 cmd = (wmi_vdev_spectral_enable_cmd_fixed_param *)wmi_buf_data(buf); 8159 WMITLV_SET_HDR(&cmd->tlv_header, 8160 WMITLV_TAG_STRUC_wmi_vdev_spectral_enable_cmd_fixed_param, 8161 WMITLV_GET_STRUCT_TLVLEN( 8162 wmi_vdev_spectral_enable_cmd_fixed_param)); 8163 8164 cmd->vdev_id = param->vdev_id; 8165 8166 if (param->active_valid) { 8167 cmd->trigger_cmd = param->active ? 1 : 2; 8168 /* 1: Trigger, 2: Clear Trigger */ 8169 } else { 8170 cmd->trigger_cmd = 0; /* 0: Ignore */ 8171 } 8172 8173 if (param->enabled_valid) { 8174 cmd->enable_cmd = param->enabled ? 1 : 2; 8175 /* 1: Enable 2: Disable */ 8176 } else { 8177 cmd->enable_cmd = 0; /* 0: Ignore */ 8178 } 8179 cmd->spectral_scan_mode = param->mode; 8180 8181 wmi_debug("vdev_id = %u trigger_cmd = %u enable_cmd = %u", 8182 cmd->vdev_id, cmd->trigger_cmd, cmd->enable_cmd); 8183 wmi_debug("spectral_scan_mode = %u", cmd->spectral_scan_mode); 8184 8185 wmi_mtrace(WMI_VDEV_SPECTRAL_SCAN_ENABLE_CMDID, cmd->vdev_id, 0); 8186 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 8187 WMI_VDEV_SPECTRAL_SCAN_ENABLE_CMDID); 8188 8189 if (ret != 0) { 8190 wmi_err("Sending scan enable CMD failed"); 8191 wmi_buf_free(buf); 8192 } 8193 8194 wmi_debug("Sent WMI_VDEV_SPECTRAL_SCAN_ENABLE_CMDID, Status: %d", 8195 ret); 8196 8197 return ret; 8198 } 8199 8200 #ifdef WLAN_CONV_SPECTRAL_ENABLE 8201 static QDF_STATUS 8202 extract_pdev_sscan_fw_cmd_fixed_param_tlv( 8203 wmi_unified_t wmi_handle, 8204 uint8_t *event, struct spectral_startscan_resp_params *param) 8205 { 8206 WMI_PDEV_SSCAN_FW_PARAM_EVENTID_param_tlvs *param_buf; 8207 wmi_pdev_sscan_fw_cmd_fixed_param *ev; 8208 8209 if (!wmi_handle) { 8210 wmi_err("WMI handle is null"); 8211 return QDF_STATUS_E_INVAL; 8212 } 8213 8214 if (!event) { 8215 wmi_err("WMI event is null"); 8216 return QDF_STATUS_E_INVAL; 8217 } 8218 8219 if (!param) { 8220 wmi_err("Spectral startscan response params is null"); 8221 return QDF_STATUS_E_INVAL; 8222 } 8223 8224 param_buf = (WMI_PDEV_SSCAN_FW_PARAM_EVENTID_param_tlvs *)event; 8225 if (!param_buf) 8226 return QDF_STATUS_E_INVAL; 8227 8228 ev = param_buf->fixed_param; 8229 if (!ev) 8230 return QDF_STATUS_E_INVAL; 8231 8232 param->pdev_id = wmi_handle->ops->convert_target_pdev_id_to_host( 8233 wmi_handle, 8234 ev->pdev_id); 8235 param->smode = ev->spectral_scan_mode; 8236 param->num_fft_bin_index = param_buf->num_fft_bin_index; 8237 param->num_det_info = param_buf->num_det_info; 8238 8239 wmi_debug("pdev id:%u smode:%u num_fft_bin_index:%u num_det_info:%u", 8240 ev->pdev_id, ev->spectral_scan_mode, 8241 param_buf->num_fft_bin_index, param_buf->num_det_info); 8242 8243 return QDF_STATUS_SUCCESS; 8244 } 8245 8246 static QDF_STATUS 8247 extract_pdev_sscan_fft_bin_index_tlv( 8248 wmi_unified_t wmi_handle, uint8_t *event, 8249 struct spectral_fft_bin_markers_160_165mhz *param) 8250 { 8251 WMI_PDEV_SSCAN_FW_PARAM_EVENTID_param_tlvs *param_buf; 8252 wmi_pdev_sscan_fft_bin_index *ev; 8253 8254 param_buf = (WMI_PDEV_SSCAN_FW_PARAM_EVENTID_param_tlvs *)event; 8255 if (!param_buf) 8256 return QDF_STATUS_E_INVAL; 8257 8258 ev = param_buf->fft_bin_index; 8259 if (!ev) 8260 return QDF_STATUS_E_INVAL; 8261 8262 param->start_pri80 = WMI_SSCAN_PRI80_START_BIN_GET(ev->pri80_bins); 8263 param->num_pri80 = WMI_SSCAN_PRI80_END_BIN_GET(ev->pri80_bins) - 8264 param->start_pri80 + 1; 8265 param->start_sec80 = WMI_SSCAN_SEC80_START_BIN_GET(ev->sec80_bins); 8266 param->num_sec80 = WMI_SSCAN_SEC80_END_BIN_GET(ev->sec80_bins) - 8267 param->start_sec80 + 1; 8268 param->start_5mhz = WMI_SSCAN_MID_5MHZ_START_BIN_GET(ev->mid_5mhz_bins); 8269 param->num_5mhz = WMI_SSCAN_MID_5MHZ_END_BIN_GET(ev->mid_5mhz_bins) - 8270 param->start_5mhz + 1; 8271 param->is_valid = true; 8272 8273 wmi_debug("start_pri80: %u num_pri80: %u start_sec80: %u num_sec80: %u start_5mhz: %u, num_5mhz: %u", 8274 param->start_pri80, param->num_pri80, 8275 param->start_sec80, param->num_sec80, 8276 param->start_5mhz, param->num_5mhz); 8277 8278 return QDF_STATUS_SUCCESS; 8279 } 8280 8281 /** 8282 * extract_pdev_spectral_session_chan_info_tlv() - Extract channel information 8283 * for a spectral scan session 8284 * @wmi_handle: handle to WMI. 8285 * @event: Event buffer 8286 * @chan_info: Spectral session channel information data structure to be filled 8287 * by this API 8288 * 8289 * Return: QDF_STATUS of operation 8290 */ 8291 static QDF_STATUS 8292 extract_pdev_spectral_session_chan_info_tlv( 8293 wmi_unified_t wmi_handle, void *event, 8294 struct spectral_session_chan_info *chan_info) 8295 { 8296 WMI_PDEV_SSCAN_FW_PARAM_EVENTID_param_tlvs *param_buf = event; 8297 wmi_pdev_sscan_chan_info *chan_info_tlv; 8298 8299 if (!param_buf) { 8300 wmi_err("param_buf is NULL"); 8301 return QDF_STATUS_E_NULL_VALUE; 8302 } 8303 8304 if (!chan_info) { 8305 wmi_err("chan_info is NULL"); 8306 return QDF_STATUS_E_NULL_VALUE; 8307 } 8308 8309 chan_info_tlv = param_buf->chan_info; 8310 if (!chan_info_tlv) { 8311 wmi_err("chan_info tlv is not present in the event"); 8312 return QDF_STATUS_E_NULL_VALUE; 8313 } 8314 8315 wmi_debug("operating_pri20_freq:%u operating_cfreq1:%u" 8316 "operating_cfreq2:%u operating_bw:%u" 8317 "operating_puncture_20mhz_bitmap:%u" 8318 "sscan_cfreq1:%u sscan_cfreq2:%u" 8319 "sscan_bw:%u sscan_puncture_20mhz_bitmap:%u", 8320 chan_info_tlv->operating_pri20_freq, 8321 chan_info_tlv->operating_cfreq1, 8322 chan_info_tlv->operating_cfreq2, chan_info_tlv->operating_bw, 8323 chan_info_tlv->operating_puncture_20mhz_bitmap, 8324 chan_info_tlv->sscan_cfreq1, chan_info_tlv->sscan_cfreq2, 8325 chan_info_tlv->sscan_bw, 8326 chan_info_tlv->sscan_puncture_20mhz_bitmap); 8327 8328 chan_info->operating_pri20_freq = 8329 (qdf_freq_t)chan_info_tlv->operating_pri20_freq; 8330 chan_info->operating_cfreq1 = 8331 (qdf_freq_t)chan_info_tlv->operating_cfreq1; 8332 chan_info->operating_cfreq2 = 8333 (qdf_freq_t)chan_info_tlv->operating_cfreq2; 8334 chan_info->operating_bw = wmi_map_ch_width(chan_info_tlv->operating_bw); 8335 chan_info->operating_puncture_20mhz_bitmap = 8336 chan_info_tlv->operating_puncture_20mhz_bitmap; 8337 8338 chan_info->sscan_cfreq1 = (qdf_freq_t)chan_info_tlv->sscan_cfreq1; 8339 chan_info->sscan_cfreq2 = (qdf_freq_t)chan_info_tlv->sscan_cfreq2; 8340 chan_info->sscan_bw = wmi_map_ch_width(chan_info_tlv->sscan_bw); 8341 chan_info->sscan_puncture_20mhz_bitmap = 8342 chan_info_tlv->sscan_puncture_20mhz_bitmap; 8343 8344 return QDF_STATUS_SUCCESS; 8345 } 8346 8347 static QDF_STATUS 8348 extract_pdev_spectral_session_detector_info_tlv( 8349 wmi_unified_t wmi_handle, void *event, 8350 struct spectral_session_det_info *det_info, uint8_t idx) 8351 { 8352 WMI_PDEV_SSCAN_FW_PARAM_EVENTID_param_tlvs *param_buf = event; 8353 wmi_pdev_sscan_per_detector_info *det_info_tlv; 8354 8355 if (!param_buf) { 8356 wmi_err("param_buf is NULL"); 8357 return QDF_STATUS_E_NULL_VALUE; 8358 } 8359 8360 if (!det_info) { 8361 wmi_err("chan_info is NULL"); 8362 return QDF_STATUS_E_NULL_VALUE; 8363 } 8364 8365 if (!param_buf->det_info) { 8366 wmi_err("det_info tlv is not present in the event"); 8367 return QDF_STATUS_E_NULL_VALUE; 8368 } 8369 8370 if (idx >= param_buf->num_det_info) { 8371 wmi_err("det_info index(%u) is greater than or equal to %u", 8372 idx, param_buf->num_det_info); 8373 return QDF_STATUS_E_FAILURE; 8374 } 8375 8376 det_info_tlv = ¶m_buf->det_info[idx]; 8377 8378 wmi_debug("det_info_idx: %u detector_id:%u start_freq:%u end_freq:%u", 8379 idx, det_info_tlv->detector_id, 8380 det_info_tlv->start_freq, det_info_tlv->end_freq); 8381 8382 det_info->det_id = det_info_tlv->detector_id; 8383 det_info->start_freq = (qdf_freq_t)det_info_tlv->start_freq; 8384 det_info->end_freq = (qdf_freq_t)det_info_tlv->end_freq; 8385 8386 return QDF_STATUS_SUCCESS; 8387 } 8388 8389 /** 8390 * extract_spectral_caps_fixed_param_tlv() - Extract fixed params from Spectral 8391 * capabilities WMI event 8392 * @wmi_handle: handle to WMI. 8393 * @event: Event buffer 8394 * @param: Spectral capabilities event parameters data structure to be filled 8395 * by this API 8396 * 8397 * Return: QDF_STATUS of operation 8398 */ 8399 static QDF_STATUS 8400 extract_spectral_caps_fixed_param_tlv( 8401 wmi_unified_t wmi_handle, void *event, 8402 struct spectral_capabilities_event_params *params) 8403 { 8404 WMI_SPECTRAL_CAPABILITIES_EVENTID_param_tlvs *param_buf = event; 8405 8406 if (!param_buf) { 8407 wmi_err("param_buf is NULL"); 8408 return QDF_STATUS_E_NULL_VALUE; 8409 } 8410 8411 if (!params) { 8412 wmi_err("event parameters is NULL"); 8413 return QDF_STATUS_E_NULL_VALUE; 8414 } 8415 8416 params->num_sscan_bw_caps = param_buf->num_sscan_bw_caps; 8417 params->num_fft_size_caps = param_buf->num_fft_size_caps; 8418 8419 wmi_debug("num_sscan_bw_caps:%u num_fft_size_caps:%u", 8420 params->num_sscan_bw_caps, params->num_fft_size_caps); 8421 8422 return QDF_STATUS_SUCCESS; 8423 } 8424 8425 /** 8426 * extract_spectral_scan_bw_caps_tlv() - Extract bandwidth caps from 8427 * Spectral capabilities WMI event 8428 * @wmi_handle: handle to WMI. 8429 * @event: Event buffer 8430 * @bw_caps: Data structure to be populated by this API after extraction 8431 * 8432 * Return: QDF_STATUS of operation 8433 */ 8434 static QDF_STATUS 8435 extract_spectral_scan_bw_caps_tlv( 8436 wmi_unified_t wmi_handle, void *event, 8437 struct spectral_scan_bw_capabilities *bw_caps) 8438 { 8439 WMI_SPECTRAL_CAPABILITIES_EVENTID_param_tlvs *param_buf = event; 8440 int idx; 8441 8442 if (!param_buf) { 8443 wmi_err("param_buf is NULL"); 8444 return QDF_STATUS_E_NULL_VALUE; 8445 } 8446 8447 if (!bw_caps) { 8448 wmi_err("bw_caps is null"); 8449 return QDF_STATUS_E_NULL_VALUE; 8450 } 8451 8452 for (idx = 0; idx < param_buf->num_sscan_bw_caps; idx++) { 8453 bw_caps[idx].pdev_id = 8454 wmi_handle->ops->convert_pdev_id_target_to_host( 8455 wmi_handle, 8456 param_buf->sscan_bw_caps[idx].pdev_id); 8457 bw_caps[idx].smode = param_buf->sscan_bw_caps[idx].sscan_mode; 8458 bw_caps[idx].operating_bw = wmi_map_ch_width( 8459 param_buf->sscan_bw_caps[idx].operating_bw); 8460 bw_caps[idx].supported_bws = 8461 param_buf->sscan_bw_caps[idx].supported_flags; 8462 8463 wmi_debug("bw_caps[%u]:: pdev_id:%u smode:%u" 8464 "operating_bw:%u supported_flags:0x%x", 8465 idx, param_buf->sscan_bw_caps[idx].pdev_id, 8466 param_buf->sscan_bw_caps[idx].sscan_mode, 8467 param_buf->sscan_bw_caps[idx].operating_bw, 8468 param_buf->sscan_bw_caps[idx].supported_flags); 8469 } 8470 8471 return QDF_STATUS_SUCCESS; 8472 } 8473 8474 /** 8475 * extract_spectral_fft_size_caps_tlv() - Extract FFT size caps from 8476 * Spectral capabilities WMI event 8477 * @wmi_handle: handle to WMI. 8478 * @event: Event buffer 8479 * @fft_size_caps: Data structure to be populated by this API after extraction 8480 * 8481 * Return: QDF_STATUS of operation 8482 */ 8483 static QDF_STATUS 8484 extract_spectral_fft_size_caps_tlv( 8485 wmi_unified_t wmi_handle, void *event, 8486 struct spectral_fft_size_capabilities *fft_size_caps) 8487 { 8488 WMI_SPECTRAL_CAPABILITIES_EVENTID_param_tlvs *param_buf = event; 8489 int idx; 8490 8491 if (!param_buf) { 8492 wmi_err("param_buf is NULL"); 8493 return QDF_STATUS_E_NULL_VALUE; 8494 } 8495 8496 if (!fft_size_caps) { 8497 wmi_err("fft size caps is NULL"); 8498 return QDF_STATUS_E_NULL_VALUE; 8499 } 8500 8501 for (idx = 0; idx < param_buf->num_fft_size_caps; idx++) { 8502 fft_size_caps[idx].pdev_id = 8503 wmi_handle->ops->convert_pdev_id_target_to_host( 8504 wmi_handle, 8505 param_buf->fft_size_caps[idx].pdev_id); 8506 fft_size_caps[idx].sscan_bw = wmi_map_ch_width( 8507 param_buf->fft_size_caps[idx].sscan_bw); 8508 fft_size_caps[idx].supports_fft_sizes = 8509 param_buf->fft_size_caps[idx].supported_flags; 8510 8511 wmi_debug("fft_size_caps[%u]:: pdev_id:%u sscan_bw:%u" 8512 "supported_flags:0x%x", 8513 idx, param_buf->fft_size_caps[idx].pdev_id, 8514 param_buf->fft_size_caps[idx].sscan_bw, 8515 param_buf->fft_size_caps[idx].supported_flags); 8516 } 8517 8518 return QDF_STATUS_SUCCESS; 8519 } 8520 #endif /* WLAN_CONV_SPECTRAL_ENABLE */ 8521 8522 #ifdef FEATURE_WPSS_THERMAL_MITIGATION 8523 static inline void 8524 wmi_fill_client_id_priority(wmi_therm_throt_config_request_fixed_param *tt_conf, 8525 struct thermal_mitigation_params *param) 8526 { 8527 tt_conf->client_id = param->client_id; 8528 tt_conf->priority = param->priority; 8529 } 8530 #else 8531 static inline void 8532 wmi_fill_client_id_priority(wmi_therm_throt_config_request_fixed_param *tt_conf, 8533 struct thermal_mitigation_params *param) 8534 { 8535 } 8536 #endif 8537 8538 /** 8539 * send_thermal_mitigation_param_cmd_tlv() - configure thermal mitigation params 8540 * @param wmi_handle : handle to WMI. 8541 * @param param : pointer to hold thermal mitigation param 8542 * 8543 * @return QDF_STATUS_SUCCESS on success and -ve on failure. 8544 */ 8545 static QDF_STATUS send_thermal_mitigation_param_cmd_tlv( 8546 wmi_unified_t wmi_handle, 8547 struct thermal_mitigation_params *param) 8548 { 8549 wmi_therm_throt_config_request_fixed_param *tt_conf = NULL; 8550 wmi_therm_throt_level_config_info *lvl_conf = NULL; 8551 wmi_buf_t buf = NULL; 8552 uint8_t *buf_ptr = NULL; 8553 int error; 8554 int32_t len; 8555 int i; 8556 8557 len = sizeof(*tt_conf) + WMI_TLV_HDR_SIZE + 8558 param->num_thermal_conf * 8559 sizeof(wmi_therm_throt_level_config_info); 8560 8561 buf = wmi_buf_alloc(wmi_handle, len); 8562 if (!buf) 8563 return QDF_STATUS_E_NOMEM; 8564 8565 tt_conf = (wmi_therm_throt_config_request_fixed_param *) wmi_buf_data(buf); 8566 8567 /* init fixed params */ 8568 WMITLV_SET_HDR(tt_conf, 8569 WMITLV_TAG_STRUC_wmi_therm_throt_config_request_fixed_param, 8570 (WMITLV_GET_STRUCT_TLVLEN(wmi_therm_throt_config_request_fixed_param))); 8571 8572 tt_conf->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 8573 wmi_handle, 8574 param->pdev_id); 8575 tt_conf->enable = param->enable; 8576 tt_conf->dc = param->dc; 8577 tt_conf->dc_per_event = param->dc_per_event; 8578 tt_conf->therm_throt_levels = param->num_thermal_conf; 8579 wmi_fill_client_id_priority(tt_conf, param); 8580 buf_ptr = (uint8_t *) ++tt_conf; 8581 /* init TLV params */ 8582 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 8583 (param->num_thermal_conf * 8584 sizeof(wmi_therm_throt_level_config_info))); 8585 8586 lvl_conf = (wmi_therm_throt_level_config_info *) (buf_ptr + WMI_TLV_HDR_SIZE); 8587 for (i = 0; i < param->num_thermal_conf; i++) { 8588 WMITLV_SET_HDR(&lvl_conf->tlv_header, 8589 WMITLV_TAG_STRUC_wmi_therm_throt_level_config_info, 8590 WMITLV_GET_STRUCT_TLVLEN(wmi_therm_throt_level_config_info)); 8591 lvl_conf->temp_lwm = param->levelconf[i].tmplwm; 8592 lvl_conf->temp_hwm = param->levelconf[i].tmphwm; 8593 lvl_conf->dc_off_percent = param->levelconf[i].dcoffpercent; 8594 lvl_conf->prio = param->levelconf[i].priority; 8595 lvl_conf++; 8596 } 8597 8598 wmi_mtrace(WMI_THERM_THROT_SET_CONF_CMDID, NO_SESSION, 0); 8599 error = wmi_unified_cmd_send(wmi_handle, buf, len, 8600 WMI_THERM_THROT_SET_CONF_CMDID); 8601 if (QDF_IS_STATUS_ERROR(error)) { 8602 wmi_buf_free(buf); 8603 wmi_err("Failed to send WMI_THERM_THROT_SET_CONF_CMDID command"); 8604 } 8605 8606 return error; 8607 } 8608 8609 /** 8610 * send_coex_config_cmd_tlv() - send coex config command to fw 8611 * @wmi_handle: wmi handle 8612 * @param: pointer to coex config param 8613 * 8614 * Return: 0 for success or error code 8615 */ 8616 static QDF_STATUS 8617 send_coex_config_cmd_tlv(wmi_unified_t wmi_handle, 8618 struct coex_config_params *param) 8619 { 8620 WMI_COEX_CONFIG_CMD_fixed_param *cmd; 8621 wmi_buf_t buf; 8622 QDF_STATUS ret; 8623 int32_t len; 8624 8625 len = sizeof(*cmd); 8626 buf = wmi_buf_alloc(wmi_handle, len); 8627 if (!buf) 8628 return QDF_STATUS_E_FAILURE; 8629 8630 cmd = (WMI_COEX_CONFIG_CMD_fixed_param *)wmi_buf_data(buf); 8631 WMITLV_SET_HDR(&cmd->tlv_header, 8632 WMITLV_TAG_STRUC_WMI_COEX_CONFIG_CMD_fixed_param, 8633 WMITLV_GET_STRUCT_TLVLEN( 8634 WMI_COEX_CONFIG_CMD_fixed_param)); 8635 8636 cmd->vdev_id = param->vdev_id; 8637 cmd->config_type = param->config_type; 8638 cmd->config_arg1 = param->config_arg1; 8639 cmd->config_arg2 = param->config_arg2; 8640 cmd->config_arg3 = param->config_arg3; 8641 cmd->config_arg4 = param->config_arg4; 8642 cmd->config_arg5 = param->config_arg5; 8643 cmd->config_arg6 = param->config_arg6; 8644 8645 wmi_mtrace(WMI_COEX_CONFIG_CMDID, cmd->vdev_id, 0); 8646 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 8647 WMI_COEX_CONFIG_CMDID); 8648 8649 if (ret != 0) { 8650 wmi_err("Sending COEX CONFIG CMD failed"); 8651 wmi_buf_free(buf); 8652 } 8653 8654 return ret; 8655 } 8656 8657 #ifdef WLAN_FEATURE_DBAM_CONFIG 8658 8659 static enum wmi_coex_dbam_mode_type 8660 map_to_wmi_coex_dbam_mode_type(enum coex_dbam_config_mode mode) 8661 { 8662 switch (mode) { 8663 case COEX_DBAM_ENABLE: 8664 return WMI_COEX_DBAM_ENABLE; 8665 case COEX_DBAM_FORCE_ENABLE: 8666 return WMI_COEX_DBAM_FORCED; 8667 case COEX_DBAM_DISABLE: 8668 default: 8669 return WMI_COEX_DBAM_DISABLE; 8670 } 8671 } 8672 8673 /** 8674 * send_dbam_config_cmd_tlv() - send coex DBAM config command to fw 8675 * @wmi_handle: wmi handle 8676 * @param: pointer to coex dbam config param 8677 * 8678 * Return: 0 for success or error code 8679 */ 8680 static QDF_STATUS 8681 send_dbam_config_cmd_tlv(wmi_unified_t wmi_handle, 8682 struct coex_dbam_config_params *param) 8683 { 8684 wmi_coex_dbam_cmd_fixed_param *cmd; 8685 wmi_buf_t buf; 8686 void *buf_ptr; 8687 QDF_STATUS ret; 8688 int32_t len; 8689 8690 len = sizeof(*cmd); 8691 buf = wmi_buf_alloc(wmi_handle, len); 8692 if (!buf) { 8693 wmi_err_rl("Failed to allocate wmi buffer"); 8694 return QDF_STATUS_E_NOMEM; 8695 } 8696 8697 buf_ptr = wmi_buf_data(buf); 8698 cmd = buf_ptr; 8699 WMITLV_SET_HDR(&cmd->tlv_header, 8700 WMITLV_TAG_STRUC_wmi_coex_dbam_cmd_fixed_param, 8701 WMITLV_GET_STRUCT_TLVLEN( 8702 wmi_coex_dbam_cmd_fixed_param)); 8703 8704 cmd->vdev_id = param->vdev_id; 8705 cmd->dbam_mode = map_to_wmi_coex_dbam_mode_type(param->dbam_mode); 8706 8707 wmi_mtrace(WMI_COEX_DBAM_CMDID, cmd->vdev_id, 0); 8708 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 8709 WMI_COEX_DBAM_CMDID); 8710 8711 if (QDF_IS_STATUS_ERROR(ret)) { 8712 wmi_err("Sending DBAM CONFIG CMD failed"); 8713 wmi_buf_free(buf); 8714 return QDF_STATUS_E_FAILURE; 8715 } 8716 8717 return ret; 8718 } 8719 8720 static enum coex_dbam_comp_status 8721 wmi_convert_dbam_comp_status(wmi_coex_dbam_comp_status status) 8722 { 8723 switch (status) { 8724 case WMI_COEX_DBAM_COMP_SUCCESS: 8725 case WMI_COEX_DBAM_COMP_ONGOING: 8726 case WMI_COEX_DBAM_COMP_DELAYED: 8727 return COEX_DBAM_COMP_SUCCESS; 8728 case WMI_COEX_DBAM_COMP_NOT_SUPPORT: 8729 return COEX_DBAM_COMP_NOT_SUPPORT; 8730 case WMI_COEX_DBAM_COMP_INVALID_PARAM: 8731 case WMI_COEX_DBAM_COMP_FAIL: 8732 default: 8733 return COEX_DBAM_COMP_FAIL; 8734 } 8735 } 8736 8737 /** 8738 * extract_dbam_comp_status_event_tlv() - extract dbam complete status event 8739 * @wmi_handle: WMI handle 8740 * @evt_buf: event buffer 8741 * @resp: pointer to coex dbam config response 8742 * 8743 * Return: QDF_STATUS 8744 */ 8745 static QDF_STATUS 8746 extract_dbam_config_resp_event_tlv(wmi_unified_t wmi_handle, void *evt_buf, 8747 struct coex_dbam_config_resp *resp) 8748 { 8749 WMI_COEX_DBAM_COMPLETE_EVENTID_param_tlvs *param_buf; 8750 wmi_coex_dbam_complete_event_fixed_param *event; 8751 8752 param_buf = (WMI_COEX_DBAM_COMPLETE_EVENTID_param_tlvs *)evt_buf; 8753 8754 event = param_buf->fixed_param; 8755 8756 resp->dbam_resp = wmi_convert_dbam_comp_status(event->comp_status); 8757 8758 return QDF_STATUS_SUCCESS; 8759 } 8760 #endif 8761 8762 #ifdef WLAN_SUPPORT_TWT 8763 static void wmi_copy_twt_resource_config(wmi_resource_config *resource_cfg, 8764 target_resource_config *tgt_res_cfg) 8765 { 8766 resource_cfg->twt_ap_pdev_count = tgt_res_cfg->twt_ap_pdev_count; 8767 resource_cfg->twt_ap_sta_count = tgt_res_cfg->twt_ap_sta_count; 8768 } 8769 #else 8770 static void wmi_copy_twt_resource_config(wmi_resource_config *resource_cfg, 8771 target_resource_config *tgt_res_cfg) 8772 { 8773 resource_cfg->twt_ap_pdev_count = 0; 8774 resource_cfg->twt_ap_sta_count = 0; 8775 } 8776 #endif 8777 8778 #ifdef WLAN_FEATURE_NAN 8779 static void wmi_set_nan_channel_support(wmi_resource_config *resource_cfg) 8780 { 8781 WMI_RSRC_CFG_HOST_SERVICE_FLAG_NAN_CHANNEL_SUPPORT_SET( 8782 resource_cfg->host_service_flags, 1); 8783 } 8784 #else 8785 static inline 8786 void wmi_set_nan_channel_support(wmi_resource_config *resource_cfg) 8787 { 8788 } 8789 #endif 8790 8791 #if defined(CONFIG_AFC_SUPPORT) 8792 static 8793 void wmi_copy_afc_deployment_config(wmi_resource_config *resource_cfg, 8794 target_resource_config *tgt_res_cfg) 8795 { 8796 WMI_RSRC_CFG_HOST_SERVICE_FLAG_AFC_INDOOR_SUPPORT_CHECK_SET( 8797 resource_cfg->host_service_flags, 8798 tgt_res_cfg->afc_indoor_support); 8799 8800 WMI_RSRC_CFG_HOST_SERVICE_FLAG_AFC_OUTDOOR_SUPPORT_CHECK_SET( 8801 resource_cfg->host_service_flags, 8802 tgt_res_cfg->afc_outdoor_support); 8803 } 8804 #else 8805 static 8806 void wmi_copy_afc_deployment_config(wmi_resource_config *resource_cfg, 8807 target_resource_config *tgt_res_cfg) 8808 { 8809 } 8810 #endif 8811 8812 static 8813 void wmi_copy_resource_config(wmi_resource_config *resource_cfg, 8814 target_resource_config *tgt_res_cfg) 8815 { 8816 resource_cfg->num_vdevs = tgt_res_cfg->num_vdevs; 8817 resource_cfg->num_peers = tgt_res_cfg->num_peers; 8818 resource_cfg->num_offload_peers = tgt_res_cfg->num_offload_peers; 8819 resource_cfg->num_offload_reorder_buffs = 8820 tgt_res_cfg->num_offload_reorder_buffs; 8821 resource_cfg->num_peer_keys = tgt_res_cfg->num_peer_keys; 8822 resource_cfg->num_tids = tgt_res_cfg->num_tids; 8823 resource_cfg->ast_skid_limit = tgt_res_cfg->ast_skid_limit; 8824 resource_cfg->tx_chain_mask = tgt_res_cfg->tx_chain_mask; 8825 resource_cfg->rx_chain_mask = tgt_res_cfg->rx_chain_mask; 8826 resource_cfg->rx_timeout_pri[0] = tgt_res_cfg->rx_timeout_pri[0]; 8827 resource_cfg->rx_timeout_pri[1] = tgt_res_cfg->rx_timeout_pri[1]; 8828 resource_cfg->rx_timeout_pri[2] = tgt_res_cfg->rx_timeout_pri[2]; 8829 resource_cfg->rx_timeout_pri[3] = tgt_res_cfg->rx_timeout_pri[3]; 8830 resource_cfg->rx_decap_mode = tgt_res_cfg->rx_decap_mode; 8831 resource_cfg->scan_max_pending_req = 8832 tgt_res_cfg->scan_max_pending_req; 8833 resource_cfg->bmiss_offload_max_vdev = 8834 tgt_res_cfg->bmiss_offload_max_vdev; 8835 resource_cfg->roam_offload_max_vdev = 8836 tgt_res_cfg->roam_offload_max_vdev; 8837 resource_cfg->roam_offload_max_ap_profiles = 8838 tgt_res_cfg->roam_offload_max_ap_profiles; 8839 resource_cfg->num_mcast_groups = tgt_res_cfg->num_mcast_groups; 8840 resource_cfg->num_mcast_table_elems = 8841 tgt_res_cfg->num_mcast_table_elems; 8842 resource_cfg->mcast2ucast_mode = tgt_res_cfg->mcast2ucast_mode; 8843 resource_cfg->tx_dbg_log_size = tgt_res_cfg->tx_dbg_log_size; 8844 resource_cfg->num_wds_entries = tgt_res_cfg->num_wds_entries; 8845 resource_cfg->dma_burst_size = tgt_res_cfg->dma_burst_size; 8846 resource_cfg->mac_aggr_delim = tgt_res_cfg->mac_aggr_delim; 8847 resource_cfg->rx_skip_defrag_timeout_dup_detection_check = 8848 tgt_res_cfg->rx_skip_defrag_timeout_dup_detection_check; 8849 resource_cfg->vow_config = tgt_res_cfg->vow_config; 8850 resource_cfg->gtk_offload_max_vdev = tgt_res_cfg->gtk_offload_max_vdev; 8851 resource_cfg->num_msdu_desc = tgt_res_cfg->num_msdu_desc; 8852 resource_cfg->max_frag_entries = tgt_res_cfg->max_frag_entries; 8853 resource_cfg->num_tdls_vdevs = tgt_res_cfg->num_tdls_vdevs; 8854 resource_cfg->num_tdls_conn_table_entries = 8855 tgt_res_cfg->num_tdls_conn_table_entries; 8856 resource_cfg->beacon_tx_offload_max_vdev = 8857 tgt_res_cfg->beacon_tx_offload_max_vdev; 8858 resource_cfg->num_multicast_filter_entries = 8859 tgt_res_cfg->num_multicast_filter_entries; 8860 resource_cfg->num_wow_filters = 8861 tgt_res_cfg->num_wow_filters; 8862 resource_cfg->num_keep_alive_pattern = 8863 tgt_res_cfg->num_keep_alive_pattern; 8864 resource_cfg->keep_alive_pattern_size = 8865 tgt_res_cfg->keep_alive_pattern_size; 8866 resource_cfg->max_tdls_concurrent_sleep_sta = 8867 tgt_res_cfg->max_tdls_concurrent_sleep_sta; 8868 resource_cfg->max_tdls_concurrent_buffer_sta = 8869 tgt_res_cfg->max_tdls_concurrent_buffer_sta; 8870 resource_cfg->wmi_send_separate = 8871 tgt_res_cfg->wmi_send_separate; 8872 resource_cfg->num_ocb_vdevs = 8873 tgt_res_cfg->num_ocb_vdevs; 8874 resource_cfg->num_ocb_channels = 8875 tgt_res_cfg->num_ocb_channels; 8876 resource_cfg->num_ocb_schedules = 8877 tgt_res_cfg->num_ocb_schedules; 8878 resource_cfg->bpf_instruction_size = tgt_res_cfg->apf_instruction_size; 8879 resource_cfg->max_bssid_rx_filters = tgt_res_cfg->max_bssid_rx_filters; 8880 resource_cfg->use_pdev_id = tgt_res_cfg->use_pdev_id; 8881 resource_cfg->max_num_dbs_scan_duty_cycle = 8882 tgt_res_cfg->max_num_dbs_scan_duty_cycle; 8883 resource_cfg->sched_params = tgt_res_cfg->scheduler_params; 8884 resource_cfg->num_packet_filters = tgt_res_cfg->num_packet_filters; 8885 resource_cfg->num_max_sta_vdevs = tgt_res_cfg->num_max_sta_vdevs; 8886 resource_cfg->max_bssid_indicator = tgt_res_cfg->max_bssid_indicator; 8887 resource_cfg->max_num_group_keys = tgt_res_cfg->max_num_group_keys; 8888 /* Deferred AI: Max rnr neighbors supported in multisoc case 8889 * where in SoC can support 6ghz. During WMI init of a SoC 8890 * currently there is no way to figure if another SOC is plugged in 8891 * and it can support 6Ghz. 8892 */ 8893 resource_cfg->max_rnr_neighbours = MAX_SUPPORTED_NEIGHBORS; 8894 resource_cfg->ema_max_vap_cnt = tgt_res_cfg->ema_max_vap_cnt; 8895 resource_cfg->ema_max_profile_period = 8896 tgt_res_cfg->ema_max_profile_period; 8897 resource_cfg->ema_init_config = tgt_res_cfg->ema_init_config; 8898 resource_cfg->carrier_config = tgt_res_cfg->carrier_profile_config; 8899 8900 if (tgt_res_cfg->max_ndp_sessions) 8901 resource_cfg->max_ndp_sessions = 8902 tgt_res_cfg->max_ndp_sessions; 8903 resource_cfg->max_ndi_interfaces = tgt_res_cfg->max_ndi; 8904 resource_cfg->num_max_active_vdevs = tgt_res_cfg->num_max_active_vdevs; 8905 8906 if (tgt_res_cfg->atf_config) 8907 WMI_RSRC_CFG_FLAG_ATF_CONFIG_ENABLE_SET(resource_cfg->flag1, 1); 8908 if (tgt_res_cfg->mgmt_comp_evt_bundle_support) 8909 WMI_RSRC_CFG_FLAG_MGMT_COMP_EVT_BUNDLE_SUPPORT_SET( 8910 resource_cfg->flag1, 1); 8911 if (tgt_res_cfg->tx_msdu_new_partition_id_support) 8912 WMI_RSRC_CFG_FLAG_TX_MSDU_ID_NEW_PARTITION_SUPPORT_SET( 8913 resource_cfg->flag1, 1); 8914 if (tgt_res_cfg->cce_disable) 8915 WMI_RSRC_CFG_FLAG_TCL_CCE_DISABLE_SET(resource_cfg->flag1, 1); 8916 if (tgt_res_cfg->enable_pci_gen) 8917 WMI_RSRC_CFG_FLAG_PCIE_GEN_SWITCH_CAPABLITY_SET( 8918 resource_cfg->flag1, 1); 8919 if (tgt_res_cfg->eapol_minrate_set) { 8920 WMI_RSRC_CFG_FLAG_EAPOL_REKEY_MINRATE_SUPPORT_ENABLE_SET( 8921 resource_cfg->flag1, 1); 8922 if (tgt_res_cfg->eapol_minrate_ac_set != 3) { 8923 WMI_RSRC_CFG_FLAG_EAPOL_AC_OVERRIDE_VALID_SET( 8924 resource_cfg->flag1, 1); 8925 WMI_RSRC_CFG_FLAG_EAPOL_AC_OVERRIDE_SET( 8926 resource_cfg->flag1, 8927 tgt_res_cfg->eapol_minrate_ac_set); 8928 } 8929 } 8930 if (tgt_res_cfg->new_htt_msg_format) { 8931 WMI_RSRC_CFG_FLAG_HTT_H2T_NO_HTC_HDR_LEN_IN_MSG_LEN_SET( 8932 resource_cfg->flag1, 1); 8933 } 8934 8935 if (tgt_res_cfg->peer_unmap_conf_support) 8936 WMI_RSRC_CFG_FLAG_PEER_UNMAP_RESPONSE_SUPPORT_SET( 8937 resource_cfg->flag1, 1); 8938 8939 if (tgt_res_cfg->tstamp64_en) 8940 WMI_RSRC_CFG_FLAG_TX_COMPLETION_TX_TSF64_ENABLE_SET( 8941 resource_cfg->flag1, 1); 8942 8943 if (tgt_res_cfg->three_way_coex_config_legacy_en) 8944 WMI_RSRC_CFG_FLAG_THREE_WAY_COEX_CONFIG_LEGACY_SUPPORT_SET( 8945 resource_cfg->flag1, 1); 8946 if (tgt_res_cfg->pktcapture_support) 8947 WMI_RSRC_CFG_FLAG_PACKET_CAPTURE_SUPPORT_SET( 8948 resource_cfg->flag1, 1); 8949 8950 /* 8951 * Control padding using config param/ini of iphdr_pad_config 8952 */ 8953 if (tgt_res_cfg->iphdr_pad_config) 8954 WMI_RSRC_CFG_FLAG_IPHR_PAD_CONFIG_ENABLE_SET( 8955 resource_cfg->flag1, 1); 8956 8957 WMI_RSRC_CFG_FLAG_IPA_DISABLE_SET(resource_cfg->flag1, 8958 tgt_res_cfg->ipa_disable); 8959 8960 if (tgt_res_cfg->time_sync_ftm) 8961 WMI_RSRC_CFG_FLAG_AUDIO_SYNC_SUPPORT_SET(resource_cfg->flag1, 8962 1); 8963 8964 wmi_copy_twt_resource_config(resource_cfg, tgt_res_cfg); 8965 resource_cfg->peer_map_unmap_versions = 8966 tgt_res_cfg->peer_map_unmap_version; 8967 resource_cfg->smart_ant_cap = tgt_res_cfg->smart_ant_cap; 8968 if (tgt_res_cfg->re_ul_resp) 8969 WMI_SET_BITS(resource_cfg->flags2, 0, 4, 8970 tgt_res_cfg->re_ul_resp); 8971 8972 /* 8973 * Enable Service Aware Wifi 8974 */ 8975 if (tgt_res_cfg->sawf) 8976 WMI_RSRC_CFG_FLAGS2_SAWF_CONFIG_ENABLE_SET(resource_cfg->flags2, 8977 tgt_res_cfg->sawf); 8978 8979 /* 8980 * Enable ast flow override per peer 8981 */ 8982 resource_cfg->msdu_flow_override_config0 = 0; 8983 WMI_MSDU_FLOW_AST_ENABLE_SET( 8984 resource_cfg->msdu_flow_override_config0, 8985 WMI_CONFIG_MSDU_AST_INDEX_1, 8986 tgt_res_cfg->ast_1_valid_mask_enable); 8987 8988 WMI_MSDU_FLOW_AST_ENABLE_SET( 8989 resource_cfg->msdu_flow_override_config0, 8990 WMI_CONFIG_MSDU_AST_INDEX_2, 8991 tgt_res_cfg->ast_2_valid_mask_enable); 8992 8993 WMI_MSDU_FLOW_AST_ENABLE_SET( 8994 resource_cfg->msdu_flow_override_config0, 8995 WMI_CONFIG_MSDU_AST_INDEX_3, 8996 tgt_res_cfg->ast_3_valid_mask_enable); 8997 8998 /* 8999 * Enable ast flow mask and TID valid mask configurations 9000 */ 9001 resource_cfg->msdu_flow_override_config1 = 0; 9002 9003 /*Enable UDP flow for Ast index 0*/ 9004 WMI_MSDU_FLOW_ASTX_MSDU_FLOW_MASKS_SET( 9005 resource_cfg->msdu_flow_override_config1, 9006 WMI_CONFIG_MSDU_AST_INDEX_0, 9007 tgt_res_cfg->ast_0_flow_mask_enable); 9008 9009 /*Enable Non UDP flow for Ast index 1*/ 9010 WMI_MSDU_FLOW_ASTX_MSDU_FLOW_MASKS_SET( 9011 resource_cfg->msdu_flow_override_config1, 9012 WMI_CONFIG_MSDU_AST_INDEX_1, 9013 tgt_res_cfg->ast_1_flow_mask_enable); 9014 9015 /*Enable Hi-Priority flow for Ast index 2*/ 9016 WMI_MSDU_FLOW_ASTX_MSDU_FLOW_MASKS_SET( 9017 resource_cfg->msdu_flow_override_config1, 9018 WMI_CONFIG_MSDU_AST_INDEX_2, 9019 tgt_res_cfg->ast_2_flow_mask_enable); 9020 9021 /*Enable Low-Priority flow for Ast index 3*/ 9022 WMI_MSDU_FLOW_ASTX_MSDU_FLOW_MASKS_SET( 9023 resource_cfg->msdu_flow_override_config1, 9024 WMI_CONFIG_MSDU_AST_INDEX_3, 9025 tgt_res_cfg->ast_3_flow_mask_enable); 9026 9027 /*Enable all 8 tid for Hi-Pririty Flow Queue*/ 9028 WMI_MSDU_FLOW_TID_VALID_HI_MASKS_SET( 9029 resource_cfg->msdu_flow_override_config1, 9030 tgt_res_cfg->ast_tid_high_mask_enable); 9031 9032 /*Enable all 8 tid for Low-Pririty Flow Queue*/ 9033 WMI_MSDU_FLOW_TID_VALID_LOW_MASKS_SET( 9034 resource_cfg->msdu_flow_override_config1, 9035 tgt_res_cfg->ast_tid_low_mask_enable); 9036 WMI_RSRC_CFG_HOST_SERVICE_FLAG_NAN_IFACE_SUPPORT_SET( 9037 resource_cfg->host_service_flags, 9038 tgt_res_cfg->nan_separate_iface_support); 9039 WMI_RSRC_CFG_HOST_SERVICE_FLAG_HOST_SUPPORT_MULTI_RADIO_EVTS_PER_RADIO_SET( 9040 resource_cfg->host_service_flags, 1); 9041 9042 WMI_RSRC_CFG_FLAG_VIDEO_OVER_WIFI_ENABLE_SET( 9043 resource_cfg->flag1, tgt_res_cfg->carrier_vow_optimization); 9044 9045 if (tgt_res_cfg->is_sap_connected_d3wow_enabled) 9046 WMI_RSRC_CFG_FLAGS2_IS_SAP_CONNECTED_D3WOW_ENABLED_SET( 9047 resource_cfg->flags2, 1); 9048 if (tgt_res_cfg->is_go_connected_d3wow_enabled) 9049 WMI_RSRC_CFG_FLAGS2_IS_GO_CONNECTED_D3WOW_ENABLED_SET( 9050 resource_cfg->flags2, 1); 9051 9052 if (tgt_res_cfg->sae_eapol_offload) 9053 WMI_RSRC_CFG_HOST_SERVICE_FLAG_SAE_EAPOL_OFFLOAD_SUPPORT_SET( 9054 resource_cfg->host_service_flags, 1); 9055 9056 WMI_RSRC_CFG_HOST_SERVICE_FLAG_REG_CC_EXT_SUPPORT_SET( 9057 resource_cfg->host_service_flags, 9058 tgt_res_cfg->is_reg_cc_ext_event_supported); 9059 9060 WMI_RSRC_CFG_HOST_SERVICE_FLAG_BANG_RADAR_320M_SUPPORT_SET( 9061 resource_cfg->host_service_flags, 9062 tgt_res_cfg->is_host_dfs_320mhz_bangradar_supported); 9063 9064 WMI_RSRC_CFG_HOST_SERVICE_FLAG_LPI_SP_MODE_SUPPORT_SET( 9065 resource_cfg->host_service_flags, 9066 tgt_res_cfg->is_6ghz_sp_pwrmode_supp_enabled); 9067 9068 WMI_RSRC_CFG_HOST_SERVICE_FLAG_REG_DISCARD_AFC_TIMER_CHECK_SET( 9069 resource_cfg->host_service_flags, 9070 tgt_res_cfg->afc_timer_check_disable); 9071 9072 WMI_RSRC_CFG_HOST_SERVICE_FLAG_REG_DISCARD_AFC_REQ_ID_CHECK_SET( 9073 resource_cfg->host_service_flags, 9074 tgt_res_cfg->afc_req_id_check_disable); 9075 9076 wmi_copy_afc_deployment_config(resource_cfg, tgt_res_cfg); 9077 9078 wmi_set_nan_channel_support(resource_cfg); 9079 9080 if (tgt_res_cfg->twt_ack_support_cap) 9081 WMI_RSRC_CFG_HOST_SERVICE_FLAG_STA_TWT_SYNC_EVT_SUPPORT_SET( 9082 resource_cfg->host_service_flags, 1); 9083 9084 if (tgt_res_cfg->reo_qdesc_shared_addr_table_enabled) 9085 WMI_RSRC_CFG_HOST_SERVICE_FLAG_REO_QREF_FEATURE_SUPPORT_SET( 9086 resource_cfg->host_service_flags, 1); 9087 9088 WMI_RSRC_CFG_FLAGS2_RX_PEER_METADATA_VERSION_SET(resource_cfg->flags2, 9089 tgt_res_cfg->target_cap_flags); 9090 if (tgt_res_cfg->notify_frame_support) 9091 WMI_RSRC_CFG_FLAGS2_NOTIFY_FRAME_CONFIG_ENABLE_SET( 9092 resource_cfg->flags2, 1); 9093 9094 } 9095 9096 #ifdef FEATURE_SET 9097 /** 9098 * convert_host_to_target_vendor1_req2_version() -Convert host vendor1 9099 * requirement2 version to target vendor1 requirement2 version 9100 * @vendor1_req2_ver: Host vendor1 requirement2 version 9101 * 9102 * Return: Target vendor1 requirement2 version 9103 */ 9104 static WMI_VENDOR1_REQ2_VERSION convert_host_to_target_vendor1_req2_version( 9105 WMI_HOST_VENDOR1_REQ2_VERSION vendor1_req2_ver) 9106 { 9107 switch (vendor1_req2_ver) { 9108 case WMI_HOST_VENDOR1_REQ2_VERSION_3_00: 9109 return WMI_VENDOR1_REQ2_VERSION_3_00; 9110 case WMI_HOST_VENDOR1_REQ2_VERSION_3_01: 9111 return WMI_VENDOR1_REQ2_VERSION_3_01; 9112 case WMI_HOST_VENDOR1_REQ2_VERSION_3_20: 9113 return WMI_VENDOR1_REQ2_VERSION_3_20; 9114 default: 9115 return WMI_VENDOR1_REQ2_VERSION_3_00; 9116 } 9117 } 9118 9119 /** 9120 * convert_host_to_target_vendor1_req1_version() -Convert host vendor1 9121 * requirement1 version to target vendor1 requirement1 version 9122 * @vendor1_req1_ver: Host vendor1 requirement1 version 9123 * 9124 * Return: Target vendor1 requirement1 version 9125 */ 9126 static WMI_VENDOR1_REQ1_VERSION convert_host_to_target_vendor1_req1_version( 9127 WMI_HOST_VENDOR1_REQ1_VERSION vendor1_req1_ver) 9128 { 9129 switch (vendor1_req1_ver) { 9130 case WMI_HOST_VENDOR1_REQ1_VERSION_3_00: 9131 return WMI_VENDOR1_REQ1_VERSION_3_00; 9132 case WMI_HOST_VENDOR1_REQ1_VERSION_3_01: 9133 return WMI_VENDOR1_REQ1_VERSION_3_01; 9134 case WMI_HOST_VENDOR1_REQ1_VERSION_3_20: 9135 return WMI_VENDOR1_REQ1_VERSION_3_20; 9136 default: 9137 return WMI_VENDOR1_REQ1_VERSION_3_00; 9138 } 9139 } 9140 9141 /** 9142 * convert_host_to_target_wifi_standard() -Convert host wifi standard to 9143 * target wifi standard 9144 * @wifi_standard: Host wifi standard 9145 * 9146 * Return: Target wifi standard 9147 */ 9148 static WMI_WIFI_STANDARD convert_host_to_target_wifi_standard( 9149 WMI_HOST_WIFI_STANDARD wifi_standard) 9150 { 9151 switch (wifi_standard) { 9152 case WMI_HOST_WIFI_STANDARD_4: 9153 return WMI_WIFI_STANDARD_4; 9154 case WMI_HOST_WIFI_STANDARD_5: 9155 return WMI_WIFI_STANDARD_5; 9156 case WMI_HOST_WIFI_STANDARD_6: 9157 return WMI_WIFI_STANDARD_6; 9158 case WMI_HOST_WIFI_STANDARD_6E: 9159 return WMI_WIFI_STANDARD_6E; 9160 case WMI_HOST_WIFI_STANDARD_7: 9161 return WMI_WIFI_STANDARD_7; 9162 default: 9163 return WMI_WIFI_STANDARD_4; 9164 } 9165 } 9166 9167 /** 9168 * convert_host_to_target_band_concurrency() -Convert host band concurrency to 9169 * target band concurrency 9170 * @band_concurrency: Host Band concurrency 9171 * 9172 * Return: Target band concurrency 9173 */ 9174 static WMI_BAND_CONCURRENCY convert_host_to_target_band_concurrency( 9175 WMI_HOST_BAND_CONCURRENCY band_concurrency) 9176 { 9177 switch (band_concurrency) { 9178 case WMI_HOST_BAND_CONCURRENCY_DBS: 9179 return WMI_HOST_DBS; 9180 case WMI_HOST_BAND_CONCURRENCY_DBS_SBS: 9181 return WMI_HOST_DBS_SBS; 9182 default: 9183 return WMI_HOST_NONE; 9184 } 9185 } 9186 9187 /** 9188 * convert_host_to_target_num_antennas() -Convert host num antennas to 9189 * target num antennas 9190 * @num_antennas: Host num antennas 9191 * 9192 * Return: Target num antennas 9193 */ 9194 static WMI_NUM_ANTENNAS convert_host_to_target_num_antennas( 9195 WMI_HOST_NUM_ANTENNAS num_antennas) 9196 { 9197 switch (num_antennas) { 9198 case WMI_HOST_SISO: 9199 return WMI_SISO; 9200 case WMI_HOST_MIMO_2X2: 9201 return WMI_MIMO_2X2; 9202 default: 9203 return WMI_SISO; 9204 } 9205 } 9206 9207 /** 9208 * convert_host_to_target_band_capability() -Convert host band capability to 9209 * target band capability 9210 * @host_band_capability: Host band capability 9211 * 9212 * Return: Target band capability bitmap 9213 */ 9214 static uint8_t 9215 convert_host_to_target_band_capability(uint32_t host_band_capability) 9216 { 9217 uint8_t band_capability; 9218 9219 band_capability = (host_band_capability & WMI_HOST_BAND_CAP_2GHZ) | 9220 (host_band_capability & WMI_HOST_BAND_CAP_5GHZ) | 9221 (host_band_capability & WMI_HOST_BAND_CAP_6GHZ); 9222 return band_capability; 9223 } 9224 9225 /** 9226 * copy_feature_set_info() -Copy feaure set info from host to target 9227 * @feature_set_bitmap: Target feature set pointer 9228 * @feature_set: Host feature set structure 9229 * 9230 * Return: None 9231 */ 9232 static inline void copy_feature_set_info(uint32_t *feature_set_bitmap, 9233 struct target_feature_set *feature_set) 9234 { 9235 WMI_NUM_ANTENNAS num_antennas; 9236 WMI_BAND_CONCURRENCY band_concurrency; 9237 WMI_WIFI_STANDARD wifi_standard; 9238 WMI_VENDOR1_REQ1_VERSION vendor1_req1_version; 9239 WMI_VENDOR1_REQ2_VERSION vendor1_req2_version; 9240 uint8_t band_capability; 9241 9242 num_antennas = convert_host_to_target_num_antennas( 9243 feature_set->num_antennas); 9244 band_concurrency = convert_host_to_target_band_concurrency( 9245 feature_set->concurrency_support); 9246 wifi_standard = convert_host_to_target_wifi_standard( 9247 feature_set->wifi_standard); 9248 vendor1_req1_version = convert_host_to_target_vendor1_req1_version( 9249 feature_set->vendor_req_1_version); 9250 vendor1_req2_version = convert_host_to_target_vendor1_req2_version( 9251 feature_set->vendor_req_2_version); 9252 9253 band_capability = 9254 convert_host_to_target_band_capability( 9255 feature_set->band_capability); 9256 9257 WMI_SET_WIFI_STANDARD(feature_set_bitmap, wifi_standard); 9258 WMI_SET_BAND_CONCURRENCY_SUPPORT(feature_set_bitmap, band_concurrency); 9259 WMI_SET_PNO_SCAN_IN_UNASSOC_STATE(feature_set_bitmap, 9260 feature_set->pno_in_unassoc_state); 9261 WMI_SET_PNO_SCAN_IN_ASSOC_STATE(feature_set_bitmap, 9262 feature_set->pno_in_assoc_state); 9263 WMI_SET_TWT_FEATURE_SUPPORT(feature_set_bitmap, 9264 feature_set->enable_twt); 9265 WMI_SET_TWT_REQUESTER(feature_set_bitmap, 9266 feature_set->enable_twt_requester); 9267 WMI_SET_TWT_BROADCAST(feature_set_bitmap, 9268 feature_set->enable_twt_broadcast); 9269 WMI_SET_TWT_FLEXIBLE(feature_set_bitmap, 9270 feature_set->enable_twt_flexible); 9271 WMI_SET_WIFI_OPT_FEATURE_SUPPORT(feature_set_bitmap, 9272 feature_set->enable_wifi_optimizer); 9273 WMI_SET_RFC8325_FEATURE_SUPPORT(feature_set_bitmap, 9274 feature_set->enable_rfc835); 9275 WMI_SET_MHS_5G_SUPPORT(feature_set_bitmap, 9276 feature_set->sap_5g_supported); 9277 WMI_SET_MHS_6G_SUPPORT(feature_set_bitmap, 9278 feature_set->sap_6g_supported); 9279 WMI_SET_MHS_MAX_CLIENTS_SUPPORT(feature_set_bitmap, 9280 feature_set->sap_max_num_clients); 9281 WMI_SET_MHS_SET_COUNTRY_CODE_HAL_SUPPORT( 9282 feature_set_bitmap, 9283 feature_set->set_country_code_hal_supported); 9284 WMI_SET_MHS_GETVALID_CHANNELS_SUPPORT( 9285 feature_set_bitmap, 9286 feature_set->get_valid_channel_supported); 9287 WMI_SET_MHS_DOT11_MODE_SUPPORT(feature_set_bitmap, 9288 feature_set->supported_dot11mode); 9289 WMI_SET_MHS_WPA3_SUPPORT(feature_set_bitmap, 9290 feature_set->sap_wpa3_support); 9291 WMI_SET_VENDOR_REQ_1_VERSION(feature_set_bitmap, vendor1_req1_version); 9292 WMI_SET_ROAMING_HIGH_CU_ROAM_TRIGGER( 9293 feature_set_bitmap, 9294 feature_set->roaming_high_cu_roam_trigger); 9295 WMI_SET_ROAMING_EMERGENCY_TRIGGER( 9296 feature_set_bitmap, 9297 feature_set->roaming_emergency_trigger); 9298 WMI_SET_ROAMING_BTM_TRIGGER(feature_set_bitmap, 9299 feature_set->roaming_btm_trihgger); 9300 WMI_SET_ROAMING_IDLE_TRIGGER(feature_set_bitmap, 9301 feature_set->roaming_idle_trigger); 9302 WMI_SET_ROAMING_WTC_TRIGGER(feature_set_bitmap, 9303 feature_set->roaming_wtc_trigger); 9304 WMI_SET_ROAMING_BTCOEX_TRIGGER(feature_set_bitmap, 9305 feature_set->roaming_btcoex_trigger); 9306 WMI_SET_ROAMING_BTW_WPA_WPA2(feature_set_bitmap, 9307 feature_set->roaming_btw_wpa_wpa2); 9308 WMI_SET_ROAMING_MANAGE_CHAN_LIST_API( 9309 feature_set_bitmap, 9310 feature_set->roaming_manage_chan_list_api); 9311 WMI_SET_ROAMING_ADAPTIVE_11R(feature_set_bitmap, 9312 feature_set->roaming_adaptive_11r); 9313 WMI_SET_ROAMING_CTRL_API_GET_SET(feature_set_bitmap, 9314 feature_set->roaming_ctrl_api_get_set); 9315 WMI_SET_ROAMING_CTRL_API_REASSOC(feature_set_bitmap, 9316 feature_set->roaming_ctrl_api_reassoc); 9317 WMI_SET_ROAMING_CTRL_GET_CU(feature_set_bitmap, 9318 feature_set->roaming_ctrl_get_cu); 9319 WMI_SET_VENDOR_REQ_2_VERSION(feature_set_bitmap, vendor1_req2_version); 9320 WMI_SET_ASSURANCE_DISCONNECT_REASON_API( 9321 feature_set_bitmap, 9322 feature_set->assurance_disconnect_reason_api); 9323 WMI_SET_FRAME_PCAP_LOG_MGMT(feature_set_bitmap, 9324 feature_set->frame_pcap_log_mgmt); 9325 WMI_SET_FRAME_PCAP_LOG_CTRL(feature_set_bitmap, 9326 feature_set->frame_pcap_log_ctrl); 9327 WMI_SET_FRAME_PCAP_LOG_DATA(feature_set_bitmap, 9328 feature_set->frame_pcap_log_data); 9329 WMI_SET_SECURITY_WPA3_SAE_H2E(feature_set_bitmap, 9330 feature_set->security_wpa3_sae_h2e); 9331 WMI_SET_SECURITY_WPA3_SAE_FT(feature_set_bitmap, 9332 feature_set->security_wpa3_sae_ft); 9333 WMI_SET_SECURITY_WPA3_ENTERP_SUITEB( 9334 feature_set_bitmap, 9335 feature_set->security_wpa3_enterp_suitb); 9336 WMI_SET_SECURITY_WPA3_ENTERP_SUITEB_192bit( 9337 feature_set_bitmap, 9338 feature_set->security_wpa3_enterp_suitb_192bit); 9339 WMI_SET_SECURITY_FILS_SHA256(feature_set_bitmap, 9340 feature_set->security_fills_sha_256); 9341 WMI_SET_SECURITY_FILS_SHA384(feature_set_bitmap, 9342 feature_set->security_fills_sha_384); 9343 WMI_SET_SECURITY_FILS_SHA256_FT(feature_set_bitmap, 9344 feature_set->security_fills_sha_256_FT); 9345 WMI_SET_SECURITY_FILS_SHA384_FT(feature_set_bitmap, 9346 feature_set->security_fills_sha_384_FT); 9347 WMI_SET_SECURITY_ENCHANCED_OPEN(feature_set_bitmap, 9348 feature_set->security_enhanced_open); 9349 WMI_SET_NAN_SUPPORT(feature_set_bitmap, feature_set->enable_nan); 9350 WMI_SET_TDLS_SUPPORT(feature_set_bitmap, feature_set->enable_tdls); 9351 WMI_SET_P2P6E_SUPPORT(feature_set_bitmap, feature_set->enable_p2p_6e); 9352 WMI_SET_TDLS_OFFCHAN_SUPPORT(feature_set_bitmap, 9353 feature_set->enable_tdls_offchannel); 9354 WMI_SET_TDLS_CAP_ENHANCE(feature_set_bitmap, 9355 feature_set->enable_tdls_capability_enhance); 9356 WMI_SET_MAX_TDLS_PEERS_SUPPORT(feature_set_bitmap, 9357 feature_set->max_tdls_peers); 9358 WMI_SET_STA_DUAL_P2P_SUPPORT(feature_set_bitmap, 9359 feature_set->sta_dual_p2p_support); 9360 WMI_SET_PEER_BIGDATA_GETBSSINFO_API_SUPPORT( 9361 feature_set_bitmap, 9362 feature_set->peer_bigdata_getbssinfo_support); 9363 WMI_SET_PEER_BIGDATA_GETASSOCREJECTINFO_API_SUPPORT( 9364 feature_set_bitmap, 9365 feature_set->peer_bigdata_assocreject_info_support); 9366 WMI_SET_PEER_BIGDATA_GETSTAINFO_API_SUPPORT( 9367 feature_set_bitmap, 9368 feature_set->peer_getstainfo_support); 9369 WMI_SET_FEATURE_SET_VERSION(feature_set_bitmap, 9370 feature_set->feature_set_version); 9371 WMI_SET_NUM_ANTENNAS(feature_set_bitmap, num_antennas); 9372 WMI_SET_HOST_BAND_CAP(feature_set_bitmap, band_capability); 9373 } 9374 9375 /** 9376 * feature_set_cmd_send_tlv() -Send feature set command 9377 * @wmi_handle: WMI handle 9378 * @feature_set: Feature set structure 9379 * 9380 * Return: QDF_STATUS_SUCCESS on success else reurn failure 9381 */ 9382 static QDF_STATUS feature_set_cmd_send_tlv( 9383 struct wmi_unified *wmi_handle, 9384 struct target_feature_set *feature_set) 9385 { 9386 wmi_pdev_featureset_cmd_fixed_param *cmd; 9387 wmi_buf_t buf; 9388 uint16_t len; 9389 QDF_STATUS ret; 9390 uint8_t *buf_ptr; 9391 uint32_t *feature_set_bitmap; 9392 9393 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE + 9394 WMI_FEATURE_SET_BITMAP_ARRAY_LEN32 * sizeof(uint32_t); 9395 buf = wmi_buf_alloc(wmi_handle, len); 9396 9397 if (!buf) 9398 return QDF_STATUS_E_NOMEM; 9399 9400 wmi_debug("Send feature set param"); 9401 9402 buf_ptr = (uint8_t *)wmi_buf_data(buf); 9403 9404 cmd = (wmi_pdev_featureset_cmd_fixed_param *)wmi_buf_data(buf); 9405 9406 WMITLV_SET_HDR(&cmd->tlv_header, 9407 WMITLV_TAG_STRUC_wmi_pdev_featureset_cmd_fixed_param, 9408 WMITLV_GET_STRUCT_TLVLEN( 9409 wmi_pdev_featureset_cmd_fixed_param)); 9410 9411 feature_set_bitmap = (uint32_t *)(buf_ptr + sizeof(*cmd) + 9412 WMI_TLV_HDR_SIZE); 9413 WMITLV_SET_HDR(buf_ptr + sizeof(*cmd), WMITLV_TAG_ARRAY_UINT32, 9414 (WMI_FEATURE_SET_BITMAP_ARRAY_LEN32 * sizeof(uint32_t))); 9415 copy_feature_set_info(feature_set_bitmap, feature_set); 9416 9417 qdf_trace_hex_dump(QDF_MODULE_ID_WMI, QDF_TRACE_LEVEL_DEBUG, 9418 feature_set_bitmap, 9419 WMI_FEATURE_SET_BITMAP_ARRAY_LEN32 * 9420 sizeof(uint32_t)); 9421 9422 wmi_mtrace(WMI_PDEV_FEATURESET_CMDID, NO_SESSION, 0); 9423 9424 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 9425 WMI_PDEV_FEATURESET_CMDID); 9426 if (QDF_IS_STATUS_ERROR(ret)) 9427 wmi_buf_free(buf); 9428 9429 return ret; 9430 } 9431 #endif 9432 9433 /* copy_hw_mode_id_in_init_cmd() - Helper routine to copy hw_mode in init cmd 9434 * @wmi_handle: pointer to wmi handle 9435 * @buf_ptr: pointer to current position in init command buffer 9436 * @len: pointer to length. This will be updated with current length of cmd 9437 * @param: point host parameters for init command 9438 * 9439 * Return: Updated pointer of buf_ptr. 9440 */ 9441 static inline uint8_t *copy_hw_mode_in_init_cmd(struct wmi_unified *wmi_handle, 9442 uint8_t *buf_ptr, int *len, struct wmi_init_cmd_param *param) 9443 { 9444 uint16_t idx; 9445 9446 if (param->hw_mode_id != WMI_HOST_HW_MODE_MAX) { 9447 wmi_pdev_set_hw_mode_cmd_fixed_param *hw_mode; 9448 wmi_pdev_band_to_mac *band_to_mac; 9449 9450 hw_mode = (wmi_pdev_set_hw_mode_cmd_fixed_param *) 9451 (buf_ptr + sizeof(wmi_init_cmd_fixed_param) + 9452 sizeof(wmi_resource_config) + 9453 WMI_TLV_HDR_SIZE + (param->num_mem_chunks * 9454 sizeof(wlan_host_memory_chunk))); 9455 9456 WMITLV_SET_HDR(&hw_mode->tlv_header, 9457 WMITLV_TAG_STRUC_wmi_pdev_set_hw_mode_cmd_fixed_param, 9458 (WMITLV_GET_STRUCT_TLVLEN 9459 (wmi_pdev_set_hw_mode_cmd_fixed_param))); 9460 9461 hw_mode->hw_mode_index = param->hw_mode_id; 9462 hw_mode->num_band_to_mac = param->num_band_to_mac; 9463 9464 buf_ptr = (uint8_t *) (hw_mode + 1); 9465 band_to_mac = (wmi_pdev_band_to_mac *) (buf_ptr + 9466 WMI_TLV_HDR_SIZE); 9467 for (idx = 0; idx < param->num_band_to_mac; idx++) { 9468 WMITLV_SET_HDR(&band_to_mac[idx].tlv_header, 9469 WMITLV_TAG_STRUC_wmi_pdev_band_to_mac, 9470 WMITLV_GET_STRUCT_TLVLEN 9471 (wmi_pdev_band_to_mac)); 9472 band_to_mac[idx].pdev_id = 9473 wmi_handle->ops->convert_pdev_id_host_to_target( 9474 wmi_handle, 9475 param->band_to_mac[idx].pdev_id); 9476 band_to_mac[idx].start_freq = 9477 param->band_to_mac[idx].start_freq; 9478 band_to_mac[idx].end_freq = 9479 param->band_to_mac[idx].end_freq; 9480 } 9481 *len += sizeof(wmi_pdev_set_hw_mode_cmd_fixed_param) + 9482 (param->num_band_to_mac * 9483 sizeof(wmi_pdev_band_to_mac)) + 9484 WMI_TLV_HDR_SIZE; 9485 9486 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 9487 (param->num_band_to_mac * 9488 sizeof(wmi_pdev_band_to_mac))); 9489 } 9490 9491 return buf_ptr; 9492 } 9493 9494 static inline void copy_fw_abi_version_tlv(wmi_unified_t wmi_handle, 9495 wmi_init_cmd_fixed_param *cmd) 9496 { 9497 int num_allowlist; 9498 wmi_abi_version my_vers; 9499 9500 num_allowlist = sizeof(version_whitelist) / 9501 sizeof(wmi_whitelist_version_info); 9502 my_vers.abi_version_0 = WMI_ABI_VERSION_0; 9503 my_vers.abi_version_1 = WMI_ABI_VERSION_1; 9504 my_vers.abi_version_ns_0 = WMI_ABI_VERSION_NS_0; 9505 my_vers.abi_version_ns_1 = WMI_ABI_VERSION_NS_1; 9506 my_vers.abi_version_ns_2 = WMI_ABI_VERSION_NS_2; 9507 my_vers.abi_version_ns_3 = WMI_ABI_VERSION_NS_3; 9508 9509 wmi_cmp_and_set_abi_version(num_allowlist, version_whitelist, 9510 &my_vers, 9511 (struct _wmi_abi_version *)&wmi_handle->fw_abi_version, 9512 &cmd->host_abi_vers); 9513 9514 qdf_print("%s: INIT_CMD version: %d, %d, 0x%x, 0x%x, 0x%x, 0x%x", 9515 __func__, 9516 WMI_VER_GET_MAJOR(cmd->host_abi_vers.abi_version_0), 9517 WMI_VER_GET_MINOR(cmd->host_abi_vers.abi_version_0), 9518 cmd->host_abi_vers.abi_version_ns_0, 9519 cmd->host_abi_vers.abi_version_ns_1, 9520 cmd->host_abi_vers.abi_version_ns_2, 9521 cmd->host_abi_vers.abi_version_ns_3); 9522 9523 /* Save version sent from host - 9524 * Will be used to check ready event 9525 */ 9526 qdf_mem_copy(&wmi_handle->final_abi_vers, &cmd->host_abi_vers, 9527 sizeof(wmi_abi_version)); 9528 } 9529 9530 /* 9531 * send_cfg_action_frm_tb_ppdu_cmd_tlv() - send action frame tb ppdu cfg to FW 9532 * @wmi_handle: Pointer to WMi handle 9533 * @ie_data: Pointer for ie data 9534 * 9535 * This function sends action frame tb ppdu cfg to FW 9536 * 9537 * Return: QDF_STATUS_SUCCESS for success otherwise failure 9538 * 9539 */ 9540 static QDF_STATUS send_cfg_action_frm_tb_ppdu_cmd_tlv(wmi_unified_t wmi_handle, 9541 struct cfg_action_frm_tb_ppdu_param *cfg_msg) 9542 { 9543 wmi_pdev_he_tb_action_frm_cmd_fixed_param *cmd; 9544 wmi_buf_t buf; 9545 uint8_t *buf_ptr; 9546 uint32_t len, frm_len_aligned; 9547 QDF_STATUS ret; 9548 9549 frm_len_aligned = roundup(cfg_msg->frm_len, sizeof(uint32_t)); 9550 /* Allocate memory for the WMI command */ 9551 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE + frm_len_aligned; 9552 9553 buf = wmi_buf_alloc(wmi_handle, len); 9554 if (!buf) 9555 return QDF_STATUS_E_NOMEM; 9556 9557 buf_ptr = wmi_buf_data(buf); 9558 qdf_mem_zero(buf_ptr, len); 9559 9560 /* Populate the WMI command */ 9561 cmd = (wmi_pdev_he_tb_action_frm_cmd_fixed_param *)buf_ptr; 9562 9563 WMITLV_SET_HDR(&cmd->tlv_header, 9564 WMITLV_TAG_STRUC_wmi_pdev_he_tb_action_frm_cmd_fixed_param, 9565 WMITLV_GET_STRUCT_TLVLEN( 9566 wmi_pdev_he_tb_action_frm_cmd_fixed_param)); 9567 cmd->enable = cfg_msg->cfg; 9568 cmd->data_len = cfg_msg->frm_len; 9569 9570 buf_ptr += sizeof(*cmd); 9571 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, frm_len_aligned); 9572 buf_ptr += WMI_TLV_HDR_SIZE; 9573 9574 qdf_mem_copy(buf_ptr, cfg_msg->data, cmd->data_len); 9575 9576 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 9577 WMI_PDEV_HE_TB_ACTION_FRM_CMDID); 9578 if (QDF_IS_STATUS_ERROR(ret)) { 9579 wmi_err("HE TB action frame cmnd send fail, ret %d", ret); 9580 wmi_buf_free(buf); 9581 } 9582 9583 return ret; 9584 } 9585 9586 static QDF_STATUS save_fw_version_cmd_tlv(wmi_unified_t wmi_handle, void *evt_buf) 9587 { 9588 WMI_SERVICE_READY_EVENTID_param_tlvs *param_buf; 9589 wmi_service_ready_event_fixed_param *ev; 9590 9591 9592 param_buf = (WMI_SERVICE_READY_EVENTID_param_tlvs *) evt_buf; 9593 9594 ev = (wmi_service_ready_event_fixed_param *) param_buf->fixed_param; 9595 if (!ev) 9596 return QDF_STATUS_E_FAILURE; 9597 9598 /*Save fw version from service ready message */ 9599 /*This will be used while sending INIT message */ 9600 qdf_mem_copy(&wmi_handle->fw_abi_version, &ev->fw_abi_vers, 9601 sizeof(wmi_handle->fw_abi_version)); 9602 9603 return QDF_STATUS_SUCCESS; 9604 } 9605 9606 /** 9607 * wmi_unified_save_fw_version_cmd() - save fw version 9608 * @wmi_handle: pointer to wmi handle 9609 * @res_cfg: resource config 9610 * @num_mem_chunks: no of mem chunck 9611 * @mem_chunk: pointer to mem chunck structure 9612 * 9613 * This function sends IE information to firmware 9614 * 9615 * Return: QDF_STATUS_SUCCESS for success otherwise failure 9616 * 9617 */ 9618 static QDF_STATUS check_and_update_fw_version_cmd_tlv(wmi_unified_t wmi_handle, 9619 void *evt_buf) 9620 { 9621 WMI_READY_EVENTID_param_tlvs *param_buf = NULL; 9622 wmi_ready_event_fixed_param *ev = NULL; 9623 9624 param_buf = (WMI_READY_EVENTID_param_tlvs *) evt_buf; 9625 ev = param_buf->fixed_param; 9626 if (!wmi_versions_are_compatible((struct _wmi_abi_version *) 9627 &wmi_handle->final_abi_vers, 9628 &ev->fw_abi_vers)) { 9629 /* 9630 * Error: Our host version and the given firmware version 9631 * are incompatible. 9632 **/ 9633 wmi_debug("Error: Incompatible WMI version." 9634 "Host: %d,%d,0x%x 0x%x 0x%x 0x%x, FW: %d,%d,0x%x 0x%x 0x%x 0x%x", 9635 WMI_VER_GET_MAJOR(wmi_handle->final_abi_vers. 9636 abi_version_0), 9637 WMI_VER_GET_MINOR(wmi_handle->final_abi_vers. 9638 abi_version_0), 9639 wmi_handle->final_abi_vers.abi_version_ns_0, 9640 wmi_handle->final_abi_vers.abi_version_ns_1, 9641 wmi_handle->final_abi_vers.abi_version_ns_2, 9642 wmi_handle->final_abi_vers.abi_version_ns_3, 9643 WMI_VER_GET_MAJOR(ev->fw_abi_vers.abi_version_0), 9644 WMI_VER_GET_MINOR(ev->fw_abi_vers.abi_version_0), 9645 ev->fw_abi_vers.abi_version_ns_0, 9646 ev->fw_abi_vers.abi_version_ns_1, 9647 ev->fw_abi_vers.abi_version_ns_2, 9648 ev->fw_abi_vers.abi_version_ns_3); 9649 9650 return QDF_STATUS_E_FAILURE; 9651 } 9652 qdf_mem_copy(&wmi_handle->final_abi_vers, &ev->fw_abi_vers, 9653 sizeof(wmi_abi_version)); 9654 qdf_mem_copy(&wmi_handle->fw_abi_version, &ev->fw_abi_vers, 9655 sizeof(wmi_abi_version)); 9656 9657 return QDF_STATUS_SUCCESS; 9658 } 9659 9660 /** 9661 * send_log_supported_evt_cmd_tlv() - Enable/Disable FW diag/log events 9662 * @handle: wmi handle 9663 * @event: Event received from FW 9664 * @len: Length of the event 9665 * 9666 * Enables the low frequency events and disables the high frequency 9667 * events. Bit 17 indicates if the event if low/high frequency. 9668 * 1 - high frequency, 0 - low frequency 9669 * 9670 * Return: 0 on successfully enabling/disabling the events 9671 */ 9672 static QDF_STATUS send_log_supported_evt_cmd_tlv(wmi_unified_t wmi_handle, 9673 uint8_t *event, 9674 uint32_t len) 9675 { 9676 uint32_t num_of_diag_events_logs; 9677 wmi_diag_event_log_config_fixed_param *cmd; 9678 wmi_buf_t buf; 9679 uint8_t *buf_ptr; 9680 uint32_t *cmd_args, *evt_args; 9681 uint32_t buf_len, i; 9682 9683 WMI_DIAG_EVENT_LOG_SUPPORTED_EVENTID_param_tlvs *param_buf; 9684 wmi_diag_event_log_supported_event_fixed_params *wmi_event; 9685 9686 wmi_debug("Received WMI_DIAG_EVENT_LOG_SUPPORTED_EVENTID"); 9687 9688 param_buf = (WMI_DIAG_EVENT_LOG_SUPPORTED_EVENTID_param_tlvs *) event; 9689 if (!param_buf) { 9690 wmi_err("Invalid log supported event buffer"); 9691 return QDF_STATUS_E_INVAL; 9692 } 9693 wmi_event = param_buf->fixed_param; 9694 num_of_diag_events_logs = wmi_event->num_of_diag_events_logs; 9695 9696 if (num_of_diag_events_logs > 9697 param_buf->num_diag_events_logs_list) { 9698 wmi_err("message number of events %d is more than tlv hdr content %d", 9699 num_of_diag_events_logs, 9700 param_buf->num_diag_events_logs_list); 9701 return QDF_STATUS_E_INVAL; 9702 } 9703 9704 evt_args = param_buf->diag_events_logs_list; 9705 if (!evt_args) { 9706 wmi_err("Event list is empty, num_of_diag_events_logs=%d", 9707 num_of_diag_events_logs); 9708 return QDF_STATUS_E_INVAL; 9709 } 9710 9711 wmi_debug("num_of_diag_events_logs=%d", num_of_diag_events_logs); 9712 9713 /* Free any previous allocation */ 9714 if (wmi_handle->events_logs_list) { 9715 qdf_mem_free(wmi_handle->events_logs_list); 9716 wmi_handle->events_logs_list = NULL; 9717 } 9718 9719 if (num_of_diag_events_logs > 9720 (WMI_SVC_MSG_MAX_SIZE / sizeof(uint32_t))) { 9721 wmi_err("excess num of logs: %d", num_of_diag_events_logs); 9722 QDF_ASSERT(0); 9723 return QDF_STATUS_E_INVAL; 9724 } 9725 /* Store the event list for run time enable/disable */ 9726 wmi_handle->events_logs_list = qdf_mem_malloc(num_of_diag_events_logs * 9727 sizeof(uint32_t)); 9728 if (!wmi_handle->events_logs_list) 9729 return QDF_STATUS_E_NOMEM; 9730 9731 wmi_handle->num_of_diag_events_logs = num_of_diag_events_logs; 9732 9733 /* Prepare the send buffer */ 9734 buf_len = sizeof(*cmd) + WMI_TLV_HDR_SIZE + 9735 (num_of_diag_events_logs * sizeof(uint32_t)); 9736 9737 buf = wmi_buf_alloc(wmi_handle, buf_len); 9738 if (!buf) { 9739 qdf_mem_free(wmi_handle->events_logs_list); 9740 wmi_handle->events_logs_list = NULL; 9741 return QDF_STATUS_E_NOMEM; 9742 } 9743 9744 cmd = (wmi_diag_event_log_config_fixed_param *) wmi_buf_data(buf); 9745 buf_ptr = (uint8_t *) cmd; 9746 9747 WMITLV_SET_HDR(&cmd->tlv_header, 9748 WMITLV_TAG_STRUC_wmi_diag_event_log_config_fixed_param, 9749 WMITLV_GET_STRUCT_TLVLEN( 9750 wmi_diag_event_log_config_fixed_param)); 9751 9752 cmd->num_of_diag_events_logs = num_of_diag_events_logs; 9753 9754 buf_ptr += sizeof(wmi_diag_event_log_config_fixed_param); 9755 9756 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, 9757 (num_of_diag_events_logs * sizeof(uint32_t))); 9758 9759 cmd_args = (uint32_t *) (buf_ptr + WMI_TLV_HDR_SIZE); 9760 9761 /* Populate the events */ 9762 for (i = 0; i < num_of_diag_events_logs; i++) { 9763 /* Low freq (0) - Enable (1) the event 9764 * High freq (1) - Disable (0) the event 9765 */ 9766 WMI_DIAG_ID_ENABLED_DISABLED_SET(cmd_args[i], 9767 !(WMI_DIAG_FREQUENCY_GET(evt_args[i]))); 9768 /* Set the event ID */ 9769 WMI_DIAG_ID_SET(cmd_args[i], 9770 WMI_DIAG_ID_GET(evt_args[i])); 9771 /* Set the type */ 9772 WMI_DIAG_TYPE_SET(cmd_args[i], 9773 WMI_DIAG_TYPE_GET(evt_args[i])); 9774 /* Storing the event/log list in WMI */ 9775 wmi_handle->events_logs_list[i] = evt_args[i]; 9776 } 9777 9778 wmi_mtrace(WMI_DIAG_EVENT_LOG_CONFIG_CMDID, NO_SESSION, 0); 9779 if (wmi_unified_cmd_send(wmi_handle, buf, buf_len, 9780 WMI_DIAG_EVENT_LOG_CONFIG_CMDID)) { 9781 wmi_err("WMI_DIAG_EVENT_LOG_CONFIG_CMDID failed"); 9782 wmi_buf_free(buf); 9783 /* Not clearing events_logs_list, though wmi cmd failed. 9784 * Host can still have this list 9785 */ 9786 return QDF_STATUS_E_INVAL; 9787 } 9788 9789 return 0; 9790 } 9791 9792 /** 9793 * send_enable_specific_fw_logs_cmd_tlv() - Start/Stop logging of diag log id 9794 * @wmi_handle: wmi handle 9795 * @start_log: Start logging related parameters 9796 * 9797 * Send the command to the FW based on which specific logging of diag 9798 * event/log id can be started/stopped 9799 * 9800 * Return: None 9801 */ 9802 static QDF_STATUS send_enable_specific_fw_logs_cmd_tlv(wmi_unified_t wmi_handle, 9803 struct wmi_wifi_start_log *start_log) 9804 { 9805 wmi_diag_event_log_config_fixed_param *cmd; 9806 wmi_buf_t buf; 9807 uint8_t *buf_ptr; 9808 uint32_t len, count, log_level, i; 9809 uint32_t *cmd_args; 9810 uint32_t total_len; 9811 count = 0; 9812 9813 if (!wmi_handle->events_logs_list) { 9814 wmi_debug("Not received event/log list from FW, yet"); 9815 return QDF_STATUS_E_NOMEM; 9816 } 9817 /* total_len stores the number of events where BITS 17 and 18 are set. 9818 * i.e., events of high frequency (17) and for extended debugging (18) 9819 */ 9820 total_len = 0; 9821 for (i = 0; i < wmi_handle->num_of_diag_events_logs; i++) { 9822 if ((WMI_DIAG_FREQUENCY_GET(wmi_handle->events_logs_list[i])) && 9823 (WMI_DIAG_EXT_FEATURE_GET(wmi_handle->events_logs_list[i]))) 9824 total_len++; 9825 } 9826 9827 len = sizeof(*cmd) + WMI_TLV_HDR_SIZE + 9828 (total_len * sizeof(uint32_t)); 9829 9830 buf = wmi_buf_alloc(wmi_handle, len); 9831 if (!buf) 9832 return QDF_STATUS_E_NOMEM; 9833 9834 cmd = (wmi_diag_event_log_config_fixed_param *) wmi_buf_data(buf); 9835 buf_ptr = (uint8_t *) cmd; 9836 9837 WMITLV_SET_HDR(&cmd->tlv_header, 9838 WMITLV_TAG_STRUC_wmi_diag_event_log_config_fixed_param, 9839 WMITLV_GET_STRUCT_TLVLEN( 9840 wmi_diag_event_log_config_fixed_param)); 9841 9842 cmd->num_of_diag_events_logs = total_len; 9843 9844 buf_ptr += sizeof(wmi_diag_event_log_config_fixed_param); 9845 9846 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, 9847 (total_len * sizeof(uint32_t))); 9848 9849 cmd_args = (uint32_t *) (buf_ptr + WMI_TLV_HDR_SIZE); 9850 9851 if (start_log->verbose_level >= WMI_LOG_LEVEL_ACTIVE) 9852 log_level = 1; 9853 else 9854 log_level = 0; 9855 9856 wmi_debug("Length: %d Log_level: %d", total_len, log_level); 9857 for (i = 0; i < wmi_handle->num_of_diag_events_logs; i++) { 9858 uint32_t val = wmi_handle->events_logs_list[i]; 9859 if ((WMI_DIAG_FREQUENCY_GET(val)) && 9860 (WMI_DIAG_EXT_FEATURE_GET(val))) { 9861 9862 WMI_DIAG_ID_SET(cmd_args[count], 9863 WMI_DIAG_ID_GET(val)); 9864 WMI_DIAG_TYPE_SET(cmd_args[count], 9865 WMI_DIAG_TYPE_GET(val)); 9866 WMI_DIAG_ID_ENABLED_DISABLED_SET(cmd_args[count], 9867 log_level); 9868 wmi_debug("Idx:%d, val:%x", i, val); 9869 count++; 9870 } 9871 } 9872 9873 wmi_mtrace(WMI_DIAG_EVENT_LOG_CONFIG_CMDID, NO_SESSION, 0); 9874 if (wmi_unified_cmd_send(wmi_handle, buf, len, 9875 WMI_DIAG_EVENT_LOG_CONFIG_CMDID)) { 9876 wmi_err("WMI_DIAG_EVENT_LOG_CONFIG_CMDID failed"); 9877 wmi_buf_free(buf); 9878 return QDF_STATUS_E_INVAL; 9879 } 9880 9881 return QDF_STATUS_SUCCESS; 9882 } 9883 9884 /** 9885 * send_flush_logs_to_fw_cmd_tlv() - Send log flush command to FW 9886 * @wmi_handle: WMI handle 9887 * 9888 * This function is used to send the flush command to the FW, 9889 * that will flush the fw logs that are residue in the FW 9890 * 9891 * Return: None 9892 */ 9893 static QDF_STATUS send_flush_logs_to_fw_cmd_tlv(wmi_unified_t wmi_handle) 9894 { 9895 wmi_debug_mesg_flush_fixed_param *cmd; 9896 wmi_buf_t buf; 9897 int len = sizeof(*cmd); 9898 QDF_STATUS ret; 9899 9900 buf = wmi_buf_alloc(wmi_handle, len); 9901 if (!buf) 9902 return QDF_STATUS_E_NOMEM; 9903 9904 cmd = (wmi_debug_mesg_flush_fixed_param *) wmi_buf_data(buf); 9905 WMITLV_SET_HDR(&cmd->tlv_header, 9906 WMITLV_TAG_STRUC_wmi_debug_mesg_flush_fixed_param, 9907 WMITLV_GET_STRUCT_TLVLEN( 9908 wmi_debug_mesg_flush_fixed_param)); 9909 cmd->reserved0 = 0; 9910 9911 wmi_mtrace(WMI_DEBUG_MESG_FLUSH_CMDID, NO_SESSION, 0); 9912 ret = wmi_unified_cmd_send(wmi_handle, 9913 buf, 9914 len, 9915 WMI_DEBUG_MESG_FLUSH_CMDID); 9916 if (QDF_IS_STATUS_ERROR(ret)) { 9917 wmi_err("Failed to send WMI_DEBUG_MESG_FLUSH_CMDID"); 9918 wmi_buf_free(buf); 9919 return QDF_STATUS_E_INVAL; 9920 } 9921 wmi_debug("Sent WMI_DEBUG_MESG_FLUSH_CMDID to FW"); 9922 9923 return ret; 9924 } 9925 9926 #ifdef BIG_ENDIAN_HOST 9927 #ifdef WLAN_FEATURE_FIPS_BER_CCMGCM 9928 /** 9929 * fips_extend_align_data_be() - LE to BE conversion of FIPS extend ev data 9930 * @param - fips extend param related parameters 9931 * 9932 * Return: QDF_STATUS - success or error status 9933 */ 9934 static QDF_STATUS fips_extend_align_data_be(wmi_unified_t wmi_handle, 9935 struct fips_extend_params *param) 9936 { 9937 unsigned char *key_unaligned, *nonce_iv_unaligned, *data_unaligned; 9938 int c; 9939 u_int8_t *key_aligned = NULL; 9940 u_int8_t *nonce_iv_aligned = NULL; 9941 u_int8_t *data_aligned = NULL; 9942 int ret = QDF_STATUS_SUCCESS; 9943 9944 /* Assigning unaligned space to copy the key */ 9945 key_unaligned = qdf_mem_malloc(sizeof(u_int8_t) * 9946 param->cmd_params.key_len + FIPS_ALIGN); 9947 /* Checking if kmalloc is successful to allocate space */ 9948 if (!key_unaligned) 9949 return QDF_STATUS_E_INVAL; 9950 9951 data_unaligned = qdf_mem_malloc(sizeof(u_int8_t) * param->data_len + 9952 FIPS_ALIGN); 9953 /* Checking if kmalloc is successful to allocate space */ 9954 if (!data_unaligned) { 9955 ret = QDF_STATUS_E_INVAL; 9956 goto fips_align_fail_data; 9957 } 9958 9959 /* Checking if space is aligned */ 9960 if (!FIPS_IS_ALIGNED(key_unaligned, FIPS_ALIGN)) { 9961 /* align to 4 */ 9962 key_aligned = (u_int8_t *)FIPS_ALIGNTO(key_unaligned, 9963 FIPS_ALIGN); 9964 } else { 9965 key_aligned = (u_int8_t *)key_unaligned; 9966 } 9967 9968 /* memset and copy content from key to key aligned */ 9969 OS_MEMSET(key_aligned, 0, param->cmd_params.key_len); 9970 OS_MEMCPY(key_aligned, param->cmd_params.key, 9971 param->cmd_params.key_len); 9972 9973 /* print a hexdump for host debug */ 9974 wmi_debug("Aligned and Copied Key: "); 9975 qdf_trace_hex_dump(QDF_MODULE_ID_WMI, QDF_TRACE_LEVEL_DEBUG, 9976 key_aligned, param->cmd_params.key_len); 9977 9978 /* Checking of space is aligned */ 9979 if (!FIPS_IS_ALIGNED(data_unaligned, FIPS_ALIGN)) { 9980 /* align to 4 */ 9981 data_aligned = 9982 (u_int8_t *)FIPS_ALIGNTO(data_unaligned, FIPS_ALIGN); 9983 } else { 9984 data_aligned = (u_int8_t *)data_unaligned; 9985 } 9986 9987 /* memset and copy content from data to data aligned */ 9988 OS_MEMSET(data_aligned, 0, param->data_len); 9989 OS_MEMCPY(data_aligned, param->data, param->data_len); 9990 9991 /* print a hexdump for host debug */ 9992 wmi_debug("\t Properly Aligned and Copied Data: "); 9993 qdf_trace_hex_dump(QDF_MODULE_ID_WMI, QDF_TRACE_LEVEL_DEBUG, 9994 data_aligned, param->data_len); 9995 9996 /* converting to little Endian */ 9997 for (c = 0; c < param->cmd_params.key_len / 4; c++) { 9998 *((u_int32_t *)key_aligned + c) = 9999 qdf_cpu_to_le32(*((u_int32_t *)key_aligned + c)); 10000 } 10001 for (c = 0; c < param->data_len / 4; c++) { 10002 *((u_int32_t *)data_aligned + c) = 10003 qdf_cpu_to_le32(*((u_int32_t *)data_aligned + c)); 10004 } 10005 10006 /* update endian data */ 10007 OS_MEMCPY(param->cmd_params.key, key_aligned, 10008 param->cmd_params.key_len); 10009 OS_MEMCPY(param->data, data_aligned, param->data_len); 10010 10011 if (param->cmd_params.nonce_iv_len) { 10012 nonce_iv_unaligned = qdf_mem_malloc(sizeof(u_int8_t) * 10013 param->cmd_params.nonce_iv_len + 10014 FIPS_ALIGN); 10015 10016 /* Checking if kmalloc is successful to allocate space */ 10017 if (!nonce_iv_unaligned) { 10018 ret = QDF_STATUS_E_INVAL; 10019 goto fips_align_fail_nonce_iv; 10020 } 10021 /* Checking if space is aligned */ 10022 if (!FIPS_IS_ALIGNED(nonce_iv_unaligned, FIPS_ALIGN)) { 10023 /* align to 4 */ 10024 nonce_iv_aligned = 10025 (u_int8_t *)FIPS_ALIGNTO(nonce_iv_unaligned, 10026 FIPS_ALIGN); 10027 } else { 10028 nonce_iv_aligned = (u_int8_t *)nonce_iv_unaligned; 10029 } 10030 10031 /* memset and copy content from iv to iv aligned */ 10032 OS_MEMSET(nonce_iv_aligned, 0, param->cmd_params.nonce_iv_len); 10033 OS_MEMCPY(nonce_iv_aligned, param->cmd_params.nonce_iv, 10034 param->cmd_params.nonce_iv_len); 10035 10036 /* print a hexdump for host debug */ 10037 wmi_debug("\t Aligned and Copied Nonce_IV: "); 10038 qdf_trace_hex_dump(QDF_MODULE_ID_WMI, QDF_TRACE_LEVEL_DEBUG, 10039 nonce_iv_aligned, 10040 param->cmd_params.nonce_iv_len); 10041 10042 for (c = 0; c < param->cmd_params.nonce_iv_len / 4; c++) { 10043 *((u_int32_t *)nonce_iv_aligned + c) = 10044 qdf_cpu_to_le32(*((u_int32_t *)nonce_iv_aligned + c)); 10045 } 10046 } 10047 10048 /* clean up allocated spaces */ 10049 qdf_mem_free(nonce_iv_unaligned); 10050 nonce_iv_unaligned = NULL; 10051 nonce_iv_aligned = NULL; 10052 10053 fips_align_fail_nonce_iv: 10054 qdf_mem_free(data_unaligned); 10055 data_unaligned = NULL; 10056 data_aligned = NULL; 10057 10058 fips_align_fail_data: 10059 qdf_mem_free(key_unaligned); 10060 key_unaligned = NULL; 10061 key_aligned = NULL; 10062 10063 return ret; 10064 } 10065 #endif 10066 10067 static QDF_STATUS fips_align_data_be(wmi_unified_t wmi_handle, 10068 struct fips_params *param) 10069 { 10070 unsigned char *key_unaligned, *data_unaligned; 10071 int c; 10072 u_int8_t *key_aligned = NULL; 10073 u_int8_t *data_aligned = NULL; 10074 10075 /* Assigning unaligned space to copy the key */ 10076 key_unaligned = qdf_mem_malloc( 10077 sizeof(u_int8_t)*param->key_len + FIPS_ALIGN); 10078 data_unaligned = qdf_mem_malloc( 10079 sizeof(u_int8_t)*param->data_len + FIPS_ALIGN); 10080 10081 /* Checking if kmalloc is successful to allocate space */ 10082 if (!key_unaligned) 10083 return QDF_STATUS_SUCCESS; 10084 /* Checking if space is aligned */ 10085 if (!FIPS_IS_ALIGNED(key_unaligned, FIPS_ALIGN)) { 10086 /* align to 4 */ 10087 key_aligned = 10088 (u_int8_t *)FIPS_ALIGNTO(key_unaligned, 10089 FIPS_ALIGN); 10090 } else { 10091 key_aligned = (u_int8_t *)key_unaligned; 10092 } 10093 10094 /* memset and copy content from key to key aligned */ 10095 OS_MEMSET(key_aligned, 0, param->key_len); 10096 OS_MEMCPY(key_aligned, param->key, param->key_len); 10097 10098 /* print a hexdump for host debug */ 10099 print_hex_dump(KERN_DEBUG, 10100 "\t Aligned and Copied Key:@@@@ ", 10101 DUMP_PREFIX_NONE, 10102 16, 1, key_aligned, param->key_len, true); 10103 10104 /* Checking if kmalloc is successful to allocate space */ 10105 if (!data_unaligned) 10106 return QDF_STATUS_SUCCESS; 10107 /* Checking of space is aligned */ 10108 if (!FIPS_IS_ALIGNED(data_unaligned, FIPS_ALIGN)) { 10109 /* align to 4 */ 10110 data_aligned = 10111 (u_int8_t *)FIPS_ALIGNTO(data_unaligned, 10112 FIPS_ALIGN); 10113 } else { 10114 data_aligned = (u_int8_t *)data_unaligned; 10115 } 10116 10117 /* memset and copy content from data to data aligned */ 10118 OS_MEMSET(data_aligned, 0, param->data_len); 10119 OS_MEMCPY(data_aligned, param->data, param->data_len); 10120 10121 /* print a hexdump for host debug */ 10122 print_hex_dump(KERN_DEBUG, 10123 "\t Properly Aligned and Copied Data:@@@@ ", 10124 DUMP_PREFIX_NONE, 10125 16, 1, data_aligned, param->data_len, true); 10126 10127 /* converting to little Endian both key_aligned and 10128 * data_aligned*/ 10129 for (c = 0; c < param->key_len/4; c++) { 10130 *((u_int32_t *)key_aligned+c) = 10131 qdf_cpu_to_le32(*((u_int32_t *)key_aligned+c)); 10132 } 10133 for (c = 0; c < param->data_len/4; c++) { 10134 *((u_int32_t *)data_aligned+c) = 10135 qdf_cpu_to_le32(*((u_int32_t *)data_aligned+c)); 10136 } 10137 10138 /* update endian data to key and data vectors */ 10139 OS_MEMCPY(param->key, key_aligned, param->key_len); 10140 OS_MEMCPY(param->data, data_aligned, param->data_len); 10141 10142 /* clean up allocated spaces */ 10143 qdf_mem_free(key_unaligned); 10144 key_unaligned = NULL; 10145 key_aligned = NULL; 10146 10147 qdf_mem_free(data_unaligned); 10148 data_unaligned = NULL; 10149 data_aligned = NULL; 10150 10151 return QDF_STATUS_SUCCESS; 10152 } 10153 #else 10154 #ifdef WLAN_FEATURE_FIPS_BER_CCMGCM 10155 /** 10156 * fips_extend_align_data_be() - DUMMY for LE platform 10157 * 10158 * Return: QDF_STATUS - success 10159 */ 10160 static QDF_STATUS fips_extend_align_data_be(wmi_unified_t wmi_handle, 10161 struct fips_extend_params *param) 10162 { 10163 return QDF_STATUS_SUCCESS; 10164 } 10165 #endif 10166 10167 /** 10168 * fips_align_data_be() - DUMMY for LE platform 10169 * 10170 * Return: QDF_STATUS - success 10171 */ 10172 static QDF_STATUS fips_align_data_be(wmi_unified_t wmi_handle, 10173 struct fips_params *param) 10174 { 10175 return QDF_STATUS_SUCCESS; 10176 } 10177 #endif 10178 10179 #ifdef WLAN_FEATURE_DISA 10180 /** 10181 * send_encrypt_decrypt_send_cmd() - send encrypt/decrypt cmd to fw 10182 * @wmi_handle: wmi handle 10183 * @params: encrypt/decrypt params 10184 * 10185 * Return: QDF_STATUS_SUCCESS for success or error code 10186 */ 10187 static QDF_STATUS 10188 send_encrypt_decrypt_send_cmd_tlv(wmi_unified_t wmi_handle, 10189 struct disa_encrypt_decrypt_req_params 10190 *encrypt_decrypt_params) 10191 { 10192 wmi_vdev_encrypt_decrypt_data_req_cmd_fixed_param *cmd; 10193 wmi_buf_t wmi_buf; 10194 uint8_t *buf_ptr; 10195 QDF_STATUS ret; 10196 uint32_t len; 10197 10198 wmi_debug("Send encrypt decrypt cmd"); 10199 10200 len = sizeof(*cmd) + 10201 encrypt_decrypt_params->data_len + 10202 WMI_TLV_HDR_SIZE; 10203 wmi_buf = wmi_buf_alloc(wmi_handle, len); 10204 if (!wmi_buf) 10205 return QDF_STATUS_E_NOMEM; 10206 10207 buf_ptr = wmi_buf_data(wmi_buf); 10208 cmd = (wmi_vdev_encrypt_decrypt_data_req_cmd_fixed_param *)buf_ptr; 10209 10210 WMITLV_SET_HDR(&cmd->tlv_header, 10211 WMITLV_TAG_STRUC_wmi_vdev_encrypt_decrypt_data_req_cmd_fixed_param, 10212 WMITLV_GET_STRUCT_TLVLEN( 10213 wmi_vdev_encrypt_decrypt_data_req_cmd_fixed_param)); 10214 10215 cmd->vdev_id = encrypt_decrypt_params->vdev_id; 10216 cmd->key_flag = encrypt_decrypt_params->key_flag; 10217 cmd->key_idx = encrypt_decrypt_params->key_idx; 10218 cmd->key_cipher = encrypt_decrypt_params->key_cipher; 10219 cmd->key_len = encrypt_decrypt_params->key_len; 10220 cmd->key_txmic_len = encrypt_decrypt_params->key_txmic_len; 10221 cmd->key_rxmic_len = encrypt_decrypt_params->key_rxmic_len; 10222 10223 qdf_mem_copy(cmd->key_data, encrypt_decrypt_params->key_data, 10224 encrypt_decrypt_params->key_len); 10225 10226 qdf_mem_copy(cmd->mac_hdr, encrypt_decrypt_params->mac_header, 10227 MAX_MAC_HEADER_LEN); 10228 10229 cmd->data_len = encrypt_decrypt_params->data_len; 10230 10231 if (cmd->data_len) { 10232 buf_ptr += sizeof(*cmd); 10233 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, 10234 roundup(encrypt_decrypt_params->data_len, 10235 sizeof(uint32_t))); 10236 buf_ptr += WMI_TLV_HDR_SIZE; 10237 qdf_mem_copy(buf_ptr, encrypt_decrypt_params->data, 10238 encrypt_decrypt_params->data_len); 10239 } 10240 10241 /* This conversion is to facilitate data to FW in little endian */ 10242 cmd->pn[5] = encrypt_decrypt_params->pn[0]; 10243 cmd->pn[4] = encrypt_decrypt_params->pn[1]; 10244 cmd->pn[3] = encrypt_decrypt_params->pn[2]; 10245 cmd->pn[2] = encrypt_decrypt_params->pn[3]; 10246 cmd->pn[1] = encrypt_decrypt_params->pn[4]; 10247 cmd->pn[0] = encrypt_decrypt_params->pn[5]; 10248 10249 wmi_mtrace(WMI_VDEV_ENCRYPT_DECRYPT_DATA_REQ_CMDID, cmd->vdev_id, 0); 10250 ret = wmi_unified_cmd_send(wmi_handle, 10251 wmi_buf, len, 10252 WMI_VDEV_ENCRYPT_DECRYPT_DATA_REQ_CMDID); 10253 if (QDF_IS_STATUS_ERROR(ret)) { 10254 wmi_err("Failed to send ENCRYPT DECRYPT cmd: %d", ret); 10255 wmi_buf_free(wmi_buf); 10256 } 10257 10258 return ret; 10259 } 10260 #endif /* WLAN_FEATURE_DISA */ 10261 10262 /** 10263 * send_pdev_fips_cmd_tlv() - send pdev fips cmd to fw 10264 * @wmi_handle: wmi handle 10265 * @param: pointer to hold pdev fips param 10266 * 10267 * Return: 0 for success or error code 10268 */ 10269 static QDF_STATUS 10270 send_pdev_fips_cmd_tlv(wmi_unified_t wmi_handle, 10271 struct fips_params *param) 10272 { 10273 wmi_pdev_fips_cmd_fixed_param *cmd; 10274 wmi_buf_t buf; 10275 uint8_t *buf_ptr; 10276 uint32_t len = sizeof(wmi_pdev_fips_cmd_fixed_param); 10277 QDF_STATUS retval = QDF_STATUS_SUCCESS; 10278 10279 /* Length TLV placeholder for array of bytes */ 10280 len += WMI_TLV_HDR_SIZE; 10281 if (param->data_len) 10282 len += (param->data_len*sizeof(uint8_t)); 10283 10284 /* 10285 * Data length must be multiples of 16 bytes - checked against 0xF - 10286 * and must be less than WMI_SVC_MSG_SIZE - static size of 10287 * wmi_pdev_fips_cmd structure 10288 */ 10289 10290 /* do sanity on the input */ 10291 if (!(((param->data_len & 0xF) == 0) && 10292 ((param->data_len > 0) && 10293 (param->data_len < (WMI_HOST_MAX_BUFFER_SIZE - 10294 sizeof(wmi_pdev_fips_cmd_fixed_param)))))) { 10295 return QDF_STATUS_E_INVAL; 10296 } 10297 10298 buf = wmi_buf_alloc(wmi_handle, len); 10299 if (!buf) 10300 return QDF_STATUS_E_FAILURE; 10301 10302 buf_ptr = (uint8_t *) wmi_buf_data(buf); 10303 cmd = (wmi_pdev_fips_cmd_fixed_param *)buf_ptr; 10304 WMITLV_SET_HDR(&cmd->tlv_header, 10305 WMITLV_TAG_STRUC_wmi_pdev_fips_cmd_fixed_param, 10306 WMITLV_GET_STRUCT_TLVLEN 10307 (wmi_pdev_fips_cmd_fixed_param)); 10308 10309 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 10310 wmi_handle, 10311 param->pdev_id); 10312 if (param->key && param->data) { 10313 cmd->key_len = param->key_len; 10314 cmd->data_len = param->data_len; 10315 cmd->fips_cmd = !!(param->op); 10316 10317 if (fips_align_data_be(wmi_handle, param) != QDF_STATUS_SUCCESS) 10318 return QDF_STATUS_E_FAILURE; 10319 10320 qdf_mem_copy(cmd->key, param->key, param->key_len); 10321 10322 if (param->mode == FIPS_ENGINE_AES_CTR || 10323 param->mode == FIPS_ENGINE_AES_MIC) { 10324 cmd->mode = param->mode; 10325 } else { 10326 cmd->mode = FIPS_ENGINE_AES_CTR; 10327 } 10328 qdf_print("Key len = %d, Data len = %d", 10329 cmd->key_len, cmd->data_len); 10330 10331 print_hex_dump(KERN_DEBUG, "Key: ", DUMP_PREFIX_NONE, 16, 1, 10332 cmd->key, cmd->key_len, true); 10333 buf_ptr += sizeof(*cmd); 10334 10335 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, param->data_len); 10336 10337 buf_ptr += WMI_TLV_HDR_SIZE; 10338 if (param->data_len) 10339 qdf_mem_copy(buf_ptr, 10340 (uint8_t *) param->data, param->data_len); 10341 10342 print_hex_dump(KERN_DEBUG, "Plain text: ", DUMP_PREFIX_NONE, 10343 16, 1, buf_ptr, cmd->data_len, true); 10344 10345 buf_ptr += param->data_len; 10346 10347 wmi_mtrace(WMI_PDEV_FIPS_CMDID, NO_SESSION, 0); 10348 retval = wmi_unified_cmd_send(wmi_handle, buf, len, 10349 WMI_PDEV_FIPS_CMDID); 10350 qdf_print("%s return value %d", __func__, retval); 10351 } else { 10352 qdf_print("\n%s:%d Key or Data is NULL", __func__, __LINE__); 10353 wmi_buf_free(buf); 10354 retval = -QDF_STATUS_E_BADMSG; 10355 } 10356 10357 return retval; 10358 } 10359 10360 #ifdef WLAN_FEATURE_FIPS_BER_CCMGCM 10361 /** 10362 * send_pdev_fips_extend_cmd_tlv() - send pdev fips cmd to fw 10363 * @wmi_handle: wmi handle 10364 * @param: pointer to hold pdev fips param 10365 * 10366 * Return: 0 for success or error code 10367 */ 10368 static QDF_STATUS 10369 send_pdev_fips_extend_cmd_tlv(wmi_unified_t wmi_handle, 10370 struct fips_extend_params *param) 10371 { 10372 wmi_pdev_fips_extend_cmd_fixed_param *cmd; 10373 wmi_buf_t buf; 10374 uint8_t *buf_ptr; 10375 uint32_t len = sizeof(wmi_pdev_fips_extend_cmd_fixed_param); 10376 uint32_t data_len_aligned; 10377 QDF_STATUS retval = QDF_STATUS_SUCCESS; 10378 10379 len += WMI_TLV_HDR_SIZE; 10380 if (param->frag_idx == 0) 10381 len += sizeof(wmi_fips_extend_cmd_init_params); 10382 10383 /* Length TLV placeholder for array of bytes */ 10384 len += WMI_TLV_HDR_SIZE; 10385 if (param->data_len) { 10386 data_len_aligned = roundup(param->data_len, sizeof(uint32_t)); 10387 len += (data_len_aligned * sizeof(uint8_t)); 10388 } 10389 10390 buf = wmi_buf_alloc(wmi_handle, len); 10391 if (!buf) 10392 return QDF_STATUS_E_FAILURE; 10393 10394 buf_ptr = (uint8_t *)wmi_buf_data(buf); 10395 cmd = (wmi_pdev_fips_extend_cmd_fixed_param *)buf_ptr; 10396 WMITLV_SET_HDR(&cmd->tlv_header, 10397 WMITLV_TAG_STRUC_wmi_pdev_fips_extend_cmd_fixed_param, 10398 WMITLV_GET_STRUCT_TLVLEN 10399 (wmi_pdev_fips_extend_cmd_fixed_param)); 10400 10401 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 10402 wmi_handle, 10403 param->pdev_id); 10404 10405 cmd->fips_cookie = param->cookie; 10406 cmd->frag_idx = param->frag_idx; 10407 cmd->more_bit = param->more_bit; 10408 cmd->data_len = param->data_len; 10409 10410 if (fips_extend_align_data_be(wmi_handle, param) != 10411 QDF_STATUS_SUCCESS) { 10412 wmi_buf_free(buf); 10413 return QDF_STATUS_E_FAILURE; 10414 } 10415 10416 buf_ptr = (uint8_t *)(cmd + 1); 10417 if (cmd->frag_idx == 0) { 10418 wmi_fips_extend_cmd_init_params *cmd_params; 10419 10420 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 10421 sizeof(wmi_fips_extend_cmd_init_params)); 10422 buf_ptr += WMI_TLV_HDR_SIZE; 10423 cmd_params = (wmi_fips_extend_cmd_init_params *)buf_ptr; 10424 WMITLV_SET_HDR(buf_ptr, 10425 WMITLV_TAG_STRUC_wmi_fips_extend_cmd_init_params, 10426 WMITLV_GET_STRUCT_TLVLEN(wmi_fips_extend_cmd_init_params)); 10427 cmd_params->fips_cmd = param->cmd_params.fips_cmd; 10428 cmd_params->key_cipher = param->cmd_params.key_cipher; 10429 cmd_params->key_len = param->cmd_params.key_len; 10430 cmd_params->nonce_iv_len = param->cmd_params.nonce_iv_len; 10431 cmd_params->tag_len = param->cmd_params.tag_len; 10432 cmd_params->aad_len = param->cmd_params.aad_len; 10433 cmd_params->payload_len = param->cmd_params.payload_len; 10434 10435 qdf_mem_copy(cmd_params->key, param->cmd_params.key, 10436 param->cmd_params.key_len); 10437 qdf_mem_copy(cmd_params->nonce_iv, param->cmd_params.nonce_iv, 10438 param->cmd_params.nonce_iv_len); 10439 10440 wmi_debug("Key len = %d, IVNoncelen = %d, Tlen = %d, Alen = %d, Plen = %d", 10441 cmd_params->key_len, cmd_params->nonce_iv_len, 10442 cmd_params->tag_len, cmd_params->aad_len, 10443 cmd_params->payload_len); 10444 10445 buf_ptr += sizeof(wmi_fips_extend_cmd_init_params); 10446 } else { 10447 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 0); 10448 buf_ptr += WMI_TLV_HDR_SIZE; 10449 } 10450 10451 if (param->data_len && param->data) { 10452 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, 10453 data_len_aligned); 10454 10455 buf_ptr += WMI_TLV_HDR_SIZE; 10456 if (param->data_len) 10457 qdf_mem_copy(buf_ptr, 10458 (uint8_t *)param->data, param->data_len); 10459 10460 wmi_debug("Data: "); 10461 qdf_trace_hex_dump(QDF_MODULE_ID_WMI, QDF_TRACE_LEVEL_DEBUG, 10462 buf_ptr, cmd->data_len); 10463 10464 if (param->data_len) 10465 buf_ptr += param->data_len; 10466 } else { 10467 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, 0); 10468 buf_ptr += WMI_TLV_HDR_SIZE; 10469 } 10470 10471 wmi_mtrace(WMI_PDEV_FIPS_EXTEND_CMDID, NO_SESSION, 0); 10472 retval = wmi_unified_cmd_send(wmi_handle, buf, len, 10473 WMI_PDEV_FIPS_EXTEND_CMDID); 10474 10475 if (retval) { 10476 wmi_err("Failed to send FIPS cmd"); 10477 wmi_buf_free(buf); 10478 } 10479 10480 return retval; 10481 } 10482 10483 /** 10484 * send_pdev_fips_mode_set_cmd_tlv() - send pdev fips cmd to fw 10485 * @wmi_handle: wmi handle 10486 * @param: pointer to hold pdev fips param 10487 * 10488 * Return: 0 for success or error code 10489 */ 10490 static QDF_STATUS 10491 send_pdev_fips_mode_set_cmd_tlv(wmi_unified_t wmi_handle, 10492 struct fips_mode_set_params *param) 10493 { 10494 wmi_pdev_fips_mode_set_cmd_fixed_param *cmd; 10495 wmi_buf_t buf; 10496 uint8_t *buf_ptr; 10497 uint32_t len = sizeof(wmi_pdev_fips_mode_set_cmd_fixed_param); 10498 QDF_STATUS retval = QDF_STATUS_SUCCESS; 10499 10500 buf = wmi_buf_alloc(wmi_handle, len); 10501 if (!buf) 10502 return QDF_STATUS_E_FAILURE; 10503 10504 buf_ptr = (uint8_t *)wmi_buf_data(buf); 10505 cmd = (wmi_pdev_fips_mode_set_cmd_fixed_param *)buf_ptr; 10506 WMITLV_SET_HDR(&cmd->tlv_header, 10507 WMITLV_TAG_STRUC_wmi_pdev_fips_mode_set_cmd_fixed_param, 10508 WMITLV_GET_STRUCT_TLVLEN 10509 (wmi_pdev_fips_mode_set_cmd_fixed_param)); 10510 10511 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 10512 wmi_handle, 10513 param->pdev_id); 10514 10515 cmd->fips_mode_set = param->mode; 10516 wmi_mtrace(WMI_PDEV_FIPS_MODE_SET_CMDID, NO_SESSION, 0); 10517 retval = wmi_unified_cmd_send(wmi_handle, buf, len, 10518 WMI_PDEV_FIPS_MODE_SET_CMDID); 10519 if (retval) { 10520 wmi_err("Failed to send FIPS mode enable cmd"); 10521 wmi_buf_free(buf); 10522 } 10523 return retval; 10524 } 10525 #endif 10526 10527 /** 10528 * send_wlan_profile_enable_cmd_tlv() - send wlan profile enable command 10529 * to fw 10530 * @wmi_handle: wmi handle 10531 * @param: pointer to wlan profile param 10532 * 10533 * Return: 0 for success or error code 10534 */ 10535 static QDF_STATUS 10536 send_wlan_profile_enable_cmd_tlv(wmi_unified_t wmi_handle, 10537 struct wlan_profile_params *param) 10538 { 10539 wmi_buf_t buf; 10540 uint16_t len; 10541 QDF_STATUS ret; 10542 wmi_wlan_profile_enable_profile_id_cmd_fixed_param *profile_enable_cmd; 10543 10544 len = sizeof(wmi_wlan_profile_enable_profile_id_cmd_fixed_param); 10545 buf = wmi_buf_alloc(wmi_handle, len); 10546 if (!buf) { 10547 wmi_err("Failed to send WMI_WLAN_PROFILE_ENABLE_PROFILE_ID_CMDID"); 10548 return QDF_STATUS_E_NOMEM; 10549 } 10550 10551 profile_enable_cmd = 10552 (wmi_wlan_profile_enable_profile_id_cmd_fixed_param *) 10553 wmi_buf_data(buf); 10554 WMITLV_SET_HDR(&profile_enable_cmd->tlv_header, 10555 WMITLV_TAG_STRUC_wmi_wlan_profile_enable_profile_id_cmd_fixed_param, 10556 WMITLV_GET_STRUCT_TLVLEN 10557 (wmi_wlan_profile_enable_profile_id_cmd_fixed_param)); 10558 10559 profile_enable_cmd->profile_id = param->profile_id; 10560 profile_enable_cmd->enable = param->enable; 10561 wmi_mtrace(WMI_WLAN_PROFILE_ENABLE_PROFILE_ID_CMDID, 10562 NO_SESSION, 0); 10563 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 10564 WMI_WLAN_PROFILE_ENABLE_PROFILE_ID_CMDID); 10565 if (ret) { 10566 wmi_err("Failed to send PROFILE_ENABLE_PROFILE_ID_CMDID"); 10567 wmi_buf_free(buf); 10568 } 10569 return ret; 10570 } 10571 10572 /** 10573 * send_wlan_profile_trigger_cmd_tlv() - send wlan profile trigger command 10574 * to fw 10575 * @wmi_handle: wmi handle 10576 * @param: pointer to wlan profile param 10577 * 10578 * Return: 0 for success or error code 10579 */ 10580 static QDF_STATUS 10581 send_wlan_profile_trigger_cmd_tlv(wmi_unified_t wmi_handle, 10582 struct wlan_profile_params *param) 10583 { 10584 wmi_buf_t buf; 10585 uint16_t len; 10586 QDF_STATUS ret; 10587 wmi_wlan_profile_trigger_cmd_fixed_param *prof_trig_cmd; 10588 10589 len = sizeof(wmi_wlan_profile_trigger_cmd_fixed_param); 10590 buf = wmi_buf_alloc(wmi_handle, len); 10591 if (!buf) { 10592 wmi_err("Failed to send WMI_WLAN_PROFILE_TRIGGER_CMDID"); 10593 return QDF_STATUS_E_NOMEM; 10594 } 10595 10596 prof_trig_cmd = 10597 (wmi_wlan_profile_trigger_cmd_fixed_param *) 10598 wmi_buf_data(buf); 10599 10600 WMITLV_SET_HDR(&prof_trig_cmd->tlv_header, 10601 WMITLV_TAG_STRUC_wmi_wlan_profile_trigger_cmd_fixed_param, 10602 WMITLV_GET_STRUCT_TLVLEN 10603 (wmi_wlan_profile_trigger_cmd_fixed_param)); 10604 10605 prof_trig_cmd->enable = param->enable; 10606 wmi_mtrace(WMI_WLAN_PROFILE_TRIGGER_CMDID, NO_SESSION, 0); 10607 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 10608 WMI_WLAN_PROFILE_TRIGGER_CMDID); 10609 if (ret) { 10610 wmi_err("Failed to send WMI_WLAN_PROFILE_TRIGGER_CMDID"); 10611 wmi_buf_free(buf); 10612 } 10613 return ret; 10614 } 10615 10616 /** 10617 * send_wlan_profile_hist_intvl_cmd_tlv() - send wlan profile interval command 10618 * to fw 10619 * @wmi_handle: wmi handle 10620 * @param: pointer to wlan profile param 10621 * 10622 * Return: 0 for success or error code 10623 */ 10624 static QDF_STATUS 10625 send_wlan_profile_hist_intvl_cmd_tlv(wmi_unified_t wmi_handle, 10626 struct wlan_profile_params *param) 10627 { 10628 wmi_buf_t buf; 10629 int32_t len = 0; 10630 QDF_STATUS ret; 10631 wmi_wlan_profile_set_hist_intvl_cmd_fixed_param *hist_intvl_cmd; 10632 10633 len = sizeof(wmi_wlan_profile_set_hist_intvl_cmd_fixed_param); 10634 buf = wmi_buf_alloc(wmi_handle, len); 10635 if (!buf) { 10636 wmi_err("Failed to send WMI_WLAN_PROFILE_SET_HIST_INTVL_CMDID"); 10637 return QDF_STATUS_E_NOMEM; 10638 } 10639 10640 hist_intvl_cmd = 10641 (wmi_wlan_profile_set_hist_intvl_cmd_fixed_param *) 10642 wmi_buf_data(buf); 10643 10644 WMITLV_SET_HDR(&hist_intvl_cmd->tlv_header, 10645 WMITLV_TAG_STRUC_wmi_wlan_profile_set_hist_intvl_cmd_fixed_param, 10646 WMITLV_GET_STRUCT_TLVLEN 10647 (wmi_wlan_profile_set_hist_intvl_cmd_fixed_param)); 10648 10649 hist_intvl_cmd->profile_id = param->profile_id; 10650 hist_intvl_cmd->value = param->enable; 10651 wmi_mtrace(WMI_WLAN_PROFILE_SET_HIST_INTVL_CMDID, 10652 NO_SESSION, 0); 10653 10654 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 10655 WMI_WLAN_PROFILE_SET_HIST_INTVL_CMDID); 10656 if (ret) { 10657 wmi_err("Failed to send PROFILE_SET_HIST_INTVL_CMDID"); 10658 wmi_buf_free(buf); 10659 } 10660 return ret; 10661 } 10662 10663 /** 10664 * send_fw_test_cmd_tlv() - send fw test command to fw. 10665 * @wmi_handle: wmi handle 10666 * @wmi_fwtest: fw test command 10667 * 10668 * This function sends fw test command to fw. 10669 * 10670 * Return: CDF STATUS 10671 */ 10672 static 10673 QDF_STATUS send_fw_test_cmd_tlv(wmi_unified_t wmi_handle, 10674 struct set_fwtest_params *wmi_fwtest) 10675 { 10676 wmi_fwtest_set_param_cmd_fixed_param *cmd; 10677 wmi_buf_t wmi_buf; 10678 uint16_t len; 10679 10680 len = sizeof(*cmd); 10681 10682 wmi_buf = wmi_buf_alloc(wmi_handle, len); 10683 if (!wmi_buf) 10684 return QDF_STATUS_E_NOMEM; 10685 10686 cmd = (wmi_fwtest_set_param_cmd_fixed_param *) wmi_buf_data(wmi_buf); 10687 WMITLV_SET_HDR(&cmd->tlv_header, 10688 WMITLV_TAG_STRUC_wmi_fwtest_set_param_cmd_fixed_param, 10689 WMITLV_GET_STRUCT_TLVLEN( 10690 wmi_fwtest_set_param_cmd_fixed_param)); 10691 cmd->param_id = wmi_fwtest->arg; 10692 cmd->param_value = wmi_fwtest->value; 10693 10694 wmi_mtrace(WMI_FWTEST_CMDID, NO_SESSION, 0); 10695 if (wmi_unified_cmd_send(wmi_handle, wmi_buf, len, 10696 WMI_FWTEST_CMDID)) { 10697 wmi_err("Failed to send fw test command"); 10698 wmi_buf_free(wmi_buf); 10699 return QDF_STATUS_E_FAILURE; 10700 } 10701 10702 return QDF_STATUS_SUCCESS; 10703 } 10704 10705 static uint16_t wfa_config_param_len(enum wfa_test_cmds config) 10706 { 10707 uint16_t len = 0; 10708 10709 if (config == WFA_CONFIG_RXNE) 10710 len += WMI_TLV_HDR_SIZE + sizeof(wmi_wfa_config_rsnxe); 10711 else 10712 len += WMI_TLV_HDR_SIZE; 10713 10714 if (config == WFA_CONFIG_CSA) 10715 len += WMI_TLV_HDR_SIZE + sizeof(wmi_wfa_config_csa); 10716 else 10717 len += WMI_TLV_HDR_SIZE; 10718 10719 if (config == WFA_CONFIG_OCV) 10720 len += WMI_TLV_HDR_SIZE + sizeof(wmi_wfa_config_ocv); 10721 else 10722 len += WMI_TLV_HDR_SIZE; 10723 10724 if (config == WFA_CONFIG_SA_QUERY) 10725 len += WMI_TLV_HDR_SIZE + sizeof(wmi_wfa_config_saquery); 10726 else 10727 len += WMI_TLV_HDR_SIZE; 10728 10729 return len; 10730 } 10731 10732 /** 10733 * wmi_fill_ocv_frame_type() - Fill host ocv frm type into WMI ocv frm type. 10734 * @host_frmtype: Host defined OCV frame type 10735 * @ocv_frmtype: Pointer to hold WMI OCV frame type 10736 * 10737 * This function converts and fills host defined OCV frame type into WMI OCV 10738 * frame type. 10739 * 10740 * Return: CDF STATUS 10741 */ 10742 static QDF_STATUS 10743 wmi_fill_ocv_frame_type(uint32_t host_frmtype, uint32_t *ocv_frmtype) 10744 { 10745 switch (host_frmtype) { 10746 case WMI_HOST_WFA_CONFIG_OCV_FRMTYPE_SAQUERY_REQ: 10747 *ocv_frmtype = WMI_WFA_CONFIG_OCV_FRMTYPE_SAQUERY_REQ; 10748 break; 10749 10750 case WMI_HOST_WFA_CONFIG_OCV_FRMTYPE_SAQUERY_RSP: 10751 *ocv_frmtype = WMI_WFA_CONFIG_OCV_FRMTYPE_SAQUERY_RSP; 10752 break; 10753 10754 case WMI_HOST_WFA_CONFIG_OCV_FRMTYPE_FT_REASSOC_REQ: 10755 *ocv_frmtype = WMI_WFA_CONFIG_OCV_FRMTYPE_FT_REASSOC_REQ; 10756 break; 10757 10758 case WMI_HOST_WFA_CONFIG_OCV_FRMTYPE_FILS_REASSOC_REQ: 10759 *ocv_frmtype = WMI_WFA_CONFIG_OCV_FRMTYPE_FILS_REASSOC_REQ; 10760 break; 10761 10762 default: 10763 wmi_err("Invalid command type cmd %d", host_frmtype); 10764 return QDF_STATUS_E_FAILURE; 10765 } 10766 10767 return QDF_STATUS_SUCCESS; 10768 } 10769 10770 /** 10771 * send_wfa_test_cmd_tlv() - send wfa test command to fw. 10772 * @wmi_handle: wmi handle 10773 * @wmi_wfatest: wfa test command 10774 * 10775 * This function sends wfa test command to fw. 10776 * 10777 * Return: CDF STATUS 10778 */ 10779 static 10780 QDF_STATUS send_wfa_test_cmd_tlv(wmi_unified_t wmi_handle, 10781 struct set_wfatest_params *wmi_wfatest) 10782 { 10783 wmi_wfa_config_cmd_fixed_param *cmd; 10784 wmi_wfa_config_rsnxe *rxne; 10785 wmi_wfa_config_csa *csa; 10786 wmi_wfa_config_ocv *ocv; 10787 wmi_wfa_config_saquery *saquery; 10788 wmi_buf_t wmi_buf; 10789 uint16_t len = sizeof(*cmd); 10790 uint8_t *buf_ptr; 10791 10792 len += wfa_config_param_len(wmi_wfatest->cmd); 10793 wmi_buf = wmi_buf_alloc(wmi_handle, len); 10794 if (!wmi_buf) 10795 return QDF_STATUS_E_NOMEM; 10796 10797 cmd = (wmi_wfa_config_cmd_fixed_param *)wmi_buf_data(wmi_buf); 10798 WMITLV_SET_HDR(&cmd->tlv_header, 10799 WMITLV_TAG_STRUC_wmi_wfa_config_cmd_fixed_param, 10800 WMITLV_GET_STRUCT_TLVLEN( 10801 wmi_wfa_config_cmd_fixed_param)); 10802 10803 cmd->vdev_id = wmi_wfatest->vdev_id; 10804 buf_ptr = (uint8_t *)(cmd + 1); 10805 10806 if (wmi_wfatest->cmd == WFA_CONFIG_RXNE) { 10807 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 10808 sizeof(wmi_wfa_config_rsnxe)); 10809 buf_ptr += WMI_TLV_HDR_SIZE; 10810 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_STRUC_wmi_wfa_config_rsnxe, 10811 WMITLV_GET_STRUCT_TLVLEN(wmi_wfa_config_rsnxe)); 10812 rxne = (wmi_wfa_config_rsnxe *)buf_ptr; 10813 rxne->rsnxe_param = wmi_wfatest->value; 10814 buf_ptr += sizeof(wmi_wfa_config_rsnxe); 10815 } else { 10816 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 0); 10817 buf_ptr += WMI_TLV_HDR_SIZE; 10818 } 10819 10820 if (wmi_wfatest->cmd == WFA_CONFIG_CSA) { 10821 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 10822 sizeof(wmi_wfa_config_csa)); 10823 buf_ptr += WMI_TLV_HDR_SIZE; 10824 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_STRUC_wmi_wfa_config_csa, 10825 WMITLV_GET_STRUCT_TLVLEN(wmi_wfa_config_csa)); 10826 csa = (wmi_wfa_config_csa *)buf_ptr; 10827 csa->ignore_csa = wmi_wfatest->value; 10828 buf_ptr += sizeof(wmi_wfa_config_csa); 10829 } else { 10830 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 0); 10831 buf_ptr += WMI_TLV_HDR_SIZE; 10832 } 10833 10834 if (wmi_wfatest->cmd == WFA_CONFIG_OCV) { 10835 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 10836 sizeof(wmi_wfa_config_ocv)); 10837 buf_ptr += WMI_TLV_HDR_SIZE; 10838 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_STRUC_wmi_wfa_config_ocv, 10839 WMITLV_GET_STRUCT_TLVLEN(wmi_wfa_config_ocv)); 10840 ocv = (wmi_wfa_config_ocv *)buf_ptr; 10841 10842 if (wmi_fill_ocv_frame_type(wmi_wfatest->ocv_param->frame_type, 10843 &ocv->frame_types)) 10844 goto error; 10845 10846 ocv->chan_freq = wmi_wfatest->ocv_param->freq; 10847 buf_ptr += sizeof(wmi_wfa_config_ocv); 10848 } else { 10849 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 0); 10850 buf_ptr += WMI_TLV_HDR_SIZE; 10851 } 10852 10853 if (wmi_wfatest->cmd == WFA_CONFIG_SA_QUERY) { 10854 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 10855 sizeof(wmi_wfa_config_saquery)); 10856 buf_ptr += WMI_TLV_HDR_SIZE; 10857 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_STRUC_wmi_wfa_config_saquery, 10858 WMITLV_GET_STRUCT_TLVLEN(wmi_wfa_config_saquery)); 10859 10860 saquery = (wmi_wfa_config_saquery *)buf_ptr; 10861 saquery->remain_connect_on_saquery_timeout = wmi_wfatest->value; 10862 } else { 10863 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 0); 10864 buf_ptr += WMI_TLV_HDR_SIZE; 10865 } 10866 10867 wmi_mtrace(WMI_WFA_CONFIG_CMDID, wmi_wfatest->vdev_id, 0); 10868 if (wmi_unified_cmd_send(wmi_handle, wmi_buf, len, 10869 WMI_WFA_CONFIG_CMDID)) { 10870 wmi_err("Failed to send wfa test command"); 10871 goto error; 10872 } 10873 10874 return QDF_STATUS_SUCCESS; 10875 10876 error: 10877 wmi_buf_free(wmi_buf); 10878 return QDF_STATUS_E_FAILURE; 10879 } 10880 10881 /** 10882 * send_unit_test_cmd_tlv() - send unit test command to fw. 10883 * @wmi_handle: wmi handle 10884 * @wmi_utest: unit test command 10885 * 10886 * This function send unit test command to fw. 10887 * 10888 * Return: CDF STATUS 10889 */ 10890 static QDF_STATUS send_unit_test_cmd_tlv(wmi_unified_t wmi_handle, 10891 struct wmi_unit_test_cmd *wmi_utest) 10892 { 10893 wmi_unit_test_cmd_fixed_param *cmd; 10894 wmi_buf_t wmi_buf; 10895 uint8_t *buf_ptr; 10896 int i; 10897 uint16_t len, args_tlv_len; 10898 uint32_t *unit_test_cmd_args; 10899 10900 args_tlv_len = 10901 WMI_TLV_HDR_SIZE + wmi_utest->num_args * sizeof(uint32_t); 10902 len = sizeof(wmi_unit_test_cmd_fixed_param) + args_tlv_len; 10903 10904 wmi_buf = wmi_buf_alloc(wmi_handle, len); 10905 if (!wmi_buf) 10906 return QDF_STATUS_E_NOMEM; 10907 10908 cmd = (wmi_unit_test_cmd_fixed_param *) wmi_buf_data(wmi_buf); 10909 buf_ptr = (uint8_t *) cmd; 10910 WMITLV_SET_HDR(&cmd->tlv_header, 10911 WMITLV_TAG_STRUC_wmi_unit_test_cmd_fixed_param, 10912 WMITLV_GET_STRUCT_TLVLEN(wmi_unit_test_cmd_fixed_param)); 10913 cmd->vdev_id = wmi_utest->vdev_id; 10914 cmd->module_id = wmi_utest->module_id; 10915 cmd->num_args = wmi_utest->num_args; 10916 cmd->diag_token = wmi_utest->diag_token; 10917 buf_ptr += sizeof(wmi_unit_test_cmd_fixed_param); 10918 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, 10919 (wmi_utest->num_args * sizeof(uint32_t))); 10920 unit_test_cmd_args = (uint32_t *) (buf_ptr + WMI_TLV_HDR_SIZE); 10921 wmi_debug("VDEV ID: %d MODULE ID: %d TOKEN: %d", 10922 cmd->vdev_id, cmd->module_id, cmd->diag_token); 10923 wmi_debug("%d num of args = ", wmi_utest->num_args); 10924 for (i = 0; (i < wmi_utest->num_args && i < WMI_UNIT_TEST_MAX_NUM_ARGS); i++) { 10925 unit_test_cmd_args[i] = wmi_utest->args[i]; 10926 wmi_debug("%d,", wmi_utest->args[i]); 10927 } 10928 wmi_mtrace(WMI_UNIT_TEST_CMDID, cmd->vdev_id, 0); 10929 if (wmi_unified_cmd_send(wmi_handle, wmi_buf, len, 10930 WMI_UNIT_TEST_CMDID)) { 10931 wmi_err("Failed to send unit test command"); 10932 wmi_buf_free(wmi_buf); 10933 return QDF_STATUS_E_FAILURE; 10934 } 10935 10936 return QDF_STATUS_SUCCESS; 10937 } 10938 10939 /** 10940 * send_power_dbg_cmd_tlv() - send power debug commands 10941 * @wmi_handle: wmi handle 10942 * @param: wmi power debug parameter 10943 * 10944 * Send WMI_POWER_DEBUG_CMDID parameters to fw. 10945 * 10946 * Return: QDF_STATUS_SUCCESS on success, QDF_STATUS_E_** on error 10947 */ 10948 static QDF_STATUS send_power_dbg_cmd_tlv(wmi_unified_t wmi_handle, 10949 struct wmi_power_dbg_params *param) 10950 { 10951 wmi_buf_t buf = NULL; 10952 QDF_STATUS status; 10953 int len, args_tlv_len; 10954 uint8_t *buf_ptr; 10955 uint8_t i; 10956 wmi_pdev_wal_power_debug_cmd_fixed_param *cmd; 10957 uint32_t *cmd_args; 10958 10959 /* Prepare and send power debug cmd parameters */ 10960 args_tlv_len = WMI_TLV_HDR_SIZE + param->num_args * sizeof(uint32_t); 10961 len = sizeof(*cmd) + args_tlv_len; 10962 buf = wmi_buf_alloc(wmi_handle, len); 10963 if (!buf) 10964 return QDF_STATUS_E_NOMEM; 10965 10966 buf_ptr = (uint8_t *) wmi_buf_data(buf); 10967 cmd = (wmi_pdev_wal_power_debug_cmd_fixed_param *) buf_ptr; 10968 WMITLV_SET_HDR(&cmd->tlv_header, 10969 WMITLV_TAG_STRUC_wmi_pdev_wal_power_debug_cmd_fixed_param, 10970 WMITLV_GET_STRUCT_TLVLEN 10971 (wmi_pdev_wal_power_debug_cmd_fixed_param)); 10972 10973 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 10974 wmi_handle, 10975 param->pdev_id); 10976 cmd->module_id = param->module_id; 10977 cmd->num_args = param->num_args; 10978 buf_ptr += sizeof(*cmd); 10979 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, 10980 (param->num_args * sizeof(uint32_t))); 10981 cmd_args = (uint32_t *) (buf_ptr + WMI_TLV_HDR_SIZE); 10982 wmi_debug("%d num of args = ", param->num_args); 10983 for (i = 0; (i < param->num_args && i < WMI_MAX_POWER_DBG_ARGS); i++) { 10984 cmd_args[i] = param->args[i]; 10985 wmi_debug("%d,", param->args[i]); 10986 } 10987 10988 wmi_mtrace(WMI_PDEV_WAL_POWER_DEBUG_CMDID, NO_SESSION, 0); 10989 status = wmi_unified_cmd_send(wmi_handle, buf, 10990 len, WMI_PDEV_WAL_POWER_DEBUG_CMDID); 10991 if (QDF_IS_STATUS_ERROR(status)) { 10992 wmi_err("wmi_unified_cmd_send WMI_PDEV_WAL_POWER_DEBUG_CMDID returned Error %d", 10993 status); 10994 goto error; 10995 } 10996 10997 return QDF_STATUS_SUCCESS; 10998 error: 10999 wmi_buf_free(buf); 11000 11001 return status; 11002 } 11003 11004 /** 11005 * send_dfs_phyerr_offload_en_cmd_tlv() - send dfs phyerr offload enable cmd 11006 * @wmi_handle: wmi handle 11007 * @pdev_id: pdev id 11008 * 11009 * Send WMI_PDEV_DFS_PHYERR_OFFLOAD_ENABLE_CMDID command to firmware. 11010 * 11011 * Return: QDF_STATUS_SUCCESS on success, QDF_STATUS_E_** on error 11012 */ 11013 static QDF_STATUS send_dfs_phyerr_offload_en_cmd_tlv(wmi_unified_t wmi_handle, 11014 uint32_t pdev_id) 11015 { 11016 wmi_pdev_dfs_phyerr_offload_enable_cmd_fixed_param *cmd; 11017 wmi_buf_t buf; 11018 uint16_t len; 11019 QDF_STATUS ret; 11020 11021 len = sizeof(*cmd); 11022 buf = wmi_buf_alloc(wmi_handle, len); 11023 11024 wmi_debug("pdev_id=%d", pdev_id); 11025 11026 if (!buf) 11027 return QDF_STATUS_E_NOMEM; 11028 11029 cmd = (wmi_pdev_dfs_phyerr_offload_enable_cmd_fixed_param *) 11030 wmi_buf_data(buf); 11031 11032 WMITLV_SET_HDR(&cmd->tlv_header, 11033 WMITLV_TAG_STRUC_wmi_pdev_dfs_phyerr_offload_enable_cmd_fixed_param, 11034 WMITLV_GET_STRUCT_TLVLEN( 11035 wmi_pdev_dfs_phyerr_offload_enable_cmd_fixed_param)); 11036 11037 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 11038 wmi_handle, 11039 pdev_id); 11040 wmi_mtrace(WMI_PDEV_DFS_PHYERR_OFFLOAD_ENABLE_CMDID, NO_SESSION, 0); 11041 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 11042 WMI_PDEV_DFS_PHYERR_OFFLOAD_ENABLE_CMDID); 11043 if (QDF_IS_STATUS_ERROR(ret)) { 11044 wmi_err("Failed to send cmd to fw, ret=%d, pdev_id=%d", 11045 ret, pdev_id); 11046 wmi_buf_free(buf); 11047 return QDF_STATUS_E_FAILURE; 11048 } 11049 11050 return QDF_STATUS_SUCCESS; 11051 } 11052 11053 /** 11054 * send_dfs_phyerr_offload_dis_cmd_tlv() - send dfs phyerr offload disable cmd 11055 * @wmi_handle: wmi handle 11056 * @pdev_id: pdev id 11057 * 11058 * Send WMI_PDEV_DFS_PHYERR_OFFLOAD_DISABLE_CMDID command to firmware. 11059 * 11060 * Return: QDF_STATUS_SUCCESS on success, QDF_STATUS_E_** on error 11061 */ 11062 static QDF_STATUS send_dfs_phyerr_offload_dis_cmd_tlv(wmi_unified_t wmi_handle, 11063 uint32_t pdev_id) 11064 { 11065 wmi_pdev_dfs_phyerr_offload_disable_cmd_fixed_param *cmd; 11066 wmi_buf_t buf; 11067 uint16_t len; 11068 QDF_STATUS ret; 11069 11070 len = sizeof(*cmd); 11071 buf = wmi_buf_alloc(wmi_handle, len); 11072 11073 wmi_debug("pdev_id=%d", pdev_id); 11074 11075 if (!buf) 11076 return QDF_STATUS_E_NOMEM; 11077 11078 cmd = (wmi_pdev_dfs_phyerr_offload_disable_cmd_fixed_param *) 11079 wmi_buf_data(buf); 11080 11081 WMITLV_SET_HDR(&cmd->tlv_header, 11082 WMITLV_TAG_STRUC_wmi_pdev_dfs_phyerr_offload_disable_cmd_fixed_param, 11083 WMITLV_GET_STRUCT_TLVLEN( 11084 wmi_pdev_dfs_phyerr_offload_disable_cmd_fixed_param)); 11085 11086 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 11087 wmi_handle, 11088 pdev_id); 11089 wmi_mtrace(WMI_PDEV_DFS_PHYERR_OFFLOAD_DISABLE_CMDID, NO_SESSION, 0); 11090 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 11091 WMI_PDEV_DFS_PHYERR_OFFLOAD_DISABLE_CMDID); 11092 if (QDF_IS_STATUS_ERROR(ret)) { 11093 wmi_err("Failed to send cmd to fw, ret=%d, pdev_id=%d", 11094 ret, pdev_id); 11095 wmi_buf_free(buf); 11096 return QDF_STATUS_E_FAILURE; 11097 } 11098 11099 return QDF_STATUS_SUCCESS; 11100 } 11101 11102 #ifdef QCA_SUPPORT_AGILE_DFS 11103 static 11104 QDF_STATUS send_adfs_ch_cfg_cmd_tlv(wmi_unified_t wmi_handle, 11105 struct vdev_adfs_ch_cfg_params *param) 11106 { 11107 /* wmi_unified_cmd_send set request of agile ADFS channel*/ 11108 wmi_vdev_adfs_ch_cfg_cmd_fixed_param *cmd; 11109 wmi_buf_t buf; 11110 QDF_STATUS ret; 11111 uint16_t len; 11112 11113 len = sizeof(*cmd); 11114 buf = wmi_buf_alloc(wmi_handle, len); 11115 11116 if (!buf) { 11117 wmi_err("wmi_buf_alloc failed"); 11118 return QDF_STATUS_E_NOMEM; 11119 } 11120 11121 cmd = (wmi_vdev_adfs_ch_cfg_cmd_fixed_param *) 11122 wmi_buf_data(buf); 11123 11124 WMITLV_SET_HDR(&cmd->tlv_header, 11125 WMITLV_TAG_STRUC_wmi_vdev_adfs_ch_cfg_cmd_fixed_param, 11126 WMITLV_GET_STRUCT_TLVLEN 11127 (wmi_vdev_adfs_ch_cfg_cmd_fixed_param)); 11128 11129 cmd->vdev_id = param->vdev_id; 11130 cmd->ocac_mode = param->ocac_mode; 11131 cmd->center_freq1 = param->center_freq1; 11132 cmd->center_freq2 = param->center_freq2; 11133 cmd->chan_freq = param->chan_freq; 11134 cmd->chan_width = param->chan_width; 11135 cmd->min_duration_ms = param->min_duration_ms; 11136 cmd->max_duration_ms = param->max_duration_ms; 11137 wmi_debug("cmd->vdev_id: %d ,cmd->ocac_mode: %d cmd->center_freq: %d", 11138 cmd->vdev_id, cmd->ocac_mode, 11139 cmd->center_freq); 11140 11141 wmi_mtrace(WMI_VDEV_ADFS_CH_CFG_CMDID, NO_SESSION, 0); 11142 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 11143 WMI_VDEV_ADFS_CH_CFG_CMDID); 11144 11145 if (QDF_IS_STATUS_ERROR(ret)) { 11146 wmi_err("Failed to send cmd to fw, ret=%d", ret); 11147 wmi_buf_free(buf); 11148 return QDF_STATUS_E_FAILURE; 11149 } 11150 11151 return QDF_STATUS_SUCCESS; 11152 } 11153 11154 static 11155 QDF_STATUS send_adfs_ocac_abort_cmd_tlv(wmi_unified_t wmi_handle, 11156 struct vdev_adfs_abort_params *param) 11157 { 11158 /*wmi_unified_cmd_send with ocac abort on ADFS channel*/ 11159 wmi_vdev_adfs_ocac_abort_cmd_fixed_param *cmd; 11160 wmi_buf_t buf; 11161 QDF_STATUS ret; 11162 uint16_t len; 11163 11164 len = sizeof(*cmd); 11165 buf = wmi_buf_alloc(wmi_handle, len); 11166 11167 if (!buf) { 11168 wmi_err("wmi_buf_alloc failed"); 11169 return QDF_STATUS_E_NOMEM; 11170 } 11171 11172 cmd = (wmi_vdev_adfs_ocac_abort_cmd_fixed_param *) 11173 wmi_buf_data(buf); 11174 11175 WMITLV_SET_HDR 11176 (&cmd->tlv_header, 11177 WMITLV_TAG_STRUC_wmi_vdev_adfs_ocac_abort_cmd_fixed_param, 11178 WMITLV_GET_STRUCT_TLVLEN 11179 (wmi_vdev_adfs_ocac_abort_cmd_fixed_param)); 11180 11181 cmd->vdev_id = param->vdev_id; 11182 11183 wmi_mtrace(WMI_VDEV_ADFS_OCAC_ABORT_CMDID, NO_SESSION, 0); 11184 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 11185 WMI_VDEV_ADFS_OCAC_ABORT_CMDID); 11186 11187 if (QDF_IS_STATUS_ERROR(ret)) { 11188 wmi_err("Failed to send cmd to fw, ret=%d", ret); 11189 wmi_buf_free(buf); 11190 return QDF_STATUS_E_FAILURE; 11191 } 11192 11193 return QDF_STATUS_SUCCESS; 11194 } 11195 #endif 11196 11197 /** 11198 * init_cmd_send_tlv() - send initialization cmd to fw 11199 * @wmi_handle: wmi handle 11200 * @param param: pointer to wmi init param 11201 * 11202 * Return: QDF_STATUS_SUCCESS for success or error code 11203 */ 11204 static QDF_STATUS init_cmd_send_tlv(wmi_unified_t wmi_handle, 11205 struct wmi_init_cmd_param *param) 11206 { 11207 wmi_buf_t buf; 11208 wmi_init_cmd_fixed_param *cmd; 11209 uint8_t *buf_ptr; 11210 wmi_resource_config *resource_cfg; 11211 wlan_host_memory_chunk *host_mem_chunks; 11212 uint32_t mem_chunk_len = 0, hw_mode_len = 0; 11213 uint16_t idx; 11214 int len; 11215 QDF_STATUS ret; 11216 11217 len = sizeof(*cmd) + sizeof(wmi_resource_config) + 11218 WMI_TLV_HDR_SIZE; 11219 mem_chunk_len = (sizeof(wlan_host_memory_chunk) * MAX_MEM_CHUNKS); 11220 11221 if (param->hw_mode_id != WMI_HOST_HW_MODE_MAX) 11222 hw_mode_len = sizeof(wmi_pdev_set_hw_mode_cmd_fixed_param) + 11223 WMI_TLV_HDR_SIZE + 11224 (param->num_band_to_mac * sizeof(wmi_pdev_band_to_mac)); 11225 11226 buf = wmi_buf_alloc(wmi_handle, len + mem_chunk_len + hw_mode_len); 11227 if (!buf) 11228 return QDF_STATUS_E_FAILURE; 11229 11230 buf_ptr = (uint8_t *) wmi_buf_data(buf); 11231 cmd = (wmi_init_cmd_fixed_param *) buf_ptr; 11232 resource_cfg = (wmi_resource_config *) (buf_ptr + sizeof(*cmd)); 11233 11234 host_mem_chunks = (wlan_host_memory_chunk *) 11235 (buf_ptr + sizeof(*cmd) + sizeof(wmi_resource_config) 11236 + WMI_TLV_HDR_SIZE); 11237 11238 WMITLV_SET_HDR(&cmd->tlv_header, 11239 WMITLV_TAG_STRUC_wmi_init_cmd_fixed_param, 11240 WMITLV_GET_STRUCT_TLVLEN(wmi_init_cmd_fixed_param)); 11241 wmi_copy_resource_config(resource_cfg, param->res_cfg); 11242 WMITLV_SET_HDR(&resource_cfg->tlv_header, 11243 WMITLV_TAG_STRUC_wmi_resource_config, 11244 WMITLV_GET_STRUCT_TLVLEN(wmi_resource_config)); 11245 11246 for (idx = 0; idx < param->num_mem_chunks; ++idx) { 11247 WMITLV_SET_HDR(&(host_mem_chunks[idx].tlv_header), 11248 WMITLV_TAG_STRUC_wlan_host_memory_chunk, 11249 WMITLV_GET_STRUCT_TLVLEN 11250 (wlan_host_memory_chunk)); 11251 host_mem_chunks[idx].ptr = param->mem_chunks[idx].paddr; 11252 host_mem_chunks[idx].size = param->mem_chunks[idx].len; 11253 host_mem_chunks[idx].req_id = param->mem_chunks[idx].req_id; 11254 if (is_service_enabled_tlv(wmi_handle, 11255 WMI_SERVICE_SUPPORT_EXTEND_ADDRESS)) 11256 host_mem_chunks[idx].ptr_high = 11257 qdf_get_upper_32_bits( 11258 param->mem_chunks[idx].paddr); 11259 QDF_TRACE(QDF_MODULE_ID_ANY, QDF_TRACE_LEVEL_DEBUG, 11260 "chunk %d len %d requested ,ptr 0x%x ", 11261 idx, host_mem_chunks[idx].size, 11262 host_mem_chunks[idx].ptr); 11263 } 11264 cmd->num_host_mem_chunks = param->num_mem_chunks; 11265 len += (param->num_mem_chunks * sizeof(wlan_host_memory_chunk)); 11266 11267 WMITLV_SET_HDR((buf_ptr + sizeof(*cmd) + sizeof(wmi_resource_config)), 11268 WMITLV_TAG_ARRAY_STRUC, 11269 (sizeof(wlan_host_memory_chunk) * 11270 param->num_mem_chunks)); 11271 11272 wmi_debug("num peers: %d , num offload peers: %d, num vdevs: %d, num tids: %d, num tdls conn tb entries: %d, num tdls vdevs: %d", 11273 resource_cfg->num_peers, resource_cfg->num_offload_peers, 11274 resource_cfg->num_vdevs, resource_cfg->num_tids, 11275 resource_cfg->num_tdls_conn_table_entries, 11276 resource_cfg->num_tdls_vdevs); 11277 11278 /* Fill hw mode id config */ 11279 buf_ptr = copy_hw_mode_in_init_cmd(wmi_handle, buf_ptr, &len, param); 11280 11281 /* Fill fw_abi_vers */ 11282 copy_fw_abi_version_tlv(wmi_handle, cmd); 11283 11284 wmi_mtrace(WMI_INIT_CMDID, NO_SESSION, 0); 11285 ret = wmi_unified_cmd_send(wmi_handle, buf, len, WMI_INIT_CMDID); 11286 if (QDF_IS_STATUS_ERROR(ret)) { 11287 wmi_err("wmi_unified_cmd_send WMI_INIT_CMDID returned Error %d", 11288 ret); 11289 wmi_buf_free(buf); 11290 } 11291 11292 return ret; 11293 11294 } 11295 11296 /** 11297 * send_addba_send_cmd_tlv() - send addba send command to fw 11298 * @wmi_handle: wmi handle 11299 * @param: pointer to delba send params 11300 * @macaddr: peer mac address 11301 * 11302 * Send WMI_ADDBA_SEND_CMDID command to firmware 11303 * Return: QDF_STATUS_SUCCESS on success. QDF_STATUS_E** on error 11304 */ 11305 static QDF_STATUS 11306 send_addba_send_cmd_tlv(wmi_unified_t wmi_handle, 11307 uint8_t macaddr[QDF_MAC_ADDR_SIZE], 11308 struct addba_send_params *param) 11309 { 11310 wmi_addba_send_cmd_fixed_param *cmd; 11311 wmi_buf_t buf; 11312 uint16_t len; 11313 QDF_STATUS ret; 11314 11315 len = sizeof(*cmd); 11316 11317 buf = wmi_buf_alloc(wmi_handle, len); 11318 if (!buf) 11319 return QDF_STATUS_E_NOMEM; 11320 11321 cmd = (wmi_addba_send_cmd_fixed_param *)wmi_buf_data(buf); 11322 11323 WMITLV_SET_HDR(&cmd->tlv_header, 11324 WMITLV_TAG_STRUC_wmi_addba_send_cmd_fixed_param, 11325 WMITLV_GET_STRUCT_TLVLEN(wmi_addba_send_cmd_fixed_param)); 11326 11327 cmd->vdev_id = param->vdev_id; 11328 WMI_CHAR_ARRAY_TO_MAC_ADDR(macaddr, &cmd->peer_macaddr); 11329 cmd->tid = param->tidno; 11330 cmd->buffersize = param->buffersize; 11331 11332 wmi_mtrace(WMI_ADDBA_SEND_CMDID, cmd->vdev_id, 0); 11333 ret = wmi_unified_cmd_send(wmi_handle, buf, len, WMI_ADDBA_SEND_CMDID); 11334 if (QDF_IS_STATUS_ERROR(ret)) { 11335 wmi_err("Failed to send cmd to fw, ret=%d", ret); 11336 wmi_buf_free(buf); 11337 return QDF_STATUS_E_FAILURE; 11338 } 11339 11340 return QDF_STATUS_SUCCESS; 11341 } 11342 11343 /** 11344 * send_delba_send_cmd_tlv() - send delba send command to fw 11345 * @wmi_handle: wmi handle 11346 * @param: pointer to delba send params 11347 * @macaddr: peer mac address 11348 * 11349 * Send WMI_DELBA_SEND_CMDID command to firmware 11350 * Return: QDF_STATUS_SUCCESS on success. QDF_STATUS_E** on error 11351 */ 11352 static QDF_STATUS 11353 send_delba_send_cmd_tlv(wmi_unified_t wmi_handle, 11354 uint8_t macaddr[QDF_MAC_ADDR_SIZE], 11355 struct delba_send_params *param) 11356 { 11357 wmi_delba_send_cmd_fixed_param *cmd; 11358 wmi_buf_t buf; 11359 uint16_t len; 11360 QDF_STATUS ret; 11361 11362 len = sizeof(*cmd); 11363 11364 buf = wmi_buf_alloc(wmi_handle, len); 11365 if (!buf) 11366 return QDF_STATUS_E_NOMEM; 11367 11368 cmd = (wmi_delba_send_cmd_fixed_param *)wmi_buf_data(buf); 11369 11370 WMITLV_SET_HDR(&cmd->tlv_header, 11371 WMITLV_TAG_STRUC_wmi_delba_send_cmd_fixed_param, 11372 WMITLV_GET_STRUCT_TLVLEN(wmi_delba_send_cmd_fixed_param)); 11373 11374 cmd->vdev_id = param->vdev_id; 11375 WMI_CHAR_ARRAY_TO_MAC_ADDR(macaddr, &cmd->peer_macaddr); 11376 cmd->tid = param->tidno; 11377 cmd->initiator = param->initiator; 11378 cmd->reasoncode = param->reasoncode; 11379 11380 wmi_mtrace(WMI_DELBA_SEND_CMDID, cmd->vdev_id, 0); 11381 ret = wmi_unified_cmd_send(wmi_handle, buf, len, WMI_DELBA_SEND_CMDID); 11382 if (QDF_IS_STATUS_ERROR(ret)) { 11383 wmi_err("Failed to send cmd to fw, ret=%d", ret); 11384 wmi_buf_free(buf); 11385 return QDF_STATUS_E_FAILURE; 11386 } 11387 11388 return QDF_STATUS_SUCCESS; 11389 } 11390 11391 /** 11392 * send_addba_clearresponse_cmd_tlv() - send addba clear response command 11393 * to fw 11394 * @wmi_handle: wmi handle 11395 * @param: pointer to addba clearresp params 11396 * @macaddr: peer mac address 11397 * Return: 0 for success or error code 11398 */ 11399 static QDF_STATUS 11400 send_addba_clearresponse_cmd_tlv(wmi_unified_t wmi_handle, 11401 uint8_t macaddr[QDF_MAC_ADDR_SIZE], 11402 struct addba_clearresponse_params *param) 11403 { 11404 wmi_addba_clear_resp_cmd_fixed_param *cmd; 11405 wmi_buf_t buf; 11406 uint16_t len; 11407 QDF_STATUS ret; 11408 11409 len = sizeof(*cmd); 11410 11411 buf = wmi_buf_alloc(wmi_handle, len); 11412 if (!buf) 11413 return QDF_STATUS_E_FAILURE; 11414 11415 cmd = (wmi_addba_clear_resp_cmd_fixed_param *)wmi_buf_data(buf); 11416 11417 WMITLV_SET_HDR(&cmd->tlv_header, 11418 WMITLV_TAG_STRUC_wmi_addba_clear_resp_cmd_fixed_param, 11419 WMITLV_GET_STRUCT_TLVLEN(wmi_addba_clear_resp_cmd_fixed_param)); 11420 11421 cmd->vdev_id = param->vdev_id; 11422 WMI_CHAR_ARRAY_TO_MAC_ADDR(macaddr, &cmd->peer_macaddr); 11423 11424 wmi_mtrace(WMI_ADDBA_CLEAR_RESP_CMDID, cmd->vdev_id, 0); 11425 ret = wmi_unified_cmd_send(wmi_handle, 11426 buf, len, WMI_ADDBA_CLEAR_RESP_CMDID); 11427 if (QDF_IS_STATUS_ERROR(ret)) { 11428 wmi_err("Failed to send cmd to fw, ret=%d", ret); 11429 wmi_buf_free(buf); 11430 return QDF_STATUS_E_FAILURE; 11431 } 11432 11433 return QDF_STATUS_SUCCESS; 11434 } 11435 11436 #ifdef OBSS_PD 11437 /** 11438 * send_obss_spatial_reuse_set_def_thresh_cmd_tlv - send obss spatial reuse set 11439 * def thresh to fw 11440 * @wmi_handle: wmi handle 11441 * @thresh: pointer to obss_spatial_reuse_def_thresh 11442 * 11443 * Return: QDF_STATUS_SUCCESS for success or error code 11444 */ 11445 static 11446 QDF_STATUS send_obss_spatial_reuse_set_def_thresh_cmd_tlv( 11447 wmi_unified_t wmi_handle, 11448 struct wmi_host_obss_spatial_reuse_set_def_thresh 11449 *thresh) 11450 { 11451 wmi_buf_t buf; 11452 wmi_obss_spatial_reuse_set_def_obss_thresh_cmd_fixed_param *cmd; 11453 QDF_STATUS ret; 11454 uint32_t cmd_len; 11455 uint32_t tlv_len; 11456 11457 cmd_len = sizeof(*cmd); 11458 11459 buf = wmi_buf_alloc(wmi_handle, cmd_len); 11460 if (!buf) 11461 return QDF_STATUS_E_NOMEM; 11462 11463 cmd = (wmi_obss_spatial_reuse_set_def_obss_thresh_cmd_fixed_param *) 11464 wmi_buf_data(buf); 11465 11466 tlv_len = WMITLV_GET_STRUCT_TLVLEN( 11467 wmi_obss_spatial_reuse_set_def_obss_thresh_cmd_fixed_param); 11468 11469 WMITLV_SET_HDR(&cmd->tlv_header, 11470 WMITLV_TAG_STRUC_wmi_obss_spatial_reuse_set_def_obss_thresh_cmd_fixed_param, 11471 tlv_len); 11472 11473 cmd->obss_min = thresh->obss_min; 11474 cmd->obss_max = thresh->obss_max; 11475 cmd->vdev_type = thresh->vdev_type; 11476 ret = wmi_unified_cmd_send(wmi_handle, buf, cmd_len, 11477 WMI_PDEV_OBSS_PD_SPATIAL_REUSE_SET_DEF_OBSS_THRESH_CMDID); 11478 if (QDF_IS_STATUS_ERROR(ret)) 11479 wmi_buf_free(buf); 11480 11481 return ret; 11482 } 11483 11484 /** 11485 * send_obss_spatial_reuse_set_cmd_tlv - send obss spatial reuse set cmd to fw 11486 * @wmi_handle: wmi handle 11487 * @obss_spatial_reuse_param: pointer to obss_spatial_reuse_param 11488 * 11489 * Return: QDF_STATUS_SUCCESS for success or error code 11490 */ 11491 static 11492 QDF_STATUS send_obss_spatial_reuse_set_cmd_tlv(wmi_unified_t wmi_handle, 11493 struct wmi_host_obss_spatial_reuse_set_param 11494 *obss_spatial_reuse_param) 11495 { 11496 wmi_buf_t buf; 11497 wmi_obss_spatial_reuse_set_cmd_fixed_param *cmd; 11498 QDF_STATUS ret; 11499 uint32_t len; 11500 11501 len = sizeof(*cmd); 11502 11503 buf = wmi_buf_alloc(wmi_handle, len); 11504 if (!buf) 11505 return QDF_STATUS_E_FAILURE; 11506 11507 cmd = (wmi_obss_spatial_reuse_set_cmd_fixed_param *)wmi_buf_data(buf); 11508 WMITLV_SET_HDR(&cmd->tlv_header, 11509 WMITLV_TAG_STRUC_wmi_obss_spatial_reuse_set_cmd_fixed_param, 11510 WMITLV_GET_STRUCT_TLVLEN 11511 (wmi_obss_spatial_reuse_set_cmd_fixed_param)); 11512 11513 cmd->enable = obss_spatial_reuse_param->enable; 11514 cmd->obss_min = obss_spatial_reuse_param->obss_min; 11515 cmd->obss_max = obss_spatial_reuse_param->obss_max; 11516 cmd->vdev_id = obss_spatial_reuse_param->vdev_id; 11517 11518 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 11519 WMI_PDEV_OBSS_PD_SPATIAL_REUSE_CMDID); 11520 11521 if (QDF_IS_STATUS_ERROR(ret)) { 11522 wmi_err( 11523 "WMI_PDEV_OBSS_PD_SPATIAL_REUSE_CMDID send returned Error %d", 11524 ret); 11525 wmi_buf_free(buf); 11526 } 11527 11528 return ret; 11529 } 11530 11531 /** 11532 * send_self_srg_bss_color_bitmap_set_cmd_tlv() - Send 64-bit BSS color bitmap 11533 * to be used by SRG based Spatial Reuse feature to the FW 11534 * @wmi_handle: wmi handle 11535 * @bitmap_0: lower 32 bits in BSS color bitmap 11536 * @bitmap_1: upper 32 bits in BSS color bitmap 11537 * @pdev_id: pdev ID 11538 * 11539 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_FAILURE for failure 11540 */ 11541 static QDF_STATUS 11542 send_self_srg_bss_color_bitmap_set_cmd_tlv( 11543 wmi_unified_t wmi_handle, uint32_t bitmap_0, 11544 uint32_t bitmap_1, uint8_t pdev_id) 11545 { 11546 wmi_buf_t buf; 11547 wmi_pdev_srg_bss_color_bitmap_cmd_fixed_param *cmd; 11548 QDF_STATUS ret; 11549 uint32_t len; 11550 11551 len = sizeof(*cmd); 11552 11553 buf = wmi_buf_alloc(wmi_handle, len); 11554 if (!buf) 11555 return QDF_STATUS_E_FAILURE; 11556 11557 cmd = (wmi_pdev_srg_bss_color_bitmap_cmd_fixed_param *) 11558 wmi_buf_data(buf); 11559 11560 WMITLV_SET_HDR( 11561 &cmd->tlv_header, 11562 WMITLV_TAG_STRUC_wmi_pdev_srg_bss_color_bitmap_cmd_fixed_param, 11563 WMITLV_GET_STRUCT_TLVLEN 11564 (wmi_pdev_srg_bss_color_bitmap_cmd_fixed_param)); 11565 11566 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 11567 wmi_handle, pdev_id); 11568 cmd->srg_bss_color_bitmap[0] = bitmap_0; 11569 cmd->srg_bss_color_bitmap[1] = bitmap_1; 11570 11571 ret = wmi_unified_cmd_send( 11572 wmi_handle, buf, len, 11573 WMI_PDEV_SET_SRG_BSS_COLOR_BITMAP_CMDID); 11574 11575 if (QDF_IS_STATUS_ERROR(ret)) { 11576 wmi_err( 11577 "WMI_PDEV_SET_SRG_BSS_COLOR_BITMAP_CMDID send returned Error %d", 11578 ret); 11579 wmi_buf_free(buf); 11580 } 11581 11582 return ret; 11583 } 11584 11585 /** 11586 * send_self_srg_partial_bssid_bitmap_set_cmd_tlv() - Send 64-bit partial BSSID 11587 * bitmap to be used by SRG based Spatial Reuse feature to the FW 11588 * @wmi_handle: wmi handle 11589 * @bitmap_0: lower 32 bits in partial BSSID bitmap 11590 * @bitmap_1: upper 32 bits in partial BSSID bitmap 11591 * @pdev_id: pdev ID 11592 * 11593 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_FAILURE for failure 11594 */ 11595 static QDF_STATUS 11596 send_self_srg_partial_bssid_bitmap_set_cmd_tlv( 11597 wmi_unified_t wmi_handle, uint32_t bitmap_0, 11598 uint32_t bitmap_1, uint8_t pdev_id) 11599 { 11600 wmi_buf_t buf; 11601 wmi_pdev_srg_partial_bssid_bitmap_cmd_fixed_param *cmd; 11602 QDF_STATUS ret; 11603 uint32_t len; 11604 11605 len = sizeof(*cmd); 11606 11607 buf = wmi_buf_alloc(wmi_handle, len); 11608 if (!buf) 11609 return QDF_STATUS_E_FAILURE; 11610 11611 cmd = (wmi_pdev_srg_partial_bssid_bitmap_cmd_fixed_param *) 11612 wmi_buf_data(buf); 11613 11614 WMITLV_SET_HDR( 11615 &cmd->tlv_header, 11616 WMITLV_TAG_STRUC_wmi_pdev_srg_partial_bssid_bitmap_cmd_fixed_param, 11617 WMITLV_GET_STRUCT_TLVLEN 11618 (wmi_pdev_srg_partial_bssid_bitmap_cmd_fixed_param)); 11619 11620 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 11621 wmi_handle, pdev_id); 11622 11623 cmd->srg_partial_bssid_bitmap[0] = bitmap_0; 11624 cmd->srg_partial_bssid_bitmap[1] = bitmap_1; 11625 11626 ret = wmi_unified_cmd_send( 11627 wmi_handle, buf, len, 11628 WMI_PDEV_SET_SRG_PARTIAL_BSSID_BITMAP_CMDID); 11629 11630 if (QDF_IS_STATUS_ERROR(ret)) { 11631 wmi_err( 11632 "WMI_PDEV_SET_SRG_PARTIAL_BSSID_BITMAP_CMDID send returned Error %d", 11633 ret); 11634 wmi_buf_free(buf); 11635 } 11636 11637 return ret; 11638 } 11639 11640 /** 11641 * send_self_srg_obss_color_enable_bitmap_cmd_tlv() - Send 64-bit BSS color 11642 * enable bitmap to be used by SRG based Spatial Reuse feature to the FW 11643 * @wmi_handle: wmi handle 11644 * @bitmap_0: lower 32 bits in BSS color enable bitmap 11645 * @bitmap_1: upper 32 bits in BSS color enable bitmap 11646 * @pdev_id: pdev ID 11647 * 11648 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_FAILURE for failure 11649 */ 11650 static QDF_STATUS 11651 send_self_srg_obss_color_enable_bitmap_cmd_tlv( 11652 wmi_unified_t wmi_handle, uint32_t bitmap_0, 11653 uint32_t bitmap_1, uint8_t pdev_id) 11654 { 11655 wmi_buf_t buf; 11656 wmi_pdev_srg_obss_color_enable_bitmap_cmd_fixed_param *cmd; 11657 QDF_STATUS ret; 11658 uint32_t len; 11659 11660 len = sizeof(*cmd); 11661 11662 buf = wmi_buf_alloc(wmi_handle, len); 11663 if (!buf) 11664 return QDF_STATUS_E_FAILURE; 11665 11666 cmd = (wmi_pdev_srg_obss_color_enable_bitmap_cmd_fixed_param *) 11667 wmi_buf_data(buf); 11668 11669 WMITLV_SET_HDR( 11670 &cmd->tlv_header, 11671 WMITLV_TAG_STRUC_wmi_pdev_srg_obss_color_enable_bitmap_cmd_fixed_param, 11672 WMITLV_GET_STRUCT_TLVLEN 11673 (wmi_pdev_srg_obss_color_enable_bitmap_cmd_fixed_param)); 11674 11675 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 11676 wmi_handle, pdev_id); 11677 cmd->srg_obss_en_color_bitmap[0] = bitmap_0; 11678 cmd->srg_obss_en_color_bitmap[1] = bitmap_1; 11679 11680 ret = wmi_unified_cmd_send( 11681 wmi_handle, buf, len, 11682 WMI_PDEV_SET_SRG_OBSS_COLOR_ENABLE_BITMAP_CMDID); 11683 11684 if (QDF_IS_STATUS_ERROR(ret)) { 11685 wmi_err( 11686 "WMI_PDEV_SET_SRG_OBSS_COLOR_ENABLE_BITMAP_CMDID send returned Error %d", 11687 ret); 11688 wmi_buf_free(buf); 11689 } 11690 11691 return ret; 11692 } 11693 11694 /** 11695 * send_self_srg_obss_bssid_enable_bitmap_cmd_tlv() - Send 64-bit OBSS BSSID 11696 * enable bitmap to be used by SRG based Spatial Reuse feature to the FW 11697 * @wmi_handle: wmi handle 11698 * @bitmap_0: lower 32 bits in BSSID enable bitmap 11699 * @bitmap_1: upper 32 bits in BSSID enable bitmap 11700 * @pdev_id: pdev ID 11701 * 11702 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_FAILURE for failure 11703 */ 11704 static QDF_STATUS 11705 send_self_srg_obss_bssid_enable_bitmap_cmd_tlv( 11706 wmi_unified_t wmi_handle, uint32_t bitmap_0, 11707 uint32_t bitmap_1, uint8_t pdev_id) 11708 { 11709 wmi_buf_t buf; 11710 wmi_pdev_srg_obss_bssid_enable_bitmap_cmd_fixed_param *cmd; 11711 QDF_STATUS ret; 11712 uint32_t len; 11713 11714 len = sizeof(*cmd); 11715 11716 buf = wmi_buf_alloc(wmi_handle, len); 11717 if (!buf) 11718 return QDF_STATUS_E_FAILURE; 11719 11720 cmd = (wmi_pdev_srg_obss_bssid_enable_bitmap_cmd_fixed_param *) 11721 wmi_buf_data(buf); 11722 11723 WMITLV_SET_HDR( 11724 &cmd->tlv_header, 11725 WMITLV_TAG_STRUC_wmi_pdev_srg_obss_bssid_enable_bitmap_cmd_fixed_param, 11726 WMITLV_GET_STRUCT_TLVLEN 11727 (wmi_pdev_srg_obss_bssid_enable_bitmap_cmd_fixed_param)); 11728 11729 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 11730 wmi_handle, pdev_id); 11731 cmd->srg_obss_en_bssid_bitmap[0] = bitmap_0; 11732 cmd->srg_obss_en_bssid_bitmap[1] = bitmap_1; 11733 11734 ret = wmi_unified_cmd_send( 11735 wmi_handle, buf, len, 11736 WMI_PDEV_SET_SRG_OBSS_BSSID_ENABLE_BITMAP_CMDID); 11737 11738 if (QDF_IS_STATUS_ERROR(ret)) { 11739 wmi_err( 11740 "WMI_PDEV_SET_SRG_OBSS_BSSID_ENABLE_BITMAP_CMDID send returned Error %d", 11741 ret); 11742 wmi_buf_free(buf); 11743 } 11744 11745 return ret; 11746 } 11747 11748 /** 11749 * send_self_non_srg_obss_color_enable_bitmap_cmd_tlv() - Send 64-bit BSS color 11750 * enable bitmap to be used by Non-SRG based Spatial Reuse feature to the FW 11751 * @wmi_handle: wmi handle 11752 * @bitmap_0: lower 32 bits in BSS color enable bitmap 11753 * @bitmap_1: upper 32 bits in BSS color enable bitmap 11754 * @pdev_id: pdev ID 11755 * 11756 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_FAILURE for failure 11757 */ 11758 static QDF_STATUS 11759 send_self_non_srg_obss_color_enable_bitmap_cmd_tlv( 11760 wmi_unified_t wmi_handle, uint32_t bitmap_0, 11761 uint32_t bitmap_1, uint8_t pdev_id) 11762 { 11763 wmi_buf_t buf; 11764 wmi_pdev_non_srg_obss_color_enable_bitmap_cmd_fixed_param *cmd; 11765 QDF_STATUS ret; 11766 uint32_t len; 11767 11768 len = sizeof(*cmd); 11769 11770 buf = wmi_buf_alloc(wmi_handle, len); 11771 if (!buf) 11772 return QDF_STATUS_E_FAILURE; 11773 11774 cmd = (wmi_pdev_non_srg_obss_color_enable_bitmap_cmd_fixed_param *) 11775 wmi_buf_data(buf); 11776 11777 WMITLV_SET_HDR( 11778 &cmd->tlv_header, 11779 WMITLV_TAG_STRUC_wmi_pdev_non_srg_obss_color_enable_bitmap_cmd_fixed_param, 11780 WMITLV_GET_STRUCT_TLVLEN 11781 (wmi_pdev_non_srg_obss_color_enable_bitmap_cmd_fixed_param)); 11782 11783 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 11784 wmi_handle, pdev_id); 11785 cmd->non_srg_obss_en_color_bitmap[0] = bitmap_0; 11786 cmd->non_srg_obss_en_color_bitmap[1] = bitmap_1; 11787 11788 ret = wmi_unified_cmd_send( 11789 wmi_handle, buf, len, 11790 WMI_PDEV_SET_NON_SRG_OBSS_COLOR_ENABLE_BITMAP_CMDID); 11791 11792 if (QDF_IS_STATUS_ERROR(ret)) { 11793 wmi_err( 11794 "WMI_PDEV_SET_NON_SRG_OBSS_COLOR_ENABLE_BITMAP_CMDID send returned Error %d", 11795 ret); 11796 wmi_buf_free(buf); 11797 } 11798 11799 return ret; 11800 } 11801 11802 /** 11803 * send_self_non_srg_obss_bssid_enable_bitmap_cmd_tlv() - Send 64-bit OBSS BSSID 11804 * enable bitmap to be used by Non-SRG based Spatial Reuse feature to the FW 11805 * @wmi_handle: wmi handle 11806 * @bitmap_0: lower 32 bits in BSSID enable bitmap 11807 * @bitmap_1: upper 32 bits in BSSID enable bitmap 11808 * @pdev_id: pdev ID 11809 * 11810 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_FAILURE for failure 11811 */ 11812 static QDF_STATUS 11813 send_self_non_srg_obss_bssid_enable_bitmap_cmd_tlv( 11814 wmi_unified_t wmi_handle, uint32_t bitmap_0, 11815 uint32_t bitmap_1, uint8_t pdev_id) 11816 { 11817 wmi_buf_t buf; 11818 wmi_pdev_non_srg_obss_bssid_enable_bitmap_cmd_fixed_param *cmd; 11819 QDF_STATUS ret; 11820 uint32_t len; 11821 11822 len = sizeof(*cmd); 11823 11824 buf = wmi_buf_alloc(wmi_handle, len); 11825 if (!buf) 11826 return QDF_STATUS_E_FAILURE; 11827 11828 cmd = (wmi_pdev_non_srg_obss_bssid_enable_bitmap_cmd_fixed_param *) 11829 wmi_buf_data(buf); 11830 11831 WMITLV_SET_HDR( 11832 &cmd->tlv_header, 11833 WMITLV_TAG_STRUC_wmi_pdev_non_srg_obss_bssid_enable_bitmap_cmd_fixed_param, 11834 WMITLV_GET_STRUCT_TLVLEN 11835 (wmi_pdev_non_srg_obss_bssid_enable_bitmap_cmd_fixed_param)); 11836 11837 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 11838 wmi_handle, pdev_id); 11839 cmd->non_srg_obss_en_bssid_bitmap[0] = bitmap_0; 11840 cmd->non_srg_obss_en_bssid_bitmap[1] = bitmap_1; 11841 11842 ret = wmi_unified_cmd_send( 11843 wmi_handle, buf, len, 11844 WMI_PDEV_SET_NON_SRG_OBSS_BSSID_ENABLE_BITMAP_CMDID); 11845 11846 if (QDF_IS_STATUS_ERROR(ret)) { 11847 wmi_err( 11848 "WMI_PDEV_SET_NON_SRG_OBSS_BSSID_ENABLE_BITMAP_CMDID send returned Error %d", 11849 ret); 11850 wmi_buf_free(buf); 11851 } 11852 11853 return ret; 11854 } 11855 #endif 11856 11857 static 11858 QDF_STATUS send_injector_config_cmd_tlv(wmi_unified_t wmi_handle, 11859 struct wmi_host_injector_frame_params *inject_config_params) 11860 { 11861 wmi_buf_t buf; 11862 wmi_frame_inject_cmd_fixed_param *cmd; 11863 QDF_STATUS ret; 11864 uint32_t len; 11865 11866 len = sizeof(*cmd); 11867 11868 buf = wmi_buf_alloc(wmi_handle, len); 11869 if (!buf) 11870 return QDF_STATUS_E_NOMEM; 11871 11872 cmd = (wmi_frame_inject_cmd_fixed_param *)wmi_buf_data(buf); 11873 WMITLV_SET_HDR(&cmd->tlv_header, 11874 WMITLV_TAG_STRUC_wmi_frame_inject_cmd_fixed_param, 11875 WMITLV_GET_STRUCT_TLVLEN 11876 (wmi_frame_inject_cmd_fixed_param)); 11877 11878 cmd->vdev_id = inject_config_params->vdev_id; 11879 cmd->enable = inject_config_params->enable; 11880 cmd->frame_type = inject_config_params->frame_type; 11881 cmd->frame_inject_period = inject_config_params->frame_inject_period; 11882 cmd->fc_duration = inject_config_params->frame_duration; 11883 WMI_CHAR_ARRAY_TO_MAC_ADDR(inject_config_params->dstmac, 11884 &cmd->frame_addr1); 11885 11886 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 11887 WMI_PDEV_FRAME_INJECT_CMDID); 11888 11889 if (QDF_IS_STATUS_ERROR(ret)) { 11890 wmi_err( 11891 "WMI_PDEV_FRAME_INJECT_CMDID send returned Error %d", 11892 ret); 11893 wmi_buf_free(buf); 11894 } 11895 11896 return ret; 11897 } 11898 #ifdef QCA_SUPPORT_CP_STATS 11899 /** 11900 * extract_cca_stats_tlv - api to extract congestion stats from event buffer 11901 * @wmi_handle: wma handle 11902 * @evt_buf: event buffer 11903 * @out_buff: buffer to populated after stats extraction 11904 * 11905 * Return: status of operation 11906 */ 11907 static QDF_STATUS extract_cca_stats_tlv(wmi_unified_t wmi_handle, 11908 void *evt_buf, struct wmi_host_congestion_stats *out_buff) 11909 { 11910 WMI_UPDATE_STATS_EVENTID_param_tlvs *param_buf; 11911 wmi_congestion_stats *congestion_stats; 11912 11913 param_buf = (WMI_UPDATE_STATS_EVENTID_param_tlvs *)evt_buf; 11914 congestion_stats = param_buf->congestion_stats; 11915 if (!congestion_stats) 11916 return QDF_STATUS_E_INVAL; 11917 11918 out_buff->vdev_id = congestion_stats->vdev_id; 11919 out_buff->congestion = congestion_stats->congestion; 11920 11921 wmi_debug("cca stats event processed"); 11922 return QDF_STATUS_SUCCESS; 11923 } 11924 #endif /* QCA_SUPPORT_CP_STATS */ 11925 11926 /** 11927 * extract_ctl_failsafe_check_ev_param_tlv() - extract ctl data from 11928 * event 11929 * @wmi_handle: wmi handle 11930 * @param evt_buf: pointer to event buffer 11931 * @param param: Pointer to hold peer ctl data 11932 * 11933 * Return: QDF_STATUS_SUCCESS for success or error code 11934 */ 11935 static QDF_STATUS extract_ctl_failsafe_check_ev_param_tlv( 11936 wmi_unified_t wmi_handle, 11937 void *evt_buf, 11938 struct wmi_host_pdev_ctl_failsafe_event *param) 11939 { 11940 WMI_PDEV_CTL_FAILSAFE_CHECK_EVENTID_param_tlvs *param_buf; 11941 wmi_pdev_ctl_failsafe_check_fixed_param *fix_param; 11942 11943 param_buf = (WMI_PDEV_CTL_FAILSAFE_CHECK_EVENTID_param_tlvs *)evt_buf; 11944 if (!param_buf) { 11945 wmi_err("Invalid ctl_failsafe event buffer"); 11946 return QDF_STATUS_E_INVAL; 11947 } 11948 11949 fix_param = param_buf->fixed_param; 11950 param->ctl_failsafe_status = fix_param->ctl_FailsafeStatus; 11951 11952 return QDF_STATUS_SUCCESS; 11953 } 11954 11955 /** 11956 * save_service_bitmap_tlv() - save service bitmap 11957 * @wmi_handle: wmi handle 11958 * @param evt_buf: pointer to event buffer 11959 * @param bitmap_buf: bitmap buffer, for converged legacy support 11960 * 11961 * Return: QDF_STATUS 11962 */ 11963 static 11964 QDF_STATUS save_service_bitmap_tlv(wmi_unified_t wmi_handle, void *evt_buf, 11965 void *bitmap_buf) 11966 { 11967 WMI_SERVICE_READY_EVENTID_param_tlvs *param_buf; 11968 struct wmi_soc *soc = wmi_handle->soc; 11969 11970 param_buf = (WMI_SERVICE_READY_EVENTID_param_tlvs *) evt_buf; 11971 11972 /* If it is already allocated, use that buffer. This can happen 11973 * during target stop/start scenarios where host allocation is skipped. 11974 */ 11975 if (!soc->wmi_service_bitmap) { 11976 soc->wmi_service_bitmap = 11977 qdf_mem_malloc(WMI_SERVICE_BM_SIZE * sizeof(uint32_t)); 11978 if (!soc->wmi_service_bitmap) 11979 return QDF_STATUS_E_NOMEM; 11980 } 11981 11982 qdf_mem_copy(soc->wmi_service_bitmap, 11983 param_buf->wmi_service_bitmap, 11984 (WMI_SERVICE_BM_SIZE * sizeof(uint32_t))); 11985 11986 if (bitmap_buf) 11987 qdf_mem_copy(bitmap_buf, 11988 param_buf->wmi_service_bitmap, 11989 (WMI_SERVICE_BM_SIZE * sizeof(uint32_t))); 11990 11991 return QDF_STATUS_SUCCESS; 11992 } 11993 11994 /** 11995 * save_ext_service_bitmap_tlv() - save extendend service bitmap 11996 * @wmi_handle: wmi handle 11997 * @param evt_buf: pointer to event buffer 11998 * @param bitmap_buf: bitmap buffer, for converged legacy support 11999 * 12000 * Return: QDF_STATUS 12001 */ 12002 static 12003 QDF_STATUS save_ext_service_bitmap_tlv(wmi_unified_t wmi_handle, void *evt_buf, 12004 void *bitmap_buf) 12005 { 12006 WMI_SERVICE_AVAILABLE_EVENTID_param_tlvs *param_buf; 12007 wmi_service_available_event_fixed_param *ev; 12008 struct wmi_soc *soc = wmi_handle->soc; 12009 uint32_t i = 0; 12010 12011 param_buf = (WMI_SERVICE_AVAILABLE_EVENTID_param_tlvs *) evt_buf; 12012 12013 ev = param_buf->fixed_param; 12014 12015 /* If it is already allocated, use that buffer. This can happen 12016 * during target stop/start scenarios where host allocation is skipped. 12017 */ 12018 if (!soc->wmi_ext_service_bitmap) { 12019 soc->wmi_ext_service_bitmap = qdf_mem_malloc( 12020 WMI_SERVICE_SEGMENT_BM_SIZE32 * sizeof(uint32_t)); 12021 if (!soc->wmi_ext_service_bitmap) 12022 return QDF_STATUS_E_NOMEM; 12023 } 12024 12025 qdf_mem_copy(soc->wmi_ext_service_bitmap, 12026 ev->wmi_service_segment_bitmap, 12027 (WMI_SERVICE_SEGMENT_BM_SIZE32 * sizeof(uint32_t))); 12028 12029 wmi_debug("wmi_ext_service_bitmap 0:0x%x, 1:0x%x, 2:0x%x, 3:0x%x", 12030 soc->wmi_ext_service_bitmap[0], soc->wmi_ext_service_bitmap[1], 12031 soc->wmi_ext_service_bitmap[2], soc->wmi_ext_service_bitmap[3]); 12032 12033 if (bitmap_buf) 12034 qdf_mem_copy(bitmap_buf, 12035 soc->wmi_ext_service_bitmap, 12036 (WMI_SERVICE_SEGMENT_BM_SIZE32 * sizeof(uint32_t))); 12037 12038 if (!param_buf->wmi_service_ext_bitmap) { 12039 wmi_debug("wmi_service_ext_bitmap not available"); 12040 return QDF_STATUS_SUCCESS; 12041 } 12042 12043 if (!soc->wmi_ext2_service_bitmap) { 12044 soc->wmi_ext2_service_bitmap = 12045 qdf_mem_malloc(param_buf->num_wmi_service_ext_bitmap * 12046 sizeof(uint32_t)); 12047 if (!soc->wmi_ext2_service_bitmap) 12048 return QDF_STATUS_E_NOMEM; 12049 } 12050 12051 qdf_mem_copy(soc->wmi_ext2_service_bitmap, 12052 param_buf->wmi_service_ext_bitmap, 12053 (param_buf->num_wmi_service_ext_bitmap * 12054 sizeof(uint32_t))); 12055 12056 for (i = 0; i < param_buf->num_wmi_service_ext_bitmap; i++) { 12057 wmi_debug("wmi_ext2_service_bitmap %u:0x%x", 12058 i, soc->wmi_ext2_service_bitmap[i]); 12059 } 12060 12061 return QDF_STATUS_SUCCESS; 12062 } 12063 12064 static inline void copy_ht_cap_info(uint32_t ev_target_cap, 12065 struct wlan_psoc_target_capability_info *cap) 12066 { 12067 /* except LDPC all flags are common betwen legacy and here 12068 * also IBFEER is not defined for TLV 12069 */ 12070 cap->ht_cap_info |= ev_target_cap & ( 12071 WMI_HT_CAP_ENABLED 12072 | WMI_HT_CAP_HT20_SGI 12073 | WMI_HT_CAP_DYNAMIC_SMPS 12074 | WMI_HT_CAP_TX_STBC 12075 | WMI_HT_CAP_TX_STBC_MASK_SHIFT 12076 | WMI_HT_CAP_RX_STBC 12077 | WMI_HT_CAP_RX_STBC_MASK_SHIFT 12078 | WMI_HT_CAP_LDPC 12079 | WMI_HT_CAP_L_SIG_TXOP_PROT 12080 | WMI_HT_CAP_MPDU_DENSITY 12081 | WMI_HT_CAP_MPDU_DENSITY_MASK_SHIFT 12082 | WMI_HT_CAP_HT40_SGI); 12083 if (ev_target_cap & WMI_HT_CAP_LDPC) 12084 cap->ht_cap_info |= WMI_HOST_HT_CAP_RX_LDPC | 12085 WMI_HOST_HT_CAP_TX_LDPC; 12086 } 12087 /** 12088 * extract_service_ready_tlv() - extract service ready event 12089 * @wmi_handle: wmi handle 12090 * @param evt_buf: pointer to received event buffer 12091 * @param cap: pointer to hold target capability information extracted from even 12092 * 12093 * Return: QDF_STATUS_SUCCESS for success or error code 12094 */ 12095 static QDF_STATUS extract_service_ready_tlv(wmi_unified_t wmi_handle, 12096 void *evt_buf, struct wlan_psoc_target_capability_info *cap) 12097 { 12098 WMI_SERVICE_READY_EVENTID_param_tlvs *param_buf; 12099 wmi_service_ready_event_fixed_param *ev; 12100 12101 12102 param_buf = (WMI_SERVICE_READY_EVENTID_param_tlvs *) evt_buf; 12103 12104 ev = (wmi_service_ready_event_fixed_param *) param_buf->fixed_param; 12105 if (!ev) { 12106 qdf_print("%s: wmi_buf_alloc failed", __func__); 12107 return QDF_STATUS_E_FAILURE; 12108 } 12109 12110 cap->phy_capability = ev->phy_capability; 12111 cap->max_frag_entry = ev->max_frag_entry; 12112 cap->num_rf_chains = ev->num_rf_chains; 12113 copy_ht_cap_info(ev->ht_cap_info, cap); 12114 cap->vht_cap_info = ev->vht_cap_info; 12115 cap->vht_supp_mcs = ev->vht_supp_mcs; 12116 cap->hw_min_tx_power = ev->hw_min_tx_power; 12117 cap->hw_max_tx_power = ev->hw_max_tx_power; 12118 cap->sys_cap_info = ev->sys_cap_info; 12119 cap->min_pkt_size_enable = ev->min_pkt_size_enable; 12120 cap->max_bcn_ie_size = ev->max_bcn_ie_size; 12121 cap->max_num_scan_channels = ev->max_num_scan_channels; 12122 cap->max_supported_macs = ev->max_supported_macs; 12123 cap->wmi_fw_sub_feat_caps = ev->wmi_fw_sub_feat_caps; 12124 cap->txrx_chainmask = ev->txrx_chainmask; 12125 cap->default_dbs_hw_mode_index = ev->default_dbs_hw_mode_index; 12126 cap->num_msdu_desc = ev->num_msdu_desc; 12127 cap->fw_version = ev->fw_build_vers; 12128 /* fw_version_1 is not available in TLV. */ 12129 cap->fw_version_1 = 0; 12130 12131 return QDF_STATUS_SUCCESS; 12132 } 12133 12134 /* convert_wireless_modes_tlv() - Convert REGDMN_MODE values sent by target 12135 * to host internal HOST_REGDMN_MODE values. 12136 * REGULATORY TODO : REGDMN_MODE_11AC_VHT*_2G values are not used by the 12137 * host currently. Add this in the future if required. 12138 * 11AX (Phase II) : 11ax related values are not currently 12139 * advertised separately by FW. As part of phase II regulatory bring-up, 12140 * finalize the advertisement mechanism. 12141 * @target_wireless_mode: target wireless mode received in message 12142 * 12143 * Return: returns the host internal wireless mode. 12144 */ 12145 static inline uint32_t convert_wireless_modes_tlv(uint32_t target_wireless_mode) 12146 { 12147 12148 uint32_t wireless_modes = 0; 12149 12150 wmi_debug("Target wireless mode: 0x%x", target_wireless_mode); 12151 12152 if (target_wireless_mode & REGDMN_MODE_11A) 12153 wireless_modes |= HOST_REGDMN_MODE_11A; 12154 12155 if (target_wireless_mode & REGDMN_MODE_TURBO) 12156 wireless_modes |= HOST_REGDMN_MODE_TURBO; 12157 12158 if (target_wireless_mode & REGDMN_MODE_11B) 12159 wireless_modes |= HOST_REGDMN_MODE_11B; 12160 12161 if (target_wireless_mode & REGDMN_MODE_PUREG) 12162 wireless_modes |= HOST_REGDMN_MODE_PUREG; 12163 12164 if (target_wireless_mode & REGDMN_MODE_11G) 12165 wireless_modes |= HOST_REGDMN_MODE_11G; 12166 12167 if (target_wireless_mode & REGDMN_MODE_108G) 12168 wireless_modes |= HOST_REGDMN_MODE_108G; 12169 12170 if (target_wireless_mode & REGDMN_MODE_108A) 12171 wireless_modes |= HOST_REGDMN_MODE_108A; 12172 12173 if (target_wireless_mode & REGDMN_MODE_11AC_VHT20_2G) 12174 wireless_modes |= HOST_REGDMN_MODE_11AC_VHT20_2G; 12175 12176 if (target_wireless_mode & REGDMN_MODE_XR) 12177 wireless_modes |= HOST_REGDMN_MODE_XR; 12178 12179 if (target_wireless_mode & REGDMN_MODE_11A_HALF_RATE) 12180 wireless_modes |= HOST_REGDMN_MODE_11A_HALF_RATE; 12181 12182 if (target_wireless_mode & REGDMN_MODE_11A_QUARTER_RATE) 12183 wireless_modes |= HOST_REGDMN_MODE_11A_QUARTER_RATE; 12184 12185 if (target_wireless_mode & REGDMN_MODE_11NG_HT20) 12186 wireless_modes |= HOST_REGDMN_MODE_11NG_HT20; 12187 12188 if (target_wireless_mode & REGDMN_MODE_11NA_HT20) 12189 wireless_modes |= HOST_REGDMN_MODE_11NA_HT20; 12190 12191 if (target_wireless_mode & REGDMN_MODE_11NG_HT40PLUS) 12192 wireless_modes |= HOST_REGDMN_MODE_11NG_HT40PLUS; 12193 12194 if (target_wireless_mode & REGDMN_MODE_11NG_HT40MINUS) 12195 wireless_modes |= HOST_REGDMN_MODE_11NG_HT40MINUS; 12196 12197 if (target_wireless_mode & REGDMN_MODE_11NA_HT40PLUS) 12198 wireless_modes |= HOST_REGDMN_MODE_11NA_HT40PLUS; 12199 12200 if (target_wireless_mode & REGDMN_MODE_11NA_HT40MINUS) 12201 wireless_modes |= HOST_REGDMN_MODE_11NA_HT40MINUS; 12202 12203 if (target_wireless_mode & REGDMN_MODE_11AC_VHT20) 12204 wireless_modes |= HOST_REGDMN_MODE_11AC_VHT20; 12205 12206 if (target_wireless_mode & REGDMN_MODE_11AC_VHT40PLUS) 12207 wireless_modes |= HOST_REGDMN_MODE_11AC_VHT40PLUS; 12208 12209 if (target_wireless_mode & REGDMN_MODE_11AC_VHT40MINUS) 12210 wireless_modes |= HOST_REGDMN_MODE_11AC_VHT40MINUS; 12211 12212 if (target_wireless_mode & REGDMN_MODE_11AC_VHT80) 12213 wireless_modes |= HOST_REGDMN_MODE_11AC_VHT80; 12214 12215 if (target_wireless_mode & REGDMN_MODE_11AC_VHT160) 12216 wireless_modes |= HOST_REGDMN_MODE_11AC_VHT160; 12217 12218 if (target_wireless_mode & REGDMN_MODE_11AC_VHT80_80) 12219 wireless_modes |= HOST_REGDMN_MODE_11AC_VHT80_80; 12220 12221 return wireless_modes; 12222 } 12223 12224 /** 12225 * convert_11be_phybitmap_to_reg_flags() - Convert 11BE phybitmap to 12226 * to regulatory flags. 12227 * @target_phybitmap: target phybitmap. 12228 * @phybitmap: host internal REGULATORY_PHYMODE set based on target 12229 * phybitmap. 12230 * 12231 * Return: None 12232 */ 12233 12234 #ifdef WLAN_FEATURE_11BE 12235 static void convert_11be_phybitmap_to_reg_flags(uint32_t target_phybitmap, 12236 uint32_t *phybitmap) 12237 { 12238 if (target_phybitmap & WMI_REGULATORY_PHYMODE_NO11BE) 12239 *phybitmap |= REGULATORY_PHYMODE_NO11BE; 12240 } 12241 #else 12242 static void convert_11be_phybitmap_to_reg_flags(uint32_t target_phybitmap, 12243 uint32_t *phybitmap) 12244 { 12245 } 12246 #endif 12247 12248 /* convert_phybitmap_tlv() - Convert WMI_REGULATORY_PHYBITMAP values sent by 12249 * target to host internal REGULATORY_PHYMODE values. 12250 * 12251 * @target_target_phybitmap: target phybitmap received in the message. 12252 * 12253 * Return: returns the host internal REGULATORY_PHYMODE. 12254 */ 12255 static uint32_t convert_phybitmap_tlv(uint32_t target_phybitmap) 12256 { 12257 uint32_t phybitmap = 0; 12258 12259 wmi_debug("Target phybitmap: 0x%x", target_phybitmap); 12260 12261 if (target_phybitmap & WMI_REGULATORY_PHYMODE_NO11A) 12262 phybitmap |= REGULATORY_PHYMODE_NO11A; 12263 12264 if (target_phybitmap & WMI_REGULATORY_PHYMODE_NO11B) 12265 phybitmap |= REGULATORY_PHYMODE_NO11B; 12266 12267 if (target_phybitmap & WMI_REGULATORY_PHYMODE_NO11G) 12268 phybitmap |= REGULATORY_PHYMODE_NO11G; 12269 12270 if (target_phybitmap & WMI_REGULATORY_PHYMODE_NO11N) 12271 phybitmap |= REGULATORY_CHAN_NO11N; 12272 12273 if (target_phybitmap & WMI_REGULATORY_PHYMODE_NO11AC) 12274 phybitmap |= REGULATORY_PHYMODE_NO11AC; 12275 12276 if (target_phybitmap & WMI_REGULATORY_PHYMODE_NO11AX) 12277 phybitmap |= REGULATORY_PHYMODE_NO11AX; 12278 12279 convert_11be_phybitmap_to_reg_flags(target_phybitmap, &phybitmap); 12280 12281 return phybitmap; 12282 } 12283 12284 /** 12285 * convert_11be_flags_to_modes_ext() - Convert 11BE wireless mode flag 12286 * advertised by the target to wireless mode ext flags. 12287 * @target_wireless_modes_ext: Target wireless mode 12288 * @wireless_modes_ext: Variable to hold all the target wireless mode caps. 12289 * 12290 * Return: None 12291 */ 12292 #ifdef WLAN_FEATURE_11BE 12293 static void convert_11be_flags_to_modes_ext(uint32_t target_wireless_modes_ext, 12294 uint64_t *wireless_modes_ext) 12295 { 12296 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEG_EHT20) 12297 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEG_EHT20; 12298 12299 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEG_EHT40PLUS) 12300 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEG_EHT40PLUS; 12301 12302 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEG_EHT40MINUS) 12303 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEG_EHT40MINUS; 12304 12305 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEA_EHT20) 12306 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEA_EHT20; 12307 12308 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEA_EHT40PLUS) 12309 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEA_EHT40PLUS; 12310 12311 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEA_EHT40MINUS) 12312 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEA_EHT40MINUS; 12313 12314 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEA_EHT80) 12315 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEA_EHT80; 12316 12317 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEA_EHT160) 12318 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEA_EHT160; 12319 12320 if (target_wireless_modes_ext & REGDMN_MODE_U32_11BEA_EHT320) 12321 *wireless_modes_ext |= HOST_REGDMN_MODE_11BEA_EHT320; 12322 } 12323 #else 12324 static void convert_11be_flags_to_modes_ext(uint32_t target_wireless_modes_ext, 12325 uint64_t *wireless_modes_ext) 12326 { 12327 } 12328 #endif 12329 12330 static inline uint64_t convert_wireless_modes_ext_tlv( 12331 uint32_t target_wireless_modes_ext) 12332 { 12333 uint64_t wireless_modes_ext = 0; 12334 12335 wmi_debug("Target wireless mode: 0x%x", target_wireless_modes_ext); 12336 12337 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXG_HE20) 12338 wireless_modes_ext |= HOST_REGDMN_MODE_11AXG_HE20; 12339 12340 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXG_HE40PLUS) 12341 wireless_modes_ext |= HOST_REGDMN_MODE_11AXG_HE40PLUS; 12342 12343 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXG_HE40MINUS) 12344 wireless_modes_ext |= HOST_REGDMN_MODE_11AXG_HE40MINUS; 12345 12346 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXA_HE20) 12347 wireless_modes_ext |= HOST_REGDMN_MODE_11AXA_HE20; 12348 12349 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXA_HE40PLUS) 12350 wireless_modes_ext |= HOST_REGDMN_MODE_11AXA_HE40PLUS; 12351 12352 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXA_HE40MINUS) 12353 wireless_modes_ext |= HOST_REGDMN_MODE_11AXA_HE40MINUS; 12354 12355 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXA_HE80) 12356 wireless_modes_ext |= HOST_REGDMN_MODE_11AXA_HE80; 12357 12358 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXA_HE160) 12359 wireless_modes_ext |= HOST_REGDMN_MODE_11AXA_HE160; 12360 12361 if (target_wireless_modes_ext & REGDMN_MODE_U32_11AXA_HE80_80) 12362 wireless_modes_ext |= HOST_REGDMN_MODE_11AXA_HE80_80; 12363 12364 convert_11be_flags_to_modes_ext(target_wireless_modes_ext, 12365 &wireless_modes_ext); 12366 12367 return wireless_modes_ext; 12368 } 12369 12370 /** 12371 * extract_hal_reg_cap_tlv() - extract HAL registered capabilities 12372 * @wmi_handle: wmi handle 12373 * @param evt_buf: Pointer to event buffer 12374 * @param cap: pointer to hold HAL reg capabilities 12375 * 12376 * Return: QDF_STATUS_SUCCESS for success or error code 12377 */ 12378 static QDF_STATUS extract_hal_reg_cap_tlv(wmi_unified_t wmi_handle, 12379 void *evt_buf, struct wlan_psoc_hal_reg_capability *cap) 12380 { 12381 WMI_SERVICE_READY_EVENTID_param_tlvs *param_buf; 12382 12383 param_buf = (WMI_SERVICE_READY_EVENTID_param_tlvs *) evt_buf; 12384 if (!param_buf || !param_buf->hal_reg_capabilities) { 12385 wmi_err("Invalid arguments"); 12386 return QDF_STATUS_E_FAILURE; 12387 } 12388 qdf_mem_copy(cap, (((uint8_t *)param_buf->hal_reg_capabilities) + 12389 sizeof(uint32_t)), 12390 sizeof(struct wlan_psoc_hal_reg_capability)); 12391 12392 cap->wireless_modes = convert_wireless_modes_tlv( 12393 param_buf->hal_reg_capabilities->wireless_modes); 12394 12395 return QDF_STATUS_SUCCESS; 12396 } 12397 12398 /** 12399 * extract_hal_reg_cap_ext2_tlv() - extract HAL registered capability ext 12400 * @wmi_handle: wmi handle 12401 * @param evt_buf: Pointer to event buffer 12402 * @param cap: pointer to hold HAL reg capabilities 12403 * 12404 * Return: QDF_STATUS_SUCCESS for success or error code 12405 */ 12406 static QDF_STATUS extract_hal_reg_cap_ext2_tlv( 12407 wmi_unified_t wmi_handle, void *evt_buf, uint8_t phy_idx, 12408 struct wlan_psoc_host_hal_reg_capabilities_ext2 *param) 12409 { 12410 WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *param_buf; 12411 WMI_HAL_REG_CAPABILITIES_EXT2 *reg_caps; 12412 12413 if (!evt_buf) { 12414 wmi_err("null evt_buf"); 12415 return QDF_STATUS_E_INVAL; 12416 } 12417 12418 param_buf = (WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *)evt_buf; 12419 12420 if (!param_buf->num_hal_reg_caps) 12421 return QDF_STATUS_SUCCESS; 12422 12423 if (phy_idx >= param_buf->num_hal_reg_caps) 12424 return QDF_STATUS_E_INVAL; 12425 12426 reg_caps = ¶m_buf->hal_reg_caps[phy_idx]; 12427 12428 param->phy_id = reg_caps->phy_id; 12429 param->wireless_modes_ext = convert_wireless_modes_ext_tlv( 12430 reg_caps->wireless_modes_ext); 12431 12432 return QDF_STATUS_SUCCESS; 12433 } 12434 12435 /** 12436 * extract_num_mem_reqs_tlv() - Extract number of memory entries requested 12437 * @wmi_handle: wmi handle 12438 * @evt_buf: pointer to event buffer 12439 * 12440 * Return: Number of entries requested 12441 */ 12442 static uint32_t extract_num_mem_reqs_tlv(wmi_unified_t wmi_handle, 12443 void *evt_buf) 12444 { 12445 WMI_SERVICE_READY_EVENTID_param_tlvs *param_buf; 12446 wmi_service_ready_event_fixed_param *ev; 12447 12448 param_buf = (WMI_SERVICE_READY_EVENTID_param_tlvs *) evt_buf; 12449 12450 ev = (wmi_service_ready_event_fixed_param *) param_buf->fixed_param; 12451 if (!ev) { 12452 qdf_print("%s: wmi_buf_alloc failed", __func__); 12453 return 0; 12454 } 12455 12456 if (ev->num_mem_reqs > param_buf->num_mem_reqs) { 12457 wmi_err("Invalid num_mem_reqs %d:%d", 12458 ev->num_mem_reqs, param_buf->num_mem_reqs); 12459 return 0; 12460 } 12461 12462 return ev->num_mem_reqs; 12463 } 12464 12465 /** 12466 * extract_host_mem_req_tlv() - Extract host memory required from 12467 * service ready event 12468 * @wmi_handle: wmi handle 12469 * @evt_buf: pointer to event buffer 12470 * @mem_reqs: pointer to host memory request structure 12471 * @num_active_peers: number of active peers for peer cache 12472 * @num_peers: number of peers 12473 * @fw_prio: FW priority 12474 * @idx: index for memory request 12475 * 12476 * Return: Host memory request parameters requested by target 12477 */ 12478 static QDF_STATUS extract_host_mem_req_tlv(wmi_unified_t wmi_handle, 12479 void *evt_buf, 12480 host_mem_req *mem_reqs, 12481 uint32_t num_active_peers, 12482 uint32_t num_peers, 12483 enum wmi_fw_mem_prio fw_prio, 12484 uint16_t idx) 12485 { 12486 WMI_SERVICE_READY_EVENTID_param_tlvs *param_buf; 12487 12488 param_buf = (WMI_SERVICE_READY_EVENTID_param_tlvs *)evt_buf; 12489 12490 mem_reqs->req_id = (uint32_t)param_buf->mem_reqs[idx].req_id; 12491 mem_reqs->unit_size = (uint32_t)param_buf->mem_reqs[idx].unit_size; 12492 mem_reqs->num_unit_info = 12493 (uint32_t)param_buf->mem_reqs[idx].num_unit_info; 12494 mem_reqs->num_units = (uint32_t)param_buf->mem_reqs[idx].num_units; 12495 mem_reqs->tgt_num_units = 0; 12496 12497 if (((fw_prio == WMI_FW_MEM_HIGH_PRIORITY) && 12498 (mem_reqs->num_unit_info & 12499 REQ_TO_HOST_FOR_CONT_MEMORY)) || 12500 ((fw_prio == WMI_FW_MEM_LOW_PRIORITY) && 12501 (!(mem_reqs->num_unit_info & 12502 REQ_TO_HOST_FOR_CONT_MEMORY)))) { 12503 /* First allocate the memory that requires contiguous memory */ 12504 mem_reqs->tgt_num_units = mem_reqs->num_units; 12505 if (mem_reqs->num_unit_info) { 12506 if (mem_reqs->num_unit_info & 12507 NUM_UNITS_IS_NUM_PEERS) { 12508 /* 12509 * number of units allocated is equal to number 12510 * of peers, 1 extra for self peer on target. 12511 * this needs to be fixed, host and target can 12512 * get out of sync 12513 */ 12514 mem_reqs->tgt_num_units = num_peers + 1; 12515 } 12516 if (mem_reqs->num_unit_info & 12517 NUM_UNITS_IS_NUM_ACTIVE_PEERS) { 12518 /* 12519 * Requesting allocation of memory using 12520 * num_active_peers in qcache. if qcache is 12521 * disabled in host, then it should allocate 12522 * memory for num_peers instead of 12523 * num_active_peers. 12524 */ 12525 if (num_active_peers) 12526 mem_reqs->tgt_num_units = 12527 num_active_peers + 1; 12528 else 12529 mem_reqs->tgt_num_units = 12530 num_peers + 1; 12531 } 12532 } 12533 12534 wmi_debug("idx %d req %d num_units %d num_unit_info %d" 12535 "unit size %d actual units %d", 12536 idx, mem_reqs->req_id, 12537 mem_reqs->num_units, 12538 mem_reqs->num_unit_info, 12539 mem_reqs->unit_size, 12540 mem_reqs->tgt_num_units); 12541 } 12542 12543 return QDF_STATUS_SUCCESS; 12544 } 12545 12546 /** 12547 * save_fw_version_in_service_ready_tlv() - Save fw version in service 12548 * ready function 12549 * @wmi_handle: wmi handle 12550 * @param evt_buf: pointer to event buffer 12551 * 12552 * Return: QDF_STATUS_SUCCESS for success or error code 12553 */ 12554 static QDF_STATUS 12555 save_fw_version_in_service_ready_tlv(wmi_unified_t wmi_handle, void *evt_buf) 12556 { 12557 WMI_SERVICE_READY_EVENTID_param_tlvs *param_buf; 12558 wmi_service_ready_event_fixed_param *ev; 12559 12560 12561 param_buf = (WMI_SERVICE_READY_EVENTID_param_tlvs *) evt_buf; 12562 12563 ev = (wmi_service_ready_event_fixed_param *) param_buf->fixed_param; 12564 if (!ev) { 12565 qdf_print("%s: wmi_buf_alloc failed", __func__); 12566 return QDF_STATUS_E_FAILURE; 12567 } 12568 12569 /*Save fw version from service ready message */ 12570 /*This will be used while sending INIT message */ 12571 qdf_mem_copy(&wmi_handle->fw_abi_version, &ev->fw_abi_vers, 12572 sizeof(wmi_handle->fw_abi_version)); 12573 12574 return QDF_STATUS_SUCCESS; 12575 } 12576 12577 /** 12578 * ready_extract_init_status_tlv() - Extract init status from ready event 12579 * @wmi_handle: wmi handle 12580 * @param evt_buf: Pointer to event buffer 12581 * 12582 * Return: ready status 12583 */ 12584 static uint32_t ready_extract_init_status_tlv(wmi_unified_t wmi_handle, 12585 void *evt_buf) 12586 { 12587 WMI_READY_EVENTID_param_tlvs *param_buf = NULL; 12588 wmi_ready_event_fixed_param *ev = NULL; 12589 12590 param_buf = (WMI_READY_EVENTID_param_tlvs *) evt_buf; 12591 ev = param_buf->fixed_param; 12592 12593 qdf_print("%s:%d", __func__, ev->status); 12594 12595 return ev->status; 12596 } 12597 12598 /** 12599 * ready_extract_mac_addr_tlv() - extract mac address from ready event 12600 * @wmi_handle: wmi handle 12601 * @param evt_buf: pointer to event buffer 12602 * @param macaddr: Pointer to hold MAC address 12603 * 12604 * Return: QDF_STATUS_SUCCESS for success or error code 12605 */ 12606 static QDF_STATUS ready_extract_mac_addr_tlv(wmi_unified_t wmi_hamdle, 12607 void *evt_buf, uint8_t *macaddr) 12608 { 12609 WMI_READY_EVENTID_param_tlvs *param_buf = NULL; 12610 wmi_ready_event_fixed_param *ev = NULL; 12611 12612 12613 param_buf = (WMI_READY_EVENTID_param_tlvs *) evt_buf; 12614 ev = param_buf->fixed_param; 12615 12616 WMI_MAC_ADDR_TO_CHAR_ARRAY(&ev->mac_addr, macaddr); 12617 12618 return QDF_STATUS_SUCCESS; 12619 } 12620 12621 /** 12622 * ready_extract_mac_addr_list_tlv() - extract MAC address list from ready event 12623 * @wmi_handle: wmi handle 12624 * @param evt_buf: pointer to event buffer 12625 * @param macaddr: Pointer to hold number of MAC addresses 12626 * 12627 * Return: Pointer to addr list 12628 */ 12629 static wmi_host_mac_addr *ready_extract_mac_addr_list_tlv(wmi_unified_t wmi_hamdle, 12630 void *evt_buf, uint8_t *num_mac) 12631 { 12632 WMI_READY_EVENTID_param_tlvs *param_buf = NULL; 12633 wmi_ready_event_fixed_param *ev = NULL; 12634 12635 param_buf = (WMI_READY_EVENTID_param_tlvs *) evt_buf; 12636 ev = param_buf->fixed_param; 12637 12638 *num_mac = ev->num_extra_mac_addr; 12639 12640 return (wmi_host_mac_addr *) param_buf->mac_addr_list; 12641 } 12642 12643 /** 12644 * extract_ready_params_tlv() - Extract data from ready event apart from 12645 * status, macaddr and version. 12646 * @wmi_handle: Pointer to WMI handle. 12647 * @evt_buf: Pointer to Ready event buffer. 12648 * @ev_param: Pointer to host defined struct to copy the data from event. 12649 * 12650 * Return: QDF_STATUS_SUCCESS on success. 12651 */ 12652 static QDF_STATUS extract_ready_event_params_tlv(wmi_unified_t wmi_handle, 12653 void *evt_buf, struct wmi_host_ready_ev_param *ev_param) 12654 { 12655 WMI_READY_EVENTID_param_tlvs *param_buf = NULL; 12656 wmi_ready_event_fixed_param *ev = NULL; 12657 12658 param_buf = (WMI_READY_EVENTID_param_tlvs *) evt_buf; 12659 ev = param_buf->fixed_param; 12660 12661 ev_param->status = ev->status; 12662 ev_param->num_dscp_table = ev->num_dscp_table; 12663 ev_param->num_extra_mac_addr = ev->num_extra_mac_addr; 12664 ev_param->num_total_peer = ev->num_total_peers; 12665 ev_param->num_extra_peer = ev->num_extra_peers; 12666 /* Agile_capability in ready event is supported in TLV target, 12667 * as per aDFS FR 12668 */ 12669 ev_param->max_ast_index = ev->max_ast_index; 12670 ev_param->pktlog_defs_checksum = ev->pktlog_defs_checksum; 12671 ev_param->agile_capability = 1; 12672 ev_param->num_max_active_vdevs = ev->num_max_active_vdevs; 12673 12674 return QDF_STATUS_SUCCESS; 12675 } 12676 12677 /** 12678 * extract_dbglog_data_len_tlv() - extract debuglog data length 12679 * @wmi_handle: wmi handle 12680 * @param evt_buf: pointer to event buffer 12681 * 12682 * Return: length 12683 */ 12684 static uint8_t *extract_dbglog_data_len_tlv(wmi_unified_t wmi_handle, 12685 void *evt_buf, uint32_t *len) 12686 { 12687 WMI_DEBUG_MESG_EVENTID_param_tlvs *param_buf; 12688 12689 param_buf = (WMI_DEBUG_MESG_EVENTID_param_tlvs *) evt_buf; 12690 12691 *len = param_buf->num_bufp; 12692 12693 return param_buf->bufp; 12694 } 12695 12696 12697 #ifdef MGMT_FRAME_RX_DECRYPT_ERROR 12698 #define IS_WMI_RX_MGMT_FRAME_STATUS_INVALID(_status) false 12699 #else 12700 #define IS_WMI_RX_MGMT_FRAME_STATUS_INVALID(_status) \ 12701 ((_status) & WMI_RXERR_DECRYPT) 12702 #endif 12703 12704 /** 12705 * extract_mgmt_rx_params_tlv() - extract management rx params from event 12706 * @wmi_handle: wmi handle 12707 * @param evt_buf: pointer to event buffer 12708 * @param hdr: Pointer to hold header 12709 * @param bufp: Pointer to hold pointer to rx param buffer 12710 * 12711 * Return: QDF_STATUS_SUCCESS for success or error code 12712 */ 12713 static QDF_STATUS extract_mgmt_rx_params_tlv(wmi_unified_t wmi_handle, 12714 void *evt_buf, struct mgmt_rx_event_params *hdr, 12715 uint8_t **bufp) 12716 { 12717 WMI_MGMT_RX_EVENTID_param_tlvs *param_tlvs = NULL; 12718 wmi_mgmt_rx_hdr *ev_hdr = NULL; 12719 int i; 12720 12721 param_tlvs = (WMI_MGMT_RX_EVENTID_param_tlvs *) evt_buf; 12722 if (!param_tlvs) { 12723 wmi_err("Get NULL point message from FW"); 12724 return QDF_STATUS_E_INVAL; 12725 } 12726 12727 ev_hdr = param_tlvs->hdr; 12728 if (!hdr) { 12729 wmi_err("Rx event is NULL"); 12730 return QDF_STATUS_E_INVAL; 12731 } 12732 12733 if (IS_WMI_RX_MGMT_FRAME_STATUS_INVALID(ev_hdr->status)) { 12734 wmi_err("RX mgmt frame decrypt error, discard it"); 12735 return QDF_STATUS_E_INVAL; 12736 } 12737 12738 if (ev_hdr->buf_len > param_tlvs->num_bufp) { 12739 wmi_err("Rx mgmt frame length mismatch, discard it"); 12740 return QDF_STATUS_E_INVAL; 12741 } 12742 12743 hdr->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 12744 wmi_handle, 12745 ev_hdr->pdev_id); 12746 hdr->chan_freq = ev_hdr->chan_freq; 12747 hdr->channel = ev_hdr->channel; 12748 hdr->snr = ev_hdr->snr; 12749 hdr->rate = ev_hdr->rate; 12750 hdr->phy_mode = ev_hdr->phy_mode; 12751 hdr->buf_len = ev_hdr->buf_len; 12752 hdr->status = ev_hdr->status; 12753 hdr->flags = ev_hdr->flags; 12754 hdr->rssi = ev_hdr->rssi; 12755 hdr->tsf_delta = ev_hdr->tsf_delta; 12756 hdr->tsf_l32 = ev_hdr->rx_tsf_l32; 12757 for (i = 0; i < ATH_MAX_ANTENNA; i++) 12758 hdr->rssi_ctl[i] = ev_hdr->rssi_ctl[i]; 12759 12760 *bufp = param_tlvs->bufp; 12761 12762 return QDF_STATUS_SUCCESS; 12763 } 12764 12765 static QDF_STATUS extract_mgmt_rx_ext_params_tlv(wmi_unified_t wmi_handle, 12766 void *evt_buf, struct mgmt_rx_event_ext_params *ext_params) 12767 { 12768 WMI_MGMT_RX_EVENTID_param_tlvs *param_tlvs; 12769 wmi_mgmt_rx_params_ext *ext_params_tlv; 12770 wmi_mgmt_rx_hdr *ev_hdr; 12771 12772 param_tlvs = (WMI_MGMT_RX_EVENTID_param_tlvs *) evt_buf; 12773 if (!param_tlvs) { 12774 wmi_err("param_tlvs is NULL"); 12775 return QDF_STATUS_E_INVAL; 12776 } 12777 12778 ev_hdr = param_tlvs->hdr; 12779 if (!ev_hdr) { 12780 wmi_err("Rx event is NULL"); 12781 return QDF_STATUS_E_INVAL; 12782 } 12783 12784 ext_params_tlv = param_tlvs->mgmt_rx_params_ext; 12785 if (ext_params_tlv) { 12786 ext_params->ba_win_size = WMI_RX_PARAM_EXT_BA_WIN_SIZE_GET( 12787 ext_params_tlv->mgmt_rx_params_ext_dword1); 12788 if (ext_params->ba_win_size > 1024) { 12789 wmi_err("ba win size from TLV is Invalid"); 12790 return QDF_STATUS_E_INVAL; 12791 } 12792 12793 ext_params->reo_win_size = WMI_RX_PARAM_EXT_REO_WIN_SIZE_GET( 12794 ext_params_tlv->mgmt_rx_params_ext_dword1); 12795 if (ext_params->reo_win_size > 2048) { 12796 wmi_err("reo win size from TLV is Invalid"); 12797 return QDF_STATUS_E_INVAL; 12798 } 12799 } else { 12800 ext_params->ba_win_size = 0; 12801 ext_params->reo_win_size = 0; 12802 } 12803 12804 return QDF_STATUS_SUCCESS; 12805 } 12806 12807 #ifdef WLAN_MGMT_RX_REO_SUPPORT 12808 /** 12809 * extract_mgmt_rx_fw_consumed_tlv() - extract MGMT Rx FW consumed event 12810 * @wmi_handle: wmi handle 12811 * @evt_buf: pointer to event buffer 12812 * @params: Pointer to MGMT Rx REO parameters 12813 * 12814 * Return: QDF_STATUS_SUCCESS for success or error code 12815 */ 12816 static QDF_STATUS 12817 extract_mgmt_rx_fw_consumed_tlv(wmi_unified_t wmi_handle, 12818 void *evt_buf, 12819 struct mgmt_rx_reo_params *params) 12820 { 12821 WMI_MGMT_RX_FW_CONSUMED_EVENTID_param_tlvs *param_tlvs; 12822 wmi_mgmt_rx_fw_consumed_hdr *ev_hdr; 12823 12824 param_tlvs = evt_buf; 12825 if (!param_tlvs) { 12826 wmi_err("param_tlvs is NULL"); 12827 return QDF_STATUS_E_INVAL; 12828 } 12829 12830 ev_hdr = param_tlvs->hdr; 12831 if (!params) { 12832 wmi_err("Rx REO parameters is NULL"); 12833 return QDF_STATUS_E_INVAL; 12834 } 12835 12836 params->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 12837 wmi_handle, 12838 ev_hdr->pdev_id); 12839 params->valid = WMI_MGMT_RX_FW_CONSUMED_PARAM_MGMT_PKT_CTR_VALID_GET( 12840 ev_hdr->mgmt_pkt_ctr_info); 12841 params->global_timestamp = ev_hdr->global_timestamp; 12842 params->mgmt_pkt_ctr = WMI_MGMT_RX_FW_CONSUMED_PARAM_MGMT_PKT_CTR_GET( 12843 ev_hdr->mgmt_pkt_ctr_info); 12844 params->duration_us = ev_hdr->rx_ppdu_duration_us; 12845 params->start_timestamp = params->global_timestamp; 12846 params->end_timestamp = params->start_timestamp + 12847 params->duration_us; 12848 12849 return QDF_STATUS_SUCCESS; 12850 } 12851 12852 /** 12853 * extract_mgmt_rx_reo_params_tlv() - extract MGMT Rx REO params from 12854 * MGMT_RX_EVENT_ID 12855 * @wmi_handle: wmi handle 12856 * @evt_buf: pointer to event buffer 12857 * @params: Pointer to MGMT Rx REO parameters 12858 * 12859 * Return: QDF_STATUS_SUCCESS for success or error code 12860 */ 12861 static QDF_STATUS extract_mgmt_rx_reo_params_tlv(wmi_unified_t wmi_handle, 12862 void *evt_buf, struct mgmt_rx_reo_params *reo_params) 12863 { 12864 WMI_MGMT_RX_EVENTID_param_tlvs *param_tlvs; 12865 wmi_mgmt_rx_reo_params *reo_params_tlv; 12866 wmi_mgmt_rx_hdr *ev_hdr; 12867 12868 param_tlvs = evt_buf; 12869 if (!param_tlvs) { 12870 wmi_err("param_tlvs is NULL"); 12871 return QDF_STATUS_E_INVAL; 12872 } 12873 12874 ev_hdr = param_tlvs->hdr; 12875 if (!ev_hdr) { 12876 wmi_err("Rx event is NULL"); 12877 return QDF_STATUS_E_INVAL; 12878 } 12879 12880 reo_params_tlv = param_tlvs->reo_params; 12881 if (!reo_params_tlv) { 12882 wmi_err("mgmt_rx_reo_params TLV is not sent by FW"); 12883 return QDF_STATUS_E_INVAL; 12884 } 12885 12886 if (!reo_params) { 12887 wmi_err("MGMT Rx REO params is NULL"); 12888 return QDF_STATUS_E_INVAL; 12889 } 12890 12891 reo_params->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 12892 wmi_handle, 12893 ev_hdr->pdev_id); 12894 reo_params->valid = WMI_MGMT_RX_REO_PARAM_MGMT_PKT_CTR_VALID_GET( 12895 reo_params_tlv->mgmt_pkt_ctr_link_info); 12896 reo_params->global_timestamp = reo_params_tlv->global_timestamp; 12897 reo_params->mgmt_pkt_ctr = WMI_MGMT_RX_REO_PARAM_MGMT_PKT_CTR_GET( 12898 reo_params_tlv->mgmt_pkt_ctr_link_info); 12899 reo_params->duration_us = reo_params_tlv->rx_ppdu_duration_us; 12900 reo_params->start_timestamp = reo_params->global_timestamp; 12901 reo_params->end_timestamp = reo_params->start_timestamp + 12902 reo_params->duration_us; 12903 12904 return QDF_STATUS_SUCCESS; 12905 } 12906 12907 /** 12908 * send_mgmt_rx_reo_filter_config_cmd_tlv() - Send MGMT Rx REO filter 12909 * configuration command 12910 * @wmi_handle: wmi handle 12911 * @pdev_id: pdev ID of the radio 12912 * @filter: Pointer to MGMT Rx REO filter 12913 * 12914 * Return: QDF_STATUS_SUCCESS for success or error code 12915 */ 12916 static QDF_STATUS send_mgmt_rx_reo_filter_config_cmd_tlv( 12917 wmi_unified_t wmi_handle, 12918 uint8_t pdev_id, 12919 struct mgmt_rx_reo_filter *filter) 12920 { 12921 QDF_STATUS ret; 12922 wmi_buf_t buf; 12923 wmi_mgmt_rx_reo_filter_configuration_cmd_fixed_param *cmd; 12924 size_t len = sizeof(*cmd); 12925 12926 if (!filter) { 12927 wmi_err("mgmt_rx_reo_filter is NULL"); 12928 return QDF_STATUS_E_INVAL; 12929 } 12930 12931 buf = wmi_buf_alloc(wmi_handle, len); 12932 if (!buf) { 12933 wmi_err("wmi_buf_alloc failed"); 12934 return QDF_STATUS_E_NOMEM; 12935 } 12936 12937 cmd = (wmi_mgmt_rx_reo_filter_configuration_cmd_fixed_param *) 12938 wmi_buf_data(buf); 12939 12940 WMITLV_SET_HDR(&cmd->tlv_header, 12941 WMITLV_TAG_STRUC_wmi_mgmt_rx_reo_filter_configuration_cmd_fixed_param, 12942 WMITLV_GET_STRUCT_TLVLEN(wmi_mgmt_rx_reo_filter_configuration_cmd_fixed_param)); 12943 12944 cmd->pdev_id = wmi_handle->ops->convert_host_pdev_id_to_target( 12945 wmi_handle, 12946 pdev_id); 12947 cmd->filter_low = filter->low; 12948 cmd->filter_high = filter->high; 12949 12950 wmi_mtrace(WMI_MGMT_RX_REO_FILTER_CONFIGURATION_CMDID, NO_SESSION, 0); 12951 ret = wmi_unified_cmd_send( 12952 wmi_handle, buf, len, 12953 WMI_MGMT_RX_REO_FILTER_CONFIGURATION_CMDID); 12954 12955 if (QDF_IS_STATUS_ERROR(ret)) { 12956 wmi_err("Failed to send WMI command"); 12957 wmi_buf_free(buf); 12958 } 12959 12960 return ret; 12961 } 12962 #endif 12963 12964 /** 12965 * extract_frame_pn_params_tlv() - extract PN params from event 12966 * @wmi_handle: wmi handle 12967 * @evt_buf: pointer to event buffer 12968 * @pn_params: Pointer to Frame PN params 12969 * 12970 * Return: QDF_STATUS_SUCCESS for success or error code 12971 */ 12972 static QDF_STATUS extract_frame_pn_params_tlv(wmi_unified_t wmi_handle, 12973 void *evt_buf, 12974 struct frame_pn_params *pn_params) 12975 { 12976 WMI_MGMT_RX_EVENTID_param_tlvs *param_tlvs; 12977 wmi_frame_pn_params *pn_params_tlv; 12978 12979 if (!is_service_enabled_tlv(wmi_handle, 12980 WMI_SERVICE_PN_REPLAY_CHECK_SUPPORT)) 12981 return QDF_STATUS_SUCCESS; 12982 12983 param_tlvs = evt_buf; 12984 if (!param_tlvs) { 12985 wmi_err("Got NULL point message from FW"); 12986 return QDF_STATUS_E_INVAL; 12987 } 12988 12989 if (!pn_params) { 12990 wmi_err("PN Params is NULL"); 12991 return QDF_STATUS_E_INVAL; 12992 } 12993 12994 /* PN Params TLV will be populated only if WMI_RXERR_PN error is 12995 * found by target 12996 */ 12997 pn_params_tlv = param_tlvs->pn_params; 12998 if (!pn_params_tlv) 12999 return QDF_STATUS_SUCCESS; 13000 13001 qdf_mem_copy(pn_params->curr_pn, pn_params_tlv->cur_pn, 13002 sizeof(pn_params->curr_pn)); 13003 qdf_mem_copy(pn_params->prev_pn, pn_params_tlv->prev_pn, 13004 sizeof(pn_params->prev_pn)); 13005 13006 return QDF_STATUS_SUCCESS; 13007 } 13008 13009 /** 13010 * extract_is_conn_ap_param_tlv() - extract is_conn_ap_frame param from event 13011 * @wmi_handle: wmi handle 13012 * @evt_buf: pointer to event buffer 13013 * @is_conn_ap: Pointer for is_conn_ap frame 13014 * 13015 * Return: QDF_STATUS_SUCCESS for success or error code 13016 */ 13017 static QDF_STATUS extract_is_conn_ap_frm_param_tlv( 13018 wmi_unified_t wmi_handle, 13019 void *evt_buf, 13020 struct frm_conn_ap *is_conn_ap) 13021 { 13022 WMI_MGMT_RX_EVENTID_param_tlvs *param_tlvs; 13023 wmi_is_my_mgmt_frame *my_frame_tlv; 13024 13025 param_tlvs = evt_buf; 13026 if (!param_tlvs) { 13027 wmi_err("Got NULL point message from FW"); 13028 return QDF_STATUS_E_INVAL; 13029 } 13030 13031 if (!is_conn_ap) { 13032 wmi_err(" is connected ap param is NULL"); 13033 return QDF_STATUS_E_INVAL; 13034 } 13035 13036 my_frame_tlv = param_tlvs->my_frame; 13037 if (!my_frame_tlv) 13038 return QDF_STATUS_SUCCESS; 13039 13040 is_conn_ap->mgmt_frm_sub_type = my_frame_tlv->mgmt_frm_sub_type; 13041 is_conn_ap->is_conn_ap_frm = my_frame_tlv->is_my_frame; 13042 13043 return QDF_STATUS_SUCCESS; 13044 } 13045 13046 /** 13047 * extract_vdev_roam_param_tlv() - extract vdev roam param from event 13048 * @wmi_handle: wmi handle 13049 * @param evt_buf: pointer to event buffer 13050 * @param param: Pointer to hold roam param 13051 * 13052 * Return: QDF_STATUS_SUCCESS for success or error code 13053 */ 13054 static QDF_STATUS extract_vdev_roam_param_tlv(wmi_unified_t wmi_handle, 13055 void *evt_buf, wmi_host_roam_event *param) 13056 { 13057 WMI_ROAM_EVENTID_param_tlvs *param_buf; 13058 wmi_roam_event_fixed_param *evt; 13059 13060 param_buf = (WMI_ROAM_EVENTID_param_tlvs *) evt_buf; 13061 if (!param_buf) { 13062 wmi_err("Invalid roam event buffer"); 13063 return QDF_STATUS_E_INVAL; 13064 } 13065 13066 evt = param_buf->fixed_param; 13067 qdf_mem_zero(param, sizeof(*param)); 13068 13069 param->vdev_id = evt->vdev_id; 13070 param->reason = evt->reason; 13071 param->rssi = evt->rssi; 13072 13073 return QDF_STATUS_SUCCESS; 13074 } 13075 13076 /** 13077 * extract_vdev_scan_ev_param_tlv() - extract vdev scan param from event 13078 * @wmi_handle: wmi handle 13079 * @param evt_buf: pointer to event buffer 13080 * @param param: Pointer to hold vdev scan param 13081 * 13082 * Return: QDF_STATUS_SUCCESS for success or error code 13083 */ 13084 static QDF_STATUS extract_vdev_scan_ev_param_tlv(wmi_unified_t wmi_handle, 13085 void *evt_buf, struct scan_event *param) 13086 { 13087 WMI_SCAN_EVENTID_param_tlvs *param_buf = NULL; 13088 wmi_scan_event_fixed_param *evt = NULL; 13089 13090 param_buf = (WMI_SCAN_EVENTID_param_tlvs *) evt_buf; 13091 evt = param_buf->fixed_param; 13092 13093 qdf_mem_zero(param, sizeof(*param)); 13094 13095 switch (evt->event) { 13096 case WMI_SCAN_EVENT_STARTED: 13097 param->type = SCAN_EVENT_TYPE_STARTED; 13098 break; 13099 case WMI_SCAN_EVENT_COMPLETED: 13100 param->type = SCAN_EVENT_TYPE_COMPLETED; 13101 break; 13102 case WMI_SCAN_EVENT_BSS_CHANNEL: 13103 param->type = SCAN_EVENT_TYPE_BSS_CHANNEL; 13104 break; 13105 case WMI_SCAN_EVENT_FOREIGN_CHANNEL: 13106 param->type = SCAN_EVENT_TYPE_FOREIGN_CHANNEL; 13107 break; 13108 case WMI_SCAN_EVENT_DEQUEUED: 13109 param->type = SCAN_EVENT_TYPE_DEQUEUED; 13110 break; 13111 case WMI_SCAN_EVENT_PREEMPTED: 13112 param->type = SCAN_EVENT_TYPE_PREEMPTED; 13113 break; 13114 case WMI_SCAN_EVENT_START_FAILED: 13115 param->type = SCAN_EVENT_TYPE_START_FAILED; 13116 break; 13117 case WMI_SCAN_EVENT_RESTARTED: 13118 param->type = SCAN_EVENT_TYPE_RESTARTED; 13119 break; 13120 case WMI_SCAN_EVENT_FOREIGN_CHANNEL_EXIT: 13121 param->type = SCAN_EVENT_TYPE_FOREIGN_CHANNEL_EXIT; 13122 break; 13123 case WMI_SCAN_EVENT_MAX: 13124 default: 13125 param->type = SCAN_EVENT_TYPE_MAX; 13126 break; 13127 }; 13128 13129 switch (evt->reason) { 13130 case WMI_SCAN_REASON_NONE: 13131 param->reason = SCAN_REASON_NONE; 13132 break; 13133 case WMI_SCAN_REASON_COMPLETED: 13134 param->reason = SCAN_REASON_COMPLETED; 13135 break; 13136 case WMI_SCAN_REASON_CANCELLED: 13137 param->reason = SCAN_REASON_CANCELLED; 13138 break; 13139 case WMI_SCAN_REASON_PREEMPTED: 13140 param->reason = SCAN_REASON_PREEMPTED; 13141 break; 13142 case WMI_SCAN_REASON_TIMEDOUT: 13143 param->reason = SCAN_REASON_TIMEDOUT; 13144 break; 13145 case WMI_SCAN_REASON_INTERNAL_FAILURE: 13146 param->reason = SCAN_REASON_INTERNAL_FAILURE; 13147 break; 13148 case WMI_SCAN_REASON_SUSPENDED: 13149 param->reason = SCAN_REASON_SUSPENDED; 13150 break; 13151 case WMI_SCAN_REASON_DFS_VIOLATION: 13152 param->reason = SCAN_REASON_DFS_VIOLATION; 13153 break; 13154 case WMI_SCAN_REASON_MAX: 13155 param->reason = SCAN_REASON_MAX; 13156 break; 13157 default: 13158 param->reason = SCAN_REASON_MAX; 13159 break; 13160 }; 13161 13162 param->chan_freq = evt->channel_freq; 13163 param->requester = evt->requestor; 13164 param->scan_id = evt->scan_id; 13165 param->vdev_id = evt->vdev_id; 13166 param->timestamp = evt->tsf_timestamp; 13167 13168 return QDF_STATUS_SUCCESS; 13169 } 13170 13171 #ifdef FEATURE_WLAN_SCAN_PNO 13172 /** 13173 * extract_nlo_match_ev_param_tlv() - extract NLO match param from event 13174 * @wmi_handle: pointer to WMI handle 13175 * @evt_buf: pointer to WMI event buffer 13176 * @param: pointer to scan event param for NLO match 13177 * 13178 * Return: QDF_STATUS_SUCCESS for success or error code 13179 */ 13180 static QDF_STATUS extract_nlo_match_ev_param_tlv(wmi_unified_t wmi_handle, 13181 void *evt_buf, 13182 struct scan_event *param) 13183 { 13184 WMI_NLO_MATCH_EVENTID_param_tlvs *param_buf = evt_buf; 13185 wmi_nlo_event *evt = param_buf->fixed_param; 13186 13187 qdf_mem_zero(param, sizeof(*param)); 13188 13189 param->type = SCAN_EVENT_TYPE_NLO_MATCH; 13190 param->vdev_id = evt->vdev_id; 13191 13192 return QDF_STATUS_SUCCESS; 13193 } 13194 13195 /** 13196 * extract_nlo_complete_ev_param_tlv() - extract NLO complete param from event 13197 * @wmi_handle: pointer to WMI handle 13198 * @evt_buf: pointer to WMI event buffer 13199 * @param: pointer to scan event param for NLO complete 13200 * 13201 * Return: QDF_STATUS_SUCCESS for success or error code 13202 */ 13203 static QDF_STATUS extract_nlo_complete_ev_param_tlv(wmi_unified_t wmi_handle, 13204 void *evt_buf, 13205 struct scan_event *param) 13206 { 13207 WMI_NLO_SCAN_COMPLETE_EVENTID_param_tlvs *param_buf = evt_buf; 13208 wmi_nlo_event *evt = param_buf->fixed_param; 13209 13210 qdf_mem_zero(param, sizeof(*param)); 13211 13212 param->type = SCAN_EVENT_TYPE_NLO_COMPLETE; 13213 param->vdev_id = evt->vdev_id; 13214 13215 return QDF_STATUS_SUCCESS; 13216 } 13217 #endif 13218 13219 /** 13220 * extract_unit_test_tlv() - extract unit test data 13221 * @wmi_handle: wmi handle 13222 * @param evt_buf: pointer to event buffer 13223 * @param unit_test: pointer to hold unit test data 13224 * @param maxspace: Amount of space in evt_buf 13225 * 13226 * Return: QDF_STATUS_SUCCESS for success or error code 13227 */ 13228 static QDF_STATUS extract_unit_test_tlv(wmi_unified_t wmi_handle, 13229 void *evt_buf, wmi_unit_test_event *unit_test, uint32_t maxspace) 13230 { 13231 WMI_UNIT_TEST_EVENTID_param_tlvs *param_buf; 13232 wmi_unit_test_event_fixed_param *ev_param; 13233 uint32_t num_bufp; 13234 uint32_t copy_size; 13235 uint8_t *bufp; 13236 13237 param_buf = (WMI_UNIT_TEST_EVENTID_param_tlvs *) evt_buf; 13238 ev_param = param_buf->fixed_param; 13239 bufp = param_buf->bufp; 13240 num_bufp = param_buf->num_bufp; 13241 unit_test->vdev_id = ev_param->vdev_id; 13242 unit_test->module_id = ev_param->module_id; 13243 unit_test->diag_token = ev_param->diag_token; 13244 unit_test->flag = ev_param->flag; 13245 unit_test->payload_len = ev_param->payload_len; 13246 wmi_debug("vdev_id:%d mod_id:%d diag_token:%d flag:%d", 13247 ev_param->vdev_id, 13248 ev_param->module_id, 13249 ev_param->diag_token, 13250 ev_param->flag); 13251 wmi_debug("Unit-test data given below %d", num_bufp); 13252 qdf_trace_hex_dump(QDF_MODULE_ID_WMI, QDF_TRACE_LEVEL_DEBUG, 13253 bufp, num_bufp); 13254 copy_size = (num_bufp < maxspace) ? num_bufp : maxspace; 13255 qdf_mem_copy(unit_test->buffer, bufp, copy_size); 13256 unit_test->buffer_len = copy_size; 13257 13258 return QDF_STATUS_SUCCESS; 13259 } 13260 13261 /** 13262 * extract_pdev_ext_stats_tlv() - extract extended pdev stats from event 13263 * @wmi_handle: wmi handle 13264 * @param evt_buf: pointer to event buffer 13265 * @param index: Index into extended pdev stats 13266 * @param pdev_ext_stats: Pointer to hold extended pdev stats 13267 * 13268 * Return: QDF_STATUS_SUCCESS for success or error code 13269 */ 13270 static QDF_STATUS extract_pdev_ext_stats_tlv(wmi_unified_t wmi_handle, 13271 void *evt_buf, uint32_t index, wmi_host_pdev_ext_stats *pdev_ext_stats) 13272 { 13273 WMI_UPDATE_STATS_EVENTID_param_tlvs *param_buf; 13274 wmi_pdev_extd_stats *ev; 13275 13276 param_buf = evt_buf; 13277 if (!param_buf) 13278 return QDF_STATUS_E_FAILURE; 13279 13280 if (!param_buf->pdev_extd_stats) 13281 return QDF_STATUS_E_FAILURE; 13282 13283 ev = param_buf->pdev_extd_stats + index; 13284 13285 pdev_ext_stats->pdev_id = 13286 wmi_handle->ops->convert_target_pdev_id_to_host( 13287 wmi_handle, 13288 ev->pdev_id); 13289 pdev_ext_stats->my_rx_count = ev->my_rx_count; 13290 pdev_ext_stats->rx_matched_11ax_msdu_cnt = ev->rx_matched_11ax_msdu_cnt; 13291 pdev_ext_stats->rx_other_11ax_msdu_cnt = ev->rx_other_11ax_msdu_cnt; 13292 13293 return QDF_STATUS_SUCCESS; 13294 } 13295 13296 /** 13297 * extract_bcn_stats_tlv() - extract bcn stats from event 13298 * @wmi_handle: wmi handle 13299 * @param evt_buf: pointer to event buffer 13300 * @param index: Index into vdev stats 13301 * @param bcn_stats: Pointer to hold bcn stats 13302 * 13303 * Return: QDF_STATUS_SUCCESS for success or error code 13304 */ 13305 static QDF_STATUS extract_bcn_stats_tlv(wmi_unified_t wmi_handle, 13306 void *evt_buf, uint32_t index, wmi_host_bcn_stats *bcn_stats) 13307 { 13308 WMI_UPDATE_STATS_EVENTID_param_tlvs *param_buf; 13309 wmi_stats_event_fixed_param *ev_param; 13310 uint8_t *data; 13311 13312 param_buf = (WMI_UPDATE_STATS_EVENTID_param_tlvs *) evt_buf; 13313 ev_param = (wmi_stats_event_fixed_param *) param_buf->fixed_param; 13314 data = (uint8_t *) param_buf->data; 13315 13316 if (index < ev_param->num_bcn_stats) { 13317 wmi_bcn_stats *ev = (wmi_bcn_stats *) ((data) + 13318 ((ev_param->num_pdev_stats) * sizeof(wmi_pdev_stats)) + 13319 ((ev_param->num_vdev_stats) * sizeof(wmi_vdev_stats)) + 13320 ((ev_param->num_peer_stats) * sizeof(wmi_peer_stats)) + 13321 ((ev_param->num_chan_stats) * sizeof(wmi_chan_stats)) + 13322 ((ev_param->num_mib_stats) * sizeof(wmi_mib_stats)) + 13323 (index * sizeof(wmi_bcn_stats))); 13324 13325 bcn_stats->vdev_id = ev->vdev_id; 13326 bcn_stats->tx_bcn_succ_cnt = ev->tx_bcn_succ_cnt; 13327 bcn_stats->tx_bcn_outage_cnt = ev->tx_bcn_outage_cnt; 13328 } 13329 13330 return QDF_STATUS_SUCCESS; 13331 } 13332 13333 /** 13334 * extract_vdev_prb_fils_stats_tlv() - extract vdev probe and fils 13335 * stats from event 13336 * @wmi_handle: wmi handle 13337 * @param evt_buf: pointer to event buffer 13338 * @param index: Index into vdev stats 13339 * @param vdev_prb_fd_stats: Pointer to hold vdev probe and fils stats 13340 * 13341 * Return: QDF_STATUS_SUCCESS for success or error code 13342 */ 13343 static QDF_STATUS 13344 extract_vdev_prb_fils_stats_tlv(wmi_unified_t wmi_handle, 13345 void *evt_buf, uint32_t index, 13346 struct wmi_host_vdev_prb_fils_stats *vdev_stats) 13347 { 13348 WMI_UPDATE_STATS_EVENTID_param_tlvs *param_buf; 13349 wmi_vdev_extd_stats *ev; 13350 13351 param_buf = (WMI_UPDATE_STATS_EVENTID_param_tlvs *)evt_buf; 13352 13353 if (param_buf->vdev_extd_stats) { 13354 ev = (wmi_vdev_extd_stats *)(param_buf->vdev_extd_stats + 13355 index); 13356 vdev_stats->vdev_id = ev->vdev_id; 13357 vdev_stats->fd_succ_cnt = ev->fd_succ_cnt; 13358 vdev_stats->fd_fail_cnt = ev->fd_fail_cnt; 13359 vdev_stats->unsolicited_prb_succ_cnt = 13360 ev->unsolicited_prb_succ_cnt; 13361 vdev_stats->unsolicited_prb_fail_cnt = 13362 ev->unsolicited_prb_fail_cnt; 13363 wmi_debug("vdev: %d, fd_s: %d, fd_f: %d, prb_s: %d, prb_f: %d", 13364 ev->vdev_id, ev->fd_succ_cnt, ev->fd_fail_cnt, 13365 ev->unsolicited_prb_succ_cnt, 13366 ev->unsolicited_prb_fail_cnt); 13367 } 13368 13369 return QDF_STATUS_SUCCESS; 13370 } 13371 13372 /** 13373 * extract_bcnflt_stats_tlv() - extract bcn fault stats from event 13374 * @wmi_handle: wmi handle 13375 * @param evt_buf: pointer to event buffer 13376 * @param index: Index into bcn fault stats 13377 * @param bcnflt_stats: Pointer to hold bcn fault stats 13378 * 13379 * Return: QDF_STATUS_SUCCESS for success or error code 13380 */ 13381 static QDF_STATUS extract_bcnflt_stats_tlv(wmi_unified_t wmi_handle, 13382 void *evt_buf, uint32_t index, wmi_host_bcnflt_stats *peer_stats) 13383 { 13384 return QDF_STATUS_SUCCESS; 13385 } 13386 13387 /** 13388 * extract_chan_stats_tlv() - extract chan stats from event 13389 * @wmi_handle: wmi handle 13390 * @param evt_buf: pointer to event buffer 13391 * @param index: Index into chan stats 13392 * @param vdev_extd_stats: Pointer to hold chan stats 13393 * 13394 * Return: QDF_STATUS_SUCCESS for success or error code 13395 */ 13396 static QDF_STATUS extract_chan_stats_tlv(wmi_unified_t wmi_handle, 13397 void *evt_buf, uint32_t index, wmi_host_chan_stats *chan_stats) 13398 { 13399 WMI_UPDATE_STATS_EVENTID_param_tlvs *param_buf; 13400 wmi_stats_event_fixed_param *ev_param; 13401 uint8_t *data; 13402 13403 param_buf = (WMI_UPDATE_STATS_EVENTID_param_tlvs *) evt_buf; 13404 ev_param = (wmi_stats_event_fixed_param *) param_buf->fixed_param; 13405 data = (uint8_t *) param_buf->data; 13406 13407 if (index < ev_param->num_chan_stats) { 13408 wmi_chan_stats *ev = (wmi_chan_stats *) ((data) + 13409 ((ev_param->num_pdev_stats) * sizeof(wmi_pdev_stats)) + 13410 ((ev_param->num_vdev_stats) * sizeof(wmi_vdev_stats)) + 13411 ((ev_param->num_peer_stats) * sizeof(wmi_peer_stats)) + 13412 (index * sizeof(wmi_chan_stats))); 13413 13414 13415 /* Non-TLV doesn't have num_chan_stats */ 13416 chan_stats->chan_mhz = ev->chan_mhz; 13417 chan_stats->sampling_period_us = ev->sampling_period_us; 13418 chan_stats->rx_clear_count = ev->rx_clear_count; 13419 chan_stats->tx_duration_us = ev->tx_duration_us; 13420 chan_stats->rx_duration_us = ev->rx_duration_us; 13421 } 13422 13423 return QDF_STATUS_SUCCESS; 13424 } 13425 13426 /** 13427 * extract_profile_ctx_tlv() - extract profile context from event 13428 * @wmi_handle: wmi handle 13429 * @param evt_buf: pointer to event buffer 13430 * @idx: profile stats index to extract 13431 * @param profile_ctx: Pointer to hold profile context 13432 * 13433 * Return: QDF_STATUS_SUCCESS for success or error code 13434 */ 13435 static QDF_STATUS extract_profile_ctx_tlv(wmi_unified_t wmi_handle, 13436 void *evt_buf, wmi_host_wlan_profile_ctx_t *profile_ctx) 13437 { 13438 WMI_WLAN_PROFILE_DATA_EVENTID_param_tlvs *param_buf; 13439 13440 wmi_wlan_profile_ctx_t *ev; 13441 13442 param_buf = (WMI_WLAN_PROFILE_DATA_EVENTID_param_tlvs *)evt_buf; 13443 if (!param_buf) { 13444 wmi_err("Invalid profile data event buf"); 13445 return QDF_STATUS_E_INVAL; 13446 } 13447 13448 ev = param_buf->profile_ctx; 13449 13450 profile_ctx->tot = ev->tot; 13451 profile_ctx->tx_msdu_cnt = ev->tx_msdu_cnt; 13452 profile_ctx->tx_mpdu_cnt = ev->tx_mpdu_cnt; 13453 profile_ctx->tx_ppdu_cnt = ev->tx_ppdu_cnt; 13454 profile_ctx->rx_msdu_cnt = ev->rx_msdu_cnt; 13455 profile_ctx->rx_mpdu_cnt = ev->rx_mpdu_cnt; 13456 profile_ctx->bin_count = ev->bin_count; 13457 13458 return QDF_STATUS_SUCCESS; 13459 } 13460 13461 /** 13462 * extract_profile_data_tlv() - extract profile data from event 13463 * @wmi_handle: wmi handle 13464 * @param evt_buf: pointer to event buffer 13465 * @param profile_data: Pointer to hold profile data 13466 * 13467 * Return: QDF_STATUS_SUCCESS for success or error code 13468 */ 13469 static QDF_STATUS extract_profile_data_tlv(wmi_unified_t wmi_handle, 13470 void *evt_buf, uint8_t idx, wmi_host_wlan_profile_t *profile_data) 13471 { 13472 WMI_WLAN_PROFILE_DATA_EVENTID_param_tlvs *param_buf; 13473 wmi_wlan_profile_t *ev; 13474 13475 param_buf = (WMI_WLAN_PROFILE_DATA_EVENTID_param_tlvs *)evt_buf; 13476 if (!param_buf) { 13477 wmi_err("Invalid profile data event buf"); 13478 return QDF_STATUS_E_INVAL; 13479 } 13480 13481 ev = ¶m_buf->profile_data[idx]; 13482 profile_data->id = ev->id; 13483 profile_data->cnt = ev->cnt; 13484 profile_data->tot = ev->tot; 13485 profile_data->min = ev->min; 13486 profile_data->max = ev->max; 13487 profile_data->hist_intvl = ev->hist_intvl; 13488 qdf_mem_copy(profile_data->hist, ev->hist, sizeof(profile_data->hist)); 13489 13490 return QDF_STATUS_SUCCESS; 13491 } 13492 13493 /** 13494 * extract_pdev_utf_event_tlv() - extract UTF data info from event 13495 * @wmi_handle: WMI handle 13496 * @param evt_buf: Pointer to event buffer 13497 * @param param: Pointer to hold data 13498 * 13499 * Return : QDF_STATUS_SUCCESS for success or error code 13500 */ 13501 static QDF_STATUS extract_pdev_utf_event_tlv(wmi_unified_t wmi_handle, 13502 uint8_t *evt_buf, 13503 struct wmi_host_pdev_utf_event *event) 13504 { 13505 WMI_PDEV_UTF_EVENTID_param_tlvs *param_buf; 13506 struct wmi_host_utf_seg_header_info *seg_hdr; 13507 13508 param_buf = (WMI_PDEV_UTF_EVENTID_param_tlvs *)evt_buf; 13509 event->data = param_buf->data; 13510 event->datalen = param_buf->num_data; 13511 13512 if (event->datalen < sizeof(struct wmi_host_utf_seg_header_info)) { 13513 wmi_err("Invalid datalen: %d", event->datalen); 13514 return QDF_STATUS_E_INVAL; 13515 } 13516 seg_hdr = (struct wmi_host_utf_seg_header_info *)param_buf->data; 13517 /* Set pdev_id=1 until FW adds support to include pdev_id */ 13518 event->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 13519 wmi_handle, 13520 seg_hdr->pdev_id); 13521 13522 return QDF_STATUS_SUCCESS; 13523 } 13524 13525 #ifdef WLAN_SUPPORT_RF_CHARACTERIZATION 13526 static QDF_STATUS extract_num_rf_characterization_entries_tlv(wmi_unified_t wmi_handle, 13527 uint8_t *event, 13528 uint32_t *num_rf_characterization_entries) 13529 { 13530 WMI_CHAN_RF_CHARACTERIZATION_INFO_EVENTID_param_tlvs *param_buf; 13531 13532 param_buf = (WMI_CHAN_RF_CHARACTERIZATION_INFO_EVENTID_param_tlvs *)event; 13533 if (!param_buf) 13534 return QDF_STATUS_E_INVAL; 13535 13536 *num_rf_characterization_entries = 13537 param_buf->num_wmi_chan_rf_characterization_info; 13538 13539 return QDF_STATUS_SUCCESS; 13540 } 13541 13542 static QDF_STATUS extract_rf_characterization_entries_tlv(wmi_unified_t wmi_handle, 13543 uint8_t *event, 13544 uint32_t num_rf_characterization_entries, 13545 struct wmi_host_rf_characterization_event_param *rf_characterization_entries) 13546 { 13547 WMI_CHAN_RF_CHARACTERIZATION_INFO_EVENTID_param_tlvs *param_buf; 13548 WMI_CHAN_RF_CHARACTERIZATION_INFO *wmi_rf_characterization_entry; 13549 uint8_t ix; 13550 13551 param_buf = (WMI_CHAN_RF_CHARACTERIZATION_INFO_EVENTID_param_tlvs *)event; 13552 if (!param_buf) 13553 return QDF_STATUS_E_INVAL; 13554 13555 wmi_rf_characterization_entry = 13556 param_buf->wmi_chan_rf_characterization_info; 13557 if (!wmi_rf_characterization_entry) 13558 return QDF_STATUS_E_INVAL; 13559 13560 /* 13561 * Using num_wmi_chan_rf_characterization instead of param_buf value 13562 * since memory for rf_characterization_entries was allocated using 13563 * the former. 13564 */ 13565 for (ix = 0; ix < num_rf_characterization_entries; ix++) { 13566 rf_characterization_entries[ix].freq = 13567 WMI_CHAN_RF_CHARACTERIZATION_FREQ_GET( 13568 &wmi_rf_characterization_entry[ix]); 13569 13570 rf_characterization_entries[ix].bw = 13571 WMI_CHAN_RF_CHARACTERIZATION_BW_GET( 13572 &wmi_rf_characterization_entry[ix]); 13573 13574 rf_characterization_entries[ix].chan_metric = 13575 WMI_CHAN_RF_CHARACTERIZATION_CHAN_METRIC_GET( 13576 &wmi_rf_characterization_entry[ix]); 13577 13578 wmi_nofl_debug("rf_characterization_entries[%u]: freq: %u, " 13579 "bw: %u, chan_metric: %u", 13580 ix, rf_characterization_entries[ix].freq, 13581 rf_characterization_entries[ix].bw, 13582 rf_characterization_entries[ix].chan_metric); 13583 } 13584 13585 return QDF_STATUS_SUCCESS; 13586 } 13587 #endif 13588 13589 #ifdef WLAN_FEATURE_11BE 13590 static void 13591 extract_11be_chainmask(struct wlan_psoc_host_chainmask_capabilities *cap, 13592 WMI_MAC_PHY_CHAINMASK_CAPABILITY *chainmask_caps) 13593 { 13594 cap->supports_chan_width_320 = 13595 WMI_SUPPORT_CHAN_WIDTH_320_GET(chainmask_caps->supported_flags); 13596 } 13597 #else 13598 static void 13599 extract_11be_chainmask(struct wlan_psoc_host_chainmask_capabilities *cap, 13600 WMI_MAC_PHY_CHAINMASK_CAPABILITY *chainmask_caps) 13601 { 13602 } 13603 #endif /* WLAN_FEATURE_11BE */ 13604 13605 /** 13606 * extract_chainmask_tables_tlv() - extract chain mask tables from event 13607 * @wmi_handle: wmi handle 13608 * @param evt_buf: pointer to event buffer 13609 * @param param: Pointer to hold evt buf 13610 * 13611 * Return: QDF_STATUS_SUCCESS for success or error code 13612 */ 13613 static QDF_STATUS extract_chainmask_tables_tlv(wmi_unified_t wmi_handle, 13614 uint8_t *event, struct wlan_psoc_host_chainmask_table *chainmask_table) 13615 { 13616 WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *param_buf; 13617 WMI_MAC_PHY_CHAINMASK_CAPABILITY *chainmask_caps; 13618 WMI_SOC_MAC_PHY_HW_MODE_CAPS *hw_caps; 13619 uint8_t i = 0, j = 0; 13620 uint32_t num_mac_phy_chainmask_caps = 0; 13621 13622 param_buf = (WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *) event; 13623 if (!param_buf) 13624 return QDF_STATUS_E_INVAL; 13625 13626 hw_caps = param_buf->soc_hw_mode_caps; 13627 if (!hw_caps) 13628 return QDF_STATUS_E_INVAL; 13629 13630 if ((!hw_caps->num_chainmask_tables) || 13631 (hw_caps->num_chainmask_tables > PSOC_MAX_CHAINMASK_TABLES) || 13632 (hw_caps->num_chainmask_tables > 13633 param_buf->num_mac_phy_chainmask_combo)) 13634 return QDF_STATUS_E_INVAL; 13635 13636 chainmask_caps = param_buf->mac_phy_chainmask_caps; 13637 13638 if (!chainmask_caps) 13639 return QDF_STATUS_E_INVAL; 13640 13641 for (i = 0; i < hw_caps->num_chainmask_tables; i++) { 13642 if (chainmask_table[i].num_valid_chainmasks > 13643 (UINT_MAX - num_mac_phy_chainmask_caps)) { 13644 wmi_err_rl("integer overflow, num_mac_phy_chainmask_caps:%d, i:%d, um_valid_chainmasks:%d", 13645 num_mac_phy_chainmask_caps, i, 13646 chainmask_table[i].num_valid_chainmasks); 13647 return QDF_STATUS_E_INVAL; 13648 } 13649 num_mac_phy_chainmask_caps += 13650 chainmask_table[i].num_valid_chainmasks; 13651 } 13652 13653 if (num_mac_phy_chainmask_caps > 13654 param_buf->num_mac_phy_chainmask_caps) { 13655 wmi_err_rl("invalid chainmask caps num, num_mac_phy_chainmask_caps:%d, param_buf->num_mac_phy_chainmask_caps:%d", 13656 num_mac_phy_chainmask_caps, 13657 param_buf->num_mac_phy_chainmask_caps); 13658 return QDF_STATUS_E_INVAL; 13659 } 13660 13661 for (i = 0; i < hw_caps->num_chainmask_tables; i++) { 13662 13663 wmi_nofl_debug("Dumping chain mask combo data for table : %d", 13664 i); 13665 for (j = 0; j < chainmask_table[i].num_valid_chainmasks; j++) { 13666 13667 chainmask_table[i].cap_list[j].chainmask = 13668 chainmask_caps->chainmask; 13669 13670 chainmask_table[i].cap_list[j].supports_chan_width_20 = 13671 WMI_SUPPORT_CHAN_WIDTH_20_GET(chainmask_caps->supported_flags); 13672 13673 chainmask_table[i].cap_list[j].supports_chan_width_40 = 13674 WMI_SUPPORT_CHAN_WIDTH_40_GET(chainmask_caps->supported_flags); 13675 13676 chainmask_table[i].cap_list[j].supports_chan_width_80 = 13677 WMI_SUPPORT_CHAN_WIDTH_80_GET(chainmask_caps->supported_flags); 13678 13679 chainmask_table[i].cap_list[j].supports_chan_width_160 = 13680 WMI_SUPPORT_CHAN_WIDTH_160_GET(chainmask_caps->supported_flags); 13681 13682 chainmask_table[i].cap_list[j].supports_chan_width_80P80 = 13683 WMI_SUPPORT_CHAN_WIDTH_80P80_GET(chainmask_caps->supported_flags); 13684 13685 chainmask_table[i].cap_list[j].chain_mask_2G = 13686 WMI_SUPPORT_CHAIN_MASK_2G_GET(chainmask_caps->supported_flags); 13687 13688 chainmask_table[i].cap_list[j].chain_mask_5G = 13689 WMI_SUPPORT_CHAIN_MASK_5G_GET(chainmask_caps->supported_flags); 13690 13691 chainmask_table[i].cap_list[j].chain_mask_tx = 13692 WMI_SUPPORT_CHAIN_MASK_TX_GET(chainmask_caps->supported_flags); 13693 13694 chainmask_table[i].cap_list[j].chain_mask_rx = 13695 WMI_SUPPORT_CHAIN_MASK_RX_GET(chainmask_caps->supported_flags); 13696 13697 chainmask_table[i].cap_list[j].supports_aDFS = 13698 WMI_SUPPORT_CHAIN_MASK_ADFS_GET(chainmask_caps->supported_flags); 13699 13700 chainmask_table[i].cap_list[j].supports_aSpectral = 13701 WMI_SUPPORT_AGILE_SPECTRAL_GET(chainmask_caps->supported_flags); 13702 13703 chainmask_table[i].cap_list[j].supports_aSpectral_160 = 13704 WMI_SUPPORT_AGILE_SPECTRAL_160_GET(chainmask_caps->supported_flags); 13705 13706 chainmask_table[i].cap_list[j].supports_aDFS_160 = 13707 WMI_SUPPORT_ADFS_160_GET(chainmask_caps->supported_flags); 13708 13709 extract_11be_chainmask(&chainmask_table[i].cap_list[j], 13710 chainmask_caps); 13711 13712 wmi_nofl_debug("supported_flags: 0x%08x chainmasks: 0x%08x", 13713 chainmask_caps->supported_flags, 13714 chainmask_caps->chainmask); 13715 chainmask_caps++; 13716 } 13717 } 13718 13719 return QDF_STATUS_SUCCESS; 13720 } 13721 13722 /** 13723 * extract_service_ready_ext_tlv() - extract basic extended service ready params 13724 * from event 13725 * @wmi_handle: wmi handle 13726 * @param evt_buf: pointer to event buffer 13727 * @param param: Pointer to hold evt buf 13728 * 13729 * Return: QDF_STATUS_SUCCESS for success or error code 13730 */ 13731 static QDF_STATUS extract_service_ready_ext_tlv(wmi_unified_t wmi_handle, 13732 uint8_t *event, struct wlan_psoc_host_service_ext_param *param) 13733 { 13734 WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *param_buf; 13735 wmi_service_ready_ext_event_fixed_param *ev; 13736 WMI_SOC_MAC_PHY_HW_MODE_CAPS *hw_caps; 13737 WMI_SOC_HAL_REG_CAPABILITIES *reg_caps; 13738 WMI_MAC_PHY_CHAINMASK_COMBO *chain_mask_combo; 13739 uint8_t i = 0; 13740 13741 param_buf = (WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *) event; 13742 if (!param_buf) 13743 return QDF_STATUS_E_INVAL; 13744 13745 ev = param_buf->fixed_param; 13746 if (!ev) 13747 return QDF_STATUS_E_INVAL; 13748 13749 /* Move this to host based bitmap */ 13750 param->default_conc_scan_config_bits = 13751 ev->default_conc_scan_config_bits; 13752 param->default_fw_config_bits = ev->default_fw_config_bits; 13753 param->he_cap_info = ev->he_cap_info; 13754 param->mpdu_density = ev->mpdu_density; 13755 param->max_bssid_rx_filters = ev->max_bssid_rx_filters; 13756 param->fw_build_vers_ext = ev->fw_build_vers_ext; 13757 param->num_dbr_ring_caps = param_buf->num_dma_ring_caps; 13758 param->num_bin_scaling_params = param_buf->num_wmi_bin_scaling_params; 13759 param->max_bssid_indicator = ev->max_bssid_indicator; 13760 qdf_mem_copy(¶m->ppet, &ev->ppet, sizeof(param->ppet)); 13761 13762 hw_caps = param_buf->soc_hw_mode_caps; 13763 if (hw_caps) 13764 param->num_hw_modes = hw_caps->num_hw_modes; 13765 else 13766 param->num_hw_modes = 0; 13767 13768 reg_caps = param_buf->soc_hal_reg_caps; 13769 if (reg_caps) 13770 param->num_phy = reg_caps->num_phy; 13771 else 13772 param->num_phy = 0; 13773 13774 if (hw_caps) { 13775 param->num_chainmask_tables = hw_caps->num_chainmask_tables; 13776 wmi_nofl_debug("Num chain mask tables: %d", 13777 hw_caps->num_chainmask_tables); 13778 } else 13779 param->num_chainmask_tables = 0; 13780 13781 if (param->num_chainmask_tables > PSOC_MAX_CHAINMASK_TABLES || 13782 param->num_chainmask_tables > 13783 param_buf->num_mac_phy_chainmask_combo) { 13784 wmi_err_rl("num_chainmask_tables is OOB: %u", 13785 param->num_chainmask_tables); 13786 return QDF_STATUS_E_INVAL; 13787 } 13788 chain_mask_combo = param_buf->mac_phy_chainmask_combo; 13789 13790 if (!chain_mask_combo) 13791 return QDF_STATUS_SUCCESS; 13792 13793 wmi_nofl_debug("Dumping chain mask combo data"); 13794 13795 for (i = 0; i < param->num_chainmask_tables; i++) { 13796 13797 wmi_nofl_debug("table_id : %d Num valid chainmasks: %d", 13798 chain_mask_combo->chainmask_table_id, 13799 chain_mask_combo->num_valid_chainmask); 13800 13801 param->chainmask_table[i].table_id = 13802 chain_mask_combo->chainmask_table_id; 13803 param->chainmask_table[i].num_valid_chainmasks = 13804 chain_mask_combo->num_valid_chainmask; 13805 chain_mask_combo++; 13806 } 13807 wmi_nofl_debug("chain mask combo end"); 13808 13809 return QDF_STATUS_SUCCESS; 13810 } 13811 13812 #if defined(CONFIG_AFC_SUPPORT) 13813 /** 13814 * extract_svc_rdy_ext2_afc_tlv() - extract service ready ext2 afc deployment 13815 * type from event 13816 * @ev: pointer to event fixed param 13817 * @param: Pointer to hold the params 13818 * 13819 * Return: void 13820 */ 13821 static void 13822 extract_svc_rdy_ext2_afc_tlv(wmi_service_ready_ext2_event_fixed_param *ev, 13823 struct wlan_psoc_host_service_ext2_param *param) 13824 { 13825 WMI_AFC_FEATURE_6G_DEPLOYMENT_TYPE tgt_afc_dev_type; 13826 enum reg_afc_dev_deploy_type reg_afc_dev_type; 13827 13828 tgt_afc_dev_type = ev->afc_deployment_type; 13829 switch (tgt_afc_dev_type) { 13830 case WMI_AFC_FEATURE_6G_DEPLOYMENT_UNSPECIFIED: 13831 reg_afc_dev_type = AFC_DEPLOYMENT_INDOOR; 13832 break; 13833 case WMI_AFC_FEATURE_6G_DEPLOYMENT_INDOOR_ONLY: 13834 reg_afc_dev_type = AFC_DEPLOYMENT_INDOOR; 13835 break; 13836 case WMI_AFC_FEATURE_6G_DEPLOYMENT_OUTDOOR_ONLY: 13837 reg_afc_dev_type = AFC_DEPLOYMENT_OUTDOOR; 13838 break; 13839 default: 13840 wmi_err("invalid afc deloyment %d", tgt_afc_dev_type); 13841 reg_afc_dev_type = AFC_DEPLOYMENT_UNKNOWN; 13842 break; 13843 } 13844 param->afc_dev_type = reg_afc_dev_type; 13845 13846 wmi_debug("afc dev type:%d", ev->afc_deployment_type); 13847 } 13848 #else 13849 static inline void 13850 extract_svc_rdy_ext2_afc_tlv(wmi_service_ready_ext2_event_fixed_param *ev, 13851 struct wlan_psoc_host_service_ext2_param *param) 13852 { 13853 } 13854 #endif 13855 13856 /** 13857 * extract_ul_mumimo_support) - extract UL-MUMIMO capability from target cap 13858 * @param: Pointer to hold the params 13859 * 13860 * Return: Void 13861 */ 13862 static void 13863 extract_ul_mumimo_support(struct wlan_psoc_host_service_ext2_param *param) 13864 { 13865 uint32_t tgt_cap = param->target_cap_flags; 13866 13867 param->ul_mumimo_rx_2g = WMI_TARGET_CAP_UL_MU_MIMO_RX_SUPPORT_2GHZ_GET(tgt_cap); 13868 param->ul_mumimo_rx_5g = WMI_TARGET_CAP_UL_MU_MIMO_RX_SUPPORT_5GHZ_GET(tgt_cap); 13869 param->ul_mumimo_rx_6g = WMI_TARGET_CAP_UL_MU_MIMO_RX_SUPPORT_6GHZ_GET(tgt_cap); 13870 param->ul_mumimo_tx_2g = WMI_TARGET_CAP_UL_MU_MIMO_TX_SUPPORT_2GHZ_GET(tgt_cap); 13871 param->ul_mumimo_tx_5g = WMI_TARGET_CAP_UL_MU_MIMO_TX_SUPPORT_5GHZ_GET(tgt_cap); 13872 param->ul_mumimo_tx_6g = WMI_TARGET_CAP_UL_MU_MIMO_TX_SUPPORT_6GHZ_GET(tgt_cap); 13873 } 13874 13875 /** 13876 * extract_service_ready_ext2_tlv() - extract service ready ext2 params from 13877 * event 13878 * @wmi_handle: wmi handle 13879 * @event: pointer to event buffer 13880 * @param: Pointer to hold the params 13881 * 13882 * Return: QDF_STATUS_SUCCESS for success or error code 13883 */ 13884 static QDF_STATUS 13885 extract_service_ready_ext2_tlv(wmi_unified_t wmi_handle, uint8_t *event, 13886 struct wlan_psoc_host_service_ext2_param *param) 13887 { 13888 WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *param_buf; 13889 wmi_service_ready_ext2_event_fixed_param *ev; 13890 13891 param_buf = (WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *)event; 13892 if (!param_buf) 13893 return QDF_STATUS_E_INVAL; 13894 13895 ev = param_buf->fixed_param; 13896 if (!ev) 13897 return QDF_STATUS_E_INVAL; 13898 13899 param->reg_db_version_major = 13900 WMI_REG_DB_VERSION_MAJOR_GET( 13901 ev->reg_db_version); 13902 param->reg_db_version_minor = 13903 WMI_REG_DB_VERSION_MINOR_GET( 13904 ev->reg_db_version); 13905 param->bdf_reg_db_version_major = 13906 WMI_BDF_REG_DB_VERSION_MAJOR_GET( 13907 ev->reg_db_version); 13908 param->bdf_reg_db_version_minor = 13909 WMI_BDF_REG_DB_VERSION_MINOR_GET( 13910 ev->reg_db_version); 13911 param->chwidth_num_peer_caps = ev->chwidth_num_peer_caps; 13912 13913 param->num_dbr_ring_caps = param_buf->num_dma_ring_caps; 13914 13915 if (param_buf->nan_cap) 13916 param->max_ndp_sessions = 13917 param_buf->nan_cap->max_ndp_sessions; 13918 else 13919 param->max_ndp_sessions = 0; 13920 13921 param->preamble_puncture_bw_cap = ev->preamble_puncture_bw; 13922 param->num_scan_radio_caps = param_buf->num_wmi_scan_radio_caps; 13923 param->max_users_dl_ofdma = WMI_MAX_USER_PER_PPDU_DL_OFDMA_GET( 13924 ev->max_user_per_ppdu_ofdma); 13925 param->max_users_ul_ofdma = WMI_MAX_USER_PER_PPDU_UL_OFDMA_GET( 13926 ev->max_user_per_ppdu_ofdma); 13927 param->max_users_dl_mumimo = WMI_MAX_USER_PER_PPDU_DL_MUMIMO_GET( 13928 ev->max_user_per_ppdu_mumimo); 13929 param->max_users_ul_mumimo = WMI_MAX_USER_PER_PPDU_UL_MUMIMO_GET( 13930 ev->max_user_per_ppdu_mumimo); 13931 param->target_cap_flags = ev->target_cap_flags; 13932 extract_ul_mumimo_support(param); 13933 wmi_debug("htt peer data :%d", ev->target_cap_flags); 13934 13935 extract_svc_rdy_ext2_afc_tlv(ev, param); 13936 13937 return QDF_STATUS_SUCCESS; 13938 } 13939 13940 /* 13941 * extract_dbs_or_sbs_cap_service_ready_ext2_tlv() - extract dbs_or_sbs cap from 13942 * service ready ext 2 13943 * 13944 * @wmi_handle: wmi handle 13945 * @event: pointer to event buffer 13946 * @sbs_lower_band_end_freq: If sbs_lower_band_end_freq is set to non-zero, 13947 * it indicates async SBS mode is supported, and 13948 * lower-band/higher band to MAC mapping is 13949 * switch-able. unit: mhz. examples 5180, 5320 13950 * 13951 * Return: QDF_STATUS_SUCCESS on success, QDF_STATUS_E_** on error 13952 */ 13953 static QDF_STATUS extract_dbs_or_sbs_cap_service_ready_ext2_tlv( 13954 wmi_unified_t wmi_handle, uint8_t *event, 13955 uint32_t *sbs_lower_band_end_freq) 13956 { 13957 WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *param_buf; 13958 wmi_dbs_or_sbs_cap_ext *dbs_or_sbs_caps; 13959 13960 param_buf = (WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *)event; 13961 if (!param_buf) 13962 return QDF_STATUS_E_INVAL; 13963 13964 dbs_or_sbs_caps = param_buf->dbs_or_sbs_cap_ext; 13965 if (!dbs_or_sbs_caps) 13966 return QDF_STATUS_E_INVAL; 13967 13968 *sbs_lower_band_end_freq = dbs_or_sbs_caps->sbs_lower_band_end_freq; 13969 13970 return QDF_STATUS_SUCCESS; 13971 } 13972 13973 /** 13974 * extract_sar_cap_service_ready_ext_tlv() - 13975 * extract SAR cap from service ready event 13976 * @wmi_handle: wmi handle 13977 * @event: pointer to event buffer 13978 * @ext_param: extended target info 13979 * 13980 * Return: QDF_STATUS_SUCCESS for success or error code 13981 */ 13982 static QDF_STATUS extract_sar_cap_service_ready_ext_tlv( 13983 wmi_unified_t wmi_handle, 13984 uint8_t *event, 13985 struct wlan_psoc_host_service_ext_param *ext_param) 13986 { 13987 WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *param_buf; 13988 WMI_SAR_CAPABILITIES *sar_caps; 13989 13990 param_buf = (WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *)event; 13991 13992 if (!param_buf) 13993 return QDF_STATUS_E_INVAL; 13994 13995 sar_caps = param_buf->sar_caps; 13996 if (sar_caps) 13997 ext_param->sar_version = sar_caps->active_version; 13998 else 13999 ext_param->sar_version = 0; 14000 14001 return QDF_STATUS_SUCCESS; 14002 } 14003 14004 /** 14005 * extract_hw_mode_cap_service_ready_ext_tlv() - 14006 * extract HW mode cap from service ready event 14007 * @wmi_handle: wmi handle 14008 * @param evt_buf: pointer to event buffer 14009 * @param param: Pointer to hold evt buf 14010 * @param hw_mode_idx: hw mode idx should be less than num_mode 14011 * 14012 * Return: QDF_STATUS_SUCCESS for success or error code 14013 */ 14014 static QDF_STATUS extract_hw_mode_cap_service_ready_ext_tlv( 14015 wmi_unified_t wmi_handle, 14016 uint8_t *event, uint8_t hw_mode_idx, 14017 struct wlan_psoc_host_hw_mode_caps *param) 14018 { 14019 WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *param_buf; 14020 WMI_SOC_MAC_PHY_HW_MODE_CAPS *hw_caps; 14021 14022 param_buf = (WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *) event; 14023 if (!param_buf) 14024 return QDF_STATUS_E_INVAL; 14025 14026 hw_caps = param_buf->soc_hw_mode_caps; 14027 if (!hw_caps) 14028 return QDF_STATUS_E_INVAL; 14029 14030 if (!hw_caps->num_hw_modes || 14031 !param_buf->hw_mode_caps || 14032 hw_caps->num_hw_modes > PSOC_MAX_HW_MODE || 14033 hw_caps->num_hw_modes > param_buf->num_hw_mode_caps) 14034 return QDF_STATUS_E_INVAL; 14035 14036 if (hw_mode_idx >= hw_caps->num_hw_modes) 14037 return QDF_STATUS_E_INVAL; 14038 14039 param->hw_mode_id = param_buf->hw_mode_caps[hw_mode_idx].hw_mode_id; 14040 param->phy_id_map = param_buf->hw_mode_caps[hw_mode_idx].phy_id_map; 14041 14042 param->hw_mode_config_type = 14043 param_buf->hw_mode_caps[hw_mode_idx].hw_mode_config_type; 14044 14045 return QDF_STATUS_SUCCESS; 14046 } 14047 14048 /** 14049 * extract_mac_phy_cap_service_ready_11be_support - api to extract 11be support 14050 * @param param: host mac phy capabilities 14051 * @param mac_phy_caps: mac phy capabilities 14052 * 14053 * Return: void 14054 */ 14055 #ifdef WLAN_FEATURE_11BE 14056 static void 14057 extract_service_ready_11be_support(struct wlan_psoc_host_mac_phy_caps *param, 14058 WMI_MAC_PHY_CAPABILITIES *mac_phy_caps) 14059 { 14060 param->supports_11be = 14061 WMI_SUPPORT_11BE_GET(mac_phy_caps->supported_flags); 14062 14063 wmi_debug("11be support %d", param->supports_11be); 14064 } 14065 #else 14066 static void 14067 extract_service_ready_11be_support(struct wlan_psoc_host_mac_phy_caps *param, 14068 WMI_MAC_PHY_CAPABILITIES *mac_phy_caps) 14069 { 14070 } 14071 #endif 14072 14073 #if defined(WLAN_FEATURE_11BE_MLO) && defined(WLAN_MLO_MULTI_CHIP) 14074 static void extract_hw_link_id(struct wlan_psoc_host_mac_phy_caps *param, 14075 WMI_MAC_PHY_CAPABILITIES *mac_phy_caps) 14076 { 14077 param->hw_link_id = WMI_PHY_GET_HW_LINK_ID(mac_phy_caps->pdev_id); 14078 } 14079 #else 14080 static void extract_hw_link_id(struct wlan_psoc_host_mac_phy_caps *param, 14081 WMI_MAC_PHY_CAPABILITIES *mac_phy_caps) 14082 { 14083 } 14084 #endif /*WLAN_FEATURE_11BE_MLO && WLAN_MLO_MULTI_CHIP*/ 14085 14086 /** 14087 * extract_mac_phy_cap_service_ready_ext_tlv() - 14088 * extract MAC phy cap from service ready event 14089 * @wmi_handle: wmi handle 14090 * @param evt_buf: pointer to event buffer 14091 * @param param: Pointer to hold evt buf 14092 * @param hw_mode_idx: hw mode idx should be less than num_mode 14093 * @param phy_id: phy id within hw_mode 14094 * 14095 * Return: QDF_STATUS_SUCCESS for success or error code 14096 */ 14097 static QDF_STATUS extract_mac_phy_cap_service_ready_ext_tlv( 14098 wmi_unified_t wmi_handle, 14099 uint8_t *event, uint8_t hw_mode_id, uint8_t phy_id, 14100 struct wlan_psoc_host_mac_phy_caps *param) 14101 { 14102 WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *param_buf; 14103 WMI_MAC_PHY_CAPABILITIES *mac_phy_caps; 14104 WMI_SOC_MAC_PHY_HW_MODE_CAPS *hw_caps; 14105 uint32_t phy_map; 14106 uint8_t hw_idx, phy_idx = 0, pdev_id; 14107 14108 param_buf = (WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *) event; 14109 if (!param_buf) 14110 return QDF_STATUS_E_INVAL; 14111 14112 hw_caps = param_buf->soc_hw_mode_caps; 14113 if (!hw_caps) 14114 return QDF_STATUS_E_INVAL; 14115 if (hw_caps->num_hw_modes > PSOC_MAX_HW_MODE || 14116 hw_caps->num_hw_modes > param_buf->num_hw_mode_caps) { 14117 wmi_err_rl("invalid num_hw_modes %d, num_hw_mode_caps %d", 14118 hw_caps->num_hw_modes, param_buf->num_hw_mode_caps); 14119 return QDF_STATUS_E_INVAL; 14120 } 14121 14122 for (hw_idx = 0; hw_idx < hw_caps->num_hw_modes; hw_idx++) { 14123 if (hw_mode_id == param_buf->hw_mode_caps[hw_idx].hw_mode_id) 14124 break; 14125 14126 phy_map = param_buf->hw_mode_caps[hw_idx].phy_id_map; 14127 while (phy_map) { 14128 phy_map >>= 1; 14129 phy_idx++; 14130 } 14131 } 14132 14133 if (hw_idx == hw_caps->num_hw_modes) 14134 return QDF_STATUS_E_INVAL; 14135 14136 phy_idx += phy_id; 14137 if (phy_idx >= param_buf->num_mac_phy_caps) 14138 return QDF_STATUS_E_INVAL; 14139 14140 mac_phy_caps = ¶m_buf->mac_phy_caps[phy_idx]; 14141 14142 param->hw_mode_id = mac_phy_caps->hw_mode_id; 14143 param->phy_idx = phy_idx; 14144 pdev_id = WMI_PHY_GET_PDEV_ID(mac_phy_caps->pdev_id); 14145 param->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 14146 wmi_handle, 14147 pdev_id); 14148 param->tgt_pdev_id = pdev_id; 14149 extract_hw_link_id(param, mac_phy_caps); 14150 param->phy_id = mac_phy_caps->phy_id; 14151 param->supports_11b = 14152 WMI_SUPPORT_11B_GET(mac_phy_caps->supported_flags); 14153 param->supports_11g = 14154 WMI_SUPPORT_11G_GET(mac_phy_caps->supported_flags); 14155 param->supports_11a = 14156 WMI_SUPPORT_11A_GET(mac_phy_caps->supported_flags); 14157 param->supports_11n = 14158 WMI_SUPPORT_11N_GET(mac_phy_caps->supported_flags); 14159 param->supports_11ac = 14160 WMI_SUPPORT_11AC_GET(mac_phy_caps->supported_flags); 14161 param->supports_11ax = 14162 WMI_SUPPORT_11AX_GET(mac_phy_caps->supported_flags); 14163 14164 extract_service_ready_11be_support(param, mac_phy_caps); 14165 14166 param->supported_bands = mac_phy_caps->supported_bands; 14167 param->ampdu_density = mac_phy_caps->ampdu_density; 14168 param->max_bw_supported_2G = mac_phy_caps->max_bw_supported_2G; 14169 param->ht_cap_info_2G = mac_phy_caps->ht_cap_info_2G; 14170 param->vht_cap_info_2G = mac_phy_caps->vht_cap_info_2G; 14171 param->vht_supp_mcs_2G = mac_phy_caps->vht_supp_mcs_2G; 14172 param->he_cap_info_2G[WMI_HOST_HECAP_MAC_WORD1] = 14173 mac_phy_caps->he_cap_info_2G; 14174 param->he_cap_info_2G[WMI_HOST_HECAP_MAC_WORD2] = 14175 mac_phy_caps->he_cap_info_2G_ext; 14176 param->he_supp_mcs_2G = mac_phy_caps->he_supp_mcs_2G; 14177 param->tx_chain_mask_2G = mac_phy_caps->tx_chain_mask_2G; 14178 param->rx_chain_mask_2G = mac_phy_caps->rx_chain_mask_2G; 14179 param->max_bw_supported_5G = mac_phy_caps->max_bw_supported_5G; 14180 param->ht_cap_info_5G = mac_phy_caps->ht_cap_info_5G; 14181 param->vht_cap_info_5G = mac_phy_caps->vht_cap_info_5G; 14182 param->vht_supp_mcs_5G = mac_phy_caps->vht_supp_mcs_5G; 14183 param->he_cap_info_5G[WMI_HOST_HECAP_MAC_WORD1] = 14184 mac_phy_caps->he_cap_info_5G; 14185 param->he_cap_info_5G[WMI_HOST_HECAP_MAC_WORD2] = 14186 mac_phy_caps->he_cap_info_5G_ext; 14187 param->he_supp_mcs_5G = mac_phy_caps->he_supp_mcs_5G; 14188 param->he_cap_info_internal = mac_phy_caps->he_cap_info_internal; 14189 param->tx_chain_mask_5G = mac_phy_caps->tx_chain_mask_5G; 14190 param->rx_chain_mask_5G = mac_phy_caps->rx_chain_mask_5G; 14191 qdf_mem_copy(¶m->he_cap_phy_info_2G, 14192 &mac_phy_caps->he_cap_phy_info_2G, 14193 sizeof(param->he_cap_phy_info_2G)); 14194 qdf_mem_copy(¶m->he_cap_phy_info_5G, 14195 &mac_phy_caps->he_cap_phy_info_5G, 14196 sizeof(param->he_cap_phy_info_5G)); 14197 qdf_mem_copy(¶m->he_ppet2G, &mac_phy_caps->he_ppet2G, 14198 sizeof(param->he_ppet2G)); 14199 qdf_mem_copy(¶m->he_ppet5G, &mac_phy_caps->he_ppet5G, 14200 sizeof(param->he_ppet5G)); 14201 param->chainmask_table_id = mac_phy_caps->chainmask_table_id; 14202 param->lmac_id = mac_phy_caps->lmac_id; 14203 param->reg_cap_ext.wireless_modes = convert_wireless_modes_tlv 14204 (mac_phy_caps->wireless_modes); 14205 param->reg_cap_ext.low_2ghz_chan = mac_phy_caps->low_2ghz_chan_freq; 14206 param->reg_cap_ext.high_2ghz_chan = mac_phy_caps->high_2ghz_chan_freq; 14207 param->reg_cap_ext.low_5ghz_chan = mac_phy_caps->low_5ghz_chan_freq; 14208 param->reg_cap_ext.high_5ghz_chan = mac_phy_caps->high_5ghz_chan_freq; 14209 param->nss_ratio_enabled = WMI_NSS_RATIO_ENABLE_DISABLE_GET( 14210 mac_phy_caps->nss_ratio); 14211 param->nss_ratio_info = WMI_NSS_RATIO_INFO_GET(mac_phy_caps->nss_ratio); 14212 14213 return QDF_STATUS_SUCCESS; 14214 } 14215 14216 #ifdef WLAN_FEATURE_11BE_MLO 14217 /** 14218 * extract_mac_phy_emlcap() - API to extract EML Capabilities 14219 * @param: host ext2 mac phy capabilities 14220 * @mac_phy_caps: ext mac phy capabilities 14221 * 14222 * Return: void 14223 */ 14224 static void extract_mac_phy_emlcap(struct wlan_psoc_host_mac_phy_caps_ext2 *param, 14225 WMI_MAC_PHY_CAPABILITIES_EXT *mac_phy_caps) 14226 { 14227 if (!param || !mac_phy_caps) 14228 return; 14229 14230 param->emlcap.emlsr_supp = WMI_SUPPORT_EMLSR_GET(mac_phy_caps->eml_capability); 14231 param->emlcap.emlsr_pad_delay = WMI_EMLSR_PADDING_DELAY_GET(mac_phy_caps->eml_capability); 14232 param->emlcap.emlsr_trans_delay = WMI_EMLSR_TRANSITION_DELAY_GET(mac_phy_caps->eml_capability); 14233 param->emlcap.emlmr_supp = WMI_SUPPORT_EMLMR_GET(mac_phy_caps->eml_capability); 14234 param->emlcap.emlmr_delay = WMI_EMLMR_DELAY_GET(mac_phy_caps->eml_capability); 14235 param->emlcap.trans_timeout = WMI_TRANSITION_TIMEOUT_GET(mac_phy_caps->eml_capability); 14236 } 14237 14238 /** 14239 * extract_mac_phy_mldcap() - API to extract MLD Capabilities 14240 * @param: host ext2 mac phy capabilities 14241 * @mac_phy_caps: ext mac phy capabilities 14242 * 14243 * Return: void 14244 */ 14245 static void extract_mac_phy_mldcap(struct wlan_psoc_host_mac_phy_caps_ext2 *param, 14246 WMI_MAC_PHY_CAPABILITIES_EXT *mac_phy_caps) 14247 { 14248 if (!param || !mac_phy_caps) 14249 return; 14250 14251 param->mldcap.max_simult_link = WMI_MAX_NUM_SIMULTANEOUS_LINKS_GET(mac_phy_caps->mld_capability); 14252 param->mldcap.srs_support = WMI_SUPPORT_SRS_GET(mac_phy_caps->mld_capability); 14253 param->mldcap.tid2link_neg_support = WMI_TID_TO_LINK_NEGOTIATION_GET(mac_phy_caps->mld_capability); 14254 param->mldcap.str_freq_sep = WMI_FREQ_SEPERATION_STR_GET(mac_phy_caps->mld_capability); 14255 param->mldcap.aar_support = WMI_SUPPORT_AAR_GET(mac_phy_caps->mld_capability); 14256 } 14257 #else 14258 static void extract_mac_phy_emlcap(struct wlan_psoc_host_mac_phy_caps_ext2 *param, 14259 WMI_MAC_PHY_CAPABILITIES_EXT *mac_phy_caps) 14260 { 14261 } 14262 14263 static void extract_mac_phy_mldcap(struct wlan_psoc_host_mac_phy_caps_ext2 *param, 14264 WMI_MAC_PHY_CAPABILITIES_EXT *mac_phy_caps) 14265 { 14266 } 14267 #endif 14268 14269 /** 14270 * extract_mac_phy_cap_ehtcaps- api to extract eht mac phy caps 14271 * @param param: host ext2 mac phy capabilities 14272 * @param mac_phy_caps: ext mac phy capabilities 14273 * 14274 * Return: void 14275 */ 14276 #ifdef WLAN_FEATURE_11BE 14277 static void extract_mac_phy_cap_ehtcaps( 14278 struct wlan_psoc_host_mac_phy_caps_ext2 *param, 14279 WMI_MAC_PHY_CAPABILITIES_EXT *mac_phy_caps) 14280 { 14281 uint32_t i; 14282 14283 param->eht_supp_mcs_2G = mac_phy_caps->eht_supp_mcs_2G; 14284 param->eht_supp_mcs_5G = mac_phy_caps->eht_supp_mcs_5G; 14285 param->eht_cap_info_internal = mac_phy_caps->eht_cap_info_internal; 14286 14287 qdf_mem_copy(¶m->eht_cap_info_2G, 14288 &mac_phy_caps->eht_cap_mac_info_2G, 14289 sizeof(param->eht_cap_info_2G)); 14290 qdf_mem_copy(¶m->eht_cap_info_5G, 14291 &mac_phy_caps->eht_cap_mac_info_5G, 14292 sizeof(param->eht_cap_info_5G)); 14293 14294 qdf_mem_copy(¶m->eht_cap_phy_info_2G, 14295 &mac_phy_caps->eht_cap_phy_info_2G, 14296 sizeof(param->eht_cap_phy_info_2G)); 14297 qdf_mem_copy(¶m->eht_cap_phy_info_5G, 14298 &mac_phy_caps->eht_cap_phy_info_5G, 14299 sizeof(param->eht_cap_phy_info_5G)); 14300 14301 qdf_mem_copy(¶m->eht_supp_mcs_ext_2G, 14302 &mac_phy_caps->eht_supp_mcs_ext_2G, 14303 sizeof(param->eht_supp_mcs_ext_2G)); 14304 qdf_mem_copy(¶m->eht_supp_mcs_ext_5G, 14305 &mac_phy_caps->eht_supp_mcs_ext_5G, 14306 sizeof(param->eht_supp_mcs_ext_5G)); 14307 14308 qdf_mem_copy(¶m->eht_ppet2G, &mac_phy_caps->eht_ppet2G, 14309 sizeof(param->eht_ppet2G)); 14310 qdf_mem_copy(¶m->eht_ppet5G, &mac_phy_caps->eht_ppet5G, 14311 sizeof(param->eht_ppet5G)); 14312 14313 wmi_debug("EHT mac caps: mac cap_info_2G %x, mac cap_info_5G %x, supp_mcs_2G %x, supp_mcs_5G %x, info_internal %x", 14314 mac_phy_caps->eht_cap_mac_info_2G[0], 14315 mac_phy_caps->eht_cap_mac_info_5G[0], 14316 mac_phy_caps->eht_supp_mcs_2G, mac_phy_caps->eht_supp_mcs_5G, 14317 mac_phy_caps->eht_cap_info_internal); 14318 14319 wmi_nofl_debug("EHT phy caps: "); 14320 14321 wmi_nofl_debug("2G:"); 14322 for (i = 0; i < PSOC_HOST_MAX_EHT_PHY_SIZE; i++) { 14323 wmi_nofl_debug("index %d value %x", 14324 i, param->eht_cap_phy_info_2G[i]); 14325 } 14326 wmi_nofl_debug("5G:"); 14327 for (i = 0; i < PSOC_HOST_MAX_EHT_PHY_SIZE; i++) { 14328 wmi_nofl_debug("index %d value %x", 14329 i, param->eht_cap_phy_info_5G[i]); 14330 } 14331 wmi_nofl_debug("2G MCS ext Map:"); 14332 for (i = 0; i < PSOC_HOST_EHT_MCS_NSS_MAP_2G_SIZE; i++) { 14333 wmi_nofl_debug("index %d value %x", 14334 i, param->eht_supp_mcs_ext_2G[i]); 14335 } 14336 wmi_nofl_debug("5G MCS ext Map:"); 14337 for (i = 0; i < PSOC_HOST_EHT_MCS_NSS_MAP_5G_SIZE; i++) { 14338 wmi_nofl_debug("index %d value %x", 14339 i, param->eht_supp_mcs_ext_5G[i]); 14340 } 14341 wmi_nofl_debug("2G PPET: numss_m1 %x ru_bit_mask %x", 14342 param->eht_ppet2G.numss_m1, 14343 param->eht_ppet2G.ru_bit_mask); 14344 for (i = 0; i < PSOC_HOST_MAX_NUM_SS; i++) { 14345 wmi_nofl_debug("index %d value %x", 14346 i, param->eht_ppet2G.ppet16_ppet8_ru3_ru0[i]); 14347 } 14348 wmi_nofl_debug("5G PPET: numss_m1 %x ru_bit_mask %x", 14349 param->eht_ppet5G.numss_m1, 14350 param->eht_ppet5G.ru_bit_mask); 14351 for (i = 0; i < PSOC_HOST_MAX_NUM_SS; i++) { 14352 wmi_nofl_debug("index %d value %x", 14353 i, param->eht_ppet5G.ppet16_ppet8_ru3_ru0[i]); 14354 } 14355 } 14356 #else 14357 static void extract_mac_phy_cap_ehtcaps( 14358 struct wlan_psoc_host_mac_phy_caps_ext2 *param, 14359 WMI_MAC_PHY_CAPABILITIES_EXT *mac_phy_caps) 14360 { 14361 } 14362 #endif 14363 14364 static QDF_STATUS extract_mac_phy_cap_service_ready_ext2_tlv( 14365 wmi_unified_t wmi_handle, 14366 uint8_t *event, uint8_t hw_mode_id, uint8_t phy_id, 14367 uint8_t phy_idx, 14368 struct wlan_psoc_host_mac_phy_caps_ext2 *param) 14369 { 14370 WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *param_buf; 14371 WMI_MAC_PHY_CAPABILITIES_EXT *mac_phy_caps; 14372 14373 if (!event) { 14374 wmi_err("null evt_buf"); 14375 return QDF_STATUS_E_INVAL; 14376 } 14377 14378 param_buf = (WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *)event; 14379 14380 if (!param_buf->num_mac_phy_caps) 14381 return QDF_STATUS_SUCCESS; 14382 14383 if (phy_idx >= param_buf->num_mac_phy_caps) 14384 return QDF_STATUS_E_INVAL; 14385 14386 mac_phy_caps = ¶m_buf->mac_phy_caps[phy_idx]; 14387 14388 if ((hw_mode_id != mac_phy_caps->hw_mode_id) || 14389 (phy_id != mac_phy_caps->phy_id)) 14390 return QDF_STATUS_E_INVAL; 14391 14392 param->hw_mode_id = mac_phy_caps->hw_mode_id; 14393 param->phy_id = mac_phy_caps->phy_id; 14394 param->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 14395 wmi_handle, WMI_PHY_GET_PDEV_ID(mac_phy_caps->pdev_id)); 14396 param->wireless_modes_ext = convert_wireless_modes_ext_tlv( 14397 mac_phy_caps->wireless_modes_ext); 14398 14399 extract_mac_phy_cap_ehtcaps(param, mac_phy_caps); 14400 extract_mac_phy_emlcap(param, mac_phy_caps); 14401 extract_mac_phy_mldcap(param, mac_phy_caps); 14402 14403 return QDF_STATUS_SUCCESS; 14404 } 14405 14406 /** 14407 * extract_reg_cap_service_ready_ext_tlv() - 14408 * extract REG cap from service ready event 14409 * @wmi_handle: wmi handle 14410 * @param evt_buf: pointer to event buffer 14411 * @param param: Pointer to hold evt buf 14412 * @param phy_idx: phy idx should be less than num_mode 14413 * 14414 * Return: QDF_STATUS_SUCCESS for success or error code 14415 */ 14416 static QDF_STATUS extract_reg_cap_service_ready_ext_tlv( 14417 wmi_unified_t wmi_handle, 14418 uint8_t *event, uint8_t phy_idx, 14419 struct wlan_psoc_host_hal_reg_capabilities_ext *param) 14420 { 14421 WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *param_buf; 14422 WMI_SOC_HAL_REG_CAPABILITIES *reg_caps; 14423 WMI_HAL_REG_CAPABILITIES_EXT *ext_reg_cap; 14424 14425 param_buf = (WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *) event; 14426 if (!param_buf) 14427 return QDF_STATUS_E_INVAL; 14428 14429 reg_caps = param_buf->soc_hal_reg_caps; 14430 if (!reg_caps) 14431 return QDF_STATUS_E_INVAL; 14432 14433 if (reg_caps->num_phy > param_buf->num_hal_reg_caps) 14434 return QDF_STATUS_E_INVAL; 14435 14436 if (phy_idx >= reg_caps->num_phy) 14437 return QDF_STATUS_E_INVAL; 14438 14439 if (!param_buf->hal_reg_caps) 14440 return QDF_STATUS_E_INVAL; 14441 14442 ext_reg_cap = ¶m_buf->hal_reg_caps[phy_idx]; 14443 14444 param->phy_id = ext_reg_cap->phy_id; 14445 param->eeprom_reg_domain = ext_reg_cap->eeprom_reg_domain; 14446 param->eeprom_reg_domain_ext = ext_reg_cap->eeprom_reg_domain_ext; 14447 param->regcap1 = ext_reg_cap->regcap1; 14448 param->regcap2 = ext_reg_cap->regcap2; 14449 param->wireless_modes = convert_wireless_modes_tlv( 14450 ext_reg_cap->wireless_modes); 14451 param->low_2ghz_chan = ext_reg_cap->low_2ghz_chan; 14452 param->high_2ghz_chan = ext_reg_cap->high_2ghz_chan; 14453 param->low_5ghz_chan = ext_reg_cap->low_5ghz_chan; 14454 param->high_5ghz_chan = ext_reg_cap->high_5ghz_chan; 14455 14456 return QDF_STATUS_SUCCESS; 14457 } 14458 14459 static QDF_STATUS validate_dbr_ring_caps_idx(uint8_t idx, 14460 uint8_t num_dma_ring_caps) 14461 { 14462 /* If dma_ring_caps is populated, num_dbr_ring_caps is non-zero */ 14463 if (!num_dma_ring_caps) { 14464 wmi_err("dma_ring_caps %d", num_dma_ring_caps); 14465 return QDF_STATUS_E_INVAL; 14466 } 14467 if (idx >= num_dma_ring_caps) { 14468 wmi_err("Index %d exceeds range", idx); 14469 return QDF_STATUS_E_INVAL; 14470 } 14471 return QDF_STATUS_SUCCESS; 14472 } 14473 14474 static void 14475 populate_dbr_ring_cap_elems(wmi_unified_t wmi_handle, 14476 struct wlan_psoc_host_dbr_ring_caps *param, 14477 WMI_DMA_RING_CAPABILITIES *dbr_ring_caps) 14478 { 14479 param->pdev_id = wmi_handle->ops->convert_target_pdev_id_to_host( 14480 wmi_handle, 14481 dbr_ring_caps->pdev_id); 14482 param->mod_id = dbr_ring_caps->mod_id; 14483 param->ring_elems_min = dbr_ring_caps->ring_elems_min; 14484 param->min_buf_size = dbr_ring_caps->min_buf_size; 14485 param->min_buf_align = dbr_ring_caps->min_buf_align; 14486 } 14487 14488 static QDF_STATUS extract_dbr_ring_cap_service_ready_ext_tlv( 14489 wmi_unified_t wmi_handle, 14490 uint8_t *event, uint8_t idx, 14491 struct wlan_psoc_host_dbr_ring_caps *param) 14492 { 14493 WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *param_buf; 14494 QDF_STATUS status; 14495 14496 param_buf = (WMI_SERVICE_READY_EXT_EVENTID_param_tlvs *)event; 14497 if (!param_buf) 14498 return QDF_STATUS_E_INVAL; 14499 14500 status = validate_dbr_ring_caps_idx(idx, param_buf->num_dma_ring_caps); 14501 if (status != QDF_STATUS_SUCCESS) 14502 return status; 14503 14504 populate_dbr_ring_cap_elems(wmi_handle, param, 14505 ¶m_buf->dma_ring_caps[idx]); 14506 return QDF_STATUS_SUCCESS; 14507 } 14508 14509 static QDF_STATUS extract_dbr_ring_cap_service_ready_ext2_tlv( 14510 wmi_unified_t wmi_handle, 14511 uint8_t *event, uint8_t idx, 14512 struct wlan_psoc_host_dbr_ring_caps *param) 14513 { 14514 WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *param_buf; 14515 QDF_STATUS status; 14516 14517 param_buf = (WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *)event; 14518 if (!param_buf) 14519 return QDF_STATUS_E_INVAL; 14520 14521 status = validate_dbr_ring_caps_idx(idx, param_buf->num_dma_ring_caps); 14522 if (status != QDF_STATUS_SUCCESS) 14523 return status; 14524 14525 populate_dbr_ring_cap_elems(wmi_handle, param, 14526 ¶m_buf->dma_ring_caps[idx]); 14527 return QDF_STATUS_SUCCESS; 14528 } 14529 14530 static QDF_STATUS extract_scan_radio_cap_service_ready_ext2_tlv( 14531 wmi_unified_t wmi_handle, 14532 uint8_t *event, uint8_t idx, 14533 struct wlan_psoc_host_scan_radio_caps *param) 14534 { 14535 WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *param_buf; 14536 WMI_SCAN_RADIO_CAPABILITIES_EXT2 *scan_radio_caps; 14537 14538 param_buf = (WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *)event; 14539 if (!param_buf) 14540 return QDF_STATUS_E_INVAL; 14541 14542 if (idx >= param_buf->num_wmi_scan_radio_caps) 14543 return QDF_STATUS_E_INVAL; 14544 14545 scan_radio_caps = ¶m_buf->wmi_scan_radio_caps[idx]; 14546 param->phy_id = scan_radio_caps->phy_id; 14547 param->scan_radio_supported = 14548 WMI_SCAN_RADIO_CAP_SCAN_RADIO_FLAG_GET(scan_radio_caps->flags); 14549 param->dfs_en = 14550 WMI_SCAN_RADIO_CAP_DFS_FLAG_GET(scan_radio_caps->flags); 14551 14552 return QDF_STATUS_SUCCESS; 14553 } 14554 14555 static QDF_STATUS extract_sw_cal_ver_ext2_tlv(wmi_unified_t wmi_handle, 14556 uint8_t *event, 14557 struct wmi_host_sw_cal_ver *cal) 14558 { 14559 WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *param_buf; 14560 wmi_sw_cal_ver_cap *fw_cap; 14561 14562 param_buf = (WMI_SERVICE_READY_EXT2_EVENTID_param_tlvs *)event; 14563 if (!param_buf) 14564 return QDF_STATUS_E_INVAL; 14565 14566 fw_cap = param_buf->sw_cal_ver_cap; 14567 if (!fw_cap) 14568 return QDF_STATUS_E_INVAL; 14569 14570 cal->bdf_cal_ver = fw_cap->bdf_cal_ver; 14571 cal->ftm_cal_ver = fw_cap->ftm_cal_ver; 14572 cal->status = fw_cap->status; 14573 14574 return QDF_STATUS_SUCCESS; 14575 } 14576 14577 /** 14578 * wmi_tgt_thermal_level_to_host() - Convert target thermal level to host enum 14579 * @level: target thermal level from WMI_THERM_THROT_STATS_EVENTID event 14580 * 14581 * Return: host thermal throt level 14582 */ 14583 static enum thermal_throttle_level 14584 wmi_tgt_thermal_level_to_host(uint32_t level) 14585 { 14586 switch (level) { 14587 case WMI_THERMAL_FULLPERF: 14588 return THERMAL_FULLPERF; 14589 case WMI_THERMAL_MITIGATION: 14590 return THERMAL_MITIGATION; 14591 case WMI_THERMAL_SHUTOFF: 14592 return THERMAL_SHUTOFF; 14593 case WMI_THERMAL_SHUTDOWN_TGT: 14594 return THERMAL_SHUTDOWN_TARGET; 14595 default: 14596 return THERMAL_UNKNOWN; 14597 } 14598 } 14599 14600 #ifdef THERMAL_STATS_SUPPORT 14601 static void 14602 populate_thermal_stats(WMI_THERM_THROT_STATS_EVENTID_param_tlvs *param_buf, 14603 uint32_t *therm_throt_levels, 14604 struct thermal_throt_level_stats *tt_temp_range_stats) 14605 { 14606 uint8_t lvl_idx; 14607 wmi_therm_throt_stats_event_fixed_param *tt_stats_event; 14608 wmi_thermal_throt_temp_range_stats *wmi_tt_stats; 14609 14610 tt_stats_event = param_buf->fixed_param; 14611 *therm_throt_levels = (tt_stats_event->therm_throt_levels > 14612 WMI_THERMAL_STATS_TEMP_THRESH_LEVEL_MAX) ? 14613 WMI_THERMAL_STATS_TEMP_THRESH_LEVEL_MAX : 14614 tt_stats_event->therm_throt_levels; 14615 14616 if (*therm_throt_levels > param_buf->num_temp_range_stats) { 14617 wmi_err("therm_throt_levels:%u oob num_temp_range_stats:%u", 14618 *therm_throt_levels, 14619 param_buf->num_temp_range_stats); 14620 return; 14621 } 14622 14623 wmi_tt_stats = param_buf->temp_range_stats; 14624 if (!wmi_tt_stats) { 14625 wmi_err("wmi_tt_stats Null"); 14626 return; 14627 } 14628 14629 for (lvl_idx = 0; lvl_idx < *therm_throt_levels; lvl_idx++) { 14630 tt_temp_range_stats[lvl_idx].start_temp_level = 14631 wmi_tt_stats[lvl_idx].start_temp_level; 14632 tt_temp_range_stats[lvl_idx].end_temp_level = 14633 wmi_tt_stats[lvl_idx].end_temp_level; 14634 tt_temp_range_stats[lvl_idx].total_time_ms_lo = 14635 wmi_tt_stats[lvl_idx].total_time_ms_lo; 14636 tt_temp_range_stats[lvl_idx].total_time_ms_hi = 14637 wmi_tt_stats[lvl_idx].total_time_ms_hi; 14638 tt_temp_range_stats[lvl_idx].num_entry = 14639 wmi_tt_stats[lvl_idx].num_entry; 14640 wmi_debug("level %d, start temp %d, end temp %d, total time low %d, total time high %d, counter %d", 14641 lvl_idx, wmi_tt_stats[lvl_idx].start_temp_level, 14642 wmi_tt_stats[lvl_idx].end_temp_level, 14643 wmi_tt_stats[lvl_idx].total_time_ms_lo, 14644 wmi_tt_stats[lvl_idx].total_time_ms_hi, 14645 wmi_tt_stats[lvl_idx].num_entry); 14646 } 14647 } 14648 #else 14649 static void 14650 populate_thermal_stats(WMI_THERM_THROT_STATS_EVENTID_param_tlvs *param_buf, 14651 uint32_t *therm_throt_levels, 14652 struct thermal_throt_level_stats *tt_temp_range_stats) 14653 { 14654 } 14655 #endif 14656 14657 /** 14658 * extract_thermal_stats_tlv() - extract thermal stats from event 14659 * @wmi_handle: wmi handle 14660 * @param evt_buf: Pointer to event buffer 14661 * @param temp: Pointer to hold extracted temperature 14662 * @param level: Pointer to hold extracted level in host enum 14663 * @param therm_throt_levels: Pointer to hold extracted thermal throttle temp 14664 * range 14665 * @param tt_temp_range_stats_event: Pointer to hold extracted thermal stats for 14666 * every level 14667 * 14668 * Return: 0 for success or error code 14669 */ 14670 static QDF_STATUS 14671 extract_thermal_stats_tlv(wmi_unified_t wmi_handle, 14672 void *evt_buf, uint32_t *temp, 14673 enum thermal_throttle_level *level, 14674 uint32_t *therm_throt_levels, 14675 struct thermal_throt_level_stats *tt_temp_range_stats_event, 14676 uint32_t *pdev_id) 14677 { 14678 WMI_THERM_THROT_STATS_EVENTID_param_tlvs *param_buf; 14679 wmi_therm_throt_stats_event_fixed_param *tt_stats_event; 14680 14681 param_buf = 14682 (WMI_THERM_THROT_STATS_EVENTID_param_tlvs *) evt_buf; 14683 if (!param_buf) 14684 return QDF_STATUS_E_INVAL; 14685 14686 tt_stats_event = param_buf->fixed_param; 14687 wmi_debug("thermal temperature %d level %d", 14688 tt_stats_event->temp, tt_stats_event->level); 14689 *pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 14690 wmi_handle, 14691 tt_stats_event->pdev_id); 14692 *temp = tt_stats_event->temp; 14693 *level = wmi_tgt_thermal_level_to_host(tt_stats_event->level); 14694 14695 if (tt_stats_event->therm_throt_levels) 14696 populate_thermal_stats(param_buf, therm_throt_levels, 14697 tt_temp_range_stats_event); 14698 14699 return QDF_STATUS_SUCCESS; 14700 } 14701 14702 /** 14703 * extract_thermal_level_stats_tlv() - extract thermal level stats from event 14704 * @wmi_handle: wmi handle 14705 * @param evt_buf: pointer to event buffer 14706 * @param idx: Index to level stats 14707 * @param levelcount: Pointer to hold levelcount 14708 * @param dccount: Pointer to hold dccount 14709 * 14710 * Return: 0 for success or error code 14711 */ 14712 static QDF_STATUS 14713 extract_thermal_level_stats_tlv(wmi_unified_t wmi_handle, 14714 void *evt_buf, uint8_t idx, uint32_t *levelcount, 14715 uint32_t *dccount) 14716 { 14717 WMI_THERM_THROT_STATS_EVENTID_param_tlvs *param_buf; 14718 wmi_therm_throt_level_stats_info *tt_level_info; 14719 14720 param_buf = 14721 (WMI_THERM_THROT_STATS_EVENTID_param_tlvs *) evt_buf; 14722 if (!param_buf) 14723 return QDF_STATUS_E_INVAL; 14724 14725 tt_level_info = param_buf->therm_throt_level_stats_info; 14726 14727 if (idx < THERMAL_LEVELS) { 14728 *levelcount = tt_level_info[idx].level_count; 14729 *dccount = tt_level_info[idx].dc_count; 14730 return QDF_STATUS_SUCCESS; 14731 } 14732 14733 return QDF_STATUS_E_FAILURE; 14734 } 14735 #ifdef BIG_ENDIAN_HOST 14736 /** 14737 * fips_conv_data_be() - LE to BE conversion of FIPS ev data 14738 * @param data_len - data length 14739 * @param data - pointer to data 14740 * 14741 * Return: QDF_STATUS - success or error status 14742 */ 14743 static QDF_STATUS fips_conv_data_be(uint32_t data_len, uint8_t *data) 14744 { 14745 uint8_t *data_aligned = NULL; 14746 int c; 14747 unsigned char *data_unaligned; 14748 14749 data_unaligned = qdf_mem_malloc(((sizeof(uint8_t) * data_len) + 14750 FIPS_ALIGN)); 14751 /* Assigning unaligned space to copy the data */ 14752 /* Checking if kmalloc does successful allocation */ 14753 if (!data_unaligned) 14754 return QDF_STATUS_E_FAILURE; 14755 14756 /* Checking if space is alligned */ 14757 if (!FIPS_IS_ALIGNED(data_unaligned, FIPS_ALIGN)) { 14758 /* align the data space */ 14759 data_aligned = 14760 (uint8_t *)FIPS_ALIGNTO(data_unaligned, FIPS_ALIGN); 14761 } else { 14762 data_aligned = (u_int8_t *)data_unaligned; 14763 } 14764 14765 /* memset and copy content from data to data aligned */ 14766 OS_MEMSET(data_aligned, 0, data_len); 14767 OS_MEMCPY(data_aligned, data, data_len); 14768 /* Endianness to LE */ 14769 for (c = 0; c < data_len/4; c++) { 14770 *((u_int32_t *)data_aligned + c) = 14771 qdf_le32_to_cpu(*((u_int32_t *)data_aligned + c)); 14772 } 14773 14774 /* Copy content to event->data */ 14775 OS_MEMCPY(data, data_aligned, data_len); 14776 14777 /* clean up allocated space */ 14778 qdf_mem_free(data_unaligned); 14779 data_aligned = NULL; 14780 data_unaligned = NULL; 14781 14782 /*************************************************************/ 14783 14784 return QDF_STATUS_SUCCESS; 14785 } 14786 #else 14787 /** 14788 * fips_conv_data_be() - DUMMY for LE platform 14789 * 14790 * Return: QDF_STATUS - success 14791 */ 14792 static QDF_STATUS fips_conv_data_be(uint32_t data_len, uint8_t *data) 14793 { 14794 return QDF_STATUS_SUCCESS; 14795 } 14796 #endif 14797 14798 /** 14799 * send_pdev_get_pn_cmd_tlv() - send get PN request params to fw 14800 * @wmi_handle - wmi handle 14801 * @params - PN request params for peer 14802 * 14803 * Return: QDF_STATUS - success or error status 14804 */ 14805 static QDF_STATUS 14806 send_pdev_get_pn_cmd_tlv(wmi_unified_t wmi_handle, 14807 struct peer_request_pn_param *params) 14808 { 14809 wmi_peer_tx_pn_request_cmd_fixed_param *cmd; 14810 wmi_buf_t buf; 14811 uint8_t *buf_ptr; 14812 uint32_t len = sizeof(wmi_peer_tx_pn_request_cmd_fixed_param); 14813 14814 buf = wmi_buf_alloc(wmi_handle, len); 14815 if (!buf) { 14816 wmi_err("wmi_buf_alloc failed"); 14817 return QDF_STATUS_E_FAILURE; 14818 } 14819 14820 buf_ptr = (uint8_t *)wmi_buf_data(buf); 14821 cmd = (wmi_peer_tx_pn_request_cmd_fixed_param *)buf_ptr; 14822 14823 WMITLV_SET_HDR(&cmd->tlv_header, 14824 WMITLV_TAG_STRUC_wmi_peer_tx_pn_request_cmd_fixed_param, 14825 WMITLV_GET_STRUCT_TLVLEN(wmi_peer_tx_pn_request_cmd_fixed_param)); 14826 14827 cmd->vdev_id = params->vdev_id; 14828 WMI_CHAR_ARRAY_TO_MAC_ADDR(params->peer_macaddr, &cmd->peer_macaddr); 14829 cmd->key_type = params->key_type; 14830 if (wmi_unified_cmd_send(wmi_handle, buf, len, 14831 WMI_PEER_TX_PN_REQUEST_CMDID)) { 14832 wmi_err("Failed to send WMI command"); 14833 wmi_buf_free(buf); 14834 return QDF_STATUS_E_FAILURE; 14835 } 14836 return QDF_STATUS_SUCCESS; 14837 } 14838 14839 /** 14840 * extract_get_pn_data_tlv() - extract pn resp 14841 * @wmi_handle - wmi handle 14842 * @params - PN response params for peer 14843 * 14844 * Return: QDF_STATUS - success or error status 14845 */ 14846 static QDF_STATUS 14847 extract_get_pn_data_tlv(wmi_unified_t wmi_handle, void *evt_buf, 14848 struct wmi_host_get_pn_event *param) 14849 { 14850 WMI_PEER_TX_PN_RESPONSE_EVENTID_param_tlvs *param_buf; 14851 wmi_peer_tx_pn_response_event_fixed_param *event = NULL; 14852 14853 param_buf = (WMI_PEER_TX_PN_RESPONSE_EVENTID_param_tlvs *)evt_buf; 14854 event = 14855 (wmi_peer_tx_pn_response_event_fixed_param *)param_buf->fixed_param; 14856 14857 param->vdev_id = event->vdev_id; 14858 param->key_type = event->key_type; 14859 qdf_mem_copy(param->pn, event->pn, sizeof(event->pn)); 14860 WMI_MAC_ADDR_TO_CHAR_ARRAY(&event->peer_macaddr, param->mac_addr); 14861 14862 return QDF_STATUS_SUCCESS; 14863 } 14864 14865 /** 14866 * send_pdev_get_rxpn_cmd_tlv() - send get Rx PN request params to fw 14867 * @wmi_handle: wmi handle 14868 * @params: Rx PN request params for peer 14869 * 14870 * Return: QDF_STATUS - success or error status 14871 */ 14872 static QDF_STATUS 14873 send_pdev_get_rxpn_cmd_tlv(wmi_unified_t wmi_handle, 14874 struct peer_request_rxpn_param *params) 14875 { 14876 wmi_peer_rx_pn_request_cmd_fixed_param *cmd; 14877 wmi_buf_t buf; 14878 uint8_t *buf_ptr; 14879 uint32_t len = sizeof(wmi_peer_rx_pn_request_cmd_fixed_param); 14880 14881 if (!is_service_enabled_tlv(wmi_handle, 14882 WMI_SERVICE_PN_REPLAY_CHECK_SUPPORT)) { 14883 wmi_err("Rx PN Replay Check not supported by target"); 14884 return QDF_STATUS_E_NOSUPPORT; 14885 } 14886 14887 buf = wmi_buf_alloc(wmi_handle, len); 14888 if (!buf) { 14889 wmi_err("wmi_buf_alloc failed"); 14890 return QDF_STATUS_E_FAILURE; 14891 } 14892 14893 buf_ptr = (uint8_t *)wmi_buf_data(buf); 14894 cmd = (wmi_peer_rx_pn_request_cmd_fixed_param *)buf_ptr; 14895 14896 WMITLV_SET_HDR(&cmd->tlv_header, 14897 WMITLV_TAG_STRUC_wmi_peer_rx_pn_request_cmd_fixed_param, 14898 WMITLV_GET_STRUCT_TLVLEN(wmi_peer_rx_pn_request_cmd_fixed_param)); 14899 14900 cmd->vdev_id = params->vdev_id; 14901 WMI_CHAR_ARRAY_TO_MAC_ADDR(params->peer_macaddr, &cmd->peer_macaddr); 14902 cmd->key_ix = params->keyix; 14903 if (wmi_unified_cmd_send(wmi_handle, buf, len, 14904 WMI_PEER_RX_PN_REQUEST_CMDID)) { 14905 wmi_err("Failed to send WMI command"); 14906 wmi_buf_free(buf); 14907 return QDF_STATUS_E_FAILURE; 14908 } 14909 return QDF_STATUS_SUCCESS; 14910 } 14911 14912 /** 14913 * extract_get_rxpn_data_tlv() - extract Rx PN resp 14914 * @wmi_handle: wmi handle 14915 * @params: Rx PN response params for peer 14916 * 14917 * Return: QDF_STATUS - success or error status 14918 */ 14919 static QDF_STATUS 14920 extract_get_rxpn_data_tlv(wmi_unified_t wmi_handle, void *evt_buf, 14921 struct wmi_host_get_rxpn_event *params) 14922 { 14923 WMI_PEER_RX_PN_RESPONSE_EVENTID_param_tlvs *param_buf; 14924 wmi_peer_rx_pn_response_event_fixed_param *event; 14925 14926 param_buf = evt_buf; 14927 event = param_buf->fixed_param; 14928 14929 params->vdev_id = event->vdev_id; 14930 params->keyix = event->key_idx; 14931 qdf_mem_copy(params->pn, event->pn, sizeof(event->pn)); 14932 WMI_MAC_ADDR_TO_CHAR_ARRAY(&event->peer_macaddr, params->mac_addr); 14933 14934 return QDF_STATUS_SUCCESS; 14935 } 14936 14937 /** 14938 * extract_fips_event_data_tlv() - extract fips event data 14939 * @wmi_handle: wmi handle 14940 * @param evt_buf: pointer to event buffer 14941 * @param param: pointer FIPS event params 14942 * 14943 * Return: 0 for success or error code 14944 */ 14945 static QDF_STATUS extract_fips_event_data_tlv(wmi_unified_t wmi_handle, 14946 void *evt_buf, struct wmi_host_fips_event_param *param) 14947 { 14948 WMI_PDEV_FIPS_EVENTID_param_tlvs *param_buf; 14949 wmi_pdev_fips_event_fixed_param *event; 14950 14951 param_buf = (WMI_PDEV_FIPS_EVENTID_param_tlvs *) evt_buf; 14952 event = (wmi_pdev_fips_event_fixed_param *) param_buf->fixed_param; 14953 14954 if (event->data_len > param_buf->num_data) 14955 return QDF_STATUS_E_FAILURE; 14956 14957 if (fips_conv_data_be(event->data_len, param_buf->data) != 14958 QDF_STATUS_SUCCESS) 14959 return QDF_STATUS_E_FAILURE; 14960 14961 param->data = (uint32_t *)param_buf->data; 14962 param->data_len = event->data_len; 14963 param->error_status = event->error_status; 14964 param->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 14965 wmi_handle, 14966 event->pdev_id); 14967 14968 return QDF_STATUS_SUCCESS; 14969 } 14970 14971 #ifdef WLAN_FEATURE_FIPS_BER_CCMGCM 14972 /** 14973 * extract_fips_extend_event_data_tlv() - extract fips event data 14974 * @wmi_handle: wmi handle 14975 * @param evt_buf: pointer to event buffer 14976 * @param param: pointer FIPS event params 14977 * 14978 * Return: 0 for success or error code 14979 */ 14980 static QDF_STATUS 14981 extract_fips_extend_event_data_tlv(wmi_unified_t wmi_handle, 14982 void *evt_buf, 14983 struct wmi_host_fips_extend_event_param 14984 *param) 14985 { 14986 WMI_PDEV_FIPS_EXTEND_EVENTID_param_tlvs *param_buf; 14987 wmi_pdev_fips_extend_event_fixed_param *event; 14988 14989 param_buf = (WMI_PDEV_FIPS_EXTEND_EVENTID_param_tlvs *)evt_buf; 14990 event = (wmi_pdev_fips_extend_event_fixed_param *)param_buf->fixed_param; 14991 14992 if (fips_conv_data_be(event->data_len, param_buf->data) != 14993 QDF_STATUS_SUCCESS) 14994 return QDF_STATUS_E_FAILURE; 14995 14996 param->data = (uint32_t *)param_buf->data; 14997 param->data_len = event->data_len; 14998 param->error_status = event->error_status; 14999 param->fips_cookie = event->fips_cookie; 15000 param->cmd_frag_idx = event->cmd_frag_idx; 15001 param->more_bit = event->more_bit; 15002 param->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 15003 wmi_handle, 15004 event->pdev_id); 15005 15006 return QDF_STATUS_SUCCESS; 15007 } 15008 #endif 15009 15010 #ifdef WLAN_FEATURE_DISA 15011 /** 15012 * extract_encrypt_decrypt_resp_event_tlv() - extract encrypt decrypt resp 15013 * params from event 15014 * @wmi_handle: wmi handle 15015 * @evt_buf: pointer to event buffer 15016 * @resp: Pointer to hold resp parameters 15017 * 15018 * Return: QDF_STATUS_SUCCESS for success or error code 15019 */ 15020 static QDF_STATUS 15021 extract_encrypt_decrypt_resp_event_tlv(wmi_unified_t wmi_handle, 15022 void *evt_buf, 15023 struct disa_encrypt_decrypt_resp_params 15024 *resp) 15025 { 15026 WMI_VDEV_ENCRYPT_DECRYPT_DATA_RESP_EVENTID_param_tlvs *param_buf; 15027 wmi_vdev_encrypt_decrypt_data_resp_event_fixed_param *data_event; 15028 15029 param_buf = evt_buf; 15030 if (!param_buf) { 15031 wmi_err("encrypt decrypt resp evt_buf is NULL"); 15032 return QDF_STATUS_E_INVAL; 15033 } 15034 15035 data_event = param_buf->fixed_param; 15036 15037 resp->vdev_id = data_event->vdev_id; 15038 resp->status = data_event->status; 15039 15040 if ((data_event->data_length > param_buf->num_enc80211_frame) || 15041 (data_event->data_length > WMI_SVC_MSG_MAX_SIZE - 15042 WMI_TLV_HDR_SIZE - sizeof(*data_event))) { 15043 wmi_err("FW msg data_len %d more than TLV hdr %d", 15044 data_event->data_length, 15045 param_buf->num_enc80211_frame); 15046 return QDF_STATUS_E_INVAL; 15047 } 15048 15049 resp->data_len = data_event->data_length; 15050 15051 if (resp->data_len) 15052 resp->data = (uint8_t *)param_buf->enc80211_frame; 15053 15054 return QDF_STATUS_SUCCESS; 15055 } 15056 #endif /* WLAN_FEATURE_DISA */ 15057 15058 static bool is_management_record_tlv(uint32_t cmd_id) 15059 { 15060 switch (cmd_id) { 15061 case WMI_MGMT_TX_SEND_CMDID: 15062 case WMI_MGMT_TX_COMPLETION_EVENTID: 15063 case WMI_OFFCHAN_DATA_TX_SEND_CMDID: 15064 case WMI_MGMT_RX_EVENTID: 15065 return true; 15066 default: 15067 return false; 15068 } 15069 } 15070 15071 static bool is_diag_event_tlv(uint32_t event_id) 15072 { 15073 if (WMI_DIAG_EVENTID == event_id) 15074 return true; 15075 15076 return false; 15077 } 15078 15079 static uint16_t wmi_tag_fw_hang_cmd(wmi_unified_t wmi_handle) 15080 { 15081 uint16_t tag = 0; 15082 15083 if (qdf_atomic_read(&wmi_handle->is_target_suspended)) { 15084 qdf_nofl_err("%s: Target is already suspended, Ignore FW Hang Command", 15085 __func__); 15086 return tag; 15087 } 15088 15089 if (wmi_handle->tag_crash_inject) 15090 tag = HTC_TX_PACKET_TAG_AUTO_PM; 15091 15092 wmi_handle->tag_crash_inject = false; 15093 return tag; 15094 } 15095 15096 /** 15097 * wmi_set_htc_tx_tag_tlv() - set HTC TX tag for WMI commands 15098 * @wmi_handle: WMI handle 15099 * @buf: WMI buffer 15100 * @cmd_id: WMI command Id 15101 * 15102 * Return htc_tx_tag 15103 */ 15104 static uint16_t wmi_set_htc_tx_tag_tlv(wmi_unified_t wmi_handle, 15105 wmi_buf_t buf, 15106 uint32_t cmd_id) 15107 { 15108 uint16_t htc_tx_tag = 0; 15109 15110 switch (cmd_id) { 15111 case WMI_WOW_ENABLE_CMDID: 15112 case WMI_PDEV_SUSPEND_CMDID: 15113 case WMI_WOW_HOSTWAKEUP_FROM_SLEEP_CMDID: 15114 case WMI_PDEV_RESUME_CMDID: 15115 case WMI_HB_SET_ENABLE_CMDID: 15116 case WMI_WOW_SET_ACTION_WAKE_UP_CMDID: 15117 #ifdef FEATURE_WLAN_D0WOW 15118 case WMI_D0_WOW_ENABLE_DISABLE_CMDID: 15119 #endif 15120 htc_tx_tag = HTC_TX_PACKET_TAG_AUTO_PM; 15121 break; 15122 case WMI_FORCE_FW_HANG_CMDID: 15123 htc_tx_tag = wmi_tag_fw_hang_cmd(wmi_handle); 15124 break; 15125 default: 15126 break; 15127 } 15128 15129 return htc_tx_tag; 15130 } 15131 15132 #ifdef CONFIG_BAND_6GHZ 15133 #ifdef CONFIG_REG_CLIENT 15134 /** 15135 * extract_ext_fcc_rules_from_wmi - extract fcc rules from WMI TLV 15136 * @num_fcc_rules: Number of FCC rules 15137 * @wmi_fcc_rule: WMI FCC rules TLV 15138 * 15139 * Return fcc_rule_ptr 15140 */ 15141 static struct cur_fcc_rule 15142 *extract_ext_fcc_rules_from_wmi(uint32_t num_fcc_rules, 15143 wmi_regulatory_fcc_rule_struct *wmi_fcc_rule) 15144 { 15145 struct cur_fcc_rule *fcc_rule_ptr; 15146 uint32_t count; 15147 15148 if (!wmi_fcc_rule) 15149 return NULL; 15150 15151 fcc_rule_ptr = qdf_mem_malloc(num_fcc_rules * 15152 sizeof(*fcc_rule_ptr)); 15153 if (!fcc_rule_ptr) 15154 return NULL; 15155 15156 for (count = 0; count < num_fcc_rules; count++) { 15157 fcc_rule_ptr[count].center_freq = 15158 WMI_REG_FCC_RULE_CHAN_FREQ_GET( 15159 wmi_fcc_rule[count].freq_info); 15160 fcc_rule_ptr[count].tx_power = 15161 WMI_REG_FCC_RULE_FCC_TX_POWER_GET( 15162 wmi_fcc_rule[count].freq_info); 15163 } 15164 15165 return fcc_rule_ptr; 15166 } 15167 #endif 15168 15169 static struct cur_reg_rule 15170 *create_ext_reg_rules_from_wmi(uint32_t num_reg_rules, 15171 wmi_regulatory_rule_ext_struct *wmi_reg_rule) 15172 { 15173 struct cur_reg_rule *reg_rule_ptr; 15174 uint32_t count; 15175 15176 if (!num_reg_rules) 15177 return NULL; 15178 15179 reg_rule_ptr = qdf_mem_malloc(num_reg_rules * 15180 sizeof(*reg_rule_ptr)); 15181 15182 if (!reg_rule_ptr) 15183 return NULL; 15184 15185 for (count = 0; count < num_reg_rules; count++) { 15186 reg_rule_ptr[count].start_freq = 15187 WMI_REG_RULE_START_FREQ_GET( 15188 wmi_reg_rule[count].freq_info); 15189 reg_rule_ptr[count].end_freq = 15190 WMI_REG_RULE_END_FREQ_GET( 15191 wmi_reg_rule[count].freq_info); 15192 reg_rule_ptr[count].max_bw = 15193 WMI_REG_RULE_MAX_BW_GET( 15194 wmi_reg_rule[count].bw_pwr_info); 15195 reg_rule_ptr[count].reg_power = 15196 WMI_REG_RULE_REG_POWER_GET( 15197 wmi_reg_rule[count].bw_pwr_info); 15198 reg_rule_ptr[count].ant_gain = 15199 WMI_REG_RULE_ANTENNA_GAIN_GET( 15200 wmi_reg_rule[count].bw_pwr_info); 15201 reg_rule_ptr[count].flags = 15202 WMI_REG_RULE_FLAGS_GET( 15203 wmi_reg_rule[count].flag_info); 15204 reg_rule_ptr[count].psd_flag = 15205 WMI_REG_RULE_PSD_FLAG_GET( 15206 wmi_reg_rule[count].psd_power_info); 15207 reg_rule_ptr[count].psd_eirp = 15208 WMI_REG_RULE_PSD_EIRP_GET( 15209 wmi_reg_rule[count].psd_power_info); 15210 } 15211 15212 return reg_rule_ptr; 15213 } 15214 #endif 15215 15216 static struct cur_reg_rule 15217 *create_reg_rules_from_wmi(uint32_t num_reg_rules, 15218 wmi_regulatory_rule_struct *wmi_reg_rule) 15219 { 15220 struct cur_reg_rule *reg_rule_ptr; 15221 uint32_t count; 15222 15223 if (!num_reg_rules) 15224 return NULL; 15225 15226 reg_rule_ptr = qdf_mem_malloc(num_reg_rules * 15227 sizeof(*reg_rule_ptr)); 15228 15229 if (!reg_rule_ptr) 15230 return NULL; 15231 15232 for (count = 0; count < num_reg_rules; count++) { 15233 reg_rule_ptr[count].start_freq = 15234 WMI_REG_RULE_START_FREQ_GET( 15235 wmi_reg_rule[count].freq_info); 15236 reg_rule_ptr[count].end_freq = 15237 WMI_REG_RULE_END_FREQ_GET( 15238 wmi_reg_rule[count].freq_info); 15239 reg_rule_ptr[count].max_bw = 15240 WMI_REG_RULE_MAX_BW_GET( 15241 wmi_reg_rule[count].bw_pwr_info); 15242 reg_rule_ptr[count].reg_power = 15243 WMI_REG_RULE_REG_POWER_GET( 15244 wmi_reg_rule[count].bw_pwr_info); 15245 reg_rule_ptr[count].ant_gain = 15246 WMI_REG_RULE_ANTENNA_GAIN_GET( 15247 wmi_reg_rule[count].bw_pwr_info); 15248 reg_rule_ptr[count].flags = 15249 WMI_REG_RULE_FLAGS_GET( 15250 wmi_reg_rule[count].flag_info); 15251 } 15252 15253 return reg_rule_ptr; 15254 } 15255 15256 static enum cc_setting_code wmi_reg_status_to_reg_status( 15257 WMI_REG_SET_CC_STATUS_CODE wmi_status_code) 15258 { 15259 if (wmi_status_code == WMI_REG_SET_CC_STATUS_PASS) 15260 return REG_SET_CC_STATUS_PASS; 15261 else if (wmi_status_code == WMI_REG_CURRENT_ALPHA2_NOT_FOUND) 15262 return REG_CURRENT_ALPHA2_NOT_FOUND; 15263 else if (wmi_status_code == WMI_REG_INIT_ALPHA2_NOT_FOUND) 15264 return REG_INIT_ALPHA2_NOT_FOUND; 15265 else if (wmi_status_code == WMI_REG_SET_CC_CHANGE_NOT_ALLOWED) 15266 return REG_SET_CC_CHANGE_NOT_ALLOWED; 15267 else if (wmi_status_code == WMI_REG_SET_CC_STATUS_NO_MEMORY) 15268 return REG_SET_CC_STATUS_NO_MEMORY; 15269 else if (wmi_status_code == WMI_REG_SET_CC_STATUS_FAIL) 15270 return REG_SET_CC_STATUS_FAIL; 15271 15272 wmi_debug("Unknown reg status code from WMI"); 15273 return REG_SET_CC_STATUS_FAIL; 15274 } 15275 15276 #ifdef CONFIG_BAND_6GHZ 15277 15278 #ifdef CONFIG_REG_CLIENT 15279 #define MAX_NUM_FCC_RULES 2 15280 15281 /** 15282 * extract_reg_fcc_rules_tlv - Extract reg fcc rules TLV 15283 * @param_buf - Pointer to WMI params TLV 15284 * @ext_chan_list_event_hdr - Pointer to REG CHAN LIST CC EXT EVENT Fixed 15285 * Params TLV 15286 * @ext_wmi_reg_rule - Pointer to REG CHAN LIST CC EXT EVENT Reg Rules TLV 15287 * @ext_wmi_chan_priority - Pointer to REG CHAN LIST CC EXT EVENT Chan 15288 * Priority TLV 15289 * @evt_buf - Pointer to REG CHAN LIST CC EXT EVENT event buffer 15290 * @reg_info - Pointer to Regulatory Info 15291 * @len - Length of REG CHAN LIST CC EXT EVENT buffer 15292 * 15293 * Return - QDF_STATUS 15294 */ 15295 static QDF_STATUS extract_reg_fcc_rules_tlv( 15296 WMI_REG_CHAN_LIST_CC_EXT_EVENTID_param_tlvs *param_buf, 15297 wmi_reg_chan_list_cc_event_ext_fixed_param *ext_chan_list_event_hdr, 15298 wmi_regulatory_rule_ext_struct *ext_wmi_reg_rule, 15299 wmi_regulatory_chan_priority_struct *ext_wmi_chan_priority, 15300 uint8_t *evt_buf, 15301 struct cur_regulatory_info *reg_info, 15302 uint32_t len) 15303 { 15304 int i; 15305 wmi_regulatory_fcc_rule_struct *ext_wmi_fcc_rule; 15306 15307 if (!param_buf) { 15308 wmi_err("invalid channel list event buf"); 15309 return QDF_STATUS_E_INVAL; 15310 } 15311 15312 reg_info->num_fcc_rules = 0; 15313 if (param_buf->reg_fcc_rule) { 15314 if (param_buf->num_reg_fcc_rule > MAX_NUM_FCC_RULES) { 15315 wmi_err("Number of fcc rules is greater than MAX_NUM_FCC_RULES"); 15316 return QDF_STATUS_E_INVAL; 15317 } 15318 15319 ext_wmi_fcc_rule = 15320 (wmi_regulatory_fcc_rule_struct *) 15321 ((uint8_t *)ext_chan_list_event_hdr + 15322 sizeof(wmi_reg_chan_list_cc_event_ext_fixed_param) + 15323 WMI_TLV_HDR_SIZE + 15324 sizeof(wmi_regulatory_rule_ext_struct) * 15325 param_buf->num_reg_rule_array + 15326 WMI_TLV_HDR_SIZE + 15327 sizeof(wmi_regulatory_chan_priority_struct) * 15328 param_buf->num_reg_chan_priority + 15329 WMI_TLV_HDR_SIZE); 15330 15331 reg_info->fcc_rules_ptr = extract_ext_fcc_rules_from_wmi( 15332 param_buf->num_reg_fcc_rule, 15333 ext_wmi_fcc_rule); 15334 15335 reg_info->num_fcc_rules = param_buf->num_reg_fcc_rule; 15336 } 15337 15338 if (reg_info->fcc_rules_ptr) { 15339 for (i = 0; i < reg_info->num_fcc_rules; i++) { 15340 wmi_debug("FCC rule %d center_freq %d tx_power %d", 15341 i, reg_info->fcc_rules_ptr[i].center_freq, 15342 reg_info->fcc_rules_ptr[i].tx_power); 15343 } 15344 } 15345 return QDF_STATUS_SUCCESS; 15346 } 15347 #else 15348 static QDF_STATUS extract_reg_fcc_rules_tlv( 15349 WMI_REG_CHAN_LIST_CC_EXT_EVENTID_param_tlvs *param_buf, 15350 wmi_reg_chan_list_cc_event_ext_fixed_param *ext_chan_list_event_hdr, 15351 wmi_regulatory_rule_ext_struct *ext_wmi_reg_rule, 15352 wmi_regulatory_chan_priority_struct *ext_wmi_chan_priority, 15353 uint8_t *evt_buf, 15354 struct cur_regulatory_info *reg_info, 15355 uint32_t len) 15356 { 15357 return QDF_STATUS_SUCCESS; 15358 } 15359 #endif 15360 15361 static QDF_STATUS extract_reg_chan_list_ext_update_event_tlv( 15362 wmi_unified_t wmi_handle, uint8_t *evt_buf, 15363 struct cur_regulatory_info *reg_info, uint32_t len) 15364 { 15365 uint32_t i, j, k; 15366 WMI_REG_CHAN_LIST_CC_EXT_EVENTID_param_tlvs *param_buf; 15367 wmi_reg_chan_list_cc_event_ext_fixed_param *ext_chan_list_event_hdr; 15368 wmi_regulatory_rule_ext_struct *ext_wmi_reg_rule; 15369 wmi_regulatory_chan_priority_struct *ext_wmi_chan_priority; 15370 uint32_t num_2g_reg_rules, num_5g_reg_rules; 15371 uint32_t num_6g_reg_rules_ap[REG_CURRENT_MAX_AP_TYPE]; 15372 uint32_t *num_6g_reg_rules_client[REG_CURRENT_MAX_AP_TYPE]; 15373 uint32_t total_reg_rules = 0; 15374 QDF_STATUS status; 15375 15376 param_buf = (WMI_REG_CHAN_LIST_CC_EXT_EVENTID_param_tlvs *)evt_buf; 15377 if (!param_buf) { 15378 wmi_err("invalid channel list event buf"); 15379 return QDF_STATUS_E_FAILURE; 15380 } 15381 15382 ext_chan_list_event_hdr = param_buf->fixed_param; 15383 ext_wmi_chan_priority = param_buf->reg_chan_priority; 15384 15385 if (ext_wmi_chan_priority) 15386 reg_info->reg_6g_thresh_priority_freq = 15387 WMI_GET_BITS(ext_wmi_chan_priority->freq_info, 0, 16); 15388 reg_info->num_2g_reg_rules = ext_chan_list_event_hdr->num_2g_reg_rules; 15389 reg_info->num_5g_reg_rules = ext_chan_list_event_hdr->num_5g_reg_rules; 15390 reg_info->num_6g_reg_rules_ap[REG_STANDARD_POWER_AP] = 15391 ext_chan_list_event_hdr->num_6g_reg_rules_ap_sp; 15392 reg_info->num_6g_reg_rules_ap[REG_INDOOR_AP] = 15393 ext_chan_list_event_hdr->num_6g_reg_rules_ap_lpi; 15394 reg_info->num_6g_reg_rules_ap[REG_VERY_LOW_POWER_AP] = 15395 ext_chan_list_event_hdr->num_6g_reg_rules_ap_vlp; 15396 15397 wmi_debug("num reg rules from fw"); 15398 wmi_debug("AP SP %d, LPI %d, VLP %d", 15399 reg_info->num_6g_reg_rules_ap[REG_STANDARD_POWER_AP], 15400 reg_info->num_6g_reg_rules_ap[REG_INDOOR_AP], 15401 reg_info->num_6g_reg_rules_ap[REG_VERY_LOW_POWER_AP]); 15402 15403 for (i = 0; i < REG_MAX_CLIENT_TYPE; i++) { 15404 reg_info->num_6g_reg_rules_client[REG_STANDARD_POWER_AP][i] = 15405 ext_chan_list_event_hdr->num_6g_reg_rules_client_sp[i]; 15406 reg_info->num_6g_reg_rules_client[REG_INDOOR_AP][i] = 15407 ext_chan_list_event_hdr->num_6g_reg_rules_client_lpi[i]; 15408 reg_info->num_6g_reg_rules_client[REG_VERY_LOW_POWER_AP][i] = 15409 ext_chan_list_event_hdr->num_6g_reg_rules_client_vlp[i]; 15410 wmi_debug("client %d SP %d, LPI %d, VLP %d", i, 15411 ext_chan_list_event_hdr->num_6g_reg_rules_client_sp[i], 15412 ext_chan_list_event_hdr->num_6g_reg_rules_client_lpi[i], 15413 ext_chan_list_event_hdr->num_6g_reg_rules_client_vlp[i]); 15414 } 15415 15416 num_2g_reg_rules = reg_info->num_2g_reg_rules; 15417 total_reg_rules += num_2g_reg_rules; 15418 num_5g_reg_rules = reg_info->num_5g_reg_rules; 15419 total_reg_rules += num_5g_reg_rules; 15420 for (i = 0; i < REG_CURRENT_MAX_AP_TYPE; i++) { 15421 num_6g_reg_rules_ap[i] = reg_info->num_6g_reg_rules_ap[i]; 15422 if (num_6g_reg_rules_ap[i] > MAX_6G_REG_RULES) { 15423 wmi_err_rl("Invalid num_6g_reg_rules_ap: %u", 15424 num_6g_reg_rules_ap[i]); 15425 return QDF_STATUS_E_FAILURE; 15426 } 15427 total_reg_rules += num_6g_reg_rules_ap[i]; 15428 num_6g_reg_rules_client[i] = 15429 reg_info->num_6g_reg_rules_client[i]; 15430 } 15431 15432 for (i = 0; i < REG_MAX_CLIENT_TYPE; i++) { 15433 total_reg_rules += 15434 num_6g_reg_rules_client[REG_STANDARD_POWER_AP][i]; 15435 total_reg_rules += num_6g_reg_rules_client[REG_INDOOR_AP][i]; 15436 total_reg_rules += 15437 num_6g_reg_rules_client[REG_VERY_LOW_POWER_AP][i]; 15438 if ((num_6g_reg_rules_client[REG_STANDARD_POWER_AP][i] > 15439 MAX_6G_REG_RULES) || 15440 (num_6g_reg_rules_client[REG_INDOOR_AP][i] > 15441 MAX_6G_REG_RULES) || 15442 (num_6g_reg_rules_client[REG_VERY_LOW_POWER_AP][i] > 15443 MAX_6G_REG_RULES)) { 15444 wmi_err_rl("Invalid num_6g_reg_rules_client_sp: %u, num_6g_reg_rules_client_lpi: %u, num_6g_reg_rules_client_vlp: %u, client %d", 15445 num_6g_reg_rules_client[REG_STANDARD_POWER_AP][i], 15446 num_6g_reg_rules_client[REG_INDOOR_AP][i], 15447 num_6g_reg_rules_client[REG_VERY_LOW_POWER_AP][i], 15448 i); 15449 return QDF_STATUS_E_FAILURE; 15450 } 15451 } 15452 15453 if (total_reg_rules != param_buf->num_reg_rule_array) { 15454 wmi_err_rl("Total reg rules %u does not match event params num reg rule %u", 15455 total_reg_rules, param_buf->num_reg_rule_array); 15456 return QDF_STATUS_E_FAILURE; 15457 } 15458 15459 if ((num_2g_reg_rules > MAX_REG_RULES) || 15460 (num_5g_reg_rules > MAX_REG_RULES)) { 15461 wmi_err_rl("Invalid num_2g_reg_rules: %u, num_5g_reg_rules: %u", 15462 num_2g_reg_rules, num_5g_reg_rules); 15463 return QDF_STATUS_E_FAILURE; 15464 } 15465 15466 if ((num_6g_reg_rules_ap[REG_STANDARD_POWER_AP] > MAX_6G_REG_RULES) || 15467 (num_6g_reg_rules_ap[REG_INDOOR_AP] > MAX_6G_REG_RULES) || 15468 (num_6g_reg_rules_ap[REG_VERY_LOW_POWER_AP] > MAX_6G_REG_RULES)) { 15469 wmi_err_rl("Invalid num_6g_reg_rules_ap_sp: %u, num_6g_reg_rules_ap_lpi: %u, num_6g_reg_rules_ap_vlp: %u", 15470 num_6g_reg_rules_ap[REG_STANDARD_POWER_AP], 15471 num_6g_reg_rules_ap[REG_INDOOR_AP], 15472 num_6g_reg_rules_ap[REG_VERY_LOW_POWER_AP]); 15473 return QDF_STATUS_E_FAILURE; 15474 } 15475 15476 if (param_buf->num_reg_rule_array > 15477 (WMI_SVC_MSG_MAX_SIZE - sizeof(*ext_chan_list_event_hdr)) / 15478 sizeof(*ext_wmi_reg_rule)) { 15479 wmi_err_rl("Invalid ext_num_reg_rule_array: %u", 15480 param_buf->num_reg_rule_array); 15481 return QDF_STATUS_E_FAILURE; 15482 } 15483 15484 qdf_mem_copy(reg_info->alpha2, &ext_chan_list_event_hdr->alpha2, 15485 REG_ALPHA2_LEN); 15486 reg_info->dfs_region = ext_chan_list_event_hdr->dfs_region; 15487 reg_info->phybitmap = convert_phybitmap_tlv( 15488 ext_chan_list_event_hdr->phybitmap); 15489 reg_info->offload_enabled = true; 15490 reg_info->num_phy = ext_chan_list_event_hdr->num_phy; 15491 reg_info->phy_id = wmi_handle->ops->convert_phy_id_target_to_host( 15492 wmi_handle, ext_chan_list_event_hdr->phy_id); 15493 reg_info->ctry_code = ext_chan_list_event_hdr->country_id; 15494 reg_info->reg_dmn_pair = ext_chan_list_event_hdr->domain_code; 15495 15496 reg_info->status_code = 15497 wmi_reg_status_to_reg_status(ext_chan_list_event_hdr-> 15498 status_code); 15499 15500 reg_info->min_bw_2g = ext_chan_list_event_hdr->min_bw_2g; 15501 reg_info->max_bw_2g = ext_chan_list_event_hdr->max_bw_2g; 15502 reg_info->min_bw_5g = ext_chan_list_event_hdr->min_bw_5g; 15503 reg_info->max_bw_5g = ext_chan_list_event_hdr->max_bw_5g; 15504 reg_info->min_bw_6g_ap[REG_STANDARD_POWER_AP] = 15505 ext_chan_list_event_hdr->min_bw_6g_ap_sp; 15506 reg_info->max_bw_6g_ap[REG_STANDARD_POWER_AP] = 15507 ext_chan_list_event_hdr->max_bw_6g_ap_sp; 15508 reg_info->min_bw_6g_ap[REG_INDOOR_AP] = 15509 ext_chan_list_event_hdr->min_bw_6g_ap_lpi; 15510 reg_info->max_bw_6g_ap[REG_INDOOR_AP] = 15511 ext_chan_list_event_hdr->max_bw_6g_ap_lpi; 15512 reg_info->min_bw_6g_ap[REG_VERY_LOW_POWER_AP] = 15513 ext_chan_list_event_hdr->min_bw_6g_ap_vlp; 15514 reg_info->max_bw_6g_ap[REG_VERY_LOW_POWER_AP] = 15515 ext_chan_list_event_hdr->max_bw_6g_ap_vlp; 15516 15517 for (i = 0; i < REG_MAX_CLIENT_TYPE; i++) { 15518 reg_info->min_bw_6g_client[REG_STANDARD_POWER_AP][i] = 15519 ext_chan_list_event_hdr->min_bw_6g_client_sp[i]; 15520 reg_info->max_bw_6g_client[REG_STANDARD_POWER_AP][i] = 15521 ext_chan_list_event_hdr->max_bw_6g_client_sp[i]; 15522 reg_info->min_bw_6g_client[REG_INDOOR_AP][i] = 15523 ext_chan_list_event_hdr->min_bw_6g_client_lpi[i]; 15524 reg_info->max_bw_6g_client[REG_INDOOR_AP][i] = 15525 ext_chan_list_event_hdr->max_bw_6g_client_lpi[i]; 15526 reg_info->min_bw_6g_client[REG_VERY_LOW_POWER_AP][i] = 15527 ext_chan_list_event_hdr->min_bw_6g_client_vlp[i]; 15528 reg_info->max_bw_6g_client[REG_VERY_LOW_POWER_AP][i] = 15529 ext_chan_list_event_hdr->max_bw_6g_client_vlp[i]; 15530 } 15531 15532 wmi_debug("num_phys = %u and phy_id = %u", 15533 reg_info->num_phy, reg_info->phy_id); 15534 15535 wmi_debug("cc %s dfs %d BW: min_2g %d max_2g %d min_5g %d max_5g %d", 15536 reg_info->alpha2, reg_info->dfs_region, reg_info->min_bw_2g, 15537 reg_info->max_bw_2g, reg_info->min_bw_5g, 15538 reg_info->max_bw_5g); 15539 15540 wmi_debug("min_bw_6g_ap_sp %d max_bw_6g_ap_sp %d min_bw_6g_ap_lpi %d max_bw_6g_ap_lpi %d min_bw_6g_ap_vlp %d max_bw_6g_ap_vlp %d", 15541 reg_info->min_bw_6g_ap[REG_STANDARD_POWER_AP], 15542 reg_info->max_bw_6g_ap[REG_STANDARD_POWER_AP], 15543 reg_info->min_bw_6g_ap[REG_INDOOR_AP], 15544 reg_info->max_bw_6g_ap[REG_INDOOR_AP], 15545 reg_info->min_bw_6g_ap[REG_VERY_LOW_POWER_AP], 15546 reg_info->max_bw_6g_ap[REG_VERY_LOW_POWER_AP]); 15547 15548 wmi_debug("min_bw_6g_def_cli_sp %d max_bw_6g_def_cli_sp %d min_bw_6g_def_cli_lpi %d max_bw_6g_def_cli_lpi %d min_bw_6g_def_cli_vlp %d max_bw_6g_def_cli_vlp %d", 15549 reg_info->min_bw_6g_client[REG_STANDARD_POWER_AP][REG_DEFAULT_CLIENT], 15550 reg_info->max_bw_6g_client[REG_STANDARD_POWER_AP][REG_DEFAULT_CLIENT], 15551 reg_info->min_bw_6g_client[REG_INDOOR_AP][REG_DEFAULT_CLIENT], 15552 reg_info->max_bw_6g_client[REG_INDOOR_AP][REG_DEFAULT_CLIENT], 15553 reg_info->min_bw_6g_client[REG_VERY_LOW_POWER_AP][REG_DEFAULT_CLIENT], 15554 reg_info->max_bw_6g_client[REG_VERY_LOW_POWER_AP][REG_DEFAULT_CLIENT]); 15555 15556 wmi_debug("min_bw_6g_sub_client_sp %d max_bw_6g_sub_client_sp %d min_bw_6g_sub_client_lpi %d max_bw_6g_sub_client_lpi %d min_bw_6g_sub_client_vlp %d max_bw_6g_sub_client_vlp %d", 15557 reg_info->min_bw_6g_client[REG_STANDARD_POWER_AP][REG_SUBORDINATE_CLIENT], 15558 reg_info->max_bw_6g_client[REG_STANDARD_POWER_AP][REG_SUBORDINATE_CLIENT], 15559 reg_info->min_bw_6g_client[REG_INDOOR_AP][REG_SUBORDINATE_CLIENT], 15560 reg_info->max_bw_6g_client[REG_INDOOR_AP][REG_SUBORDINATE_CLIENT], 15561 reg_info->min_bw_6g_client[REG_VERY_LOW_POWER_AP][REG_SUBORDINATE_CLIENT], 15562 reg_info->max_bw_6g_client[REG_VERY_LOW_POWER_AP][REG_SUBORDINATE_CLIENT]); 15563 15564 wmi_debug("num_2g_reg_rules %d num_5g_reg_rules %d", 15565 num_2g_reg_rules, num_5g_reg_rules); 15566 15567 wmi_debug("num_6g_ap_sp_reg_rules %d num_6g_ap_lpi_reg_rules %d num_6g_ap_vlp_reg_rules %d", 15568 reg_info->num_6g_reg_rules_ap[REG_STANDARD_POWER_AP], 15569 reg_info->num_6g_reg_rules_ap[REG_INDOOR_AP], 15570 reg_info->num_6g_reg_rules_ap[REG_VERY_LOW_POWER_AP]); 15571 15572 wmi_debug("num_6g_def_cli_sp_reg_rules %d num_6g_def_cli_lpi_reg_rules %d num_6g_def_cli_vlp_reg_rules %d", 15573 reg_info->num_6g_reg_rules_client[REG_STANDARD_POWER_AP][REG_DEFAULT_CLIENT], 15574 reg_info->num_6g_reg_rules_client[REG_INDOOR_AP][REG_DEFAULT_CLIENT], 15575 reg_info->num_6g_reg_rules_client[REG_VERY_LOW_POWER_AP][REG_DEFAULT_CLIENT]); 15576 15577 wmi_debug("num_6g_sub_cli_sp_reg_rules %d num_6g_sub_cli_lpi_reg_rules %d num_6g_sub_cli_vlp_reg_rules %d", 15578 reg_info->num_6g_reg_rules_client[REG_STANDARD_POWER_AP][REG_SUBORDINATE_CLIENT], 15579 reg_info->num_6g_reg_rules_client[REG_INDOOR_AP][REG_SUBORDINATE_CLIENT], 15580 reg_info->num_6g_reg_rules_client[REG_VERY_LOW_POWER_AP][REG_SUBORDINATE_CLIENT]); 15581 15582 ext_wmi_reg_rule = 15583 (wmi_regulatory_rule_ext_struct *) 15584 ((uint8_t *)ext_chan_list_event_hdr + 15585 sizeof(wmi_reg_chan_list_cc_event_ext_fixed_param) + 15586 WMI_TLV_HDR_SIZE); 15587 reg_info->reg_rules_2g_ptr = 15588 create_ext_reg_rules_from_wmi(num_2g_reg_rules, 15589 ext_wmi_reg_rule); 15590 ext_wmi_reg_rule += num_2g_reg_rules; 15591 for (i = 0; i < num_2g_reg_rules; i++) { 15592 if (!reg_info->reg_rules_2g_ptr) 15593 break; 15594 wmi_debug("2g rule %d start freq %d end freq %d flags %d", 15595 i, reg_info->reg_rules_2g_ptr[i].start_freq, 15596 reg_info->reg_rules_2g_ptr[i].end_freq, 15597 reg_info->reg_rules_2g_ptr[i].flags); 15598 } 15599 reg_info->reg_rules_5g_ptr = 15600 create_ext_reg_rules_from_wmi(num_5g_reg_rules, 15601 ext_wmi_reg_rule); 15602 ext_wmi_reg_rule += num_5g_reg_rules; 15603 for (i = 0; i < num_5g_reg_rules; i++) { 15604 if (!reg_info->reg_rules_5g_ptr) 15605 break; 15606 wmi_debug("5g rule %d start freq %d end freq %d flags %d", 15607 i, reg_info->reg_rules_5g_ptr[i].start_freq, 15608 reg_info->reg_rules_5g_ptr[i].end_freq, 15609 reg_info->reg_rules_5g_ptr[i].flags); 15610 } 15611 15612 for (i = 0; i < REG_CURRENT_MAX_AP_TYPE; i++) { 15613 reg_info->reg_rules_6g_ap_ptr[i] = 15614 create_ext_reg_rules_from_wmi(num_6g_reg_rules_ap[i], 15615 ext_wmi_reg_rule); 15616 15617 ext_wmi_reg_rule += num_6g_reg_rules_ap[i]; 15618 for (j = 0; j < num_6g_reg_rules_ap[i]; j++) { 15619 if (!reg_info->reg_rules_6g_ap_ptr[i]) 15620 break; 15621 wmi_debug("6g pwr type %d AP rule %d start freq %d end freq %d flags %d", 15622 i, j, 15623 reg_info->reg_rules_6g_ap_ptr[i][j].start_freq, 15624 reg_info->reg_rules_6g_ap_ptr[i][j].end_freq, 15625 reg_info->reg_rules_6g_ap_ptr[i][j].flags); 15626 } 15627 } 15628 15629 for (j = 0; j < REG_CURRENT_MAX_AP_TYPE; j++) { 15630 for (i = 0; i < REG_MAX_CLIENT_TYPE; i++) { 15631 reg_info->reg_rules_6g_client_ptr[j][i] = 15632 create_ext_reg_rules_from_wmi( 15633 num_6g_reg_rules_client[j][i], 15634 ext_wmi_reg_rule); 15635 15636 ext_wmi_reg_rule += num_6g_reg_rules_client[j][i]; 15637 for (k = 0; k < num_6g_reg_rules_client[j][i]; k++) { 15638 if (!reg_info->reg_rules_6g_client_ptr[j][i]) 15639 break; 15640 wmi_debug("6g pwr type %d cli type %d CLI rule %d start freq %d end freq %d flags %d", 15641 j, i, k, 15642 reg_info->reg_rules_6g_client_ptr[j][i][k].start_freq, 15643 reg_info->reg_rules_6g_client_ptr[j][i][k].end_freq, 15644 reg_info->reg_rules_6g_client_ptr[j][i][k].flags); 15645 } 15646 } 15647 } 15648 15649 reg_info->client_type = ext_chan_list_event_hdr->client_type; 15650 reg_info->rnr_tpe_usable = ext_chan_list_event_hdr->rnr_tpe_usable; 15651 reg_info->unspecified_ap_usable = 15652 ext_chan_list_event_hdr->unspecified_ap_usable; 15653 reg_info->domain_code_6g_ap[REG_STANDARD_POWER_AP] = 15654 ext_chan_list_event_hdr->domain_code_6g_ap_sp; 15655 reg_info->domain_code_6g_ap[REG_INDOOR_AP] = 15656 ext_chan_list_event_hdr->domain_code_6g_ap_lpi; 15657 reg_info->domain_code_6g_ap[REG_VERY_LOW_POWER_AP] = 15658 ext_chan_list_event_hdr->domain_code_6g_ap_vlp; 15659 15660 wmi_debug("client type %d", reg_info->client_type); 15661 wmi_debug("RNR TPE usable %d", reg_info->rnr_tpe_usable); 15662 wmi_debug("unspecified AP usable %d", reg_info->unspecified_ap_usable); 15663 wmi_debug("domain code AP SP %d, LPI %d, VLP %d", 15664 reg_info->domain_code_6g_ap[REG_STANDARD_POWER_AP], 15665 reg_info->domain_code_6g_ap[REG_INDOOR_AP], 15666 reg_info->domain_code_6g_ap[REG_VERY_LOW_POWER_AP]); 15667 15668 for (i = 0; i < REG_MAX_CLIENT_TYPE; i++) { 15669 reg_info->domain_code_6g_client[REG_STANDARD_POWER_AP][i] = 15670 ext_chan_list_event_hdr->domain_code_6g_client_sp[i]; 15671 reg_info->domain_code_6g_client[REG_INDOOR_AP][i] = 15672 ext_chan_list_event_hdr->domain_code_6g_client_lpi[i]; 15673 reg_info->domain_code_6g_client[REG_VERY_LOW_POWER_AP][i] = 15674 ext_chan_list_event_hdr->domain_code_6g_client_vlp[i]; 15675 wmi_debug("domain code client %d SP %d, LPI %d, VLP %d", i, 15676 reg_info->domain_code_6g_client[REG_STANDARD_POWER_AP][i], 15677 reg_info->domain_code_6g_client[REG_INDOOR_AP][i], 15678 reg_info->domain_code_6g_client[REG_VERY_LOW_POWER_AP][i]); 15679 } 15680 15681 reg_info->domain_code_6g_super_id = 15682 ext_chan_list_event_hdr->domain_code_6g_super_id; 15683 15684 status = extract_reg_fcc_rules_tlv(param_buf, ext_chan_list_event_hdr, 15685 ext_wmi_reg_rule, ext_wmi_chan_priority, 15686 evt_buf, reg_info, len); 15687 if (status != QDF_STATUS_SUCCESS) 15688 return status; 15689 15690 wmi_debug("processed regulatory extended channel list"); 15691 15692 return QDF_STATUS_SUCCESS; 15693 } 15694 15695 #ifdef CONFIG_AFC_SUPPORT 15696 /** 15697 * copy_afc_chan_eirp_info() - Copy the channel EIRP object from 15698 * chan_eirp_power_info_hdr to the internal buffer chan_eirp_info. Since the 15699 * cfi and eirp is continuously filled in chan_eirp_power_info_hdr, there is 15700 * an index pointer required to store the current index of 15701 * chan_eirp_power_info_hdr, to fill into the chan_eirp_info object. 15702 * @chan_eirp_info: pointer to chan_eirp_info 15703 * @num_chans: Number of channels 15704 * @chan_eirp_power_info_hdr: Pointer to chan_eirp_power_info_hdr 15705 * @index: Pointer to index 15706 * 15707 * Return: void 15708 */ 15709 static void 15710 copy_afc_chan_eirp_info(struct chan_eirp_obj *chan_eirp_info, 15711 uint8_t num_chans, 15712 wmi_afc_chan_eirp_power_info *chan_eirp_power_info_hdr, 15713 uint8_t *index) 15714 { 15715 uint8_t chan_idx; 15716 15717 for (chan_idx = 0; chan_idx < num_chans; chan_idx++, (*index)++) { 15718 chan_eirp_info[chan_idx].cfi = 15719 chan_eirp_power_info_hdr[*index].channel_cfi; 15720 chan_eirp_info[chan_idx].eirp_power = 15721 chan_eirp_power_info_hdr[*index].eirp_pwr; 15722 wmi_debug("Chan idx = %d chan freq idx = %d EIRP power = %d", 15723 chan_idx, 15724 chan_eirp_info[chan_idx].cfi, 15725 chan_eirp_info[chan_idx].eirp_power); 15726 } 15727 } 15728 15729 /** 15730 * copy_afc_chan_obj_info() - Copy the channel object from channel_info_hdr to 15731 * to the internal buffer afc_chan_info. 15732 * @afc_chan_info: pointer to afc_chan_info 15733 * @num_chan_objs: Number of channel objects 15734 * @channel_info_hdr: Pointer to channel_info_hdr 15735 * @chan_eirp_power_info_hdr: Pointer to chan_eirp_power_info_hdr 15736 * 15737 * Return: void 15738 */ 15739 static void 15740 copy_afc_chan_obj_info(struct afc_chan_obj *afc_chan_info, 15741 uint8_t num_chan_objs, 15742 wmi_6g_afc_channel_info *channel_info_hdr, 15743 wmi_afc_chan_eirp_power_info *chan_eirp_power_info_hdr) 15744 { 15745 uint8_t count; 15746 uint8_t src_pwr_index = 0; 15747 15748 for (count = 0; count < num_chan_objs; count++) { 15749 afc_chan_info[count].global_opclass = 15750 channel_info_hdr[count].global_operating_class; 15751 afc_chan_info[count].num_chans = 15752 channel_info_hdr[count].num_channels; 15753 wmi_debug("Chan object count = %d global opclasss = %d", 15754 count, 15755 afc_chan_info[count].global_opclass); 15756 wmi_debug("Number of Channel EIRP objects = %d", 15757 afc_chan_info[count].num_chans); 15758 15759 if (afc_chan_info[count].num_chans > 0) { 15760 struct chan_eirp_obj *chan_eirp_info; 15761 15762 chan_eirp_info = 15763 qdf_mem_malloc(afc_chan_info[count].num_chans * 15764 sizeof(*chan_eirp_info)); 15765 15766 if (!chan_eirp_info) 15767 return; 15768 15769 copy_afc_chan_eirp_info(chan_eirp_info, 15770 afc_chan_info[count].num_chans, 15771 chan_eirp_power_info_hdr, 15772 &src_pwr_index); 15773 afc_chan_info[count].chan_eirp_info = chan_eirp_info; 15774 } else { 15775 wmi_err("Number of channels is zero in object idx %d", 15776 count); 15777 } 15778 } 15779 } 15780 15781 static void copy_afc_freq_obj_info(struct afc_freq_obj *afc_freq_info, 15782 uint8_t num_freq_objs, 15783 wmi_6g_afc_frequency_info *freq_info_hdr) 15784 { 15785 uint8_t count; 15786 15787 for (count = 0; count < num_freq_objs; count++) { 15788 afc_freq_info[count].low_freq = 15789 WMI_REG_RULE_START_FREQ_GET(freq_info_hdr[count].freq_info); 15790 afc_freq_info[count].high_freq = 15791 WMI_REG_RULE_END_FREQ_GET(freq_info_hdr[count].freq_info); 15792 afc_freq_info[count].max_psd = 15793 freq_info_hdr[count].psd_power_info; 15794 wmi_debug("count = %d low_freq = %d high_freq = %d max_psd = %d", 15795 count, 15796 afc_freq_info[count].low_freq, 15797 afc_freq_info[count].high_freq, 15798 afc_freq_info[count].max_psd); 15799 } 15800 } 15801 15802 /** 15803 * copy_afc_event_fixed_hdr_power_info() - Copy the fixed header portion of 15804 * the power event info from the WMI AFC event buffer to the internal buffer 15805 * power_info. 15806 * @power_info: pointer to power_info 15807 * @afc_power_event_hdr: pointer to afc_power_event_hdr 15808 * 15809 * Return: void 15810 */ 15811 static void 15812 copy_afc_event_fixed_hdr_power_info( 15813 struct reg_fw_afc_power_event *power_info, 15814 wmi_afc_power_event_param *afc_power_event_hdr) 15815 { 15816 power_info->fw_status_code = afc_power_event_hdr->fw_status_code; 15817 power_info->resp_id = afc_power_event_hdr->resp_id; 15818 power_info->serv_resp_code = afc_power_event_hdr->afc_serv_resp_code; 15819 power_info->afc_wfa_version = 15820 WMI_AFC_WFA_MINOR_VERSION_GET(afc_power_event_hdr->afc_wfa_version); 15821 power_info->afc_wfa_version |= 15822 WMI_AFC_WFA_MAJOR_VERSION_GET(afc_power_event_hdr->afc_wfa_version); 15823 15824 power_info->avail_exp_time_d = 15825 WMI_AVAIL_EXPIRY_TIME_DAY_GET(afc_power_event_hdr->avail_exp_time_d); 15826 power_info->avail_exp_time_d |= 15827 WMI_AVAIL_EXPIRY_TIME_MONTH_GET(afc_power_event_hdr->avail_exp_time_d); 15828 power_info->avail_exp_time_d |= 15829 WMI_AVAIL_EXPIRY_TIME_YEAR_GET(afc_power_event_hdr->avail_exp_time_d); 15830 15831 power_info->avail_exp_time_t = 15832 WMI_AVAIL_EXPIRY_TIME_SEC_GET(afc_power_event_hdr->avail_exp_time_t); 15833 power_info->avail_exp_time_t |= 15834 WMI_AVAIL_EXPIRY_TIME_MINUTE_GET(afc_power_event_hdr->avail_exp_time_t); 15835 power_info->avail_exp_time_t |= 15836 WMI_AVAIL_EXPIRY_TIME_HOUR_GET(afc_power_event_hdr->avail_exp_time_t); 15837 wmi_debug("FW status = %d resp_id = %d serv_resp_code = %d", 15838 power_info->fw_status_code, 15839 power_info->resp_id, 15840 power_info->serv_resp_code); 15841 wmi_debug("AFC version = %u exp_date = %u exp_time = %u", 15842 power_info->afc_wfa_version, 15843 power_info->avail_exp_time_d, 15844 power_info->avail_exp_time_t); 15845 } 15846 15847 /** 15848 * copy_power_event() - Copy the power event parameters from the AFC event 15849 * buffer to the power_info within the afc_info. 15850 * @afc_info: pointer to afc_info 15851 * @param_buf: pointer to param_buf 15852 * 15853 * Return: void 15854 */ 15855 static void copy_power_event(struct afc_regulatory_info *afc_info, 15856 WMI_AFC_EVENTID_param_tlvs *param_buf) 15857 { 15858 struct reg_fw_afc_power_event *power_info; 15859 wmi_afc_power_event_param *afc_power_event_hdr; 15860 struct afc_freq_obj *afc_freq_info; 15861 15862 power_info = qdf_mem_malloc(sizeof(*power_info)); 15863 15864 if (!power_info) 15865 return; 15866 15867 afc_power_event_hdr = param_buf->afc_power_event_param; 15868 copy_afc_event_fixed_hdr_power_info(power_info, afc_power_event_hdr); 15869 afc_info->power_info = power_info; 15870 15871 power_info->num_freq_objs = param_buf->num_freq_info_array; 15872 wmi_debug("Number of frequency objects = %d", 15873 power_info->num_freq_objs); 15874 if (power_info->num_freq_objs > 0) { 15875 wmi_6g_afc_frequency_info *freq_info_hdr; 15876 15877 freq_info_hdr = param_buf->freq_info_array; 15878 afc_freq_info = qdf_mem_malloc(power_info->num_freq_objs * 15879 sizeof(*afc_freq_info)); 15880 15881 if (!afc_freq_info) 15882 return; 15883 15884 copy_afc_freq_obj_info(afc_freq_info, power_info->num_freq_objs, 15885 freq_info_hdr); 15886 power_info->afc_freq_info = afc_freq_info; 15887 } else { 15888 wmi_err("Number of frequency objects is zero"); 15889 } 15890 15891 power_info->num_chan_objs = param_buf->num_channel_info_array; 15892 wmi_debug("Number of channel objects = %d", power_info->num_chan_objs); 15893 if (power_info->num_chan_objs > 0) { 15894 struct afc_chan_obj *afc_chan_info; 15895 wmi_6g_afc_channel_info *channel_info_hdr; 15896 15897 channel_info_hdr = param_buf->channel_info_array; 15898 afc_chan_info = qdf_mem_malloc(power_info->num_chan_objs * 15899 sizeof(*afc_chan_info)); 15900 15901 if (!afc_chan_info) 15902 return; 15903 15904 copy_afc_chan_obj_info(afc_chan_info, 15905 power_info->num_chan_objs, 15906 channel_info_hdr, 15907 param_buf->chan_eirp_power_info_array); 15908 power_info->afc_chan_info = afc_chan_info; 15909 } else { 15910 wmi_err("Number of channel objects is zero"); 15911 } 15912 } 15913 15914 static void copy_expiry_event(struct afc_regulatory_info *afc_info, 15915 WMI_AFC_EVENTID_param_tlvs *param_buf) 15916 { 15917 struct reg_afc_expiry_event *expiry_info; 15918 15919 expiry_info = qdf_mem_malloc(sizeof(*expiry_info)); 15920 15921 if (!expiry_info) 15922 return; 15923 15924 expiry_info->request_id = 15925 param_buf->expiry_event_param->request_id; 15926 expiry_info->event_subtype = 15927 param_buf->expiry_event_param->event_subtype; 15928 wmi_debug("Event subtype %d request ID %d", 15929 expiry_info->event_subtype, 15930 expiry_info->request_id); 15931 afc_info->expiry_info = expiry_info; 15932 } 15933 15934 /** 15935 * copy_afc_event_common_info() - Copy the phy_id and event_type parameters 15936 * in the AFC event. 'Common' indicates that these parameters are common for 15937 * WMI_AFC_EVENT_POWER_INFO and WMI_AFC_EVENT_TIMER_EXPIRY. 15938 * @wmi_handle: wmi handle 15939 * @afc_info: pointer to afc_info 15940 * @event_fixed_hdr: pointer to event_fixed_hdr 15941 * 15942 * Return: void 15943 */ 15944 static void 15945 copy_afc_event_common_info(wmi_unified_t wmi_handle, 15946 struct afc_regulatory_info *afc_info, 15947 wmi_afc_event_fixed_param *event_fixed_hdr) 15948 { 15949 afc_info->phy_id = wmi_handle->ops->convert_phy_id_target_to_host( 15950 wmi_handle, event_fixed_hdr->phy_id); 15951 wmi_debug("phy_id %d", afc_info->phy_id); 15952 afc_info->event_type = event_fixed_hdr->event_type; 15953 } 15954 15955 static QDF_STATUS extract_afc_event_tlv(wmi_unified_t wmi_handle, 15956 uint8_t *evt_buf, 15957 struct afc_regulatory_info *afc_info, 15958 uint32_t len) 15959 { 15960 WMI_AFC_EVENTID_param_tlvs *param_buf; 15961 wmi_afc_event_fixed_param *event_fixed_hdr; 15962 15963 param_buf = (WMI_AFC_EVENTID_param_tlvs *)evt_buf; 15964 if (!param_buf) { 15965 wmi_err("Invalid AFC event buf"); 15966 return QDF_STATUS_E_FAILURE; 15967 } 15968 15969 event_fixed_hdr = param_buf->fixed_param; 15970 copy_afc_event_common_info(wmi_handle, afc_info, event_fixed_hdr); 15971 wmi_debug("AFC event type %d received", afc_info->event_type); 15972 15973 switch (afc_info->event_type) { 15974 case WMI_AFC_EVENT_POWER_INFO: 15975 copy_power_event(afc_info, param_buf); 15976 break; 15977 case WMI_AFC_EVENT_TIMER_EXPIRY: 15978 copy_expiry_event(afc_info, param_buf); 15979 return QDF_STATUS_SUCCESS; 15980 default: 15981 wmi_err("Invalid event type"); 15982 return QDF_STATUS_E_FAILURE; 15983 } 15984 15985 return QDF_STATUS_SUCCESS; 15986 } 15987 #endif 15988 #endif 15989 15990 static QDF_STATUS extract_reg_chan_list_update_event_tlv( 15991 wmi_unified_t wmi_handle, uint8_t *evt_buf, 15992 struct cur_regulatory_info *reg_info, uint32_t len) 15993 { 15994 WMI_REG_CHAN_LIST_CC_EVENTID_param_tlvs *param_buf; 15995 wmi_reg_chan_list_cc_event_fixed_param *chan_list_event_hdr; 15996 wmi_regulatory_rule_struct *wmi_reg_rule; 15997 uint32_t num_2g_reg_rules, num_5g_reg_rules; 15998 15999 wmi_debug("processing regulatory channel list"); 16000 16001 param_buf = (WMI_REG_CHAN_LIST_CC_EVENTID_param_tlvs *)evt_buf; 16002 if (!param_buf) { 16003 wmi_err("invalid channel list event buf"); 16004 return QDF_STATUS_E_FAILURE; 16005 } 16006 16007 chan_list_event_hdr = param_buf->fixed_param; 16008 16009 reg_info->num_2g_reg_rules = chan_list_event_hdr->num_2g_reg_rules; 16010 reg_info->num_5g_reg_rules = chan_list_event_hdr->num_5g_reg_rules; 16011 num_2g_reg_rules = reg_info->num_2g_reg_rules; 16012 num_5g_reg_rules = reg_info->num_5g_reg_rules; 16013 if ((num_2g_reg_rules > MAX_REG_RULES) || 16014 (num_5g_reg_rules > MAX_REG_RULES) || 16015 (num_2g_reg_rules + num_5g_reg_rules > MAX_REG_RULES) || 16016 (num_2g_reg_rules + num_5g_reg_rules != 16017 param_buf->num_reg_rule_array)) { 16018 wmi_err_rl("Invalid num_2g_reg_rules: %u, num_5g_reg_rules: %u", 16019 num_2g_reg_rules, num_5g_reg_rules); 16020 return QDF_STATUS_E_FAILURE; 16021 } 16022 if (param_buf->num_reg_rule_array > 16023 (WMI_SVC_MSG_MAX_SIZE - sizeof(*chan_list_event_hdr)) / 16024 sizeof(*wmi_reg_rule)) { 16025 wmi_err_rl("Invalid num_reg_rule_array: %u", 16026 param_buf->num_reg_rule_array); 16027 return QDF_STATUS_E_FAILURE; 16028 } 16029 16030 qdf_mem_copy(reg_info->alpha2, &(chan_list_event_hdr->alpha2), 16031 REG_ALPHA2_LEN); 16032 reg_info->dfs_region = chan_list_event_hdr->dfs_region; 16033 reg_info->phybitmap = convert_phybitmap_tlv( 16034 chan_list_event_hdr->phybitmap); 16035 reg_info->offload_enabled = true; 16036 reg_info->num_phy = chan_list_event_hdr->num_phy; 16037 reg_info->phy_id = wmi_handle->ops->convert_phy_id_target_to_host( 16038 wmi_handle, chan_list_event_hdr->phy_id); 16039 reg_info->ctry_code = chan_list_event_hdr->country_id; 16040 reg_info->reg_dmn_pair = chan_list_event_hdr->domain_code; 16041 16042 reg_info->status_code = 16043 wmi_reg_status_to_reg_status(chan_list_event_hdr->status_code); 16044 16045 reg_info->min_bw_2g = chan_list_event_hdr->min_bw_2g; 16046 reg_info->max_bw_2g = chan_list_event_hdr->max_bw_2g; 16047 reg_info->min_bw_5g = chan_list_event_hdr->min_bw_5g; 16048 reg_info->max_bw_5g = chan_list_event_hdr->max_bw_5g; 16049 16050 wmi_debug("num_phys = %u and phy_id = %u", 16051 reg_info->num_phy, reg_info->phy_id); 16052 16053 wmi_debug("cc %s dfs %d BW: min_2g %d max_2g %d min_5g %d max_5g %d", 16054 reg_info->alpha2, reg_info->dfs_region, 16055 reg_info->min_bw_2g, reg_info->max_bw_2g, 16056 reg_info->min_bw_5g, reg_info->max_bw_5g); 16057 16058 wmi_debug("num_2g_reg_rules %d num_5g_reg_rules %d", 16059 num_2g_reg_rules, num_5g_reg_rules); 16060 wmi_reg_rule = 16061 (wmi_regulatory_rule_struct *)((uint8_t *)chan_list_event_hdr 16062 + sizeof(wmi_reg_chan_list_cc_event_fixed_param) 16063 + WMI_TLV_HDR_SIZE); 16064 reg_info->reg_rules_2g_ptr = create_reg_rules_from_wmi(num_2g_reg_rules, 16065 wmi_reg_rule); 16066 wmi_reg_rule += num_2g_reg_rules; 16067 16068 reg_info->reg_rules_5g_ptr = create_reg_rules_from_wmi(num_5g_reg_rules, 16069 wmi_reg_rule); 16070 16071 wmi_debug("processed regulatory channel list"); 16072 16073 return QDF_STATUS_SUCCESS; 16074 } 16075 16076 static QDF_STATUS extract_reg_11d_new_country_event_tlv( 16077 wmi_unified_t wmi_handle, uint8_t *evt_buf, 16078 struct reg_11d_new_country *reg_11d_country, uint32_t len) 16079 { 16080 wmi_11d_new_country_event_fixed_param *reg_11d_country_event; 16081 WMI_11D_NEW_COUNTRY_EVENTID_param_tlvs *param_buf; 16082 16083 param_buf = (WMI_11D_NEW_COUNTRY_EVENTID_param_tlvs *)evt_buf; 16084 if (!param_buf) { 16085 wmi_err("invalid 11d country event buf"); 16086 return QDF_STATUS_E_FAILURE; 16087 } 16088 16089 reg_11d_country_event = param_buf->fixed_param; 16090 16091 qdf_mem_copy(reg_11d_country->alpha2, 16092 ®_11d_country_event->new_alpha2, REG_ALPHA2_LEN); 16093 reg_11d_country->alpha2[REG_ALPHA2_LEN] = '\0'; 16094 16095 wmi_debug("processed 11d country event, new cc %s", 16096 reg_11d_country->alpha2); 16097 16098 return QDF_STATUS_SUCCESS; 16099 } 16100 16101 static QDF_STATUS extract_reg_ch_avoid_event_tlv( 16102 wmi_unified_t wmi_handle, uint8_t *evt_buf, 16103 struct ch_avoid_ind_type *ch_avoid_ind, uint32_t len) 16104 { 16105 wmi_avoid_freq_ranges_event_fixed_param *afr_fixed_param; 16106 wmi_avoid_freq_range_desc *afr_desc; 16107 uint32_t num_freq_ranges, freq_range_idx; 16108 WMI_WLAN_FREQ_AVOID_EVENTID_param_tlvs *param_buf = 16109 (WMI_WLAN_FREQ_AVOID_EVENTID_param_tlvs *) evt_buf; 16110 16111 if (!param_buf) { 16112 wmi_err("Invalid channel avoid event buffer"); 16113 return QDF_STATUS_E_INVAL; 16114 } 16115 16116 afr_fixed_param = param_buf->fixed_param; 16117 if (!afr_fixed_param) { 16118 wmi_err("Invalid channel avoid event fixed param buffer"); 16119 return QDF_STATUS_E_INVAL; 16120 } 16121 16122 if (!ch_avoid_ind) { 16123 wmi_err("Invalid channel avoid indication buffer"); 16124 return QDF_STATUS_E_INVAL; 16125 } 16126 if (param_buf->num_avd_freq_range < afr_fixed_param->num_freq_ranges) { 16127 wmi_err("no.of freq ranges exceeded the limit"); 16128 return QDF_STATUS_E_INVAL; 16129 } 16130 num_freq_ranges = (afr_fixed_param->num_freq_ranges > 16131 CH_AVOID_MAX_RANGE) ? CH_AVOID_MAX_RANGE : 16132 afr_fixed_param->num_freq_ranges; 16133 16134 wmi_debug("Channel avoid event received with %d ranges", 16135 num_freq_ranges); 16136 16137 ch_avoid_ind->ch_avoid_range_cnt = num_freq_ranges; 16138 afr_desc = (wmi_avoid_freq_range_desc *)(param_buf->avd_freq_range); 16139 for (freq_range_idx = 0; freq_range_idx < num_freq_ranges; 16140 freq_range_idx++) { 16141 ch_avoid_ind->avoid_freq_range[freq_range_idx].start_freq = 16142 afr_desc->start_freq; 16143 ch_avoid_ind->avoid_freq_range[freq_range_idx].end_freq = 16144 afr_desc->end_freq; 16145 wmi_debug("range %d tlv id %u, start freq %u, end freq %u", 16146 freq_range_idx, afr_desc->tlv_header, 16147 afr_desc->start_freq, afr_desc->end_freq); 16148 afr_desc++; 16149 } 16150 16151 return QDF_STATUS_SUCCESS; 16152 } 16153 16154 #ifdef DFS_COMPONENT_ENABLE 16155 /** 16156 * extract_dfs_cac_complete_event_tlv() - extract cac complete event 16157 * @wmi_handle: wma handle 16158 * @evt_buf: event buffer 16159 * @vdev_id: vdev id 16160 * @len: length of buffer 16161 * 16162 * Return: 0 for success or error code 16163 */ 16164 static QDF_STATUS extract_dfs_cac_complete_event_tlv(wmi_unified_t wmi_handle, 16165 uint8_t *evt_buf, 16166 uint32_t *vdev_id, 16167 uint32_t len) 16168 { 16169 WMI_VDEV_DFS_CAC_COMPLETE_EVENTID_param_tlvs *param_tlvs; 16170 wmi_vdev_dfs_cac_complete_event_fixed_param *cac_event; 16171 16172 param_tlvs = (WMI_VDEV_DFS_CAC_COMPLETE_EVENTID_param_tlvs *) evt_buf; 16173 if (!param_tlvs) { 16174 wmi_err("invalid cac complete event buf"); 16175 return QDF_STATUS_E_FAILURE; 16176 } 16177 16178 cac_event = param_tlvs->fixed_param; 16179 *vdev_id = cac_event->vdev_id; 16180 wmi_debug("processed cac complete event vdev %d", *vdev_id); 16181 16182 return QDF_STATUS_SUCCESS; 16183 } 16184 16185 /** 16186 * extract_dfs_ocac_complete_event_tlv() - extract cac complete event 16187 * @wmi_handle: wma handle 16188 * @evt_buf: event buffer 16189 * @vdev_id: vdev id 16190 * @len: length of buffer 16191 * 16192 * Return: 0 for success or error code 16193 */ 16194 static QDF_STATUS 16195 extract_dfs_ocac_complete_event_tlv(wmi_unified_t wmi_handle, 16196 uint8_t *evt_buf, 16197 struct vdev_adfs_complete_status *param) 16198 { 16199 WMI_VDEV_ADFS_OCAC_COMPLETE_EVENTID_param_tlvs *param_tlvs; 16200 wmi_vdev_adfs_ocac_complete_event_fixed_param *ocac_complete_status; 16201 16202 param_tlvs = (WMI_VDEV_ADFS_OCAC_COMPLETE_EVENTID_param_tlvs *)evt_buf; 16203 if (!param_tlvs) { 16204 wmi_err("invalid ocac complete event buf"); 16205 return QDF_STATUS_E_FAILURE; 16206 } 16207 16208 if (!param_tlvs->fixed_param) { 16209 wmi_err("invalid param_tlvs->fixed_param"); 16210 return QDF_STATUS_E_FAILURE; 16211 } 16212 16213 ocac_complete_status = param_tlvs->fixed_param; 16214 param->vdev_id = ocac_complete_status->vdev_id; 16215 param->chan_freq = ocac_complete_status->chan_freq; 16216 param->center_freq1 = ocac_complete_status->center_freq1; 16217 param->center_freq2 = ocac_complete_status->center_freq2; 16218 param->ocac_status = ocac_complete_status->status; 16219 param->chan_width = ocac_complete_status->chan_width; 16220 wmi_debug("processed ocac complete event vdev %d" 16221 " agile chan %d %d width %d status %d", 16222 param->vdev_id, 16223 param->center_freq1, 16224 param->center_freq2, 16225 param->chan_width, 16226 param->ocac_status); 16227 16228 return QDF_STATUS_SUCCESS; 16229 } 16230 16231 /** 16232 * extract_dfs_radar_detection_event_tlv() - extract radar found event 16233 * @wmi_handle: wma handle 16234 * @evt_buf: event buffer 16235 * @radar_found: radar found event info 16236 * @len: length of buffer 16237 * 16238 * Return: 0 for success or error code 16239 */ 16240 static QDF_STATUS extract_dfs_radar_detection_event_tlv( 16241 wmi_unified_t wmi_handle, 16242 uint8_t *evt_buf, 16243 struct radar_found_info *radar_found, 16244 uint32_t len) 16245 { 16246 WMI_PDEV_DFS_RADAR_DETECTION_EVENTID_param_tlvs *param_tlv; 16247 wmi_pdev_dfs_radar_detection_event_fixed_param *radar_event; 16248 16249 param_tlv = (WMI_PDEV_DFS_RADAR_DETECTION_EVENTID_param_tlvs *) evt_buf; 16250 if (!param_tlv) { 16251 wmi_err("invalid radar detection event buf"); 16252 return QDF_STATUS_E_FAILURE; 16253 } 16254 16255 radar_event = param_tlv->fixed_param; 16256 16257 radar_found->pdev_id = convert_target_pdev_id_to_host_pdev_id( 16258 wmi_handle, 16259 radar_event->pdev_id); 16260 16261 if (radar_found->pdev_id == WMI_HOST_PDEV_ID_INVALID) 16262 return QDF_STATUS_E_FAILURE; 16263 16264 radar_found->detection_mode = radar_event->detection_mode; 16265 radar_found->chan_freq = radar_event->chan_freq; 16266 radar_found->chan_width = radar_event->chan_width; 16267 radar_found->detector_id = radar_event->detector_id; 16268 radar_found->segment_id = radar_event->segment_id; 16269 radar_found->timestamp = radar_event->timestamp; 16270 radar_found->is_chirp = radar_event->is_chirp; 16271 radar_found->freq_offset = radar_event->freq_offset; 16272 radar_found->sidx = radar_event->sidx; 16273 16274 wmi_debug("processed radar found event pdev %d," 16275 "Radar Event Info:pdev_id %d,timestamp %d,chan_freq (dur) %d," 16276 "chan_width (RSSI) %d,detector_id (false_radar) %d," 16277 "freq_offset (radar_check) %d,segment_id %d,sidx %d," 16278 "is_chirp %d,detection mode %d", 16279 radar_event->pdev_id, radar_found->pdev_id, 16280 radar_event->timestamp, radar_event->chan_freq, 16281 radar_event->chan_width, radar_event->detector_id, 16282 radar_event->freq_offset, radar_event->segment_id, 16283 radar_event->sidx, radar_event->is_chirp, 16284 radar_event->detection_mode); 16285 16286 return QDF_STATUS_SUCCESS; 16287 } 16288 16289 #ifdef MOBILE_DFS_SUPPORT 16290 /** 16291 * extract_wlan_radar_event_info_tlv() - extract radar pulse event 16292 * @wmi_handle: wma handle 16293 * @evt_buf: event buffer 16294 * @wlan_radar_event: Pointer to struct radar_event_info 16295 * @len: length of buffer 16296 * 16297 * Return: QDF_STATUS 16298 */ 16299 static QDF_STATUS extract_wlan_radar_event_info_tlv( 16300 wmi_unified_t wmi_handle, 16301 uint8_t *evt_buf, 16302 struct radar_event_info *wlan_radar_event, 16303 uint32_t len) 16304 { 16305 WMI_DFS_RADAR_EVENTID_param_tlvs *param_tlv; 16306 wmi_dfs_radar_event_fixed_param *radar_event; 16307 16308 param_tlv = (WMI_DFS_RADAR_EVENTID_param_tlvs *)evt_buf; 16309 if (!param_tlv) { 16310 wmi_err("invalid wlan radar event buf"); 16311 return QDF_STATUS_E_FAILURE; 16312 } 16313 16314 radar_event = param_tlv->fixed_param; 16315 wlan_radar_event->pulse_is_chirp = radar_event->pulse_is_chirp; 16316 wlan_radar_event->pulse_center_freq = radar_event->pulse_center_freq; 16317 wlan_radar_event->pulse_duration = radar_event->pulse_duration; 16318 wlan_radar_event->rssi = radar_event->rssi; 16319 wlan_radar_event->pulse_detect_ts = radar_event->pulse_detect_ts; 16320 wlan_radar_event->upload_fullts_high = radar_event->upload_fullts_high; 16321 wlan_radar_event->upload_fullts_low = radar_event->upload_fullts_low; 16322 wlan_radar_event->peak_sidx = radar_event->peak_sidx; 16323 wlan_radar_event->delta_peak = radar_event->pulse_delta_peak; 16324 wlan_radar_event->delta_diff = radar_event->pulse_delta_diff; 16325 if (radar_event->pulse_flags & 16326 WMI_DFS_RADAR_PULSE_FLAG_MASK_PSIDX_DIFF_VALID) { 16327 wlan_radar_event->is_psidx_diff_valid = true; 16328 wlan_radar_event->psidx_diff = radar_event->psidx_diff; 16329 } else { 16330 wlan_radar_event->is_psidx_diff_valid = false; 16331 } 16332 16333 wlan_radar_event->pdev_id = radar_event->pdev_id; 16334 16335 return QDF_STATUS_SUCCESS; 16336 } 16337 #else 16338 static QDF_STATUS extract_wlan_radar_event_info_tlv( 16339 wmi_unified_t wmi_handle, 16340 uint8_t *evt_buf, 16341 struct radar_event_info *wlan_radar_event, 16342 uint32_t len) 16343 { 16344 return QDF_STATUS_SUCCESS; 16345 } 16346 #endif 16347 #endif 16348 16349 /** 16350 * send_get_rcpi_cmd_tlv() - send request for rcpi value 16351 * @wmi_handle: wmi handle 16352 * @get_rcpi_param: rcpi params 16353 * 16354 * Return: QDF status 16355 */ 16356 static QDF_STATUS send_get_rcpi_cmd_tlv(wmi_unified_t wmi_handle, 16357 struct rcpi_req *get_rcpi_param) 16358 { 16359 wmi_buf_t buf; 16360 wmi_request_rcpi_cmd_fixed_param *cmd; 16361 uint8_t len = sizeof(wmi_request_rcpi_cmd_fixed_param); 16362 16363 buf = wmi_buf_alloc(wmi_handle, len); 16364 if (!buf) 16365 return QDF_STATUS_E_NOMEM; 16366 16367 cmd = (wmi_request_rcpi_cmd_fixed_param *) wmi_buf_data(buf); 16368 WMITLV_SET_HDR(&cmd->tlv_header, 16369 WMITLV_TAG_STRUC_wmi_request_rcpi_cmd_fixed_param, 16370 WMITLV_GET_STRUCT_TLVLEN 16371 (wmi_request_rcpi_cmd_fixed_param)); 16372 16373 cmd->vdev_id = get_rcpi_param->vdev_id; 16374 WMI_CHAR_ARRAY_TO_MAC_ADDR(get_rcpi_param->mac_addr, 16375 &cmd->peer_macaddr); 16376 16377 switch (get_rcpi_param->measurement_type) { 16378 16379 case RCPI_MEASUREMENT_TYPE_AVG_MGMT: 16380 cmd->measurement_type = WMI_RCPI_MEASUREMENT_TYPE_AVG_MGMT; 16381 break; 16382 16383 case RCPI_MEASUREMENT_TYPE_AVG_DATA: 16384 cmd->measurement_type = WMI_RCPI_MEASUREMENT_TYPE_AVG_DATA; 16385 break; 16386 16387 case RCPI_MEASUREMENT_TYPE_LAST_MGMT: 16388 cmd->measurement_type = WMI_RCPI_MEASUREMENT_TYPE_LAST_MGMT; 16389 break; 16390 16391 case RCPI_MEASUREMENT_TYPE_LAST_DATA: 16392 cmd->measurement_type = WMI_RCPI_MEASUREMENT_TYPE_LAST_DATA; 16393 break; 16394 16395 default: 16396 /* 16397 * invalid rcpi measurement type, fall back to 16398 * RCPI_MEASUREMENT_TYPE_AVG_MGMT 16399 */ 16400 cmd->measurement_type = WMI_RCPI_MEASUREMENT_TYPE_AVG_MGMT; 16401 break; 16402 } 16403 wmi_debug("RCPI REQ VDEV_ID:%d-->", cmd->vdev_id); 16404 wmi_mtrace(WMI_REQUEST_RCPI_CMDID, cmd->vdev_id, 0); 16405 if (wmi_unified_cmd_send(wmi_handle, buf, len, 16406 WMI_REQUEST_RCPI_CMDID)) { 16407 16408 wmi_err("Failed to send WMI_REQUEST_RCPI_CMDID"); 16409 wmi_buf_free(buf); 16410 return QDF_STATUS_E_FAILURE; 16411 } 16412 16413 return QDF_STATUS_SUCCESS; 16414 } 16415 16416 /** 16417 * extract_rcpi_response_event_tlv() - Extract RCPI event params 16418 * @wmi_handle: wmi handle 16419 * @evt_buf: pointer to event buffer 16420 * @res: pointer to hold rcpi response from firmware 16421 * 16422 * Return: QDF_STATUS_SUCCESS for successful event parse 16423 * else QDF_STATUS_E_INVAL or QDF_STATUS_E_FAILURE 16424 */ 16425 static QDF_STATUS 16426 extract_rcpi_response_event_tlv(wmi_unified_t wmi_handle, 16427 void *evt_buf, struct rcpi_res *res) 16428 { 16429 WMI_UPDATE_RCPI_EVENTID_param_tlvs *param_buf; 16430 wmi_update_rcpi_event_fixed_param *event; 16431 16432 param_buf = (WMI_UPDATE_RCPI_EVENTID_param_tlvs *)evt_buf; 16433 if (!param_buf) { 16434 wmi_err("Invalid rcpi event"); 16435 return QDF_STATUS_E_INVAL; 16436 } 16437 16438 event = param_buf->fixed_param; 16439 res->vdev_id = event->vdev_id; 16440 WMI_MAC_ADDR_TO_CHAR_ARRAY(&event->peer_macaddr, res->mac_addr); 16441 16442 switch (event->measurement_type) { 16443 16444 case WMI_RCPI_MEASUREMENT_TYPE_AVG_MGMT: 16445 res->measurement_type = RCPI_MEASUREMENT_TYPE_AVG_MGMT; 16446 break; 16447 16448 case WMI_RCPI_MEASUREMENT_TYPE_AVG_DATA: 16449 res->measurement_type = RCPI_MEASUREMENT_TYPE_AVG_DATA; 16450 break; 16451 16452 case WMI_RCPI_MEASUREMENT_TYPE_LAST_MGMT: 16453 res->measurement_type = RCPI_MEASUREMENT_TYPE_LAST_MGMT; 16454 break; 16455 16456 case WMI_RCPI_MEASUREMENT_TYPE_LAST_DATA: 16457 res->measurement_type = RCPI_MEASUREMENT_TYPE_LAST_DATA; 16458 break; 16459 16460 default: 16461 wmi_err("Invalid rcpi measurement type from firmware"); 16462 res->measurement_type = RCPI_MEASUREMENT_TYPE_INVALID; 16463 return QDF_STATUS_E_FAILURE; 16464 } 16465 16466 if (event->status) 16467 return QDF_STATUS_E_FAILURE; 16468 else 16469 return QDF_STATUS_SUCCESS; 16470 } 16471 16472 /** 16473 * convert_host_pdev_id_to_target_pdev_id_legacy() - Convert pdev_id from 16474 * host to target defines. For legacy there is not conversion 16475 * required. Just return pdev_id as it is. 16476 * @param pdev_id: host pdev_id to be converted. 16477 * Return: target pdev_id after conversion. 16478 */ 16479 static uint32_t convert_host_pdev_id_to_target_pdev_id_legacy( 16480 wmi_unified_t wmi_handle, 16481 uint32_t pdev_id) 16482 { 16483 if (pdev_id == WMI_HOST_PDEV_ID_SOC) 16484 return WMI_PDEV_ID_SOC; 16485 16486 /*No conversion required*/ 16487 return pdev_id; 16488 } 16489 16490 /** 16491 * convert_target_pdev_id_to_host_pdev_id_legacy() - Convert pdev_id from 16492 * target to host defines. For legacy there is not conversion 16493 * required. Just return pdev_id as it is. 16494 * @param pdev_id: target pdev_id to be converted. 16495 * Return: host pdev_id after conversion. 16496 */ 16497 static uint32_t convert_target_pdev_id_to_host_pdev_id_legacy( 16498 wmi_unified_t wmi_handle, 16499 uint32_t pdev_id) 16500 { 16501 /*No conversion required*/ 16502 return pdev_id; 16503 } 16504 16505 /** 16506 * convert_host_phy_id_to_target_phy_id_legacy() - Convert phy_id from 16507 * host to target defines. For legacy there is not conversion 16508 * required. Just return phy_id as it is. 16509 * @param pdev_id: host phy_id to be converted. 16510 * Return: target phy_id after conversion. 16511 */ 16512 static uint32_t convert_host_phy_id_to_target_phy_id_legacy( 16513 wmi_unified_t wmi_handle, 16514 uint32_t phy_id) 16515 { 16516 /*No conversion required*/ 16517 return phy_id; 16518 } 16519 16520 /** 16521 * convert_target_phy_id_to_host_phy_id_legacy() - Convert phy_id from 16522 * target to host defines. For legacy there is not conversion 16523 * required. Just return phy_id as it is. 16524 * @param pdev_id: target phy_id to be converted. 16525 * Return: host phy_id after conversion. 16526 */ 16527 static uint32_t convert_target_phy_id_to_host_phy_id_legacy( 16528 wmi_unified_t wmi_handle, 16529 uint32_t phy_id) 16530 { 16531 /*No conversion required*/ 16532 return phy_id; 16533 } 16534 16535 /** 16536 * send_set_country_cmd_tlv() - WMI scan channel list function 16537 * @param wmi_handle : handle to WMI. 16538 * @param param : pointer to hold scan channel list parameter 16539 * 16540 * Return: 0 on success and -ve on failure. 16541 */ 16542 static QDF_STATUS send_set_country_cmd_tlv(wmi_unified_t wmi_handle, 16543 struct set_country *params) 16544 { 16545 wmi_buf_t buf; 16546 QDF_STATUS qdf_status; 16547 wmi_set_current_country_cmd_fixed_param *cmd; 16548 uint16_t len = sizeof(*cmd); 16549 uint8_t pdev_id = params->pdev_id; 16550 16551 buf = wmi_buf_alloc(wmi_handle, len); 16552 if (!buf) { 16553 qdf_status = QDF_STATUS_E_NOMEM; 16554 goto end; 16555 } 16556 16557 cmd = (wmi_set_current_country_cmd_fixed_param *)wmi_buf_data(buf); 16558 WMITLV_SET_HDR(&cmd->tlv_header, 16559 WMITLV_TAG_STRUC_wmi_set_current_country_cmd_fixed_param, 16560 WMITLV_GET_STRUCT_TLVLEN 16561 (wmi_set_current_country_cmd_fixed_param)); 16562 16563 cmd->pdev_id = wmi_handle->ops->convert_host_pdev_id_to_target( 16564 wmi_handle, 16565 pdev_id); 16566 wmi_debug("setting current country to %s and target pdev_id = %u", 16567 params->country, cmd->pdev_id); 16568 16569 qdf_mem_copy((uint8_t *)&cmd->new_alpha2, params->country, 3); 16570 16571 wmi_mtrace(WMI_SET_CURRENT_COUNTRY_CMDID, NO_SESSION, 0); 16572 qdf_status = wmi_unified_cmd_send(wmi_handle, 16573 buf, len, WMI_SET_CURRENT_COUNTRY_CMDID); 16574 16575 if (QDF_IS_STATUS_ERROR(qdf_status)) { 16576 wmi_err("Failed to send WMI_SET_CURRENT_COUNTRY_CMDID"); 16577 wmi_buf_free(buf); 16578 } 16579 16580 end: 16581 return qdf_status; 16582 } 16583 16584 #define WMI_REG_COUNTRY_ALPHA_SET(alpha, val0, val1, val2) do { \ 16585 WMI_SET_BITS(alpha, 0, 8, val0); \ 16586 WMI_SET_BITS(alpha, 8, 8, val1); \ 16587 WMI_SET_BITS(alpha, 16, 8, val2); \ 16588 } while (0) 16589 16590 static QDF_STATUS send_user_country_code_cmd_tlv(wmi_unified_t wmi_handle, 16591 uint8_t pdev_id, struct cc_regdmn_s *rd) 16592 { 16593 wmi_set_init_country_cmd_fixed_param *cmd; 16594 uint16_t len; 16595 wmi_buf_t buf; 16596 int ret; 16597 16598 len = sizeof(wmi_set_init_country_cmd_fixed_param); 16599 buf = wmi_buf_alloc(wmi_handle, len); 16600 if (!buf) 16601 return QDF_STATUS_E_NOMEM; 16602 16603 cmd = (wmi_set_init_country_cmd_fixed_param *) wmi_buf_data(buf); 16604 WMITLV_SET_HDR(&cmd->tlv_header, 16605 WMITLV_TAG_STRUC_wmi_set_init_country_cmd_fixed_param, 16606 WMITLV_GET_STRUCT_TLVLEN 16607 (wmi_set_init_country_cmd_fixed_param)); 16608 16609 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 16610 wmi_handle, 16611 pdev_id); 16612 16613 if (rd->flags == CC_IS_SET) { 16614 cmd->countrycode_type = WMI_COUNTRYCODE_COUNTRY_ID; 16615 cmd->country_code.country_id = rd->cc.country_code; 16616 } else if (rd->flags == ALPHA_IS_SET) { 16617 cmd->countrycode_type = WMI_COUNTRYCODE_ALPHA2; 16618 WMI_REG_COUNTRY_ALPHA_SET(cmd->country_code.alpha2, 16619 rd->cc.alpha[0], 16620 rd->cc.alpha[1], 16621 rd->cc.alpha[2]); 16622 } else if (rd->flags == REGDMN_IS_SET) { 16623 cmd->countrycode_type = WMI_COUNTRYCODE_DOMAIN_CODE; 16624 WMI_SET_BITS(cmd->country_code.domain_code, 0, 16, 16625 rd->cc.regdmn.reg_2g_5g_pair_id); 16626 WMI_SET_BITS(cmd->country_code.domain_code, 16, 16, 16627 rd->cc.regdmn.sixg_superdmn_id); 16628 } 16629 16630 wmi_mtrace(WMI_SET_INIT_COUNTRY_CMDID, NO_SESSION, 0); 16631 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 16632 WMI_SET_INIT_COUNTRY_CMDID); 16633 if (ret) { 16634 wmi_err("Failed to config wow wakeup event"); 16635 wmi_buf_free(buf); 16636 return QDF_STATUS_E_FAILURE; 16637 } 16638 16639 return QDF_STATUS_SUCCESS; 16640 } 16641 16642 /** 16643 * send_obss_detection_cfg_cmd_tlv() - send obss detection 16644 * configurations to firmware. 16645 * @wmi_handle: wmi handle 16646 * @obss_cfg_param: obss detection configurations 16647 * 16648 * Send WMI_SAP_OBSS_DETECTION_CFG_CMDID parameters to fw. 16649 * 16650 * Return: QDF_STATUS 16651 */ 16652 static QDF_STATUS send_obss_detection_cfg_cmd_tlv(wmi_unified_t wmi_handle, 16653 struct wmi_obss_detection_cfg_param *obss_cfg_param) 16654 { 16655 wmi_buf_t buf; 16656 wmi_sap_obss_detection_cfg_cmd_fixed_param *cmd; 16657 uint8_t len = sizeof(wmi_sap_obss_detection_cfg_cmd_fixed_param); 16658 16659 buf = wmi_buf_alloc(wmi_handle, len); 16660 if (!buf) 16661 return QDF_STATUS_E_NOMEM; 16662 16663 cmd = (wmi_sap_obss_detection_cfg_cmd_fixed_param *)wmi_buf_data(buf); 16664 WMITLV_SET_HDR(&cmd->tlv_header, 16665 WMITLV_TAG_STRUC_wmi_sap_obss_detection_cfg_cmd_fixed_param, 16666 WMITLV_GET_STRUCT_TLVLEN 16667 (wmi_sap_obss_detection_cfg_cmd_fixed_param)); 16668 16669 cmd->vdev_id = obss_cfg_param->vdev_id; 16670 cmd->detect_period_ms = obss_cfg_param->obss_detect_period_ms; 16671 cmd->b_ap_detect_mode = obss_cfg_param->obss_11b_ap_detect_mode; 16672 cmd->b_sta_detect_mode = obss_cfg_param->obss_11b_sta_detect_mode; 16673 cmd->g_ap_detect_mode = obss_cfg_param->obss_11g_ap_detect_mode; 16674 cmd->a_detect_mode = obss_cfg_param->obss_11a_detect_mode; 16675 cmd->ht_legacy_detect_mode = obss_cfg_param->obss_ht_legacy_detect_mode; 16676 cmd->ht_mixed_detect_mode = obss_cfg_param->obss_ht_mixed_detect_mode; 16677 cmd->ht_20mhz_detect_mode = obss_cfg_param->obss_ht_20mhz_detect_mode; 16678 16679 wmi_mtrace(WMI_SAP_OBSS_DETECTION_CFG_CMDID, cmd->vdev_id, 0); 16680 if (wmi_unified_cmd_send(wmi_handle, buf, len, 16681 WMI_SAP_OBSS_DETECTION_CFG_CMDID)) { 16682 wmi_err("Failed to send WMI_SAP_OBSS_DETECTION_CFG_CMDID"); 16683 wmi_buf_free(buf); 16684 return QDF_STATUS_E_FAILURE; 16685 } 16686 16687 return QDF_STATUS_SUCCESS; 16688 } 16689 16690 /** 16691 * extract_obss_detection_info_tlv() - Extract obss detection info 16692 * received from firmware. 16693 * @evt_buf: pointer to event buffer 16694 * @obss_detection: Pointer to hold obss detection info 16695 * 16696 * Return: QDF_STATUS 16697 */ 16698 static QDF_STATUS extract_obss_detection_info_tlv(uint8_t *evt_buf, 16699 struct wmi_obss_detect_info 16700 *obss_detection) 16701 { 16702 WMI_SAP_OBSS_DETECTION_REPORT_EVENTID_param_tlvs *param_buf; 16703 wmi_sap_obss_detection_info_evt_fixed_param *fix_param; 16704 16705 if (!obss_detection) { 16706 wmi_err("Invalid obss_detection event buffer"); 16707 return QDF_STATUS_E_INVAL; 16708 } 16709 16710 param_buf = (WMI_SAP_OBSS_DETECTION_REPORT_EVENTID_param_tlvs *)evt_buf; 16711 if (!param_buf) { 16712 wmi_err("Invalid evt_buf"); 16713 return QDF_STATUS_E_INVAL; 16714 } 16715 16716 fix_param = param_buf->fixed_param; 16717 obss_detection->vdev_id = fix_param->vdev_id; 16718 obss_detection->matched_detection_masks = 16719 fix_param->matched_detection_masks; 16720 WMI_MAC_ADDR_TO_CHAR_ARRAY(&fix_param->matched_bssid_addr, 16721 &obss_detection->matched_bssid_addr[0]); 16722 switch (fix_param->reason) { 16723 case WMI_SAP_OBSS_DETECTION_EVENT_REASON_NOT_SUPPORT: 16724 obss_detection->reason = OBSS_OFFLOAD_DETECTION_DISABLED; 16725 break; 16726 case WMI_SAP_OBSS_DETECTION_EVENT_REASON_PRESENT_NOTIFY: 16727 obss_detection->reason = OBSS_OFFLOAD_DETECTION_PRESENT; 16728 break; 16729 case WMI_SAP_OBSS_DETECTION_EVENT_REASON_ABSENT_TIMEOUT: 16730 obss_detection->reason = OBSS_OFFLOAD_DETECTION_ABSENT; 16731 break; 16732 default: 16733 wmi_err("Invalid reason: %d", fix_param->reason); 16734 return QDF_STATUS_E_INVAL; 16735 } 16736 16737 return QDF_STATUS_SUCCESS; 16738 } 16739 16740 /** 16741 * send_roam_scan_stats_cmd_tlv() - Send roam scan stats req command to fw 16742 * @wmi_handle: wmi handle 16743 * @params: pointer to request structure 16744 * 16745 * Return: QDF_STATUS 16746 */ 16747 static QDF_STATUS 16748 send_roam_scan_stats_cmd_tlv(wmi_unified_t wmi_handle, 16749 struct wmi_roam_scan_stats_req *params) 16750 { 16751 wmi_buf_t buf; 16752 wmi_request_roam_scan_stats_cmd_fixed_param *cmd; 16753 WMITLV_TAG_ID tag; 16754 uint32_t size; 16755 uint32_t len = sizeof(*cmd); 16756 16757 buf = wmi_buf_alloc(wmi_handle, len); 16758 if (!buf) 16759 return QDF_STATUS_E_FAILURE; 16760 16761 cmd = (wmi_request_roam_scan_stats_cmd_fixed_param *)wmi_buf_data(buf); 16762 16763 tag = WMITLV_TAG_STRUC_wmi_request_roam_scan_stats_cmd_fixed_param; 16764 size = WMITLV_GET_STRUCT_TLVLEN( 16765 wmi_request_roam_scan_stats_cmd_fixed_param); 16766 WMITLV_SET_HDR(&cmd->tlv_header, tag, size); 16767 16768 cmd->vdev_id = params->vdev_id; 16769 16770 wmi_debug("Roam Scan Stats Req vdev_id: %u", cmd->vdev_id); 16771 if (wmi_unified_cmd_send(wmi_handle, buf, len, 16772 WMI_REQUEST_ROAM_SCAN_STATS_CMDID)) { 16773 wmi_err("Failed to send WMI_REQUEST_ROAM_SCAN_STATS_CMDID"); 16774 wmi_buf_free(buf); 16775 return QDF_STATUS_E_FAILURE; 16776 } 16777 16778 return QDF_STATUS_SUCCESS; 16779 } 16780 16781 /** 16782 * send_roam_scan_ch_list_req_cmd_tlv() - send wmi cmd to get roam scan 16783 * channel list from firmware 16784 * @wmi_handle: wmi handler 16785 * @vdev_id: vdev id 16786 * 16787 * Return: QDF_STATUS 16788 */ 16789 static QDF_STATUS send_roam_scan_ch_list_req_cmd_tlv(wmi_unified_t wmi_handle, 16790 uint32_t vdev_id) 16791 { 16792 wmi_buf_t buf; 16793 wmi_roam_get_scan_channel_list_cmd_fixed_param *cmd; 16794 uint16_t len = sizeof(*cmd); 16795 int ret; 16796 16797 buf = wmi_buf_alloc(wmi_handle, len); 16798 if (!buf) { 16799 wmi_err("Failed to allocate wmi buffer"); 16800 return QDF_STATUS_E_NOMEM; 16801 } 16802 16803 cmd = (wmi_roam_get_scan_channel_list_cmd_fixed_param *) 16804 wmi_buf_data(buf); 16805 WMITLV_SET_HDR(&cmd->tlv_header, 16806 WMITLV_TAG_STRUC_wmi_roam_get_scan_channel_list_cmd_fixed_param, 16807 WMITLV_GET_STRUCT_TLVLEN( 16808 wmi_roam_get_scan_channel_list_cmd_fixed_param)); 16809 cmd->vdev_id = vdev_id; 16810 wmi_mtrace(WMI_ROAM_GET_SCAN_CHANNEL_LIST_CMDID, vdev_id, 0); 16811 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 16812 WMI_ROAM_GET_SCAN_CHANNEL_LIST_CMDID); 16813 if (QDF_IS_STATUS_ERROR(ret)) { 16814 wmi_err("Failed to send get roam scan channels request = %d", 16815 ret); 16816 wmi_buf_free(buf); 16817 } 16818 return ret; 16819 } 16820 16821 /** 16822 * extract_roam_scan_stats_res_evt_tlv() - Extract roam scan stats event 16823 * @wmi_handle: wmi handle 16824 * @evt_buf: pointer to event buffer 16825 * @vdev_id: output pointer to hold vdev id 16826 * @res_param: output pointer to hold the allocated response 16827 * 16828 * Return: QDF_STATUS 16829 */ 16830 static QDF_STATUS 16831 extract_roam_scan_stats_res_evt_tlv(wmi_unified_t wmi_handle, void *evt_buf, 16832 uint32_t *vdev_id, 16833 struct wmi_roam_scan_stats_res **res_param) 16834 { 16835 WMI_ROAM_SCAN_STATS_EVENTID_param_tlvs *param_buf; 16836 wmi_roam_scan_stats_event_fixed_param *fixed_param; 16837 uint32_t *client_id = NULL; 16838 wmi_roaming_timestamp *timestamp = NULL; 16839 uint32_t *num_channels = NULL; 16840 uint32_t *chan_info = NULL; 16841 wmi_mac_addr *old_bssid = NULL; 16842 uint32_t *is_roaming_success = NULL; 16843 wmi_mac_addr *new_bssid = NULL; 16844 uint32_t *num_roam_candidates = NULL; 16845 wmi_roam_scan_trigger_reason *roam_reason = NULL; 16846 wmi_mac_addr *bssid = NULL; 16847 uint32_t *score = NULL; 16848 uint32_t *channel = NULL; 16849 uint32_t *rssi = NULL; 16850 int chan_idx = 0, cand_idx = 0; 16851 uint32_t total_len; 16852 struct wmi_roam_scan_stats_res *res; 16853 uint32_t i, j; 16854 uint32_t num_scans, scan_param_size; 16855 16856 *res_param = NULL; 16857 *vdev_id = 0xFF; /* Initialize to invalid vdev id */ 16858 param_buf = (WMI_ROAM_SCAN_STATS_EVENTID_param_tlvs *)evt_buf; 16859 if (!param_buf) { 16860 wmi_err("Invalid roam scan stats event"); 16861 return QDF_STATUS_E_INVAL; 16862 } 16863 16864 fixed_param = param_buf->fixed_param; 16865 16866 num_scans = fixed_param->num_roam_scans; 16867 scan_param_size = sizeof(struct wmi_roam_scan_stats_params); 16868 *vdev_id = fixed_param->vdev_id; 16869 if (num_scans > WMI_ROAM_SCAN_STATS_MAX) { 16870 wmi_err_rl("%u exceeded maximum roam scan stats: %u", 16871 num_scans, WMI_ROAM_SCAN_STATS_MAX); 16872 return QDF_STATUS_E_INVAL; 16873 } 16874 16875 total_len = sizeof(*res) + num_scans * scan_param_size; 16876 16877 res = qdf_mem_malloc(total_len); 16878 if (!res) 16879 return QDF_STATUS_E_NOMEM; 16880 16881 if (!num_scans) { 16882 *res_param = res; 16883 return QDF_STATUS_SUCCESS; 16884 } 16885 16886 if (param_buf->client_id && 16887 param_buf->num_client_id == num_scans) 16888 client_id = param_buf->client_id; 16889 16890 if (param_buf->timestamp && 16891 param_buf->num_timestamp == num_scans) 16892 timestamp = param_buf->timestamp; 16893 16894 if (param_buf->old_bssid && 16895 param_buf->num_old_bssid == num_scans) 16896 old_bssid = param_buf->old_bssid; 16897 16898 if (param_buf->new_bssid && 16899 param_buf->num_new_bssid == num_scans) 16900 new_bssid = param_buf->new_bssid; 16901 16902 if (param_buf->is_roaming_success && 16903 param_buf->num_is_roaming_success == num_scans) 16904 is_roaming_success = param_buf->is_roaming_success; 16905 16906 if (param_buf->roam_reason && 16907 param_buf->num_roam_reason == num_scans) 16908 roam_reason = param_buf->roam_reason; 16909 16910 if (param_buf->num_channels && 16911 param_buf->num_num_channels == num_scans) { 16912 uint32_t count, chan_info_sum = 0; 16913 16914 num_channels = param_buf->num_channels; 16915 for (count = 0; count < param_buf->num_num_channels; count++) { 16916 if (param_buf->num_channels[count] > 16917 WMI_ROAM_SCAN_STATS_CHANNELS_MAX) { 16918 wmi_err_rl("%u exceeded max scan channels %u", 16919 param_buf->num_channels[count], 16920 WMI_ROAM_SCAN_STATS_CHANNELS_MAX); 16921 goto error; 16922 } 16923 chan_info_sum += param_buf->num_channels[count]; 16924 } 16925 16926 if (param_buf->chan_info && 16927 param_buf->num_chan_info == chan_info_sum) 16928 chan_info = param_buf->chan_info; 16929 } 16930 16931 if (param_buf->num_roam_candidates && 16932 param_buf->num_num_roam_candidates == num_scans) { 16933 uint32_t cnt, roam_cand_sum = 0; 16934 16935 num_roam_candidates = param_buf->num_roam_candidates; 16936 for (cnt = 0; cnt < param_buf->num_num_roam_candidates; cnt++) { 16937 if (param_buf->num_roam_candidates[cnt] > 16938 WMI_ROAM_SCAN_STATS_CANDIDATES_MAX) { 16939 wmi_err_rl("%u exceeded max scan cand %u", 16940 param_buf->num_roam_candidates[cnt], 16941 WMI_ROAM_SCAN_STATS_CANDIDATES_MAX); 16942 goto error; 16943 } 16944 roam_cand_sum += param_buf->num_roam_candidates[cnt]; 16945 } 16946 16947 if (param_buf->bssid && 16948 param_buf->num_bssid == roam_cand_sum) 16949 bssid = param_buf->bssid; 16950 16951 if (param_buf->score && 16952 param_buf->num_score == roam_cand_sum) 16953 score = param_buf->score; 16954 16955 if (param_buf->channel && 16956 param_buf->num_channel == roam_cand_sum) 16957 channel = param_buf->channel; 16958 16959 if (param_buf->rssi && 16960 param_buf->num_rssi == roam_cand_sum) 16961 rssi = param_buf->rssi; 16962 } 16963 16964 res->num_roam_scans = num_scans; 16965 for (i = 0; i < num_scans; i++) { 16966 struct wmi_roam_scan_stats_params *roam = &res->roam_scan[i]; 16967 16968 if (timestamp) 16969 roam->time_stamp = timestamp[i].lower32bit | 16970 (timestamp[i].upper32bit << 31); 16971 16972 if (client_id) 16973 roam->client_id = client_id[i]; 16974 16975 if (num_channels) { 16976 roam->num_scan_chans = num_channels[i]; 16977 if (chan_info) { 16978 for (j = 0; j < num_channels[i]; j++) 16979 roam->scan_freqs[j] = 16980 chan_info[chan_idx++]; 16981 } 16982 } 16983 16984 if (is_roaming_success) 16985 roam->is_roam_successful = is_roaming_success[i]; 16986 16987 if (roam_reason) { 16988 roam->trigger_id = roam_reason[i].trigger_id; 16989 roam->trigger_value = roam_reason[i].trigger_value; 16990 } 16991 16992 if (num_roam_candidates) { 16993 roam->num_roam_candidates = num_roam_candidates[i]; 16994 16995 for (j = 0; j < num_roam_candidates[i]; j++) { 16996 if (score) 16997 roam->cand[j].score = score[cand_idx]; 16998 if (rssi) 16999 roam->cand[j].rssi = rssi[cand_idx]; 17000 if (channel) 17001 roam->cand[j].freq = 17002 channel[cand_idx]; 17003 17004 if (bssid) 17005 WMI_MAC_ADDR_TO_CHAR_ARRAY( 17006 &bssid[cand_idx], 17007 roam->cand[j].bssid); 17008 17009 cand_idx++; 17010 } 17011 } 17012 17013 if (old_bssid) 17014 WMI_MAC_ADDR_TO_CHAR_ARRAY(&old_bssid[i], 17015 roam->old_bssid); 17016 17017 if (new_bssid) 17018 WMI_MAC_ADDR_TO_CHAR_ARRAY(&new_bssid[i], 17019 roam->new_bssid); 17020 } 17021 17022 *res_param = res; 17023 17024 return QDF_STATUS_SUCCESS; 17025 error: 17026 qdf_mem_free(res); 17027 return QDF_STATUS_E_FAILURE; 17028 } 17029 17030 /** 17031 * extract_offload_bcn_tx_status_evt() - Extract beacon-tx status event 17032 * @wmi_handle: wmi handle 17033 * @evt_buf: pointer to event buffer 17034 * @vdev_id: output pointer to hold vdev id 17035 * @tx_status: output pointer to hold the tx_status 17036 * 17037 * Return: QDF_STATUS 17038 */ 17039 static QDF_STATUS extract_offload_bcn_tx_status_evt(wmi_unified_t wmi_handle, 17040 void *evt_buf, 17041 uint32_t *vdev_id, 17042 uint32_t *tx_status) { 17043 WMI_OFFLOAD_BCN_TX_STATUS_EVENTID_param_tlvs *param_buf; 17044 wmi_offload_bcn_tx_status_event_fixed_param *bcn_tx_status_event; 17045 17046 param_buf = (WMI_OFFLOAD_BCN_TX_STATUS_EVENTID_param_tlvs *)evt_buf; 17047 if (!param_buf) { 17048 wmi_err("Invalid offload bcn tx status event buffer"); 17049 return QDF_STATUS_E_INVAL; 17050 } 17051 17052 bcn_tx_status_event = param_buf->fixed_param; 17053 *vdev_id = bcn_tx_status_event->vdev_id; 17054 *tx_status = bcn_tx_status_event->tx_status; 17055 17056 return QDF_STATUS_SUCCESS; 17057 } 17058 17059 #ifdef WLAN_SUPPORT_GREEN_AP 17060 static QDF_STATUS extract_green_ap_egap_status_info_tlv( 17061 uint8_t *evt_buf, 17062 struct wlan_green_ap_egap_status_info *egap_status_info_params) 17063 { 17064 WMI_AP_PS_EGAP_INFO_EVENTID_param_tlvs *param_buf; 17065 wmi_ap_ps_egap_info_event_fixed_param *egap_info_event; 17066 wmi_ap_ps_egap_info_chainmask_list *chainmask_event; 17067 17068 param_buf = (WMI_AP_PS_EGAP_INFO_EVENTID_param_tlvs *)evt_buf; 17069 if (!param_buf) { 17070 wmi_err("Invalid EGAP Info status event buffer"); 17071 return QDF_STATUS_E_INVAL; 17072 } 17073 17074 egap_info_event = (wmi_ap_ps_egap_info_event_fixed_param *) 17075 param_buf->fixed_param; 17076 chainmask_event = (wmi_ap_ps_egap_info_chainmask_list *) 17077 param_buf->chainmask_list; 17078 17079 if (!egap_info_event || !chainmask_event) { 17080 wmi_err("Invalid EGAP Info event or chainmask event"); 17081 return QDF_STATUS_E_INVAL; 17082 } 17083 17084 egap_status_info_params->status = egap_info_event->status; 17085 egap_status_info_params->mac_id = chainmask_event->mac_id; 17086 egap_status_info_params->tx_chainmask = chainmask_event->tx_chainmask; 17087 egap_status_info_params->rx_chainmask = chainmask_event->rx_chainmask; 17088 17089 return QDF_STATUS_SUCCESS; 17090 } 17091 #endif 17092 17093 /* 17094 * extract_comb_phyerr_tlv() - extract comb phy error from event 17095 * @wmi_handle: wmi handle 17096 * @evt_buf: pointer to event buffer 17097 * @datalen: data length of event buffer 17098 * @buf_offset: Pointer to hold value of current event buffer offset 17099 * post extraction 17100 * @phyerr: Pointer to hold phyerr 17101 * 17102 * Return: QDF_STATUS 17103 */ 17104 static QDF_STATUS extract_comb_phyerr_tlv(wmi_unified_t wmi_handle, 17105 void *evt_buf, 17106 uint16_t datalen, 17107 uint16_t *buf_offset, 17108 wmi_host_phyerr_t *phyerr) 17109 { 17110 WMI_PHYERR_EVENTID_param_tlvs *param_tlvs; 17111 wmi_comb_phyerr_rx_hdr *pe_hdr; 17112 17113 param_tlvs = (WMI_PHYERR_EVENTID_param_tlvs *)evt_buf; 17114 if (!param_tlvs) { 17115 wmi_debug("Received null data from FW"); 17116 return QDF_STATUS_E_FAILURE; 17117 } 17118 17119 pe_hdr = param_tlvs->hdr; 17120 if (!pe_hdr) { 17121 wmi_debug("Received Data PE Header is NULL"); 17122 return QDF_STATUS_E_FAILURE; 17123 } 17124 17125 /* Ensure it's at least the size of the header */ 17126 if (datalen < sizeof(*pe_hdr)) { 17127 wmi_debug("Expected minimum size %zu, received %d", 17128 sizeof(*pe_hdr), datalen); 17129 return QDF_STATUS_E_FAILURE; 17130 } 17131 17132 phyerr->pdev_id = wmi_handle->ops-> 17133 convert_pdev_id_target_to_host(wmi_handle, pe_hdr->pdev_id); 17134 phyerr->tsf64 = pe_hdr->tsf_l32; 17135 phyerr->tsf64 |= (((uint64_t)pe_hdr->tsf_u32) << 32); 17136 phyerr->bufp = param_tlvs->bufp; 17137 17138 if (pe_hdr->buf_len > param_tlvs->num_bufp) { 17139 wmi_debug("Invalid buf_len %d, num_bufp %d", 17140 pe_hdr->buf_len, param_tlvs->num_bufp); 17141 return QDF_STATUS_E_FAILURE; 17142 } 17143 17144 phyerr->buf_len = pe_hdr->buf_len; 17145 phyerr->phy_err_mask0 = pe_hdr->rsPhyErrMask0; 17146 phyerr->phy_err_mask1 = pe_hdr->rsPhyErrMask1; 17147 *buf_offset = sizeof(*pe_hdr) + sizeof(uint32_t); 17148 17149 return QDF_STATUS_SUCCESS; 17150 } 17151 17152 /** 17153 * extract_single_phyerr_tlv() - extract single phy error from event 17154 * @wmi_handle: wmi handle 17155 * @evt_buf: pointer to event buffer 17156 * @datalen: data length of event buffer 17157 * @buf_offset: Pointer to hold value of current event buffer offset 17158 * post extraction 17159 * @phyerr: Pointer to hold phyerr 17160 * 17161 * Return: QDF_STATUS 17162 */ 17163 static QDF_STATUS extract_single_phyerr_tlv(wmi_unified_t wmi_handle, 17164 void *evt_buf, 17165 uint16_t datalen, 17166 uint16_t *buf_offset, 17167 wmi_host_phyerr_t *phyerr) 17168 { 17169 wmi_single_phyerr_rx_event *ev; 17170 uint16_t n = *buf_offset; 17171 uint8_t *data = (uint8_t *)evt_buf; 17172 17173 if (n < datalen) { 17174 if ((datalen - n) < sizeof(ev->hdr)) { 17175 wmi_debug("Not enough space. len=%d, n=%d, hdr=%zu", 17176 datalen, n, sizeof(ev->hdr)); 17177 return QDF_STATUS_E_FAILURE; 17178 } 17179 17180 /* 17181 * Obtain a pointer to the beginning of the current event. 17182 * data[0] is the beginning of the WMI payload. 17183 */ 17184 ev = (wmi_single_phyerr_rx_event *)&data[n]; 17185 17186 /* 17187 * Sanity check the buffer length of the event against 17188 * what we currently have. 17189 * 17190 * Since buf_len is 32 bits, we check if it overflows 17191 * a large 32 bit value. It's not 0x7fffffff because 17192 * we increase n by (buf_len + sizeof(hdr)), which would 17193 * in itself cause n to overflow. 17194 * 17195 * If "int" is 64 bits then this becomes a moot point. 17196 */ 17197 if (ev->hdr.buf_len > PHYERROR_MAX_BUFFER_LENGTH) { 17198 wmi_debug("buf_len is garbage 0x%x", ev->hdr.buf_len); 17199 return QDF_STATUS_E_FAILURE; 17200 } 17201 17202 if ((n + ev->hdr.buf_len) > datalen) { 17203 wmi_debug("len exceeds n=%d, buf_len=%d, datalen=%d", 17204 n, ev->hdr.buf_len, datalen); 17205 return QDF_STATUS_E_FAILURE; 17206 } 17207 17208 phyerr->phy_err_code = WMI_UNIFIED_PHYERRCODE_GET(&ev->hdr); 17209 phyerr->tsf_timestamp = ev->hdr.tsf_timestamp; 17210 phyerr->bufp = &ev->bufp[0]; 17211 phyerr->buf_len = ev->hdr.buf_len; 17212 phyerr->rf_info.rssi_comb = WMI_UNIFIED_RSSI_COMB_GET(&ev->hdr); 17213 17214 /* 17215 * Advance the buffer pointer to the next PHY error. 17216 * buflen is the length of this payload, so we need to 17217 * advance past the current header _AND_ the payload. 17218 */ 17219 n += sizeof(*ev) + ev->hdr.buf_len; 17220 } 17221 *buf_offset = n; 17222 17223 return QDF_STATUS_SUCCESS; 17224 } 17225 17226 /** 17227 * extract_esp_estimation_ev_param_tlv() - extract air time from event 17228 * @wmi_handle: wmi handle 17229 * @evt_buf: pointer to event buffer 17230 * @param: Pointer to hold esp event 17231 * 17232 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_INVAL on failure 17233 */ 17234 static QDF_STATUS 17235 extract_esp_estimation_ev_param_tlv(wmi_unified_t wmi_handle, 17236 void *evt_buf, 17237 struct esp_estimation_event *param) 17238 { 17239 WMI_ESP_ESTIMATE_EVENTID_param_tlvs *param_buf; 17240 wmi_esp_estimate_event_fixed_param *esp_event; 17241 17242 param_buf = (WMI_ESP_ESTIMATE_EVENTID_param_tlvs *)evt_buf; 17243 if (!param_buf) { 17244 wmi_err("Invalid ESP Estimate Event buffer"); 17245 return QDF_STATUS_E_INVAL; 17246 } 17247 esp_event = param_buf->fixed_param; 17248 param->ac_airtime_percentage = esp_event->ac_airtime_percentage; 17249 17250 param->pdev_id = convert_target_pdev_id_to_host_pdev_id( 17251 wmi_handle, 17252 esp_event->pdev_id); 17253 17254 if (param->pdev_id == WMI_HOST_PDEV_ID_INVALID) 17255 return QDF_STATUS_E_FAILURE; 17256 17257 return QDF_STATUS_SUCCESS; 17258 } 17259 17260 /* 17261 * send_bss_color_change_enable_cmd_tlv() - Send command to enable or disable of 17262 * updating bss color change within firmware when AP announces bss color change. 17263 * @wmi_handle: wmi handle 17264 * @vdev_id: vdev ID 17265 * @enable: enable bss color change within firmware 17266 * 17267 * Send WMI_BSS_COLOR_CHANGE_ENABLE_CMDID parameters to fw. 17268 * 17269 * Return: QDF_STATUS 17270 */ 17271 static QDF_STATUS send_bss_color_change_enable_cmd_tlv(wmi_unified_t wmi_handle, 17272 uint32_t vdev_id, 17273 bool enable) 17274 { 17275 wmi_buf_t buf; 17276 wmi_bss_color_change_enable_fixed_param *cmd; 17277 uint8_t len = sizeof(wmi_bss_color_change_enable_fixed_param); 17278 17279 buf = wmi_buf_alloc(wmi_handle, len); 17280 if (!buf) 17281 return QDF_STATUS_E_NOMEM; 17282 17283 cmd = (wmi_bss_color_change_enable_fixed_param *)wmi_buf_data(buf); 17284 WMITLV_SET_HDR(&cmd->tlv_header, 17285 WMITLV_TAG_STRUC_wmi_bss_color_change_enable_fixed_param, 17286 WMITLV_GET_STRUCT_TLVLEN 17287 (wmi_bss_color_change_enable_fixed_param)); 17288 cmd->vdev_id = vdev_id; 17289 cmd->enable = enable; 17290 wmi_mtrace(WMI_BSS_COLOR_CHANGE_ENABLE_CMDID, cmd->vdev_id, 0); 17291 if (wmi_unified_cmd_send(wmi_handle, buf, len, 17292 WMI_BSS_COLOR_CHANGE_ENABLE_CMDID)) { 17293 wmi_err("Failed to send WMI_BSS_COLOR_CHANGE_ENABLE_CMDID"); 17294 wmi_buf_free(buf); 17295 return QDF_STATUS_E_FAILURE; 17296 } 17297 17298 return QDF_STATUS_SUCCESS; 17299 } 17300 17301 /** 17302 * send_obss_color_collision_cfg_cmd_tlv() - send bss color detection 17303 * configurations to firmware. 17304 * @wmi_handle: wmi handle 17305 * @cfg_param: obss detection configurations 17306 * 17307 * Send WMI_OBSS_COLOR_COLLISION_DET_CONFIG_CMDID parameters to fw. 17308 * 17309 * Return: QDF_STATUS 17310 */ 17311 static QDF_STATUS send_obss_color_collision_cfg_cmd_tlv( 17312 wmi_unified_t wmi_handle, 17313 struct wmi_obss_color_collision_cfg_param *cfg_param) 17314 { 17315 wmi_buf_t buf; 17316 wmi_obss_color_collision_det_config_fixed_param *cmd; 17317 uint8_t len = sizeof(wmi_obss_color_collision_det_config_fixed_param); 17318 17319 buf = wmi_buf_alloc(wmi_handle, len); 17320 if (!buf) 17321 return QDF_STATUS_E_NOMEM; 17322 17323 cmd = (wmi_obss_color_collision_det_config_fixed_param *)wmi_buf_data( 17324 buf); 17325 WMITLV_SET_HDR(&cmd->tlv_header, 17326 WMITLV_TAG_STRUC_wmi_obss_color_collision_det_config_fixed_param, 17327 WMITLV_GET_STRUCT_TLVLEN 17328 (wmi_obss_color_collision_det_config_fixed_param)); 17329 cmd->vdev_id = cfg_param->vdev_id; 17330 cmd->flags = cfg_param->flags; 17331 cmd->current_bss_color = cfg_param->current_bss_color; 17332 cmd->detection_period_ms = cfg_param->detection_period_ms; 17333 cmd->scan_period_ms = cfg_param->scan_period_ms; 17334 cmd->free_slot_expiry_time_ms = cfg_param->free_slot_expiry_time_ms; 17335 17336 switch (cfg_param->evt_type) { 17337 case OBSS_COLOR_COLLISION_DETECTION_DISABLE: 17338 cmd->evt_type = WMI_BSS_COLOR_COLLISION_DISABLE; 17339 break; 17340 case OBSS_COLOR_COLLISION_DETECTION: 17341 cmd->evt_type = WMI_BSS_COLOR_COLLISION_DETECTION; 17342 break; 17343 case OBSS_COLOR_FREE_SLOT_TIMER_EXPIRY: 17344 cmd->evt_type = WMI_BSS_COLOR_FREE_SLOT_TIMER_EXPIRY; 17345 break; 17346 case OBSS_COLOR_FREE_SLOT_AVAILABLE: 17347 cmd->evt_type = WMI_BSS_COLOR_FREE_SLOT_AVAILABLE; 17348 break; 17349 default: 17350 wmi_err("Invalid event type: %d", cfg_param->evt_type); 17351 wmi_buf_free(buf); 17352 return QDF_STATUS_E_FAILURE; 17353 } 17354 17355 wmi_debug("evt_type: %d vdev id: %d current_bss_color: %d " 17356 "detection_period_ms: %d scan_period_ms: %d " 17357 "free_slot_expiry_timer_ms: %d", 17358 cmd->evt_type, cmd->vdev_id, cmd->current_bss_color, 17359 cmd->detection_period_ms, cmd->scan_period_ms, 17360 cmd->free_slot_expiry_time_ms); 17361 17362 wmi_mtrace(WMI_OBSS_COLOR_COLLISION_DET_CONFIG_CMDID, cmd->vdev_id, 0); 17363 if (wmi_unified_cmd_send(wmi_handle, buf, len, 17364 WMI_OBSS_COLOR_COLLISION_DET_CONFIG_CMDID)) { 17365 wmi_err("Sending OBSS color det cmd failed, vdev_id: %d", 17366 cfg_param->vdev_id); 17367 wmi_buf_free(buf); 17368 return QDF_STATUS_E_FAILURE; 17369 } 17370 17371 return QDF_STATUS_SUCCESS; 17372 } 17373 17374 /** 17375 * extract_obss_color_collision_info_tlv() - Extract bss color collision info 17376 * received from firmware. 17377 * @evt_buf: pointer to event buffer 17378 * @info: Pointer to hold bss collision info 17379 * 17380 * Return: QDF_STATUS 17381 */ 17382 static QDF_STATUS extract_obss_color_collision_info_tlv(uint8_t *evt_buf, 17383 struct wmi_obss_color_collision_info *info) 17384 { 17385 WMI_OBSS_COLOR_COLLISION_DETECTION_EVENTID_param_tlvs *param_buf; 17386 wmi_obss_color_collision_evt_fixed_param *fix_param; 17387 17388 if (!info) { 17389 wmi_err("Invalid obss color buffer"); 17390 return QDF_STATUS_E_INVAL; 17391 } 17392 17393 param_buf = (WMI_OBSS_COLOR_COLLISION_DETECTION_EVENTID_param_tlvs *) 17394 evt_buf; 17395 if (!param_buf) { 17396 wmi_err("Invalid evt_buf"); 17397 return QDF_STATUS_E_INVAL; 17398 } 17399 17400 fix_param = param_buf->fixed_param; 17401 info->vdev_id = fix_param->vdev_id; 17402 info->obss_color_bitmap_bit0to31 = 17403 fix_param->bss_color_bitmap_bit0to31; 17404 info->obss_color_bitmap_bit32to63 = 17405 fix_param->bss_color_bitmap_bit32to63; 17406 17407 switch (fix_param->evt_type) { 17408 case WMI_BSS_COLOR_COLLISION_DISABLE: 17409 info->evt_type = OBSS_COLOR_COLLISION_DETECTION_DISABLE; 17410 break; 17411 case WMI_BSS_COLOR_COLLISION_DETECTION: 17412 info->evt_type = OBSS_COLOR_COLLISION_DETECTION; 17413 break; 17414 case WMI_BSS_COLOR_FREE_SLOT_TIMER_EXPIRY: 17415 info->evt_type = OBSS_COLOR_FREE_SLOT_TIMER_EXPIRY; 17416 break; 17417 case WMI_BSS_COLOR_FREE_SLOT_AVAILABLE: 17418 info->evt_type = OBSS_COLOR_FREE_SLOT_AVAILABLE; 17419 break; 17420 default: 17421 wmi_err("Invalid event type: %d, vdev_id: %d", 17422 fix_param->evt_type, fix_param->vdev_id); 17423 return QDF_STATUS_E_FAILURE; 17424 } 17425 17426 return QDF_STATUS_SUCCESS; 17427 } 17428 17429 static void wmi_11ax_bss_color_attach_tlv(struct wmi_unified *wmi_handle) 17430 { 17431 struct wmi_ops *ops = wmi_handle->ops; 17432 17433 ops->send_obss_color_collision_cfg_cmd = 17434 send_obss_color_collision_cfg_cmd_tlv; 17435 ops->extract_obss_color_collision_info = 17436 extract_obss_color_collision_info_tlv; 17437 } 17438 17439 #if defined(WLAN_SUPPORT_FILS) || defined(CONFIG_BAND_6GHZ) 17440 static QDF_STATUS 17441 send_vdev_fils_enable_cmd_send(struct wmi_unified *wmi_handle, 17442 struct config_fils_params *param) 17443 { 17444 wmi_buf_t buf; 17445 wmi_enable_fils_cmd_fixed_param *cmd; 17446 uint8_t len = sizeof(wmi_enable_fils_cmd_fixed_param); 17447 17448 buf = wmi_buf_alloc(wmi_handle, len); 17449 if (!buf) 17450 return QDF_STATUS_E_NOMEM; 17451 17452 cmd = (wmi_enable_fils_cmd_fixed_param *)wmi_buf_data( 17453 buf); 17454 WMITLV_SET_HDR(&cmd->tlv_header, 17455 WMITLV_TAG_STRUC_wmi_enable_fils_cmd_fixed_param, 17456 WMITLV_GET_STRUCT_TLVLEN 17457 (wmi_enable_fils_cmd_fixed_param)); 17458 cmd->vdev_id = param->vdev_id; 17459 cmd->fd_period = param->fd_period; 17460 if (param->send_prb_rsp_frame) 17461 cmd->flags |= WMI_FILS_FLAGS_BITMAP_BCAST_PROBE_RSP; 17462 wmi_debug("vdev id: %d fd_period: %d cmd->Flags %d", 17463 cmd->vdev_id, cmd->fd_period, cmd->flags); 17464 wmi_mtrace(WMI_ENABLE_FILS_CMDID, cmd->vdev_id, cmd->fd_period); 17465 if (wmi_unified_cmd_send(wmi_handle, buf, len, 17466 WMI_ENABLE_FILS_CMDID)) { 17467 wmi_err("Sending FILS cmd failed, vdev_id: %d", param->vdev_id); 17468 wmi_buf_free(buf); 17469 return QDF_STATUS_E_FAILURE; 17470 } 17471 17472 return QDF_STATUS_SUCCESS; 17473 } 17474 #endif 17475 17476 #ifdef WLAN_MWS_INFO_DEBUGFS 17477 /** 17478 * send_mws_coex_status_req_cmd_tlv() - send coex cmd to fw 17479 * 17480 * @wmi_handle: wmi handle 17481 * @vdev_id: vdev id 17482 * @cmd_id: Coex command id 17483 * 17484 * Send WMI_VDEV_GET_MWS_COEX_INFO_CMDID to fw. 17485 * 17486 * Return: QDF_STATUS 17487 */ 17488 static QDF_STATUS send_mws_coex_status_req_cmd_tlv(wmi_unified_t wmi_handle, 17489 uint32_t vdev_id, 17490 uint32_t cmd_id) 17491 { 17492 wmi_buf_t buf; 17493 wmi_vdev_get_mws_coex_info_cmd_fixed_param *cmd; 17494 uint16_t len = sizeof(*cmd); 17495 int ret; 17496 17497 buf = wmi_buf_alloc(wmi_handle, len); 17498 if (!buf) { 17499 wmi_err("Failed to allocate wmi buffer"); 17500 return QDF_STATUS_E_NOMEM; 17501 } 17502 17503 cmd = (wmi_vdev_get_mws_coex_info_cmd_fixed_param *)wmi_buf_data(buf); 17504 WMITLV_SET_HDR(&cmd->tlv_header, 17505 WMITLV_TAG_STRUC_wmi_vdev_get_mws_coex_info_cmd_fixed_param, 17506 WMITLV_GET_STRUCT_TLVLEN 17507 (wmi_vdev_get_mws_coex_info_cmd_fixed_param)); 17508 cmd->vdev_id = vdev_id; 17509 cmd->cmd_id = cmd_id; 17510 wmi_mtrace(WMI_VDEV_GET_MWS_COEX_INFO_CMDID, vdev_id, 0); 17511 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 17512 WMI_VDEV_GET_MWS_COEX_INFO_CMDID); 17513 if (QDF_IS_STATUS_ERROR(ret)) { 17514 wmi_err("Failed to send set param command ret = %d", ret); 17515 wmi_buf_free(buf); 17516 } 17517 return ret; 17518 } 17519 #endif 17520 17521 #ifdef FEATURE_MEC_OFFLOAD 17522 static QDF_STATUS 17523 send_pdev_set_mec_timer_cmd_tlv(struct wmi_unified *wmi_handle, 17524 struct set_mec_timer_params *param) 17525 { 17526 wmi_pdev_mec_aging_timer_config_cmd_fixed_param *cmd; 17527 wmi_buf_t buf; 17528 int32_t len = sizeof(*cmd); 17529 17530 buf = wmi_buf_alloc(wmi_handle, len); 17531 if (!buf) { 17532 wmi_err("wmi_buf_alloc failed"); 17533 return QDF_STATUS_E_FAILURE; 17534 } 17535 cmd = (wmi_pdev_mec_aging_timer_config_cmd_fixed_param *) 17536 wmi_buf_data(buf); 17537 WMITLV_SET_HDR(&cmd->tlv_header, 17538 WMITLV_TAG_STRUC_wmi_pdev_mec_aging_timer_config_cmd_fixed_param, 17539 WMITLV_GET_STRUCT_TLVLEN( 17540 wmi_pdev_mec_aging_timer_config_cmd_fixed_param)); 17541 cmd->pdev_id = param->pdev_id; 17542 cmd->mec_aging_timer_threshold = param->mec_aging_timer_threshold; 17543 17544 wmi_mtrace(WMI_PDEV_MEC_AGING_TIMER_CONFIG_CMDID, param->vdev_id, 0); 17545 if (wmi_unified_cmd_send(wmi_handle, buf, len, 17546 WMI_PDEV_MEC_AGING_TIMER_CONFIG_CMDID)) { 17547 wmi_err("Failed to set mec aging timer param"); 17548 wmi_buf_free(buf); 17549 return QDF_STATUS_E_FAILURE; 17550 } 17551 17552 return QDF_STATUS_SUCCESS; 17553 } 17554 #endif 17555 17556 #ifdef WIFI_POS_CONVERGED 17557 /** 17558 * extract_oem_response_param_tlv() - Extract oem response params 17559 * @wmi_handle: wmi handle 17560 * @resp_buf: response buffer 17561 * @oem_resp_param: pointer to hold oem response params 17562 * 17563 * Return: QDF_STATUS_SUCCESS on success or proper error code. 17564 */ 17565 static QDF_STATUS 17566 extract_oem_response_param_tlv(wmi_unified_t wmi_handle, void *resp_buf, 17567 struct wmi_oem_response_param *oem_resp_param) 17568 { 17569 uint64_t temp_addr; 17570 WMI_OEM_RESPONSE_EVENTID_param_tlvs *param_buf = 17571 (WMI_OEM_RESPONSE_EVENTID_param_tlvs *)resp_buf; 17572 17573 if (!param_buf) { 17574 wmi_err("Invalid OEM response"); 17575 return QDF_STATUS_E_INVAL; 17576 } 17577 17578 if (param_buf->num_data) { 17579 oem_resp_param->num_data1 = param_buf->num_data; 17580 oem_resp_param->data_1 = param_buf->data; 17581 } 17582 17583 if (param_buf->num_data2) { 17584 oem_resp_param->num_data2 = param_buf->num_data2; 17585 oem_resp_param->data_2 = param_buf->data2; 17586 } 17587 17588 if (param_buf->indirect_data) { 17589 oem_resp_param->indirect_data.pdev_id = 17590 param_buf->indirect_data->pdev_id; 17591 temp_addr = (param_buf->indirect_data->addr_hi) & 0xf; 17592 oem_resp_param->indirect_data.addr = 17593 param_buf->indirect_data->addr_lo + 17594 ((uint64_t)temp_addr << 32); 17595 oem_resp_param->indirect_data.len = 17596 param_buf->indirect_data->len; 17597 } 17598 17599 return QDF_STATUS_SUCCESS; 17600 } 17601 #endif /* WIFI_POS_CONVERGED */ 17602 17603 #if defined(WIFI_POS_CONVERGED) && defined(WLAN_FEATURE_RTT_11AZ_SUPPORT) 17604 #define WLAN_PASN_LTF_KEY_SEED_REQUIRED 0x2 17605 17606 static QDF_STATUS 17607 extract_pasn_peer_create_req_event_tlv(wmi_unified_t wmi_handle, void *evt_buf, 17608 struct wifi_pos_pasn_peer_data *dst) 17609 { 17610 WMI_RTT_PASN_PEER_CREATE_REQ_EVENTID_param_tlvs *param_buf; 17611 wmi_rtt_pasn_peer_create_req_event_fixed_param *fixed_param; 17612 wmi_rtt_pasn_peer_create_req_param *buf; 17613 uint8_t security_mode, i; 17614 17615 param_buf = (WMI_RTT_PASN_PEER_CREATE_REQ_EVENTID_param_tlvs *)evt_buf; 17616 if (!param_buf) { 17617 wmi_err("Invalid peer_create req buffer"); 17618 return QDF_STATUS_E_INVAL; 17619 } 17620 17621 fixed_param = param_buf->fixed_param; 17622 17623 if (param_buf->num_rtt_pasn_peer_param > 17624 ((WMI_SVC_MSG_MAX_SIZE - sizeof(*fixed_param)) / 17625 sizeof(wmi_rtt_pasn_peer_create_req_param))) { 17626 wmi_err("Invalid TLV size"); 17627 return QDF_STATUS_E_INVAL; 17628 } 17629 17630 if (!param_buf->num_rtt_pasn_peer_param || 17631 param_buf->num_rtt_pasn_peer_param > WLAN_MAX_11AZ_PEERS) { 17632 wmi_err("Invalid num TLV:%d", 17633 param_buf->num_rtt_pasn_peer_param); 17634 return QDF_STATUS_E_INVAL; 17635 } 17636 17637 dst->vdev_id = fixed_param->vdev_id; 17638 if (dst->vdev_id >= WLAN_UMAC_PDEV_MAX_VDEVS) { 17639 wmi_err("Invalid vdev id:%d", dst->vdev_id); 17640 return QDF_STATUS_E_INVAL; 17641 } 17642 17643 buf = param_buf->rtt_pasn_peer_param; 17644 if (!buf) { 17645 wmi_err("NULL peer param TLV"); 17646 return QDF_STATUS_E_INVAL; 17647 } 17648 17649 for (i = 0; i < param_buf->num_rtt_pasn_peer_param; i++) { 17650 WMI_MAC_ADDR_TO_CHAR_ARRAY(&buf->self_mac_addr, 17651 dst->peer_info[i].self_mac.bytes); 17652 WMI_MAC_ADDR_TO_CHAR_ARRAY(&buf->dest_mac_addr, 17653 dst->peer_info[i].peer_mac.bytes); 17654 security_mode = WMI_RTT_PASN_PEER_CREATE_SECURITY_MODE_GET( 17655 buf->control_flag); 17656 if (security_mode) 17657 dst->peer_info[i].peer_type = 17658 WLAN_WIFI_POS_PASN_SECURE_PEER; 17659 else 17660 dst->peer_info[i].peer_type = 17661 WLAN_WIFI_POS_PASN_UNSECURE_PEER; 17662 if (security_mode & WLAN_PASN_LTF_KEY_SEED_REQUIRED) 17663 dst->peer_info[i].is_ltf_keyseed_required = true; 17664 17665 dst->peer_info[i].force_self_mac_usage = 17666 WMI_RTT_PASN_PEER_CREATE_FORCE_SELF_MAC_USE_GET( 17667 buf->control_flag); 17668 dst->num_peers++; 17669 buf++; 17670 } 17671 17672 return QDF_STATUS_SUCCESS; 17673 } 17674 17675 static QDF_STATUS 17676 extract_pasn_peer_delete_req_event_tlv(wmi_unified_t wmi_handle, void *evt_buf, 17677 struct wifi_pos_pasn_peer_data *dst) 17678 { 17679 WMI_RTT_PASN_PEER_DELETE_EVENTID_param_tlvs *param_buf; 17680 wmi_rtt_pasn_peer_delete_event_fixed_param *fixed_param; 17681 wmi_rtt_pasn_peer_delete_param *buf; 17682 uint8_t i; 17683 17684 param_buf = (WMI_RTT_PASN_PEER_DELETE_EVENTID_param_tlvs *)evt_buf; 17685 if (!param_buf) { 17686 wmi_err("Invalid peer_delete evt buffer"); 17687 return QDF_STATUS_E_INVAL; 17688 } 17689 17690 fixed_param = param_buf->fixed_param; 17691 17692 if (param_buf->num_rtt_pasn_peer_param > 17693 ((WMI_SVC_MSG_MAX_SIZE - sizeof(*fixed_param)) / 17694 sizeof(wmi_rtt_pasn_peer_delete_param))) { 17695 wmi_err("Invalid TLV size"); 17696 return QDF_STATUS_E_INVAL; 17697 } 17698 17699 if (!param_buf->num_rtt_pasn_peer_param || 17700 param_buf->num_rtt_pasn_peer_param > WLAN_MAX_11AZ_PEERS) { 17701 wmi_err("Invalid num TLV:%d", 17702 param_buf->num_rtt_pasn_peer_param); 17703 return QDF_STATUS_E_INVAL; 17704 } 17705 17706 dst->vdev_id = fixed_param->vdev_id; 17707 if (dst->vdev_id >= WLAN_UMAC_PDEV_MAX_VDEVS) { 17708 wmi_err("Invalid vdev id:%d", dst->vdev_id); 17709 return QDF_STATUS_E_INVAL; 17710 } 17711 17712 buf = param_buf->rtt_pasn_peer_param; 17713 if (!buf) { 17714 wmi_err("NULL peer param TLV"); 17715 return QDF_STATUS_E_INVAL; 17716 } 17717 17718 for (i = 0; i < param_buf->num_rtt_pasn_peer_param; i++) { 17719 WMI_MAC_ADDR_TO_CHAR_ARRAY(&buf->peer_mac_addr, 17720 dst->peer_info[i].peer_mac.bytes); 17721 dst->peer_info[i].control_flags = buf->control_flag; 17722 17723 dst->num_peers++; 17724 buf++; 17725 } 17726 17727 return QDF_STATUS_SUCCESS; 17728 } 17729 17730 static QDF_STATUS 17731 send_rtt_pasn_auth_status_cmd_tlv(wmi_unified_t wmi_handle, 17732 struct wlan_pasn_auth_status *data) 17733 { 17734 QDF_STATUS status; 17735 wmi_buf_t buf; 17736 wmi_rtt_pasn_auth_status_cmd_fixed_param *fixed_param; 17737 uint8_t *buf_ptr; 17738 uint8_t i; 17739 size_t len = sizeof(*fixed_param) + 17740 data->num_peers * sizeof(wmi_rtt_pasn_auth_status_param) + 17741 WMI_TLV_HDR_SIZE; 17742 17743 buf = wmi_buf_alloc(wmi_handle, len); 17744 if (!buf) { 17745 wmi_err("wmi_buf_alloc failed"); 17746 return QDF_STATUS_E_FAILURE; 17747 } 17748 buf_ptr = (uint8_t *)wmi_buf_data(buf); 17749 fixed_param = 17750 (wmi_rtt_pasn_auth_status_cmd_fixed_param *)wmi_buf_data(buf); 17751 WMITLV_SET_HDR(&fixed_param->tlv_header, 17752 WMITLV_TAG_STRUC_wmi_rtt_pasn_auth_status_cmd_fixed_param, 17753 WMITLV_GET_STRUCT_TLVLEN( 17754 wmi_rtt_pasn_auth_status_cmd_fixed_param)); 17755 buf_ptr += sizeof(*fixed_param); 17756 17757 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 17758 (data->num_peers * 17759 sizeof(wmi_rtt_pasn_auth_status_param))); 17760 buf_ptr += WMI_TLV_HDR_SIZE; 17761 17762 for (i = 0; i < data->num_peers; i++) { 17763 wmi_rtt_pasn_auth_status_param *auth_status_tlv = 17764 (wmi_rtt_pasn_auth_status_param *)buf_ptr; 17765 17766 WMITLV_SET_HDR(&auth_status_tlv->tlv_header, 17767 WMITLV_TAG_STRUC_wmi_rtt_pasn_auth_status_param, 17768 WMITLV_GET_STRUCT_TLVLEN(wmi_rtt_pasn_auth_status_param)); 17769 17770 WMI_CHAR_ARRAY_TO_MAC_ADDR(data->auth_status[i].peer_mac.bytes, 17771 &auth_status_tlv->peer_mac_addr); 17772 WMI_CHAR_ARRAY_TO_MAC_ADDR(data->auth_status[i].self_mac.bytes, 17773 &auth_status_tlv->source_mac_addr); 17774 auth_status_tlv->status = data->auth_status[i].status; 17775 wmi_debug("peer_mac: " QDF_MAC_ADDR_FMT " self_mac:" QDF_MAC_ADDR_FMT " status:%d", 17776 QDF_MAC_ADDR_REF(data->auth_status[i].peer_mac.bytes), 17777 QDF_MAC_ADDR_REF(data->auth_status[i].self_mac.bytes), 17778 auth_status_tlv->status); 17779 17780 buf_ptr += sizeof(wmi_rtt_pasn_auth_status_param); 17781 } 17782 17783 wmi_mtrace(WMI_RTT_PASN_AUTH_STATUS_CMD, 0, 0); 17784 status = wmi_unified_cmd_send(wmi_handle, buf, len, 17785 WMI_RTT_PASN_AUTH_STATUS_CMD); 17786 if (QDF_IS_STATUS_ERROR(status)) { 17787 wmi_err("Failed to send Auth status command ret = %d", status); 17788 wmi_buf_free(buf); 17789 } 17790 17791 return status; 17792 } 17793 17794 static QDF_STATUS 17795 send_rtt_pasn_deauth_cmd_tlv(wmi_unified_t wmi_handle, 17796 struct qdf_mac_addr *peer_mac) 17797 { 17798 QDF_STATUS status; 17799 wmi_buf_t buf; 17800 wmi_rtt_pasn_deauth_cmd_fixed_param *fixed_param; 17801 size_t len = sizeof(*fixed_param); 17802 17803 buf = wmi_buf_alloc(wmi_handle, len); 17804 if (!buf) { 17805 wmi_err("wmi_buf_alloc failed"); 17806 return QDF_STATUS_E_FAILURE; 17807 } 17808 fixed_param = 17809 (wmi_rtt_pasn_deauth_cmd_fixed_param *)wmi_buf_data(buf); 17810 WMITLV_SET_HDR(&fixed_param->tlv_header, 17811 WMITLV_TAG_STRUC_wmi_rtt_pasn_deauth_cmd_fixed_param, 17812 WMITLV_GET_STRUCT_TLVLEN( 17813 wmi_rtt_pasn_deauth_cmd_fixed_param)); 17814 WMI_CHAR_ARRAY_TO_MAC_ADDR(peer_mac->bytes, 17815 &fixed_param->peer_mac_addr); 17816 17817 wmi_mtrace(WMI_RTT_PASN_DEAUTH_CMD, 0, 0); 17818 status = wmi_unified_cmd_send(wmi_handle, buf, len, 17819 WMI_RTT_PASN_DEAUTH_CMD); 17820 if (QDF_IS_STATUS_ERROR(status)) { 17821 wmi_err("Failed to send pasn deauth command ret = %d", status); 17822 wmi_buf_free(buf); 17823 } 17824 17825 return status; 17826 } 17827 #endif /* WLAN_FEATURE_RTT_11AZ_SUPPORT */ 17828 17829 static QDF_STATUS 17830 send_vdev_set_ltf_key_seed_cmd_tlv(wmi_unified_t wmi_handle, 17831 struct wlan_crypto_ltf_keyseed_data *data) 17832 { 17833 QDF_STATUS status; 17834 wmi_buf_t buf; 17835 wmi_vdev_set_ltf_key_seed_cmd_fixed_param *fixed_param; 17836 uint8_t *buf_ptr; 17837 size_t len = sizeof(*fixed_param) + data->key_seed_len + 17838 WMI_TLV_HDR_SIZE; 17839 17840 buf = wmi_buf_alloc(wmi_handle, len); 17841 if (!buf) { 17842 wmi_err("wmi_buf_alloc failed"); 17843 return QDF_STATUS_E_FAILURE; 17844 } 17845 17846 buf_ptr = (uint8_t *)wmi_buf_data(buf); 17847 fixed_param = 17848 (wmi_vdev_set_ltf_key_seed_cmd_fixed_param *)wmi_buf_data(buf); 17849 WMITLV_SET_HDR(&fixed_param->tlv_header, 17850 WMITLV_TAG_STRUC_wmi_vdev_set_ltf_key_seed_cmd_fixed_param, 17851 WMITLV_GET_STRUCT_TLVLEN( 17852 wmi_vdev_set_ltf_key_seed_cmd_fixed_param)); 17853 17854 fixed_param->vdev_id = data->vdev_id; 17855 WMI_CHAR_ARRAY_TO_MAC_ADDR(data->peer_mac_addr.bytes, 17856 &fixed_param->peer_macaddr); 17857 fixed_param->key_seed_len = data->key_seed_len; 17858 fixed_param->rsn_authmode = data->rsn_authmode; 17859 17860 buf_ptr += sizeof(*fixed_param); 17861 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_BYTE, 17862 (fixed_param->key_seed_len * sizeof(A_UINT8))); 17863 buf_ptr += WMI_TLV_HDR_SIZE; 17864 17865 qdf_mem_copy(buf_ptr, data->key_seed, fixed_param->key_seed_len); 17866 17867 wmi_mtrace(WMI_VDEV_SET_LTF_KEY_SEED_CMDID, 0, 0); 17868 status = wmi_unified_cmd_send(wmi_handle, buf, len, 17869 WMI_VDEV_SET_LTF_KEY_SEED_CMDID); 17870 if (QDF_IS_STATUS_ERROR(status)) { 17871 wmi_err("Failed to send ltf keyseed command ret = %d", status); 17872 wmi_buf_free(buf); 17873 } 17874 17875 return status; 17876 } 17877 17878 /** 17879 * extract_hw_mode_resp_event_status_tlv() - Extract HW mode change status 17880 * @wmi_handle: wmi handle 17881 * @event_buf: pointer to event buffer 17882 * @cmd_status: status of HW mode change command 17883 * 17884 * Return QDF_STATUS_SUCCESS on success or proper error code. 17885 */ 17886 static QDF_STATUS 17887 extract_hw_mode_resp_event_status_tlv(wmi_unified_t wmi_handle, void *evt_buf, 17888 uint32_t *cmd_status) 17889 { 17890 WMI_PDEV_SET_HW_MODE_RESP_EVENTID_param_tlvs *param_buf; 17891 wmi_pdev_set_hw_mode_response_event_fixed_param *fixed_param; 17892 17893 param_buf = (WMI_PDEV_SET_HW_MODE_RESP_EVENTID_param_tlvs *)evt_buf; 17894 if (!param_buf) { 17895 wmi_err("Invalid mode change event buffer"); 17896 return QDF_STATUS_E_INVAL; 17897 } 17898 17899 fixed_param = param_buf->fixed_param; 17900 if (!fixed_param) { 17901 wmi_err("Invalid fixed param"); 17902 return QDF_STATUS_E_INVAL; 17903 } 17904 17905 *cmd_status = fixed_param->status; 17906 return QDF_STATUS_SUCCESS; 17907 } 17908 17909 #ifdef FEATURE_ANI_LEVEL_REQUEST 17910 static QDF_STATUS send_ani_level_cmd_tlv(wmi_unified_t wmi_handle, 17911 uint32_t *freqs, 17912 uint8_t num_freqs) 17913 { 17914 wmi_buf_t buf; 17915 wmi_get_channel_ani_cmd_fixed_param *cmd; 17916 QDF_STATUS ret; 17917 uint32_t len; 17918 A_UINT32 *chan_list; 17919 uint8_t i, *buf_ptr; 17920 17921 len = sizeof(wmi_get_channel_ani_cmd_fixed_param) + 17922 WMI_TLV_HDR_SIZE + 17923 num_freqs * sizeof(A_UINT32); 17924 17925 buf = wmi_buf_alloc(wmi_handle, len); 17926 if (!buf) 17927 return QDF_STATUS_E_FAILURE; 17928 17929 buf_ptr = (uint8_t *)wmi_buf_data(buf); 17930 cmd = (wmi_get_channel_ani_cmd_fixed_param *)buf_ptr; 17931 WMITLV_SET_HDR(&cmd->tlv_header, 17932 WMITLV_TAG_STRUC_wmi_get_channel_ani_cmd_fixed_param, 17933 WMITLV_GET_STRUCT_TLVLEN( 17934 wmi_get_channel_ani_cmd_fixed_param)); 17935 17936 buf_ptr += sizeof(wmi_get_channel_ani_cmd_fixed_param); 17937 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_UINT32, 17938 (num_freqs * sizeof(A_UINT32))); 17939 17940 chan_list = (A_UINT32 *)(buf_ptr + WMI_TLV_HDR_SIZE); 17941 for (i = 0; i < num_freqs; i++) { 17942 chan_list[i] = freqs[i]; 17943 wmi_debug("Requesting ANI for channel[%d]", chan_list[i]); 17944 } 17945 17946 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 17947 WMI_GET_CHANNEL_ANI_CMDID); 17948 17949 if (QDF_IS_STATUS_ERROR(ret)) { 17950 wmi_err("WMI_GET_CHANNEL_ANI_CMDID send error %d", ret); 17951 wmi_buf_free(buf); 17952 } 17953 17954 return ret; 17955 } 17956 17957 static QDF_STATUS extract_ani_level_tlv(uint8_t *evt_buf, 17958 struct wmi_host_ani_level_event **info, 17959 uint32_t *num_freqs) 17960 { 17961 WMI_GET_CHANNEL_ANI_EVENTID_param_tlvs *param_buf; 17962 wmi_get_channel_ani_event_fixed_param *fixed_param; 17963 wmi_channel_ani_info_tlv_param *tlv_params; 17964 uint8_t *buf_ptr, i; 17965 17966 param_buf = (WMI_GET_CHANNEL_ANI_EVENTID_param_tlvs *)evt_buf; 17967 if (!param_buf) { 17968 wmi_err("Invalid ani level event buffer"); 17969 return QDF_STATUS_E_INVAL; 17970 } 17971 17972 fixed_param = 17973 (wmi_get_channel_ani_event_fixed_param *)param_buf->fixed_param; 17974 if (!fixed_param) { 17975 wmi_err("Invalid fixed param"); 17976 return QDF_STATUS_E_INVAL; 17977 } 17978 17979 buf_ptr = (uint8_t *)fixed_param; 17980 buf_ptr += sizeof(wmi_get_channel_ani_event_fixed_param); 17981 buf_ptr += WMI_TLV_HDR_SIZE; 17982 17983 *num_freqs = param_buf->num_ani_info; 17984 if (*num_freqs > MAX_NUM_FREQS_FOR_ANI_LEVEL) { 17985 wmi_err("Invalid number of freqs received"); 17986 return QDF_STATUS_E_INVAL; 17987 } 17988 17989 *info = qdf_mem_malloc(*num_freqs * 17990 sizeof(struct wmi_host_ani_level_event)); 17991 if (!(*info)) 17992 return QDF_STATUS_E_NOMEM; 17993 17994 tlv_params = (wmi_channel_ani_info_tlv_param *)buf_ptr; 17995 for (i = 0; i < param_buf->num_ani_info; i++) { 17996 (*info)[i].ani_level = tlv_params->ani_level; 17997 (*info)[i].chan_freq = tlv_params->chan_freq; 17998 tlv_params++; 17999 } 18000 18001 return QDF_STATUS_SUCCESS; 18002 } 18003 #endif /* FEATURE_ANI_LEVEL_REQUEST */ 18004 18005 #ifdef WLAN_FEATURE_ROAM_OFFLOAD 18006 /** 18007 * convert_wtc_scan_mode() - Function to convert TLV specific 18008 * ROAM_TRIGGER_SCAN_MODE scan mode to unified Roam trigger scan mode enum 18009 * @scan_mode: scan freq scheme coming from firmware 18010 * 18011 * Return: ROAM_TRIGGER_SCAN_MODE 18012 */ 18013 static enum roam_scan_freq_scheme 18014 convert_wtc_scan_mode(WMI_ROAM_TRIGGER_SCAN_MODE scan_mode) 18015 { 18016 switch (scan_mode) { 18017 case ROAM_TRIGGER_SCAN_MODE_NO_SCAN_DISCONNECTION: 18018 return ROAM_SCAN_FREQ_SCHEME_NO_SCAN; 18019 case ROAM_TRIGGER_SCAN_MODE_PARTIAL: 18020 return ROAM_SCAN_FREQ_SCHEME_PARTIAL_SCAN; 18021 case ROAM_TRIGGER_SCAN_MODE_FULL: 18022 return ROAM_SCAN_FREQ_SCHEME_FULL_SCAN; 18023 default: 18024 return ROAM_SCAN_FREQ_SCHEME_NONE; 18025 } 18026 } 18027 18028 static uint32_t wmi_convert_fw_to_cm_trig_reason(uint32_t fw_trig_reason) 18029 { 18030 switch (fw_trig_reason) { 18031 case WMI_ROAM_TRIGGER_REASON_NONE: 18032 return ROAM_TRIGGER_REASON_NONE; 18033 case WMI_ROAM_TRIGGER_REASON_PER: 18034 return ROAM_TRIGGER_REASON_PER; 18035 case WMI_ROAM_TRIGGER_REASON_BMISS: 18036 return ROAM_TRIGGER_REASON_BMISS; 18037 case WMI_ROAM_TRIGGER_REASON_LOW_RSSI: 18038 return ROAM_TRIGGER_REASON_LOW_RSSI; 18039 case WMI_ROAM_TRIGGER_REASON_HIGH_RSSI: 18040 return ROAM_TRIGGER_REASON_HIGH_RSSI; 18041 case WMI_ROAM_TRIGGER_REASON_PERIODIC: 18042 return ROAM_TRIGGER_REASON_PERIODIC; 18043 case WMI_ROAM_TRIGGER_REASON_MAWC: 18044 return ROAM_TRIGGER_REASON_MAWC; 18045 case WMI_ROAM_TRIGGER_REASON_DENSE: 18046 return ROAM_TRIGGER_REASON_DENSE; 18047 case WMI_ROAM_TRIGGER_REASON_BACKGROUND: 18048 return ROAM_TRIGGER_REASON_BACKGROUND; 18049 case WMI_ROAM_TRIGGER_REASON_FORCED: 18050 return ROAM_TRIGGER_REASON_FORCED; 18051 case WMI_ROAM_TRIGGER_REASON_BTM: 18052 return ROAM_TRIGGER_REASON_BTM; 18053 case WMI_ROAM_TRIGGER_REASON_UNIT_TEST: 18054 return ROAM_TRIGGER_REASON_UNIT_TEST; 18055 case WMI_ROAM_TRIGGER_REASON_BSS_LOAD: 18056 return ROAM_TRIGGER_REASON_BSS_LOAD; 18057 case WMI_ROAM_TRIGGER_REASON_DEAUTH: 18058 return ROAM_TRIGGER_REASON_DEAUTH; 18059 case WMI_ROAM_TRIGGER_REASON_IDLE: 18060 return ROAM_TRIGGER_REASON_IDLE; 18061 case WMI_ROAM_TRIGGER_REASON_STA_KICKOUT: 18062 return ROAM_TRIGGER_REASON_STA_KICKOUT; 18063 case WMI_ROAM_TRIGGER_REASON_ESS_RSSI: 18064 return ROAM_TRIGGER_REASON_ESS_RSSI; 18065 case WMI_ROAM_TRIGGER_REASON_WTC_BTM: 18066 return ROAM_TRIGGER_REASON_WTC_BTM; 18067 case WMI_ROAM_TRIGGER_REASON_PMK_TIMEOUT: 18068 return ROAM_TRIGGER_REASON_PMK_TIMEOUT; 18069 case WMI_ROAM_TRIGGER_REASON_BTC: 18070 return ROAM_TRIGGER_REASON_BTC; 18071 case WMI_ROAM_TRIGGER_EXT_REASON_MAX: 18072 return ROAM_TRIGGER_REASON_MAX; 18073 default: 18074 return ROAM_TRIGGER_REASON_NONE; 18075 } 18076 } 18077 18078 /** 18079 * extract_roam_11kv_candidate_info - Extract btm candidate info 18080 * @wmi_handle: wmi_handle 18081 * @evt_buf: Event buffer 18082 * @dst_info: Destination buffer 18083 * 18084 * Return: QDF_STATUS 18085 */ 18086 static QDF_STATUS 18087 extract_roam_11kv_candidate_info(wmi_unified_t wmi_handle, void *evt_buf, 18088 struct wmi_btm_req_candidate_info *dst_info, 18089 uint8_t btm_idx, uint16_t num_cand) 18090 { 18091 WMI_ROAM_STATS_EVENTID_param_tlvs *param_buf; 18092 wmi_roam_btm_request_candidate_info *src_data; 18093 uint8_t i; 18094 18095 param_buf = (WMI_ROAM_STATS_EVENTID_param_tlvs *)evt_buf; 18096 if (!param_buf || !param_buf->roam_btm_request_candidate_info || 18097 !param_buf->num_roam_btm_request_candidate_info || 18098 (btm_idx + 18099 num_cand) > param_buf->num_roam_btm_request_candidate_info) 18100 return QDF_STATUS_SUCCESS; 18101 18102 src_data = ¶m_buf->roam_btm_request_candidate_info[btm_idx]; 18103 if (num_cand > WLAN_MAX_BTM_CANDIDATE) 18104 num_cand = WLAN_MAX_BTM_CANDIDATE; 18105 for (i = 0; i < num_cand; i++) { 18106 WMI_MAC_ADDR_TO_CHAR_ARRAY(&src_data->btm_candidate_bssid, 18107 dst_info->candidate_bssid.bytes); 18108 dst_info->preference = src_data->preference; 18109 src_data++; 18110 dst_info++; 18111 } 18112 18113 return QDF_STATUS_SUCCESS; 18114 } 18115 18116 static enum roam_trigger_sub_reason 18117 wmi_convert_roam_sub_reason(WMI_ROAM_TRIGGER_SUB_REASON_ID subreason) 18118 { 18119 switch (subreason) { 18120 case WMI_ROAM_TRIGGER_SUB_REASON_PERIODIC_TIMER: 18121 return ROAM_TRIGGER_SUB_REASON_PERIODIC_TIMER; 18122 case WMI_ROAM_TRIGGER_SUB_REASON_INACTIVITY_TIMER: 18123 return ROAM_TRIGGER_SUB_REASON_INACTIVITY_TIMER_LOW_RSSI; 18124 case WMI_ROAM_TRIGGER_SUB_REASON_BTM_DI_TIMER: 18125 return ROAM_TRIGGER_SUB_REASON_BTM_DI_TIMER; 18126 case WMI_ROAM_TRIGGER_SUB_REASON_FULL_SCAN: 18127 return ROAM_TRIGGER_SUB_REASON_FULL_SCAN; 18128 case WMI_ROAM_TRIGGER_SUB_REASON_LOW_RSSI_PERIODIC: 18129 return ROAM_TRIGGER_SUB_REASON_LOW_RSSI_PERIODIC; 18130 case WMI_ROAM_TRIGGER_SUB_REASON_CU_PERIODIC: 18131 return ROAM_TRIGGER_SUB_REASON_CU_PERIODIC; 18132 case WMI_ROAM_TRIGGER_SUB_REASON_PERIODIC_TIMER_AFTER_INACTIVITY: 18133 return ROAM_TRIGGER_SUB_REASON_PERIODIC_TIMER_AFTER_INACTIVITY; 18134 case WMI_ROAM_TRIGGER_SUB_REASON_PERIODIC_TIMER_AFTER_INACTIVITY_CU: 18135 return ROAM_TRIGGER_SUB_REASON_PERIODIC_TIMER_AFTER_INACTIVITY_CU; 18136 case WMI_ROAM_TRIGGER_SUB_REASON_INACTIVITY_TIMER_CU: 18137 return ROAM_TRIGGER_SUB_REASON_INACTIVITY_TIMER_CU; 18138 default: 18139 break; 18140 } 18141 18142 return 0; 18143 } 18144 18145 /** 18146 * extract_roam_trigger_stats_tlv() - Extract the Roam trigger stats 18147 * from the WMI_ROAM_STATS_EVENTID 18148 * @wmi_handle: wmi handle 18149 * @evt_buf: Pointer to the event buffer 18150 * @trig: Pointer to destination structure to fill data 18151 * @idx: TLV id 18152 */ 18153 static QDF_STATUS 18154 extract_roam_trigger_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18155 struct wmi_roam_trigger_info *trig, uint8_t idx, 18156 uint8_t btm_idx) 18157 { 18158 WMI_ROAM_STATS_EVENTID_param_tlvs *param_buf; 18159 wmi_roam_trigger_reason *src_data = NULL; 18160 uint32_t trig_reason; 18161 18162 param_buf = (WMI_ROAM_STATS_EVENTID_param_tlvs *)evt_buf; 18163 if (!param_buf || !param_buf->roam_trigger_reason) 18164 return QDF_STATUS_E_FAILURE; 18165 18166 src_data = ¶m_buf->roam_trigger_reason[idx]; 18167 18168 trig->present = true; 18169 trig_reason = src_data->trigger_reason; 18170 trig->trigger_reason = wmi_convert_fw_to_cm_trig_reason(trig_reason); 18171 trig->trigger_sub_reason = 18172 wmi_convert_roam_sub_reason(src_data->trigger_sub_reason); 18173 trig->current_rssi = src_data->current_rssi; 18174 trig->timestamp = src_data->timestamp; 18175 18176 switch (trig_reason) { 18177 case WMI_ROAM_TRIGGER_REASON_PER: 18178 case WMI_ROAM_TRIGGER_REASON_BMISS: 18179 case WMI_ROAM_TRIGGER_REASON_HIGH_RSSI: 18180 case WMI_ROAM_TRIGGER_REASON_MAWC: 18181 case WMI_ROAM_TRIGGER_REASON_DENSE: 18182 case WMI_ROAM_TRIGGER_REASON_BACKGROUND: 18183 case WMI_ROAM_TRIGGER_REASON_IDLE: 18184 case WMI_ROAM_TRIGGER_REASON_FORCED: 18185 case WMI_ROAM_TRIGGER_REASON_UNIT_TEST: 18186 case WMI_ROAM_TRIGGER_REASON_BTC: 18187 return QDF_STATUS_SUCCESS; 18188 18189 case WMI_ROAM_TRIGGER_REASON_BTM: 18190 trig->btm_trig_data.btm_request_mode = 18191 src_data->btm_request_mode; 18192 trig->btm_trig_data.disassoc_timer = 18193 src_data->disassoc_imminent_timer; 18194 trig->btm_trig_data.validity_interval = 18195 src_data->validity_internal; 18196 trig->btm_trig_data.candidate_list_count = 18197 src_data->candidate_list_count; 18198 trig->btm_trig_data.btm_resp_status = 18199 src_data->btm_response_status_code; 18200 trig->btm_trig_data.btm_bss_termination_timeout = 18201 src_data->btm_bss_termination_timeout; 18202 trig->btm_trig_data.btm_mbo_assoc_retry_timeout = 18203 src_data->btm_mbo_assoc_retry_timeout; 18204 trig->btm_trig_data.token = src_data->btm_req_dialog_token; 18205 if ((btm_idx + trig->btm_trig_data.candidate_list_count) <= 18206 param_buf->num_roam_btm_request_candidate_info) 18207 extract_roam_11kv_candidate_info( 18208 wmi_handle, evt_buf, 18209 trig->btm_trig_data.btm_cand, 18210 btm_idx, 18211 src_data->candidate_list_count); 18212 18213 return QDF_STATUS_SUCCESS; 18214 18215 case WMI_ROAM_TRIGGER_REASON_BSS_LOAD: 18216 trig->cu_trig_data.cu_load = src_data->cu_load; 18217 return QDF_STATUS_SUCCESS; 18218 18219 case WMI_ROAM_TRIGGER_REASON_DEAUTH: 18220 trig->deauth_trig_data.type = src_data->deauth_type; 18221 trig->deauth_trig_data.reason = src_data->deauth_reason; 18222 return QDF_STATUS_SUCCESS; 18223 18224 case WMI_ROAM_TRIGGER_REASON_PERIODIC: 18225 case WMI_ROAM_TRIGGER_REASON_LOW_RSSI: 18226 trig->rssi_trig_data.threshold = src_data->roam_rssi_threshold; 18227 return QDF_STATUS_SUCCESS; 18228 18229 case WMI_ROAM_TRIGGER_REASON_WTC_BTM: 18230 trig->wtc_btm_trig_data.roaming_mode = 18231 src_data->vendor_specific1[0]; 18232 trig->wtc_btm_trig_data.vsie_trigger_reason = 18233 src_data->vendor_specific1[1]; 18234 trig->wtc_btm_trig_data.sub_code = 18235 src_data->vendor_specific1[2]; 18236 trig->wtc_btm_trig_data.wtc_mode = 18237 src_data->vendor_specific1[3]; 18238 trig->wtc_btm_trig_data.wtc_scan_mode = 18239 convert_wtc_scan_mode(src_data->vendor_specific1[4]); 18240 trig->wtc_btm_trig_data.wtc_rssi_th = 18241 src_data->vendor_specific1[5]; 18242 trig->wtc_btm_trig_data.wtc_candi_rssi_th = 18243 src_data->vendor_specific1[6]; 18244 18245 trig->wtc_btm_trig_data.wtc_candi_rssi_ext_present = 18246 src_data->vendor_specific2[0]; 18247 trig->wtc_btm_trig_data.wtc_candi_rssi_th_5g = 18248 src_data->vendor_specific2[1]; 18249 trig->wtc_btm_trig_data.wtc_candi_rssi_th_6g = 18250 src_data->vendor_specific2[2]; 18251 trig->wtc_btm_trig_data.duration = 18252 src_data->vendor_specific2[3]; 18253 18254 return QDF_STATUS_SUCCESS; 18255 default: 18256 return QDF_STATUS_SUCCESS; 18257 } 18258 18259 return QDF_STATUS_SUCCESS; 18260 } 18261 18262 /** 18263 * extract_roam_scan_ap_stats_tlv() - Extract the Roam trigger stats 18264 * from the WMI_ROAM_STATS_EVENTID 18265 * @wmi_handle: wmi handle 18266 * @evt_buf: Pointer to the event buffer 18267 * @dst: Pointer to destination structure to fill data 18268 * @ap_idx: TLV index for this roam scan 18269 * @num_cand: number of candidates list in the roam scan 18270 */ 18271 static QDF_STATUS 18272 extract_roam_scan_ap_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18273 struct wmi_roam_candidate_info *dst, 18274 uint8_t ap_idx, uint16_t num_cand) 18275 { 18276 WMI_ROAM_STATS_EVENTID_param_tlvs *param_buf; 18277 wmi_roam_ap_info *src = NULL; 18278 uint8_t i; 18279 18280 param_buf = (WMI_ROAM_STATS_EVENTID_param_tlvs *)evt_buf; 18281 if (!param_buf) { 18282 wmi_err("Param buf is NULL"); 18283 return QDF_STATUS_E_FAILURE; 18284 } 18285 18286 if (ap_idx >= param_buf->num_roam_ap_info) { 18287 wmi_err("Invalid roam scan AP tlv ap_idx:%d total_ap:%d", 18288 ap_idx, param_buf->num_roam_ap_info); 18289 return QDF_STATUS_E_FAILURE; 18290 } 18291 18292 src = ¶m_buf->roam_ap_info[ap_idx]; 18293 18294 for (i = 0; i < num_cand; i++) { 18295 WMI_MAC_ADDR_TO_CHAR_ARRAY(&src->bssid, dst->bssid.bytes); 18296 dst->type = src->candidate_type; 18297 dst->freq = src->channel; 18298 dst->etp = src->etp; 18299 dst->rssi = src->rssi; 18300 dst->rssi_score = src->rssi_score; 18301 dst->cu_load = src->cu_load; 18302 dst->cu_score = src->cu_score; 18303 dst->total_score = src->total_score; 18304 dst->timestamp = src->timestamp; 18305 dst->dl_reason = src->bl_reason; 18306 dst->dl_source = src->bl_source; 18307 dst->dl_timestamp = src->bl_timestamp; 18308 dst->dl_original_timeout = src->bl_original_timeout; 18309 18310 src++; 18311 dst++; 18312 } 18313 18314 return QDF_STATUS_SUCCESS; 18315 } 18316 18317 /** 18318 * extract_roam_scan_stats_tlv() - Extract the Roam trigger stats 18319 * from the WMI_ROAM_STATS_EVENTID 18320 * @wmi_handle: wmi handle 18321 * @evt_buf: Pointer to the event buffer 18322 * @dst: Pointer to destination structure to fill data 18323 * @idx: TLV id 18324 * @chan_idx: Index of the channel tlv for the current roam trigger 18325 * @ap_idx: Index of the candidate AP TLV for the current roam trigger 18326 */ 18327 static QDF_STATUS 18328 extract_roam_scan_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18329 struct wmi_roam_scan_data *dst, uint8_t idx, 18330 uint8_t chan_idx, uint8_t ap_idx) 18331 { 18332 WMI_ROAM_STATS_EVENTID_param_tlvs *param_buf; 18333 wmi_roam_scan_info *src_data = NULL; 18334 wmi_roam_scan_channel_info *src_chan = NULL; 18335 QDF_STATUS status; 18336 uint8_t i; 18337 18338 param_buf = (WMI_ROAM_STATS_EVENTID_param_tlvs *)evt_buf; 18339 if (!param_buf || !param_buf->roam_scan_info || 18340 idx >= param_buf->num_roam_scan_info) 18341 return QDF_STATUS_E_FAILURE; 18342 18343 src_data = ¶m_buf->roam_scan_info[idx]; 18344 18345 dst->present = true; 18346 dst->type = src_data->roam_scan_type; 18347 dst->num_chan = src_data->roam_scan_channel_count; 18348 dst->next_rssi_threshold = src_data->next_rssi_trigger_threshold; 18349 dst->is_btcoex_active = WMI_GET_BTCONNECT_STATUS(src_data->flags); 18350 dst->frame_info_count = src_data->frame_info_count; 18351 if (dst->frame_info_count > WLAN_ROAM_MAX_FRAME_INFO) 18352 dst->frame_info_count = WLAN_ROAM_MAX_FRAME_INFO; 18353 18354 /* Read the channel data only for dst->type is 0 (partial scan) */ 18355 if (dst->num_chan && !dst->type && param_buf->num_roam_scan_chan_info && 18356 chan_idx < param_buf->num_roam_scan_chan_info) { 18357 if (dst->num_chan > MAX_ROAM_SCAN_CHAN) 18358 dst->num_chan = MAX_ROAM_SCAN_CHAN; 18359 18360 src_chan = ¶m_buf->roam_scan_chan_info[chan_idx]; 18361 for (i = 0; i < dst->num_chan; i++) { 18362 dst->chan_freq[i] = src_chan->channel; 18363 src_chan++; 18364 } 18365 } 18366 18367 if (!src_data->roam_ap_count || !param_buf->num_roam_ap_info) 18368 return QDF_STATUS_SUCCESS; 18369 18370 dst->num_ap = src_data->roam_ap_count; 18371 if (dst->num_ap > MAX_ROAM_CANDIDATE_AP) 18372 dst->num_ap = MAX_ROAM_CANDIDATE_AP; 18373 18374 status = extract_roam_scan_ap_stats_tlv(wmi_handle, evt_buf, dst->ap, 18375 ap_idx, dst->num_ap); 18376 if (QDF_IS_STATUS_ERROR(status)) { 18377 wmi_err("Extract candidate stats for tlv[%d] failed", idx); 18378 return status; 18379 } 18380 18381 return QDF_STATUS_SUCCESS; 18382 } 18383 18384 /** 18385 * wlan_roam_fail_reason_code() - Convert FW enum to Host enum 18386 * @wmi_roam_fail_reason: roam fail enum 18387 * 18388 * Return: Roaming failure reason codes 18389 */ 18390 static enum wlan_roam_failure_reason_code 18391 wlan_roam_fail_reason_code(uint16_t wmi_roam_fail_reason) 18392 { 18393 switch (wmi_roam_fail_reason) { 18394 case WMI_ROAM_FAIL_REASON_NO_SCAN_START: 18395 return ROAM_FAIL_REASON_NO_SCAN_START; 18396 case WMI_ROAM_FAIL_REASON_NO_AP_FOUND: 18397 return ROAM_FAIL_REASON_NO_AP_FOUND; 18398 case WMI_ROAM_FAIL_REASON_NO_CAND_AP_FOUND: 18399 return ROAM_FAIL_REASON_NO_CAND_AP_FOUND; 18400 case WMI_ROAM_FAIL_REASON_HOST: 18401 return ROAM_FAIL_REASON_HOST; 18402 case WMI_ROAM_FAIL_REASON_AUTH_SEND: 18403 return ROAM_FAIL_REASON_AUTH_SEND; 18404 case WMI_ROAM_FAIL_REASON_AUTH_RECV: 18405 return ROAM_FAIL_REASON_AUTH_RECV; 18406 case WMI_ROAM_FAIL_REASON_NO_AUTH_RESP: 18407 return ROAM_FAIL_REASON_NO_AUTH_RESP; 18408 case WMI_ROAM_FAIL_REASON_REASSOC_SEND: 18409 return ROAM_FAIL_REASON_REASSOC_SEND; 18410 case WMI_ROAM_FAIL_REASON_REASSOC_RECV: 18411 return ROAM_FAIL_REASON_REASSOC_RECV; 18412 case WMI_ROAM_FAIL_REASON_NO_REASSOC_RESP: 18413 return ROAM_FAIL_REASON_NO_REASSOC_RESP; 18414 case WMI_ROAM_FAIL_REASON_EAPOL_TIMEOUT: 18415 return ROAM_FAIL_REASON_EAPOL_TIMEOUT; 18416 case WMI_ROAM_FAIL_REASON_MLME: 18417 return ROAM_FAIL_REASON_MLME; 18418 case WMI_ROAM_FAIL_REASON_INTERNAL_ABORT: 18419 return ROAM_FAIL_REASON_INTERNAL_ABORT; 18420 case WMI_ROAM_FAIL_REASON_SCAN_START: 18421 return ROAM_FAIL_REASON_SCAN_START; 18422 case WMI_ROAM_FAIL_REASON_AUTH_NO_ACK: 18423 return ROAM_FAIL_REASON_AUTH_NO_ACK; 18424 case WMI_ROAM_FAIL_REASON_AUTH_INTERNAL_DROP: 18425 return ROAM_FAIL_REASON_AUTH_INTERNAL_DROP; 18426 case WMI_ROAM_FAIL_REASON_REASSOC_NO_ACK: 18427 return ROAM_FAIL_REASON_REASSOC_NO_ACK; 18428 case WMI_ROAM_FAIL_REASON_REASSOC_INTERNAL_DROP: 18429 return ROAM_FAIL_REASON_REASSOC_INTERNAL_DROP; 18430 case WMI_ROAM_FAIL_REASON_EAPOL_M2_SEND: 18431 return ROAM_FAIL_REASON_EAPOL_M2_SEND; 18432 case WMI_ROAM_FAIL_REASON_EAPOL_M2_INTERNAL_DROP: 18433 return ROAM_FAIL_REASON_EAPOL_M2_INTERNAL_DROP; 18434 case WMI_ROAM_FAIL_REASON_EAPOL_M2_NO_ACK: 18435 return ROAM_FAIL_REASON_EAPOL_M2_NO_ACK; 18436 case WMI_ROAM_FAIL_REASON_EAPOL_M3_TIMEOUT: 18437 return ROAM_FAIL_REASON_EAPOL_M3_TIMEOUT; 18438 case WMI_ROAM_FAIL_REASON_EAPOL_M4_SEND: 18439 return ROAM_FAIL_REASON_EAPOL_M4_SEND; 18440 case WMI_ROAM_FAIL_REASON_EAPOL_M4_INTERNAL_DROP: 18441 return ROAM_FAIL_REASON_EAPOL_M4_INTERNAL_DROP; 18442 case WMI_ROAM_FAIL_REASON_EAPOL_M4_NO_ACK: 18443 return ROAM_FAIL_REASON_EAPOL_M4_NO_ACK; 18444 case WMI_ROAM_FAIL_REASON_NO_SCAN_FOR_FINAL_BMISS: 18445 return ROAM_FAIL_REASON_NO_SCAN_FOR_FINAL_BMISS; 18446 case WMI_ROAM_FAIL_REASON_DISCONNECT: 18447 return ROAM_FAIL_REASON_DISCONNECT; 18448 case WMI_ROAM_FAIL_REASON_SYNC: 18449 return ROAM_FAIL_REASON_SYNC; 18450 case WMI_ROAM_FAIL_REASON_SAE_INVALID_PMKID: 18451 return ROAM_FAIL_REASON_SAE_INVALID_PMKID; 18452 case WMI_ROAM_FAIL_REASON_SAE_PREAUTH_TIMEOUT: 18453 return ROAM_FAIL_REASON_SAE_PREAUTH_TIMEOUT; 18454 case WMI_ROAM_FAIL_REASON_SAE_PREAUTH_FAIL: 18455 return ROAM_FAIL_REASON_SAE_PREAUTH_FAIL; 18456 case WMI_ROAM_FAIL_REASON_UNABLE_TO_START_ROAM_HO: 18457 return ROAM_FAIL_REASON_UNABLE_TO_START_ROAM_HO; 18458 default: 18459 return ROAM_FAIL_REASON_UNKNOWN; 18460 } 18461 } 18462 18463 /** 18464 * extract_roam_scan_stats_tlv() - Extract the Roam trigger stats 18465 * from the WMI_ROAM_STATS_EVENTID 18466 * @wmi_handle: wmi handle 18467 * @evt_buf: Pointer to the event buffer 18468 * @dst: Pointer to destination structure to fill data 18469 * @idx: TLV id 18470 */ 18471 static QDF_STATUS 18472 extract_roam_result_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18473 struct wmi_roam_result *dst, uint8_t idx) 18474 { 18475 WMI_ROAM_STATS_EVENTID_param_tlvs *param_buf; 18476 wmi_roam_result *src_data = NULL; 18477 18478 param_buf = (WMI_ROAM_STATS_EVENTID_param_tlvs *)evt_buf; 18479 if (!param_buf || !param_buf->roam_result || 18480 idx >= param_buf->num_roam_result) 18481 return QDF_STATUS_E_FAILURE; 18482 18483 src_data = ¶m_buf->roam_result[idx]; 18484 18485 dst->present = true; 18486 dst->status = src_data->roam_status; 18487 dst->timestamp = src_data->timestamp; 18488 dst->fail_reason = 18489 wlan_roam_fail_reason_code(src_data->roam_fail_reason); 18490 WMI_MAC_ADDR_TO_CHAR_ARRAY(&src_data->bssid, dst->fail_bssid.bytes); 18491 18492 return QDF_STATUS_SUCCESS; 18493 } 18494 18495 /** 18496 * extract_roam_11kv_stats_tlv() - Extract the Roam trigger stats 18497 * from the WMI_ROAM_STATS_EVENTID 18498 * @wmi_handle: wmi handle 18499 * @evt_buf: Pointer to the event buffer 18500 * @dst: Pointer to destination structure to fill data 18501 * @idx: TLV id 18502 * @rpt_idx: Neighbor report Channel index 18503 */ 18504 static QDF_STATUS 18505 extract_roam_11kv_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18506 struct wmi_neighbor_report_data *dst, 18507 uint8_t idx, uint8_t rpt_idx) 18508 { 18509 WMI_ROAM_STATS_EVENTID_param_tlvs *param_buf; 18510 wmi_roam_neighbor_report_info *src_data = NULL; 18511 wmi_roam_neighbor_report_channel_info *src_freq = NULL; 18512 uint8_t i; 18513 18514 param_buf = (WMI_ROAM_STATS_EVENTID_param_tlvs *)evt_buf; 18515 if (!param_buf || !param_buf->roam_neighbor_report_info || 18516 !param_buf->num_roam_neighbor_report_info || 18517 idx >= param_buf->num_roam_neighbor_report_info) { 18518 wmi_debug("Invalid 1kv param buf"); 18519 return QDF_STATUS_E_FAILURE; 18520 } 18521 18522 src_data = ¶m_buf->roam_neighbor_report_info[idx]; 18523 18524 dst->present = true; 18525 dst->req_type = src_data->request_type; 18526 dst->num_freq = src_data->neighbor_report_channel_count; 18527 dst->req_time = src_data->neighbor_report_request_timestamp; 18528 dst->resp_time = src_data->neighbor_report_response_timestamp; 18529 dst->btm_query_token = src_data->btm_query_token; 18530 dst->btm_query_reason = src_data->btm_query_reason_code; 18531 18532 if (!dst->num_freq || !param_buf->num_roam_neighbor_report_chan_info || 18533 rpt_idx >= param_buf->num_roam_neighbor_report_chan_info) 18534 return QDF_STATUS_SUCCESS; 18535 18536 if (!param_buf->roam_neighbor_report_chan_info) { 18537 wmi_debug("11kv channel present, but TLV is NULL num_freq:%d", 18538 dst->num_freq); 18539 dst->num_freq = 0; 18540 /* return success as its optional tlv and we can print neighbor 18541 * report received info 18542 */ 18543 return QDF_STATUS_SUCCESS; 18544 } 18545 18546 src_freq = ¶m_buf->roam_neighbor_report_chan_info[rpt_idx]; 18547 18548 if (dst->num_freq > MAX_ROAM_SCAN_CHAN) 18549 dst->num_freq = MAX_ROAM_SCAN_CHAN; 18550 18551 for (i = 0; i < dst->num_freq; i++) { 18552 dst->freq[i] = src_freq->channel; 18553 src_freq++; 18554 } 18555 18556 return QDF_STATUS_SUCCESS; 18557 } 18558 18559 /** 18560 * send_roam_set_param_cmd_tlv() - WMI roam set parameter function 18561 * @wmi_handle : handle to WMI. 18562 * @roam_param : pointer to hold roam set parameter 18563 * 18564 * Return: 0 on success and -ve on failure. 18565 */ 18566 static QDF_STATUS 18567 send_roam_set_param_cmd_tlv(wmi_unified_t wmi_handle, 18568 struct vdev_set_params *roam_param) 18569 { 18570 QDF_STATUS ret; 18571 wmi_roam_set_param_cmd_fixed_param *cmd; 18572 wmi_buf_t buf; 18573 uint16_t len = sizeof(*cmd); 18574 18575 buf = wmi_buf_alloc(wmi_handle, len); 18576 if (!buf) 18577 return QDF_STATUS_E_NOMEM; 18578 18579 cmd = (wmi_roam_set_param_cmd_fixed_param *)wmi_buf_data(buf); 18580 WMITLV_SET_HDR(&cmd->tlv_header, 18581 WMITLV_TAG_STRUC_wmi_roam_set_param_cmd_fixed_param, 18582 WMITLV_GET_STRUCT_TLVLEN 18583 (wmi_roam_set_param_cmd_fixed_param)); 18584 cmd->vdev_id = roam_param->vdev_id; 18585 cmd->param_id = roam_param->param_id; 18586 cmd->param_value = roam_param->param_value; 18587 wmi_debug("Setting vdev %d roam_param = %x, value = %u", 18588 cmd->vdev_id, cmd->param_id, cmd->param_value); 18589 wmi_mtrace(WMI_ROAM_SET_PARAM_CMDID, cmd->vdev_id, 0); 18590 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 18591 WMI_ROAM_SET_PARAM_CMDID); 18592 if (QDF_IS_STATUS_ERROR(ret)) { 18593 wmi_err("Failed to send roam set param command, ret = %d", ret); 18594 wmi_buf_free(buf); 18595 } 18596 18597 return ret; 18598 } 18599 #else 18600 static inline QDF_STATUS 18601 extract_roam_trigger_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18602 struct wmi_roam_trigger_info *trig, uint8_t idx, 18603 uint8_t btm_idx) 18604 { 18605 return QDF_STATUS_E_NOSUPPORT; 18606 } 18607 18608 static inline QDF_STATUS 18609 extract_roam_result_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18610 struct wmi_roam_result *dst, uint8_t idx) 18611 { 18612 return QDF_STATUS_E_NOSUPPORT; 18613 } 18614 18615 static QDF_STATUS 18616 extract_roam_11kv_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18617 struct wmi_neighbor_report_data *dst, 18618 uint8_t idx, uint8_t rpt_idx) 18619 { 18620 return QDF_STATUS_E_NOSUPPORT; 18621 } 18622 18623 static QDF_STATUS 18624 extract_roam_scan_stats_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18625 struct wmi_roam_scan_data *dst, uint8_t idx, 18626 uint8_t chan_idx, uint8_t ap_idx) 18627 { 18628 return QDF_STATUS_E_NOSUPPORT; 18629 } 18630 #endif 18631 18632 #ifdef WLAN_FEATURE_PKT_CAPTURE 18633 static QDF_STATUS 18634 extract_vdev_mgmt_offload_event_tlv(void *handle, void *evt_buf, 18635 struct mgmt_offload_event_params *params) 18636 { 18637 WMI_VDEV_MGMT_OFFLOAD_EVENTID_param_tlvs *param_tlvs; 18638 wmi_mgmt_hdr *hdr; 18639 18640 param_tlvs = (WMI_VDEV_MGMT_OFFLOAD_EVENTID_param_tlvs *)evt_buf; 18641 if (!param_tlvs) 18642 return QDF_STATUS_E_INVAL; 18643 18644 hdr = param_tlvs->fixed_param; 18645 if (!hdr) 18646 return QDF_STATUS_E_INVAL; 18647 18648 if (hdr->buf_len > param_tlvs->num_bufp) 18649 return QDF_STATUS_E_INVAL; 18650 18651 params->tsf_l32 = hdr->tsf_l32; 18652 params->chan_freq = hdr->chan_freq; 18653 params->rate_kbps = hdr->rate_kbps; 18654 params->rssi = hdr->rssi; 18655 params->buf_len = hdr->buf_len; 18656 params->tx_status = hdr->tx_status; 18657 params->buf = param_tlvs->bufp; 18658 params->tx_retry_cnt = hdr->tx_retry_cnt; 18659 return QDF_STATUS_SUCCESS; 18660 } 18661 #endif /* WLAN_FEATURE_PKT_CAPTURE */ 18662 18663 #ifdef WLAN_FEATURE_PKT_CAPTURE_V2 18664 static QDF_STATUS 18665 extract_smart_monitor_event_tlv(void *handle, void *evt_buf, 18666 struct smu_event_params *params) 18667 { 18668 WMI_VDEV_SMART_MONITOR_EVENTID_param_tlvs *param_buf = NULL; 18669 wmi_vdev_smart_monitor_event_fixed_param *smu_event = NULL; 18670 18671 param_buf = (WMI_VDEV_SMART_MONITOR_EVENTID_param_tlvs *)evt_buf; 18672 if (!param_buf) { 18673 wmi_err("Invalid smart monitor event"); 18674 return QDF_STATUS_E_INVAL; 18675 } 18676 18677 smu_event = param_buf->fixed_param; 18678 if (!smu_event) { 18679 wmi_err("smart monitor event fixed param is NULL"); 18680 return QDF_STATUS_E_INVAL; 18681 } 18682 18683 params->vdev_id = smu_event->vdev_id; 18684 if (params->vdev_id >= WLAN_UMAC_PDEV_MAX_VDEVS) 18685 return QDF_STATUS_E_INVAL; 18686 18687 params->rx_avg_rssi = smu_event->avg_rssi_data_dbm; 18688 18689 return QDF_STATUS_SUCCESS; 18690 } 18691 #endif /* WLAN_FEATURE_PKT_CAPTURE_V2 */ 18692 18693 #ifdef FEATURE_WLAN_TIME_SYNC_FTM 18694 /** 18695 * send_wlan_ts_ftm_trigger_cmd_tlv(): send wlan time sync cmd to FW 18696 * 18697 * @wmi: wmi handle 18698 * @vdev_id: vdev id 18699 * @burst_mode: Indicates whether relation derived using FTM is needed for 18700 * each FTM frame or only aggregated result is required. 18701 * 18702 * Send WMI_AUDIO_SYNC_TRIGGER_CMDID to FW. 18703 * 18704 * Return: QDF_STATUS 18705 */ 18706 static QDF_STATUS send_wlan_ts_ftm_trigger_cmd_tlv(wmi_unified_t wmi, 18707 uint32_t vdev_id, 18708 bool burst_mode) 18709 { 18710 wmi_audio_sync_trigger_cmd_fixed_param *cmd; 18711 wmi_buf_t buf; 18712 int32_t len = sizeof(*cmd); 18713 18714 buf = wmi_buf_alloc(wmi, len); 18715 if (!buf) { 18716 wmi_err("wmi_buf_alloc failed"); 18717 return QDF_STATUS_E_NOMEM; 18718 } 18719 cmd = (wmi_audio_sync_trigger_cmd_fixed_param *)wmi_buf_data(buf); 18720 WMITLV_SET_HDR(&cmd->tlv_header, 18721 WMITLV_TAG_STRUC_wmi_audio_sync_trigger_cmd_fixed_param, 18722 WMITLV_GET_STRUCT_TLVLEN(wmi_audio_sync_trigger_cmd_fixed_param)); 18723 cmd->vdev_id = vdev_id; 18724 cmd->agg_relation = burst_mode ? false : true; 18725 if (wmi_unified_cmd_send(wmi, buf, len, WMI_VDEV_AUDIO_SYNC_TRIGGER_CMDID)) { 18726 wmi_err("Failed to send audio sync trigger cmd"); 18727 wmi_buf_free(buf); 18728 return QDF_STATUS_E_FAILURE; 18729 } 18730 18731 return QDF_STATUS_SUCCESS; 18732 } 18733 18734 static QDF_STATUS send_wlan_ts_qtime_cmd_tlv(wmi_unified_t wmi, 18735 uint32_t vdev_id, 18736 uint64_t lpass_ts) 18737 { 18738 wmi_audio_sync_qtimer_cmd_fixed_param *cmd; 18739 wmi_buf_t buf; 18740 int32_t len = sizeof(*cmd); 18741 18742 buf = wmi_buf_alloc(wmi, len); 18743 if (!buf) { 18744 wmi_err("wmi_buf_alloc failed"); 18745 return QDF_STATUS_E_NOMEM; 18746 } 18747 cmd = (wmi_audio_sync_qtimer_cmd_fixed_param *)wmi_buf_data(buf); 18748 WMITLV_SET_HDR(&cmd->tlv_header, 18749 WMITLV_TAG_STRUC_wmi_audio_sync_qtimer_cmd_fixed_param, 18750 WMITLV_GET_STRUCT_TLVLEN(wmi_audio_sync_qtimer_cmd_fixed_param)); 18751 cmd->vdev_id = vdev_id; 18752 cmd->qtimer_u32 = (uint32_t)((lpass_ts & 0xffffffff00000000LL) >> 32); 18753 cmd->qtimer_l32 = (uint32_t)(lpass_ts & 0xffffffffLL); 18754 18755 if (wmi_unified_cmd_send(wmi, buf, len, WMI_VDEV_AUDIO_SYNC_QTIMER_CMDID)) { 18756 wmi_err("Failed to send audio qtime command"); 18757 wmi_buf_free(buf); 18758 return QDF_STATUS_E_FAILURE; 18759 } 18760 18761 return QDF_STATUS_SUCCESS; 18762 } 18763 18764 static QDF_STATUS extract_time_sync_ftm_start_stop_event_tlv( 18765 wmi_unified_t wmi, void *buf, 18766 struct ftm_time_sync_start_stop_params *param) 18767 { 18768 WMI_VDEV_AUDIO_SYNC_START_STOP_EVENTID_param_tlvs *param_buf; 18769 wmi_audio_sync_start_stop_event_fixed_param *resp_event; 18770 18771 param_buf = (WMI_VDEV_AUDIO_SYNC_START_STOP_EVENTID_param_tlvs *)buf; 18772 if (!param_buf) { 18773 wmi_err("Invalid audio sync start stop event buffer"); 18774 return QDF_STATUS_E_FAILURE; 18775 } 18776 18777 resp_event = param_buf->fixed_param; 18778 if (!resp_event) { 18779 wmi_err("Invalid audio sync start stop fixed param buffer"); 18780 return QDF_STATUS_E_FAILURE; 18781 } 18782 18783 param->vdev_id = resp_event->vdev_id; 18784 param->timer_interval = resp_event->periodicity; 18785 param->num_reads = resp_event->reads_needed; 18786 param->qtime = ((uint64_t)resp_event->qtimer_u32 << 32) | 18787 resp_event->qtimer_l32; 18788 param->mac_time = ((uint64_t)resp_event->mac_timer_u32 << 32) | 18789 resp_event->mac_timer_l32; 18790 18791 wmi_debug("FTM time sync time_interval %d, num_reads %d", 18792 param->timer_interval, param->num_reads); 18793 18794 return QDF_STATUS_SUCCESS; 18795 } 18796 18797 static QDF_STATUS 18798 extract_time_sync_ftm_offset_event_tlv(wmi_unified_t wmi, void *buf, 18799 struct ftm_time_sync_offset *param) 18800 { 18801 WMI_VDEV_AUDIO_SYNC_Q_MASTER_SLAVE_OFFSET_EVENTID_param_tlvs *param_buf; 18802 wmi_audio_sync_q_master_slave_offset_event_fixed_param *resp_event; 18803 wmi_audio_sync_q_master_slave_times *q_pair; 18804 int iter; 18805 18806 param_buf = 18807 (WMI_VDEV_AUDIO_SYNC_Q_MASTER_SLAVE_OFFSET_EVENTID_param_tlvs *)buf; 18808 if (!param_buf) { 18809 wmi_err("Invalid timesync ftm offset event buffer"); 18810 return QDF_STATUS_E_FAILURE; 18811 } 18812 18813 resp_event = param_buf->fixed_param; 18814 if (!resp_event) { 18815 wmi_err("Invalid timesync ftm offset fixed param buffer"); 18816 return QDF_STATUS_E_FAILURE; 18817 } 18818 18819 param->vdev_id = resp_event->vdev_id; 18820 param->num_qtime = param_buf->num_audio_sync_q_master_slave_times; 18821 if (param->num_qtime > FTM_TIME_SYNC_QTIME_PAIR_MAX) 18822 param->num_qtime = FTM_TIME_SYNC_QTIME_PAIR_MAX; 18823 18824 q_pair = param_buf->audio_sync_q_master_slave_times; 18825 if (!q_pair) { 18826 wmi_err("Invalid q_master_slave_times buffer"); 18827 return QDF_STATUS_E_FAILURE; 18828 } 18829 18830 for (iter = 0; iter < param->num_qtime; iter++) { 18831 param->pairs[iter].qtime_initiator = ( 18832 (uint64_t)q_pair[iter].qmaster_u32 << 32) | 18833 q_pair[iter].qmaster_l32; 18834 param->pairs[iter].qtime_target = ( 18835 (uint64_t)q_pair[iter].qslave_u32 << 32) | 18836 q_pair[iter].qslave_l32; 18837 } 18838 return QDF_STATUS_SUCCESS; 18839 } 18840 #endif /* FEATURE_WLAN_TIME_SYNC_FTM */ 18841 18842 /** 18843 * send_vdev_tsf_tstamp_action_cmd_tlv() - send vdev tsf action command 18844 * @wmi: wmi handle 18845 * @vdev_id: vdev id 18846 * 18847 * TSF_TSTAMP_READ_VALUE is the only operation supported 18848 * Return: QDF_STATUS_SUCCESS for success or erro code 18849 */ 18850 static QDF_STATUS 18851 send_vdev_tsf_tstamp_action_cmd_tlv(wmi_unified_t wmi, uint8_t vdev_id) 18852 { 18853 wmi_vdev_tsf_tstamp_action_cmd_fixed_param *cmd; 18854 wmi_buf_t buf; 18855 int32_t len = sizeof(*cmd); 18856 18857 buf = wmi_buf_alloc(wmi, len); 18858 if (!buf) 18859 return QDF_STATUS_E_NOMEM; 18860 18861 cmd = (wmi_vdev_tsf_tstamp_action_cmd_fixed_param *)wmi_buf_data(buf); 18862 WMITLV_SET_HDR(&cmd->tlv_header, 18863 WMITLV_TAG_STRUC_wmi_vdev_tsf_tstamp_action_cmd_fixed_param, 18864 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_tsf_tstamp_action_cmd_fixed_param)); 18865 cmd->vdev_id = vdev_id; 18866 cmd->tsf_action = TSF_TSTAMP_QTIMER_CAPTURE_REQ; 18867 wmi_mtrace(WMI_VDEV_TSF_TSTAMP_ACTION_CMDID, cmd->vdev_id, 0); 18868 if (wmi_unified_cmd_send(wmi, buf, len, 18869 WMI_VDEV_TSF_TSTAMP_ACTION_CMDID)) { 18870 wmi_err("%s: Failed to send WMI_VDEV_TSF_TSTAMP_ACTION_CMDID", 18871 __func__); 18872 wmi_buf_free(buf); 18873 return QDF_STATUS_E_FAILURE; 18874 } 18875 18876 return QDF_STATUS_SUCCESS; 18877 } 18878 18879 /** 18880 * extract_vdev_tsf_report_event_tlv() - extract vdev tsf report from event 18881 * @wmi_handle: wmi handle 18882 * @param evt_buf: pointer to event buffer 18883 * @wmi_host_tsf_event param: Pointer to struct to hold event info 18884 * 18885 * Return: QDF_STATUS_SUCCESS on success and QDF_STATUS_E_FAILURE for failure 18886 */ 18887 static QDF_STATUS 18888 extract_vdev_tsf_report_event_tlv(wmi_unified_t wmi_handle, void *evt_buf, 18889 struct wmi_host_tsf_event *param) 18890 { 18891 WMI_VDEV_TSF_REPORT_EVENTID_param_tlvs *param_buf; 18892 wmi_vdev_tsf_report_event_fixed_param *evt; 18893 18894 param_buf = (WMI_VDEV_TSF_REPORT_EVENTID_param_tlvs *)evt_buf; 18895 if (!param_buf) { 18896 wmi_err("Invalid tsf report event buffer"); 18897 return QDF_STATUS_E_INVAL; 18898 } 18899 18900 evt = param_buf->fixed_param; 18901 param->vdev_id = evt->vdev_id; 18902 param->tsf = ((uint64_t)(evt->tsf_high) << 32) | evt->tsf_low; 18903 param->tsf_low = evt->tsf_low; 18904 param->tsf_high = evt->tsf_high; 18905 param->qtimer_low = evt->qtimer_low; 18906 param->qtimer_high = evt->qtimer_high; 18907 param->tsf_id = evt->tsf_id; 18908 param->tsf_id_valid = evt->tsf_id_valid; 18909 param->mac_id = evt->mac_id; 18910 param->mac_id_valid = evt->mac_id_valid; 18911 param->wlan_global_tsf_low = evt->wlan_global_tsf_low; 18912 param->wlan_global_tsf_high = evt->wlan_global_tsf_high; 18913 param->tqm_timer_low = evt->tqm_timer_low; 18914 param->tqm_timer_high = evt->tqm_timer_high; 18915 param->use_tqm_timer = evt->use_tqm_timer; 18916 18917 return QDF_STATUS_SUCCESS; 18918 } 18919 18920 /** 18921 * extract_pdev_csa_switch_count_status_tlv() - extract pdev csa switch count 18922 * status tlv 18923 * @wmi_handle: wmi handle 18924 * @param evt_buf: pointer to event buffer 18925 * @param param: Pointer to hold csa switch count status event param 18926 * 18927 * Return: QDF_STATUS_SUCCESS for success or error code 18928 */ 18929 static QDF_STATUS extract_pdev_csa_switch_count_status_tlv( 18930 wmi_unified_t wmi_handle, 18931 void *evt_buf, 18932 struct pdev_csa_switch_count_status *param) 18933 { 18934 WMI_PDEV_CSA_SWITCH_COUNT_STATUS_EVENTID_param_tlvs *param_buf; 18935 wmi_pdev_csa_switch_count_status_event_fixed_param *csa_status; 18936 18937 param_buf = (WMI_PDEV_CSA_SWITCH_COUNT_STATUS_EVENTID_param_tlvs *) 18938 evt_buf; 18939 if (!param_buf) { 18940 wmi_err("Invalid CSA status event"); 18941 return QDF_STATUS_E_INVAL; 18942 } 18943 18944 csa_status = param_buf->fixed_param; 18945 18946 param->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host( 18947 wmi_handle, 18948 csa_status->pdev_id); 18949 param->current_switch_count = csa_status->current_switch_count; 18950 param->num_vdevs = csa_status->num_vdevs; 18951 param->vdev_ids = param_buf->vdev_ids; 18952 18953 return QDF_STATUS_SUCCESS; 18954 } 18955 18956 #ifdef CONFIG_AFC_SUPPORT 18957 /** 18958 * send_afc_cmd_tlv() - Sends the AFC indication to FW 18959 * @wmi_handle: wmi handle 18960 * @pdev_id: Pdev id 18961 * @param: Pointer to hold AFC indication. 18962 * 18963 * Return: QDF_STATUS_SUCCESS for success or error code 18964 */ 18965 static 18966 QDF_STATUS send_afc_cmd_tlv(wmi_unified_t wmi_handle, 18967 uint8_t pdev_id, 18968 struct reg_afc_resp_rx_ind_info *param) 18969 { 18970 wmi_buf_t buf; 18971 wmi_afc_cmd_fixed_param *cmd; 18972 uint32_t len; 18973 uint8_t *buf_ptr; 18974 QDF_STATUS ret; 18975 18976 len = sizeof(wmi_afc_cmd_fixed_param); 18977 buf = wmi_buf_alloc(wmi_handle, len); 18978 if (!buf) 18979 return QDF_STATUS_E_NOMEM; 18980 18981 buf_ptr = (uint8_t *)wmi_buf_data(buf); 18982 cmd = (wmi_afc_cmd_fixed_param *)buf_ptr; 18983 18984 WMITLV_SET_HDR(&cmd->tlv_header, 18985 WMITLV_TAG_STRUC_wmi_afc_cmd_fixed_param, 18986 WMITLV_GET_STRUCT_TLVLEN(wmi_afc_cmd_fixed_param)); 18987 18988 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target( 18989 wmi_handle, 18990 pdev_id); 18991 cmd->cmd_type = param->cmd_type; 18992 cmd->serv_resp_format = param->serv_resp_format; 18993 18994 wmi_mtrace(WMI_AFC_CMDID, NO_SESSION, 0); 18995 ret = wmi_unified_cmd_send(wmi_handle, buf, len, WMI_AFC_CMDID); 18996 if (QDF_IS_STATUS_ERROR(ret)) { 18997 wmi_err("Failed to send WMI_AFC_CMDID"); 18998 wmi_buf_free(buf); 18999 return QDF_STATUS_E_FAILURE; 19000 } 19001 19002 return QDF_STATUS_SUCCESS; 19003 } 19004 #endif 19005 19006 /** 19007 * send_set_tpc_power_cmd_tlv() - Sends the set TPC power level to FW 19008 * @wmi_handle: wmi handle 19009 * @param: Pointer to hold TX power info 19010 * 19011 * Return: QDF_STATUS_SUCCESS for success or error code 19012 */ 19013 static QDF_STATUS send_set_tpc_power_cmd_tlv(wmi_unified_t wmi_handle, 19014 uint8_t vdev_id, 19015 struct reg_tpc_power_info *param) 19016 { 19017 wmi_buf_t buf; 19018 wmi_vdev_set_tpc_power_fixed_param *tpc_power_info_param; 19019 wmi_vdev_ch_power_info *ch_power_info; 19020 uint8_t *buf_ptr; 19021 uint16_t idx; 19022 uint32_t len; 19023 QDF_STATUS ret; 19024 19025 len = sizeof(wmi_vdev_set_tpc_power_fixed_param) + WMI_TLV_HDR_SIZE; 19026 len += (sizeof(wmi_vdev_ch_power_info) * param->num_pwr_levels); 19027 19028 buf = wmi_buf_alloc(wmi_handle, len); 19029 if (!buf) 19030 return QDF_STATUS_E_NOMEM; 19031 19032 buf_ptr = (uint8_t *)wmi_buf_data(buf); 19033 tpc_power_info_param = (wmi_vdev_set_tpc_power_fixed_param *)buf_ptr; 19034 19035 WMITLV_SET_HDR(&tpc_power_info_param->tlv_header, 19036 WMITLV_TAG_STRUC_wmi_vdev_set_tpc_power_cmd_fixed_param, 19037 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_set_tpc_power_fixed_param)); 19038 19039 tpc_power_info_param->vdev_id = vdev_id; 19040 tpc_power_info_param->psd_power = param->is_psd_power; 19041 tpc_power_info_param->eirp_power = param->eirp_power; 19042 tpc_power_info_param->power_type_6ghz = param->power_type_6g; 19043 wmi_debug("eirp_power = %d is_psd_power = %d power_type_6ghz = %d", 19044 tpc_power_info_param->eirp_power, 19045 tpc_power_info_param->psd_power, 19046 tpc_power_info_param->power_type_6ghz); 19047 19048 buf_ptr += sizeof(wmi_vdev_set_tpc_power_fixed_param); 19049 WMITLV_SET_HDR(buf_ptr, WMITLV_TAG_ARRAY_STRUC, 19050 param->num_pwr_levels * sizeof(wmi_vdev_ch_power_info)); 19051 19052 buf_ptr += WMI_TLV_HDR_SIZE; 19053 ch_power_info = (wmi_vdev_ch_power_info *)buf_ptr; 19054 19055 for (idx = 0; idx < param->num_pwr_levels; ++idx) { 19056 WMITLV_SET_HDR(&ch_power_info[idx].tlv_header, 19057 WMITLV_TAG_STRUC_wmi_vdev_ch_power_info, 19058 WMITLV_GET_STRUCT_TLVLEN(wmi_vdev_ch_power_info)); 19059 ch_power_info[idx].chan_cfreq = 19060 param->chan_power_info[idx].chan_cfreq; 19061 ch_power_info[idx].tx_power = 19062 param->chan_power_info[idx].tx_power; 19063 wmi_debug("chan_cfreq = %d tx_power = %d", 19064 ch_power_info[idx].chan_cfreq, 19065 ch_power_info[idx].tx_power); 19066 buf_ptr += sizeof(wmi_vdev_ch_power_info); 19067 } 19068 19069 wmi_mtrace(WMI_VDEV_SET_TPC_POWER_CMDID, vdev_id, 0); 19070 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 19071 WMI_VDEV_SET_TPC_POWER_CMDID); 19072 if (QDF_IS_STATUS_ERROR(ret)) 19073 wmi_buf_free(buf); 19074 19075 19076 return ret; 19077 } 19078 19079 /** 19080 * extract_dpd_status_ev_param_tlv() - extract dpd status from FW event 19081 * @wmi_handle: wmi handle 19082 * @evt_buf: event buffer 19083 * @param: dpd status info 19084 * 19085 * Return: QDF_STATUS_SUCCESS for success or error code 19086 */ 19087 static QDF_STATUS 19088 extract_dpd_status_ev_param_tlv(wmi_unified_t wmi_handle, 19089 void *evt_buf, 19090 struct wmi_host_pdev_get_dpd_status_event *param) 19091 { 19092 WMI_PDEV_GET_DPD_STATUS_EVENTID_param_tlvs *param_buf; 19093 wmi_pdev_get_dpd_status_evt_fixed_param *dpd_status; 19094 19095 param_buf = (WMI_PDEV_GET_DPD_STATUS_EVENTID_param_tlvs *)evt_buf; 19096 if (!param_buf) { 19097 wmi_err("Invalid get dpd_status event"); 19098 return QDF_STATUS_E_INVAL; 19099 } 19100 19101 dpd_status = param_buf->fixed_param; 19102 param->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host 19103 (wmi_handle, dpd_status->pdev_id); 19104 param->dpd_status = dpd_status->dpd_status; 19105 19106 return QDF_STATUS_SUCCESS; 19107 } 19108 19109 static int 19110 convert_halphy_status(wmi_pdev_get_halphy_cal_status_evt_fixed_param *status, 19111 WMI_HALPHY_CAL_VALID_BITMAP_STATUS valid_bit) 19112 { 19113 if (status->halphy_cal_valid_bmap && valid_bit) 19114 return (status->halphy_cal_status && valid_bit); 19115 19116 return 0; 19117 } 19118 19119 static QDF_STATUS 19120 extract_halphy_cal_status_ev_param_tlv(wmi_unified_t wmi_handle, 19121 void *evt_buf, 19122 struct wmi_host_pdev_get_halphy_cal_status_event *param) 19123 { 19124 WMI_PDEV_GET_HALPHY_CAL_STATUS_EVENTID_param_tlvs *param_buf; 19125 wmi_pdev_get_halphy_cal_status_evt_fixed_param *halphy_cal_status; 19126 19127 param_buf = (WMI_PDEV_GET_HALPHY_CAL_STATUS_EVENTID_param_tlvs *)evt_buf; 19128 if (!param_buf) { 19129 wmi_err("Invalid get halphy cal status event"); 19130 return QDF_STATUS_E_INVAL; 19131 } 19132 19133 halphy_cal_status = param_buf->fixed_param; 19134 param->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host 19135 (wmi_handle, halphy_cal_status->pdev_id); 19136 param->halphy_cal_adc_status = 19137 convert_halphy_status(halphy_cal_status, 19138 WMI_HALPHY_CAL_ADC_BMAP); 19139 param->halphy_cal_bwfilter_status = 19140 convert_halphy_status(halphy_cal_status, 19141 WMI_HALPHY_CAL_BWFILTER_BMAP); 19142 param->halphy_cal_pdet_and_pal_status = 19143 convert_halphy_status(halphy_cal_status, 19144 WMI_HALPHY_CAL_PDET_AND_PAL_BMAP); 19145 param->halphy_cal_rxdco_status = 19146 convert_halphy_status(halphy_cal_status, 19147 WMI_HALPHY_CAL_RXDCO_BMAP); 19148 param->halphy_cal_comb_txiq_rxiq_status = 19149 convert_halphy_status(halphy_cal_status, 19150 WMI_HALPHY_CAL_COMB_TXLO_TXIQ_RXIQ_BMAP); 19151 param->halphy_cal_ibf_status = 19152 convert_halphy_status(halphy_cal_status, 19153 WMI_HALPHY_CAL_IBF_BMAP); 19154 param->halphy_cal_pa_droop_status = 19155 convert_halphy_status(halphy_cal_status, 19156 WMI_HALPHY_CAL_PA_DROOP_BMAP); 19157 param->halphy_cal_dac_status = 19158 convert_halphy_status(halphy_cal_status, 19159 WMI_HALPHY_CAL_DAC_BMAP); 19160 param->halphy_cal_ani_status = 19161 convert_halphy_status(halphy_cal_status, 19162 WMI_HALPHY_CAL_ANI_BMAP); 19163 param->halphy_cal_noise_floor_status = 19164 convert_halphy_status(halphy_cal_status, 19165 WMI_HALPHY_CAL_NOISE_FLOOR_BMAP); 19166 19167 return QDF_STATUS_SUCCESS; 19168 } 19169 19170 /** 19171 * set_halphy_cal_fw_status_to_host_status() - Convert set halphy cal status to host enum 19172 * @fw_status: set halphy cal status from WMI_PDEV_SET_HALPHY_CAL_BMAP_EVENTID event 19173 * 19174 * Return: host_set_halphy_cal_status 19175 */ 19176 static enum wmi_host_set_halphy_cal_status 19177 set_halphy_cal_fw_status_to_host_status(uint32_t fw_status) 19178 { 19179 if (fw_status == 0) 19180 return WMI_HOST_SET_HALPHY_CAL_STATUS_SUCCESS; 19181 else if (fw_status == 1) 19182 return WMI_HOST_SET_HALPHY_CAL_STATUS_FAIL; 19183 19184 wmi_debug("Unknown set halphy status code(%u) from WMI", fw_status); 19185 return WMI_HOST_SET_HALPHY_CAL_STATUS_FAIL; 19186 } 19187 19188 /** 19189 * extract_halphy_cal_ev_param_tlv() - extract dpd status from FW event 19190 * @wmi_handle: wmi handle 19191 * @evt_buf: event buffer 19192 * @param: set halphy cal status info 19193 * 19194 * Return: QDF_STATUS_SUCCESS for success or error code 19195 */ 19196 static QDF_STATUS 19197 extract_halphy_cal_ev_param_tlv(wmi_unified_t wmi_handle, 19198 void *evt_buf, 19199 struct wmi_host_pdev_set_halphy_cal_event *param) 19200 { 19201 WMI_PDEV_SET_HALPHY_CAL_BMAP_EVENTID_param_tlvs *param_buf; 19202 wmi_pdev_set_halphy_cal_bmap_evt_fixed_param *set_halphy_status; 19203 19204 param_buf = (WMI_PDEV_SET_HALPHY_CAL_BMAP_EVENTID_param_tlvs *)evt_buf; 19205 if (!param_buf) { 19206 wmi_err("Invalid set halphy_status event"); 19207 return QDF_STATUS_E_INVAL; 19208 } 19209 19210 set_halphy_status = param_buf->fixed_param; 19211 param->pdev_id = wmi_handle->ops->convert_pdev_id_target_to_host 19212 (wmi_handle, set_halphy_status->pdev_id); 19213 param->status = set_halphy_cal_fw_status_to_host_status(set_halphy_status->status); 19214 19215 return QDF_STATUS_SUCCESS; 19216 } 19217 19218 /** 19219 * extract_install_key_comp_event_tlv() - extract install key complete event tlv 19220 * @wmi_handle: wmi handle 19221 * @evt_buf: pointer to event buffer 19222 * @len: length of the event buffer 19223 * @param: Pointer to hold install key complete event param 19224 * 19225 * Return: QDF_STATUS_SUCCESS for success or error code 19226 */ 19227 static QDF_STATUS 19228 extract_install_key_comp_event_tlv(wmi_unified_t wmi_handle, 19229 void *evt_buf, uint32_t len, 19230 struct wmi_install_key_comp_event *param) 19231 { 19232 WMI_VDEV_INSTALL_KEY_COMPLETE_EVENTID_param_tlvs *param_buf; 19233 wmi_vdev_install_key_complete_event_fixed_param *key_fp; 19234 19235 if (len < sizeof(*param_buf)) { 19236 wmi_err("invalid event buf len %d", len); 19237 return QDF_STATUS_E_INVAL; 19238 } 19239 19240 param_buf = (WMI_VDEV_INSTALL_KEY_COMPLETE_EVENTID_param_tlvs *)evt_buf; 19241 if (!param_buf) { 19242 wmi_err("received null buf from target"); 19243 return QDF_STATUS_E_INVAL; 19244 } 19245 19246 key_fp = param_buf->fixed_param; 19247 if (!key_fp) { 19248 wmi_err("received null event data from target"); 19249 return QDF_STATUS_E_INVAL; 19250 } 19251 19252 param->vdev_id = key_fp->vdev_id; 19253 param->key_ix = key_fp->key_ix; 19254 param->key_flags = key_fp->key_flags; 19255 param->status = key_fp->status; 19256 WMI_MAC_ADDR_TO_CHAR_ARRAY(&key_fp->peer_macaddr, 19257 param->peer_macaddr); 19258 19259 return QDF_STATUS_SUCCESS; 19260 } 19261 19262 static QDF_STATUS 19263 send_set_halphy_cal_tlv(wmi_unified_t wmi_handle, 19264 struct wmi_host_send_set_halphy_cal_info *param) 19265 { 19266 wmi_buf_t buf; 19267 wmi_pdev_set_halphy_cal_bmap_cmd_fixed_param *cmd; 19268 QDF_STATUS ret; 19269 uint32_t len; 19270 19271 len = sizeof(*cmd); 19272 19273 buf = wmi_buf_alloc(wmi_handle, len); 19274 if (!buf) 19275 return QDF_STATUS_E_FAILURE; 19276 19277 cmd = (void *)wmi_buf_data(buf); 19278 19279 WMITLV_SET_HDR(&cmd->tlv_header, 19280 WMITLV_TAG_STRUC_wmi_pdev_set_halphy_cal_bmap_cmd_fixed_param, 19281 WMITLV_GET_STRUCT_TLVLEN(wmi_pdev_set_halphy_cal_bmap_cmd_fixed_param)); 19282 19283 cmd->pdev_id = wmi_handle->ops->convert_pdev_id_host_to_target(wmi_handle, 19284 param->pdev_id); 19285 cmd->online_halphy_cals_bmap = param->value; 19286 cmd->home_scan_channel = param->chan_sel; 19287 19288 ret = wmi_unified_cmd_send(wmi_handle, buf, len, 19289 WMI_PDEV_SET_HALPHY_CAL_BMAP_CMDID); 19290 if (QDF_IS_STATUS_ERROR(ret)) { 19291 wmi_err("WMI_PDEV_SET_HALPHY_CAL_BMAP_CMDID send returned Error %d",ret); 19292 wmi_buf_free(buf); 19293 } 19294 19295 return ret; 19296 } 19297 19298 #ifdef WLAN_FEATURE_DYNAMIC_MAC_ADDR_UPDATE 19299 /** 19300 * send_set_mac_address_cmd_tlv() - send set MAC address command to fw 19301 * @wmi: wmi handle 19302 * @params: set MAC address command params 19303 * 19304 * Return: QDF_STATUS_SUCCESS for success or error code 19305 */ 19306 static QDF_STATUS 19307 send_set_mac_address_cmd_tlv(wmi_unified_t wmi, 19308 struct set_mac_addr_params *params) 19309 { 19310 wmi_vdev_update_mac_addr_cmd_fixed_param *cmd; 19311 wmi_buf_t buf; 19312 int32_t len = sizeof(*cmd); 19313 19314 buf = wmi_buf_alloc(wmi, len); 19315 if (!buf) 19316 return QDF_STATUS_E_NOMEM; 19317 19318 cmd = (wmi_vdev_update_mac_addr_cmd_fixed_param *)wmi_buf_data(buf); 19319 WMITLV_SET_HDR( 19320 &cmd->tlv_header, 19321 WMITLV_TAG_STRUC_wmi_vdev_update_mac_addr_cmd_fixed_param, 19322 WMITLV_GET_STRUCT_TLVLEN 19323 (wmi_vdev_update_mac_addr_cmd_fixed_param)); 19324 cmd->vdev_id = params->vdev_id; 19325 WMI_CHAR_ARRAY_TO_MAC_ADDR(params->mac_addr.bytes, &cmd->vdev_macaddr); 19326 WMI_CHAR_ARRAY_TO_MAC_ADDR(params->mld_addr.bytes, &cmd->mld_macaddr); 19327 19328 wmi_debug("vdev %d mac_addr " QDF_MAC_ADDR_FMT " mld_addr " 19329 QDF_MAC_ADDR_FMT, cmd->vdev_id, 19330 QDF_MAC_ADDR_REF(params->mac_addr.bytes), 19331 QDF_MAC_ADDR_REF(params->mld_addr.bytes)); 19332 wmi_mtrace(WMI_VDEV_UPDATE_MAC_ADDR_CMDID, cmd->vdev_id, 0); 19333 if (wmi_unified_cmd_send(wmi, buf, len, 19334 WMI_VDEV_UPDATE_MAC_ADDR_CMDID)) { 19335 wmi_buf_free(buf); 19336 return QDF_STATUS_E_FAILURE; 19337 } 19338 19339 return QDF_STATUS_SUCCESS; 19340 } 19341 19342 /** 19343 * extract_update_mac_address_event_tlv() - extract update MAC address event 19344 * @wmi_handle: WMI handle 19345 * @evt_buf: event buffer 19346 * @vdev_id: VDEV ID 19347 * @status: FW status of the set MAC address operation 19348 * 19349 * Return: QDF_STATUS 19350 */ 19351 static QDF_STATUS extract_update_mac_address_event_tlv( 19352 wmi_unified_t wmi_handle, void *evt_buf, 19353 uint8_t *vdev_id, uint8_t *status) 19354 { 19355 WMI_VDEV_UPDATE_MAC_ADDR_CONF_EVENTID_param_tlvs *param_buf; 19356 wmi_vdev_update_mac_addr_conf_event_fixed_param *event; 19357 19358 param_buf = 19359 (WMI_VDEV_UPDATE_MAC_ADDR_CONF_EVENTID_param_tlvs *)evt_buf; 19360 19361 event = param_buf->fixed_param; 19362 19363 *vdev_id = event->vdev_id; 19364 *status = event->status; 19365 19366 return QDF_STATUS_SUCCESS; 19367 } 19368 #endif 19369 19370 #ifdef WLAN_FEATURE_11BE_MLO 19371 /** 19372 * extract_quiet_offload_event_tlv() - extract quiet offload event 19373 * @wmi_handle: WMI handle 19374 * @evt_buf: event buffer 19375 * @mld_mac: mld mac address 19376 * @link_mac: link mac address 19377 * @link_id: link id 19378 * @quiet_status: quiet is started or stopped 19379 * 19380 * Return: QDF_STATUS 19381 */ 19382 static QDF_STATUS extract_quiet_offload_event_tlv( 19383 wmi_unified_t wmi_handle, void *evt_buf, 19384 struct vdev_sta_quiet_event *quiet_event) 19385 { 19386 WMI_QUIET_HANDLING_EVENTID_param_tlvs *param_buf; 19387 wmi_quiet_event_fixed_param *event; 19388 19389 param_buf = (WMI_QUIET_HANDLING_EVENTID_param_tlvs *)evt_buf; 19390 19391 event = param_buf->fixed_param; 19392 19393 if (!(event->mld_mac_address_present && event->linkid_present) && 19394 !event->link_mac_address_present) { 19395 wmi_err("Invalid sta quiet offload event. present bit: mld mac %d link mac %d linkid %d", 19396 event->mld_mac_address_present, 19397 event->linkid_present, 19398 event->link_mac_address_present); 19399 return QDF_STATUS_E_INVAL; 19400 } 19401 19402 if (event->mld_mac_address_present) 19403 WMI_MAC_ADDR_TO_CHAR_ARRAY(&event->mld_mac_address, 19404 quiet_event->mld_mac.bytes); 19405 if (event->link_mac_address_present) 19406 WMI_MAC_ADDR_TO_CHAR_ARRAY(&event->link_mac_address, 19407 quiet_event->link_mac.bytes); 19408 if (event->linkid_present) 19409 quiet_event->link_id = event->linkid; 19410 quiet_event->quiet_status = (event->quiet_status == 19411 WMI_QUIET_EVENT_START); 19412 19413 return QDF_STATUS_SUCCESS; 19414 } 19415 #endif 19416 19417 /** 19418 * send_vdev_pn_mgmt_rxfilter_cmd_tlv() - Send PN mgmt RxFilter command to FW 19419 * @wmi_handle: wmi handle 19420 * @params: RxFilter params 19421 * 19422 * Return: QDF_STATUS_SUCCESS for success or error code 19423 */ 19424 static QDF_STATUS 19425 send_vdev_pn_mgmt_rxfilter_cmd_tlv(wmi_unified_t wmi_handle, 19426 struct vdev_pn_mgmt_rxfilter_params *params) 19427 { 19428 wmi_vdev_pn_mgmt_rx_filter_cmd_fixed_param *cmd; 19429 wmi_buf_t buf; 19430 uint32_t len = sizeof(wmi_vdev_pn_mgmt_rx_filter_cmd_fixed_param); 19431 19432 if (!is_service_enabled_tlv(wmi_handle, 19433 WMI_SERVICE_PN_REPLAY_CHECK_SUPPORT)) { 19434 wmi_err("Rx PN Replay Check not supported by target"); 19435 return QDF_STATUS_E_NOSUPPORT; 19436 } 19437 19438 buf = wmi_buf_alloc(wmi_handle, len); 19439 if (!buf) { 19440 wmi_err("wmi buf alloc failed"); 19441 return QDF_STATUS_E_NOMEM; 19442 } 19443 19444 cmd = (wmi_vdev_pn_mgmt_rx_filter_cmd_fixed_param *)wmi_buf_data(buf); 19445 WMITLV_SET_HDR( 19446 &cmd->tlv_header, 19447 WMITLV_TAG_STRUC_wmi_vdev_pn_mgmt_rx_filter_cmd_fixed_param, 19448 WMITLV_GET_STRUCT_TLVLEN 19449 (wmi_vdev_pn_mgmt_rx_filter_cmd_fixed_param)); 19450 19451 cmd->vdev_id = params->vdev_id; 19452 cmd->pn_rx_filter = params->pn_rxfilter; 19453 19454 if (wmi_unified_cmd_send(wmi_handle, buf, len, 19455 WMI_VDEV_PN_MGMT_RX_FILTER_CMDID)) { 19456 wmi_err("Failed to send WMI command"); 19457 wmi_buf_free(buf); 19458 return QDF_STATUS_E_FAILURE; 19459 } 19460 19461 return QDF_STATUS_SUCCESS; 19462 } 19463 19464 static QDF_STATUS 19465 extract_pktlog_decode_info_event_tlv(wmi_unified_t wmi_handle, void *evt_buf, 19466 uint8_t *pdev_id, uint8_t *software_image, 19467 uint8_t *chip_info, 19468 uint32_t *pktlog_json_version) 19469 { 19470 WMI_PDEV_PKTLOG_DECODE_INFO_EVENTID_param_tlvs *param_buf; 19471 wmi_pdev_pktlog_decode_info_evt_fixed_param *event; 19472 19473 param_buf = 19474 (WMI_PDEV_PKTLOG_DECODE_INFO_EVENTID_param_tlvs *)evt_buf; 19475 19476 event = param_buf->fixed_param; 19477 19478 if ((event->software_image[0] == '\0') || 19479 (event->chip_info[0] == '\0')) { 19480 *pdev_id = event->pdev_id; 19481 return QDF_STATUS_E_INVAL; 19482 } 19483 19484 qdf_mem_copy(software_image, event->software_image, 40); 19485 qdf_mem_copy(chip_info, event->chip_info, 40); 19486 *pktlog_json_version = event->pktlog_defs_json_version; 19487 *pdev_id = event->pdev_id; 19488 return QDF_STATUS_SUCCESS; 19489 } 19490 19491 #ifdef HEALTH_MON_SUPPORT 19492 /** 19493 * extract_health_mon_init_done_info_event_tlv() - Extract health monitor from 19494 * fw 19495 * @wmi_handle: wmi handle 19496 * @evt_buf: pointer to event buffer 19497 * @params: health monitor params 19498 * 19499 * Return: QDF_STATUS_SUCCESS for success or error code 19500 */ 19501 static QDF_STATUS 19502 extract_health_mon_init_done_info_event_tlv(wmi_unified_t wmi_handle, 19503 void *evt_buf, 19504 struct wmi_health_mon_params *param) 19505 { 19506 WMI_HEALTH_MON_INIT_DONE_EVENTID_param_tlvs *param_buf; 19507 wmi_health_mon_init_done_fixed_param *event; 19508 19509 param_buf = 19510 (WMI_HEALTH_MON_INIT_DONE_EVENTID_param_tlvs *)evt_buf; 19511 19512 event = param_buf->fixed_param; 19513 19514 param->ring_buf_paddr_low = event->ring_buf_paddr_low; 19515 param->ring_buf_paddr_high = event->ring_buf_paddr_high; 19516 param->initial_upload_period_ms = event->initial_upload_period_ms; 19517 param->read_index = 0; 19518 19519 return QDF_STATUS_SUCCESS; 19520 } 19521 #endif /* HEALTH_MON_SUPPORT */ 19522 19523 /** 19524 * extract_pdev_telemetry_stats_tlv - extract pdev telemetry stats 19525 * @wmi_handle: wmi handle 19526 * @evt_buf: pointer to event buffer 19527 * @pdev stats: Pointer to hold pdev telemetry stats 19528 * 19529 * Return: QDF_STATUS_SUCCESS for success or error code 19530 */ 19531 static QDF_STATUS 19532 extract_pdev_telemetry_stats_tlv( 19533 wmi_unified_t wmi_handle, void *evt_buf, 19534 struct wmi_host_pdev_telemetry_stats *pdev_stats) 19535 { 19536 WMI_UPDATE_STATS_EVENTID_param_tlvs *param_buf; 19537 wmi_pdev_telemetry_stats *ev; 19538 19539 param_buf = (WMI_UPDATE_STATS_EVENTID_param_tlvs *)evt_buf; 19540 19541 if (param_buf->pdev_telemetry_stats) { 19542 ev = (wmi_pdev_telemetry_stats *)(param_buf->pdev_telemetry_stats); 19543 qdf_mem_copy(pdev_stats->avg_chan_lat_per_ac, 19544 ev->avg_chan_lat_per_ac, 19545 sizeof(ev->avg_chan_lat_per_ac)); 19546 pdev_stats->estimated_air_time_per_ac = 19547 ev->estimated_air_time_per_ac; 19548 } 19549 19550 return QDF_STATUS_SUCCESS; 19551 } 19552 19553 struct wmi_ops tlv_ops = { 19554 .send_vdev_create_cmd = send_vdev_create_cmd_tlv, 19555 .send_vdev_delete_cmd = send_vdev_delete_cmd_tlv, 19556 .send_vdev_nss_chain_params_cmd = send_vdev_nss_chain_params_cmd_tlv, 19557 .send_vdev_down_cmd = send_vdev_down_cmd_tlv, 19558 .send_vdev_start_cmd = send_vdev_start_cmd_tlv, 19559 .send_peer_flush_tids_cmd = send_peer_flush_tids_cmd_tlv, 19560 .send_peer_param_cmd = send_peer_param_cmd_tlv, 19561 .send_vdev_up_cmd = send_vdev_up_cmd_tlv, 19562 .send_vdev_stop_cmd = send_vdev_stop_cmd_tlv, 19563 .send_peer_create_cmd = send_peer_create_cmd_tlv, 19564 .send_peer_delete_cmd = send_peer_delete_cmd_tlv, 19565 .send_peer_delete_all_cmd = send_peer_delete_all_cmd_tlv, 19566 .send_peer_rx_reorder_queue_setup_cmd = 19567 send_peer_rx_reorder_queue_setup_cmd_tlv, 19568 .send_peer_rx_reorder_queue_remove_cmd = 19569 send_peer_rx_reorder_queue_remove_cmd_tlv, 19570 .send_pdev_utf_cmd = send_pdev_utf_cmd_tlv, 19571 .send_pdev_param_cmd = send_pdev_param_cmd_tlv, 19572 .send_multiple_pdev_param_cmd = send_multiple_pdev_param_cmd_tlv, 19573 .send_pdev_set_hw_mode_cmd = send_pdev_set_hw_mode_cmd_tlv, 19574 .send_suspend_cmd = send_suspend_cmd_tlv, 19575 .send_resume_cmd = send_resume_cmd_tlv, 19576 .send_wow_enable_cmd = send_wow_enable_cmd_tlv, 19577 .send_set_ap_ps_param_cmd = send_set_ap_ps_param_cmd_tlv, 19578 .send_set_sta_ps_param_cmd = send_set_sta_ps_param_cmd_tlv, 19579 .send_crash_inject_cmd = send_crash_inject_cmd_tlv, 19580 .send_dbglog_cmd = send_dbglog_cmd_tlv, 19581 .send_vdev_set_param_cmd = send_vdev_set_param_cmd_tlv, 19582 .send_vdev_set_mu_snif_cmd = send_vdev_set_mu_snif_cmd_tlv, 19583 .send_packet_log_enable_cmd = send_packet_log_enable_cmd_tlv, 19584 .send_peer_based_pktlog_cmd = send_peer_based_pktlog_cmd, 19585 .send_time_stamp_sync_cmd = send_time_stamp_sync_cmd_tlv, 19586 .send_packet_log_disable_cmd = send_packet_log_disable_cmd_tlv, 19587 .send_beacon_tmpl_send_cmd = send_beacon_tmpl_send_cmd_tlv, 19588 .send_fd_tmpl_cmd = send_fd_tmpl_cmd_tlv, 19589 .send_peer_assoc_cmd = send_peer_assoc_cmd_tlv, 19590 .send_scan_start_cmd = send_scan_start_cmd_tlv, 19591 .send_scan_stop_cmd = send_scan_stop_cmd_tlv, 19592 .send_scan_chan_list_cmd = send_scan_chan_list_cmd_tlv, 19593 .send_mgmt_cmd = send_mgmt_cmd_tlv, 19594 .send_offchan_data_tx_cmd = send_offchan_data_tx_cmd_tlv, 19595 .send_modem_power_state_cmd = send_modem_power_state_cmd_tlv, 19596 .send_set_sta_ps_mode_cmd = send_set_sta_ps_mode_cmd_tlv, 19597 .send_idle_roam_monitor_cmd = send_idle_roam_monitor_cmd_tlv, 19598 .send_set_sta_uapsd_auto_trig_cmd = 19599 send_set_sta_uapsd_auto_trig_cmd_tlv, 19600 .send_get_temperature_cmd = send_get_temperature_cmd_tlv, 19601 .send_set_smps_params_cmd = send_set_smps_params_cmd_tlv, 19602 .send_set_mimops_cmd = send_set_mimops_cmd_tlv, 19603 .send_set_thermal_mgmt_cmd = send_set_thermal_mgmt_cmd_tlv, 19604 .send_lro_config_cmd = send_lro_config_cmd_tlv, 19605 .send_peer_rate_report_cmd = send_peer_rate_report_cmd_tlv, 19606 .send_probe_rsp_tmpl_send_cmd = 19607 send_probe_rsp_tmpl_send_cmd_tlv, 19608 .send_p2p_go_set_beacon_ie_cmd = 19609 send_p2p_go_set_beacon_ie_cmd_tlv, 19610 .send_setup_install_key_cmd = 19611 send_setup_install_key_cmd_tlv, 19612 .send_scan_probe_setoui_cmd = 19613 send_scan_probe_setoui_cmd_tlv, 19614 #ifdef IPA_OFFLOAD 19615 .send_ipa_offload_control_cmd = 19616 send_ipa_offload_control_cmd_tlv, 19617 #endif 19618 .send_pno_stop_cmd = send_pno_stop_cmd_tlv, 19619 .send_pno_start_cmd = send_pno_start_cmd_tlv, 19620 .send_obss_disable_cmd = send_obss_disable_cmd_tlv, 19621 .send_nlo_mawc_cmd = send_nlo_mawc_cmd_tlv, 19622 #ifdef WLAN_FEATURE_LINK_LAYER_STATS 19623 .send_process_ll_stats_clear_cmd = send_process_ll_stats_clear_cmd_tlv, 19624 .send_process_ll_stats_set_cmd = send_process_ll_stats_set_cmd_tlv, 19625 .send_process_ll_stats_get_cmd = send_process_ll_stats_get_cmd_tlv, 19626 #ifdef FEATURE_CLUB_LL_STATS_AND_GET_STATION 19627 .send_unified_ll_stats_get_sta_cmd = 19628 send_unified_ll_stats_get_sta_cmd_tlv, 19629 #endif /* FEATURE_CLUB_LL_STATS_AND_GET_STATION */ 19630 #endif /* WLAN_FEATURE_LINK_LAYER_STATS*/ 19631 .send_congestion_cmd = send_congestion_cmd_tlv, 19632 .send_snr_request_cmd = send_snr_request_cmd_tlv, 19633 .send_snr_cmd = send_snr_cmd_tlv, 19634 .send_link_status_req_cmd = send_link_status_req_cmd_tlv, 19635 #if !defined(REMOVE_PKT_LOG) && defined(FEATURE_PKTLOG) 19636 .send_pktlog_wmi_send_cmd = send_pktlog_wmi_send_cmd_tlv, 19637 #endif 19638 #ifdef WLAN_SUPPORT_GREEN_AP 19639 .send_egap_conf_params_cmd = send_egap_conf_params_cmd_tlv, 19640 .send_green_ap_ps_cmd = send_green_ap_ps_cmd_tlv, 19641 .extract_green_ap_egap_status_info = 19642 extract_green_ap_egap_status_info_tlv, 19643 #endif 19644 .send_csa_offload_enable_cmd = send_csa_offload_enable_cmd_tlv, 19645 .send_start_oem_data_cmd = send_start_oem_data_cmd_tlv, 19646 #ifdef FEATURE_OEM_DATA 19647 .send_start_oemv2_data_cmd = send_start_oemv2_data_cmd_tlv, 19648 #endif 19649 #ifdef WLAN_FEATURE_CIF_CFR 19650 .send_oem_dma_cfg_cmd = send_oem_dma_cfg_cmd_tlv, 19651 #endif 19652 .send_dfs_phyerr_filter_offload_en_cmd = 19653 send_dfs_phyerr_filter_offload_en_cmd_tlv, 19654 .send_stats_ext_req_cmd = send_stats_ext_req_cmd_tlv, 19655 .send_process_dhcpserver_offload_cmd = 19656 send_process_dhcpserver_offload_cmd_tlv, 19657 .send_pdev_set_regdomain_cmd = 19658 send_pdev_set_regdomain_cmd_tlv, 19659 .send_regdomain_info_to_fw_cmd = send_regdomain_info_to_fw_cmd_tlv, 19660 .send_cfg_action_frm_tb_ppdu_cmd = send_cfg_action_frm_tb_ppdu_cmd_tlv, 19661 .save_fw_version_cmd = save_fw_version_cmd_tlv, 19662 .check_and_update_fw_version = 19663 check_and_update_fw_version_cmd_tlv, 19664 .send_log_supported_evt_cmd = send_log_supported_evt_cmd_tlv, 19665 .send_enable_specific_fw_logs_cmd = 19666 send_enable_specific_fw_logs_cmd_tlv, 19667 .send_flush_logs_to_fw_cmd = send_flush_logs_to_fw_cmd_tlv, 19668 .send_unit_test_cmd = send_unit_test_cmd_tlv, 19669 #ifdef FEATURE_WLAN_APF 19670 .send_set_active_apf_mode_cmd = wmi_send_set_active_apf_mode_cmd_tlv, 19671 .send_apf_enable_cmd = wmi_send_apf_enable_cmd_tlv, 19672 .send_apf_write_work_memory_cmd = 19673 wmi_send_apf_write_work_memory_cmd_tlv, 19674 .send_apf_read_work_memory_cmd = 19675 wmi_send_apf_read_work_memory_cmd_tlv, 19676 .extract_apf_read_memory_resp_event = 19677 wmi_extract_apf_read_memory_resp_event_tlv, 19678 #endif /* FEATURE_WLAN_APF */ 19679 .init_cmd_send = init_cmd_send_tlv, 19680 .send_vdev_set_custom_aggr_size_cmd = 19681 send_vdev_set_custom_aggr_size_cmd_tlv, 19682 .send_vdev_set_qdepth_thresh_cmd = 19683 send_vdev_set_qdepth_thresh_cmd_tlv, 19684 .send_set_vap_dscp_tid_map_cmd = send_set_vap_dscp_tid_map_cmd_tlv, 19685 .send_vdev_set_fwtest_param_cmd = send_vdev_set_fwtest_param_cmd_tlv, 19686 .send_phyerr_disable_cmd = send_phyerr_disable_cmd_tlv, 19687 .send_phyerr_enable_cmd = send_phyerr_enable_cmd_tlv, 19688 .send_periodic_chan_stats_config_cmd = 19689 send_periodic_chan_stats_config_cmd_tlv, 19690 #ifdef WLAN_IOT_SIM_SUPPORT 19691 .send_simulation_test_cmd = send_simulation_test_cmd_tlv, 19692 #endif 19693 .send_vdev_spectral_configure_cmd = 19694 send_vdev_spectral_configure_cmd_tlv, 19695 .send_vdev_spectral_enable_cmd = 19696 send_vdev_spectral_enable_cmd_tlv, 19697 #ifdef WLAN_CONV_SPECTRAL_ENABLE 19698 .extract_pdev_sscan_fw_cmd_fixed_param = 19699 extract_pdev_sscan_fw_cmd_fixed_param_tlv, 19700 .extract_pdev_sscan_fft_bin_index = 19701 extract_pdev_sscan_fft_bin_index_tlv, 19702 .extract_pdev_spectral_session_chan_info = 19703 extract_pdev_spectral_session_chan_info_tlv, 19704 .extract_pdev_spectral_session_detector_info = 19705 extract_pdev_spectral_session_detector_info_tlv, 19706 .extract_spectral_caps_fixed_param = 19707 extract_spectral_caps_fixed_param_tlv, 19708 .extract_spectral_scan_bw_caps = 19709 extract_spectral_scan_bw_caps_tlv, 19710 .extract_spectral_fft_size_caps = 19711 extract_spectral_fft_size_caps_tlv, 19712 #endif /* WLAN_CONV_SPECTRAL_ENABLE */ 19713 .send_thermal_mitigation_param_cmd = 19714 send_thermal_mitigation_param_cmd_tlv, 19715 .send_process_update_edca_param_cmd = 19716 send_process_update_edca_param_cmd_tlv, 19717 .send_bss_color_change_enable_cmd = 19718 send_bss_color_change_enable_cmd_tlv, 19719 .send_coex_config_cmd = send_coex_config_cmd_tlv, 19720 .send_set_country_cmd = send_set_country_cmd_tlv, 19721 .send_addba_send_cmd = send_addba_send_cmd_tlv, 19722 .send_delba_send_cmd = send_delba_send_cmd_tlv, 19723 .send_addba_clearresponse_cmd = send_addba_clearresponse_cmd_tlv, 19724 .get_target_cap_from_service_ready = extract_service_ready_tlv, 19725 .extract_hal_reg_cap = extract_hal_reg_cap_tlv, 19726 .extract_num_mem_reqs = extract_num_mem_reqs_tlv, 19727 .extract_host_mem_req = extract_host_mem_req_tlv, 19728 .save_service_bitmap = save_service_bitmap_tlv, 19729 .save_ext_service_bitmap = save_ext_service_bitmap_tlv, 19730 .is_service_enabled = is_service_enabled_tlv, 19731 .save_fw_version = save_fw_version_in_service_ready_tlv, 19732 .ready_extract_init_status = ready_extract_init_status_tlv, 19733 .ready_extract_mac_addr = ready_extract_mac_addr_tlv, 19734 .ready_extract_mac_addr_list = ready_extract_mac_addr_list_tlv, 19735 .extract_ready_event_params = extract_ready_event_params_tlv, 19736 .extract_dbglog_data_len = extract_dbglog_data_len_tlv, 19737 .extract_mgmt_rx_params = extract_mgmt_rx_params_tlv, 19738 .extract_frame_pn_params = extract_frame_pn_params_tlv, 19739 .extract_is_conn_ap_frame = extract_is_conn_ap_frm_param_tlv, 19740 .extract_vdev_roam_param = extract_vdev_roam_param_tlv, 19741 .extract_vdev_scan_ev_param = extract_vdev_scan_ev_param_tlv, 19742 #ifdef FEATURE_WLAN_SCAN_PNO 19743 .extract_nlo_match_ev_param = extract_nlo_match_ev_param_tlv, 19744 .extract_nlo_complete_ev_param = extract_nlo_complete_ev_param_tlv, 19745 #endif 19746 .extract_unit_test = extract_unit_test_tlv, 19747 .extract_pdev_ext_stats = extract_pdev_ext_stats_tlv, 19748 .extract_bcn_stats = extract_bcn_stats_tlv, 19749 .extract_bcnflt_stats = extract_bcnflt_stats_tlv, 19750 .extract_chan_stats = extract_chan_stats_tlv, 19751 .extract_vdev_prb_fils_stats = extract_vdev_prb_fils_stats_tlv, 19752 .extract_profile_ctx = extract_profile_ctx_tlv, 19753 .extract_profile_data = extract_profile_data_tlv, 19754 .send_fw_test_cmd = send_fw_test_cmd_tlv, 19755 .send_wfa_test_cmd = send_wfa_test_cmd_tlv, 19756 .send_power_dbg_cmd = send_power_dbg_cmd_tlv, 19757 .extract_service_ready_ext = extract_service_ready_ext_tlv, 19758 .extract_service_ready_ext2 = extract_service_ready_ext2_tlv, 19759 .extract_dbs_or_sbs_service_ready_ext2 = 19760 extract_dbs_or_sbs_cap_service_ready_ext2_tlv, 19761 .extract_hw_mode_cap_service_ready_ext = 19762 extract_hw_mode_cap_service_ready_ext_tlv, 19763 .extract_mac_phy_cap_service_ready_ext = 19764 extract_mac_phy_cap_service_ready_ext_tlv, 19765 .extract_mac_phy_cap_service_ready_ext2 = 19766 extract_mac_phy_cap_service_ready_ext2_tlv, 19767 .extract_reg_cap_service_ready_ext = 19768 extract_reg_cap_service_ready_ext_tlv, 19769 .extract_hal_reg_cap_ext2 = extract_hal_reg_cap_ext2_tlv, 19770 .extract_dbr_ring_cap_service_ready_ext = 19771 extract_dbr_ring_cap_service_ready_ext_tlv, 19772 .extract_dbr_ring_cap_service_ready_ext2 = 19773 extract_dbr_ring_cap_service_ready_ext2_tlv, 19774 .extract_scan_radio_cap_service_ready_ext2 = 19775 extract_scan_radio_cap_service_ready_ext2_tlv, 19776 .extract_sw_cal_ver_ext2 = extract_sw_cal_ver_ext2_tlv, 19777 .extract_sar_cap_service_ready_ext = 19778 extract_sar_cap_service_ready_ext_tlv, 19779 .extract_pdev_utf_event = extract_pdev_utf_event_tlv, 19780 .wmi_set_htc_tx_tag = wmi_set_htc_tx_tag_tlv, 19781 .extract_fips_event_data = extract_fips_event_data_tlv, 19782 #ifdef WLAN_FEATURE_FIPS_BER_CCMGCM 19783 .extract_fips_extend_ev_data = extract_fips_extend_event_data_tlv, 19784 #endif 19785 #if defined(WLAN_SUPPORT_FILS) || defined(CONFIG_BAND_6GHZ) 19786 .send_vdev_fils_enable_cmd = send_vdev_fils_enable_cmd_send, 19787 #endif 19788 #ifdef WLAN_FEATURE_DISA 19789 .extract_encrypt_decrypt_resp_event = 19790 extract_encrypt_decrypt_resp_event_tlv, 19791 #endif 19792 .send_pdev_fips_cmd = send_pdev_fips_cmd_tlv, 19793 #ifdef WLAN_FEATURE_FIPS_BER_CCMGCM 19794 .send_pdev_fips_extend_cmd = send_pdev_fips_extend_cmd_tlv, 19795 .send_pdev_fips_mode_set_cmd = send_pdev_fips_mode_set_cmd_tlv, 19796 #endif 19797 .extract_get_pn_data = extract_get_pn_data_tlv, 19798 .send_pdev_get_pn_cmd = send_pdev_get_pn_cmd_tlv, 19799 .extract_get_rxpn_data = extract_get_rxpn_data_tlv, 19800 .send_pdev_get_rxpn_cmd = send_pdev_get_rxpn_cmd_tlv, 19801 .send_wlan_profile_enable_cmd = send_wlan_profile_enable_cmd_tlv, 19802 #ifdef WLAN_FEATURE_DISA 19803 .send_encrypt_decrypt_send_cmd = send_encrypt_decrypt_send_cmd_tlv, 19804 #endif 19805 .send_wlan_profile_trigger_cmd = send_wlan_profile_trigger_cmd_tlv, 19806 .send_wlan_profile_hist_intvl_cmd = 19807 send_wlan_profile_hist_intvl_cmd_tlv, 19808 .is_management_record = is_management_record_tlv, 19809 .is_diag_event = is_diag_event_tlv, 19810 #ifdef WLAN_FEATURE_ACTION_OUI 19811 .send_action_oui_cmd = send_action_oui_cmd_tlv, 19812 #endif 19813 .send_dfs_phyerr_offload_en_cmd = send_dfs_phyerr_offload_en_cmd_tlv, 19814 #ifdef QCA_SUPPORT_AGILE_DFS 19815 .send_adfs_ch_cfg_cmd = send_adfs_ch_cfg_cmd_tlv, 19816 .send_adfs_ocac_abort_cmd = send_adfs_ocac_abort_cmd_tlv, 19817 #endif 19818 .send_dfs_phyerr_offload_dis_cmd = send_dfs_phyerr_offload_dis_cmd_tlv, 19819 .extract_reg_chan_list_update_event = 19820 extract_reg_chan_list_update_event_tlv, 19821 #ifdef CONFIG_BAND_6GHZ 19822 .extract_reg_chan_list_ext_update_event = 19823 extract_reg_chan_list_ext_update_event_tlv, 19824 #ifdef CONFIG_AFC_SUPPORT 19825 .extract_afc_event = extract_afc_event_tlv, 19826 #endif 19827 #endif 19828 #ifdef WLAN_SUPPORT_RF_CHARACTERIZATION 19829 .extract_num_rf_characterization_entries = 19830 extract_num_rf_characterization_entries_tlv, 19831 .extract_rf_characterization_entries = 19832 extract_rf_characterization_entries_tlv, 19833 #endif 19834 .extract_chainmask_tables = 19835 extract_chainmask_tables_tlv, 19836 .extract_thermal_stats = extract_thermal_stats_tlv, 19837 .extract_thermal_level_stats = extract_thermal_level_stats_tlv, 19838 .send_get_rcpi_cmd = send_get_rcpi_cmd_tlv, 19839 .extract_rcpi_response_event = extract_rcpi_response_event_tlv, 19840 #ifdef DFS_COMPONENT_ENABLE 19841 .extract_dfs_cac_complete_event = extract_dfs_cac_complete_event_tlv, 19842 .extract_dfs_ocac_complete_event = extract_dfs_ocac_complete_event_tlv, 19843 .extract_dfs_radar_detection_event = 19844 extract_dfs_radar_detection_event_tlv, 19845 .extract_wlan_radar_event_info = extract_wlan_radar_event_info_tlv, 19846 #endif 19847 .convert_pdev_id_host_to_target = 19848 convert_host_pdev_id_to_target_pdev_id_legacy, 19849 .convert_pdev_id_target_to_host = 19850 convert_target_pdev_id_to_host_pdev_id_legacy, 19851 19852 .convert_host_pdev_id_to_target = 19853 convert_host_pdev_id_to_target_pdev_id, 19854 .convert_target_pdev_id_to_host = 19855 convert_target_pdev_id_to_host_pdev_id, 19856 19857 .convert_host_vdev_param_tlv = convert_host_vdev_param_tlv, 19858 19859 .convert_phy_id_host_to_target = 19860 convert_host_phy_id_to_target_phy_id_legacy, 19861 .convert_phy_id_target_to_host = 19862 convert_target_phy_id_to_host_phy_id_legacy, 19863 19864 .convert_host_phy_id_to_target = 19865 convert_host_phy_id_to_target_phy_id, 19866 .convert_target_phy_id_to_host = 19867 convert_target_phy_id_to_host_phy_id, 19868 19869 .send_start_11d_scan_cmd = send_start_11d_scan_cmd_tlv, 19870 .send_stop_11d_scan_cmd = send_stop_11d_scan_cmd_tlv, 19871 .extract_reg_11d_new_country_event = 19872 extract_reg_11d_new_country_event_tlv, 19873 .send_user_country_code_cmd = send_user_country_code_cmd_tlv, 19874 .extract_reg_ch_avoid_event = 19875 extract_reg_ch_avoid_event_tlv, 19876 .send_obss_detection_cfg_cmd = send_obss_detection_cfg_cmd_tlv, 19877 .extract_obss_detection_info = extract_obss_detection_info_tlv, 19878 .wmi_pdev_id_conversion_enable = wmi_tlv_pdev_id_conversion_enable, 19879 .wmi_free_allocated_event = wmitlv_free_allocated_event_tlvs, 19880 .wmi_check_and_pad_event = wmitlv_check_and_pad_event_tlvs, 19881 .wmi_check_command_params = wmitlv_check_command_tlv_params, 19882 .extract_comb_phyerr = extract_comb_phyerr_tlv, 19883 .extract_single_phyerr = extract_single_phyerr_tlv, 19884 #ifdef QCA_SUPPORT_CP_STATS 19885 .extract_cca_stats = extract_cca_stats_tlv, 19886 #endif 19887 .extract_esp_estimation_ev_param = 19888 extract_esp_estimation_ev_param_tlv, 19889 .send_roam_scan_stats_cmd = send_roam_scan_stats_cmd_tlv, 19890 .extract_roam_scan_stats_res_evt = extract_roam_scan_stats_res_evt_tlv, 19891 #ifdef OBSS_PD 19892 .send_obss_spatial_reuse_set = send_obss_spatial_reuse_set_cmd_tlv, 19893 .send_obss_spatial_reuse_set_def_thresh = 19894 send_obss_spatial_reuse_set_def_thresh_cmd_tlv, 19895 .send_self_srg_bss_color_bitmap_set = 19896 send_self_srg_bss_color_bitmap_set_cmd_tlv, 19897 .send_self_srg_partial_bssid_bitmap_set = 19898 send_self_srg_partial_bssid_bitmap_set_cmd_tlv, 19899 .send_self_srg_obss_color_enable_bitmap = 19900 send_self_srg_obss_color_enable_bitmap_cmd_tlv, 19901 .send_self_srg_obss_bssid_enable_bitmap = 19902 send_self_srg_obss_bssid_enable_bitmap_cmd_tlv, 19903 .send_self_non_srg_obss_color_enable_bitmap = 19904 send_self_non_srg_obss_color_enable_bitmap_cmd_tlv, 19905 .send_self_non_srg_obss_bssid_enable_bitmap = 19906 send_self_non_srg_obss_bssid_enable_bitmap_cmd_tlv, 19907 #endif 19908 .extract_offload_bcn_tx_status_evt = extract_offload_bcn_tx_status_evt, 19909 .extract_ctl_failsafe_check_ev_param = 19910 extract_ctl_failsafe_check_ev_param_tlv, 19911 #ifdef WIFI_POS_CONVERGED 19912 .extract_oem_response_param = extract_oem_response_param_tlv, 19913 #endif /* WIFI_POS_CONVERGED */ 19914 #if defined(WIFI_POS_CONVERGED) && defined(WLAN_FEATURE_RTT_11AZ_SUPPORT) 19915 .extract_pasn_peer_create_req_event = 19916 extract_pasn_peer_create_req_event_tlv, 19917 .extract_pasn_peer_delete_req_event = 19918 extract_pasn_peer_delete_req_event_tlv, 19919 .send_rtt_pasn_auth_status_cmd = 19920 send_rtt_pasn_auth_status_cmd_tlv, 19921 .send_rtt_pasn_deauth_cmd = 19922 send_rtt_pasn_deauth_cmd_tlv, 19923 #endif 19924 #ifdef WLAN_MWS_INFO_DEBUGFS 19925 .send_mws_coex_status_req_cmd = send_mws_coex_status_req_cmd_tlv, 19926 #endif 19927 .extract_hw_mode_resp_event = extract_hw_mode_resp_event_status_tlv, 19928 #ifdef FEATURE_ANI_LEVEL_REQUEST 19929 .send_ani_level_cmd = send_ani_level_cmd_tlv, 19930 .extract_ani_level = extract_ani_level_tlv, 19931 #endif /* FEATURE_ANI_LEVEL_REQUEST */ 19932 .extract_roam_trigger_stats = extract_roam_trigger_stats_tlv, 19933 .extract_roam_scan_stats = extract_roam_scan_stats_tlv, 19934 .extract_roam_result_stats = extract_roam_result_stats_tlv, 19935 .extract_roam_11kv_stats = extract_roam_11kv_stats_tlv, 19936 #ifdef WLAN_FEATURE_PKT_CAPTURE 19937 .extract_vdev_mgmt_offload_event = extract_vdev_mgmt_offload_event_tlv, 19938 #endif 19939 #ifdef WLAN_FEATURE_PKT_CAPTURE_V2 19940 .extract_smart_monitor_event = extract_smart_monitor_event_tlv, 19941 #endif 19942 19943 #ifdef FEATURE_WLAN_TIME_SYNC_FTM 19944 .send_wlan_time_sync_ftm_trigger_cmd = send_wlan_ts_ftm_trigger_cmd_tlv, 19945 .send_wlan_ts_qtime_cmd = send_wlan_ts_qtime_cmd_tlv, 19946 .extract_time_sync_ftm_start_stop_event = 19947 extract_time_sync_ftm_start_stop_event_tlv, 19948 .extract_time_sync_ftm_offset_event = 19949 extract_time_sync_ftm_offset_event_tlv, 19950 #endif /* FEATURE_WLAN_TIME_SYNC_FTM */ 19951 .send_roam_scan_ch_list_req_cmd = send_roam_scan_ch_list_req_cmd_tlv, 19952 .send_injector_config_cmd = send_injector_config_cmd_tlv, 19953 .send_cp_stats_cmd = send_cp_stats_cmd_tlv, 19954 .send_halphy_stats_cmd = send_halphy_stats_cmd_tlv, 19955 #ifdef FEATURE_MEC_OFFLOAD 19956 .send_pdev_set_mec_timer_cmd = send_pdev_set_mec_timer_cmd_tlv, 19957 #endif 19958 #ifdef WLAN_SUPPORT_INFRA_CTRL_PATH_STATS 19959 .extract_infra_cp_stats = extract_infra_cp_stats_tlv, 19960 #endif /* WLAN_SUPPORT_INFRA_CTRL_PATH_STATS */ 19961 .extract_cp_stats_more_pending = 19962 extract_cp_stats_more_pending_tlv, 19963 .extract_halphy_stats_end_of_event = 19964 extract_halphy_stats_end_of_event_tlv, 19965 .extract_halphy_stats_event_count = 19966 extract_halphy_stats_event_count_tlv, 19967 .send_vdev_tsf_tstamp_action_cmd = send_vdev_tsf_tstamp_action_cmd_tlv, 19968 .extract_vdev_tsf_report_event = extract_vdev_tsf_report_event_tlv, 19969 .extract_pdev_csa_switch_count_status = 19970 extract_pdev_csa_switch_count_status_tlv, 19971 .send_set_tpc_power_cmd = send_set_tpc_power_cmd_tlv, 19972 #ifdef CONFIG_AFC_SUPPORT 19973 .send_afc_cmd = send_afc_cmd_tlv, 19974 #endif 19975 .extract_dpd_status_ev_param = extract_dpd_status_ev_param_tlv, 19976 .extract_install_key_comp_event = extract_install_key_comp_event_tlv, 19977 .send_vdev_set_ltf_key_seed_cmd = 19978 send_vdev_set_ltf_key_seed_cmd_tlv, 19979 .extract_halphy_cal_status_ev_param = extract_halphy_cal_status_ev_param_tlv, 19980 .send_set_halphy_cal = send_set_halphy_cal_tlv, 19981 .extract_halphy_cal_ev_param = extract_halphy_cal_ev_param_tlv, 19982 #ifdef WLAN_MGMT_RX_REO_SUPPORT 19983 .extract_mgmt_rx_fw_consumed = extract_mgmt_rx_fw_consumed_tlv, 19984 .extract_mgmt_rx_reo_params = extract_mgmt_rx_reo_params_tlv, 19985 .send_mgmt_rx_reo_filter_config_cmd = 19986 send_mgmt_rx_reo_filter_config_cmd_tlv, 19987 #endif 19988 19989 #ifdef WLAN_FEATURE_ROAM_OFFLOAD 19990 .send_roam_set_param_cmd = send_roam_set_param_cmd_tlv, 19991 #endif /* WLAN_FEATURE_ROAM_OFFLOAD */ 19992 19993 #ifdef WLAN_FEATURE_DYNAMIC_MAC_ADDR_UPDATE 19994 .send_set_mac_address_cmd = send_set_mac_address_cmd_tlv, 19995 .extract_update_mac_address_event = 19996 extract_update_mac_address_event_tlv, 19997 #endif 19998 19999 #ifdef WLAN_FEATURE_11BE_MLO 20000 .extract_quiet_offload_event = 20001 extract_quiet_offload_event_tlv, 20002 #endif 20003 20004 #ifdef WLAN_SUPPORT_PPEDS 20005 .peer_ppe_ds_param_send = peer_ppe_ds_param_send_tlv, 20006 #endif /* WLAN_SUPPORT_PPEDS */ 20007 20008 .send_vdev_pn_mgmt_rxfilter_cmd = send_vdev_pn_mgmt_rxfilter_cmd_tlv, 20009 .extract_pktlog_decode_info_event = 20010 extract_pktlog_decode_info_event_tlv, 20011 .extract_pdev_telemetry_stats = extract_pdev_telemetry_stats_tlv, 20012 .extract_mgmt_rx_ext_params = extract_mgmt_rx_ext_params_tlv, 20013 #ifdef WLAN_FEATURE_PEER_TXQ_FLUSH_CONF 20014 .send_peer_txq_flush_config_cmd = send_peer_txq_flush_config_cmd_tlv, 20015 #endif 20016 #ifdef WLAN_FEATURE_DBAM_CONFIG 20017 .send_dbam_config_cmd = send_dbam_config_cmd_tlv, 20018 .extract_dbam_config_resp_event = extract_dbam_config_resp_event_tlv, 20019 #endif 20020 #ifdef FEATURE_SET 20021 .feature_set_cmd_send = feature_set_cmd_send_tlv, 20022 #endif 20023 #ifdef HEALTH_MON_SUPPORT 20024 .extract_health_mon_init_done_info_event = 20025 extract_health_mon_init_done_info_event_tlv, 20026 #endif /* HEALTH_MON_SUPPORT */ 20027 .send_multiple_vdev_param_cmd = send_multiple_vdev_param_cmd_tlv, 20028 }; 20029 20030 #ifdef WLAN_FEATURE_11BE_MLO 20031 static void populate_tlv_events_id_mlo(uint32_t *event_ids) 20032 { 20033 event_ids[wmi_mlo_setup_complete_event_id] = 20034 WMI_MLO_SETUP_COMPLETE_EVENTID; 20035 event_ids[wmi_mlo_teardown_complete_event_id] = 20036 WMI_MLO_TEARDOWN_COMPLETE_EVENTID; 20037 event_ids[wmi_mlo_link_set_active_resp_eventid] = 20038 WMI_MLO_LINK_SET_ACTIVE_RESP_EVENTID; 20039 event_ids[wmi_vdev_quiet_offload_eventid] = 20040 WMI_QUIET_HANDLING_EVENTID; 20041 } 20042 #else /* WLAN_FEATURE_11BE_MLO */ 20043 static inline void populate_tlv_events_id_mlo(uint32_t *event_ids) 20044 { 20045 } 20046 #endif /* WLAN_FEATURE_11BE_MLO */ 20047 20048 /** 20049 * populate_tlv_event_id() - populates wmi event ids 20050 * 20051 * @param event_ids: Pointer to hold event ids 20052 * Return: None 20053 */ 20054 static void populate_tlv_events_id(uint32_t *event_ids) 20055 { 20056 event_ids[wmi_service_ready_event_id] = WMI_SERVICE_READY_EVENTID; 20057 event_ids[wmi_ready_event_id] = WMI_READY_EVENTID; 20058 event_ids[wmi_scan_event_id] = WMI_SCAN_EVENTID; 20059 event_ids[wmi_pdev_tpc_config_event_id] = WMI_PDEV_TPC_CONFIG_EVENTID; 20060 event_ids[wmi_chan_info_event_id] = WMI_CHAN_INFO_EVENTID; 20061 event_ids[wmi_phyerr_event_id] = WMI_PHYERR_EVENTID; 20062 event_ids[wmi_pdev_dump_event_id] = WMI_PDEV_DUMP_EVENTID; 20063 event_ids[wmi_tx_pause_event_id] = WMI_TX_PAUSE_EVENTID; 20064 event_ids[wmi_dfs_radar_event_id] = WMI_DFS_RADAR_EVENTID; 20065 event_ids[wmi_pdev_l1ss_track_event_id] = WMI_PDEV_L1SS_TRACK_EVENTID; 20066 event_ids[wmi_pdev_temperature_event_id] = WMI_PDEV_TEMPERATURE_EVENTID; 20067 event_ids[wmi_service_ready_ext_event_id] = 20068 WMI_SERVICE_READY_EXT_EVENTID; 20069 event_ids[wmi_service_ready_ext2_event_id] = 20070 WMI_SERVICE_READY_EXT2_EVENTID; 20071 event_ids[wmi_vdev_start_resp_event_id] = WMI_VDEV_START_RESP_EVENTID; 20072 event_ids[wmi_vdev_stopped_event_id] = WMI_VDEV_STOPPED_EVENTID; 20073 event_ids[wmi_vdev_install_key_complete_event_id] = 20074 WMI_VDEV_INSTALL_KEY_COMPLETE_EVENTID; 20075 event_ids[wmi_vdev_mcc_bcn_intvl_change_req_event_id] = 20076 WMI_VDEV_MCC_BCN_INTERVAL_CHANGE_REQ_EVENTID; 20077 20078 event_ids[wmi_vdev_tsf_report_event_id] = WMI_VDEV_TSF_REPORT_EVENTID; 20079 event_ids[wmi_peer_sta_kickout_event_id] = WMI_PEER_STA_KICKOUT_EVENTID; 20080 event_ids[wmi_peer_info_event_id] = WMI_PEER_INFO_EVENTID; 20081 event_ids[wmi_peer_tx_fail_cnt_thr_event_id] = 20082 WMI_PEER_TX_FAIL_CNT_THR_EVENTID; 20083 event_ids[wmi_peer_estimated_linkspeed_event_id] = 20084 WMI_PEER_ESTIMATED_LINKSPEED_EVENTID; 20085 event_ids[wmi_peer_state_event_id] = WMI_PEER_STATE_EVENTID; 20086 event_ids[wmi_peer_create_conf_event_id] = 20087 WMI_PEER_CREATE_CONF_EVENTID; 20088 event_ids[wmi_peer_delete_response_event_id] = 20089 WMI_PEER_DELETE_RESP_EVENTID; 20090 event_ids[wmi_peer_delete_all_response_event_id] = 20091 WMI_VDEV_DELETE_ALL_PEER_RESP_EVENTID; 20092 event_ids[wmi_mgmt_rx_event_id] = WMI_MGMT_RX_EVENTID; 20093 event_ids[wmi_host_swba_event_id] = WMI_HOST_SWBA_EVENTID; 20094 event_ids[wmi_tbttoffset_update_event_id] = 20095 WMI_TBTTOFFSET_UPDATE_EVENTID; 20096 event_ids[wmi_ext_tbttoffset_update_event_id] = 20097 WMI_TBTTOFFSET_EXT_UPDATE_EVENTID; 20098 event_ids[wmi_offload_bcn_tx_status_event_id] = 20099 WMI_OFFLOAD_BCN_TX_STATUS_EVENTID; 20100 event_ids[wmi_offload_prob_resp_tx_status_event_id] = 20101 WMI_OFFLOAD_PROB_RESP_TX_STATUS_EVENTID; 20102 event_ids[wmi_mgmt_tx_completion_event_id] = 20103 WMI_MGMT_TX_COMPLETION_EVENTID; 20104 event_ids[wmi_pdev_nfcal_power_all_channels_event_id] = 20105 WMI_PDEV_NFCAL_POWER_ALL_CHANNELS_EVENTID; 20106 event_ids[wmi_tx_delba_complete_event_id] = 20107 WMI_TX_DELBA_COMPLETE_EVENTID; 20108 event_ids[wmi_tx_addba_complete_event_id] = 20109 WMI_TX_ADDBA_COMPLETE_EVENTID; 20110 event_ids[wmi_ba_rsp_ssn_event_id] = WMI_BA_RSP_SSN_EVENTID; 20111 20112 event_ids[wmi_aggr_state_trig_event_id] = WMI_AGGR_STATE_TRIG_EVENTID; 20113 20114 event_ids[wmi_roam_event_id] = WMI_ROAM_EVENTID; 20115 event_ids[wmi_profile_match] = WMI_PROFILE_MATCH; 20116 20117 event_ids[wmi_roam_synch_event_id] = WMI_ROAM_SYNCH_EVENTID; 20118 event_ids[wmi_roam_synch_frame_event_id] = WMI_ROAM_SYNCH_FRAME_EVENTID; 20119 20120 event_ids[wmi_p2p_disc_event_id] = WMI_P2P_DISC_EVENTID; 20121 20122 event_ids[wmi_p2p_noa_event_id] = WMI_P2P_NOA_EVENTID; 20123 event_ids[wmi_p2p_lo_stop_event_id] = 20124 WMI_P2P_LISTEN_OFFLOAD_STOPPED_EVENTID; 20125 event_ids[wmi_vdev_add_macaddr_rx_filter_event_id] = 20126 WMI_VDEV_ADD_MAC_ADDR_TO_RX_FILTER_STATUS_EVENTID; 20127 event_ids[wmi_pdev_resume_event_id] = WMI_PDEV_RESUME_EVENTID; 20128 event_ids[wmi_wow_wakeup_host_event_id] = WMI_WOW_WAKEUP_HOST_EVENTID; 20129 event_ids[wmi_d0_wow_disable_ack_event_id] = 20130 WMI_D0_WOW_DISABLE_ACK_EVENTID; 20131 event_ids[wmi_wow_initial_wakeup_event_id] = 20132 WMI_WOW_INITIAL_WAKEUP_EVENTID; 20133 20134 event_ids[wmi_rtt_meas_report_event_id] = 20135 WMI_RTT_MEASUREMENT_REPORT_EVENTID; 20136 event_ids[wmi_tsf_meas_report_event_id] = 20137 WMI_TSF_MEASUREMENT_REPORT_EVENTID; 20138 event_ids[wmi_rtt_error_report_event_id] = WMI_RTT_ERROR_REPORT_EVENTID; 20139 event_ids[wmi_stats_ext_event_id] = WMI_STATS_EXT_EVENTID; 20140 event_ids[wmi_iface_link_stats_event_id] = WMI_IFACE_LINK_STATS_EVENTID; 20141 event_ids[wmi_peer_link_stats_event_id] = WMI_PEER_LINK_STATS_EVENTID; 20142 event_ids[wmi_radio_link_stats_link] = WMI_RADIO_LINK_STATS_EVENTID; 20143 event_ids[wmi_diag_event_id_log_supported_event_id] = 20144 WMI_DIAG_EVENT_LOG_SUPPORTED_EVENTID; 20145 event_ids[wmi_nlo_match_event_id] = WMI_NLO_MATCH_EVENTID; 20146 event_ids[wmi_nlo_scan_complete_event_id] = 20147 WMI_NLO_SCAN_COMPLETE_EVENTID; 20148 event_ids[wmi_apfind_event_id] = WMI_APFIND_EVENTID; 20149 event_ids[wmi_passpoint_match_event_id] = WMI_PASSPOINT_MATCH_EVENTID; 20150 20151 event_ids[wmi_gtk_offload_status_event_id] = 20152 WMI_GTK_OFFLOAD_STATUS_EVENTID; 20153 event_ids[wmi_gtk_rekey_fail_event_id] = WMI_GTK_REKEY_FAIL_EVENTID; 20154 event_ids[wmi_csa_handling_event_id] = WMI_CSA_HANDLING_EVENTID; 20155 event_ids[wmi_chatter_pc_query_event_id] = WMI_CHATTER_PC_QUERY_EVENTID; 20156 20157 event_ids[wmi_echo_event_id] = WMI_ECHO_EVENTID; 20158 20159 event_ids[wmi_pdev_utf_event_id] = WMI_PDEV_UTF_EVENTID; 20160 20161 event_ids[wmi_dbg_msg_event_id] = WMI_DEBUG_MESG_EVENTID; 20162 event_ids[wmi_update_stats_event_id] = WMI_UPDATE_STATS_EVENTID; 20163 event_ids[wmi_debug_print_event_id] = WMI_DEBUG_PRINT_EVENTID; 20164 event_ids[wmi_dcs_interference_event_id] = WMI_DCS_INTERFERENCE_EVENTID; 20165 event_ids[wmi_pdev_qvit_event_id] = WMI_PDEV_QVIT_EVENTID; 20166 event_ids[wmi_wlan_profile_data_event_id] = 20167 WMI_WLAN_PROFILE_DATA_EVENTID; 20168 event_ids[wmi_pdev_ftm_intg_event_id] = WMI_PDEV_FTM_INTG_EVENTID; 20169 event_ids[wmi_wlan_freq_avoid_event_id] = WMI_WLAN_FREQ_AVOID_EVENTID; 20170 event_ids[wmi_vdev_get_keepalive_event_id] = 20171 WMI_VDEV_GET_KEEPALIVE_EVENTID; 20172 event_ids[wmi_thermal_mgmt_event_id] = WMI_THERMAL_MGMT_EVENTID; 20173 20174 event_ids[wmi_diag_container_event_id] = 20175 WMI_DIAG_DATA_CONTAINER_EVENTID; 20176 20177 event_ids[wmi_host_auto_shutdown_event_id] = 20178 WMI_HOST_AUTO_SHUTDOWN_EVENTID; 20179 20180 event_ids[wmi_update_whal_mib_stats_event_id] = 20181 WMI_UPDATE_WHAL_MIB_STATS_EVENTID; 20182 20183 /*update ht/vht info based on vdev (rx and tx NSS and preamble) */ 20184 event_ids[wmi_update_vdev_rate_stats_event_id] = 20185 WMI_UPDATE_VDEV_RATE_STATS_EVENTID; 20186 20187 event_ids[wmi_diag_event_id] = WMI_DIAG_EVENTID; 20188 event_ids[wmi_unit_test_event_id] = WMI_UNIT_TEST_EVENTID; 20189 20190 /** Set OCB Sched Response, deprecated */ 20191 event_ids[wmi_ocb_set_sched_event_id] = WMI_OCB_SET_SCHED_EVENTID; 20192 20193 event_ids[wmi_dbg_mesg_flush_complete_event_id] = 20194 WMI_DEBUG_MESG_FLUSH_COMPLETE_EVENTID; 20195 event_ids[wmi_rssi_breach_event_id] = WMI_RSSI_BREACH_EVENTID; 20196 20197 /* GPIO Event */ 20198 event_ids[wmi_gpio_input_event_id] = WMI_GPIO_INPUT_EVENTID; 20199 event_ids[wmi_uploadh_event_id] = WMI_UPLOADH_EVENTID; 20200 20201 event_ids[wmi_captureh_event_id] = WMI_CAPTUREH_EVENTID; 20202 event_ids[wmi_rfkill_state_change_event_id] = 20203 WMI_RFKILL_STATE_CHANGE_EVENTID; 20204 20205 /* TDLS Event */ 20206 event_ids[wmi_tdls_peer_event_id] = WMI_TDLS_PEER_EVENTID; 20207 20208 event_ids[wmi_batch_scan_enabled_event_id] = 20209 WMI_BATCH_SCAN_ENABLED_EVENTID; 20210 event_ids[wmi_batch_scan_result_event_id] = 20211 WMI_BATCH_SCAN_RESULT_EVENTID; 20212 /* OEM Event */ 20213 event_ids[wmi_oem_cap_event_id] = WMI_OEM_CAPABILITY_EVENTID; 20214 event_ids[wmi_oem_meas_report_event_id] = 20215 WMI_OEM_MEASUREMENT_REPORT_EVENTID; 20216 event_ids[wmi_oem_report_event_id] = WMI_OEM_ERROR_REPORT_EVENTID; 20217 20218 /* NAN Event */ 20219 event_ids[wmi_nan_event_id] = WMI_NAN_EVENTID; 20220 20221 /* LPI Event */ 20222 event_ids[wmi_lpi_result_event_id] = WMI_LPI_RESULT_EVENTID; 20223 event_ids[wmi_lpi_status_event_id] = WMI_LPI_STATUS_EVENTID; 20224 event_ids[wmi_lpi_handoff_event_id] = WMI_LPI_HANDOFF_EVENTID; 20225 20226 /* ExtScan events */ 20227 event_ids[wmi_extscan_start_stop_event_id] = 20228 WMI_EXTSCAN_START_STOP_EVENTID; 20229 event_ids[wmi_extscan_operation_event_id] = 20230 WMI_EXTSCAN_OPERATION_EVENTID; 20231 event_ids[wmi_extscan_table_usage_event_id] = 20232 WMI_EXTSCAN_TABLE_USAGE_EVENTID; 20233 event_ids[wmi_extscan_cached_results_event_id] = 20234 WMI_EXTSCAN_CACHED_RESULTS_EVENTID; 20235 event_ids[wmi_extscan_wlan_change_results_event_id] = 20236 WMI_EXTSCAN_WLAN_CHANGE_RESULTS_EVENTID; 20237 event_ids[wmi_extscan_hotlist_match_event_id] = 20238 WMI_EXTSCAN_HOTLIST_MATCH_EVENTID; 20239 event_ids[wmi_extscan_capabilities_event_id] = 20240 WMI_EXTSCAN_CAPABILITIES_EVENTID; 20241 event_ids[wmi_extscan_hotlist_ssid_match_event_id] = 20242 WMI_EXTSCAN_HOTLIST_SSID_MATCH_EVENTID; 20243 20244 /* mDNS offload events */ 20245 event_ids[wmi_mdns_stats_event_id] = WMI_MDNS_STATS_EVENTID; 20246 20247 /* SAP Authentication offload events */ 20248 event_ids[wmi_sap_ofl_add_sta_event_id] = WMI_SAP_OFL_ADD_STA_EVENTID; 20249 event_ids[wmi_sap_ofl_del_sta_event_id] = WMI_SAP_OFL_DEL_STA_EVENTID; 20250 20251 /** Out-of-context-of-bss (OCB) events */ 20252 event_ids[wmi_ocb_set_config_resp_event_id] = 20253 WMI_OCB_SET_CONFIG_RESP_EVENTID; 20254 event_ids[wmi_ocb_get_tsf_timer_resp_event_id] = 20255 WMI_OCB_GET_TSF_TIMER_RESP_EVENTID; 20256 event_ids[wmi_dcc_get_stats_resp_event_id] = 20257 WMI_DCC_GET_STATS_RESP_EVENTID; 20258 event_ids[wmi_dcc_update_ndl_resp_event_id] = 20259 WMI_DCC_UPDATE_NDL_RESP_EVENTID; 20260 event_ids[wmi_dcc_stats_event_id] = WMI_DCC_STATS_EVENTID; 20261 /* System-On-Chip events */ 20262 event_ids[wmi_soc_set_hw_mode_resp_event_id] = 20263 WMI_SOC_SET_HW_MODE_RESP_EVENTID; 20264 event_ids[wmi_soc_hw_mode_transition_event_id] = 20265 WMI_SOC_HW_MODE_TRANSITION_EVENTID; 20266 event_ids[wmi_soc_set_dual_mac_config_resp_event_id] = 20267 WMI_SOC_SET_DUAL_MAC_CONFIG_RESP_EVENTID; 20268 event_ids[wmi_pdev_fips_event_id] = WMI_PDEV_FIPS_EVENTID; 20269 #ifdef WLAN_FEATURE_FIPS_BER_CCMGCM 20270 event_ids[wmi_pdev_fips_extend_event_id] = WMI_PDEV_FIPS_EXTEND_EVENTID; 20271 #endif 20272 event_ids[wmi_pdev_csa_switch_count_status_event_id] = 20273 WMI_PDEV_CSA_SWITCH_COUNT_STATUS_EVENTID; 20274 event_ids[wmi_vdev_ocac_complete_event_id] = 20275 WMI_VDEV_ADFS_OCAC_COMPLETE_EVENTID; 20276 event_ids[wmi_reg_chan_list_cc_event_id] = WMI_REG_CHAN_LIST_CC_EVENTID; 20277 event_ids[wmi_reg_chan_list_cc_ext_event_id] = 20278 WMI_REG_CHAN_LIST_CC_EXT_EVENTID; 20279 #ifdef CONFIG_AFC_SUPPORT 20280 event_ids[wmi_afc_event_id] = WMI_AFC_EVENTID, 20281 #endif 20282 event_ids[wmi_inst_rssi_stats_event_id] = WMI_INST_RSSI_STATS_EVENTID; 20283 event_ids[wmi_pdev_tpc_config_event_id] = WMI_PDEV_TPC_CONFIG_EVENTID; 20284 event_ids[wmi_peer_sta_ps_statechg_event_id] = 20285 WMI_PEER_STA_PS_STATECHG_EVENTID; 20286 event_ids[wmi_pdev_channel_hopping_event_id] = 20287 WMI_PDEV_CHANNEL_HOPPING_EVENTID; 20288 event_ids[wmi_offchan_data_tx_completion_event] = 20289 WMI_OFFCHAN_DATA_TX_COMPLETION_EVENTID; 20290 event_ids[wmi_dfs_cac_complete_id] = WMI_VDEV_DFS_CAC_COMPLETE_EVENTID; 20291 event_ids[wmi_dfs_radar_detection_event_id] = 20292 WMI_PDEV_DFS_RADAR_DETECTION_EVENTID; 20293 event_ids[wmi_tt_stats_event_id] = WMI_THERM_THROT_STATS_EVENTID; 20294 event_ids[wmi_11d_new_country_event_id] = WMI_11D_NEW_COUNTRY_EVENTID; 20295 event_ids[wmi_pdev_tpc_event_id] = WMI_PDEV_TPC_EVENTID; 20296 event_ids[wmi_get_arp_stats_req_id] = WMI_VDEV_GET_ARP_STAT_EVENTID; 20297 event_ids[wmi_service_available_event_id] = 20298 WMI_SERVICE_AVAILABLE_EVENTID; 20299 event_ids[wmi_update_rcpi_event_id] = WMI_UPDATE_RCPI_EVENTID; 20300 event_ids[wmi_pdev_check_cal_version_event_id] = WMI_PDEV_CHECK_CAL_VERSION_EVENTID; 20301 /* NDP events */ 20302 event_ids[wmi_ndp_initiator_rsp_event_id] = 20303 WMI_NDP_INITIATOR_RSP_EVENTID; 20304 event_ids[wmi_ndp_indication_event_id] = WMI_NDP_INDICATION_EVENTID; 20305 event_ids[wmi_ndp_confirm_event_id] = WMI_NDP_CONFIRM_EVENTID; 20306 event_ids[wmi_ndp_responder_rsp_event_id] = 20307 WMI_NDP_RESPONDER_RSP_EVENTID; 20308 event_ids[wmi_ndp_end_indication_event_id] = 20309 WMI_NDP_END_INDICATION_EVENTID; 20310 event_ids[wmi_ndp_end_rsp_event_id] = WMI_NDP_END_RSP_EVENTID; 20311 event_ids[wmi_ndl_schedule_update_event_id] = 20312 WMI_NDL_SCHEDULE_UPDATE_EVENTID; 20313 event_ids[wmi_ndp_event_id] = WMI_NDP_EVENTID; 20314 20315 event_ids[wmi_oem_response_event_id] = WMI_OEM_RESPONSE_EVENTID; 20316 event_ids[wmi_peer_stats_info_event_id] = WMI_PEER_STATS_INFO_EVENTID; 20317 event_ids[wmi_pdev_chip_power_stats_event_id] = 20318 WMI_PDEV_CHIP_POWER_STATS_EVENTID; 20319 event_ids[wmi_ap_ps_egap_info_event_id] = WMI_AP_PS_EGAP_INFO_EVENTID; 20320 event_ids[wmi_peer_assoc_conf_event_id] = WMI_PEER_ASSOC_CONF_EVENTID; 20321 event_ids[wmi_vdev_delete_resp_event_id] = WMI_VDEV_DELETE_RESP_EVENTID; 20322 event_ids[wmi_apf_capability_info_event_id] = 20323 WMI_BPF_CAPABILIY_INFO_EVENTID; 20324 event_ids[wmi_vdev_encrypt_decrypt_data_rsp_event_id] = 20325 WMI_VDEV_ENCRYPT_DECRYPT_DATA_RESP_EVENTID; 20326 event_ids[wmi_report_rx_aggr_failure_event_id] = 20327 WMI_REPORT_RX_AGGR_FAILURE_EVENTID; 20328 event_ids[wmi_pdev_chip_pwr_save_failure_detect_event_id] = 20329 WMI_PDEV_CHIP_POWER_SAVE_FAILURE_DETECTED_EVENTID; 20330 event_ids[wmi_peer_antdiv_info_event_id] = WMI_PEER_ANTDIV_INFO_EVENTID; 20331 event_ids[wmi_pdev_set_hw_mode_rsp_event_id] = 20332 WMI_PDEV_SET_HW_MODE_RESP_EVENTID; 20333 event_ids[wmi_pdev_hw_mode_transition_event_id] = 20334 WMI_PDEV_HW_MODE_TRANSITION_EVENTID; 20335 event_ids[wmi_pdev_set_mac_config_resp_event_id] = 20336 WMI_PDEV_SET_MAC_CONFIG_RESP_EVENTID; 20337 event_ids[wmi_coex_bt_activity_event_id] = 20338 WMI_WLAN_COEX_BT_ACTIVITY_EVENTID; 20339 event_ids[wmi_mgmt_tx_bundle_completion_event_id] = 20340 WMI_MGMT_TX_BUNDLE_COMPLETION_EVENTID; 20341 event_ids[wmi_radio_tx_power_level_stats_event_id] = 20342 WMI_RADIO_TX_POWER_LEVEL_STATS_EVENTID; 20343 event_ids[wmi_report_stats_event_id] = WMI_REPORT_STATS_EVENTID; 20344 event_ids[wmi_dma_buf_release_event_id] = 20345 WMI_PDEV_DMA_RING_BUF_RELEASE_EVENTID; 20346 event_ids[wmi_sap_obss_detection_report_event_id] = 20347 WMI_SAP_OBSS_DETECTION_REPORT_EVENTID; 20348 event_ids[wmi_host_swfda_event_id] = WMI_HOST_SWFDA_EVENTID; 20349 event_ids[wmi_sar_get_limits_event_id] = WMI_SAR_GET_LIMITS_EVENTID; 20350 event_ids[wmi_obss_color_collision_report_event_id] = 20351 WMI_OBSS_COLOR_COLLISION_DETECTION_EVENTID; 20352 event_ids[wmi_pdev_div_rssi_antid_event_id] = 20353 WMI_PDEV_DIV_RSSI_ANTID_EVENTID; 20354 #ifdef WLAN_SUPPORT_TWT 20355 event_ids[wmi_twt_enable_complete_event_id] = 20356 WMI_TWT_ENABLE_COMPLETE_EVENTID; 20357 event_ids[wmi_twt_disable_complete_event_id] = 20358 WMI_TWT_DISABLE_COMPLETE_EVENTID; 20359 event_ids[wmi_twt_add_dialog_complete_event_id] = 20360 WMI_TWT_ADD_DIALOG_COMPLETE_EVENTID; 20361 event_ids[wmi_twt_del_dialog_complete_event_id] = 20362 WMI_TWT_DEL_DIALOG_COMPLETE_EVENTID; 20363 event_ids[wmi_twt_pause_dialog_complete_event_id] = 20364 WMI_TWT_PAUSE_DIALOG_COMPLETE_EVENTID; 20365 event_ids[wmi_twt_resume_dialog_complete_event_id] = 20366 WMI_TWT_RESUME_DIALOG_COMPLETE_EVENTID; 20367 event_ids[wmi_twt_nudge_dialog_complete_event_id] = 20368 WMI_TWT_NUDGE_DIALOG_COMPLETE_EVENTID; 20369 event_ids[wmi_twt_session_stats_event_id] = 20370 WMI_TWT_SESSION_STATS_EVENTID; 20371 event_ids[wmi_twt_notify_event_id] = 20372 WMI_TWT_NOTIFY_EVENTID; 20373 event_ids[wmi_twt_ack_complete_event_id] = 20374 WMI_TWT_ACK_EVENTID; 20375 #endif 20376 event_ids[wmi_apf_get_vdev_work_memory_resp_event_id] = 20377 WMI_BPF_GET_VDEV_WORK_MEMORY_RESP_EVENTID; 20378 event_ids[wmi_wlan_sar2_result_event_id] = WMI_SAR2_RESULT_EVENTID; 20379 event_ids[wmi_esp_estimate_event_id] = WMI_ESP_ESTIMATE_EVENTID; 20380 event_ids[wmi_roam_scan_stats_event_id] = WMI_ROAM_SCAN_STATS_EVENTID; 20381 #ifdef WLAN_FEATURE_INTEROP_ISSUES_AP 20382 event_ids[wmi_pdev_interop_issues_ap_event_id] = 20383 WMI_PDEV_RAP_INFO_EVENTID; 20384 #endif 20385 #ifdef AST_HKV1_WORKAROUND 20386 event_ids[wmi_wds_peer_event_id] = WMI_WDS_PEER_EVENTID; 20387 #endif 20388 event_ids[wmi_pdev_ctl_failsafe_check_event_id] = 20389 WMI_PDEV_CTL_FAILSAFE_CHECK_EVENTID; 20390 event_ids[wmi_vdev_bcn_reception_stats_event_id] = 20391 WMI_VDEV_BCN_RECEPTION_STATS_EVENTID; 20392 event_ids[wmi_roam_denylist_event_id] = WMI_ROAM_BLACKLIST_EVENTID; 20393 event_ids[wmi_wlm_stats_event_id] = WMI_WLM_STATS_EVENTID; 20394 event_ids[wmi_peer_cfr_capture_event_id] = WMI_PEER_CFR_CAPTURE_EVENTID; 20395 event_ids[wmi_pdev_cold_boot_cal_event_id] = 20396 WMI_PDEV_COLD_BOOT_CAL_DATA_EVENTID; 20397 #ifdef WLAN_MWS_INFO_DEBUGFS 20398 event_ids[wmi_vdev_get_mws_coex_state_eventid] = 20399 WMI_VDEV_GET_MWS_COEX_STATE_EVENTID; 20400 event_ids[wmi_vdev_get_mws_coex_dpwb_state_eventid] = 20401 WMI_VDEV_GET_MWS_COEX_DPWB_STATE_EVENTID; 20402 event_ids[wmi_vdev_get_mws_coex_tdm_state_eventid] = 20403 WMI_VDEV_GET_MWS_COEX_TDM_STATE_EVENTID; 20404 event_ids[wmi_vdev_get_mws_coex_idrx_state_eventid] = 20405 WMI_VDEV_GET_MWS_COEX_IDRX_STATE_EVENTID; 20406 event_ids[wmi_vdev_get_mws_coex_antenna_sharing_state_eventid] = 20407 WMI_VDEV_GET_MWS_COEX_ANTENNA_SHARING_STATE_EVENTID; 20408 #endif 20409 event_ids[wmi_coex_report_antenna_isolation_event_id] = 20410 WMI_COEX_REPORT_ANTENNA_ISOLATION_EVENTID; 20411 event_ids[wmi_peer_ratecode_list_event_id] = 20412 WMI_PEER_RATECODE_LIST_EVENTID; 20413 event_ids[wmi_chan_rf_characterization_info_event_id] = 20414 WMI_CHAN_RF_CHARACTERIZATION_INFO_EVENTID; 20415 event_ids[wmi_roam_auth_offload_event_id] = 20416 WMI_ROAM_PREAUTH_START_EVENTID; 20417 event_ids[wmi_get_elna_bypass_event_id] = WMI_GET_ELNA_BYPASS_EVENTID; 20418 event_ids[wmi_motion_det_host_eventid] = WMI_MOTION_DET_HOST_EVENTID; 20419 event_ids[wmi_motion_det_base_line_host_eventid] = 20420 WMI_MOTION_DET_BASE_LINE_HOST_EVENTID; 20421 event_ids[wmi_get_ani_level_event_id] = WMI_GET_CHANNEL_ANI_EVENTID; 20422 event_ids[wmi_peer_tx_pn_response_event_id] = 20423 WMI_PEER_TX_PN_RESPONSE_EVENTID; 20424 event_ids[wmi_roam_stats_event_id] = WMI_ROAM_STATS_EVENTID; 20425 event_ids[wmi_oem_data_event_id] = WMI_OEM_DATA_EVENTID; 20426 event_ids[wmi_mgmt_offload_data_event_id] = 20427 WMI_VDEV_MGMT_OFFLOAD_EVENTID; 20428 event_ids[wmi_nan_dmesg_event_id] = 20429 WMI_NAN_DMESG_EVENTID; 20430 event_ids[wmi_pdev_multi_vdev_restart_response_event_id] = 20431 WMI_PDEV_MULTIPLE_VDEV_RESTART_RESP_EVENTID; 20432 event_ids[wmi_roam_pmkid_request_event_id] = 20433 WMI_ROAM_PMKID_REQUEST_EVENTID; 20434 #ifdef FEATURE_WLAN_TIME_SYNC_FTM 20435 event_ids[wmi_wlan_time_sync_ftm_start_stop_event_id] = 20436 WMI_VDEV_AUDIO_SYNC_START_STOP_EVENTID; 20437 event_ids[wmi_wlan_time_sync_q_initiator_target_offset_eventid] = 20438 WMI_VDEV_AUDIO_SYNC_Q_MASTER_SLAVE_OFFSET_EVENTID; 20439 #endif 20440 event_ids[wmi_roam_scan_chan_list_id] = 20441 WMI_ROAM_SCAN_CHANNEL_LIST_EVENTID; 20442 event_ids[wmi_muedca_params_config_eventid] = 20443 WMI_MUEDCA_PARAMS_CONFIG_EVENTID; 20444 event_ids[wmi_pdev_sscan_fw_param_eventid] = 20445 WMI_PDEV_SSCAN_FW_PARAM_EVENTID; 20446 event_ids[wmi_roam_cap_report_event_id] = 20447 WMI_ROAM_CAPABILITY_REPORT_EVENTID; 20448 event_ids[wmi_vdev_bcn_latency_event_id] = 20449 WMI_VDEV_BCN_LATENCY_EVENTID; 20450 event_ids[wmi_vdev_disconnect_event_id] = 20451 WMI_VDEV_DISCONNECT_EVENTID; 20452 event_ids[wmi_peer_create_conf_event_id] = 20453 WMI_PEER_CREATE_CONF_EVENTID; 20454 event_ids[wmi_pdev_cp_fwstats_eventid] = 20455 WMI_CTRL_PATH_STATS_EVENTID; 20456 event_ids[wmi_pdev_halphy_fwstats_eventid] = 20457 WMI_HALPHY_CTRL_PATH_STATS_EVENTID; 20458 event_ids[wmi_vdev_send_big_data_p2_eventid] = 20459 WMI_VDEV_SEND_BIG_DATA_P2_EVENTID; 20460 event_ids[wmi_pdev_get_dpd_status_event_id] = 20461 WMI_PDEV_GET_DPD_STATUS_EVENTID; 20462 #ifdef WLAN_FEATURE_PKT_CAPTURE_V2 20463 event_ids[wmi_vdev_smart_monitor_event_id] = 20464 WMI_VDEV_SMART_MONITOR_EVENTID; 20465 #endif 20466 event_ids[wmi_pdev_get_halphy_cal_status_event_id] = 20467 WMI_PDEV_GET_HALPHY_CAL_STATUS_EVENTID; 20468 event_ids[wmi_pdev_set_halphy_cal_event_id] = 20469 WMI_PDEV_SET_HALPHY_CAL_BMAP_EVENTID; 20470 event_ids[wmi_pdev_aoa_phasedelta_event_id] = 20471 WMI_PDEV_AOA_PHASEDELTA_EVENTID; 20472 #ifdef WLAN_MGMT_RX_REO_SUPPORT 20473 event_ids[wmi_mgmt_rx_fw_consumed_eventid] = 20474 WMI_MGMT_RX_FW_CONSUMED_EVENTID; 20475 #endif 20476 populate_tlv_events_id_mlo(event_ids); 20477 event_ids[wmi_roam_frame_event_id] = 20478 WMI_ROAM_FRAME_EVENTID; 20479 #ifdef WLAN_FEATURE_DYNAMIC_MAC_ADDR_UPDATE 20480 event_ids[wmi_vdev_update_mac_addr_conf_eventid] = 20481 WMI_VDEV_UPDATE_MAC_ADDR_CONF_EVENTID; 20482 #endif 20483 #ifdef WLAN_FEATURE_MCC_QUOTA 20484 event_ids[wmi_resmgr_chan_time_quota_changed_eventid] = 20485 WMI_RESMGR_CHAN_TIME_QUOTA_CHANGED_EVENTID; 20486 #endif 20487 event_ids[wmi_peer_rx_pn_response_event_id] = 20488 WMI_PEER_RX_PN_RESPONSE_EVENTID; 20489 event_ids[wmi_extract_pktlog_decode_info_eventid] = 20490 WMI_PDEV_PKTLOG_DECODE_INFO_EVENTID; 20491 #ifdef QCA_RSSI_DB2DBM 20492 event_ids[wmi_pdev_rssi_dbm_conversion_params_info_eventid] = 20493 WMI_PDEV_RSSI_DBM_CONVERSION_PARAMS_INFO_EVENTID; 20494 #endif 20495 #ifdef MULTI_CLIENT_LL_SUPPORT 20496 event_ids[wmi_vdev_latency_event_id] = WMI_VDEV_LATENCY_LEVEL_EVENTID; 20497 #endif 20498 #if defined(WIFI_POS_CONVERGED) && defined(WLAN_FEATURE_RTT_11AZ_SUPPORT) 20499 event_ids[wmi_rtt_pasn_peer_create_req_eventid] = 20500 WMI_RTT_PASN_PEER_CREATE_REQ_EVENTID; 20501 event_ids[wmi_rtt_pasn_peer_delete_eventid] = 20502 WMI_RTT_PASN_PEER_DELETE_EVENTID; 20503 #endif 20504 #ifdef WLAN_VENDOR_HANDOFF_CONTROL 20505 event_ids[wmi_get_roam_vendor_control_param_event_id] = 20506 WMI_ROAM_GET_VENDOR_CONTROL_PARAM_EVENTID; 20507 #endif 20508 #ifdef WLAN_FEATURE_DBAM_CONFIG 20509 event_ids[wmi_coex_dbam_complete_event_id] = 20510 WMI_COEX_DBAM_COMPLETE_EVENTID; 20511 #endif 20512 event_ids[wmi_spectral_capabilities_eventid] = 20513 WMI_SPECTRAL_CAPABILITIES_EVENTID; 20514 #ifdef WLAN_FEATURE_COAP 20515 event_ids[wmi_wow_coap_buf_info_eventid] = 20516 WMI_WOW_COAP_BUF_INFO_EVENTID; 20517 #endif 20518 #ifdef HEALTH_MON_SUPPORT 20519 event_ids[wmi_extract_health_mon_init_done_info_eventid] = 20520 WMI_HEALTH_MON_INIT_DONE_EVENTID; 20521 #endif /* HEALTH_MON_SUPPORT */ 20522 } 20523 20524 #ifdef WLAN_FEATURE_LINK_LAYER_STATS 20525 #ifdef FEATURE_CLUB_LL_STATS_AND_GET_STATION 20526 static void wmi_populate_service_get_sta_in_ll_stats_req(uint32_t *wmi_service) 20527 { 20528 wmi_service[wmi_service_get_station_in_ll_stats_req] = 20529 WMI_SERVICE_UNIFIED_LL_GET_STA_CMD_SUPPORT; 20530 } 20531 #else 20532 static void wmi_populate_service_get_sta_in_ll_stats_req(uint32_t *wmi_service) 20533 { 20534 } 20535 #endif /* FEATURE_CLUB_LL_STATS_AND_GET_STATION */ 20536 #else 20537 static void wmi_populate_service_get_sta_in_ll_stats_req(uint32_t *wmi_service) 20538 { 20539 } 20540 #endif /* WLAN_FEATURE_LINK_LAYER_STATS */ 20541 20542 #ifdef WLAN_FEATURE_11BE_MLO 20543 static void populate_tlv_service_mlo(uint32_t *wmi_service) 20544 { 20545 wmi_service[wmi_service_mlo_sta_nan_ndi_support] = 20546 WMI_SERVICE_MLO_STA_NAN_NDI_SUPPORT; 20547 } 20548 #else /* WLAN_FEATURE_11BE_MLO */ 20549 static inline void populate_tlv_service_mlo(uint32_t *wmi_service) 20550 { 20551 } 20552 #endif /* WLAN_FEATURE_11BE_MLO */ 20553 20554 /** 20555 * populate_tlv_service() - populates wmi services 20556 * 20557 * @param wmi_service: Pointer to hold wmi_service 20558 * Return: None 20559 */ 20560 static void populate_tlv_service(uint32_t *wmi_service) 20561 { 20562 wmi_service[wmi_service_beacon_offload] = WMI_SERVICE_BEACON_OFFLOAD; 20563 wmi_service[wmi_service_ack_timeout] = WMI_SERVICE_ACK_TIMEOUT; 20564 wmi_service[wmi_service_scan_offload] = WMI_SERVICE_SCAN_OFFLOAD; 20565 wmi_service[wmi_service_roam_scan_offload] = 20566 WMI_SERVICE_ROAM_SCAN_OFFLOAD; 20567 wmi_service[wmi_service_bcn_miss_offload] = 20568 WMI_SERVICE_BCN_MISS_OFFLOAD; 20569 wmi_service[wmi_service_sta_pwrsave] = WMI_SERVICE_STA_PWRSAVE; 20570 wmi_service[wmi_service_sta_advanced_pwrsave] = 20571 WMI_SERVICE_STA_ADVANCED_PWRSAVE; 20572 wmi_service[wmi_service_ap_uapsd] = WMI_SERVICE_AP_UAPSD; 20573 wmi_service[wmi_service_ap_dfs] = WMI_SERVICE_AP_DFS; 20574 wmi_service[wmi_service_11ac] = WMI_SERVICE_11AC; 20575 wmi_service[wmi_service_blockack] = WMI_SERVICE_BLOCKACK; 20576 wmi_service[wmi_service_phyerr] = WMI_SERVICE_PHYERR; 20577 wmi_service[wmi_service_bcn_filter] = WMI_SERVICE_BCN_FILTER; 20578 wmi_service[wmi_service_rtt] = WMI_SERVICE_RTT; 20579 wmi_service[wmi_service_wow] = WMI_SERVICE_WOW; 20580 wmi_service[wmi_service_ratectrl_cache] = WMI_SERVICE_RATECTRL_CACHE; 20581 wmi_service[wmi_service_iram_tids] = WMI_SERVICE_IRAM_TIDS; 20582 wmi_service[wmi_service_arpns_offload] = WMI_SERVICE_ARPNS_OFFLOAD; 20583 wmi_service[wmi_service_nlo] = WMI_SERVICE_NLO; 20584 wmi_service[wmi_service_gtk_offload] = WMI_SERVICE_GTK_OFFLOAD; 20585 wmi_service[wmi_service_scan_sch] = WMI_SERVICE_SCAN_SCH; 20586 wmi_service[wmi_service_csa_offload] = WMI_SERVICE_CSA_OFFLOAD; 20587 wmi_service[wmi_service_chatter] = WMI_SERVICE_CHATTER; 20588 wmi_service[wmi_service_coex_freqavoid] = WMI_SERVICE_COEX_FREQAVOID; 20589 wmi_service[wmi_service_packet_power_save] = 20590 WMI_SERVICE_PACKET_POWER_SAVE; 20591 wmi_service[wmi_service_force_fw_hang] = WMI_SERVICE_FORCE_FW_HANG; 20592 wmi_service[wmi_service_gpio] = WMI_SERVICE_GPIO; 20593 wmi_service[wmi_service_sta_dtim_ps_modulated_dtim] = 20594 WMI_SERVICE_STA_DTIM_PS_MODULATED_DTIM; 20595 wmi_service[wmi_sta_uapsd_basic_auto_trig] = 20596 WMI_STA_UAPSD_BASIC_AUTO_TRIG; 20597 wmi_service[wmi_sta_uapsd_var_auto_trig] = WMI_STA_UAPSD_VAR_AUTO_TRIG; 20598 wmi_service[wmi_service_sta_keep_alive] = WMI_SERVICE_STA_KEEP_ALIVE; 20599 wmi_service[wmi_service_tx_encap] = WMI_SERVICE_TX_ENCAP; 20600 wmi_service[wmi_service_ap_ps_detect_out_of_sync] = 20601 WMI_SERVICE_AP_PS_DETECT_OUT_OF_SYNC; 20602 wmi_service[wmi_service_early_rx] = WMI_SERVICE_EARLY_RX; 20603 wmi_service[wmi_service_sta_smps] = WMI_SERVICE_STA_SMPS; 20604 wmi_service[wmi_service_fwtest] = WMI_SERVICE_FWTEST; 20605 wmi_service[wmi_service_sta_wmmac] = WMI_SERVICE_STA_WMMAC; 20606 wmi_service[wmi_service_tdls] = WMI_SERVICE_TDLS; 20607 wmi_service[wmi_service_burst] = WMI_SERVICE_BURST; 20608 wmi_service[wmi_service_mcc_bcn_interval_change] = 20609 WMI_SERVICE_MCC_BCN_INTERVAL_CHANGE; 20610 wmi_service[wmi_service_adaptive_ocs] = WMI_SERVICE_ADAPTIVE_OCS; 20611 wmi_service[wmi_service_ba_ssn_support] = WMI_SERVICE_BA_SSN_SUPPORT; 20612 wmi_service[wmi_service_filter_ipsec_natkeepalive] = 20613 WMI_SERVICE_FILTER_IPSEC_NATKEEPALIVE; 20614 wmi_service[wmi_service_wlan_hb] = WMI_SERVICE_WLAN_HB; 20615 wmi_service[wmi_service_lte_ant_share_support] = 20616 WMI_SERVICE_LTE_ANT_SHARE_SUPPORT; 20617 wmi_service[wmi_service_batch_scan] = WMI_SERVICE_BATCH_SCAN; 20618 wmi_service[wmi_service_qpower] = WMI_SERVICE_QPOWER; 20619 wmi_service[wmi_service_plmreq] = WMI_SERVICE_PLMREQ; 20620 wmi_service[wmi_service_thermal_mgmt] = WMI_SERVICE_THERMAL_MGMT; 20621 wmi_service[wmi_service_rmc] = WMI_SERVICE_RMC; 20622 wmi_service[wmi_service_mhf_offload] = WMI_SERVICE_MHF_OFFLOAD; 20623 wmi_service[wmi_service_coex_sar] = WMI_SERVICE_COEX_SAR; 20624 wmi_service[wmi_service_bcn_txrate_override] = 20625 WMI_SERVICE_BCN_TXRATE_OVERRIDE; 20626 wmi_service[wmi_service_nan] = WMI_SERVICE_NAN; 20627 wmi_service[wmi_service_l1ss_stat] = WMI_SERVICE_L1SS_STAT; 20628 wmi_service[wmi_service_estimate_linkspeed] = 20629 WMI_SERVICE_ESTIMATE_LINKSPEED; 20630 wmi_service[wmi_service_obss_scan] = WMI_SERVICE_OBSS_SCAN; 20631 wmi_service[wmi_service_tdls_offchan] = WMI_SERVICE_TDLS_OFFCHAN; 20632 wmi_service[wmi_service_tdls_uapsd_buffer_sta] = 20633 WMI_SERVICE_TDLS_UAPSD_BUFFER_STA; 20634 wmi_service[wmi_service_tdls_uapsd_sleep_sta] = 20635 WMI_SERVICE_TDLS_UAPSD_SLEEP_STA; 20636 wmi_service[wmi_service_ibss_pwrsave] = WMI_SERVICE_IBSS_PWRSAVE; 20637 wmi_service[wmi_service_lpass] = WMI_SERVICE_LPASS; 20638 wmi_service[wmi_service_extscan] = WMI_SERVICE_EXTSCAN; 20639 wmi_service[wmi_service_d0wow] = WMI_SERVICE_D0WOW; 20640 wmi_service[wmi_service_hsoffload] = WMI_SERVICE_HSOFFLOAD; 20641 wmi_service[wmi_service_roam_ho_offload] = WMI_SERVICE_ROAM_HO_OFFLOAD; 20642 wmi_service[wmi_service_rx_full_reorder] = WMI_SERVICE_RX_FULL_REORDER; 20643 wmi_service[wmi_service_dhcp_offload] = WMI_SERVICE_DHCP_OFFLOAD; 20644 wmi_service[wmi_service_sta_rx_ipa_offload_support] = 20645 WMI_SERVICE_STA_RX_IPA_OFFLOAD_SUPPORT; 20646 wmi_service[wmi_service_mdns_offload] = WMI_SERVICE_MDNS_OFFLOAD; 20647 wmi_service[wmi_service_sap_auth_offload] = 20648 WMI_SERVICE_SAP_AUTH_OFFLOAD; 20649 wmi_service[wmi_service_dual_band_simultaneous_support] = 20650 WMI_SERVICE_DUAL_BAND_SIMULTANEOUS_SUPPORT; 20651 wmi_service[wmi_service_ocb] = WMI_SERVICE_OCB; 20652 wmi_service[wmi_service_ap_arpns_offload] = 20653 WMI_SERVICE_AP_ARPNS_OFFLOAD; 20654 wmi_service[wmi_service_per_band_chainmask_support] = 20655 WMI_SERVICE_PER_BAND_CHAINMASK_SUPPORT; 20656 wmi_service[wmi_service_packet_filter_offload] = 20657 WMI_SERVICE_PACKET_FILTER_OFFLOAD; 20658 wmi_service[wmi_service_mgmt_tx_htt] = WMI_SERVICE_MGMT_TX_HTT; 20659 wmi_service[wmi_service_mgmt_tx_wmi] = WMI_SERVICE_MGMT_TX_WMI; 20660 wmi_service[wmi_service_ext_msg] = WMI_SERVICE_EXT_MSG; 20661 wmi_service[wmi_service_ext2_msg] = WMI_SERVICE_EXT2_MSG; 20662 wmi_service[wmi_service_mawc] = WMI_SERVICE_MAWC; 20663 wmi_service[wmi_service_multiple_vdev_restart] = 20664 WMI_SERVICE_MULTIPLE_VDEV_RESTART; 20665 wmi_service[wmi_service_smart_antenna_sw_support] = 20666 WMI_SERVICE_SMART_ANTENNA_SW_SUPPORT; 20667 wmi_service[wmi_service_smart_antenna_hw_support] = 20668 WMI_SERVICE_SMART_ANTENNA_HW_SUPPORT; 20669 20670 wmi_service[wmi_service_roam_offload] = WMI_SERVICE_UNAVAILABLE; 20671 wmi_service[wmi_service_ratectrl] = WMI_SERVICE_UNAVAILABLE; 20672 wmi_service[wmi_service_enhanced_proxy_sta] = WMI_SERVICE_UNAVAILABLE; 20673 wmi_service[wmi_service_tt] = WMI_SERVICE_THERM_THROT; 20674 wmi_service[wmi_service_atf] = WMI_SERVICE_ATF; 20675 wmi_service[wmi_service_peer_caching] = WMI_SERVICE_UNAVAILABLE; 20676 wmi_service[wmi_service_coex_gpio] = WMI_SERVICE_UNAVAILABLE; 20677 wmi_service[wmi_service_aux_spectral_intf] = WMI_SERVICE_UNAVAILABLE; 20678 wmi_service[wmi_service_aux_chan_load_intf] = WMI_SERVICE_UNAVAILABLE; 20679 wmi_service[wmi_service_bss_channel_info_64] = WMI_SERVICE_UNAVAILABLE; 20680 wmi_service[wmi_service_ext_res_cfg_support] = WMI_SERVICE_UNAVAILABLE; 20681 wmi_service[wmi_service_mesh] = WMI_SERVICE_UNAVAILABLE; 20682 wmi_service[wmi_service_restrt_chnl_support] = WMI_SERVICE_UNAVAILABLE; 20683 wmi_service[wmi_service_peer_stats] = WMI_SERVICE_UNAVAILABLE; 20684 wmi_service[wmi_service_mesh_11s] = WMI_SERVICE_UNAVAILABLE; 20685 wmi_service[wmi_service_periodic_chan_stat_support] = 20686 WMI_SERVICE_PERIODIC_CHAN_STAT_SUPPORT; 20687 wmi_service[wmi_service_tx_mode_push_only] = WMI_SERVICE_UNAVAILABLE; 20688 wmi_service[wmi_service_tx_mode_push_pull] = WMI_SERVICE_UNAVAILABLE; 20689 wmi_service[wmi_service_tx_mode_dynamic] = WMI_SERVICE_UNAVAILABLE; 20690 wmi_service[wmi_service_btcoex_duty_cycle] = WMI_SERVICE_UNAVAILABLE; 20691 wmi_service[wmi_service_4_wire_coex_support] = WMI_SERVICE_UNAVAILABLE; 20692 wmi_service[wmi_service_mesh] = WMI_SERVICE_ENTERPRISE_MESH; 20693 wmi_service[wmi_service_peer_assoc_conf] = WMI_SERVICE_PEER_ASSOC_CONF; 20694 wmi_service[wmi_service_egap] = WMI_SERVICE_EGAP; 20695 wmi_service[wmi_service_sta_pmf_offload] = WMI_SERVICE_STA_PMF_OFFLOAD; 20696 wmi_service[wmi_service_unified_wow_capability] = 20697 WMI_SERVICE_UNIFIED_WOW_CAPABILITY; 20698 wmi_service[wmi_service_enterprise_mesh] = WMI_SERVICE_ENTERPRISE_MESH; 20699 wmi_service[wmi_service_apf_offload] = WMI_SERVICE_BPF_OFFLOAD; 20700 wmi_service[wmi_service_sync_delete_cmds] = 20701 WMI_SERVICE_SYNC_DELETE_CMDS; 20702 wmi_service[wmi_service_ratectrl_limit_max_min_rates] = 20703 WMI_SERVICE_RATECTRL_LIMIT_MAX_MIN_RATES; 20704 wmi_service[wmi_service_nan_data] = WMI_SERVICE_NAN_DATA; 20705 wmi_service[wmi_service_nan_rtt] = WMI_SERVICE_NAN_RTT; 20706 wmi_service[wmi_service_11ax] = WMI_SERVICE_11AX; 20707 wmi_service[wmi_service_deprecated_replace] = 20708 WMI_SERVICE_DEPRECATED_REPLACE; 20709 wmi_service[wmi_service_tdls_conn_tracker_in_host_mode] = 20710 WMI_SERVICE_TDLS_CONN_TRACKER_IN_HOST_MODE; 20711 wmi_service[wmi_service_enhanced_mcast_filter] = 20712 WMI_SERVICE_ENHANCED_MCAST_FILTER; 20713 wmi_service[wmi_service_half_rate_quarter_rate_support] = 20714 WMI_SERVICE_HALF_RATE_QUARTER_RATE_SUPPORT; 20715 wmi_service[wmi_service_vdev_rx_filter] = WMI_SERVICE_VDEV_RX_FILTER; 20716 wmi_service[wmi_service_p2p_listen_offload_support] = 20717 WMI_SERVICE_P2P_LISTEN_OFFLOAD_SUPPORT; 20718 wmi_service[wmi_service_mark_first_wakeup_packet] = 20719 WMI_SERVICE_MARK_FIRST_WAKEUP_PACKET; 20720 wmi_service[wmi_service_multiple_mcast_filter_set] = 20721 WMI_SERVICE_MULTIPLE_MCAST_FILTER_SET; 20722 wmi_service[wmi_service_host_managed_rx_reorder] = 20723 WMI_SERVICE_HOST_MANAGED_RX_REORDER; 20724 wmi_service[wmi_service_flash_rdwr_support] = 20725 WMI_SERVICE_FLASH_RDWR_SUPPORT; 20726 wmi_service[wmi_service_wlan_stats_report] = 20727 WMI_SERVICE_WLAN_STATS_REPORT; 20728 wmi_service[wmi_service_tx_msdu_id_new_partition_support] = 20729 WMI_SERVICE_TX_MSDU_ID_NEW_PARTITION_SUPPORT; 20730 wmi_service[wmi_service_dfs_phyerr_offload] = 20731 WMI_SERVICE_DFS_PHYERR_OFFLOAD; 20732 wmi_service[wmi_service_rcpi_support] = WMI_SERVICE_RCPI_SUPPORT; 20733 wmi_service[wmi_service_fw_mem_dump_support] = 20734 WMI_SERVICE_FW_MEM_DUMP_SUPPORT; 20735 wmi_service[wmi_service_peer_stats_info] = WMI_SERVICE_PEER_STATS_INFO; 20736 wmi_service[wmi_service_regulatory_db] = WMI_SERVICE_REGULATORY_DB; 20737 wmi_service[wmi_service_11d_offload] = WMI_SERVICE_11D_OFFLOAD; 20738 wmi_service[wmi_service_hw_data_filtering] = 20739 WMI_SERVICE_HW_DATA_FILTERING; 20740 wmi_service[wmi_service_pkt_routing] = WMI_SERVICE_PKT_ROUTING; 20741 wmi_service[wmi_service_offchan_tx_wmi] = WMI_SERVICE_OFFCHAN_TX_WMI; 20742 wmi_service[wmi_service_chan_load_info] = WMI_SERVICE_CHAN_LOAD_INFO; 20743 wmi_service[wmi_service_extended_nss_support] = 20744 WMI_SERVICE_EXTENDED_NSS_SUPPORT; 20745 wmi_service[wmi_service_widebw_scan] = WMI_SERVICE_SCAN_PHYMODE_SUPPORT; 20746 wmi_service[wmi_service_bcn_offload_start_stop_support] = 20747 WMI_SERVICE_BCN_OFFLOAD_START_STOP_SUPPORT; 20748 wmi_service[wmi_service_offchan_data_tid_support] = 20749 WMI_SERVICE_OFFCHAN_DATA_TID_SUPPORT; 20750 wmi_service[wmi_service_support_dma] = 20751 WMI_SERVICE_SUPPORT_DIRECT_DMA; 20752 wmi_service[wmi_service_8ss_tx_bfee] = WMI_SERVICE_8SS_TX_BFEE; 20753 wmi_service[wmi_service_fils_support] = WMI_SERVICE_FILS_SUPPORT; 20754 wmi_service[wmi_service_mawc_support] = WMI_SERVICE_MAWC_SUPPORT; 20755 wmi_service[wmi_service_wow_wakeup_by_timer_pattern] = 20756 WMI_SERVICE_WOW_WAKEUP_BY_TIMER_PATTERN; 20757 wmi_service[wmi_service_11k_neighbour_report_support] = 20758 WMI_SERVICE_11K_NEIGHBOUR_REPORT_SUPPORT; 20759 wmi_service[wmi_service_ap_obss_detection_offload] = 20760 WMI_SERVICE_AP_OBSS_DETECTION_OFFLOAD; 20761 wmi_service[wmi_service_bss_color_offload] = 20762 WMI_SERVICE_BSS_COLOR_OFFLOAD; 20763 wmi_service[wmi_service_gmac_offload_support] = 20764 WMI_SERVICE_GMAC_OFFLOAD_SUPPORT; 20765 wmi_service[wmi_service_dual_beacon_on_single_mac_scc_support] = 20766 WMI_SERVICE_DUAL_BEACON_ON_SINGLE_MAC_SCC_SUPPORT; 20767 wmi_service[wmi_service_dual_beacon_on_single_mac_mcc_support] = 20768 WMI_SERVICE_DUAL_BEACON_ON_SINGLE_MAC_MCC_SUPPORT; 20769 wmi_service[wmi_service_twt_requestor] = WMI_SERVICE_STA_TWT; 20770 wmi_service[wmi_service_twt_responder] = WMI_SERVICE_AP_TWT; 20771 wmi_service[wmi_service_listen_interval_offload_support] = 20772 WMI_SERVICE_LISTEN_INTERVAL_OFFLOAD_SUPPORT; 20773 wmi_service[wmi_service_esp_support] = WMI_SERVICE_ESP_SUPPORT; 20774 wmi_service[wmi_service_obss_spatial_reuse] = 20775 WMI_SERVICE_OBSS_SPATIAL_REUSE; 20776 wmi_service[wmi_service_per_vdev_chain_support] = 20777 WMI_SERVICE_PER_VDEV_CHAINMASK_CONFIG_SUPPORT; 20778 wmi_service[wmi_service_new_htt_msg_format] = 20779 WMI_SERVICE_HTT_H2T_NO_HTC_HDR_LEN_IN_MSG_LEN; 20780 wmi_service[wmi_service_peer_unmap_cnf_support] = 20781 WMI_SERVICE_PEER_UNMAP_RESPONSE_SUPPORT; 20782 wmi_service[wmi_service_beacon_reception_stats] = 20783 WMI_SERVICE_BEACON_RECEPTION_STATS; 20784 wmi_service[wmi_service_vdev_latency_config] = 20785 WMI_SERVICE_VDEV_LATENCY_CONFIG; 20786 wmi_service[wmi_service_nan_dbs_support] = WMI_SERVICE_NAN_DBS_SUPPORT; 20787 wmi_service[wmi_service_ndi_dbs_support] = WMI_SERVICE_NDI_DBS_SUPPORT; 20788 wmi_service[wmi_service_nan_sap_support] = WMI_SERVICE_NAN_SAP_SUPPORT; 20789 wmi_service[wmi_service_ndi_sap_support] = WMI_SERVICE_NDI_SAP_SUPPORT; 20790 wmi_service[wmi_service_nan_disable_support] = 20791 WMI_SERVICE_NAN_DISABLE_SUPPORT; 20792 wmi_service[wmi_service_sta_plus_sta_support] = 20793 WMI_SERVICE_STA_PLUS_STA_SUPPORT; 20794 wmi_service[wmi_service_hw_db2dbm_support] = 20795 WMI_SERVICE_HW_DB2DBM_CONVERSION_SUPPORT; 20796 wmi_service[wmi_service_wlm_stats_support] = 20797 WMI_SERVICE_WLM_STATS_REQUEST; 20798 wmi_service[wmi_service_infra_mbssid] = WMI_SERVICE_INFRA_MBSSID; 20799 wmi_service[wmi_service_ema_ap_support] = WMI_SERVICE_EMA_AP_SUPPORT; 20800 wmi_service[wmi_service_ul_ru26_allowed] = WMI_SERVICE_UL_RU26_ALLOWED; 20801 wmi_service[wmi_service_cfr_capture_support] = 20802 WMI_SERVICE_CFR_CAPTURE_SUPPORT; 20803 wmi_service[wmi_service_bcast_twt_support] = 20804 WMI_SERVICE_BROADCAST_TWT; 20805 wmi_service[wmi_service_wpa3_ft_sae_support] = 20806 WMI_SERVICE_WPA3_FT_SAE_SUPPORT; 20807 wmi_service[wmi_service_wpa3_ft_suite_b_support] = 20808 WMI_SERVICE_WPA3_FT_SUITE_B_SUPPORT; 20809 wmi_service[wmi_service_ft_fils] = 20810 WMI_SERVICE_WPA3_FT_FILS; 20811 wmi_service[wmi_service_adaptive_11r_support] = 20812 WMI_SERVICE_ADAPTIVE_11R_ROAM; 20813 wmi_service[wmi_service_tx_compl_tsf64] = 20814 WMI_SERVICE_TX_COMPL_TSF64; 20815 wmi_service[wmi_service_data_stall_recovery_support] = 20816 WMI_SERVICE_DSM_ROAM_FILTER; 20817 wmi_service[wmi_service_vdev_delete_all_peer] = 20818 WMI_SERVICE_DELETE_ALL_PEER_SUPPORT; 20819 wmi_service[wmi_service_three_way_coex_config_legacy] = 20820 WMI_SERVICE_THREE_WAY_COEX_CONFIG_LEGACY; 20821 wmi_service[wmi_service_rx_fse_support] = 20822 WMI_SERVICE_RX_FSE_SUPPORT; 20823 wmi_service[wmi_service_sae_roam_support] = 20824 WMI_SERVICE_WPA3_SAE_ROAM_SUPPORT; 20825 wmi_service[wmi_service_owe_roam_support] = 20826 WMI_SERVICE_WPA3_OWE_ROAM_SUPPORT; 20827 wmi_service[wmi_service_6ghz_support] = 20828 WMI_SERVICE_6GHZ_SUPPORT; 20829 wmi_service[wmi_service_bw_165mhz_support] = 20830 WMI_SERVICE_BW_165MHZ_SUPPORT; 20831 wmi_service[wmi_service_bw_restricted_80p80_support] = 20832 WMI_SERVICE_BW_RESTRICTED_80P80_SUPPORT; 20833 wmi_service[wmi_service_packet_capture_support] = 20834 WMI_SERVICE_PACKET_CAPTURE_SUPPORT; 20835 wmi_service[wmi_service_nan_vdev] = WMI_SERVICE_NAN_VDEV_SUPPORT; 20836 wmi_service[wmi_service_peer_delete_no_peer_flush_tids_cmd] = 20837 WMI_SERVICE_PEER_DELETE_NO_PEER_FLUSH_TIDS_CMD; 20838 wmi_service[wmi_service_multiple_vdev_restart_ext] = 20839 WMI_SERVICE_UNAVAILABLE; 20840 wmi_service[wmi_service_time_sync_ftm] = 20841 WMI_SERVICE_AUDIO_SYNC_SUPPORT; 20842 wmi_service[wmi_service_nss_ratio_to_host_support] = 20843 WMI_SERVICE_NSS_RATIO_TO_HOST_SUPPORT; 20844 wmi_service[wmi_roam_scan_chan_list_to_host_support] = 20845 WMI_SERVICE_ROAM_SCAN_CHANNEL_LIST_TO_HOST_SUPPORT; 20846 wmi_service[wmi_beacon_protection_support] = 20847 WMI_SERVICE_BEACON_PROTECTION_SUPPORT; 20848 wmi_service[wmi_service_sta_nan_ndi_four_port] = 20849 WMI_SERVICE_NDI_NDI_STA_SUPPORT; 20850 wmi_service[wmi_service_host_scan_stop_vdev_all] = 20851 WMI_SERVICE_HOST_SCAN_STOP_VDEV_ALL_SUPPORT; 20852 wmi_service[wmi_support_extend_address] = 20853 WMI_SERVICE_SUPPORT_EXTEND_ADDRESS; 20854 wmi_service[wmi_service_srg_srp_spatial_reuse_support] = 20855 WMI_SERVICE_SRG_SRP_SPATIAL_REUSE_SUPPORT; 20856 wmi_service[wmi_service_suiteb_roam_support] = 20857 WMI_SERVICE_WPA3_SUITEB_ROAM_SUPPORT; 20858 wmi_service[wmi_service_no_interband_mcc_support] = 20859 WMI_SERVICE_NO_INTERBAND_MCC_SUPPORT; 20860 wmi_service[wmi_service_dual_sta_roam_support] = 20861 WMI_SERVICE_DUAL_STA_ROAM_SUPPORT; 20862 wmi_service[wmi_service_peer_create_conf] = 20863 WMI_SERVICE_PEER_CREATE_CONF; 20864 wmi_service[wmi_service_configure_roam_trigger_param_support] = 20865 WMI_SERVICE_CONFIGURE_ROAM_TRIGGER_PARAM_SUPPORT; 20866 wmi_service[wmi_service_5dot9_ghz_support] = 20867 WMI_SERVICE_5_DOT_9GHZ_SUPPORT; 20868 wmi_service[wmi_service_cfr_ta_ra_as_fp_support] = 20869 WMI_SERVICE_CFR_TA_RA_AS_FP_SUPPORT; 20870 wmi_service[wmi_service_cfr_capture_count_support] = 20871 WMI_SERVICE_CFR_CAPTURE_COUNT_SUPPORT; 20872 wmi_service[wmi_service_ocv_support] = 20873 WMI_SERVICE_OCV_SUPPORT; 20874 wmi_service[wmi_service_ll_stats_per_chan_rx_tx_time] = 20875 WMI_SERVICE_LL_STATS_PER_CHAN_RX_TX_TIME_SUPPORT; 20876 wmi_service[wmi_service_thermal_multi_client_support] = 20877 WMI_SERVICE_THERMAL_MULTI_CLIENT_SUPPORT; 20878 wmi_service[wmi_service_mbss_param_in_vdev_start_support] = 20879 WMI_SERVICE_MBSS_PARAM_IN_VDEV_START_SUPPORT; 20880 wmi_service[wmi_service_fse_cmem_alloc_support] = 20881 WMI_SERVICE_FSE_CMEM_ALLOC_SUPPORT; 20882 wmi_service[wmi_service_scan_conf_per_ch_support] = 20883 WMI_SERVICE_SCAN_CONFIG_PER_CHANNEL; 20884 wmi_service[wmi_service_csa_beacon_template] = 20885 WMI_SERVICE_CSA_BEACON_TEMPLATE; 20886 #if defined(WIFI_POS_CONVERGED) && defined(WLAN_FEATURE_RTT_11AZ_SUPPORT) 20887 wmi_service[wmi_service_rtt_11az_ntb_support] = 20888 WMI_SERVICE_RTT_11AZ_NTB_SUPPORT; 20889 wmi_service[wmi_service_rtt_11az_tb_support] = 20890 WMI_SERVICE_RTT_11AZ_TB_SUPPORT; 20891 wmi_service[wmi_service_rtt_11az_mac_sec_support] = 20892 WMI_SERVICE_RTT_11AZ_MAC_SEC_SUPPORT; 20893 wmi_service[wmi_service_rtt_11az_mac_phy_sec_support] = 20894 WMI_SERVICE_RTT_11AZ_MAC_PHY_SEC_SUPPORT; 20895 #endif 20896 #ifdef WLAN_FEATURE_IGMP_OFFLOAD 20897 wmi_service[wmi_service_igmp_offload_support] = 20898 WMI_SERVICE_IGMP_OFFLOAD_SUPPORT; 20899 #endif 20900 20901 #ifdef FEATURE_WLAN_TDLS 20902 #ifdef WLAN_FEATURE_11AX 20903 wmi_service[wmi_service_tdls_ax_support] = 20904 WMI_SERVICE_11AX_TDLS_SUPPORT; 20905 wmi_service[wmi_service_tdls_6g_support] = 20906 WMI_SERVICE_TDLS_6GHZ_SUPPORT; 20907 #endif 20908 wmi_service[wmi_service_tdls_wideband_support] = 20909 WMI_SERVICE_TDLS_WIDEBAND_SUPPORT; 20910 #endif 20911 20912 #ifdef WLAN_SUPPORT_TWT 20913 wmi_service[wmi_service_twt_bcast_req_support] = 20914 WMI_SERVICE_BROADCAST_TWT_REQUESTER; 20915 wmi_service[wmi_service_twt_bcast_resp_support] = 20916 WMI_SERVICE_BROADCAST_TWT_RESPONDER; 20917 wmi_service[wmi_service_twt_nudge] = 20918 WMI_SERVICE_TWT_NUDGE; 20919 wmi_service[wmi_service_all_twt] = 20920 WMI_SERVICE_TWT_ALL_DIALOG_ID; 20921 wmi_service[wmi_service_twt_statistics] = 20922 WMI_SERVICE_TWT_STATS; 20923 #endif 20924 wmi_service[wmi_service_spectral_scan_disabled] = 20925 WMI_SERVICE_SPECTRAL_SCAN_DISABLED; 20926 wmi_service[wmi_service_sae_eapol_offload_support] = 20927 WMI_SERVICE_SAE_EAPOL_OFFLOAD_SUPPORT; 20928 wmi_populate_service_get_sta_in_ll_stats_req(wmi_service); 20929 20930 wmi_service[wmi_service_wapi_concurrency_supported] = 20931 WMI_SERVICE_WAPI_CONCURRENCY_SUPPORTED; 20932 wmi_service[wmi_service_sap_connected_d3_wow] = 20933 WMI_SERVICE_SAP_CONNECTED_D3WOW; 20934 wmi_service[wmi_service_go_connected_d3_wow] = 20935 WMI_SERVICE_SAP_CONNECTED_D3WOW; 20936 wmi_service[wmi_service_ext_tpc_reg_support] = 20937 WMI_SERVICE_EXT_TPC_REG_SUPPORT; 20938 wmi_service[wmi_service_ndi_txbf_support] = 20939 WMI_SERVICE_NDI_TXBF_SUPPORT; 20940 wmi_service[wmi_service_reg_cc_ext_event_support] = 20941 WMI_SERVICE_REG_CC_EXT_EVENT_SUPPORT; 20942 wmi_service[wmi_service_bang_radar_320_support] = 20943 WMI_SERVICE_BANG_RADAR_320_SUPPORT; 20944 #if defined(CONFIG_BAND_6GHZ) 20945 wmi_service[wmi_service_lower_6g_edge_ch_supp] = 20946 WMI_SERVICE_ENABLE_LOWER_6G_EDGE_CH_SUPP; 20947 wmi_service[wmi_service_disable_upper_6g_edge_ch_supp] = 20948 WMI_SERVICE_DISABLE_UPPER_6G_EDGE_CH_SUPP; 20949 #endif 20950 wmi_service[wmi_service_dcs_awgn_int_support] = 20951 WMI_SERVICE_DCS_AWGN_INT_SUPPORT; 20952 wmi_populate_service_11be(wmi_service); 20953 20954 #ifdef WLAN_FEATURE_BIG_DATA_STATS 20955 wmi_service[wmi_service_big_data_support] = 20956 WMI_SERVICE_BIG_DATA_SUPPORT; 20957 #endif 20958 wmi_service[wmi_service_ampdu_tx_buf_size_256_support] = 20959 WMI_SERVICE_AMPDU_TX_BUF_SIZE_256_SUPPORT; 20960 wmi_service[wmi_service_halphy_cal_enable_disable_support] = 20961 WMI_SERVICE_HALPHY_CAL_ENABLE_DISABLE_SUPPORT; 20962 wmi_service[wmi_service_halphy_cal_status] = 20963 WMI_SERVICE_HALPHY_CAL_STATUS; 20964 wmi_service[wmi_service_rtt_ap_initiator_staggered_mode_supported] = 20965 WMI_SERVICE_RTT_AP_INITIATOR_STAGGERED_MODE_SUPPORTED; 20966 wmi_service[wmi_service_rtt_ap_initiator_bursted_mode_supported] = 20967 WMI_SERVICE_RTT_AP_INITIATOR_BURSTED_MODE_SUPPORTED; 20968 wmi_service[wmi_service_ema_multiple_group_supported] = 20969 WMI_SERVICE_EMA_MULTIPLE_GROUP_SUPPORT; 20970 wmi_service[wmi_service_large_beacon_supported] = 20971 WMI_SERVICE_LARGE_BEACON_SUPPORT; 20972 wmi_service[wmi_service_aoa_for_rcc_supported] = 20973 WMI_SERVICE_AOA_FOR_RCC_SUPPORTED; 20974 #ifdef WLAN_FEATURE_P2P_P2P_STA 20975 wmi_service[wmi_service_p2p_p2p_cc_support] = 20976 WMI_SERVICE_P2P_P2P_CONCURRENCY_SUPPORT; 20977 #endif 20978 #ifdef THERMAL_STATS_SUPPORT 20979 wmi_service[wmi_service_thermal_stats_temp_range_supported] = 20980 WMI_SERVICE_THERMAL_THROT_STATS_TEMP_RANGE_SUPPORT; 20981 #endif 20982 wmi_service[wmi_service_hw_mode_policy_offload_support] = 20983 WMI_SERVICE_HW_MODE_POLICY_OFFLOAD_SUPPORT; 20984 wmi_service[wmi_service_mgmt_rx_reo_supported] = 20985 WMI_SERVICE_MGMT_RX_REO_SUPPORTED; 20986 wmi_service[wmi_service_phy_dma_byte_swap_support] = 20987 WMI_SERVICE_UNAVAILABLE; 20988 wmi_service[wmi_service_spectral_session_info_support] = 20989 WMI_SERVICE_SPECTRAL_SESSION_INFO_SUPPORT; 20990 wmi_service[wmi_service_umac_hang_recovery_support] = 20991 WMI_SERVICE_UMAC_HANG_RECOVERY_SUPPORT; 20992 wmi_service[wmi_service_mu_snif] = WMI_SERVICE_MU_SNIF; 20993 #ifdef WLAN_FEATURE_DYNAMIC_MAC_ADDR_UPDATE 20994 wmi_service[wmi_service_dynamic_update_vdev_macaddr_support] = 20995 WMI_SERVICE_DYNAMIC_VDEV_MAC_ADDR_UPDATE_SUPPORT; 20996 #endif 20997 wmi_service[wmi_service_probe_all_bw_support] = 20998 WMI_SERVICE_PROBE_ALL_BW_SUPPORT; 20999 wmi_service[wmi_service_pno_scan_conf_per_ch_support] = 21000 WMI_SERVICE_PNO_SCAN_CONFIG_PER_CHANNEL; 21001 #ifdef QCA_UNDECODED_METADATA_SUPPORT 21002 wmi_service[wmi_service_fp_phy_err_filter_support] = 21003 WMI_SERVICE_FP_PHY_ERR_FILTER_SUPPORT; 21004 #endif 21005 populate_tlv_service_mlo(wmi_service); 21006 wmi_service[wmi_service_pdev_rate_config_support] = 21007 WMI_SERVICE_PDEV_RATE_CONFIG_SUPPORT; 21008 wmi_service[wmi_service_multi_peer_group_cmd_support] = 21009 WMI_SERVICE_MULTIPLE_PEER_GROUP_CMD_SUPPORT; 21010 #ifdef WLAN_FEATURE_11BE 21011 wmi_service[wmi_service_radar_found_chan_freq_eq_center_freq] = 21012 WMI_IS_RADAR_FOUND_CHAN_FREQ_IS_CENTER_FREQ; 21013 #endif 21014 #ifdef WLAN_PDEV_VDEV_SEND_MULTI_PARAM 21015 wmi_service[wmi_service_combined_set_param_support] = 21016 WMI_SERVICE_COMBINED_SET_PARAM_SUPPORT; 21017 #endif 21018 wmi_service[wmi_service_pn_replay_check_support] = 21019 WMI_SERVICE_PN_REPLAY_CHECK_SUPPORT; 21020 #ifdef QCA_RSSI_DB2DBM 21021 wmi_service[wmi_service_pdev_rssi_dbm_conv_event_support] = 21022 WMI_SERVICE_PDEV_RSSI_DBM_CONV_EVENT_SUPPORT; 21023 #endif 21024 wmi_service[wmi_service_pktlog_decode_info_support] = 21025 WMI_SERVICE_PKTLOG_DECODE_INFO_SUPPORT; 21026 #ifdef WLAN_FEATURE_ROAM_OFFLOAD 21027 wmi_service[wmi_service_roam_stats_per_candidate_frame_info] = 21028 WMI_SERVICE_ROAM_STAT_PER_CANDIDATE_FRAME_INFO_SUPPORT; 21029 #endif 21030 #ifdef MULTI_CLIENT_LL_SUPPORT 21031 wmi_service[wmi_service_configure_multi_client_ll_support] = 21032 WMI_SERVICE_MULTI_CLIENT_LL_SUPPORT; 21033 #endif 21034 #ifdef WLAN_VENDOR_HANDOFF_CONTROL 21035 wmi_service[wmi_service_configure_vendor_handoff_control_support] = 21036 WMI_SERVICE_FW_INI_PARSE_SUPPORT; 21037 #endif 21038 wmi_service[wmi_service_linkspeed_roam_trigger_support] = 21039 WMI_SERVICE_LINKSPEED_ROAM_TRIGGER_SUPPORT; 21040 #ifdef FEATURE_SET 21041 wmi_service[wmi_service_feature_set_event_support] = 21042 WMI_SERVICE_FEATURE_SET_EVENT_SUPPORT; 21043 #endif 21044 } 21045 21046 /** 21047 * wmi_ocb_ut_attach() - Attach OCB test framework 21048 * @wmi_handle: wmi handle 21049 * 21050 * Return: None 21051 */ 21052 #ifdef WLAN_OCB_UT 21053 void wmi_ocb_ut_attach(struct wmi_unified *wmi_handle); 21054 #else 21055 static inline void wmi_ocb_ut_attach(struct wmi_unified *wmi_handle) 21056 { 21057 return; 21058 } 21059 #endif 21060 21061 /** 21062 * wmi_tlv_attach() - Attach TLV APIs 21063 * 21064 * Return: None 21065 */ 21066 void wmi_tlv_attach(wmi_unified_t wmi_handle) 21067 { 21068 wmi_handle->ops = &tlv_ops; 21069 wmi_ocb_ut_attach(wmi_handle); 21070 wmi_handle->soc->svc_ids = &multi_svc_ids[0]; 21071 #ifdef WMI_INTERFACE_EVENT_LOGGING 21072 /* Skip saving WMI_CMD_HDR and TLV HDR */ 21073 wmi_handle->soc->buf_offset_command = 8; 21074 /* WMI_CMD_HDR is already stripped, skip saving TLV HDR */ 21075 wmi_handle->soc->buf_offset_event = 4; 21076 #endif 21077 populate_tlv_events_id(wmi_handle->wmi_events); 21078 populate_tlv_service(wmi_handle->services); 21079 wmi_wds_attach_tlv(wmi_handle); 21080 wmi_twt_attach_tlv(wmi_handle); 21081 wmi_extscan_attach_tlv(wmi_handle); 21082 wmi_smart_ant_attach_tlv(wmi_handle); 21083 wmi_dbr_attach_tlv(wmi_handle); 21084 wmi_atf_attach_tlv(wmi_handle); 21085 wmi_ap_attach_tlv(wmi_handle); 21086 wmi_bcn_attach_tlv(wmi_handle); 21087 wmi_ocb_attach_tlv(wmi_handle); 21088 wmi_nan_attach_tlv(wmi_handle); 21089 wmi_p2p_attach_tlv(wmi_handle); 21090 wmi_interop_issues_ap_attach_tlv(wmi_handle); 21091 wmi_dcs_attach_tlv(wmi_handle); 21092 wmi_roam_attach_tlv(wmi_handle); 21093 wmi_concurrency_attach_tlv(wmi_handle); 21094 wmi_pmo_attach_tlv(wmi_handle); 21095 wmi_sta_attach_tlv(wmi_handle); 21096 wmi_11ax_bss_color_attach_tlv(wmi_handle); 21097 wmi_fwol_attach_tlv(wmi_handle); 21098 wmi_vdev_attach_tlv(wmi_handle); 21099 wmi_cfr_attach_tlv(wmi_handle); 21100 wmi_cp_stats_attach_tlv(wmi_handle); 21101 wmi_gpio_attach_tlv(wmi_handle); 21102 wmi_11be_attach_tlv(wmi_handle); 21103 wmi_coap_attach_tlv(wmi_handle); 21104 } 21105 qdf_export_symbol(wmi_tlv_attach); 21106 21107 /** 21108 * wmi_tlv_init() - Initialize WMI TLV module by registering TLV attach routine 21109 * 21110 * Return: None 21111 */ 21112 void wmi_tlv_init(void) 21113 { 21114 wmi_unified_register_module(WMI_TLV_TARGET, &wmi_tlv_attach); 21115 } 21116