File Index
Files and directories
Sign in
FILE

wmi.c

File preview with syntax highlighting.

linux-6.19.14/drivers/net/wireless/ath/ath12k/wmi.c C
    1// SPDX-License-Identifier: BSD-3-Clause-Clear
    2/*
    3 * Copyright (c) 2018-2021 The Linux Foundation. All rights reserved.
    4 * Copyright (c) Qualcomm Technologies, Inc. and/or its subsidiaries.
    5 */
    6#include <linux/skbuff.h>
    7#include <linux/ctype.h>
    8#include <net/mac80211.h>
    9#include <net/cfg80211.h>
   10#include <linux/completion.h>
   11#include <linux/if_ether.h>
   12#include <linux/types.h>
   13#include <linux/pci.h>
   14#include <linux/uuid.h>
   15#include <linux/time.h>
   16#include <linux/of.h>
   17#include <linux/cleanup.h>
   18#include "core.h"
   19#include "debugfs.h"
   20#include "debug.h"
   21#include "mac.h"
   22#include "hw.h"
   23#include "peer.h"
   24#include "p2p.h"
   25#include "testmode.h"
   26
   27struct ath12k_wmi_svc_ready_parse {
   28	bool wmi_svc_bitmap_done;
   29};
   30
   31struct wmi_tlv_fw_stats_parse {
   32	const struct wmi_stats_event *ev;
   33	struct ath12k_fw_stats *stats;
   34	const struct wmi_per_chain_rssi_stat_params *rssi;
   35	int rssi_num;
   36	bool chain_rssi_done;
   37};
   38
   39struct ath12k_wmi_dma_ring_caps_parse {
   40	struct ath12k_wmi_dma_ring_caps_params *dma_ring_caps;
   41	u32 n_dma_ring_caps;
   42};
   43
   44struct ath12k_wmi_service_ext_arg {
   45	u32 default_conc_scan_config_bits;
   46	u32 default_fw_config_bits;
   47	struct ath12k_wmi_ppe_threshold_arg ppet;
   48	u32 he_cap_info;
   49	u32 mpdu_density;
   50	u32 max_bssid_rx_filters;
   51	u32 num_hw_modes;
   52	u32 num_phy;
   53};
   54
   55struct ath12k_wmi_svc_rdy_ext_parse {
   56	struct ath12k_wmi_service_ext_arg arg;
   57	const struct ath12k_wmi_soc_mac_phy_hw_mode_caps_params *hw_caps;
   58	const struct ath12k_wmi_hw_mode_cap_params *hw_mode_caps;
   59	u32 n_hw_mode_caps;
   60	u32 tot_phy_id;
   61	struct ath12k_wmi_hw_mode_cap_params pref_hw_mode_caps;
   62	struct ath12k_wmi_mac_phy_caps_params *mac_phy_caps;
   63	u32 n_mac_phy_caps;
   64	const struct ath12k_wmi_soc_hal_reg_caps_params *soc_hal_reg_caps;
   65	const struct ath12k_wmi_hal_reg_caps_ext_params *ext_hal_reg_caps;
   66	u32 n_ext_hal_reg_caps;
   67	struct ath12k_wmi_dma_ring_caps_parse dma_caps_parse;
   68	bool hw_mode_done;
   69	bool mac_phy_done;
   70	bool ext_hal_reg_done;
   71	bool mac_phy_chainmask_combo_done;
   72	bool mac_phy_chainmask_cap_done;
   73	bool oem_dma_ring_cap_done;
   74	bool dma_ring_cap_done;
   75};
   76
   77struct ath12k_wmi_svc_rdy_ext2_arg {
   78	u32 reg_db_version;
   79	u32 hw_min_max_tx_power_2ghz;
   80	u32 hw_min_max_tx_power_5ghz;
   81	u32 chwidth_num_peer_caps;
   82	u32 preamble_puncture_bw;
   83	u32 max_user_per_ppdu_ofdma;
   84	u32 max_user_per_ppdu_mumimo;
   85	u32 target_cap_flags;
   86	u32 eht_cap_mac_info[WMI_MAX_EHTCAP_MAC_SIZE];
   87	u32 max_num_linkview_peers;
   88	u32 max_num_msduq_supported_per_tid;
   89	u32 default_num_msduq_supported_per_tid;
   90};
   91
   92struct ath12k_wmi_svc_rdy_ext2_parse {
   93	struct ath12k_wmi_svc_rdy_ext2_arg arg;
   94	struct ath12k_wmi_dma_ring_caps_parse dma_caps_parse;
   95	bool dma_ring_cap_done;
   96	bool spectral_bin_scaling_done;
   97	bool mac_phy_caps_ext_done;
   98	bool hal_reg_caps_ext2_done;
   99	bool scan_radio_caps_ext2_done;
  100	bool twt_caps_done;
  101	bool htt_msdu_idx_to_qtype_map_done;
  102	bool dbs_or_sbs_cap_ext_done;
  103};
  104
  105struct ath12k_wmi_rdy_parse {
  106	u32 num_extra_mac_addr;
  107};
  108
  109struct ath12k_wmi_dma_buf_release_arg {
  110	struct ath12k_wmi_dma_buf_release_fixed_params fixed;
  111	const struct ath12k_wmi_dma_buf_release_entry_params *buf_entry;
  112	const struct ath12k_wmi_dma_buf_release_meta_data_params *meta_data;
  113	u32 num_buf_entry;
  114	u32 num_meta;
  115	bool buf_entry_done;
  116	bool meta_data_done;
  117};
  118
  119struct ath12k_wmi_tlv_policy {
  120	size_t min_len;
  121};
  122
  123struct wmi_tlv_mgmt_rx_parse {
  124	const struct ath12k_wmi_mgmt_rx_params *fixed;
  125	const u8 *frame_buf;
  126	bool frame_buf_done;
  127};
  128
  129static const struct ath12k_wmi_tlv_policy ath12k_wmi_tlv_policies[] = {
  130	[WMI_TAG_ARRAY_BYTE] = { .min_len = 0 },
  131	[WMI_TAG_ARRAY_UINT32] = { .min_len = 0 },
  132	[WMI_TAG_SERVICE_READY_EVENT] = {
  133		.min_len = sizeof(struct wmi_service_ready_event) },
  134	[WMI_TAG_SERVICE_READY_EXT_EVENT] = {
  135		.min_len = sizeof(struct wmi_service_ready_ext_event) },
  136	[WMI_TAG_SOC_MAC_PHY_HW_MODE_CAPS] = {
  137		.min_len = sizeof(struct ath12k_wmi_soc_mac_phy_hw_mode_caps_params) },
  138	[WMI_TAG_SOC_HAL_REG_CAPABILITIES] = {
  139		.min_len = sizeof(struct ath12k_wmi_soc_hal_reg_caps_params) },
  140	[WMI_TAG_VDEV_START_RESPONSE_EVENT] = {
  141		.min_len = sizeof(struct wmi_vdev_start_resp_event) },
  142	[WMI_TAG_PEER_DELETE_RESP_EVENT] = {
  143		.min_len = sizeof(struct wmi_peer_delete_resp_event) },
  144	[WMI_TAG_OFFLOAD_BCN_TX_STATUS_EVENT] = {
  145		.min_len = sizeof(struct wmi_bcn_tx_status_event) },
  146	[WMI_TAG_VDEV_STOPPED_EVENT] = {
  147		.min_len = sizeof(struct wmi_vdev_stopped_event) },
  148	[WMI_TAG_REG_CHAN_LIST_CC_EXT_EVENT] = {
  149		.min_len = sizeof(struct wmi_reg_chan_list_cc_ext_event) },
  150	[WMI_TAG_MGMT_RX_HDR] = {
  151		.min_len = sizeof(struct ath12k_wmi_mgmt_rx_params) },
  152	[WMI_TAG_MGMT_TX_COMPL_EVENT] = {
  153		.min_len = sizeof(struct wmi_mgmt_tx_compl_event) },
  154	[WMI_TAG_SCAN_EVENT] = {
  155		.min_len = sizeof(struct wmi_scan_event) },
  156	[WMI_TAG_PEER_STA_KICKOUT_EVENT] = {
  157		.min_len = sizeof(struct wmi_peer_sta_kickout_event) },
  158	[WMI_TAG_ROAM_EVENT] = {
  159		.min_len = sizeof(struct wmi_roam_event) },
  160	[WMI_TAG_CHAN_INFO_EVENT] = {
  161		.min_len = sizeof(struct wmi_chan_info_event) },
  162	[WMI_TAG_PDEV_BSS_CHAN_INFO_EVENT] = {
  163		.min_len = sizeof(struct wmi_pdev_bss_chan_info_event) },
  164	[WMI_TAG_VDEV_INSTALL_KEY_COMPLETE_EVENT] = {
  165		.min_len = sizeof(struct wmi_vdev_install_key_compl_event) },
  166	[WMI_TAG_READY_EVENT] = {
  167		.min_len = sizeof(struct ath12k_wmi_ready_event_min_params) },
  168	[WMI_TAG_SERVICE_AVAILABLE_EVENT] = {
  169		.min_len = sizeof(struct wmi_service_available_event) },
  170	[WMI_TAG_PEER_ASSOC_CONF_EVENT] = {
  171		.min_len = sizeof(struct wmi_peer_assoc_conf_event) },
  172	[WMI_TAG_RFKILL_EVENT] = {
  173		.min_len = sizeof(struct wmi_rfkill_state_change_event) },
  174	[WMI_TAG_PDEV_CTL_FAILSAFE_CHECK_EVENT] = {
  175		.min_len = sizeof(struct wmi_pdev_ctl_failsafe_chk_event) },
  176	[WMI_TAG_HOST_SWFDA_EVENT] = {
  177		.min_len = sizeof(struct wmi_fils_discovery_event) },
  178	[WMI_TAG_OFFLOAD_PRB_RSP_TX_STATUS_EVENT] = {
  179		.min_len = sizeof(struct wmi_probe_resp_tx_status_event) },
  180	[WMI_TAG_VDEV_DELETE_RESP_EVENT] = {
  181		.min_len = sizeof(struct wmi_vdev_delete_resp_event) },
  182	[WMI_TAG_TWT_ENABLE_COMPLETE_EVENT] = {
  183		.min_len = sizeof(struct wmi_twt_enable_event) },
  184	[WMI_TAG_TWT_DISABLE_COMPLETE_EVENT] = {
  185		.min_len = sizeof(struct wmi_twt_disable_event) },
  186	[WMI_TAG_P2P_NOA_INFO] = {
  187		.min_len = sizeof(struct ath12k_wmi_p2p_noa_info) },
  188	[WMI_TAG_P2P_NOA_EVENT] = {
  189		.min_len = sizeof(struct wmi_p2p_noa_event) },
  190	[WMI_TAG_11D_NEW_COUNTRY_EVENT] = {
  191		.min_len = sizeof(struct wmi_11d_new_cc_event) },
  192	[WMI_TAG_PER_CHAIN_RSSI_STATS] = {
  193		.min_len = sizeof(struct wmi_per_chain_rssi_stat_params) },
  194	[WMI_TAG_OBSS_COLOR_COLLISION_EVT] = {
  195		.min_len = sizeof(struct wmi_obss_color_collision_event) },
  196};
  197
  198__le32 ath12k_wmi_tlv_hdr(u32 cmd, u32 len)
  199{
  200	return le32_encode_bits(cmd, WMI_TLV_TAG) |
  201		le32_encode_bits(len, WMI_TLV_LEN);
  202}
  203
  204static __le32 ath12k_wmi_tlv_cmd_hdr(u32 cmd, u32 len)
  205{
  206	return ath12k_wmi_tlv_hdr(cmd, len - TLV_HDR_SIZE);
  207}
  208
  209void ath12k_wmi_init_qcn9274(struct ath12k_base *ab,
  210			     struct ath12k_wmi_resource_config_arg *config)
  211{
  212	config->num_vdevs = ab->num_radios * TARGET_NUM_VDEVS(ab);
  213	config->num_peers = ab->num_radios *
  214		ath12k_core_get_max_peers_per_radio(ab);
  215	config->num_offload_peers = TARGET_NUM_OFFLD_PEERS;
  216	config->num_offload_reorder_buffs = TARGET_NUM_OFFLD_REORDER_BUFFS;
  217	config->num_peer_keys = TARGET_NUM_PEER_KEYS;
  218	config->ast_skid_limit = TARGET_AST_SKID_LIMIT;
  219	config->tx_chain_mask = (1 << ab->target_caps.num_rf_chains) - 1;
  220	config->rx_chain_mask = (1 << ab->target_caps.num_rf_chains) - 1;
  221	config->rx_timeout_pri[0] = TARGET_RX_TIMEOUT_LO_PRI;
  222	config->rx_timeout_pri[1] = TARGET_RX_TIMEOUT_LO_PRI;
  223	config->rx_timeout_pri[2] = TARGET_RX_TIMEOUT_LO_PRI;
  224	config->rx_timeout_pri[3] = TARGET_RX_TIMEOUT_HI_PRI;
  225
  226	if (test_bit(ATH12K_FLAG_RAW_MODE, &ab->dev_flags))
  227		config->rx_decap_mode = TARGET_DECAP_MODE_RAW;
  228	else
  229		config->rx_decap_mode = TARGET_DECAP_MODE_NATIVE_WIFI;
  230
  231	config->scan_max_pending_req = TARGET_SCAN_MAX_PENDING_REQS;
  232	config->bmiss_offload_max_vdev = TARGET_BMISS_OFFLOAD_MAX_VDEV;
  233	config->roam_offload_max_vdev = TARGET_ROAM_OFFLOAD_MAX_VDEV;
  234	config->roam_offload_max_ap_profiles = TARGET_ROAM_OFFLOAD_MAX_AP_PROFILES;
  235	config->num_mcast_groups = TARGET_NUM_MCAST_GROUPS;
  236	config->num_mcast_table_elems = TARGET_NUM_MCAST_TABLE_ELEMS;
  237	config->mcast2ucast_mode = TARGET_MCAST2UCAST_MODE;
  238	config->tx_dbg_log_size = TARGET_TX_DBG_LOG_SIZE;
  239	config->num_wds_entries = TARGET_NUM_WDS_ENTRIES;
  240	config->dma_burst_size = TARGET_DMA_BURST_SIZE;
  241	config->rx_skip_defrag_timeout_dup_detection_check =
  242		TARGET_RX_SKIP_DEFRAG_TIMEOUT_DUP_DETECTION_CHECK;
  243	config->vow_config = TARGET_VOW_CONFIG;
  244	config->gtk_offload_max_vdev = TARGET_GTK_OFFLOAD_MAX_VDEV;
  245	config->num_msdu_desc = TARGET_NUM_MSDU_DESC;
  246	config->beacon_tx_offload_max_vdev = ab->num_radios * TARGET_MAX_BCN_OFFLD;
  247	config->rx_batchmode = TARGET_RX_BATCHMODE;
  248	/* Indicates host supports peer map v3 and unmap v2 support */
  249	config->peer_map_unmap_version = 0x32;
  250	config->twt_ap_pdev_count = ab->num_radios;
  251	config->twt_ap_sta_count = 1000;
  252	config->ema_max_vap_cnt = ab->num_radios;
  253	config->ema_max_profile_period = TARGET_EMA_MAX_PROFILE_PERIOD;
  254	config->beacon_tx_offload_max_vdev += config->ema_max_vap_cnt;
  255
  256	if (test_bit(WMI_TLV_SERVICE_PEER_METADATA_V1A_V1B_SUPPORT, ab->wmi_ab.svc_map))
  257		config->peer_metadata_ver = ATH12K_PEER_METADATA_V1B;
  258}
  259
  260void ath12k_wmi_init_wcn7850(struct ath12k_base *ab,
  261			     struct ath12k_wmi_resource_config_arg *config)
  262{
  263	config->num_vdevs = 4;
  264	config->num_peers = 16;
  265	config->num_tids = 32;
  266
  267	config->num_offload_peers = 3;
  268	config->num_offload_reorder_buffs = 3;
  269	config->num_peer_keys = TARGET_NUM_PEER_KEYS;
  270	config->ast_skid_limit = TARGET_AST_SKID_LIMIT;
  271	config->tx_chain_mask = (1 << ab->target_caps.num_rf_chains) - 1;
  272	config->rx_chain_mask = (1 << ab->target_caps.num_rf_chains) - 1;
  273	config->rx_timeout_pri[0] = TARGET_RX_TIMEOUT_LO_PRI;
  274	config->rx_timeout_pri[1] = TARGET_RX_TIMEOUT_LO_PRI;
  275	config->rx_timeout_pri[2] = TARGET_RX_TIMEOUT_LO_PRI;
  276	config->rx_timeout_pri[3] = TARGET_RX_TIMEOUT_HI_PRI;
  277	config->rx_decap_mode = TARGET_DECAP_MODE_NATIVE_WIFI;
  278	config->scan_max_pending_req = TARGET_SCAN_MAX_PENDING_REQS;
  279	config->bmiss_offload_max_vdev = TARGET_BMISS_OFFLOAD_MAX_VDEV;
  280	config->roam_offload_max_vdev = TARGET_ROAM_OFFLOAD_MAX_VDEV;
  281	config->roam_offload_max_ap_profiles = TARGET_ROAM_OFFLOAD_MAX_AP_PROFILES;
  282	config->num_mcast_groups = 0;
  283	config->num_mcast_table_elems = 0;
  284	config->mcast2ucast_mode = 0;
  285	config->tx_dbg_log_size = TARGET_TX_DBG_LOG_SIZE;
  286	config->num_wds_entries = 0;
  287	config->dma_burst_size = 0;
  288	config->rx_skip_defrag_timeout_dup_detection_check = 0;
  289	config->vow_config = TARGET_VOW_CONFIG;
  290	config->gtk_offload_max_vdev = 2;
  291	config->num_msdu_desc = 0x400;
  292	config->beacon_tx_offload_max_vdev = 2;
  293	config->rx_batchmode = TARGET_RX_BATCHMODE;
  294
  295	config->peer_map_unmap_version = 0x1;
  296	config->use_pdev_id = 1;
  297	config->max_frag_entries = 0xa;
  298	config->num_tdls_vdevs = 0x1;
  299	config->num_tdls_conn_table_entries = 8;
  300	config->beacon_tx_offload_max_vdev = 0x2;
  301	config->num_multicast_filter_entries = 0x20;
  302	config->num_wow_filters = 0x16;
  303	config->num_keep_alive_pattern = 0;
  304}
  305
  306#define PRIMAP(_hw_mode_) \
  307	[_hw_mode_] = _hw_mode_##_PRI
  308
  309static const int ath12k_hw_mode_pri_map[] = {
  310	PRIMAP(WMI_HOST_HW_MODE_SINGLE),
  311	PRIMAP(WMI_HOST_HW_MODE_DBS),
  312	PRIMAP(WMI_HOST_HW_MODE_SBS_PASSIVE),
  313	PRIMAP(WMI_HOST_HW_MODE_SBS),
  314	PRIMAP(WMI_HOST_HW_MODE_DBS_SBS),
  315	PRIMAP(WMI_HOST_HW_MODE_DBS_OR_SBS),
  316	/* keep last */
  317	PRIMAP(WMI_HOST_HW_MODE_MAX),
  318};
  319
  320static int
  321ath12k_wmi_tlv_iter(struct ath12k_base *ab, const void *ptr, size_t len,
  322		    int (*iter)(struct ath12k_base *ab, u16 tag, u16 len,
  323				const void *ptr, void *data),
  324		    void *data)
  325{
  326	const void *begin = ptr;
  327	const struct wmi_tlv *tlv;
  328	u16 tlv_tag, tlv_len;
  329	int ret;
  330
  331	while (len > 0) {
  332		if (len < sizeof(*tlv)) {
  333			ath12k_err(ab, "wmi tlv parse failure at byte %zd (%zu bytes left, %zu expected)\n",
  334				   ptr - begin, len, sizeof(*tlv));
  335			return -EINVAL;
  336		}
  337
  338		tlv = ptr;
  339		tlv_tag = le32_get_bits(tlv->header, WMI_TLV_TAG);
  340		tlv_len = le32_get_bits(tlv->header, WMI_TLV_LEN);
  341		ptr += sizeof(*tlv);
  342		len -= sizeof(*tlv);
  343
  344		if (tlv_len > len) {
  345			ath12k_err(ab, "wmi tlv parse failure of tag %u at byte %zd (%zu bytes left, %u expected)\n",
  346				   tlv_tag, ptr - begin, len, tlv_len);
  347			return -EINVAL;
  348		}
  349
  350		if (tlv_tag < ARRAY_SIZE(ath12k_wmi_tlv_policies) &&
  351		    ath12k_wmi_tlv_policies[tlv_tag].min_len &&
  352		    ath12k_wmi_tlv_policies[tlv_tag].min_len > tlv_len) {
  353			ath12k_err(ab, "wmi tlv parse failure of tag %u at byte %zd (%u bytes is less than min length %zu)\n",
  354				   tlv_tag, ptr - begin, tlv_len,
  355				   ath12k_wmi_tlv_policies[tlv_tag].min_len);
  356			return -EINVAL;
  357		}
  358
  359		ret = iter(ab, tlv_tag, tlv_len, ptr, data);
  360		if (ret)
  361			return ret;
  362
  363		ptr += tlv_len;
  364		len -= tlv_len;
  365	}
  366
  367	return 0;
  368}
  369
  370static int ath12k_wmi_tlv_iter_parse(struct ath12k_base *ab, u16 tag, u16 len,
  371				     const void *ptr, void *data)
  372{
  373	const void **tb = data;
  374
  375	if (tag < WMI_TAG_MAX)
  376		tb[tag] = ptr;
  377
  378	return 0;
  379}
  380
  381static int ath12k_wmi_tlv_parse(struct ath12k_base *ar, const void **tb,
  382				const void *ptr, size_t len)
  383{
  384	return ath12k_wmi_tlv_iter(ar, ptr, len, ath12k_wmi_tlv_iter_parse,
  385				   (void *)tb);
  386}
  387
  388static const void **
  389ath12k_wmi_tlv_parse_alloc(struct ath12k_base *ab,
  390			   struct sk_buff *skb, gfp_t gfp)
  391{
  392	const void **tb;
  393	int ret;
  394
  395	tb = kcalloc(WMI_TAG_MAX, sizeof(*tb), gfp);
  396	if (!tb)
  397		return ERR_PTR(-ENOMEM);
  398
  399	ret = ath12k_wmi_tlv_parse(ab, tb, skb->data, skb->len);
  400	if (ret) {
  401		kfree(tb);
  402		return ERR_PTR(ret);
  403	}
  404
  405	return tb;
  406}
  407
  408static int ath12k_wmi_cmd_send_nowait(struct ath12k_wmi_pdev *wmi, struct sk_buff *skb,
  409				      u32 cmd_id)
  410{
  411	struct ath12k_skb_cb *skb_cb = ATH12K_SKB_CB(skb);
  412	struct ath12k_base *ab = wmi->wmi_ab->ab;
  413	struct wmi_cmd_hdr *cmd_hdr;
  414	int ret;
  415
  416	if (!skb_push(skb, sizeof(struct wmi_cmd_hdr)))
  417		return -ENOMEM;
  418
  419	cmd_hdr = (struct wmi_cmd_hdr *)skb->data;
  420	cmd_hdr->cmd_id = le32_encode_bits(cmd_id, WMI_CMD_HDR_CMD_ID);
  421
  422	memset(skb_cb, 0, sizeof(*skb_cb));
  423	ret = ath12k_htc_send(&ab->htc, wmi->eid, skb);
  424
  425	if (ret)
  426		goto err_pull;
  427
  428	return 0;
  429
  430err_pull:
  431	skb_pull(skb, sizeof(struct wmi_cmd_hdr));
  432	return ret;
  433}
  434
  435int ath12k_wmi_cmd_send(struct ath12k_wmi_pdev *wmi, struct sk_buff *skb,
  436			u32 cmd_id)
  437{
  438	struct ath12k_wmi_base *wmi_ab = wmi->wmi_ab;
  439	int ret = -EOPNOTSUPP;
  440
  441	might_sleep();
  442
  443	wait_event_timeout(wmi_ab->tx_credits_wq, ({
  444		ret = ath12k_wmi_cmd_send_nowait(wmi, skb, cmd_id);
  445
  446		if (ret && test_bit(ATH12K_FLAG_CRASH_FLUSH, &wmi_ab->ab->dev_flags))
  447			ret = -ESHUTDOWN;
  448
  449		(ret != -EAGAIN);
  450	}), WMI_SEND_TIMEOUT_HZ);
  451
  452	if (ret == -EAGAIN)
  453		ath12k_warn(wmi_ab->ab, "wmi command %d timeout\n", cmd_id);
  454
  455	return ret;
  456}
  457
  458static int ath12k_pull_svc_ready_ext(struct ath12k_wmi_pdev *wmi_handle,
  459				     const void *ptr,
  460				     struct ath12k_wmi_service_ext_arg *arg)
  461{
  462	const struct wmi_service_ready_ext_event *ev = ptr;
  463	int i;
  464
  465	if (!ev)
  466		return -EINVAL;
  467
  468	/* Move this to host based bitmap */
  469	arg->default_conc_scan_config_bits =
  470		le32_to_cpu(ev->default_conc_scan_config_bits);
  471	arg->default_fw_config_bits = le32_to_cpu(ev->default_fw_config_bits);
  472	arg->he_cap_info = le32_to_cpu(ev->he_cap_info);
  473	arg->mpdu_density = le32_to_cpu(ev->mpdu_density);
  474	arg->max_bssid_rx_filters = le32_to_cpu(ev->max_bssid_rx_filters);
  475	arg->ppet.numss_m1 = le32_to_cpu(ev->ppet.numss_m1);
  476	arg->ppet.ru_bit_mask = le32_to_cpu(ev->ppet.ru_info);
  477
  478	for (i = 0; i < WMI_MAX_NUM_SS; i++)
  479		arg->ppet.ppet16_ppet8_ru3_ru0[i] =
  480			le32_to_cpu(ev->ppet.ppet16_ppet8_ru3_ru0[i]);
  481
  482	return 0;
  483}
  484
  485static int
  486ath12k_pull_mac_phy_cap_svc_ready_ext(struct ath12k_wmi_pdev *wmi_handle,
  487				      struct ath12k_wmi_svc_rdy_ext_parse *svc,
  488				      u8 hw_mode_id, u8 phy_id,
  489				      struct ath12k_pdev *pdev)
  490{
  491	const struct ath12k_wmi_mac_phy_caps_params *mac_caps;
  492	const struct ath12k_wmi_soc_mac_phy_hw_mode_caps_params *hw_caps = svc->hw_caps;
  493	const struct ath12k_wmi_hw_mode_cap_params *wmi_hw_mode_caps = svc->hw_mode_caps;
  494	const struct ath12k_wmi_mac_phy_caps_params *wmi_mac_phy_caps = svc->mac_phy_caps;
  495	struct ath12k_base *ab = wmi_handle->wmi_ab->ab;
  496	struct ath12k_band_cap *cap_band;
  497	struct ath12k_pdev_cap *pdev_cap = &pdev->cap;
  498	struct ath12k_fw_pdev *fw_pdev;
  499	u32 supported_bands;
  500	u32 phy_map;
  501	u32 hw_idx, phy_idx = 0;
  502	int i;
  503
  504	if (!hw_caps || !wmi_hw_mode_caps || !svc->soc_hal_reg_caps)
  505		return -EINVAL;
  506
  507	for (hw_idx = 0; hw_idx < le32_to_cpu(hw_caps->num_hw_modes); hw_idx++) {
  508		if (hw_mode_id == le32_to_cpu(wmi_hw_mode_caps[hw_idx].hw_mode_id))
  509			break;
  510
  511		phy_map = le32_to_cpu(wmi_hw_mode_caps[hw_idx].phy_id_map);
  512		phy_idx = fls(phy_map);
  513	}
  514
  515	if (hw_idx == le32_to_cpu(hw_caps->num_hw_modes))
  516		return -EINVAL;
  517
  518	phy_idx += phy_id;
  519	if (phy_id >= le32_to_cpu(svc->soc_hal_reg_caps->num_phy))
  520		return -EINVAL;
  521
  522	mac_caps = wmi_mac_phy_caps + phy_idx;
  523	supported_bands = le32_to_cpu(mac_caps->supported_bands);
  524
  525	if (!(supported_bands & WMI_HOST_WLAN_2GHZ_CAP) &&
  526	    !(supported_bands & WMI_HOST_WLAN_5GHZ_CAP))
  527		return -EINVAL;
  528
  529	pdev->pdev_id = ath12k_wmi_mac_phy_get_pdev_id(mac_caps);
  530	pdev->hw_link_id = ath12k_wmi_mac_phy_get_hw_link_id(mac_caps);
  531	pdev_cap->supported_bands |= supported_bands;
  532	pdev_cap->ampdu_density = le32_to_cpu(mac_caps->ampdu_density);
  533
  534	fw_pdev = &ab->fw_pdev[ab->fw_pdev_count];
  535	fw_pdev->supported_bands = supported_bands;
  536	fw_pdev->pdev_id = ath12k_wmi_mac_phy_get_pdev_id(mac_caps);
  537	fw_pdev->phy_id = le32_to_cpu(mac_caps->phy_id);
  538	ab->fw_pdev_count++;
  539
  540	/* Take non-zero tx/rx chainmask. If tx/rx chainmask differs from
  541	 * band to band for a single radio, need to see how this should be
  542	 * handled.
  543	 */
  544	if (supported_bands & WMI_HOST_WLAN_2GHZ_CAP) {
  545		pdev_cap->tx_chain_mask = le32_to_cpu(mac_caps->tx_chain_mask_2g);
  546		pdev_cap->rx_chain_mask = le32_to_cpu(mac_caps->rx_chain_mask_2g);
  547	}
  548
  549	if (supported_bands & WMI_HOST_WLAN_5GHZ_CAP) {
  550		pdev_cap->vht_cap = le32_to_cpu(mac_caps->vht_cap_info_5g);
  551		pdev_cap->vht_mcs = le32_to_cpu(mac_caps->vht_supp_mcs_5g);
  552		pdev_cap->he_mcs = le32_to_cpu(mac_caps->he_supp_mcs_5g);
  553		pdev_cap->tx_chain_mask = le32_to_cpu(mac_caps->tx_chain_mask_5g);
  554		pdev_cap->rx_chain_mask = le32_to_cpu(mac_caps->rx_chain_mask_5g);
  555		pdev_cap->nss_ratio_enabled =
  556			WMI_NSS_RATIO_EN_DIS_GET(mac_caps->nss_ratio);
  557		pdev_cap->nss_ratio_info =
  558			WMI_NSS_RATIO_INFO_GET(mac_caps->nss_ratio);
  559	}
  560
  561	/* tx/rx chainmask reported from fw depends on the actual hw chains used,
  562	 * For example, for 4x4 capable macphys, first 4 chains can be used for first
  563	 * mac and the remaining 4 chains can be used for the second mac or vice-versa.
  564	 * In this case, tx/rx chainmask 0xf will be advertised for first mac and 0xf0
  565	 * will be advertised for second mac or vice-versa. Compute the shift value
  566	 * for tx/rx chainmask which will be used to advertise supported ht/vht rates to
  567	 * mac80211.
  568	 */
  569	pdev_cap->tx_chain_mask_shift =
  570			find_first_bit((unsigned long *)&pdev_cap->tx_chain_mask, 32);
  571	pdev_cap->rx_chain_mask_shift =
  572			find_first_bit((unsigned long *)&pdev_cap->rx_chain_mask, 32);
  573
  574	if (supported_bands & WMI_HOST_WLAN_2GHZ_CAP) {
  575		cap_band = &pdev_cap->band[NL80211_BAND_2GHZ];
  576		cap_band->phy_id = le32_to_cpu(mac_caps->phy_id);
  577		cap_band->max_bw_supported = le32_to_cpu(mac_caps->max_bw_supported_2g);
  578		cap_band->ht_cap_info = le32_to_cpu(mac_caps->ht_cap_info_2g);
  579		cap_band->he_cap_info[0] = le32_to_cpu(mac_caps->he_cap_info_2g);
  580		cap_band->he_cap_info[1] = le32_to_cpu(mac_caps->he_cap_info_2g_ext);
  581		cap_band->he_mcs = le32_to_cpu(mac_caps->he_supp_mcs_2g);
  582		for (i = 0; i < WMI_MAX_HECAP_PHY_SIZE; i++)
  583			cap_band->he_cap_phy_info[i] =
  584				le32_to_cpu(mac_caps->he_cap_phy_info_2g[i]);
  585
  586		cap_band->he_ppet.numss_m1 = le32_to_cpu(mac_caps->he_ppet2g.numss_m1);
  587		cap_band->he_ppet.ru_bit_mask = le32_to_cpu(mac_caps->he_ppet2g.ru_info);
  588
  589		for (i = 0; i < WMI_MAX_NUM_SS; i++)
  590			cap_band->he_ppet.ppet16_ppet8_ru3_ru0[i] =
  591				le32_to_cpu(mac_caps->he_ppet2g.ppet16_ppet8_ru3_ru0[i]);
  592	}
  593
  594	if (supported_bands & WMI_HOST_WLAN_5GHZ_CAP) {
  595		cap_band = &pdev_cap->band[NL80211_BAND_5GHZ];
  596		cap_band->phy_id = le32_to_cpu(mac_caps->phy_id);
  597		cap_band->max_bw_supported =
  598			le32_to_cpu(mac_caps->max_bw_supported_5g);
  599		cap_band->ht_cap_info = le32_to_cpu(mac_caps->ht_cap_info_5g);
  600		cap_band->he_cap_info[0] = le32_to_cpu(mac_caps->he_cap_info_5g);
  601		cap_band->he_cap_info[1] = le32_to_cpu(mac_caps->he_cap_info_5g_ext);
  602		cap_band->he_mcs = le32_to_cpu(mac_caps->he_supp_mcs_5g);
  603		for (i = 0; i < WMI_MAX_HECAP_PHY_SIZE; i++)
  604			cap_band->he_cap_phy_info[i] =
  605				le32_to_cpu(mac_caps->he_cap_phy_info_5g[i]);
  606
  607		cap_band->he_ppet.numss_m1 = le32_to_cpu(mac_caps->he_ppet5g.numss_m1);
  608		cap_band->he_ppet.ru_bit_mask = le32_to_cpu(mac_caps->he_ppet5g.ru_info);
  609
  610		for (i = 0; i < WMI_MAX_NUM_SS; i++)
  611			cap_band->he_ppet.ppet16_ppet8_ru3_ru0[i] =
  612				le32_to_cpu(mac_caps->he_ppet5g.ppet16_ppet8_ru3_ru0[i]);
  613
  614		cap_band = &pdev_cap->band[NL80211_BAND_6GHZ];
  615		cap_band->max_bw_supported =
  616			le32_to_cpu(mac_caps->max_bw_supported_5g);
  617		cap_band->ht_cap_info = le32_to_cpu(mac_caps->ht_cap_info_5g);
  618		cap_band->he_cap_info[0] = le32_to_cpu(mac_caps->he_cap_info_5g);
  619		cap_band->he_cap_info[1] = le32_to_cpu(mac_caps->he_cap_info_5g_ext);
  620		cap_band->he_mcs = le32_to_cpu(mac_caps->he_supp_mcs_5g);
  621		for (i = 0; i < WMI_MAX_HECAP_PHY_SIZE; i++)
  622			cap_band->he_cap_phy_info[i] =
  623				le32_to_cpu(mac_caps->he_cap_phy_info_5g[i]);
  624
  625		cap_band->he_ppet.numss_m1 = le32_to_cpu(mac_caps->he_ppet5g.numss_m1);
  626		cap_band->he_ppet.ru_bit_mask = le32_to_cpu(mac_caps->he_ppet5g.ru_info);
  627
  628		for (i = 0; i < WMI_MAX_NUM_SS; i++)
  629			cap_band->he_ppet.ppet16_ppet8_ru3_ru0[i] =
  630				le32_to_cpu(mac_caps->he_ppet5g.ppet16_ppet8_ru3_ru0[i]);
  631	}
  632
  633	return 0;
  634}
  635
  636static int
  637ath12k_pull_reg_cap_svc_rdy_ext(struct ath12k_wmi_pdev *wmi_handle,
  638				const struct ath12k_wmi_soc_hal_reg_caps_params *reg_caps,
  639				const struct ath12k_wmi_hal_reg_caps_ext_params *ext_caps,
  640				u8 phy_idx,
  641				struct ath12k_wmi_hal_reg_capabilities_ext_arg *param)
  642{
  643	const struct ath12k_wmi_hal_reg_caps_ext_params *ext_reg_cap;
  644
  645	if (!reg_caps || !ext_caps)
  646		return -EINVAL;
  647
  648	if (phy_idx >= le32_to_cpu(reg_caps->num_phy))
  649		return -EINVAL;
  650
  651	ext_reg_cap = &ext_caps[phy_idx];
  652
  653	param->phy_id = le32_to_cpu(ext_reg_cap->phy_id);
  654	param->eeprom_reg_domain = le32_to_cpu(ext_reg_cap->eeprom_reg_domain);
  655	param->eeprom_reg_domain_ext =
  656		le32_to_cpu(ext_reg_cap->eeprom_reg_domain_ext);
  657	param->regcap1 = le32_to_cpu(ext_reg_cap->regcap1);
  658	param->regcap2 = le32_to_cpu(ext_reg_cap->regcap2);
  659	/* check if param->wireless_mode is needed */
  660	param->low_2ghz_chan = le32_to_cpu(ext_reg_cap->low_2ghz_chan);
  661	param->high_2ghz_chan = le32_to_cpu(ext_reg_cap->high_2ghz_chan);
  662	param->low_5ghz_chan = le32_to_cpu(ext_reg_cap->low_5ghz_chan);
  663	param->high_5ghz_chan = le32_to_cpu(ext_reg_cap->high_5ghz_chan);
  664
  665	return 0;
  666}
  667
  668static int ath12k_pull_service_ready_tlv(struct ath12k_base *ab,
  669					 const void *evt_buf,
  670					 struct ath12k_wmi_target_cap_arg *cap)
  671{
  672	const struct wmi_service_ready_event *ev = evt_buf;
  673
  674	if (!ev) {
  675		ath12k_err(ab, "%s: failed by NULL param\n",
  676			   __func__);
  677		return -EINVAL;
  678	}
  679
  680	cap->phy_capability = le32_to_cpu(ev->phy_capability);
  681	cap->max_frag_entry = le32_to_cpu(ev->max_frag_entry);
  682	cap->num_rf_chains = le32_to_cpu(ev->num_rf_chains);
  683	cap->ht_cap_info = le32_to_cpu(ev->ht_cap_info);
  684	cap->vht_cap_info = le32_to_cpu(ev->vht_cap_info);
  685	cap->vht_supp_mcs = le32_to_cpu(ev->vht_supp_mcs);
  686	cap->hw_min_tx_power = le32_to_cpu(ev->hw_min_tx_power);
  687	cap->hw_max_tx_power = le32_to_cpu(ev->hw_max_tx_power);
  688	cap->sys_cap_info = le32_to_cpu(ev->sys_cap_info);
  689	cap->min_pkt_size_enable = le32_to_cpu(ev->min_pkt_size_enable);
  690	cap->max_bcn_ie_size = le32_to_cpu(ev->max_bcn_ie_size);
  691	cap->max_num_scan_channels = le32_to_cpu(ev->max_num_scan_channels);
  692	cap->max_supported_macs = le32_to_cpu(ev->max_supported_macs);
  693	cap->wmi_fw_sub_feat_caps = le32_to_cpu(ev->wmi_fw_sub_feat_caps);
  694	cap->txrx_chainmask = le32_to_cpu(ev->txrx_chainmask);
  695	cap->default_dbs_hw_mode_index = le32_to_cpu(ev->default_dbs_hw_mode_index);
  696	cap->num_msdu_desc = le32_to_cpu(ev->num_msdu_desc);
  697
  698	return 0;
  699}
  700
  701/* Save the wmi_service_bitmap into a linear bitmap. The wmi_services in
  702 * wmi_service ready event are advertised in b0-b3 (LSB 4-bits) of each
  703 * 4-byte word.
  704 */
  705static void ath12k_wmi_service_bitmap_copy(struct ath12k_wmi_pdev *wmi,
  706					   const u32 *wmi_svc_bm)
  707{
  708	int i, j;
  709
  710	for (i = 0, j = 0; i < WMI_SERVICE_BM_SIZE && j < WMI_MAX_SERVICE; i++) {
  711		do {
  712			if (wmi_svc_bm[i] & BIT(j % WMI_SERVICE_BITS_IN_SIZE32))
  713				set_bit(j, wmi->wmi_ab->svc_map);
  714		} while (++j % WMI_SERVICE_BITS_IN_SIZE32);
  715	}
  716}
  717
  718static int ath12k_wmi_svc_rdy_parse(struct ath12k_base *ab, u16 tag, u16 len,
  719				    const void *ptr, void *data)
  720{
  721	struct ath12k_wmi_svc_ready_parse *svc_ready = data;
  722	struct ath12k_wmi_pdev *wmi_handle = &ab->wmi_ab.wmi[0];
  723	u16 expect_len;
  724
  725	switch (tag) {
  726	case WMI_TAG_SERVICE_READY_EVENT:
  727		if (ath12k_pull_service_ready_tlv(ab, ptr, &ab->target_caps))
  728			return -EINVAL;
  729		break;
  730
  731	case WMI_TAG_ARRAY_UINT32:
  732		if (!svc_ready->wmi_svc_bitmap_done) {
  733			expect_len = WMI_SERVICE_BM_SIZE * sizeof(u32);
  734			if (len < expect_len) {
  735				ath12k_warn(ab, "invalid len %d for the tag 0x%x\n",
  736					    len, tag);
  737				return -EINVAL;
  738			}
  739
  740			ath12k_wmi_service_bitmap_copy(wmi_handle, ptr);
  741
  742			svc_ready->wmi_svc_bitmap_done = true;
  743		}
  744		break;
  745	default:
  746		break;
  747	}
  748
  749	return 0;
  750}
  751
  752static int ath12k_service_ready_event(struct ath12k_base *ab, struct sk_buff *skb)
  753{
  754	struct ath12k_wmi_svc_ready_parse svc_ready = { };
  755	int ret;
  756
  757	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
  758				  ath12k_wmi_svc_rdy_parse,
  759				  &svc_ready);
  760	if (ret) {
  761		ath12k_warn(ab, "failed to parse tlv %d\n", ret);
  762		return ret;
  763	}
  764
  765	return 0;
  766}
  767
  768static u32 ath12k_wmi_mgmt_get_freq(struct ath12k *ar,
  769				    struct ieee80211_tx_info *info)
  770{
  771	struct ath12k_base *ab = ar->ab;
  772	u32 freq = 0;
  773
  774	if (ab->hw_params->single_pdev_only &&
  775	    ar->scan.is_roc &&
  776	    (info->flags & IEEE80211_TX_CTL_TX_OFFCHAN))
  777		freq = ar->scan.roc_freq;
  778
  779	return freq;
  780}
  781
  782struct sk_buff *ath12k_wmi_alloc_skb(struct ath12k_wmi_base *wmi_ab, u32 len)
  783{
  784	struct sk_buff *skb;
  785	struct ath12k_base *ab = wmi_ab->ab;
  786	u32 round_len = roundup(len, 4);
  787
  788	skb = ath12k_htc_alloc_skb(ab, WMI_SKB_HEADROOM + round_len);
  789	if (!skb)
  790		return NULL;
  791
  792	skb_reserve(skb, WMI_SKB_HEADROOM);
  793	if (!IS_ALIGNED((unsigned long)skb->data, 4))
  794		ath12k_warn(ab, "unaligned WMI skb data\n");
  795
  796	skb_put(skb, round_len);
  797	memset(skb->data, 0, round_len);
  798
  799	return skb;
  800}
  801
  802int ath12k_wmi_mgmt_send(struct ath12k_link_vif *arvif, u32 buf_id,
  803			 struct sk_buff *frame)
  804{
  805	struct ath12k *ar = arvif->ar;
  806	struct ath12k_wmi_pdev *wmi = ar->wmi;
  807	struct wmi_mgmt_send_cmd *cmd;
  808	struct ieee80211_tx_info *info = IEEE80211_SKB_CB(frame);
  809	struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)frame->data;
  810	struct ieee80211_vif *vif = ath12k_ahvif_to_vif(arvif->ahvif);
  811	int cmd_len = sizeof(struct ath12k_wmi_mgmt_send_tx_params);
  812	struct ieee80211_mgmt *mgmt = (struct ieee80211_mgmt *)hdr;
  813	struct ath12k_wmi_mlo_mgmt_send_params *ml_params;
  814	struct ath12k_base *ab = ar->ab;
  815	struct wmi_tlv *frame_tlv, *tlv;
  816	struct ath12k_skb_cb *skb_cb;
  817	u32 buf_len, buf_len_aligned;
  818	u32 vdev_id = arvif->vdev_id;
  819	bool link_agnostic = false;
  820	struct sk_buff *skb;
  821	int ret, len;
  822	void *ptr;
  823
  824	buf_len = min_t(int, frame->len, WMI_MGMT_SEND_DOWNLD_LEN);
  825
  826	buf_len_aligned = roundup(buf_len, sizeof(u32));
  827
  828	len = sizeof(*cmd) + sizeof(*frame_tlv) + buf_len_aligned;
  829
  830	if (ieee80211_vif_is_mld(vif)) {
  831		skb_cb = ATH12K_SKB_CB(frame);
  832		if ((skb_cb->flags & ATH12K_SKB_MLO_STA) &&
  833		    ab->hw_params->hw_ops->is_frame_link_agnostic &&
  834		    ab->hw_params->hw_ops->is_frame_link_agnostic(arvif, mgmt)) {
  835			len += cmd_len + TLV_HDR_SIZE + sizeof(*ml_params);
  836			ath12k_generic_dbg(ATH12K_DBG_MGMT,
  837					   "Sending Mgmt Frame fc 0x%0x as link agnostic",
  838					   mgmt->frame_control);
  839			link_agnostic = true;
  840		}
  841	}
  842
  843	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
  844	if (!skb)
  845		return -ENOMEM;
  846
  847	cmd = (struct wmi_mgmt_send_cmd *)skb->data;
  848	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MGMT_TX_SEND_CMD,
  849						 sizeof(*cmd));
  850	cmd->vdev_id = cpu_to_le32(vdev_id);
  851	cmd->desc_id = cpu_to_le32(buf_id);
  852	cmd->chanfreq = cpu_to_le32(ath12k_wmi_mgmt_get_freq(ar, info));
  853	cmd->paddr_lo = cpu_to_le32(lower_32_bits(ATH12K_SKB_CB(frame)->paddr));
  854	cmd->paddr_hi = cpu_to_le32(upper_32_bits(ATH12K_SKB_CB(frame)->paddr));
  855	cmd->frame_len = cpu_to_le32(frame->len);
  856	cmd->buf_len = cpu_to_le32(buf_len);
  857	cmd->tx_params_valid = 0;
  858
  859	frame_tlv = (struct wmi_tlv *)(skb->data + sizeof(*cmd));
  860	frame_tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, buf_len_aligned);
  861
  862	memcpy(frame_tlv->value, frame->data, buf_len);
  863
  864	if (!link_agnostic)
  865		goto send;
  866
  867	ptr = skb->data + sizeof(*cmd) + sizeof(*frame_tlv) + buf_len_aligned;
  868
  869	tlv = ptr;
  870
  871	/* Tx params not used currently */
  872	tlv->header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_TX_SEND_PARAMS, cmd_len);
  873	ptr += cmd_len;
  874
  875	tlv = ptr;
  876	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, sizeof(*ml_params));
  877	ptr += TLV_HDR_SIZE;
  878
  879	ml_params = ptr;
  880	ml_params->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_TX_SEND_PARAMS,
  881						       sizeof(*ml_params));
  882
  883	ml_params->hw_link_id = cpu_to_le32(WMI_MGMT_LINK_AGNOSTIC_ID);
  884
  885send:
  886	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_MGMT_TX_SEND_CMDID);
  887	if (ret) {
  888		ath12k_warn(ar->ab,
  889			    "failed to submit WMI_MGMT_TX_SEND_CMDID cmd\n");
  890		dev_kfree_skb(skb);
  891	}
  892
  893	return ret;
  894}
  895
  896int ath12k_wmi_send_stats_request_cmd(struct ath12k *ar, u32 stats_id,
  897				      u32 vdev_id, u32 pdev_id)
  898{
  899	struct ath12k_wmi_pdev *wmi = ar->wmi;
  900	struct wmi_request_stats_cmd *cmd;
  901	struct sk_buff *skb;
  902	int ret;
  903
  904	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
  905	if (!skb)
  906		return -ENOMEM;
  907
  908	cmd = (struct wmi_request_stats_cmd *)skb->data;
  909	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_REQUEST_STATS_CMD,
  910						 sizeof(*cmd));
  911
  912	cmd->stats_id = cpu_to_le32(stats_id);
  913	cmd->vdev_id = cpu_to_le32(vdev_id);
  914	cmd->pdev_id = cpu_to_le32(pdev_id);
  915
  916	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_REQUEST_STATS_CMDID);
  917	if (ret) {
  918		ath12k_warn(ar->ab, "failed to send WMI_REQUEST_STATS cmd\n");
  919		dev_kfree_skb(skb);
  920	}
  921
  922	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
  923		   "WMI request stats 0x%x vdev id %d pdev id %d\n",
  924		   stats_id, vdev_id, pdev_id);
  925
  926	return ret;
  927}
  928
  929int ath12k_wmi_vdev_create(struct ath12k *ar, u8 *macaddr,
  930			   struct ath12k_wmi_vdev_create_arg *args)
  931{
  932	struct ath12k_wmi_pdev *wmi = ar->wmi;
  933	struct wmi_vdev_create_cmd *cmd;
  934	struct sk_buff *skb;
  935	struct ath12k_wmi_vdev_txrx_streams_params *txrx_streams;
  936	bool is_ml_vdev = is_valid_ether_addr(args->mld_addr);
  937	struct wmi_vdev_create_mlo_params *ml_params;
  938	struct wmi_tlv *tlv;
  939	int ret, len;
  940	void *ptr;
  941
  942	/* It can be optimized my sending tx/rx chain configuration
  943	 * only for supported bands instead of always sending it for
  944	 * both the bands.
  945	 */
  946	len = sizeof(*cmd) + TLV_HDR_SIZE +
  947		(WMI_NUM_SUPPORTED_BAND_MAX * sizeof(*txrx_streams)) +
  948		(is_ml_vdev ? TLV_HDR_SIZE + sizeof(*ml_params) : 0);
  949
  950	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
  951	if (!skb)
  952		return -ENOMEM;
  953
  954	cmd = (struct wmi_vdev_create_cmd *)skb->data;
  955	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_CREATE_CMD,
  956						 sizeof(*cmd));
  957
  958	cmd->vdev_id = cpu_to_le32(args->if_id);
  959	cmd->vdev_type = cpu_to_le32(args->type);
  960	cmd->vdev_subtype = cpu_to_le32(args->subtype);
  961	cmd->num_cfg_txrx_streams = cpu_to_le32(WMI_NUM_SUPPORTED_BAND_MAX);
  962	cmd->pdev_id = cpu_to_le32(args->pdev_id);
  963	cmd->mbssid_flags = cpu_to_le32(args->mbssid_flags);
  964	cmd->mbssid_tx_vdev_id = cpu_to_le32(args->mbssid_tx_vdev_id);
  965	cmd->vdev_stats_id = cpu_to_le32(args->if_stats_id);
  966	ether_addr_copy(cmd->vdev_macaddr.addr, macaddr);
  967
  968	if (args->if_stats_id != ATH12K_INVAL_VDEV_STATS_ID)
  969		cmd->vdev_stats_id_valid = cpu_to_le32(BIT(0));
  970
  971	ptr = skb->data + sizeof(*cmd);
  972	len = WMI_NUM_SUPPORTED_BAND_MAX * sizeof(*txrx_streams);
  973
  974	tlv = ptr;
  975	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, len);
  976
  977	ptr += TLV_HDR_SIZE;
  978	txrx_streams = ptr;
  979	len = sizeof(*txrx_streams);
  980	txrx_streams->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_TXRX_STREAMS,
  981							  len);
  982	txrx_streams->band = cpu_to_le32(WMI_TPC_CHAINMASK_CONFIG_BAND_2G);
  983	txrx_streams->supported_tx_streams =
  984				cpu_to_le32(args->chains[NL80211_BAND_2GHZ].tx);
  985	txrx_streams->supported_rx_streams =
  986				cpu_to_le32(args->chains[NL80211_BAND_2GHZ].rx);
  987
  988	txrx_streams++;
  989	txrx_streams->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_TXRX_STREAMS,
  990							  len);
  991	txrx_streams->band = cpu_to_le32(WMI_TPC_CHAINMASK_CONFIG_BAND_5G);
  992	txrx_streams->supported_tx_streams =
  993				cpu_to_le32(args->chains[NL80211_BAND_5GHZ].tx);
  994	txrx_streams->supported_rx_streams =
  995				cpu_to_le32(args->chains[NL80211_BAND_5GHZ].rx);
  996
  997	ptr += WMI_NUM_SUPPORTED_BAND_MAX * sizeof(*txrx_streams);
  998
  999	if (is_ml_vdev) {
 1000		tlv = ptr;
 1001		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
 1002						 sizeof(*ml_params));
 1003		ptr += TLV_HDR_SIZE;
 1004		ml_params = ptr;
 1005
 1006		ml_params->tlv_header =
 1007			ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_VDEV_CREATE_PARAMS,
 1008					       sizeof(*ml_params));
 1009		ether_addr_copy(ml_params->mld_macaddr.addr, args->mld_addr);
 1010	}
 1011
 1012	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1013		   "WMI vdev create: id %d type %d subtype %d macaddr %pM pdevid %d\n",
 1014		   args->if_id, args->type, args->subtype,
 1015		   macaddr, args->pdev_id);
 1016
 1017	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_VDEV_CREATE_CMDID);
 1018	if (ret) {
 1019		ath12k_warn(ar->ab,
 1020			    "failed to submit WMI_VDEV_CREATE_CMDID\n");
 1021		dev_kfree_skb(skb);
 1022	}
 1023
 1024	return ret;
 1025}
 1026
 1027int ath12k_wmi_vdev_delete(struct ath12k *ar, u8 vdev_id)
 1028{
 1029	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1030	struct wmi_vdev_delete_cmd *cmd;
 1031	struct sk_buff *skb;
 1032	int ret;
 1033
 1034	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1035	if (!skb)
 1036		return -ENOMEM;
 1037
 1038	cmd = (struct wmi_vdev_delete_cmd *)skb->data;
 1039	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_DELETE_CMD,
 1040						 sizeof(*cmd));
 1041	cmd->vdev_id = cpu_to_le32(vdev_id);
 1042
 1043	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "WMI vdev delete id %d\n", vdev_id);
 1044
 1045	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_VDEV_DELETE_CMDID);
 1046	if (ret) {
 1047		ath12k_warn(ar->ab, "failed to submit WMI_VDEV_DELETE_CMDID\n");
 1048		dev_kfree_skb(skb);
 1049	}
 1050
 1051	return ret;
 1052}
 1053
 1054int ath12k_wmi_vdev_stop(struct ath12k *ar, u8 vdev_id)
 1055{
 1056	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1057	struct wmi_vdev_stop_cmd *cmd;
 1058	struct sk_buff *skb;
 1059	int ret;
 1060
 1061	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1062	if (!skb)
 1063		return -ENOMEM;
 1064
 1065	cmd = (struct wmi_vdev_stop_cmd *)skb->data;
 1066
 1067	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_STOP_CMD,
 1068						 sizeof(*cmd));
 1069	cmd->vdev_id = cpu_to_le32(vdev_id);
 1070
 1071	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "WMI vdev stop id 0x%x\n", vdev_id);
 1072
 1073	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_VDEV_STOP_CMDID);
 1074	if (ret) {
 1075		ath12k_warn(ar->ab, "failed to submit WMI_VDEV_STOP cmd\n");
 1076		dev_kfree_skb(skb);
 1077	}
 1078
 1079	return ret;
 1080}
 1081
 1082int ath12k_wmi_vdev_down(struct ath12k *ar, u8 vdev_id)
 1083{
 1084	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1085	struct wmi_vdev_down_cmd *cmd;
 1086	struct sk_buff *skb;
 1087	int ret;
 1088
 1089	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1090	if (!skb)
 1091		return -ENOMEM;
 1092
 1093	cmd = (struct wmi_vdev_down_cmd *)skb->data;
 1094
 1095	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_DOWN_CMD,
 1096						 sizeof(*cmd));
 1097	cmd->vdev_id = cpu_to_le32(vdev_id);
 1098
 1099	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "WMI vdev down id 0x%x\n", vdev_id);
 1100
 1101	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_VDEV_DOWN_CMDID);
 1102	if (ret) {
 1103		ath12k_warn(ar->ab, "failed to submit WMI_VDEV_DOWN cmd\n");
 1104		dev_kfree_skb(skb);
 1105	}
 1106
 1107	return ret;
 1108}
 1109
 1110static void ath12k_wmi_put_wmi_channel(struct ath12k_wmi_channel_params *chan,
 1111				       struct wmi_vdev_start_req_arg *arg)
 1112{
 1113	u32 center_freq1 = arg->band_center_freq1;
 1114
 1115	memset(chan, 0, sizeof(*chan));
 1116
 1117	chan->mhz = cpu_to_le32(arg->freq);
 1118	chan->band_center_freq1 = cpu_to_le32(center_freq1);
 1119	if (arg->mode == MODE_11BE_EHT320) {
 1120		if (arg->freq > center_freq1)
 1121			chan->band_center_freq1 = cpu_to_le32(center_freq1 + 80);
 1122		else
 1123			chan->band_center_freq1 = cpu_to_le32(center_freq1 - 80);
 1124
 1125		chan->band_center_freq2 = cpu_to_le32(center_freq1);
 1126
 1127	} else if (arg->mode == MODE_11BE_EHT160 ||
 1128		   arg->mode == MODE_11AX_HE160) {
 1129		if (arg->freq > center_freq1)
 1130			chan->band_center_freq1 = cpu_to_le32(center_freq1 + 40);
 1131		else
 1132			chan->band_center_freq1 = cpu_to_le32(center_freq1 - 40);
 1133
 1134		chan->band_center_freq2 = cpu_to_le32(center_freq1);
 1135	} else {
 1136		chan->band_center_freq2 = 0;
 1137	}
 1138
 1139	chan->info |= le32_encode_bits(arg->mode, WMI_CHAN_INFO_MODE);
 1140	if (arg->passive)
 1141		chan->info |= cpu_to_le32(WMI_CHAN_INFO_PASSIVE);
 1142	if (arg->allow_ibss)
 1143		chan->info |= cpu_to_le32(WMI_CHAN_INFO_ADHOC_ALLOWED);
 1144	if (arg->allow_ht)
 1145		chan->info |= cpu_to_le32(WMI_CHAN_INFO_ALLOW_HT);
 1146	if (arg->allow_vht)
 1147		chan->info |= cpu_to_le32(WMI_CHAN_INFO_ALLOW_VHT);
 1148	if (arg->allow_he)
 1149		chan->info |= cpu_to_le32(WMI_CHAN_INFO_ALLOW_HE);
 1150	if (arg->ht40plus)
 1151		chan->info |= cpu_to_le32(WMI_CHAN_INFO_HT40_PLUS);
 1152	if (arg->chan_radar)
 1153		chan->info |= cpu_to_le32(WMI_CHAN_INFO_DFS);
 1154	if (arg->freq2_radar)
 1155		chan->info |= cpu_to_le32(WMI_CHAN_INFO_DFS_FREQ2);
 1156
 1157	chan->reg_info_1 = le32_encode_bits(arg->max_power,
 1158					    WMI_CHAN_REG_INFO1_MAX_PWR) |
 1159		le32_encode_bits(arg->max_reg_power,
 1160				 WMI_CHAN_REG_INFO1_MAX_REG_PWR);
 1161
 1162	chan->reg_info_2 = le32_encode_bits(arg->max_antenna_gain,
 1163					    WMI_CHAN_REG_INFO2_ANT_MAX) |
 1164		le32_encode_bits(arg->max_power, WMI_CHAN_REG_INFO2_MAX_TX_PWR);
 1165}
 1166
 1167int ath12k_wmi_vdev_start(struct ath12k *ar, struct wmi_vdev_start_req_arg *arg,
 1168			  bool restart)
 1169{
 1170	struct wmi_vdev_start_mlo_params *ml_params;
 1171	struct wmi_partner_link_info *partner_info;
 1172	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1173	struct wmi_vdev_start_request_cmd *cmd;
 1174	struct sk_buff *skb;
 1175	struct ath12k_wmi_channel_params *chan;
 1176	struct wmi_tlv *tlv;
 1177	void *ptr;
 1178	int ret, len, i, ml_arg_size = 0;
 1179
 1180	if (WARN_ON(arg->ssid_len > sizeof(cmd->ssid.ssid)))
 1181		return -EINVAL;
 1182
 1183	len = sizeof(*cmd) + sizeof(*chan) + TLV_HDR_SIZE;
 1184
 1185	if (!restart && arg->ml.enabled) {
 1186		ml_arg_size = TLV_HDR_SIZE + sizeof(*ml_params) +
 1187			      TLV_HDR_SIZE + (arg->ml.num_partner_links *
 1188					      sizeof(*partner_info));
 1189		len += ml_arg_size;
 1190	}
 1191	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 1192	if (!skb)
 1193		return -ENOMEM;
 1194
 1195	cmd = (struct wmi_vdev_start_request_cmd *)skb->data;
 1196	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_START_REQUEST_CMD,
 1197						 sizeof(*cmd));
 1198	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 1199	cmd->beacon_interval = cpu_to_le32(arg->bcn_intval);
 1200	cmd->bcn_tx_rate = cpu_to_le32(arg->bcn_tx_rate);
 1201	cmd->dtim_period = cpu_to_le32(arg->dtim_period);
 1202	cmd->num_noa_descriptors = cpu_to_le32(arg->num_noa_descriptors);
 1203	cmd->preferred_rx_streams = cpu_to_le32(arg->pref_rx_streams);
 1204	cmd->preferred_tx_streams = cpu_to_le32(arg->pref_tx_streams);
 1205	cmd->cac_duration_ms = cpu_to_le32(arg->cac_duration_ms);
 1206	cmd->regdomain = cpu_to_le32(arg->regdomain);
 1207	cmd->he_ops = cpu_to_le32(arg->he_ops);
 1208	cmd->punct_bitmap = cpu_to_le32(arg->punct_bitmap);
 1209	cmd->mbssid_flags = cpu_to_le32(arg->mbssid_flags);
 1210	cmd->mbssid_tx_vdev_id = cpu_to_le32(arg->mbssid_tx_vdev_id);
 1211
 1212	if (!restart) {
 1213		if (arg->ssid) {
 1214			cmd->ssid.ssid_len = cpu_to_le32(arg->ssid_len);
 1215			memcpy(cmd->ssid.ssid, arg->ssid, arg->ssid_len);
 1216		}
 1217		if (arg->hidden_ssid)
 1218			cmd->flags |= cpu_to_le32(WMI_VDEV_START_HIDDEN_SSID);
 1219		if (arg->pmf_enabled)
 1220			cmd->flags |= cpu_to_le32(WMI_VDEV_START_PMF_ENABLED);
 1221	}
 1222
 1223	cmd->flags |= cpu_to_le32(WMI_VDEV_START_LDPC_RX_ENABLED);
 1224
 1225	ptr = skb->data + sizeof(*cmd);
 1226	chan = ptr;
 1227
 1228	ath12k_wmi_put_wmi_channel(chan, arg);
 1229
 1230	chan->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_CHANNEL,
 1231						  sizeof(*chan));
 1232	ptr += sizeof(*chan);
 1233
 1234	tlv = ptr;
 1235	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, 0);
 1236
 1237	/* Note: This is a nested TLV containing:
 1238	 * [wmi_tlv][ath12k_wmi_p2p_noa_descriptor][wmi_tlv]..
 1239	 */
 1240
 1241	ptr += sizeof(*tlv);
 1242
 1243	if (ml_arg_size) {
 1244		tlv = ptr;
 1245		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
 1246						 sizeof(*ml_params));
 1247		ptr += TLV_HDR_SIZE;
 1248
 1249		ml_params = ptr;
 1250
 1251		ml_params->tlv_header =
 1252			ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_VDEV_START_PARAMS,
 1253					       sizeof(*ml_params));
 1254
 1255		ml_params->flags = le32_encode_bits(arg->ml.enabled,
 1256						    ATH12K_WMI_FLAG_MLO_ENABLED) |
 1257				   le32_encode_bits(arg->ml.assoc_link,
 1258						    ATH12K_WMI_FLAG_MLO_ASSOC_LINK) |
 1259				   le32_encode_bits(arg->ml.mcast_link,
 1260						    ATH12K_WMI_FLAG_MLO_MCAST_VDEV) |
 1261				   le32_encode_bits(arg->ml.link_add,
 1262						    ATH12K_WMI_FLAG_MLO_LINK_ADD);
 1263
 1264		ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "vdev %d start ml flags 0x%x\n",
 1265			   arg->vdev_id, ml_params->flags);
 1266
 1267		ptr += sizeof(*ml_params);
 1268
 1269		tlv = ptr;
 1270		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
 1271						 arg->ml.num_partner_links *
 1272						 sizeof(*partner_info));
 1273		ptr += TLV_HDR_SIZE;
 1274
 1275		partner_info = ptr;
 1276
 1277		for (i = 0; i < arg->ml.num_partner_links; i++) {
 1278			partner_info->tlv_header =
 1279				ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_PARTNER_LINK_PARAMS,
 1280						       sizeof(*partner_info));
 1281			partner_info->vdev_id =
 1282				cpu_to_le32(arg->ml.partner_info[i].vdev_id);
 1283			partner_info->hw_link_id =
 1284				cpu_to_le32(arg->ml.partner_info[i].hw_link_id);
 1285			ether_addr_copy(partner_info->vdev_addr.addr,
 1286					arg->ml.partner_info[i].addr);
 1287
 1288			ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "partner vdev %d hw_link_id %d macaddr%pM\n",
 1289				   partner_info->vdev_id, partner_info->hw_link_id,
 1290				   partner_info->vdev_addr.addr);
 1291
 1292			partner_info++;
 1293		}
 1294
 1295		ptr = partner_info;
 1296	}
 1297
 1298	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "vdev %s id 0x%x freq 0x%x mode 0x%x\n",
 1299		   restart ? "restart" : "start", arg->vdev_id,
 1300		   arg->freq, arg->mode);
 1301
 1302	if (restart)
 1303		ret = ath12k_wmi_cmd_send(wmi, skb,
 1304					  WMI_VDEV_RESTART_REQUEST_CMDID);
 1305	else
 1306		ret = ath12k_wmi_cmd_send(wmi, skb,
 1307					  WMI_VDEV_START_REQUEST_CMDID);
 1308	if (ret) {
 1309		ath12k_warn(ar->ab, "failed to submit vdev_%s cmd\n",
 1310			    restart ? "restart" : "start");
 1311		dev_kfree_skb(skb);
 1312	}
 1313
 1314	return ret;
 1315}
 1316
 1317int ath12k_wmi_vdev_up(struct ath12k *ar, struct ath12k_wmi_vdev_up_params *params)
 1318{
 1319	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1320	struct wmi_vdev_up_cmd *cmd;
 1321	struct sk_buff *skb;
 1322	int ret;
 1323
 1324	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1325	if (!skb)
 1326		return -ENOMEM;
 1327
 1328	cmd = (struct wmi_vdev_up_cmd *)skb->data;
 1329
 1330	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_UP_CMD,
 1331						 sizeof(*cmd));
 1332	cmd->vdev_id = cpu_to_le32(params->vdev_id);
 1333	cmd->vdev_assoc_id = cpu_to_le32(params->aid);
 1334
 1335	ether_addr_copy(cmd->vdev_bssid.addr, params->bssid);
 1336
 1337	if (params->tx_bssid) {
 1338		ether_addr_copy(cmd->tx_vdev_bssid.addr, params->tx_bssid);
 1339		cmd->nontx_profile_idx = cpu_to_le32(params->nontx_profile_idx);
 1340		cmd->nontx_profile_cnt = cpu_to_le32(params->nontx_profile_cnt);
 1341	}
 1342
 1343	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1344		   "WMI mgmt vdev up id 0x%x assoc id %d bssid %pM\n",
 1345		   params->vdev_id, params->aid, params->bssid);
 1346
 1347	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_VDEV_UP_CMDID);
 1348	if (ret) {
 1349		ath12k_warn(ar->ab, "failed to submit WMI_VDEV_UP cmd\n");
 1350		dev_kfree_skb(skb);
 1351	}
 1352
 1353	return ret;
 1354}
 1355
 1356int ath12k_wmi_send_peer_create_cmd(struct ath12k *ar,
 1357				    struct ath12k_wmi_peer_create_arg *arg)
 1358{
 1359	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1360	struct wmi_peer_create_cmd *cmd;
 1361	struct sk_buff *skb;
 1362	int ret, len;
 1363	struct wmi_peer_create_mlo_params *ml_param;
 1364	void *ptr;
 1365	struct wmi_tlv *tlv;
 1366
 1367	len = sizeof(*cmd) + TLV_HDR_SIZE + sizeof(*ml_param);
 1368
 1369	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 1370	if (!skb)
 1371		return -ENOMEM;
 1372
 1373	cmd = (struct wmi_peer_create_cmd *)skb->data;
 1374	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PEER_CREATE_CMD,
 1375						 sizeof(*cmd));
 1376
 1377	ether_addr_copy(cmd->peer_macaddr.addr, arg->peer_addr);
 1378	cmd->peer_type = cpu_to_le32(arg->peer_type);
 1379	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 1380
 1381	ptr = skb->data + sizeof(*cmd);
 1382	tlv = ptr;
 1383	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
 1384					 sizeof(*ml_param));
 1385	ptr += TLV_HDR_SIZE;
 1386	ml_param = ptr;
 1387	ml_param->tlv_header =
 1388			ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_PEER_CREATE_PARAMS,
 1389					       sizeof(*ml_param));
 1390	if (arg->ml_enabled)
 1391		ml_param->flags = cpu_to_le32(ATH12K_WMI_FLAG_MLO_ENABLED);
 1392
 1393	ptr += sizeof(*ml_param);
 1394
 1395	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1396		   "WMI peer create vdev_id %d peer_addr %pM ml_flags 0x%x\n",
 1397		   arg->vdev_id, arg->peer_addr, ml_param->flags);
 1398
 1399	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PEER_CREATE_CMDID);
 1400	if (ret) {
 1401		ath12k_warn(ar->ab, "failed to submit WMI_PEER_CREATE cmd\n");
 1402		dev_kfree_skb(skb);
 1403	}
 1404
 1405	return ret;
 1406}
 1407
 1408int ath12k_wmi_send_peer_delete_cmd(struct ath12k *ar,
 1409				    const u8 *peer_addr, u8 vdev_id)
 1410{
 1411	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1412	struct wmi_peer_delete_cmd *cmd;
 1413	struct sk_buff *skb;
 1414	int ret;
 1415
 1416	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1417	if (!skb)
 1418		return -ENOMEM;
 1419
 1420	cmd = (struct wmi_peer_delete_cmd *)skb->data;
 1421	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PEER_DELETE_CMD,
 1422						 sizeof(*cmd));
 1423
 1424	ether_addr_copy(cmd->peer_macaddr.addr, peer_addr);
 1425	cmd->vdev_id = cpu_to_le32(vdev_id);
 1426
 1427	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1428		   "WMI peer delete vdev_id %d peer_addr %pM\n",
 1429		   vdev_id,  peer_addr);
 1430
 1431	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PEER_DELETE_CMDID);
 1432	if (ret) {
 1433		ath12k_warn(ar->ab, "failed to send WMI_PEER_DELETE cmd\n");
 1434		dev_kfree_skb(skb);
 1435	}
 1436
 1437	return ret;
 1438}
 1439
 1440int ath12k_wmi_send_pdev_set_regdomain(struct ath12k *ar,
 1441				       struct ath12k_wmi_pdev_set_regdomain_arg *arg)
 1442{
 1443	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1444	struct wmi_pdev_set_regdomain_cmd *cmd;
 1445	struct sk_buff *skb;
 1446	int ret;
 1447
 1448	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1449	if (!skb)
 1450		return -ENOMEM;
 1451
 1452	cmd = (struct wmi_pdev_set_regdomain_cmd *)skb->data;
 1453	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_SET_REGDOMAIN_CMD,
 1454						 sizeof(*cmd));
 1455
 1456	cmd->reg_domain = cpu_to_le32(arg->current_rd_in_use);
 1457	cmd->reg_domain_2g = cpu_to_le32(arg->current_rd_2g);
 1458	cmd->reg_domain_5g = cpu_to_le32(arg->current_rd_5g);
 1459	cmd->conformance_test_limit_2g = cpu_to_le32(arg->ctl_2g);
 1460	cmd->conformance_test_limit_5g = cpu_to_le32(arg->ctl_5g);
 1461	cmd->dfs_domain = cpu_to_le32(arg->dfs_domain);
 1462	cmd->pdev_id = cpu_to_le32(arg->pdev_id);
 1463
 1464	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1465		   "WMI pdev regd rd %d rd2g %d rd5g %d domain %d pdev id %d\n",
 1466		   arg->current_rd_in_use, arg->current_rd_2g,
 1467		   arg->current_rd_5g, arg->dfs_domain, arg->pdev_id);
 1468
 1469	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PDEV_SET_REGDOMAIN_CMDID);
 1470	if (ret) {
 1471		ath12k_warn(ar->ab,
 1472			    "failed to send WMI_PDEV_SET_REGDOMAIN cmd\n");
 1473		dev_kfree_skb(skb);
 1474	}
 1475
 1476	return ret;
 1477}
 1478
 1479int ath12k_wmi_set_peer_param(struct ath12k *ar, const u8 *peer_addr,
 1480			      u32 vdev_id, u32 param_id, u32 param_val)
 1481{
 1482	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1483	struct wmi_peer_set_param_cmd *cmd;
 1484	struct sk_buff *skb;
 1485	int ret;
 1486
 1487	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1488	if (!skb)
 1489		return -ENOMEM;
 1490
 1491	cmd = (struct wmi_peer_set_param_cmd *)skb->data;
 1492	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PEER_SET_PARAM_CMD,
 1493						 sizeof(*cmd));
 1494	ether_addr_copy(cmd->peer_macaddr.addr, peer_addr);
 1495	cmd->vdev_id = cpu_to_le32(vdev_id);
 1496	cmd->param_id = cpu_to_le32(param_id);
 1497	cmd->param_value = cpu_to_le32(param_val);
 1498
 1499	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1500		   "WMI vdev %d peer 0x%pM set param %d value %d\n",
 1501		   vdev_id, peer_addr, param_id, param_val);
 1502
 1503	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PEER_SET_PARAM_CMDID);
 1504	if (ret) {
 1505		ath12k_warn(ar->ab, "failed to send WMI_PEER_SET_PARAM cmd\n");
 1506		dev_kfree_skb(skb);
 1507	}
 1508
 1509	return ret;
 1510}
 1511
 1512int ath12k_wmi_send_peer_flush_tids_cmd(struct ath12k *ar,
 1513					u8 peer_addr[ETH_ALEN],
 1514					u32 peer_tid_bitmap,
 1515					u8 vdev_id)
 1516{
 1517	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1518	struct wmi_peer_flush_tids_cmd *cmd;
 1519	struct sk_buff *skb;
 1520	int ret;
 1521
 1522	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1523	if (!skb)
 1524		return -ENOMEM;
 1525
 1526	cmd = (struct wmi_peer_flush_tids_cmd *)skb->data;
 1527	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PEER_FLUSH_TIDS_CMD,
 1528						 sizeof(*cmd));
 1529
 1530	ether_addr_copy(cmd->peer_macaddr.addr, peer_addr);
 1531	cmd->peer_tid_bitmap = cpu_to_le32(peer_tid_bitmap);
 1532	cmd->vdev_id = cpu_to_le32(vdev_id);
 1533
 1534	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1535		   "WMI peer flush vdev_id %d peer_addr %pM tids %08x\n",
 1536		   vdev_id, peer_addr, peer_tid_bitmap);
 1537
 1538	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PEER_FLUSH_TIDS_CMDID);
 1539	if (ret) {
 1540		ath12k_warn(ar->ab,
 1541			    "failed to send WMI_PEER_FLUSH_TIDS cmd\n");
 1542		dev_kfree_skb(skb);
 1543	}
 1544
 1545	return ret;
 1546}
 1547
 1548int ath12k_wmi_peer_rx_reorder_queue_setup(struct ath12k *ar,
 1549					   int vdev_id, const u8 *addr,
 1550					   dma_addr_t paddr, u8 tid,
 1551					   u8 ba_window_size_valid,
 1552					   u32 ba_window_size)
 1553{
 1554	struct wmi_peer_reorder_queue_setup_cmd *cmd;
 1555	struct sk_buff *skb;
 1556	int ret;
 1557
 1558	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd));
 1559	if (!skb)
 1560		return -ENOMEM;
 1561
 1562	cmd = (struct wmi_peer_reorder_queue_setup_cmd *)skb->data;
 1563	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_REORDER_QUEUE_SETUP_CMD,
 1564						 sizeof(*cmd));
 1565
 1566	ether_addr_copy(cmd->peer_macaddr.addr, addr);
 1567	cmd->vdev_id = cpu_to_le32(vdev_id);
 1568	cmd->tid = cpu_to_le32(tid);
 1569	cmd->queue_ptr_lo = cpu_to_le32(lower_32_bits(paddr));
 1570	cmd->queue_ptr_hi = cpu_to_le32(upper_32_bits(paddr));
 1571	cmd->queue_no = cpu_to_le32(tid);
 1572	cmd->ba_window_size_valid = cpu_to_le32(ba_window_size_valid);
 1573	cmd->ba_window_size = cpu_to_le32(ba_window_size);
 1574
 1575	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1576		   "wmi rx reorder queue setup addr %pM vdev_id %d tid %d\n",
 1577		   addr, vdev_id, tid);
 1578
 1579	ret = ath12k_wmi_cmd_send(ar->wmi, skb,
 1580				  WMI_PEER_REORDER_QUEUE_SETUP_CMDID);
 1581	if (ret) {
 1582		ath12k_warn(ar->ab,
 1583			    "failed to send WMI_PEER_REORDER_QUEUE_SETUP\n");
 1584		dev_kfree_skb(skb);
 1585	}
 1586
 1587	return ret;
 1588}
 1589
 1590int
 1591ath12k_wmi_rx_reord_queue_remove(struct ath12k *ar,
 1592				 struct ath12k_wmi_rx_reorder_queue_remove_arg *arg)
 1593{
 1594	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1595	struct wmi_peer_reorder_queue_remove_cmd *cmd;
 1596	struct sk_buff *skb;
 1597	int ret;
 1598
 1599	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1600	if (!skb)
 1601		return -ENOMEM;
 1602
 1603	cmd = (struct wmi_peer_reorder_queue_remove_cmd *)skb->data;
 1604	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_REORDER_QUEUE_REMOVE_CMD,
 1605						 sizeof(*cmd));
 1606
 1607	ether_addr_copy(cmd->peer_macaddr.addr, arg->peer_macaddr);
 1608	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 1609	cmd->tid_mask = cpu_to_le32(arg->peer_tid_bitmap);
 1610
 1611	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1612		   "%s: peer_macaddr %pM vdev_id %d, tid_map %d", __func__,
 1613		   arg->peer_macaddr, arg->vdev_id, arg->peer_tid_bitmap);
 1614
 1615	ret = ath12k_wmi_cmd_send(wmi, skb,
 1616				  WMI_PEER_REORDER_QUEUE_REMOVE_CMDID);
 1617	if (ret) {
 1618		ath12k_warn(ar->ab,
 1619			    "failed to send WMI_PEER_REORDER_QUEUE_REMOVE_CMDID");
 1620		dev_kfree_skb(skb);
 1621	}
 1622
 1623	return ret;
 1624}
 1625
 1626int ath12k_wmi_pdev_set_param(struct ath12k *ar, u32 param_id,
 1627			      u32 param_value, u8 pdev_id)
 1628{
 1629	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1630	struct wmi_pdev_set_param_cmd *cmd;
 1631	struct sk_buff *skb;
 1632	int ret;
 1633
 1634	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1635	if (!skb)
 1636		return -ENOMEM;
 1637
 1638	cmd = (struct wmi_pdev_set_param_cmd *)skb->data;
 1639	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_SET_PARAM_CMD,
 1640						 sizeof(*cmd));
 1641	cmd->pdev_id = cpu_to_le32(pdev_id);
 1642	cmd->param_id = cpu_to_le32(param_id);
 1643	cmd->param_value = cpu_to_le32(param_value);
 1644
 1645	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1646		   "WMI pdev set param %d pdev id %d value %d\n",
 1647		   param_id, pdev_id, param_value);
 1648
 1649	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PDEV_SET_PARAM_CMDID);
 1650	if (ret) {
 1651		ath12k_warn(ar->ab, "failed to send WMI_PDEV_SET_PARAM cmd\n");
 1652		dev_kfree_skb(skb);
 1653	}
 1654
 1655	return ret;
 1656}
 1657
 1658int ath12k_wmi_pdev_set_ps_mode(struct ath12k *ar, int vdev_id, u32 enable)
 1659{
 1660	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1661	struct wmi_pdev_set_ps_mode_cmd *cmd;
 1662	struct sk_buff *skb;
 1663	int ret;
 1664
 1665	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1666	if (!skb)
 1667		return -ENOMEM;
 1668
 1669	cmd = (struct wmi_pdev_set_ps_mode_cmd *)skb->data;
 1670	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_STA_POWERSAVE_MODE_CMD,
 1671						 sizeof(*cmd));
 1672	cmd->vdev_id = cpu_to_le32(vdev_id);
 1673	cmd->sta_ps_mode = cpu_to_le32(enable);
 1674
 1675	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1676		   "WMI vdev set psmode %d vdev id %d\n",
 1677		   enable, vdev_id);
 1678
 1679	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_STA_POWERSAVE_MODE_CMDID);
 1680	if (ret) {
 1681		ath12k_warn(ar->ab, "failed to send WMI_PDEV_SET_PARAM cmd\n");
 1682		dev_kfree_skb(skb);
 1683	}
 1684
 1685	return ret;
 1686}
 1687
 1688int ath12k_wmi_pdev_suspend(struct ath12k *ar, u32 suspend_opt,
 1689			    u32 pdev_id)
 1690{
 1691	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1692	struct wmi_pdev_suspend_cmd *cmd;
 1693	struct sk_buff *skb;
 1694	int ret;
 1695
 1696	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1697	if (!skb)
 1698		return -ENOMEM;
 1699
 1700	cmd = (struct wmi_pdev_suspend_cmd *)skb->data;
 1701
 1702	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_SUSPEND_CMD,
 1703						 sizeof(*cmd));
 1704
 1705	cmd->suspend_opt = cpu_to_le32(suspend_opt);
 1706	cmd->pdev_id = cpu_to_le32(pdev_id);
 1707
 1708	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1709		   "WMI pdev suspend pdev_id %d\n", pdev_id);
 1710
 1711	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PDEV_SUSPEND_CMDID);
 1712	if (ret) {
 1713		ath12k_warn(ar->ab, "failed to send WMI_PDEV_SUSPEND cmd\n");
 1714		dev_kfree_skb(skb);
 1715	}
 1716
 1717	return ret;
 1718}
 1719
 1720int ath12k_wmi_pdev_resume(struct ath12k *ar, u32 pdev_id)
 1721{
 1722	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1723	struct wmi_pdev_resume_cmd *cmd;
 1724	struct sk_buff *skb;
 1725	int ret;
 1726
 1727	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1728	if (!skb)
 1729		return -ENOMEM;
 1730
 1731	cmd = (struct wmi_pdev_resume_cmd *)skb->data;
 1732
 1733	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_RESUME_CMD,
 1734						 sizeof(*cmd));
 1735	cmd->pdev_id = cpu_to_le32(pdev_id);
 1736
 1737	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1738		   "WMI pdev resume pdev id %d\n", pdev_id);
 1739
 1740	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PDEV_RESUME_CMDID);
 1741	if (ret) {
 1742		ath12k_warn(ar->ab, "failed to send WMI_PDEV_RESUME cmd\n");
 1743		dev_kfree_skb(skb);
 1744	}
 1745
 1746	return ret;
 1747}
 1748
 1749/* TODO FW Support for the cmd is not available yet.
 1750 * Can be tested once the command and corresponding
 1751 * event is implemented in FW
 1752 */
 1753int ath12k_wmi_pdev_bss_chan_info_request(struct ath12k *ar,
 1754					  enum wmi_bss_chan_info_req_type type)
 1755{
 1756	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1757	struct wmi_pdev_bss_chan_info_req_cmd *cmd;
 1758	struct sk_buff *skb;
 1759	int ret;
 1760
 1761	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1762	if (!skb)
 1763		return -ENOMEM;
 1764
 1765	cmd = (struct wmi_pdev_bss_chan_info_req_cmd *)skb->data;
 1766
 1767	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_BSS_CHAN_INFO_REQUEST,
 1768						 sizeof(*cmd));
 1769	cmd->req_type = cpu_to_le32(type);
 1770	cmd->pdev_id = cpu_to_le32(ar->pdev->pdev_id);
 1771
 1772	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1773		   "WMI bss chan info req type %d\n", type);
 1774
 1775	ret = ath12k_wmi_cmd_send(wmi, skb,
 1776				  WMI_PDEV_BSS_CHAN_INFO_REQUEST_CMDID);
 1777	if (ret) {
 1778		ath12k_warn(ar->ab,
 1779			    "failed to send WMI_PDEV_BSS_CHAN_INFO_REQUEST cmd\n");
 1780		dev_kfree_skb(skb);
 1781	}
 1782
 1783	return ret;
 1784}
 1785
 1786int ath12k_wmi_send_set_ap_ps_param_cmd(struct ath12k *ar, u8 *peer_addr,
 1787					struct ath12k_wmi_ap_ps_arg *arg)
 1788{
 1789	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1790	struct wmi_ap_ps_peer_cmd *cmd;
 1791	struct sk_buff *skb;
 1792	int ret;
 1793
 1794	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1795	if (!skb)
 1796		return -ENOMEM;
 1797
 1798	cmd = (struct wmi_ap_ps_peer_cmd *)skb->data;
 1799	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_AP_PS_PEER_CMD,
 1800						 sizeof(*cmd));
 1801
 1802	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 1803	ether_addr_copy(cmd->peer_macaddr.addr, peer_addr);
 1804	cmd->param = cpu_to_le32(arg->param);
 1805	cmd->value = cpu_to_le32(arg->value);
 1806
 1807	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1808		   "WMI set ap ps vdev id %d peer %pM param %d value %d\n",
 1809		   arg->vdev_id, peer_addr, arg->param, arg->value);
 1810
 1811	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_AP_PS_PEER_PARAM_CMDID);
 1812	if (ret) {
 1813		ath12k_warn(ar->ab,
 1814			    "failed to send WMI_AP_PS_PEER_PARAM_CMDID\n");
 1815		dev_kfree_skb(skb);
 1816	}
 1817
 1818	return ret;
 1819}
 1820
 1821int ath12k_wmi_set_sta_ps_param(struct ath12k *ar, u32 vdev_id,
 1822				u32 param, u32 param_value)
 1823{
 1824	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1825	struct wmi_sta_powersave_param_cmd *cmd;
 1826	struct sk_buff *skb;
 1827	int ret;
 1828
 1829	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1830	if (!skb)
 1831		return -ENOMEM;
 1832
 1833	cmd = (struct wmi_sta_powersave_param_cmd *)skb->data;
 1834	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_STA_POWERSAVE_PARAM_CMD,
 1835						 sizeof(*cmd));
 1836
 1837	cmd->vdev_id = cpu_to_le32(vdev_id);
 1838	cmd->param = cpu_to_le32(param);
 1839	cmd->value = cpu_to_le32(param_value);
 1840
 1841	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1842		   "WMI set sta ps vdev_id %d param %d value %d\n",
 1843		   vdev_id, param, param_value);
 1844
 1845	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_STA_POWERSAVE_PARAM_CMDID);
 1846	if (ret) {
 1847		ath12k_warn(ar->ab, "failed to send WMI_STA_POWERSAVE_PARAM_CMDID");
 1848		dev_kfree_skb(skb);
 1849	}
 1850
 1851	return ret;
 1852}
 1853
 1854int ath12k_wmi_force_fw_hang_cmd(struct ath12k *ar, u32 type, u32 delay_time_ms)
 1855{
 1856	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1857	struct wmi_force_fw_hang_cmd *cmd;
 1858	struct sk_buff *skb;
 1859	int ret, len;
 1860
 1861	len = sizeof(*cmd);
 1862
 1863	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 1864	if (!skb)
 1865		return -ENOMEM;
 1866
 1867	cmd = (struct wmi_force_fw_hang_cmd *)skb->data;
 1868	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_FORCE_FW_HANG_CMD,
 1869						 len);
 1870
 1871	cmd->type = cpu_to_le32(type);
 1872	cmd->delay_time_ms = cpu_to_le32(delay_time_ms);
 1873
 1874	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_FORCE_FW_HANG_CMDID);
 1875
 1876	if (ret) {
 1877		ath12k_warn(ar->ab, "Failed to send WMI_FORCE_FW_HANG_CMDID");
 1878		dev_kfree_skb(skb);
 1879	}
 1880	return ret;
 1881}
 1882
 1883int ath12k_wmi_vdev_set_param_cmd(struct ath12k *ar, u32 vdev_id,
 1884				  u32 param_id, u32 param_value)
 1885{
 1886	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1887	struct wmi_vdev_set_param_cmd *cmd;
 1888	struct sk_buff *skb;
 1889	int ret;
 1890
 1891	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1892	if (!skb)
 1893		return -ENOMEM;
 1894
 1895	cmd = (struct wmi_vdev_set_param_cmd *)skb->data;
 1896	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_SET_PARAM_CMD,
 1897						 sizeof(*cmd));
 1898
 1899	cmd->vdev_id = cpu_to_le32(vdev_id);
 1900	cmd->param_id = cpu_to_le32(param_id);
 1901	cmd->param_value = cpu_to_le32(param_value);
 1902
 1903	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1904		   "WMI vdev id 0x%x set param %d value %d\n",
 1905		   vdev_id, param_id, param_value);
 1906
 1907	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_VDEV_SET_PARAM_CMDID);
 1908	if (ret) {
 1909		ath12k_warn(ar->ab,
 1910			    "failed to send WMI_VDEV_SET_PARAM_CMDID\n");
 1911		dev_kfree_skb(skb);
 1912	}
 1913
 1914	return ret;
 1915}
 1916
 1917int ath12k_wmi_send_pdev_temperature_cmd(struct ath12k *ar)
 1918{
 1919	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1920	struct wmi_get_pdev_temperature_cmd *cmd;
 1921	struct sk_buff *skb;
 1922	int ret;
 1923
 1924	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1925	if (!skb)
 1926		return -ENOMEM;
 1927
 1928	cmd = (struct wmi_get_pdev_temperature_cmd *)skb->data;
 1929	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_GET_TEMPERATURE_CMD,
 1930						 sizeof(*cmd));
 1931	cmd->pdev_id = cpu_to_le32(ar->pdev->pdev_id);
 1932
 1933	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1934		   "WMI pdev get temperature for pdev_id %d\n", ar->pdev->pdev_id);
 1935
 1936	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PDEV_GET_TEMPERATURE_CMDID);
 1937	if (ret) {
 1938		ath12k_warn(ar->ab, "failed to send WMI_PDEV_GET_TEMPERATURE cmd\n");
 1939		dev_kfree_skb(skb);
 1940	}
 1941
 1942	return ret;
 1943}
 1944
 1945int ath12k_wmi_send_bcn_offload_control_cmd(struct ath12k *ar,
 1946					    u32 vdev_id, u32 bcn_ctrl_op)
 1947{
 1948	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1949	struct wmi_bcn_offload_ctrl_cmd *cmd;
 1950	struct sk_buff *skb;
 1951	int ret;
 1952
 1953	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 1954	if (!skb)
 1955		return -ENOMEM;
 1956
 1957	cmd = (struct wmi_bcn_offload_ctrl_cmd *)skb->data;
 1958	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_BCN_OFFLOAD_CTRL_CMD,
 1959						 sizeof(*cmd));
 1960
 1961	cmd->vdev_id = cpu_to_le32(vdev_id);
 1962	cmd->bcn_ctrl_op = cpu_to_le32(bcn_ctrl_op);
 1963
 1964	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 1965		   "WMI bcn ctrl offload vdev id %d ctrl_op %d\n",
 1966		   vdev_id, bcn_ctrl_op);
 1967
 1968	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_BCN_OFFLOAD_CTRL_CMDID);
 1969	if (ret) {
 1970		ath12k_warn(ar->ab,
 1971			    "failed to send WMI_BCN_OFFLOAD_CTRL_CMDID\n");
 1972		dev_kfree_skb(skb);
 1973	}
 1974
 1975	return ret;
 1976}
 1977
 1978int ath12k_wmi_p2p_go_bcn_ie(struct ath12k *ar, u32 vdev_id,
 1979			     const u8 *p2p_ie)
 1980{
 1981	struct ath12k_wmi_pdev *wmi = ar->wmi;
 1982	struct wmi_p2p_go_set_beacon_ie_cmd *cmd;
 1983	size_t p2p_ie_len, aligned_len;
 1984	struct wmi_tlv *tlv;
 1985	struct sk_buff *skb;
 1986	void *ptr;
 1987	int ret, len;
 1988
 1989	p2p_ie_len = p2p_ie[1] + 2;
 1990	aligned_len = roundup(p2p_ie_len, sizeof(u32));
 1991
 1992	len = sizeof(*cmd) + TLV_HDR_SIZE + aligned_len;
 1993
 1994	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 1995	if (!skb)
 1996		return -ENOMEM;
 1997
 1998	ptr = skb->data;
 1999	cmd = ptr;
 2000	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_P2P_GO_SET_BEACON_IE,
 2001						 sizeof(*cmd));
 2002	cmd->vdev_id = cpu_to_le32(vdev_id);
 2003	cmd->ie_buf_len = cpu_to_le32(p2p_ie_len);
 2004
 2005	ptr += sizeof(*cmd);
 2006	tlv = ptr;
 2007	tlv->header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_ARRAY_BYTE,
 2008					     aligned_len);
 2009	memcpy(tlv->value, p2p_ie, p2p_ie_len);
 2010
 2011	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_P2P_GO_SET_BEACON_IE);
 2012	if (ret) {
 2013		ath12k_warn(ar->ab, "failed to send WMI_P2P_GO_SET_BEACON_IE\n");
 2014		dev_kfree_skb(skb);
 2015	}
 2016
 2017	return ret;
 2018}
 2019
 2020int ath12k_wmi_bcn_tmpl(struct ath12k_link_vif *arvif,
 2021			struct ieee80211_mutable_offsets *offs,
 2022			struct sk_buff *bcn,
 2023			struct ath12k_wmi_bcn_tmpl_ema_arg *ema_args)
 2024{
 2025	struct ath12k *ar = arvif->ar;
 2026	struct ath12k_wmi_pdev *wmi = ar->wmi;
 2027	struct ath12k_base *ab = ar->ab;
 2028	struct wmi_bcn_tmpl_cmd *cmd;
 2029	struct ath12k_wmi_bcn_prb_info_params *bcn_prb_info;
 2030	struct ath12k_vif *ahvif = arvif->ahvif;
 2031	struct ieee80211_bss_conf *conf;
 2032	u32 vdev_id = arvif->vdev_id;
 2033	struct wmi_tlv *tlv;
 2034	struct sk_buff *skb;
 2035	u32 ema_params = 0;
 2036	void *ptr;
 2037	int ret, len;
 2038	size_t aligned_len = roundup(bcn->len, 4);
 2039
 2040	conf = ath12k_mac_get_link_bss_conf(arvif);
 2041	if (!conf) {
 2042		ath12k_warn(ab,
 2043			    "unable to access bss link conf in beacon template command for vif %pM link %u\n",
 2044			    ahvif->vif->addr, arvif->link_id);
 2045		return -EINVAL;
 2046	}
 2047
 2048	len = sizeof(*cmd) + sizeof(*bcn_prb_info) + TLV_HDR_SIZE + aligned_len;
 2049
 2050	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 2051	if (!skb)
 2052		return -ENOMEM;
 2053
 2054	cmd = (struct wmi_bcn_tmpl_cmd *)skb->data;
 2055	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_BCN_TMPL_CMD,
 2056						 sizeof(*cmd));
 2057	cmd->vdev_id = cpu_to_le32(vdev_id);
 2058	cmd->tim_ie_offset = cpu_to_le32(offs->tim_offset);
 2059
 2060	if (conf->csa_active) {
 2061		cmd->csa_switch_count_offset =
 2062				cpu_to_le32(offs->cntdwn_counter_offs[0]);
 2063		cmd->ext_csa_switch_count_offset =
 2064				cpu_to_le32(offs->cntdwn_counter_offs[1]);
 2065		cmd->csa_event_bitmap = cpu_to_le32(0xFFFFFFFF);
 2066		arvif->current_cntdown_counter = bcn->data[offs->cntdwn_counter_offs[0]];
 2067	}
 2068
 2069	cmd->buf_len = cpu_to_le32(bcn->len);
 2070	cmd->mbssid_ie_offset = cpu_to_le32(offs->mbssid_off);
 2071	if (ema_args) {
 2072		u32p_replace_bits(&ema_params, ema_args->bcn_cnt, WMI_EMA_BEACON_CNT);
 2073		u32p_replace_bits(&ema_params, ema_args->bcn_index, WMI_EMA_BEACON_IDX);
 2074		if (ema_args->bcn_index == 0)
 2075			u32p_replace_bits(&ema_params, 1, WMI_EMA_BEACON_FIRST);
 2076		if (ema_args->bcn_index + 1 == ema_args->bcn_cnt)
 2077			u32p_replace_bits(&ema_params, 1, WMI_EMA_BEACON_LAST);
 2078		cmd->ema_params = cpu_to_le32(ema_params);
 2079	}
 2080	cmd->feature_enable_bitmap =
 2081		cpu_to_le32(u32_encode_bits(arvif->beacon_prot,
 2082					    WMI_BEACON_PROTECTION_EN_BIT));
 2083
 2084	ptr = skb->data + sizeof(*cmd);
 2085
 2086	bcn_prb_info = ptr;
 2087	len = sizeof(*bcn_prb_info);
 2088	bcn_prb_info->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_BCN_PRB_INFO,
 2089							  len);
 2090	bcn_prb_info->caps = 0;
 2091	bcn_prb_info->erp = 0;
 2092
 2093	ptr += sizeof(*bcn_prb_info);
 2094
 2095	tlv = ptr;
 2096	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, aligned_len);
 2097	memcpy(tlv->value, bcn->data, bcn->len);
 2098
 2099	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_BCN_TMPL_CMDID);
 2100	if (ret) {
 2101		ath12k_warn(ab, "failed to send WMI_BCN_TMPL_CMDID\n");
 2102		dev_kfree_skb(skb);
 2103	}
 2104
 2105	return ret;
 2106}
 2107
 2108int ath12k_wmi_vdev_install_key(struct ath12k *ar,
 2109				struct wmi_vdev_install_key_arg *arg)
 2110{
 2111	struct ath12k_wmi_pdev *wmi = ar->wmi;
 2112	struct wmi_vdev_install_key_cmd *cmd;
 2113	struct wmi_tlv *tlv;
 2114	struct sk_buff *skb;
 2115	int ret, len, key_len_aligned;
 2116
 2117	/* WMI_TAG_ARRAY_BYTE needs to be aligned with 4, the actual key
 2118	 * length is specified in cmd->key_len.
 2119	 */
 2120	key_len_aligned = roundup(arg->key_len, 4);
 2121
 2122	len = sizeof(*cmd) + TLV_HDR_SIZE + key_len_aligned;
 2123
 2124	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 2125	if (!skb)
 2126		return -ENOMEM;
 2127
 2128	cmd = (struct wmi_vdev_install_key_cmd *)skb->data;
 2129	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_INSTALL_KEY_CMD,
 2130						 sizeof(*cmd));
 2131	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 2132	ether_addr_copy(cmd->peer_macaddr.addr, arg->macaddr);
 2133	cmd->key_idx = cpu_to_le32(arg->key_idx);
 2134	cmd->key_flags = cpu_to_le32(arg->key_flags);
 2135	cmd->key_cipher = cpu_to_le32(arg->key_cipher);
 2136	cmd->key_len = cpu_to_le32(arg->key_len);
 2137	cmd->key_txmic_len = cpu_to_le32(arg->key_txmic_len);
 2138	cmd->key_rxmic_len = cpu_to_le32(arg->key_rxmic_len);
 2139
 2140	if (arg->key_rsc_counter)
 2141		cmd->key_rsc_counter = cpu_to_le64(arg->key_rsc_counter);
 2142
 2143	tlv = (struct wmi_tlv *)(skb->data + sizeof(*cmd));
 2144	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, key_len_aligned);
 2145	memcpy(tlv->value, arg->key_data, arg->key_len);
 2146
 2147	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 2148		   "WMI vdev install key idx %d cipher %d len %d\n",
 2149		   arg->key_idx, arg->key_cipher, arg->key_len);
 2150
 2151	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_VDEV_INSTALL_KEY_CMDID);
 2152	if (ret) {
 2153		ath12k_warn(ar->ab,
 2154			    "failed to send WMI_VDEV_INSTALL_KEY cmd\n");
 2155		dev_kfree_skb(skb);
 2156	}
 2157
 2158	return ret;
 2159}
 2160
 2161static void ath12k_wmi_copy_peer_flags(struct wmi_peer_assoc_complete_cmd *cmd,
 2162				       struct ath12k_wmi_peer_assoc_arg *arg,
 2163				       bool hw_crypto_disabled)
 2164{
 2165	cmd->peer_flags = 0;
 2166	cmd->peer_flags_ext = 0;
 2167
 2168	if (arg->is_wme_set) {
 2169		if (arg->qos_flag)
 2170			cmd->peer_flags |= cpu_to_le32(WMI_PEER_QOS);
 2171		if (arg->apsd_flag)
 2172			cmd->peer_flags |= cpu_to_le32(WMI_PEER_APSD);
 2173		if (arg->ht_flag)
 2174			cmd->peer_flags |= cpu_to_le32(WMI_PEER_HT);
 2175		if (arg->bw_40)
 2176			cmd->peer_flags |= cpu_to_le32(WMI_PEER_40MHZ);
 2177		if (arg->bw_80)
 2178			cmd->peer_flags |= cpu_to_le32(WMI_PEER_80MHZ);
 2179		if (arg->bw_160)
 2180			cmd->peer_flags |= cpu_to_le32(WMI_PEER_160MHZ);
 2181		if (arg->bw_320)
 2182			cmd->peer_flags_ext |= cpu_to_le32(WMI_PEER_EXT_320MHZ);
 2183
 2184		/* Typically if STBC is enabled for VHT it should be enabled
 2185		 * for HT as well
 2186		 **/
 2187		if (arg->stbc_flag)
 2188			cmd->peer_flags |= cpu_to_le32(WMI_PEER_STBC);
 2189
 2190		/* Typically if LDPC is enabled for VHT it should be enabled
 2191		 * for HT as well
 2192		 **/
 2193		if (arg->ldpc_flag)
 2194			cmd->peer_flags |= cpu_to_le32(WMI_PEER_LDPC);
 2195
 2196		if (arg->static_mimops_flag)
 2197			cmd->peer_flags |= cpu_to_le32(WMI_PEER_STATIC_MIMOPS);
 2198		if (arg->dynamic_mimops_flag)
 2199			cmd->peer_flags |= cpu_to_le32(WMI_PEER_DYN_MIMOPS);
 2200		if (arg->spatial_mux_flag)
 2201			cmd->peer_flags |= cpu_to_le32(WMI_PEER_SPATIAL_MUX);
 2202		if (arg->vht_flag)
 2203			cmd->peer_flags |= cpu_to_le32(WMI_PEER_VHT);
 2204		if (arg->he_flag)
 2205			cmd->peer_flags |= cpu_to_le32(WMI_PEER_HE);
 2206		if (arg->twt_requester)
 2207			cmd->peer_flags |= cpu_to_le32(WMI_PEER_TWT_REQ);
 2208		if (arg->twt_responder)
 2209			cmd->peer_flags |= cpu_to_le32(WMI_PEER_TWT_RESP);
 2210		if (arg->eht_flag)
 2211			cmd->peer_flags_ext |= cpu_to_le32(WMI_PEER_EXT_EHT);
 2212	}
 2213
 2214	/* Suppress authorization for all AUTH modes that need 4-way handshake
 2215	 * (during re-association).
 2216	 * Authorization will be done for these modes on key installation.
 2217	 */
 2218	if (arg->auth_flag)
 2219		cmd->peer_flags |= cpu_to_le32(WMI_PEER_AUTH);
 2220	if (arg->need_ptk_4_way) {
 2221		cmd->peer_flags |= cpu_to_le32(WMI_PEER_NEED_PTK_4_WAY);
 2222		if (!hw_crypto_disabled && arg->is_assoc)
 2223			cmd->peer_flags &= cpu_to_le32(~WMI_PEER_AUTH);
 2224	}
 2225	if (arg->need_gtk_2_way)
 2226		cmd->peer_flags |= cpu_to_le32(WMI_PEER_NEED_GTK_2_WAY);
 2227	/* safe mode bypass the 4-way handshake */
 2228	if (arg->safe_mode_enabled)
 2229		cmd->peer_flags &= cpu_to_le32(~(WMI_PEER_NEED_PTK_4_WAY |
 2230						 WMI_PEER_NEED_GTK_2_WAY));
 2231
 2232	if (arg->is_pmf_enabled)
 2233		cmd->peer_flags |= cpu_to_le32(WMI_PEER_PMF);
 2234
 2235	/* Disable AMSDU for station transmit, if user configures it */
 2236	/* Disable AMSDU for AP transmit to 11n Stations, if user configures
 2237	 * it
 2238	 * if (arg->amsdu_disable) Add after FW support
 2239	 **/
 2240
 2241	/* Target asserts if node is marked HT and all MCS is set to 0.
 2242	 * Mark the node as non-HT if all the mcs rates are disabled through
 2243	 * iwpriv
 2244	 **/
 2245	if (arg->peer_ht_rates.num_rates == 0)
 2246		cmd->peer_flags &= cpu_to_le32(~WMI_PEER_HT);
 2247}
 2248
 2249int ath12k_wmi_send_peer_assoc_cmd(struct ath12k *ar,
 2250				   struct ath12k_wmi_peer_assoc_arg *arg)
 2251{
 2252	struct ath12k_wmi_pdev *wmi = ar->wmi;
 2253	struct wmi_peer_assoc_complete_cmd *cmd;
 2254	struct ath12k_wmi_vht_rate_set_params *mcs;
 2255	struct ath12k_wmi_he_rate_set_params *he_mcs;
 2256	struct ath12k_wmi_eht_rate_set_params *eht_mcs;
 2257	struct wmi_peer_assoc_mlo_params *ml_params;
 2258	struct wmi_peer_assoc_mlo_partner_info_params *partner_info;
 2259	struct sk_buff *skb;
 2260	struct wmi_tlv *tlv;
 2261	void *ptr;
 2262	u32 peer_legacy_rates_align, eml_pad_delay, eml_trans_delay;
 2263	u32 peer_ht_rates_align, eml_trans_timeout;
 2264	int i, ret, len;
 2265	u16 eml_cap;
 2266	__le32 v;
 2267
 2268	peer_legacy_rates_align = roundup(arg->peer_legacy_rates.num_rates,
 2269					  sizeof(u32));
 2270	peer_ht_rates_align = roundup(arg->peer_ht_rates.num_rates,
 2271				      sizeof(u32));
 2272
 2273	len = sizeof(*cmd) +
 2274	      TLV_HDR_SIZE + (peer_legacy_rates_align * sizeof(u8)) +
 2275	      TLV_HDR_SIZE + (peer_ht_rates_align * sizeof(u8)) +
 2276	      sizeof(*mcs) + TLV_HDR_SIZE +
 2277	      (sizeof(*he_mcs) * arg->peer_he_mcs_count) +
 2278	      TLV_HDR_SIZE + (sizeof(*eht_mcs) * arg->peer_eht_mcs_count);
 2279
 2280	if (arg->ml.enabled)
 2281		len += TLV_HDR_SIZE + sizeof(*ml_params) +
 2282		       TLV_HDR_SIZE + (arg->ml.num_partner_links * sizeof(*partner_info));
 2283	else
 2284		len += (2 * TLV_HDR_SIZE);
 2285
 2286	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 2287	if (!skb)
 2288		return -ENOMEM;
 2289
 2290	ptr = skb->data;
 2291
 2292	cmd = ptr;
 2293	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PEER_ASSOC_COMPLETE_CMD,
 2294						 sizeof(*cmd));
 2295
 2296	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 2297
 2298	cmd->peer_new_assoc = cpu_to_le32(arg->peer_new_assoc);
 2299	cmd->peer_associd = cpu_to_le32(arg->peer_associd);
 2300	cmd->punct_bitmap = cpu_to_le32(arg->punct_bitmap);
 2301
 2302	ath12k_wmi_copy_peer_flags(cmd, arg,
 2303				   test_bit(ATH12K_FLAG_HW_CRYPTO_DISABLED,
 2304					    &ar->ab->dev_flags));
 2305
 2306	ether_addr_copy(cmd->peer_macaddr.addr, arg->peer_mac);
 2307
 2308	cmd->peer_rate_caps = cpu_to_le32(arg->peer_rate_caps);
 2309	cmd->peer_caps = cpu_to_le32(arg->peer_caps);
 2310	cmd->peer_listen_intval = cpu_to_le32(arg->peer_listen_intval);
 2311	cmd->peer_ht_caps = cpu_to_le32(arg->peer_ht_caps);
 2312	cmd->peer_max_mpdu = cpu_to_le32(arg->peer_max_mpdu);
 2313	cmd->peer_mpdu_density = cpu_to_le32(arg->peer_mpdu_density);
 2314	cmd->peer_vht_caps = cpu_to_le32(arg->peer_vht_caps);
 2315	cmd->peer_phymode = cpu_to_le32(arg->peer_phymode);
 2316
 2317	/* Update 11ax capabilities */
 2318	cmd->peer_he_cap_info = cpu_to_le32(arg->peer_he_cap_macinfo[0]);
 2319	cmd->peer_he_cap_info_ext = cpu_to_le32(arg->peer_he_cap_macinfo[1]);
 2320	cmd->peer_he_cap_info_internal = cpu_to_le32(arg->peer_he_cap_macinfo_internal);
 2321	cmd->peer_he_caps_6ghz = cpu_to_le32(arg->peer_he_caps_6ghz);
 2322	cmd->peer_he_ops = cpu_to_le32(arg->peer_he_ops);
 2323	for (i = 0; i < WMI_MAX_HECAP_PHY_SIZE; i++)
 2324		cmd->peer_he_cap_phy[i] =
 2325			cpu_to_le32(arg->peer_he_cap_phyinfo[i]);
 2326	cmd->peer_ppet.numss_m1 = cpu_to_le32(arg->peer_ppet.numss_m1);
 2327	cmd->peer_ppet.ru_info = cpu_to_le32(arg->peer_ppet.ru_bit_mask);
 2328	for (i = 0; i < WMI_MAX_NUM_SS; i++)
 2329		cmd->peer_ppet.ppet16_ppet8_ru3_ru0[i] =
 2330			cpu_to_le32(arg->peer_ppet.ppet16_ppet8_ru3_ru0[i]);
 2331
 2332	/* Update 11be capabilities */
 2333	memcpy_and_pad(cmd->peer_eht_cap_mac, sizeof(cmd->peer_eht_cap_mac),
 2334		       arg->peer_eht_cap_mac, sizeof(arg->peer_eht_cap_mac),
 2335		       0);
 2336	memcpy_and_pad(cmd->peer_eht_cap_phy, sizeof(cmd->peer_eht_cap_phy),
 2337		       arg->peer_eht_cap_phy, sizeof(arg->peer_eht_cap_phy),
 2338		       0);
 2339	memcpy_and_pad(&cmd->peer_eht_ppet, sizeof(cmd->peer_eht_ppet),
 2340		       &arg->peer_eht_ppet, sizeof(arg->peer_eht_ppet), 0);
 2341
 2342	/* Update peer legacy rate information */
 2343	ptr += sizeof(*cmd);
 2344
 2345	tlv = ptr;
 2346	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, peer_legacy_rates_align);
 2347
 2348	ptr += TLV_HDR_SIZE;
 2349
 2350	cmd->num_peer_legacy_rates = cpu_to_le32(arg->peer_legacy_rates.num_rates);
 2351	memcpy(ptr, arg->peer_legacy_rates.rates,
 2352	       arg->peer_legacy_rates.num_rates);
 2353
 2354	/* Update peer HT rate information */
 2355	ptr += peer_legacy_rates_align;
 2356
 2357	tlv = ptr;
 2358	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, peer_ht_rates_align);
 2359	ptr += TLV_HDR_SIZE;
 2360	cmd->num_peer_ht_rates = cpu_to_le32(arg->peer_ht_rates.num_rates);
 2361	memcpy(ptr, arg->peer_ht_rates.rates,
 2362	       arg->peer_ht_rates.num_rates);
 2363
 2364	/* VHT Rates */
 2365	ptr += peer_ht_rates_align;
 2366
 2367	mcs = ptr;
 2368
 2369	mcs->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VHT_RATE_SET,
 2370						 sizeof(*mcs));
 2371
 2372	cmd->peer_nss = cpu_to_le32(arg->peer_nss);
 2373
 2374	/* Update bandwidth-NSS mapping */
 2375	cmd->peer_bw_rxnss_override = 0;
 2376	cmd->peer_bw_rxnss_override |= cpu_to_le32(arg->peer_bw_rxnss_override);
 2377
 2378	if (arg->vht_capable) {
 2379		/* Firmware interprets mcs->tx_mcs_set field as peer's
 2380		 * RX capability
 2381		 */
 2382		mcs->rx_max_rate = cpu_to_le32(arg->tx_max_rate);
 2383		mcs->rx_mcs_set = cpu_to_le32(arg->tx_mcs_set);
 2384		mcs->tx_max_rate = cpu_to_le32(arg->rx_max_rate);
 2385		mcs->tx_mcs_set = cpu_to_le32(arg->rx_mcs_set);
 2386	}
 2387
 2388	/* HE Rates */
 2389	cmd->peer_he_mcs = cpu_to_le32(arg->peer_he_mcs_count);
 2390	cmd->min_data_rate = cpu_to_le32(arg->min_data_rate);
 2391
 2392	ptr += sizeof(*mcs);
 2393
 2394	len = arg->peer_he_mcs_count * sizeof(*he_mcs);
 2395
 2396	tlv = ptr;
 2397	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, len);
 2398	ptr += TLV_HDR_SIZE;
 2399
 2400	/* Loop through the HE rate set */
 2401	for (i = 0; i < arg->peer_he_mcs_count; i++) {
 2402		he_mcs = ptr;
 2403		he_mcs->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_HE_RATE_SET,
 2404							    sizeof(*he_mcs));
 2405
 2406		he_mcs->rx_mcs_set = cpu_to_le32(arg->peer_he_rx_mcs_set[i]);
 2407		he_mcs->tx_mcs_set = cpu_to_le32(arg->peer_he_tx_mcs_set[i]);
 2408		ptr += sizeof(*he_mcs);
 2409	}
 2410
 2411	tlv = ptr;
 2412	len = arg->ml.enabled ? sizeof(*ml_params) : 0;
 2413	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, len);
 2414	ptr += TLV_HDR_SIZE;
 2415	if (!len)
 2416		goto skip_ml_params;
 2417
 2418	ml_params = ptr;
 2419	ml_params->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_PEER_ASSOC_PARAMS,
 2420						       len);
 2421	ml_params->flags = cpu_to_le32(ATH12K_WMI_FLAG_MLO_ENABLED);
 2422
 2423	if (arg->ml.assoc_link)
 2424		ml_params->flags |= cpu_to_le32(ATH12K_WMI_FLAG_MLO_ASSOC_LINK);
 2425
 2426	if (arg->ml.primary_umac)
 2427		ml_params->flags |= cpu_to_le32(ATH12K_WMI_FLAG_MLO_PRIMARY_UMAC);
 2428
 2429	if (arg->ml.logical_link_idx_valid)
 2430		ml_params->flags |=
 2431			cpu_to_le32(ATH12K_WMI_FLAG_MLO_LOGICAL_LINK_IDX_VALID);
 2432
 2433	if (arg->ml.peer_id_valid)
 2434		ml_params->flags |= cpu_to_le32(ATH12K_WMI_FLAG_MLO_PEER_ID_VALID);
 2435
 2436	ether_addr_copy(ml_params->mld_addr.addr, arg->ml.mld_addr);
 2437	ml_params->logical_link_idx = cpu_to_le32(arg->ml.logical_link_idx);
 2438	ml_params->ml_peer_id = cpu_to_le32(arg->ml.ml_peer_id);
 2439	ml_params->ieee_link_id = cpu_to_le32(arg->ml.ieee_link_id);
 2440
 2441	eml_cap = arg->ml.eml_cap;
 2442	if (u16_get_bits(eml_cap, IEEE80211_EML_CAP_EMLSR_SUPP)) {
 2443		ml_params->flags |= cpu_to_le32(ATH12K_WMI_FLAG_MLO_EMLSR_SUPPORT);
 2444		/* Padding delay */
 2445		eml_pad_delay = ieee80211_emlsr_pad_delay_in_us(eml_cap);
 2446		ml_params->emlsr_padding_delay_us = cpu_to_le32(eml_pad_delay);
 2447		/* Transition delay */
 2448		eml_trans_delay = ieee80211_emlsr_trans_delay_in_us(eml_cap);
 2449		ml_params->emlsr_trans_delay_us = cpu_to_le32(eml_trans_delay);
 2450		/* Transition timeout */
 2451		eml_trans_timeout = ieee80211_eml_trans_timeout_in_us(eml_cap);
 2452		ml_params->emlsr_trans_timeout_us =
 2453					cpu_to_le32(eml_trans_timeout);
 2454		ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "wmi peer %pM emlsr padding delay %u, trans delay %u trans timeout %u",
 2455			   arg->peer_mac, eml_pad_delay, eml_trans_delay,
 2456			   eml_trans_timeout);
 2457	}
 2458
 2459	ptr += sizeof(*ml_params);
 2460
 2461skip_ml_params:
 2462	/* Loop through the EHT rate set */
 2463	len = arg->peer_eht_mcs_count * sizeof(*eht_mcs);
 2464	tlv = ptr;
 2465	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, len);
 2466	ptr += TLV_HDR_SIZE;
 2467
 2468	for (i = 0; i < arg->peer_eht_mcs_count; i++) {
 2469		eht_mcs = ptr;
 2470		eht_mcs->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_EHT_RATE_SET,
 2471							     sizeof(*eht_mcs));
 2472
 2473		eht_mcs->rx_mcs_set = cpu_to_le32(arg->peer_eht_rx_mcs_set[i]);
 2474		eht_mcs->tx_mcs_set = cpu_to_le32(arg->peer_eht_tx_mcs_set[i]);
 2475		ptr += sizeof(*eht_mcs);
 2476	}
 2477
 2478	/* Update MCS15 capability */
 2479	if (arg->eht_disable_mcs15)
 2480		cmd->peer_eht_ops = cpu_to_le32(IEEE80211_EHT_OPER_MCS15_DISABLE);
 2481
 2482	tlv = ptr;
 2483	len = arg->ml.enabled ? arg->ml.num_partner_links * sizeof(*partner_info) : 0;
 2484	/* fill ML Partner links */
 2485	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, len);
 2486	ptr += TLV_HDR_SIZE;
 2487
 2488	if (len == 0)
 2489		goto send;
 2490
 2491	for (i = 0; i < arg->ml.num_partner_links; i++) {
 2492		u32 cmd = WMI_TAG_MLO_PARTNER_LINK_PARAMS_PEER_ASSOC;
 2493
 2494		partner_info = ptr;
 2495		partner_info->tlv_header = ath12k_wmi_tlv_cmd_hdr(cmd,
 2496								  sizeof(*partner_info));
 2497		partner_info->vdev_id = cpu_to_le32(arg->ml.partner_info[i].vdev_id);
 2498		partner_info->hw_link_id =
 2499			cpu_to_le32(arg->ml.partner_info[i].hw_link_id);
 2500		partner_info->flags = cpu_to_le32(ATH12K_WMI_FLAG_MLO_ENABLED);
 2501
 2502		if (arg->ml.partner_info[i].assoc_link)
 2503			partner_info->flags |=
 2504				cpu_to_le32(ATH12K_WMI_FLAG_MLO_ASSOC_LINK);
 2505
 2506		if (arg->ml.partner_info[i].primary_umac)
 2507			partner_info->flags |=
 2508				cpu_to_le32(ATH12K_WMI_FLAG_MLO_PRIMARY_UMAC);
 2509
 2510		if (arg->ml.partner_info[i].logical_link_idx_valid) {
 2511			v = cpu_to_le32(ATH12K_WMI_FLAG_MLO_LINK_ID_VALID);
 2512			partner_info->flags |= v;
 2513		}
 2514
 2515		partner_info->logical_link_idx =
 2516			cpu_to_le32(arg->ml.partner_info[i].logical_link_idx);
 2517		ptr += sizeof(*partner_info);
 2518	}
 2519
 2520send:
 2521	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 2522		   "wmi peer assoc vdev id %d assoc id %d peer mac %pM peer_flags %x rate_caps %x peer_caps %x listen_intval %d ht_caps %x max_mpdu %d nss %d phymode %d peer_mpdu_density %d vht_caps %x he cap_info %x he ops %x he cap_info_ext %x he phy %x %x %x peer_bw_rxnss_override %x peer_flags_ext %x eht mac_cap %x %x eht phy_cap %x %x %x peer_eht_ops %x\n",
 2523		   cmd->vdev_id, cmd->peer_associd, arg->peer_mac,
 2524		   cmd->peer_flags, cmd->peer_rate_caps, cmd->peer_caps,
 2525		   cmd->peer_listen_intval, cmd->peer_ht_caps,
 2526		   cmd->peer_max_mpdu, cmd->peer_nss, cmd->peer_phymode,
 2527		   cmd->peer_mpdu_density,
 2528		   cmd->peer_vht_caps, cmd->peer_he_cap_info,
 2529		   cmd->peer_he_ops, cmd->peer_he_cap_info_ext,
 2530		   cmd->peer_he_cap_phy[0], cmd->peer_he_cap_phy[1],
 2531		   cmd->peer_he_cap_phy[2],
 2532		   cmd->peer_bw_rxnss_override, cmd->peer_flags_ext,
 2533		   cmd->peer_eht_cap_mac[0], cmd->peer_eht_cap_mac[1],
 2534		   cmd->peer_eht_cap_phy[0], cmd->peer_eht_cap_phy[1],
 2535		   cmd->peer_eht_cap_phy[2], cmd->peer_eht_ops);
 2536
 2537	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_PEER_ASSOC_CMDID);
 2538	if (ret) {
 2539		ath12k_warn(ar->ab,
 2540			    "failed to send WMI_PEER_ASSOC_CMDID\n");
 2541		dev_kfree_skb(skb);
 2542	}
 2543
 2544	return ret;
 2545}
 2546
 2547void ath12k_wmi_start_scan_init(struct ath12k *ar,
 2548				struct ath12k_wmi_scan_req_arg *arg)
 2549{
 2550	/* setup commonly used values */
 2551	arg->scan_req_id = 1;
 2552	arg->scan_priority = WMI_SCAN_PRIORITY_LOW;
 2553	arg->dwell_time_active = 50;
 2554	arg->dwell_time_active_2g = 0;
 2555	arg->dwell_time_passive = 150;
 2556	arg->dwell_time_active_6g = 70;
 2557	arg->dwell_time_passive_6g = 70;
 2558	arg->min_rest_time = 50;
 2559	arg->max_rest_time = 500;
 2560	arg->repeat_probe_time = 0;
 2561	arg->probe_spacing_time = 0;
 2562	arg->idle_time = 0;
 2563	arg->max_scan_time = 20000;
 2564	arg->probe_delay = 5;
 2565	arg->notify_scan_events = WMI_SCAN_EVENT_STARTED |
 2566				  WMI_SCAN_EVENT_COMPLETED |
 2567				  WMI_SCAN_EVENT_BSS_CHANNEL |
 2568				  WMI_SCAN_EVENT_FOREIGN_CHAN |
 2569				  WMI_SCAN_EVENT_DEQUEUED;
 2570	arg->scan_f_chan_stat_evnt = 1;
 2571	arg->num_bssid = 1;
 2572
 2573	/* fill bssid_list[0] with 0xff, otherwise bssid and RA will be
 2574	 * ZEROs in probe request
 2575	 */
 2576	eth_broadcast_addr(arg->bssid_list[0].addr);
 2577}
 2578
 2579static void ath12k_wmi_copy_scan_event_cntrl_flags(struct wmi_start_scan_cmd *cmd,
 2580						   struct ath12k_wmi_scan_req_arg *arg)
 2581{
 2582	/* Scan events subscription */
 2583	if (arg->scan_ev_started)
 2584		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_STARTED);
 2585	if (arg->scan_ev_completed)
 2586		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_COMPLETED);
 2587	if (arg->scan_ev_bss_chan)
 2588		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_BSS_CHANNEL);
 2589	if (arg->scan_ev_foreign_chan)
 2590		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_FOREIGN_CHAN);
 2591	if (arg->scan_ev_dequeued)
 2592		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_DEQUEUED);
 2593	if (arg->scan_ev_preempted)
 2594		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_PREEMPTED);
 2595	if (arg->scan_ev_start_failed)
 2596		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_START_FAILED);
 2597	if (arg->scan_ev_restarted)
 2598		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_RESTARTED);
 2599	if (arg->scan_ev_foreign_chn_exit)
 2600		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_FOREIGN_CHAN_EXIT);
 2601	if (arg->scan_ev_suspended)
 2602		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_SUSPENDED);
 2603	if (arg->scan_ev_resumed)
 2604		cmd->notify_scan_events |= cpu_to_le32(WMI_SCAN_EVENT_RESUMED);
 2605
 2606	/** Set scan control flags */
 2607	cmd->scan_ctrl_flags = 0;
 2608	if (arg->scan_f_passive)
 2609		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_FLAG_PASSIVE);
 2610	if (arg->scan_f_strict_passive_pch)
 2611		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_FLAG_STRICT_PASSIVE_ON_PCHN);
 2612	if (arg->scan_f_promisc_mode)
 2613		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_FILTER_PROMISCUOS);
 2614	if (arg->scan_f_capture_phy_err)
 2615		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_CAPTURE_PHY_ERROR);
 2616	if (arg->scan_f_half_rate)
 2617		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_FLAG_HALF_RATE_SUPPORT);
 2618	if (arg->scan_f_quarter_rate)
 2619		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_FLAG_QUARTER_RATE_SUPPORT);
 2620	if (arg->scan_f_cck_rates)
 2621		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_ADD_CCK_RATES);
 2622	if (arg->scan_f_ofdm_rates)
 2623		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_ADD_OFDM_RATES);
 2624	if (arg->scan_f_chan_stat_evnt)
 2625		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_CHAN_STAT_EVENT);
 2626	if (arg->scan_f_filter_prb_req)
 2627		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_FILTER_PROBE_REQ);
 2628	if (arg->scan_f_bcast_probe)
 2629		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_ADD_BCAST_PROBE_REQ);
 2630	if (arg->scan_f_offchan_mgmt_tx)
 2631		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_OFFCHAN_MGMT_TX);
 2632	if (arg->scan_f_offchan_data_tx)
 2633		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_OFFCHAN_DATA_TX);
 2634	if (arg->scan_f_force_active_dfs_chn)
 2635		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_FLAG_FORCE_ACTIVE_ON_DFS);
 2636	if (arg->scan_f_add_tpc_ie_in_probe)
 2637		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_ADD_TPC_IE_IN_PROBE_REQ);
 2638	if (arg->scan_f_add_ds_ie_in_probe)
 2639		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_ADD_DS_IE_IN_PROBE_REQ);
 2640	if (arg->scan_f_add_spoofed_mac_in_probe)
 2641		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_ADD_SPOOF_MAC_IN_PROBE_REQ);
 2642	if (arg->scan_f_add_rand_seq_in_probe)
 2643		cmd->scan_ctrl_flags |= cpu_to_le32(WMI_SCAN_RANDOM_SEQ_NO_IN_PROBE_REQ);
 2644	if (arg->scan_f_en_ie_whitelist_in_probe)
 2645		cmd->scan_ctrl_flags |=
 2646			cpu_to_le32(WMI_SCAN_ENABLE_IE_WHTELIST_IN_PROBE_REQ);
 2647
 2648	cmd->scan_ctrl_flags |= le32_encode_bits(arg->adaptive_dwell_time_mode,
 2649						 WMI_SCAN_DWELL_MODE_MASK);
 2650}
 2651
 2652int ath12k_wmi_send_scan_start_cmd(struct ath12k *ar,
 2653				   struct ath12k_wmi_scan_req_arg *arg)
 2654{
 2655	struct ath12k_wmi_pdev *wmi = ar->wmi;
 2656	struct wmi_start_scan_cmd *cmd;
 2657	struct ath12k_wmi_ssid_params *ssid = NULL;
 2658	struct ath12k_wmi_mac_addr_params *bssid;
 2659	struct sk_buff *skb;
 2660	struct wmi_tlv *tlv;
 2661	void *ptr;
 2662	int i, ret, len;
 2663	u32 *tmp_ptr, extraie_len_with_pad = 0;
 2664	struct ath12k_wmi_hint_short_ssid_arg *s_ssid = NULL;
 2665	struct ath12k_wmi_hint_bssid_arg *hint_bssid = NULL;
 2666
 2667	len = sizeof(*cmd);
 2668
 2669	len += TLV_HDR_SIZE;
 2670	if (arg->num_chan)
 2671		len += arg->num_chan * sizeof(u32);
 2672
 2673	len += TLV_HDR_SIZE;
 2674	if (arg->num_ssids)
 2675		len += arg->num_ssids * sizeof(*ssid);
 2676
 2677	len += TLV_HDR_SIZE;
 2678	if (arg->num_bssid)
 2679		len += sizeof(*bssid) * arg->num_bssid;
 2680
 2681	if (arg->num_hint_bssid)
 2682		len += TLV_HDR_SIZE +
 2683		       arg->num_hint_bssid * sizeof(*hint_bssid);
 2684
 2685	if (arg->num_hint_s_ssid)
 2686		len += TLV_HDR_SIZE +
 2687		       arg->num_hint_s_ssid * sizeof(*s_ssid);
 2688
 2689	len += TLV_HDR_SIZE;
 2690	if (arg->extraie.len)
 2691		extraie_len_with_pad =
 2692			roundup(arg->extraie.len, sizeof(u32));
 2693	if (extraie_len_with_pad <= (wmi->wmi_ab->max_msg_len[ar->pdev_idx] - len)) {
 2694		len += extraie_len_with_pad;
 2695	} else {
 2696		ath12k_warn(ar->ab, "discard large size %d bytes extraie for scan start\n",
 2697			    arg->extraie.len);
 2698		extraie_len_with_pad = 0;
 2699	}
 2700
 2701	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 2702	if (!skb)
 2703		return -ENOMEM;
 2704
 2705	ptr = skb->data;
 2706
 2707	cmd = ptr;
 2708	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_START_SCAN_CMD,
 2709						 sizeof(*cmd));
 2710
 2711	cmd->scan_id = cpu_to_le32(arg->scan_id);
 2712	cmd->scan_req_id = cpu_to_le32(arg->scan_req_id);
 2713	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 2714	if (ar->state_11d == ATH12K_11D_PREPARING)
 2715		arg->scan_priority = WMI_SCAN_PRIORITY_MEDIUM;
 2716	else
 2717		arg->scan_priority = WMI_SCAN_PRIORITY_LOW;
 2718	cmd->notify_scan_events = cpu_to_le32(arg->notify_scan_events);
 2719
 2720	ath12k_wmi_copy_scan_event_cntrl_flags(cmd, arg);
 2721
 2722	cmd->dwell_time_active = cpu_to_le32(arg->dwell_time_active);
 2723	cmd->dwell_time_active_2g = cpu_to_le32(arg->dwell_time_active_2g);
 2724	cmd->dwell_time_passive = cpu_to_le32(arg->dwell_time_passive);
 2725	cmd->dwell_time_active_6g = cpu_to_le32(arg->dwell_time_active_6g);
 2726	cmd->dwell_time_passive_6g = cpu_to_le32(arg->dwell_time_passive_6g);
 2727	cmd->min_rest_time = cpu_to_le32(arg->min_rest_time);
 2728	cmd->max_rest_time = cpu_to_le32(arg->max_rest_time);
 2729	cmd->repeat_probe_time = cpu_to_le32(arg->repeat_probe_time);
 2730	cmd->probe_spacing_time = cpu_to_le32(arg->probe_spacing_time);
 2731	cmd->idle_time = cpu_to_le32(arg->idle_time);
 2732	cmd->max_scan_time = cpu_to_le32(arg->max_scan_time);
 2733	cmd->probe_delay = cpu_to_le32(arg->probe_delay);
 2734	cmd->burst_duration = cpu_to_le32(arg->burst_duration);
 2735	cmd->num_chan = cpu_to_le32(arg->num_chan);
 2736	cmd->num_bssid = cpu_to_le32(arg->num_bssid);
 2737	cmd->num_ssids = cpu_to_le32(arg->num_ssids);
 2738	cmd->ie_len = cpu_to_le32(arg->extraie.len);
 2739	cmd->n_probes = cpu_to_le32(arg->n_probes);
 2740
 2741	ptr += sizeof(*cmd);
 2742
 2743	len = arg->num_chan * sizeof(u32);
 2744
 2745	tlv = ptr;
 2746	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, len);
 2747	ptr += TLV_HDR_SIZE;
 2748	tmp_ptr = (u32 *)ptr;
 2749
 2750	memcpy(tmp_ptr, arg->chan_list, arg->num_chan * 4);
 2751
 2752	ptr += len;
 2753
 2754	len = arg->num_ssids * sizeof(*ssid);
 2755	tlv = ptr;
 2756	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_FIXED_STRUCT, len);
 2757
 2758	ptr += TLV_HDR_SIZE;
 2759
 2760	if (arg->num_ssids) {
 2761		ssid = ptr;
 2762		for (i = 0; i < arg->num_ssids; ++i) {
 2763			ssid->ssid_len = cpu_to_le32(arg->ssid[i].ssid_len);
 2764			memcpy(ssid->ssid, arg->ssid[i].ssid,
 2765			       arg->ssid[i].ssid_len);
 2766			ssid++;
 2767		}
 2768	}
 2769
 2770	ptr += (arg->num_ssids * sizeof(*ssid));
 2771	len = arg->num_bssid * sizeof(*bssid);
 2772	tlv = ptr;
 2773	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_FIXED_STRUCT, len);
 2774
 2775	ptr += TLV_HDR_SIZE;
 2776	bssid = ptr;
 2777
 2778	if (arg->num_bssid) {
 2779		for (i = 0; i < arg->num_bssid; ++i) {
 2780			ether_addr_copy(bssid->addr,
 2781					arg->bssid_list[i].addr);
 2782			bssid++;
 2783		}
 2784	}
 2785
 2786	ptr += arg->num_bssid * sizeof(*bssid);
 2787
 2788	len = extraie_len_with_pad;
 2789	tlv = ptr;
 2790	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, len);
 2791	ptr += TLV_HDR_SIZE;
 2792
 2793	if (extraie_len_with_pad)
 2794		memcpy(ptr, arg->extraie.ptr,
 2795		       arg->extraie.len);
 2796
 2797	ptr += extraie_len_with_pad;
 2798
 2799	if (arg->num_hint_s_ssid) {
 2800		len = arg->num_hint_s_ssid * sizeof(*s_ssid);
 2801		tlv = ptr;
 2802		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_FIXED_STRUCT, len);
 2803		ptr += TLV_HDR_SIZE;
 2804		s_ssid = ptr;
 2805		for (i = 0; i < arg->num_hint_s_ssid; ++i) {
 2806			s_ssid->freq_flags = arg->hint_s_ssid[i].freq_flags;
 2807			s_ssid->short_ssid = arg->hint_s_ssid[i].short_ssid;
 2808			s_ssid++;
 2809		}
 2810		ptr += len;
 2811	}
 2812
 2813	if (arg->num_hint_bssid) {
 2814		len = arg->num_hint_bssid * sizeof(struct ath12k_wmi_hint_bssid_arg);
 2815		tlv = ptr;
 2816		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_FIXED_STRUCT, len);
 2817		ptr += TLV_HDR_SIZE;
 2818		hint_bssid = ptr;
 2819		for (i = 0; i < arg->num_hint_bssid; ++i) {
 2820			hint_bssid->freq_flags =
 2821				arg->hint_bssid[i].freq_flags;
 2822			ether_addr_copy(&arg->hint_bssid[i].bssid.addr[0],
 2823					&hint_bssid->bssid.addr[0]);
 2824			hint_bssid++;
 2825		}
 2826	}
 2827
 2828	ret = ath12k_wmi_cmd_send(wmi, skb,
 2829				  WMI_START_SCAN_CMDID);
 2830	if (ret) {
 2831		ath12k_warn(ar->ab, "failed to send WMI_START_SCAN_CMDID\n");
 2832		dev_kfree_skb(skb);
 2833	}
 2834
 2835	return ret;
 2836}
 2837
 2838int ath12k_wmi_send_scan_stop_cmd(struct ath12k *ar,
 2839				  struct ath12k_wmi_scan_cancel_arg *arg)
 2840{
 2841	struct ath12k_wmi_pdev *wmi = ar->wmi;
 2842	struct wmi_stop_scan_cmd *cmd;
 2843	struct sk_buff *skb;
 2844	int ret;
 2845
 2846	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 2847	if (!skb)
 2848		return -ENOMEM;
 2849
 2850	cmd = (struct wmi_stop_scan_cmd *)skb->data;
 2851
 2852	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_STOP_SCAN_CMD,
 2853						 sizeof(*cmd));
 2854
 2855	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 2856	cmd->requestor = cpu_to_le32(arg->requester);
 2857	cmd->scan_id = cpu_to_le32(arg->scan_id);
 2858	cmd->pdev_id = cpu_to_le32(arg->pdev_id);
 2859	/* stop the scan with the corresponding scan_id */
 2860	if (arg->req_type == WLAN_SCAN_CANCEL_PDEV_ALL) {
 2861		/* Cancelling all scans */
 2862		cmd->req_type = cpu_to_le32(WMI_SCAN_STOP_ALL);
 2863	} else if (arg->req_type == WLAN_SCAN_CANCEL_VDEV_ALL) {
 2864		/* Cancelling VAP scans */
 2865		cmd->req_type = cpu_to_le32(WMI_SCAN_STOP_VAP_ALL);
 2866	} else if (arg->req_type == WLAN_SCAN_CANCEL_SINGLE) {
 2867		/* Cancelling specific scan */
 2868		cmd->req_type = WMI_SCAN_STOP_ONE;
 2869	} else {
 2870		ath12k_warn(ar->ab, "invalid scan cancel req_type %d",
 2871			    arg->req_type);
 2872		dev_kfree_skb(skb);
 2873		return -EINVAL;
 2874	}
 2875
 2876	ret = ath12k_wmi_cmd_send(wmi, skb,
 2877				  WMI_STOP_SCAN_CMDID);
 2878	if (ret) {
 2879		ath12k_warn(ar->ab, "failed to send WMI_STOP_SCAN_CMDID\n");
 2880		dev_kfree_skb(skb);
 2881	}
 2882
 2883	return ret;
 2884}
 2885
 2886int ath12k_wmi_send_scan_chan_list_cmd(struct ath12k *ar,
 2887				       struct ath12k_wmi_scan_chan_list_arg *arg)
 2888{
 2889	struct ath12k_wmi_pdev *wmi = ar->wmi;
 2890	struct wmi_scan_chan_list_cmd *cmd;
 2891	struct sk_buff *skb;
 2892	struct ath12k_wmi_channel_params *chan_info;
 2893	struct ath12k_wmi_channel_arg *channel_arg;
 2894	struct wmi_tlv *tlv;
 2895	void *ptr;
 2896	int i, ret, len;
 2897	u16 num_send_chans, num_sends = 0, max_chan_limit = 0;
 2898	__le32 *reg1, *reg2;
 2899
 2900	channel_arg = &arg->channel[0];
 2901	while (arg->nallchans) {
 2902		len = sizeof(*cmd) + TLV_HDR_SIZE;
 2903		max_chan_limit = (wmi->wmi_ab->max_msg_len[ar->pdev_idx] - len) /
 2904			sizeof(*chan_info);
 2905
 2906		num_send_chans = min(arg->nallchans, max_chan_limit);
 2907
 2908		arg->nallchans -= num_send_chans;
 2909		len += sizeof(*chan_info) * num_send_chans;
 2910
 2911		skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 2912		if (!skb)
 2913			return -ENOMEM;
 2914
 2915		cmd = (struct wmi_scan_chan_list_cmd *)skb->data;
 2916		cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_SCAN_CHAN_LIST_CMD,
 2917							 sizeof(*cmd));
 2918		cmd->pdev_id = cpu_to_le32(arg->pdev_id);
 2919		cmd->num_scan_chans = cpu_to_le32(num_send_chans);
 2920		if (num_sends)
 2921			cmd->flags |= cpu_to_le32(WMI_APPEND_TO_EXISTING_CHAN_LIST_FLAG);
 2922
 2923		ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 2924			   "WMI no.of chan = %d len = %d pdev_id = %d num_sends = %d\n",
 2925			   num_send_chans, len, cmd->pdev_id, num_sends);
 2926
 2927		ptr = skb->data + sizeof(*cmd);
 2928
 2929		len = sizeof(*chan_info) * num_send_chans;
 2930		tlv = ptr;
 2931		tlv->header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_ARRAY_STRUCT,
 2932						     len);
 2933		ptr += TLV_HDR_SIZE;
 2934
 2935		for (i = 0; i < num_send_chans; ++i) {
 2936			chan_info = ptr;
 2937			memset(chan_info, 0, sizeof(*chan_info));
 2938			len = sizeof(*chan_info);
 2939			chan_info->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_CHANNEL,
 2940								       len);
 2941
 2942			reg1 = &chan_info->reg_info_1;
 2943			reg2 = &chan_info->reg_info_2;
 2944			chan_info->mhz = cpu_to_le32(channel_arg->mhz);
 2945			chan_info->band_center_freq1 = cpu_to_le32(channel_arg->cfreq1);
 2946			chan_info->band_center_freq2 = cpu_to_le32(channel_arg->cfreq2);
 2947
 2948			if (channel_arg->is_chan_passive)
 2949				chan_info->info |= cpu_to_le32(WMI_CHAN_INFO_PASSIVE);
 2950			if (channel_arg->allow_he)
 2951				chan_info->info |= cpu_to_le32(WMI_CHAN_INFO_ALLOW_HE);
 2952			else if (channel_arg->allow_vht)
 2953				chan_info->info |= cpu_to_le32(WMI_CHAN_INFO_ALLOW_VHT);
 2954			else if (channel_arg->allow_ht)
 2955				chan_info->info |= cpu_to_le32(WMI_CHAN_INFO_ALLOW_HT);
 2956			if (channel_arg->half_rate)
 2957				chan_info->info |= cpu_to_le32(WMI_CHAN_INFO_HALF_RATE);
 2958			if (channel_arg->quarter_rate)
 2959				chan_info->info |=
 2960					cpu_to_le32(WMI_CHAN_INFO_QUARTER_RATE);
 2961
 2962			if (channel_arg->psc_channel)
 2963				chan_info->info |= cpu_to_le32(WMI_CHAN_INFO_PSC);
 2964
 2965			if (channel_arg->dfs_set)
 2966				chan_info->info |= cpu_to_le32(WMI_CHAN_INFO_DFS);
 2967
 2968			chan_info->info |= le32_encode_bits(channel_arg->phy_mode,
 2969							    WMI_CHAN_INFO_MODE);
 2970			*reg1 |= le32_encode_bits(channel_arg->minpower,
 2971						  WMI_CHAN_REG_INFO1_MIN_PWR);
 2972			*reg1 |= le32_encode_bits(channel_arg->maxpower,
 2973						  WMI_CHAN_REG_INFO1_MAX_PWR);
 2974			*reg1 |= le32_encode_bits(channel_arg->maxregpower,
 2975						  WMI_CHAN_REG_INFO1_MAX_REG_PWR);
 2976			*reg1 |= le32_encode_bits(channel_arg->reg_class_id,
 2977						  WMI_CHAN_REG_INFO1_REG_CLS);
 2978			*reg2 |= le32_encode_bits(channel_arg->antennamax,
 2979						  WMI_CHAN_REG_INFO2_ANT_MAX);
 2980			*reg2 |= le32_encode_bits(channel_arg->maxregpower,
 2981						  WMI_CHAN_REG_INFO2_MAX_TX_PWR);
 2982
 2983			ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 2984				   "WMI chan scan list chan[%d] = %u, chan_info->info %8x\n",
 2985				   i, chan_info->mhz, chan_info->info);
 2986
 2987			ptr += sizeof(*chan_info);
 2988
 2989			channel_arg++;
 2990		}
 2991
 2992		ret = ath12k_wmi_cmd_send(wmi, skb, WMI_SCAN_CHAN_LIST_CMDID);
 2993		if (ret) {
 2994			ath12k_warn(ar->ab, "failed to send WMI_SCAN_CHAN_LIST cmd\n");
 2995			dev_kfree_skb(skb);
 2996			return ret;
 2997		}
 2998
 2999		num_sends++;
 3000	}
 3001
 3002	return 0;
 3003}
 3004
 3005int ath12k_wmi_send_wmm_update_cmd(struct ath12k *ar, u32 vdev_id,
 3006				   struct wmi_wmm_params_all_arg *param)
 3007{
 3008	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3009	struct wmi_vdev_set_wmm_params_cmd *cmd;
 3010	struct wmi_wmm_params *wmm_param;
 3011	struct wmi_wmm_params_arg *wmi_wmm_arg;
 3012	struct sk_buff *skb;
 3013	int ret, ac;
 3014
 3015	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3016	if (!skb)
 3017		return -ENOMEM;
 3018
 3019	cmd = (struct wmi_vdev_set_wmm_params_cmd *)skb->data;
 3020	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_SET_WMM_PARAMS_CMD,
 3021						 sizeof(*cmd));
 3022
 3023	cmd->vdev_id = cpu_to_le32(vdev_id);
 3024	cmd->wmm_param_type = 0;
 3025
 3026	for (ac = 0; ac < WME_NUM_AC; ac++) {
 3027		switch (ac) {
 3028		case WME_AC_BE:
 3029			wmi_wmm_arg = &param->ac_be;
 3030			break;
 3031		case WME_AC_BK:
 3032			wmi_wmm_arg = &param->ac_bk;
 3033			break;
 3034		case WME_AC_VI:
 3035			wmi_wmm_arg = &param->ac_vi;
 3036			break;
 3037		case WME_AC_VO:
 3038			wmi_wmm_arg = &param->ac_vo;
 3039			break;
 3040		}
 3041
 3042		wmm_param = (struct wmi_wmm_params *)&cmd->wmm_params[ac];
 3043		wmm_param->tlv_header =
 3044			ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_SET_WMM_PARAMS_CMD,
 3045					       sizeof(*wmm_param));
 3046
 3047		wmm_param->aifs = cpu_to_le32(wmi_wmm_arg->aifs);
 3048		wmm_param->cwmin = cpu_to_le32(wmi_wmm_arg->cwmin);
 3049		wmm_param->cwmax = cpu_to_le32(wmi_wmm_arg->cwmax);
 3050		wmm_param->txoplimit = cpu_to_le32(wmi_wmm_arg->txop);
 3051		wmm_param->acm = cpu_to_le32(wmi_wmm_arg->acm);
 3052		wmm_param->no_ack = cpu_to_le32(wmi_wmm_arg->no_ack);
 3053
 3054		ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3055			   "wmi wmm set ac %d aifs %d cwmin %d cwmax %d txop %d acm %d no_ack %d\n",
 3056			   ac, wmm_param->aifs, wmm_param->cwmin,
 3057			   wmm_param->cwmax, wmm_param->txoplimit,
 3058			   wmm_param->acm, wmm_param->no_ack);
 3059	}
 3060	ret = ath12k_wmi_cmd_send(wmi, skb,
 3061				  WMI_VDEV_SET_WMM_PARAMS_CMDID);
 3062	if (ret) {
 3063		ath12k_warn(ar->ab,
 3064			    "failed to send WMI_VDEV_SET_WMM_PARAMS_CMDID");
 3065		dev_kfree_skb(skb);
 3066	}
 3067
 3068	return ret;
 3069}
 3070
 3071int ath12k_wmi_send_dfs_phyerr_offload_enable_cmd(struct ath12k *ar,
 3072						  u32 pdev_id)
 3073{
 3074	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3075	struct wmi_dfs_phyerr_offload_cmd *cmd;
 3076	struct sk_buff *skb;
 3077	int ret;
 3078
 3079	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3080	if (!skb)
 3081		return -ENOMEM;
 3082
 3083	cmd = (struct wmi_dfs_phyerr_offload_cmd *)skb->data;
 3084	cmd->tlv_header =
 3085		ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_DFS_PHYERR_OFFLOAD_ENABLE_CMD,
 3086				       sizeof(*cmd));
 3087
 3088	cmd->pdev_id = cpu_to_le32(pdev_id);
 3089
 3090	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3091		   "WMI dfs phy err offload enable pdev id %d\n", pdev_id);
 3092
 3093	ret = ath12k_wmi_cmd_send(wmi, skb,
 3094				  WMI_PDEV_DFS_PHYERR_OFFLOAD_ENABLE_CMDID);
 3095	if (ret) {
 3096		ath12k_warn(ar->ab,
 3097			    "failed to send WMI_PDEV_DFS_PHYERR_OFFLOAD_ENABLE cmd\n");
 3098		dev_kfree_skb(skb);
 3099	}
 3100
 3101	return ret;
 3102}
 3103
 3104int ath12k_wmi_set_bios_cmd(struct ath12k_base *ab, u32 param_id,
 3105			    const u8 *buf, size_t buf_len)
 3106{
 3107	struct ath12k_wmi_base *wmi_ab = &ab->wmi_ab;
 3108	struct wmi_pdev_set_bios_interface_cmd *cmd;
 3109	struct wmi_tlv *tlv;
 3110	struct sk_buff *skb;
 3111	u8 *ptr;
 3112	u32 len, len_aligned;
 3113	int ret;
 3114
 3115	len_aligned = roundup(buf_len, sizeof(u32));
 3116	len = sizeof(*cmd) + TLV_HDR_SIZE + len_aligned;
 3117
 3118	skb = ath12k_wmi_alloc_skb(wmi_ab, len);
 3119	if (!skb)
 3120		return -ENOMEM;
 3121
 3122	cmd = (struct wmi_pdev_set_bios_interface_cmd *)skb->data;
 3123	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_SET_BIOS_INTERFACE_CMD,
 3124						 sizeof(*cmd));
 3125	cmd->pdev_id = cpu_to_le32(WMI_PDEV_ID_SOC);
 3126	cmd->param_type_id = cpu_to_le32(param_id);
 3127	cmd->length = cpu_to_le32(buf_len);
 3128
 3129	ptr = skb->data + sizeof(*cmd);
 3130	tlv = (struct wmi_tlv *)ptr;
 3131	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, len_aligned);
 3132	ptr += TLV_HDR_SIZE;
 3133	memcpy(ptr, buf, buf_len);
 3134
 3135	ret = ath12k_wmi_cmd_send(&wmi_ab->wmi[0],
 3136				  skb,
 3137				  WMI_PDEV_SET_BIOS_INTERFACE_CMDID);
 3138	if (ret) {
 3139		ath12k_warn(ab,
 3140			    "failed to send WMI_PDEV_SET_BIOS_INTERFACE_CMDID parameter id %d: %d\n",
 3141			    param_id, ret);
 3142		dev_kfree_skb(skb);
 3143	}
 3144
 3145	return 0;
 3146}
 3147
 3148int ath12k_wmi_set_bios_sar_cmd(struct ath12k_base *ab, const u8 *psar_table)
 3149{
 3150	struct ath12k_wmi_base *wmi_ab = &ab->wmi_ab;
 3151	struct wmi_pdev_set_bios_sar_table_cmd *cmd;
 3152	struct wmi_tlv *tlv;
 3153	struct sk_buff *skb;
 3154	int ret;
 3155	u8 *buf_ptr;
 3156	u32 len, sar_table_len_aligned, sar_dbs_backoff_len_aligned;
 3157	const u8 *psar_value = psar_table + ATH12K_ACPI_POWER_LIMIT_DATA_OFFSET;
 3158	const u8 *pdbs_value = psar_table + ATH12K_ACPI_DBS_BACKOFF_DATA_OFFSET;
 3159
 3160	sar_table_len_aligned = roundup(ATH12K_ACPI_BIOS_SAR_TABLE_LEN, sizeof(u32));
 3161	sar_dbs_backoff_len_aligned = roundup(ATH12K_ACPI_BIOS_SAR_DBS_BACKOFF_LEN,
 3162					      sizeof(u32));
 3163	len = sizeof(*cmd) + TLV_HDR_SIZE + sar_table_len_aligned +
 3164		TLV_HDR_SIZE + sar_dbs_backoff_len_aligned;
 3165
 3166	skb = ath12k_wmi_alloc_skb(wmi_ab, len);
 3167	if (!skb)
 3168		return -ENOMEM;
 3169
 3170	cmd = (struct wmi_pdev_set_bios_sar_table_cmd *)skb->data;
 3171	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_SET_BIOS_SAR_TABLE_CMD,
 3172						 sizeof(*cmd));
 3173	cmd->pdev_id = cpu_to_le32(WMI_PDEV_ID_SOC);
 3174	cmd->sar_len = cpu_to_le32(ATH12K_ACPI_BIOS_SAR_TABLE_LEN);
 3175	cmd->dbs_backoff_len = cpu_to_le32(ATH12K_ACPI_BIOS_SAR_DBS_BACKOFF_LEN);
 3176
 3177	buf_ptr = skb->data + sizeof(*cmd);
 3178	tlv = (struct wmi_tlv *)buf_ptr;
 3179	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE,
 3180					 sar_table_len_aligned);
 3181	buf_ptr += TLV_HDR_SIZE;
 3182	memcpy(buf_ptr, psar_value, ATH12K_ACPI_BIOS_SAR_TABLE_LEN);
 3183
 3184	buf_ptr += sar_table_len_aligned;
 3185	tlv = (struct wmi_tlv *)buf_ptr;
 3186	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE,
 3187					 sar_dbs_backoff_len_aligned);
 3188	buf_ptr += TLV_HDR_SIZE;
 3189	memcpy(buf_ptr, pdbs_value, ATH12K_ACPI_BIOS_SAR_DBS_BACKOFF_LEN);
 3190
 3191	ret = ath12k_wmi_cmd_send(&wmi_ab->wmi[0],
 3192				  skb,
 3193				  WMI_PDEV_SET_BIOS_SAR_TABLE_CMDID);
 3194	if (ret) {
 3195		ath12k_warn(ab,
 3196			    "failed to send WMI_PDEV_SET_BIOS_INTERFACE_CMDID %d\n",
 3197			    ret);
 3198		dev_kfree_skb(skb);
 3199	}
 3200
 3201	return ret;
 3202}
 3203
 3204int ath12k_wmi_set_bios_geo_cmd(struct ath12k_base *ab, const u8 *pgeo_table)
 3205{
 3206	struct ath12k_wmi_base *wmi_ab = &ab->wmi_ab;
 3207	struct wmi_pdev_set_bios_geo_table_cmd *cmd;
 3208	struct wmi_tlv *tlv;
 3209	struct sk_buff *skb;
 3210	int ret;
 3211	u8 *buf_ptr;
 3212	u32 len, sar_geo_len_aligned;
 3213	const u8 *pgeo_value = pgeo_table + ATH12K_ACPI_GEO_OFFSET_DATA_OFFSET;
 3214
 3215	sar_geo_len_aligned = roundup(ATH12K_ACPI_BIOS_SAR_GEO_OFFSET_LEN, sizeof(u32));
 3216	len = sizeof(*cmd) + TLV_HDR_SIZE + sar_geo_len_aligned;
 3217
 3218	skb = ath12k_wmi_alloc_skb(wmi_ab, len);
 3219	if (!skb)
 3220		return -ENOMEM;
 3221
 3222	cmd = (struct wmi_pdev_set_bios_geo_table_cmd *)skb->data;
 3223	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_SET_BIOS_GEO_TABLE_CMD,
 3224						 sizeof(*cmd));
 3225	cmd->pdev_id = cpu_to_le32(WMI_PDEV_ID_SOC);
 3226	cmd->geo_len = cpu_to_le32(ATH12K_ACPI_BIOS_SAR_GEO_OFFSET_LEN);
 3227
 3228	buf_ptr = skb->data + sizeof(*cmd);
 3229	tlv = (struct wmi_tlv *)buf_ptr;
 3230	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, sar_geo_len_aligned);
 3231	buf_ptr += TLV_HDR_SIZE;
 3232	memcpy(buf_ptr, pgeo_value, ATH12K_ACPI_BIOS_SAR_GEO_OFFSET_LEN);
 3233
 3234	ret = ath12k_wmi_cmd_send(&wmi_ab->wmi[0],
 3235				  skb,
 3236				  WMI_PDEV_SET_BIOS_GEO_TABLE_CMDID);
 3237	if (ret) {
 3238		ath12k_warn(ab,
 3239			    "failed to send WMI_PDEV_SET_BIOS_GEO_TABLE_CMDID %d\n",
 3240			    ret);
 3241		dev_kfree_skb(skb);
 3242	}
 3243
 3244	return ret;
 3245}
 3246
 3247int ath12k_wmi_delba_send(struct ath12k *ar, u32 vdev_id, const u8 *mac,
 3248			  u32 tid, u32 initiator, u32 reason)
 3249{
 3250	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3251	struct wmi_delba_send_cmd *cmd;
 3252	struct sk_buff *skb;
 3253	int ret;
 3254
 3255	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3256	if (!skb)
 3257		return -ENOMEM;
 3258
 3259	cmd = (struct wmi_delba_send_cmd *)skb->data;
 3260	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_DELBA_SEND_CMD,
 3261						 sizeof(*cmd));
 3262	cmd->vdev_id = cpu_to_le32(vdev_id);
 3263	ether_addr_copy(cmd->peer_macaddr.addr, mac);
 3264	cmd->tid = cpu_to_le32(tid);
 3265	cmd->initiator = cpu_to_le32(initiator);
 3266	cmd->reasoncode = cpu_to_le32(reason);
 3267
 3268	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3269		   "wmi delba send vdev_id 0x%X mac_addr %pM tid %u initiator %u reason %u\n",
 3270		   vdev_id, mac, tid, initiator, reason);
 3271
 3272	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_DELBA_SEND_CMDID);
 3273
 3274	if (ret) {
 3275		ath12k_warn(ar->ab,
 3276			    "failed to send WMI_DELBA_SEND_CMDID cmd\n");
 3277		dev_kfree_skb(skb);
 3278	}
 3279
 3280	return ret;
 3281}
 3282
 3283int ath12k_wmi_addba_set_resp(struct ath12k *ar, u32 vdev_id, const u8 *mac,
 3284			      u32 tid, u32 status)
 3285{
 3286	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3287	struct wmi_addba_setresponse_cmd *cmd;
 3288	struct sk_buff *skb;
 3289	int ret;
 3290
 3291	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3292	if (!skb)
 3293		return -ENOMEM;
 3294
 3295	cmd = (struct wmi_addba_setresponse_cmd *)skb->data;
 3296	cmd->tlv_header =
 3297		ath12k_wmi_tlv_cmd_hdr(WMI_TAG_ADDBA_SETRESPONSE_CMD,
 3298				       sizeof(*cmd));
 3299	cmd->vdev_id = cpu_to_le32(vdev_id);
 3300	ether_addr_copy(cmd->peer_macaddr.addr, mac);
 3301	cmd->tid = cpu_to_le32(tid);
 3302	cmd->statuscode = cpu_to_le32(status);
 3303
 3304	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3305		   "wmi addba set resp vdev_id 0x%X mac_addr %pM tid %u status %u\n",
 3306		   vdev_id, mac, tid, status);
 3307
 3308	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_ADDBA_SET_RESP_CMDID);
 3309
 3310	if (ret) {
 3311		ath12k_warn(ar->ab,
 3312			    "failed to send WMI_ADDBA_SET_RESP_CMDID cmd\n");
 3313		dev_kfree_skb(skb);
 3314	}
 3315
 3316	return ret;
 3317}
 3318
 3319int ath12k_wmi_addba_send(struct ath12k *ar, u32 vdev_id, const u8 *mac,
 3320			  u32 tid, u32 buf_size)
 3321{
 3322	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3323	struct wmi_addba_send_cmd *cmd;
 3324	struct sk_buff *skb;
 3325	int ret;
 3326
 3327	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3328	if (!skb)
 3329		return -ENOMEM;
 3330
 3331	cmd = (struct wmi_addba_send_cmd *)skb->data;
 3332	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_ADDBA_SEND_CMD,
 3333						 sizeof(*cmd));
 3334	cmd->vdev_id = cpu_to_le32(vdev_id);
 3335	ether_addr_copy(cmd->peer_macaddr.addr, mac);
 3336	cmd->tid = cpu_to_le32(tid);
 3337	cmd->buffersize = cpu_to_le32(buf_size);
 3338
 3339	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3340		   "wmi addba send vdev_id 0x%X mac_addr %pM tid %u bufsize %u\n",
 3341		   vdev_id, mac, tid, buf_size);
 3342
 3343	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_ADDBA_SEND_CMDID);
 3344
 3345	if (ret) {
 3346		ath12k_warn(ar->ab,
 3347			    "failed to send WMI_ADDBA_SEND_CMDID cmd\n");
 3348		dev_kfree_skb(skb);
 3349	}
 3350
 3351	return ret;
 3352}
 3353
 3354int ath12k_wmi_addba_clear_resp(struct ath12k *ar, u32 vdev_id, const u8 *mac)
 3355{
 3356	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3357	struct wmi_addba_clear_resp_cmd *cmd;
 3358	struct sk_buff *skb;
 3359	int ret;
 3360
 3361	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3362	if (!skb)
 3363		return -ENOMEM;
 3364
 3365	cmd = (struct wmi_addba_clear_resp_cmd *)skb->data;
 3366	cmd->tlv_header =
 3367		ath12k_wmi_tlv_cmd_hdr(WMI_TAG_ADDBA_CLEAR_RESP_CMD,
 3368				       sizeof(*cmd));
 3369	cmd->vdev_id = cpu_to_le32(vdev_id);
 3370	ether_addr_copy(cmd->peer_macaddr.addr, mac);
 3371
 3372	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3373		   "wmi addba clear resp vdev_id 0x%X mac_addr %pM\n",
 3374		   vdev_id, mac);
 3375
 3376	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_ADDBA_CLEAR_RESP_CMDID);
 3377
 3378	if (ret) {
 3379		ath12k_warn(ar->ab,
 3380			    "failed to send WMI_ADDBA_CLEAR_RESP_CMDID cmd\n");
 3381		dev_kfree_skb(skb);
 3382	}
 3383
 3384	return ret;
 3385}
 3386
 3387int ath12k_wmi_send_init_country_cmd(struct ath12k *ar,
 3388				     struct ath12k_wmi_init_country_arg *arg)
 3389{
 3390	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3391	struct wmi_init_country_cmd *cmd;
 3392	struct sk_buff *skb;
 3393	int ret;
 3394
 3395	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3396	if (!skb)
 3397		return -ENOMEM;
 3398
 3399	cmd = (struct wmi_init_country_cmd *)skb->data;
 3400	cmd->tlv_header =
 3401		ath12k_wmi_tlv_cmd_hdr(WMI_TAG_SET_INIT_COUNTRY_CMD,
 3402				       sizeof(*cmd));
 3403
 3404	cmd->pdev_id = cpu_to_le32(ar->pdev->pdev_id);
 3405
 3406	switch (arg->flags) {
 3407	case ALPHA_IS_SET:
 3408		cmd->init_cc_type = WMI_COUNTRY_INFO_TYPE_ALPHA;
 3409		memcpy(&cmd->cc_info.alpha2, arg->cc_info.alpha2, 3);
 3410		break;
 3411	case CC_IS_SET:
 3412		cmd->init_cc_type = cpu_to_le32(WMI_COUNTRY_INFO_TYPE_COUNTRY_CODE);
 3413		cmd->cc_info.country_code =
 3414			cpu_to_le32(arg->cc_info.country_code);
 3415		break;
 3416	case REGDMN_IS_SET:
 3417		cmd->init_cc_type = cpu_to_le32(WMI_COUNTRY_INFO_TYPE_REGDOMAIN);
 3418		cmd->cc_info.regdom_id = cpu_to_le32(arg->cc_info.regdom_id);
 3419		break;
 3420	default:
 3421		ret = -EINVAL;
 3422		goto out;
 3423	}
 3424
 3425	ret = ath12k_wmi_cmd_send(wmi, skb,
 3426				  WMI_SET_INIT_COUNTRY_CMDID);
 3427
 3428out:
 3429	if (ret) {
 3430		ath12k_warn(ar->ab,
 3431			    "failed to send WMI_SET_INIT_COUNTRY CMD :%d\n",
 3432			    ret);
 3433		dev_kfree_skb(skb);
 3434	}
 3435
 3436	return ret;
 3437}
 3438
 3439int ath12k_wmi_send_set_current_country_cmd(struct ath12k *ar,
 3440					    struct wmi_set_current_country_arg *arg)
 3441{
 3442	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3443	struct wmi_set_current_country_cmd *cmd;
 3444	struct sk_buff *skb;
 3445	int ret;
 3446
 3447	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3448	if (!skb)
 3449		return -ENOMEM;
 3450
 3451	cmd = (struct wmi_set_current_country_cmd *)skb->data;
 3452	cmd->tlv_header =
 3453		ath12k_wmi_tlv_cmd_hdr(WMI_TAG_SET_CURRENT_COUNTRY_CMD,
 3454				       sizeof(*cmd));
 3455
 3456	cmd->pdev_id = cpu_to_le32(ar->pdev->pdev_id);
 3457	memcpy(&cmd->new_alpha2, &arg->alpha2, sizeof(arg->alpha2));
 3458	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_SET_CURRENT_COUNTRY_CMDID);
 3459
 3460	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3461		   "set current country pdev id %d alpha2 %c%c\n",
 3462		   ar->pdev->pdev_id,
 3463		   arg->alpha2[0],
 3464		   arg->alpha2[1]);
 3465
 3466	if (ret) {
 3467		ath12k_warn(ar->ab,
 3468			    "failed to send WMI_SET_CURRENT_COUNTRY_CMDID: %d\n", ret);
 3469		dev_kfree_skb(skb);
 3470	}
 3471
 3472	return ret;
 3473}
 3474
 3475int ath12k_wmi_send_11d_scan_start_cmd(struct ath12k *ar,
 3476				       struct wmi_11d_scan_start_arg *arg)
 3477{
 3478	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3479	struct wmi_11d_scan_start_cmd *cmd;
 3480	struct sk_buff *skb;
 3481	int ret;
 3482
 3483	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3484	if (!skb)
 3485		return -ENOMEM;
 3486
 3487	cmd = (struct wmi_11d_scan_start_cmd *)skb->data;
 3488	cmd->tlv_header =
 3489		ath12k_wmi_tlv_cmd_hdr(WMI_TAG_11D_SCAN_START_CMD,
 3490				       sizeof(*cmd));
 3491
 3492	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 3493	cmd->scan_period_msec = cpu_to_le32(arg->scan_period_msec);
 3494	cmd->start_interval_msec = cpu_to_le32(arg->start_interval_msec);
 3495	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_11D_SCAN_START_CMDID);
 3496
 3497	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3498		   "send 11d scan start vdev id %d period %d ms internal %d ms\n",
 3499		   arg->vdev_id, arg->scan_period_msec,
 3500		   arg->start_interval_msec);
 3501
 3502	if (ret) {
 3503		ath12k_warn(ar->ab,
 3504			    "failed to send WMI_11D_SCAN_START_CMDID: %d\n", ret);
 3505		dev_kfree_skb(skb);
 3506	}
 3507
 3508	return ret;
 3509}
 3510
 3511int ath12k_wmi_send_11d_scan_stop_cmd(struct ath12k *ar, u32 vdev_id)
 3512{
 3513	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3514	struct wmi_11d_scan_stop_cmd *cmd;
 3515	struct sk_buff *skb;
 3516	int ret;
 3517
 3518	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd));
 3519	if (!skb)
 3520		return -ENOMEM;
 3521
 3522	cmd = (struct wmi_11d_scan_stop_cmd *)skb->data;
 3523	cmd->tlv_header =
 3524		ath12k_wmi_tlv_cmd_hdr(WMI_TAG_11D_SCAN_STOP_CMD,
 3525				       sizeof(*cmd));
 3526
 3527	cmd->vdev_id = cpu_to_le32(vdev_id);
 3528	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_11D_SCAN_STOP_CMDID);
 3529
 3530	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3531		   "send 11d scan stop vdev id %d\n",
 3532		   cmd->vdev_id);
 3533
 3534	if (ret) {
 3535		ath12k_warn(ar->ab,
 3536			    "failed to send WMI_11D_SCAN_STOP_CMDID: %d\n", ret);
 3537		dev_kfree_skb(skb);
 3538	}
 3539
 3540	return ret;
 3541}
 3542
 3543int
 3544ath12k_wmi_send_twt_enable_cmd(struct ath12k *ar, u32 pdev_id)
 3545{
 3546	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3547	struct ath12k_base *ab = wmi->wmi_ab->ab;
 3548	struct wmi_twt_enable_params_cmd *cmd;
 3549	struct sk_buff *skb;
 3550	int ret, len;
 3551
 3552	len = sizeof(*cmd);
 3553
 3554	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 3555	if (!skb)
 3556		return -ENOMEM;
 3557
 3558	cmd = (struct wmi_twt_enable_params_cmd *)skb->data;
 3559	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_TWT_ENABLE_CMD,
 3560						 len);
 3561	cmd->pdev_id = cpu_to_le32(pdev_id);
 3562	cmd->sta_cong_timer_ms = cpu_to_le32(ATH12K_TWT_DEF_STA_CONG_TIMER_MS);
 3563	cmd->default_slot_size = cpu_to_le32(ATH12K_TWT_DEF_DEFAULT_SLOT_SIZE);
 3564	cmd->congestion_thresh_setup =
 3565		cpu_to_le32(ATH12K_TWT_DEF_CONGESTION_THRESH_SETUP);
 3566	cmd->congestion_thresh_teardown =
 3567		cpu_to_le32(ATH12K_TWT_DEF_CONGESTION_THRESH_TEARDOWN);
 3568	cmd->congestion_thresh_critical =
 3569		cpu_to_le32(ATH12K_TWT_DEF_CONGESTION_THRESH_CRITICAL);
 3570	cmd->interference_thresh_teardown =
 3571		cpu_to_le32(ATH12K_TWT_DEF_INTERFERENCE_THRESH_TEARDOWN);
 3572	cmd->interference_thresh_setup =
 3573		cpu_to_le32(ATH12K_TWT_DEF_INTERFERENCE_THRESH_SETUP);
 3574	cmd->min_no_sta_setup = cpu_to_le32(ATH12K_TWT_DEF_MIN_NO_STA_SETUP);
 3575	cmd->min_no_sta_teardown = cpu_to_le32(ATH12K_TWT_DEF_MIN_NO_STA_TEARDOWN);
 3576	cmd->no_of_bcast_mcast_slots =
 3577		cpu_to_le32(ATH12K_TWT_DEF_NO_OF_BCAST_MCAST_SLOTS);
 3578	cmd->min_no_twt_slots = cpu_to_le32(ATH12K_TWT_DEF_MIN_NO_TWT_SLOTS);
 3579	cmd->max_no_sta_twt = cpu_to_le32(ATH12K_TWT_DEF_MAX_NO_STA_TWT);
 3580	cmd->mode_check_interval = cpu_to_le32(ATH12K_TWT_DEF_MODE_CHECK_INTERVAL);
 3581	cmd->add_sta_slot_interval = cpu_to_le32(ATH12K_TWT_DEF_ADD_STA_SLOT_INTERVAL);
 3582	cmd->remove_sta_slot_interval =
 3583		cpu_to_le32(ATH12K_TWT_DEF_REMOVE_STA_SLOT_INTERVAL);
 3584	/* TODO add MBSSID support */
 3585	cmd->mbss_support = 0;
 3586
 3587	ret = ath12k_wmi_cmd_send(wmi, skb,
 3588				  WMI_TWT_ENABLE_CMDID);
 3589	if (ret) {
 3590		ath12k_warn(ab, "Failed to send WMI_TWT_ENABLE_CMDID");
 3591		dev_kfree_skb(skb);
 3592	}
 3593	return ret;
 3594}
 3595
 3596int
 3597ath12k_wmi_send_twt_disable_cmd(struct ath12k *ar, u32 pdev_id)
 3598{
 3599	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3600	struct ath12k_base *ab = wmi->wmi_ab->ab;
 3601	struct wmi_twt_disable_params_cmd *cmd;
 3602	struct sk_buff *skb;
 3603	int ret, len;
 3604
 3605	len = sizeof(*cmd);
 3606
 3607	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 3608	if (!skb)
 3609		return -ENOMEM;
 3610
 3611	cmd = (struct wmi_twt_disable_params_cmd *)skb->data;
 3612	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_TWT_DISABLE_CMD,
 3613						 len);
 3614	cmd->pdev_id = cpu_to_le32(pdev_id);
 3615
 3616	ret = ath12k_wmi_cmd_send(wmi, skb,
 3617				  WMI_TWT_DISABLE_CMDID);
 3618	if (ret) {
 3619		ath12k_warn(ab, "Failed to send WMI_TWT_DISABLE_CMDID");
 3620		dev_kfree_skb(skb);
 3621	}
 3622	return ret;
 3623}
 3624
 3625int
 3626ath12k_wmi_send_obss_spr_cmd(struct ath12k *ar, u32 vdev_id,
 3627			     struct ieee80211_he_obss_pd *he_obss_pd)
 3628{
 3629	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3630	struct ath12k_base *ab = wmi->wmi_ab->ab;
 3631	struct wmi_obss_spatial_reuse_params_cmd *cmd;
 3632	struct sk_buff *skb;
 3633	int ret, len;
 3634
 3635	len = sizeof(*cmd);
 3636
 3637	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 3638	if (!skb)
 3639		return -ENOMEM;
 3640
 3641	cmd = (struct wmi_obss_spatial_reuse_params_cmd *)skb->data;
 3642	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_OBSS_SPATIAL_REUSE_SET_CMD,
 3643						 len);
 3644	cmd->vdev_id = cpu_to_le32(vdev_id);
 3645	cmd->enable = cpu_to_le32(he_obss_pd->enable);
 3646	cmd->obss_min = a_cpu_to_sle32(he_obss_pd->min_offset);
 3647	cmd->obss_max = a_cpu_to_sle32(he_obss_pd->max_offset);
 3648
 3649	ret = ath12k_wmi_cmd_send(wmi, skb,
 3650				  WMI_PDEV_OBSS_PD_SPATIAL_REUSE_CMDID);
 3651	if (ret) {
 3652		ath12k_warn(ab,
 3653			    "Failed to send WMI_PDEV_OBSS_PD_SPATIAL_REUSE_CMDID");
 3654		dev_kfree_skb(skb);
 3655	}
 3656	return ret;
 3657}
 3658
 3659int ath12k_wmi_obss_color_cfg_cmd(struct ath12k *ar, u32 vdev_id,
 3660				  u8 bss_color, u32 period,
 3661				  bool enable)
 3662{
 3663	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3664	struct ath12k_base *ab = wmi->wmi_ab->ab;
 3665	struct wmi_obss_color_collision_cfg_params_cmd *cmd;
 3666	struct sk_buff *skb;
 3667	int ret, len;
 3668
 3669	len = sizeof(*cmd);
 3670
 3671	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 3672	if (!skb)
 3673		return -ENOMEM;
 3674
 3675	cmd = (struct wmi_obss_color_collision_cfg_params_cmd *)skb->data;
 3676	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_OBSS_COLOR_COLLISION_DET_CONFIG,
 3677						 len);
 3678	cmd->vdev_id = cpu_to_le32(vdev_id);
 3679	cmd->evt_type = enable ? cpu_to_le32(ATH12K_OBSS_COLOR_COLLISION_DETECTION) :
 3680		cpu_to_le32(ATH12K_OBSS_COLOR_COLLISION_DETECTION_DISABLE);
 3681	cmd->current_bss_color = cpu_to_le32(bss_color);
 3682	cmd->detection_period_ms = cpu_to_le32(period);
 3683	cmd->scan_period_ms = cpu_to_le32(ATH12K_BSS_COLOR_COLLISION_SCAN_PERIOD_MS);
 3684	cmd->free_slot_expiry_time_ms = 0;
 3685	cmd->flags = 0;
 3686
 3687	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3688		   "wmi_send_obss_color_collision_cfg id %d type %d bss_color %d detect_period %d scan_period %d\n",
 3689		   cmd->vdev_id, cmd->evt_type, cmd->current_bss_color,
 3690		   cmd->detection_period_ms, cmd->scan_period_ms);
 3691
 3692	ret = ath12k_wmi_cmd_send(wmi, skb,
 3693				  WMI_OBSS_COLOR_COLLISION_DET_CONFIG_CMDID);
 3694	if (ret) {
 3695		ath12k_warn(ab, "Failed to send WMI_OBSS_COLOR_COLLISION_DET_CONFIG_CMDID");
 3696		dev_kfree_skb(skb);
 3697	}
 3698	return ret;
 3699}
 3700
 3701int ath12k_wmi_send_bss_color_change_enable_cmd(struct ath12k *ar, u32 vdev_id,
 3702						bool enable)
 3703{
 3704	struct ath12k_wmi_pdev *wmi = ar->wmi;
 3705	struct ath12k_base *ab = wmi->wmi_ab->ab;
 3706	struct wmi_bss_color_change_enable_params_cmd *cmd;
 3707	struct sk_buff *skb;
 3708	int ret, len;
 3709
 3710	len = sizeof(*cmd);
 3711
 3712	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 3713	if (!skb)
 3714		return -ENOMEM;
 3715
 3716	cmd = (struct wmi_bss_color_change_enable_params_cmd *)skb->data;
 3717	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_BSS_COLOR_CHANGE_ENABLE,
 3718						 len);
 3719	cmd->vdev_id = cpu_to_le32(vdev_id);
 3720	cmd->enable = enable ? cpu_to_le32(1) : 0;
 3721
 3722	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3723		   "wmi_send_bss_color_change_enable id %d enable %d\n",
 3724		   cmd->vdev_id, cmd->enable);
 3725
 3726	ret = ath12k_wmi_cmd_send(wmi, skb,
 3727				  WMI_BSS_COLOR_CHANGE_ENABLE_CMDID);
 3728	if (ret) {
 3729		ath12k_warn(ab, "Failed to send WMI_BSS_COLOR_CHANGE_ENABLE_CMDID");
 3730		dev_kfree_skb(skb);
 3731	}
 3732	return ret;
 3733}
 3734
 3735int ath12k_wmi_fils_discovery_tmpl(struct ath12k *ar, u32 vdev_id,
 3736				   struct sk_buff *tmpl)
 3737{
 3738	struct wmi_tlv *tlv;
 3739	struct sk_buff *skb;
 3740	void *ptr;
 3741	int ret, len;
 3742	size_t aligned_len;
 3743	struct wmi_fils_discovery_tmpl_cmd *cmd;
 3744
 3745	aligned_len = roundup(tmpl->len, 4);
 3746	len = sizeof(*cmd) + TLV_HDR_SIZE + aligned_len;
 3747
 3748	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3749		   "WMI vdev %i set FILS discovery template\n", vdev_id);
 3750
 3751	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
 3752	if (!skb)
 3753		return -ENOMEM;
 3754
 3755	cmd = (struct wmi_fils_discovery_tmpl_cmd *)skb->data;
 3756	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_FILS_DISCOVERY_TMPL_CMD,
 3757						 sizeof(*cmd));
 3758	cmd->vdev_id = cpu_to_le32(vdev_id);
 3759	cmd->buf_len = cpu_to_le32(tmpl->len);
 3760	ptr = skb->data + sizeof(*cmd);
 3761
 3762	tlv = ptr;
 3763	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, aligned_len);
 3764	memcpy(tlv->value, tmpl->data, tmpl->len);
 3765
 3766	ret = ath12k_wmi_cmd_send(ar->wmi, skb, WMI_FILS_DISCOVERY_TMPL_CMDID);
 3767	if (ret) {
 3768		ath12k_warn(ar->ab,
 3769			    "WMI vdev %i failed to send FILS discovery template command\n",
 3770			    vdev_id);
 3771		dev_kfree_skb(skb);
 3772	}
 3773	return ret;
 3774}
 3775
 3776int ath12k_wmi_probe_resp_tmpl(struct ath12k *ar, u32 vdev_id,
 3777			       struct sk_buff *tmpl)
 3778{
 3779	struct wmi_probe_tmpl_cmd *cmd;
 3780	struct ath12k_wmi_bcn_prb_info_params *probe_info;
 3781	struct wmi_tlv *tlv;
 3782	struct sk_buff *skb;
 3783	void *ptr;
 3784	int ret, len;
 3785	size_t aligned_len = roundup(tmpl->len, 4);
 3786
 3787	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3788		   "WMI vdev %i set probe response template\n", vdev_id);
 3789
 3790	len = sizeof(*cmd) + sizeof(*probe_info) + TLV_HDR_SIZE + aligned_len;
 3791
 3792	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
 3793	if (!skb)
 3794		return -ENOMEM;
 3795
 3796	cmd = (struct wmi_probe_tmpl_cmd *)skb->data;
 3797	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PRB_TMPL_CMD,
 3798						 sizeof(*cmd));
 3799	cmd->vdev_id = cpu_to_le32(vdev_id);
 3800	cmd->buf_len = cpu_to_le32(tmpl->len);
 3801
 3802	ptr = skb->data + sizeof(*cmd);
 3803
 3804	probe_info = ptr;
 3805	len = sizeof(*probe_info);
 3806	probe_info->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_BCN_PRB_INFO,
 3807							len);
 3808	probe_info->caps = 0;
 3809	probe_info->erp = 0;
 3810
 3811	ptr += sizeof(*probe_info);
 3812
 3813	tlv = ptr;
 3814	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, aligned_len);
 3815	memcpy(tlv->value, tmpl->data, tmpl->len);
 3816
 3817	ret = ath12k_wmi_cmd_send(ar->wmi, skb, WMI_PRB_TMPL_CMDID);
 3818	if (ret) {
 3819		ath12k_warn(ar->ab,
 3820			    "WMI vdev %i failed to send probe response template command\n",
 3821			    vdev_id);
 3822		dev_kfree_skb(skb);
 3823	}
 3824	return ret;
 3825}
 3826
 3827int ath12k_wmi_fils_discovery(struct ath12k *ar, u32 vdev_id, u32 interval,
 3828			      bool unsol_bcast_probe_resp_enabled)
 3829{
 3830	struct sk_buff *skb;
 3831	int ret, len;
 3832	struct wmi_fils_discovery_cmd *cmd;
 3833
 3834	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 3835		   "WMI vdev %i set %s interval to %u TU\n",
 3836		   vdev_id, unsol_bcast_probe_resp_enabled ?
 3837		   "unsolicited broadcast probe response" : "FILS discovery",
 3838		   interval);
 3839
 3840	len = sizeof(*cmd);
 3841	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
 3842	if (!skb)
 3843		return -ENOMEM;
 3844
 3845	cmd = (struct wmi_fils_discovery_cmd *)skb->data;
 3846	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_ENABLE_FILS_CMD,
 3847						 len);
 3848	cmd->vdev_id = cpu_to_le32(vdev_id);
 3849	cmd->interval = cpu_to_le32(interval);
 3850	cmd->config = cpu_to_le32(unsol_bcast_probe_resp_enabled);
 3851
 3852	ret = ath12k_wmi_cmd_send(ar->wmi, skb, WMI_ENABLE_FILS_CMDID);
 3853	if (ret) {
 3854		ath12k_warn(ar->ab,
 3855			    "WMI vdev %i failed to send FILS discovery enable/disable command\n",
 3856			    vdev_id);
 3857		dev_kfree_skb(skb);
 3858	}
 3859	return ret;
 3860}
 3861
 3862static void
 3863ath12k_wmi_obss_color_collision_event(struct ath12k_base *ab, struct sk_buff *skb)
 3864{
 3865	const struct wmi_obss_color_collision_event *ev;
 3866	struct ath12k_link_vif *arvif;
 3867	u32 vdev_id, evt_type;
 3868	u64 bitmap;
 3869
 3870	const void **tb __free(kfree) = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 3871	if (IS_ERR(tb)) {
 3872		ath12k_warn(ab, "failed to parse OBSS color collision tlv %ld\n",
 3873			    PTR_ERR(tb));
 3874		return;
 3875	}
 3876
 3877	ev = tb[WMI_TAG_OBSS_COLOR_COLLISION_EVT];
 3878	if (!ev) {
 3879		ath12k_warn(ab, "failed to fetch OBSS color collision event\n");
 3880		return;
 3881	}
 3882
 3883	vdev_id = le32_to_cpu(ev->vdev_id);
 3884	evt_type = le32_to_cpu(ev->evt_type);
 3885	bitmap = le64_to_cpu(ev->obss_color_bitmap);
 3886
 3887	guard(rcu)();
 3888
 3889	arvif = ath12k_mac_get_arvif_by_vdev_id(ab, vdev_id);
 3890	if (!arvif) {
 3891		ath12k_warn(ab, "no arvif found for vdev %u in OBSS color collision event\n",
 3892			    vdev_id);
 3893		return;
 3894	}
 3895
 3896	switch (evt_type) {
 3897	case WMI_BSS_COLOR_COLLISION_DETECTION:
 3898		ieee80211_obss_color_collision_notify(arvif->ahvif->vif,
 3899						      bitmap,
 3900						      arvif->link_id);
 3901		ath12k_dbg(ab, ATH12K_DBG_WMI,
 3902			   "obss color collision detected vdev %u event %d bitmap %016llx\n",
 3903			   vdev_id, evt_type, bitmap);
 3904		break;
 3905	case WMI_BSS_COLOR_COLLISION_DISABLE:
 3906	case WMI_BSS_COLOR_FREE_SLOT_TIMER_EXPIRY:
 3907	case WMI_BSS_COLOR_FREE_SLOT_AVAILABLE:
 3908		break;
 3909	default:
 3910		ath12k_warn(ab, "unknown OBSS color collision event type %d\n", evt_type);
 3911	}
 3912}
 3913
 3914static void
 3915ath12k_fill_band_to_mac_param(struct ath12k_base  *soc,
 3916			      struct ath12k_wmi_pdev_band_arg *arg)
 3917{
 3918	u8 i;
 3919	struct ath12k_wmi_hal_reg_capabilities_ext_arg *hal_reg_cap;
 3920	struct ath12k_pdev *pdev;
 3921
 3922	for (i = 0; i < soc->num_radios; i++) {
 3923		pdev = &soc->pdevs[i];
 3924		hal_reg_cap = &soc->hal_reg_cap[i];
 3925		arg[i].pdev_id = pdev->pdev_id;
 3926
 3927		switch (pdev->cap.supported_bands) {
 3928		case WMI_HOST_WLAN_2GHZ_5GHZ_CAP:
 3929			arg[i].start_freq = hal_reg_cap->low_2ghz_chan;
 3930			arg[i].end_freq = hal_reg_cap->high_5ghz_chan;
 3931			break;
 3932		case WMI_HOST_WLAN_2GHZ_CAP:
 3933			arg[i].start_freq = hal_reg_cap->low_2ghz_chan;
 3934			arg[i].end_freq = hal_reg_cap->high_2ghz_chan;
 3935			break;
 3936		case WMI_HOST_WLAN_5GHZ_CAP:
 3937			arg[i].start_freq = hal_reg_cap->low_5ghz_chan;
 3938			arg[i].end_freq = hal_reg_cap->high_5ghz_chan;
 3939			break;
 3940		default:
 3941			break;
 3942		}
 3943	}
 3944}
 3945
 3946static void
 3947ath12k_wmi_copy_resource_config(struct ath12k_base *ab,
 3948				struct ath12k_wmi_resource_config_params *wmi_cfg,
 3949				struct ath12k_wmi_resource_config_arg *tg_cfg)
 3950{
 3951	wmi_cfg->num_vdevs = cpu_to_le32(tg_cfg->num_vdevs);
 3952	wmi_cfg->num_peers = cpu_to_le32(tg_cfg->num_peers);
 3953	wmi_cfg->num_offload_peers = cpu_to_le32(tg_cfg->num_offload_peers);
 3954	wmi_cfg->num_offload_reorder_buffs =
 3955		cpu_to_le32(tg_cfg->num_offload_reorder_buffs);
 3956	wmi_cfg->num_peer_keys = cpu_to_le32(tg_cfg->num_peer_keys);
 3957	wmi_cfg->num_tids = cpu_to_le32(tg_cfg->num_tids);
 3958	wmi_cfg->ast_skid_limit = cpu_to_le32(tg_cfg->ast_skid_limit);
 3959	wmi_cfg->tx_chain_mask = cpu_to_le32(tg_cfg->tx_chain_mask);
 3960	wmi_cfg->rx_chain_mask = cpu_to_le32(tg_cfg->rx_chain_mask);
 3961	wmi_cfg->rx_timeout_pri[0] = cpu_to_le32(tg_cfg->rx_timeout_pri[0]);
 3962	wmi_cfg->rx_timeout_pri[1] = cpu_to_le32(tg_cfg->rx_timeout_pri[1]);
 3963	wmi_cfg->rx_timeout_pri[2] = cpu_to_le32(tg_cfg->rx_timeout_pri[2]);
 3964	wmi_cfg->rx_timeout_pri[3] = cpu_to_le32(tg_cfg->rx_timeout_pri[3]);
 3965	wmi_cfg->rx_decap_mode = cpu_to_le32(tg_cfg->rx_decap_mode);
 3966	wmi_cfg->scan_max_pending_req = cpu_to_le32(tg_cfg->scan_max_pending_req);
 3967	wmi_cfg->bmiss_offload_max_vdev = cpu_to_le32(tg_cfg->bmiss_offload_max_vdev);
 3968	wmi_cfg->roam_offload_max_vdev = cpu_to_le32(tg_cfg->roam_offload_max_vdev);
 3969	wmi_cfg->roam_offload_max_ap_profiles =
 3970		cpu_to_le32(tg_cfg->roam_offload_max_ap_profiles);
 3971	wmi_cfg->num_mcast_groups = cpu_to_le32(tg_cfg->num_mcast_groups);
 3972	wmi_cfg->num_mcast_table_elems = cpu_to_le32(tg_cfg->num_mcast_table_elems);
 3973	wmi_cfg->mcast2ucast_mode = cpu_to_le32(tg_cfg->mcast2ucast_mode);
 3974	wmi_cfg->tx_dbg_log_size = cpu_to_le32(tg_cfg->tx_dbg_log_size);
 3975	wmi_cfg->num_wds_entries = cpu_to_le32(tg_cfg->num_wds_entries);
 3976	wmi_cfg->dma_burst_size = cpu_to_le32(tg_cfg->dma_burst_size);
 3977	wmi_cfg->mac_aggr_delim = cpu_to_le32(tg_cfg->mac_aggr_delim);
 3978	wmi_cfg->rx_skip_defrag_timeout_dup_detection_check =
 3979		cpu_to_le32(tg_cfg->rx_skip_defrag_timeout_dup_detection_check);
 3980	wmi_cfg->vow_config = cpu_to_le32(tg_cfg->vow_config);
 3981	wmi_cfg->gtk_offload_max_vdev = cpu_to_le32(tg_cfg->gtk_offload_max_vdev);
 3982	wmi_cfg->num_msdu_desc = cpu_to_le32(tg_cfg->num_msdu_desc);
 3983	wmi_cfg->max_frag_entries = cpu_to_le32(tg_cfg->max_frag_entries);
 3984	wmi_cfg->num_tdls_vdevs = cpu_to_le32(tg_cfg->num_tdls_vdevs);
 3985	wmi_cfg->num_tdls_conn_table_entries =
 3986		cpu_to_le32(tg_cfg->num_tdls_conn_table_entries);
 3987	wmi_cfg->beacon_tx_offload_max_vdev =
 3988		cpu_to_le32(tg_cfg->beacon_tx_offload_max_vdev);
 3989	wmi_cfg->num_multicast_filter_entries =
 3990		cpu_to_le32(tg_cfg->num_multicast_filter_entries);
 3991	wmi_cfg->num_wow_filters = cpu_to_le32(tg_cfg->num_wow_filters);
 3992	wmi_cfg->num_keep_alive_pattern = cpu_to_le32(tg_cfg->num_keep_alive_pattern);
 3993	wmi_cfg->keep_alive_pattern_size = cpu_to_le32(tg_cfg->keep_alive_pattern_size);
 3994	wmi_cfg->max_tdls_concurrent_sleep_sta =
 3995		cpu_to_le32(tg_cfg->max_tdls_concurrent_sleep_sta);
 3996	wmi_cfg->max_tdls_concurrent_buffer_sta =
 3997		cpu_to_le32(tg_cfg->max_tdls_concurrent_buffer_sta);
 3998	wmi_cfg->wmi_send_separate = cpu_to_le32(tg_cfg->wmi_send_separate);
 3999	wmi_cfg->num_ocb_vdevs = cpu_to_le32(tg_cfg->num_ocb_vdevs);
 4000	wmi_cfg->num_ocb_channels = cpu_to_le32(tg_cfg->num_ocb_channels);
 4001	wmi_cfg->num_ocb_schedules = cpu_to_le32(tg_cfg->num_ocb_schedules);
 4002	wmi_cfg->bpf_instruction_size = cpu_to_le32(tg_cfg->bpf_instruction_size);
 4003	wmi_cfg->max_bssid_rx_filters = cpu_to_le32(tg_cfg->max_bssid_rx_filters);
 4004	wmi_cfg->use_pdev_id = cpu_to_le32(tg_cfg->use_pdev_id);
 4005	wmi_cfg->flag1 = cpu_to_le32(tg_cfg->atf_config |
 4006				     WMI_RSRC_CFG_FLAG1_BSS_CHANNEL_INFO_64 |
 4007				     WMI_RSRC_CFG_FLAG1_ACK_RSSI);
 4008	wmi_cfg->peer_map_unmap_version = cpu_to_le32(tg_cfg->peer_map_unmap_version);
 4009	wmi_cfg->sched_params = cpu_to_le32(tg_cfg->sched_params);
 4010	wmi_cfg->twt_ap_pdev_count = cpu_to_le32(tg_cfg->twt_ap_pdev_count);
 4011	wmi_cfg->twt_ap_sta_count = cpu_to_le32(tg_cfg->twt_ap_sta_count);
 4012	wmi_cfg->flags2 = le32_encode_bits(tg_cfg->peer_metadata_ver,
 4013					   WMI_RSRC_CFG_FLAGS2_RX_PEER_METADATA_VERSION);
 4014	wmi_cfg->host_service_flags = cpu_to_le32(tg_cfg->is_reg_cc_ext_event_supported <<
 4015				WMI_RSRC_CFG_HOST_SVC_FLAG_REG_CC_EXT_SUPPORT_BIT);
 4016	if (ab->hw_params->reoq_lut_support)
 4017		wmi_cfg->host_service_flags |=
 4018			cpu_to_le32(1 << WMI_RSRC_CFG_HOST_SVC_FLAG_REO_QREF_SUPPORT_BIT);
 4019	wmi_cfg->ema_max_vap_cnt = cpu_to_le32(tg_cfg->ema_max_vap_cnt);
 4020	wmi_cfg->ema_max_profile_period = cpu_to_le32(tg_cfg->ema_max_profile_period);
 4021	wmi_cfg->flags2 |= cpu_to_le32(WMI_RSRC_CFG_FLAGS2_CALC_NEXT_DTIM_COUNT_SET);
 4022}
 4023
 4024static int ath12k_init_cmd_send(struct ath12k_wmi_pdev *wmi,
 4025				struct ath12k_wmi_init_cmd_arg *arg)
 4026{
 4027	struct ath12k_base *ab = wmi->wmi_ab->ab;
 4028	struct sk_buff *skb;
 4029	struct wmi_init_cmd *cmd;
 4030	struct ath12k_wmi_resource_config_params *cfg;
 4031	struct ath12k_wmi_pdev_set_hw_mode_cmd *hw_mode;
 4032	struct ath12k_wmi_pdev_band_to_mac_params *band_to_mac;
 4033	struct ath12k_wmi_host_mem_chunk_params *host_mem_chunks;
 4034	struct wmi_tlv *tlv;
 4035	size_t ret, len;
 4036	void *ptr;
 4037	u32 hw_mode_len = 0;
 4038	u16 idx;
 4039
 4040	if (arg->hw_mode_id != WMI_HOST_HW_MODE_MAX)
 4041		hw_mode_len = sizeof(*hw_mode) + TLV_HDR_SIZE +
 4042			      (arg->num_band_to_mac * sizeof(*band_to_mac));
 4043
 4044	len = sizeof(*cmd) + TLV_HDR_SIZE + sizeof(*cfg) + hw_mode_len +
 4045	      (arg->num_mem_chunks ? (sizeof(*host_mem_chunks) * WMI_MAX_MEM_REQS) : 0);
 4046
 4047	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
 4048	if (!skb)
 4049		return -ENOMEM;
 4050
 4051	cmd = (struct wmi_init_cmd *)skb->data;
 4052
 4053	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_INIT_CMD,
 4054						 sizeof(*cmd));
 4055
 4056	ptr = skb->data + sizeof(*cmd);
 4057	cfg = ptr;
 4058
 4059	ath12k_wmi_copy_resource_config(ab, cfg, &arg->res_cfg);
 4060
 4061	cfg->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_RESOURCE_CONFIG,
 4062						 sizeof(*cfg));
 4063
 4064	ptr += sizeof(*cfg);
 4065	host_mem_chunks = ptr + TLV_HDR_SIZE;
 4066	len = sizeof(struct ath12k_wmi_host_mem_chunk_params);
 4067
 4068	for (idx = 0; idx < arg->num_mem_chunks; ++idx) {
 4069		host_mem_chunks[idx].tlv_header =
 4070			ath12k_wmi_tlv_hdr(WMI_TAG_WLAN_HOST_MEMORY_CHUNK,
 4071					   len);
 4072
 4073		host_mem_chunks[idx].ptr = cpu_to_le32(arg->mem_chunks[idx].paddr);
 4074		host_mem_chunks[idx].size = cpu_to_le32(arg->mem_chunks[idx].len);
 4075		host_mem_chunks[idx].req_id = cpu_to_le32(arg->mem_chunks[idx].req_id);
 4076
 4077		ath12k_dbg(ab, ATH12K_DBG_WMI,
 4078			   "WMI host mem chunk req_id %d paddr 0x%llx len %d\n",
 4079			   arg->mem_chunks[idx].req_id,
 4080			   (u64)arg->mem_chunks[idx].paddr,
 4081			   arg->mem_chunks[idx].len);
 4082	}
 4083	cmd->num_host_mem_chunks = cpu_to_le32(arg->num_mem_chunks);
 4084	len = sizeof(struct ath12k_wmi_host_mem_chunk_params) * arg->num_mem_chunks;
 4085
 4086	/* num_mem_chunks is zero */
 4087	tlv = ptr;
 4088	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, len);
 4089	ptr += TLV_HDR_SIZE + len;
 4090
 4091	if (arg->hw_mode_id != WMI_HOST_HW_MODE_MAX) {
 4092		hw_mode = (struct ath12k_wmi_pdev_set_hw_mode_cmd *)ptr;
 4093		hw_mode->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_SET_HW_MODE_CMD,
 4094							     sizeof(*hw_mode));
 4095
 4096		hw_mode->hw_mode_index = cpu_to_le32(arg->hw_mode_id);
 4097		hw_mode->num_band_to_mac = cpu_to_le32(arg->num_band_to_mac);
 4098
 4099		ptr += sizeof(*hw_mode);
 4100
 4101		len = arg->num_band_to_mac * sizeof(*band_to_mac);
 4102		tlv = ptr;
 4103		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, len);
 4104
 4105		ptr += TLV_HDR_SIZE;
 4106		len = sizeof(*band_to_mac);
 4107
 4108		for (idx = 0; idx < arg->num_band_to_mac; idx++) {
 4109			band_to_mac = (void *)ptr;
 4110
 4111			band_to_mac->tlv_header =
 4112				ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_BAND_TO_MAC,
 4113						       len);
 4114			band_to_mac->pdev_id = cpu_to_le32(arg->band_to_mac[idx].pdev_id);
 4115			band_to_mac->start_freq =
 4116				cpu_to_le32(arg->band_to_mac[idx].start_freq);
 4117			band_to_mac->end_freq =
 4118				cpu_to_le32(arg->band_to_mac[idx].end_freq);
 4119			ptr += sizeof(*band_to_mac);
 4120		}
 4121	}
 4122
 4123	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_INIT_CMDID);
 4124	if (ret) {
 4125		ath12k_warn(ab, "failed to send WMI_INIT_CMDID\n");
 4126		dev_kfree_skb(skb);
 4127	}
 4128
 4129	return ret;
 4130}
 4131
 4132int ath12k_wmi_pdev_lro_cfg(struct ath12k *ar,
 4133			    int pdev_id)
 4134{
 4135	struct ath12k_wmi_pdev_lro_config_cmd *cmd;
 4136	struct sk_buff *skb;
 4137	int ret;
 4138
 4139	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd));
 4140	if (!skb)
 4141		return -ENOMEM;
 4142
 4143	cmd = (struct ath12k_wmi_pdev_lro_config_cmd *)skb->data;
 4144	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_LRO_INFO_CMD,
 4145						 sizeof(*cmd));
 4146
 4147	get_random_bytes(cmd->th_4, sizeof(cmd->th_4));
 4148	get_random_bytes(cmd->th_6, sizeof(cmd->th_6));
 4149
 4150	cmd->pdev_id = cpu_to_le32(pdev_id);
 4151
 4152	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 4153		   "WMI lro cfg cmd pdev_id 0x%x\n", pdev_id);
 4154
 4155	ret = ath12k_wmi_cmd_send(ar->wmi, skb, WMI_LRO_CONFIG_CMDID);
 4156	if (ret) {
 4157		ath12k_warn(ar->ab,
 4158			    "failed to send lro cfg req wmi cmd\n");
 4159		goto err;
 4160	}
 4161
 4162	return 0;
 4163err:
 4164	dev_kfree_skb(skb);
 4165	return ret;
 4166}
 4167
 4168int ath12k_wmi_wait_for_service_ready(struct ath12k_base *ab)
 4169{
 4170	unsigned long time_left;
 4171
 4172	time_left = wait_for_completion_timeout(&ab->wmi_ab.service_ready,
 4173						WMI_SERVICE_READY_TIMEOUT_HZ);
 4174	if (!time_left)
 4175		return -ETIMEDOUT;
 4176
 4177	return 0;
 4178}
 4179
 4180int ath12k_wmi_wait_for_unified_ready(struct ath12k_base *ab)
 4181{
 4182	unsigned long time_left;
 4183
 4184	time_left = wait_for_completion_timeout(&ab->wmi_ab.unified_ready,
 4185						WMI_SERVICE_READY_TIMEOUT_HZ);
 4186	if (!time_left)
 4187		return -ETIMEDOUT;
 4188
 4189	return 0;
 4190}
 4191
 4192int ath12k_wmi_set_hw_mode(struct ath12k_base *ab,
 4193			   enum wmi_host_hw_mode_config_type mode)
 4194{
 4195	struct ath12k_wmi_pdev_set_hw_mode_cmd *cmd;
 4196	struct sk_buff *skb;
 4197	struct ath12k_wmi_base *wmi_ab = &ab->wmi_ab;
 4198	int len;
 4199	int ret;
 4200
 4201	len = sizeof(*cmd);
 4202
 4203	skb = ath12k_wmi_alloc_skb(wmi_ab, len);
 4204	if (!skb)
 4205		return -ENOMEM;
 4206
 4207	cmd = (struct ath12k_wmi_pdev_set_hw_mode_cmd *)skb->data;
 4208
 4209	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_PDEV_SET_HW_MODE_CMD,
 4210						 sizeof(*cmd));
 4211
 4212	cmd->pdev_id = WMI_PDEV_ID_SOC;
 4213	cmd->hw_mode_index = cpu_to_le32(mode);
 4214
 4215	ret = ath12k_wmi_cmd_send(&wmi_ab->wmi[0], skb, WMI_PDEV_SET_HW_MODE_CMDID);
 4216	if (ret) {
 4217		ath12k_warn(ab, "failed to send WMI_PDEV_SET_HW_MODE_CMDID\n");
 4218		dev_kfree_skb(skb);
 4219	}
 4220
 4221	return ret;
 4222}
 4223
 4224int ath12k_wmi_cmd_init(struct ath12k_base *ab)
 4225{
 4226	struct ath12k_wmi_base *wmi_ab = &ab->wmi_ab;
 4227	struct ath12k_wmi_init_cmd_arg arg = {};
 4228
 4229	if (test_bit(WMI_TLV_SERVICE_REG_CC_EXT_EVENT_SUPPORT,
 4230		     ab->wmi_ab.svc_map))
 4231		arg.res_cfg.is_reg_cc_ext_event_supported = true;
 4232
 4233	ab->hw_params->wmi_init(ab, &arg.res_cfg);
 4234	ab->wow.wmi_conf_rx_decap_mode = arg.res_cfg.rx_decap_mode;
 4235
 4236	arg.num_mem_chunks = wmi_ab->num_mem_chunks;
 4237	arg.hw_mode_id = wmi_ab->preferred_hw_mode;
 4238	arg.mem_chunks = wmi_ab->mem_chunks;
 4239
 4240	if (ab->hw_params->single_pdev_only)
 4241		arg.hw_mode_id = WMI_HOST_HW_MODE_MAX;
 4242
 4243	arg.num_band_to_mac = ab->num_radios;
 4244	ath12k_fill_band_to_mac_param(ab, arg.band_to_mac);
 4245
 4246	ab->dp.peer_metadata_ver = arg.res_cfg.peer_metadata_ver;
 4247
 4248	return ath12k_init_cmd_send(&wmi_ab->wmi[0], &arg);
 4249}
 4250
 4251int ath12k_wmi_vdev_spectral_conf(struct ath12k *ar,
 4252				  struct ath12k_wmi_vdev_spectral_conf_arg *arg)
 4253{
 4254	struct ath12k_wmi_vdev_spectral_conf_cmd *cmd;
 4255	struct sk_buff *skb;
 4256	int ret;
 4257
 4258	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd));
 4259	if (!skb)
 4260		return -ENOMEM;
 4261
 4262	cmd = (struct ath12k_wmi_vdev_spectral_conf_cmd *)skb->data;
 4263	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_SPECTRAL_CONFIGURE_CMD,
 4264						 sizeof(*cmd));
 4265	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
 4266	cmd->scan_count = cpu_to_le32(arg->scan_count);
 4267	cmd->scan_period = cpu_to_le32(arg->scan_period);
 4268	cmd->scan_priority = cpu_to_le32(arg->scan_priority);
 4269	cmd->scan_fft_size = cpu_to_le32(arg->scan_fft_size);
 4270	cmd->scan_gc_ena = cpu_to_le32(arg->scan_gc_ena);
 4271	cmd->scan_restart_ena = cpu_to_le32(arg->scan_restart_ena);
 4272	cmd->scan_noise_floor_ref = cpu_to_le32(arg->scan_noise_floor_ref);
 4273	cmd->scan_init_delay = cpu_to_le32(arg->scan_init_delay);
 4274	cmd->scan_nb_tone_thr = cpu_to_le32(arg->scan_nb_tone_thr);
 4275	cmd->scan_str_bin_thr = cpu_to_le32(arg->scan_str_bin_thr);
 4276	cmd->scan_wb_rpt_mode = cpu_to_le32(arg->scan_wb_rpt_mode);
 4277	cmd->scan_rssi_rpt_mode = cpu_to_le32(arg->scan_rssi_rpt_mode);
 4278	cmd->scan_rssi_thr = cpu_to_le32(arg->scan_rssi_thr);
 4279	cmd->scan_pwr_format = cpu_to_le32(arg->scan_pwr_format);
 4280	cmd->scan_rpt_mode = cpu_to_le32(arg->scan_rpt_mode);
 4281	cmd->scan_bin_scale = cpu_to_le32(arg->scan_bin_scale);
 4282	cmd->scan_dbm_adj = cpu_to_le32(arg->scan_dbm_adj);
 4283	cmd->scan_chn_mask = cpu_to_le32(arg->scan_chn_mask);
 4284
 4285	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 4286		   "WMI spectral scan config cmd vdev_id 0x%x\n",
 4287		   arg->vdev_id);
 4288
 4289	ret = ath12k_wmi_cmd_send(ar->wmi, skb,
 4290				  WMI_VDEV_SPECTRAL_SCAN_CONFIGURE_CMDID);
 4291	if (ret) {
 4292		ath12k_warn(ar->ab,
 4293			    "failed to send spectral scan config wmi cmd\n");
 4294		goto err;
 4295	}
 4296
 4297	return 0;
 4298err:
 4299	dev_kfree_skb(skb);
 4300	return ret;
 4301}
 4302
 4303int ath12k_wmi_vdev_spectral_enable(struct ath12k *ar, u32 vdev_id,
 4304				    u32 trigger, u32 enable)
 4305{
 4306	struct ath12k_wmi_vdev_spectral_enable_cmd *cmd;
 4307	struct sk_buff *skb;
 4308	int ret;
 4309
 4310	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd));
 4311	if (!skb)
 4312		return -ENOMEM;
 4313
 4314	cmd = (struct ath12k_wmi_vdev_spectral_enable_cmd *)skb->data;
 4315	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_SPECTRAL_ENABLE_CMD,
 4316						 sizeof(*cmd));
 4317
 4318	cmd->vdev_id = cpu_to_le32(vdev_id);
 4319	cmd->trigger_cmd = cpu_to_le32(trigger);
 4320	cmd->enable_cmd = cpu_to_le32(enable);
 4321
 4322	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 4323		   "WMI spectral enable cmd vdev id 0x%x\n",
 4324		   vdev_id);
 4325
 4326	ret = ath12k_wmi_cmd_send(ar->wmi, skb,
 4327				  WMI_VDEV_SPECTRAL_SCAN_ENABLE_CMDID);
 4328	if (ret) {
 4329		ath12k_warn(ar->ab,
 4330			    "failed to send spectral enable wmi cmd\n");
 4331		goto err;
 4332	}
 4333
 4334	return 0;
 4335err:
 4336	dev_kfree_skb(skb);
 4337	return ret;
 4338}
 4339
 4340int ath12k_wmi_pdev_dma_ring_cfg(struct ath12k *ar,
 4341				 struct ath12k_wmi_pdev_dma_ring_cfg_arg *arg)
 4342{
 4343	struct ath12k_wmi_pdev_dma_ring_cfg_req_cmd *cmd;
 4344	struct sk_buff *skb;
 4345	int ret;
 4346
 4347	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd));
 4348	if (!skb)
 4349		return -ENOMEM;
 4350
 4351	cmd = (struct ath12k_wmi_pdev_dma_ring_cfg_req_cmd *)skb->data;
 4352	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_DMA_RING_CFG_REQ,
 4353						 sizeof(*cmd));
 4354
 4355	cmd->pdev_id = cpu_to_le32(arg->pdev_id);
 4356	cmd->module_id = cpu_to_le32(arg->module_id);
 4357	cmd->base_paddr_lo = cpu_to_le32(arg->base_paddr_lo);
 4358	cmd->base_paddr_hi = cpu_to_le32(arg->base_paddr_hi);
 4359	cmd->head_idx_paddr_lo = cpu_to_le32(arg->head_idx_paddr_lo);
 4360	cmd->head_idx_paddr_hi = cpu_to_le32(arg->head_idx_paddr_hi);
 4361	cmd->tail_idx_paddr_lo = cpu_to_le32(arg->tail_idx_paddr_lo);
 4362	cmd->tail_idx_paddr_hi = cpu_to_le32(arg->tail_idx_paddr_hi);
 4363	cmd->num_elems = cpu_to_le32(arg->num_elems);
 4364	cmd->buf_size = cpu_to_le32(arg->buf_size);
 4365	cmd->num_resp_per_event = cpu_to_le32(arg->num_resp_per_event);
 4366	cmd->event_timeout_ms = cpu_to_le32(arg->event_timeout_ms);
 4367
 4368	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
 4369		   "WMI DMA ring cfg req cmd pdev_id 0x%x\n",
 4370		   arg->pdev_id);
 4371
 4372	ret = ath12k_wmi_cmd_send(ar->wmi, skb,
 4373				  WMI_PDEV_DMA_RING_CFG_REQ_CMDID);
 4374	if (ret) {
 4375		ath12k_warn(ar->ab,
 4376			    "failed to send dma ring cfg req wmi cmd\n");
 4377		goto err;
 4378	}
 4379
 4380	return 0;
 4381err:
 4382	dev_kfree_skb(skb);
 4383	return ret;
 4384}
 4385
 4386static int ath12k_wmi_dma_buf_entry_parse(struct ath12k_base *soc,
 4387					  u16 tag, u16 len,
 4388					  const void *ptr, void *data)
 4389{
 4390	struct ath12k_wmi_dma_buf_release_arg *arg = data;
 4391
 4392	if (tag != WMI_TAG_DMA_BUF_RELEASE_ENTRY)
 4393		return -EPROTO;
 4394
 4395	if (arg->num_buf_entry >= le32_to_cpu(arg->fixed.num_buf_release_entry))
 4396		return -ENOBUFS;
 4397
 4398	arg->num_buf_entry++;
 4399	return 0;
 4400}
 4401
 4402static int ath12k_wmi_dma_buf_meta_parse(struct ath12k_base *soc,
 4403					 u16 tag, u16 len,
 4404					 const void *ptr, void *data)
 4405{
 4406	struct ath12k_wmi_dma_buf_release_arg *arg = data;
 4407
 4408	if (tag != WMI_TAG_DMA_BUF_RELEASE_SPECTRAL_META_DATA)
 4409		return -EPROTO;
 4410
 4411	if (arg->num_meta >= le32_to_cpu(arg->fixed.num_meta_data_entry))
 4412		return -ENOBUFS;
 4413
 4414	arg->num_meta++;
 4415
 4416	return 0;
 4417}
 4418
 4419static int ath12k_wmi_dma_buf_parse(struct ath12k_base *ab,
 4420				    u16 tag, u16 len,
 4421				    const void *ptr, void *data)
 4422{
 4423	struct ath12k_wmi_dma_buf_release_arg *arg = data;
 4424	const struct ath12k_wmi_dma_buf_release_fixed_params *fixed;
 4425	u32 pdev_id;
 4426	int ret;
 4427
 4428	switch (tag) {
 4429	case WMI_TAG_DMA_BUF_RELEASE:
 4430		fixed = ptr;
 4431		arg->fixed = *fixed;
 4432		pdev_id = DP_HW2SW_MACID(le32_to_cpu(fixed->pdev_id));
 4433		arg->fixed.pdev_id = cpu_to_le32(pdev_id);
 4434		break;
 4435	case WMI_TAG_ARRAY_STRUCT:
 4436		if (!arg->buf_entry_done) {
 4437			arg->num_buf_entry = 0;
 4438			arg->buf_entry = ptr;
 4439
 4440			ret = ath12k_wmi_tlv_iter(ab, ptr, len,
 4441						  ath12k_wmi_dma_buf_entry_parse,
 4442						  arg);
 4443			if (ret) {
 4444				ath12k_warn(ab, "failed to parse dma buf entry tlv %d\n",
 4445					    ret);
 4446				return ret;
 4447			}
 4448
 4449			arg->buf_entry_done = true;
 4450		} else if (!arg->meta_data_done) {
 4451			arg->num_meta = 0;
 4452			arg->meta_data = ptr;
 4453
 4454			ret = ath12k_wmi_tlv_iter(ab, ptr, len,
 4455						  ath12k_wmi_dma_buf_meta_parse,
 4456						  arg);
 4457			if (ret) {
 4458				ath12k_warn(ab, "failed to parse dma buf meta tlv %d\n",
 4459					    ret);
 4460				return ret;
 4461			}
 4462
 4463			arg->meta_data_done = true;
 4464		}
 4465		break;
 4466	default:
 4467		break;
 4468	}
 4469	return 0;
 4470}
 4471
 4472static void ath12k_wmi_pdev_dma_ring_buf_release_event(struct ath12k_base *ab,
 4473						       struct sk_buff *skb)
 4474{
 4475	struct ath12k_wmi_dma_buf_release_arg arg = {};
 4476	struct ath12k_dbring_buf_release_event param;
 4477	int ret;
 4478
 4479	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 4480				  ath12k_wmi_dma_buf_parse,
 4481				  &arg);
 4482	if (ret) {
 4483		ath12k_warn(ab, "failed to parse dma buf release tlv %d\n", ret);
 4484		return;
 4485	}
 4486
 4487	param.fixed = arg.fixed;
 4488	param.buf_entry = arg.buf_entry;
 4489	param.num_buf_entry = arg.num_buf_entry;
 4490	param.meta_data = arg.meta_data;
 4491	param.num_meta = arg.num_meta;
 4492
 4493	ret = ath12k_dbring_buffer_release_event(ab, &param);
 4494	if (ret) {
 4495		ath12k_warn(ab, "failed to handle dma buf release event %d\n", ret);
 4496		return;
 4497	}
 4498}
 4499
 4500static int ath12k_wmi_hw_mode_caps_parse(struct ath12k_base *soc,
 4501					 u16 tag, u16 len,
 4502					 const void *ptr, void *data)
 4503{
 4504	struct ath12k_wmi_svc_rdy_ext_parse *svc_rdy_ext = data;
 4505	struct ath12k_wmi_hw_mode_cap_params *hw_mode_cap;
 4506	u32 phy_map = 0;
 4507
 4508	if (tag != WMI_TAG_HW_MODE_CAPABILITIES)
 4509		return -EPROTO;
 4510
 4511	if (svc_rdy_ext->n_hw_mode_caps >= svc_rdy_ext->arg.num_hw_modes)
 4512		return -ENOBUFS;
 4513
 4514	hw_mode_cap = container_of(ptr, struct ath12k_wmi_hw_mode_cap_params,
 4515				   hw_mode_id);
 4516	svc_rdy_ext->n_hw_mode_caps++;
 4517
 4518	phy_map = le32_to_cpu(hw_mode_cap->phy_id_map);
 4519	svc_rdy_ext->tot_phy_id += fls(phy_map);
 4520
 4521	return 0;
 4522}
 4523
 4524static int ath12k_wmi_hw_mode_caps(struct ath12k_base *soc,
 4525				   u16 len, const void *ptr, void *data)
 4526{
 4527	struct ath12k_svc_ext_info *svc_ext_info = &soc->wmi_ab.svc_ext_info;
 4528	struct ath12k_wmi_svc_rdy_ext_parse *svc_rdy_ext = data;
 4529	const struct ath12k_wmi_hw_mode_cap_params *hw_mode_caps;
 4530	enum wmi_host_hw_mode_config_type mode, pref;
 4531	u32 i;
 4532	int ret;
 4533
 4534	svc_rdy_ext->n_hw_mode_caps = 0;
 4535	svc_rdy_ext->hw_mode_caps = ptr;
 4536
 4537	ret = ath12k_wmi_tlv_iter(soc, ptr, len,
 4538				  ath12k_wmi_hw_mode_caps_parse,
 4539				  svc_rdy_ext);
 4540	if (ret) {
 4541		ath12k_warn(soc, "failed to parse tlv %d\n", ret);
 4542		return ret;
 4543	}
 4544
 4545	for (i = 0 ; i < svc_rdy_ext->n_hw_mode_caps; i++) {
 4546		hw_mode_caps = &svc_rdy_ext->hw_mode_caps[i];
 4547		mode = le32_to_cpu(hw_mode_caps->hw_mode_id);
 4548
 4549		if (mode >= WMI_HOST_HW_MODE_MAX)
 4550			continue;
 4551
 4552		pref = soc->wmi_ab.preferred_hw_mode;
 4553
 4554		if (ath12k_hw_mode_pri_map[mode] <= ath12k_hw_mode_pri_map[pref]) {
 4555			svc_rdy_ext->pref_hw_mode_caps = *hw_mode_caps;
 4556			soc->wmi_ab.preferred_hw_mode = mode;
 4557		}
 4558	}
 4559
 4560	svc_ext_info->num_hw_modes = svc_rdy_ext->n_hw_mode_caps;
 4561
 4562	ath12k_dbg(soc, ATH12K_DBG_WMI, "num hw modes %u preferred_hw_mode %d\n",
 4563		   svc_ext_info->num_hw_modes, soc->wmi_ab.preferred_hw_mode);
 4564
 4565	if (soc->wmi_ab.preferred_hw_mode == WMI_HOST_HW_MODE_MAX)
 4566		return -EINVAL;
 4567
 4568	return 0;
 4569}
 4570
 4571static int ath12k_wmi_mac_phy_caps_parse(struct ath12k_base *soc,
 4572					 u16 tag, u16 len,
 4573					 const void *ptr, void *data)
 4574{
 4575	struct ath12k_wmi_svc_rdy_ext_parse *svc_rdy_ext = data;
 4576
 4577	if (tag != WMI_TAG_MAC_PHY_CAPABILITIES)
 4578		return -EPROTO;
 4579
 4580	if (svc_rdy_ext->n_mac_phy_caps >= svc_rdy_ext->tot_phy_id)
 4581		return -ENOBUFS;
 4582
 4583	len = min_t(u16, len, sizeof(struct ath12k_wmi_mac_phy_caps_params));
 4584	if (!svc_rdy_ext->n_mac_phy_caps) {
 4585		svc_rdy_ext->mac_phy_caps = kzalloc((svc_rdy_ext->tot_phy_id) * len,
 4586						    GFP_ATOMIC);
 4587		if (!svc_rdy_ext->mac_phy_caps)
 4588			return -ENOMEM;
 4589	}
 4590
 4591	memcpy(svc_rdy_ext->mac_phy_caps + svc_rdy_ext->n_mac_phy_caps, ptr, len);
 4592	svc_rdy_ext->n_mac_phy_caps++;
 4593	return 0;
 4594}
 4595
 4596static int ath12k_wmi_ext_hal_reg_caps_parse(struct ath12k_base *soc,
 4597					     u16 tag, u16 len,
 4598					     const void *ptr, void *data)
 4599{
 4600	struct ath12k_wmi_svc_rdy_ext_parse *svc_rdy_ext = data;
 4601
 4602	if (tag != WMI_TAG_HAL_REG_CAPABILITIES_EXT)
 4603		return -EPROTO;
 4604
 4605	if (svc_rdy_ext->n_ext_hal_reg_caps >= svc_rdy_ext->arg.num_phy)
 4606		return -ENOBUFS;
 4607
 4608	svc_rdy_ext->n_ext_hal_reg_caps++;
 4609	return 0;
 4610}
 4611
 4612static int ath12k_wmi_ext_hal_reg_caps(struct ath12k_base *soc,
 4613				       u16 len, const void *ptr, void *data)
 4614{
 4615	struct ath12k_wmi_pdev *wmi_handle = &soc->wmi_ab.wmi[0];
 4616	struct ath12k_wmi_svc_rdy_ext_parse *svc_rdy_ext = data;
 4617	struct ath12k_wmi_hal_reg_capabilities_ext_arg reg_cap;
 4618	int ret;
 4619	u32 i;
 4620
 4621	svc_rdy_ext->n_ext_hal_reg_caps = 0;
 4622	svc_rdy_ext->ext_hal_reg_caps = ptr;
 4623	ret = ath12k_wmi_tlv_iter(soc, ptr, len,
 4624				  ath12k_wmi_ext_hal_reg_caps_parse,
 4625				  svc_rdy_ext);
 4626	if (ret) {
 4627		ath12k_warn(soc, "failed to parse tlv %d\n", ret);
 4628		return ret;
 4629	}
 4630
 4631	for (i = 0; i < svc_rdy_ext->arg.num_phy; i++) {
 4632		ret = ath12k_pull_reg_cap_svc_rdy_ext(wmi_handle,
 4633						      svc_rdy_ext->soc_hal_reg_caps,
 4634						      svc_rdy_ext->ext_hal_reg_caps, i,
 4635						      &reg_cap);
 4636		if (ret) {
 4637			ath12k_warn(soc, "failed to extract reg cap %d\n", i);
 4638			return ret;
 4639		}
 4640
 4641		if (reg_cap.phy_id >= MAX_RADIOS) {
 4642			ath12k_warn(soc, "unexpected phy id %u\n", reg_cap.phy_id);
 4643			return -EINVAL;
 4644		}
 4645
 4646		soc->hal_reg_cap[reg_cap.phy_id] = reg_cap;
 4647	}
 4648	return 0;
 4649}
 4650
 4651static int ath12k_wmi_ext_soc_hal_reg_caps_parse(struct ath12k_base *soc,
 4652						 u16 len, const void *ptr,
 4653						 void *data)
 4654{
 4655	struct ath12k_wmi_pdev *wmi_handle = &soc->wmi_ab.wmi[0];
 4656	struct ath12k_wmi_svc_rdy_ext_parse *svc_rdy_ext = data;
 4657	u8 hw_mode_id = le32_to_cpu(svc_rdy_ext->pref_hw_mode_caps.hw_mode_id);
 4658	u32 phy_id_map;
 4659	int pdev_index = 0;
 4660	int ret;
 4661
 4662	svc_rdy_ext->soc_hal_reg_caps = ptr;
 4663	svc_rdy_ext->arg.num_phy = le32_to_cpu(svc_rdy_ext->soc_hal_reg_caps->num_phy);
 4664
 4665	soc->num_radios = 0;
 4666	phy_id_map = le32_to_cpu(svc_rdy_ext->pref_hw_mode_caps.phy_id_map);
 4667	soc->fw_pdev_count = 0;
 4668
 4669	while (phy_id_map && soc->num_radios < MAX_RADIOS) {
 4670		ret = ath12k_pull_mac_phy_cap_svc_ready_ext(wmi_handle,
 4671							    svc_rdy_ext,
 4672							    hw_mode_id, soc->num_radios,
 4673							    &soc->pdevs[pdev_index]);
 4674		if (ret) {
 4675			ath12k_warn(soc, "failed to extract mac caps, idx :%d\n",
 4676				    soc->num_radios);
 4677			return ret;
 4678		}
 4679
 4680		soc->num_radios++;
 4681
 4682		/* For single_pdev_only targets,
 4683		 * save mac_phy capability in the same pdev
 4684		 */
 4685		if (soc->hw_params->single_pdev_only)
 4686			pdev_index = 0;
 4687		else
 4688			pdev_index = soc->num_radios;
 4689
 4690		/* TODO: mac_phy_cap prints */
 4691		phy_id_map >>= 1;
 4692	}
 4693
 4694	if (soc->hw_params->single_pdev_only) {
 4695		soc->num_radios = 1;
 4696		soc->pdevs[0].pdev_id = 0;
 4697	}
 4698
 4699	return 0;
 4700}
 4701
 4702static int ath12k_wmi_dma_ring_caps_parse(struct ath12k_base *soc,
 4703					  u16 tag, u16 len,
 4704					  const void *ptr, void *data)
 4705{
 4706	struct ath12k_wmi_dma_ring_caps_parse *parse = data;
 4707
 4708	if (tag != WMI_TAG_DMA_RING_CAPABILITIES)
 4709		return -EPROTO;
 4710
 4711	parse->n_dma_ring_caps++;
 4712	return 0;
 4713}
 4714
 4715static int ath12k_wmi_alloc_dbring_caps(struct ath12k_base *ab,
 4716					u32 num_cap)
 4717{
 4718	size_t sz;
 4719	void *ptr;
 4720
 4721	sz = num_cap * sizeof(struct ath12k_dbring_cap);
 4722	ptr = kzalloc(sz, GFP_ATOMIC);
 4723	if (!ptr)
 4724		return -ENOMEM;
 4725
 4726	ab->db_caps = ptr;
 4727	ab->num_db_cap = num_cap;
 4728
 4729	return 0;
 4730}
 4731
 4732static void ath12k_wmi_free_dbring_caps(struct ath12k_base *ab)
 4733{
 4734	kfree(ab->db_caps);
 4735	ab->db_caps = NULL;
 4736	ab->num_db_cap = 0;
 4737}
 4738
 4739static int ath12k_wmi_dma_ring_caps(struct ath12k_base *ab,
 4740				    u16 len, const void *ptr, void *data)
 4741{
 4742	struct ath12k_wmi_dma_ring_caps_parse *dma_caps_parse = data;
 4743	struct ath12k_wmi_dma_ring_caps_params *dma_caps;
 4744	struct ath12k_dbring_cap *dir_buff_caps;
 4745	int ret;
 4746	u32 i;
 4747
 4748	dma_caps_parse->n_dma_ring_caps = 0;
 4749	dma_caps = (struct ath12k_wmi_dma_ring_caps_params *)ptr;
 4750	ret = ath12k_wmi_tlv_iter(ab, ptr, len,
 4751				  ath12k_wmi_dma_ring_caps_parse,
 4752				  dma_caps_parse);
 4753	if (ret) {
 4754		ath12k_warn(ab, "failed to parse dma ring caps tlv %d\n", ret);
 4755		return ret;
 4756	}
 4757
 4758	if (!dma_caps_parse->n_dma_ring_caps)
 4759		return 0;
 4760
 4761	if (ab->num_db_cap) {
 4762		ath12k_warn(ab, "Already processed, so ignoring dma ring caps\n");
 4763		return 0;
 4764	}
 4765
 4766	ret = ath12k_wmi_alloc_dbring_caps(ab, dma_caps_parse->n_dma_ring_caps);
 4767	if (ret)
 4768		return ret;
 4769
 4770	dir_buff_caps = ab->db_caps;
 4771	for (i = 0; i < dma_caps_parse->n_dma_ring_caps; i++) {
 4772		if (le32_to_cpu(dma_caps[i].module_id) >= WMI_DIRECT_BUF_MAX) {
 4773			ath12k_warn(ab, "Invalid module id %d\n",
 4774				    le32_to_cpu(dma_caps[i].module_id));
 4775			ret = -EINVAL;
 4776			goto free_dir_buff;
 4777		}
 4778
 4779		dir_buff_caps[i].id = le32_to_cpu(dma_caps[i].module_id);
 4780		dir_buff_caps[i].pdev_id =
 4781			DP_HW2SW_MACID(le32_to_cpu(dma_caps[i].pdev_id));
 4782		dir_buff_caps[i].min_elem = le32_to_cpu(dma_caps[i].min_elem);
 4783		dir_buff_caps[i].min_buf_sz = le32_to_cpu(dma_caps[i].min_buf_sz);
 4784		dir_buff_caps[i].min_buf_align = le32_to_cpu(dma_caps[i].min_buf_align);
 4785	}
 4786
 4787	return 0;
 4788
 4789free_dir_buff:
 4790	ath12k_wmi_free_dbring_caps(ab);
 4791	return ret;
 4792}
 4793
 4794static void
 4795ath12k_wmi_save_mac_phy_info(struct ath12k_base *ab,
 4796			     const struct ath12k_wmi_mac_phy_caps_params *mac_phy_cap,
 4797			     struct ath12k_svc_ext_mac_phy_info *mac_phy_info)
 4798{
 4799	mac_phy_info->phy_id = __le32_to_cpu(mac_phy_cap->phy_id);
 4800	mac_phy_info->supported_bands = __le32_to_cpu(mac_phy_cap->supported_bands);
 4801	mac_phy_info->hw_freq_range.low_2ghz_freq =
 4802					__le32_to_cpu(mac_phy_cap->low_2ghz_chan_freq);
 4803	mac_phy_info->hw_freq_range.high_2ghz_freq =
 4804					__le32_to_cpu(mac_phy_cap->high_2ghz_chan_freq);
 4805	mac_phy_info->hw_freq_range.low_5ghz_freq =
 4806					__le32_to_cpu(mac_phy_cap->low_5ghz_chan_freq);
 4807	mac_phy_info->hw_freq_range.high_5ghz_freq =
 4808					__le32_to_cpu(mac_phy_cap->high_5ghz_chan_freq);
 4809}
 4810
 4811static void
 4812ath12k_wmi_save_all_mac_phy_info(struct ath12k_base *ab,
 4813				 struct ath12k_wmi_svc_rdy_ext_parse *svc_rdy_ext)
 4814{
 4815	struct ath12k_svc_ext_info *svc_ext_info = &ab->wmi_ab.svc_ext_info;
 4816	const struct ath12k_wmi_mac_phy_caps_params *mac_phy_cap;
 4817	const struct ath12k_wmi_hw_mode_cap_params *hw_mode_cap;
 4818	struct ath12k_svc_ext_mac_phy_info *mac_phy_info;
 4819	u32 hw_mode_id, phy_bit_map;
 4820	u8 hw_idx;
 4821
 4822	mac_phy_info = &svc_ext_info->mac_phy_info[0];
 4823	mac_phy_cap = svc_rdy_ext->mac_phy_caps;
 4824
 4825	for (hw_idx = 0; hw_idx < svc_ext_info->num_hw_modes; hw_idx++) {
 4826		hw_mode_cap = &svc_rdy_ext->hw_mode_caps[hw_idx];
 4827		hw_mode_id = __le32_to_cpu(hw_mode_cap->hw_mode_id);
 4828		phy_bit_map = __le32_to_cpu(hw_mode_cap->phy_id_map);
 4829
 4830		while (phy_bit_map) {
 4831			ath12k_wmi_save_mac_phy_info(ab, mac_phy_cap, mac_phy_info);
 4832			mac_phy_info->hw_mode_config_type =
 4833					le32_get_bits(hw_mode_cap->hw_mode_config_type,
 4834						      WMI_HW_MODE_CAP_CFG_TYPE);
 4835			ath12k_dbg(ab, ATH12K_DBG_WMI,
 4836				   "hw_idx %u hw_mode_id %u hw_mode_config_type %u supported_bands %u phy_id %u 2 GHz [%u - %u] 5 GHz [%u - %u]\n",
 4837				   hw_idx, hw_mode_id,
 4838				   mac_phy_info->hw_mode_config_type,
 4839				   mac_phy_info->supported_bands, mac_phy_info->phy_id,
 4840				   mac_phy_info->hw_freq_range.low_2ghz_freq,
 4841				   mac_phy_info->hw_freq_range.high_2ghz_freq,
 4842				   mac_phy_info->hw_freq_range.low_5ghz_freq,
 4843				   mac_phy_info->hw_freq_range.high_5ghz_freq);
 4844
 4845			mac_phy_cap++;
 4846			mac_phy_info++;
 4847
 4848			phy_bit_map >>= 1;
 4849		}
 4850	}
 4851}
 4852
 4853static int ath12k_wmi_svc_rdy_ext_parse(struct ath12k_base *ab,
 4854					u16 tag, u16 len,
 4855					const void *ptr, void *data)
 4856{
 4857	struct ath12k_wmi_pdev *wmi_handle = &ab->wmi_ab.wmi[0];
 4858	struct ath12k_wmi_svc_rdy_ext_parse *svc_rdy_ext = data;
 4859	int ret;
 4860
 4861	switch (tag) {
 4862	case WMI_TAG_SERVICE_READY_EXT_EVENT:
 4863		ret = ath12k_pull_svc_ready_ext(wmi_handle, ptr,
 4864						&svc_rdy_ext->arg);
 4865		if (ret) {
 4866			ath12k_warn(ab, "unable to extract ext params\n");
 4867			return ret;
 4868		}
 4869		break;
 4870
 4871	case WMI_TAG_SOC_MAC_PHY_HW_MODE_CAPS:
 4872		svc_rdy_ext->hw_caps = ptr;
 4873		svc_rdy_ext->arg.num_hw_modes =
 4874			le32_to_cpu(svc_rdy_ext->hw_caps->num_hw_modes);
 4875		break;
 4876
 4877	case WMI_TAG_SOC_HAL_REG_CAPABILITIES:
 4878		ret = ath12k_wmi_ext_soc_hal_reg_caps_parse(ab, len, ptr,
 4879							    svc_rdy_ext);
 4880		if (ret)
 4881			return ret;
 4882		break;
 4883
 4884	case WMI_TAG_ARRAY_STRUCT:
 4885		if (!svc_rdy_ext->hw_mode_done) {
 4886			ret = ath12k_wmi_hw_mode_caps(ab, len, ptr, svc_rdy_ext);
 4887			if (ret)
 4888				return ret;
 4889
 4890			svc_rdy_ext->hw_mode_done = true;
 4891		} else if (!svc_rdy_ext->mac_phy_done) {
 4892			svc_rdy_ext->n_mac_phy_caps = 0;
 4893			ret = ath12k_wmi_tlv_iter(ab, ptr, len,
 4894						  ath12k_wmi_mac_phy_caps_parse,
 4895						  svc_rdy_ext);
 4896			if (ret) {
 4897				ath12k_warn(ab, "failed to parse tlv %d\n", ret);
 4898				return ret;
 4899			}
 4900
 4901			ath12k_wmi_save_all_mac_phy_info(ab, svc_rdy_ext);
 4902
 4903			svc_rdy_ext->mac_phy_done = true;
 4904		} else if (!svc_rdy_ext->ext_hal_reg_done) {
 4905			ret = ath12k_wmi_ext_hal_reg_caps(ab, len, ptr, svc_rdy_ext);
 4906			if (ret)
 4907				return ret;
 4908
 4909			svc_rdy_ext->ext_hal_reg_done = true;
 4910		} else if (!svc_rdy_ext->mac_phy_chainmask_combo_done) {
 4911			svc_rdy_ext->mac_phy_chainmask_combo_done = true;
 4912		} else if (!svc_rdy_ext->mac_phy_chainmask_cap_done) {
 4913			svc_rdy_ext->mac_phy_chainmask_cap_done = true;
 4914		} else if (!svc_rdy_ext->oem_dma_ring_cap_done) {
 4915			svc_rdy_ext->oem_dma_ring_cap_done = true;
 4916		} else if (!svc_rdy_ext->dma_ring_cap_done) {
 4917			ret = ath12k_wmi_dma_ring_caps(ab, len, ptr,
 4918						       &svc_rdy_ext->dma_caps_parse);
 4919			if (ret)
 4920				return ret;
 4921
 4922			svc_rdy_ext->dma_ring_cap_done = true;
 4923		}
 4924		break;
 4925
 4926	default:
 4927		break;
 4928	}
 4929	return 0;
 4930}
 4931
 4932static int ath12k_service_ready_ext_event(struct ath12k_base *ab,
 4933					  struct sk_buff *skb)
 4934{
 4935	struct ath12k_wmi_svc_rdy_ext_parse svc_rdy_ext = { };
 4936	int ret;
 4937
 4938	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 4939				  ath12k_wmi_svc_rdy_ext_parse,
 4940				  &svc_rdy_ext);
 4941	if (ret) {
 4942		ath12k_warn(ab, "failed to parse tlv %d\n", ret);
 4943		goto err;
 4944	}
 4945
 4946	if (!test_bit(WMI_TLV_SERVICE_EXT2_MSG, ab->wmi_ab.svc_map))
 4947		complete(&ab->wmi_ab.service_ready);
 4948
 4949	kfree(svc_rdy_ext.mac_phy_caps);
 4950	return 0;
 4951
 4952err:
 4953	kfree(svc_rdy_ext.mac_phy_caps);
 4954	ath12k_wmi_free_dbring_caps(ab);
 4955	return ret;
 4956}
 4957
 4958static int ath12k_pull_svc_ready_ext2(struct ath12k_wmi_pdev *wmi_handle,
 4959				      const void *ptr,
 4960				      struct ath12k_wmi_svc_rdy_ext2_arg *arg)
 4961{
 4962	const struct wmi_service_ready_ext2_event *ev = ptr;
 4963
 4964	if (!ev)
 4965		return -EINVAL;
 4966
 4967	arg->reg_db_version = le32_to_cpu(ev->reg_db_version);
 4968	arg->hw_min_max_tx_power_2ghz = le32_to_cpu(ev->hw_min_max_tx_power_2ghz);
 4969	arg->hw_min_max_tx_power_5ghz = le32_to_cpu(ev->hw_min_max_tx_power_5ghz);
 4970	arg->chwidth_num_peer_caps = le32_to_cpu(ev->chwidth_num_peer_caps);
 4971	arg->preamble_puncture_bw = le32_to_cpu(ev->preamble_puncture_bw);
 4972	arg->max_user_per_ppdu_ofdma = le32_to_cpu(ev->max_user_per_ppdu_ofdma);
 4973	arg->max_user_per_ppdu_mumimo = le32_to_cpu(ev->max_user_per_ppdu_mumimo);
 4974	arg->target_cap_flags = le32_to_cpu(ev->target_cap_flags);
 4975	return 0;
 4976}
 4977
 4978static void ath12k_wmi_eht_caps_parse(struct ath12k_pdev *pdev, u32 band,
 4979				      const __le32 cap_mac_info[],
 4980				      const __le32 cap_phy_info[],
 4981				      const __le32 supp_mcs[],
 4982				      const struct ath12k_wmi_ppe_threshold_params *ppet,
 4983				       __le32 cap_info_internal)
 4984{
 4985	struct ath12k_band_cap *cap_band = &pdev->cap.band[band];
 4986	u32 support_320mhz;
 4987	u8 i;
 4988
 4989	if (band == NL80211_BAND_6GHZ)
 4990		support_320mhz = cap_band->eht_cap_phy_info[0] &
 4991					IEEE80211_EHT_PHY_CAP0_320MHZ_IN_6GHZ;
 4992
 4993	for (i = 0; i < WMI_MAX_EHTCAP_MAC_SIZE; i++)
 4994		cap_band->eht_cap_mac_info[i] = le32_to_cpu(cap_mac_info[i]);
 4995
 4996	for (i = 0; i < WMI_MAX_EHTCAP_PHY_SIZE; i++)
 4997		cap_band->eht_cap_phy_info[i] = le32_to_cpu(cap_phy_info[i]);
 4998
 4999	if (band == NL80211_BAND_6GHZ)
 5000		cap_band->eht_cap_phy_info[0] |= support_320mhz;
 5001
 5002	cap_band->eht_mcs_20_only = le32_to_cpu(supp_mcs[0]);
 5003	cap_band->eht_mcs_80 = le32_to_cpu(supp_mcs[1]);
 5004	if (band != NL80211_BAND_2GHZ) {
 5005		cap_band->eht_mcs_160 = le32_to_cpu(supp_mcs[2]);
 5006		cap_band->eht_mcs_320 = le32_to_cpu(supp_mcs[3]);
 5007	}
 5008
 5009	cap_band->eht_ppet.numss_m1 = le32_to_cpu(ppet->numss_m1);
 5010	cap_band->eht_ppet.ru_bit_mask = le32_to_cpu(ppet->ru_info);
 5011	for (i = 0; i < WMI_MAX_NUM_SS; i++)
 5012		cap_band->eht_ppet.ppet16_ppet8_ru3_ru0[i] =
 5013			le32_to_cpu(ppet->ppet16_ppet8_ru3_ru0[i]);
 5014
 5015	cap_band->eht_cap_info_internal = le32_to_cpu(cap_info_internal);
 5016}
 5017
 5018static int
 5019ath12k_wmi_tlv_mac_phy_caps_ext_parse(struct ath12k_base *ab,
 5020				      const struct ath12k_wmi_caps_ext_params *caps,
 5021				      struct ath12k_pdev *pdev)
 5022{
 5023	struct ath12k_band_cap *cap_band;
 5024	u32 bands, support_320mhz;
 5025	int i;
 5026
 5027	if (ab->hw_params->single_pdev_only) {
 5028		if (caps->hw_mode_id == WMI_HOST_HW_MODE_SINGLE) {
 5029			support_320mhz = le32_to_cpu(caps->eht_cap_phy_info_5ghz[0]) &
 5030				IEEE80211_EHT_PHY_CAP0_320MHZ_IN_6GHZ;
 5031			cap_band = &pdev->cap.band[NL80211_BAND_6GHZ];
 5032			cap_band->eht_cap_phy_info[0] |= support_320mhz;
 5033			return 0;
 5034		}
 5035
 5036		for (i = 0; i < ab->fw_pdev_count; i++) {
 5037			struct ath12k_fw_pdev *fw_pdev = &ab->fw_pdev[i];
 5038
 5039			if (fw_pdev->pdev_id == ath12k_wmi_caps_ext_get_pdev_id(caps) &&
 5040			    fw_pdev->phy_id == le32_to_cpu(caps->phy_id)) {
 5041				bands = fw_pdev->supported_bands;
 5042				break;
 5043			}
 5044		}
 5045
 5046		if (i == ab->fw_pdev_count)
 5047			return -EINVAL;
 5048	} else {
 5049		bands = pdev->cap.supported_bands;
 5050	}
 5051
 5052	if (bands & WMI_HOST_WLAN_2GHZ_CAP) {
 5053		ath12k_wmi_eht_caps_parse(pdev, NL80211_BAND_2GHZ,
 5054					  caps->eht_cap_mac_info_2ghz,
 5055					  caps->eht_cap_phy_info_2ghz,
 5056					  caps->eht_supp_mcs_ext_2ghz,
 5057					  &caps->eht_ppet_2ghz,
 5058					  caps->eht_cap_info_internal);
 5059	}
 5060
 5061	if (bands & WMI_HOST_WLAN_5GHZ_CAP) {
 5062		ath12k_wmi_eht_caps_parse(pdev, NL80211_BAND_5GHZ,
 5063					  caps->eht_cap_mac_info_5ghz,
 5064					  caps->eht_cap_phy_info_5ghz,
 5065					  caps->eht_supp_mcs_ext_5ghz,
 5066					  &caps->eht_ppet_5ghz,
 5067					  caps->eht_cap_info_internal);
 5068
 5069		ath12k_wmi_eht_caps_parse(pdev, NL80211_BAND_6GHZ,
 5070					  caps->eht_cap_mac_info_5ghz,
 5071					  caps->eht_cap_phy_info_5ghz,
 5072					  caps->eht_supp_mcs_ext_5ghz,
 5073					  &caps->eht_ppet_5ghz,
 5074					  caps->eht_cap_info_internal);
 5075	}
 5076
 5077	pdev->cap.eml_cap = le32_to_cpu(caps->eml_capability);
 5078	pdev->cap.mld_cap = le32_to_cpu(caps->mld_capability);
 5079
 5080	return 0;
 5081}
 5082
 5083static int ath12k_wmi_tlv_mac_phy_caps_ext(struct ath12k_base *ab, u16 tag,
 5084					   u16 len, const void *ptr,
 5085					   void *data)
 5086{
 5087	const struct ath12k_wmi_caps_ext_params *caps = ptr;
 5088	int i = 0, ret;
 5089
 5090	if (tag != WMI_TAG_MAC_PHY_CAPABILITIES_EXT)
 5091		return -EPROTO;
 5092
 5093	if (ab->hw_params->single_pdev_only) {
 5094		if (ab->wmi_ab.preferred_hw_mode != le32_to_cpu(caps->hw_mode_id) &&
 5095		    caps->hw_mode_id != WMI_HOST_HW_MODE_SINGLE)
 5096			return 0;
 5097	} else {
 5098		for (i = 0; i < ab->num_radios; i++) {
 5099			if (ab->pdevs[i].pdev_id ==
 5100			    ath12k_wmi_caps_ext_get_pdev_id(caps))
 5101				break;
 5102		}
 5103
 5104		if (i == ab->num_radios)
 5105			return -EINVAL;
 5106	}
 5107
 5108	ret = ath12k_wmi_tlv_mac_phy_caps_ext_parse(ab, caps, &ab->pdevs[i]);
 5109	if (ret) {
 5110		ath12k_warn(ab,
 5111			    "failed to parse extended MAC PHY capabilities for pdev %d: %d\n",
 5112			    ret, ab->pdevs[i].pdev_id);
 5113		return ret;
 5114	}
 5115
 5116	return 0;
 5117}
 5118
 5119static void
 5120ath12k_wmi_update_freq_info(struct ath12k_base *ab,
 5121			    struct ath12k_svc_ext_mac_phy_info *mac_cap,
 5122			    enum ath12k_hw_mode mode,
 5123			    u32 phy_id)
 5124{
 5125	struct ath12k_hw_mode_info *hw_mode_info = &ab->wmi_ab.hw_mode_info;
 5126	struct ath12k_hw_mode_freq_range_arg *mac_range;
 5127
 5128	mac_range = &hw_mode_info->freq_range_caps[mode][phy_id];
 5129
 5130	if (mac_cap->supported_bands & WMI_HOST_WLAN_2GHZ_CAP) {
 5131		mac_range->low_2ghz_freq = max_t(u32,
 5132						 mac_cap->hw_freq_range.low_2ghz_freq,
 5133						 ATH12K_MIN_2GHZ_FREQ);
 5134		mac_range->high_2ghz_freq = mac_cap->hw_freq_range.high_2ghz_freq ?
 5135					    min_t(u32,
 5136						  mac_cap->hw_freq_range.high_2ghz_freq,
 5137						  ATH12K_MAX_2GHZ_FREQ) :
 5138					    ATH12K_MAX_2GHZ_FREQ;
 5139	}
 5140
 5141	if (mac_cap->supported_bands & WMI_HOST_WLAN_5GHZ_CAP) {
 5142		mac_range->low_5ghz_freq = max_t(u32,
 5143						 mac_cap->hw_freq_range.low_5ghz_freq,
 5144						 ATH12K_MIN_5GHZ_FREQ);
 5145		mac_range->high_5ghz_freq = mac_cap->hw_freq_range.high_5ghz_freq ?
 5146					    min_t(u32,
 5147						  mac_cap->hw_freq_range.high_5ghz_freq,
 5148						  ATH12K_MAX_6GHZ_FREQ) :
 5149					    ATH12K_MAX_6GHZ_FREQ;
 5150	}
 5151}
 5152
 5153static bool
 5154ath12k_wmi_all_phy_range_updated(struct ath12k_base *ab,
 5155				 enum ath12k_hw_mode hwmode)
 5156{
 5157	struct ath12k_hw_mode_info *hw_mode_info = &ab->wmi_ab.hw_mode_info;
 5158	struct ath12k_hw_mode_freq_range_arg *mac_range;
 5159	u8 phy_id;
 5160
 5161	for (phy_id = 0; phy_id < MAX_RADIOS; phy_id++) {
 5162		mac_range = &hw_mode_info->freq_range_caps[hwmode][phy_id];
 5163		/* modify SBS/DBS range only when both phy for DBS are filled */
 5164		if (!mac_range->low_2ghz_freq && !mac_range->low_5ghz_freq)
 5165			return false;
 5166	}
 5167
 5168	return true;
 5169}
 5170
 5171static void ath12k_wmi_update_dbs_freq_info(struct ath12k_base *ab)
 5172{
 5173	struct ath12k_hw_mode_info *hw_mode_info = &ab->wmi_ab.hw_mode_info;
 5174	struct ath12k_hw_mode_freq_range_arg *mac_range;
 5175	u8 phy_id;
 5176
 5177	mac_range = hw_mode_info->freq_range_caps[ATH12K_HW_MODE_DBS];
 5178	/* Reset 5 GHz range for shared mac for DBS */
 5179	for (phy_id = 0; phy_id < MAX_RADIOS; phy_id++) {
 5180		if (mac_range[phy_id].low_2ghz_freq &&
 5181		    mac_range[phy_id].low_5ghz_freq) {
 5182			mac_range[phy_id].low_5ghz_freq = 0;
 5183			mac_range[phy_id].high_5ghz_freq = 0;
 5184		}
 5185	}
 5186}
 5187
 5188static u32
 5189ath12k_wmi_get_highest_5ghz_freq_from_range(struct ath12k_hw_mode_freq_range_arg *range)
 5190{
 5191	u32 highest_freq = 0;
 5192	u8 phy_id;
 5193
 5194	for (phy_id = 0; phy_id < MAX_RADIOS; phy_id++) {
 5195		if (range[phy_id].high_5ghz_freq > highest_freq)
 5196			highest_freq = range[phy_id].high_5ghz_freq;
 5197	}
 5198
 5199	return highest_freq ? highest_freq : ATH12K_MAX_6GHZ_FREQ;
 5200}
 5201
 5202static u32
 5203ath12k_wmi_get_lowest_5ghz_freq_from_range(struct ath12k_hw_mode_freq_range_arg *range)
 5204{
 5205	u32 lowest_freq = 0;
 5206	u8 phy_id;
 5207
 5208	for (phy_id = 0; phy_id < MAX_RADIOS; phy_id++) {
 5209		if ((!lowest_freq && range[phy_id].low_5ghz_freq) ||
 5210		    range[phy_id].low_5ghz_freq < lowest_freq)
 5211			lowest_freq = range[phy_id].low_5ghz_freq;
 5212	}
 5213
 5214	return lowest_freq ? lowest_freq : ATH12K_MIN_5GHZ_FREQ;
 5215}
 5216
 5217static void
 5218ath12k_wmi_fill_upper_share_sbs_freq(struct ath12k_base *ab,
 5219				     u16 sbs_range_sep,
 5220				     struct ath12k_hw_mode_freq_range_arg *ref_freq)
 5221{
 5222	struct ath12k_hw_mode_info *hw_mode_info = &ab->wmi_ab.hw_mode_info;
 5223	struct ath12k_hw_mode_freq_range_arg *upper_sbs_freq_range;
 5224	u8 phy_id;
 5225
 5226	upper_sbs_freq_range =
 5227			hw_mode_info->freq_range_caps[ATH12K_HW_MODE_SBS_UPPER_SHARE];
 5228
 5229	for (phy_id = 0; phy_id < MAX_RADIOS; phy_id++) {
 5230		upper_sbs_freq_range[phy_id].low_2ghz_freq =
 5231						ref_freq[phy_id].low_2ghz_freq;
 5232		upper_sbs_freq_range[phy_id].high_2ghz_freq =
 5233						ref_freq[phy_id].high_2ghz_freq;
 5234
 5235		/* update for shared mac */
 5236		if (upper_sbs_freq_range[phy_id].low_2ghz_freq) {
 5237			upper_sbs_freq_range[phy_id].low_5ghz_freq = sbs_range_sep + 10;
 5238			upper_sbs_freq_range[phy_id].high_5ghz_freq =
 5239				ath12k_wmi_get_highest_5ghz_freq_from_range(ref_freq);
 5240		} else {
 5241			upper_sbs_freq_range[phy_id].low_5ghz_freq =
 5242				ath12k_wmi_get_lowest_5ghz_freq_from_range(ref_freq);
 5243			upper_sbs_freq_range[phy_id].high_5ghz_freq = sbs_range_sep;
 5244		}
 5245	}
 5246}
 5247
 5248static void
 5249ath12k_wmi_fill_lower_share_sbs_freq(struct ath12k_base *ab,
 5250				     u16 sbs_range_sep,
 5251				     struct ath12k_hw_mode_freq_range_arg *ref_freq)
 5252{
 5253	struct ath12k_hw_mode_info *hw_mode_info = &ab->wmi_ab.hw_mode_info;
 5254	struct ath12k_hw_mode_freq_range_arg *lower_sbs_freq_range;
 5255	u8 phy_id;
 5256
 5257	lower_sbs_freq_range =
 5258			hw_mode_info->freq_range_caps[ATH12K_HW_MODE_SBS_LOWER_SHARE];
 5259
 5260	for (phy_id = 0; phy_id < MAX_RADIOS; phy_id++) {
 5261		lower_sbs_freq_range[phy_id].low_2ghz_freq =
 5262						ref_freq[phy_id].low_2ghz_freq;
 5263		lower_sbs_freq_range[phy_id].high_2ghz_freq =
 5264						ref_freq[phy_id].high_2ghz_freq;
 5265
 5266		/* update for shared mac */
 5267		if (lower_sbs_freq_range[phy_id].low_2ghz_freq) {
 5268			lower_sbs_freq_range[phy_id].low_5ghz_freq =
 5269				ath12k_wmi_get_lowest_5ghz_freq_from_range(ref_freq);
 5270			lower_sbs_freq_range[phy_id].high_5ghz_freq = sbs_range_sep;
 5271		} else {
 5272			lower_sbs_freq_range[phy_id].low_5ghz_freq = sbs_range_sep + 10;
 5273			lower_sbs_freq_range[phy_id].high_5ghz_freq =
 5274				ath12k_wmi_get_highest_5ghz_freq_from_range(ref_freq);
 5275		}
 5276	}
 5277}
 5278
 5279static const char *ath12k_wmi_hw_mode_to_str(enum ath12k_hw_mode hw_mode)
 5280{
 5281	static const char * const mode_str[] = {
 5282		[ATH12K_HW_MODE_SMM] = "SMM",
 5283		[ATH12K_HW_MODE_DBS] = "DBS",
 5284		[ATH12K_HW_MODE_SBS] = "SBS",
 5285		[ATH12K_HW_MODE_SBS_UPPER_SHARE] = "SBS_UPPER_SHARE",
 5286		[ATH12K_HW_MODE_SBS_LOWER_SHARE] = "SBS_LOWER_SHARE",
 5287	};
 5288
 5289	if (hw_mode >= ARRAY_SIZE(mode_str))
 5290		return "Unknown";
 5291
 5292	return mode_str[hw_mode];
 5293}
 5294
 5295static void
 5296ath12k_wmi_dump_freq_range_per_mac(struct ath12k_base *ab,
 5297				   struct ath12k_hw_mode_freq_range_arg *freq_range,
 5298				   enum ath12k_hw_mode hw_mode)
 5299{
 5300	u8 i;
 5301
 5302	for (i = 0; i < MAX_RADIOS; i++)
 5303		if (freq_range[i].low_2ghz_freq || freq_range[i].low_5ghz_freq)
 5304			ath12k_dbg(ab, ATH12K_DBG_WMI,
 5305				   "frequency range: %s(%d) mac %d 2 GHz [%d - %d] 5 GHz [%d - %d]",
 5306				   ath12k_wmi_hw_mode_to_str(hw_mode),
 5307				   hw_mode, i,
 5308				   freq_range[i].low_2ghz_freq,
 5309				   freq_range[i].high_2ghz_freq,
 5310				   freq_range[i].low_5ghz_freq,
 5311				   freq_range[i].high_5ghz_freq);
 5312}
 5313
 5314static void ath12k_wmi_dump_freq_range(struct ath12k_base *ab)
 5315{
 5316	struct ath12k_hw_mode_freq_range_arg *freq_range;
 5317	u8 i;
 5318
 5319	for (i = ATH12K_HW_MODE_SMM; i < ATH12K_HW_MODE_MAX; i++) {
 5320		freq_range = ab->wmi_ab.hw_mode_info.freq_range_caps[i];
 5321		ath12k_wmi_dump_freq_range_per_mac(ab, freq_range, i);
 5322	}
 5323}
 5324
 5325static int ath12k_wmi_modify_sbs_freq(struct ath12k_base *ab, u8 phy_id)
 5326{
 5327	struct ath12k_hw_mode_info *hw_mode_info = &ab->wmi_ab.hw_mode_info;
 5328	struct ath12k_hw_mode_freq_range_arg *sbs_mac_range, *shared_mac_range;
 5329	struct ath12k_hw_mode_freq_range_arg *non_shared_range;
 5330	u8 shared_phy_id;
 5331
 5332	sbs_mac_range = &hw_mode_info->freq_range_caps[ATH12K_HW_MODE_SBS][phy_id];
 5333
 5334	/* if SBS mac range has both 2.4 and 5 GHz ranges, i.e. shared phy_id
 5335	 * keep the range as it is in SBS
 5336	 */
 5337	if (sbs_mac_range->low_2ghz_freq && sbs_mac_range->low_5ghz_freq)
 5338		return 0;
 5339
 5340	if (sbs_mac_range->low_2ghz_freq && !sbs_mac_range->low_5ghz_freq) {
 5341		ath12k_err(ab, "Invalid DBS/SBS mode with only 2.4Ghz");
 5342		ath12k_wmi_dump_freq_range_per_mac(ab, sbs_mac_range, ATH12K_HW_MODE_SBS);
 5343		return -EINVAL;
 5344	}
 5345
 5346	non_shared_range = sbs_mac_range;
 5347	/* if SBS mac range has only 5 GHz then it's the non-shared phy, so
 5348	 * modify the range as per the shared mac.
 5349	 */
 5350	shared_phy_id = phy_id ? 0 : 1;
 5351	shared_mac_range =
 5352		&hw_mode_info->freq_range_caps[ATH12K_HW_MODE_SBS][shared_phy_id];
 5353
 5354	if (shared_mac_range->low_5ghz_freq > non_shared_range->low_5ghz_freq) {
 5355		ath12k_dbg(ab, ATH12K_DBG_WMI, "high 5 GHz shared");
 5356		/* If the shared mac lower 5 GHz frequency is greater than
 5357		 * non-shared mac lower 5 GHz frequency then the shared mac has
 5358		 * high 5 GHz shared with 2.4 GHz. So non-shared mac's 5 GHz high
 5359		 * freq should be less than the shared mac's low 5 GHz freq.
 5360		 */
 5361		if (non_shared_range->high_5ghz_freq >=
 5362		    shared_mac_range->low_5ghz_freq)
 5363			non_shared_range->high_5ghz_freq =
 5364				max_t(u32, shared_mac_range->low_5ghz_freq - 10,
 5365				      non_shared_range->low_5ghz_freq);
 5366	} else if (shared_mac_range->high_5ghz_freq <
 5367		   non_shared_range->high_5ghz_freq) {
 5368		ath12k_dbg(ab, ATH12K_DBG_WMI, "low 5 GHz shared");
 5369		/* If the shared mac high 5 GHz frequency is less than
 5370		 * non-shared mac high 5 GHz frequency then the shared mac has
 5371		 * low 5 GHz shared with 2.4 GHz. So non-shared mac's 5 GHz low
 5372		 * freq should be greater than the shared mac's high 5 GHz freq.
 5373		 */
 5374		if (shared_mac_range->high_5ghz_freq >=
 5375		    non_shared_range->low_5ghz_freq)
 5376			non_shared_range->low_5ghz_freq =
 5377				min_t(u32, shared_mac_range->high_5ghz_freq + 10,
 5378				      non_shared_range->high_5ghz_freq);
 5379	} else {
 5380		ath12k_warn(ab, "invalid SBS range with all 5 GHz shared");
 5381		return -EINVAL;
 5382	}
 5383
 5384	return 0;
 5385}
 5386
 5387static void ath12k_wmi_update_sbs_freq_info(struct ath12k_base *ab)
 5388{
 5389	struct ath12k_hw_mode_info *hw_mode_info = &ab->wmi_ab.hw_mode_info;
 5390	struct ath12k_hw_mode_freq_range_arg *mac_range;
 5391	u16 sbs_range_sep;
 5392	u8 phy_id;
 5393	int ret;
 5394
 5395	mac_range = hw_mode_info->freq_range_caps[ATH12K_HW_MODE_SBS];
 5396
 5397	/* If sbs_lower_band_end_freq has a value, then the frequency range
 5398	 * will be split using that value.
 5399	 */
 5400	sbs_range_sep = ab->wmi_ab.sbs_lower_band_end_freq;
 5401	if (sbs_range_sep) {
 5402		ath12k_wmi_fill_upper_share_sbs_freq(ab, sbs_range_sep,
 5403						     mac_range);
 5404		ath12k_wmi_fill_lower_share_sbs_freq(ab, sbs_range_sep,
 5405						     mac_range);
 5406		/* Hardware specifies the range boundary with sbs_range_sep,
 5407		 * (i.e. the boundary between 5 GHz high and 5 GHz low),
 5408		 * reset the original one to make sure it will not get used.
 5409		 */
 5410		memset(mac_range, 0, sizeof(*mac_range) * MAX_RADIOS);
 5411		return;
 5412	}
 5413
 5414	/* If sbs_lower_band_end_freq is not set that means firmware will send one
 5415	 * shared mac range and one non-shared mac range. so update that freq.
 5416	 */
 5417	for (phy_id = 0; phy_id < MAX_RADIOS; phy_id++) {
 5418		ret = ath12k_wmi_modify_sbs_freq(ab, phy_id);
 5419		if (ret) {
 5420			memset(mac_range, 0, sizeof(*mac_range) * MAX_RADIOS);
 5421			break;
 5422		}
 5423	}
 5424}
 5425
 5426static void
 5427ath12k_wmi_update_mac_freq_info(struct ath12k_base *ab,
 5428				enum wmi_host_hw_mode_config_type hw_config_type,
 5429				u32 phy_id,
 5430				struct ath12k_svc_ext_mac_phy_info *mac_cap)
 5431{
 5432	if (phy_id >= MAX_RADIOS) {
 5433		ath12k_err(ab, "mac more than two not supported: %d", phy_id);
 5434		return;
 5435	}
 5436
 5437	ath12k_dbg(ab, ATH12K_DBG_WMI,
 5438		   "hw_mode_cfg %d mac %d band 0x%x SBS cutoff freq %d 2 GHz [%d - %d] 5 GHz [%d - %d]",
 5439		   hw_config_type, phy_id, mac_cap->supported_bands,
 5440		   ab->wmi_ab.sbs_lower_band_end_freq,
 5441		   mac_cap->hw_freq_range.low_2ghz_freq,
 5442		   mac_cap->hw_freq_range.high_2ghz_freq,
 5443		   mac_cap->hw_freq_range.low_5ghz_freq,
 5444		   mac_cap->hw_freq_range.high_5ghz_freq);
 5445
 5446	switch (hw_config_type) {
 5447	case WMI_HOST_HW_MODE_SINGLE:
 5448		if (phy_id) {
 5449			ath12k_dbg(ab, ATH12K_DBG_WMI, "mac phy 1 is not supported");
 5450			break;
 5451		}
 5452		ath12k_wmi_update_freq_info(ab, mac_cap, ATH12K_HW_MODE_SMM, phy_id);
 5453		break;
 5454
 5455	case WMI_HOST_HW_MODE_DBS:
 5456		if (!ath12k_wmi_all_phy_range_updated(ab, ATH12K_HW_MODE_DBS))
 5457			ath12k_wmi_update_freq_info(ab, mac_cap,
 5458						    ATH12K_HW_MODE_DBS, phy_id);
 5459		break;
 5460	case WMI_HOST_HW_MODE_DBS_SBS:
 5461	case WMI_HOST_HW_MODE_DBS_OR_SBS:
 5462		ath12k_wmi_update_freq_info(ab, mac_cap, ATH12K_HW_MODE_DBS, phy_id);
 5463		if (ab->wmi_ab.sbs_lower_band_end_freq ||
 5464		    mac_cap->hw_freq_range.low_5ghz_freq ||
 5465		    mac_cap->hw_freq_range.low_2ghz_freq)
 5466			ath12k_wmi_update_freq_info(ab, mac_cap, ATH12K_HW_MODE_SBS,
 5467						    phy_id);
 5468
 5469		if (ath12k_wmi_all_phy_range_updated(ab, ATH12K_HW_MODE_DBS))
 5470			ath12k_wmi_update_dbs_freq_info(ab);
 5471		if (ath12k_wmi_all_phy_range_updated(ab, ATH12K_HW_MODE_SBS))
 5472			ath12k_wmi_update_sbs_freq_info(ab);
 5473		break;
 5474	case WMI_HOST_HW_MODE_SBS:
 5475	case WMI_HOST_HW_MODE_SBS_PASSIVE:
 5476		ath12k_wmi_update_freq_info(ab, mac_cap, ATH12K_HW_MODE_SBS, phy_id);
 5477		if (ath12k_wmi_all_phy_range_updated(ab, ATH12K_HW_MODE_SBS))
 5478			ath12k_wmi_update_sbs_freq_info(ab);
 5479
 5480		break;
 5481	default:
 5482		break;
 5483	}
 5484}
 5485
 5486static bool ath12k_wmi_sbs_range_present(struct ath12k_base *ab)
 5487{
 5488	if (ath12k_wmi_all_phy_range_updated(ab, ATH12K_HW_MODE_SBS) ||
 5489	    (ab->wmi_ab.sbs_lower_band_end_freq &&
 5490	     ath12k_wmi_all_phy_range_updated(ab, ATH12K_HW_MODE_SBS_LOWER_SHARE) &&
 5491	     ath12k_wmi_all_phy_range_updated(ab, ATH12K_HW_MODE_SBS_UPPER_SHARE)))
 5492		return true;
 5493
 5494	return false;
 5495}
 5496
 5497static int ath12k_wmi_update_hw_mode_list(struct ath12k_base *ab)
 5498{
 5499	struct ath12k_svc_ext_info *svc_ext_info = &ab->wmi_ab.svc_ext_info;
 5500	struct ath12k_hw_mode_info *info = &ab->wmi_ab.hw_mode_info;
 5501	enum wmi_host_hw_mode_config_type hw_config_type;
 5502	struct ath12k_svc_ext_mac_phy_info *tmp;
 5503	bool dbs_mode = false, sbs_mode = false;
 5504	u32 i, j = 0;
 5505
 5506	if (!svc_ext_info->num_hw_modes) {
 5507		ath12k_err(ab, "invalid number of hw modes");
 5508		return -EINVAL;
 5509	}
 5510
 5511	ath12k_dbg(ab, ATH12K_DBG_WMI, "updated HW mode list: num modes %d",
 5512		   svc_ext_info->num_hw_modes);
 5513
 5514	memset(info->freq_range_caps, 0, sizeof(info->freq_range_caps));
 5515
 5516	for (i = 0; i < svc_ext_info->num_hw_modes; i++) {
 5517		if (j >= ATH12K_MAX_MAC_PHY_CAP)
 5518			return -EINVAL;
 5519
 5520		/* Update for MAC0 */
 5521		tmp = &svc_ext_info->mac_phy_info[j++];
 5522		hw_config_type = tmp->hw_mode_config_type;
 5523		ath12k_wmi_update_mac_freq_info(ab, hw_config_type, tmp->phy_id, tmp);
 5524
 5525		/* SBS and DBS have dual MAC. Up to 2 MACs are considered. */
 5526		if (hw_config_type == WMI_HOST_HW_MODE_DBS ||
 5527		    hw_config_type == WMI_HOST_HW_MODE_SBS_PASSIVE ||
 5528		    hw_config_type == WMI_HOST_HW_MODE_SBS ||
 5529		    hw_config_type == WMI_HOST_HW_MODE_DBS_OR_SBS) {
 5530			if (j >= ATH12K_MAX_MAC_PHY_CAP)
 5531				return -EINVAL;
 5532			/* Update for MAC1 */
 5533			tmp = &svc_ext_info->mac_phy_info[j++];
 5534			ath12k_wmi_update_mac_freq_info(ab, hw_config_type,
 5535							tmp->phy_id, tmp);
 5536
 5537			if (hw_config_type == WMI_HOST_HW_MODE_DBS ||
 5538			    hw_config_type == WMI_HOST_HW_MODE_DBS_OR_SBS)
 5539				dbs_mode = true;
 5540
 5541			if (ath12k_wmi_sbs_range_present(ab) &&
 5542			    (hw_config_type == WMI_HOST_HW_MODE_SBS_PASSIVE ||
 5543			     hw_config_type == WMI_HOST_HW_MODE_SBS ||
 5544			     hw_config_type == WMI_HOST_HW_MODE_DBS_OR_SBS))
 5545				sbs_mode = true;
 5546		}
 5547	}
 5548
 5549	info->support_dbs = dbs_mode;
 5550	info->support_sbs = sbs_mode;
 5551
 5552	ath12k_wmi_dump_freq_range(ab);
 5553
 5554	return 0;
 5555}
 5556
 5557static int ath12k_wmi_svc_rdy_ext2_parse(struct ath12k_base *ab,
 5558					 u16 tag, u16 len,
 5559					 const void *ptr, void *data)
 5560{
 5561	const struct ath12k_wmi_dbs_or_sbs_cap_params *dbs_or_sbs_caps;
 5562	struct ath12k_wmi_pdev *wmi_handle = &ab->wmi_ab.wmi[0];
 5563	struct ath12k_wmi_svc_rdy_ext2_parse *parse = data;
 5564	int ret;
 5565
 5566	switch (tag) {
 5567	case WMI_TAG_SERVICE_READY_EXT2_EVENT:
 5568		ret = ath12k_pull_svc_ready_ext2(wmi_handle, ptr,
 5569						 &parse->arg);
 5570		if (ret) {
 5571			ath12k_warn(ab,
 5572				    "failed to extract wmi service ready ext2 parameters: %d\n",
 5573				    ret);
 5574			return ret;
 5575		}
 5576		break;
 5577
 5578	case WMI_TAG_ARRAY_STRUCT:
 5579		if (!parse->dma_ring_cap_done) {
 5580			ret = ath12k_wmi_dma_ring_caps(ab, len, ptr,
 5581						       &parse->dma_caps_parse);
 5582			if (ret)
 5583				return ret;
 5584
 5585			parse->dma_ring_cap_done = true;
 5586		} else if (!parse->spectral_bin_scaling_done) {
 5587			/* TODO: This is a place-holder as WMI tag for
 5588			 * spectral scaling is before
 5589			 * WMI_TAG_MAC_PHY_CAPABILITIES_EXT
 5590			 */
 5591			parse->spectral_bin_scaling_done = true;
 5592		} else if (!parse->mac_phy_caps_ext_done) {
 5593			ret = ath12k_wmi_tlv_iter(ab, ptr, len,
 5594						  ath12k_wmi_tlv_mac_phy_caps_ext,
 5595						  parse);
 5596			if (ret) {
 5597				ath12k_warn(ab, "failed to parse extended MAC PHY capabilities WMI TLV: %d\n",
 5598					    ret);
 5599				return ret;
 5600			}
 5601
 5602			parse->mac_phy_caps_ext_done = true;
 5603		} else if (!parse->hal_reg_caps_ext2_done) {
 5604			parse->hal_reg_caps_ext2_done = true;
 5605		} else if (!parse->scan_radio_caps_ext2_done) {
 5606			parse->scan_radio_caps_ext2_done = true;
 5607		} else if (!parse->twt_caps_done) {
 5608			parse->twt_caps_done = true;
 5609		} else if (!parse->htt_msdu_idx_to_qtype_map_done) {
 5610			parse->htt_msdu_idx_to_qtype_map_done = true;
 5611		} else if (!parse->dbs_or_sbs_cap_ext_done) {
 5612			dbs_or_sbs_caps = ptr;
 5613			ab->wmi_ab.sbs_lower_band_end_freq =
 5614				__le32_to_cpu(dbs_or_sbs_caps->sbs_lower_band_end_freq);
 5615
 5616			ath12k_dbg(ab, ATH12K_DBG_WMI, "sbs_lower_band_end_freq %u\n",
 5617				   ab->wmi_ab.sbs_lower_band_end_freq);
 5618
 5619			ret = ath12k_wmi_update_hw_mode_list(ab);
 5620			if (ret) {
 5621				ath12k_warn(ab, "failed to update hw mode list: %d\n",
 5622					    ret);
 5623				return ret;
 5624			}
 5625
 5626			parse->dbs_or_sbs_cap_ext_done = true;
 5627		}
 5628
 5629		break;
 5630	default:
 5631		break;
 5632	}
 5633
 5634	return 0;
 5635}
 5636
 5637static int ath12k_service_ready_ext2_event(struct ath12k_base *ab,
 5638					   struct sk_buff *skb)
 5639{
 5640	struct ath12k_wmi_svc_rdy_ext2_parse svc_rdy_ext2 = { };
 5641	int ret;
 5642
 5643	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 5644				  ath12k_wmi_svc_rdy_ext2_parse,
 5645				  &svc_rdy_ext2);
 5646	if (ret) {
 5647		ath12k_warn(ab, "failed to parse ext2 event tlv %d\n", ret);
 5648		goto err;
 5649	}
 5650
 5651	complete(&ab->wmi_ab.service_ready);
 5652
 5653	return 0;
 5654
 5655err:
 5656	ath12k_wmi_free_dbring_caps(ab);
 5657	return ret;
 5658}
 5659
 5660static int ath12k_pull_vdev_start_resp_tlv(struct ath12k_base *ab, struct sk_buff *skb,
 5661					   struct wmi_vdev_start_resp_event *vdev_rsp)
 5662{
 5663	const void **tb;
 5664	const struct wmi_vdev_start_resp_event *ev;
 5665	int ret;
 5666
 5667	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 5668	if (IS_ERR(tb)) {
 5669		ret = PTR_ERR(tb);
 5670		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 5671		return ret;
 5672	}
 5673
 5674	ev = tb[WMI_TAG_VDEV_START_RESPONSE_EVENT];
 5675	if (!ev) {
 5676		ath12k_warn(ab, "failed to fetch vdev start resp ev");
 5677		kfree(tb);
 5678		return -EPROTO;
 5679	}
 5680
 5681	*vdev_rsp = *ev;
 5682
 5683	kfree(tb);
 5684	return 0;
 5685}
 5686
 5687static struct ath12k_reg_rule
 5688*create_ext_reg_rules_from_wmi(u32 num_reg_rules,
 5689			       struct ath12k_wmi_reg_rule_ext_params *wmi_reg_rule)
 5690{
 5691	struct ath12k_reg_rule *reg_rule_ptr;
 5692	u32 count;
 5693
 5694	reg_rule_ptr = kzalloc((num_reg_rules * sizeof(*reg_rule_ptr)),
 5695			       GFP_ATOMIC);
 5696
 5697	if (!reg_rule_ptr)
 5698		return NULL;
 5699
 5700	for (count = 0; count < num_reg_rules; count++) {
 5701		reg_rule_ptr[count].start_freq =
 5702			le32_get_bits(wmi_reg_rule[count].freq_info,
 5703				      REG_RULE_START_FREQ);
 5704		reg_rule_ptr[count].end_freq =
 5705			le32_get_bits(wmi_reg_rule[count].freq_info,
 5706				      REG_RULE_END_FREQ);
 5707		reg_rule_ptr[count].max_bw =
 5708			le32_get_bits(wmi_reg_rule[count].bw_pwr_info,
 5709				      REG_RULE_MAX_BW);
 5710		reg_rule_ptr[count].reg_power =
 5711			le32_get_bits(wmi_reg_rule[count].bw_pwr_info,
 5712				      REG_RULE_REG_PWR);
 5713		reg_rule_ptr[count].ant_gain =
 5714			le32_get_bits(wmi_reg_rule[count].bw_pwr_info,
 5715				      REG_RULE_ANT_GAIN);
 5716		reg_rule_ptr[count].flags =
 5717			le32_get_bits(wmi_reg_rule[count].flag_info,
 5718				      REG_RULE_FLAGS);
 5719		reg_rule_ptr[count].psd_flag =
 5720			le32_get_bits(wmi_reg_rule[count].psd_power_info,
 5721				      REG_RULE_PSD_INFO);
 5722		reg_rule_ptr[count].psd_eirp =
 5723			le32_get_bits(wmi_reg_rule[count].psd_power_info,
 5724				      REG_RULE_PSD_EIRP);
 5725	}
 5726
 5727	return reg_rule_ptr;
 5728}
 5729
 5730static u8 ath12k_wmi_ignore_num_extra_rules(struct ath12k_wmi_reg_rule_ext_params *rule,
 5731					    u32 num_reg_rules)
 5732{
 5733	u8 num_invalid_5ghz_rules = 0;
 5734	u32 count, start_freq;
 5735
 5736	for (count = 0; count < num_reg_rules; count++) {
 5737		start_freq = le32_get_bits(rule[count].freq_info, REG_RULE_START_FREQ);
 5738
 5739		if (start_freq >= ATH12K_MIN_6GHZ_FREQ)
 5740			num_invalid_5ghz_rules++;
 5741	}
 5742
 5743	return num_invalid_5ghz_rules;
 5744}
 5745
 5746static int ath12k_pull_reg_chan_list_ext_update_ev(struct ath12k_base *ab,
 5747						   struct sk_buff *skb,
 5748						   struct ath12k_reg_info *reg_info)
 5749{
 5750	const void **tb;
 5751	const struct wmi_reg_chan_list_cc_ext_event *ev;
 5752	struct ath12k_wmi_reg_rule_ext_params *ext_wmi_reg_rule;
 5753	u32 num_2g_reg_rules, num_5g_reg_rules;
 5754	u32 num_6g_reg_rules_ap[WMI_REG_CURRENT_MAX_AP_TYPE];
 5755	u32 num_6g_reg_rules_cl[WMI_REG_CURRENT_MAX_AP_TYPE][WMI_REG_MAX_CLIENT_TYPE];
 5756	u8 num_invalid_5ghz_ext_rules;
 5757	u32 total_reg_rules = 0;
 5758	int ret, i, j;
 5759
 5760	ath12k_dbg(ab, ATH12K_DBG_WMI, "processing regulatory ext channel list\n");
 5761
 5762	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 5763	if (IS_ERR(tb)) {
 5764		ret = PTR_ERR(tb);
 5765		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 5766		return ret;
 5767	}
 5768
 5769	ev = tb[WMI_TAG_REG_CHAN_LIST_CC_EXT_EVENT];
 5770	if (!ev) {
 5771		ath12k_warn(ab, "failed to fetch reg chan list ext update ev\n");
 5772		kfree(tb);
 5773		return -EPROTO;
 5774	}
 5775
 5776	reg_info->num_2g_reg_rules = le32_to_cpu(ev->num_2g_reg_rules);
 5777	reg_info->num_5g_reg_rules = le32_to_cpu(ev->num_5g_reg_rules);
 5778	reg_info->num_6g_reg_rules_ap[WMI_REG_INDOOR_AP] =
 5779		le32_to_cpu(ev->num_6g_reg_rules_ap_lpi);
 5780	reg_info->num_6g_reg_rules_ap[WMI_REG_STD_POWER_AP] =
 5781		le32_to_cpu(ev->num_6g_reg_rules_ap_sp);
 5782	reg_info->num_6g_reg_rules_ap[WMI_REG_VLP_AP] =
 5783		le32_to_cpu(ev->num_6g_reg_rules_ap_vlp);
 5784
 5785	for (i = 0; i < WMI_REG_MAX_CLIENT_TYPE; i++) {
 5786		reg_info->num_6g_reg_rules_cl[WMI_REG_INDOOR_AP][i] =
 5787			le32_to_cpu(ev->num_6g_reg_rules_cl_lpi[i]);
 5788		reg_info->num_6g_reg_rules_cl[WMI_REG_STD_POWER_AP][i] =
 5789			le32_to_cpu(ev->num_6g_reg_rules_cl_sp[i]);
 5790		reg_info->num_6g_reg_rules_cl[WMI_REG_VLP_AP][i] =
 5791			le32_to_cpu(ev->num_6g_reg_rules_cl_vlp[i]);
 5792	}
 5793
 5794	num_2g_reg_rules = reg_info->num_2g_reg_rules;
 5795	total_reg_rules += num_2g_reg_rules;
 5796	num_5g_reg_rules = reg_info->num_5g_reg_rules;
 5797	total_reg_rules += num_5g_reg_rules;
 5798
 5799	if (num_2g_reg_rules > MAX_REG_RULES || num_5g_reg_rules > MAX_REG_RULES) {
 5800		ath12k_warn(ab, "Num reg rules for 2G/5G exceeds max limit (num_2g_reg_rules: %d num_5g_reg_rules: %d max_rules: %d)\n",
 5801			    num_2g_reg_rules, num_5g_reg_rules, MAX_REG_RULES);
 5802		kfree(tb);
 5803		return -EINVAL;
 5804	}
 5805
 5806	for (i = 0; i < WMI_REG_CURRENT_MAX_AP_TYPE; i++) {
 5807		num_6g_reg_rules_ap[i] = reg_info->num_6g_reg_rules_ap[i];
 5808
 5809		if (num_6g_reg_rules_ap[i] > MAX_6GHZ_REG_RULES) {
 5810			ath12k_warn(ab, "Num 6G reg rules for AP mode(%d) exceeds max limit (num_6g_reg_rules_ap: %d, max_rules: %d)\n",
 5811				    i, num_6g_reg_rules_ap[i], MAX_6GHZ_REG_RULES);
 5812			kfree(tb);
 5813			return -EINVAL;
 5814		}
 5815
 5816		total_reg_rules += num_6g_reg_rules_ap[i];
 5817	}
 5818
 5819	for (i = 0; i < WMI_REG_MAX_CLIENT_TYPE; i++) {
 5820		num_6g_reg_rules_cl[WMI_REG_INDOOR_AP][i] =
 5821				reg_info->num_6g_reg_rules_cl[WMI_REG_INDOOR_AP][i];
 5822		total_reg_rules += num_6g_reg_rules_cl[WMI_REG_INDOOR_AP][i];
 5823
 5824		num_6g_reg_rules_cl[WMI_REG_STD_POWER_AP][i] =
 5825				reg_info->num_6g_reg_rules_cl[WMI_REG_STD_POWER_AP][i];
 5826		total_reg_rules += num_6g_reg_rules_cl[WMI_REG_STD_POWER_AP][i];
 5827
 5828		num_6g_reg_rules_cl[WMI_REG_VLP_AP][i] =
 5829				reg_info->num_6g_reg_rules_cl[WMI_REG_VLP_AP][i];
 5830		total_reg_rules += num_6g_reg_rules_cl[WMI_REG_VLP_AP][i];
 5831
 5832		if (num_6g_reg_rules_cl[WMI_REG_INDOOR_AP][i] > MAX_6GHZ_REG_RULES ||
 5833		    num_6g_reg_rules_cl[WMI_REG_STD_POWER_AP][i] > MAX_6GHZ_REG_RULES ||
 5834		    num_6g_reg_rules_cl[WMI_REG_VLP_AP][i] >  MAX_6GHZ_REG_RULES) {
 5835			ath12k_warn(ab, "Num 6g client reg rules exceeds max limit, for client(type: %d)\n",
 5836				    i);
 5837			kfree(tb);
 5838			return -EINVAL;
 5839		}
 5840	}
 5841
 5842	if (!total_reg_rules) {
 5843		ath12k_warn(ab, "No reg rules available\n");
 5844		kfree(tb);
 5845		return -EINVAL;
 5846	}
 5847
 5848	memcpy(reg_info->alpha2, &ev->alpha2, REG_ALPHA2_LEN);
 5849
 5850	reg_info->dfs_region = le32_to_cpu(ev->dfs_region);
 5851	reg_info->phybitmap = le32_to_cpu(ev->phybitmap);
 5852	reg_info->num_phy = le32_to_cpu(ev->num_phy);
 5853	reg_info->phy_id = le32_to_cpu(ev->phy_id);
 5854	reg_info->ctry_code = le32_to_cpu(ev->country_id);
 5855	reg_info->reg_dmn_pair = le32_to_cpu(ev->domain_code);
 5856
 5857	switch (le32_to_cpu(ev->status_code)) {
 5858	case WMI_REG_SET_CC_STATUS_PASS:
 5859		reg_info->status_code = REG_SET_CC_STATUS_PASS;
 5860		break;
 5861	case WMI_REG_CURRENT_ALPHA2_NOT_FOUND:
 5862		reg_info->status_code = REG_CURRENT_ALPHA2_NOT_FOUND;
 5863		break;
 5864	case WMI_REG_INIT_ALPHA2_NOT_FOUND:
 5865		reg_info->status_code = REG_INIT_ALPHA2_NOT_FOUND;
 5866		break;
 5867	case WMI_REG_SET_CC_CHANGE_NOT_ALLOWED:
 5868		reg_info->status_code = REG_SET_CC_CHANGE_NOT_ALLOWED;
 5869		break;
 5870	case WMI_REG_SET_CC_STATUS_NO_MEMORY:
 5871		reg_info->status_code = REG_SET_CC_STATUS_NO_MEMORY;
 5872		break;
 5873	case WMI_REG_SET_CC_STATUS_FAIL:
 5874		reg_info->status_code = REG_SET_CC_STATUS_FAIL;
 5875		break;
 5876	}
 5877
 5878	reg_info->is_ext_reg_event = true;
 5879
 5880	reg_info->min_bw_2g = le32_to_cpu(ev->min_bw_2g);
 5881	reg_info->max_bw_2g = le32_to_cpu(ev->max_bw_2g);
 5882	reg_info->min_bw_5g = le32_to_cpu(ev->min_bw_5g);
 5883	reg_info->max_bw_5g = le32_to_cpu(ev->max_bw_5g);
 5884	reg_info->min_bw_6g_ap[WMI_REG_INDOOR_AP] = le32_to_cpu(ev->min_bw_6g_ap_lpi);
 5885	reg_info->max_bw_6g_ap[WMI_REG_INDOOR_AP] = le32_to_cpu(ev->max_bw_6g_ap_lpi);
 5886	reg_info->min_bw_6g_ap[WMI_REG_STD_POWER_AP] = le32_to_cpu(ev->min_bw_6g_ap_sp);
 5887	reg_info->max_bw_6g_ap[WMI_REG_STD_POWER_AP] = le32_to_cpu(ev->max_bw_6g_ap_sp);
 5888	reg_info->min_bw_6g_ap[WMI_REG_VLP_AP] = le32_to_cpu(ev->min_bw_6g_ap_vlp);
 5889	reg_info->max_bw_6g_ap[WMI_REG_VLP_AP] = le32_to_cpu(ev->max_bw_6g_ap_vlp);
 5890
 5891	for (i = 0; i < WMI_REG_MAX_CLIENT_TYPE; i++) {
 5892		reg_info->min_bw_6g_client[WMI_REG_INDOOR_AP][i] =
 5893			le32_to_cpu(ev->min_bw_6g_client_lpi[i]);
 5894		reg_info->max_bw_6g_client[WMI_REG_INDOOR_AP][i] =
 5895			le32_to_cpu(ev->max_bw_6g_client_lpi[i]);
 5896		reg_info->min_bw_6g_client[WMI_REG_STD_POWER_AP][i] =
 5897			le32_to_cpu(ev->min_bw_6g_client_sp[i]);
 5898		reg_info->max_bw_6g_client[WMI_REG_STD_POWER_AP][i] =
 5899			le32_to_cpu(ev->max_bw_6g_client_sp[i]);
 5900		reg_info->min_bw_6g_client[WMI_REG_VLP_AP][i] =
 5901			le32_to_cpu(ev->min_bw_6g_client_vlp[i]);
 5902		reg_info->max_bw_6g_client[WMI_REG_VLP_AP][i] =
 5903			le32_to_cpu(ev->max_bw_6g_client_vlp[i]);
 5904	}
 5905
 5906	ath12k_dbg(ab, ATH12K_DBG_WMI,
 5907		   "%s:cc_ext %s dfs %d BW: min_2g %d max_2g %d min_5g %d max_5g %d phy_bitmap 0x%x",
 5908		   __func__, reg_info->alpha2, reg_info->dfs_region,
 5909		   reg_info->min_bw_2g, reg_info->max_bw_2g,
 5910		   reg_info->min_bw_5g, reg_info->max_bw_5g,
 5911		   reg_info->phybitmap);
 5912
 5913	ath12k_dbg(ab, ATH12K_DBG_WMI,
 5914		   "num_2g_reg_rules %d num_5g_reg_rules %d",
 5915		   num_2g_reg_rules, num_5g_reg_rules);
 5916
 5917	ath12k_dbg(ab, ATH12K_DBG_WMI,
 5918		   "num_6g_reg_rules_ap_lpi: %d num_6g_reg_rules_ap_sp: %d num_6g_reg_rules_ap_vlp: %d",
 5919		   num_6g_reg_rules_ap[WMI_REG_INDOOR_AP],
 5920		   num_6g_reg_rules_ap[WMI_REG_STD_POWER_AP],
 5921		   num_6g_reg_rules_ap[WMI_REG_VLP_AP]);
 5922
 5923	ath12k_dbg(ab, ATH12K_DBG_WMI,
 5924		   "6g Regular client: num_6g_reg_rules_lpi: %d num_6g_reg_rules_sp: %d num_6g_reg_rules_vlp: %d",
 5925		   num_6g_reg_rules_cl[WMI_REG_INDOOR_AP][WMI_REG_DEFAULT_CLIENT],
 5926		   num_6g_reg_rules_cl[WMI_REG_STD_POWER_AP][WMI_REG_DEFAULT_CLIENT],
 5927		   num_6g_reg_rules_cl[WMI_REG_VLP_AP][WMI_REG_DEFAULT_CLIENT]);
 5928
 5929	ath12k_dbg(ab, ATH12K_DBG_WMI,
 5930		   "6g Subordinate client: num_6g_reg_rules_lpi: %d num_6g_reg_rules_sp: %d num_6g_reg_rules_vlp: %d",
 5931		   num_6g_reg_rules_cl[WMI_REG_INDOOR_AP][WMI_REG_SUBORDINATE_CLIENT],
 5932		   num_6g_reg_rules_cl[WMI_REG_STD_POWER_AP][WMI_REG_SUBORDINATE_CLIENT],
 5933		   num_6g_reg_rules_cl[WMI_REG_VLP_AP][WMI_REG_SUBORDINATE_CLIENT]);
 5934
 5935	ext_wmi_reg_rule =
 5936		(struct ath12k_wmi_reg_rule_ext_params *)((u8 *)ev
 5937			+ sizeof(*ev)
 5938			+ sizeof(struct wmi_tlv));
 5939
 5940	if (num_2g_reg_rules) {
 5941		reg_info->reg_rules_2g_ptr =
 5942			create_ext_reg_rules_from_wmi(num_2g_reg_rules,
 5943						      ext_wmi_reg_rule);
 5944
 5945		if (!reg_info->reg_rules_2g_ptr) {
 5946			kfree(tb);
 5947			ath12k_warn(ab, "Unable to Allocate memory for 2g rules\n");
 5948			return -ENOMEM;
 5949		}
 5950	}
 5951
 5952	ext_wmi_reg_rule += num_2g_reg_rules;
 5953
 5954	/* Firmware might include 6 GHz reg rule in 5 GHz rule list
 5955	 * for few countries along with separate 6 GHz rule.
 5956	 * Having same 6 GHz reg rule in 5 GHz and 6 GHz rules list
 5957	 * causes intersect check to be true, and same rules will be
 5958	 * shown multiple times in iw cmd.
 5959	 * Hence, avoid parsing 6 GHz rule from 5 GHz reg rule list
 5960	 */
 5961	num_invalid_5ghz_ext_rules = ath12k_wmi_ignore_num_extra_rules(ext_wmi_reg_rule,
 5962								       num_5g_reg_rules);
 5963
 5964	if (num_invalid_5ghz_ext_rules) {
 5965		ath12k_dbg(ab, ATH12K_DBG_WMI,
 5966			   "CC: %s 5 GHz reg rules number %d from fw, %d number of invalid 5 GHz rules",
 5967			   reg_info->alpha2, reg_info->num_5g_reg_rules,
 5968			   num_invalid_5ghz_ext_rules);
 5969
 5970		num_5g_reg_rules = num_5g_reg_rules - num_invalid_5ghz_ext_rules;
 5971		reg_info->num_5g_reg_rules = num_5g_reg_rules;
 5972	}
 5973
 5974	if (num_5g_reg_rules) {
 5975		reg_info->reg_rules_5g_ptr =
 5976			create_ext_reg_rules_from_wmi(num_5g_reg_rules,
 5977						      ext_wmi_reg_rule);
 5978
 5979		if (!reg_info->reg_rules_5g_ptr) {
 5980			kfree(tb);
 5981			ath12k_warn(ab, "Unable to Allocate memory for 5g rules\n");
 5982			return -ENOMEM;
 5983		}
 5984	}
 5985
 5986	/* We have adjusted the number of 5 GHz reg rules above. But still those
 5987	 * many rules needs to be adjusted in ext_wmi_reg_rule.
 5988	 *
 5989	 * NOTE: num_invalid_5ghz_ext_rules will be 0 for rest other cases.
 5990	 */
 5991	ext_wmi_reg_rule += (num_5g_reg_rules + num_invalid_5ghz_ext_rules);
 5992
 5993	for (i = 0; i < WMI_REG_CURRENT_MAX_AP_TYPE; i++) {
 5994		reg_info->reg_rules_6g_ap_ptr[i] =
 5995			create_ext_reg_rules_from_wmi(num_6g_reg_rules_ap[i],
 5996						      ext_wmi_reg_rule);
 5997
 5998		if (!reg_info->reg_rules_6g_ap_ptr[i]) {
 5999			kfree(tb);
 6000			ath12k_warn(ab, "Unable to Allocate memory for 6g ap rules\n");
 6001			return -ENOMEM;
 6002		}
 6003
 6004		ext_wmi_reg_rule += num_6g_reg_rules_ap[i];
 6005	}
 6006
 6007	for (j = 0; j < WMI_REG_CURRENT_MAX_AP_TYPE; j++) {
 6008		for (i = 0; i < WMI_REG_MAX_CLIENT_TYPE; i++) {
 6009			reg_info->reg_rules_6g_client_ptr[j][i] =
 6010				create_ext_reg_rules_from_wmi(num_6g_reg_rules_cl[j][i],
 6011							      ext_wmi_reg_rule);
 6012
 6013			if (!reg_info->reg_rules_6g_client_ptr[j][i]) {
 6014				kfree(tb);
 6015				ath12k_warn(ab, "Unable to Allocate memory for 6g client rules\n");
 6016				return -ENOMEM;
 6017			}
 6018
 6019			ext_wmi_reg_rule += num_6g_reg_rules_cl[j][i];
 6020		}
 6021	}
 6022
 6023	reg_info->client_type = le32_to_cpu(ev->client_type);
 6024	reg_info->rnr_tpe_usable = ev->rnr_tpe_usable;
 6025	reg_info->unspecified_ap_usable = ev->unspecified_ap_usable;
 6026	reg_info->domain_code_6g_ap[WMI_REG_INDOOR_AP] =
 6027		le32_to_cpu(ev->domain_code_6g_ap_lpi);
 6028	reg_info->domain_code_6g_ap[WMI_REG_STD_POWER_AP] =
 6029		le32_to_cpu(ev->domain_code_6g_ap_sp);
 6030	reg_info->domain_code_6g_ap[WMI_REG_VLP_AP] =
 6031		le32_to_cpu(ev->domain_code_6g_ap_vlp);
 6032
 6033	for (i = 0; i < WMI_REG_MAX_CLIENT_TYPE; i++) {
 6034		reg_info->domain_code_6g_client[WMI_REG_INDOOR_AP][i] =
 6035			le32_to_cpu(ev->domain_code_6g_client_lpi[i]);
 6036		reg_info->domain_code_6g_client[WMI_REG_STD_POWER_AP][i] =
 6037			le32_to_cpu(ev->domain_code_6g_client_sp[i]);
 6038		reg_info->domain_code_6g_client[WMI_REG_VLP_AP][i] =
 6039			le32_to_cpu(ev->domain_code_6g_client_vlp[i]);
 6040	}
 6041
 6042	reg_info->domain_code_6g_super_id = le32_to_cpu(ev->domain_code_6g_super_id);
 6043
 6044	ath12k_dbg(ab, ATH12K_DBG_WMI, "6g client_type: %d domain_code_6g_super_id: %d",
 6045		   reg_info->client_type, reg_info->domain_code_6g_super_id);
 6046
 6047	ath12k_dbg(ab, ATH12K_DBG_WMI, "processed regulatory ext channel list\n");
 6048
 6049	kfree(tb);
 6050	return 0;
 6051}
 6052
 6053static int ath12k_pull_peer_del_resp_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6054					struct wmi_peer_delete_resp_event *peer_del_resp)
 6055{
 6056	const void **tb;
 6057	const struct wmi_peer_delete_resp_event *ev;
 6058	int ret;
 6059
 6060	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6061	if (IS_ERR(tb)) {
 6062		ret = PTR_ERR(tb);
 6063		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6064		return ret;
 6065	}
 6066
 6067	ev = tb[WMI_TAG_PEER_DELETE_RESP_EVENT];
 6068	if (!ev) {
 6069		ath12k_warn(ab, "failed to fetch peer delete resp ev");
 6070		kfree(tb);
 6071		return -EPROTO;
 6072	}
 6073
 6074	memset(peer_del_resp, 0, sizeof(*peer_del_resp));
 6075
 6076	peer_del_resp->vdev_id = ev->vdev_id;
 6077	ether_addr_copy(peer_del_resp->peer_macaddr.addr,
 6078			ev->peer_macaddr.addr);
 6079
 6080	kfree(tb);
 6081	return 0;
 6082}
 6083
 6084static int ath12k_pull_vdev_del_resp_ev(struct ath12k_base *ab,
 6085					struct sk_buff *skb,
 6086					u32 *vdev_id)
 6087{
 6088	const void **tb;
 6089	const struct wmi_vdev_delete_resp_event *ev;
 6090	int ret;
 6091
 6092	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6093	if (IS_ERR(tb)) {
 6094		ret = PTR_ERR(tb);
 6095		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6096		return ret;
 6097	}
 6098
 6099	ev = tb[WMI_TAG_VDEV_DELETE_RESP_EVENT];
 6100	if (!ev) {
 6101		ath12k_warn(ab, "failed to fetch vdev delete resp ev");
 6102		kfree(tb);
 6103		return -EPROTO;
 6104	}
 6105
 6106	*vdev_id = le32_to_cpu(ev->vdev_id);
 6107
 6108	kfree(tb);
 6109	return 0;
 6110}
 6111
 6112static int ath12k_pull_bcn_tx_status_ev(struct ath12k_base *ab,
 6113					struct sk_buff *skb,
 6114					u32 *vdev_id, u32 *tx_status)
 6115{
 6116	const void **tb;
 6117	const struct wmi_bcn_tx_status_event *ev;
 6118	int ret;
 6119
 6120	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6121	if (IS_ERR(tb)) {
 6122		ret = PTR_ERR(tb);
 6123		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6124		return ret;
 6125	}
 6126
 6127	ev = tb[WMI_TAG_OFFLOAD_BCN_TX_STATUS_EVENT];
 6128	if (!ev) {
 6129		ath12k_warn(ab, "failed to fetch bcn tx status ev");
 6130		kfree(tb);
 6131		return -EPROTO;
 6132	}
 6133
 6134	*vdev_id = le32_to_cpu(ev->vdev_id);
 6135	*tx_status = le32_to_cpu(ev->tx_status);
 6136
 6137	kfree(tb);
 6138	return 0;
 6139}
 6140
 6141static int ath12k_pull_vdev_stopped_param_tlv(struct ath12k_base *ab, struct sk_buff *skb,
 6142					      u32 *vdev_id)
 6143{
 6144	const void **tb;
 6145	const struct wmi_vdev_stopped_event *ev;
 6146	int ret;
 6147
 6148	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6149	if (IS_ERR(tb)) {
 6150		ret = PTR_ERR(tb);
 6151		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6152		return ret;
 6153	}
 6154
 6155	ev = tb[WMI_TAG_VDEV_STOPPED_EVENT];
 6156	if (!ev) {
 6157		ath12k_warn(ab, "failed to fetch vdev stop ev");
 6158		kfree(tb);
 6159		return -EPROTO;
 6160	}
 6161
 6162	*vdev_id = le32_to_cpu(ev->vdev_id);
 6163
 6164	kfree(tb);
 6165	return 0;
 6166}
 6167
 6168static int ath12k_wmi_tlv_mgmt_rx_parse(struct ath12k_base *ab,
 6169					u16 tag, u16 len,
 6170					const void *ptr, void *data)
 6171{
 6172	struct wmi_tlv_mgmt_rx_parse *parse = data;
 6173
 6174	switch (tag) {
 6175	case WMI_TAG_MGMT_RX_HDR:
 6176		parse->fixed = ptr;
 6177		break;
 6178	case WMI_TAG_ARRAY_BYTE:
 6179		if (!parse->frame_buf_done) {
 6180			parse->frame_buf = ptr;
 6181			parse->frame_buf_done = true;
 6182		}
 6183		break;
 6184	}
 6185	return 0;
 6186}
 6187
 6188static int ath12k_pull_mgmt_rx_params_tlv(struct ath12k_base *ab,
 6189					  struct sk_buff *skb,
 6190					  struct ath12k_wmi_mgmt_rx_arg *hdr)
 6191{
 6192	struct wmi_tlv_mgmt_rx_parse parse = { };
 6193	const struct ath12k_wmi_mgmt_rx_params *ev;
 6194	const u8 *frame;
 6195	int i, ret;
 6196
 6197	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 6198				  ath12k_wmi_tlv_mgmt_rx_parse,
 6199				  &parse);
 6200	if (ret) {
 6201		ath12k_warn(ab, "failed to parse mgmt rx tlv %d\n", ret);
 6202		return ret;
 6203	}
 6204
 6205	ev = parse.fixed;
 6206	frame = parse.frame_buf;
 6207
 6208	if (!ev || !frame) {
 6209		ath12k_warn(ab, "failed to fetch mgmt rx hdr");
 6210		return -EPROTO;
 6211	}
 6212
 6213	hdr->pdev_id = le32_to_cpu(ev->pdev_id);
 6214	hdr->chan_freq = le32_to_cpu(ev->chan_freq);
 6215	hdr->channel = le32_to_cpu(ev->channel);
 6216	hdr->snr = le32_to_cpu(ev->snr);
 6217	hdr->rate = le32_to_cpu(ev->rate);
 6218	hdr->phy_mode = le32_to_cpu(ev->phy_mode);
 6219	hdr->buf_len = le32_to_cpu(ev->buf_len);
 6220	hdr->status = le32_to_cpu(ev->status);
 6221	hdr->flags = le32_to_cpu(ev->flags);
 6222	hdr->rssi = a_sle32_to_cpu(ev->rssi);
 6223	hdr->tsf_delta = le32_to_cpu(ev->tsf_delta);
 6224
 6225	for (i = 0; i < ATH_MAX_ANTENNA; i++)
 6226		hdr->rssi_ctl[i] = le32_to_cpu(ev->rssi_ctl[i]);
 6227
 6228	if (skb->len < (frame - skb->data) + hdr->buf_len) {
 6229		ath12k_warn(ab, "invalid length in mgmt rx hdr ev");
 6230		return -EPROTO;
 6231	}
 6232
 6233	/* shift the sk_buff to point to `frame` */
 6234	skb_trim(skb, 0);
 6235	skb_put(skb, frame - skb->data);
 6236	skb_pull(skb, frame - skb->data);
 6237	skb_put(skb, hdr->buf_len);
 6238
 6239	return 0;
 6240}
 6241
 6242static int wmi_process_mgmt_tx_comp(struct ath12k *ar, u32 desc_id,
 6243				    u32 status, u32 ack_rssi)
 6244{
 6245	struct sk_buff *msdu;
 6246	struct ieee80211_tx_info *info;
 6247	struct ath12k_skb_cb *skb_cb;
 6248	int num_mgmt;
 6249
 6250	spin_lock_bh(&ar->txmgmt_idr_lock);
 6251	msdu = idr_find(&ar->txmgmt_idr, desc_id);
 6252
 6253	if (!msdu) {
 6254		ath12k_warn(ar->ab, "received mgmt tx compl for invalid msdu_id: %d\n",
 6255			    desc_id);
 6256		spin_unlock_bh(&ar->txmgmt_idr_lock);
 6257		return -ENOENT;
 6258	}
 6259
 6260	idr_remove(&ar->txmgmt_idr, desc_id);
 6261	spin_unlock_bh(&ar->txmgmt_idr_lock);
 6262
 6263	skb_cb = ATH12K_SKB_CB(msdu);
 6264	dma_unmap_single(ar->ab->dev, skb_cb->paddr, msdu->len, DMA_TO_DEVICE);
 6265
 6266	info = IEEE80211_SKB_CB(msdu);
 6267	memset(&info->status, 0, sizeof(info->status));
 6268
 6269	/* skip tx rate update from ieee80211_status*/
 6270	info->status.rates[0].idx = -1;
 6271
 6272	if ((!(info->flags & IEEE80211_TX_CTL_NO_ACK)) && !status) {
 6273		info->flags |= IEEE80211_TX_STAT_ACK;
 6274		info->status.ack_signal = ack_rssi;
 6275		info->status.flags |= IEEE80211_TX_STATUS_ACK_SIGNAL_VALID;
 6276	}
 6277
 6278	if ((info->flags & IEEE80211_TX_CTL_NO_ACK) && !status)
 6279		info->flags |= IEEE80211_TX_STAT_NOACK_TRANSMITTED;
 6280
 6281	ieee80211_tx_status_irqsafe(ath12k_ar_to_hw(ar), msdu);
 6282
 6283	num_mgmt = atomic_dec_if_positive(&ar->num_pending_mgmt_tx);
 6284
 6285	/* WARN when we received this event without doing any mgmt tx */
 6286	if (num_mgmt < 0)
 6287		WARN_ON_ONCE(1);
 6288
 6289	if (!num_mgmt)
 6290		wake_up(&ar->txmgmt_empty_waitq);
 6291
 6292	return 0;
 6293}
 6294
 6295static int ath12k_pull_mgmt_tx_compl_param_tlv(struct ath12k_base *ab,
 6296					       struct sk_buff *skb,
 6297					       struct wmi_mgmt_tx_compl_event *param)
 6298{
 6299	const void **tb;
 6300	const struct wmi_mgmt_tx_compl_event *ev;
 6301	int ret;
 6302
 6303	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6304	if (IS_ERR(tb)) {
 6305		ret = PTR_ERR(tb);
 6306		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6307		return ret;
 6308	}
 6309
 6310	ev = tb[WMI_TAG_MGMT_TX_COMPL_EVENT];
 6311	if (!ev) {
 6312		ath12k_warn(ab, "failed to fetch mgmt tx compl ev");
 6313		kfree(tb);
 6314		return -EPROTO;
 6315	}
 6316
 6317	param->pdev_id = ev->pdev_id;
 6318	param->desc_id = ev->desc_id;
 6319	param->status = ev->status;
 6320	param->ppdu_id = ev->ppdu_id;
 6321	param->ack_rssi = ev->ack_rssi;
 6322
 6323	kfree(tb);
 6324	return 0;
 6325}
 6326
 6327static void ath12k_wmi_event_scan_started(struct ath12k *ar)
 6328{
 6329	lockdep_assert_held(&ar->data_lock);
 6330
 6331	switch (ar->scan.state) {
 6332	case ATH12K_SCAN_IDLE:
 6333	case ATH12K_SCAN_RUNNING:
 6334	case ATH12K_SCAN_ABORTING:
 6335		ath12k_warn(ar->ab, "received scan started event in an invalid scan state: %s (%d)\n",
 6336			    ath12k_scan_state_str(ar->scan.state),
 6337			    ar->scan.state);
 6338		break;
 6339	case ATH12K_SCAN_STARTING:
 6340		ar->scan.state = ATH12K_SCAN_RUNNING;
 6341
 6342		if (ar->scan.is_roc)
 6343			ieee80211_ready_on_channel(ath12k_ar_to_hw(ar));
 6344
 6345		complete(&ar->scan.started);
 6346		break;
 6347	}
 6348}
 6349
 6350static void ath12k_wmi_event_scan_start_failed(struct ath12k *ar)
 6351{
 6352	lockdep_assert_held(&ar->data_lock);
 6353
 6354	switch (ar->scan.state) {
 6355	case ATH12K_SCAN_IDLE:
 6356	case ATH12K_SCAN_RUNNING:
 6357	case ATH12K_SCAN_ABORTING:
 6358		ath12k_warn(ar->ab, "received scan start failed event in an invalid scan state: %s (%d)\n",
 6359			    ath12k_scan_state_str(ar->scan.state),
 6360			    ar->scan.state);
 6361		break;
 6362	case ATH12K_SCAN_STARTING:
 6363		complete(&ar->scan.started);
 6364		__ath12k_mac_scan_finish(ar);
 6365		break;
 6366	}
 6367}
 6368
 6369static void ath12k_wmi_event_scan_completed(struct ath12k *ar)
 6370{
 6371	lockdep_assert_held(&ar->data_lock);
 6372
 6373	switch (ar->scan.state) {
 6374	case ATH12K_SCAN_IDLE:
 6375	case ATH12K_SCAN_STARTING:
 6376		/* One suspected reason scan can be completed while starting is
 6377		 * if firmware fails to deliver all scan events to the host,
 6378		 * e.g. when transport pipe is full. This has been observed
 6379		 * with spectral scan phyerr events starving wmi transport
 6380		 * pipe. In such case the "scan completed" event should be (and
 6381		 * is) ignored by the host as it may be just firmware's scan
 6382		 * state machine recovering.
 6383		 */
 6384		ath12k_warn(ar->ab, "received scan completed event in an invalid scan state: %s (%d)\n",
 6385			    ath12k_scan_state_str(ar->scan.state),
 6386			    ar->scan.state);
 6387		break;
 6388	case ATH12K_SCAN_RUNNING:
 6389	case ATH12K_SCAN_ABORTING:
 6390		__ath12k_mac_scan_finish(ar);
 6391		break;
 6392	}
 6393}
 6394
 6395static void ath12k_wmi_event_scan_bss_chan(struct ath12k *ar)
 6396{
 6397	lockdep_assert_held(&ar->data_lock);
 6398
 6399	switch (ar->scan.state) {
 6400	case ATH12K_SCAN_IDLE:
 6401	case ATH12K_SCAN_STARTING:
 6402		ath12k_warn(ar->ab, "received scan bss chan event in an invalid scan state: %s (%d)\n",
 6403			    ath12k_scan_state_str(ar->scan.state),
 6404			    ar->scan.state);
 6405		break;
 6406	case ATH12K_SCAN_RUNNING:
 6407	case ATH12K_SCAN_ABORTING:
 6408		ar->scan_channel = NULL;
 6409		break;
 6410	}
 6411}
 6412
 6413static void ath12k_wmi_event_scan_foreign_chan(struct ath12k *ar, u32 freq)
 6414{
 6415	struct ieee80211_hw *hw = ath12k_ar_to_hw(ar);
 6416
 6417	lockdep_assert_held(&ar->data_lock);
 6418
 6419	switch (ar->scan.state) {
 6420	case ATH12K_SCAN_IDLE:
 6421	case ATH12K_SCAN_STARTING:
 6422		ath12k_warn(ar->ab, "received scan foreign chan event in an invalid scan state: %s (%d)\n",
 6423			    ath12k_scan_state_str(ar->scan.state),
 6424			    ar->scan.state);
 6425		break;
 6426	case ATH12K_SCAN_RUNNING:
 6427	case ATH12K_SCAN_ABORTING:
 6428		ar->scan_channel = ieee80211_get_channel(hw->wiphy, freq);
 6429
 6430		if (ar->scan.is_roc && ar->scan.roc_freq == freq)
 6431			complete(&ar->scan.on_channel);
 6432
 6433		break;
 6434	}
 6435}
 6436
 6437static const char *
 6438ath12k_wmi_event_scan_type_str(enum wmi_scan_event_type type,
 6439			       enum wmi_scan_completion_reason reason)
 6440{
 6441	switch (type) {
 6442	case WMI_SCAN_EVENT_STARTED:
 6443		return "started";
 6444	case WMI_SCAN_EVENT_COMPLETED:
 6445		switch (reason) {
 6446		case WMI_SCAN_REASON_COMPLETED:
 6447			return "completed";
 6448		case WMI_SCAN_REASON_CANCELLED:
 6449			return "completed [cancelled]";
 6450		case WMI_SCAN_REASON_PREEMPTED:
 6451			return "completed [preempted]";
 6452		case WMI_SCAN_REASON_TIMEDOUT:
 6453			return "completed [timedout]";
 6454		case WMI_SCAN_REASON_INTERNAL_FAILURE:
 6455			return "completed [internal err]";
 6456		case WMI_SCAN_REASON_MAX:
 6457			break;
 6458		}
 6459		return "completed [unknown]";
 6460	case WMI_SCAN_EVENT_BSS_CHANNEL:
 6461		return "bss channel";
 6462	case WMI_SCAN_EVENT_FOREIGN_CHAN:
 6463		return "foreign channel";
 6464	case WMI_SCAN_EVENT_DEQUEUED:
 6465		return "dequeued";
 6466	case WMI_SCAN_EVENT_PREEMPTED:
 6467		return "preempted";
 6468	case WMI_SCAN_EVENT_START_FAILED:
 6469		return "start failed";
 6470	case WMI_SCAN_EVENT_RESTARTED:
 6471		return "restarted";
 6472	case WMI_SCAN_EVENT_FOREIGN_CHAN_EXIT:
 6473		return "foreign channel exit";
 6474	default:
 6475		return "unknown";
 6476	}
 6477}
 6478
 6479static int ath12k_pull_scan_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6480			       struct wmi_scan_event *scan_evt_param)
 6481{
 6482	const void **tb;
 6483	const struct wmi_scan_event *ev;
 6484	int ret;
 6485
 6486	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6487	if (IS_ERR(tb)) {
 6488		ret = PTR_ERR(tb);
 6489		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6490		return ret;
 6491	}
 6492
 6493	ev = tb[WMI_TAG_SCAN_EVENT];
 6494	if (!ev) {
 6495		ath12k_warn(ab, "failed to fetch scan ev");
 6496		kfree(tb);
 6497		return -EPROTO;
 6498	}
 6499
 6500	scan_evt_param->event_type = ev->event_type;
 6501	scan_evt_param->reason = ev->reason;
 6502	scan_evt_param->channel_freq = ev->channel_freq;
 6503	scan_evt_param->scan_req_id = ev->scan_req_id;
 6504	scan_evt_param->scan_id = ev->scan_id;
 6505	scan_evt_param->vdev_id = ev->vdev_id;
 6506	scan_evt_param->tsf_timestamp = ev->tsf_timestamp;
 6507
 6508	kfree(tb);
 6509	return 0;
 6510}
 6511
 6512static int ath12k_pull_peer_sta_kickout_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6513					   struct wmi_peer_sta_kickout_arg *arg)
 6514{
 6515	const void **tb;
 6516	const struct wmi_peer_sta_kickout_event *ev;
 6517	int ret;
 6518
 6519	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6520	if (IS_ERR(tb)) {
 6521		ret = PTR_ERR(tb);
 6522		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6523		return ret;
 6524	}
 6525
 6526	ev = tb[WMI_TAG_PEER_STA_KICKOUT_EVENT];
 6527	if (!ev) {
 6528		ath12k_warn(ab, "failed to fetch peer sta kickout ev");
 6529		kfree(tb);
 6530		return -EPROTO;
 6531	}
 6532
 6533	arg->mac_addr = ev->peer_macaddr.addr;
 6534	arg->reason = le32_to_cpu(ev->reason);
 6535	arg->rssi = le32_to_cpu(ev->rssi);
 6536
 6537	kfree(tb);
 6538	return 0;
 6539}
 6540
 6541static int ath12k_pull_roam_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6542			       struct wmi_roam_event *roam_ev)
 6543{
 6544	const void **tb;
 6545	const struct wmi_roam_event *ev;
 6546	int ret;
 6547
 6548	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6549	if (IS_ERR(tb)) {
 6550		ret = PTR_ERR(tb);
 6551		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6552		return ret;
 6553	}
 6554
 6555	ev = tb[WMI_TAG_ROAM_EVENT];
 6556	if (!ev) {
 6557		ath12k_warn(ab, "failed to fetch roam ev");
 6558		kfree(tb);
 6559		return -EPROTO;
 6560	}
 6561
 6562	roam_ev->vdev_id = ev->vdev_id;
 6563	roam_ev->reason = ev->reason;
 6564	roam_ev->rssi = ev->rssi;
 6565
 6566	kfree(tb);
 6567	return 0;
 6568}
 6569
 6570static int freq_to_idx(struct ath12k *ar, int freq)
 6571{
 6572	struct ieee80211_supported_band *sband;
 6573	struct ieee80211_hw *hw = ath12k_ar_to_hw(ar);
 6574	int band, ch, idx = 0;
 6575
 6576	for (band = NL80211_BAND_2GHZ; band < NUM_NL80211_BANDS; band++) {
 6577		if (!ar->mac.sbands[band].channels)
 6578			continue;
 6579
 6580		sband = hw->wiphy->bands[band];
 6581		if (!sband)
 6582			continue;
 6583
 6584		for (ch = 0; ch < sband->n_channels; ch++, idx++)
 6585			if (sband->channels[ch].center_freq == freq)
 6586				goto exit;
 6587	}
 6588
 6589exit:
 6590	return idx;
 6591}
 6592
 6593static int ath12k_pull_chan_info_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6594				    struct wmi_chan_info_event *ch_info_ev)
 6595{
 6596	const void **tb;
 6597	const struct wmi_chan_info_event *ev;
 6598	int ret;
 6599
 6600	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6601	if (IS_ERR(tb)) {
 6602		ret = PTR_ERR(tb);
 6603		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6604		return ret;
 6605	}
 6606
 6607	ev = tb[WMI_TAG_CHAN_INFO_EVENT];
 6608	if (!ev) {
 6609		ath12k_warn(ab, "failed to fetch chan info ev");
 6610		kfree(tb);
 6611		return -EPROTO;
 6612	}
 6613
 6614	ch_info_ev->err_code = ev->err_code;
 6615	ch_info_ev->freq = ev->freq;
 6616	ch_info_ev->cmd_flags = ev->cmd_flags;
 6617	ch_info_ev->noise_floor = ev->noise_floor;
 6618	ch_info_ev->rx_clear_count = ev->rx_clear_count;
 6619	ch_info_ev->cycle_count = ev->cycle_count;
 6620	ch_info_ev->chan_tx_pwr_range = ev->chan_tx_pwr_range;
 6621	ch_info_ev->chan_tx_pwr_tp = ev->chan_tx_pwr_tp;
 6622	ch_info_ev->rx_frame_count = ev->rx_frame_count;
 6623	ch_info_ev->tx_frame_cnt = ev->tx_frame_cnt;
 6624	ch_info_ev->mac_clk_mhz = ev->mac_clk_mhz;
 6625	ch_info_ev->vdev_id = ev->vdev_id;
 6626
 6627	kfree(tb);
 6628	return 0;
 6629}
 6630
 6631static int
 6632ath12k_pull_pdev_bss_chan_info_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6633				  struct wmi_pdev_bss_chan_info_event *bss_ch_info_ev)
 6634{
 6635	const void **tb;
 6636	const struct wmi_pdev_bss_chan_info_event *ev;
 6637	int ret;
 6638
 6639	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6640	if (IS_ERR(tb)) {
 6641		ret = PTR_ERR(tb);
 6642		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6643		return ret;
 6644	}
 6645
 6646	ev = tb[WMI_TAG_PDEV_BSS_CHAN_INFO_EVENT];
 6647	if (!ev) {
 6648		ath12k_warn(ab, "failed to fetch pdev bss chan info ev");
 6649		kfree(tb);
 6650		return -EPROTO;
 6651	}
 6652
 6653	bss_ch_info_ev->pdev_id = ev->pdev_id;
 6654	bss_ch_info_ev->freq = ev->freq;
 6655	bss_ch_info_ev->noise_floor = ev->noise_floor;
 6656	bss_ch_info_ev->rx_clear_count_low = ev->rx_clear_count_low;
 6657	bss_ch_info_ev->rx_clear_count_high = ev->rx_clear_count_high;
 6658	bss_ch_info_ev->cycle_count_low = ev->cycle_count_low;
 6659	bss_ch_info_ev->cycle_count_high = ev->cycle_count_high;
 6660	bss_ch_info_ev->tx_cycle_count_low = ev->tx_cycle_count_low;
 6661	bss_ch_info_ev->tx_cycle_count_high = ev->tx_cycle_count_high;
 6662	bss_ch_info_ev->rx_cycle_count_low = ev->rx_cycle_count_low;
 6663	bss_ch_info_ev->rx_cycle_count_high = ev->rx_cycle_count_high;
 6664	bss_ch_info_ev->rx_bss_cycle_count_low = ev->rx_bss_cycle_count_low;
 6665	bss_ch_info_ev->rx_bss_cycle_count_high = ev->rx_bss_cycle_count_high;
 6666
 6667	kfree(tb);
 6668	return 0;
 6669}
 6670
 6671static int
 6672ath12k_pull_vdev_install_key_compl_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6673				      struct wmi_vdev_install_key_complete_arg *arg)
 6674{
 6675	const void **tb;
 6676	const struct wmi_vdev_install_key_compl_event *ev;
 6677	int ret;
 6678
 6679	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6680	if (IS_ERR(tb)) {
 6681		ret = PTR_ERR(tb);
 6682		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6683		return ret;
 6684	}
 6685
 6686	ev = tb[WMI_TAG_VDEV_INSTALL_KEY_COMPLETE_EVENT];
 6687	if (!ev) {
 6688		ath12k_warn(ab, "failed to fetch vdev install key compl ev");
 6689		kfree(tb);
 6690		return -EPROTO;
 6691	}
 6692
 6693	arg->vdev_id = le32_to_cpu(ev->vdev_id);
 6694	arg->macaddr = ev->peer_macaddr.addr;
 6695	arg->key_idx = le32_to_cpu(ev->key_idx);
 6696	arg->key_flags = le32_to_cpu(ev->key_flags);
 6697	arg->status = le32_to_cpu(ev->status);
 6698
 6699	kfree(tb);
 6700	return 0;
 6701}
 6702
 6703static int ath12k_pull_peer_assoc_conf_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6704					  struct wmi_peer_assoc_conf_arg *peer_assoc_conf)
 6705{
 6706	const void **tb;
 6707	const struct wmi_peer_assoc_conf_event *ev;
 6708	int ret;
 6709
 6710	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6711	if (IS_ERR(tb)) {
 6712		ret = PTR_ERR(tb);
 6713		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6714		return ret;
 6715	}
 6716
 6717	ev = tb[WMI_TAG_PEER_ASSOC_CONF_EVENT];
 6718	if (!ev) {
 6719		ath12k_warn(ab, "failed to fetch peer assoc conf ev");
 6720		kfree(tb);
 6721		return -EPROTO;
 6722	}
 6723
 6724	peer_assoc_conf->vdev_id = le32_to_cpu(ev->vdev_id);
 6725	peer_assoc_conf->macaddr = ev->peer_macaddr.addr;
 6726
 6727	kfree(tb);
 6728	return 0;
 6729}
 6730
 6731static int
 6732ath12k_pull_pdev_temp_ev(struct ath12k_base *ab, struct sk_buff *skb,
 6733			 const struct wmi_pdev_temperature_event *ev)
 6734{
 6735	const void **tb;
 6736	int ret;
 6737
 6738	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6739	if (IS_ERR(tb)) {
 6740		ret = PTR_ERR(tb);
 6741		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6742		return ret;
 6743	}
 6744
 6745	ev = tb[WMI_TAG_PDEV_TEMPERATURE_EVENT];
 6746	if (!ev) {
 6747		ath12k_warn(ab, "failed to fetch pdev temp ev");
 6748		kfree(tb);
 6749		return -EPROTO;
 6750	}
 6751
 6752	kfree(tb);
 6753	return 0;
 6754}
 6755
 6756static void ath12k_wmi_op_ep_tx_credits(struct ath12k_base *ab)
 6757{
 6758	/* try to send pending beacons first. they take priority */
 6759	wake_up(&ab->wmi_ab.tx_credits_wq);
 6760}
 6761
 6762static int ath12k_reg_11d_new_cc_event(struct ath12k_base *ab, struct sk_buff *skb)
 6763{
 6764	const struct wmi_11d_new_cc_event *ev;
 6765	struct ath12k *ar;
 6766	struct ath12k_pdev *pdev;
 6767	const void **tb;
 6768	int ret, i;
 6769
 6770	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 6771	if (IS_ERR(tb)) {
 6772		ret = PTR_ERR(tb);
 6773		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 6774		return ret;
 6775	}
 6776
 6777	ev = tb[WMI_TAG_11D_NEW_COUNTRY_EVENT];
 6778	if (!ev) {
 6779		kfree(tb);
 6780		ath12k_warn(ab, "failed to fetch 11d new cc ev");
 6781		return -EPROTO;
 6782	}
 6783
 6784	spin_lock_bh(&ab->base_lock);
 6785	memcpy(&ab->new_alpha2, &ev->new_alpha2, REG_ALPHA2_LEN);
 6786	spin_unlock_bh(&ab->base_lock);
 6787
 6788	ath12k_dbg(ab, ATH12K_DBG_WMI, "wmi 11d new cc %c%c\n",
 6789		   ab->new_alpha2[0],
 6790		   ab->new_alpha2[1]);
 6791
 6792	kfree(tb);
 6793
 6794	for (i = 0; i < ab->num_radios; i++) {
 6795		pdev = &ab->pdevs[i];
 6796		ar = pdev->ar;
 6797		ar->state_11d = ATH12K_11D_IDLE;
 6798		ar->ah->regd_updated = false;
 6799		complete(&ar->completed_11d_scan);
 6800	}
 6801
 6802	queue_work(ab->workqueue, &ab->update_11d_work);
 6803
 6804	return 0;
 6805}
 6806
 6807static void ath12k_wmi_htc_tx_complete(struct ath12k_base *ab,
 6808				       struct sk_buff *skb)
 6809{
 6810	dev_kfree_skb(skb);
 6811}
 6812
 6813static int ath12k_reg_chan_list_event(struct ath12k_base *ab, struct sk_buff *skb)
 6814{
 6815	struct ath12k_reg_info *reg_info;
 6816	struct ath12k *ar = NULL;
 6817	u8 pdev_idx = 255;
 6818	int ret;
 6819
 6820	reg_info = kzalloc(sizeof(*reg_info), GFP_ATOMIC);
 6821	if (!reg_info) {
 6822		ret = -ENOMEM;
 6823		goto fallback;
 6824	}
 6825
 6826	ret = ath12k_pull_reg_chan_list_ext_update_ev(ab, skb, reg_info);
 6827	if (ret) {
 6828		ath12k_warn(ab, "failed to extract regulatory info from received event\n");
 6829		goto mem_free;
 6830	}
 6831
 6832	ret = ath12k_reg_validate_reg_info(ab, reg_info);
 6833	if (ret == ATH12K_REG_STATUS_FALLBACK) {
 6834		ath12k_warn(ab, "failed to validate reg info %d\n", ret);
 6835		/* firmware has successfully switches to new regd but host can not
 6836		 * continue, so free reginfo and fallback to old regd
 6837		 */
 6838		goto mem_free;
 6839	} else if (ret == ATH12K_REG_STATUS_DROP) {
 6840		/* reg info is valid but we will not store it and
 6841		 * not going to create new regd for it
 6842		 */
 6843		ret = ATH12K_REG_STATUS_VALID;
 6844		goto mem_free;
 6845	}
 6846
 6847	/* free old reg_info if it exist */
 6848	pdev_idx = reg_info->phy_id;
 6849	if (ab->reg_info[pdev_idx]) {
 6850		ath12k_reg_reset_reg_info(ab->reg_info[pdev_idx]);
 6851		kfree(ab->reg_info[pdev_idx]);
 6852	}
 6853	/* reg_info is valid, we store it for later use
 6854	 * even below regd build failed
 6855	 */
 6856	ab->reg_info[pdev_idx] = reg_info;
 6857
 6858	ret = ath12k_reg_handle_chan_list(ab, reg_info, WMI_VDEV_TYPE_UNSPEC,
 6859					  IEEE80211_REG_UNSET_AP);
 6860	if (ret) {
 6861		ath12k_warn(ab, "failed to handle chan list %d\n", ret);
 6862		goto fallback;
 6863	}
 6864
 6865	goto out;
 6866
 6867mem_free:
 6868	ath12k_reg_reset_reg_info(reg_info);
 6869	kfree(reg_info);
 6870
 6871	if (ret == ATH12K_REG_STATUS_VALID)
 6872		goto out;
 6873
 6874fallback:
 6875	/* Fallback to older reg (by sending previous country setting
 6876	 * again if fw has succeeded and we failed to process here.
 6877	 * The Regdomain should be uniform across driver and fw. Since the
 6878	 * FW has processed the command and sent a success status, we expect
 6879	 * this function to succeed as well. If it doesn't, CTRY needs to be
 6880	 * reverted at the fw and the old SCAN_CHAN_LIST cmd needs to be sent.
 6881	 */
 6882	/* TODO: This is rare, but still should also be handled */
 6883	WARN_ON(1);
 6884
 6885out:
 6886	/* In some error cases, even a valid pdev_idx might not be available */
 6887	if (pdev_idx != 255)
 6888		ar = ab->pdevs[pdev_idx].ar;
 6889
 6890	/* During the boot-time update, 'ar' might not be allocated,
 6891	 * so the completion cannot be marked at that point.
 6892	 * This boot-time update is handled in ath12k_mac_hw_register()
 6893	 * before registering the hardware.
 6894	 */
 6895	if (ar)
 6896		complete_all(&ar->regd_update_completed);
 6897
 6898	return ret;
 6899}
 6900
 6901static int ath12k_wmi_rdy_parse(struct ath12k_base *ab, u16 tag, u16 len,
 6902				const void *ptr, void *data)
 6903{
 6904	struct ath12k_wmi_rdy_parse *rdy_parse = data;
 6905	struct wmi_ready_event fixed_param;
 6906	struct ath12k_wmi_mac_addr_params *addr_list;
 6907	struct ath12k_pdev *pdev;
 6908	u32 num_mac_addr;
 6909	int i;
 6910
 6911	switch (tag) {
 6912	case WMI_TAG_READY_EVENT:
 6913		memset(&fixed_param, 0, sizeof(fixed_param));
 6914		memcpy(&fixed_param, (struct wmi_ready_event *)ptr,
 6915		       min_t(u16, sizeof(fixed_param), len));
 6916		ab->wlan_init_status = le32_to_cpu(fixed_param.ready_event_min.status);
 6917		rdy_parse->num_extra_mac_addr =
 6918			le32_to_cpu(fixed_param.ready_event_min.num_extra_mac_addr);
 6919
 6920		ether_addr_copy(ab->mac_addr,
 6921				fixed_param.ready_event_min.mac_addr.addr);
 6922		ab->pktlog_defs_checksum = le32_to_cpu(fixed_param.pktlog_defs_checksum);
 6923		ab->wmi_ready = true;
 6924		break;
 6925	case WMI_TAG_ARRAY_FIXED_STRUCT:
 6926		addr_list = (struct ath12k_wmi_mac_addr_params *)ptr;
 6927		num_mac_addr = rdy_parse->num_extra_mac_addr;
 6928
 6929		if (!(ab->num_radios > 1 && num_mac_addr >= ab->num_radios))
 6930			break;
 6931
 6932		for (i = 0; i < ab->num_radios; i++) {
 6933			pdev = &ab->pdevs[i];
 6934			ether_addr_copy(pdev->mac_addr, addr_list[i].addr);
 6935		}
 6936		ab->pdevs_macaddr_valid = true;
 6937		break;
 6938	default:
 6939		break;
 6940	}
 6941
 6942	return 0;
 6943}
 6944
 6945static int ath12k_ready_event(struct ath12k_base *ab, struct sk_buff *skb)
 6946{
 6947	struct ath12k_wmi_rdy_parse rdy_parse = { };
 6948	int ret;
 6949
 6950	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 6951				  ath12k_wmi_rdy_parse, &rdy_parse);
 6952	if (ret) {
 6953		ath12k_warn(ab, "failed to parse tlv %d\n", ret);
 6954		return ret;
 6955	}
 6956
 6957	complete(&ab->wmi_ab.unified_ready);
 6958	return 0;
 6959}
 6960
 6961static void ath12k_peer_delete_resp_event(struct ath12k_base *ab, struct sk_buff *skb)
 6962{
 6963	struct wmi_peer_delete_resp_event peer_del_resp;
 6964	struct ath12k *ar;
 6965
 6966	if (ath12k_pull_peer_del_resp_ev(ab, skb, &peer_del_resp) != 0) {
 6967		ath12k_warn(ab, "failed to extract peer delete resp");
 6968		return;
 6969	}
 6970
 6971	rcu_read_lock();
 6972	ar = ath12k_mac_get_ar_by_vdev_id(ab, le32_to_cpu(peer_del_resp.vdev_id));
 6973	if (!ar) {
 6974		ath12k_warn(ab, "invalid vdev id in peer delete resp ev %d",
 6975			    peer_del_resp.vdev_id);
 6976		rcu_read_unlock();
 6977		return;
 6978	}
 6979
 6980	complete(&ar->peer_delete_done);
 6981	rcu_read_unlock();
 6982	ath12k_dbg(ab, ATH12K_DBG_WMI, "peer delete resp for vdev id %d addr %pM\n",
 6983		   peer_del_resp.vdev_id, peer_del_resp.peer_macaddr.addr);
 6984}
 6985
 6986static void ath12k_vdev_delete_resp_event(struct ath12k_base *ab,
 6987					  struct sk_buff *skb)
 6988{
 6989	struct ath12k *ar;
 6990	u32 vdev_id = 0;
 6991
 6992	if (ath12k_pull_vdev_del_resp_ev(ab, skb, &vdev_id) != 0) {
 6993		ath12k_warn(ab, "failed to extract vdev delete resp");
 6994		return;
 6995	}
 6996
 6997	rcu_read_lock();
 6998	ar = ath12k_mac_get_ar_by_vdev_id(ab, vdev_id);
 6999	if (!ar) {
 7000		ath12k_warn(ab, "invalid vdev id in vdev delete resp ev %d",
 7001			    vdev_id);
 7002		rcu_read_unlock();
 7003		return;
 7004	}
 7005
 7006	complete(&ar->vdev_delete_done);
 7007
 7008	rcu_read_unlock();
 7009
 7010	ath12k_dbg(ab, ATH12K_DBG_WMI, "vdev delete resp for vdev id %d\n",
 7011		   vdev_id);
 7012}
 7013
 7014static const char *ath12k_wmi_vdev_resp_print(u32 vdev_resp_status)
 7015{
 7016	switch (vdev_resp_status) {
 7017	case WMI_VDEV_START_RESPONSE_INVALID_VDEVID:
 7018		return "invalid vdev id";
 7019	case WMI_VDEV_START_RESPONSE_NOT_SUPPORTED:
 7020		return "not supported";
 7021	case WMI_VDEV_START_RESPONSE_DFS_VIOLATION:
 7022		return "dfs violation";
 7023	case WMI_VDEV_START_RESPONSE_INVALID_REGDOMAIN:
 7024		return "invalid regdomain";
 7025	default:
 7026		return "unknown";
 7027	}
 7028}
 7029
 7030static void ath12k_vdev_start_resp_event(struct ath12k_base *ab, struct sk_buff *skb)
 7031{
 7032	struct wmi_vdev_start_resp_event vdev_start_resp;
 7033	struct ath12k *ar;
 7034	u32 status;
 7035
 7036	if (ath12k_pull_vdev_start_resp_tlv(ab, skb, &vdev_start_resp) != 0) {
 7037		ath12k_warn(ab, "failed to extract vdev start resp");
 7038		return;
 7039	}
 7040
 7041	rcu_read_lock();
 7042	ar = ath12k_mac_get_ar_by_vdev_id(ab, le32_to_cpu(vdev_start_resp.vdev_id));
 7043	if (!ar) {
 7044		ath12k_warn(ab, "invalid vdev id in vdev start resp ev %d",
 7045			    vdev_start_resp.vdev_id);
 7046		rcu_read_unlock();
 7047		return;
 7048	}
 7049
 7050	ar->last_wmi_vdev_start_status = 0;
 7051
 7052	status = le32_to_cpu(vdev_start_resp.status);
 7053	if (WARN_ON_ONCE(status)) {
 7054		ath12k_warn(ab, "vdev start resp error status %d (%s)\n",
 7055			    status, ath12k_wmi_vdev_resp_print(status));
 7056		ar->last_wmi_vdev_start_status = status;
 7057	}
 7058
 7059	ar->max_allowed_tx_power = (s8)le32_to_cpu(vdev_start_resp.max_allowed_tx_power);
 7060
 7061	complete(&ar->vdev_setup_done);
 7062
 7063	rcu_read_unlock();
 7064
 7065	ath12k_dbg(ab, ATH12K_DBG_WMI, "vdev start resp for vdev id %d",
 7066		   vdev_start_resp.vdev_id);
 7067}
 7068
 7069static void ath12k_bcn_tx_status_event(struct ath12k_base *ab, struct sk_buff *skb)
 7070{
 7071	struct ath12k_link_vif *arvif;
 7072	struct ath12k *ar;
 7073	u32 vdev_id, tx_status;
 7074
 7075	if (ath12k_pull_bcn_tx_status_ev(ab, skb, &vdev_id, &tx_status) != 0) {
 7076		ath12k_warn(ab, "failed to extract bcn tx status");
 7077		return;
 7078	}
 7079
 7080	guard(rcu)();
 7081
 7082	arvif = ath12k_mac_get_arvif_by_vdev_id(ab, vdev_id);
 7083	if (!arvif) {
 7084		ath12k_warn(ab, "invalid vdev %u in bcn tx status\n",
 7085			    vdev_id);
 7086		return;
 7087	}
 7088
 7089	ar = arvif->ar;
 7090	wiphy_work_queue(ath12k_ar_to_hw(ar)->wiphy, &arvif->bcn_tx_work);
 7091}
 7092
 7093static void ath12k_vdev_stopped_event(struct ath12k_base *ab, struct sk_buff *skb)
 7094{
 7095	struct ath12k *ar;
 7096	u32 vdev_id = 0;
 7097
 7098	if (ath12k_pull_vdev_stopped_param_tlv(ab, skb, &vdev_id) != 0) {
 7099		ath12k_warn(ab, "failed to extract vdev stopped event");
 7100		return;
 7101	}
 7102
 7103	rcu_read_lock();
 7104	ar = ath12k_mac_get_ar_by_vdev_id(ab, vdev_id);
 7105	if (!ar) {
 7106		ath12k_warn(ab, "invalid vdev id in vdev stopped ev %d",
 7107			    vdev_id);
 7108		rcu_read_unlock();
 7109		return;
 7110	}
 7111
 7112	complete(&ar->vdev_setup_done);
 7113
 7114	rcu_read_unlock();
 7115
 7116	ath12k_dbg(ab, ATH12K_DBG_WMI, "vdev stopped for vdev id %d", vdev_id);
 7117}
 7118
 7119static void ath12k_mgmt_rx_event(struct ath12k_base *ab, struct sk_buff *skb)
 7120{
 7121	struct ath12k_wmi_mgmt_rx_arg rx_ev = {};
 7122	struct ath12k *ar;
 7123	struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb);
 7124	struct ieee80211_hdr *hdr;
 7125	u16 fc;
 7126	struct ieee80211_supported_band *sband;
 7127	s32 noise_floor;
 7128
 7129	if (ath12k_pull_mgmt_rx_params_tlv(ab, skb, &rx_ev) != 0) {
 7130		ath12k_warn(ab, "failed to extract mgmt rx event");
 7131		dev_kfree_skb(skb);
 7132		return;
 7133	}
 7134
 7135	memset(status, 0, sizeof(*status));
 7136
 7137	ath12k_dbg(ab, ATH12K_DBG_MGMT, "mgmt rx event status %08x\n",
 7138		   rx_ev.status);
 7139
 7140	rcu_read_lock();
 7141	ar = ath12k_mac_get_ar_by_pdev_id(ab, rx_ev.pdev_id);
 7142
 7143	if (!ar) {
 7144		ath12k_warn(ab, "invalid pdev_id %d in mgmt_rx_event\n",
 7145			    rx_ev.pdev_id);
 7146		dev_kfree_skb(skb);
 7147		goto exit;
 7148	}
 7149
 7150	if ((test_bit(ATH12K_FLAG_CAC_RUNNING, &ar->dev_flags)) ||
 7151	    (rx_ev.status & (WMI_RX_STATUS_ERR_DECRYPT |
 7152			     WMI_RX_STATUS_ERR_KEY_CACHE_MISS |
 7153			     WMI_RX_STATUS_ERR_CRC))) {
 7154		dev_kfree_skb(skb);
 7155		goto exit;
 7156	}
 7157
 7158	if (rx_ev.status & WMI_RX_STATUS_ERR_MIC)
 7159		status->flag |= RX_FLAG_MMIC_ERROR;
 7160
 7161	if (rx_ev.chan_freq >= ATH12K_MIN_6GHZ_FREQ &&
 7162	    rx_ev.chan_freq <= ATH12K_MAX_6GHZ_FREQ) {
 7163		status->band = NL80211_BAND_6GHZ;
 7164		status->freq = rx_ev.chan_freq;
 7165	} else if (rx_ev.channel >= 1 && rx_ev.channel <= 14) {
 7166		status->band = NL80211_BAND_2GHZ;
 7167	} else if (rx_ev.channel >= 36 && rx_ev.channel <= ATH12K_MAX_5GHZ_CHAN) {
 7168		status->band = NL80211_BAND_5GHZ;
 7169	} else {
 7170		/* Shouldn't happen unless list of advertised channels to
 7171		 * mac80211 has been changed.
 7172		 */
 7173		WARN_ON_ONCE(1);
 7174		dev_kfree_skb(skb);
 7175		goto exit;
 7176	}
 7177
 7178	if (rx_ev.phy_mode == MODE_11B &&
 7179	    (status->band == NL80211_BAND_5GHZ || status->band == NL80211_BAND_6GHZ))
 7180		ath12k_dbg(ab, ATH12K_DBG_WMI,
 7181			   "wmi mgmt rx 11b (CCK) on 5/6GHz, band = %d\n", status->band);
 7182
 7183	sband = &ar->mac.sbands[status->band];
 7184
 7185	if (status->band != NL80211_BAND_6GHZ)
 7186		status->freq = ieee80211_channel_to_frequency(rx_ev.channel,
 7187							      status->band);
 7188
 7189	spin_lock_bh(&ar->data_lock);
 7190	noise_floor = ath12k_pdev_get_noise_floor(ar);
 7191	spin_unlock_bh(&ar->data_lock);
 7192
 7193	status->signal = rx_ev.snr + noise_floor;
 7194	status->rate_idx = ath12k_mac_bitrate_to_idx(sband, rx_ev.rate / 100);
 7195
 7196	hdr = (struct ieee80211_hdr *)skb->data;
 7197	fc = le16_to_cpu(hdr->frame_control);
 7198
 7199	/* Firmware is guaranteed to report all essential management frames via
 7200	 * WMI while it can deliver some extra via HTT. Since there can be
 7201	 * duplicates split the reporting wrt monitor/sniffing.
 7202	 */
 7203	status->flag |= RX_FLAG_SKIP_MONITOR;
 7204
 7205	/* In case of PMF, FW delivers decrypted frames with Protected Bit set
 7206	 * including group privacy action frames.
 7207	 */
 7208	if (ieee80211_has_protected(hdr->frame_control)) {
 7209		status->flag |= RX_FLAG_DECRYPTED;
 7210
 7211		if (!ieee80211_is_robust_mgmt_frame(skb)) {
 7212			status->flag |= RX_FLAG_IV_STRIPPED |
 7213					RX_FLAG_MMIC_STRIPPED;
 7214			hdr->frame_control = __cpu_to_le16(fc &
 7215					     ~IEEE80211_FCTL_PROTECTED);
 7216		}
 7217	}
 7218
 7219	if (ieee80211_is_beacon(hdr->frame_control))
 7220		ath12k_mac_handle_beacon(ar, skb);
 7221
 7222	ath12k_dbg(ab, ATH12K_DBG_MGMT,
 7223		   "event mgmt rx skb %p len %d ftype %02x stype %02x\n",
 7224		   skb, skb->len,
 7225		   fc & IEEE80211_FCTL_FTYPE, fc & IEEE80211_FCTL_STYPE);
 7226
 7227	ath12k_dbg(ab, ATH12K_DBG_MGMT,
 7228		   "event mgmt rx freq %d band %d snr %d, rate_idx %d\n",
 7229		   status->freq, status->band, status->signal,
 7230		   status->rate_idx);
 7231
 7232	ieee80211_rx_ni(ath12k_ar_to_hw(ar), skb);
 7233
 7234exit:
 7235	rcu_read_unlock();
 7236}
 7237
 7238static void ath12k_mgmt_tx_compl_event(struct ath12k_base *ab, struct sk_buff *skb)
 7239{
 7240	struct wmi_mgmt_tx_compl_event tx_compl_param = {};
 7241	struct ath12k *ar;
 7242
 7243	if (ath12k_pull_mgmt_tx_compl_param_tlv(ab, skb, &tx_compl_param) != 0) {
 7244		ath12k_warn(ab, "failed to extract mgmt tx compl event");
 7245		return;
 7246	}
 7247
 7248	rcu_read_lock();
 7249	ar = ath12k_mac_get_ar_by_pdev_id(ab, le32_to_cpu(tx_compl_param.pdev_id));
 7250	if (!ar) {
 7251		ath12k_warn(ab, "invalid pdev id %d in mgmt_tx_compl_event\n",
 7252			    tx_compl_param.pdev_id);
 7253		goto exit;
 7254	}
 7255
 7256	wmi_process_mgmt_tx_comp(ar, le32_to_cpu(tx_compl_param.desc_id),
 7257				 le32_to_cpu(tx_compl_param.status),
 7258				 le32_to_cpu(tx_compl_param.ack_rssi));
 7259
 7260	ath12k_dbg(ab, ATH12K_DBG_MGMT,
 7261		   "mgmt tx compl ev pdev_id %d, desc_id %d, status %d",
 7262		   tx_compl_param.pdev_id, tx_compl_param.desc_id,
 7263		   tx_compl_param.status);
 7264
 7265exit:
 7266	rcu_read_unlock();
 7267}
 7268
 7269static struct ath12k *ath12k_get_ar_on_scan_state(struct ath12k_base *ab,
 7270						  u32 vdev_id,
 7271						  enum ath12k_scan_state state)
 7272{
 7273	int i;
 7274	struct ath12k_pdev *pdev;
 7275	struct ath12k *ar;
 7276
 7277	for (i = 0; i < ab->num_radios; i++) {
 7278		pdev = rcu_dereference(ab->pdevs_active[i]);
 7279		if (pdev && pdev->ar) {
 7280			ar = pdev->ar;
 7281
 7282			spin_lock_bh(&ar->data_lock);
 7283			if (ar->scan.state == state &&
 7284			    ar->scan.arvif &&
 7285			    ar->scan.arvif->vdev_id == vdev_id) {
 7286				spin_unlock_bh(&ar->data_lock);
 7287				return ar;
 7288			}
 7289			spin_unlock_bh(&ar->data_lock);
 7290		}
 7291	}
 7292	return NULL;
 7293}
 7294
 7295static void ath12k_scan_event(struct ath12k_base *ab, struct sk_buff *skb)
 7296{
 7297	struct ath12k *ar;
 7298	struct wmi_scan_event scan_ev = {};
 7299
 7300	if (ath12k_pull_scan_ev(ab, skb, &scan_ev) != 0) {
 7301		ath12k_warn(ab, "failed to extract scan event");
 7302		return;
 7303	}
 7304
 7305	rcu_read_lock();
 7306
 7307	/* In case the scan was cancelled, ex. during interface teardown,
 7308	 * the interface will not be found in active interfaces.
 7309	 * Rather, in such scenarios, iterate over the active pdev's to
 7310	 * search 'ar' if the corresponding 'ar' scan is ABORTING and the
 7311	 * aborting scan's vdev id matches this event info.
 7312	 */
 7313	if (le32_to_cpu(scan_ev.event_type) == WMI_SCAN_EVENT_COMPLETED &&
 7314	    le32_to_cpu(scan_ev.reason) == WMI_SCAN_REASON_CANCELLED) {
 7315		ar = ath12k_get_ar_on_scan_state(ab, le32_to_cpu(scan_ev.vdev_id),
 7316						 ATH12K_SCAN_ABORTING);
 7317		if (!ar)
 7318			ar = ath12k_get_ar_on_scan_state(ab, le32_to_cpu(scan_ev.vdev_id),
 7319							 ATH12K_SCAN_RUNNING);
 7320	} else {
 7321		ar = ath12k_mac_get_ar_by_vdev_id(ab, le32_to_cpu(scan_ev.vdev_id));
 7322	}
 7323
 7324	if (!ar) {
 7325		ath12k_warn(ab, "Received scan event for unknown vdev");
 7326		rcu_read_unlock();
 7327		return;
 7328	}
 7329
 7330	spin_lock_bh(&ar->data_lock);
 7331
 7332	ath12k_dbg(ab, ATH12K_DBG_WMI,
 7333		   "scan event %s type %d reason %d freq %d req_id %d scan_id %d vdev_id %d state %s (%d)\n",
 7334		   ath12k_wmi_event_scan_type_str(le32_to_cpu(scan_ev.event_type),
 7335						  le32_to_cpu(scan_ev.reason)),
 7336		   le32_to_cpu(scan_ev.event_type),
 7337		   le32_to_cpu(scan_ev.reason),
 7338		   le32_to_cpu(scan_ev.channel_freq),
 7339		   le32_to_cpu(scan_ev.scan_req_id),
 7340		   le32_to_cpu(scan_ev.scan_id),
 7341		   le32_to_cpu(scan_ev.vdev_id),
 7342		   ath12k_scan_state_str(ar->scan.state), ar->scan.state);
 7343
 7344	switch (le32_to_cpu(scan_ev.event_type)) {
 7345	case WMI_SCAN_EVENT_STARTED:
 7346		ath12k_wmi_event_scan_started(ar);
 7347		break;
 7348	case WMI_SCAN_EVENT_COMPLETED:
 7349		ath12k_wmi_event_scan_completed(ar);
 7350		break;
 7351	case WMI_SCAN_EVENT_BSS_CHANNEL:
 7352		ath12k_wmi_event_scan_bss_chan(ar);
 7353		break;
 7354	case WMI_SCAN_EVENT_FOREIGN_CHAN:
 7355		ath12k_wmi_event_scan_foreign_chan(ar, le32_to_cpu(scan_ev.channel_freq));
 7356		break;
 7357	case WMI_SCAN_EVENT_START_FAILED:
 7358		ath12k_warn(ab, "received scan start failure event\n");
 7359		ath12k_wmi_event_scan_start_failed(ar);
 7360		break;
 7361	case WMI_SCAN_EVENT_DEQUEUED:
 7362		__ath12k_mac_scan_finish(ar);
 7363		break;
 7364	case WMI_SCAN_EVENT_PREEMPTED:
 7365	case WMI_SCAN_EVENT_RESTARTED:
 7366	case WMI_SCAN_EVENT_FOREIGN_CHAN_EXIT:
 7367	default:
 7368		break;
 7369	}
 7370
 7371	spin_unlock_bh(&ar->data_lock);
 7372
 7373	rcu_read_unlock();
 7374}
 7375
 7376static void ath12k_peer_sta_kickout_event(struct ath12k_base *ab, struct sk_buff *skb)
 7377{
 7378	struct wmi_peer_sta_kickout_arg arg = {};
 7379	struct ath12k_link_vif *arvif;
 7380	struct ieee80211_sta *sta;
 7381	struct ath12k_peer *peer;
 7382	unsigned int link_id;
 7383	struct ath12k *ar;
 7384
 7385	if (ath12k_pull_peer_sta_kickout_ev(ab, skb, &arg) != 0) {
 7386		ath12k_warn(ab, "failed to extract peer sta kickout event");
 7387		return;
 7388	}
 7389
 7390	rcu_read_lock();
 7391
 7392	spin_lock_bh(&ab->base_lock);
 7393
 7394	peer = ath12k_peer_find_by_addr(ab, arg.mac_addr);
 7395
 7396	if (!peer) {
 7397		ath12k_warn(ab, "peer not found %pM\n",
 7398			    arg.mac_addr);
 7399		goto exit;
 7400	}
 7401
 7402	arvif = ath12k_mac_get_arvif_by_vdev_id(ab, peer->vdev_id);
 7403	if (!arvif) {
 7404		ath12k_warn(ab, "invalid vdev id in peer sta kickout ev %d",
 7405			    peer->vdev_id);
 7406		goto exit;
 7407	}
 7408
 7409	ar = arvif->ar;
 7410
 7411	if (peer->mlo) {
 7412		sta = ieee80211_find_sta_by_link_addrs(ath12k_ar_to_hw(ar),
 7413						       arg.mac_addr,
 7414						       NULL, &link_id);
 7415		if (peer->link_id != link_id) {
 7416			ath12k_warn(ab,
 7417				    "Spurious quick kickout for MLO STA %pM with invalid link_id, peer: %d, sta: %d\n",
 7418				    arg.mac_addr, peer->link_id, link_id);
 7419			goto exit;
 7420		}
 7421	} else {
 7422		sta = ieee80211_find_sta_by_ifaddr(ath12k_ar_to_hw(ar),
 7423						   arg.mac_addr, NULL);
 7424	}
 7425	if (!sta) {
 7426		ath12k_warn(ab, "Spurious quick kickout for %sSTA %pM\n",
 7427			    peer->mlo ? "MLO " : "", arg.mac_addr);
 7428		goto exit;
 7429	}
 7430
 7431	ath12k_dbg(ab, ATH12K_DBG_WMI,
 7432		   "peer sta kickout event %pM reason: %d rssi: %d\n",
 7433		   arg.mac_addr, arg.reason, arg.rssi);
 7434
 7435	switch (arg.reason) {
 7436	case WMI_PEER_STA_KICKOUT_REASON_INACTIVITY:
 7437		if (arvif->ahvif->vif->type == NL80211_IFTYPE_STATION) {
 7438			ath12k_mac_handle_beacon_miss(ar, arvif);
 7439			break;
 7440		}
 7441		fallthrough;
 7442	default:
 7443		ieee80211_report_low_ack(sta, 10);
 7444	}
 7445
 7446exit:
 7447	spin_unlock_bh(&ab->base_lock);
 7448	rcu_read_unlock();
 7449}
 7450
 7451static void ath12k_roam_event(struct ath12k_base *ab, struct sk_buff *skb)
 7452{
 7453	struct ath12k_link_vif *arvif;
 7454	struct wmi_roam_event roam_ev = {};
 7455	struct ath12k *ar;
 7456	u32 vdev_id;
 7457	u8 roam_reason;
 7458
 7459	if (ath12k_pull_roam_ev(ab, skb, &roam_ev) != 0) {
 7460		ath12k_warn(ab, "failed to extract roam event");
 7461		return;
 7462	}
 7463
 7464	vdev_id = le32_to_cpu(roam_ev.vdev_id);
 7465	roam_reason = u32_get_bits(le32_to_cpu(roam_ev.reason),
 7466				   WMI_ROAM_REASON_MASK);
 7467
 7468	ath12k_dbg(ab, ATH12K_DBG_WMI,
 7469		   "wmi roam event vdev %u reason %d rssi %d\n",
 7470		   vdev_id, roam_reason, roam_ev.rssi);
 7471
 7472	guard(rcu)();
 7473	arvif = ath12k_mac_get_arvif_by_vdev_id(ab, vdev_id);
 7474	if (!arvif) {
 7475		ath12k_warn(ab, "invalid vdev id in roam ev %d", vdev_id);
 7476		return;
 7477	}
 7478
 7479	ar = arvif->ar;
 7480
 7481	if (roam_reason >= WMI_ROAM_REASON_MAX)
 7482		ath12k_warn(ab, "ignoring unknown roam event reason %d on vdev %i\n",
 7483			    roam_reason, vdev_id);
 7484
 7485	switch (roam_reason) {
 7486	case WMI_ROAM_REASON_BEACON_MISS:
 7487		ath12k_mac_handle_beacon_miss(ar, arvif);
 7488		break;
 7489	case WMI_ROAM_REASON_BETTER_AP:
 7490	case WMI_ROAM_REASON_LOW_RSSI:
 7491	case WMI_ROAM_REASON_SUITABLE_AP_FOUND:
 7492	case WMI_ROAM_REASON_HO_FAILED:
 7493		ath12k_warn(ab, "ignoring not implemented roam event reason %d on vdev %i\n",
 7494			    roam_reason, vdev_id);
 7495		break;
 7496	}
 7497}
 7498
 7499static void ath12k_chan_info_event(struct ath12k_base *ab, struct sk_buff *skb)
 7500{
 7501	struct wmi_chan_info_event ch_info_ev = {};
 7502	struct ath12k *ar;
 7503	struct survey_info *survey;
 7504	int idx;
 7505	/* HW channel counters frequency value in hertz */
 7506	u32 cc_freq_hz = ab->cc_freq_hz;
 7507
 7508	if (ath12k_pull_chan_info_ev(ab, skb, &ch_info_ev) != 0) {
 7509		ath12k_warn(ab, "failed to extract chan info event");
 7510		return;
 7511	}
 7512
 7513	ath12k_dbg(ab, ATH12K_DBG_WMI,
 7514		   "chan info vdev_id %d err_code %d freq %d cmd_flags %d noise_floor %d rx_clear_count %d cycle_count %d mac_clk_mhz %d\n",
 7515		   ch_info_ev.vdev_id, ch_info_ev.err_code, ch_info_ev.freq,
 7516		   ch_info_ev.cmd_flags, ch_info_ev.noise_floor,
 7517		   ch_info_ev.rx_clear_count, ch_info_ev.cycle_count,
 7518		   ch_info_ev.mac_clk_mhz);
 7519
 7520	if (le32_to_cpu(ch_info_ev.cmd_flags) == WMI_CHAN_INFO_END_RESP) {
 7521		ath12k_dbg(ab, ATH12K_DBG_WMI, "chan info report completed\n");
 7522		return;
 7523	}
 7524
 7525	rcu_read_lock();
 7526	ar = ath12k_mac_get_ar_by_vdev_id(ab, le32_to_cpu(ch_info_ev.vdev_id));
 7527	if (!ar) {
 7528		ath12k_warn(ab, "invalid vdev id in chan info ev %d",
 7529			    ch_info_ev.vdev_id);
 7530		rcu_read_unlock();
 7531		return;
 7532	}
 7533	spin_lock_bh(&ar->data_lock);
 7534
 7535	switch (ar->scan.state) {
 7536	case ATH12K_SCAN_IDLE:
 7537	case ATH12K_SCAN_STARTING:
 7538		ath12k_warn(ab, "received chan info event without a scan request, ignoring\n");
 7539		goto exit;
 7540	case ATH12K_SCAN_RUNNING:
 7541	case ATH12K_SCAN_ABORTING:
 7542		break;
 7543	}
 7544
 7545	idx = freq_to_idx(ar, le32_to_cpu(ch_info_ev.freq));
 7546	if (idx >= ARRAY_SIZE(ar->survey)) {
 7547		ath12k_warn(ab, "chan info: invalid frequency %d (idx %d out of bounds)\n",
 7548			    ch_info_ev.freq, idx);
 7549		goto exit;
 7550	}
 7551
 7552	/* If FW provides MAC clock frequency in Mhz, overriding the initialized
 7553	 * HW channel counters frequency value
 7554	 */
 7555	if (ch_info_ev.mac_clk_mhz)
 7556		cc_freq_hz = (le32_to_cpu(ch_info_ev.mac_clk_mhz) * 1000);
 7557
 7558	if (ch_info_ev.cmd_flags == WMI_CHAN_INFO_START_RESP) {
 7559		survey = &ar->survey[idx];
 7560		memset(survey, 0, sizeof(*survey));
 7561		survey->noise = le32_to_cpu(ch_info_ev.noise_floor);
 7562		survey->filled = SURVEY_INFO_NOISE_DBM | SURVEY_INFO_TIME |
 7563				 SURVEY_INFO_TIME_BUSY;
 7564		survey->time = div_u64(le32_to_cpu(ch_info_ev.cycle_count), cc_freq_hz);
 7565		survey->time_busy = div_u64(le32_to_cpu(ch_info_ev.rx_clear_count),
 7566					    cc_freq_hz);
 7567	}
 7568exit:
 7569	spin_unlock_bh(&ar->data_lock);
 7570	rcu_read_unlock();
 7571}
 7572
 7573static void
 7574ath12k_pdev_bss_chan_info_event(struct ath12k_base *ab, struct sk_buff *skb)
 7575{
 7576	struct wmi_pdev_bss_chan_info_event bss_ch_info_ev = {};
 7577	struct survey_info *survey;
 7578	struct ath12k *ar;
 7579	u32 cc_freq_hz = ab->cc_freq_hz;
 7580	u64 busy, total, tx, rx, rx_bss;
 7581	int idx;
 7582
 7583	if (ath12k_pull_pdev_bss_chan_info_ev(ab, skb, &bss_ch_info_ev) != 0) {
 7584		ath12k_warn(ab, "failed to extract pdev bss chan info event");
 7585		return;
 7586	}
 7587
 7588	busy = (u64)(le32_to_cpu(bss_ch_info_ev.rx_clear_count_high)) << 32 |
 7589		le32_to_cpu(bss_ch_info_ev.rx_clear_count_low);
 7590
 7591	total = (u64)(le32_to_cpu(bss_ch_info_ev.cycle_count_high)) << 32 |
 7592		le32_to_cpu(bss_ch_info_ev.cycle_count_low);
 7593
 7594	tx = (u64)(le32_to_cpu(bss_ch_info_ev.tx_cycle_count_high)) << 32 |
 7595		le32_to_cpu(bss_ch_info_ev.tx_cycle_count_low);
 7596
 7597	rx = (u64)(le32_to_cpu(bss_ch_info_ev.rx_cycle_count_high)) << 32 |
 7598		le32_to_cpu(bss_ch_info_ev.rx_cycle_count_low);
 7599
 7600	rx_bss = (u64)(le32_to_cpu(bss_ch_info_ev.rx_bss_cycle_count_high)) << 32 |
 7601		le32_to_cpu(bss_ch_info_ev.rx_bss_cycle_count_low);
 7602
 7603	ath12k_dbg(ab, ATH12K_DBG_WMI,
 7604		   "pdev bss chan info:\n pdev_id: %d freq: %d noise: %d cycle: busy %llu total %llu tx %llu rx %llu rx_bss %llu\n",
 7605		   bss_ch_info_ev.pdev_id, bss_ch_info_ev.freq,
 7606		   bss_ch_info_ev.noise_floor, busy, total,
 7607		   tx, rx, rx_bss);
 7608
 7609	rcu_read_lock();
 7610	ar = ath12k_mac_get_ar_by_pdev_id(ab, le32_to_cpu(bss_ch_info_ev.pdev_id));
 7611
 7612	if (!ar) {
 7613		ath12k_warn(ab, "invalid pdev id %d in bss_chan_info event\n",
 7614			    bss_ch_info_ev.pdev_id);
 7615		rcu_read_unlock();
 7616		return;
 7617	}
 7618
 7619	spin_lock_bh(&ar->data_lock);
 7620	idx = freq_to_idx(ar, le32_to_cpu(bss_ch_info_ev.freq));
 7621	if (idx >= ARRAY_SIZE(ar->survey)) {
 7622		ath12k_warn(ab, "bss chan info: invalid frequency %d (idx %d out of bounds)\n",
 7623			    bss_ch_info_ev.freq, idx);
 7624		goto exit;
 7625	}
 7626
 7627	survey = &ar->survey[idx];
 7628
 7629	survey->noise     = le32_to_cpu(bss_ch_info_ev.noise_floor);
 7630	survey->time      = div_u64(total, cc_freq_hz);
 7631	survey->time_busy = div_u64(busy, cc_freq_hz);
 7632	survey->time_rx   = div_u64(rx_bss, cc_freq_hz);
 7633	survey->time_tx   = div_u64(tx, cc_freq_hz);
 7634	survey->filled   |= (SURVEY_INFO_NOISE_DBM |
 7635			     SURVEY_INFO_TIME |
 7636			     SURVEY_INFO_TIME_BUSY |
 7637			     SURVEY_INFO_TIME_RX |
 7638			     SURVEY_INFO_TIME_TX);
 7639exit:
 7640	spin_unlock_bh(&ar->data_lock);
 7641	complete(&ar->bss_survey_done);
 7642
 7643	rcu_read_unlock();
 7644}
 7645
 7646static void ath12k_vdev_install_key_compl_event(struct ath12k_base *ab,
 7647						struct sk_buff *skb)
 7648{
 7649	struct wmi_vdev_install_key_complete_arg install_key_compl = {};
 7650	struct ath12k *ar;
 7651
 7652	if (ath12k_pull_vdev_install_key_compl_ev(ab, skb, &install_key_compl) != 0) {
 7653		ath12k_warn(ab, "failed to extract install key compl event");
 7654		return;
 7655	}
 7656
 7657	ath12k_dbg(ab, ATH12K_DBG_WMI,
 7658		   "vdev install key ev idx %d flags %08x macaddr %pM status %d\n",
 7659		   install_key_compl.key_idx, install_key_compl.key_flags,
 7660		   install_key_compl.macaddr, install_key_compl.status);
 7661
 7662	rcu_read_lock();
 7663	ar = ath12k_mac_get_ar_by_vdev_id(ab, install_key_compl.vdev_id);
 7664	if (!ar) {
 7665		ath12k_warn(ab, "invalid vdev id in install key compl ev %d",
 7666			    install_key_compl.vdev_id);
 7667		rcu_read_unlock();
 7668		return;
 7669	}
 7670
 7671	ar->install_key_status = 0;
 7672
 7673	if (install_key_compl.status != WMI_VDEV_INSTALL_KEY_COMPL_STATUS_SUCCESS) {
 7674		ath12k_warn(ab, "install key failed for %pM status %d\n",
 7675			    install_key_compl.macaddr, install_key_compl.status);
 7676		ar->install_key_status = install_key_compl.status;
 7677	}
 7678
 7679	complete(&ar->install_key_done);
 7680	rcu_read_unlock();
 7681}
 7682
 7683static int ath12k_wmi_tlv_services_parser(struct ath12k_base *ab,
 7684					  u16 tag, u16 len,
 7685					  const void *ptr,
 7686					  void *data)
 7687{
 7688	const struct wmi_service_available_event *ev;
 7689	u16 wmi_ext2_service_words;
 7690	__le32 *wmi_ext2_service_bitmap;
 7691	int i, j;
 7692	u16 expected_len;
 7693
 7694	expected_len = WMI_SERVICE_SEGMENT_BM_SIZE32 * sizeof(u32);
 7695	if (len < expected_len) {
 7696		ath12k_warn(ab, "invalid length %d for the WMI services available tag 0x%x\n",
 7697			    len, tag);
 7698		return -EINVAL;
 7699	}
 7700
 7701	switch (tag) {
 7702	case WMI_TAG_SERVICE_AVAILABLE_EVENT:
 7703		ev = (struct wmi_service_available_event *)ptr;
 7704		for (i = 0, j = WMI_MAX_SERVICE;
 7705		     i < WMI_SERVICE_SEGMENT_BM_SIZE32 && j < WMI_MAX_EXT_SERVICE;
 7706		     i++) {
 7707			do {
 7708				if (le32_to_cpu(ev->wmi_service_segment_bitmap[i]) &
 7709				    BIT(j % WMI_AVAIL_SERVICE_BITS_IN_SIZE32))
 7710					set_bit(j, ab->wmi_ab.svc_map);
 7711			} while (++j % WMI_AVAIL_SERVICE_BITS_IN_SIZE32);
 7712		}
 7713
 7714		ath12k_dbg(ab, ATH12K_DBG_WMI,
 7715			   "wmi_ext_service_bitmap 0x%x 0x%x 0x%x 0x%x",
 7716			   ev->wmi_service_segment_bitmap[0],
 7717			   ev->wmi_service_segment_bitmap[1],
 7718			   ev->wmi_service_segment_bitmap[2],
 7719			   ev->wmi_service_segment_bitmap[3]);
 7720		break;
 7721	case WMI_TAG_ARRAY_UINT32:
 7722		wmi_ext2_service_bitmap = (__le32 *)ptr;
 7723		wmi_ext2_service_words = len / sizeof(u32);
 7724		for (i = 0, j = WMI_MAX_EXT_SERVICE;
 7725		     i < wmi_ext2_service_words && j < WMI_MAX_EXT2_SERVICE;
 7726		     i++) {
 7727			do {
 7728				if (__le32_to_cpu(wmi_ext2_service_bitmap[i]) &
 7729				    BIT(j % WMI_AVAIL_SERVICE_BITS_IN_SIZE32))
 7730					set_bit(j, ab->wmi_ab.svc_map);
 7731			} while (++j % WMI_AVAIL_SERVICE_BITS_IN_SIZE32);
 7732			ath12k_dbg(ab, ATH12K_DBG_WMI,
 7733				   "wmi_ext2_service bitmap 0x%08x\n",
 7734				   __le32_to_cpu(wmi_ext2_service_bitmap[i]));
 7735		}
 7736
 7737		break;
 7738	}
 7739	return 0;
 7740}
 7741
 7742static int ath12k_service_available_event(struct ath12k_base *ab, struct sk_buff *skb)
 7743{
 7744	int ret;
 7745
 7746	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 7747				  ath12k_wmi_tlv_services_parser,
 7748				  NULL);
 7749	return ret;
 7750}
 7751
 7752static void ath12k_peer_assoc_conf_event(struct ath12k_base *ab, struct sk_buff *skb)
 7753{
 7754	struct wmi_peer_assoc_conf_arg peer_assoc_conf = {};
 7755	struct ath12k *ar;
 7756
 7757	if (ath12k_pull_peer_assoc_conf_ev(ab, skb, &peer_assoc_conf) != 0) {
 7758		ath12k_warn(ab, "failed to extract peer assoc conf event");
 7759		return;
 7760	}
 7761
 7762	ath12k_dbg(ab, ATH12K_DBG_WMI,
 7763		   "peer assoc conf ev vdev id %d macaddr %pM\n",
 7764		   peer_assoc_conf.vdev_id, peer_assoc_conf.macaddr);
 7765
 7766	rcu_read_lock();
 7767	ar = ath12k_mac_get_ar_by_vdev_id(ab, peer_assoc_conf.vdev_id);
 7768
 7769	if (!ar) {
 7770		ath12k_warn(ab, "invalid vdev id in peer assoc conf ev %d",
 7771			    peer_assoc_conf.vdev_id);
 7772		rcu_read_unlock();
 7773		return;
 7774	}
 7775
 7776	complete(&ar->peer_assoc_done);
 7777	rcu_read_unlock();
 7778}
 7779
 7780static void
 7781ath12k_wmi_fw_vdev_stats_dump(struct ath12k *ar,
 7782			      struct ath12k_fw_stats *fw_stats,
 7783			      char *buf, u32 *length)
 7784{
 7785	const struct ath12k_fw_stats_vdev *vdev;
 7786	u32 buf_len = ATH12K_FW_STATS_BUF_SIZE;
 7787	struct ath12k_link_vif *arvif;
 7788	u32 len = *length;
 7789	u8 *vif_macaddr;
 7790	int i;
 7791
 7792	len += scnprintf(buf + len, buf_len - len, "\n");
 7793	len += scnprintf(buf + len, buf_len - len, "%30s\n",
 7794			 "ath12k VDEV stats");
 7795	len += scnprintf(buf + len, buf_len - len, "%30s\n\n",
 7796			 "=================");
 7797
 7798	list_for_each_entry(vdev, &fw_stats->vdevs, list) {
 7799		arvif = ath12k_mac_get_arvif(ar, vdev->vdev_id);
 7800		if (!arvif)
 7801			continue;
 7802		vif_macaddr = arvif->ahvif->vif->addr;
 7803
 7804		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7805				 "VDEV ID", vdev->vdev_id);
 7806		len += scnprintf(buf + len, buf_len - len, "%30s %pM\n",
 7807				 "VDEV MAC address", vif_macaddr);
 7808		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7809				 "beacon snr", vdev->beacon_snr);
 7810		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7811				 "data snr", vdev->data_snr);
 7812		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7813				 "num rx frames", vdev->num_rx_frames);
 7814		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7815				 "num rts fail", vdev->num_rts_fail);
 7816		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7817				 "num rts success", vdev->num_rts_success);
 7818		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7819				 "num rx err", vdev->num_rx_err);
 7820		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7821				 "num rx discard", vdev->num_rx_discard);
 7822		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7823				 "num tx not acked", vdev->num_tx_not_acked);
 7824
 7825		for (i = 0 ; i < WLAN_MAX_AC; i++)
 7826			len += scnprintf(buf + len, buf_len - len,
 7827					"%25s [%02d] %u\n",
 7828					"num tx frames", i,
 7829					vdev->num_tx_frames[i]);
 7830
 7831		for (i = 0 ; i < WLAN_MAX_AC; i++)
 7832			len += scnprintf(buf + len, buf_len - len,
 7833					"%25s [%02d] %u\n",
 7834					"num tx frames retries", i,
 7835					vdev->num_tx_frames_retries[i]);
 7836
 7837		for (i = 0 ; i < WLAN_MAX_AC; i++)
 7838			len += scnprintf(buf + len, buf_len - len,
 7839					"%25s [%02d] %u\n",
 7840					"num tx frames failures", i,
 7841					vdev->num_tx_frames_failures[i]);
 7842
 7843		for (i = 0 ; i < MAX_TX_RATE_VALUES; i++)
 7844			len += scnprintf(buf + len, buf_len - len,
 7845					"%25s [%02d] 0x%08x\n",
 7846					"tx rate history", i,
 7847					vdev->tx_rate_history[i]);
 7848		for (i = 0 ; i < MAX_TX_RATE_VALUES; i++)
 7849			len += scnprintf(buf + len, buf_len - len,
 7850					"%25s [%02d] %u\n",
 7851					"beacon rssi history", i,
 7852					vdev->beacon_rssi_history[i]);
 7853
 7854		len += scnprintf(buf + len, buf_len - len, "\n");
 7855		*length = len;
 7856	}
 7857}
 7858
 7859static void
 7860ath12k_wmi_fw_bcn_stats_dump(struct ath12k *ar,
 7861			     struct ath12k_fw_stats *fw_stats,
 7862			     char *buf, u32 *length)
 7863{
 7864	const struct ath12k_fw_stats_bcn *bcn;
 7865	u32 buf_len = ATH12K_FW_STATS_BUF_SIZE;
 7866	struct ath12k_link_vif *arvif;
 7867	u32 len = *length;
 7868	size_t num_bcn;
 7869
 7870	num_bcn = list_count_nodes(&fw_stats->bcn);
 7871
 7872	len += scnprintf(buf + len, buf_len - len, "\n");
 7873	len += scnprintf(buf + len, buf_len - len, "%30s (%zu)\n",
 7874			 "ath12k Beacon stats", num_bcn);
 7875	len += scnprintf(buf + len, buf_len - len, "%30s\n\n",
 7876			 "===================");
 7877
 7878	list_for_each_entry(bcn, &fw_stats->bcn, list) {
 7879		arvif = ath12k_mac_get_arvif(ar, bcn->vdev_id);
 7880		if (!arvif)
 7881			continue;
 7882		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7883				 "VDEV ID", bcn->vdev_id);
 7884		len += scnprintf(buf + len, buf_len - len, "%30s %pM\n",
 7885				 "VDEV MAC address", arvif->ahvif->vif->addr);
 7886		len += scnprintf(buf + len, buf_len - len, "%30s\n\n",
 7887				 "================");
 7888		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7889				 "Num of beacon tx success", bcn->tx_bcn_succ_cnt);
 7890		len += scnprintf(buf + len, buf_len - len, "%30s %u\n",
 7891				 "Num of beacon tx failures", bcn->tx_bcn_outage_cnt);
 7892
 7893		len += scnprintf(buf + len, buf_len - len, "\n");
 7894		*length = len;
 7895	}
 7896}
 7897
 7898static void
 7899ath12k_wmi_fw_pdev_base_stats_dump(const struct ath12k_fw_stats_pdev *pdev,
 7900				   char *buf, u32 *length, u64 fw_soc_drop_cnt)
 7901{
 7902	u32 len = *length;
 7903	u32 buf_len = ATH12K_FW_STATS_BUF_SIZE;
 7904
 7905	len = scnprintf(buf + len, buf_len - len, "\n");
 7906	len += scnprintf(buf + len, buf_len - len, "%30s\n",
 7907			"ath12k PDEV stats");
 7908	len += scnprintf(buf + len, buf_len - len, "%30s\n\n",
 7909			"=================");
 7910
 7911	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7912			"Channel noise floor", pdev->ch_noise_floor);
 7913	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7914			"Channel TX power", pdev->chan_tx_power);
 7915	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7916			"TX frame count", pdev->tx_frame_count);
 7917	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7918			"RX frame count", pdev->rx_frame_count);
 7919	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7920			"RX clear count", pdev->rx_clear_count);
 7921	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7922			"Cycle count", pdev->cycle_count);
 7923	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7924			"PHY error count", pdev->phy_err_count);
 7925	len += scnprintf(buf + len, buf_len - len, "%30s %10llu\n",
 7926			"soc drop count", fw_soc_drop_cnt);
 7927
 7928	*length = len;
 7929}
 7930
 7931static void
 7932ath12k_wmi_fw_pdev_tx_stats_dump(const struct ath12k_fw_stats_pdev *pdev,
 7933				 char *buf, u32 *length)
 7934{
 7935	u32 len = *length;
 7936	u32 buf_len = ATH12K_FW_STATS_BUF_SIZE;
 7937
 7938	len += scnprintf(buf + len, buf_len - len, "\n%30s\n",
 7939			 "ath12k PDEV TX stats");
 7940	len += scnprintf(buf + len, buf_len - len, "%30s\n\n",
 7941			 "====================");
 7942
 7943	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7944			 "HTT cookies queued", pdev->comp_queued);
 7945	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7946			 "HTT cookies disp.", pdev->comp_delivered);
 7947	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7948			 "MSDU queued", pdev->msdu_enqued);
 7949	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7950			 "MPDU queued", pdev->mpdu_enqued);
 7951	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7952			 "MSDUs dropped", pdev->wmm_drop);
 7953	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7954			 "Local enqued", pdev->local_enqued);
 7955	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7956			 "Local freed", pdev->local_freed);
 7957	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7958			 "HW queued", pdev->hw_queued);
 7959	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7960			 "PPDUs reaped", pdev->hw_reaped);
 7961	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7962			 "Num underruns", pdev->underrun);
 7963	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7964			 "PPDUs cleaned", pdev->tx_abort);
 7965	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 7966			 "MPDUs requeued", pdev->mpdus_requed);
 7967	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7968			 "Excessive retries", pdev->tx_ko);
 7969	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7970			 "HW rate", pdev->data_rc);
 7971	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7972			 "Sched self triggers", pdev->self_triggers);
 7973	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7974			 "Dropped due to SW retries",
 7975			 pdev->sw_retry_failure);
 7976	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7977			 "Illegal rate phy errors",
 7978			 pdev->illgl_rate_phy_err);
 7979	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7980			 "PDEV continuous xretry", pdev->pdev_cont_xretry);
 7981	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7982			 "TX timeout", pdev->pdev_tx_timeout);
 7983	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7984			 "PDEV resets", pdev->pdev_resets);
 7985	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7986			 "Stateless TIDs alloc failures",
 7987			 pdev->stateless_tid_alloc_failure);
 7988	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7989			 "PHY underrun", pdev->phy_underrun);
 7990	len += scnprintf(buf + len, buf_len - len, "%30s %10u\n",
 7991			 "MPDU is more than txop limit", pdev->txop_ovf);
 7992	*length = len;
 7993}
 7994
 7995static void
 7996ath12k_wmi_fw_pdev_rx_stats_dump(const struct ath12k_fw_stats_pdev *pdev,
 7997				 char *buf, u32 *length)
 7998{
 7999	u32 len = *length;
 8000	u32 buf_len = ATH12K_FW_STATS_BUF_SIZE;
 8001
 8002	len += scnprintf(buf + len, buf_len - len, "\n%30s\n",
 8003			 "ath12k PDEV RX stats");
 8004	len += scnprintf(buf + len, buf_len - len, "%30s\n\n",
 8005			 "====================");
 8006
 8007	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8008			 "Mid PPDU route change",
 8009			 pdev->mid_ppdu_route_change);
 8010	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8011			 "Tot. number of statuses", pdev->status_rcvd);
 8012	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8013			 "Extra frags on rings 0", pdev->r0_frags);
 8014	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8015			 "Extra frags on rings 1", pdev->r1_frags);
 8016	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8017			 "Extra frags on rings 2", pdev->r2_frags);
 8018	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8019			 "Extra frags on rings 3", pdev->r3_frags);
 8020	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8021			 "MSDUs delivered to HTT", pdev->htt_msdus);
 8022	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8023			 "MPDUs delivered to HTT", pdev->htt_mpdus);
 8024	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8025			 "MSDUs delivered to stack", pdev->loc_msdus);
 8026	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8027			 "MPDUs delivered to stack", pdev->loc_mpdus);
 8028	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8029			 "Oversized AMSUs", pdev->oversize_amsdu);
 8030	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8031			 "PHY errors", pdev->phy_errs);
 8032	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8033			 "PHY errors drops", pdev->phy_err_drop);
 8034	len += scnprintf(buf + len, buf_len - len, "%30s %10d\n",
 8035			 "MPDU errors (FCS, MIC, ENC)", pdev->mpdu_errs);
 8036	*length = len;
 8037}
 8038
 8039static void
 8040ath12k_wmi_fw_pdev_stats_dump(struct ath12k *ar,
 8041			      struct ath12k_fw_stats *fw_stats,
 8042			      char *buf, u32 *length)
 8043{
 8044	const struct ath12k_fw_stats_pdev *pdev;
 8045	u32 len = *length;
 8046
 8047	pdev = list_first_entry_or_null(&fw_stats->pdevs,
 8048					struct ath12k_fw_stats_pdev, list);
 8049	if (!pdev) {
 8050		ath12k_warn(ar->ab, "failed to get pdev stats\n");
 8051		return;
 8052	}
 8053
 8054	ath12k_wmi_fw_pdev_base_stats_dump(pdev, buf, &len,
 8055					   ar->ab->fw_soc_drop_count);
 8056	ath12k_wmi_fw_pdev_tx_stats_dump(pdev, buf, &len);
 8057	ath12k_wmi_fw_pdev_rx_stats_dump(pdev, buf, &len);
 8058
 8059	*length = len;
 8060}
 8061
 8062void ath12k_wmi_fw_stats_dump(struct ath12k *ar,
 8063			      struct ath12k_fw_stats *fw_stats,
 8064			      u32 stats_id, char *buf)
 8065{
 8066	u32 len = 0;
 8067	u32 buf_len = ATH12K_FW_STATS_BUF_SIZE;
 8068
 8069	spin_lock_bh(&ar->data_lock);
 8070
 8071	switch (stats_id) {
 8072	case WMI_REQUEST_VDEV_STAT:
 8073		ath12k_wmi_fw_vdev_stats_dump(ar, fw_stats, buf, &len);
 8074		break;
 8075	case WMI_REQUEST_BCN_STAT:
 8076		ath12k_wmi_fw_bcn_stats_dump(ar, fw_stats, buf, &len);
 8077		break;
 8078	case WMI_REQUEST_PDEV_STAT:
 8079		ath12k_wmi_fw_pdev_stats_dump(ar, fw_stats, buf, &len);
 8080		break;
 8081	default:
 8082		break;
 8083	}
 8084
 8085	spin_unlock_bh(&ar->data_lock);
 8086
 8087	if (len >= buf_len)
 8088		buf[len - 1] = 0;
 8089	else
 8090		buf[len] = 0;
 8091}
 8092
 8093static void
 8094ath12k_wmi_pull_vdev_stats(const struct wmi_vdev_stats_params *src,
 8095			   struct ath12k_fw_stats_vdev *dst)
 8096{
 8097	int i;
 8098
 8099	dst->vdev_id = le32_to_cpu(src->vdev_id);
 8100	dst->beacon_snr = le32_to_cpu(src->beacon_snr);
 8101	dst->data_snr = le32_to_cpu(src->data_snr);
 8102	dst->num_rx_frames = le32_to_cpu(src->num_rx_frames);
 8103	dst->num_rts_fail = le32_to_cpu(src->num_rts_fail);
 8104	dst->num_rts_success = le32_to_cpu(src->num_rts_success);
 8105	dst->num_rx_err = le32_to_cpu(src->num_rx_err);
 8106	dst->num_rx_discard = le32_to_cpu(src->num_rx_discard);
 8107	dst->num_tx_not_acked = le32_to_cpu(src->num_tx_not_acked);
 8108
 8109	for (i = 0; i < WLAN_MAX_AC; i++)
 8110		dst->num_tx_frames[i] =
 8111			le32_to_cpu(src->num_tx_frames[i]);
 8112
 8113	for (i = 0; i < WLAN_MAX_AC; i++)
 8114		dst->num_tx_frames_retries[i] =
 8115			le32_to_cpu(src->num_tx_frames_retries[i]);
 8116
 8117	for (i = 0; i < WLAN_MAX_AC; i++)
 8118		dst->num_tx_frames_failures[i] =
 8119			le32_to_cpu(src->num_tx_frames_failures[i]);
 8120
 8121	for (i = 0; i < MAX_TX_RATE_VALUES; i++)
 8122		dst->tx_rate_history[i] =
 8123			le32_to_cpu(src->tx_rate_history[i]);
 8124
 8125	for (i = 0; i < MAX_TX_RATE_VALUES; i++)
 8126		dst->beacon_rssi_history[i] =
 8127			le32_to_cpu(src->beacon_rssi_history[i]);
 8128}
 8129
 8130static void
 8131ath12k_wmi_pull_bcn_stats(const struct ath12k_wmi_bcn_stats_params *src,
 8132			  struct ath12k_fw_stats_bcn *dst)
 8133{
 8134	dst->vdev_id = le32_to_cpu(src->vdev_id);
 8135	dst->tx_bcn_succ_cnt = le32_to_cpu(src->tx_bcn_succ_cnt);
 8136	dst->tx_bcn_outage_cnt = le32_to_cpu(src->tx_bcn_outage_cnt);
 8137}
 8138
 8139static void
 8140ath12k_wmi_pull_pdev_stats_base(const struct ath12k_wmi_pdev_base_stats_params *src,
 8141				struct ath12k_fw_stats_pdev *dst)
 8142{
 8143	dst->ch_noise_floor = a_sle32_to_cpu(src->chan_nf);
 8144	dst->tx_frame_count = __le32_to_cpu(src->tx_frame_count);
 8145	dst->rx_frame_count = __le32_to_cpu(src->rx_frame_count);
 8146	dst->rx_clear_count = __le32_to_cpu(src->rx_clear_count);
 8147	dst->cycle_count = __le32_to_cpu(src->cycle_count);
 8148	dst->phy_err_count = __le32_to_cpu(src->phy_err_count);
 8149	dst->chan_tx_power = __le32_to_cpu(src->chan_tx_pwr);
 8150}
 8151
 8152static void
 8153ath12k_wmi_pull_pdev_stats_tx(const struct ath12k_wmi_pdev_tx_stats_params *src,
 8154			      struct ath12k_fw_stats_pdev *dst)
 8155{
 8156	dst->comp_queued = a_sle32_to_cpu(src->comp_queued);
 8157	dst->comp_delivered = a_sle32_to_cpu(src->comp_delivered);
 8158	dst->msdu_enqued = a_sle32_to_cpu(src->msdu_enqued);
 8159	dst->mpdu_enqued = a_sle32_to_cpu(src->mpdu_enqued);
 8160	dst->wmm_drop = a_sle32_to_cpu(src->wmm_drop);
 8161	dst->local_enqued = a_sle32_to_cpu(src->local_enqued);
 8162	dst->local_freed = a_sle32_to_cpu(src->local_freed);
 8163	dst->hw_queued = a_sle32_to_cpu(src->hw_queued);
 8164	dst->hw_reaped = a_sle32_to_cpu(src->hw_reaped);
 8165	dst->underrun = a_sle32_to_cpu(src->underrun);
 8166	dst->tx_abort = a_sle32_to_cpu(src->tx_abort);
 8167	dst->mpdus_requed = a_sle32_to_cpu(src->mpdus_requed);
 8168	dst->tx_ko = __le32_to_cpu(src->tx_ko);
 8169	dst->data_rc = __le32_to_cpu(src->data_rc);
 8170	dst->self_triggers = __le32_to_cpu(src->self_triggers);
 8171	dst->sw_retry_failure = __le32_to_cpu(src->sw_retry_failure);
 8172	dst->illgl_rate_phy_err = __le32_to_cpu(src->illgl_rate_phy_err);
 8173	dst->pdev_cont_xretry = __le32_to_cpu(src->pdev_cont_xretry);
 8174	dst->pdev_tx_timeout = __le32_to_cpu(src->pdev_tx_timeout);
 8175	dst->pdev_resets = __le32_to_cpu(src->pdev_resets);
 8176	dst->stateless_tid_alloc_failure =
 8177		__le32_to_cpu(src->stateless_tid_alloc_failure);
 8178	dst->phy_underrun = __le32_to_cpu(src->phy_underrun);
 8179	dst->txop_ovf = __le32_to_cpu(src->txop_ovf);
 8180}
 8181
 8182static void
 8183ath12k_wmi_pull_pdev_stats_rx(const struct ath12k_wmi_pdev_rx_stats_params *src,
 8184			      struct ath12k_fw_stats_pdev *dst)
 8185{
 8186	dst->mid_ppdu_route_change =
 8187		a_sle32_to_cpu(src->mid_ppdu_route_change);
 8188	dst->status_rcvd = a_sle32_to_cpu(src->status_rcvd);
 8189	dst->r0_frags = a_sle32_to_cpu(src->r0_frags);
 8190	dst->r1_frags = a_sle32_to_cpu(src->r1_frags);
 8191	dst->r2_frags = a_sle32_to_cpu(src->r2_frags);
 8192	dst->r3_frags = a_sle32_to_cpu(src->r3_frags);
 8193	dst->htt_msdus = a_sle32_to_cpu(src->htt_msdus);
 8194	dst->htt_mpdus = a_sle32_to_cpu(src->htt_mpdus);
 8195	dst->loc_msdus = a_sle32_to_cpu(src->loc_msdus);
 8196	dst->loc_mpdus = a_sle32_to_cpu(src->loc_mpdus);
 8197	dst->oversize_amsdu = a_sle32_to_cpu(src->oversize_amsdu);
 8198	dst->phy_errs = a_sle32_to_cpu(src->phy_errs);
 8199	dst->phy_err_drop = a_sle32_to_cpu(src->phy_err_drop);
 8200	dst->mpdu_errs = a_sle32_to_cpu(src->mpdu_errs);
 8201}
 8202
 8203static int ath12k_wmi_tlv_fw_stats_data_parse(struct ath12k_base *ab,
 8204					      struct wmi_tlv_fw_stats_parse *parse,
 8205					      const void *ptr,
 8206					      u16 len)
 8207{
 8208	const struct wmi_stats_event *ev = parse->ev;
 8209	struct ath12k_fw_stats *stats = parse->stats;
 8210	struct ath12k *ar;
 8211	struct ath12k_link_vif *arvif;
 8212	struct ieee80211_sta *sta;
 8213	struct ath12k_sta *ahsta;
 8214	struct ath12k_link_sta *arsta;
 8215	int i, ret = 0;
 8216	const void *data = ptr;
 8217
 8218	if (!ev) {
 8219		ath12k_warn(ab, "failed to fetch update stats ev");
 8220		return -EPROTO;
 8221	}
 8222
 8223	if (!stats)
 8224		return -EINVAL;
 8225
 8226	rcu_read_lock();
 8227
 8228	stats->pdev_id = le32_to_cpu(ev->pdev_id);
 8229	ar = ath12k_mac_get_ar_by_pdev_id(ab, stats->pdev_id);
 8230	if (!ar) {
 8231		ath12k_warn(ab, "invalid pdev id %d in update stats event\n",
 8232			    le32_to_cpu(ev->pdev_id));
 8233		ret = -EPROTO;
 8234		goto exit;
 8235	}
 8236
 8237	for (i = 0; i < le32_to_cpu(ev->num_vdev_stats); i++) {
 8238		const struct wmi_vdev_stats_params *src;
 8239		struct ath12k_fw_stats_vdev *dst;
 8240
 8241		src = data;
 8242		if (len < sizeof(*src)) {
 8243			ret = -EPROTO;
 8244			goto exit;
 8245		}
 8246
 8247		arvif = ath12k_mac_get_arvif(ar, le32_to_cpu(src->vdev_id));
 8248		if (arvif) {
 8249			sta = ieee80211_find_sta_by_ifaddr(ath12k_ar_to_hw(ar),
 8250							   arvif->bssid,
 8251							   NULL);
 8252			if (sta) {
 8253				ahsta = ath12k_sta_to_ahsta(sta);
 8254				arsta = &ahsta->deflink;
 8255				arsta->rssi_beacon = le32_to_cpu(src->beacon_snr);
 8256				ath12k_dbg(ab, ATH12K_DBG_WMI,
 8257					   "wmi stats vdev id %d snr %d\n",
 8258					   src->vdev_id, src->beacon_snr);
 8259			} else {
 8260				ath12k_dbg(ab, ATH12K_DBG_WMI,
 8261					   "not found station bssid %pM for vdev stat\n",
 8262					   arvif->bssid);
 8263			}
 8264		}
 8265
 8266		data += sizeof(*src);
 8267		len -= sizeof(*src);
 8268		dst = kzalloc(sizeof(*dst), GFP_ATOMIC);
 8269		if (!dst)
 8270			continue;
 8271		ath12k_wmi_pull_vdev_stats(src, dst);
 8272		stats->stats_id = WMI_REQUEST_VDEV_STAT;
 8273		list_add_tail(&dst->list, &stats->vdevs);
 8274	}
 8275	for (i = 0; i < le32_to_cpu(ev->num_bcn_stats); i++) {
 8276		const struct ath12k_wmi_bcn_stats_params *src;
 8277		struct ath12k_fw_stats_bcn *dst;
 8278
 8279		src = data;
 8280		if (len < sizeof(*src)) {
 8281			ret = -EPROTO;
 8282			goto exit;
 8283		}
 8284
 8285		data += sizeof(*src);
 8286		len -= sizeof(*src);
 8287		dst = kzalloc(sizeof(*dst), GFP_ATOMIC);
 8288		if (!dst)
 8289			continue;
 8290		ath12k_wmi_pull_bcn_stats(src, dst);
 8291		stats->stats_id = WMI_REQUEST_BCN_STAT;
 8292		list_add_tail(&dst->list, &stats->bcn);
 8293	}
 8294	for (i = 0; i < le32_to_cpu(ev->num_pdev_stats); i++) {
 8295		const struct ath12k_wmi_pdev_stats_params *src;
 8296		struct ath12k_fw_stats_pdev *dst;
 8297
 8298		src = data;
 8299		if (len < sizeof(*src)) {
 8300			ret = -EPROTO;
 8301			goto exit;
 8302		}
 8303
 8304		stats->stats_id = WMI_REQUEST_PDEV_STAT;
 8305
 8306		data += sizeof(*src);
 8307		len -= sizeof(*src);
 8308
 8309		dst = kzalloc(sizeof(*dst), GFP_ATOMIC);
 8310		if (!dst)
 8311			continue;
 8312
 8313		ath12k_wmi_pull_pdev_stats_base(&src->base, dst);
 8314		ath12k_wmi_pull_pdev_stats_tx(&src->tx, dst);
 8315		ath12k_wmi_pull_pdev_stats_rx(&src->rx, dst);
 8316		list_add_tail(&dst->list, &stats->pdevs);
 8317	}
 8318
 8319exit:
 8320	rcu_read_unlock();
 8321	return ret;
 8322}
 8323
 8324static int ath12k_wmi_tlv_rssi_chain_parse(struct ath12k_base *ab,
 8325					   u16 tag, u16 len,
 8326					   const void *ptr, void *data)
 8327{
 8328	const struct wmi_rssi_stat_params *stats_rssi = ptr;
 8329	struct wmi_tlv_fw_stats_parse *parse = data;
 8330	const struct wmi_stats_event *ev = parse->ev;
 8331	struct ath12k_fw_stats *stats = parse->stats;
 8332	struct ath12k_link_vif *arvif;
 8333	struct ath12k_link_sta *arsta;
 8334	struct ieee80211_sta *sta;
 8335	struct ath12k_sta *ahsta;
 8336	struct ath12k *ar;
 8337	int vdev_id;
 8338	int j;
 8339
 8340	if (!ev) {
 8341		ath12k_warn(ab, "failed to fetch update stats ev");
 8342		return -EPROTO;
 8343	}
 8344
 8345	if (tag != WMI_TAG_RSSI_STATS)
 8346		return -EPROTO;
 8347
 8348	if (!stats)
 8349		return -EINVAL;
 8350
 8351	stats->pdev_id = le32_to_cpu(ev->pdev_id);
 8352	vdev_id = le32_to_cpu(stats_rssi->vdev_id);
 8353	guard(rcu)();
 8354	ar = ath12k_mac_get_ar_by_pdev_id(ab, stats->pdev_id);
 8355	if (!ar) {
 8356		ath12k_warn(ab, "invalid pdev id %d in rssi chain parse\n",
 8357			    stats->pdev_id);
 8358		return -EPROTO;
 8359	}
 8360
 8361	arvif = ath12k_mac_get_arvif(ar, vdev_id);
 8362	if (!arvif) {
 8363		ath12k_warn(ab, "not found vif for vdev id %d\n", vdev_id);
 8364		return -EPROTO;
 8365	}
 8366
 8367	ath12k_dbg(ab, ATH12K_DBG_WMI,
 8368		   "stats bssid %pM vif %p\n",
 8369		   arvif->bssid, arvif->ahvif->vif);
 8370
 8371	sta = ieee80211_find_sta_by_ifaddr(ath12k_ar_to_hw(ar),
 8372					   arvif->bssid,
 8373					   NULL);
 8374	if (!sta) {
 8375		ath12k_dbg(ab, ATH12K_DBG_WMI,
 8376			   "not found station of bssid %pM for rssi chain\n",
 8377			   arvif->bssid);
 8378		return -EPROTO;
 8379	}
 8380
 8381	ahsta = ath12k_sta_to_ahsta(sta);
 8382	arsta = &ahsta->deflink;
 8383
 8384	BUILD_BUG_ON(ARRAY_SIZE(arsta->chain_signal) >
 8385		     ARRAY_SIZE(stats_rssi->rssi_avg_beacon));
 8386
 8387	for (j = 0; j < ARRAY_SIZE(arsta->chain_signal); j++)
 8388		arsta->chain_signal[j] = le32_to_cpu(stats_rssi->rssi_avg_beacon[j]);
 8389
 8390	stats->stats_id = WMI_REQUEST_RSSI_PER_CHAIN_STAT;
 8391
 8392	return 0;
 8393}
 8394
 8395static int ath12k_wmi_tlv_fw_stats_parse(struct ath12k_base *ab,
 8396					 u16 tag, u16 len,
 8397					 const void *ptr, void *data)
 8398{
 8399	struct wmi_tlv_fw_stats_parse *parse = data;
 8400	int ret = 0;
 8401
 8402	switch (tag) {
 8403	case WMI_TAG_STATS_EVENT:
 8404		parse->ev = ptr;
 8405		break;
 8406	case WMI_TAG_ARRAY_BYTE:
 8407		ret = ath12k_wmi_tlv_fw_stats_data_parse(ab, parse, ptr, len);
 8408		break;
 8409	case WMI_TAG_PER_CHAIN_RSSI_STATS:
 8410		parse->rssi = ptr;
 8411		if (le32_to_cpu(parse->ev->stats_id) & WMI_REQUEST_RSSI_PER_CHAIN_STAT)
 8412			parse->rssi_num = le32_to_cpu(parse->rssi->num_per_chain_rssi);
 8413		break;
 8414	case WMI_TAG_ARRAY_STRUCT:
 8415		if (parse->rssi_num && !parse->chain_rssi_done) {
 8416			ret = ath12k_wmi_tlv_iter(ab, ptr, len,
 8417						  ath12k_wmi_tlv_rssi_chain_parse,
 8418						  parse);
 8419			if (ret)
 8420				return ret;
 8421
 8422			parse->chain_rssi_done = true;
 8423		}
 8424		break;
 8425	default:
 8426		break;
 8427	}
 8428	return ret;
 8429}
 8430
 8431static int ath12k_wmi_pull_fw_stats(struct ath12k_base *ab, struct sk_buff *skb,
 8432				    struct ath12k_fw_stats *stats)
 8433{
 8434	struct wmi_tlv_fw_stats_parse parse = {};
 8435
 8436	stats->stats_id = 0;
 8437	parse.stats = stats;
 8438
 8439	return ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 8440				   ath12k_wmi_tlv_fw_stats_parse,
 8441				   &parse);
 8442}
 8443
 8444static void ath12k_wmi_fw_stats_process(struct ath12k *ar,
 8445					struct ath12k_fw_stats *stats)
 8446{
 8447	struct ath12k_base *ab = ar->ab;
 8448	struct ath12k_pdev *pdev;
 8449	bool is_end = true;
 8450	size_t total_vdevs_started = 0;
 8451	int i;
 8452
 8453	if (stats->stats_id == WMI_REQUEST_VDEV_STAT) {
 8454		if (list_empty(&stats->vdevs)) {
 8455			ath12k_warn(ab, "empty vdev stats");
 8456			return;
 8457		}
 8458		/* FW sends all the active VDEV stats irrespective of PDEV,
 8459		 * hence limit until the count of all VDEVs started
 8460		 */
 8461		rcu_read_lock();
 8462		for (i = 0; i < ab->num_radios; i++) {
 8463			pdev = rcu_dereference(ab->pdevs_active[i]);
 8464			if (pdev && pdev->ar)
 8465				total_vdevs_started += pdev->ar->num_started_vdevs;
 8466		}
 8467		rcu_read_unlock();
 8468
 8469		if (total_vdevs_started)
 8470			is_end = ((++ar->fw_stats.num_vdev_recvd) ==
 8471				  total_vdevs_started);
 8472
 8473		list_splice_tail_init(&stats->vdevs,
 8474				      &ar->fw_stats.vdevs);
 8475
 8476		if (is_end)
 8477			complete(&ar->fw_stats_done);
 8478
 8479		return;
 8480	}
 8481
 8482	if (stats->stats_id == WMI_REQUEST_BCN_STAT) {
 8483		if (list_empty(&stats->bcn)) {
 8484			ath12k_warn(ab, "empty beacon stats");
 8485			return;
 8486		}
 8487
 8488		list_splice_tail_init(&stats->bcn,
 8489				      &ar->fw_stats.bcn);
 8490		complete(&ar->fw_stats_done);
 8491	}
 8492}
 8493
 8494static void ath12k_update_stats_event(struct ath12k_base *ab, struct sk_buff *skb)
 8495{
 8496	struct ath12k_fw_stats stats = {};
 8497	struct ath12k *ar;
 8498	int ret;
 8499
 8500	INIT_LIST_HEAD(&stats.pdevs);
 8501	INIT_LIST_HEAD(&stats.vdevs);
 8502	INIT_LIST_HEAD(&stats.bcn);
 8503
 8504	ret = ath12k_wmi_pull_fw_stats(ab, skb, &stats);
 8505	if (ret) {
 8506		ath12k_warn(ab, "failed to pull fw stats: %d\n", ret);
 8507		goto free;
 8508	}
 8509
 8510	ath12k_dbg(ab, ATH12K_DBG_WMI, "event update stats");
 8511
 8512	rcu_read_lock();
 8513	ar = ath12k_mac_get_ar_by_pdev_id(ab, stats.pdev_id);
 8514	if (!ar) {
 8515		rcu_read_unlock();
 8516		ath12k_warn(ab, "failed to get ar for pdev_id %d: %d\n",
 8517			    stats.pdev_id, ret);
 8518		goto free;
 8519	}
 8520
 8521	spin_lock_bh(&ar->data_lock);
 8522
 8523	/* Handle WMI_REQUEST_PDEV_STAT status update */
 8524	if (stats.stats_id == WMI_REQUEST_PDEV_STAT) {
 8525		list_splice_tail_init(&stats.pdevs, &ar->fw_stats.pdevs);
 8526		complete(&ar->fw_stats_done);
 8527		goto complete;
 8528	}
 8529
 8530	/* Handle WMI_REQUEST_RSSI_PER_CHAIN_STAT status update */
 8531	if (stats.stats_id == WMI_REQUEST_RSSI_PER_CHAIN_STAT) {
 8532		complete(&ar->fw_stats_done);
 8533		goto complete;
 8534	}
 8535
 8536	/* Handle WMI_REQUEST_VDEV_STAT and WMI_REQUEST_BCN_STAT updates. */
 8537	ath12k_wmi_fw_stats_process(ar, &stats);
 8538
 8539complete:
 8540	complete(&ar->fw_stats_complete);
 8541	spin_unlock_bh(&ar->data_lock);
 8542	rcu_read_unlock();
 8543
 8544	/* Since the stats's pdev, vdev and beacon list are spliced and reinitialised
 8545	 * at this point, no need to free the individual list.
 8546	 */
 8547	return;
 8548
 8549free:
 8550	ath12k_fw_stats_free(&stats);
 8551}
 8552
 8553/* PDEV_CTL_FAILSAFE_CHECK_EVENT is received from FW when the frequency scanned
 8554 * is not part of BDF CTL(Conformance test limits) table entries.
 8555 */
 8556static void ath12k_pdev_ctl_failsafe_check_event(struct ath12k_base *ab,
 8557						 struct sk_buff *skb)
 8558{
 8559	const void **tb;
 8560	const struct wmi_pdev_ctl_failsafe_chk_event *ev;
 8561	int ret;
 8562
 8563	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8564	if (IS_ERR(tb)) {
 8565		ret = PTR_ERR(tb);
 8566		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 8567		return;
 8568	}
 8569
 8570	ev = tb[WMI_TAG_PDEV_CTL_FAILSAFE_CHECK_EVENT];
 8571	if (!ev) {
 8572		ath12k_warn(ab, "failed to fetch pdev ctl failsafe check ev");
 8573		kfree(tb);
 8574		return;
 8575	}
 8576
 8577	ath12k_dbg(ab, ATH12K_DBG_WMI,
 8578		   "pdev ctl failsafe check ev status %d\n",
 8579		   ev->ctl_failsafe_status);
 8580
 8581	/* If ctl_failsafe_status is set to 1 FW will max out the Transmit power
 8582	 * to 10 dBm else the CTL power entry in the BDF would be picked up.
 8583	 */
 8584	if (ev->ctl_failsafe_status != 0)
 8585		ath12k_warn(ab, "pdev ctl failsafe failure status %d",
 8586			    ev->ctl_failsafe_status);
 8587
 8588	kfree(tb);
 8589}
 8590
 8591static void
 8592ath12k_wmi_process_csa_switch_count_event(struct ath12k_base *ab,
 8593					  const struct ath12k_wmi_pdev_csa_event *ev,
 8594					  const u32 *vdev_ids)
 8595{
 8596	u32 current_switch_count = le32_to_cpu(ev->current_switch_count);
 8597	u32 num_vdevs = le32_to_cpu(ev->num_vdevs);
 8598	struct ieee80211_bss_conf *conf;
 8599	struct ath12k_link_vif *arvif;
 8600	struct ath12k_vif *ahvif;
 8601	int i;
 8602
 8603	rcu_read_lock();
 8604	for (i = 0; i < num_vdevs; i++) {
 8605		arvif = ath12k_mac_get_arvif_by_vdev_id(ab, vdev_ids[i]);
 8606
 8607		if (!arvif) {
 8608			ath12k_warn(ab, "Recvd csa status for unknown vdev %d",
 8609				    vdev_ids[i]);
 8610			continue;
 8611		}
 8612		ahvif = arvif->ahvif;
 8613
 8614		if (arvif->link_id >= IEEE80211_MLD_MAX_NUM_LINKS) {
 8615			ath12k_warn(ab, "Invalid CSA switch count even link id: %d\n",
 8616				    arvif->link_id);
 8617			continue;
 8618		}
 8619
 8620		conf = rcu_dereference(ahvif->vif->link_conf[arvif->link_id]);
 8621		if (!conf) {
 8622			ath12k_warn(ab, "unable to access bss link conf in process csa for vif %pM link %u\n",
 8623				    ahvif->vif->addr, arvif->link_id);
 8624			continue;
 8625		}
 8626
 8627		if (!arvif->is_up || !conf->csa_active)
 8628			continue;
 8629
 8630		/* Finish CSA when counter reaches zero */
 8631		if (!current_switch_count) {
 8632			ieee80211_csa_finish(ahvif->vif, arvif->link_id);
 8633			arvif->current_cntdown_counter = 0;
 8634		} else if (current_switch_count > 1) {
 8635			/* If the count in event is not what we expect, don't update the
 8636			 * mac80211 count. Since during beacon Tx failure, count in the
 8637			 * firmware will not decrement and this event will come with the
 8638			 * previous count value again
 8639			 */
 8640			if (current_switch_count != arvif->current_cntdown_counter)
 8641				continue;
 8642
 8643			arvif->current_cntdown_counter =
 8644				ieee80211_beacon_update_cntdwn(ahvif->vif,
 8645							       arvif->link_id);
 8646		}
 8647	}
 8648	rcu_read_unlock();
 8649}
 8650
 8651static void
 8652ath12k_wmi_pdev_csa_switch_count_status_event(struct ath12k_base *ab,
 8653					      struct sk_buff *skb)
 8654{
 8655	const void **tb;
 8656	const struct ath12k_wmi_pdev_csa_event *ev;
 8657	const u32 *vdev_ids;
 8658	int ret;
 8659
 8660	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8661	if (IS_ERR(tb)) {
 8662		ret = PTR_ERR(tb);
 8663		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 8664		return;
 8665	}
 8666
 8667	ev = tb[WMI_TAG_PDEV_CSA_SWITCH_COUNT_STATUS_EVENT];
 8668	vdev_ids = tb[WMI_TAG_ARRAY_UINT32];
 8669
 8670	if (!ev || !vdev_ids) {
 8671		ath12k_warn(ab, "failed to fetch pdev csa switch count ev");
 8672		kfree(tb);
 8673		return;
 8674	}
 8675
 8676	ath12k_dbg(ab, ATH12K_DBG_WMI,
 8677		   "pdev csa switch count %d for pdev %d, num_vdevs %d",
 8678		   ev->current_switch_count, ev->pdev_id,
 8679		   ev->num_vdevs);
 8680
 8681	ath12k_wmi_process_csa_switch_count_event(ab, ev, vdev_ids);
 8682
 8683	kfree(tb);
 8684}
 8685
 8686static void
 8687ath12k_wmi_pdev_dfs_radar_detected_event(struct ath12k_base *ab, struct sk_buff *skb)
 8688{
 8689	const void **tb;
 8690	struct ath12k_mac_get_any_chanctx_conf_arg arg;
 8691	const struct ath12k_wmi_pdev_radar_event *ev;
 8692	struct ath12k *ar;
 8693	int ret;
 8694
 8695	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8696	if (IS_ERR(tb)) {
 8697		ret = PTR_ERR(tb);
 8698		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 8699		return;
 8700	}
 8701
 8702	ev = tb[WMI_TAG_PDEV_DFS_RADAR_DETECTION_EVENT];
 8703
 8704	if (!ev) {
 8705		ath12k_warn(ab, "failed to fetch pdev dfs radar detected ev");
 8706		kfree(tb);
 8707		return;
 8708	}
 8709
 8710	ath12k_dbg(ab, ATH12K_DBG_WMI,
 8711		   "pdev dfs radar detected on pdev %d, detection mode %d, chan freq %d, chan_width %d, detector id %d, seg id %d, timestamp %d, chirp %d, freq offset %d, sidx %d",
 8712		   ev->pdev_id, ev->detection_mode, ev->chan_freq, ev->chan_width,
 8713		   ev->detector_id, ev->segment_id, ev->timestamp, ev->is_chirp,
 8714		   ev->freq_offset, ev->sidx);
 8715
 8716	rcu_read_lock();
 8717
 8718	ar = ath12k_mac_get_ar_by_pdev_id(ab, le32_to_cpu(ev->pdev_id));
 8719
 8720	if (!ar) {
 8721		ath12k_warn(ab, "radar detected in invalid pdev %d\n",
 8722			    ev->pdev_id);
 8723		goto exit;
 8724	}
 8725
 8726	arg.ar = ar;
 8727	arg.chanctx_conf = NULL;
 8728	ieee80211_iter_chan_contexts_atomic(ath12k_ar_to_hw(ar),
 8729					    ath12k_mac_get_any_chanctx_conf_iter, &arg);
 8730	if (!arg.chanctx_conf) {
 8731		ath12k_warn(ab, "failed to find valid chanctx_conf in radar detected event\n");
 8732		goto exit;
 8733	}
 8734
 8735	ath12k_dbg(ar->ab, ATH12K_DBG_REG, "DFS Radar Detected in pdev %d\n",
 8736		   ev->pdev_id);
 8737
 8738	if (ar->dfs_block_radar_events)
 8739		ath12k_info(ab, "DFS Radar detected, but ignored as requested\n");
 8740	else
 8741		ieee80211_radar_detected(ath12k_ar_to_hw(ar), arg.chanctx_conf);
 8742
 8743exit:
 8744	rcu_read_unlock();
 8745
 8746	kfree(tb);
 8747}
 8748
 8749static void ath12k_tm_wmi_event_segmented(struct ath12k_base *ab, u32 cmd_id,
 8750					  struct sk_buff *skb)
 8751{
 8752	const struct ath12k_wmi_ftm_event *ev;
 8753	const void **tb;
 8754	int ret;
 8755	u16 length;
 8756
 8757	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8758
 8759	if (IS_ERR(tb)) {
 8760		ret = PTR_ERR(tb);
 8761		ath12k_warn(ab, "failed to parse ftm event tlv: %d\n", ret);
 8762		return;
 8763	}
 8764
 8765	ev = tb[WMI_TAG_ARRAY_BYTE];
 8766	if (!ev) {
 8767		ath12k_warn(ab, "failed to fetch ftm msg\n");
 8768		kfree(tb);
 8769		return;
 8770	}
 8771
 8772	length = skb->len - TLV_HDR_SIZE;
 8773	ath12k_tm_process_event(ab, cmd_id, ev, length);
 8774	kfree(tb);
 8775	tb = NULL;
 8776}
 8777
 8778static void
 8779ath12k_wmi_pdev_temperature_event(struct ath12k_base *ab,
 8780				  struct sk_buff *skb)
 8781{
 8782	struct ath12k *ar;
 8783	struct wmi_pdev_temperature_event ev = {};
 8784
 8785	if (ath12k_pull_pdev_temp_ev(ab, skb, &ev) != 0) {
 8786		ath12k_warn(ab, "failed to extract pdev temperature event");
 8787		return;
 8788	}
 8789
 8790	ath12k_dbg(ab, ATH12K_DBG_WMI,
 8791		   "pdev temperature ev temp %d pdev_id %d\n", ev.temp, ev.pdev_id);
 8792
 8793	rcu_read_lock();
 8794
 8795	ar = ath12k_mac_get_ar_by_pdev_id(ab, le32_to_cpu(ev.pdev_id));
 8796	if (!ar) {
 8797		ath12k_warn(ab, "invalid pdev id in pdev temperature ev %d", ev.pdev_id);
 8798		goto exit;
 8799	}
 8800
 8801exit:
 8802	rcu_read_unlock();
 8803}
 8804
 8805static void ath12k_fils_discovery_event(struct ath12k_base *ab,
 8806					struct sk_buff *skb)
 8807{
 8808	const void **tb;
 8809	const struct wmi_fils_discovery_event *ev;
 8810	int ret;
 8811
 8812	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8813	if (IS_ERR(tb)) {
 8814		ret = PTR_ERR(tb);
 8815		ath12k_warn(ab,
 8816			    "failed to parse FILS discovery event tlv %d\n",
 8817			    ret);
 8818		return;
 8819	}
 8820
 8821	ev = tb[WMI_TAG_HOST_SWFDA_EVENT];
 8822	if (!ev) {
 8823		ath12k_warn(ab, "failed to fetch FILS discovery event\n");
 8824		kfree(tb);
 8825		return;
 8826	}
 8827
 8828	ath12k_warn(ab,
 8829		    "FILS discovery frame expected from host for vdev_id: %u, transmission scheduled at %u, next TBTT: %u\n",
 8830		    ev->vdev_id, ev->fils_tt, ev->tbtt);
 8831
 8832	kfree(tb);
 8833}
 8834
 8835static void ath12k_probe_resp_tx_status_event(struct ath12k_base *ab,
 8836					      struct sk_buff *skb)
 8837{
 8838	const void **tb;
 8839	const struct wmi_probe_resp_tx_status_event *ev;
 8840	int ret;
 8841
 8842	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8843	if (IS_ERR(tb)) {
 8844		ret = PTR_ERR(tb);
 8845		ath12k_warn(ab,
 8846			    "failed to parse probe response transmission status event tlv: %d\n",
 8847			    ret);
 8848		return;
 8849	}
 8850
 8851	ev = tb[WMI_TAG_OFFLOAD_PRB_RSP_TX_STATUS_EVENT];
 8852	if (!ev) {
 8853		ath12k_warn(ab,
 8854			    "failed to fetch probe response transmission status event");
 8855		kfree(tb);
 8856		return;
 8857	}
 8858
 8859	if (ev->tx_status)
 8860		ath12k_warn(ab,
 8861			    "Probe response transmission failed for vdev_id %u, status %u\n",
 8862			    ev->vdev_id, ev->tx_status);
 8863
 8864	kfree(tb);
 8865}
 8866
 8867static int ath12k_wmi_p2p_noa_event(struct ath12k_base *ab,
 8868				    struct sk_buff *skb)
 8869{
 8870	const void **tb;
 8871	const struct wmi_p2p_noa_event *ev;
 8872	const struct ath12k_wmi_p2p_noa_info *noa;
 8873	struct ath12k *ar;
 8874	int ret, vdev_id;
 8875
 8876	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8877	if (IS_ERR(tb)) {
 8878		ret = PTR_ERR(tb);
 8879		ath12k_warn(ab, "failed to parse P2P NoA TLV: %d\n", ret);
 8880		return ret;
 8881	}
 8882
 8883	ev = tb[WMI_TAG_P2P_NOA_EVENT];
 8884	noa = tb[WMI_TAG_P2P_NOA_INFO];
 8885
 8886	if (!ev || !noa) {
 8887		ret = -EPROTO;
 8888		goto out;
 8889	}
 8890
 8891	vdev_id = __le32_to_cpu(ev->vdev_id);
 8892
 8893	ath12k_dbg(ab, ATH12K_DBG_WMI,
 8894		   "wmi tlv p2p noa vdev_id %i descriptors %u\n",
 8895		   vdev_id, le32_get_bits(noa->noa_attr, WMI_P2P_NOA_INFO_DESC_NUM));
 8896
 8897	rcu_read_lock();
 8898	ar = ath12k_mac_get_ar_by_vdev_id(ab, vdev_id);
 8899	if (!ar) {
 8900		ath12k_warn(ab, "invalid vdev id %d in P2P NoA event\n",
 8901			    vdev_id);
 8902		ret = -EINVAL;
 8903		goto unlock;
 8904	}
 8905
 8906	ath12k_p2p_noa_update_by_vdev_id(ar, vdev_id, noa);
 8907
 8908	ret = 0;
 8909
 8910unlock:
 8911	rcu_read_unlock();
 8912out:
 8913	kfree(tb);
 8914	return ret;
 8915}
 8916
 8917static void ath12k_rfkill_state_change_event(struct ath12k_base *ab,
 8918					     struct sk_buff *skb)
 8919{
 8920	const struct wmi_rfkill_state_change_event *ev;
 8921	const void **tb;
 8922	int ret;
 8923
 8924	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8925	if (IS_ERR(tb)) {
 8926		ret = PTR_ERR(tb);
 8927		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 8928		return;
 8929	}
 8930
 8931	ev = tb[WMI_TAG_RFKILL_EVENT];
 8932	if (!ev) {
 8933		kfree(tb);
 8934		return;
 8935	}
 8936
 8937	ath12k_dbg(ab, ATH12K_DBG_MAC,
 8938		   "wmi tlv rfkill state change gpio %d type %d radio_state %d\n",
 8939		   le32_to_cpu(ev->gpio_pin_num),
 8940		   le32_to_cpu(ev->int_type),
 8941		   le32_to_cpu(ev->radio_state));
 8942
 8943	spin_lock_bh(&ab->base_lock);
 8944	ab->rfkill_radio_on = (ev->radio_state == cpu_to_le32(WMI_RFKILL_RADIO_STATE_ON));
 8945	spin_unlock_bh(&ab->base_lock);
 8946
 8947	queue_work(ab->workqueue, &ab->rfkill_work);
 8948	kfree(tb);
 8949}
 8950
 8951static void
 8952ath12k_wmi_diag_event(struct ath12k_base *ab, struct sk_buff *skb)
 8953{
 8954	trace_ath12k_wmi_diag(ab, skb->data, skb->len);
 8955}
 8956
 8957static void ath12k_wmi_twt_enable_event(struct ath12k_base *ab,
 8958					struct sk_buff *skb)
 8959{
 8960	const void **tb;
 8961	const struct wmi_twt_enable_event *ev;
 8962	int ret;
 8963
 8964	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8965	if (IS_ERR(tb)) {
 8966		ret = PTR_ERR(tb);
 8967		ath12k_warn(ab, "failed to parse wmi twt enable status event tlv: %d\n",
 8968			    ret);
 8969		return;
 8970	}
 8971
 8972	ev = tb[WMI_TAG_TWT_ENABLE_COMPLETE_EVENT];
 8973	if (!ev) {
 8974		ath12k_warn(ab, "failed to fetch twt enable wmi event\n");
 8975		goto exit;
 8976	}
 8977
 8978	ath12k_dbg(ab, ATH12K_DBG_MAC, "wmi twt enable event pdev id %u status %u\n",
 8979		   le32_to_cpu(ev->pdev_id),
 8980		   le32_to_cpu(ev->status));
 8981
 8982exit:
 8983	kfree(tb);
 8984}
 8985
 8986static void ath12k_wmi_twt_disable_event(struct ath12k_base *ab,
 8987					 struct sk_buff *skb)
 8988{
 8989	const void **tb;
 8990	const struct wmi_twt_disable_event *ev;
 8991	int ret;
 8992
 8993	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 8994	if (IS_ERR(tb)) {
 8995		ret = PTR_ERR(tb);
 8996		ath12k_warn(ab, "failed to parse wmi twt disable status event tlv: %d\n",
 8997			    ret);
 8998		return;
 8999	}
 9000
 9001	ev = tb[WMI_TAG_TWT_DISABLE_COMPLETE_EVENT];
 9002	if (!ev) {
 9003		ath12k_warn(ab, "failed to fetch twt disable wmi event\n");
 9004		goto exit;
 9005	}
 9006
 9007	ath12k_dbg(ab, ATH12K_DBG_MAC, "wmi twt disable event pdev id %d status %u\n",
 9008		   le32_to_cpu(ev->pdev_id),
 9009		   le32_to_cpu(ev->status));
 9010
 9011exit:
 9012	kfree(tb);
 9013}
 9014
 9015static int ath12k_wmi_wow_wakeup_host_parse(struct ath12k_base *ab,
 9016					    u16 tag, u16 len,
 9017					    const void *ptr, void *data)
 9018{
 9019	const struct wmi_wow_ev_pg_fault_param *pf_param;
 9020	const struct wmi_wow_ev_param *param;
 9021	struct wmi_wow_ev_arg *arg = data;
 9022	int pf_len;
 9023
 9024	switch (tag) {
 9025	case WMI_TAG_WOW_EVENT_INFO:
 9026		param = ptr;
 9027		arg->wake_reason = le32_to_cpu(param->wake_reason);
 9028		ath12k_dbg(ab, ATH12K_DBG_WMI, "wow wakeup host reason %d %s\n",
 9029			   arg->wake_reason, wow_reason(arg->wake_reason));
 9030		break;
 9031
 9032	case WMI_TAG_ARRAY_BYTE:
 9033		if (arg && arg->wake_reason == WOW_REASON_PAGE_FAULT) {
 9034			pf_param = ptr;
 9035			pf_len = le32_to_cpu(pf_param->len);
 9036			if (pf_len > len - sizeof(pf_len) ||
 9037			    pf_len < 0) {
 9038				ath12k_warn(ab, "invalid wo reason page fault buffer len %d\n",
 9039					    pf_len);
 9040				return -EINVAL;
 9041			}
 9042			ath12k_dbg(ab, ATH12K_DBG_WMI, "wow_reason_page_fault len %d\n",
 9043				   pf_len);
 9044			ath12k_dbg_dump(ab, ATH12K_DBG_WMI,
 9045					"wow_reason_page_fault packet present",
 9046					"wow_pg_fault ",
 9047					pf_param->data,
 9048					pf_len);
 9049		}
 9050		break;
 9051	default:
 9052		break;
 9053	}
 9054
 9055	return 0;
 9056}
 9057
 9058static void ath12k_wmi_event_wow_wakeup_host(struct ath12k_base *ab, struct sk_buff *skb)
 9059{
 9060	struct wmi_wow_ev_arg arg = { };
 9061	int ret;
 9062
 9063	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 9064				  ath12k_wmi_wow_wakeup_host_parse,
 9065				  &arg);
 9066	if (ret) {
 9067		ath12k_warn(ab, "failed to parse wmi wow wakeup host event tlv: %d\n",
 9068			    ret);
 9069		return;
 9070	}
 9071
 9072	complete(&ab->wow.wakeup_completed);
 9073}
 9074
 9075static void ath12k_wmi_gtk_offload_status_event(struct ath12k_base *ab,
 9076						struct sk_buff *skb)
 9077{
 9078	const struct wmi_gtk_offload_status_event *ev;
 9079	struct ath12k_link_vif *arvif;
 9080	__be64 replay_ctr_be;
 9081	u64 replay_ctr;
 9082	const void **tb;
 9083	int ret;
 9084
 9085	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 9086	if (IS_ERR(tb)) {
 9087		ret = PTR_ERR(tb);
 9088		ath12k_warn(ab, "failed to parse tlv: %d\n", ret);
 9089		return;
 9090	}
 9091
 9092	ev = tb[WMI_TAG_GTK_OFFLOAD_STATUS_EVENT];
 9093	if (!ev) {
 9094		ath12k_warn(ab, "failed to fetch gtk offload status ev");
 9095		kfree(tb);
 9096		return;
 9097	}
 9098
 9099	rcu_read_lock();
 9100	arvif = ath12k_mac_get_arvif_by_vdev_id(ab, le32_to_cpu(ev->vdev_id));
 9101	if (!arvif) {
 9102		rcu_read_unlock();
 9103		ath12k_warn(ab, "failed to get arvif for vdev_id:%d\n",
 9104			    le32_to_cpu(ev->vdev_id));
 9105		kfree(tb);
 9106		return;
 9107	}
 9108
 9109	replay_ctr = le64_to_cpu(ev->replay_ctr);
 9110	arvif->rekey_data.replay_ctr = replay_ctr;
 9111	ath12k_dbg(ab, ATH12K_DBG_WMI, "wmi gtk offload event refresh_cnt %d replay_ctr %llu\n",
 9112		   le32_to_cpu(ev->refresh_cnt), replay_ctr);
 9113
 9114	/* supplicant expects big-endian replay counter */
 9115	replay_ctr_be = cpu_to_be64(replay_ctr);
 9116
 9117	ieee80211_gtk_rekey_notify(arvif->ahvif->vif, arvif->bssid,
 9118				   (void *)&replay_ctr_be, GFP_ATOMIC);
 9119
 9120	rcu_read_unlock();
 9121
 9122	kfree(tb);
 9123}
 9124
 9125static void ath12k_wmi_event_mlo_setup_complete(struct ath12k_base *ab,
 9126						struct sk_buff *skb)
 9127{
 9128	const struct wmi_mlo_setup_complete_event *ev;
 9129	struct ath12k *ar = NULL;
 9130	struct ath12k_pdev *pdev;
 9131	const void **tb;
 9132	int ret, i;
 9133
 9134	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 9135	if (IS_ERR(tb)) {
 9136		ret = PTR_ERR(tb);
 9137		ath12k_warn(ab, "failed to parse mlo setup complete event tlv: %d\n",
 9138			    ret);
 9139		return;
 9140	}
 9141
 9142	ev = tb[WMI_TAG_MLO_SETUP_COMPLETE_EVENT];
 9143	if (!ev) {
 9144		ath12k_warn(ab, "failed to fetch mlo setup complete event\n");
 9145		kfree(tb);
 9146		return;
 9147	}
 9148
 9149	if (le32_to_cpu(ev->pdev_id) > ab->num_radios)
 9150		goto skip_lookup;
 9151
 9152	for (i = 0; i < ab->num_radios; i++) {
 9153		pdev = &ab->pdevs[i];
 9154		if (pdev && pdev->pdev_id == le32_to_cpu(ev->pdev_id)) {
 9155			ar = pdev->ar;
 9156			break;
 9157		}
 9158	}
 9159
 9160skip_lookup:
 9161	if (!ar) {
 9162		ath12k_warn(ab, "invalid pdev_id %d status %u in setup complete event\n",
 9163			    ev->pdev_id, ev->status);
 9164		goto out;
 9165	}
 9166
 9167	ar->mlo_setup_status = le32_to_cpu(ev->status);
 9168	complete(&ar->mlo_setup_done);
 9169
 9170out:
 9171	kfree(tb);
 9172}
 9173
 9174static void ath12k_wmi_event_teardown_complete(struct ath12k_base *ab,
 9175					       struct sk_buff *skb)
 9176{
 9177	const struct wmi_mlo_teardown_complete_event *ev;
 9178	const void **tb;
 9179	int ret;
 9180
 9181	tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC);
 9182	if (IS_ERR(tb)) {
 9183		ret = PTR_ERR(tb);
 9184		ath12k_warn(ab, "failed to parse teardown complete event tlv: %d\n", ret);
 9185		return;
 9186	}
 9187
 9188	ev = tb[WMI_TAG_MLO_TEARDOWN_COMPLETE];
 9189	if (!ev) {
 9190		ath12k_warn(ab, "failed to fetch teardown complete event\n");
 9191		kfree(tb);
 9192		return;
 9193	}
 9194
 9195	kfree(tb);
 9196}
 9197
 9198#ifdef CONFIG_ATH12K_DEBUGFS
 9199static int ath12k_wmi_tpc_stats_copy_buffer(struct ath12k_base *ab,
 9200					    const void *ptr, u16 tag, u16 len,
 9201					    struct wmi_tpc_stats_arg *tpc_stats)
 9202{
 9203	u32 len1, len2, len3, len4;
 9204	s16 *dst_ptr;
 9205	s8 *dst_ptr_ctl;
 9206
 9207	len1 = le32_to_cpu(tpc_stats->max_reg_allowed_power.tpc_reg_pwr.reg_array_len);
 9208	len2 = le32_to_cpu(tpc_stats->rates_array1.tpc_rates_array.rate_array_len);
 9209	len3 = le32_to_cpu(tpc_stats->rates_array2.tpc_rates_array.rate_array_len);
 9210	len4 = le32_to_cpu(tpc_stats->ctl_array.tpc_ctl_pwr.ctl_array_len);
 9211
 9212	switch (tpc_stats->event_count) {
 9213	case ATH12K_TPC_STATS_CONFIG_REG_PWR_EVENT:
 9214		if (len1 > len)
 9215			return -ENOBUFS;
 9216
 9217		if (tpc_stats->tlvs_rcvd & WMI_TPC_REG_PWR_ALLOWED) {
 9218			dst_ptr = tpc_stats->max_reg_allowed_power.reg_pwr_array;
 9219			memcpy(dst_ptr, ptr, len1);
 9220		}
 9221		break;
 9222	case ATH12K_TPC_STATS_RATES_EVENT1:
 9223		if (len2 > len)
 9224			return -ENOBUFS;
 9225
 9226		if (tpc_stats->tlvs_rcvd & WMI_TPC_RATES_ARRAY1) {
 9227			dst_ptr = tpc_stats->rates_array1.rate_array;
 9228			memcpy(dst_ptr, ptr, len2);
 9229		}
 9230		break;
 9231	case ATH12K_TPC_STATS_RATES_EVENT2:
 9232		if (len3 > len)
 9233			return -ENOBUFS;
 9234
 9235		if (tpc_stats->tlvs_rcvd & WMI_TPC_RATES_ARRAY2) {
 9236			dst_ptr = tpc_stats->rates_array2.rate_array;
 9237			memcpy(dst_ptr, ptr, len3);
 9238		}
 9239		break;
 9240	case ATH12K_TPC_STATS_CTL_TABLE_EVENT:
 9241		if (len4 > len)
 9242			return -ENOBUFS;
 9243
 9244		if (tpc_stats->tlvs_rcvd & WMI_TPC_CTL_PWR_ARRAY) {
 9245			dst_ptr_ctl = tpc_stats->ctl_array.ctl_pwr_table;
 9246			memcpy(dst_ptr_ctl, ptr, len4);
 9247		}
 9248		break;
 9249	}
 9250	return 0;
 9251}
 9252
 9253static int ath12k_tpc_get_reg_pwr(struct ath12k_base *ab,
 9254				  struct wmi_tpc_stats_arg *tpc_stats,
 9255				  struct wmi_max_reg_power_fixed_params *ev)
 9256{
 9257	struct wmi_max_reg_power_allowed_arg *reg_pwr;
 9258	u32 total_size;
 9259
 9260	ath12k_dbg(ab, ATH12K_DBG_WMI,
 9261		   "Received reg power array type %d length %d for tpc stats\n",
 9262		   ev->reg_power_type, ev->reg_array_len);
 9263
 9264	switch (le32_to_cpu(ev->reg_power_type)) {
 9265	case TPC_STATS_REG_PWR_ALLOWED_TYPE:
 9266		reg_pwr = &tpc_stats->max_reg_allowed_power;
 9267		break;
 9268	default:
 9269		return -EINVAL;
 9270	}
 9271
 9272	/* Each entry is 2 byte hence multiplying the indices with 2 */
 9273	total_size = le32_to_cpu(ev->d1) * le32_to_cpu(ev->d2) *
 9274		     le32_to_cpu(ev->d3) * le32_to_cpu(ev->d4) * 2;
 9275	if (le32_to_cpu(ev->reg_array_len) != total_size) {
 9276		ath12k_warn(ab,
 9277			    "Total size and reg_array_len doesn't match for tpc stats\n");
 9278		return -EINVAL;
 9279	}
 9280
 9281	memcpy(&reg_pwr->tpc_reg_pwr, ev, sizeof(struct wmi_max_reg_power_fixed_params));
 9282
 9283	reg_pwr->reg_pwr_array = kzalloc(le32_to_cpu(reg_pwr->tpc_reg_pwr.reg_array_len),
 9284					 GFP_ATOMIC);
 9285	if (!reg_pwr->reg_pwr_array)
 9286		return -ENOMEM;
 9287
 9288	tpc_stats->tlvs_rcvd |= WMI_TPC_REG_PWR_ALLOWED;
 9289
 9290	return 0;
 9291}
 9292
 9293static int ath12k_tpc_get_rate_array(struct ath12k_base *ab,
 9294				     struct wmi_tpc_stats_arg *tpc_stats,
 9295				     struct wmi_tpc_rates_array_fixed_params *ev)
 9296{
 9297	struct wmi_tpc_rates_array_arg *rates_array;
 9298	u32 flag = 0, rate_array_len;
 9299
 9300	ath12k_dbg(ab, ATH12K_DBG_WMI,
 9301		   "Received rates array type %d length %d for tpc stats\n",
 9302		   ev->rate_array_type, ev->rate_array_len);
 9303
 9304	switch (le32_to_cpu(ev->rate_array_type)) {
 9305	case ATH12K_TPC_STATS_RATES_ARRAY1:
 9306		rates_array = &tpc_stats->rates_array1;
 9307		flag = WMI_TPC_RATES_ARRAY1;
 9308		break;
 9309	case ATH12K_TPC_STATS_RATES_ARRAY2:
 9310		rates_array = &tpc_stats->rates_array2;
 9311		flag = WMI_TPC_RATES_ARRAY2;
 9312		break;
 9313	default:
 9314		ath12k_warn(ab,
 9315			    "Received invalid type of rates array for tpc stats\n");
 9316		return -EINVAL;
 9317	}
 9318	memcpy(&rates_array->tpc_rates_array, ev,
 9319	       sizeof(struct wmi_tpc_rates_array_fixed_params));
 9320	rate_array_len = le32_to_cpu(rates_array->tpc_rates_array.rate_array_len);
 9321	rates_array->rate_array = kzalloc(rate_array_len, GFP_ATOMIC);
 9322	if (!rates_array->rate_array)
 9323		return -ENOMEM;
 9324
 9325	tpc_stats->tlvs_rcvd |= flag;
 9326	return 0;
 9327}
 9328
 9329static int ath12k_tpc_get_ctl_pwr_tbl(struct ath12k_base *ab,
 9330				      struct wmi_tpc_stats_arg *tpc_stats,
 9331				      struct wmi_tpc_ctl_pwr_fixed_params *ev)
 9332{
 9333	struct wmi_tpc_ctl_pwr_table_arg *ctl_array;
 9334	u32 total_size, ctl_array_len, flag = 0;
 9335
 9336	ath12k_dbg(ab, ATH12K_DBG_WMI,
 9337		   "Received ctl array type %d length %d for tpc stats\n",
 9338		   ev->ctl_array_type, ev->ctl_array_len);
 9339
 9340	switch (le32_to_cpu(ev->ctl_array_type)) {
 9341	case ATH12K_TPC_STATS_CTL_ARRAY:
 9342		ctl_array = &tpc_stats->ctl_array;
 9343		flag = WMI_TPC_CTL_PWR_ARRAY;
 9344		break;
 9345	default:
 9346		ath12k_warn(ab,
 9347			    "Received invalid type of ctl pwr table for tpc stats\n");
 9348		return -EINVAL;
 9349	}
 9350
 9351	total_size = le32_to_cpu(ev->d1) * le32_to_cpu(ev->d2) *
 9352		     le32_to_cpu(ev->d3) * le32_to_cpu(ev->d4);
 9353	if (le32_to_cpu(ev->ctl_array_len) != total_size) {
 9354		ath12k_warn(ab,
 9355			    "Total size and ctl_array_len doesn't match for tpc stats\n");
 9356		return -EINVAL;
 9357	}
 9358
 9359	memcpy(&ctl_array->tpc_ctl_pwr, ev, sizeof(struct wmi_tpc_ctl_pwr_fixed_params));
 9360	ctl_array_len = le32_to_cpu(ctl_array->tpc_ctl_pwr.ctl_array_len);
 9361	ctl_array->ctl_pwr_table = kzalloc(ctl_array_len, GFP_ATOMIC);
 9362	if (!ctl_array->ctl_pwr_table)
 9363		return -ENOMEM;
 9364
 9365	tpc_stats->tlvs_rcvd |= flag;
 9366	return 0;
 9367}
 9368
 9369static int ath12k_wmi_tpc_stats_subtlv_parser(struct ath12k_base *ab,
 9370					      u16 tag, u16 len,
 9371					      const void *ptr, void *data)
 9372{
 9373	struct wmi_tpc_rates_array_fixed_params *tpc_rates_array;
 9374	struct wmi_max_reg_power_fixed_params *tpc_reg_pwr;
 9375	struct wmi_tpc_ctl_pwr_fixed_params *tpc_ctl_pwr;
 9376	struct wmi_tpc_stats_arg *tpc_stats = data;
 9377	struct wmi_tpc_config_params *tpc_config;
 9378	int ret = 0;
 9379
 9380	if (!tpc_stats) {
 9381		ath12k_warn(ab, "tpc stats memory unavailable\n");
 9382		return -EINVAL;
 9383	}
 9384
 9385	switch (tag) {
 9386	case WMI_TAG_TPC_STATS_CONFIG_EVENT:
 9387		tpc_config = (struct wmi_tpc_config_params *)ptr;
 9388		memcpy(&tpc_stats->tpc_config, tpc_config,
 9389		       sizeof(struct wmi_tpc_config_params));
 9390		break;
 9391	case WMI_TAG_TPC_STATS_REG_PWR_ALLOWED:
 9392		tpc_reg_pwr = (struct wmi_max_reg_power_fixed_params *)ptr;
 9393		ret = ath12k_tpc_get_reg_pwr(ab, tpc_stats, tpc_reg_pwr);
 9394		break;
 9395	case WMI_TAG_TPC_STATS_RATES_ARRAY:
 9396		tpc_rates_array = (struct wmi_tpc_rates_array_fixed_params *)ptr;
 9397		ret = ath12k_tpc_get_rate_array(ab, tpc_stats, tpc_rates_array);
 9398		break;
 9399	case WMI_TAG_TPC_STATS_CTL_PWR_TABLE_EVENT:
 9400		tpc_ctl_pwr = (struct wmi_tpc_ctl_pwr_fixed_params *)ptr;
 9401		ret = ath12k_tpc_get_ctl_pwr_tbl(ab, tpc_stats, tpc_ctl_pwr);
 9402		break;
 9403	default:
 9404		ath12k_warn(ab,
 9405			    "Received invalid tag for tpc stats in subtlvs\n");
 9406		return -EINVAL;
 9407	}
 9408	return ret;
 9409}
 9410
 9411static int ath12k_wmi_tpc_stats_event_parser(struct ath12k_base *ab,
 9412					     u16 tag, u16 len,
 9413					     const void *ptr, void *data)
 9414{
 9415	struct wmi_tpc_stats_arg *tpc_stats = (struct wmi_tpc_stats_arg *)data;
 9416	int ret;
 9417
 9418	switch (tag) {
 9419	case WMI_TAG_HALPHY_CTRL_PATH_EVENT_FIXED_PARAM:
 9420		ret = 0;
 9421		/* Fixed param is already processed*/
 9422		break;
 9423	case WMI_TAG_ARRAY_STRUCT:
 9424		/* len 0 is expected for array of struct when there
 9425		 * is no content of that type to pack inside that tlv
 9426		 */
 9427		if (len == 0)
 9428			return 0;
 9429		ret = ath12k_wmi_tlv_iter(ab, ptr, len,
 9430					  ath12k_wmi_tpc_stats_subtlv_parser,
 9431					  tpc_stats);
 9432		break;
 9433	case WMI_TAG_ARRAY_INT16:
 9434		if (len == 0)
 9435			return 0;
 9436		ret = ath12k_wmi_tpc_stats_copy_buffer(ab, ptr,
 9437						       WMI_TAG_ARRAY_INT16,
 9438						       len, tpc_stats);
 9439		break;
 9440	case WMI_TAG_ARRAY_BYTE:
 9441		if (len == 0)
 9442			return 0;
 9443		ret = ath12k_wmi_tpc_stats_copy_buffer(ab, ptr,
 9444						       WMI_TAG_ARRAY_BYTE,
 9445						       len, tpc_stats);
 9446		break;
 9447	default:
 9448		ath12k_warn(ab, "Received invalid tag for tpc stats\n");
 9449		ret = -EINVAL;
 9450		break;
 9451	}
 9452	return ret;
 9453}
 9454
 9455void ath12k_wmi_free_tpc_stats_mem(struct ath12k *ar)
 9456{
 9457	struct wmi_tpc_stats_arg *tpc_stats = ar->debug.tpc_stats;
 9458
 9459	lockdep_assert_held(&ar->data_lock);
 9460	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "tpc stats mem free\n");
 9461	if (tpc_stats) {
 9462		kfree(tpc_stats->max_reg_allowed_power.reg_pwr_array);
 9463		kfree(tpc_stats->rates_array1.rate_array);
 9464		kfree(tpc_stats->rates_array2.rate_array);
 9465		kfree(tpc_stats->ctl_array.ctl_pwr_table);
 9466		kfree(tpc_stats);
 9467		ar->debug.tpc_stats = NULL;
 9468	}
 9469}
 9470
 9471static void ath12k_wmi_process_tpc_stats(struct ath12k_base *ab,
 9472					 struct sk_buff *skb)
 9473{
 9474	struct ath12k_wmi_pdev_tpc_stats_event_fixed_params *fixed_param;
 9475	struct wmi_tpc_stats_arg *tpc_stats;
 9476	const struct wmi_tlv *tlv;
 9477	void *ptr = skb->data;
 9478	struct ath12k *ar;
 9479	u16 tlv_tag;
 9480	u32 event_count;
 9481	int ret;
 9482
 9483	if (!skb->data) {
 9484		ath12k_warn(ab, "No data present in tpc stats event\n");
 9485		return;
 9486	}
 9487
 9488	if (skb->len < (sizeof(*fixed_param) + TLV_HDR_SIZE)) {
 9489		ath12k_warn(ab, "TPC stats event size invalid\n");
 9490		return;
 9491	}
 9492
 9493	tlv = (struct wmi_tlv *)ptr;
 9494	tlv_tag = le32_get_bits(tlv->header, WMI_TLV_TAG);
 9495	ptr += sizeof(*tlv);
 9496
 9497	if (tlv_tag != WMI_TAG_HALPHY_CTRL_PATH_EVENT_FIXED_PARAM) {
 9498		ath12k_warn(ab, "TPC stats without fixed param tlv at start\n");
 9499		return;
 9500	}
 9501
 9502	fixed_param = (struct ath12k_wmi_pdev_tpc_stats_event_fixed_params *)ptr;
 9503	rcu_read_lock();
 9504	ar = ath12k_mac_get_ar_by_pdev_id(ab, le32_to_cpu(fixed_param->pdev_id) + 1);
 9505	if (!ar) {
 9506		ath12k_warn(ab, "Failed to get ar for tpc stats\n");
 9507		rcu_read_unlock();
 9508		return;
 9509	}
 9510	spin_lock_bh(&ar->data_lock);
 9511	if (!ar->debug.tpc_request) {
 9512		/* Event is received either without request or the
 9513		 * timeout, if memory is already allocated free it
 9514		 */
 9515		if (ar->debug.tpc_stats) {
 9516			ath12k_warn(ab, "Freeing memory for tpc_stats\n");
 9517			ath12k_wmi_free_tpc_stats_mem(ar);
 9518		}
 9519		goto unlock;
 9520	}
 9521
 9522	event_count = le32_to_cpu(fixed_param->event_count);
 9523	if (event_count == 0) {
 9524		if (ar->debug.tpc_stats) {
 9525			ath12k_warn(ab,
 9526				    "Invalid tpc memory present\n");
 9527			goto unlock;
 9528		}
 9529		ar->debug.tpc_stats =
 9530			kzalloc(sizeof(struct wmi_tpc_stats_arg),
 9531				GFP_ATOMIC);
 9532		if (!ar->debug.tpc_stats) {
 9533			ath12k_warn(ab,
 9534				    "Failed to allocate memory for tpc stats\n");
 9535			goto unlock;
 9536		}
 9537	}
 9538
 9539	tpc_stats = ar->debug.tpc_stats;
 9540	if (!tpc_stats) {
 9541		ath12k_warn(ab, "tpc stats memory unavailable\n");
 9542		goto unlock;
 9543	}
 9544
 9545	if (!(event_count == 0)) {
 9546		if (event_count != tpc_stats->event_count + 1) {
 9547			ath12k_warn(ab,
 9548				    "Invalid tpc event received\n");
 9549			goto unlock;
 9550		}
 9551	}
 9552	tpc_stats->pdev_id = le32_to_cpu(fixed_param->pdev_id);
 9553	tpc_stats->end_of_event = le32_to_cpu(fixed_param->end_of_event);
 9554	tpc_stats->event_count = le32_to_cpu(fixed_param->event_count);
 9555	ath12k_dbg(ab, ATH12K_DBG_WMI,
 9556		   "tpc stats event_count %d\n",
 9557		   tpc_stats->event_count);
 9558	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 9559				  ath12k_wmi_tpc_stats_event_parser,
 9560				  tpc_stats);
 9561	if (ret) {
 9562		ath12k_wmi_free_tpc_stats_mem(ar);
 9563		ath12k_warn(ab, "failed to parse tpc_stats tlv: %d\n", ret);
 9564		goto unlock;
 9565	}
 9566
 9567	if (tpc_stats->end_of_event)
 9568		complete(&ar->debug.tpc_complete);
 9569
 9570unlock:
 9571	spin_unlock_bh(&ar->data_lock);
 9572	rcu_read_unlock();
 9573}
 9574#else
 9575static void ath12k_wmi_process_tpc_stats(struct ath12k_base *ab,
 9576					 struct sk_buff *skb)
 9577{
 9578}
 9579#endif
 9580
 9581static int
 9582ath12k_wmi_rssi_dbm_conv_info_evt_subtlv_parser(struct ath12k_base *ab,
 9583						u16 tag, u16 len,
 9584						const void *ptr, void *data)
 9585{
 9586	const struct ath12k_wmi_rssi_dbm_conv_temp_info_params *temp_info;
 9587	const struct ath12k_wmi_rssi_dbm_conv_info_params *param_info;
 9588	struct ath12k_wmi_rssi_dbm_conv_info_arg *rssi_info = data;
 9589	struct ath12k_wmi_rssi_dbm_conv_param_arg param_arg;
 9590	s32 nf_hw_dbm[ATH12K_MAX_NUM_NF_HW_DBM];
 9591	u8 num_20mhz_segments;
 9592	s8 min_nf, *nf_ptr;
 9593	int i, j;
 9594
 9595	switch (tag) {
 9596	case WMI_TAG_RSSI_DBM_CONVERSION_PARAMS_INFO:
 9597		if (len < sizeof(*param_info)) {
 9598			ath12k_warn(ab,
 9599				    "RSSI dbm conv subtlv 0x%x invalid len %d rcvd",
 9600				    tag, len);
 9601			return -EINVAL;
 9602		}
 9603
 9604		param_info = ptr;
 9605
 9606		param_arg.curr_bw = le32_to_cpu(param_info->curr_bw);
 9607		param_arg.curr_rx_chainmask = le32_to_cpu(param_info->curr_rx_chainmask);
 9608
 9609		/* The received array is actually a 2D byte-array for per chain,
 9610		 * per 20MHz subband. Convert to 2D byte-array
 9611		 */
 9612		nf_ptr = &param_arg.nf_hw_dbm[0][0];
 9613
 9614		for (i = 0; i < ATH12K_MAX_NUM_NF_HW_DBM; i++) {
 9615			nf_hw_dbm[i] = a_sle32_to_cpu(param_info->nf_hw_dbm[i]);
 9616
 9617			for (j = 0; j < 4; j++) {
 9618				*nf_ptr = (nf_hw_dbm[i] >> (j * 8)) & 0xFF;
 9619				nf_ptr++;
 9620			}
 9621		}
 9622
 9623		switch (param_arg.curr_bw) {
 9624		case WMI_CHAN_WIDTH_20:
 9625			num_20mhz_segments = 1;
 9626			break;
 9627		case WMI_CHAN_WIDTH_40:
 9628			num_20mhz_segments = 2;
 9629			break;
 9630		case WMI_CHAN_WIDTH_80:
 9631			num_20mhz_segments = 4;
 9632			break;
 9633		case WMI_CHAN_WIDTH_160:
 9634			num_20mhz_segments = 8;
 9635			break;
 9636		case WMI_CHAN_WIDTH_320:
 9637			num_20mhz_segments = 16;
 9638			break;
 9639		default:
 9640			ath12k_warn(ab, "Invalid current bandwidth %d in RSSI dbm event",
 9641				    param_arg.curr_bw);
 9642			/* In error case, still consider the primary 20 MHz segment since
 9643			 * that would be much better than instead of dropping the whole
 9644			 * event
 9645			 */
 9646			num_20mhz_segments = 1;
 9647		}
 9648
 9649		min_nf = ATH12K_DEFAULT_NOISE_FLOOR;
 9650
 9651		for (i = 0; i < ATH12K_MAX_NUM_ANTENNA; i++) {
 9652			if (!(param_arg.curr_rx_chainmask & BIT(i)))
 9653				continue;
 9654
 9655			for (j = 0; j < num_20mhz_segments; j++) {
 9656				if (param_arg.nf_hw_dbm[i][j] < min_nf)
 9657					min_nf = param_arg.nf_hw_dbm[i][j];
 9658			}
 9659		}
 9660
 9661		rssi_info->min_nf_dbm = min_nf;
 9662		rssi_info->nf_dbm_present = true;
 9663		break;
 9664	case WMI_TAG_RSSI_DBM_CONVERSION_TEMP_OFFSET_INFO:
 9665		if (len < sizeof(*temp_info)) {
 9666			ath12k_warn(ab,
 9667				    "RSSI dbm conv subtlv 0x%x invalid len %d rcvd",
 9668				    tag, len);
 9669			return -EINVAL;
 9670		}
 9671
 9672		temp_info = ptr;
 9673		rssi_info->temp_offset = a_sle32_to_cpu(temp_info->offset);
 9674		rssi_info->temp_offset_present = true;
 9675		break;
 9676	default:
 9677		ath12k_dbg(ab, ATH12K_DBG_WMI,
 9678			   "Unknown subtlv 0x%x in RSSI dbm conversion event\n", tag);
 9679	}
 9680
 9681	return 0;
 9682}
 9683
 9684static int
 9685ath12k_wmi_rssi_dbm_conv_info_event_parser(struct ath12k_base *ab,
 9686					   u16 tag, u16 len,
 9687					   const void *ptr, void *data)
 9688{
 9689	int ret = 0;
 9690
 9691	switch (tag) {
 9692	case WMI_TAG_RSSI_DBM_CONVERSION_PARAMS_INFO_FIXED_PARAM:
 9693		/* Fixed param is already processed*/
 9694		break;
 9695	case WMI_TAG_ARRAY_STRUCT:
 9696		/* len 0 is expected for array of struct when there
 9697		 * is no content of that type inside that tlv
 9698		 */
 9699		if (len == 0)
 9700			return 0;
 9701
 9702		ret = ath12k_wmi_tlv_iter(ab, ptr, len,
 9703					  ath12k_wmi_rssi_dbm_conv_info_evt_subtlv_parser,
 9704					  data);
 9705		break;
 9706	default:
 9707		ath12k_dbg(ab, ATH12K_DBG_WMI,
 9708			   "Received invalid tag 0x%x for RSSI dbm conv info event\n",
 9709			   tag);
 9710		break;
 9711	}
 9712
 9713	return ret;
 9714}
 9715
 9716static int
 9717ath12k_wmi_rssi_dbm_conv_info_process_fixed_param(struct ath12k_base *ab, u8 *ptr,
 9718						  size_t len, int *pdev_id)
 9719{
 9720	struct ath12k_wmi_rssi_dbm_conv_info_fixed_params *fixed_param;
 9721	const struct wmi_tlv *tlv;
 9722	u16 tlv_tag;
 9723
 9724	if (len < (sizeof(*fixed_param) + TLV_HDR_SIZE)) {
 9725		ath12k_warn(ab, "invalid RSSI dbm conv event size %zu\n", len);
 9726		return -EINVAL;
 9727	}
 9728
 9729	tlv = (struct wmi_tlv *)ptr;
 9730	tlv_tag = le32_get_bits(tlv->header, WMI_TLV_TAG);
 9731	ptr += sizeof(*tlv);
 9732
 9733	if (tlv_tag != WMI_TAG_RSSI_DBM_CONVERSION_PARAMS_INFO_FIXED_PARAM) {
 9734		ath12k_warn(ab, "RSSI dbm conv event received without fixed param tlv\n");
 9735		return -EINVAL;
 9736	}
 9737
 9738	fixed_param = (struct ath12k_wmi_rssi_dbm_conv_info_fixed_params *)ptr;
 9739	*pdev_id = le32_to_cpu(fixed_param->pdev_id);
 9740
 9741	return 0;
 9742}
 9743
 9744static void
 9745ath12k_wmi_update_rssi_offsets(struct ath12k *ar,
 9746			       struct ath12k_wmi_rssi_dbm_conv_info_arg *rssi_info)
 9747{
 9748	struct ath12k_pdev_rssi_offsets *info = &ar->rssi_info;
 9749
 9750	lockdep_assert_held(&ar->data_lock);
 9751
 9752	if (rssi_info->temp_offset_present)
 9753		info->temp_offset = rssi_info->temp_offset;
 9754
 9755	if (rssi_info->nf_dbm_present)
 9756		info->min_nf_dbm = rssi_info->min_nf_dbm;
 9757
 9758	info->noise_floor = info->min_nf_dbm + info->temp_offset;
 9759}
 9760
 9761static void
 9762ath12k_wmi_rssi_dbm_conversion_params_info_event(struct ath12k_base *ab,
 9763						 struct sk_buff *skb)
 9764{
 9765	struct ath12k_wmi_rssi_dbm_conv_info_arg rssi_info;
 9766	struct ath12k *ar;
 9767	s32 noise_floor;
 9768	u32 pdev_id;
 9769	int ret;
 9770
 9771	ret = ath12k_wmi_rssi_dbm_conv_info_process_fixed_param(ab, skb->data, skb->len,
 9772								&pdev_id);
 9773	if (ret) {
 9774		ath12k_warn(ab, "failed to parse fixed param in RSSI dbm conv event: %d\n",
 9775			    ret);
 9776		return;
 9777	}
 9778
 9779	rcu_read_lock();
 9780	ar = ath12k_mac_get_ar_by_pdev_id(ab, pdev_id);
 9781	/* If pdev is not active, ignore the event */
 9782	if (!ar)
 9783		goto out_unlock;
 9784
 9785	ret = ath12k_wmi_tlv_iter(ab, skb->data, skb->len,
 9786				  ath12k_wmi_rssi_dbm_conv_info_event_parser,
 9787				  &rssi_info);
 9788	if (ret) {
 9789		ath12k_warn(ab, "unable to parse RSSI dbm conversion event\n");
 9790		goto out_unlock;
 9791	}
 9792
 9793	spin_lock_bh(&ar->data_lock);
 9794	ath12k_wmi_update_rssi_offsets(ar, &rssi_info);
 9795	noise_floor = ath12k_pdev_get_noise_floor(ar);
 9796	spin_unlock_bh(&ar->data_lock);
 9797
 9798	ath12k_dbg(ab, ATH12K_DBG_WMI,
 9799		   "RSSI noise floor updated, new value is %d dbm\n", noise_floor);
 9800out_unlock:
 9801	rcu_read_unlock();
 9802}
 9803
 9804static void ath12k_wmi_op_rx(struct ath12k_base *ab, struct sk_buff *skb)
 9805{
 9806	struct wmi_cmd_hdr *cmd_hdr;
 9807	enum wmi_tlv_event_id id;
 9808
 9809	cmd_hdr = (struct wmi_cmd_hdr *)skb->data;
 9810	id = le32_get_bits(cmd_hdr->cmd_id, WMI_CMD_HDR_CMD_ID);
 9811
 9812	if (!skb_pull(skb, sizeof(struct wmi_cmd_hdr)))
 9813		goto out;
 9814
 9815	switch (id) {
 9816		/* Process all the WMI events here */
 9817	case WMI_SERVICE_READY_EVENTID:
 9818		ath12k_service_ready_event(ab, skb);
 9819		break;
 9820	case WMI_SERVICE_READY_EXT_EVENTID:
 9821		ath12k_service_ready_ext_event(ab, skb);
 9822		break;
 9823	case WMI_SERVICE_READY_EXT2_EVENTID:
 9824		ath12k_service_ready_ext2_event(ab, skb);
 9825		break;
 9826	case WMI_REG_CHAN_LIST_CC_EXT_EVENTID:
 9827		ath12k_reg_chan_list_event(ab, skb);
 9828		break;
 9829	case WMI_READY_EVENTID:
 9830		ath12k_ready_event(ab, skb);
 9831		break;
 9832	case WMI_PEER_DELETE_RESP_EVENTID:
 9833		ath12k_peer_delete_resp_event(ab, skb);
 9834		break;
 9835	case WMI_VDEV_START_RESP_EVENTID:
 9836		ath12k_vdev_start_resp_event(ab, skb);
 9837		break;
 9838	case WMI_OFFLOAD_BCN_TX_STATUS_EVENTID:
 9839		ath12k_bcn_tx_status_event(ab, skb);
 9840		break;
 9841	case WMI_VDEV_STOPPED_EVENTID:
 9842		ath12k_vdev_stopped_event(ab, skb);
 9843		break;
 9844	case WMI_MGMT_RX_EVENTID:
 9845		ath12k_mgmt_rx_event(ab, skb);
 9846		/* mgmt_rx_event() owns the skb now! */
 9847		return;
 9848	case WMI_MGMT_TX_COMPLETION_EVENTID:
 9849		ath12k_mgmt_tx_compl_event(ab, skb);
 9850		break;
 9851	case WMI_SCAN_EVENTID:
 9852		ath12k_scan_event(ab, skb);
 9853		break;
 9854	case WMI_PEER_STA_KICKOUT_EVENTID:
 9855		ath12k_peer_sta_kickout_event(ab, skb);
 9856		break;
 9857	case WMI_ROAM_EVENTID:
 9858		ath12k_roam_event(ab, skb);
 9859		break;
 9860	case WMI_CHAN_INFO_EVENTID:
 9861		ath12k_chan_info_event(ab, skb);
 9862		break;
 9863	case WMI_PDEV_BSS_CHAN_INFO_EVENTID:
 9864		ath12k_pdev_bss_chan_info_event(ab, skb);
 9865		break;
 9866	case WMI_VDEV_INSTALL_KEY_COMPLETE_EVENTID:
 9867		ath12k_vdev_install_key_compl_event(ab, skb);
 9868		break;
 9869	case WMI_SERVICE_AVAILABLE_EVENTID:
 9870		ath12k_service_available_event(ab, skb);
 9871		break;
 9872	case WMI_PEER_ASSOC_CONF_EVENTID:
 9873		ath12k_peer_assoc_conf_event(ab, skb);
 9874		break;
 9875	case WMI_UPDATE_STATS_EVENTID:
 9876		ath12k_update_stats_event(ab, skb);
 9877		break;
 9878	case WMI_PDEV_CTL_FAILSAFE_CHECK_EVENTID:
 9879		ath12k_pdev_ctl_failsafe_check_event(ab, skb);
 9880		break;
 9881	case WMI_PDEV_CSA_SWITCH_COUNT_STATUS_EVENTID:
 9882		ath12k_wmi_pdev_csa_switch_count_status_event(ab, skb);
 9883		break;
 9884	case WMI_PDEV_TEMPERATURE_EVENTID:
 9885		ath12k_wmi_pdev_temperature_event(ab, skb);
 9886		break;
 9887	case WMI_PDEV_DMA_RING_BUF_RELEASE_EVENTID:
 9888		ath12k_wmi_pdev_dma_ring_buf_release_event(ab, skb);
 9889		break;
 9890	case WMI_HOST_FILS_DISCOVERY_EVENTID:
 9891		ath12k_fils_discovery_event(ab, skb);
 9892		break;
 9893	case WMI_OFFLOAD_PROB_RESP_TX_STATUS_EVENTID:
 9894		ath12k_probe_resp_tx_status_event(ab, skb);
 9895		break;
 9896	case WMI_RFKILL_STATE_CHANGE_EVENTID:
 9897		ath12k_rfkill_state_change_event(ab, skb);
 9898		break;
 9899	case WMI_TWT_ENABLE_EVENTID:
 9900		ath12k_wmi_twt_enable_event(ab, skb);
 9901		break;
 9902	case WMI_TWT_DISABLE_EVENTID:
 9903		ath12k_wmi_twt_disable_event(ab, skb);
 9904		break;
 9905	case WMI_P2P_NOA_EVENTID:
 9906		ath12k_wmi_p2p_noa_event(ab, skb);
 9907		break;
 9908	case WMI_PDEV_DFS_RADAR_DETECTION_EVENTID:
 9909		ath12k_wmi_pdev_dfs_radar_detected_event(ab, skb);
 9910		break;
 9911	case WMI_VDEV_DELETE_RESP_EVENTID:
 9912		ath12k_vdev_delete_resp_event(ab, skb);
 9913		break;
 9914	case WMI_DIAG_EVENTID:
 9915		ath12k_wmi_diag_event(ab, skb);
 9916		break;
 9917	case WMI_WOW_WAKEUP_HOST_EVENTID:
 9918		ath12k_wmi_event_wow_wakeup_host(ab, skb);
 9919		break;
 9920	case WMI_GTK_OFFLOAD_STATUS_EVENTID:
 9921		ath12k_wmi_gtk_offload_status_event(ab, skb);
 9922		break;
 9923	case WMI_MLO_SETUP_COMPLETE_EVENTID:
 9924		ath12k_wmi_event_mlo_setup_complete(ab, skb);
 9925		break;
 9926	case WMI_MLO_TEARDOWN_COMPLETE_EVENTID:
 9927		ath12k_wmi_event_teardown_complete(ab, skb);
 9928		break;
 9929	case WMI_HALPHY_STATS_CTRL_PATH_EVENTID:
 9930		ath12k_wmi_process_tpc_stats(ab, skb);
 9931		break;
 9932	case WMI_11D_NEW_COUNTRY_EVENTID:
 9933		ath12k_reg_11d_new_cc_event(ab, skb);
 9934		break;
 9935	case WMI_PDEV_RSSI_DBM_CONVERSION_PARAMS_INFO_EVENTID:
 9936		ath12k_wmi_rssi_dbm_conversion_params_info_event(ab, skb);
 9937		break;
 9938	case WMI_OBSS_COLOR_COLLISION_DETECTION_EVENTID:
 9939		ath12k_wmi_obss_color_collision_event(ab, skb);
 9940		break;
 9941	/* add Unsupported events (rare) here */
 9942	case WMI_TBTTOFFSET_EXT_UPDATE_EVENTID:
 9943	case WMI_PEER_OPER_MODE_CHANGE_EVENTID:
 9944	case WMI_PDEV_DMA_RING_CFG_RSP_EVENTID:
 9945		ath12k_dbg(ab, ATH12K_DBG_WMI,
 9946			   "ignoring unsupported event 0x%x\n", id);
 9947		break;
 9948	/* add Unsupported events (frequent) here */
 9949	case WMI_PDEV_GET_HALPHY_CAL_STATUS_EVENTID:
 9950	case WMI_MGMT_RX_FW_CONSUMED_EVENTID:
 9951		/* debug might flood hence silently ignore (no-op) */
 9952		break;
 9953	case WMI_PDEV_UTF_EVENTID:
 9954		if (test_bit(ATH12K_FLAG_FTM_SEGMENTED, &ab->dev_flags))
 9955			ath12k_tm_wmi_event_segmented(ab, id, skb);
 9956		else
 9957			ath12k_tm_wmi_event_unsegmented(ab, id, skb);
 9958		break;
 9959	default:
 9960		ath12k_dbg(ab, ATH12K_DBG_WMI, "Unknown eventid: 0x%x\n", id);
 9961		break;
 9962	}
 9963
 9964out:
 9965	dev_kfree_skb(skb);
 9966}
 9967
 9968static int ath12k_connect_pdev_htc_service(struct ath12k_base *ab,
 9969					   u32 pdev_idx)
 9970{
 9971	int status;
 9972	static const u32 svc_id[] = {
 9973		ATH12K_HTC_SVC_ID_WMI_CONTROL,
 9974		ATH12K_HTC_SVC_ID_WMI_CONTROL_MAC1,
 9975		ATH12K_HTC_SVC_ID_WMI_CONTROL_MAC2
 9976	};
 9977	struct ath12k_htc_svc_conn_req conn_req = {};
 9978	struct ath12k_htc_svc_conn_resp conn_resp = {};
 9979
 9980	/* these fields are the same for all service endpoints */
 9981	conn_req.ep_ops.ep_tx_complete = ath12k_wmi_htc_tx_complete;
 9982	conn_req.ep_ops.ep_rx_complete = ath12k_wmi_op_rx;
 9983	conn_req.ep_ops.ep_tx_credits = ath12k_wmi_op_ep_tx_credits;
 9984
 9985	/* connect to control service */
 9986	conn_req.service_id = svc_id[pdev_idx];
 9987
 9988	status = ath12k_htc_connect_service(&ab->htc, &conn_req, &conn_resp);
 9989	if (status) {
 9990		ath12k_warn(ab, "failed to connect to WMI CONTROL service status: %d\n",
 9991			    status);
 9992		return status;
 9993	}
 9994
 9995	ab->wmi_ab.wmi_endpoint_id[pdev_idx] = conn_resp.eid;
 9996	ab->wmi_ab.wmi[pdev_idx].eid = conn_resp.eid;
 9997	ab->wmi_ab.max_msg_len[pdev_idx] = conn_resp.max_msg_len;
 9998
 9999	return 0;
10000}
10001
10002static int
10003ath12k_wmi_send_unit_test_cmd(struct ath12k *ar,
10004			      struct wmi_unit_test_cmd ut_cmd,
10005			      u32 *test_args)
10006{
10007	struct ath12k_wmi_pdev *wmi = ar->wmi;
10008	struct wmi_unit_test_cmd *cmd;
10009	struct sk_buff *skb;
10010	struct wmi_tlv *tlv;
10011	void *ptr;
10012	u32 *ut_cmd_args;
10013	int buf_len, arg_len;
10014	int ret;
10015	int i;
10016
10017	arg_len = sizeof(u32) * le32_to_cpu(ut_cmd.num_args);
10018	buf_len = sizeof(ut_cmd) + arg_len + TLV_HDR_SIZE;
10019
10020	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, buf_len);
10021	if (!skb)
10022		return -ENOMEM;
10023
10024	cmd = (struct wmi_unit_test_cmd *)skb->data;
10025	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_UNIT_TEST_CMD,
10026						 sizeof(ut_cmd));
10027
10028	cmd->vdev_id = ut_cmd.vdev_id;
10029	cmd->module_id = ut_cmd.module_id;
10030	cmd->num_args = ut_cmd.num_args;
10031	cmd->diag_token = ut_cmd.diag_token;
10032
10033	ptr = skb->data + sizeof(ut_cmd);
10034
10035	tlv = ptr;
10036	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, arg_len);
10037
10038	ptr += TLV_HDR_SIZE;
10039
10040	ut_cmd_args = ptr;
10041	for (i = 0; i < le32_to_cpu(ut_cmd.num_args); i++)
10042		ut_cmd_args[i] = test_args[i];
10043
10044	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
10045		   "WMI unit test : module %d vdev %d n_args %d token %d\n",
10046		   cmd->module_id, cmd->vdev_id, cmd->num_args,
10047		   cmd->diag_token);
10048
10049	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_UNIT_TEST_CMDID);
10050
10051	if (ret) {
10052		ath12k_warn(ar->ab, "failed to send WMI_UNIT_TEST CMD :%d\n",
10053			    ret);
10054		dev_kfree_skb(skb);
10055	}
10056
10057	return ret;
10058}
10059
10060int ath12k_wmi_simulate_radar(struct ath12k *ar)
10061{
10062	struct ath12k_link_vif *arvif;
10063	u32 dfs_args[DFS_MAX_TEST_ARGS];
10064	struct wmi_unit_test_cmd wmi_ut;
10065	bool arvif_found = false;
10066
10067	list_for_each_entry(arvif, &ar->arvifs, list) {
10068		if (arvif->is_started && arvif->ahvif->vdev_type == WMI_VDEV_TYPE_AP) {
10069			arvif_found = true;
10070			break;
10071		}
10072	}
10073
10074	if (!arvif_found)
10075		return -EINVAL;
10076
10077	dfs_args[DFS_TEST_CMDID] = 0;
10078	dfs_args[DFS_TEST_PDEV_ID] = ar->pdev->pdev_id;
10079	/* Currently we could pass segment_id(b0 - b1), chirp(b2)
10080	 * freq offset (b3 - b10) to unit test. For simulation
10081	 * purpose this can be set to 0 which is valid.
10082	 */
10083	dfs_args[DFS_TEST_RADAR_PARAM] = 0;
10084
10085	wmi_ut.vdev_id = cpu_to_le32(arvif->vdev_id);
10086	wmi_ut.module_id = cpu_to_le32(DFS_UNIT_TEST_MODULE);
10087	wmi_ut.num_args = cpu_to_le32(DFS_MAX_TEST_ARGS);
10088	wmi_ut.diag_token = cpu_to_le32(DFS_UNIT_TEST_TOKEN);
10089
10090	ath12k_dbg(ar->ab, ATH12K_DBG_REG, "Triggering Radar Simulation\n");
10091
10092	return ath12k_wmi_send_unit_test_cmd(ar, wmi_ut, dfs_args);
10093}
10094
10095int ath12k_wmi_send_tpc_stats_request(struct ath12k *ar,
10096				      enum wmi_halphy_ctrl_path_stats_id tpc_stats_type)
10097{
10098	struct wmi_request_halphy_ctrl_path_stats_cmd_fixed_params *cmd;
10099	struct ath12k_wmi_pdev *wmi = ar->wmi;
10100	struct sk_buff *skb;
10101	struct wmi_tlv *tlv;
10102	__le32 *pdev_id;
10103	u32 buf_len;
10104	void *ptr;
10105	int ret;
10106
10107	buf_len = sizeof(*cmd) + TLV_HDR_SIZE + sizeof(u32) + TLV_HDR_SIZE + TLV_HDR_SIZE;
10108
10109	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, buf_len);
10110	if (!skb)
10111		return -ENOMEM;
10112	cmd = (struct wmi_request_halphy_ctrl_path_stats_cmd_fixed_params *)skb->data;
10113	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_HALPHY_CTRL_PATH_CMD_FIXED_PARAM,
10114						 sizeof(*cmd));
10115
10116	cmd->stats_id_mask = cpu_to_le32(WMI_REQ_CTRL_PATH_PDEV_TX_STAT);
10117	cmd->action = cpu_to_le32(WMI_REQUEST_CTRL_PATH_STAT_GET);
10118	cmd->subid = cpu_to_le32(tpc_stats_type);
10119
10120	ptr = skb->data + sizeof(*cmd);
10121
10122	/* The below TLV arrays optionally follow this fixed param TLV structure
10123	 * 1. ARRAY_UINT32 pdev_ids[]
10124	 *      If this array is present and non-zero length, stats should only
10125	 *      be provided from the pdevs identified in the array.
10126	 * 2. ARRAY_UNIT32 vdev_ids[]
10127	 *      If this array is present and non-zero length, stats should only
10128	 *      be provided from the vdevs identified in the array.
10129	 * 3. ath12k_wmi_mac_addr_params peer_macaddr[];
10130	 *      If this array is present and non-zero length, stats should only
10131	 *      be provided from the peers with the MAC addresses specified
10132	 *      in the array
10133	 */
10134	tlv = ptr;
10135	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, sizeof(u32));
10136	ptr += TLV_HDR_SIZE;
10137
10138	pdev_id = ptr;
10139	*pdev_id = cpu_to_le32(ath12k_mac_get_target_pdev_id(ar));
10140	ptr += sizeof(*pdev_id);
10141
10142	tlv = ptr;
10143	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, 0);
10144	ptr += TLV_HDR_SIZE;
10145
10146	tlv = ptr;
10147	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_FIXED_STRUCT, 0);
10148	ptr += TLV_HDR_SIZE;
10149
10150	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_REQUEST_HALPHY_CTRL_PATH_STATS_CMDID);
10151	if (ret) {
10152		ath12k_warn(ar->ab,
10153			    "failed to submit WMI_REQUEST_STATS_CTRL_PATH_CMDID\n");
10154		dev_kfree_skb(skb);
10155		return ret;
10156	}
10157	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "WMI get TPC STATS sent on pdev %d\n",
10158		   ar->pdev->pdev_id);
10159
10160	return ret;
10161}
10162
10163int ath12k_wmi_connect(struct ath12k_base *ab)
10164{
10165	u32 i;
10166	u8 wmi_ep_count;
10167
10168	wmi_ep_count = ab->htc.wmi_ep_count;
10169	if (wmi_ep_count > ab->hw_params->max_radios)
10170		return -1;
10171
10172	for (i = 0; i < wmi_ep_count; i++)
10173		ath12k_connect_pdev_htc_service(ab, i);
10174
10175	return 0;
10176}
10177
10178static void ath12k_wmi_pdev_detach(struct ath12k_base *ab, u8 pdev_id)
10179{
10180	if (WARN_ON(pdev_id >= MAX_RADIOS))
10181		return;
10182
10183	/* TODO: Deinit any pdev specific wmi resource */
10184}
10185
10186int ath12k_wmi_pdev_attach(struct ath12k_base *ab,
10187			   u8 pdev_id)
10188{
10189	struct ath12k_wmi_pdev *wmi_handle;
10190
10191	if (pdev_id >= ab->hw_params->max_radios)
10192		return -EINVAL;
10193
10194	wmi_handle = &ab->wmi_ab.wmi[pdev_id];
10195
10196	wmi_handle->wmi_ab = &ab->wmi_ab;
10197
10198	ab->wmi_ab.ab = ab;
10199	/* TODO: Init remaining resource specific to pdev */
10200
10201	return 0;
10202}
10203
10204int ath12k_wmi_attach(struct ath12k_base *ab)
10205{
10206	int ret;
10207
10208	ret = ath12k_wmi_pdev_attach(ab, 0);
10209	if (ret)
10210		return ret;
10211
10212	ab->wmi_ab.ab = ab;
10213	ab->wmi_ab.preferred_hw_mode = WMI_HOST_HW_MODE_MAX;
10214
10215	/* It's overwritten when service_ext_ready is handled */
10216	if (ab->hw_params->single_pdev_only)
10217		ab->wmi_ab.preferred_hw_mode = WMI_HOST_HW_MODE_SINGLE;
10218
10219	/* TODO: Init remaining wmi soc resources required */
10220	init_completion(&ab->wmi_ab.service_ready);
10221	init_completion(&ab->wmi_ab.unified_ready);
10222
10223	return 0;
10224}
10225
10226void ath12k_wmi_detach(struct ath12k_base *ab)
10227{
10228	int i;
10229
10230	/* TODO: Deinit wmi resource specific to SOC as required */
10231
10232	for (i = 0; i < ab->htc.wmi_ep_count; i++)
10233		ath12k_wmi_pdev_detach(ab, i);
10234
10235	ath12k_wmi_free_dbring_caps(ab);
10236}
10237
10238int ath12k_wmi_hw_data_filter_cmd(struct ath12k *ar, struct wmi_hw_data_filter_arg *arg)
10239{
10240	struct wmi_hw_data_filter_cmd *cmd;
10241	struct sk_buff *skb;
10242	int len;
10243
10244	len = sizeof(*cmd);
10245	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10246
10247	if (!skb)
10248		return -ENOMEM;
10249
10250	cmd = (struct wmi_hw_data_filter_cmd *)skb->data;
10251	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_HW_DATA_FILTER_CMD,
10252						 sizeof(*cmd));
10253	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
10254	cmd->enable = cpu_to_le32(arg->enable ? 1 : 0);
10255
10256	/* Set all modes in case of disable */
10257	if (arg->enable)
10258		cmd->hw_filter_bitmap = cpu_to_le32(arg->hw_filter_bitmap);
10259	else
10260		cmd->hw_filter_bitmap = cpu_to_le32((u32)~0U);
10261
10262	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
10263		   "wmi hw data filter enable %d filter_bitmap 0x%x\n",
10264		   arg->enable, arg->hw_filter_bitmap);
10265
10266	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_HW_DATA_FILTER_CMDID);
10267}
10268
10269int ath12k_wmi_wow_host_wakeup_ind(struct ath12k *ar)
10270{
10271	struct wmi_wow_host_wakeup_cmd *cmd;
10272	struct sk_buff *skb;
10273	size_t len;
10274
10275	len = sizeof(*cmd);
10276	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10277	if (!skb)
10278		return -ENOMEM;
10279
10280	cmd = (struct wmi_wow_host_wakeup_cmd *)skb->data;
10281	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_WOW_HOSTWAKEUP_FROM_SLEEP_CMD,
10282						 sizeof(*cmd));
10283
10284	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "wmi tlv wow host wakeup ind\n");
10285
10286	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_WOW_HOSTWAKEUP_FROM_SLEEP_CMDID);
10287}
10288
10289int ath12k_wmi_wow_enable(struct ath12k *ar)
10290{
10291	struct wmi_wow_enable_cmd *cmd;
10292	struct sk_buff *skb;
10293	int len;
10294
10295	len = sizeof(*cmd);
10296	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10297	if (!skb)
10298		return -ENOMEM;
10299
10300	cmd = (struct wmi_wow_enable_cmd *)skb->data;
10301	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_WOW_ENABLE_CMD,
10302						 sizeof(*cmd));
10303
10304	cmd->enable = cpu_to_le32(1);
10305	cmd->pause_iface_config = cpu_to_le32(WOW_IFACE_PAUSE_ENABLED);
10306	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "wmi tlv wow enable\n");
10307
10308	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_WOW_ENABLE_CMDID);
10309}
10310
10311int ath12k_wmi_wow_add_wakeup_event(struct ath12k *ar, u32 vdev_id,
10312				    enum wmi_wow_wakeup_event event,
10313				    u32 enable)
10314{
10315	struct wmi_wow_add_del_event_cmd *cmd;
10316	struct sk_buff *skb;
10317	size_t len;
10318
10319	len = sizeof(*cmd);
10320	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10321	if (!skb)
10322		return -ENOMEM;
10323
10324	cmd = (struct wmi_wow_add_del_event_cmd *)skb->data;
10325	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_WOW_ADD_DEL_EVT_CMD,
10326						 sizeof(*cmd));
10327	cmd->vdev_id = cpu_to_le32(vdev_id);
10328	cmd->is_add = cpu_to_le32(enable);
10329	cmd->event_bitmap = cpu_to_le32((1 << event));
10330
10331	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "wmi tlv wow add wakeup event %s enable %d vdev_id %d\n",
10332		   wow_wakeup_event(event), enable, vdev_id);
10333
10334	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_WOW_ENABLE_DISABLE_WAKE_EVENT_CMDID);
10335}
10336
10337int ath12k_wmi_wow_add_pattern(struct ath12k *ar, u32 vdev_id, u32 pattern_id,
10338			       const u8 *pattern, const u8 *mask,
10339			       int pattern_len, int pattern_offset)
10340{
10341	struct wmi_wow_add_pattern_cmd *cmd;
10342	struct wmi_wow_bitmap_pattern_params *bitmap;
10343	struct wmi_tlv *tlv;
10344	struct sk_buff *skb;
10345	void *ptr;
10346	size_t len;
10347
10348	len = sizeof(*cmd) +
10349	      sizeof(*tlv) +			/* array struct */
10350	      sizeof(*bitmap) +			/* bitmap */
10351	      sizeof(*tlv) +			/* empty ipv4 sync */
10352	      sizeof(*tlv) +			/* empty ipv6 sync */
10353	      sizeof(*tlv) +			/* empty magic */
10354	      sizeof(*tlv) +			/* empty info timeout */
10355	      sizeof(*tlv) + sizeof(u32);	/* ratelimit interval */
10356
10357	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10358	if (!skb)
10359		return -ENOMEM;
10360
10361	/* cmd */
10362	ptr = skb->data;
10363	cmd = ptr;
10364	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_WOW_ADD_PATTERN_CMD,
10365						 sizeof(*cmd));
10366	cmd->vdev_id = cpu_to_le32(vdev_id);
10367	cmd->pattern_id = cpu_to_le32(pattern_id);
10368	cmd->pattern_type = cpu_to_le32(WOW_BITMAP_PATTERN);
10369
10370	ptr += sizeof(*cmd);
10371
10372	/* bitmap */
10373	tlv = ptr;
10374	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, sizeof(*bitmap));
10375
10376	ptr += sizeof(*tlv);
10377
10378	bitmap = ptr;
10379	bitmap->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_WOW_BITMAP_PATTERN_T,
10380						    sizeof(*bitmap));
10381	memcpy(bitmap->patternbuf, pattern, pattern_len);
10382	memcpy(bitmap->bitmaskbuf, mask, pattern_len);
10383	bitmap->pattern_offset = cpu_to_le32(pattern_offset);
10384	bitmap->pattern_len = cpu_to_le32(pattern_len);
10385	bitmap->bitmask_len = cpu_to_le32(pattern_len);
10386	bitmap->pattern_id = cpu_to_le32(pattern_id);
10387
10388	ptr += sizeof(*bitmap);
10389
10390	/* ipv4 sync */
10391	tlv = ptr;
10392	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, 0);
10393
10394	ptr += sizeof(*tlv);
10395
10396	/* ipv6 sync */
10397	tlv = ptr;
10398	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, 0);
10399
10400	ptr += sizeof(*tlv);
10401
10402	/* magic */
10403	tlv = ptr;
10404	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, 0);
10405
10406	ptr += sizeof(*tlv);
10407
10408	/* pattern info timeout */
10409	tlv = ptr;
10410	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, 0);
10411
10412	ptr += sizeof(*tlv);
10413
10414	/* ratelimit interval */
10415	tlv = ptr;
10416	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, sizeof(u32));
10417
10418	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "wmi tlv wow add pattern vdev_id %d pattern_id %d pattern_offset %d pattern_len %d\n",
10419		   vdev_id, pattern_id, pattern_offset, pattern_len);
10420
10421	ath12k_dbg_dump(ar->ab, ATH12K_DBG_WMI, NULL, "wow pattern: ",
10422			bitmap->patternbuf, pattern_len);
10423	ath12k_dbg_dump(ar->ab, ATH12K_DBG_WMI, NULL, "wow bitmask: ",
10424			bitmap->bitmaskbuf, pattern_len);
10425
10426	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_WOW_ADD_WAKE_PATTERN_CMDID);
10427}
10428
10429int ath12k_wmi_wow_del_pattern(struct ath12k *ar, u32 vdev_id, u32 pattern_id)
10430{
10431	struct wmi_wow_del_pattern_cmd *cmd;
10432	struct sk_buff *skb;
10433	size_t len;
10434
10435	len = sizeof(*cmd);
10436	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10437	if (!skb)
10438		return -ENOMEM;
10439
10440	cmd = (struct wmi_wow_del_pattern_cmd *)skb->data;
10441	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_WOW_DEL_PATTERN_CMD,
10442						 sizeof(*cmd));
10443	cmd->vdev_id = cpu_to_le32(vdev_id);
10444	cmd->pattern_id = cpu_to_le32(pattern_id);
10445	cmd->pattern_type = cpu_to_le32(WOW_BITMAP_PATTERN);
10446
10447	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "wmi tlv wow del pattern vdev_id %d pattern_id %d\n",
10448		   vdev_id, pattern_id);
10449
10450	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_WOW_DEL_WAKE_PATTERN_CMDID);
10451}
10452
10453static struct sk_buff *
10454ath12k_wmi_op_gen_config_pno_start(struct ath12k *ar, u32 vdev_id,
10455				   struct wmi_pno_scan_req_arg *pno)
10456{
10457	struct nlo_configured_params *nlo_list;
10458	size_t len, nlo_list_len, channel_list_len;
10459	struct wmi_wow_nlo_config_cmd *cmd;
10460	__le32 *channel_list;
10461	struct wmi_tlv *tlv;
10462	struct sk_buff *skb;
10463	void *ptr;
10464	u32 i;
10465
10466	len = sizeof(*cmd) +
10467	      sizeof(*tlv) +
10468	      /* TLV place holder for array of structures
10469	       * nlo_configured_params(nlo_list)
10470	       */
10471	      sizeof(*tlv);
10472	      /* TLV place holder for array of uint32 channel_list */
10473
10474	channel_list_len = sizeof(u32) * pno->a_networks[0].channel_count;
10475	len += channel_list_len;
10476
10477	nlo_list_len = sizeof(*nlo_list) * pno->uc_networks_count;
10478	len += nlo_list_len;
10479
10480	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10481	if (!skb)
10482		return ERR_PTR(-ENOMEM);
10483
10484	ptr = skb->data;
10485	cmd = ptr;
10486	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_NLO_CONFIG_CMD, sizeof(*cmd));
10487
10488	cmd->vdev_id = cpu_to_le32(pno->vdev_id);
10489	cmd->flags = cpu_to_le32(WMI_NLO_CONFIG_START | WMI_NLO_CONFIG_SSID_HIDE_EN);
10490
10491	/* current FW does not support min-max range for dwell time */
10492	cmd->active_dwell_time = cpu_to_le32(pno->active_max_time);
10493	cmd->passive_dwell_time = cpu_to_le32(pno->passive_max_time);
10494
10495	if (pno->do_passive_scan)
10496		cmd->flags |= cpu_to_le32(WMI_NLO_CONFIG_SCAN_PASSIVE);
10497
10498	cmd->fast_scan_period = cpu_to_le32(pno->fast_scan_period);
10499	cmd->slow_scan_period = cpu_to_le32(pno->slow_scan_period);
10500	cmd->fast_scan_max_cycles = cpu_to_le32(pno->fast_scan_max_cycles);
10501	cmd->delay_start_time = cpu_to_le32(pno->delay_start_time);
10502
10503	if (pno->enable_pno_scan_randomization) {
10504		cmd->flags |= cpu_to_le32(WMI_NLO_CONFIG_SPOOFED_MAC_IN_PROBE_REQ |
10505					  WMI_NLO_CONFIG_RANDOM_SEQ_NO_IN_PROBE_REQ);
10506		ether_addr_copy(cmd->mac_addr.addr, pno->mac_addr);
10507		ether_addr_copy(cmd->mac_mask.addr, pno->mac_addr_mask);
10508	}
10509
10510	ptr += sizeof(*cmd);
10511
10512	/* nlo_configured_params(nlo_list) */
10513	cmd->no_of_ssids = cpu_to_le32(pno->uc_networks_count);
10514	tlv = ptr;
10515	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, nlo_list_len);
10516
10517	ptr += sizeof(*tlv);
10518	nlo_list = ptr;
10519	for (i = 0; i < pno->uc_networks_count; i++) {
10520		tlv = (struct wmi_tlv *)(&nlo_list[i].tlv_header);
10521		tlv->header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_ARRAY_BYTE,
10522						     sizeof(*nlo_list));
10523
10524		nlo_list[i].ssid.valid = cpu_to_le32(1);
10525		nlo_list[i].ssid.ssid.ssid_len =
10526			cpu_to_le32(pno->a_networks[i].ssid.ssid_len);
10527		memcpy(nlo_list[i].ssid.ssid.ssid,
10528		       pno->a_networks[i].ssid.ssid,
10529		       le32_to_cpu(nlo_list[i].ssid.ssid.ssid_len));
10530
10531		if (pno->a_networks[i].rssi_threshold &&
10532		    pno->a_networks[i].rssi_threshold > -300) {
10533			nlo_list[i].rssi_cond.valid = cpu_to_le32(1);
10534			nlo_list[i].rssi_cond.rssi =
10535					cpu_to_le32(pno->a_networks[i].rssi_threshold);
10536		}
10537
10538		nlo_list[i].bcast_nw_type.valid = cpu_to_le32(1);
10539		nlo_list[i].bcast_nw_type.bcast_nw_type =
10540					cpu_to_le32(pno->a_networks[i].bcast_nw_type);
10541	}
10542
10543	ptr += nlo_list_len;
10544	cmd->num_of_channels = cpu_to_le32(pno->a_networks[0].channel_count);
10545	tlv = ptr;
10546	tlv->header =  ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, channel_list_len);
10547	ptr += sizeof(*tlv);
10548	channel_list = ptr;
10549
10550	for (i = 0; i < pno->a_networks[0].channel_count; i++)
10551		channel_list[i] = cpu_to_le32(pno->a_networks[0].channels[i]);
10552
10553	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "wmi tlv start pno config vdev_id %d\n",
10554		   vdev_id);
10555
10556	return skb;
10557}
10558
10559static struct sk_buff *ath12k_wmi_op_gen_config_pno_stop(struct ath12k *ar,
10560							 u32 vdev_id)
10561{
10562	struct wmi_wow_nlo_config_cmd *cmd;
10563	struct sk_buff *skb;
10564	size_t len;
10565
10566	len = sizeof(*cmd);
10567	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10568	if (!skb)
10569		return ERR_PTR(-ENOMEM);
10570
10571	cmd = (struct wmi_wow_nlo_config_cmd *)skb->data;
10572	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_NLO_CONFIG_CMD, len);
10573
10574	cmd->vdev_id = cpu_to_le32(vdev_id);
10575	cmd->flags = cpu_to_le32(WMI_NLO_CONFIG_STOP);
10576
10577	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
10578		   "wmi tlv stop pno config vdev_id %d\n", vdev_id);
10579	return skb;
10580}
10581
10582int ath12k_wmi_wow_config_pno(struct ath12k *ar, u32 vdev_id,
10583			      struct wmi_pno_scan_req_arg  *pno_scan)
10584{
10585	struct sk_buff *skb;
10586
10587	if (pno_scan->enable)
10588		skb = ath12k_wmi_op_gen_config_pno_start(ar, vdev_id, pno_scan);
10589	else
10590		skb = ath12k_wmi_op_gen_config_pno_stop(ar, vdev_id);
10591
10592	if (IS_ERR_OR_NULL(skb))
10593		return -ENOMEM;
10594
10595	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_NETWORK_LIST_OFFLOAD_CONFIG_CMDID);
10596}
10597
10598static void ath12k_wmi_fill_ns_offload(struct ath12k *ar,
10599				       struct wmi_arp_ns_offload_arg *offload,
10600				       void **ptr,
10601				       bool enable,
10602				       bool ext)
10603{
10604	struct wmi_ns_offload_params *ns;
10605	struct wmi_tlv *tlv;
10606	void *buf_ptr = *ptr;
10607	u32 ns_cnt, ns_ext_tuples;
10608	int i, max_offloads;
10609
10610	ns_cnt = offload->ipv6_count;
10611
10612	tlv  = buf_ptr;
10613
10614	if (ext) {
10615		ns_ext_tuples = offload->ipv6_count - WMI_MAX_NS_OFFLOADS;
10616		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
10617						 ns_ext_tuples * sizeof(*ns));
10618		i = WMI_MAX_NS_OFFLOADS;
10619		max_offloads = offload->ipv6_count;
10620	} else {
10621		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
10622						 WMI_MAX_NS_OFFLOADS * sizeof(*ns));
10623		i = 0;
10624		max_offloads = WMI_MAX_NS_OFFLOADS;
10625	}
10626
10627	buf_ptr += sizeof(*tlv);
10628
10629	for (; i < max_offloads; i++) {
10630		ns = buf_ptr;
10631		ns->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_NS_OFFLOAD_TUPLE,
10632							sizeof(*ns));
10633
10634		if (enable) {
10635			if (i < ns_cnt)
10636				ns->flags |= cpu_to_le32(WMI_NSOL_FLAGS_VALID);
10637
10638			memcpy(ns->target_ipaddr[0], offload->ipv6_addr[i], 16);
10639			memcpy(ns->solicitation_ipaddr, offload->self_ipv6_addr[i], 16);
10640
10641			if (offload->ipv6_type[i])
10642				ns->flags |= cpu_to_le32(WMI_NSOL_FLAGS_IS_IPV6_ANYCAST);
10643
10644			memcpy(ns->target_mac.addr, offload->mac_addr, ETH_ALEN);
10645
10646			if (!is_zero_ether_addr(ns->target_mac.addr))
10647				ns->flags |= cpu_to_le32(WMI_NSOL_FLAGS_MAC_VALID);
10648
10649			ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
10650				   "wmi index %d ns_solicited %pI6 target %pI6",
10651				   i, ns->solicitation_ipaddr,
10652				   ns->target_ipaddr[0]);
10653		}
10654
10655		buf_ptr += sizeof(*ns);
10656	}
10657
10658	*ptr = buf_ptr;
10659}
10660
10661static void ath12k_wmi_fill_arp_offload(struct ath12k *ar,
10662					struct wmi_arp_ns_offload_arg *offload,
10663					void **ptr,
10664					bool enable)
10665{
10666	struct wmi_arp_offload_params *arp;
10667	struct wmi_tlv *tlv;
10668	void *buf_ptr = *ptr;
10669	int i;
10670
10671	/* fill arp tuple */
10672	tlv = buf_ptr;
10673	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
10674					 WMI_MAX_ARP_OFFLOADS * sizeof(*arp));
10675	buf_ptr += sizeof(*tlv);
10676
10677	for (i = 0; i < WMI_MAX_ARP_OFFLOADS; i++) {
10678		arp = buf_ptr;
10679		arp->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_ARP_OFFLOAD_TUPLE,
10680							 sizeof(*arp));
10681
10682		if (enable && i < offload->ipv4_count) {
10683			/* Copy the target ip addr and flags */
10684			arp->flags = cpu_to_le32(WMI_ARPOL_FLAGS_VALID);
10685			memcpy(arp->target_ipaddr, offload->ipv4_addr[i], 4);
10686
10687			ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "wmi arp offload address %pI4",
10688				   arp->target_ipaddr);
10689		}
10690
10691		buf_ptr += sizeof(*arp);
10692	}
10693
10694	*ptr = buf_ptr;
10695}
10696
10697int ath12k_wmi_arp_ns_offload(struct ath12k *ar,
10698			      struct ath12k_link_vif *arvif,
10699			      struct wmi_arp_ns_offload_arg *offload,
10700			      bool enable)
10701{
10702	struct wmi_set_arp_ns_offload_cmd *cmd;
10703	struct wmi_tlv *tlv;
10704	struct sk_buff *skb;
10705	void *buf_ptr;
10706	size_t len;
10707	u8 ns_cnt, ns_ext_tuples = 0;
10708
10709	ns_cnt = offload->ipv6_count;
10710
10711	len = sizeof(*cmd) +
10712	      sizeof(*tlv) +
10713	      WMI_MAX_NS_OFFLOADS * sizeof(struct wmi_ns_offload_params) +
10714	      sizeof(*tlv) +
10715	      WMI_MAX_ARP_OFFLOADS * sizeof(struct wmi_arp_offload_params);
10716
10717	if (ns_cnt > WMI_MAX_NS_OFFLOADS) {
10718		ns_ext_tuples = ns_cnt - WMI_MAX_NS_OFFLOADS;
10719		len += sizeof(*tlv) +
10720		       ns_ext_tuples * sizeof(struct wmi_ns_offload_params);
10721	}
10722
10723	skb = ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10724	if (!skb)
10725		return -ENOMEM;
10726
10727	buf_ptr = skb->data;
10728	cmd = buf_ptr;
10729	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_SET_ARP_NS_OFFLOAD_CMD,
10730						 sizeof(*cmd));
10731	cmd->flags = cpu_to_le32(0);
10732	cmd->vdev_id = cpu_to_le32(arvif->vdev_id);
10733	cmd->num_ns_ext_tuples = cpu_to_le32(ns_ext_tuples);
10734
10735	buf_ptr += sizeof(*cmd);
10736
10737	ath12k_wmi_fill_ns_offload(ar, offload, &buf_ptr, enable, 0);
10738	ath12k_wmi_fill_arp_offload(ar, offload, &buf_ptr, enable);
10739
10740	if (ns_ext_tuples)
10741		ath12k_wmi_fill_ns_offload(ar, offload, &buf_ptr, enable, 1);
10742
10743	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_SET_ARP_NS_OFFLOAD_CMDID);
10744}
10745
10746int ath12k_wmi_gtk_rekey_offload(struct ath12k *ar,
10747				 struct ath12k_link_vif *arvif, bool enable)
10748{
10749	struct ath12k_rekey_data *rekey_data = &arvif->rekey_data;
10750	struct wmi_gtk_rekey_offload_cmd *cmd;
10751	struct sk_buff *skb;
10752	__le64 replay_ctr;
10753	int len;
10754
10755	len = sizeof(*cmd);
10756	skb =  ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10757	if (!skb)
10758		return -ENOMEM;
10759
10760	cmd = (struct wmi_gtk_rekey_offload_cmd *)skb->data;
10761	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_GTK_OFFLOAD_CMD, sizeof(*cmd));
10762	cmd->vdev_id = cpu_to_le32(arvif->vdev_id);
10763
10764	if (enable) {
10765		cmd->flags = cpu_to_le32(GTK_OFFLOAD_ENABLE_OPCODE);
10766
10767		/* the length in rekey_data and cmd is equal */
10768		memcpy(cmd->kck, rekey_data->kck, sizeof(cmd->kck));
10769		memcpy(cmd->kek, rekey_data->kek, sizeof(cmd->kek));
10770
10771		replay_ctr = cpu_to_le64(rekey_data->replay_ctr);
10772		memcpy(cmd->replay_ctr, &replay_ctr,
10773		       sizeof(replay_ctr));
10774	} else {
10775		cmd->flags = cpu_to_le32(GTK_OFFLOAD_DISABLE_OPCODE);
10776	}
10777
10778	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "offload gtk rekey vdev: %d %d\n",
10779		   arvif->vdev_id, enable);
10780	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_GTK_OFFLOAD_CMDID);
10781}
10782
10783int ath12k_wmi_gtk_rekey_getinfo(struct ath12k *ar,
10784				 struct ath12k_link_vif *arvif)
10785{
10786	struct wmi_gtk_rekey_offload_cmd *cmd;
10787	struct sk_buff *skb;
10788	int len;
10789
10790	len = sizeof(*cmd);
10791	skb =  ath12k_wmi_alloc_skb(ar->wmi->wmi_ab, len);
10792	if (!skb)
10793		return -ENOMEM;
10794
10795	cmd = (struct wmi_gtk_rekey_offload_cmd *)skb->data;
10796	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_GTK_OFFLOAD_CMD, sizeof(*cmd));
10797	cmd->vdev_id = cpu_to_le32(arvif->vdev_id);
10798	cmd->flags = cpu_to_le32(GTK_OFFLOAD_REQUEST_STATUS_OPCODE);
10799
10800	ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "get gtk rekey vdev_id: %d\n",
10801		   arvif->vdev_id);
10802	return ath12k_wmi_cmd_send(ar->wmi, skb, WMI_GTK_OFFLOAD_CMDID);
10803}
10804
10805int ath12k_wmi_sta_keepalive(struct ath12k *ar,
10806			     const struct wmi_sta_keepalive_arg *arg)
10807{
10808	struct wmi_sta_keepalive_arp_resp_params *arp;
10809	struct ath12k_wmi_pdev *wmi = ar->wmi;
10810	struct wmi_sta_keepalive_cmd *cmd;
10811	struct sk_buff *skb;
10812	size_t len;
10813
10814	len = sizeof(*cmd) + sizeof(*arp);
10815	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
10816	if (!skb)
10817		return -ENOMEM;
10818
10819	cmd = (struct wmi_sta_keepalive_cmd *)skb->data;
10820	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_STA_KEEPALIVE_CMD, sizeof(*cmd));
10821	cmd->vdev_id = cpu_to_le32(arg->vdev_id);
10822	cmd->enabled = cpu_to_le32(arg->enabled);
10823	cmd->interval = cpu_to_le32(arg->interval);
10824	cmd->method = cpu_to_le32(arg->method);
10825
10826	arp = (struct wmi_sta_keepalive_arp_resp_params *)(cmd + 1);
10827	arp->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_STA_KEEPALVE_ARP_RESPONSE,
10828						 sizeof(*arp));
10829	if (arg->method == WMI_STA_KEEPALIVE_METHOD_UNSOLICITED_ARP_RESPONSE ||
10830	    arg->method == WMI_STA_KEEPALIVE_METHOD_GRATUITOUS_ARP_REQUEST) {
10831		arp->src_ip4_addr = cpu_to_le32(arg->src_ip4_addr);
10832		arp->dest_ip4_addr = cpu_to_le32(arg->dest_ip4_addr);
10833		ether_addr_copy(arp->dest_mac_addr.addr, arg->dest_mac_addr);
10834	}
10835
10836	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
10837		   "wmi sta keepalive vdev %d enabled %d method %d interval %d\n",
10838		   arg->vdev_id, arg->enabled, arg->method, arg->interval);
10839
10840	return ath12k_wmi_cmd_send(wmi, skb, WMI_STA_KEEPALIVE_CMDID);
10841}
10842
10843int ath12k_wmi_mlo_setup(struct ath12k *ar, struct wmi_mlo_setup_arg *mlo_params)
10844{
10845	struct wmi_mlo_setup_cmd *cmd;
10846	struct ath12k_wmi_pdev *wmi = ar->wmi;
10847	u32 *partner_links, num_links;
10848	int i, ret, buf_len, arg_len;
10849	struct sk_buff *skb;
10850	struct wmi_tlv *tlv;
10851	void *ptr;
10852
10853	num_links = mlo_params->num_partner_links;
10854	arg_len = num_links * sizeof(u32);
10855	buf_len = sizeof(*cmd) + TLV_HDR_SIZE + arg_len;
10856
10857	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, buf_len);
10858	if (!skb)
10859		return -ENOMEM;
10860
10861	cmd = (struct wmi_mlo_setup_cmd *)skb->data;
10862	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_SETUP_CMD,
10863						 sizeof(*cmd));
10864	cmd->mld_group_id = mlo_params->group_id;
10865	cmd->pdev_id = cpu_to_le32(ar->pdev->pdev_id);
10866	ptr = skb->data + sizeof(*cmd);
10867
10868	tlv = ptr;
10869	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, arg_len);
10870	ptr += TLV_HDR_SIZE;
10871
10872	partner_links = ptr;
10873	for (i = 0; i < num_links; i++)
10874		partner_links[i] = mlo_params->partner_link_id[i];
10875
10876	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_MLO_SETUP_CMDID);
10877	if (ret) {
10878		ath12k_warn(ar->ab, "failed to submit WMI_MLO_SETUP_CMDID command: %d\n",
10879			    ret);
10880		dev_kfree_skb(skb);
10881		return ret;
10882	}
10883
10884	return 0;
10885}
10886
10887int ath12k_wmi_mlo_ready(struct ath12k *ar)
10888{
10889	struct wmi_mlo_ready_cmd *cmd;
10890	struct ath12k_wmi_pdev *wmi = ar->wmi;
10891	struct sk_buff *skb;
10892	int ret, len;
10893
10894	len = sizeof(*cmd);
10895	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
10896	if (!skb)
10897		return -ENOMEM;
10898
10899	cmd = (struct wmi_mlo_ready_cmd *)skb->data;
10900	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_READY_CMD,
10901						 sizeof(*cmd));
10902	cmd->pdev_id = cpu_to_le32(ar->pdev->pdev_id);
10903
10904	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_MLO_READY_CMDID);
10905	if (ret) {
10906		ath12k_warn(ar->ab, "failed to submit WMI_MLO_READY_CMDID command: %d\n",
10907			    ret);
10908		dev_kfree_skb(skb);
10909		return ret;
10910	}
10911
10912	return 0;
10913}
10914
10915int ath12k_wmi_mlo_teardown(struct ath12k *ar)
10916{
10917	struct wmi_mlo_teardown_cmd *cmd;
10918	struct ath12k_wmi_pdev *wmi = ar->wmi;
10919	struct sk_buff *skb;
10920	int ret, len;
10921
10922	len = sizeof(*cmd);
10923	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
10924	if (!skb)
10925		return -ENOMEM;
10926
10927	cmd = (struct wmi_mlo_teardown_cmd *)skb->data;
10928	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_TEARDOWN_CMD,
10929						 sizeof(*cmd));
10930	cmd->pdev_id = cpu_to_le32(ar->pdev->pdev_id);
10931	cmd->reason_code = WMI_MLO_TEARDOWN_SSR_REASON;
10932
10933	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_MLO_TEARDOWN_CMDID);
10934	if (ret) {
10935		ath12k_warn(ar->ab, "failed to submit WMI MLO teardown command: %d\n",
10936			    ret);
10937		dev_kfree_skb(skb);
10938		return ret;
10939	}
10940
10941	return 0;
10942}
10943
10944bool ath12k_wmi_supports_6ghz_cc_ext(struct ath12k *ar)
10945{
10946	return test_bit(WMI_TLV_SERVICE_REG_CC_EXT_EVENT_SUPPORT,
10947			ar->ab->wmi_ab.svc_map) && ar->supports_6ghz;
10948}
10949
10950int ath12k_wmi_send_vdev_set_tpc_power(struct ath12k *ar,
10951				       u32 vdev_id,
10952				       struct ath12k_reg_tpc_power_info *param)
10953{
10954	struct wmi_vdev_set_tpc_power_cmd *cmd;
10955	struct ath12k_wmi_pdev *wmi = ar->wmi;
10956	struct wmi_vdev_ch_power_params *ch;
10957	int i, ret, len, array_len;
10958	struct sk_buff *skb;
10959	struct wmi_tlv *tlv;
10960	u8 *ptr;
10961
10962	array_len = sizeof(*ch) * param->num_pwr_levels;
10963	len = sizeof(*cmd) + TLV_HDR_SIZE + array_len;
10964
10965	skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
10966	if (!skb)
10967		return -ENOMEM;
10968
10969	ptr = skb->data;
10970
10971	cmd = (struct wmi_vdev_set_tpc_power_cmd *)ptr;
10972	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_SET_TPC_POWER_CMD,
10973						 sizeof(*cmd));
10974	cmd->vdev_id = cpu_to_le32(vdev_id);
10975	cmd->psd_power = cpu_to_le32(param->is_psd_power);
10976	cmd->eirp_power = cpu_to_le32(param->eirp_power);
10977	cmd->power_type_6ghz = cpu_to_le32(param->ap_power_type);
10978
10979	ath12k_dbg(ar->ab, ATH12K_DBG_WMI,
10980		   "tpc vdev id %d is psd power %d eirp power %d 6 ghz power type %d\n",
10981		   vdev_id, param->is_psd_power, param->eirp_power, param->ap_power_type);
10982
10983	ptr += sizeof(*cmd);
10984	tlv = (struct wmi_tlv *)ptr;
10985	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT, array_len);
10986
10987	ptr += TLV_HDR_SIZE;
10988	ch = (struct wmi_vdev_ch_power_params *)ptr;
10989
10990	for (i = 0; i < param->num_pwr_levels; i++, ch++) {
10991		ch->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_VDEV_CH_POWER_INFO,
10992							sizeof(*ch));
10993		ch->chan_cfreq = cpu_to_le32(param->chan_power_info[i].chan_cfreq);
10994		ch->tx_power = cpu_to_le32(param->chan_power_info[i].tx_power);
10995
10996		ath12k_dbg(ar->ab, ATH12K_DBG_WMI, "tpc chan freq %d TX power %d\n",
10997			   ch->chan_cfreq, ch->tx_power);
10998	}
10999
11000	ret = ath12k_wmi_cmd_send(wmi, skb, WMI_VDEV_SET_TPC_POWER_CMDID);
11001	if (ret) {
11002		ath12k_warn(ar->ab, "failed to send WMI_VDEV_SET_TPC_POWER_CMDID\n");
11003		dev_kfree_skb(skb);
11004		return ret;
11005	}
11006
11007	return 0;
11008}
11009
11010static int
11011ath12k_wmi_fill_disallowed_bmap(struct ath12k_base *ab,
11012				struct wmi_disallowed_mlo_mode_bitmap_params *dislw_bmap,
11013				struct wmi_mlo_link_set_active_arg *arg)
11014{
11015	struct wmi_ml_disallow_mode_bmap_arg *dislw_bmap_arg;
11016	u8 i;
11017
11018	if (arg->num_disallow_mode_comb >
11019	    ARRAY_SIZE(arg->disallow_bmap)) {
11020		ath12k_warn(ab, "invalid num_disallow_mode_comb: %d",
11021			    arg->num_disallow_mode_comb);
11022		return -EINVAL;
11023	}
11024
11025	dislw_bmap_arg = &arg->disallow_bmap[0];
11026	for (i = 0; i < arg->num_disallow_mode_comb; i++) {
11027		dislw_bmap->tlv_header =
11028				ath12k_wmi_tlv_cmd_hdr(0, sizeof(*dislw_bmap));
11029		dislw_bmap->disallowed_mode_bitmap =
11030				cpu_to_le32(dislw_bmap_arg->disallowed_mode);
11031		dislw_bmap->ieee_link_id_comb =
11032			le32_encode_bits(dislw_bmap_arg->ieee_link_id[0],
11033					 WMI_DISALW_MLO_MODE_BMAP_IEEE_LINK_ID_COMB_1) |
11034			le32_encode_bits(dislw_bmap_arg->ieee_link_id[1],
11035					 WMI_DISALW_MLO_MODE_BMAP_IEEE_LINK_ID_COMB_2) |
11036			le32_encode_bits(dislw_bmap_arg->ieee_link_id[2],
11037					 WMI_DISALW_MLO_MODE_BMAP_IEEE_LINK_ID_COMB_3) |
11038			le32_encode_bits(dislw_bmap_arg->ieee_link_id[3],
11039					 WMI_DISALW_MLO_MODE_BMAP_IEEE_LINK_ID_COMB_4);
11040
11041		ath12k_dbg(ab, ATH12K_DBG_WMI,
11042			   "entry %d disallowed_mode %d ieee_link_id_comb 0x%x",
11043			   i, dislw_bmap_arg->disallowed_mode,
11044			   dislw_bmap_arg->ieee_link_id_comb);
11045		dislw_bmap++;
11046		dislw_bmap_arg++;
11047	}
11048
11049	return 0;
11050}
11051
11052int ath12k_wmi_send_mlo_link_set_active_cmd(struct ath12k_base *ab,
11053					    struct wmi_mlo_link_set_active_arg *arg)
11054{
11055	struct wmi_disallowed_mlo_mode_bitmap_params *disallowed_mode_bmap;
11056	struct wmi_mlo_set_active_link_number_params *link_num_param;
11057	u32 num_link_num_param = 0, num_vdev_bitmap = 0;
11058	struct ath12k_wmi_base *wmi_ab = &ab->wmi_ab;
11059	struct wmi_mlo_link_set_active_cmd *cmd;
11060	u32 num_inactive_vdev_bitmap = 0;
11061	u32 num_disallow_mode_comb = 0;
11062	struct wmi_tlv *tlv;
11063	struct sk_buff *skb;
11064	__le32 *vdev_bitmap;
11065	void *buf_ptr;
11066	int i, ret;
11067	u32 len;
11068
11069	if (!arg->num_vdev_bitmap && !arg->num_link_entry) {
11070		ath12k_warn(ab, "Invalid num_vdev_bitmap and num_link_entry");
11071		return -EINVAL;
11072	}
11073
11074	switch (arg->force_mode) {
11075	case WMI_MLO_LINK_FORCE_MODE_ACTIVE_LINK_NUM:
11076	case WMI_MLO_LINK_FORCE_MODE_INACTIVE_LINK_NUM:
11077		num_link_num_param = arg->num_link_entry;
11078		fallthrough;
11079	case WMI_MLO_LINK_FORCE_MODE_ACTIVE:
11080	case WMI_MLO_LINK_FORCE_MODE_INACTIVE:
11081	case WMI_MLO_LINK_FORCE_MODE_NO_FORCE:
11082		num_vdev_bitmap = arg->num_vdev_bitmap;
11083		break;
11084	case WMI_MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE:
11085		num_vdev_bitmap = arg->num_vdev_bitmap;
11086		num_inactive_vdev_bitmap = arg->num_inactive_vdev_bitmap;
11087		break;
11088	default:
11089		ath12k_warn(ab, "Invalid force mode: %u", arg->force_mode);
11090		return -EINVAL;
11091	}
11092
11093	num_disallow_mode_comb = arg->num_disallow_mode_comb;
11094	len = sizeof(*cmd) +
11095	      TLV_HDR_SIZE + sizeof(*link_num_param) * num_link_num_param +
11096	      TLV_HDR_SIZE + sizeof(*vdev_bitmap) * num_vdev_bitmap +
11097	      TLV_HDR_SIZE + TLV_HDR_SIZE + TLV_HDR_SIZE +
11098	      TLV_HDR_SIZE + sizeof(*disallowed_mode_bmap) * num_disallow_mode_comb;
11099	if (arg->force_mode == WMI_MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE)
11100		len += sizeof(*vdev_bitmap) * num_inactive_vdev_bitmap;
11101
11102	skb = ath12k_wmi_alloc_skb(wmi_ab, len);
11103	if (!skb)
11104		return -ENOMEM;
11105
11106	cmd = (struct wmi_mlo_link_set_active_cmd *)skb->data;
11107	cmd->tlv_header = ath12k_wmi_tlv_cmd_hdr(WMI_TAG_MLO_LINK_SET_ACTIVE_CMD,
11108						 sizeof(*cmd));
11109	cmd->force_mode = cpu_to_le32(arg->force_mode);
11110	cmd->reason = cpu_to_le32(arg->reason);
11111	ath12k_dbg(ab, ATH12K_DBG_WMI,
11112		   "mode %d reason %d num_link_num_param %d num_vdev_bitmap %d inactive %d num_disallow_mode_comb %d",
11113		   arg->force_mode, arg->reason, num_link_num_param,
11114		   num_vdev_bitmap, num_inactive_vdev_bitmap,
11115		   num_disallow_mode_comb);
11116
11117	buf_ptr = skb->data + sizeof(*cmd);
11118	tlv = buf_ptr;
11119	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
11120					 sizeof(*link_num_param) * num_link_num_param);
11121	buf_ptr += TLV_HDR_SIZE;
11122
11123	if (num_link_num_param) {
11124		cmd->ctrl_flags =
11125			le32_encode_bits(arg->ctrl_flags.dync_force_link_num ? 1 : 0,
11126					 CRTL_F_DYNC_FORCE_LINK_NUM);
11127
11128		link_num_param = buf_ptr;
11129		for (i = 0; i < num_link_num_param; i++) {
11130			link_num_param->tlv_header =
11131				ath12k_wmi_tlv_cmd_hdr(0, sizeof(*link_num_param));
11132			link_num_param->num_of_link =
11133				cpu_to_le32(arg->link_num[i].num_of_link);
11134			link_num_param->vdev_type =
11135				cpu_to_le32(arg->link_num[i].vdev_type);
11136			link_num_param->vdev_subtype =
11137				cpu_to_le32(arg->link_num[i].vdev_subtype);
11138			link_num_param->home_freq =
11139				cpu_to_le32(arg->link_num[i].home_freq);
11140			ath12k_dbg(ab, ATH12K_DBG_WMI,
11141				   "entry %d num_of_link %d vdev type %d subtype %d freq %d control_flags %d",
11142				   i, arg->link_num[i].num_of_link,
11143				   arg->link_num[i].vdev_type,
11144				   arg->link_num[i].vdev_subtype,
11145				   arg->link_num[i].home_freq,
11146				   __le32_to_cpu(cmd->ctrl_flags));
11147			link_num_param++;
11148		}
11149
11150		buf_ptr += sizeof(*link_num_param) * num_link_num_param;
11151	}
11152
11153	tlv = buf_ptr;
11154	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32,
11155					 sizeof(*vdev_bitmap) * num_vdev_bitmap);
11156	buf_ptr += TLV_HDR_SIZE;
11157
11158	if (num_vdev_bitmap) {
11159		vdev_bitmap = buf_ptr;
11160		for (i = 0; i < num_vdev_bitmap; i++) {
11161			vdev_bitmap[i] = cpu_to_le32(arg->vdev_bitmap[i]);
11162			ath12k_dbg(ab, ATH12K_DBG_WMI, "entry %d vdev_id_bitmap 0x%x",
11163				   i, arg->vdev_bitmap[i]);
11164		}
11165
11166		buf_ptr += sizeof(*vdev_bitmap) * num_vdev_bitmap;
11167	}
11168
11169	if (arg->force_mode == WMI_MLO_LINK_FORCE_MODE_ACTIVE_INACTIVE) {
11170		tlv = buf_ptr;
11171		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32,
11172						 sizeof(*vdev_bitmap) *
11173						 num_inactive_vdev_bitmap);
11174		buf_ptr += TLV_HDR_SIZE;
11175
11176		if (num_inactive_vdev_bitmap) {
11177			vdev_bitmap = buf_ptr;
11178			for (i = 0; i < num_inactive_vdev_bitmap; i++) {
11179				vdev_bitmap[i] =
11180					cpu_to_le32(arg->inactive_vdev_bitmap[i]);
11181				ath12k_dbg(ab, ATH12K_DBG_WMI,
11182					   "entry %d inactive_vdev_id_bitmap 0x%x",
11183					    i, arg->inactive_vdev_bitmap[i]);
11184			}
11185
11186			buf_ptr += sizeof(*vdev_bitmap) * num_inactive_vdev_bitmap;
11187		}
11188	} else {
11189		/* add empty vdev bitmap2 tlv */
11190		tlv = buf_ptr;
11191		tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, 0);
11192		buf_ptr += TLV_HDR_SIZE;
11193	}
11194
11195	/* add empty ieee_link_id_bitmap tlv */
11196	tlv = buf_ptr;
11197	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, 0);
11198	buf_ptr += TLV_HDR_SIZE;
11199
11200	/* add empty ieee_link_id_bitmap2 tlv */
11201	tlv = buf_ptr;
11202	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_UINT32, 0);
11203	buf_ptr += TLV_HDR_SIZE;
11204
11205	tlv = buf_ptr;
11206	tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_STRUCT,
11207					 sizeof(*disallowed_mode_bmap) *
11208					 arg->num_disallow_mode_comb);
11209	buf_ptr += TLV_HDR_SIZE;
11210
11211	ret = ath12k_wmi_fill_disallowed_bmap(ab, buf_ptr, arg);
11212	if (ret)
11213		goto free_skb;
11214
11215	ret = ath12k_wmi_cmd_send(&wmi_ab->wmi[0], skb, WMI_MLO_LINK_SET_ACTIVE_CMDID);
11216	if (ret) {
11217		ath12k_warn(ab,
11218			    "failed to send WMI_MLO_LINK_SET_ACTIVE_CMDID: %d\n", ret);
11219		goto free_skb;
11220	}
11221
11222	ath12k_dbg(ab, ATH12K_DBG_WMI, "WMI mlo link set active cmd");
11223
11224	return ret;
11225
11226free_skb:
11227	dev_kfree_skb(skb);
11228	return ret;
11229}
~/ Read-only file preview.