1 // SPDX-License-Identifier: BSD-3-Clause-Clear 2 /* 3 * Copyright (c) 2018-2019 The Linux Foundation. All rights reserved. 4 */ 5 #include <linux/skbuff.h> 6 #include <linux/ctype.h> 7 #include <net/mac80211.h> 8 #include <net/cfg80211.h> 9 #include <linux/completion.h> 10 #include <linux/if_ether.h> 11 #include <linux/types.h> 12 #include <linux/pci.h> 13 #include <linux/uuid.h> 14 #include <linux/time.h> 15 #include <linux/of.h> 16 #include "core.h" 17 #include "debug.h" 18 #include "mac.h" 19 #include "hw.h" 20 #include "peer.h" 21 22 struct wmi_tlv_policy { 23 size_t min_len; 24 }; 25 26 struct wmi_tlv_svc_ready_parse { 27 bool wmi_svc_bitmap_done; 28 }; 29 30 struct wmi_tlv_dma_ring_caps_parse { 31 struct wmi_dma_ring_capabilities *dma_ring_caps; 32 u32 n_dma_ring_caps; 33 }; 34 35 struct wmi_tlv_svc_rdy_ext_parse { 36 struct ath11k_service_ext_param param; 37 struct wmi_soc_mac_phy_hw_mode_caps *hw_caps; 38 struct wmi_hw_mode_capabilities *hw_mode_caps; 39 u32 n_hw_mode_caps; 40 u32 tot_phy_id; 41 struct wmi_hw_mode_capabilities pref_hw_mode_caps; 42 struct wmi_mac_phy_capabilities *mac_phy_caps; 43 u32 n_mac_phy_caps; 44 struct wmi_soc_hal_reg_capabilities *soc_hal_reg_caps; 45 struct wmi_hal_reg_capabilities_ext *ext_hal_reg_caps; 46 u32 n_ext_hal_reg_caps; 47 struct wmi_tlv_dma_ring_caps_parse dma_caps_parse; 48 bool hw_mode_done; 49 bool mac_phy_done; 50 bool ext_hal_reg_done; 51 bool mac_phy_chainmask_combo_done; 52 bool mac_phy_chainmask_cap_done; 53 bool oem_dma_ring_cap_done; 54 bool dma_ring_cap_done; 55 }; 56 57 struct wmi_tlv_svc_rdy_ext2_parse { 58 struct wmi_tlv_dma_ring_caps_parse dma_caps_parse; 59 bool dma_ring_cap_done; 60 }; 61 62 struct wmi_tlv_rdy_parse { 63 u32 num_extra_mac_addr; 64 }; 65 66 struct wmi_tlv_dma_buf_release_parse { 67 struct ath11k_wmi_dma_buf_release_fixed_param fixed; 68 struct wmi_dma_buf_release_entry *buf_entry; 69 struct wmi_dma_buf_release_meta_data *meta_data; 70 u32 num_buf_entry; 71 u32 num_meta; 72 bool buf_entry_done; 73 bool meta_data_done; 74 }; 75 76 struct wmi_tlv_fw_stats_parse { 77 const struct wmi_stats_event *ev; 78 const struct wmi_per_chain_rssi_stats *rssi; 79 struct ath11k_fw_stats *stats; 80 int rssi_num; 81 bool chain_rssi_done; 82 }; 83 84 static const struct wmi_tlv_policy wmi_tlv_policies[] = { 85 [WMI_TAG_ARRAY_BYTE] 86 = { .min_len = 0 }, 87 [WMI_TAG_ARRAY_UINT32] 88 = { .min_len = 0 }, 89 [WMI_TAG_SERVICE_READY_EVENT] 90 = { .min_len = sizeof(struct wmi_service_ready_event) }, 91 [WMI_TAG_SERVICE_READY_EXT_EVENT] 92 = { .min_len = sizeof(struct wmi_service_ready_ext_event) }, 93 [WMI_TAG_SOC_MAC_PHY_HW_MODE_CAPS] 94 = { .min_len = sizeof(struct wmi_soc_mac_phy_hw_mode_caps) }, 95 [WMI_TAG_SOC_HAL_REG_CAPABILITIES] 96 = { .min_len = sizeof(struct wmi_soc_hal_reg_capabilities) }, 97 [WMI_TAG_VDEV_START_RESPONSE_EVENT] 98 = { .min_len = sizeof(struct wmi_vdev_start_resp_event) }, 99 [WMI_TAG_PEER_DELETE_RESP_EVENT] 100 = { .min_len = sizeof(struct wmi_peer_delete_resp_event) }, 101 [WMI_TAG_OFFLOAD_BCN_TX_STATUS_EVENT] 102 = { .min_len = sizeof(struct wmi_bcn_tx_status_event) }, 103 [WMI_TAG_VDEV_STOPPED_EVENT] 104 = { .min_len = sizeof(struct wmi_vdev_stopped_event) }, 105 [WMI_TAG_REG_CHAN_LIST_CC_EVENT] 106 = { .min_len = sizeof(struct wmi_reg_chan_list_cc_event) }, 107 [WMI_TAG_MGMT_RX_HDR] 108 = { .min_len = sizeof(struct wmi_mgmt_rx_hdr) }, 109 [WMI_TAG_MGMT_TX_COMPL_EVENT] 110 = { .min_len = sizeof(struct wmi_mgmt_tx_compl_event) }, 111 [WMI_TAG_SCAN_EVENT] 112 = { .min_len = sizeof(struct wmi_scan_event) }, 113 [WMI_TAG_PEER_STA_KICKOUT_EVENT] 114 = { .min_len = sizeof(struct wmi_peer_sta_kickout_event) }, 115 [WMI_TAG_ROAM_EVENT] 116 = { .min_len = sizeof(struct wmi_roam_event) }, 117 [WMI_TAG_CHAN_INFO_EVENT] 118 = { .min_len = sizeof(struct wmi_chan_info_event) }, 119 [WMI_TAG_PDEV_BSS_CHAN_INFO_EVENT] 120 = { .min_len = sizeof(struct wmi_pdev_bss_chan_info_event) }, 121 [WMI_TAG_VDEV_INSTALL_KEY_COMPLETE_EVENT] 122 = { .min_len = sizeof(struct wmi_vdev_install_key_compl_event) }, 123 [WMI_TAG_READY_EVENT] = { 124 .min_len = sizeof(struct wmi_ready_event_min) }, 125 [WMI_TAG_SERVICE_AVAILABLE_EVENT] 126 = {.min_len = sizeof(struct wmi_service_available_event) }, 127 [WMI_TAG_PEER_ASSOC_CONF_EVENT] 128 = { .min_len = sizeof(struct wmi_peer_assoc_conf_event) }, 129 [WMI_TAG_STATS_EVENT] 130 = { .min_len = sizeof(struct wmi_stats_event) }, 131 [WMI_TAG_RFKILL_EVENT] = { 132 .min_len = sizeof(struct wmi_rfkill_state_change_ev) }, 133 [WMI_TAG_PDEV_CTL_FAILSAFE_CHECK_EVENT] 134 = { .min_len = sizeof(struct wmi_pdev_ctl_failsafe_chk_event) }, 135 [WMI_TAG_HOST_SWFDA_EVENT] = { 136 .min_len = sizeof(struct wmi_fils_discovery_event) }, 137 [WMI_TAG_OFFLOAD_PRB_RSP_TX_STATUS_EVENT] = { 138 .min_len = sizeof(struct wmi_probe_resp_tx_status_event) }, 139 [WMI_TAG_VDEV_DELETE_RESP_EVENT] = { 140 .min_len = sizeof(struct wmi_vdev_delete_resp_event) }, 141 [WMI_TAG_OBSS_COLOR_COLLISION_EVT] = { 142 .min_len = sizeof(struct wmi_obss_color_collision_event) }, 143 [WMI_TAG_11D_NEW_COUNTRY_EVENT] = { 144 .min_len = sizeof(struct wmi_11d_new_cc_ev) }, 145 [WMI_TAG_PER_CHAIN_RSSI_STATS] = { 146 .min_len = sizeof(struct wmi_per_chain_rssi_stats) }, 147 [WMI_TAG_TWT_ADD_DIALOG_COMPLETE_EVENT] = { 148 .min_len = sizeof(struct wmi_twt_add_dialog_event) }, 149 }; 150 151 #define PRIMAP(_hw_mode_) \ 152 [_hw_mode_] = _hw_mode_##_PRI 153 154 static const int ath11k_hw_mode_pri_map[] = { 155 PRIMAP(WMI_HOST_HW_MODE_SINGLE), 156 PRIMAP(WMI_HOST_HW_MODE_DBS), 157 PRIMAP(WMI_HOST_HW_MODE_SBS_PASSIVE), 158 PRIMAP(WMI_HOST_HW_MODE_SBS), 159 PRIMAP(WMI_HOST_HW_MODE_DBS_SBS), 160 PRIMAP(WMI_HOST_HW_MODE_DBS_OR_SBS), 161 /* keep last */ 162 PRIMAP(WMI_HOST_HW_MODE_MAX), 163 }; 164 165 static int 166 ath11k_wmi_tlv_iter(struct ath11k_base *ab, const void *ptr, size_t len, 167 int (*iter)(struct ath11k_base *ab, u16 tag, u16 len, 168 const void *ptr, void *data), 169 void *data) 170 { 171 const void *begin = ptr; 172 const struct wmi_tlv *tlv; 173 u16 tlv_tag, tlv_len; 174 int ret; 175 176 while (len > 0) { 177 if (len < sizeof(*tlv)) { 178 ath11k_err(ab, "wmi tlv parse failure at byte %zd (%zu bytes left, %zu expected)\n", 179 ptr - begin, len, sizeof(*tlv)); 180 return -EINVAL; 181 } 182 183 tlv = ptr; 184 tlv_tag = FIELD_GET(WMI_TLV_TAG, tlv->header); 185 tlv_len = FIELD_GET(WMI_TLV_LEN, tlv->header); 186 ptr += sizeof(*tlv); 187 len -= sizeof(*tlv); 188 189 if (tlv_len > len) { 190 ath11k_err(ab, "wmi tlv parse failure of tag %u at byte %zd (%zu bytes left, %u expected)\n", 191 tlv_tag, ptr - begin, len, tlv_len); 192 return -EINVAL; 193 } 194 195 if (tlv_tag < ARRAY_SIZE(wmi_tlv_policies) && 196 wmi_tlv_policies[tlv_tag].min_len && 197 wmi_tlv_policies[tlv_tag].min_len > tlv_len) { 198 ath11k_err(ab, "wmi tlv parse failure of tag %u at byte %zd (%u bytes is less than min length %zu)\n", 199 tlv_tag, ptr - begin, tlv_len, 200 wmi_tlv_policies[tlv_tag].min_len); 201 return -EINVAL; 202 } 203 204 ret = iter(ab, tlv_tag, tlv_len, ptr, data); 205 if (ret) 206 return ret; 207 208 ptr += tlv_len; 209 len -= tlv_len; 210 } 211 212 return 0; 213 } 214 215 static int ath11k_wmi_tlv_iter_parse(struct ath11k_base *ab, u16 tag, u16 len, 216 const void *ptr, void *data) 217 { 218 const void **tb = data; 219 220 if (tag < WMI_TAG_MAX) 221 tb[tag] = ptr; 222 223 return 0; 224 } 225 226 static int ath11k_wmi_tlv_parse(struct ath11k_base *ar, const void **tb, 227 const void *ptr, size_t len) 228 { 229 return ath11k_wmi_tlv_iter(ar, ptr, len, ath11k_wmi_tlv_iter_parse, 230 (void *)tb); 231 } 232 233 static const void ** 234 ath11k_wmi_tlv_parse_alloc(struct ath11k_base *ab, const void *ptr, 235 size_t len, gfp_t gfp) 236 { 237 const void **tb; 238 int ret; 239 240 tb = kcalloc(WMI_TAG_MAX, sizeof(*tb), gfp); 241 if (!tb) 242 return ERR_PTR(-ENOMEM); 243 244 ret = ath11k_wmi_tlv_parse(ab, tb, ptr, len); 245 if (ret) { 246 kfree(tb); 247 return ERR_PTR(ret); 248 } 249 250 return tb; 251 } 252 253 static int ath11k_wmi_cmd_send_nowait(struct ath11k_pdev_wmi *wmi, struct sk_buff *skb, 254 u32 cmd_id) 255 { 256 struct ath11k_skb_cb *skb_cb = ATH11K_SKB_CB(skb); 257 struct ath11k_base *ab = wmi->wmi_ab->ab; 258 struct wmi_cmd_hdr *cmd_hdr; 259 int ret; 260 u32 cmd = 0; 261 262 if (skb_push(skb, sizeof(struct wmi_cmd_hdr)) == NULL) 263 return -ENOMEM; 264 265 cmd |= FIELD_PREP(WMI_CMD_HDR_CMD_ID, cmd_id); 266 267 cmd_hdr = (struct wmi_cmd_hdr *)skb->data; 268 cmd_hdr->cmd_id = cmd; 269 270 trace_ath11k_wmi_cmd(ab, cmd_id, skb->data, skb->len); 271 272 memset(skb_cb, 0, sizeof(*skb_cb)); 273 ret = ath11k_htc_send(&ab->htc, wmi->eid, skb); 274 275 if (ret) 276 goto err_pull; 277 278 return 0; 279 280 err_pull: 281 skb_pull(skb, sizeof(struct wmi_cmd_hdr)); 282 return ret; 283 } 284 285 int ath11k_wmi_cmd_send(struct ath11k_pdev_wmi *wmi, struct sk_buff *skb, 286 u32 cmd_id) 287 { 288 struct ath11k_wmi_base *wmi_sc = wmi->wmi_ab; 289 int ret = -EOPNOTSUPP; 290 struct ath11k_base *ab = wmi_sc->ab; 291 292 might_sleep(); 293 294 if (ab->hw_params.credit_flow) { 295 wait_event_timeout(wmi_sc->tx_credits_wq, ({ 296 ret = ath11k_wmi_cmd_send_nowait(wmi, skb, cmd_id); 297 298 if (ret && test_bit(ATH11K_FLAG_CRASH_FLUSH, 299 &wmi_sc->ab->dev_flags)) 300 ret = -ESHUTDOWN; 301 302 (ret != -EAGAIN); 303 }), WMI_SEND_TIMEOUT_HZ); 304 } else { 305 wait_event_timeout(wmi->tx_ce_desc_wq, ({ 306 ret = ath11k_wmi_cmd_send_nowait(wmi, skb, cmd_id); 307 308 if (ret && test_bit(ATH11K_FLAG_CRASH_FLUSH, 309 &wmi_sc->ab->dev_flags)) 310 ret = -ESHUTDOWN; 311 312 (ret != -ENOBUFS); 313 }), WMI_SEND_TIMEOUT_HZ); 314 } 315 316 if (ret == -EAGAIN) 317 ath11k_warn(wmi_sc->ab, "wmi command %d timeout\n", cmd_id); 318 319 if (ret == -ENOBUFS) 320 ath11k_warn(wmi_sc->ab, "ce desc not available for wmi command %d\n", 321 cmd_id); 322 323 return ret; 324 } 325 326 static int ath11k_pull_svc_ready_ext(struct ath11k_pdev_wmi *wmi_handle, 327 const void *ptr, 328 struct ath11k_service_ext_param *param) 329 { 330 const struct wmi_service_ready_ext_event *ev = ptr; 331 332 if (!ev) 333 return -EINVAL; 334 335 /* Move this to host based bitmap */ 336 param->default_conc_scan_config_bits = ev->default_conc_scan_config_bits; 337 param->default_fw_config_bits = ev->default_fw_config_bits; 338 param->he_cap_info = ev->he_cap_info; 339 param->mpdu_density = ev->mpdu_density; 340 param->max_bssid_rx_filters = ev->max_bssid_rx_filters; 341 memcpy(¶m->ppet, &ev->ppet, sizeof(param->ppet)); 342 343 return 0; 344 } 345 346 static int 347 ath11k_pull_mac_phy_cap_svc_ready_ext(struct ath11k_pdev_wmi *wmi_handle, 348 struct wmi_soc_mac_phy_hw_mode_caps *hw_caps, 349 struct wmi_hw_mode_capabilities *wmi_hw_mode_caps, 350 struct wmi_soc_hal_reg_capabilities *hal_reg_caps, 351 struct wmi_mac_phy_capabilities *wmi_mac_phy_caps, 352 u8 hw_mode_id, u8 phy_id, 353 struct ath11k_pdev *pdev) 354 { 355 struct wmi_mac_phy_capabilities *mac_phy_caps; 356 struct ath11k_base *ab = wmi_handle->wmi_ab->ab; 357 struct ath11k_band_cap *cap_band; 358 struct ath11k_pdev_cap *pdev_cap = &pdev->cap; 359 u32 phy_map; 360 u32 hw_idx, phy_idx = 0; 361 362 if (!hw_caps || !wmi_hw_mode_caps || !hal_reg_caps) 363 return -EINVAL; 364 365 for (hw_idx = 0; hw_idx < hw_caps->num_hw_modes; hw_idx++) { 366 if (hw_mode_id == wmi_hw_mode_caps[hw_idx].hw_mode_id) 367 break; 368 369 phy_map = wmi_hw_mode_caps[hw_idx].phy_id_map; 370 while (phy_map) { 371 phy_map >>= 1; 372 phy_idx++; 373 } 374 } 375 376 if (hw_idx == hw_caps->num_hw_modes) 377 return -EINVAL; 378 379 phy_idx += phy_id; 380 if (phy_id >= hal_reg_caps->num_phy) 381 return -EINVAL; 382 383 mac_phy_caps = wmi_mac_phy_caps + phy_idx; 384 385 pdev->pdev_id = mac_phy_caps->pdev_id; 386 pdev_cap->supported_bands |= mac_phy_caps->supported_bands; 387 pdev_cap->ampdu_density = mac_phy_caps->ampdu_density; 388 ab->target_pdev_ids[ab->target_pdev_count].supported_bands = 389 mac_phy_caps->supported_bands; 390 ab->target_pdev_ids[ab->target_pdev_count].pdev_id = mac_phy_caps->pdev_id; 391 ab->target_pdev_count++; 392 393 /* Take non-zero tx/rx chainmask. If tx/rx chainmask differs from 394 * band to band for a single radio, need to see how this should be 395 * handled. 396 */ 397 if (mac_phy_caps->supported_bands & WMI_HOST_WLAN_2G_CAP) { 398 pdev_cap->tx_chain_mask = mac_phy_caps->tx_chain_mask_2g; 399 pdev_cap->rx_chain_mask = mac_phy_caps->rx_chain_mask_2g; 400 } else if (mac_phy_caps->supported_bands & WMI_HOST_WLAN_5G_CAP) { 401 pdev_cap->vht_cap = mac_phy_caps->vht_cap_info_5g; 402 pdev_cap->vht_mcs = mac_phy_caps->vht_supp_mcs_5g; 403 pdev_cap->he_mcs = mac_phy_caps->he_supp_mcs_5g; 404 pdev_cap->tx_chain_mask = mac_phy_caps->tx_chain_mask_5g; 405 pdev_cap->rx_chain_mask = mac_phy_caps->rx_chain_mask_5g; 406 pdev_cap->nss_ratio_enabled = 407 WMI_NSS_RATIO_ENABLE_DISABLE_GET(mac_phy_caps->nss_ratio); 408 pdev_cap->nss_ratio_info = 409 WMI_NSS_RATIO_INFO_GET(mac_phy_caps->nss_ratio); 410 } else { 411 return -EINVAL; 412 } 413 414 /* tx/rx chainmask reported from fw depends on the actual hw chains used, 415 * For example, for 4x4 capable macphys, first 4 chains can be used for first 416 * mac and the remaing 4 chains can be used for the second mac or vice-versa. 417 * In this case, tx/rx chainmask 0xf will be advertised for first mac and 0xf0 418 * will be advertised for second mac or vice-versa. Compute the shift value 419 * for tx/rx chainmask which will be used to advertise supported ht/vht rates to 420 * mac80211. 421 */ 422 pdev_cap->tx_chain_mask_shift = 423 find_first_bit((unsigned long *)&pdev_cap->tx_chain_mask, 32); 424 pdev_cap->rx_chain_mask_shift = 425 find_first_bit((unsigned long *)&pdev_cap->rx_chain_mask, 32); 426 427 if (mac_phy_caps->supported_bands & WMI_HOST_WLAN_2G_CAP) { 428 cap_band = &pdev_cap->band[NL80211_BAND_2GHZ]; 429 cap_band->phy_id = mac_phy_caps->phy_id; 430 cap_band->max_bw_supported = mac_phy_caps->max_bw_supported_2g; 431 cap_band->ht_cap_info = mac_phy_caps->ht_cap_info_2g; 432 cap_band->he_cap_info[0] = mac_phy_caps->he_cap_info_2g; 433 cap_band->he_cap_info[1] = mac_phy_caps->he_cap_info_2g_ext; 434 cap_band->he_mcs = mac_phy_caps->he_supp_mcs_2g; 435 memcpy(cap_band->he_cap_phy_info, &mac_phy_caps->he_cap_phy_info_2g, 436 sizeof(u32) * PSOC_HOST_MAX_PHY_SIZE); 437 memcpy(&cap_band->he_ppet, &mac_phy_caps->he_ppet2g, 438 sizeof(struct ath11k_ppe_threshold)); 439 } 440 441 if (mac_phy_caps->supported_bands & WMI_HOST_WLAN_5G_CAP) { 442 cap_band = &pdev_cap->band[NL80211_BAND_5GHZ]; 443 cap_band->phy_id = mac_phy_caps->phy_id; 444 cap_band->max_bw_supported = mac_phy_caps->max_bw_supported_5g; 445 cap_band->ht_cap_info = mac_phy_caps->ht_cap_info_5g; 446 cap_band->he_cap_info[0] = mac_phy_caps->he_cap_info_5g; 447 cap_band->he_cap_info[1] = mac_phy_caps->he_cap_info_5g_ext; 448 cap_band->he_mcs = mac_phy_caps->he_supp_mcs_5g; 449 memcpy(cap_band->he_cap_phy_info, &mac_phy_caps->he_cap_phy_info_5g, 450 sizeof(u32) * PSOC_HOST_MAX_PHY_SIZE); 451 memcpy(&cap_band->he_ppet, &mac_phy_caps->he_ppet5g, 452 sizeof(struct ath11k_ppe_threshold)); 453 454 cap_band = &pdev_cap->band[NL80211_BAND_6GHZ]; 455 cap_band->max_bw_supported = mac_phy_caps->max_bw_supported_5g; 456 cap_band->ht_cap_info = mac_phy_caps->ht_cap_info_5g; 457 cap_band->he_cap_info[0] = mac_phy_caps->he_cap_info_5g; 458 cap_band->he_cap_info[1] = mac_phy_caps->he_cap_info_5g_ext; 459 cap_band->he_mcs = mac_phy_caps->he_supp_mcs_5g; 460 memcpy(cap_band->he_cap_phy_info, &mac_phy_caps->he_cap_phy_info_5g, 461 sizeof(u32) * PSOC_HOST_MAX_PHY_SIZE); 462 memcpy(&cap_band->he_ppet, &mac_phy_caps->he_ppet5g, 463 sizeof(struct ath11k_ppe_threshold)); 464 } 465 466 return 0; 467 } 468 469 static int 470 ath11k_pull_reg_cap_svc_rdy_ext(struct ath11k_pdev_wmi *wmi_handle, 471 struct wmi_soc_hal_reg_capabilities *reg_caps, 472 struct wmi_hal_reg_capabilities_ext *wmi_ext_reg_cap, 473 u8 phy_idx, 474 struct ath11k_hal_reg_capabilities_ext *param) 475 { 476 struct wmi_hal_reg_capabilities_ext *ext_reg_cap; 477 478 if (!reg_caps || !wmi_ext_reg_cap) 479 return -EINVAL; 480 481 if (phy_idx >= reg_caps->num_phy) 482 return -EINVAL; 483 484 ext_reg_cap = &wmi_ext_reg_cap[phy_idx]; 485 486 param->phy_id = ext_reg_cap->phy_id; 487 param->eeprom_reg_domain = ext_reg_cap->eeprom_reg_domain; 488 param->eeprom_reg_domain_ext = 489 ext_reg_cap->eeprom_reg_domain_ext; 490 param->regcap1 = ext_reg_cap->regcap1; 491 param->regcap2 = ext_reg_cap->regcap2; 492 /* check if param->wireless_mode is needed */ 493 param->low_2ghz_chan = ext_reg_cap->low_2ghz_chan; 494 param->high_2ghz_chan = ext_reg_cap->high_2ghz_chan; 495 param->low_5ghz_chan = ext_reg_cap->low_5ghz_chan; 496 param->high_5ghz_chan = ext_reg_cap->high_5ghz_chan; 497 498 return 0; 499 } 500 501 static int ath11k_pull_service_ready_tlv(struct ath11k_base *ab, 502 const void *evt_buf, 503 struct ath11k_targ_cap *cap) 504 { 505 const struct wmi_service_ready_event *ev = evt_buf; 506 507 if (!ev) { 508 ath11k_err(ab, "%s: failed by NULL param\n", 509 __func__); 510 return -EINVAL; 511 } 512 513 cap->phy_capability = ev->phy_capability; 514 cap->max_frag_entry = ev->max_frag_entry; 515 cap->num_rf_chains = ev->num_rf_chains; 516 cap->ht_cap_info = ev->ht_cap_info; 517 cap->vht_cap_info = ev->vht_cap_info; 518 cap->vht_supp_mcs = ev->vht_supp_mcs; 519 cap->hw_min_tx_power = ev->hw_min_tx_power; 520 cap->hw_max_tx_power = ev->hw_max_tx_power; 521 cap->sys_cap_info = ev->sys_cap_info; 522 cap->min_pkt_size_enable = ev->min_pkt_size_enable; 523 cap->max_bcn_ie_size = ev->max_bcn_ie_size; 524 cap->max_num_scan_channels = ev->max_num_scan_channels; 525 cap->max_supported_macs = ev->max_supported_macs; 526 cap->wmi_fw_sub_feat_caps = ev->wmi_fw_sub_feat_caps; 527 cap->txrx_chainmask = ev->txrx_chainmask; 528 cap->default_dbs_hw_mode_index = ev->default_dbs_hw_mode_index; 529 cap->num_msdu_desc = ev->num_msdu_desc; 530 531 ath11k_dbg(ab, ATH11K_DBG_WMI, "wmi sys cap info 0x%x\n", cap->sys_cap_info); 532 533 return 0; 534 } 535 536 /* Save the wmi_service_bitmap into a linear bitmap. The wmi_services in 537 * wmi_service ready event are advertised in b0-b3 (LSB 4-bits) of each 538 * 4-byte word. 539 */ 540 static void ath11k_wmi_service_bitmap_copy(struct ath11k_pdev_wmi *wmi, 541 const u32 *wmi_svc_bm) 542 { 543 int i, j; 544 545 for (i = 0, j = 0; i < WMI_SERVICE_BM_SIZE && j < WMI_MAX_SERVICE; i++) { 546 do { 547 if (wmi_svc_bm[i] & BIT(j % WMI_SERVICE_BITS_IN_SIZE32)) 548 set_bit(j, wmi->wmi_ab->svc_map); 549 } while (++j % WMI_SERVICE_BITS_IN_SIZE32); 550 } 551 } 552 553 static int ath11k_wmi_tlv_svc_rdy_parse(struct ath11k_base *ab, u16 tag, u16 len, 554 const void *ptr, void *data) 555 { 556 struct wmi_tlv_svc_ready_parse *svc_ready = data; 557 struct ath11k_pdev_wmi *wmi_handle = &ab->wmi_ab.wmi[0]; 558 u16 expect_len; 559 560 switch (tag) { 561 case WMI_TAG_SERVICE_READY_EVENT: 562 if (ath11k_pull_service_ready_tlv(ab, ptr, &ab->target_caps)) 563 return -EINVAL; 564 break; 565 566 case WMI_TAG_ARRAY_UINT32: 567 if (!svc_ready->wmi_svc_bitmap_done) { 568 expect_len = WMI_SERVICE_BM_SIZE * sizeof(u32); 569 if (len < expect_len) { 570 ath11k_warn(ab, "invalid len %d for the tag 0x%x\n", 571 len, tag); 572 return -EINVAL; 573 } 574 575 ath11k_wmi_service_bitmap_copy(wmi_handle, ptr); 576 577 svc_ready->wmi_svc_bitmap_done = true; 578 } 579 break; 580 default: 581 break; 582 } 583 584 return 0; 585 } 586 587 static int ath11k_service_ready_event(struct ath11k_base *ab, struct sk_buff *skb) 588 { 589 struct wmi_tlv_svc_ready_parse svc_ready = { }; 590 int ret; 591 592 ret = ath11k_wmi_tlv_iter(ab, skb->data, skb->len, 593 ath11k_wmi_tlv_svc_rdy_parse, 594 &svc_ready); 595 if (ret) { 596 ath11k_warn(ab, "failed to parse tlv %d\n", ret); 597 return ret; 598 } 599 600 return 0; 601 } 602 603 struct sk_buff *ath11k_wmi_alloc_skb(struct ath11k_wmi_base *wmi_sc, u32 len) 604 { 605 struct sk_buff *skb; 606 struct ath11k_base *ab = wmi_sc->ab; 607 u32 round_len = roundup(len, 4); 608 609 skb = ath11k_htc_alloc_skb(ab, WMI_SKB_HEADROOM + round_len); 610 if (!skb) 611 return NULL; 612 613 skb_reserve(skb, WMI_SKB_HEADROOM); 614 if (!IS_ALIGNED((unsigned long)skb->data, 4)) 615 ath11k_warn(ab, "unaligned WMI skb data\n"); 616 617 skb_put(skb, round_len); 618 memset(skb->data, 0, round_len); 619 620 return skb; 621 } 622 623 int ath11k_wmi_mgmt_send(struct ath11k *ar, u32 vdev_id, u32 buf_id, 624 struct sk_buff *frame) 625 { 626 struct ath11k_pdev_wmi *wmi = ar->wmi; 627 struct wmi_mgmt_send_cmd *cmd; 628 struct wmi_tlv *frame_tlv; 629 struct sk_buff *skb; 630 u32 buf_len; 631 int ret, len; 632 633 buf_len = frame->len < WMI_MGMT_SEND_DOWNLD_LEN ? 634 frame->len : WMI_MGMT_SEND_DOWNLD_LEN; 635 636 len = sizeof(*cmd) + sizeof(*frame_tlv) + roundup(buf_len, 4); 637 638 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 639 if (!skb) 640 return -ENOMEM; 641 642 cmd = (struct wmi_mgmt_send_cmd *)skb->data; 643 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_MGMT_TX_SEND_CMD) | 644 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 645 cmd->vdev_id = vdev_id; 646 cmd->desc_id = buf_id; 647 cmd->chanfreq = 0; 648 cmd->paddr_lo = lower_32_bits(ATH11K_SKB_CB(frame)->paddr); 649 cmd->paddr_hi = upper_32_bits(ATH11K_SKB_CB(frame)->paddr); 650 cmd->frame_len = frame->len; 651 cmd->buf_len = buf_len; 652 cmd->tx_params_valid = 0; 653 654 frame_tlv = (struct wmi_tlv *)(skb->data + sizeof(*cmd)); 655 frame_tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_BYTE) | 656 FIELD_PREP(WMI_TLV_LEN, buf_len); 657 658 memcpy(frame_tlv->value, frame->data, buf_len); 659 660 ath11k_ce_byte_swap(frame_tlv->value, buf_len); 661 662 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_MGMT_TX_SEND_CMDID); 663 if (ret) { 664 ath11k_warn(ar->ab, 665 "failed to submit WMI_MGMT_TX_SEND_CMDID cmd\n"); 666 dev_kfree_skb(skb); 667 } 668 669 return ret; 670 } 671 672 int ath11k_wmi_vdev_create(struct ath11k *ar, u8 *macaddr, 673 struct vdev_create_params *param) 674 { 675 struct ath11k_pdev_wmi *wmi = ar->wmi; 676 struct wmi_vdev_create_cmd *cmd; 677 struct sk_buff *skb; 678 struct wmi_vdev_txrx_streams *txrx_streams; 679 struct wmi_tlv *tlv; 680 int ret, len; 681 void *ptr; 682 683 /* It can be optimized my sending tx/rx chain configuration 684 * only for supported bands instead of always sending it for 685 * both the bands. 686 */ 687 len = sizeof(*cmd) + TLV_HDR_SIZE + 688 (WMI_NUM_SUPPORTED_BAND_MAX * sizeof(*txrx_streams)); 689 690 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 691 if (!skb) 692 return -ENOMEM; 693 694 cmd = (struct wmi_vdev_create_cmd *)skb->data; 695 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_CREATE_CMD) | 696 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 697 698 cmd->vdev_id = param->if_id; 699 cmd->vdev_type = param->type; 700 cmd->vdev_subtype = param->subtype; 701 cmd->num_cfg_txrx_streams = WMI_NUM_SUPPORTED_BAND_MAX; 702 cmd->pdev_id = param->pdev_id; 703 ether_addr_copy(cmd->vdev_macaddr.addr, macaddr); 704 705 ptr = skb->data + sizeof(*cmd); 706 len = WMI_NUM_SUPPORTED_BAND_MAX * sizeof(*txrx_streams); 707 708 tlv = ptr; 709 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_STRUCT) | 710 FIELD_PREP(WMI_TLV_LEN, len); 711 712 ptr += TLV_HDR_SIZE; 713 txrx_streams = ptr; 714 len = sizeof(*txrx_streams); 715 txrx_streams->tlv_header = 716 FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_TXRX_STREAMS) | 717 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 718 txrx_streams->band = WMI_TPC_CHAINMASK_CONFIG_BAND_2G; 719 txrx_streams->supported_tx_streams = 720 param->chains[NL80211_BAND_2GHZ].tx; 721 txrx_streams->supported_rx_streams = 722 param->chains[NL80211_BAND_2GHZ].rx; 723 724 txrx_streams++; 725 txrx_streams->tlv_header = 726 FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_TXRX_STREAMS) | 727 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 728 txrx_streams->band = WMI_TPC_CHAINMASK_CONFIG_BAND_5G; 729 txrx_streams->supported_tx_streams = 730 param->chains[NL80211_BAND_5GHZ].tx; 731 txrx_streams->supported_rx_streams = 732 param->chains[NL80211_BAND_5GHZ].rx; 733 734 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_VDEV_CREATE_CMDID); 735 if (ret) { 736 ath11k_warn(ar->ab, 737 "failed to submit WMI_VDEV_CREATE_CMDID\n"); 738 dev_kfree_skb(skb); 739 } 740 741 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 742 "WMI vdev create: id %d type %d subtype %d macaddr %pM pdevid %d\n", 743 param->if_id, param->type, param->subtype, 744 macaddr, param->pdev_id); 745 746 return ret; 747 } 748 749 int ath11k_wmi_vdev_delete(struct ath11k *ar, u8 vdev_id) 750 { 751 struct ath11k_pdev_wmi *wmi = ar->wmi; 752 struct wmi_vdev_delete_cmd *cmd; 753 struct sk_buff *skb; 754 int ret; 755 756 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 757 if (!skb) 758 return -ENOMEM; 759 760 cmd = (struct wmi_vdev_delete_cmd *)skb->data; 761 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_DELETE_CMD) | 762 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 763 cmd->vdev_id = vdev_id; 764 765 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_VDEV_DELETE_CMDID); 766 if (ret) { 767 ath11k_warn(ar->ab, "failed to submit WMI_VDEV_DELETE_CMDID\n"); 768 dev_kfree_skb(skb); 769 } 770 771 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, "WMI vdev delete id %d\n", vdev_id); 772 773 return ret; 774 } 775 776 int ath11k_wmi_vdev_stop(struct ath11k *ar, u8 vdev_id) 777 { 778 struct ath11k_pdev_wmi *wmi = ar->wmi; 779 struct wmi_vdev_stop_cmd *cmd; 780 struct sk_buff *skb; 781 int ret; 782 783 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 784 if (!skb) 785 return -ENOMEM; 786 787 cmd = (struct wmi_vdev_stop_cmd *)skb->data; 788 789 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_STOP_CMD) | 790 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 791 cmd->vdev_id = vdev_id; 792 793 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_VDEV_STOP_CMDID); 794 if (ret) { 795 ath11k_warn(ar->ab, "failed to submit WMI_VDEV_STOP cmd\n"); 796 dev_kfree_skb(skb); 797 } 798 799 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, "WMI vdev stop id 0x%x\n", vdev_id); 800 801 return ret; 802 } 803 804 int ath11k_wmi_vdev_down(struct ath11k *ar, u8 vdev_id) 805 { 806 struct ath11k_pdev_wmi *wmi = ar->wmi; 807 struct wmi_vdev_down_cmd *cmd; 808 struct sk_buff *skb; 809 int ret; 810 811 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 812 if (!skb) 813 return -ENOMEM; 814 815 cmd = (struct wmi_vdev_down_cmd *)skb->data; 816 817 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_DOWN_CMD) | 818 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 819 cmd->vdev_id = vdev_id; 820 821 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_VDEV_DOWN_CMDID); 822 if (ret) { 823 ath11k_warn(ar->ab, "failed to submit WMI_VDEV_DOWN cmd\n"); 824 dev_kfree_skb(skb); 825 } 826 827 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, "WMI vdev down id 0x%x\n", vdev_id); 828 829 return ret; 830 } 831 832 static void ath11k_wmi_put_wmi_channel(struct wmi_channel *chan, 833 struct wmi_vdev_start_req_arg *arg) 834 { 835 u32 center_freq1 = arg->channel.band_center_freq1; 836 837 memset(chan, 0, sizeof(*chan)); 838 839 chan->mhz = arg->channel.freq; 840 chan->band_center_freq1 = arg->channel.band_center_freq1; 841 842 if (arg->channel.mode == MODE_11AX_HE160) { 843 if (arg->channel.freq > arg->channel.band_center_freq1) 844 chan->band_center_freq1 = center_freq1 + 40; 845 else 846 chan->band_center_freq1 = center_freq1 - 40; 847 848 chan->band_center_freq2 = arg->channel.band_center_freq1; 849 850 } else if (arg->channel.mode == MODE_11AC_VHT80_80) { 851 chan->band_center_freq2 = arg->channel.band_center_freq2; 852 } else { 853 chan->band_center_freq2 = 0; 854 } 855 856 chan->info |= FIELD_PREP(WMI_CHAN_INFO_MODE, arg->channel.mode); 857 if (arg->channel.passive) 858 chan->info |= WMI_CHAN_INFO_PASSIVE; 859 if (arg->channel.allow_ibss) 860 chan->info |= WMI_CHAN_INFO_ADHOC_ALLOWED; 861 if (arg->channel.allow_ht) 862 chan->info |= WMI_CHAN_INFO_ALLOW_HT; 863 if (arg->channel.allow_vht) 864 chan->info |= WMI_CHAN_INFO_ALLOW_VHT; 865 if (arg->channel.allow_he) 866 chan->info |= WMI_CHAN_INFO_ALLOW_HE; 867 if (arg->channel.ht40plus) 868 chan->info |= WMI_CHAN_INFO_HT40_PLUS; 869 if (arg->channel.chan_radar) 870 chan->info |= WMI_CHAN_INFO_DFS; 871 if (arg->channel.freq2_radar) 872 chan->info |= WMI_CHAN_INFO_DFS_FREQ2; 873 874 chan->reg_info_1 = FIELD_PREP(WMI_CHAN_REG_INFO1_MAX_PWR, 875 arg->channel.max_power) | 876 FIELD_PREP(WMI_CHAN_REG_INFO1_MAX_REG_PWR, 877 arg->channel.max_reg_power); 878 879 chan->reg_info_2 = FIELD_PREP(WMI_CHAN_REG_INFO2_ANT_MAX, 880 arg->channel.max_antenna_gain) | 881 FIELD_PREP(WMI_CHAN_REG_INFO2_MAX_TX_PWR, 882 arg->channel.max_power); 883 } 884 885 int ath11k_wmi_vdev_start(struct ath11k *ar, struct wmi_vdev_start_req_arg *arg, 886 bool restart) 887 { 888 struct ath11k_pdev_wmi *wmi = ar->wmi; 889 struct wmi_vdev_start_request_cmd *cmd; 890 struct sk_buff *skb; 891 struct wmi_channel *chan; 892 struct wmi_tlv *tlv; 893 void *ptr; 894 int ret, len; 895 896 if (WARN_ON(arg->ssid_len > sizeof(cmd->ssid.ssid))) 897 return -EINVAL; 898 899 len = sizeof(*cmd) + sizeof(*chan) + TLV_HDR_SIZE; 900 901 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 902 if (!skb) 903 return -ENOMEM; 904 905 cmd = (struct wmi_vdev_start_request_cmd *)skb->data; 906 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 907 WMI_TAG_VDEV_START_REQUEST_CMD) | 908 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 909 cmd->vdev_id = arg->vdev_id; 910 cmd->beacon_interval = arg->bcn_intval; 911 cmd->bcn_tx_rate = arg->bcn_tx_rate; 912 cmd->dtim_period = arg->dtim_period; 913 cmd->num_noa_descriptors = arg->num_noa_descriptors; 914 cmd->preferred_rx_streams = arg->pref_rx_streams; 915 cmd->preferred_tx_streams = arg->pref_tx_streams; 916 cmd->cac_duration_ms = arg->cac_duration_ms; 917 cmd->regdomain = arg->regdomain; 918 cmd->he_ops = arg->he_ops; 919 920 if (!restart) { 921 if (arg->ssid) { 922 cmd->ssid.ssid_len = arg->ssid_len; 923 memcpy(cmd->ssid.ssid, arg->ssid, arg->ssid_len); 924 } 925 if (arg->hidden_ssid) 926 cmd->flags |= WMI_VDEV_START_HIDDEN_SSID; 927 if (arg->pmf_enabled) 928 cmd->flags |= WMI_VDEV_START_PMF_ENABLED; 929 } 930 931 cmd->flags |= WMI_VDEV_START_LDPC_RX_ENABLED; 932 if (test_bit(ATH11K_FLAG_HW_CRYPTO_DISABLED, &ar->ab->dev_flags)) 933 cmd->flags |= WMI_VDEV_START_HW_ENCRYPTION_DISABLED; 934 935 ptr = skb->data + sizeof(*cmd); 936 chan = ptr; 937 938 ath11k_wmi_put_wmi_channel(chan, arg); 939 940 chan->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_CHANNEL) | 941 FIELD_PREP(WMI_TLV_LEN, 942 sizeof(*chan) - TLV_HDR_SIZE); 943 ptr += sizeof(*chan); 944 945 tlv = ptr; 946 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_STRUCT) | 947 FIELD_PREP(WMI_TLV_LEN, 0); 948 949 /* Note: This is a nested TLV containing: 950 * [wmi_tlv][wmi_p2p_noa_descriptor][wmi_tlv].. 951 */ 952 953 ptr += sizeof(*tlv); 954 955 if (restart) 956 ret = ath11k_wmi_cmd_send(wmi, skb, 957 WMI_VDEV_RESTART_REQUEST_CMDID); 958 else 959 ret = ath11k_wmi_cmd_send(wmi, skb, 960 WMI_VDEV_START_REQUEST_CMDID); 961 if (ret) { 962 ath11k_warn(ar->ab, "failed to submit vdev_%s cmd\n", 963 restart ? "restart" : "start"); 964 dev_kfree_skb(skb); 965 } 966 967 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, "vdev %s id 0x%x freq 0x%x mode 0x%x\n", 968 restart ? "restart" : "start", arg->vdev_id, 969 arg->channel.freq, arg->channel.mode); 970 971 return ret; 972 } 973 974 int ath11k_wmi_vdev_up(struct ath11k *ar, u32 vdev_id, u32 aid, const u8 *bssid) 975 { 976 struct ath11k_pdev_wmi *wmi = ar->wmi; 977 struct wmi_vdev_up_cmd *cmd; 978 struct sk_buff *skb; 979 int ret; 980 981 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 982 if (!skb) 983 return -ENOMEM; 984 985 cmd = (struct wmi_vdev_up_cmd *)skb->data; 986 987 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_UP_CMD) | 988 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 989 cmd->vdev_id = vdev_id; 990 cmd->vdev_assoc_id = aid; 991 992 ether_addr_copy(cmd->vdev_bssid.addr, bssid); 993 994 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_VDEV_UP_CMDID); 995 if (ret) { 996 ath11k_warn(ar->ab, "failed to submit WMI_VDEV_UP cmd\n"); 997 dev_kfree_skb(skb); 998 } 999 1000 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1001 "WMI mgmt vdev up id 0x%x assoc id %d bssid %pM\n", 1002 vdev_id, aid, bssid); 1003 1004 return ret; 1005 } 1006 1007 int ath11k_wmi_send_peer_create_cmd(struct ath11k *ar, 1008 struct peer_create_params *param) 1009 { 1010 struct ath11k_pdev_wmi *wmi = ar->wmi; 1011 struct wmi_peer_create_cmd *cmd; 1012 struct sk_buff *skb; 1013 int ret; 1014 1015 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1016 if (!skb) 1017 return -ENOMEM; 1018 1019 cmd = (struct wmi_peer_create_cmd *)skb->data; 1020 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PEER_CREATE_CMD) | 1021 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1022 1023 ether_addr_copy(cmd->peer_macaddr.addr, param->peer_addr); 1024 cmd->peer_type = param->peer_type; 1025 cmd->vdev_id = param->vdev_id; 1026 1027 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PEER_CREATE_CMDID); 1028 if (ret) { 1029 ath11k_warn(ar->ab, "failed to submit WMI_PEER_CREATE cmd\n"); 1030 dev_kfree_skb(skb); 1031 } 1032 1033 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1034 "WMI peer create vdev_id %d peer_addr %pM\n", 1035 param->vdev_id, param->peer_addr); 1036 1037 return ret; 1038 } 1039 1040 int ath11k_wmi_send_peer_delete_cmd(struct ath11k *ar, 1041 const u8 *peer_addr, u8 vdev_id) 1042 { 1043 struct ath11k_pdev_wmi *wmi = ar->wmi; 1044 struct wmi_peer_delete_cmd *cmd; 1045 struct sk_buff *skb; 1046 int ret; 1047 1048 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1049 if (!skb) 1050 return -ENOMEM; 1051 1052 cmd = (struct wmi_peer_delete_cmd *)skb->data; 1053 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PEER_DELETE_CMD) | 1054 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1055 1056 ether_addr_copy(cmd->peer_macaddr.addr, peer_addr); 1057 cmd->vdev_id = vdev_id; 1058 1059 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1060 "WMI peer delete vdev_id %d peer_addr %pM\n", 1061 vdev_id, peer_addr); 1062 1063 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PEER_DELETE_CMDID); 1064 if (ret) { 1065 ath11k_warn(ar->ab, "failed to send WMI_PEER_DELETE cmd\n"); 1066 dev_kfree_skb(skb); 1067 } 1068 1069 return ret; 1070 } 1071 1072 int ath11k_wmi_send_pdev_set_regdomain(struct ath11k *ar, 1073 struct pdev_set_regdomain_params *param) 1074 { 1075 struct ath11k_pdev_wmi *wmi = ar->wmi; 1076 struct wmi_pdev_set_regdomain_cmd *cmd; 1077 struct sk_buff *skb; 1078 int ret; 1079 1080 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1081 if (!skb) 1082 return -ENOMEM; 1083 1084 cmd = (struct wmi_pdev_set_regdomain_cmd *)skb->data; 1085 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1086 WMI_TAG_PDEV_SET_REGDOMAIN_CMD) | 1087 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1088 1089 cmd->reg_domain = param->current_rd_in_use; 1090 cmd->reg_domain_2g = param->current_rd_2g; 1091 cmd->reg_domain_5g = param->current_rd_5g; 1092 cmd->conformance_test_limit_2g = param->ctl_2g; 1093 cmd->conformance_test_limit_5g = param->ctl_5g; 1094 cmd->dfs_domain = param->dfs_domain; 1095 cmd->pdev_id = param->pdev_id; 1096 1097 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1098 "WMI pdev regd rd %d rd2g %d rd5g %d domain %d pdev id %d\n", 1099 param->current_rd_in_use, param->current_rd_2g, 1100 param->current_rd_5g, param->dfs_domain, param->pdev_id); 1101 1102 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PDEV_SET_REGDOMAIN_CMDID); 1103 if (ret) { 1104 ath11k_warn(ar->ab, 1105 "failed to send WMI_PDEV_SET_REGDOMAIN cmd\n"); 1106 dev_kfree_skb(skb); 1107 } 1108 1109 return ret; 1110 } 1111 1112 int ath11k_wmi_set_peer_param(struct ath11k *ar, const u8 *peer_addr, 1113 u32 vdev_id, u32 param_id, u32 param_val) 1114 { 1115 struct ath11k_pdev_wmi *wmi = ar->wmi; 1116 struct wmi_peer_set_param_cmd *cmd; 1117 struct sk_buff *skb; 1118 int ret; 1119 1120 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1121 if (!skb) 1122 return -ENOMEM; 1123 1124 cmd = (struct wmi_peer_set_param_cmd *)skb->data; 1125 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PEER_SET_PARAM_CMD) | 1126 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1127 ether_addr_copy(cmd->peer_macaddr.addr, peer_addr); 1128 cmd->vdev_id = vdev_id; 1129 cmd->param_id = param_id; 1130 cmd->param_value = param_val; 1131 1132 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PEER_SET_PARAM_CMDID); 1133 if (ret) { 1134 ath11k_warn(ar->ab, "failed to send WMI_PEER_SET_PARAM cmd\n"); 1135 dev_kfree_skb(skb); 1136 } 1137 1138 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1139 "WMI vdev %d peer 0x%pM set param %d value %d\n", 1140 vdev_id, peer_addr, param_id, param_val); 1141 1142 return ret; 1143 } 1144 1145 int ath11k_wmi_send_peer_flush_tids_cmd(struct ath11k *ar, 1146 u8 peer_addr[ETH_ALEN], 1147 struct peer_flush_params *param) 1148 { 1149 struct ath11k_pdev_wmi *wmi = ar->wmi; 1150 struct wmi_peer_flush_tids_cmd *cmd; 1151 struct sk_buff *skb; 1152 int ret; 1153 1154 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1155 if (!skb) 1156 return -ENOMEM; 1157 1158 cmd = (struct wmi_peer_flush_tids_cmd *)skb->data; 1159 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PEER_FLUSH_TIDS_CMD) | 1160 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1161 1162 ether_addr_copy(cmd->peer_macaddr.addr, peer_addr); 1163 cmd->peer_tid_bitmap = param->peer_tid_bitmap; 1164 cmd->vdev_id = param->vdev_id; 1165 1166 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PEER_FLUSH_TIDS_CMDID); 1167 if (ret) { 1168 ath11k_warn(ar->ab, 1169 "failed to send WMI_PEER_FLUSH_TIDS cmd\n"); 1170 dev_kfree_skb(skb); 1171 } 1172 1173 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1174 "WMI peer flush vdev_id %d peer_addr %pM tids %08x\n", 1175 param->vdev_id, peer_addr, param->peer_tid_bitmap); 1176 1177 return ret; 1178 } 1179 1180 int ath11k_wmi_peer_rx_reorder_queue_setup(struct ath11k *ar, 1181 int vdev_id, const u8 *addr, 1182 dma_addr_t paddr, u8 tid, 1183 u8 ba_window_size_valid, 1184 u32 ba_window_size) 1185 { 1186 struct wmi_peer_reorder_queue_setup_cmd *cmd; 1187 struct sk_buff *skb; 1188 int ret; 1189 1190 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd)); 1191 if (!skb) 1192 return -ENOMEM; 1193 1194 cmd = (struct wmi_peer_reorder_queue_setup_cmd *)skb->data; 1195 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1196 WMI_TAG_REORDER_QUEUE_SETUP_CMD) | 1197 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1198 1199 ether_addr_copy(cmd->peer_macaddr.addr, addr); 1200 cmd->vdev_id = vdev_id; 1201 cmd->tid = tid; 1202 cmd->queue_ptr_lo = lower_32_bits(paddr); 1203 cmd->queue_ptr_hi = upper_32_bits(paddr); 1204 cmd->queue_no = tid; 1205 cmd->ba_window_size_valid = ba_window_size_valid; 1206 cmd->ba_window_size = ba_window_size; 1207 1208 ret = ath11k_wmi_cmd_send(ar->wmi, skb, 1209 WMI_PEER_REORDER_QUEUE_SETUP_CMDID); 1210 if (ret) { 1211 ath11k_warn(ar->ab, 1212 "failed to send WMI_PEER_REORDER_QUEUE_SETUP\n"); 1213 dev_kfree_skb(skb); 1214 } 1215 1216 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1217 "wmi rx reorder queue setup addr %pM vdev_id %d tid %d\n", 1218 addr, vdev_id, tid); 1219 1220 return ret; 1221 } 1222 1223 int 1224 ath11k_wmi_rx_reord_queue_remove(struct ath11k *ar, 1225 struct rx_reorder_queue_remove_params *param) 1226 { 1227 struct ath11k_pdev_wmi *wmi = ar->wmi; 1228 struct wmi_peer_reorder_queue_remove_cmd *cmd; 1229 struct sk_buff *skb; 1230 int ret; 1231 1232 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1233 if (!skb) 1234 return -ENOMEM; 1235 1236 cmd = (struct wmi_peer_reorder_queue_remove_cmd *)skb->data; 1237 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1238 WMI_TAG_REORDER_QUEUE_REMOVE_CMD) | 1239 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1240 1241 ether_addr_copy(cmd->peer_macaddr.addr, param->peer_macaddr); 1242 cmd->vdev_id = param->vdev_id; 1243 cmd->tid_mask = param->peer_tid_bitmap; 1244 1245 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1246 "%s: peer_macaddr %pM vdev_id %d, tid_map %d", __func__, 1247 param->peer_macaddr, param->vdev_id, param->peer_tid_bitmap); 1248 1249 ret = ath11k_wmi_cmd_send(wmi, skb, 1250 WMI_PEER_REORDER_QUEUE_REMOVE_CMDID); 1251 if (ret) { 1252 ath11k_warn(ar->ab, 1253 "failed to send WMI_PEER_REORDER_QUEUE_REMOVE_CMDID"); 1254 dev_kfree_skb(skb); 1255 } 1256 1257 return ret; 1258 } 1259 1260 int ath11k_wmi_pdev_set_param(struct ath11k *ar, u32 param_id, 1261 u32 param_value, u8 pdev_id) 1262 { 1263 struct ath11k_pdev_wmi *wmi = ar->wmi; 1264 struct wmi_pdev_set_param_cmd *cmd; 1265 struct sk_buff *skb; 1266 int ret; 1267 1268 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1269 if (!skb) 1270 return -ENOMEM; 1271 1272 cmd = (struct wmi_pdev_set_param_cmd *)skb->data; 1273 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_SET_PARAM_CMD) | 1274 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1275 cmd->pdev_id = pdev_id; 1276 cmd->param_id = param_id; 1277 cmd->param_value = param_value; 1278 1279 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PDEV_SET_PARAM_CMDID); 1280 if (ret) { 1281 ath11k_warn(ar->ab, "failed to send WMI_PDEV_SET_PARAM cmd\n"); 1282 dev_kfree_skb(skb); 1283 } 1284 1285 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1286 "WMI pdev set param %d pdev id %d value %d\n", 1287 param_id, pdev_id, param_value); 1288 1289 return ret; 1290 } 1291 1292 int ath11k_wmi_pdev_set_ps_mode(struct ath11k *ar, int vdev_id, 1293 enum wmi_sta_ps_mode psmode) 1294 { 1295 struct ath11k_pdev_wmi *wmi = ar->wmi; 1296 struct wmi_pdev_set_ps_mode_cmd *cmd; 1297 struct sk_buff *skb; 1298 int ret; 1299 1300 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1301 if (!skb) 1302 return -ENOMEM; 1303 1304 cmd = (struct wmi_pdev_set_ps_mode_cmd *)skb->data; 1305 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_STA_POWERSAVE_MODE_CMD) | 1306 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1307 cmd->vdev_id = vdev_id; 1308 cmd->sta_ps_mode = psmode; 1309 1310 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_STA_POWERSAVE_MODE_CMDID); 1311 if (ret) { 1312 ath11k_warn(ar->ab, "failed to send WMI_PDEV_SET_PARAM cmd\n"); 1313 dev_kfree_skb(skb); 1314 } 1315 1316 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1317 "WMI vdev set psmode %d vdev id %d\n", 1318 psmode, vdev_id); 1319 1320 return ret; 1321 } 1322 1323 int ath11k_wmi_pdev_suspend(struct ath11k *ar, u32 suspend_opt, 1324 u32 pdev_id) 1325 { 1326 struct ath11k_pdev_wmi *wmi = ar->wmi; 1327 struct wmi_pdev_suspend_cmd *cmd; 1328 struct sk_buff *skb; 1329 int ret; 1330 1331 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1332 if (!skb) 1333 return -ENOMEM; 1334 1335 cmd = (struct wmi_pdev_suspend_cmd *)skb->data; 1336 1337 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_SUSPEND_CMD) | 1338 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1339 1340 cmd->suspend_opt = suspend_opt; 1341 cmd->pdev_id = pdev_id; 1342 1343 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PDEV_SUSPEND_CMDID); 1344 if (ret) { 1345 ath11k_warn(ar->ab, "failed to send WMI_PDEV_SUSPEND cmd\n"); 1346 dev_kfree_skb(skb); 1347 } 1348 1349 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1350 "WMI pdev suspend pdev_id %d\n", pdev_id); 1351 1352 return ret; 1353 } 1354 1355 int ath11k_wmi_pdev_resume(struct ath11k *ar, u32 pdev_id) 1356 { 1357 struct ath11k_pdev_wmi *wmi = ar->wmi; 1358 struct wmi_pdev_resume_cmd *cmd; 1359 struct sk_buff *skb; 1360 int ret; 1361 1362 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1363 if (!skb) 1364 return -ENOMEM; 1365 1366 cmd = (struct wmi_pdev_resume_cmd *)skb->data; 1367 1368 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_RESUME_CMD) | 1369 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1370 cmd->pdev_id = pdev_id; 1371 1372 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1373 "WMI pdev resume pdev id %d\n", pdev_id); 1374 1375 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PDEV_RESUME_CMDID); 1376 if (ret) { 1377 ath11k_warn(ar->ab, "failed to send WMI_PDEV_RESUME cmd\n"); 1378 dev_kfree_skb(skb); 1379 } 1380 1381 return ret; 1382 } 1383 1384 /* TODO FW Support for the cmd is not available yet. 1385 * Can be tested once the command and corresponding 1386 * event is implemented in FW 1387 */ 1388 int ath11k_wmi_pdev_bss_chan_info_request(struct ath11k *ar, 1389 enum wmi_bss_chan_info_req_type type) 1390 { 1391 struct ath11k_pdev_wmi *wmi = ar->wmi; 1392 struct wmi_pdev_bss_chan_info_req_cmd *cmd; 1393 struct sk_buff *skb; 1394 int ret; 1395 1396 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1397 if (!skb) 1398 return -ENOMEM; 1399 1400 cmd = (struct wmi_pdev_bss_chan_info_req_cmd *)skb->data; 1401 1402 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1403 WMI_TAG_PDEV_BSS_CHAN_INFO_REQUEST) | 1404 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1405 cmd->req_type = type; 1406 cmd->pdev_id = ar->pdev->pdev_id; 1407 1408 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1409 "WMI bss chan info req type %d\n", type); 1410 1411 ret = ath11k_wmi_cmd_send(wmi, skb, 1412 WMI_PDEV_BSS_CHAN_INFO_REQUEST_CMDID); 1413 if (ret) { 1414 ath11k_warn(ar->ab, 1415 "failed to send WMI_PDEV_BSS_CHAN_INFO_REQUEST cmd\n"); 1416 dev_kfree_skb(skb); 1417 } 1418 1419 return ret; 1420 } 1421 1422 int ath11k_wmi_send_set_ap_ps_param_cmd(struct ath11k *ar, u8 *peer_addr, 1423 struct ap_ps_params *param) 1424 { 1425 struct ath11k_pdev_wmi *wmi = ar->wmi; 1426 struct wmi_ap_ps_peer_cmd *cmd; 1427 struct sk_buff *skb; 1428 int ret; 1429 1430 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1431 if (!skb) 1432 return -ENOMEM; 1433 1434 cmd = (struct wmi_ap_ps_peer_cmd *)skb->data; 1435 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_AP_PS_PEER_CMD) | 1436 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1437 1438 cmd->vdev_id = param->vdev_id; 1439 ether_addr_copy(cmd->peer_macaddr.addr, peer_addr); 1440 cmd->param = param->param; 1441 cmd->value = param->value; 1442 1443 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_AP_PS_PEER_PARAM_CMDID); 1444 if (ret) { 1445 ath11k_warn(ar->ab, 1446 "failed to send WMI_AP_PS_PEER_PARAM_CMDID\n"); 1447 dev_kfree_skb(skb); 1448 } 1449 1450 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1451 "WMI set ap ps vdev id %d peer %pM param %d value %d\n", 1452 param->vdev_id, peer_addr, param->param, param->value); 1453 1454 return ret; 1455 } 1456 1457 int ath11k_wmi_set_sta_ps_param(struct ath11k *ar, u32 vdev_id, 1458 u32 param, u32 param_value) 1459 { 1460 struct ath11k_pdev_wmi *wmi = ar->wmi; 1461 struct wmi_sta_powersave_param_cmd *cmd; 1462 struct sk_buff *skb; 1463 int ret; 1464 1465 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1466 if (!skb) 1467 return -ENOMEM; 1468 1469 cmd = (struct wmi_sta_powersave_param_cmd *)skb->data; 1470 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1471 WMI_TAG_STA_POWERSAVE_PARAM_CMD) | 1472 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1473 1474 cmd->vdev_id = vdev_id; 1475 cmd->param = param; 1476 cmd->value = param_value; 1477 1478 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1479 "WMI set sta ps vdev_id %d param %d value %d\n", 1480 vdev_id, param, param_value); 1481 1482 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_STA_POWERSAVE_PARAM_CMDID); 1483 if (ret) { 1484 ath11k_warn(ar->ab, "failed to send WMI_STA_POWERSAVE_PARAM_CMDID"); 1485 dev_kfree_skb(skb); 1486 } 1487 1488 return ret; 1489 } 1490 1491 int ath11k_wmi_force_fw_hang_cmd(struct ath11k *ar, u32 type, u32 delay_time_ms) 1492 { 1493 struct ath11k_pdev_wmi *wmi = ar->wmi; 1494 struct wmi_force_fw_hang_cmd *cmd; 1495 struct sk_buff *skb; 1496 int ret, len; 1497 1498 len = sizeof(*cmd); 1499 1500 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 1501 if (!skb) 1502 return -ENOMEM; 1503 1504 cmd = (struct wmi_force_fw_hang_cmd *)skb->data; 1505 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_FORCE_FW_HANG_CMD) | 1506 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 1507 1508 cmd->type = type; 1509 cmd->delay_time_ms = delay_time_ms; 1510 1511 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_FORCE_FW_HANG_CMDID); 1512 1513 if (ret) { 1514 ath11k_warn(ar->ab, "Failed to send WMI_FORCE_FW_HANG_CMDID"); 1515 dev_kfree_skb(skb); 1516 } 1517 return ret; 1518 } 1519 1520 int ath11k_wmi_vdev_set_param_cmd(struct ath11k *ar, u32 vdev_id, 1521 u32 param_id, u32 param_value) 1522 { 1523 struct ath11k_pdev_wmi *wmi = ar->wmi; 1524 struct wmi_vdev_set_param_cmd *cmd; 1525 struct sk_buff *skb; 1526 int ret; 1527 1528 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1529 if (!skb) 1530 return -ENOMEM; 1531 1532 cmd = (struct wmi_vdev_set_param_cmd *)skb->data; 1533 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_SET_PARAM_CMD) | 1534 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1535 1536 cmd->vdev_id = vdev_id; 1537 cmd->param_id = param_id; 1538 cmd->param_value = param_value; 1539 1540 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_VDEV_SET_PARAM_CMDID); 1541 if (ret) { 1542 ath11k_warn(ar->ab, 1543 "failed to send WMI_VDEV_SET_PARAM_CMDID\n"); 1544 dev_kfree_skb(skb); 1545 } 1546 1547 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1548 "WMI vdev id 0x%x set param %d value %d\n", 1549 vdev_id, param_id, param_value); 1550 1551 return ret; 1552 } 1553 1554 int ath11k_wmi_send_stats_request_cmd(struct ath11k *ar, 1555 struct stats_request_params *param) 1556 { 1557 struct ath11k_pdev_wmi *wmi = ar->wmi; 1558 struct wmi_request_stats_cmd *cmd; 1559 struct sk_buff *skb; 1560 int ret; 1561 1562 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1563 if (!skb) 1564 return -ENOMEM; 1565 1566 cmd = (struct wmi_request_stats_cmd *)skb->data; 1567 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_REQUEST_STATS_CMD) | 1568 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1569 1570 cmd->stats_id = param->stats_id; 1571 cmd->vdev_id = param->vdev_id; 1572 cmd->pdev_id = param->pdev_id; 1573 1574 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_REQUEST_STATS_CMDID); 1575 if (ret) { 1576 ath11k_warn(ar->ab, "failed to send WMI_REQUEST_STATS cmd\n"); 1577 dev_kfree_skb(skb); 1578 } 1579 1580 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1581 "WMI request stats 0x%x vdev id %d pdev id %d\n", 1582 param->stats_id, param->vdev_id, param->pdev_id); 1583 1584 return ret; 1585 } 1586 1587 int ath11k_wmi_send_pdev_temperature_cmd(struct ath11k *ar) 1588 { 1589 struct ath11k_pdev_wmi *wmi = ar->wmi; 1590 struct wmi_get_pdev_temperature_cmd *cmd; 1591 struct sk_buff *skb; 1592 int ret; 1593 1594 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1595 if (!skb) 1596 return -ENOMEM; 1597 1598 cmd = (struct wmi_get_pdev_temperature_cmd *)skb->data; 1599 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_GET_TEMPERATURE_CMD) | 1600 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1601 cmd->pdev_id = ar->pdev->pdev_id; 1602 1603 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PDEV_GET_TEMPERATURE_CMDID); 1604 if (ret) { 1605 ath11k_warn(ar->ab, "failed to send WMI_PDEV_GET_TEMPERATURE cmd\n"); 1606 dev_kfree_skb(skb); 1607 } 1608 1609 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1610 "WMI pdev get temperature for pdev_id %d\n", ar->pdev->pdev_id); 1611 1612 return ret; 1613 } 1614 1615 int ath11k_wmi_send_bcn_offload_control_cmd(struct ath11k *ar, 1616 u32 vdev_id, u32 bcn_ctrl_op) 1617 { 1618 struct ath11k_pdev_wmi *wmi = ar->wmi; 1619 struct wmi_bcn_offload_ctrl_cmd *cmd; 1620 struct sk_buff *skb; 1621 int ret; 1622 1623 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 1624 if (!skb) 1625 return -ENOMEM; 1626 1627 cmd = (struct wmi_bcn_offload_ctrl_cmd *)skb->data; 1628 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1629 WMI_TAG_BCN_OFFLOAD_CTRL_CMD) | 1630 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1631 1632 cmd->vdev_id = vdev_id; 1633 cmd->bcn_ctrl_op = bcn_ctrl_op; 1634 1635 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1636 "WMI bcn ctrl offload vdev id %d ctrl_op %d\n", 1637 vdev_id, bcn_ctrl_op); 1638 1639 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_BCN_OFFLOAD_CTRL_CMDID); 1640 if (ret) { 1641 ath11k_warn(ar->ab, 1642 "failed to send WMI_BCN_OFFLOAD_CTRL_CMDID\n"); 1643 dev_kfree_skb(skb); 1644 } 1645 1646 return ret; 1647 } 1648 1649 int ath11k_wmi_bcn_tmpl(struct ath11k *ar, u32 vdev_id, 1650 struct ieee80211_mutable_offsets *offs, 1651 struct sk_buff *bcn) 1652 { 1653 struct ath11k_pdev_wmi *wmi = ar->wmi; 1654 struct wmi_bcn_tmpl_cmd *cmd; 1655 struct wmi_bcn_prb_info *bcn_prb_info; 1656 struct wmi_tlv *tlv; 1657 struct sk_buff *skb; 1658 void *ptr; 1659 int ret, len; 1660 size_t aligned_len = roundup(bcn->len, 4); 1661 struct ieee80211_vif *vif; 1662 struct ath11k_vif *arvif = ath11k_mac_get_arvif(ar, vdev_id); 1663 1664 if (!arvif) { 1665 ath11k_warn(ar->ab, "failed to find arvif with vdev id %d\n", vdev_id); 1666 return -EINVAL; 1667 } 1668 1669 vif = arvif->vif; 1670 1671 len = sizeof(*cmd) + sizeof(*bcn_prb_info) + TLV_HDR_SIZE + aligned_len; 1672 1673 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 1674 if (!skb) 1675 return -ENOMEM; 1676 1677 cmd = (struct wmi_bcn_tmpl_cmd *)skb->data; 1678 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_BCN_TMPL_CMD) | 1679 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1680 cmd->vdev_id = vdev_id; 1681 cmd->tim_ie_offset = offs->tim_offset; 1682 1683 if (vif->csa_active) { 1684 cmd->csa_switch_count_offset = offs->cntdwn_counter_offs[0]; 1685 cmd->ext_csa_switch_count_offset = offs->cntdwn_counter_offs[1]; 1686 } 1687 1688 cmd->buf_len = bcn->len; 1689 1690 ptr = skb->data + sizeof(*cmd); 1691 1692 bcn_prb_info = ptr; 1693 len = sizeof(*bcn_prb_info); 1694 bcn_prb_info->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1695 WMI_TAG_BCN_PRB_INFO) | 1696 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 1697 bcn_prb_info->caps = 0; 1698 bcn_prb_info->erp = 0; 1699 1700 ptr += sizeof(*bcn_prb_info); 1701 1702 tlv = ptr; 1703 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_BYTE) | 1704 FIELD_PREP(WMI_TLV_LEN, aligned_len); 1705 memcpy(tlv->value, bcn->data, bcn->len); 1706 1707 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_BCN_TMPL_CMDID); 1708 if (ret) { 1709 ath11k_warn(ar->ab, "failed to send WMI_BCN_TMPL_CMDID\n"); 1710 dev_kfree_skb(skb); 1711 } 1712 1713 return ret; 1714 } 1715 1716 int ath11k_wmi_vdev_install_key(struct ath11k *ar, 1717 struct wmi_vdev_install_key_arg *arg) 1718 { 1719 struct ath11k_pdev_wmi *wmi = ar->wmi; 1720 struct wmi_vdev_install_key_cmd *cmd; 1721 struct wmi_tlv *tlv; 1722 struct sk_buff *skb; 1723 int ret, len; 1724 int key_len_aligned = roundup(arg->key_len, sizeof(uint32_t)); 1725 1726 len = sizeof(*cmd) + TLV_HDR_SIZE + key_len_aligned; 1727 1728 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 1729 if (!skb) 1730 return -ENOMEM; 1731 1732 cmd = (struct wmi_vdev_install_key_cmd *)skb->data; 1733 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VDEV_INSTALL_KEY_CMD) | 1734 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1735 cmd->vdev_id = arg->vdev_id; 1736 ether_addr_copy(cmd->peer_macaddr.addr, arg->macaddr); 1737 cmd->key_idx = arg->key_idx; 1738 cmd->key_flags = arg->key_flags; 1739 cmd->key_cipher = arg->key_cipher; 1740 cmd->key_len = arg->key_len; 1741 cmd->key_txmic_len = arg->key_txmic_len; 1742 cmd->key_rxmic_len = arg->key_rxmic_len; 1743 1744 if (arg->key_rsc_counter) 1745 memcpy(&cmd->key_rsc_counter, &arg->key_rsc_counter, 1746 sizeof(struct wmi_key_seq_counter)); 1747 1748 tlv = (struct wmi_tlv *)(skb->data + sizeof(*cmd)); 1749 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_BYTE) | 1750 FIELD_PREP(WMI_TLV_LEN, key_len_aligned); 1751 if (arg->key_data) 1752 memcpy(tlv->value, (u8 *)arg->key_data, key_len_aligned); 1753 1754 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_VDEV_INSTALL_KEY_CMDID); 1755 if (ret) { 1756 ath11k_warn(ar->ab, 1757 "failed to send WMI_VDEV_INSTALL_KEY cmd\n"); 1758 dev_kfree_skb(skb); 1759 } 1760 1761 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1762 "WMI vdev install key idx %d cipher %d len %d\n", 1763 arg->key_idx, arg->key_cipher, arg->key_len); 1764 1765 return ret; 1766 } 1767 1768 static inline void 1769 ath11k_wmi_copy_peer_flags(struct wmi_peer_assoc_complete_cmd *cmd, 1770 struct peer_assoc_params *param, 1771 bool hw_crypto_disabled) 1772 { 1773 cmd->peer_flags = 0; 1774 1775 if (param->is_wme_set) { 1776 if (param->qos_flag) 1777 cmd->peer_flags |= WMI_PEER_QOS; 1778 if (param->apsd_flag) 1779 cmd->peer_flags |= WMI_PEER_APSD; 1780 if (param->ht_flag) 1781 cmd->peer_flags |= WMI_PEER_HT; 1782 if (param->bw_40) 1783 cmd->peer_flags |= WMI_PEER_40MHZ; 1784 if (param->bw_80) 1785 cmd->peer_flags |= WMI_PEER_80MHZ; 1786 if (param->bw_160) 1787 cmd->peer_flags |= WMI_PEER_160MHZ; 1788 1789 /* Typically if STBC is enabled for VHT it should be enabled 1790 * for HT as well 1791 **/ 1792 if (param->stbc_flag) 1793 cmd->peer_flags |= WMI_PEER_STBC; 1794 1795 /* Typically if LDPC is enabled for VHT it should be enabled 1796 * for HT as well 1797 **/ 1798 if (param->ldpc_flag) 1799 cmd->peer_flags |= WMI_PEER_LDPC; 1800 1801 if (param->static_mimops_flag) 1802 cmd->peer_flags |= WMI_PEER_STATIC_MIMOPS; 1803 if (param->dynamic_mimops_flag) 1804 cmd->peer_flags |= WMI_PEER_DYN_MIMOPS; 1805 if (param->spatial_mux_flag) 1806 cmd->peer_flags |= WMI_PEER_SPATIAL_MUX; 1807 if (param->vht_flag) 1808 cmd->peer_flags |= WMI_PEER_VHT; 1809 if (param->he_flag) 1810 cmd->peer_flags |= WMI_PEER_HE; 1811 if (param->twt_requester) 1812 cmd->peer_flags |= WMI_PEER_TWT_REQ; 1813 if (param->twt_responder) 1814 cmd->peer_flags |= WMI_PEER_TWT_RESP; 1815 } 1816 1817 /* Suppress authorization for all AUTH modes that need 4-way handshake 1818 * (during re-association). 1819 * Authorization will be done for these modes on key installation. 1820 */ 1821 if (param->auth_flag) 1822 cmd->peer_flags |= WMI_PEER_AUTH; 1823 if (param->need_ptk_4_way) { 1824 cmd->peer_flags |= WMI_PEER_NEED_PTK_4_WAY; 1825 if (!hw_crypto_disabled && param->is_assoc) 1826 cmd->peer_flags &= ~WMI_PEER_AUTH; 1827 } 1828 if (param->need_gtk_2_way) 1829 cmd->peer_flags |= WMI_PEER_NEED_GTK_2_WAY; 1830 /* safe mode bypass the 4-way handshake */ 1831 if (param->safe_mode_enabled) 1832 cmd->peer_flags &= ~(WMI_PEER_NEED_PTK_4_WAY | 1833 WMI_PEER_NEED_GTK_2_WAY); 1834 1835 if (param->is_pmf_enabled) 1836 cmd->peer_flags |= WMI_PEER_PMF; 1837 1838 /* Disable AMSDU for station transmit, if user configures it */ 1839 /* Disable AMSDU for AP transmit to 11n Stations, if user configures 1840 * it 1841 * if (param->amsdu_disable) Add after FW support 1842 **/ 1843 1844 /* Target asserts if node is marked HT and all MCS is set to 0. 1845 * Mark the node as non-HT if all the mcs rates are disabled through 1846 * iwpriv 1847 **/ 1848 if (param->peer_ht_rates.num_rates == 0) 1849 cmd->peer_flags &= ~WMI_PEER_HT; 1850 } 1851 1852 int ath11k_wmi_send_peer_assoc_cmd(struct ath11k *ar, 1853 struct peer_assoc_params *param) 1854 { 1855 struct ath11k_pdev_wmi *wmi = ar->wmi; 1856 struct wmi_peer_assoc_complete_cmd *cmd; 1857 struct wmi_vht_rate_set *mcs; 1858 struct wmi_he_rate_set *he_mcs; 1859 struct sk_buff *skb; 1860 struct wmi_tlv *tlv; 1861 void *ptr; 1862 u32 peer_legacy_rates_align; 1863 u32 peer_ht_rates_align; 1864 int i, ret, len; 1865 1866 peer_legacy_rates_align = roundup(param->peer_legacy_rates.num_rates, 1867 sizeof(u32)); 1868 peer_ht_rates_align = roundup(param->peer_ht_rates.num_rates, 1869 sizeof(u32)); 1870 1871 len = sizeof(*cmd) + 1872 TLV_HDR_SIZE + (peer_legacy_rates_align * sizeof(u8)) + 1873 TLV_HDR_SIZE + (peer_ht_rates_align * sizeof(u8)) + 1874 sizeof(*mcs) + TLV_HDR_SIZE + 1875 (sizeof(*he_mcs) * param->peer_he_mcs_count); 1876 1877 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 1878 if (!skb) 1879 return -ENOMEM; 1880 1881 ptr = skb->data; 1882 1883 cmd = ptr; 1884 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1885 WMI_TAG_PEER_ASSOC_COMPLETE_CMD) | 1886 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 1887 1888 cmd->vdev_id = param->vdev_id; 1889 1890 cmd->peer_new_assoc = param->peer_new_assoc; 1891 cmd->peer_associd = param->peer_associd; 1892 1893 ath11k_wmi_copy_peer_flags(cmd, param, 1894 test_bit(ATH11K_FLAG_HW_CRYPTO_DISABLED, 1895 &ar->ab->dev_flags)); 1896 1897 ether_addr_copy(cmd->peer_macaddr.addr, param->peer_mac); 1898 1899 cmd->peer_rate_caps = param->peer_rate_caps; 1900 cmd->peer_caps = param->peer_caps; 1901 cmd->peer_listen_intval = param->peer_listen_intval; 1902 cmd->peer_ht_caps = param->peer_ht_caps; 1903 cmd->peer_max_mpdu = param->peer_max_mpdu; 1904 cmd->peer_mpdu_density = param->peer_mpdu_density; 1905 cmd->peer_vht_caps = param->peer_vht_caps; 1906 cmd->peer_phymode = param->peer_phymode; 1907 1908 /* Update 11ax capabilities */ 1909 cmd->peer_he_cap_info = param->peer_he_cap_macinfo[0]; 1910 cmd->peer_he_cap_info_ext = param->peer_he_cap_macinfo[1]; 1911 cmd->peer_he_cap_info_internal = param->peer_he_cap_macinfo_internal; 1912 cmd->peer_he_caps_6ghz = param->peer_he_caps_6ghz; 1913 cmd->peer_he_ops = param->peer_he_ops; 1914 memcpy(&cmd->peer_he_cap_phy, ¶m->peer_he_cap_phyinfo, 1915 sizeof(param->peer_he_cap_phyinfo)); 1916 memcpy(&cmd->peer_ppet, ¶m->peer_ppet, 1917 sizeof(param->peer_ppet)); 1918 1919 /* Update peer legacy rate information */ 1920 ptr += sizeof(*cmd); 1921 1922 tlv = ptr; 1923 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_BYTE) | 1924 FIELD_PREP(WMI_TLV_LEN, peer_legacy_rates_align); 1925 1926 ptr += TLV_HDR_SIZE; 1927 1928 cmd->num_peer_legacy_rates = param->peer_legacy_rates.num_rates; 1929 memcpy(ptr, param->peer_legacy_rates.rates, 1930 param->peer_legacy_rates.num_rates); 1931 1932 /* Update peer HT rate information */ 1933 ptr += peer_legacy_rates_align; 1934 1935 tlv = ptr; 1936 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_BYTE) | 1937 FIELD_PREP(WMI_TLV_LEN, peer_ht_rates_align); 1938 ptr += TLV_HDR_SIZE; 1939 cmd->num_peer_ht_rates = param->peer_ht_rates.num_rates; 1940 memcpy(ptr, param->peer_ht_rates.rates, 1941 param->peer_ht_rates.num_rates); 1942 1943 /* VHT Rates */ 1944 ptr += peer_ht_rates_align; 1945 1946 mcs = ptr; 1947 1948 mcs->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_VHT_RATE_SET) | 1949 FIELD_PREP(WMI_TLV_LEN, sizeof(*mcs) - TLV_HDR_SIZE); 1950 1951 cmd->peer_nss = param->peer_nss; 1952 1953 /* Update bandwidth-NSS mapping */ 1954 cmd->peer_bw_rxnss_override = 0; 1955 cmd->peer_bw_rxnss_override |= param->peer_bw_rxnss_override; 1956 1957 if (param->vht_capable) { 1958 mcs->rx_max_rate = param->rx_max_rate; 1959 mcs->rx_mcs_set = param->rx_mcs_set; 1960 mcs->tx_max_rate = param->tx_max_rate; 1961 mcs->tx_mcs_set = param->tx_mcs_set; 1962 } 1963 1964 /* HE Rates */ 1965 cmd->peer_he_mcs = param->peer_he_mcs_count; 1966 cmd->min_data_rate = param->min_data_rate; 1967 1968 ptr += sizeof(*mcs); 1969 1970 len = param->peer_he_mcs_count * sizeof(*he_mcs); 1971 1972 tlv = ptr; 1973 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_STRUCT) | 1974 FIELD_PREP(WMI_TLV_LEN, len); 1975 ptr += TLV_HDR_SIZE; 1976 1977 /* Loop through the HE rate set */ 1978 for (i = 0; i < param->peer_he_mcs_count; i++) { 1979 he_mcs = ptr; 1980 he_mcs->tlv_header = FIELD_PREP(WMI_TLV_TAG, 1981 WMI_TAG_HE_RATE_SET) | 1982 FIELD_PREP(WMI_TLV_LEN, 1983 sizeof(*he_mcs) - TLV_HDR_SIZE); 1984 1985 he_mcs->rx_mcs_set = param->peer_he_tx_mcs_set[i]; 1986 he_mcs->tx_mcs_set = param->peer_he_rx_mcs_set[i]; 1987 ptr += sizeof(*he_mcs); 1988 } 1989 1990 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_PEER_ASSOC_CMDID); 1991 if (ret) { 1992 ath11k_warn(ar->ab, 1993 "failed to send WMI_PEER_ASSOC_CMDID\n"); 1994 dev_kfree_skb(skb); 1995 } 1996 1997 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 1998 "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\n", 1999 cmd->vdev_id, cmd->peer_associd, param->peer_mac, 2000 cmd->peer_flags, cmd->peer_rate_caps, cmd->peer_caps, 2001 cmd->peer_listen_intval, cmd->peer_ht_caps, 2002 cmd->peer_max_mpdu, cmd->peer_nss, cmd->peer_phymode, 2003 cmd->peer_mpdu_density, 2004 cmd->peer_vht_caps, cmd->peer_he_cap_info, 2005 cmd->peer_he_ops, cmd->peer_he_cap_info_ext, 2006 cmd->peer_he_cap_phy[0], cmd->peer_he_cap_phy[1], 2007 cmd->peer_he_cap_phy[2], 2008 cmd->peer_bw_rxnss_override); 2009 2010 return ret; 2011 } 2012 2013 void ath11k_wmi_start_scan_init(struct ath11k *ar, 2014 struct scan_req_params *arg) 2015 { 2016 /* setup commonly used values */ 2017 arg->scan_req_id = 1; 2018 if (ar->state_11d == ATH11K_11D_PREPARING) 2019 arg->scan_priority = WMI_SCAN_PRIORITY_MEDIUM; 2020 else 2021 arg->scan_priority = WMI_SCAN_PRIORITY_LOW; 2022 arg->dwell_time_active = 50; 2023 arg->dwell_time_active_2g = 0; 2024 arg->dwell_time_passive = 150; 2025 arg->dwell_time_active_6g = 40; 2026 arg->dwell_time_passive_6g = 30; 2027 arg->min_rest_time = 50; 2028 arg->max_rest_time = 500; 2029 arg->repeat_probe_time = 0; 2030 arg->probe_spacing_time = 0; 2031 arg->idle_time = 0; 2032 arg->max_scan_time = 20000; 2033 arg->probe_delay = 5; 2034 arg->notify_scan_events = WMI_SCAN_EVENT_STARTED | 2035 WMI_SCAN_EVENT_COMPLETED | 2036 WMI_SCAN_EVENT_BSS_CHANNEL | 2037 WMI_SCAN_EVENT_FOREIGN_CHAN | 2038 WMI_SCAN_EVENT_DEQUEUED; 2039 arg->scan_flags |= WMI_SCAN_CHAN_STAT_EVENT; 2040 arg->num_bssid = 1; 2041 2042 /* fill bssid_list[0] with 0xff, otherwise bssid and RA will be 2043 * ZEROs in probe request 2044 */ 2045 eth_broadcast_addr(arg->bssid_list[0].addr); 2046 } 2047 2048 static inline void 2049 ath11k_wmi_copy_scan_event_cntrl_flags(struct wmi_start_scan_cmd *cmd, 2050 struct scan_req_params *param) 2051 { 2052 /* Scan events subscription */ 2053 if (param->scan_ev_started) 2054 cmd->notify_scan_events |= WMI_SCAN_EVENT_STARTED; 2055 if (param->scan_ev_completed) 2056 cmd->notify_scan_events |= WMI_SCAN_EVENT_COMPLETED; 2057 if (param->scan_ev_bss_chan) 2058 cmd->notify_scan_events |= WMI_SCAN_EVENT_BSS_CHANNEL; 2059 if (param->scan_ev_foreign_chan) 2060 cmd->notify_scan_events |= WMI_SCAN_EVENT_FOREIGN_CHAN; 2061 if (param->scan_ev_dequeued) 2062 cmd->notify_scan_events |= WMI_SCAN_EVENT_DEQUEUED; 2063 if (param->scan_ev_preempted) 2064 cmd->notify_scan_events |= WMI_SCAN_EVENT_PREEMPTED; 2065 if (param->scan_ev_start_failed) 2066 cmd->notify_scan_events |= WMI_SCAN_EVENT_START_FAILED; 2067 if (param->scan_ev_restarted) 2068 cmd->notify_scan_events |= WMI_SCAN_EVENT_RESTARTED; 2069 if (param->scan_ev_foreign_chn_exit) 2070 cmd->notify_scan_events |= WMI_SCAN_EVENT_FOREIGN_CHAN_EXIT; 2071 if (param->scan_ev_suspended) 2072 cmd->notify_scan_events |= WMI_SCAN_EVENT_SUSPENDED; 2073 if (param->scan_ev_resumed) 2074 cmd->notify_scan_events |= WMI_SCAN_EVENT_RESUMED; 2075 2076 /** Set scan control flags */ 2077 cmd->scan_ctrl_flags = 0; 2078 if (param->scan_f_passive) 2079 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_PASSIVE; 2080 if (param->scan_f_strict_passive_pch) 2081 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_STRICT_PASSIVE_ON_PCHN; 2082 if (param->scan_f_promisc_mode) 2083 cmd->scan_ctrl_flags |= WMI_SCAN_FILTER_PROMISCUOS; 2084 if (param->scan_f_capture_phy_err) 2085 cmd->scan_ctrl_flags |= WMI_SCAN_CAPTURE_PHY_ERROR; 2086 if (param->scan_f_half_rate) 2087 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_HALF_RATE_SUPPORT; 2088 if (param->scan_f_quarter_rate) 2089 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_QUARTER_RATE_SUPPORT; 2090 if (param->scan_f_cck_rates) 2091 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_CCK_RATES; 2092 if (param->scan_f_ofdm_rates) 2093 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_OFDM_RATES; 2094 if (param->scan_f_chan_stat_evnt) 2095 cmd->scan_ctrl_flags |= WMI_SCAN_CHAN_STAT_EVENT; 2096 if (param->scan_f_filter_prb_req) 2097 cmd->scan_ctrl_flags |= WMI_SCAN_FILTER_PROBE_REQ; 2098 if (param->scan_f_bcast_probe) 2099 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_BCAST_PROBE_REQ; 2100 if (param->scan_f_offchan_mgmt_tx) 2101 cmd->scan_ctrl_flags |= WMI_SCAN_OFFCHAN_MGMT_TX; 2102 if (param->scan_f_offchan_data_tx) 2103 cmd->scan_ctrl_flags |= WMI_SCAN_OFFCHAN_DATA_TX; 2104 if (param->scan_f_force_active_dfs_chn) 2105 cmd->scan_ctrl_flags |= WMI_SCAN_FLAG_FORCE_ACTIVE_ON_DFS; 2106 if (param->scan_f_add_tpc_ie_in_probe) 2107 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_TPC_IE_IN_PROBE_REQ; 2108 if (param->scan_f_add_ds_ie_in_probe) 2109 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_DS_IE_IN_PROBE_REQ; 2110 if (param->scan_f_add_spoofed_mac_in_probe) 2111 cmd->scan_ctrl_flags |= WMI_SCAN_ADD_SPOOF_MAC_IN_PROBE_REQ; 2112 if (param->scan_f_add_rand_seq_in_probe) 2113 cmd->scan_ctrl_flags |= WMI_SCAN_RANDOM_SEQ_NO_IN_PROBE_REQ; 2114 if (param->scan_f_en_ie_whitelist_in_probe) 2115 cmd->scan_ctrl_flags |= 2116 WMI_SCAN_ENABLE_IE_WHTELIST_IN_PROBE_REQ; 2117 2118 /* for adaptive scan mode using 3 bits (21 - 23 bits) */ 2119 WMI_SCAN_SET_DWELL_MODE(cmd->scan_ctrl_flags, 2120 param->adaptive_dwell_time_mode); 2121 } 2122 2123 int ath11k_wmi_send_scan_start_cmd(struct ath11k *ar, 2124 struct scan_req_params *params) 2125 { 2126 struct ath11k_pdev_wmi *wmi = ar->wmi; 2127 struct wmi_start_scan_cmd *cmd; 2128 struct wmi_ssid *ssid = NULL; 2129 struct wmi_mac_addr *bssid; 2130 struct sk_buff *skb; 2131 struct wmi_tlv *tlv; 2132 void *ptr; 2133 int i, ret, len; 2134 u32 *tmp_ptr; 2135 u16 extraie_len_with_pad = 0; 2136 struct hint_short_ssid *s_ssid = NULL; 2137 struct hint_bssid *hint_bssid = NULL; 2138 2139 len = sizeof(*cmd); 2140 2141 len += TLV_HDR_SIZE; 2142 if (params->num_chan) 2143 len += params->num_chan * sizeof(u32); 2144 2145 len += TLV_HDR_SIZE; 2146 if (params->num_ssids) 2147 len += params->num_ssids * sizeof(*ssid); 2148 2149 len += TLV_HDR_SIZE; 2150 if (params->num_bssid) 2151 len += sizeof(*bssid) * params->num_bssid; 2152 2153 len += TLV_HDR_SIZE; 2154 if (params->extraie.len && params->extraie.len <= 0xFFFF) 2155 extraie_len_with_pad = 2156 roundup(params->extraie.len, sizeof(u32)); 2157 len += extraie_len_with_pad; 2158 2159 if (params->num_hint_bssid) 2160 len += TLV_HDR_SIZE + 2161 params->num_hint_bssid * sizeof(struct hint_bssid); 2162 2163 if (params->num_hint_s_ssid) 2164 len += TLV_HDR_SIZE + 2165 params->num_hint_s_ssid * sizeof(struct hint_short_ssid); 2166 2167 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 2168 if (!skb) 2169 return -ENOMEM; 2170 2171 ptr = skb->data; 2172 2173 cmd = ptr; 2174 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_START_SCAN_CMD) | 2175 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2176 2177 cmd->scan_id = params->scan_id; 2178 cmd->scan_req_id = params->scan_req_id; 2179 cmd->vdev_id = params->vdev_id; 2180 cmd->scan_priority = params->scan_priority; 2181 cmd->notify_scan_events = params->notify_scan_events; 2182 2183 ath11k_wmi_copy_scan_event_cntrl_flags(cmd, params); 2184 2185 cmd->dwell_time_active = params->dwell_time_active; 2186 cmd->dwell_time_active_2g = params->dwell_time_active_2g; 2187 cmd->dwell_time_passive = params->dwell_time_passive; 2188 cmd->dwell_time_active_6g = params->dwell_time_active_6g; 2189 cmd->dwell_time_passive_6g = params->dwell_time_passive_6g; 2190 cmd->min_rest_time = params->min_rest_time; 2191 cmd->max_rest_time = params->max_rest_time; 2192 cmd->repeat_probe_time = params->repeat_probe_time; 2193 cmd->probe_spacing_time = params->probe_spacing_time; 2194 cmd->idle_time = params->idle_time; 2195 cmd->max_scan_time = params->max_scan_time; 2196 cmd->probe_delay = params->probe_delay; 2197 cmd->burst_duration = params->burst_duration; 2198 cmd->num_chan = params->num_chan; 2199 cmd->num_bssid = params->num_bssid; 2200 cmd->num_ssids = params->num_ssids; 2201 cmd->ie_len = params->extraie.len; 2202 cmd->n_probes = params->n_probes; 2203 ether_addr_copy(cmd->mac_addr.addr, params->mac_addr.addr); 2204 ether_addr_copy(cmd->mac_mask.addr, params->mac_mask.addr); 2205 2206 ptr += sizeof(*cmd); 2207 2208 len = params->num_chan * sizeof(u32); 2209 2210 tlv = ptr; 2211 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_UINT32) | 2212 FIELD_PREP(WMI_TLV_LEN, len); 2213 ptr += TLV_HDR_SIZE; 2214 tmp_ptr = (u32 *)ptr; 2215 2216 for (i = 0; i < params->num_chan; ++i) 2217 tmp_ptr[i] = params->chan_list[i]; 2218 2219 ptr += len; 2220 2221 len = params->num_ssids * sizeof(*ssid); 2222 tlv = ptr; 2223 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_FIXED_STRUCT) | 2224 FIELD_PREP(WMI_TLV_LEN, len); 2225 2226 ptr += TLV_HDR_SIZE; 2227 2228 if (params->num_ssids) { 2229 ssid = ptr; 2230 for (i = 0; i < params->num_ssids; ++i) { 2231 ssid->ssid_len = params->ssid[i].length; 2232 memcpy(ssid->ssid, params->ssid[i].ssid, 2233 params->ssid[i].length); 2234 ssid++; 2235 } 2236 } 2237 2238 ptr += (params->num_ssids * sizeof(*ssid)); 2239 len = params->num_bssid * sizeof(*bssid); 2240 tlv = ptr; 2241 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_FIXED_STRUCT) | 2242 FIELD_PREP(WMI_TLV_LEN, len); 2243 2244 ptr += TLV_HDR_SIZE; 2245 bssid = ptr; 2246 2247 if (params->num_bssid) { 2248 for (i = 0; i < params->num_bssid; ++i) { 2249 ether_addr_copy(bssid->addr, 2250 params->bssid_list[i].addr); 2251 bssid++; 2252 } 2253 } 2254 2255 ptr += params->num_bssid * sizeof(*bssid); 2256 2257 len = extraie_len_with_pad; 2258 tlv = ptr; 2259 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_BYTE) | 2260 FIELD_PREP(WMI_TLV_LEN, len); 2261 ptr += TLV_HDR_SIZE; 2262 2263 if (extraie_len_with_pad) 2264 memcpy(ptr, params->extraie.ptr, 2265 params->extraie.len); 2266 2267 ptr += extraie_len_with_pad; 2268 2269 if (params->num_hint_s_ssid) { 2270 len = params->num_hint_s_ssid * sizeof(struct hint_short_ssid); 2271 tlv = ptr; 2272 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_FIXED_STRUCT) | 2273 FIELD_PREP(WMI_TLV_LEN, len); 2274 ptr += TLV_HDR_SIZE; 2275 s_ssid = ptr; 2276 for (i = 0; i < params->num_hint_s_ssid; ++i) { 2277 s_ssid->freq_flags = params->hint_s_ssid[i].freq_flags; 2278 s_ssid->short_ssid = params->hint_s_ssid[i].short_ssid; 2279 s_ssid++; 2280 } 2281 ptr += len; 2282 } 2283 2284 if (params->num_hint_bssid) { 2285 len = params->num_hint_bssid * sizeof(struct hint_bssid); 2286 tlv = ptr; 2287 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_FIXED_STRUCT) | 2288 FIELD_PREP(WMI_TLV_LEN, len); 2289 ptr += TLV_HDR_SIZE; 2290 hint_bssid = ptr; 2291 for (i = 0; i < params->num_hint_bssid; ++i) { 2292 hint_bssid->freq_flags = 2293 params->hint_bssid[i].freq_flags; 2294 ether_addr_copy(¶ms->hint_bssid[i].bssid.addr[0], 2295 &hint_bssid->bssid.addr[0]); 2296 hint_bssid++; 2297 } 2298 } 2299 2300 ret = ath11k_wmi_cmd_send(wmi, skb, 2301 WMI_START_SCAN_CMDID); 2302 if (ret) { 2303 ath11k_warn(ar->ab, "failed to send WMI_START_SCAN_CMDID\n"); 2304 dev_kfree_skb(skb); 2305 } 2306 2307 return ret; 2308 } 2309 2310 int ath11k_wmi_send_scan_stop_cmd(struct ath11k *ar, 2311 struct scan_cancel_param *param) 2312 { 2313 struct ath11k_pdev_wmi *wmi = ar->wmi; 2314 struct wmi_stop_scan_cmd *cmd; 2315 struct sk_buff *skb; 2316 int ret; 2317 2318 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2319 if (!skb) 2320 return -ENOMEM; 2321 2322 cmd = (struct wmi_stop_scan_cmd *)skb->data; 2323 2324 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_STOP_SCAN_CMD) | 2325 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2326 2327 cmd->vdev_id = param->vdev_id; 2328 cmd->requestor = param->requester; 2329 cmd->scan_id = param->scan_id; 2330 cmd->pdev_id = param->pdev_id; 2331 /* stop the scan with the corresponding scan_id */ 2332 if (param->req_type == WLAN_SCAN_CANCEL_PDEV_ALL) { 2333 /* Cancelling all scans */ 2334 cmd->req_type = WMI_SCAN_STOP_ALL; 2335 } else if (param->req_type == WLAN_SCAN_CANCEL_VDEV_ALL) { 2336 /* Cancelling VAP scans */ 2337 cmd->req_type = WMI_SCN_STOP_VAP_ALL; 2338 } else if (param->req_type == WLAN_SCAN_CANCEL_SINGLE) { 2339 /* Cancelling specific scan */ 2340 cmd->req_type = WMI_SCAN_STOP_ONE; 2341 } else { 2342 ath11k_warn(ar->ab, "invalid scan cancel param %d", 2343 param->req_type); 2344 dev_kfree_skb(skb); 2345 return -EINVAL; 2346 } 2347 2348 ret = ath11k_wmi_cmd_send(wmi, skb, 2349 WMI_STOP_SCAN_CMDID); 2350 if (ret) { 2351 ath11k_warn(ar->ab, "failed to send WMI_STOP_SCAN_CMDID\n"); 2352 dev_kfree_skb(skb); 2353 } 2354 2355 return ret; 2356 } 2357 2358 int ath11k_wmi_send_scan_chan_list_cmd(struct ath11k *ar, 2359 struct scan_chan_list_params *chan_list) 2360 { 2361 struct ath11k_pdev_wmi *wmi = ar->wmi; 2362 struct wmi_scan_chan_list_cmd *cmd; 2363 struct sk_buff *skb; 2364 struct wmi_channel *chan_info; 2365 struct channel_param *tchan_info; 2366 struct wmi_tlv *tlv; 2367 void *ptr; 2368 int i, ret, len; 2369 u16 num_send_chans, num_sends = 0, max_chan_limit = 0; 2370 u32 *reg1, *reg2; 2371 2372 tchan_info = chan_list->ch_param; 2373 while (chan_list->nallchans) { 2374 len = sizeof(*cmd) + TLV_HDR_SIZE; 2375 max_chan_limit = (wmi->wmi_ab->max_msg_len[ar->pdev_idx] - len) / 2376 sizeof(*chan_info); 2377 2378 if (chan_list->nallchans > max_chan_limit) 2379 num_send_chans = max_chan_limit; 2380 else 2381 num_send_chans = chan_list->nallchans; 2382 2383 chan_list->nallchans -= num_send_chans; 2384 len += sizeof(*chan_info) * num_send_chans; 2385 2386 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 2387 if (!skb) 2388 return -ENOMEM; 2389 2390 cmd = (struct wmi_scan_chan_list_cmd *)skb->data; 2391 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_SCAN_CHAN_LIST_CMD) | 2392 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2393 cmd->pdev_id = chan_list->pdev_id; 2394 cmd->num_scan_chans = num_send_chans; 2395 if (num_sends) 2396 cmd->flags |= WMI_APPEND_TO_EXISTING_CHAN_LIST_FLAG; 2397 2398 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2399 "WMI no.of chan = %d len = %d pdev_id = %d num_sends = %d\n", 2400 num_send_chans, len, cmd->pdev_id, num_sends); 2401 2402 ptr = skb->data + sizeof(*cmd); 2403 2404 len = sizeof(*chan_info) * num_send_chans; 2405 tlv = ptr; 2406 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_STRUCT) | 2407 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 2408 ptr += TLV_HDR_SIZE; 2409 2410 for (i = 0; i < num_send_chans; ++i) { 2411 chan_info = ptr; 2412 memset(chan_info, 0, sizeof(*chan_info)); 2413 len = sizeof(*chan_info); 2414 chan_info->tlv_header = FIELD_PREP(WMI_TLV_TAG, 2415 WMI_TAG_CHANNEL) | 2416 FIELD_PREP(WMI_TLV_LEN, 2417 len - TLV_HDR_SIZE); 2418 2419 reg1 = &chan_info->reg_info_1; 2420 reg2 = &chan_info->reg_info_2; 2421 chan_info->mhz = tchan_info->mhz; 2422 chan_info->band_center_freq1 = tchan_info->cfreq1; 2423 chan_info->band_center_freq2 = tchan_info->cfreq2; 2424 2425 if (tchan_info->is_chan_passive) 2426 chan_info->info |= WMI_CHAN_INFO_PASSIVE; 2427 if (tchan_info->allow_he) 2428 chan_info->info |= WMI_CHAN_INFO_ALLOW_HE; 2429 else if (tchan_info->allow_vht) 2430 chan_info->info |= WMI_CHAN_INFO_ALLOW_VHT; 2431 else if (tchan_info->allow_ht) 2432 chan_info->info |= WMI_CHAN_INFO_ALLOW_HT; 2433 if (tchan_info->half_rate) 2434 chan_info->info |= WMI_CHAN_INFO_HALF_RATE; 2435 if (tchan_info->quarter_rate) 2436 chan_info->info |= WMI_CHAN_INFO_QUARTER_RATE; 2437 if (tchan_info->psc_channel) 2438 chan_info->info |= WMI_CHAN_INFO_PSC; 2439 if (tchan_info->dfs_set) 2440 chan_info->info |= WMI_CHAN_INFO_DFS; 2441 2442 chan_info->info |= FIELD_PREP(WMI_CHAN_INFO_MODE, 2443 tchan_info->phy_mode); 2444 *reg1 |= FIELD_PREP(WMI_CHAN_REG_INFO1_MIN_PWR, 2445 tchan_info->minpower); 2446 *reg1 |= FIELD_PREP(WMI_CHAN_REG_INFO1_MAX_PWR, 2447 tchan_info->maxpower); 2448 *reg1 |= FIELD_PREP(WMI_CHAN_REG_INFO1_MAX_REG_PWR, 2449 tchan_info->maxregpower); 2450 *reg1 |= FIELD_PREP(WMI_CHAN_REG_INFO1_REG_CLS, 2451 tchan_info->reg_class_id); 2452 *reg2 |= FIELD_PREP(WMI_CHAN_REG_INFO2_ANT_MAX, 2453 tchan_info->antennamax); 2454 *reg2 |= FIELD_PREP(WMI_CHAN_REG_INFO2_MAX_TX_PWR, 2455 tchan_info->maxregpower); 2456 2457 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2458 "WMI chan scan list chan[%d] = %u, chan_info->info %8x\n", 2459 i, chan_info->mhz, chan_info->info); 2460 2461 ptr += sizeof(*chan_info); 2462 2463 tchan_info++; 2464 } 2465 2466 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_SCAN_CHAN_LIST_CMDID); 2467 if (ret) { 2468 ath11k_warn(ar->ab, "failed to send WMI_SCAN_CHAN_LIST cmd\n"); 2469 dev_kfree_skb(skb); 2470 return ret; 2471 } 2472 2473 num_sends++; 2474 } 2475 2476 return 0; 2477 } 2478 2479 int ath11k_wmi_send_wmm_update_cmd_tlv(struct ath11k *ar, u32 vdev_id, 2480 struct wmi_wmm_params_all_arg *param) 2481 { 2482 struct ath11k_pdev_wmi *wmi = ar->wmi; 2483 struct wmi_vdev_set_wmm_params_cmd *cmd; 2484 struct wmi_wmm_params *wmm_param; 2485 struct wmi_wmm_params_arg *wmi_wmm_arg; 2486 struct sk_buff *skb; 2487 int ret, ac; 2488 2489 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2490 if (!skb) 2491 return -ENOMEM; 2492 2493 cmd = (struct wmi_vdev_set_wmm_params_cmd *)skb->data; 2494 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 2495 WMI_TAG_VDEV_SET_WMM_PARAMS_CMD) | 2496 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2497 2498 cmd->vdev_id = vdev_id; 2499 cmd->wmm_param_type = 0; 2500 2501 for (ac = 0; ac < WME_NUM_AC; ac++) { 2502 switch (ac) { 2503 case WME_AC_BE: 2504 wmi_wmm_arg = ¶m->ac_be; 2505 break; 2506 case WME_AC_BK: 2507 wmi_wmm_arg = ¶m->ac_bk; 2508 break; 2509 case WME_AC_VI: 2510 wmi_wmm_arg = ¶m->ac_vi; 2511 break; 2512 case WME_AC_VO: 2513 wmi_wmm_arg = ¶m->ac_vo; 2514 break; 2515 } 2516 2517 wmm_param = (struct wmi_wmm_params *)&cmd->wmm_params[ac]; 2518 wmm_param->tlv_header = 2519 FIELD_PREP(WMI_TLV_TAG, 2520 WMI_TAG_VDEV_SET_WMM_PARAMS_CMD) | 2521 FIELD_PREP(WMI_TLV_LEN, 2522 sizeof(*wmm_param) - TLV_HDR_SIZE); 2523 2524 wmm_param->aifs = wmi_wmm_arg->aifs; 2525 wmm_param->cwmin = wmi_wmm_arg->cwmin; 2526 wmm_param->cwmax = wmi_wmm_arg->cwmax; 2527 wmm_param->txoplimit = wmi_wmm_arg->txop; 2528 wmm_param->acm = wmi_wmm_arg->acm; 2529 wmm_param->no_ack = wmi_wmm_arg->no_ack; 2530 2531 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2532 "wmi wmm set ac %d aifs %d cwmin %d cwmax %d txop %d acm %d no_ack %d\n", 2533 ac, wmm_param->aifs, wmm_param->cwmin, 2534 wmm_param->cwmax, wmm_param->txoplimit, 2535 wmm_param->acm, wmm_param->no_ack); 2536 } 2537 ret = ath11k_wmi_cmd_send(wmi, skb, 2538 WMI_VDEV_SET_WMM_PARAMS_CMDID); 2539 if (ret) { 2540 ath11k_warn(ar->ab, 2541 "failed to send WMI_VDEV_SET_WMM_PARAMS_CMDID"); 2542 dev_kfree_skb(skb); 2543 } 2544 2545 return ret; 2546 } 2547 2548 int ath11k_wmi_send_dfs_phyerr_offload_enable_cmd(struct ath11k *ar, 2549 u32 pdev_id) 2550 { 2551 struct ath11k_pdev_wmi *wmi = ar->wmi; 2552 struct wmi_dfs_phyerr_offload_cmd *cmd; 2553 struct sk_buff *skb; 2554 int ret; 2555 2556 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2557 if (!skb) 2558 return -ENOMEM; 2559 2560 cmd = (struct wmi_dfs_phyerr_offload_cmd *)skb->data; 2561 cmd->tlv_header = 2562 FIELD_PREP(WMI_TLV_TAG, 2563 WMI_TAG_PDEV_DFS_PHYERR_OFFLOAD_ENABLE_CMD) | 2564 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2565 2566 cmd->pdev_id = pdev_id; 2567 2568 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2569 "WMI dfs phy err offload enable pdev id %d\n", pdev_id); 2570 2571 ret = ath11k_wmi_cmd_send(wmi, skb, 2572 WMI_PDEV_DFS_PHYERR_OFFLOAD_ENABLE_CMDID); 2573 if (ret) { 2574 ath11k_warn(ar->ab, 2575 "failed to send WMI_PDEV_DFS_PHYERR_OFFLOAD_ENABLE cmd\n"); 2576 dev_kfree_skb(skb); 2577 } 2578 2579 return ret; 2580 } 2581 2582 int ath11k_wmi_delba_send(struct ath11k *ar, u32 vdev_id, const u8 *mac, 2583 u32 tid, u32 initiator, u32 reason) 2584 { 2585 struct ath11k_pdev_wmi *wmi = ar->wmi; 2586 struct wmi_delba_send_cmd *cmd; 2587 struct sk_buff *skb; 2588 int ret; 2589 2590 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2591 if (!skb) 2592 return -ENOMEM; 2593 2594 cmd = (struct wmi_delba_send_cmd *)skb->data; 2595 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_DELBA_SEND_CMD) | 2596 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2597 cmd->vdev_id = vdev_id; 2598 ether_addr_copy(cmd->peer_macaddr.addr, mac); 2599 cmd->tid = tid; 2600 cmd->initiator = initiator; 2601 cmd->reasoncode = reason; 2602 2603 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2604 "wmi delba send vdev_id 0x%X mac_addr %pM tid %u initiator %u reason %u\n", 2605 vdev_id, mac, tid, initiator, reason); 2606 2607 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_DELBA_SEND_CMDID); 2608 2609 if (ret) { 2610 ath11k_warn(ar->ab, 2611 "failed to send WMI_DELBA_SEND_CMDID cmd\n"); 2612 dev_kfree_skb(skb); 2613 } 2614 2615 return ret; 2616 } 2617 2618 int ath11k_wmi_addba_set_resp(struct ath11k *ar, u32 vdev_id, const u8 *mac, 2619 u32 tid, u32 status) 2620 { 2621 struct ath11k_pdev_wmi *wmi = ar->wmi; 2622 struct wmi_addba_setresponse_cmd *cmd; 2623 struct sk_buff *skb; 2624 int ret; 2625 2626 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2627 if (!skb) 2628 return -ENOMEM; 2629 2630 cmd = (struct wmi_addba_setresponse_cmd *)skb->data; 2631 cmd->tlv_header = 2632 FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ADDBA_SETRESPONSE_CMD) | 2633 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2634 cmd->vdev_id = vdev_id; 2635 ether_addr_copy(cmd->peer_macaddr.addr, mac); 2636 cmd->tid = tid; 2637 cmd->statuscode = status; 2638 2639 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2640 "wmi addba set resp vdev_id 0x%X mac_addr %pM tid %u status %u\n", 2641 vdev_id, mac, tid, status); 2642 2643 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_ADDBA_SET_RESP_CMDID); 2644 2645 if (ret) { 2646 ath11k_warn(ar->ab, 2647 "failed to send WMI_ADDBA_SET_RESP_CMDID cmd\n"); 2648 dev_kfree_skb(skb); 2649 } 2650 2651 return ret; 2652 } 2653 2654 int ath11k_wmi_addba_send(struct ath11k *ar, u32 vdev_id, const u8 *mac, 2655 u32 tid, u32 buf_size) 2656 { 2657 struct ath11k_pdev_wmi *wmi = ar->wmi; 2658 struct wmi_addba_send_cmd *cmd; 2659 struct sk_buff *skb; 2660 int ret; 2661 2662 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2663 if (!skb) 2664 return -ENOMEM; 2665 2666 cmd = (struct wmi_addba_send_cmd *)skb->data; 2667 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ADDBA_SEND_CMD) | 2668 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2669 cmd->vdev_id = vdev_id; 2670 ether_addr_copy(cmd->peer_macaddr.addr, mac); 2671 cmd->tid = tid; 2672 cmd->buffersize = buf_size; 2673 2674 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2675 "wmi addba send vdev_id 0x%X mac_addr %pM tid %u bufsize %u\n", 2676 vdev_id, mac, tid, buf_size); 2677 2678 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_ADDBA_SEND_CMDID); 2679 2680 if (ret) { 2681 ath11k_warn(ar->ab, 2682 "failed to send WMI_ADDBA_SEND_CMDID cmd\n"); 2683 dev_kfree_skb(skb); 2684 } 2685 2686 return ret; 2687 } 2688 2689 int ath11k_wmi_addba_clear_resp(struct ath11k *ar, u32 vdev_id, const u8 *mac) 2690 { 2691 struct ath11k_pdev_wmi *wmi = ar->wmi; 2692 struct wmi_addba_clear_resp_cmd *cmd; 2693 struct sk_buff *skb; 2694 int ret; 2695 2696 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2697 if (!skb) 2698 return -ENOMEM; 2699 2700 cmd = (struct wmi_addba_clear_resp_cmd *)skb->data; 2701 cmd->tlv_header = 2702 FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ADDBA_CLEAR_RESP_CMD) | 2703 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2704 cmd->vdev_id = vdev_id; 2705 ether_addr_copy(cmd->peer_macaddr.addr, mac); 2706 2707 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2708 "wmi addba clear resp vdev_id 0x%X mac_addr %pM\n", 2709 vdev_id, mac); 2710 2711 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_ADDBA_CLEAR_RESP_CMDID); 2712 2713 if (ret) { 2714 ath11k_warn(ar->ab, 2715 "failed to send WMI_ADDBA_CLEAR_RESP_CMDID cmd\n"); 2716 dev_kfree_skb(skb); 2717 } 2718 2719 return ret; 2720 } 2721 2722 int ath11k_wmi_pdev_peer_pktlog_filter(struct ath11k *ar, u8 *addr, u8 enable) 2723 { 2724 struct ath11k_pdev_wmi *wmi = ar->wmi; 2725 struct wmi_pdev_pktlog_filter_cmd *cmd; 2726 struct wmi_pdev_pktlog_filter_info *info; 2727 struct sk_buff *skb; 2728 struct wmi_tlv *tlv; 2729 void *ptr; 2730 int ret, len; 2731 2732 len = sizeof(*cmd) + sizeof(*info) + TLV_HDR_SIZE; 2733 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 2734 if (!skb) 2735 return -ENOMEM; 2736 2737 cmd = (struct wmi_pdev_pktlog_filter_cmd *)skb->data; 2738 2739 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_PEER_PKTLOG_FILTER_CMD) | 2740 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2741 2742 cmd->pdev_id = DP_HW2SW_MACID(ar->pdev->pdev_id); 2743 cmd->num_mac = 1; 2744 cmd->enable = enable; 2745 2746 ptr = skb->data + sizeof(*cmd); 2747 2748 tlv = ptr; 2749 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_STRUCT) | 2750 FIELD_PREP(WMI_TLV_LEN, sizeof(*info)); 2751 2752 ptr += TLV_HDR_SIZE; 2753 info = ptr; 2754 2755 ether_addr_copy(info->peer_macaddr.addr, addr); 2756 info->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_PEER_PKTLOG_FILTER_INFO) | 2757 FIELD_PREP(WMI_TLV_LEN, 2758 sizeof(*info) - TLV_HDR_SIZE); 2759 2760 ret = ath11k_wmi_cmd_send(wmi, skb, 2761 WMI_PDEV_PKTLOG_FILTER_CMDID); 2762 if (ret) { 2763 ath11k_warn(ar->ab, "failed to send WMI_PDEV_PKTLOG_ENABLE_CMDID\n"); 2764 dev_kfree_skb(skb); 2765 } 2766 2767 return ret; 2768 } 2769 2770 int 2771 ath11k_wmi_send_init_country_cmd(struct ath11k *ar, 2772 struct wmi_init_country_params init_cc_params) 2773 { 2774 struct ath11k_pdev_wmi *wmi = ar->wmi; 2775 struct wmi_init_country_cmd *cmd; 2776 struct sk_buff *skb; 2777 int ret; 2778 2779 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2780 if (!skb) 2781 return -ENOMEM; 2782 2783 cmd = (struct wmi_init_country_cmd *)skb->data; 2784 cmd->tlv_header = 2785 FIELD_PREP(WMI_TLV_TAG, 2786 WMI_TAG_SET_INIT_COUNTRY_CMD) | 2787 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2788 2789 cmd->pdev_id = ar->pdev->pdev_id; 2790 2791 switch (init_cc_params.flags) { 2792 case ALPHA_IS_SET: 2793 cmd->init_cc_type = WMI_COUNTRY_INFO_TYPE_ALPHA; 2794 memcpy((u8 *)&cmd->cc_info.alpha2, 2795 init_cc_params.cc_info.alpha2, 3); 2796 break; 2797 case CC_IS_SET: 2798 cmd->init_cc_type = WMI_COUNTRY_INFO_TYPE_COUNTRY_CODE; 2799 cmd->cc_info.country_code = init_cc_params.cc_info.country_code; 2800 break; 2801 case REGDMN_IS_SET: 2802 cmd->init_cc_type = WMI_COUNTRY_INFO_TYPE_REGDOMAIN; 2803 cmd->cc_info.regdom_id = init_cc_params.cc_info.regdom_id; 2804 break; 2805 default: 2806 ret = -EINVAL; 2807 goto out; 2808 } 2809 2810 ret = ath11k_wmi_cmd_send(wmi, skb, 2811 WMI_SET_INIT_COUNTRY_CMDID); 2812 2813 out: 2814 if (ret) { 2815 ath11k_warn(ar->ab, 2816 "failed to send WMI_SET_INIT_COUNTRY CMD :%d\n", 2817 ret); 2818 dev_kfree_skb(skb); 2819 } 2820 2821 return ret; 2822 } 2823 2824 int ath11k_wmi_send_set_current_country_cmd(struct ath11k *ar, 2825 struct wmi_set_current_country_params *param) 2826 { 2827 struct ath11k_pdev_wmi *wmi = ar->wmi; 2828 struct wmi_set_current_country_cmd *cmd; 2829 struct sk_buff *skb; 2830 int ret; 2831 2832 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2833 if (!skb) 2834 return -ENOMEM; 2835 2836 cmd = (struct wmi_set_current_country_cmd *)skb->data; 2837 cmd->tlv_header = 2838 FIELD_PREP(WMI_TLV_TAG, WMI_TAG_SET_CURRENT_COUNTRY_CMD) | 2839 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2840 2841 cmd->pdev_id = ar->pdev->pdev_id; 2842 memcpy(&cmd->new_alpha2, ¶m->alpha2, 3); 2843 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_SET_CURRENT_COUNTRY_CMDID); 2844 2845 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2846 "set current country pdev id %d alpha2 %c%c\n", 2847 ar->pdev->pdev_id, 2848 param->alpha2[0], 2849 param->alpha2[1]); 2850 2851 if (ret) { 2852 ath11k_warn(ar->ab, 2853 "failed to send WMI_SET_CURRENT_COUNTRY_CMDID: %d\n", ret); 2854 dev_kfree_skb(skb); 2855 } 2856 2857 return ret; 2858 } 2859 2860 int 2861 ath11k_wmi_send_thermal_mitigation_param_cmd(struct ath11k *ar, 2862 struct thermal_mitigation_params *param) 2863 { 2864 struct ath11k_pdev_wmi *wmi = ar->wmi; 2865 struct wmi_therm_throt_config_request_cmd *cmd; 2866 struct wmi_therm_throt_level_config_info *lvl_conf; 2867 struct wmi_tlv *tlv; 2868 struct sk_buff *skb; 2869 int i, ret, len; 2870 2871 len = sizeof(*cmd) + TLV_HDR_SIZE + 2872 THERMAL_LEVELS * sizeof(struct wmi_therm_throt_level_config_info); 2873 2874 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 2875 if (!skb) 2876 return -ENOMEM; 2877 2878 cmd = (struct wmi_therm_throt_config_request_cmd *)skb->data; 2879 2880 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_THERM_THROT_CONFIG_REQUEST) | 2881 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2882 2883 cmd->pdev_id = ar->pdev->pdev_id; 2884 cmd->enable = param->enable; 2885 cmd->dc = param->dc; 2886 cmd->dc_per_event = param->dc_per_event; 2887 cmd->therm_throt_levels = THERMAL_LEVELS; 2888 2889 tlv = (struct wmi_tlv *)(skb->data + sizeof(*cmd)); 2890 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_STRUCT) | 2891 FIELD_PREP(WMI_TLV_LEN, 2892 (THERMAL_LEVELS * 2893 sizeof(struct wmi_therm_throt_level_config_info))); 2894 2895 lvl_conf = (struct wmi_therm_throt_level_config_info *)(skb->data + 2896 sizeof(*cmd) + 2897 TLV_HDR_SIZE); 2898 for (i = 0; i < THERMAL_LEVELS; i++) { 2899 lvl_conf->tlv_header = 2900 FIELD_PREP(WMI_TLV_TAG, WMI_TAG_THERM_THROT_LEVEL_CONFIG_INFO) | 2901 FIELD_PREP(WMI_TLV_LEN, sizeof(*lvl_conf) - TLV_HDR_SIZE); 2902 2903 lvl_conf->temp_lwm = param->levelconf[i].tmplwm; 2904 lvl_conf->temp_hwm = param->levelconf[i].tmphwm; 2905 lvl_conf->dc_off_percent = param->levelconf[i].dcoffpercent; 2906 lvl_conf->prio = param->levelconf[i].priority; 2907 lvl_conf++; 2908 } 2909 2910 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_THERM_THROT_SET_CONF_CMDID); 2911 if (ret) { 2912 ath11k_warn(ar->ab, "failed to send THERM_THROT_SET_CONF cmd\n"); 2913 dev_kfree_skb(skb); 2914 } 2915 2916 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2917 "WMI vdev set thermal throt pdev_id %d enable %d dc %d dc_per_event %x levels %d\n", 2918 ar->pdev->pdev_id, param->enable, param->dc, 2919 param->dc_per_event, THERMAL_LEVELS); 2920 2921 return ret; 2922 } 2923 2924 int ath11k_wmi_send_11d_scan_start_cmd(struct ath11k *ar, 2925 struct wmi_11d_scan_start_params *param) 2926 { 2927 struct ath11k_pdev_wmi *wmi = ar->wmi; 2928 struct wmi_11d_scan_start_cmd *cmd; 2929 struct sk_buff *skb; 2930 int ret; 2931 2932 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2933 if (!skb) 2934 return -ENOMEM; 2935 2936 cmd = (struct wmi_11d_scan_start_cmd *)skb->data; 2937 cmd->tlv_header = 2938 FIELD_PREP(WMI_TLV_TAG, WMI_TAG_11D_SCAN_START_CMD) | 2939 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2940 2941 cmd->vdev_id = param->vdev_id; 2942 cmd->scan_period_msec = param->scan_period_msec; 2943 cmd->start_interval_msec = param->start_interval_msec; 2944 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_11D_SCAN_START_CMDID); 2945 2946 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2947 "send 11d scan start vdev id %d period %d ms internal %d ms\n", 2948 cmd->vdev_id, 2949 cmd->scan_period_msec, 2950 cmd->start_interval_msec); 2951 2952 if (ret) { 2953 ath11k_warn(ar->ab, 2954 "failed to send WMI_11D_SCAN_START_CMDID: %d\n", ret); 2955 dev_kfree_skb(skb); 2956 } 2957 2958 return ret; 2959 } 2960 2961 int ath11k_wmi_send_11d_scan_stop_cmd(struct ath11k *ar, u32 vdev_id) 2962 { 2963 struct ath11k_pdev_wmi *wmi = ar->wmi; 2964 struct wmi_11d_scan_stop_cmd *cmd; 2965 struct sk_buff *skb; 2966 int ret; 2967 2968 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 2969 if (!skb) 2970 return -ENOMEM; 2971 2972 cmd = (struct wmi_11d_scan_stop_cmd *)skb->data; 2973 cmd->tlv_header = 2974 FIELD_PREP(WMI_TLV_TAG, WMI_TAG_11D_SCAN_STOP_CMD) | 2975 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 2976 2977 cmd->vdev_id = vdev_id; 2978 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_11D_SCAN_STOP_CMDID); 2979 2980 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 2981 "send 11d scan stop vdev id %d\n", 2982 cmd->vdev_id); 2983 2984 if (ret) { 2985 ath11k_warn(ar->ab, 2986 "failed to send WMI_11D_SCAN_STOP_CMDID: %d\n", ret); 2987 dev_kfree_skb(skb); 2988 } 2989 2990 return ret; 2991 } 2992 2993 int ath11k_wmi_pdev_pktlog_enable(struct ath11k *ar, u32 pktlog_filter) 2994 { 2995 struct ath11k_pdev_wmi *wmi = ar->wmi; 2996 struct wmi_pktlog_enable_cmd *cmd; 2997 struct sk_buff *skb; 2998 int ret; 2999 3000 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 3001 if (!skb) 3002 return -ENOMEM; 3003 3004 cmd = (struct wmi_pktlog_enable_cmd *)skb->data; 3005 3006 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_PKTLOG_ENABLE_CMD) | 3007 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 3008 3009 cmd->pdev_id = DP_HW2SW_MACID(ar->pdev->pdev_id); 3010 cmd->evlist = pktlog_filter; 3011 cmd->enable = ATH11K_WMI_PKTLOG_ENABLE_FORCE; 3012 3013 ret = ath11k_wmi_cmd_send(wmi, skb, 3014 WMI_PDEV_PKTLOG_ENABLE_CMDID); 3015 if (ret) { 3016 ath11k_warn(ar->ab, "failed to send WMI_PDEV_PKTLOG_ENABLE_CMDID\n"); 3017 dev_kfree_skb(skb); 3018 } 3019 3020 return ret; 3021 } 3022 3023 int ath11k_wmi_pdev_pktlog_disable(struct ath11k *ar) 3024 { 3025 struct ath11k_pdev_wmi *wmi = ar->wmi; 3026 struct wmi_pktlog_disable_cmd *cmd; 3027 struct sk_buff *skb; 3028 int ret; 3029 3030 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); 3031 if (!skb) 3032 return -ENOMEM; 3033 3034 cmd = (struct wmi_pktlog_disable_cmd *)skb->data; 3035 3036 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_PKTLOG_DISABLE_CMD) | 3037 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 3038 3039 cmd->pdev_id = DP_HW2SW_MACID(ar->pdev->pdev_id); 3040 3041 ret = ath11k_wmi_cmd_send(wmi, skb, 3042 WMI_PDEV_PKTLOG_DISABLE_CMDID); 3043 if (ret) { 3044 ath11k_warn(ar->ab, "failed to send WMI_PDEV_PKTLOG_ENABLE_CMDID\n"); 3045 dev_kfree_skb(skb); 3046 } 3047 3048 return ret; 3049 } 3050 3051 int 3052 ath11k_wmi_send_twt_enable_cmd(struct ath11k *ar, u32 pdev_id) 3053 { 3054 struct ath11k_pdev_wmi *wmi = ar->wmi; 3055 struct ath11k_base *ab = wmi->wmi_ab->ab; 3056 struct wmi_twt_enable_params_cmd *cmd; 3057 struct sk_buff *skb; 3058 int ret, len; 3059 3060 len = sizeof(*cmd); 3061 3062 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3063 if (!skb) 3064 return -ENOMEM; 3065 3066 cmd = (struct wmi_twt_enable_params_cmd *)skb->data; 3067 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_TWT_ENABLE_CMD) | 3068 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3069 cmd->pdev_id = pdev_id; 3070 cmd->sta_cong_timer_ms = ATH11K_TWT_DEF_STA_CONG_TIMER_MS; 3071 cmd->default_slot_size = ATH11K_TWT_DEF_DEFAULT_SLOT_SIZE; 3072 cmd->congestion_thresh_setup = ATH11K_TWT_DEF_CONGESTION_THRESH_SETUP; 3073 cmd->congestion_thresh_teardown = 3074 ATH11K_TWT_DEF_CONGESTION_THRESH_TEARDOWN; 3075 cmd->congestion_thresh_critical = 3076 ATH11K_TWT_DEF_CONGESTION_THRESH_CRITICAL; 3077 cmd->interference_thresh_teardown = 3078 ATH11K_TWT_DEF_INTERFERENCE_THRESH_TEARDOWN; 3079 cmd->interference_thresh_setup = 3080 ATH11K_TWT_DEF_INTERFERENCE_THRESH_SETUP; 3081 cmd->min_no_sta_setup = ATH11K_TWT_DEF_MIN_NO_STA_SETUP; 3082 cmd->min_no_sta_teardown = ATH11K_TWT_DEF_MIN_NO_STA_TEARDOWN; 3083 cmd->no_of_bcast_mcast_slots = ATH11K_TWT_DEF_NO_OF_BCAST_MCAST_SLOTS; 3084 cmd->min_no_twt_slots = ATH11K_TWT_DEF_MIN_NO_TWT_SLOTS; 3085 cmd->max_no_sta_twt = ATH11K_TWT_DEF_MAX_NO_STA_TWT; 3086 cmd->mode_check_interval = ATH11K_TWT_DEF_MODE_CHECK_INTERVAL; 3087 cmd->add_sta_slot_interval = ATH11K_TWT_DEF_ADD_STA_SLOT_INTERVAL; 3088 cmd->remove_sta_slot_interval = 3089 ATH11K_TWT_DEF_REMOVE_STA_SLOT_INTERVAL; 3090 /* TODO add MBSSID support */ 3091 cmd->mbss_support = 0; 3092 3093 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_TWT_ENABLE_CMDID); 3094 if (ret) { 3095 ath11k_warn(ab, "Failed to send WMI_TWT_ENABLE_CMDID"); 3096 dev_kfree_skb(skb); 3097 } else { 3098 ar->twt_enabled = 1; 3099 } 3100 return ret; 3101 } 3102 3103 int 3104 ath11k_wmi_send_twt_disable_cmd(struct ath11k *ar, u32 pdev_id) 3105 { 3106 struct ath11k_pdev_wmi *wmi = ar->wmi; 3107 struct ath11k_base *ab = wmi->wmi_ab->ab; 3108 struct wmi_twt_disable_params_cmd *cmd; 3109 struct sk_buff *skb; 3110 int ret, len; 3111 3112 len = sizeof(*cmd); 3113 3114 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3115 if (!skb) 3116 return -ENOMEM; 3117 3118 cmd = (struct wmi_twt_disable_params_cmd *)skb->data; 3119 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_TWT_DISABLE_CMD) | 3120 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3121 cmd->pdev_id = pdev_id; 3122 3123 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_TWT_DISABLE_CMDID); 3124 if (ret) { 3125 ath11k_warn(ab, "Failed to send WMI_TWT_DISABLE_CMDID"); 3126 dev_kfree_skb(skb); 3127 } else { 3128 ar->twt_enabled = 0; 3129 } 3130 return ret; 3131 } 3132 3133 int ath11k_wmi_send_twt_add_dialog_cmd(struct ath11k *ar, 3134 struct wmi_twt_add_dialog_params *params) 3135 { 3136 struct ath11k_pdev_wmi *wmi = ar->wmi; 3137 struct ath11k_base *ab = wmi->wmi_ab->ab; 3138 struct wmi_twt_add_dialog_params_cmd *cmd; 3139 struct sk_buff *skb; 3140 int ret, len; 3141 3142 len = sizeof(*cmd); 3143 3144 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3145 if (!skb) 3146 return -ENOMEM; 3147 3148 cmd = (struct wmi_twt_add_dialog_params_cmd *)skb->data; 3149 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_TWT_ADD_DIALOG_CMD) | 3150 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3151 3152 cmd->vdev_id = params->vdev_id; 3153 ether_addr_copy(cmd->peer_macaddr.addr, params->peer_macaddr); 3154 cmd->dialog_id = params->dialog_id; 3155 cmd->wake_intvl_us = params->wake_intvl_us; 3156 cmd->wake_intvl_mantis = params->wake_intvl_mantis; 3157 cmd->wake_dura_us = params->wake_dura_us; 3158 cmd->sp_offset_us = params->sp_offset_us; 3159 cmd->flags = params->twt_cmd; 3160 if (params->flag_bcast) 3161 cmd->flags |= WMI_TWT_ADD_DIALOG_FLAG_BCAST; 3162 if (params->flag_trigger) 3163 cmd->flags |= WMI_TWT_ADD_DIALOG_FLAG_TRIGGER; 3164 if (params->flag_flow_type) 3165 cmd->flags |= WMI_TWT_ADD_DIALOG_FLAG_FLOW_TYPE; 3166 if (params->flag_protection) 3167 cmd->flags |= WMI_TWT_ADD_DIALOG_FLAG_PROTECTION; 3168 3169 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3170 "wmi add twt dialog vdev %u dialog id %u wake interval %u mantissa %u wake duration %u service period offset %u flags 0x%x\n", 3171 cmd->vdev_id, cmd->dialog_id, cmd->wake_intvl_us, 3172 cmd->wake_intvl_mantis, cmd->wake_dura_us, cmd->sp_offset_us, 3173 cmd->flags); 3174 3175 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_TWT_ADD_DIALOG_CMDID); 3176 3177 if (ret) { 3178 ath11k_warn(ab, 3179 "failed to send wmi command to add twt dialog: %d", 3180 ret); 3181 dev_kfree_skb(skb); 3182 } 3183 return ret; 3184 } 3185 3186 int ath11k_wmi_send_twt_del_dialog_cmd(struct ath11k *ar, 3187 struct wmi_twt_del_dialog_params *params) 3188 { 3189 struct ath11k_pdev_wmi *wmi = ar->wmi; 3190 struct ath11k_base *ab = wmi->wmi_ab->ab; 3191 struct wmi_twt_del_dialog_params_cmd *cmd; 3192 struct sk_buff *skb; 3193 int ret, len; 3194 3195 len = sizeof(*cmd); 3196 3197 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3198 if (!skb) 3199 return -ENOMEM; 3200 3201 cmd = (struct wmi_twt_del_dialog_params_cmd *)skb->data; 3202 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_TWT_DEL_DIALOG_CMD) | 3203 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3204 3205 cmd->vdev_id = params->vdev_id; 3206 ether_addr_copy(cmd->peer_macaddr.addr, params->peer_macaddr); 3207 cmd->dialog_id = params->dialog_id; 3208 3209 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3210 "wmi delete twt dialog vdev %u dialog id %u\n", 3211 cmd->vdev_id, cmd->dialog_id); 3212 3213 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_TWT_DEL_DIALOG_CMDID); 3214 if (ret) { 3215 ath11k_warn(ab, 3216 "failed to send wmi command to delete twt dialog: %d", 3217 ret); 3218 dev_kfree_skb(skb); 3219 } 3220 return ret; 3221 } 3222 3223 int ath11k_wmi_send_twt_pause_dialog_cmd(struct ath11k *ar, 3224 struct wmi_twt_pause_dialog_params *params) 3225 { 3226 struct ath11k_pdev_wmi *wmi = ar->wmi; 3227 struct ath11k_base *ab = wmi->wmi_ab->ab; 3228 struct wmi_twt_pause_dialog_params_cmd *cmd; 3229 struct sk_buff *skb; 3230 int ret, len; 3231 3232 len = sizeof(*cmd); 3233 3234 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3235 if (!skb) 3236 return -ENOMEM; 3237 3238 cmd = (struct wmi_twt_pause_dialog_params_cmd *)skb->data; 3239 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 3240 WMI_TAG_TWT_PAUSE_DIALOG_CMD) | 3241 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3242 3243 cmd->vdev_id = params->vdev_id; 3244 ether_addr_copy(cmd->peer_macaddr.addr, params->peer_macaddr); 3245 cmd->dialog_id = params->dialog_id; 3246 3247 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3248 "wmi pause twt dialog vdev %u dialog id %u\n", 3249 cmd->vdev_id, cmd->dialog_id); 3250 3251 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_TWT_PAUSE_DIALOG_CMDID); 3252 if (ret) { 3253 ath11k_warn(ab, 3254 "failed to send wmi command to pause twt dialog: %d", 3255 ret); 3256 dev_kfree_skb(skb); 3257 } 3258 return ret; 3259 } 3260 3261 int ath11k_wmi_send_twt_resume_dialog_cmd(struct ath11k *ar, 3262 struct wmi_twt_resume_dialog_params *params) 3263 { 3264 struct ath11k_pdev_wmi *wmi = ar->wmi; 3265 struct ath11k_base *ab = wmi->wmi_ab->ab; 3266 struct wmi_twt_resume_dialog_params_cmd *cmd; 3267 struct sk_buff *skb; 3268 int ret, len; 3269 3270 len = sizeof(*cmd); 3271 3272 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3273 if (!skb) 3274 return -ENOMEM; 3275 3276 cmd = (struct wmi_twt_resume_dialog_params_cmd *)skb->data; 3277 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 3278 WMI_TAG_TWT_RESUME_DIALOG_CMD) | 3279 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3280 3281 cmd->vdev_id = params->vdev_id; 3282 ether_addr_copy(cmd->peer_macaddr.addr, params->peer_macaddr); 3283 cmd->dialog_id = params->dialog_id; 3284 cmd->sp_offset_us = params->sp_offset_us; 3285 cmd->next_twt_size = params->next_twt_size; 3286 3287 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3288 "wmi resume twt dialog vdev %u dialog id %u service period offset %u next twt subfield size %u\n", 3289 cmd->vdev_id, cmd->dialog_id, cmd->sp_offset_us, 3290 cmd->next_twt_size); 3291 3292 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_TWT_RESUME_DIALOG_CMDID); 3293 if (ret) { 3294 ath11k_warn(ab, 3295 "failed to send wmi command to resume twt dialog: %d", 3296 ret); 3297 dev_kfree_skb(skb); 3298 } 3299 return ret; 3300 } 3301 3302 int 3303 ath11k_wmi_send_obss_spr_cmd(struct ath11k *ar, u32 vdev_id, 3304 struct ieee80211_he_obss_pd *he_obss_pd) 3305 { 3306 struct ath11k_pdev_wmi *wmi = ar->wmi; 3307 struct ath11k_base *ab = wmi->wmi_ab->ab; 3308 struct wmi_obss_spatial_reuse_params_cmd *cmd; 3309 struct sk_buff *skb; 3310 int ret, len; 3311 3312 len = sizeof(*cmd); 3313 3314 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3315 if (!skb) 3316 return -ENOMEM; 3317 3318 cmd = (struct wmi_obss_spatial_reuse_params_cmd *)skb->data; 3319 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 3320 WMI_TAG_OBSS_SPATIAL_REUSE_SET_CMD) | 3321 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3322 cmd->vdev_id = vdev_id; 3323 cmd->enable = he_obss_pd->enable; 3324 cmd->obss_min = he_obss_pd->min_offset; 3325 cmd->obss_max = he_obss_pd->max_offset; 3326 3327 ret = ath11k_wmi_cmd_send(wmi, skb, 3328 WMI_PDEV_OBSS_PD_SPATIAL_REUSE_CMDID); 3329 if (ret) { 3330 ath11k_warn(ab, 3331 "Failed to send WMI_PDEV_OBSS_PD_SPATIAL_REUSE_CMDID"); 3332 dev_kfree_skb(skb); 3333 } 3334 return ret; 3335 } 3336 3337 int 3338 ath11k_wmi_pdev_set_srg_bss_color_bitmap(struct ath11k *ar, u32 *bitmap) 3339 { 3340 struct ath11k_pdev_wmi *wmi = ar->wmi; 3341 struct ath11k_base *ab = wmi->wmi_ab->ab; 3342 struct wmi_pdev_obss_pd_bitmap_cmd *cmd; 3343 struct sk_buff *skb; 3344 int ret, len; 3345 3346 len = sizeof(*cmd); 3347 3348 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3349 if (!skb) 3350 return -ENOMEM; 3351 3352 cmd = (struct wmi_pdev_obss_pd_bitmap_cmd *)skb->data; 3353 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 3354 WMI_TAG_PDEV_SRG_BSS_COLOR_BITMAP_CMD) | 3355 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3356 cmd->pdev_id = ar->pdev->pdev_id; 3357 memcpy(cmd->bitmap, bitmap, sizeof(cmd->bitmap)); 3358 3359 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3360 "obss pd pdev_id %d bss color bitmap %08x %08x\n", 3361 cmd->pdev_id, cmd->bitmap[0], cmd->bitmap[1]); 3362 3363 ret = ath11k_wmi_cmd_send(wmi, skb, 3364 WMI_PDEV_SET_SRG_BSS_COLOR_BITMAP_CMDID); 3365 if (ret) { 3366 ath11k_warn(ab, 3367 "failed to send WMI_PDEV_SET_SRG_BSS_COLOR_BITMAP_CMDID"); 3368 dev_kfree_skb(skb); 3369 } 3370 3371 return ret; 3372 } 3373 3374 int 3375 ath11k_wmi_pdev_set_srg_patial_bssid_bitmap(struct ath11k *ar, u32 *bitmap) 3376 { 3377 struct ath11k_pdev_wmi *wmi = ar->wmi; 3378 struct ath11k_base *ab = wmi->wmi_ab->ab; 3379 struct wmi_pdev_obss_pd_bitmap_cmd *cmd; 3380 struct sk_buff *skb; 3381 int ret, len; 3382 3383 len = sizeof(*cmd); 3384 3385 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3386 if (!skb) 3387 return -ENOMEM; 3388 3389 cmd = (struct wmi_pdev_obss_pd_bitmap_cmd *)skb->data; 3390 cmd->tlv_header = 3391 FIELD_PREP(WMI_TLV_TAG, 3392 WMI_TAG_PDEV_SRG_PARTIAL_BSSID_BITMAP_CMD) | 3393 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3394 cmd->pdev_id = ar->pdev->pdev_id; 3395 memcpy(cmd->bitmap, bitmap, sizeof(cmd->bitmap)); 3396 3397 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3398 "obss pd pdev_id %d partial bssid bitmap %08x %08x\n", 3399 cmd->pdev_id, cmd->bitmap[0], cmd->bitmap[1]); 3400 3401 ret = ath11k_wmi_cmd_send(wmi, skb, 3402 WMI_PDEV_SET_SRG_PARTIAL_BSSID_BITMAP_CMDID); 3403 if (ret) { 3404 ath11k_warn(ab, 3405 "failed to send WMI_PDEV_SET_SRG_PARTIAL_BSSID_BITMAP_CMDID"); 3406 dev_kfree_skb(skb); 3407 } 3408 3409 return ret; 3410 } 3411 3412 int 3413 ath11k_wmi_pdev_srg_obss_color_enable_bitmap(struct ath11k *ar, u32 *bitmap) 3414 { 3415 struct ath11k_pdev_wmi *wmi = ar->wmi; 3416 struct ath11k_base *ab = wmi->wmi_ab->ab; 3417 struct wmi_pdev_obss_pd_bitmap_cmd *cmd; 3418 struct sk_buff *skb; 3419 int ret, len; 3420 3421 len = sizeof(*cmd); 3422 3423 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3424 if (!skb) 3425 return -ENOMEM; 3426 3427 cmd = (struct wmi_pdev_obss_pd_bitmap_cmd *)skb->data; 3428 cmd->tlv_header = 3429 FIELD_PREP(WMI_TLV_TAG, 3430 WMI_TAG_PDEV_SRG_OBSS_COLOR_ENABLE_BITMAP_CMD) | 3431 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3432 cmd->pdev_id = ar->pdev->pdev_id; 3433 memcpy(cmd->bitmap, bitmap, sizeof(cmd->bitmap)); 3434 3435 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3436 "obss pd srg pdev_id %d bss color enable bitmap %08x %08x\n", 3437 cmd->pdev_id, cmd->bitmap[0], cmd->bitmap[1]); 3438 3439 ret = ath11k_wmi_cmd_send(wmi, skb, 3440 WMI_PDEV_SET_SRG_OBSS_COLOR_ENABLE_BITMAP_CMDID); 3441 if (ret) { 3442 ath11k_warn(ab, 3443 "failed to send WMI_PDEV_SET_SRG_OBSS_COLOR_ENABLE_BITMAP_CMDID"); 3444 dev_kfree_skb(skb); 3445 } 3446 3447 return ret; 3448 } 3449 3450 int 3451 ath11k_wmi_pdev_srg_obss_bssid_enable_bitmap(struct ath11k *ar, u32 *bitmap) 3452 { 3453 struct ath11k_pdev_wmi *wmi = ar->wmi; 3454 struct ath11k_base *ab = wmi->wmi_ab->ab; 3455 struct wmi_pdev_obss_pd_bitmap_cmd *cmd; 3456 struct sk_buff *skb; 3457 int ret, len; 3458 3459 len = sizeof(*cmd); 3460 3461 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3462 if (!skb) 3463 return -ENOMEM; 3464 3465 cmd = (struct wmi_pdev_obss_pd_bitmap_cmd *)skb->data; 3466 cmd->tlv_header = 3467 FIELD_PREP(WMI_TLV_TAG, 3468 WMI_TAG_PDEV_SRG_OBSS_BSSID_ENABLE_BITMAP_CMD) | 3469 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3470 cmd->pdev_id = ar->pdev->pdev_id; 3471 memcpy(cmd->bitmap, bitmap, sizeof(cmd->bitmap)); 3472 3473 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3474 "obss pd srg pdev_id %d bssid enable bitmap %08x %08x\n", 3475 cmd->pdev_id, cmd->bitmap[0], cmd->bitmap[1]); 3476 3477 ret = ath11k_wmi_cmd_send(wmi, skb, 3478 WMI_PDEV_SET_SRG_OBSS_BSSID_ENABLE_BITMAP_CMDID); 3479 if (ret) { 3480 ath11k_warn(ab, 3481 "failed to send WMI_PDEV_SET_SRG_OBSS_BSSID_ENABLE_BITMAP_CMDID"); 3482 dev_kfree_skb(skb); 3483 } 3484 3485 return ret; 3486 } 3487 3488 int 3489 ath11k_wmi_pdev_non_srg_obss_color_enable_bitmap(struct ath11k *ar, u32 *bitmap) 3490 { 3491 struct ath11k_pdev_wmi *wmi = ar->wmi; 3492 struct ath11k_base *ab = wmi->wmi_ab->ab; 3493 struct wmi_pdev_obss_pd_bitmap_cmd *cmd; 3494 struct sk_buff *skb; 3495 int ret, len; 3496 3497 len = sizeof(*cmd); 3498 3499 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3500 if (!skb) 3501 return -ENOMEM; 3502 3503 cmd = (struct wmi_pdev_obss_pd_bitmap_cmd *)skb->data; 3504 cmd->tlv_header = 3505 FIELD_PREP(WMI_TLV_TAG, 3506 WMI_TAG_PDEV_NON_SRG_OBSS_COLOR_ENABLE_BITMAP_CMD) | 3507 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3508 cmd->pdev_id = ar->pdev->pdev_id; 3509 memcpy(cmd->bitmap, bitmap, sizeof(cmd->bitmap)); 3510 3511 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3512 "obss pd non_srg pdev_id %d bss color enable bitmap %08x %08x\n", 3513 cmd->pdev_id, cmd->bitmap[0], cmd->bitmap[1]); 3514 3515 ret = ath11k_wmi_cmd_send(wmi, skb, 3516 WMI_PDEV_SET_NON_SRG_OBSS_COLOR_ENABLE_BITMAP_CMDID); 3517 if (ret) { 3518 ath11k_warn(ab, 3519 "failed to send WMI_PDEV_SET_NON_SRG_OBSS_COLOR_ENABLE_BITMAP_CMDID"); 3520 dev_kfree_skb(skb); 3521 } 3522 3523 return ret; 3524 } 3525 3526 int 3527 ath11k_wmi_pdev_non_srg_obss_bssid_enable_bitmap(struct ath11k *ar, u32 *bitmap) 3528 { 3529 struct ath11k_pdev_wmi *wmi = ar->wmi; 3530 struct ath11k_base *ab = wmi->wmi_ab->ab; 3531 struct wmi_pdev_obss_pd_bitmap_cmd *cmd; 3532 struct sk_buff *skb; 3533 int ret, len; 3534 3535 len = sizeof(*cmd); 3536 3537 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3538 if (!skb) 3539 return -ENOMEM; 3540 3541 cmd = (struct wmi_pdev_obss_pd_bitmap_cmd *)skb->data; 3542 cmd->tlv_header = 3543 FIELD_PREP(WMI_TLV_TAG, 3544 WMI_TAG_PDEV_NON_SRG_OBSS_BSSID_ENABLE_BITMAP_CMD) | 3545 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3546 cmd->pdev_id = ar->pdev->pdev_id; 3547 memcpy(cmd->bitmap, bitmap, sizeof(cmd->bitmap)); 3548 3549 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3550 "obss pd non_srg pdev_id %d bssid enable bitmap %08x %08x\n", 3551 cmd->pdev_id, cmd->bitmap[0], cmd->bitmap[1]); 3552 3553 ret = ath11k_wmi_cmd_send(wmi, skb, 3554 WMI_PDEV_SET_NON_SRG_OBSS_BSSID_ENABLE_BITMAP_CMDID); 3555 if (ret) { 3556 ath11k_warn(ab, 3557 "failed to send WMI_PDEV_SET_NON_SRG_OBSS_BSSID_ENABLE_BITMAP_CMDID"); 3558 dev_kfree_skb(skb); 3559 } 3560 3561 return ret; 3562 } 3563 3564 int 3565 ath11k_wmi_send_obss_color_collision_cfg_cmd(struct ath11k *ar, u32 vdev_id, 3566 u8 bss_color, u32 period, 3567 bool enable) 3568 { 3569 struct ath11k_pdev_wmi *wmi = ar->wmi; 3570 struct ath11k_base *ab = wmi->wmi_ab->ab; 3571 struct wmi_obss_color_collision_cfg_params_cmd *cmd; 3572 struct sk_buff *skb; 3573 int ret, len; 3574 3575 len = sizeof(*cmd); 3576 3577 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3578 if (!skb) 3579 return -ENOMEM; 3580 3581 cmd = (struct wmi_obss_color_collision_cfg_params_cmd *)skb->data; 3582 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 3583 WMI_TAG_OBSS_COLOR_COLLISION_DET_CONFIG) | 3584 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3585 cmd->vdev_id = vdev_id; 3586 cmd->evt_type = enable ? ATH11K_OBSS_COLOR_COLLISION_DETECTION : 3587 ATH11K_OBSS_COLOR_COLLISION_DETECTION_DISABLE; 3588 cmd->current_bss_color = bss_color; 3589 cmd->detection_period_ms = period; 3590 cmd->scan_period_ms = ATH11K_BSS_COLOR_COLLISION_SCAN_PERIOD_MS; 3591 cmd->free_slot_expiry_time_ms = 0; 3592 cmd->flags = 0; 3593 3594 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3595 "wmi_send_obss_color_collision_cfg id %d type %d bss_color %d detect_period %d scan_period %d\n", 3596 cmd->vdev_id, cmd->evt_type, cmd->current_bss_color, 3597 cmd->detection_period_ms, cmd->scan_period_ms); 3598 3599 ret = ath11k_wmi_cmd_send(wmi, skb, 3600 WMI_OBSS_COLOR_COLLISION_DET_CONFIG_CMDID); 3601 if (ret) { 3602 ath11k_warn(ab, "Failed to send WMI_OBSS_COLOR_COLLISION_DET_CONFIG_CMDID"); 3603 dev_kfree_skb(skb); 3604 } 3605 return ret; 3606 } 3607 3608 int ath11k_wmi_send_bss_color_change_enable_cmd(struct ath11k *ar, u32 vdev_id, 3609 bool enable) 3610 { 3611 struct ath11k_pdev_wmi *wmi = ar->wmi; 3612 struct ath11k_base *ab = wmi->wmi_ab->ab; 3613 struct wmi_bss_color_change_enable_params_cmd *cmd; 3614 struct sk_buff *skb; 3615 int ret, len; 3616 3617 len = sizeof(*cmd); 3618 3619 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3620 if (!skb) 3621 return -ENOMEM; 3622 3623 cmd = (struct wmi_bss_color_change_enable_params_cmd *)skb->data; 3624 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_BSS_COLOR_CHANGE_ENABLE) | 3625 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3626 cmd->vdev_id = vdev_id; 3627 cmd->enable = enable ? 1 : 0; 3628 3629 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3630 "wmi_send_bss_color_change_enable id %d enable %d\n", 3631 cmd->vdev_id, cmd->enable); 3632 3633 ret = ath11k_wmi_cmd_send(wmi, skb, 3634 WMI_BSS_COLOR_CHANGE_ENABLE_CMDID); 3635 if (ret) { 3636 ath11k_warn(ab, "Failed to send WMI_BSS_COLOR_CHANGE_ENABLE_CMDID"); 3637 dev_kfree_skb(skb); 3638 } 3639 return ret; 3640 } 3641 3642 int ath11k_wmi_fils_discovery_tmpl(struct ath11k *ar, u32 vdev_id, 3643 struct sk_buff *tmpl) 3644 { 3645 struct wmi_tlv *tlv; 3646 struct sk_buff *skb; 3647 void *ptr; 3648 int ret, len; 3649 size_t aligned_len; 3650 struct wmi_fils_discovery_tmpl_cmd *cmd; 3651 3652 aligned_len = roundup(tmpl->len, 4); 3653 len = sizeof(*cmd) + TLV_HDR_SIZE + aligned_len; 3654 3655 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3656 "WMI vdev %i set FILS discovery template\n", vdev_id); 3657 3658 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, len); 3659 if (!skb) 3660 return -ENOMEM; 3661 3662 cmd = (struct wmi_fils_discovery_tmpl_cmd *)skb->data; 3663 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 3664 WMI_TAG_FILS_DISCOVERY_TMPL_CMD) | 3665 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 3666 cmd->vdev_id = vdev_id; 3667 cmd->buf_len = tmpl->len; 3668 ptr = skb->data + sizeof(*cmd); 3669 3670 tlv = ptr; 3671 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_BYTE) | 3672 FIELD_PREP(WMI_TLV_LEN, aligned_len); 3673 memcpy(tlv->value, tmpl->data, tmpl->len); 3674 3675 ret = ath11k_wmi_cmd_send(ar->wmi, skb, WMI_FILS_DISCOVERY_TMPL_CMDID); 3676 if (ret) { 3677 ath11k_warn(ar->ab, 3678 "WMI vdev %i failed to send FILS discovery template command\n", 3679 vdev_id); 3680 dev_kfree_skb(skb); 3681 } 3682 return ret; 3683 } 3684 3685 int ath11k_wmi_probe_resp_tmpl(struct ath11k *ar, u32 vdev_id, 3686 struct sk_buff *tmpl) 3687 { 3688 struct wmi_probe_tmpl_cmd *cmd; 3689 struct wmi_bcn_prb_info *probe_info; 3690 struct wmi_tlv *tlv; 3691 struct sk_buff *skb; 3692 void *ptr; 3693 int ret, len; 3694 size_t aligned_len = roundup(tmpl->len, 4); 3695 3696 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3697 "WMI vdev %i set probe response template\n", vdev_id); 3698 3699 len = sizeof(*cmd) + sizeof(*probe_info) + TLV_HDR_SIZE + aligned_len; 3700 3701 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, len); 3702 if (!skb) 3703 return -ENOMEM; 3704 3705 cmd = (struct wmi_probe_tmpl_cmd *)skb->data; 3706 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PRB_TMPL_CMD) | 3707 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 3708 cmd->vdev_id = vdev_id; 3709 cmd->buf_len = tmpl->len; 3710 3711 ptr = skb->data + sizeof(*cmd); 3712 3713 probe_info = ptr; 3714 len = sizeof(*probe_info); 3715 probe_info->tlv_header = FIELD_PREP(WMI_TLV_TAG, 3716 WMI_TAG_BCN_PRB_INFO) | 3717 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3718 probe_info->caps = 0; 3719 probe_info->erp = 0; 3720 3721 ptr += sizeof(*probe_info); 3722 3723 tlv = ptr; 3724 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_BYTE) | 3725 FIELD_PREP(WMI_TLV_LEN, aligned_len); 3726 memcpy(tlv->value, tmpl->data, tmpl->len); 3727 3728 ret = ath11k_wmi_cmd_send(ar->wmi, skb, WMI_PRB_TMPL_CMDID); 3729 if (ret) { 3730 ath11k_warn(ar->ab, 3731 "WMI vdev %i failed to send probe response template command\n", 3732 vdev_id); 3733 dev_kfree_skb(skb); 3734 } 3735 return ret; 3736 } 3737 3738 int ath11k_wmi_fils_discovery(struct ath11k *ar, u32 vdev_id, u32 interval, 3739 bool unsol_bcast_probe_resp_enabled) 3740 { 3741 struct sk_buff *skb; 3742 int ret, len; 3743 struct wmi_fils_discovery_cmd *cmd; 3744 3745 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 3746 "WMI vdev %i set %s interval to %u TU\n", 3747 vdev_id, unsol_bcast_probe_resp_enabled ? 3748 "unsolicited broadcast probe response" : "FILS discovery", 3749 interval); 3750 3751 len = sizeof(*cmd); 3752 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, len); 3753 if (!skb) 3754 return -ENOMEM; 3755 3756 cmd = (struct wmi_fils_discovery_cmd *)skb->data; 3757 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ENABLE_FILS_CMD) | 3758 FIELD_PREP(WMI_TLV_LEN, len - TLV_HDR_SIZE); 3759 cmd->vdev_id = vdev_id; 3760 cmd->interval = interval; 3761 cmd->config = unsol_bcast_probe_resp_enabled; 3762 3763 ret = ath11k_wmi_cmd_send(ar->wmi, skb, WMI_ENABLE_FILS_CMDID); 3764 if (ret) { 3765 ath11k_warn(ar->ab, 3766 "WMI vdev %i failed to send FILS discovery enable/disable command\n", 3767 vdev_id); 3768 dev_kfree_skb(skb); 3769 } 3770 return ret; 3771 } 3772 3773 static void 3774 ath11k_wmi_obss_color_collision_event(struct ath11k_base *ab, struct sk_buff *skb) 3775 { 3776 const void **tb; 3777 const struct wmi_obss_color_collision_event *ev; 3778 struct ath11k_vif *arvif; 3779 int ret; 3780 3781 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 3782 if (IS_ERR(tb)) { 3783 ret = PTR_ERR(tb); 3784 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 3785 return; 3786 } 3787 3788 rcu_read_lock(); 3789 3790 ev = tb[WMI_TAG_OBSS_COLOR_COLLISION_EVT]; 3791 if (!ev) { 3792 ath11k_warn(ab, "failed to fetch obss color collision ev"); 3793 goto exit; 3794 } 3795 3796 arvif = ath11k_mac_get_arvif_by_vdev_id(ab, ev->vdev_id); 3797 if (!arvif) { 3798 ath11k_warn(ab, "failed to find arvif with vedv id %d in obss_color_collision_event\n", 3799 ev->vdev_id); 3800 goto exit; 3801 } 3802 3803 switch (ev->evt_type) { 3804 case WMI_BSS_COLOR_COLLISION_DETECTION: 3805 ieeee80211_obss_color_collision_notify(arvif->vif, ev->obss_color_bitmap); 3806 ath11k_dbg(ab, ATH11K_DBG_WMI, 3807 "OBSS color collision detected vdev:%d, event:%d, bitmap:%08llx\n", 3808 ev->vdev_id, ev->evt_type, ev->obss_color_bitmap); 3809 break; 3810 case WMI_BSS_COLOR_COLLISION_DISABLE: 3811 case WMI_BSS_COLOR_FREE_SLOT_TIMER_EXPIRY: 3812 case WMI_BSS_COLOR_FREE_SLOT_AVAILABLE: 3813 break; 3814 default: 3815 ath11k_warn(ab, "received unknown obss color collision detection event\n"); 3816 } 3817 3818 exit: 3819 kfree(tb); 3820 rcu_read_unlock(); 3821 } 3822 3823 static void 3824 ath11k_fill_band_to_mac_param(struct ath11k_base *soc, 3825 struct wmi_host_pdev_band_to_mac *band_to_mac) 3826 { 3827 u8 i; 3828 struct ath11k_hal_reg_capabilities_ext *hal_reg_cap; 3829 struct ath11k_pdev *pdev; 3830 3831 for (i = 0; i < soc->num_radios; i++) { 3832 pdev = &soc->pdevs[i]; 3833 hal_reg_cap = &soc->hal_reg_cap[i]; 3834 band_to_mac[i].pdev_id = pdev->pdev_id; 3835 3836 switch (pdev->cap.supported_bands) { 3837 case WMI_HOST_WLAN_2G_5G_CAP: 3838 band_to_mac[i].start_freq = hal_reg_cap->low_2ghz_chan; 3839 band_to_mac[i].end_freq = hal_reg_cap->high_5ghz_chan; 3840 break; 3841 case WMI_HOST_WLAN_2G_CAP: 3842 band_to_mac[i].start_freq = hal_reg_cap->low_2ghz_chan; 3843 band_to_mac[i].end_freq = hal_reg_cap->high_2ghz_chan; 3844 break; 3845 case WMI_HOST_WLAN_5G_CAP: 3846 band_to_mac[i].start_freq = hal_reg_cap->low_5ghz_chan; 3847 band_to_mac[i].end_freq = hal_reg_cap->high_5ghz_chan; 3848 break; 3849 default: 3850 break; 3851 } 3852 } 3853 } 3854 3855 static void 3856 ath11k_wmi_copy_resource_config(struct wmi_resource_config *wmi_cfg, 3857 struct target_resource_config *tg_cfg) 3858 { 3859 wmi_cfg->num_vdevs = tg_cfg->num_vdevs; 3860 wmi_cfg->num_peers = tg_cfg->num_peers; 3861 wmi_cfg->num_offload_peers = tg_cfg->num_offload_peers; 3862 wmi_cfg->num_offload_reorder_buffs = tg_cfg->num_offload_reorder_buffs; 3863 wmi_cfg->num_peer_keys = tg_cfg->num_peer_keys; 3864 wmi_cfg->num_tids = tg_cfg->num_tids; 3865 wmi_cfg->ast_skid_limit = tg_cfg->ast_skid_limit; 3866 wmi_cfg->tx_chain_mask = tg_cfg->tx_chain_mask; 3867 wmi_cfg->rx_chain_mask = tg_cfg->rx_chain_mask; 3868 wmi_cfg->rx_timeout_pri[0] = tg_cfg->rx_timeout_pri[0]; 3869 wmi_cfg->rx_timeout_pri[1] = tg_cfg->rx_timeout_pri[1]; 3870 wmi_cfg->rx_timeout_pri[2] = tg_cfg->rx_timeout_pri[2]; 3871 wmi_cfg->rx_timeout_pri[3] = tg_cfg->rx_timeout_pri[3]; 3872 wmi_cfg->rx_decap_mode = tg_cfg->rx_decap_mode; 3873 wmi_cfg->scan_max_pending_req = tg_cfg->scan_max_pending_req; 3874 wmi_cfg->bmiss_offload_max_vdev = tg_cfg->bmiss_offload_max_vdev; 3875 wmi_cfg->roam_offload_max_vdev = tg_cfg->roam_offload_max_vdev; 3876 wmi_cfg->roam_offload_max_ap_profiles = 3877 tg_cfg->roam_offload_max_ap_profiles; 3878 wmi_cfg->num_mcast_groups = tg_cfg->num_mcast_groups; 3879 wmi_cfg->num_mcast_table_elems = tg_cfg->num_mcast_table_elems; 3880 wmi_cfg->mcast2ucast_mode = tg_cfg->mcast2ucast_mode; 3881 wmi_cfg->tx_dbg_log_size = tg_cfg->tx_dbg_log_size; 3882 wmi_cfg->num_wds_entries = tg_cfg->num_wds_entries; 3883 wmi_cfg->dma_burst_size = tg_cfg->dma_burst_size; 3884 wmi_cfg->mac_aggr_delim = tg_cfg->mac_aggr_delim; 3885 wmi_cfg->rx_skip_defrag_timeout_dup_detection_check = 3886 tg_cfg->rx_skip_defrag_timeout_dup_detection_check; 3887 wmi_cfg->vow_config = tg_cfg->vow_config; 3888 wmi_cfg->gtk_offload_max_vdev = tg_cfg->gtk_offload_max_vdev; 3889 wmi_cfg->num_msdu_desc = tg_cfg->num_msdu_desc; 3890 wmi_cfg->max_frag_entries = tg_cfg->max_frag_entries; 3891 wmi_cfg->num_tdls_vdevs = tg_cfg->num_tdls_vdevs; 3892 wmi_cfg->num_tdls_conn_table_entries = 3893 tg_cfg->num_tdls_conn_table_entries; 3894 wmi_cfg->beacon_tx_offload_max_vdev = 3895 tg_cfg->beacon_tx_offload_max_vdev; 3896 wmi_cfg->num_multicast_filter_entries = 3897 tg_cfg->num_multicast_filter_entries; 3898 wmi_cfg->num_wow_filters = tg_cfg->num_wow_filters; 3899 wmi_cfg->num_keep_alive_pattern = tg_cfg->num_keep_alive_pattern; 3900 wmi_cfg->keep_alive_pattern_size = tg_cfg->keep_alive_pattern_size; 3901 wmi_cfg->max_tdls_concurrent_sleep_sta = 3902 tg_cfg->max_tdls_concurrent_sleep_sta; 3903 wmi_cfg->max_tdls_concurrent_buffer_sta = 3904 tg_cfg->max_tdls_concurrent_buffer_sta; 3905 wmi_cfg->wmi_send_separate = tg_cfg->wmi_send_separate; 3906 wmi_cfg->num_ocb_vdevs = tg_cfg->num_ocb_vdevs; 3907 wmi_cfg->num_ocb_channels = tg_cfg->num_ocb_channels; 3908 wmi_cfg->num_ocb_schedules = tg_cfg->num_ocb_schedules; 3909 wmi_cfg->bpf_instruction_size = tg_cfg->bpf_instruction_size; 3910 wmi_cfg->max_bssid_rx_filters = tg_cfg->max_bssid_rx_filters; 3911 wmi_cfg->use_pdev_id = tg_cfg->use_pdev_id; 3912 wmi_cfg->flag1 = tg_cfg->flag1; 3913 wmi_cfg->peer_map_unmap_v2_support = tg_cfg->peer_map_unmap_v2_support; 3914 wmi_cfg->sched_params = tg_cfg->sched_params; 3915 wmi_cfg->twt_ap_pdev_count = tg_cfg->twt_ap_pdev_count; 3916 wmi_cfg->twt_ap_sta_count = tg_cfg->twt_ap_sta_count; 3917 } 3918 3919 static int ath11k_init_cmd_send(struct ath11k_pdev_wmi *wmi, 3920 struct wmi_init_cmd_param *param) 3921 { 3922 struct ath11k_base *ab = wmi->wmi_ab->ab; 3923 struct sk_buff *skb; 3924 struct wmi_init_cmd *cmd; 3925 struct wmi_resource_config *cfg; 3926 struct wmi_pdev_set_hw_mode_cmd_param *hw_mode; 3927 struct wmi_pdev_band_to_mac *band_to_mac; 3928 struct wlan_host_mem_chunk *host_mem_chunks; 3929 struct wmi_tlv *tlv; 3930 size_t ret, len; 3931 void *ptr; 3932 u32 hw_mode_len = 0; 3933 u16 idx; 3934 3935 if (param->hw_mode_id != WMI_HOST_HW_MODE_MAX) 3936 hw_mode_len = sizeof(*hw_mode) + TLV_HDR_SIZE + 3937 (param->num_band_to_mac * sizeof(*band_to_mac)); 3938 3939 len = sizeof(*cmd) + TLV_HDR_SIZE + sizeof(*cfg) + hw_mode_len + 3940 (param->num_mem_chunks ? (sizeof(*host_mem_chunks) * WMI_MAX_MEM_REQS) : 0); 3941 3942 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 3943 if (!skb) 3944 return -ENOMEM; 3945 3946 cmd = (struct wmi_init_cmd *)skb->data; 3947 3948 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_INIT_CMD) | 3949 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 3950 3951 ptr = skb->data + sizeof(*cmd); 3952 cfg = ptr; 3953 3954 ath11k_wmi_copy_resource_config(cfg, param->res_cfg); 3955 3956 cfg->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_RESOURCE_CONFIG) | 3957 FIELD_PREP(WMI_TLV_LEN, sizeof(*cfg) - TLV_HDR_SIZE); 3958 3959 ptr += sizeof(*cfg); 3960 host_mem_chunks = ptr + TLV_HDR_SIZE; 3961 len = sizeof(struct wlan_host_mem_chunk); 3962 3963 for (idx = 0; idx < param->num_mem_chunks; ++idx) { 3964 host_mem_chunks[idx].tlv_header = 3965 FIELD_PREP(WMI_TLV_TAG, 3966 WMI_TAG_WLAN_HOST_MEMORY_CHUNK) | 3967 FIELD_PREP(WMI_TLV_LEN, len); 3968 3969 host_mem_chunks[idx].ptr = param->mem_chunks[idx].paddr; 3970 host_mem_chunks[idx].size = param->mem_chunks[idx].len; 3971 host_mem_chunks[idx].req_id = param->mem_chunks[idx].req_id; 3972 3973 ath11k_dbg(ab, ATH11K_DBG_WMI, 3974 "WMI host mem chunk req_id %d paddr 0x%llx len %d\n", 3975 param->mem_chunks[idx].req_id, 3976 (u64)param->mem_chunks[idx].paddr, 3977 param->mem_chunks[idx].len); 3978 } 3979 cmd->num_host_mem_chunks = param->num_mem_chunks; 3980 len = sizeof(struct wlan_host_mem_chunk) * param->num_mem_chunks; 3981 3982 /* num_mem_chunks is zero */ 3983 tlv = ptr; 3984 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_STRUCT) | 3985 FIELD_PREP(WMI_TLV_LEN, len); 3986 ptr += TLV_HDR_SIZE + len; 3987 3988 if (param->hw_mode_id != WMI_HOST_HW_MODE_MAX) { 3989 hw_mode = (struct wmi_pdev_set_hw_mode_cmd_param *)ptr; 3990 hw_mode->tlv_header = FIELD_PREP(WMI_TLV_TAG, 3991 WMI_TAG_PDEV_SET_HW_MODE_CMD) | 3992 FIELD_PREP(WMI_TLV_LEN, 3993 sizeof(*hw_mode) - TLV_HDR_SIZE); 3994 3995 hw_mode->hw_mode_index = param->hw_mode_id; 3996 hw_mode->num_band_to_mac = param->num_band_to_mac; 3997 3998 ptr += sizeof(*hw_mode); 3999 4000 len = param->num_band_to_mac * sizeof(*band_to_mac); 4001 tlv = ptr; 4002 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_STRUCT) | 4003 FIELD_PREP(WMI_TLV_LEN, len); 4004 4005 ptr += TLV_HDR_SIZE; 4006 len = sizeof(*band_to_mac); 4007 4008 for (idx = 0; idx < param->num_band_to_mac; idx++) { 4009 band_to_mac = (void *)ptr; 4010 4011 band_to_mac->tlv_header = FIELD_PREP(WMI_TLV_TAG, 4012 WMI_TAG_PDEV_BAND_TO_MAC) | 4013 FIELD_PREP(WMI_TLV_LEN, 4014 len - TLV_HDR_SIZE); 4015 band_to_mac->pdev_id = param->band_to_mac[idx].pdev_id; 4016 band_to_mac->start_freq = 4017 param->band_to_mac[idx].start_freq; 4018 band_to_mac->end_freq = 4019 param->band_to_mac[idx].end_freq; 4020 ptr += sizeof(*band_to_mac); 4021 } 4022 } 4023 4024 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_INIT_CMDID); 4025 if (ret) { 4026 ath11k_warn(ab, "failed to send WMI_INIT_CMDID\n"); 4027 dev_kfree_skb(skb); 4028 } 4029 4030 return ret; 4031 } 4032 4033 int ath11k_wmi_pdev_lro_cfg(struct ath11k *ar, 4034 int pdev_id) 4035 { 4036 struct ath11k_wmi_pdev_lro_config_cmd *cmd; 4037 struct sk_buff *skb; 4038 int ret; 4039 4040 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd)); 4041 if (!skb) 4042 return -ENOMEM; 4043 4044 cmd = (struct ath11k_wmi_pdev_lro_config_cmd *)skb->data; 4045 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_LRO_INFO_CMD) | 4046 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 4047 4048 get_random_bytes(cmd->th_4, sizeof(uint32_t) * ATH11K_IPV4_TH_SEED_SIZE); 4049 get_random_bytes(cmd->th_6, sizeof(uint32_t) * ATH11K_IPV6_TH_SEED_SIZE); 4050 4051 cmd->pdev_id = pdev_id; 4052 4053 ret = ath11k_wmi_cmd_send(ar->wmi, skb, WMI_LRO_CONFIG_CMDID); 4054 if (ret) { 4055 ath11k_warn(ar->ab, 4056 "failed to send lro cfg req wmi cmd\n"); 4057 goto err; 4058 } 4059 4060 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 4061 "WMI lro cfg cmd pdev_id 0x%x\n", pdev_id); 4062 return 0; 4063 err: 4064 dev_kfree_skb(skb); 4065 return ret; 4066 } 4067 4068 int ath11k_wmi_wait_for_service_ready(struct ath11k_base *ab) 4069 { 4070 unsigned long time_left; 4071 4072 time_left = wait_for_completion_timeout(&ab->wmi_ab.service_ready, 4073 WMI_SERVICE_READY_TIMEOUT_HZ); 4074 if (!time_left) 4075 return -ETIMEDOUT; 4076 4077 return 0; 4078 } 4079 4080 int ath11k_wmi_wait_for_unified_ready(struct ath11k_base *ab) 4081 { 4082 unsigned long time_left; 4083 4084 time_left = wait_for_completion_timeout(&ab->wmi_ab.unified_ready, 4085 WMI_SERVICE_READY_TIMEOUT_HZ); 4086 if (!time_left) 4087 return -ETIMEDOUT; 4088 4089 return 0; 4090 } 4091 4092 int ath11k_wmi_set_hw_mode(struct ath11k_base *ab, 4093 enum wmi_host_hw_mode_config_type mode) 4094 { 4095 struct wmi_pdev_set_hw_mode_cmd_param *cmd; 4096 struct sk_buff *skb; 4097 struct ath11k_wmi_base *wmi_ab = &ab->wmi_ab; 4098 int len; 4099 int ret; 4100 4101 len = sizeof(*cmd); 4102 4103 skb = ath11k_wmi_alloc_skb(wmi_ab, len); 4104 if (!skb) 4105 return -ENOMEM; 4106 4107 cmd = (struct wmi_pdev_set_hw_mode_cmd_param *)skb->data; 4108 4109 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_PDEV_SET_HW_MODE_CMD) | 4110 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 4111 4112 cmd->pdev_id = WMI_PDEV_ID_SOC; 4113 cmd->hw_mode_index = mode; 4114 4115 ret = ath11k_wmi_cmd_send(&wmi_ab->wmi[0], skb, WMI_PDEV_SET_HW_MODE_CMDID); 4116 if (ret) { 4117 ath11k_warn(ab, "failed to send WMI_PDEV_SET_HW_MODE_CMDID\n"); 4118 dev_kfree_skb(skb); 4119 } 4120 4121 return ret; 4122 } 4123 4124 int ath11k_wmi_cmd_init(struct ath11k_base *ab) 4125 { 4126 struct ath11k_wmi_base *wmi_sc = &ab->wmi_ab; 4127 struct wmi_init_cmd_param init_param; 4128 struct target_resource_config config; 4129 4130 memset(&init_param, 0, sizeof(init_param)); 4131 memset(&config, 0, sizeof(config)); 4132 4133 ab->hw_params.hw_ops->wmi_init_config(ab, &config); 4134 4135 memcpy(&wmi_sc->wlan_resource_config, &config, sizeof(config)); 4136 4137 init_param.res_cfg = &wmi_sc->wlan_resource_config; 4138 init_param.num_mem_chunks = wmi_sc->num_mem_chunks; 4139 init_param.hw_mode_id = wmi_sc->preferred_hw_mode; 4140 init_param.mem_chunks = wmi_sc->mem_chunks; 4141 4142 if (ab->hw_params.single_pdev_only) 4143 init_param.hw_mode_id = WMI_HOST_HW_MODE_MAX; 4144 4145 init_param.num_band_to_mac = ab->num_radios; 4146 ath11k_fill_band_to_mac_param(ab, init_param.band_to_mac); 4147 4148 return ath11k_init_cmd_send(&wmi_sc->wmi[0], &init_param); 4149 } 4150 4151 int ath11k_wmi_vdev_spectral_conf(struct ath11k *ar, 4152 struct ath11k_wmi_vdev_spectral_conf_param *param) 4153 { 4154 struct ath11k_wmi_vdev_spectral_conf_cmd *cmd; 4155 struct sk_buff *skb; 4156 int ret; 4157 4158 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd)); 4159 if (!skb) 4160 return -ENOMEM; 4161 4162 cmd = (struct ath11k_wmi_vdev_spectral_conf_cmd *)skb->data; 4163 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 4164 WMI_TAG_VDEV_SPECTRAL_CONFIGURE_CMD) | 4165 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 4166 4167 memcpy(&cmd->param, param, sizeof(*param)); 4168 4169 ret = ath11k_wmi_cmd_send(ar->wmi, skb, 4170 WMI_VDEV_SPECTRAL_SCAN_CONFIGURE_CMDID); 4171 if (ret) { 4172 ath11k_warn(ar->ab, 4173 "failed to send spectral scan config wmi cmd\n"); 4174 goto err; 4175 } 4176 4177 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 4178 "WMI spectral scan config cmd vdev_id 0x%x\n", 4179 param->vdev_id); 4180 4181 return 0; 4182 err: 4183 dev_kfree_skb(skb); 4184 return ret; 4185 } 4186 4187 int ath11k_wmi_vdev_spectral_enable(struct ath11k *ar, u32 vdev_id, 4188 u32 trigger, u32 enable) 4189 { 4190 struct ath11k_wmi_vdev_spectral_enable_cmd *cmd; 4191 struct sk_buff *skb; 4192 int ret; 4193 4194 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd)); 4195 if (!skb) 4196 return -ENOMEM; 4197 4198 cmd = (struct ath11k_wmi_vdev_spectral_enable_cmd *)skb->data; 4199 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 4200 WMI_TAG_VDEV_SPECTRAL_ENABLE_CMD) | 4201 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 4202 4203 cmd->vdev_id = vdev_id; 4204 cmd->trigger_cmd = trigger; 4205 cmd->enable_cmd = enable; 4206 4207 ret = ath11k_wmi_cmd_send(ar->wmi, skb, 4208 WMI_VDEV_SPECTRAL_SCAN_ENABLE_CMDID); 4209 if (ret) { 4210 ath11k_warn(ar->ab, 4211 "failed to send spectral enable wmi cmd\n"); 4212 goto err; 4213 } 4214 4215 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 4216 "WMI spectral enable cmd vdev id 0x%x\n", 4217 vdev_id); 4218 4219 return 0; 4220 err: 4221 dev_kfree_skb(skb); 4222 return ret; 4223 } 4224 4225 int ath11k_wmi_pdev_dma_ring_cfg(struct ath11k *ar, 4226 struct ath11k_wmi_pdev_dma_ring_cfg_req_cmd *param) 4227 { 4228 struct ath11k_wmi_pdev_dma_ring_cfg_req_cmd *cmd; 4229 struct sk_buff *skb; 4230 int ret; 4231 4232 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, sizeof(*cmd)); 4233 if (!skb) 4234 return -ENOMEM; 4235 4236 cmd = (struct ath11k_wmi_pdev_dma_ring_cfg_req_cmd *)skb->data; 4237 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_DMA_RING_CFG_REQ) | 4238 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 4239 4240 cmd->pdev_id = param->pdev_id; 4241 cmd->module_id = param->module_id; 4242 cmd->base_paddr_lo = param->base_paddr_lo; 4243 cmd->base_paddr_hi = param->base_paddr_hi; 4244 cmd->head_idx_paddr_lo = param->head_idx_paddr_lo; 4245 cmd->head_idx_paddr_hi = param->head_idx_paddr_hi; 4246 cmd->tail_idx_paddr_lo = param->tail_idx_paddr_lo; 4247 cmd->tail_idx_paddr_hi = param->tail_idx_paddr_hi; 4248 cmd->num_elems = param->num_elems; 4249 cmd->buf_size = param->buf_size; 4250 cmd->num_resp_per_event = param->num_resp_per_event; 4251 cmd->event_timeout_ms = param->event_timeout_ms; 4252 4253 ret = ath11k_wmi_cmd_send(ar->wmi, skb, 4254 WMI_PDEV_DMA_RING_CFG_REQ_CMDID); 4255 if (ret) { 4256 ath11k_warn(ar->ab, 4257 "failed to send dma ring cfg req wmi cmd\n"); 4258 goto err; 4259 } 4260 4261 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 4262 "WMI DMA ring cfg req cmd pdev_id 0x%x\n", 4263 param->pdev_id); 4264 4265 return 0; 4266 err: 4267 dev_kfree_skb(skb); 4268 return ret; 4269 } 4270 4271 static int ath11k_wmi_tlv_dma_buf_entry_parse(struct ath11k_base *soc, 4272 u16 tag, u16 len, 4273 const void *ptr, void *data) 4274 { 4275 struct wmi_tlv_dma_buf_release_parse *parse = data; 4276 4277 if (tag != WMI_TAG_DMA_BUF_RELEASE_ENTRY) 4278 return -EPROTO; 4279 4280 if (parse->num_buf_entry >= parse->fixed.num_buf_release_entry) 4281 return -ENOBUFS; 4282 4283 parse->num_buf_entry++; 4284 return 0; 4285 } 4286 4287 static int ath11k_wmi_tlv_dma_buf_meta_parse(struct ath11k_base *soc, 4288 u16 tag, u16 len, 4289 const void *ptr, void *data) 4290 { 4291 struct wmi_tlv_dma_buf_release_parse *parse = data; 4292 4293 if (tag != WMI_TAG_DMA_BUF_RELEASE_SPECTRAL_META_DATA) 4294 return -EPROTO; 4295 4296 if (parse->num_meta >= parse->fixed.num_meta_data_entry) 4297 return -ENOBUFS; 4298 4299 parse->num_meta++; 4300 return 0; 4301 } 4302 4303 static int ath11k_wmi_tlv_dma_buf_parse(struct ath11k_base *ab, 4304 u16 tag, u16 len, 4305 const void *ptr, void *data) 4306 { 4307 struct wmi_tlv_dma_buf_release_parse *parse = data; 4308 int ret; 4309 4310 switch (tag) { 4311 case WMI_TAG_DMA_BUF_RELEASE: 4312 memcpy(&parse->fixed, ptr, 4313 sizeof(struct ath11k_wmi_dma_buf_release_fixed_param)); 4314 parse->fixed.pdev_id = DP_HW2SW_MACID(parse->fixed.pdev_id); 4315 break; 4316 case WMI_TAG_ARRAY_STRUCT: 4317 if (!parse->buf_entry_done) { 4318 parse->num_buf_entry = 0; 4319 parse->buf_entry = (struct wmi_dma_buf_release_entry *)ptr; 4320 4321 ret = ath11k_wmi_tlv_iter(ab, ptr, len, 4322 ath11k_wmi_tlv_dma_buf_entry_parse, 4323 parse); 4324 if (ret) { 4325 ath11k_warn(ab, "failed to parse dma buf entry tlv %d\n", 4326 ret); 4327 return ret; 4328 } 4329 4330 parse->buf_entry_done = true; 4331 } else if (!parse->meta_data_done) { 4332 parse->num_meta = 0; 4333 parse->meta_data = (struct wmi_dma_buf_release_meta_data *)ptr; 4334 4335 ret = ath11k_wmi_tlv_iter(ab, ptr, len, 4336 ath11k_wmi_tlv_dma_buf_meta_parse, 4337 parse); 4338 if (ret) { 4339 ath11k_warn(ab, "failed to parse dma buf meta tlv %d\n", 4340 ret); 4341 return ret; 4342 } 4343 4344 parse->meta_data_done = true; 4345 } 4346 break; 4347 default: 4348 break; 4349 } 4350 return 0; 4351 } 4352 4353 static void ath11k_wmi_pdev_dma_ring_buf_release_event(struct ath11k_base *ab, 4354 struct sk_buff *skb) 4355 { 4356 struct wmi_tlv_dma_buf_release_parse parse = { }; 4357 struct ath11k_dbring_buf_release_event param; 4358 int ret; 4359 4360 ret = ath11k_wmi_tlv_iter(ab, skb->data, skb->len, 4361 ath11k_wmi_tlv_dma_buf_parse, 4362 &parse); 4363 if (ret) { 4364 ath11k_warn(ab, "failed to parse dma buf release tlv %d\n", ret); 4365 return; 4366 } 4367 4368 param.fixed = parse.fixed; 4369 param.buf_entry = parse.buf_entry; 4370 param.num_buf_entry = parse.num_buf_entry; 4371 param.meta_data = parse.meta_data; 4372 param.num_meta = parse.num_meta; 4373 4374 ret = ath11k_dbring_buffer_release_event(ab, ¶m); 4375 if (ret) { 4376 ath11k_warn(ab, "failed to handle dma buf release event %d\n", ret); 4377 return; 4378 } 4379 } 4380 4381 static int ath11k_wmi_tlv_hw_mode_caps_parse(struct ath11k_base *soc, 4382 u16 tag, u16 len, 4383 const void *ptr, void *data) 4384 { 4385 struct wmi_tlv_svc_rdy_ext_parse *svc_rdy_ext = data; 4386 struct wmi_hw_mode_capabilities *hw_mode_cap; 4387 u32 phy_map = 0; 4388 4389 if (tag != WMI_TAG_HW_MODE_CAPABILITIES) 4390 return -EPROTO; 4391 4392 if (svc_rdy_ext->n_hw_mode_caps >= svc_rdy_ext->param.num_hw_modes) 4393 return -ENOBUFS; 4394 4395 hw_mode_cap = container_of(ptr, struct wmi_hw_mode_capabilities, 4396 hw_mode_id); 4397 svc_rdy_ext->n_hw_mode_caps++; 4398 4399 phy_map = hw_mode_cap->phy_id_map; 4400 while (phy_map) { 4401 svc_rdy_ext->tot_phy_id++; 4402 phy_map = phy_map >> 1; 4403 } 4404 4405 return 0; 4406 } 4407 4408 static int ath11k_wmi_tlv_hw_mode_caps(struct ath11k_base *soc, 4409 u16 len, const void *ptr, void *data) 4410 { 4411 struct wmi_tlv_svc_rdy_ext_parse *svc_rdy_ext = data; 4412 struct wmi_hw_mode_capabilities *hw_mode_caps; 4413 enum wmi_host_hw_mode_config_type mode, pref; 4414 u32 i; 4415 int ret; 4416 4417 svc_rdy_ext->n_hw_mode_caps = 0; 4418 svc_rdy_ext->hw_mode_caps = (struct wmi_hw_mode_capabilities *)ptr; 4419 4420 ret = ath11k_wmi_tlv_iter(soc, ptr, len, 4421 ath11k_wmi_tlv_hw_mode_caps_parse, 4422 svc_rdy_ext); 4423 if (ret) { 4424 ath11k_warn(soc, "failed to parse tlv %d\n", ret); 4425 return ret; 4426 } 4427 4428 i = 0; 4429 while (i < svc_rdy_ext->n_hw_mode_caps) { 4430 hw_mode_caps = &svc_rdy_ext->hw_mode_caps[i]; 4431 mode = hw_mode_caps->hw_mode_id; 4432 pref = soc->wmi_ab.preferred_hw_mode; 4433 4434 if (ath11k_hw_mode_pri_map[mode] < ath11k_hw_mode_pri_map[pref]) { 4435 svc_rdy_ext->pref_hw_mode_caps = *hw_mode_caps; 4436 soc->wmi_ab.preferred_hw_mode = mode; 4437 } 4438 i++; 4439 } 4440 4441 ath11k_dbg(soc, ATH11K_DBG_WMI, "preferred_hw_mode:%d\n", 4442 soc->wmi_ab.preferred_hw_mode); 4443 if (soc->wmi_ab.preferred_hw_mode == WMI_HOST_HW_MODE_MAX) 4444 return -EINVAL; 4445 4446 return 0; 4447 } 4448 4449 static int ath11k_wmi_tlv_mac_phy_caps_parse(struct ath11k_base *soc, 4450 u16 tag, u16 len, 4451 const void *ptr, void *data) 4452 { 4453 struct wmi_tlv_svc_rdy_ext_parse *svc_rdy_ext = data; 4454 4455 if (tag != WMI_TAG_MAC_PHY_CAPABILITIES) 4456 return -EPROTO; 4457 4458 if (svc_rdy_ext->n_mac_phy_caps >= svc_rdy_ext->tot_phy_id) 4459 return -ENOBUFS; 4460 4461 len = min_t(u16, len, sizeof(struct wmi_mac_phy_capabilities)); 4462 if (!svc_rdy_ext->n_mac_phy_caps) { 4463 svc_rdy_ext->mac_phy_caps = kcalloc(svc_rdy_ext->tot_phy_id, 4464 len, GFP_ATOMIC); 4465 if (!svc_rdy_ext->mac_phy_caps) 4466 return -ENOMEM; 4467 } 4468 4469 memcpy(svc_rdy_ext->mac_phy_caps + svc_rdy_ext->n_mac_phy_caps, ptr, len); 4470 svc_rdy_ext->n_mac_phy_caps++; 4471 return 0; 4472 } 4473 4474 static int ath11k_wmi_tlv_ext_hal_reg_caps_parse(struct ath11k_base *soc, 4475 u16 tag, u16 len, 4476 const void *ptr, void *data) 4477 { 4478 struct wmi_tlv_svc_rdy_ext_parse *svc_rdy_ext = data; 4479 4480 if (tag != WMI_TAG_HAL_REG_CAPABILITIES_EXT) 4481 return -EPROTO; 4482 4483 if (svc_rdy_ext->n_ext_hal_reg_caps >= svc_rdy_ext->param.num_phy) 4484 return -ENOBUFS; 4485 4486 svc_rdy_ext->n_ext_hal_reg_caps++; 4487 return 0; 4488 } 4489 4490 static int ath11k_wmi_tlv_ext_hal_reg_caps(struct ath11k_base *soc, 4491 u16 len, const void *ptr, void *data) 4492 { 4493 struct ath11k_pdev_wmi *wmi_handle = &soc->wmi_ab.wmi[0]; 4494 struct wmi_tlv_svc_rdy_ext_parse *svc_rdy_ext = data; 4495 struct ath11k_hal_reg_capabilities_ext reg_cap; 4496 int ret; 4497 u32 i; 4498 4499 svc_rdy_ext->n_ext_hal_reg_caps = 0; 4500 svc_rdy_ext->ext_hal_reg_caps = (struct wmi_hal_reg_capabilities_ext *)ptr; 4501 ret = ath11k_wmi_tlv_iter(soc, ptr, len, 4502 ath11k_wmi_tlv_ext_hal_reg_caps_parse, 4503 svc_rdy_ext); 4504 if (ret) { 4505 ath11k_warn(soc, "failed to parse tlv %d\n", ret); 4506 return ret; 4507 } 4508 4509 for (i = 0; i < svc_rdy_ext->param.num_phy; i++) { 4510 ret = ath11k_pull_reg_cap_svc_rdy_ext(wmi_handle, 4511 svc_rdy_ext->soc_hal_reg_caps, 4512 svc_rdy_ext->ext_hal_reg_caps, i, 4513 ®_cap); 4514 if (ret) { 4515 ath11k_warn(soc, "failed to extract reg cap %d\n", i); 4516 return ret; 4517 } 4518 4519 memcpy(&soc->hal_reg_cap[reg_cap.phy_id], 4520 ®_cap, sizeof(reg_cap)); 4521 } 4522 return 0; 4523 } 4524 4525 static int ath11k_wmi_tlv_ext_soc_hal_reg_caps_parse(struct ath11k_base *soc, 4526 u16 len, const void *ptr, 4527 void *data) 4528 { 4529 struct ath11k_pdev_wmi *wmi_handle = &soc->wmi_ab.wmi[0]; 4530 struct wmi_tlv_svc_rdy_ext_parse *svc_rdy_ext = data; 4531 u8 hw_mode_id = svc_rdy_ext->pref_hw_mode_caps.hw_mode_id; 4532 u32 phy_id_map; 4533 int pdev_index = 0; 4534 int ret; 4535 4536 svc_rdy_ext->soc_hal_reg_caps = (struct wmi_soc_hal_reg_capabilities *)ptr; 4537 svc_rdy_ext->param.num_phy = svc_rdy_ext->soc_hal_reg_caps->num_phy; 4538 4539 soc->num_radios = 0; 4540 soc->target_pdev_count = 0; 4541 phy_id_map = svc_rdy_ext->pref_hw_mode_caps.phy_id_map; 4542 4543 while (phy_id_map && soc->num_radios < MAX_RADIOS) { 4544 ret = ath11k_pull_mac_phy_cap_svc_ready_ext(wmi_handle, 4545 svc_rdy_ext->hw_caps, 4546 svc_rdy_ext->hw_mode_caps, 4547 svc_rdy_ext->soc_hal_reg_caps, 4548 svc_rdy_ext->mac_phy_caps, 4549 hw_mode_id, soc->num_radios, 4550 &soc->pdevs[pdev_index]); 4551 if (ret) { 4552 ath11k_warn(soc, "failed to extract mac caps, idx :%d\n", 4553 soc->num_radios); 4554 return ret; 4555 } 4556 4557 soc->num_radios++; 4558 4559 /* For QCA6390, save mac_phy capability in the same pdev */ 4560 if (soc->hw_params.single_pdev_only) 4561 pdev_index = 0; 4562 else 4563 pdev_index = soc->num_radios; 4564 4565 /* TODO: mac_phy_cap prints */ 4566 phy_id_map >>= 1; 4567 } 4568 4569 /* For QCA6390, set num_radios to 1 because host manages 4570 * both 2G and 5G radio in one pdev. 4571 * Set pdev_id = 0 and 0 means soc level. 4572 */ 4573 if (soc->hw_params.single_pdev_only) { 4574 soc->num_radios = 1; 4575 soc->pdevs[0].pdev_id = 0; 4576 } 4577 4578 return 0; 4579 } 4580 4581 static int ath11k_wmi_tlv_dma_ring_caps_parse(struct ath11k_base *soc, 4582 u16 tag, u16 len, 4583 const void *ptr, void *data) 4584 { 4585 struct wmi_tlv_dma_ring_caps_parse *parse = data; 4586 4587 if (tag != WMI_TAG_DMA_RING_CAPABILITIES) 4588 return -EPROTO; 4589 4590 parse->n_dma_ring_caps++; 4591 return 0; 4592 } 4593 4594 static int ath11k_wmi_alloc_dbring_caps(struct ath11k_base *ab, 4595 u32 num_cap) 4596 { 4597 size_t sz; 4598 void *ptr; 4599 4600 sz = num_cap * sizeof(struct ath11k_dbring_cap); 4601 ptr = kzalloc(sz, GFP_ATOMIC); 4602 if (!ptr) 4603 return -ENOMEM; 4604 4605 ab->db_caps = ptr; 4606 ab->num_db_cap = num_cap; 4607 4608 return 0; 4609 } 4610 4611 static void ath11k_wmi_free_dbring_caps(struct ath11k_base *ab) 4612 { 4613 kfree(ab->db_caps); 4614 ab->db_caps = NULL; 4615 } 4616 4617 static int ath11k_wmi_tlv_dma_ring_caps(struct ath11k_base *ab, 4618 u16 len, const void *ptr, void *data) 4619 { 4620 struct wmi_tlv_dma_ring_caps_parse *dma_caps_parse = data; 4621 struct wmi_dma_ring_capabilities *dma_caps; 4622 struct ath11k_dbring_cap *dir_buff_caps; 4623 int ret; 4624 u32 i; 4625 4626 dma_caps_parse->n_dma_ring_caps = 0; 4627 dma_caps = (struct wmi_dma_ring_capabilities *)ptr; 4628 ret = ath11k_wmi_tlv_iter(ab, ptr, len, 4629 ath11k_wmi_tlv_dma_ring_caps_parse, 4630 dma_caps_parse); 4631 if (ret) { 4632 ath11k_warn(ab, "failed to parse dma ring caps tlv %d\n", ret); 4633 return ret; 4634 } 4635 4636 if (!dma_caps_parse->n_dma_ring_caps) 4637 return 0; 4638 4639 if (ab->num_db_cap) { 4640 ath11k_warn(ab, "Already processed, so ignoring dma ring caps\n"); 4641 return 0; 4642 } 4643 4644 ret = ath11k_wmi_alloc_dbring_caps(ab, dma_caps_parse->n_dma_ring_caps); 4645 if (ret) 4646 return ret; 4647 4648 dir_buff_caps = ab->db_caps; 4649 for (i = 0; i < dma_caps_parse->n_dma_ring_caps; i++) { 4650 if (dma_caps[i].module_id >= WMI_DIRECT_BUF_MAX) { 4651 ath11k_warn(ab, "Invalid module id %d\n", dma_caps[i].module_id); 4652 ret = -EINVAL; 4653 goto free_dir_buff; 4654 } 4655 4656 dir_buff_caps[i].id = dma_caps[i].module_id; 4657 dir_buff_caps[i].pdev_id = DP_HW2SW_MACID(dma_caps[i].pdev_id); 4658 dir_buff_caps[i].min_elem = dma_caps[i].min_elem; 4659 dir_buff_caps[i].min_buf_sz = dma_caps[i].min_buf_sz; 4660 dir_buff_caps[i].min_buf_align = dma_caps[i].min_buf_align; 4661 } 4662 4663 return 0; 4664 4665 free_dir_buff: 4666 ath11k_wmi_free_dbring_caps(ab); 4667 return ret; 4668 } 4669 4670 static int ath11k_wmi_tlv_svc_rdy_ext_parse(struct ath11k_base *ab, 4671 u16 tag, u16 len, 4672 const void *ptr, void *data) 4673 { 4674 struct ath11k_pdev_wmi *wmi_handle = &ab->wmi_ab.wmi[0]; 4675 struct wmi_tlv_svc_rdy_ext_parse *svc_rdy_ext = data; 4676 int ret; 4677 4678 switch (tag) { 4679 case WMI_TAG_SERVICE_READY_EXT_EVENT: 4680 ret = ath11k_pull_svc_ready_ext(wmi_handle, ptr, 4681 &svc_rdy_ext->param); 4682 if (ret) { 4683 ath11k_warn(ab, "unable to extract ext params\n"); 4684 return ret; 4685 } 4686 break; 4687 4688 case WMI_TAG_SOC_MAC_PHY_HW_MODE_CAPS: 4689 svc_rdy_ext->hw_caps = (struct wmi_soc_mac_phy_hw_mode_caps *)ptr; 4690 svc_rdy_ext->param.num_hw_modes = svc_rdy_ext->hw_caps->num_hw_modes; 4691 break; 4692 4693 case WMI_TAG_SOC_HAL_REG_CAPABILITIES: 4694 ret = ath11k_wmi_tlv_ext_soc_hal_reg_caps_parse(ab, len, ptr, 4695 svc_rdy_ext); 4696 if (ret) 4697 return ret; 4698 break; 4699 4700 case WMI_TAG_ARRAY_STRUCT: 4701 if (!svc_rdy_ext->hw_mode_done) { 4702 ret = ath11k_wmi_tlv_hw_mode_caps(ab, len, ptr, 4703 svc_rdy_ext); 4704 if (ret) 4705 return ret; 4706 4707 svc_rdy_ext->hw_mode_done = true; 4708 } else if (!svc_rdy_ext->mac_phy_done) { 4709 svc_rdy_ext->n_mac_phy_caps = 0; 4710 ret = ath11k_wmi_tlv_iter(ab, ptr, len, 4711 ath11k_wmi_tlv_mac_phy_caps_parse, 4712 svc_rdy_ext); 4713 if (ret) { 4714 ath11k_warn(ab, "failed to parse tlv %d\n", ret); 4715 return ret; 4716 } 4717 4718 svc_rdy_ext->mac_phy_done = true; 4719 } else if (!svc_rdy_ext->ext_hal_reg_done) { 4720 ret = ath11k_wmi_tlv_ext_hal_reg_caps(ab, len, ptr, 4721 svc_rdy_ext); 4722 if (ret) 4723 return ret; 4724 4725 svc_rdy_ext->ext_hal_reg_done = true; 4726 } else if (!svc_rdy_ext->mac_phy_chainmask_combo_done) { 4727 svc_rdy_ext->mac_phy_chainmask_combo_done = true; 4728 } else if (!svc_rdy_ext->mac_phy_chainmask_cap_done) { 4729 svc_rdy_ext->mac_phy_chainmask_cap_done = true; 4730 } else if (!svc_rdy_ext->oem_dma_ring_cap_done) { 4731 svc_rdy_ext->oem_dma_ring_cap_done = true; 4732 } else if (!svc_rdy_ext->dma_ring_cap_done) { 4733 ret = ath11k_wmi_tlv_dma_ring_caps(ab, len, ptr, 4734 &svc_rdy_ext->dma_caps_parse); 4735 if (ret) 4736 return ret; 4737 4738 svc_rdy_ext->dma_ring_cap_done = true; 4739 } 4740 break; 4741 4742 default: 4743 break; 4744 } 4745 return 0; 4746 } 4747 4748 static int ath11k_service_ready_ext_event(struct ath11k_base *ab, 4749 struct sk_buff *skb) 4750 { 4751 struct wmi_tlv_svc_rdy_ext_parse svc_rdy_ext = { }; 4752 int ret; 4753 4754 ret = ath11k_wmi_tlv_iter(ab, skb->data, skb->len, 4755 ath11k_wmi_tlv_svc_rdy_ext_parse, 4756 &svc_rdy_ext); 4757 if (ret) { 4758 ath11k_warn(ab, "failed to parse tlv %d\n", ret); 4759 goto err; 4760 } 4761 4762 if (!test_bit(WMI_TLV_SERVICE_EXT2_MSG, ab->wmi_ab.svc_map)) 4763 complete(&ab->wmi_ab.service_ready); 4764 4765 kfree(svc_rdy_ext.mac_phy_caps); 4766 return 0; 4767 4768 err: 4769 ath11k_wmi_free_dbring_caps(ab); 4770 return ret; 4771 } 4772 4773 static int ath11k_wmi_tlv_svc_rdy_ext2_parse(struct ath11k_base *ab, 4774 u16 tag, u16 len, 4775 const void *ptr, void *data) 4776 { 4777 struct wmi_tlv_svc_rdy_ext2_parse *parse = data; 4778 int ret; 4779 4780 switch (tag) { 4781 case WMI_TAG_ARRAY_STRUCT: 4782 if (!parse->dma_ring_cap_done) { 4783 ret = ath11k_wmi_tlv_dma_ring_caps(ab, len, ptr, 4784 &parse->dma_caps_parse); 4785 if (ret) 4786 return ret; 4787 4788 parse->dma_ring_cap_done = true; 4789 } 4790 break; 4791 default: 4792 break; 4793 } 4794 4795 return 0; 4796 } 4797 4798 static int ath11k_service_ready_ext2_event(struct ath11k_base *ab, 4799 struct sk_buff *skb) 4800 { 4801 struct wmi_tlv_svc_rdy_ext2_parse svc_rdy_ext2 = { }; 4802 int ret; 4803 4804 ret = ath11k_wmi_tlv_iter(ab, skb->data, skb->len, 4805 ath11k_wmi_tlv_svc_rdy_ext2_parse, 4806 &svc_rdy_ext2); 4807 if (ret) { 4808 ath11k_warn(ab, "failed to parse ext2 event tlv %d\n", ret); 4809 goto err; 4810 } 4811 4812 complete(&ab->wmi_ab.service_ready); 4813 4814 return 0; 4815 4816 err: 4817 ath11k_wmi_free_dbring_caps(ab); 4818 return ret; 4819 } 4820 4821 static int ath11k_pull_vdev_start_resp_tlv(struct ath11k_base *ab, struct sk_buff *skb, 4822 struct wmi_vdev_start_resp_event *vdev_rsp) 4823 { 4824 const void **tb; 4825 const struct wmi_vdev_start_resp_event *ev; 4826 int ret; 4827 4828 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 4829 if (IS_ERR(tb)) { 4830 ret = PTR_ERR(tb); 4831 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 4832 return ret; 4833 } 4834 4835 ev = tb[WMI_TAG_VDEV_START_RESPONSE_EVENT]; 4836 if (!ev) { 4837 ath11k_warn(ab, "failed to fetch vdev start resp ev"); 4838 kfree(tb); 4839 return -EPROTO; 4840 } 4841 4842 memset(vdev_rsp, 0, sizeof(*vdev_rsp)); 4843 4844 vdev_rsp->vdev_id = ev->vdev_id; 4845 vdev_rsp->requestor_id = ev->requestor_id; 4846 vdev_rsp->resp_type = ev->resp_type; 4847 vdev_rsp->status = ev->status; 4848 vdev_rsp->chain_mask = ev->chain_mask; 4849 vdev_rsp->smps_mode = ev->smps_mode; 4850 vdev_rsp->mac_id = ev->mac_id; 4851 vdev_rsp->cfgd_tx_streams = ev->cfgd_tx_streams; 4852 vdev_rsp->cfgd_rx_streams = ev->cfgd_rx_streams; 4853 4854 kfree(tb); 4855 return 0; 4856 } 4857 4858 static struct cur_reg_rule 4859 *create_reg_rules_from_wmi(u32 num_reg_rules, 4860 struct wmi_regulatory_rule_struct *wmi_reg_rule) 4861 { 4862 struct cur_reg_rule *reg_rule_ptr; 4863 u32 count; 4864 4865 reg_rule_ptr = kcalloc(num_reg_rules, sizeof(*reg_rule_ptr), 4866 GFP_ATOMIC); 4867 4868 if (!reg_rule_ptr) 4869 return NULL; 4870 4871 for (count = 0; count < num_reg_rules; count++) { 4872 reg_rule_ptr[count].start_freq = 4873 FIELD_GET(REG_RULE_START_FREQ, 4874 wmi_reg_rule[count].freq_info); 4875 reg_rule_ptr[count].end_freq = 4876 FIELD_GET(REG_RULE_END_FREQ, 4877 wmi_reg_rule[count].freq_info); 4878 reg_rule_ptr[count].max_bw = 4879 FIELD_GET(REG_RULE_MAX_BW, 4880 wmi_reg_rule[count].bw_pwr_info); 4881 reg_rule_ptr[count].reg_power = 4882 FIELD_GET(REG_RULE_REG_PWR, 4883 wmi_reg_rule[count].bw_pwr_info); 4884 reg_rule_ptr[count].ant_gain = 4885 FIELD_GET(REG_RULE_ANT_GAIN, 4886 wmi_reg_rule[count].bw_pwr_info); 4887 reg_rule_ptr[count].flags = 4888 FIELD_GET(REG_RULE_FLAGS, 4889 wmi_reg_rule[count].flag_info); 4890 } 4891 4892 return reg_rule_ptr; 4893 } 4894 4895 static int ath11k_pull_reg_chan_list_update_ev(struct ath11k_base *ab, 4896 struct sk_buff *skb, 4897 struct cur_regulatory_info *reg_info) 4898 { 4899 const void **tb; 4900 const struct wmi_reg_chan_list_cc_event *chan_list_event_hdr; 4901 struct wmi_regulatory_rule_struct *wmi_reg_rule; 4902 u32 num_2g_reg_rules, num_5g_reg_rules; 4903 int ret; 4904 4905 ath11k_dbg(ab, ATH11K_DBG_WMI, "processing regulatory channel list\n"); 4906 4907 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 4908 if (IS_ERR(tb)) { 4909 ret = PTR_ERR(tb); 4910 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 4911 return ret; 4912 } 4913 4914 chan_list_event_hdr = tb[WMI_TAG_REG_CHAN_LIST_CC_EVENT]; 4915 if (!chan_list_event_hdr) { 4916 ath11k_warn(ab, "failed to fetch reg chan list update ev\n"); 4917 kfree(tb); 4918 return -EPROTO; 4919 } 4920 4921 reg_info->num_2g_reg_rules = chan_list_event_hdr->num_2g_reg_rules; 4922 reg_info->num_5g_reg_rules = chan_list_event_hdr->num_5g_reg_rules; 4923 4924 if (!(reg_info->num_2g_reg_rules + reg_info->num_5g_reg_rules)) { 4925 ath11k_warn(ab, "No regulatory rules available in the event info\n"); 4926 kfree(tb); 4927 return -EINVAL; 4928 } 4929 4930 memcpy(reg_info->alpha2, &chan_list_event_hdr->alpha2, 4931 REG_ALPHA2_LEN); 4932 reg_info->dfs_region = chan_list_event_hdr->dfs_region; 4933 reg_info->phybitmap = chan_list_event_hdr->phybitmap; 4934 reg_info->num_phy = chan_list_event_hdr->num_phy; 4935 reg_info->phy_id = chan_list_event_hdr->phy_id; 4936 reg_info->ctry_code = chan_list_event_hdr->country_id; 4937 reg_info->reg_dmn_pair = chan_list_event_hdr->domain_code; 4938 if (chan_list_event_hdr->status_code == WMI_REG_SET_CC_STATUS_PASS) 4939 reg_info->status_code = REG_SET_CC_STATUS_PASS; 4940 else if (chan_list_event_hdr->status_code == WMI_REG_CURRENT_ALPHA2_NOT_FOUND) 4941 reg_info->status_code = REG_CURRENT_ALPHA2_NOT_FOUND; 4942 else if (chan_list_event_hdr->status_code == WMI_REG_INIT_ALPHA2_NOT_FOUND) 4943 reg_info->status_code = REG_INIT_ALPHA2_NOT_FOUND; 4944 else if (chan_list_event_hdr->status_code == WMI_REG_SET_CC_CHANGE_NOT_ALLOWED) 4945 reg_info->status_code = REG_SET_CC_CHANGE_NOT_ALLOWED; 4946 else if (chan_list_event_hdr->status_code == WMI_REG_SET_CC_STATUS_NO_MEMORY) 4947 reg_info->status_code = REG_SET_CC_STATUS_NO_MEMORY; 4948 else if (chan_list_event_hdr->status_code == WMI_REG_SET_CC_STATUS_FAIL) 4949 reg_info->status_code = REG_SET_CC_STATUS_FAIL; 4950 4951 reg_info->min_bw_2g = chan_list_event_hdr->min_bw_2g; 4952 reg_info->max_bw_2g = chan_list_event_hdr->max_bw_2g; 4953 reg_info->min_bw_5g = chan_list_event_hdr->min_bw_5g; 4954 reg_info->max_bw_5g = chan_list_event_hdr->max_bw_5g; 4955 4956 num_2g_reg_rules = reg_info->num_2g_reg_rules; 4957 num_5g_reg_rules = reg_info->num_5g_reg_rules; 4958 4959 ath11k_dbg(ab, ATH11K_DBG_WMI, 4960 "%s:cc %s dsf %d BW: min_2g %d max_2g %d min_5g %d max_5g %d", 4961 __func__, reg_info->alpha2, reg_info->dfs_region, 4962 reg_info->min_bw_2g, reg_info->max_bw_2g, 4963 reg_info->min_bw_5g, reg_info->max_bw_5g); 4964 4965 ath11k_dbg(ab, ATH11K_DBG_WMI, 4966 "%s: num_2g_reg_rules %d num_5g_reg_rules %d", __func__, 4967 num_2g_reg_rules, num_5g_reg_rules); 4968 4969 wmi_reg_rule = 4970 (struct wmi_regulatory_rule_struct *)((u8 *)chan_list_event_hdr 4971 + sizeof(*chan_list_event_hdr) 4972 + sizeof(struct wmi_tlv)); 4973 4974 if (num_2g_reg_rules) { 4975 reg_info->reg_rules_2g_ptr = create_reg_rules_from_wmi(num_2g_reg_rules, 4976 wmi_reg_rule); 4977 if (!reg_info->reg_rules_2g_ptr) { 4978 kfree(tb); 4979 ath11k_warn(ab, "Unable to Allocate memory for 2g rules\n"); 4980 return -ENOMEM; 4981 } 4982 } 4983 4984 if (num_5g_reg_rules) { 4985 wmi_reg_rule += num_2g_reg_rules; 4986 reg_info->reg_rules_5g_ptr = create_reg_rules_from_wmi(num_5g_reg_rules, 4987 wmi_reg_rule); 4988 if (!reg_info->reg_rules_5g_ptr) { 4989 kfree(tb); 4990 ath11k_warn(ab, "Unable to Allocate memory for 5g rules\n"); 4991 return -ENOMEM; 4992 } 4993 } 4994 4995 ath11k_dbg(ab, ATH11K_DBG_WMI, "processed regulatory channel list\n"); 4996 4997 kfree(tb); 4998 return 0; 4999 } 5000 5001 static int ath11k_pull_peer_del_resp_ev(struct ath11k_base *ab, struct sk_buff *skb, 5002 struct wmi_peer_delete_resp_event *peer_del_resp) 5003 { 5004 const void **tb; 5005 const struct wmi_peer_delete_resp_event *ev; 5006 int ret; 5007 5008 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5009 if (IS_ERR(tb)) { 5010 ret = PTR_ERR(tb); 5011 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5012 return ret; 5013 } 5014 5015 ev = tb[WMI_TAG_PEER_DELETE_RESP_EVENT]; 5016 if (!ev) { 5017 ath11k_warn(ab, "failed to fetch peer delete resp ev"); 5018 kfree(tb); 5019 return -EPROTO; 5020 } 5021 5022 memset(peer_del_resp, 0, sizeof(*peer_del_resp)); 5023 5024 peer_del_resp->vdev_id = ev->vdev_id; 5025 ether_addr_copy(peer_del_resp->peer_macaddr.addr, 5026 ev->peer_macaddr.addr); 5027 5028 kfree(tb); 5029 return 0; 5030 } 5031 5032 static int ath11k_pull_vdev_del_resp_ev(struct ath11k_base *ab, 5033 struct sk_buff *skb, 5034 u32 *vdev_id) 5035 { 5036 const void **tb; 5037 const struct wmi_vdev_delete_resp_event *ev; 5038 int ret; 5039 5040 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5041 if (IS_ERR(tb)) { 5042 ret = PTR_ERR(tb); 5043 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5044 return ret; 5045 } 5046 5047 ev = tb[WMI_TAG_VDEV_DELETE_RESP_EVENT]; 5048 if (!ev) { 5049 ath11k_warn(ab, "failed to fetch vdev delete resp ev"); 5050 kfree(tb); 5051 return -EPROTO; 5052 } 5053 5054 *vdev_id = ev->vdev_id; 5055 5056 kfree(tb); 5057 return 0; 5058 } 5059 5060 static int ath11k_pull_bcn_tx_status_ev(struct ath11k_base *ab, void *evt_buf, 5061 u32 len, u32 *vdev_id, 5062 u32 *tx_status) 5063 { 5064 const void **tb; 5065 const struct wmi_bcn_tx_status_event *ev; 5066 int ret; 5067 5068 tb = ath11k_wmi_tlv_parse_alloc(ab, evt_buf, len, GFP_ATOMIC); 5069 if (IS_ERR(tb)) { 5070 ret = PTR_ERR(tb); 5071 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5072 return ret; 5073 } 5074 5075 ev = tb[WMI_TAG_OFFLOAD_BCN_TX_STATUS_EVENT]; 5076 if (!ev) { 5077 ath11k_warn(ab, "failed to fetch bcn tx status ev"); 5078 kfree(tb); 5079 return -EPROTO; 5080 } 5081 5082 *vdev_id = ev->vdev_id; 5083 *tx_status = ev->tx_status; 5084 5085 kfree(tb); 5086 return 0; 5087 } 5088 5089 static int ath11k_pull_vdev_stopped_param_tlv(struct ath11k_base *ab, struct sk_buff *skb, 5090 u32 *vdev_id) 5091 { 5092 const void **tb; 5093 const struct wmi_vdev_stopped_event *ev; 5094 int ret; 5095 5096 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5097 if (IS_ERR(tb)) { 5098 ret = PTR_ERR(tb); 5099 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5100 return ret; 5101 } 5102 5103 ev = tb[WMI_TAG_VDEV_STOPPED_EVENT]; 5104 if (!ev) { 5105 ath11k_warn(ab, "failed to fetch vdev stop ev"); 5106 kfree(tb); 5107 return -EPROTO; 5108 } 5109 5110 *vdev_id = ev->vdev_id; 5111 5112 kfree(tb); 5113 return 0; 5114 } 5115 5116 static int ath11k_pull_mgmt_rx_params_tlv(struct ath11k_base *ab, 5117 struct sk_buff *skb, 5118 struct mgmt_rx_event_params *hdr) 5119 { 5120 const void **tb; 5121 const struct wmi_mgmt_rx_hdr *ev; 5122 const u8 *frame; 5123 int ret; 5124 5125 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5126 if (IS_ERR(tb)) { 5127 ret = PTR_ERR(tb); 5128 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5129 return ret; 5130 } 5131 5132 ev = tb[WMI_TAG_MGMT_RX_HDR]; 5133 frame = tb[WMI_TAG_ARRAY_BYTE]; 5134 5135 if (!ev || !frame) { 5136 ath11k_warn(ab, "failed to fetch mgmt rx hdr"); 5137 kfree(tb); 5138 return -EPROTO; 5139 } 5140 5141 hdr->pdev_id = ev->pdev_id; 5142 hdr->chan_freq = ev->chan_freq; 5143 hdr->channel = ev->channel; 5144 hdr->snr = ev->snr; 5145 hdr->rate = ev->rate; 5146 hdr->phy_mode = ev->phy_mode; 5147 hdr->buf_len = ev->buf_len; 5148 hdr->status = ev->status; 5149 hdr->flags = ev->flags; 5150 hdr->rssi = ev->rssi; 5151 hdr->tsf_delta = ev->tsf_delta; 5152 memcpy(hdr->rssi_ctl, ev->rssi_ctl, sizeof(hdr->rssi_ctl)); 5153 5154 if (skb->len < (frame - skb->data) + hdr->buf_len) { 5155 ath11k_warn(ab, "invalid length in mgmt rx hdr ev"); 5156 kfree(tb); 5157 return -EPROTO; 5158 } 5159 5160 /* shift the sk_buff to point to `frame` */ 5161 skb_trim(skb, 0); 5162 skb_put(skb, frame - skb->data); 5163 skb_pull(skb, frame - skb->data); 5164 skb_put(skb, hdr->buf_len); 5165 5166 ath11k_ce_byte_swap(skb->data, hdr->buf_len); 5167 5168 kfree(tb); 5169 return 0; 5170 } 5171 5172 static int wmi_process_mgmt_tx_comp(struct ath11k *ar, u32 desc_id, 5173 u32 status) 5174 { 5175 struct sk_buff *msdu; 5176 struct ieee80211_tx_info *info; 5177 struct ath11k_skb_cb *skb_cb; 5178 int num_mgmt; 5179 5180 spin_lock_bh(&ar->txmgmt_idr_lock); 5181 msdu = idr_find(&ar->txmgmt_idr, desc_id); 5182 5183 if (!msdu) { 5184 ath11k_warn(ar->ab, "received mgmt tx compl for invalid msdu_id: %d\n", 5185 desc_id); 5186 spin_unlock_bh(&ar->txmgmt_idr_lock); 5187 return -ENOENT; 5188 } 5189 5190 idr_remove(&ar->txmgmt_idr, desc_id); 5191 spin_unlock_bh(&ar->txmgmt_idr_lock); 5192 5193 skb_cb = ATH11K_SKB_CB(msdu); 5194 dma_unmap_single(ar->ab->dev, skb_cb->paddr, msdu->len, DMA_TO_DEVICE); 5195 5196 info = IEEE80211_SKB_CB(msdu); 5197 if ((!(info->flags & IEEE80211_TX_CTL_NO_ACK)) && !status) 5198 info->flags |= IEEE80211_TX_STAT_ACK; 5199 5200 ieee80211_tx_status_irqsafe(ar->hw, msdu); 5201 5202 num_mgmt = atomic_dec_if_positive(&ar->num_pending_mgmt_tx); 5203 5204 /* WARN when we received this event without doing any mgmt tx */ 5205 if (num_mgmt < 0) 5206 WARN_ON_ONCE(1); 5207 5208 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 5209 "wmi mgmt tx comp pending %d desc id %d\n", 5210 num_mgmt, desc_id); 5211 5212 if (!num_mgmt) 5213 wake_up(&ar->txmgmt_empty_waitq); 5214 5215 return 0; 5216 } 5217 5218 static int ath11k_pull_mgmt_tx_compl_param_tlv(struct ath11k_base *ab, 5219 struct sk_buff *skb, 5220 struct wmi_mgmt_tx_compl_event *param) 5221 { 5222 const void **tb; 5223 const struct wmi_mgmt_tx_compl_event *ev; 5224 int ret; 5225 5226 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5227 if (IS_ERR(tb)) { 5228 ret = PTR_ERR(tb); 5229 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5230 return ret; 5231 } 5232 5233 ev = tb[WMI_TAG_MGMT_TX_COMPL_EVENT]; 5234 if (!ev) { 5235 ath11k_warn(ab, "failed to fetch mgmt tx compl ev"); 5236 kfree(tb); 5237 return -EPROTO; 5238 } 5239 5240 param->pdev_id = ev->pdev_id; 5241 param->desc_id = ev->desc_id; 5242 param->status = ev->status; 5243 5244 kfree(tb); 5245 return 0; 5246 } 5247 5248 static void ath11k_wmi_event_scan_started(struct ath11k *ar) 5249 { 5250 lockdep_assert_held(&ar->data_lock); 5251 5252 switch (ar->scan.state) { 5253 case ATH11K_SCAN_IDLE: 5254 case ATH11K_SCAN_RUNNING: 5255 case ATH11K_SCAN_ABORTING: 5256 ath11k_warn(ar->ab, "received scan started event in an invalid scan state: %s (%d)\n", 5257 ath11k_scan_state_str(ar->scan.state), 5258 ar->scan.state); 5259 break; 5260 case ATH11K_SCAN_STARTING: 5261 ar->scan.state = ATH11K_SCAN_RUNNING; 5262 complete(&ar->scan.started); 5263 break; 5264 } 5265 } 5266 5267 static void ath11k_wmi_event_scan_start_failed(struct ath11k *ar) 5268 { 5269 lockdep_assert_held(&ar->data_lock); 5270 5271 switch (ar->scan.state) { 5272 case ATH11K_SCAN_IDLE: 5273 case ATH11K_SCAN_RUNNING: 5274 case ATH11K_SCAN_ABORTING: 5275 ath11k_warn(ar->ab, "received scan start failed event in an invalid scan state: %s (%d)\n", 5276 ath11k_scan_state_str(ar->scan.state), 5277 ar->scan.state); 5278 break; 5279 case ATH11K_SCAN_STARTING: 5280 complete(&ar->scan.started); 5281 __ath11k_mac_scan_finish(ar); 5282 break; 5283 } 5284 } 5285 5286 static void ath11k_wmi_event_scan_completed(struct ath11k *ar) 5287 { 5288 lockdep_assert_held(&ar->data_lock); 5289 5290 switch (ar->scan.state) { 5291 case ATH11K_SCAN_IDLE: 5292 case ATH11K_SCAN_STARTING: 5293 /* One suspected reason scan can be completed while starting is 5294 * if firmware fails to deliver all scan events to the host, 5295 * e.g. when transport pipe is full. This has been observed 5296 * with spectral scan phyerr events starving wmi transport 5297 * pipe. In such case the "scan completed" event should be (and 5298 * is) ignored by the host as it may be just firmware's scan 5299 * state machine recovering. 5300 */ 5301 ath11k_warn(ar->ab, "received scan completed event in an invalid scan state: %s (%d)\n", 5302 ath11k_scan_state_str(ar->scan.state), 5303 ar->scan.state); 5304 break; 5305 case ATH11K_SCAN_RUNNING: 5306 case ATH11K_SCAN_ABORTING: 5307 __ath11k_mac_scan_finish(ar); 5308 break; 5309 } 5310 } 5311 5312 static void ath11k_wmi_event_scan_bss_chan(struct ath11k *ar) 5313 { 5314 lockdep_assert_held(&ar->data_lock); 5315 5316 switch (ar->scan.state) { 5317 case ATH11K_SCAN_IDLE: 5318 case ATH11K_SCAN_STARTING: 5319 ath11k_warn(ar->ab, "received scan bss chan event in an invalid scan state: %s (%d)\n", 5320 ath11k_scan_state_str(ar->scan.state), 5321 ar->scan.state); 5322 break; 5323 case ATH11K_SCAN_RUNNING: 5324 case ATH11K_SCAN_ABORTING: 5325 ar->scan_channel = NULL; 5326 break; 5327 } 5328 } 5329 5330 static void ath11k_wmi_event_scan_foreign_chan(struct ath11k *ar, u32 freq) 5331 { 5332 lockdep_assert_held(&ar->data_lock); 5333 5334 switch (ar->scan.state) { 5335 case ATH11K_SCAN_IDLE: 5336 case ATH11K_SCAN_STARTING: 5337 ath11k_warn(ar->ab, "received scan foreign chan event in an invalid scan state: %s (%d)\n", 5338 ath11k_scan_state_str(ar->scan.state), 5339 ar->scan.state); 5340 break; 5341 case ATH11K_SCAN_RUNNING: 5342 case ATH11K_SCAN_ABORTING: 5343 ar->scan_channel = ieee80211_get_channel(ar->hw->wiphy, freq); 5344 break; 5345 } 5346 } 5347 5348 static const char * 5349 ath11k_wmi_event_scan_type_str(enum wmi_scan_event_type type, 5350 enum wmi_scan_completion_reason reason) 5351 { 5352 switch (type) { 5353 case WMI_SCAN_EVENT_STARTED: 5354 return "started"; 5355 case WMI_SCAN_EVENT_COMPLETED: 5356 switch (reason) { 5357 case WMI_SCAN_REASON_COMPLETED: 5358 return "completed"; 5359 case WMI_SCAN_REASON_CANCELLED: 5360 return "completed [cancelled]"; 5361 case WMI_SCAN_REASON_PREEMPTED: 5362 return "completed [preempted]"; 5363 case WMI_SCAN_REASON_TIMEDOUT: 5364 return "completed [timedout]"; 5365 case WMI_SCAN_REASON_INTERNAL_FAILURE: 5366 return "completed [internal err]"; 5367 case WMI_SCAN_REASON_MAX: 5368 break; 5369 } 5370 return "completed [unknown]"; 5371 case WMI_SCAN_EVENT_BSS_CHANNEL: 5372 return "bss channel"; 5373 case WMI_SCAN_EVENT_FOREIGN_CHAN: 5374 return "foreign channel"; 5375 case WMI_SCAN_EVENT_DEQUEUED: 5376 return "dequeued"; 5377 case WMI_SCAN_EVENT_PREEMPTED: 5378 return "preempted"; 5379 case WMI_SCAN_EVENT_START_FAILED: 5380 return "start failed"; 5381 case WMI_SCAN_EVENT_RESTARTED: 5382 return "restarted"; 5383 case WMI_SCAN_EVENT_FOREIGN_CHAN_EXIT: 5384 return "foreign channel exit"; 5385 default: 5386 return "unknown"; 5387 } 5388 } 5389 5390 static int ath11k_pull_scan_ev(struct ath11k_base *ab, struct sk_buff *skb, 5391 struct wmi_scan_event *scan_evt_param) 5392 { 5393 const void **tb; 5394 const struct wmi_scan_event *ev; 5395 int ret; 5396 5397 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5398 if (IS_ERR(tb)) { 5399 ret = PTR_ERR(tb); 5400 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5401 return ret; 5402 } 5403 5404 ev = tb[WMI_TAG_SCAN_EVENT]; 5405 if (!ev) { 5406 ath11k_warn(ab, "failed to fetch scan ev"); 5407 kfree(tb); 5408 return -EPROTO; 5409 } 5410 5411 scan_evt_param->event_type = ev->event_type; 5412 scan_evt_param->reason = ev->reason; 5413 scan_evt_param->channel_freq = ev->channel_freq; 5414 scan_evt_param->scan_req_id = ev->scan_req_id; 5415 scan_evt_param->scan_id = ev->scan_id; 5416 scan_evt_param->vdev_id = ev->vdev_id; 5417 scan_evt_param->tsf_timestamp = ev->tsf_timestamp; 5418 5419 kfree(tb); 5420 return 0; 5421 } 5422 5423 static int ath11k_pull_peer_sta_kickout_ev(struct ath11k_base *ab, struct sk_buff *skb, 5424 struct wmi_peer_sta_kickout_arg *arg) 5425 { 5426 const void **tb; 5427 const struct wmi_peer_sta_kickout_event *ev; 5428 int ret; 5429 5430 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5431 if (IS_ERR(tb)) { 5432 ret = PTR_ERR(tb); 5433 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5434 return ret; 5435 } 5436 5437 ev = tb[WMI_TAG_PEER_STA_KICKOUT_EVENT]; 5438 if (!ev) { 5439 ath11k_warn(ab, "failed to fetch peer sta kickout ev"); 5440 kfree(tb); 5441 return -EPROTO; 5442 } 5443 5444 arg->mac_addr = ev->peer_macaddr.addr; 5445 5446 kfree(tb); 5447 return 0; 5448 } 5449 5450 static int ath11k_pull_roam_ev(struct ath11k_base *ab, struct sk_buff *skb, 5451 struct wmi_roam_event *roam_ev) 5452 { 5453 const void **tb; 5454 const struct wmi_roam_event *ev; 5455 int ret; 5456 5457 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5458 if (IS_ERR(tb)) { 5459 ret = PTR_ERR(tb); 5460 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5461 return ret; 5462 } 5463 5464 ev = tb[WMI_TAG_ROAM_EVENT]; 5465 if (!ev) { 5466 ath11k_warn(ab, "failed to fetch roam ev"); 5467 kfree(tb); 5468 return -EPROTO; 5469 } 5470 5471 roam_ev->vdev_id = ev->vdev_id; 5472 roam_ev->reason = ev->reason; 5473 roam_ev->rssi = ev->rssi; 5474 5475 kfree(tb); 5476 return 0; 5477 } 5478 5479 static int freq_to_idx(struct ath11k *ar, int freq) 5480 { 5481 struct ieee80211_supported_band *sband; 5482 int band, ch, idx = 0; 5483 5484 for (band = NL80211_BAND_2GHZ; band < NUM_NL80211_BANDS; band++) { 5485 sband = ar->hw->wiphy->bands[band]; 5486 if (!sband) 5487 continue; 5488 5489 for (ch = 0; ch < sband->n_channels; ch++, idx++) 5490 if (sband->channels[ch].center_freq == freq) 5491 goto exit; 5492 } 5493 5494 exit: 5495 return idx; 5496 } 5497 5498 static int ath11k_pull_chan_info_ev(struct ath11k_base *ab, u8 *evt_buf, 5499 u32 len, struct wmi_chan_info_event *ch_info_ev) 5500 { 5501 const void **tb; 5502 const struct wmi_chan_info_event *ev; 5503 int ret; 5504 5505 tb = ath11k_wmi_tlv_parse_alloc(ab, evt_buf, len, GFP_ATOMIC); 5506 if (IS_ERR(tb)) { 5507 ret = PTR_ERR(tb); 5508 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5509 return ret; 5510 } 5511 5512 ev = tb[WMI_TAG_CHAN_INFO_EVENT]; 5513 if (!ev) { 5514 ath11k_warn(ab, "failed to fetch chan info ev"); 5515 kfree(tb); 5516 return -EPROTO; 5517 } 5518 5519 ch_info_ev->err_code = ev->err_code; 5520 ch_info_ev->freq = ev->freq; 5521 ch_info_ev->cmd_flags = ev->cmd_flags; 5522 ch_info_ev->noise_floor = ev->noise_floor; 5523 ch_info_ev->rx_clear_count = ev->rx_clear_count; 5524 ch_info_ev->cycle_count = ev->cycle_count; 5525 ch_info_ev->chan_tx_pwr_range = ev->chan_tx_pwr_range; 5526 ch_info_ev->chan_tx_pwr_tp = ev->chan_tx_pwr_tp; 5527 ch_info_ev->rx_frame_count = ev->rx_frame_count; 5528 ch_info_ev->tx_frame_cnt = ev->tx_frame_cnt; 5529 ch_info_ev->mac_clk_mhz = ev->mac_clk_mhz; 5530 ch_info_ev->vdev_id = ev->vdev_id; 5531 5532 kfree(tb); 5533 return 0; 5534 } 5535 5536 static int 5537 ath11k_pull_pdev_bss_chan_info_ev(struct ath11k_base *ab, struct sk_buff *skb, 5538 struct wmi_pdev_bss_chan_info_event *bss_ch_info_ev) 5539 { 5540 const void **tb; 5541 const struct wmi_pdev_bss_chan_info_event *ev; 5542 int ret; 5543 5544 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5545 if (IS_ERR(tb)) { 5546 ret = PTR_ERR(tb); 5547 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5548 return ret; 5549 } 5550 5551 ev = tb[WMI_TAG_PDEV_BSS_CHAN_INFO_EVENT]; 5552 if (!ev) { 5553 ath11k_warn(ab, "failed to fetch pdev bss chan info ev"); 5554 kfree(tb); 5555 return -EPROTO; 5556 } 5557 5558 bss_ch_info_ev->pdev_id = ev->pdev_id; 5559 bss_ch_info_ev->freq = ev->freq; 5560 bss_ch_info_ev->noise_floor = ev->noise_floor; 5561 bss_ch_info_ev->rx_clear_count_low = ev->rx_clear_count_low; 5562 bss_ch_info_ev->rx_clear_count_high = ev->rx_clear_count_high; 5563 bss_ch_info_ev->cycle_count_low = ev->cycle_count_low; 5564 bss_ch_info_ev->cycle_count_high = ev->cycle_count_high; 5565 bss_ch_info_ev->tx_cycle_count_low = ev->tx_cycle_count_low; 5566 bss_ch_info_ev->tx_cycle_count_high = ev->tx_cycle_count_high; 5567 bss_ch_info_ev->rx_cycle_count_low = ev->rx_cycle_count_low; 5568 bss_ch_info_ev->rx_cycle_count_high = ev->rx_cycle_count_high; 5569 bss_ch_info_ev->rx_bss_cycle_count_low = ev->rx_bss_cycle_count_low; 5570 bss_ch_info_ev->rx_bss_cycle_count_high = ev->rx_bss_cycle_count_high; 5571 5572 kfree(tb); 5573 return 0; 5574 } 5575 5576 static int 5577 ath11k_pull_vdev_install_key_compl_ev(struct ath11k_base *ab, struct sk_buff *skb, 5578 struct wmi_vdev_install_key_complete_arg *arg) 5579 { 5580 const void **tb; 5581 const struct wmi_vdev_install_key_compl_event *ev; 5582 int ret; 5583 5584 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5585 if (IS_ERR(tb)) { 5586 ret = PTR_ERR(tb); 5587 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5588 return ret; 5589 } 5590 5591 ev = tb[WMI_TAG_VDEV_INSTALL_KEY_COMPLETE_EVENT]; 5592 if (!ev) { 5593 ath11k_warn(ab, "failed to fetch vdev install key compl ev"); 5594 kfree(tb); 5595 return -EPROTO; 5596 } 5597 5598 arg->vdev_id = ev->vdev_id; 5599 arg->macaddr = ev->peer_macaddr.addr; 5600 arg->key_idx = ev->key_idx; 5601 arg->key_flags = ev->key_flags; 5602 arg->status = ev->status; 5603 5604 kfree(tb); 5605 return 0; 5606 } 5607 5608 static int ath11k_pull_peer_assoc_conf_ev(struct ath11k_base *ab, struct sk_buff *skb, 5609 struct wmi_peer_assoc_conf_arg *peer_assoc_conf) 5610 { 5611 const void **tb; 5612 const struct wmi_peer_assoc_conf_event *ev; 5613 int ret; 5614 5615 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 5616 if (IS_ERR(tb)) { 5617 ret = PTR_ERR(tb); 5618 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 5619 return ret; 5620 } 5621 5622 ev = tb[WMI_TAG_PEER_ASSOC_CONF_EVENT]; 5623 if (!ev) { 5624 ath11k_warn(ab, "failed to fetch peer assoc conf ev"); 5625 kfree(tb); 5626 return -EPROTO; 5627 } 5628 5629 peer_assoc_conf->vdev_id = ev->vdev_id; 5630 peer_assoc_conf->macaddr = ev->peer_macaddr.addr; 5631 5632 kfree(tb); 5633 return 0; 5634 } 5635 5636 static void ath11k_wmi_pull_pdev_stats_base(const struct wmi_pdev_stats_base *src, 5637 struct ath11k_fw_stats_pdev *dst) 5638 { 5639 dst->ch_noise_floor = src->chan_nf; 5640 dst->tx_frame_count = src->tx_frame_count; 5641 dst->rx_frame_count = src->rx_frame_count; 5642 dst->rx_clear_count = src->rx_clear_count; 5643 dst->cycle_count = src->cycle_count; 5644 dst->phy_err_count = src->phy_err_count; 5645 dst->chan_tx_power = src->chan_tx_pwr; 5646 } 5647 5648 static void 5649 ath11k_wmi_pull_pdev_stats_tx(const struct wmi_pdev_stats_tx *src, 5650 struct ath11k_fw_stats_pdev *dst) 5651 { 5652 dst->comp_queued = src->comp_queued; 5653 dst->comp_delivered = src->comp_delivered; 5654 dst->msdu_enqued = src->msdu_enqued; 5655 dst->mpdu_enqued = src->mpdu_enqued; 5656 dst->wmm_drop = src->wmm_drop; 5657 dst->local_enqued = src->local_enqued; 5658 dst->local_freed = src->local_freed; 5659 dst->hw_queued = src->hw_queued; 5660 dst->hw_reaped = src->hw_reaped; 5661 dst->underrun = src->underrun; 5662 dst->hw_paused = src->hw_paused; 5663 dst->tx_abort = src->tx_abort; 5664 dst->mpdus_requeued = src->mpdus_requeued; 5665 dst->tx_ko = src->tx_ko; 5666 dst->tx_xretry = src->tx_xretry; 5667 dst->data_rc = src->data_rc; 5668 dst->self_triggers = src->self_triggers; 5669 dst->sw_retry_failure = src->sw_retry_failure; 5670 dst->illgl_rate_phy_err = src->illgl_rate_phy_err; 5671 dst->pdev_cont_xretry = src->pdev_cont_xretry; 5672 dst->pdev_tx_timeout = src->pdev_tx_timeout; 5673 dst->pdev_resets = src->pdev_resets; 5674 dst->stateless_tid_alloc_failure = src->stateless_tid_alloc_failure; 5675 dst->phy_underrun = src->phy_underrun; 5676 dst->txop_ovf = src->txop_ovf; 5677 dst->seq_posted = src->seq_posted; 5678 dst->seq_failed_queueing = src->seq_failed_queueing; 5679 dst->seq_completed = src->seq_completed; 5680 dst->seq_restarted = src->seq_restarted; 5681 dst->mu_seq_posted = src->mu_seq_posted; 5682 dst->mpdus_sw_flush = src->mpdus_sw_flush; 5683 dst->mpdus_hw_filter = src->mpdus_hw_filter; 5684 dst->mpdus_truncated = src->mpdus_truncated; 5685 dst->mpdus_ack_failed = src->mpdus_ack_failed; 5686 dst->mpdus_expired = src->mpdus_expired; 5687 } 5688 5689 static void ath11k_wmi_pull_pdev_stats_rx(const struct wmi_pdev_stats_rx *src, 5690 struct ath11k_fw_stats_pdev *dst) 5691 { 5692 dst->mid_ppdu_route_change = src->mid_ppdu_route_change; 5693 dst->status_rcvd = src->status_rcvd; 5694 dst->r0_frags = src->r0_frags; 5695 dst->r1_frags = src->r1_frags; 5696 dst->r2_frags = src->r2_frags; 5697 dst->r3_frags = src->r3_frags; 5698 dst->htt_msdus = src->htt_msdus; 5699 dst->htt_mpdus = src->htt_mpdus; 5700 dst->loc_msdus = src->loc_msdus; 5701 dst->loc_mpdus = src->loc_mpdus; 5702 dst->oversize_amsdu = src->oversize_amsdu; 5703 dst->phy_errs = src->phy_errs; 5704 dst->phy_err_drop = src->phy_err_drop; 5705 dst->mpdu_errs = src->mpdu_errs; 5706 dst->rx_ovfl_errs = src->rx_ovfl_errs; 5707 } 5708 5709 static void 5710 ath11k_wmi_pull_vdev_stats(const struct wmi_vdev_stats *src, 5711 struct ath11k_fw_stats_vdev *dst) 5712 { 5713 int i; 5714 5715 dst->vdev_id = src->vdev_id; 5716 dst->beacon_snr = src->beacon_snr; 5717 dst->data_snr = src->data_snr; 5718 dst->num_rx_frames = src->num_rx_frames; 5719 dst->num_rts_fail = src->num_rts_fail; 5720 dst->num_rts_success = src->num_rts_success; 5721 dst->num_rx_err = src->num_rx_err; 5722 dst->num_rx_discard = src->num_rx_discard; 5723 dst->num_tx_not_acked = src->num_tx_not_acked; 5724 5725 for (i = 0; i < ARRAY_SIZE(src->num_tx_frames); i++) 5726 dst->num_tx_frames[i] = src->num_tx_frames[i]; 5727 5728 for (i = 0; i < ARRAY_SIZE(src->num_tx_frames_retries); i++) 5729 dst->num_tx_frames_retries[i] = src->num_tx_frames_retries[i]; 5730 5731 for (i = 0; i < ARRAY_SIZE(src->num_tx_frames_failures); i++) 5732 dst->num_tx_frames_failures[i] = src->num_tx_frames_failures[i]; 5733 5734 for (i = 0; i < ARRAY_SIZE(src->tx_rate_history); i++) 5735 dst->tx_rate_history[i] = src->tx_rate_history[i]; 5736 5737 for (i = 0; i < ARRAY_SIZE(src->beacon_rssi_history); i++) 5738 dst->beacon_rssi_history[i] = src->beacon_rssi_history[i]; 5739 } 5740 5741 static void 5742 ath11k_wmi_pull_bcn_stats(const struct wmi_bcn_stats *src, 5743 struct ath11k_fw_stats_bcn *dst) 5744 { 5745 dst->vdev_id = src->vdev_id; 5746 dst->tx_bcn_succ_cnt = src->tx_bcn_succ_cnt; 5747 dst->tx_bcn_outage_cnt = src->tx_bcn_outage_cnt; 5748 } 5749 5750 static int ath11k_wmi_tlv_rssi_chain_parse(struct ath11k_base *ab, 5751 u16 tag, u16 len, 5752 const void *ptr, void *data) 5753 { 5754 struct wmi_tlv_fw_stats_parse *parse = data; 5755 const struct wmi_stats_event *ev = parse->ev; 5756 struct ath11k_fw_stats *stats = parse->stats; 5757 struct ath11k *ar; 5758 struct ath11k_vif *arvif; 5759 struct ieee80211_sta *sta; 5760 struct ath11k_sta *arsta; 5761 const struct wmi_rssi_stats *stats_rssi = (const struct wmi_rssi_stats *)ptr; 5762 int j, ret = 0; 5763 5764 if (tag != WMI_TAG_RSSI_STATS) 5765 return -EPROTO; 5766 5767 rcu_read_lock(); 5768 5769 ar = ath11k_mac_get_ar_by_pdev_id(ab, ev->pdev_id); 5770 stats->stats_id = WMI_REQUEST_RSSI_PER_CHAIN_STAT; 5771 5772 ath11k_dbg(ab, ATH11K_DBG_WMI, 5773 "wmi stats vdev id %d mac %pM\n", 5774 stats_rssi->vdev_id, stats_rssi->peer_macaddr.addr); 5775 5776 arvif = ath11k_mac_get_arvif(ar, stats_rssi->vdev_id); 5777 if (!arvif) { 5778 ath11k_warn(ab, "not found vif for vdev id %d\n", 5779 stats_rssi->vdev_id); 5780 ret = -EPROTO; 5781 goto exit; 5782 } 5783 5784 ath11k_dbg(ab, ATH11K_DBG_WMI, 5785 "wmi stats bssid %pM vif %pK\n", 5786 arvif->bssid, arvif->vif); 5787 5788 sta = ieee80211_find_sta_by_ifaddr(ar->hw, 5789 arvif->bssid, 5790 NULL); 5791 if (!sta) { 5792 ath11k_warn(ab, "not found station for bssid %pM\n", 5793 arvif->bssid); 5794 ret = -EPROTO; 5795 goto exit; 5796 } 5797 5798 arsta = (struct ath11k_sta *)sta->drv_priv; 5799 5800 BUILD_BUG_ON(ARRAY_SIZE(arsta->chain_signal) > 5801 ARRAY_SIZE(stats_rssi->rssi_avg_beacon)); 5802 5803 for (j = 0; j < ARRAY_SIZE(arsta->chain_signal); j++) { 5804 arsta->chain_signal[j] = stats_rssi->rssi_avg_beacon[j]; 5805 ath11k_dbg(ab, ATH11K_DBG_WMI, 5806 "wmi stats beacon rssi[%d] %d data rssi[%d] %d\n", 5807 j, 5808 stats_rssi->rssi_avg_beacon[j], 5809 j, 5810 stats_rssi->rssi_avg_data[j]); 5811 } 5812 5813 exit: 5814 rcu_read_unlock(); 5815 return ret; 5816 } 5817 5818 static int ath11k_wmi_tlv_fw_stats_data_parse(struct ath11k_base *ab, 5819 struct wmi_tlv_fw_stats_parse *parse, 5820 const void *ptr, 5821 u16 len) 5822 { 5823 struct ath11k_fw_stats *stats = parse->stats; 5824 const struct wmi_stats_event *ev = parse->ev; 5825 struct ath11k *ar; 5826 struct ath11k_vif *arvif; 5827 struct ieee80211_sta *sta; 5828 struct ath11k_sta *arsta; 5829 int i, ret = 0; 5830 const void *data = ptr; 5831 5832 if (!ev) { 5833 ath11k_warn(ab, "failed to fetch update stats ev"); 5834 return -EPROTO; 5835 } 5836 5837 stats->stats_id = 0; 5838 5839 rcu_read_lock(); 5840 5841 ar = ath11k_mac_get_ar_by_pdev_id(ab, ev->pdev_id); 5842 5843 for (i = 0; i < ev->num_pdev_stats; i++) { 5844 const struct wmi_pdev_stats *src; 5845 struct ath11k_fw_stats_pdev *dst; 5846 5847 src = data; 5848 if (len < sizeof(*src)) { 5849 ret = -EPROTO; 5850 goto exit; 5851 } 5852 5853 stats->stats_id = WMI_REQUEST_PDEV_STAT; 5854 5855 data += sizeof(*src); 5856 len -= sizeof(*src); 5857 5858 dst = kzalloc(sizeof(*dst), GFP_ATOMIC); 5859 if (!dst) 5860 continue; 5861 5862 ath11k_wmi_pull_pdev_stats_base(&src->base, dst); 5863 ath11k_wmi_pull_pdev_stats_tx(&src->tx, dst); 5864 ath11k_wmi_pull_pdev_stats_rx(&src->rx, dst); 5865 list_add_tail(&dst->list, &stats->pdevs); 5866 } 5867 5868 for (i = 0; i < ev->num_vdev_stats; i++) { 5869 const struct wmi_vdev_stats *src; 5870 struct ath11k_fw_stats_vdev *dst; 5871 5872 src = data; 5873 if (len < sizeof(*src)) { 5874 ret = -EPROTO; 5875 goto exit; 5876 } 5877 5878 stats->stats_id = WMI_REQUEST_VDEV_STAT; 5879 5880 arvif = ath11k_mac_get_arvif(ar, src->vdev_id); 5881 if (arvif) { 5882 sta = ieee80211_find_sta_by_ifaddr(ar->hw, 5883 arvif->bssid, 5884 NULL); 5885 if (sta) { 5886 arsta = (struct ath11k_sta *)sta->drv_priv; 5887 arsta->rssi_beacon = src->beacon_snr; 5888 ath11k_dbg(ab, ATH11K_DBG_WMI, 5889 "wmi stats vdev id %d snr %d\n", 5890 src->vdev_id, src->beacon_snr); 5891 } else { 5892 ath11k_warn(ab, "not found station for bssid %pM\n", 5893 arvif->bssid); 5894 } 5895 } 5896 5897 data += sizeof(*src); 5898 len -= sizeof(*src); 5899 5900 dst = kzalloc(sizeof(*dst), GFP_ATOMIC); 5901 if (!dst) 5902 continue; 5903 5904 ath11k_wmi_pull_vdev_stats(src, dst); 5905 list_add_tail(&dst->list, &stats->vdevs); 5906 } 5907 5908 for (i = 0; i < ev->num_bcn_stats; i++) { 5909 const struct wmi_bcn_stats *src; 5910 struct ath11k_fw_stats_bcn *dst; 5911 5912 src = data; 5913 if (len < sizeof(*src)) { 5914 ret = -EPROTO; 5915 goto exit; 5916 } 5917 5918 stats->stats_id = WMI_REQUEST_BCN_STAT; 5919 5920 data += sizeof(*src); 5921 len -= sizeof(*src); 5922 5923 dst = kzalloc(sizeof(*dst), GFP_ATOMIC); 5924 if (!dst) 5925 continue; 5926 5927 ath11k_wmi_pull_bcn_stats(src, dst); 5928 list_add_tail(&dst->list, &stats->bcn); 5929 } 5930 5931 exit: 5932 rcu_read_unlock(); 5933 return ret; 5934 } 5935 5936 static int ath11k_wmi_tlv_fw_stats_parse(struct ath11k_base *ab, 5937 u16 tag, u16 len, 5938 const void *ptr, void *data) 5939 { 5940 struct wmi_tlv_fw_stats_parse *parse = data; 5941 int ret = 0; 5942 5943 switch (tag) { 5944 case WMI_TAG_STATS_EVENT: 5945 parse->ev = (struct wmi_stats_event *)ptr; 5946 parse->stats->pdev_id = parse->ev->pdev_id; 5947 break; 5948 case WMI_TAG_ARRAY_BYTE: 5949 ret = ath11k_wmi_tlv_fw_stats_data_parse(ab, parse, ptr, len); 5950 break; 5951 case WMI_TAG_PER_CHAIN_RSSI_STATS: 5952 parse->rssi = (struct wmi_per_chain_rssi_stats *)ptr; 5953 5954 if (parse->ev->stats_id & WMI_REQUEST_RSSI_PER_CHAIN_STAT) 5955 parse->rssi_num = parse->rssi->num_per_chain_rssi_stats; 5956 5957 ath11k_dbg(ab, ATH11K_DBG_WMI, 5958 "wmi stats id 0x%x num chain %d\n", 5959 parse->ev->stats_id, 5960 parse->rssi_num); 5961 break; 5962 case WMI_TAG_ARRAY_STRUCT: 5963 if (parse->rssi_num && !parse->chain_rssi_done) { 5964 ret = ath11k_wmi_tlv_iter(ab, ptr, len, 5965 ath11k_wmi_tlv_rssi_chain_parse, 5966 parse); 5967 if (ret) { 5968 ath11k_warn(ab, "failed to parse rssi chain %d\n", 5969 ret); 5970 return ret; 5971 } 5972 parse->chain_rssi_done = true; 5973 } 5974 break; 5975 default: 5976 break; 5977 } 5978 return ret; 5979 } 5980 5981 int ath11k_wmi_pull_fw_stats(struct ath11k_base *ab, struct sk_buff *skb, 5982 struct ath11k_fw_stats *stats) 5983 { 5984 struct wmi_tlv_fw_stats_parse parse = { }; 5985 5986 stats->stats_id = 0; 5987 parse.stats = stats; 5988 5989 return ath11k_wmi_tlv_iter(ab, skb->data, skb->len, 5990 ath11k_wmi_tlv_fw_stats_parse, 5991 &parse); 5992 } 5993 5994 size_t ath11k_wmi_fw_stats_num_vdevs(struct list_head *head) 5995 { 5996 struct ath11k_fw_stats_vdev *i; 5997 size_t num = 0; 5998 5999 list_for_each_entry(i, head, list) 6000 ++num; 6001 6002 return num; 6003 } 6004 6005 static size_t ath11k_wmi_fw_stats_num_bcn(struct list_head *head) 6006 { 6007 struct ath11k_fw_stats_bcn *i; 6008 size_t num = 0; 6009 6010 list_for_each_entry(i, head, list) 6011 ++num; 6012 6013 return num; 6014 } 6015 6016 static void 6017 ath11k_wmi_fw_pdev_base_stats_fill(const struct ath11k_fw_stats_pdev *pdev, 6018 char *buf, u32 *length) 6019 { 6020 u32 len = *length; 6021 u32 buf_len = ATH11K_FW_STATS_BUF_SIZE; 6022 6023 len += scnprintf(buf + len, buf_len - len, "\n"); 6024 len += scnprintf(buf + len, buf_len - len, "%30s\n", 6025 "ath11k PDEV stats"); 6026 len += scnprintf(buf + len, buf_len - len, "%30s\n\n", 6027 "================="); 6028 6029 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6030 "Channel noise floor", pdev->ch_noise_floor); 6031 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6032 "Channel TX power", pdev->chan_tx_power); 6033 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6034 "TX frame count", pdev->tx_frame_count); 6035 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6036 "RX frame count", pdev->rx_frame_count); 6037 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6038 "RX clear count", pdev->rx_clear_count); 6039 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6040 "Cycle count", pdev->cycle_count); 6041 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6042 "PHY error count", pdev->phy_err_count); 6043 6044 *length = len; 6045 } 6046 6047 static void 6048 ath11k_wmi_fw_pdev_tx_stats_fill(const struct ath11k_fw_stats_pdev *pdev, 6049 char *buf, u32 *length) 6050 { 6051 u32 len = *length; 6052 u32 buf_len = ATH11K_FW_STATS_BUF_SIZE; 6053 6054 len += scnprintf(buf + len, buf_len - len, "\n%30s\n", 6055 "ath11k PDEV TX stats"); 6056 len += scnprintf(buf + len, buf_len - len, "%30s\n\n", 6057 "===================="); 6058 6059 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6060 "HTT cookies queued", pdev->comp_queued); 6061 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6062 "HTT cookies disp.", pdev->comp_delivered); 6063 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6064 "MSDU queued", pdev->msdu_enqued); 6065 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6066 "MPDU queued", pdev->mpdu_enqued); 6067 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6068 "MSDUs dropped", pdev->wmm_drop); 6069 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6070 "Local enqued", pdev->local_enqued); 6071 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6072 "Local freed", pdev->local_freed); 6073 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6074 "HW queued", pdev->hw_queued); 6075 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6076 "PPDUs reaped", pdev->hw_reaped); 6077 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6078 "Num underruns", pdev->underrun); 6079 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6080 "Num HW Paused", pdev->hw_paused); 6081 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6082 "PPDUs cleaned", pdev->tx_abort); 6083 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6084 "MPDUs requeued", pdev->mpdus_requeued); 6085 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6086 "PPDU OK", pdev->tx_ko); 6087 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6088 "Excessive retries", pdev->tx_xretry); 6089 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6090 "HW rate", pdev->data_rc); 6091 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6092 "Sched self triggers", pdev->self_triggers); 6093 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6094 "Dropped due to SW retries", 6095 pdev->sw_retry_failure); 6096 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6097 "Illegal rate phy errors", 6098 pdev->illgl_rate_phy_err); 6099 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6100 "PDEV continuous xretry", pdev->pdev_cont_xretry); 6101 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6102 "TX timeout", pdev->pdev_tx_timeout); 6103 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6104 "PDEV resets", pdev->pdev_resets); 6105 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6106 "Stateless TIDs alloc failures", 6107 pdev->stateless_tid_alloc_failure); 6108 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6109 "PHY underrun", pdev->phy_underrun); 6110 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6111 "MPDU is more than txop limit", pdev->txop_ovf); 6112 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6113 "Num sequences posted", pdev->seq_posted); 6114 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6115 "Num seq failed queueing ", pdev->seq_failed_queueing); 6116 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6117 "Num sequences completed ", pdev->seq_completed); 6118 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6119 "Num sequences restarted ", pdev->seq_restarted); 6120 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6121 "Num of MU sequences posted ", pdev->mu_seq_posted); 6122 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6123 "Num of MPDUS SW flushed ", pdev->mpdus_sw_flush); 6124 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6125 "Num of MPDUS HW filtered ", pdev->mpdus_hw_filter); 6126 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6127 "Num of MPDUS truncated ", pdev->mpdus_truncated); 6128 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6129 "Num of MPDUS ACK failed ", pdev->mpdus_ack_failed); 6130 len += scnprintf(buf + len, buf_len - len, "%30s %10u\n", 6131 "Num of MPDUS expired ", pdev->mpdus_expired); 6132 *length = len; 6133 } 6134 6135 static void 6136 ath11k_wmi_fw_pdev_rx_stats_fill(const struct ath11k_fw_stats_pdev *pdev, 6137 char *buf, u32 *length) 6138 { 6139 u32 len = *length; 6140 u32 buf_len = ATH11K_FW_STATS_BUF_SIZE; 6141 6142 len += scnprintf(buf + len, buf_len - len, "\n%30s\n", 6143 "ath11k PDEV RX stats"); 6144 len += scnprintf(buf + len, buf_len - len, "%30s\n\n", 6145 "===================="); 6146 6147 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6148 "Mid PPDU route change", 6149 pdev->mid_ppdu_route_change); 6150 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6151 "Tot. number of statuses", pdev->status_rcvd); 6152 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6153 "Extra frags on rings 0", pdev->r0_frags); 6154 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6155 "Extra frags on rings 1", pdev->r1_frags); 6156 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6157 "Extra frags on rings 2", pdev->r2_frags); 6158 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6159 "Extra frags on rings 3", pdev->r3_frags); 6160 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6161 "MSDUs delivered to HTT", pdev->htt_msdus); 6162 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6163 "MPDUs delivered to HTT", pdev->htt_mpdus); 6164 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6165 "MSDUs delivered to stack", pdev->loc_msdus); 6166 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6167 "MPDUs delivered to stack", pdev->loc_mpdus); 6168 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6169 "Oversized AMSUs", pdev->oversize_amsdu); 6170 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6171 "PHY errors", pdev->phy_errs); 6172 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6173 "PHY errors drops", pdev->phy_err_drop); 6174 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6175 "MPDU errors (FCS, MIC, ENC)", pdev->mpdu_errs); 6176 len += scnprintf(buf + len, buf_len - len, "%30s %10d\n", 6177 "Overflow errors", pdev->rx_ovfl_errs); 6178 *length = len; 6179 } 6180 6181 static void 6182 ath11k_wmi_fw_vdev_stats_fill(struct ath11k *ar, 6183 const struct ath11k_fw_stats_vdev *vdev, 6184 char *buf, u32 *length) 6185 { 6186 u32 len = *length; 6187 u32 buf_len = ATH11K_FW_STATS_BUF_SIZE; 6188 struct ath11k_vif *arvif = ath11k_mac_get_arvif(ar, vdev->vdev_id); 6189 u8 *vif_macaddr; 6190 int i; 6191 6192 /* VDEV stats has all the active VDEVs of other PDEVs as well, 6193 * ignoring those not part of requested PDEV 6194 */ 6195 if (!arvif) 6196 return; 6197 6198 vif_macaddr = arvif->vif->addr; 6199 6200 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6201 "VDEV ID", vdev->vdev_id); 6202 len += scnprintf(buf + len, buf_len - len, "%30s %pM\n", 6203 "VDEV MAC address", vif_macaddr); 6204 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6205 "beacon snr", vdev->beacon_snr); 6206 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6207 "data snr", vdev->data_snr); 6208 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6209 "num rx frames", vdev->num_rx_frames); 6210 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6211 "num rts fail", vdev->num_rts_fail); 6212 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6213 "num rts success", vdev->num_rts_success); 6214 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6215 "num rx err", vdev->num_rx_err); 6216 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6217 "num rx discard", vdev->num_rx_discard); 6218 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6219 "num tx not acked", vdev->num_tx_not_acked); 6220 6221 for (i = 0 ; i < ARRAY_SIZE(vdev->num_tx_frames); i++) 6222 len += scnprintf(buf + len, buf_len - len, 6223 "%25s [%02d] %u\n", 6224 "num tx frames", i, 6225 vdev->num_tx_frames[i]); 6226 6227 for (i = 0 ; i < ARRAY_SIZE(vdev->num_tx_frames_retries); i++) 6228 len += scnprintf(buf + len, buf_len - len, 6229 "%25s [%02d] %u\n", 6230 "num tx frames retries", i, 6231 vdev->num_tx_frames_retries[i]); 6232 6233 for (i = 0 ; i < ARRAY_SIZE(vdev->num_tx_frames_failures); i++) 6234 len += scnprintf(buf + len, buf_len - len, 6235 "%25s [%02d] %u\n", 6236 "num tx frames failures", i, 6237 vdev->num_tx_frames_failures[i]); 6238 6239 for (i = 0 ; i < ARRAY_SIZE(vdev->tx_rate_history); i++) 6240 len += scnprintf(buf + len, buf_len - len, 6241 "%25s [%02d] 0x%08x\n", 6242 "tx rate history", i, 6243 vdev->tx_rate_history[i]); 6244 6245 for (i = 0 ; i < ARRAY_SIZE(vdev->beacon_rssi_history); i++) 6246 len += scnprintf(buf + len, buf_len - len, 6247 "%25s [%02d] %u\n", 6248 "beacon rssi history", i, 6249 vdev->beacon_rssi_history[i]); 6250 6251 len += scnprintf(buf + len, buf_len - len, "\n"); 6252 *length = len; 6253 } 6254 6255 static void 6256 ath11k_wmi_fw_bcn_stats_fill(struct ath11k *ar, 6257 const struct ath11k_fw_stats_bcn *bcn, 6258 char *buf, u32 *length) 6259 { 6260 u32 len = *length; 6261 u32 buf_len = ATH11K_FW_STATS_BUF_SIZE; 6262 struct ath11k_vif *arvif = ath11k_mac_get_arvif(ar, bcn->vdev_id); 6263 u8 *vdev_macaddr; 6264 6265 if (!arvif) { 6266 ath11k_warn(ar->ab, "invalid vdev id %d in bcn stats", 6267 bcn->vdev_id); 6268 return; 6269 } 6270 6271 vdev_macaddr = arvif->vif->addr; 6272 6273 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6274 "VDEV ID", bcn->vdev_id); 6275 len += scnprintf(buf + len, buf_len - len, "%30s %pM\n", 6276 "VDEV MAC address", vdev_macaddr); 6277 len += scnprintf(buf + len, buf_len - len, "%30s\n\n", 6278 "================"); 6279 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6280 "Num of beacon tx success", bcn->tx_bcn_succ_cnt); 6281 len += scnprintf(buf + len, buf_len - len, "%30s %u\n", 6282 "Num of beacon tx failures", bcn->tx_bcn_outage_cnt); 6283 6284 len += scnprintf(buf + len, buf_len - len, "\n"); 6285 *length = len; 6286 } 6287 6288 void ath11k_wmi_fw_stats_fill(struct ath11k *ar, 6289 struct ath11k_fw_stats *fw_stats, 6290 u32 stats_id, char *buf) 6291 { 6292 u32 len = 0; 6293 u32 buf_len = ATH11K_FW_STATS_BUF_SIZE; 6294 const struct ath11k_fw_stats_pdev *pdev; 6295 const struct ath11k_fw_stats_vdev *vdev; 6296 const struct ath11k_fw_stats_bcn *bcn; 6297 size_t num_bcn; 6298 6299 spin_lock_bh(&ar->data_lock); 6300 6301 if (stats_id == WMI_REQUEST_PDEV_STAT) { 6302 pdev = list_first_entry_or_null(&fw_stats->pdevs, 6303 struct ath11k_fw_stats_pdev, list); 6304 if (!pdev) { 6305 ath11k_warn(ar->ab, "failed to get pdev stats\n"); 6306 goto unlock; 6307 } 6308 6309 ath11k_wmi_fw_pdev_base_stats_fill(pdev, buf, &len); 6310 ath11k_wmi_fw_pdev_tx_stats_fill(pdev, buf, &len); 6311 ath11k_wmi_fw_pdev_rx_stats_fill(pdev, buf, &len); 6312 } 6313 6314 if (stats_id == WMI_REQUEST_VDEV_STAT) { 6315 len += scnprintf(buf + len, buf_len - len, "\n"); 6316 len += scnprintf(buf + len, buf_len - len, "%30s\n", 6317 "ath11k VDEV stats"); 6318 len += scnprintf(buf + len, buf_len - len, "%30s\n\n", 6319 "================="); 6320 6321 list_for_each_entry(vdev, &fw_stats->vdevs, list) 6322 ath11k_wmi_fw_vdev_stats_fill(ar, vdev, buf, &len); 6323 } 6324 6325 if (stats_id == WMI_REQUEST_BCN_STAT) { 6326 num_bcn = ath11k_wmi_fw_stats_num_bcn(&fw_stats->bcn); 6327 6328 len += scnprintf(buf + len, buf_len - len, "\n"); 6329 len += scnprintf(buf + len, buf_len - len, "%30s (%zu)\n", 6330 "ath11k Beacon stats", num_bcn); 6331 len += scnprintf(buf + len, buf_len - len, "%30s\n\n", 6332 "==================="); 6333 6334 list_for_each_entry(bcn, &fw_stats->bcn, list) 6335 ath11k_wmi_fw_bcn_stats_fill(ar, bcn, buf, &len); 6336 } 6337 6338 unlock: 6339 spin_unlock_bh(&ar->data_lock); 6340 6341 if (len >= buf_len) 6342 buf[len - 1] = 0; 6343 else 6344 buf[len] = 0; 6345 } 6346 6347 static void ath11k_wmi_op_ep_tx_credits(struct ath11k_base *ab) 6348 { 6349 /* try to send pending beacons first. they take priority */ 6350 wake_up(&ab->wmi_ab.tx_credits_wq); 6351 } 6352 6353 static int ath11k_reg_11d_new_cc_event(struct ath11k_base *ab, struct sk_buff *skb) 6354 { 6355 const struct wmi_11d_new_cc_ev *ev; 6356 struct ath11k *ar; 6357 struct ath11k_pdev *pdev; 6358 const void **tb; 6359 int ret, i; 6360 6361 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 6362 if (IS_ERR(tb)) { 6363 ret = PTR_ERR(tb); 6364 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 6365 return ret; 6366 } 6367 6368 ev = tb[WMI_TAG_11D_NEW_COUNTRY_EVENT]; 6369 if (!ev) { 6370 kfree(tb); 6371 ath11k_warn(ab, "failed to fetch 11d new cc ev"); 6372 return -EPROTO; 6373 } 6374 6375 spin_lock_bh(&ab->base_lock); 6376 memcpy(&ab->new_alpha2, &ev->new_alpha2, 2); 6377 spin_unlock_bh(&ab->base_lock); 6378 6379 ath11k_dbg(ab, ATH11K_DBG_WMI, "wmi 11d new cc %c%c\n", 6380 ab->new_alpha2[0], 6381 ab->new_alpha2[1]); 6382 6383 kfree(tb); 6384 6385 for (i = 0; i < ab->num_radios; i++) { 6386 pdev = &ab->pdevs[i]; 6387 ar = pdev->ar; 6388 ar->state_11d = ATH11K_11D_IDLE; 6389 complete(&ar->completed_11d_scan); 6390 } 6391 6392 queue_work(ab->workqueue, &ab->update_11d_work); 6393 6394 return 0; 6395 } 6396 6397 static void ath11k_wmi_htc_tx_complete(struct ath11k_base *ab, 6398 struct sk_buff *skb) 6399 { 6400 struct ath11k_pdev_wmi *wmi = NULL; 6401 u32 i; 6402 u8 wmi_ep_count; 6403 u8 eid; 6404 6405 eid = ATH11K_SKB_CB(skb)->eid; 6406 dev_kfree_skb(skb); 6407 6408 if (eid >= ATH11K_HTC_EP_COUNT) 6409 return; 6410 6411 wmi_ep_count = ab->htc.wmi_ep_count; 6412 if (wmi_ep_count > ab->hw_params.max_radios) 6413 return; 6414 6415 for (i = 0; i < ab->htc.wmi_ep_count; i++) { 6416 if (ab->wmi_ab.wmi[i].eid == eid) { 6417 wmi = &ab->wmi_ab.wmi[i]; 6418 break; 6419 } 6420 } 6421 6422 if (wmi) 6423 wake_up(&wmi->tx_ce_desc_wq); 6424 } 6425 6426 static bool ath11k_reg_is_world_alpha(char *alpha) 6427 { 6428 if (alpha[0] == '0' && alpha[1] == '0') 6429 return true; 6430 6431 if (alpha[0] == 'n' && alpha[1] == 'a') 6432 return true; 6433 6434 return false; 6435 } 6436 6437 static int ath11k_reg_chan_list_event(struct ath11k_base *ab, struct sk_buff *skb) 6438 { 6439 struct cur_regulatory_info *reg_info = NULL; 6440 struct ieee80211_regdomain *regd = NULL; 6441 bool intersect = false; 6442 int ret = 0, pdev_idx; 6443 struct ath11k *ar; 6444 6445 reg_info = kzalloc(sizeof(*reg_info), GFP_ATOMIC); 6446 if (!reg_info) { 6447 ret = -ENOMEM; 6448 goto fallback; 6449 } 6450 6451 ret = ath11k_pull_reg_chan_list_update_ev(ab, skb, reg_info); 6452 if (ret) { 6453 ath11k_warn(ab, "failed to extract regulatory info from received event\n"); 6454 goto fallback; 6455 } 6456 6457 if (reg_info->status_code != REG_SET_CC_STATUS_PASS) { 6458 /* In case of failure to set the requested ctry, 6459 * fw retains the current regd. We print a failure info 6460 * and return from here. 6461 */ 6462 ath11k_warn(ab, "Failed to set the requested Country regulatory setting\n"); 6463 goto mem_free; 6464 } 6465 6466 pdev_idx = reg_info->phy_id; 6467 6468 /* Avoid default reg rule updates sent during FW recovery if 6469 * it is already available 6470 */ 6471 spin_lock(&ab->base_lock); 6472 if (test_bit(ATH11K_FLAG_RECOVERY, &ab->dev_flags) && 6473 ab->default_regd[pdev_idx]) { 6474 spin_unlock(&ab->base_lock); 6475 goto mem_free; 6476 } 6477 spin_unlock(&ab->base_lock); 6478 6479 if (pdev_idx >= ab->num_radios) { 6480 /* Process the event for phy0 only if single_pdev_only 6481 * is true. If pdev_idx is valid but not 0, discard the 6482 * event. Otherwise, it goes to fallback. 6483 */ 6484 if (ab->hw_params.single_pdev_only && 6485 pdev_idx < ab->hw_params.num_rxmda_per_pdev) 6486 goto mem_free; 6487 else 6488 goto fallback; 6489 } 6490 6491 /* Avoid multiple overwrites to default regd, during core 6492 * stop-start after mac registration. 6493 */ 6494 if (ab->default_regd[pdev_idx] && !ab->new_regd[pdev_idx] && 6495 !memcmp((char *)ab->default_regd[pdev_idx]->alpha2, 6496 (char *)reg_info->alpha2, 2)) 6497 goto mem_free; 6498 6499 /* Intersect new rules with default regd if a new country setting was 6500 * requested, i.e a default regd was already set during initialization 6501 * and the regd coming from this event has a valid country info. 6502 */ 6503 if (ab->default_regd[pdev_idx] && 6504 !ath11k_reg_is_world_alpha((char *) 6505 ab->default_regd[pdev_idx]->alpha2) && 6506 !ath11k_reg_is_world_alpha((char *)reg_info->alpha2)) 6507 intersect = true; 6508 6509 regd = ath11k_reg_build_regd(ab, reg_info, intersect); 6510 if (!regd) { 6511 ath11k_warn(ab, "failed to build regd from reg_info\n"); 6512 goto fallback; 6513 } 6514 6515 spin_lock(&ab->base_lock); 6516 if (ab->default_regd[pdev_idx]) { 6517 /* The initial rules from FW after WMI Init is to build 6518 * the default regd. From then on, any rules updated for 6519 * the pdev could be due to user reg changes. 6520 * Free previously built regd before assigning the newly 6521 * generated regd to ar. NULL pointer handling will be 6522 * taken care by kfree itself. 6523 */ 6524 ar = ab->pdevs[pdev_idx].ar; 6525 kfree(ab->new_regd[pdev_idx]); 6526 ab->new_regd[pdev_idx] = regd; 6527 queue_work(ab->workqueue, &ar->regd_update_work); 6528 } else { 6529 /* This regd would be applied during mac registration and is 6530 * held constant throughout for regd intersection purpose 6531 */ 6532 ab->default_regd[pdev_idx] = regd; 6533 } 6534 ab->dfs_region = reg_info->dfs_region; 6535 spin_unlock(&ab->base_lock); 6536 6537 goto mem_free; 6538 6539 fallback: 6540 /* Fallback to older reg (by sending previous country setting 6541 * again if fw has succeded and we failed to process here. 6542 * The Regdomain should be uniform across driver and fw. Since the 6543 * FW has processed the command and sent a success status, we expect 6544 * this function to succeed as well. If it doesn't, CTRY needs to be 6545 * reverted at the fw and the old SCAN_CHAN_LIST cmd needs to be sent. 6546 */ 6547 /* TODO: This is rare, but still should also be handled */ 6548 WARN_ON(1); 6549 mem_free: 6550 if (reg_info) { 6551 kfree(reg_info->reg_rules_2g_ptr); 6552 kfree(reg_info->reg_rules_5g_ptr); 6553 kfree(reg_info); 6554 } 6555 return ret; 6556 } 6557 6558 static int ath11k_wmi_tlv_rdy_parse(struct ath11k_base *ab, u16 tag, u16 len, 6559 const void *ptr, void *data) 6560 { 6561 struct wmi_tlv_rdy_parse *rdy_parse = data; 6562 struct wmi_ready_event fixed_param; 6563 struct wmi_mac_addr *addr_list; 6564 struct ath11k_pdev *pdev; 6565 u32 num_mac_addr; 6566 int i; 6567 6568 switch (tag) { 6569 case WMI_TAG_READY_EVENT: 6570 memset(&fixed_param, 0, sizeof(fixed_param)); 6571 memcpy(&fixed_param, (struct wmi_ready_event *)ptr, 6572 min_t(u16, sizeof(fixed_param), len)); 6573 ab->wlan_init_status = fixed_param.ready_event_min.status; 6574 rdy_parse->num_extra_mac_addr = 6575 fixed_param.ready_event_min.num_extra_mac_addr; 6576 6577 ether_addr_copy(ab->mac_addr, 6578 fixed_param.ready_event_min.mac_addr.addr); 6579 ab->pktlog_defs_checksum = fixed_param.pktlog_defs_checksum; 6580 ab->wmi_ready = true; 6581 break; 6582 case WMI_TAG_ARRAY_FIXED_STRUCT: 6583 addr_list = (struct wmi_mac_addr *)ptr; 6584 num_mac_addr = rdy_parse->num_extra_mac_addr; 6585 6586 if (!(ab->num_radios > 1 && num_mac_addr >= ab->num_radios)) 6587 break; 6588 6589 for (i = 0; i < ab->num_radios; i++) { 6590 pdev = &ab->pdevs[i]; 6591 ether_addr_copy(pdev->mac_addr, addr_list[i].addr); 6592 } 6593 ab->pdevs_macaddr_valid = true; 6594 break; 6595 default: 6596 break; 6597 } 6598 6599 return 0; 6600 } 6601 6602 static int ath11k_ready_event(struct ath11k_base *ab, struct sk_buff *skb) 6603 { 6604 struct wmi_tlv_rdy_parse rdy_parse = { }; 6605 int ret; 6606 6607 ret = ath11k_wmi_tlv_iter(ab, skb->data, skb->len, 6608 ath11k_wmi_tlv_rdy_parse, &rdy_parse); 6609 if (ret) { 6610 ath11k_warn(ab, "failed to parse tlv %d\n", ret); 6611 return ret; 6612 } 6613 6614 complete(&ab->wmi_ab.unified_ready); 6615 return 0; 6616 } 6617 6618 static void ath11k_peer_delete_resp_event(struct ath11k_base *ab, struct sk_buff *skb) 6619 { 6620 struct wmi_peer_delete_resp_event peer_del_resp; 6621 struct ath11k *ar; 6622 6623 if (ath11k_pull_peer_del_resp_ev(ab, skb, &peer_del_resp) != 0) { 6624 ath11k_warn(ab, "failed to extract peer delete resp"); 6625 return; 6626 } 6627 6628 rcu_read_lock(); 6629 ar = ath11k_mac_get_ar_by_vdev_id(ab, peer_del_resp.vdev_id); 6630 if (!ar) { 6631 ath11k_warn(ab, "invalid vdev id in peer delete resp ev %d", 6632 peer_del_resp.vdev_id); 6633 rcu_read_unlock(); 6634 return; 6635 } 6636 6637 complete(&ar->peer_delete_done); 6638 rcu_read_unlock(); 6639 ath11k_dbg(ab, ATH11K_DBG_WMI, "peer delete resp for vdev id %d addr %pM\n", 6640 peer_del_resp.vdev_id, peer_del_resp.peer_macaddr.addr); 6641 } 6642 6643 static void ath11k_vdev_delete_resp_event(struct ath11k_base *ab, 6644 struct sk_buff *skb) 6645 { 6646 struct ath11k *ar; 6647 u32 vdev_id = 0; 6648 6649 if (ath11k_pull_vdev_del_resp_ev(ab, skb, &vdev_id) != 0) { 6650 ath11k_warn(ab, "failed to extract vdev delete resp"); 6651 return; 6652 } 6653 6654 rcu_read_lock(); 6655 ar = ath11k_mac_get_ar_by_vdev_id(ab, vdev_id); 6656 if (!ar) { 6657 ath11k_warn(ab, "invalid vdev id in vdev delete resp ev %d", 6658 vdev_id); 6659 rcu_read_unlock(); 6660 return; 6661 } 6662 6663 complete(&ar->vdev_delete_done); 6664 6665 rcu_read_unlock(); 6666 6667 ath11k_dbg(ab, ATH11K_DBG_WMI, "vdev delete resp for vdev id %d\n", 6668 vdev_id); 6669 } 6670 6671 static inline const char *ath11k_wmi_vdev_resp_print(u32 vdev_resp_status) 6672 { 6673 switch (vdev_resp_status) { 6674 case WMI_VDEV_START_RESPONSE_INVALID_VDEVID: 6675 return "invalid vdev id"; 6676 case WMI_VDEV_START_RESPONSE_NOT_SUPPORTED: 6677 return "not supported"; 6678 case WMI_VDEV_START_RESPONSE_DFS_VIOLATION: 6679 return "dfs violation"; 6680 case WMI_VDEV_START_RESPONSE_INVALID_REGDOMAIN: 6681 return "invalid regdomain"; 6682 default: 6683 return "unknown"; 6684 } 6685 } 6686 6687 static void ath11k_vdev_start_resp_event(struct ath11k_base *ab, struct sk_buff *skb) 6688 { 6689 struct wmi_vdev_start_resp_event vdev_start_resp; 6690 struct ath11k *ar; 6691 u32 status; 6692 6693 if (ath11k_pull_vdev_start_resp_tlv(ab, skb, &vdev_start_resp) != 0) { 6694 ath11k_warn(ab, "failed to extract vdev start resp"); 6695 return; 6696 } 6697 6698 rcu_read_lock(); 6699 ar = ath11k_mac_get_ar_by_vdev_id(ab, vdev_start_resp.vdev_id); 6700 if (!ar) { 6701 ath11k_warn(ab, "invalid vdev id in vdev start resp ev %d", 6702 vdev_start_resp.vdev_id); 6703 rcu_read_unlock(); 6704 return; 6705 } 6706 6707 ar->last_wmi_vdev_start_status = 0; 6708 6709 status = vdev_start_resp.status; 6710 6711 if (WARN_ON_ONCE(status)) { 6712 ath11k_warn(ab, "vdev start resp error status %d (%s)\n", 6713 status, ath11k_wmi_vdev_resp_print(status)); 6714 ar->last_wmi_vdev_start_status = status; 6715 } 6716 6717 complete(&ar->vdev_setup_done); 6718 6719 rcu_read_unlock(); 6720 6721 ath11k_dbg(ab, ATH11K_DBG_WMI, "vdev start resp for vdev id %d", 6722 vdev_start_resp.vdev_id); 6723 } 6724 6725 static void ath11k_bcn_tx_status_event(struct ath11k_base *ab, struct sk_buff *skb) 6726 { 6727 struct ath11k_vif *arvif; 6728 u32 vdev_id, tx_status; 6729 6730 if (ath11k_pull_bcn_tx_status_ev(ab, skb->data, skb->len, 6731 &vdev_id, &tx_status) != 0) { 6732 ath11k_warn(ab, "failed to extract bcn tx status"); 6733 return; 6734 } 6735 6736 rcu_read_lock(); 6737 arvif = ath11k_mac_get_arvif_by_vdev_id(ab, vdev_id); 6738 if (!arvif) { 6739 ath11k_warn(ab, "invalid vdev id %d in bcn_tx_status", 6740 vdev_id); 6741 rcu_read_unlock(); 6742 return; 6743 } 6744 ath11k_mac_bcn_tx_event(arvif); 6745 rcu_read_unlock(); 6746 } 6747 6748 static void ath11k_vdev_stopped_event(struct ath11k_base *ab, struct sk_buff *skb) 6749 { 6750 struct ath11k *ar; 6751 u32 vdev_id = 0; 6752 6753 if (ath11k_pull_vdev_stopped_param_tlv(ab, skb, &vdev_id) != 0) { 6754 ath11k_warn(ab, "failed to extract vdev stopped event"); 6755 return; 6756 } 6757 6758 rcu_read_lock(); 6759 ar = ath11k_mac_get_ar_by_vdev_id(ab, vdev_id); 6760 if (!ar) { 6761 ath11k_warn(ab, "invalid vdev id in vdev stopped ev %d", 6762 vdev_id); 6763 rcu_read_unlock(); 6764 return; 6765 } 6766 6767 complete(&ar->vdev_setup_done); 6768 6769 rcu_read_unlock(); 6770 6771 ath11k_dbg(ab, ATH11K_DBG_WMI, "vdev stopped for vdev id %d", vdev_id); 6772 } 6773 6774 static void ath11k_mgmt_rx_event(struct ath11k_base *ab, struct sk_buff *skb) 6775 { 6776 struct mgmt_rx_event_params rx_ev = {0}; 6777 struct ath11k *ar; 6778 struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); 6779 struct ieee80211_hdr *hdr; 6780 u16 fc; 6781 struct ieee80211_supported_band *sband; 6782 6783 if (ath11k_pull_mgmt_rx_params_tlv(ab, skb, &rx_ev) != 0) { 6784 ath11k_warn(ab, "failed to extract mgmt rx event"); 6785 dev_kfree_skb(skb); 6786 return; 6787 } 6788 6789 memset(status, 0, sizeof(*status)); 6790 6791 ath11k_dbg(ab, ATH11K_DBG_MGMT, "mgmt rx event status %08x\n", 6792 rx_ev.status); 6793 6794 rcu_read_lock(); 6795 ar = ath11k_mac_get_ar_by_pdev_id(ab, rx_ev.pdev_id); 6796 6797 if (!ar) { 6798 ath11k_warn(ab, "invalid pdev_id %d in mgmt_rx_event\n", 6799 rx_ev.pdev_id); 6800 dev_kfree_skb(skb); 6801 goto exit; 6802 } 6803 6804 if ((test_bit(ATH11K_CAC_RUNNING, &ar->dev_flags)) || 6805 (rx_ev.status & (WMI_RX_STATUS_ERR_DECRYPT | 6806 WMI_RX_STATUS_ERR_KEY_CACHE_MISS | WMI_RX_STATUS_ERR_CRC))) { 6807 dev_kfree_skb(skb); 6808 goto exit; 6809 } 6810 6811 if (rx_ev.status & WMI_RX_STATUS_ERR_MIC) 6812 status->flag |= RX_FLAG_MMIC_ERROR; 6813 6814 if (rx_ev.chan_freq >= ATH11K_MIN_6G_FREQ && 6815 rx_ev.chan_freq <= ATH11K_MAX_6G_FREQ) { 6816 status->band = NL80211_BAND_6GHZ; 6817 status->freq = rx_ev.chan_freq; 6818 } else if (rx_ev.channel >= 1 && rx_ev.channel <= 14) { 6819 status->band = NL80211_BAND_2GHZ; 6820 } else if (rx_ev.channel >= 36 && rx_ev.channel <= ATH11K_MAX_5G_CHAN) { 6821 status->band = NL80211_BAND_5GHZ; 6822 } else { 6823 /* Shouldn't happen unless list of advertised channels to 6824 * mac80211 has been changed. 6825 */ 6826 WARN_ON_ONCE(1); 6827 dev_kfree_skb(skb); 6828 goto exit; 6829 } 6830 6831 if (rx_ev.phy_mode == MODE_11B && 6832 (status->band == NL80211_BAND_5GHZ || status->band == NL80211_BAND_6GHZ)) 6833 ath11k_dbg(ab, ATH11K_DBG_WMI, 6834 "wmi mgmt rx 11b (CCK) on 5/6GHz, band = %d\n", status->band); 6835 6836 sband = &ar->mac.sbands[status->band]; 6837 6838 if (status->band != NL80211_BAND_6GHZ) 6839 status->freq = ieee80211_channel_to_frequency(rx_ev.channel, 6840 status->band); 6841 6842 status->signal = rx_ev.snr + ATH11K_DEFAULT_NOISE_FLOOR; 6843 status->rate_idx = ath11k_mac_bitrate_to_idx(sband, rx_ev.rate / 100); 6844 6845 hdr = (struct ieee80211_hdr *)skb->data; 6846 fc = le16_to_cpu(hdr->frame_control); 6847 6848 /* Firmware is guaranteed to report all essential management frames via 6849 * WMI while it can deliver some extra via HTT. Since there can be 6850 * duplicates split the reporting wrt monitor/sniffing. 6851 */ 6852 status->flag |= RX_FLAG_SKIP_MONITOR; 6853 6854 /* In case of PMF, FW delivers decrypted frames with Protected Bit set. 6855 * Don't clear that. Also, FW delivers broadcast management frames 6856 * (ex: group privacy action frames in mesh) as encrypted payload. 6857 */ 6858 if (ieee80211_has_protected(hdr->frame_control) && 6859 !is_multicast_ether_addr(ieee80211_get_DA(hdr))) { 6860 status->flag |= RX_FLAG_DECRYPTED; 6861 6862 if (!ieee80211_is_robust_mgmt_frame(skb)) { 6863 status->flag |= RX_FLAG_IV_STRIPPED | 6864 RX_FLAG_MMIC_STRIPPED; 6865 hdr->frame_control = __cpu_to_le16(fc & 6866 ~IEEE80211_FCTL_PROTECTED); 6867 } 6868 } 6869 6870 if (ieee80211_is_beacon(hdr->frame_control)) 6871 ath11k_mac_handle_beacon(ar, skb); 6872 6873 ath11k_dbg(ab, ATH11K_DBG_MGMT, 6874 "event mgmt rx skb %pK len %d ftype %02x stype %02x\n", 6875 skb, skb->len, 6876 fc & IEEE80211_FCTL_FTYPE, fc & IEEE80211_FCTL_STYPE); 6877 6878 ath11k_dbg(ab, ATH11K_DBG_MGMT, 6879 "event mgmt rx freq %d band %d snr %d, rate_idx %d\n", 6880 status->freq, status->band, status->signal, 6881 status->rate_idx); 6882 6883 ieee80211_rx_ni(ar->hw, skb); 6884 6885 exit: 6886 rcu_read_unlock(); 6887 } 6888 6889 static void ath11k_mgmt_tx_compl_event(struct ath11k_base *ab, struct sk_buff *skb) 6890 { 6891 struct wmi_mgmt_tx_compl_event tx_compl_param = {0}; 6892 struct ath11k *ar; 6893 6894 if (ath11k_pull_mgmt_tx_compl_param_tlv(ab, skb, &tx_compl_param) != 0) { 6895 ath11k_warn(ab, "failed to extract mgmt tx compl event"); 6896 return; 6897 } 6898 6899 rcu_read_lock(); 6900 ar = ath11k_mac_get_ar_by_pdev_id(ab, tx_compl_param.pdev_id); 6901 if (!ar) { 6902 ath11k_warn(ab, "invalid pdev id %d in mgmt_tx_compl_event\n", 6903 tx_compl_param.pdev_id); 6904 goto exit; 6905 } 6906 6907 wmi_process_mgmt_tx_comp(ar, tx_compl_param.desc_id, 6908 tx_compl_param.status); 6909 6910 ath11k_dbg(ab, ATH11K_DBG_MGMT, 6911 "mgmt tx compl ev pdev_id %d, desc_id %d, status %d", 6912 tx_compl_param.pdev_id, tx_compl_param.desc_id, 6913 tx_compl_param.status); 6914 6915 exit: 6916 rcu_read_unlock(); 6917 } 6918 6919 static struct ath11k *ath11k_get_ar_on_scan_state(struct ath11k_base *ab, 6920 u32 vdev_id, 6921 enum ath11k_scan_state state) 6922 { 6923 int i; 6924 struct ath11k_pdev *pdev; 6925 struct ath11k *ar; 6926 6927 for (i = 0; i < ab->num_radios; i++) { 6928 pdev = rcu_dereference(ab->pdevs_active[i]); 6929 if (pdev && pdev->ar) { 6930 ar = pdev->ar; 6931 6932 spin_lock_bh(&ar->data_lock); 6933 if (ar->scan.state == state && 6934 ar->scan.vdev_id == vdev_id) { 6935 spin_unlock_bh(&ar->data_lock); 6936 return ar; 6937 } 6938 spin_unlock_bh(&ar->data_lock); 6939 } 6940 } 6941 return NULL; 6942 } 6943 6944 static void ath11k_scan_event(struct ath11k_base *ab, struct sk_buff *skb) 6945 { 6946 struct ath11k *ar; 6947 struct wmi_scan_event scan_ev = {0}; 6948 6949 if (ath11k_pull_scan_ev(ab, skb, &scan_ev) != 0) { 6950 ath11k_warn(ab, "failed to extract scan event"); 6951 return; 6952 } 6953 6954 rcu_read_lock(); 6955 6956 /* In case the scan was cancelled, ex. during interface teardown, 6957 * the interface will not be found in active interfaces. 6958 * Rather, in such scenarios, iterate over the active pdev's to 6959 * search 'ar' if the corresponding 'ar' scan is ABORTING and the 6960 * aborting scan's vdev id matches this event info. 6961 */ 6962 if (scan_ev.event_type == WMI_SCAN_EVENT_COMPLETED && 6963 scan_ev.reason == WMI_SCAN_REASON_CANCELLED) { 6964 ar = ath11k_get_ar_on_scan_state(ab, scan_ev.vdev_id, 6965 ATH11K_SCAN_ABORTING); 6966 if (!ar) 6967 ar = ath11k_get_ar_on_scan_state(ab, scan_ev.vdev_id, 6968 ATH11K_SCAN_RUNNING); 6969 } else { 6970 ar = ath11k_mac_get_ar_by_vdev_id(ab, scan_ev.vdev_id); 6971 } 6972 6973 if (!ar) { 6974 ath11k_warn(ab, "Received scan event for unknown vdev"); 6975 rcu_read_unlock(); 6976 return; 6977 } 6978 6979 spin_lock_bh(&ar->data_lock); 6980 6981 ath11k_dbg(ab, ATH11K_DBG_WMI, 6982 "scan event %s type %d reason %d freq %d req_id %d scan_id %d vdev_id %d state %s (%d)\n", 6983 ath11k_wmi_event_scan_type_str(scan_ev.event_type, scan_ev.reason), 6984 scan_ev.event_type, scan_ev.reason, scan_ev.channel_freq, 6985 scan_ev.scan_req_id, scan_ev.scan_id, scan_ev.vdev_id, 6986 ath11k_scan_state_str(ar->scan.state), ar->scan.state); 6987 6988 switch (scan_ev.event_type) { 6989 case WMI_SCAN_EVENT_STARTED: 6990 ath11k_wmi_event_scan_started(ar); 6991 break; 6992 case WMI_SCAN_EVENT_COMPLETED: 6993 ath11k_wmi_event_scan_completed(ar); 6994 break; 6995 case WMI_SCAN_EVENT_BSS_CHANNEL: 6996 ath11k_wmi_event_scan_bss_chan(ar); 6997 break; 6998 case WMI_SCAN_EVENT_FOREIGN_CHAN: 6999 ath11k_wmi_event_scan_foreign_chan(ar, scan_ev.channel_freq); 7000 break; 7001 case WMI_SCAN_EVENT_START_FAILED: 7002 ath11k_warn(ab, "received scan start failure event\n"); 7003 ath11k_wmi_event_scan_start_failed(ar); 7004 break; 7005 case WMI_SCAN_EVENT_DEQUEUED: 7006 __ath11k_mac_scan_finish(ar); 7007 break; 7008 case WMI_SCAN_EVENT_PREEMPTED: 7009 case WMI_SCAN_EVENT_RESTARTED: 7010 case WMI_SCAN_EVENT_FOREIGN_CHAN_EXIT: 7011 default: 7012 break; 7013 } 7014 7015 spin_unlock_bh(&ar->data_lock); 7016 7017 rcu_read_unlock(); 7018 } 7019 7020 static void ath11k_peer_sta_kickout_event(struct ath11k_base *ab, struct sk_buff *skb) 7021 { 7022 struct wmi_peer_sta_kickout_arg arg = {}; 7023 struct ieee80211_sta *sta; 7024 struct ath11k_peer *peer; 7025 struct ath11k *ar; 7026 u32 vdev_id; 7027 7028 if (ath11k_pull_peer_sta_kickout_ev(ab, skb, &arg) != 0) { 7029 ath11k_warn(ab, "failed to extract peer sta kickout event"); 7030 return; 7031 } 7032 7033 rcu_read_lock(); 7034 7035 spin_lock_bh(&ab->base_lock); 7036 7037 peer = ath11k_peer_find_by_addr(ab, arg.mac_addr); 7038 7039 if (!peer) { 7040 ath11k_warn(ab, "peer not found %pM\n", 7041 arg.mac_addr); 7042 spin_unlock_bh(&ab->base_lock); 7043 goto exit; 7044 } 7045 7046 vdev_id = peer->vdev_id; 7047 7048 spin_unlock_bh(&ab->base_lock); 7049 7050 ar = ath11k_mac_get_ar_by_vdev_id(ab, vdev_id); 7051 if (!ar) { 7052 ath11k_warn(ab, "invalid vdev id in peer sta kickout ev %d", 7053 peer->vdev_id); 7054 goto exit; 7055 } 7056 7057 sta = ieee80211_find_sta_by_ifaddr(ar->hw, 7058 arg.mac_addr, NULL); 7059 if (!sta) { 7060 ath11k_warn(ab, "Spurious quick kickout for STA %pM\n", 7061 arg.mac_addr); 7062 goto exit; 7063 } 7064 7065 ath11k_dbg(ab, ATH11K_DBG_WMI, "peer sta kickout event %pM", 7066 arg.mac_addr); 7067 7068 ieee80211_report_low_ack(sta, 10); 7069 7070 exit: 7071 rcu_read_unlock(); 7072 } 7073 7074 static void ath11k_roam_event(struct ath11k_base *ab, struct sk_buff *skb) 7075 { 7076 struct wmi_roam_event roam_ev = {}; 7077 struct ath11k *ar; 7078 7079 if (ath11k_pull_roam_ev(ab, skb, &roam_ev) != 0) { 7080 ath11k_warn(ab, "failed to extract roam event"); 7081 return; 7082 } 7083 7084 ath11k_dbg(ab, ATH11K_DBG_WMI, 7085 "wmi roam event vdev %u reason 0x%08x rssi %d\n", 7086 roam_ev.vdev_id, roam_ev.reason, roam_ev.rssi); 7087 7088 rcu_read_lock(); 7089 ar = ath11k_mac_get_ar_by_vdev_id(ab, roam_ev.vdev_id); 7090 if (!ar) { 7091 ath11k_warn(ab, "invalid vdev id in roam ev %d", 7092 roam_ev.vdev_id); 7093 rcu_read_unlock(); 7094 return; 7095 } 7096 7097 if (roam_ev.reason >= WMI_ROAM_REASON_MAX) 7098 ath11k_warn(ab, "ignoring unknown roam event reason %d on vdev %i\n", 7099 roam_ev.reason, roam_ev.vdev_id); 7100 7101 switch (roam_ev.reason) { 7102 case WMI_ROAM_REASON_BEACON_MISS: 7103 ath11k_mac_handle_beacon_miss(ar, roam_ev.vdev_id); 7104 break; 7105 case WMI_ROAM_REASON_BETTER_AP: 7106 case WMI_ROAM_REASON_LOW_RSSI: 7107 case WMI_ROAM_REASON_SUITABLE_AP_FOUND: 7108 case WMI_ROAM_REASON_HO_FAILED: 7109 ath11k_warn(ab, "ignoring not implemented roam event reason %d on vdev %i\n", 7110 roam_ev.reason, roam_ev.vdev_id); 7111 break; 7112 } 7113 7114 rcu_read_unlock(); 7115 } 7116 7117 static void ath11k_chan_info_event(struct ath11k_base *ab, struct sk_buff *skb) 7118 { 7119 struct wmi_chan_info_event ch_info_ev = {0}; 7120 struct ath11k *ar; 7121 struct survey_info *survey; 7122 int idx; 7123 /* HW channel counters frequency value in hertz */ 7124 u32 cc_freq_hz = ab->cc_freq_hz; 7125 7126 if (ath11k_pull_chan_info_ev(ab, skb->data, skb->len, &ch_info_ev) != 0) { 7127 ath11k_warn(ab, "failed to extract chan info event"); 7128 return; 7129 } 7130 7131 ath11k_dbg(ab, ATH11K_DBG_WMI, 7132 "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", 7133 ch_info_ev.vdev_id, ch_info_ev.err_code, ch_info_ev.freq, 7134 ch_info_ev.cmd_flags, ch_info_ev.noise_floor, 7135 ch_info_ev.rx_clear_count, ch_info_ev.cycle_count, 7136 ch_info_ev.mac_clk_mhz); 7137 7138 if (ch_info_ev.cmd_flags == WMI_CHAN_INFO_END_RESP) { 7139 ath11k_dbg(ab, ATH11K_DBG_WMI, "chan info report completed\n"); 7140 return; 7141 } 7142 7143 rcu_read_lock(); 7144 ar = ath11k_mac_get_ar_by_vdev_id(ab, ch_info_ev.vdev_id); 7145 if (!ar) { 7146 ath11k_warn(ab, "invalid vdev id in chan info ev %d", 7147 ch_info_ev.vdev_id); 7148 rcu_read_unlock(); 7149 return; 7150 } 7151 spin_lock_bh(&ar->data_lock); 7152 7153 switch (ar->scan.state) { 7154 case ATH11K_SCAN_IDLE: 7155 case ATH11K_SCAN_STARTING: 7156 ath11k_warn(ab, "received chan info event without a scan request, ignoring\n"); 7157 goto exit; 7158 case ATH11K_SCAN_RUNNING: 7159 case ATH11K_SCAN_ABORTING: 7160 break; 7161 } 7162 7163 idx = freq_to_idx(ar, ch_info_ev.freq); 7164 if (idx >= ARRAY_SIZE(ar->survey)) { 7165 ath11k_warn(ab, "chan info: invalid frequency %d (idx %d out of bounds)\n", 7166 ch_info_ev.freq, idx); 7167 goto exit; 7168 } 7169 7170 /* If FW provides MAC clock frequency in Mhz, overriding the initialized 7171 * HW channel counters frequency value 7172 */ 7173 if (ch_info_ev.mac_clk_mhz) 7174 cc_freq_hz = (ch_info_ev.mac_clk_mhz * 1000); 7175 7176 if (ch_info_ev.cmd_flags == WMI_CHAN_INFO_START_RESP) { 7177 survey = &ar->survey[idx]; 7178 memset(survey, 0, sizeof(*survey)); 7179 survey->noise = ch_info_ev.noise_floor; 7180 survey->filled = SURVEY_INFO_NOISE_DBM | SURVEY_INFO_TIME | 7181 SURVEY_INFO_TIME_BUSY; 7182 survey->time = div_u64(ch_info_ev.cycle_count, cc_freq_hz); 7183 survey->time_busy = div_u64(ch_info_ev.rx_clear_count, cc_freq_hz); 7184 } 7185 exit: 7186 spin_unlock_bh(&ar->data_lock); 7187 rcu_read_unlock(); 7188 } 7189 7190 static void 7191 ath11k_pdev_bss_chan_info_event(struct ath11k_base *ab, struct sk_buff *skb) 7192 { 7193 struct wmi_pdev_bss_chan_info_event bss_ch_info_ev = {}; 7194 struct survey_info *survey; 7195 struct ath11k *ar; 7196 u32 cc_freq_hz = ab->cc_freq_hz; 7197 u64 busy, total, tx, rx, rx_bss; 7198 int idx; 7199 7200 if (ath11k_pull_pdev_bss_chan_info_ev(ab, skb, &bss_ch_info_ev) != 0) { 7201 ath11k_warn(ab, "failed to extract pdev bss chan info event"); 7202 return; 7203 } 7204 7205 busy = (u64)(bss_ch_info_ev.rx_clear_count_high) << 32 | 7206 bss_ch_info_ev.rx_clear_count_low; 7207 7208 total = (u64)(bss_ch_info_ev.cycle_count_high) << 32 | 7209 bss_ch_info_ev.cycle_count_low; 7210 7211 tx = (u64)(bss_ch_info_ev.tx_cycle_count_high) << 32 | 7212 bss_ch_info_ev.tx_cycle_count_low; 7213 7214 rx = (u64)(bss_ch_info_ev.rx_cycle_count_high) << 32 | 7215 bss_ch_info_ev.rx_cycle_count_low; 7216 7217 rx_bss = (u64)(bss_ch_info_ev.rx_bss_cycle_count_high) << 32 | 7218 bss_ch_info_ev.rx_bss_cycle_count_low; 7219 7220 ath11k_dbg(ab, ATH11K_DBG_WMI, 7221 "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", 7222 bss_ch_info_ev.pdev_id, bss_ch_info_ev.freq, 7223 bss_ch_info_ev.noise_floor, busy, total, 7224 tx, rx, rx_bss); 7225 7226 rcu_read_lock(); 7227 ar = ath11k_mac_get_ar_by_pdev_id(ab, bss_ch_info_ev.pdev_id); 7228 7229 if (!ar) { 7230 ath11k_warn(ab, "invalid pdev id %d in bss_chan_info event\n", 7231 bss_ch_info_ev.pdev_id); 7232 rcu_read_unlock(); 7233 return; 7234 } 7235 7236 spin_lock_bh(&ar->data_lock); 7237 idx = freq_to_idx(ar, bss_ch_info_ev.freq); 7238 if (idx >= ARRAY_SIZE(ar->survey)) { 7239 ath11k_warn(ab, "bss chan info: invalid frequency %d (idx %d out of bounds)\n", 7240 bss_ch_info_ev.freq, idx); 7241 goto exit; 7242 } 7243 7244 survey = &ar->survey[idx]; 7245 7246 survey->noise = bss_ch_info_ev.noise_floor; 7247 survey->time = div_u64(total, cc_freq_hz); 7248 survey->time_busy = div_u64(busy, cc_freq_hz); 7249 survey->time_rx = div_u64(rx_bss, cc_freq_hz); 7250 survey->time_tx = div_u64(tx, cc_freq_hz); 7251 survey->filled |= (SURVEY_INFO_NOISE_DBM | 7252 SURVEY_INFO_TIME | 7253 SURVEY_INFO_TIME_BUSY | 7254 SURVEY_INFO_TIME_RX | 7255 SURVEY_INFO_TIME_TX); 7256 exit: 7257 spin_unlock_bh(&ar->data_lock); 7258 complete(&ar->bss_survey_done); 7259 7260 rcu_read_unlock(); 7261 } 7262 7263 static void ath11k_vdev_install_key_compl_event(struct ath11k_base *ab, 7264 struct sk_buff *skb) 7265 { 7266 struct wmi_vdev_install_key_complete_arg install_key_compl = {0}; 7267 struct ath11k *ar; 7268 7269 if (ath11k_pull_vdev_install_key_compl_ev(ab, skb, &install_key_compl) != 0) { 7270 ath11k_warn(ab, "failed to extract install key compl event"); 7271 return; 7272 } 7273 7274 ath11k_dbg(ab, ATH11K_DBG_WMI, 7275 "vdev install key ev idx %d flags %08x macaddr %pM status %d\n", 7276 install_key_compl.key_idx, install_key_compl.key_flags, 7277 install_key_compl.macaddr, install_key_compl.status); 7278 7279 rcu_read_lock(); 7280 ar = ath11k_mac_get_ar_by_vdev_id(ab, install_key_compl.vdev_id); 7281 if (!ar) { 7282 ath11k_warn(ab, "invalid vdev id in install key compl ev %d", 7283 install_key_compl.vdev_id); 7284 rcu_read_unlock(); 7285 return; 7286 } 7287 7288 ar->install_key_status = 0; 7289 7290 if (install_key_compl.status != WMI_VDEV_INSTALL_KEY_COMPL_STATUS_SUCCESS) { 7291 ath11k_warn(ab, "install key failed for %pM status %d\n", 7292 install_key_compl.macaddr, install_key_compl.status); 7293 ar->install_key_status = install_key_compl.status; 7294 } 7295 7296 complete(&ar->install_key_done); 7297 rcu_read_unlock(); 7298 } 7299 7300 static void ath11k_service_available_event(struct ath11k_base *ab, struct sk_buff *skb) 7301 { 7302 const void **tb; 7303 const struct wmi_service_available_event *ev; 7304 int ret; 7305 int i, j; 7306 7307 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7308 if (IS_ERR(tb)) { 7309 ret = PTR_ERR(tb); 7310 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 7311 return; 7312 } 7313 7314 ev = tb[WMI_TAG_SERVICE_AVAILABLE_EVENT]; 7315 if (!ev) { 7316 ath11k_warn(ab, "failed to fetch svc available ev"); 7317 kfree(tb); 7318 return; 7319 } 7320 7321 /* TODO: Use wmi_service_segment_offset information to get the service 7322 * especially when more services are advertised in multiple sevice 7323 * available events. 7324 */ 7325 for (i = 0, j = WMI_MAX_SERVICE; 7326 i < WMI_SERVICE_SEGMENT_BM_SIZE32 && j < WMI_MAX_EXT_SERVICE; 7327 i++) { 7328 do { 7329 if (ev->wmi_service_segment_bitmap[i] & 7330 BIT(j % WMI_AVAIL_SERVICE_BITS_IN_SIZE32)) 7331 set_bit(j, ab->wmi_ab.svc_map); 7332 } while (++j % WMI_AVAIL_SERVICE_BITS_IN_SIZE32); 7333 } 7334 7335 ath11k_dbg(ab, ATH11K_DBG_WMI, 7336 "wmi_ext_service_bitmap 0:0x%x, 1:0x%x, 2:0x%x, 3:0x%x", 7337 ev->wmi_service_segment_bitmap[0], ev->wmi_service_segment_bitmap[1], 7338 ev->wmi_service_segment_bitmap[2], ev->wmi_service_segment_bitmap[3]); 7339 7340 kfree(tb); 7341 } 7342 7343 static void ath11k_peer_assoc_conf_event(struct ath11k_base *ab, struct sk_buff *skb) 7344 { 7345 struct wmi_peer_assoc_conf_arg peer_assoc_conf = {0}; 7346 struct ath11k *ar; 7347 7348 if (ath11k_pull_peer_assoc_conf_ev(ab, skb, &peer_assoc_conf) != 0) { 7349 ath11k_warn(ab, "failed to extract peer assoc conf event"); 7350 return; 7351 } 7352 7353 ath11k_dbg(ab, ATH11K_DBG_WMI, 7354 "peer assoc conf ev vdev id %d macaddr %pM\n", 7355 peer_assoc_conf.vdev_id, peer_assoc_conf.macaddr); 7356 7357 rcu_read_lock(); 7358 ar = ath11k_mac_get_ar_by_vdev_id(ab, peer_assoc_conf.vdev_id); 7359 7360 if (!ar) { 7361 ath11k_warn(ab, "invalid vdev id in peer assoc conf ev %d", 7362 peer_assoc_conf.vdev_id); 7363 rcu_read_unlock(); 7364 return; 7365 } 7366 7367 complete(&ar->peer_assoc_done); 7368 rcu_read_unlock(); 7369 } 7370 7371 static void ath11k_update_stats_event(struct ath11k_base *ab, struct sk_buff *skb) 7372 { 7373 ath11k_debugfs_fw_stats_process(ab, skb); 7374 } 7375 7376 /* PDEV_CTL_FAILSAFE_CHECK_EVENT is received from FW when the frequency scanned 7377 * is not part of BDF CTL(Conformance test limits) table entries. 7378 */ 7379 static void ath11k_pdev_ctl_failsafe_check_event(struct ath11k_base *ab, 7380 struct sk_buff *skb) 7381 { 7382 const void **tb; 7383 const struct wmi_pdev_ctl_failsafe_chk_event *ev; 7384 int ret; 7385 7386 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7387 if (IS_ERR(tb)) { 7388 ret = PTR_ERR(tb); 7389 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 7390 return; 7391 } 7392 7393 ev = tb[WMI_TAG_PDEV_CTL_FAILSAFE_CHECK_EVENT]; 7394 if (!ev) { 7395 ath11k_warn(ab, "failed to fetch pdev ctl failsafe check ev"); 7396 kfree(tb); 7397 return; 7398 } 7399 7400 ath11k_dbg(ab, ATH11K_DBG_WMI, 7401 "pdev ctl failsafe check ev status %d\n", 7402 ev->ctl_failsafe_status); 7403 7404 /* If ctl_failsafe_status is set to 1 FW will max out the Transmit power 7405 * to 10 dBm else the CTL power entry in the BDF would be picked up. 7406 */ 7407 if (ev->ctl_failsafe_status != 0) 7408 ath11k_warn(ab, "pdev ctl failsafe failure status %d", 7409 ev->ctl_failsafe_status); 7410 7411 kfree(tb); 7412 } 7413 7414 static void 7415 ath11k_wmi_process_csa_switch_count_event(struct ath11k_base *ab, 7416 const struct wmi_pdev_csa_switch_ev *ev, 7417 const u32 *vdev_ids) 7418 { 7419 int i; 7420 struct ath11k_vif *arvif; 7421 7422 /* Finish CSA once the switch count becomes NULL */ 7423 if (ev->current_switch_count) 7424 return; 7425 7426 rcu_read_lock(); 7427 for (i = 0; i < ev->num_vdevs; i++) { 7428 arvif = ath11k_mac_get_arvif_by_vdev_id(ab, vdev_ids[i]); 7429 7430 if (!arvif) { 7431 ath11k_warn(ab, "Recvd csa status for unknown vdev %d", 7432 vdev_ids[i]); 7433 continue; 7434 } 7435 7436 if (arvif->is_up && arvif->vif->csa_active) 7437 ieee80211_csa_finish(arvif->vif); 7438 } 7439 rcu_read_unlock(); 7440 } 7441 7442 static void 7443 ath11k_wmi_pdev_csa_switch_count_status_event(struct ath11k_base *ab, 7444 struct sk_buff *skb) 7445 { 7446 const void **tb; 7447 const struct wmi_pdev_csa_switch_ev *ev; 7448 const u32 *vdev_ids; 7449 int ret; 7450 7451 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7452 if (IS_ERR(tb)) { 7453 ret = PTR_ERR(tb); 7454 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 7455 return; 7456 } 7457 7458 ev = tb[WMI_TAG_PDEV_CSA_SWITCH_COUNT_STATUS_EVENT]; 7459 vdev_ids = tb[WMI_TAG_ARRAY_UINT32]; 7460 7461 if (!ev || !vdev_ids) { 7462 ath11k_warn(ab, "failed to fetch pdev csa switch count ev"); 7463 kfree(tb); 7464 return; 7465 } 7466 7467 ath11k_dbg(ab, ATH11K_DBG_WMI, 7468 "pdev csa switch count %d for pdev %d, num_vdevs %d", 7469 ev->current_switch_count, ev->pdev_id, 7470 ev->num_vdevs); 7471 7472 ath11k_wmi_process_csa_switch_count_event(ab, ev, vdev_ids); 7473 7474 kfree(tb); 7475 } 7476 7477 static void 7478 ath11k_wmi_pdev_dfs_radar_detected_event(struct ath11k_base *ab, struct sk_buff *skb) 7479 { 7480 const void **tb; 7481 const struct wmi_pdev_radar_ev *ev; 7482 struct ath11k *ar; 7483 int ret; 7484 7485 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7486 if (IS_ERR(tb)) { 7487 ret = PTR_ERR(tb); 7488 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 7489 return; 7490 } 7491 7492 ev = tb[WMI_TAG_PDEV_DFS_RADAR_DETECTION_EVENT]; 7493 7494 if (!ev) { 7495 ath11k_warn(ab, "failed to fetch pdev dfs radar detected ev"); 7496 kfree(tb); 7497 return; 7498 } 7499 7500 ath11k_dbg(ab, ATH11K_DBG_WMI, 7501 "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", 7502 ev->pdev_id, ev->detection_mode, ev->chan_freq, ev->chan_width, 7503 ev->detector_id, ev->segment_id, ev->timestamp, ev->is_chirp, 7504 ev->freq_offset, ev->sidx); 7505 7506 ar = ath11k_mac_get_ar_by_pdev_id(ab, ev->pdev_id); 7507 7508 if (!ar) { 7509 ath11k_warn(ab, "radar detected in invalid pdev %d\n", 7510 ev->pdev_id); 7511 goto exit; 7512 } 7513 7514 ath11k_dbg(ar->ab, ATH11K_DBG_REG, "DFS Radar Detected in pdev %d\n", 7515 ev->pdev_id); 7516 7517 if (ar->dfs_block_radar_events) 7518 ath11k_info(ab, "DFS Radar detected, but ignored as requested\n"); 7519 else 7520 ieee80211_radar_detected(ar->hw); 7521 7522 exit: 7523 kfree(tb); 7524 } 7525 7526 static void ath11k_rfkill_state_change_event(struct ath11k_base *ab, 7527 struct sk_buff *skb) 7528 { 7529 const struct wmi_rfkill_state_change_ev *ev; 7530 const void **tb; 7531 int ret; 7532 7533 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7534 if (IS_ERR(tb)) { 7535 ret = PTR_ERR(tb); 7536 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 7537 return; 7538 } 7539 7540 ev = tb[WMI_TAG_RFKILL_EVENT]; 7541 if (!ev) { 7542 kfree(tb); 7543 return; 7544 } 7545 7546 ath11k_dbg(ab, ATH11K_DBG_MAC, 7547 "wmi tlv rfkill state change gpio %d type %d radio_state %d\n", 7548 ev->gpio_pin_num, 7549 ev->int_type, 7550 ev->radio_state); 7551 7552 spin_lock_bh(&ab->base_lock); 7553 ab->rfkill_radio_on = (ev->radio_state == WMI_RFKILL_RADIO_STATE_ON); 7554 spin_unlock_bh(&ab->base_lock); 7555 7556 queue_work(ab->workqueue, &ab->rfkill_work); 7557 kfree(tb); 7558 } 7559 7560 static void 7561 ath11k_wmi_pdev_temperature_event(struct ath11k_base *ab, 7562 struct sk_buff *skb) 7563 { 7564 struct ath11k *ar; 7565 const void **tb; 7566 const struct wmi_pdev_temperature_event *ev; 7567 int ret; 7568 7569 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7570 if (IS_ERR(tb)) { 7571 ret = PTR_ERR(tb); 7572 ath11k_warn(ab, "failed to parse tlv: %d\n", ret); 7573 return; 7574 } 7575 7576 ev = tb[WMI_TAG_PDEV_TEMPERATURE_EVENT]; 7577 if (!ev) { 7578 ath11k_warn(ab, "failed to fetch pdev temp ev"); 7579 kfree(tb); 7580 return; 7581 } 7582 7583 ath11k_dbg(ab, ATH11K_DBG_WMI, 7584 "pdev temperature ev temp %d pdev_id %d\n", ev->temp, ev->pdev_id); 7585 7586 ar = ath11k_mac_get_ar_by_pdev_id(ab, ev->pdev_id); 7587 if (!ar) { 7588 ath11k_warn(ab, "invalid pdev id in pdev temperature ev %d", ev->pdev_id); 7589 kfree(tb); 7590 return; 7591 } 7592 7593 ath11k_thermal_event_temperature(ar, ev->temp); 7594 7595 kfree(tb); 7596 } 7597 7598 static void ath11k_fils_discovery_event(struct ath11k_base *ab, 7599 struct sk_buff *skb) 7600 { 7601 const void **tb; 7602 const struct wmi_fils_discovery_event *ev; 7603 int ret; 7604 7605 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7606 if (IS_ERR(tb)) { 7607 ret = PTR_ERR(tb); 7608 ath11k_warn(ab, 7609 "failed to parse FILS discovery event tlv %d\n", 7610 ret); 7611 return; 7612 } 7613 7614 ev = tb[WMI_TAG_HOST_SWFDA_EVENT]; 7615 if (!ev) { 7616 ath11k_warn(ab, "failed to fetch FILS discovery event\n"); 7617 kfree(tb); 7618 return; 7619 } 7620 7621 ath11k_warn(ab, 7622 "FILS discovery frame expected from host for vdev_id: %u, transmission scheduled at %u, next TBTT: %u\n", 7623 ev->vdev_id, ev->fils_tt, ev->tbtt); 7624 7625 kfree(tb); 7626 } 7627 7628 static void ath11k_probe_resp_tx_status_event(struct ath11k_base *ab, 7629 struct sk_buff *skb) 7630 { 7631 const void **tb; 7632 const struct wmi_probe_resp_tx_status_event *ev; 7633 int ret; 7634 7635 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7636 if (IS_ERR(tb)) { 7637 ret = PTR_ERR(tb); 7638 ath11k_warn(ab, 7639 "failed to parse probe response transmission status event tlv: %d\n", 7640 ret); 7641 return; 7642 } 7643 7644 ev = tb[WMI_TAG_OFFLOAD_PRB_RSP_TX_STATUS_EVENT]; 7645 if (!ev) { 7646 ath11k_warn(ab, 7647 "failed to fetch probe response transmission status event"); 7648 kfree(tb); 7649 return; 7650 } 7651 7652 if (ev->tx_status) 7653 ath11k_warn(ab, 7654 "Probe response transmission failed for vdev_id %u, status %u\n", 7655 ev->vdev_id, ev->tx_status); 7656 7657 kfree(tb); 7658 } 7659 7660 static int ath11k_wmi_tlv_wow_wakeup_host_parse(struct ath11k_base *ab, 7661 u16 tag, u16 len, 7662 const void *ptr, void *data) 7663 { 7664 struct wmi_wow_ev_arg *ev = data; 7665 const char *wow_pg_fault; 7666 int wow_pg_len; 7667 7668 switch (tag) { 7669 case WMI_TAG_WOW_EVENT_INFO: 7670 memcpy(ev, ptr, sizeof(*ev)); 7671 ath11k_dbg(ab, ATH11K_DBG_WMI, "wow wakeup host reason %d %s\n", 7672 ev->wake_reason, wow_reason(ev->wake_reason)); 7673 break; 7674 7675 case WMI_TAG_ARRAY_BYTE: 7676 if (ev && ev->wake_reason == WOW_REASON_PAGE_FAULT) { 7677 wow_pg_fault = ptr; 7678 /* the first 4 bytes are length */ 7679 wow_pg_len = *(int *)wow_pg_fault; 7680 wow_pg_fault += sizeof(int); 7681 ath11k_dbg(ab, ATH11K_DBG_WMI, "wow data_len = %d\n", 7682 wow_pg_len); 7683 ath11k_dbg_dump(ab, ATH11K_DBG_WMI, 7684 "wow_event_info_type packet present", 7685 "wow_pg_fault ", 7686 wow_pg_fault, 7687 wow_pg_len); 7688 } 7689 break; 7690 default: 7691 break; 7692 } 7693 7694 return 0; 7695 } 7696 7697 static void ath11k_wmi_event_wow_wakeup_host(struct ath11k_base *ab, struct sk_buff *skb) 7698 { 7699 struct wmi_wow_ev_arg ev = { }; 7700 int ret; 7701 7702 ret = ath11k_wmi_tlv_iter(ab, skb->data, skb->len, 7703 ath11k_wmi_tlv_wow_wakeup_host_parse, 7704 &ev); 7705 if (ret) { 7706 ath11k_warn(ab, "failed to parse wmi wow tlv: %d\n", ret); 7707 return; 7708 } 7709 7710 complete(&ab->wow.wakeup_completed); 7711 } 7712 7713 static void 7714 ath11k_wmi_diag_event(struct ath11k_base *ab, 7715 struct sk_buff *skb) 7716 { 7717 trace_ath11k_wmi_diag(ab, skb->data, skb->len); 7718 } 7719 7720 static const char *ath11k_wmi_twt_add_dialog_event_status(u32 status) 7721 { 7722 switch (status) { 7723 case WMI_ADD_TWT_STATUS_OK: 7724 return "ok"; 7725 case WMI_ADD_TWT_STATUS_TWT_NOT_ENABLED: 7726 return "twt disabled"; 7727 case WMI_ADD_TWT_STATUS_USED_DIALOG_ID: 7728 return "dialog id in use"; 7729 case WMI_ADD_TWT_STATUS_INVALID_PARAM: 7730 return "invalid parameters"; 7731 case WMI_ADD_TWT_STATUS_NOT_READY: 7732 return "not ready"; 7733 case WMI_ADD_TWT_STATUS_NO_RESOURCE: 7734 return "resource unavailable"; 7735 case WMI_ADD_TWT_STATUS_NO_ACK: 7736 return "no ack"; 7737 case WMI_ADD_TWT_STATUS_NO_RESPONSE: 7738 return "no response"; 7739 case WMI_ADD_TWT_STATUS_DENIED: 7740 return "denied"; 7741 case WMI_ADD_TWT_STATUS_UNKNOWN_ERROR: 7742 fallthrough; 7743 default: 7744 return "unknown error"; 7745 } 7746 } 7747 7748 static void ath11k_wmi_twt_add_dialog_event(struct ath11k_base *ab, 7749 struct sk_buff *skb) 7750 { 7751 const void **tb; 7752 const struct wmi_twt_add_dialog_event *ev; 7753 int ret; 7754 7755 tb = ath11k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC); 7756 if (IS_ERR(tb)) { 7757 ret = PTR_ERR(tb); 7758 ath11k_warn(ab, 7759 "failed to parse wmi twt add dialog status event tlv: %d\n", 7760 ret); 7761 return; 7762 } 7763 7764 ev = tb[WMI_TAG_TWT_ADD_DIALOG_COMPLETE_EVENT]; 7765 if (!ev) { 7766 ath11k_warn(ab, "failed to fetch twt add dialog wmi event\n"); 7767 goto exit; 7768 } 7769 7770 if (ev->status) 7771 ath11k_warn(ab, 7772 "wmi add twt dialog event vdev %d dialog id %d status %s\n", 7773 ev->vdev_id, ev->dialog_id, 7774 ath11k_wmi_twt_add_dialog_event_status(ev->status)); 7775 7776 exit: 7777 kfree(tb); 7778 } 7779 7780 static void ath11k_wmi_tlv_op_rx(struct ath11k_base *ab, struct sk_buff *skb) 7781 { 7782 struct wmi_cmd_hdr *cmd_hdr; 7783 enum wmi_tlv_event_id id; 7784 7785 cmd_hdr = (struct wmi_cmd_hdr *)skb->data; 7786 id = FIELD_GET(WMI_CMD_HDR_CMD_ID, (cmd_hdr->cmd_id)); 7787 7788 trace_ath11k_wmi_event(ab, id, skb->data, skb->len); 7789 7790 if (skb_pull(skb, sizeof(struct wmi_cmd_hdr)) == NULL) 7791 goto out; 7792 7793 switch (id) { 7794 /* Process all the WMI events here */ 7795 case WMI_SERVICE_READY_EVENTID: 7796 ath11k_service_ready_event(ab, skb); 7797 break; 7798 case WMI_SERVICE_READY_EXT_EVENTID: 7799 ath11k_service_ready_ext_event(ab, skb); 7800 break; 7801 case WMI_SERVICE_READY_EXT2_EVENTID: 7802 ath11k_service_ready_ext2_event(ab, skb); 7803 break; 7804 case WMI_REG_CHAN_LIST_CC_EVENTID: 7805 ath11k_reg_chan_list_event(ab, skb); 7806 break; 7807 case WMI_READY_EVENTID: 7808 ath11k_ready_event(ab, skb); 7809 break; 7810 case WMI_PEER_DELETE_RESP_EVENTID: 7811 ath11k_peer_delete_resp_event(ab, skb); 7812 break; 7813 case WMI_VDEV_START_RESP_EVENTID: 7814 ath11k_vdev_start_resp_event(ab, skb); 7815 break; 7816 case WMI_OFFLOAD_BCN_TX_STATUS_EVENTID: 7817 ath11k_bcn_tx_status_event(ab, skb); 7818 break; 7819 case WMI_VDEV_STOPPED_EVENTID: 7820 ath11k_vdev_stopped_event(ab, skb); 7821 break; 7822 case WMI_MGMT_RX_EVENTID: 7823 ath11k_mgmt_rx_event(ab, skb); 7824 /* mgmt_rx_event() owns the skb now! */ 7825 return; 7826 case WMI_MGMT_TX_COMPLETION_EVENTID: 7827 ath11k_mgmt_tx_compl_event(ab, skb); 7828 break; 7829 case WMI_SCAN_EVENTID: 7830 ath11k_scan_event(ab, skb); 7831 break; 7832 case WMI_PEER_STA_KICKOUT_EVENTID: 7833 ath11k_peer_sta_kickout_event(ab, skb); 7834 break; 7835 case WMI_ROAM_EVENTID: 7836 ath11k_roam_event(ab, skb); 7837 break; 7838 case WMI_CHAN_INFO_EVENTID: 7839 ath11k_chan_info_event(ab, skb); 7840 break; 7841 case WMI_PDEV_BSS_CHAN_INFO_EVENTID: 7842 ath11k_pdev_bss_chan_info_event(ab, skb); 7843 break; 7844 case WMI_VDEV_INSTALL_KEY_COMPLETE_EVENTID: 7845 ath11k_vdev_install_key_compl_event(ab, skb); 7846 break; 7847 case WMI_SERVICE_AVAILABLE_EVENTID: 7848 ath11k_service_available_event(ab, skb); 7849 break; 7850 case WMI_PEER_ASSOC_CONF_EVENTID: 7851 ath11k_peer_assoc_conf_event(ab, skb); 7852 break; 7853 case WMI_UPDATE_STATS_EVENTID: 7854 ath11k_update_stats_event(ab, skb); 7855 break; 7856 case WMI_PDEV_CTL_FAILSAFE_CHECK_EVENTID: 7857 ath11k_pdev_ctl_failsafe_check_event(ab, skb); 7858 break; 7859 case WMI_PDEV_CSA_SWITCH_COUNT_STATUS_EVENTID: 7860 ath11k_wmi_pdev_csa_switch_count_status_event(ab, skb); 7861 break; 7862 case WMI_PDEV_TEMPERATURE_EVENTID: 7863 ath11k_wmi_pdev_temperature_event(ab, skb); 7864 break; 7865 case WMI_PDEV_DMA_RING_BUF_RELEASE_EVENTID: 7866 ath11k_wmi_pdev_dma_ring_buf_release_event(ab, skb); 7867 break; 7868 case WMI_HOST_FILS_DISCOVERY_EVENTID: 7869 ath11k_fils_discovery_event(ab, skb); 7870 break; 7871 case WMI_OFFLOAD_PROB_RESP_TX_STATUS_EVENTID: 7872 ath11k_probe_resp_tx_status_event(ab, skb); 7873 break; 7874 case WMI_OBSS_COLOR_COLLISION_DETECTION_EVENTID: 7875 ath11k_wmi_obss_color_collision_event(ab, skb); 7876 break; 7877 case WMI_TWT_ADD_DIALOG_EVENTID: 7878 ath11k_wmi_twt_add_dialog_event(ab, skb); 7879 break; 7880 /* add Unsupported events here */ 7881 case WMI_TBTTOFFSET_EXT_UPDATE_EVENTID: 7882 case WMI_PEER_OPER_MODE_CHANGE_EVENTID: 7883 case WMI_TWT_ENABLE_EVENTID: 7884 case WMI_TWT_DISABLE_EVENTID: 7885 case WMI_TWT_DEL_DIALOG_EVENTID: 7886 case WMI_TWT_PAUSE_DIALOG_EVENTID: 7887 case WMI_TWT_RESUME_DIALOG_EVENTID: 7888 case WMI_PDEV_DMA_RING_CFG_RSP_EVENTID: 7889 case WMI_PEER_CREATE_CONF_EVENTID: 7890 ath11k_dbg(ab, ATH11K_DBG_WMI, 7891 "ignoring unsupported event 0x%x\n", id); 7892 break; 7893 case WMI_PDEV_DFS_RADAR_DETECTION_EVENTID: 7894 ath11k_wmi_pdev_dfs_radar_detected_event(ab, skb); 7895 break; 7896 case WMI_VDEV_DELETE_RESP_EVENTID: 7897 ath11k_vdev_delete_resp_event(ab, skb); 7898 break; 7899 case WMI_WOW_WAKEUP_HOST_EVENTID: 7900 ath11k_wmi_event_wow_wakeup_host(ab, skb); 7901 break; 7902 case WMI_11D_NEW_COUNTRY_EVENTID: 7903 ath11k_reg_11d_new_cc_event(ab, skb); 7904 break; 7905 case WMI_RFKILL_STATE_CHANGE_EVENTID: 7906 ath11k_rfkill_state_change_event(ab, skb); 7907 break; 7908 case WMI_DIAG_EVENTID: 7909 ath11k_wmi_diag_event(ab, skb); 7910 break; 7911 /* TODO: Add remaining events */ 7912 default: 7913 ath11k_dbg(ab, ATH11K_DBG_WMI, "Unknown eventid: 0x%x\n", id); 7914 break; 7915 } 7916 7917 out: 7918 dev_kfree_skb(skb); 7919 } 7920 7921 static int ath11k_connect_pdev_htc_service(struct ath11k_base *ab, 7922 u32 pdev_idx) 7923 { 7924 int status; 7925 u32 svc_id[] = { ATH11K_HTC_SVC_ID_WMI_CONTROL, 7926 ATH11K_HTC_SVC_ID_WMI_CONTROL_MAC1, 7927 ATH11K_HTC_SVC_ID_WMI_CONTROL_MAC2 }; 7928 7929 struct ath11k_htc_svc_conn_req conn_req; 7930 struct ath11k_htc_svc_conn_resp conn_resp; 7931 7932 memset(&conn_req, 0, sizeof(conn_req)); 7933 memset(&conn_resp, 0, sizeof(conn_resp)); 7934 7935 /* these fields are the same for all service endpoints */ 7936 conn_req.ep_ops.ep_tx_complete = ath11k_wmi_htc_tx_complete; 7937 conn_req.ep_ops.ep_rx_complete = ath11k_wmi_tlv_op_rx; 7938 conn_req.ep_ops.ep_tx_credits = ath11k_wmi_op_ep_tx_credits; 7939 7940 /* connect to control service */ 7941 conn_req.service_id = svc_id[pdev_idx]; 7942 7943 status = ath11k_htc_connect_service(&ab->htc, &conn_req, &conn_resp); 7944 if (status) { 7945 ath11k_warn(ab, "failed to connect to WMI CONTROL service status: %d\n", 7946 status); 7947 return status; 7948 } 7949 7950 ab->wmi_ab.wmi_endpoint_id[pdev_idx] = conn_resp.eid; 7951 ab->wmi_ab.wmi[pdev_idx].eid = conn_resp.eid; 7952 ab->wmi_ab.max_msg_len[pdev_idx] = conn_resp.max_msg_len; 7953 init_waitqueue_head(&ab->wmi_ab.wmi[pdev_idx].tx_ce_desc_wq); 7954 7955 return 0; 7956 } 7957 7958 static int 7959 ath11k_wmi_send_unit_test_cmd(struct ath11k *ar, 7960 struct wmi_unit_test_cmd ut_cmd, 7961 u32 *test_args) 7962 { 7963 struct ath11k_pdev_wmi *wmi = ar->wmi; 7964 struct wmi_unit_test_cmd *cmd; 7965 struct sk_buff *skb; 7966 struct wmi_tlv *tlv; 7967 void *ptr; 7968 u32 *ut_cmd_args; 7969 int buf_len, arg_len; 7970 int ret; 7971 int i; 7972 7973 arg_len = sizeof(u32) * ut_cmd.num_args; 7974 buf_len = sizeof(ut_cmd) + arg_len + TLV_HDR_SIZE; 7975 7976 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, buf_len); 7977 if (!skb) 7978 return -ENOMEM; 7979 7980 cmd = (struct wmi_unit_test_cmd *)skb->data; 7981 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_UNIT_TEST_CMD) | 7982 FIELD_PREP(WMI_TLV_LEN, sizeof(ut_cmd) - TLV_HDR_SIZE); 7983 7984 cmd->vdev_id = ut_cmd.vdev_id; 7985 cmd->module_id = ut_cmd.module_id; 7986 cmd->num_args = ut_cmd.num_args; 7987 cmd->diag_token = ut_cmd.diag_token; 7988 7989 ptr = skb->data + sizeof(ut_cmd); 7990 7991 tlv = ptr; 7992 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_UINT32) | 7993 FIELD_PREP(WMI_TLV_LEN, arg_len); 7994 7995 ptr += TLV_HDR_SIZE; 7996 7997 ut_cmd_args = ptr; 7998 for (i = 0; i < ut_cmd.num_args; i++) 7999 ut_cmd_args[i] = test_args[i]; 8000 8001 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_UNIT_TEST_CMDID); 8002 8003 if (ret) { 8004 ath11k_warn(ar->ab, "failed to send WMI_UNIT_TEST CMD :%d\n", 8005 ret); 8006 dev_kfree_skb(skb); 8007 } 8008 8009 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, 8010 "WMI unit test : module %d vdev %d n_args %d token %d\n", 8011 cmd->module_id, cmd->vdev_id, cmd->num_args, 8012 cmd->diag_token); 8013 8014 return ret; 8015 } 8016 8017 int ath11k_wmi_simulate_radar(struct ath11k *ar) 8018 { 8019 struct ath11k_vif *arvif; 8020 u32 dfs_args[DFS_MAX_TEST_ARGS]; 8021 struct wmi_unit_test_cmd wmi_ut; 8022 bool arvif_found = false; 8023 8024 list_for_each_entry(arvif, &ar->arvifs, list) { 8025 if (arvif->is_started && arvif->vdev_type == WMI_VDEV_TYPE_AP) { 8026 arvif_found = true; 8027 break; 8028 } 8029 } 8030 8031 if (!arvif_found) 8032 return -EINVAL; 8033 8034 dfs_args[DFS_TEST_CMDID] = 0; 8035 dfs_args[DFS_TEST_PDEV_ID] = ar->pdev->pdev_id; 8036 /* Currently we could pass segment_id(b0 - b1), chirp(b2) 8037 * freq offset (b3 - b10) to unit test. For simulation 8038 * purpose this can be set to 0 which is valid. 8039 */ 8040 dfs_args[DFS_TEST_RADAR_PARAM] = 0; 8041 8042 wmi_ut.vdev_id = arvif->vdev_id; 8043 wmi_ut.module_id = DFS_UNIT_TEST_MODULE; 8044 wmi_ut.num_args = DFS_MAX_TEST_ARGS; 8045 wmi_ut.diag_token = DFS_UNIT_TEST_TOKEN; 8046 8047 ath11k_dbg(ar->ab, ATH11K_DBG_REG, "Triggering Radar Simulation\n"); 8048 8049 return ath11k_wmi_send_unit_test_cmd(ar, wmi_ut, dfs_args); 8050 } 8051 8052 int ath11k_wmi_fw_dbglog_cfg(struct ath11k *ar, u32 *module_id_bitmap, 8053 struct ath11k_fw_dbglog *dbglog) 8054 { 8055 struct ath11k_pdev_wmi *wmi = ar->wmi; 8056 struct wmi_debug_log_config_cmd_fixed_param *cmd; 8057 struct sk_buff *skb; 8058 struct wmi_tlv *tlv; 8059 int ret, len; 8060 8061 len = sizeof(*cmd) + TLV_HDR_SIZE + (MAX_MODULE_ID_BITMAP_WORDS * sizeof(u32)); 8062 skb = ath11k_wmi_alloc_skb(wmi->wmi_ab, len); 8063 if (!skb) 8064 return -ENOMEM; 8065 8066 cmd = (struct wmi_debug_log_config_cmd_fixed_param *)skb->data; 8067 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_DEBUG_LOG_CONFIG_CMD) | 8068 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 8069 cmd->dbg_log_param = dbglog->param; 8070 8071 tlv = (struct wmi_tlv *)((u8 *)cmd + sizeof(*cmd)); 8072 tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_UINT32) | 8073 FIELD_PREP(WMI_TLV_LEN, MAX_MODULE_ID_BITMAP_WORDS * sizeof(u32)); 8074 8075 switch (dbglog->param) { 8076 case WMI_DEBUG_LOG_PARAM_LOG_LEVEL: 8077 case WMI_DEBUG_LOG_PARAM_VDEV_ENABLE: 8078 case WMI_DEBUG_LOG_PARAM_VDEV_DISABLE: 8079 case WMI_DEBUG_LOG_PARAM_VDEV_ENABLE_BITMAP: 8080 cmd->value = dbglog->value; 8081 break; 8082 case WMI_DEBUG_LOG_PARAM_MOD_ENABLE_BITMAP: 8083 case WMI_DEBUG_LOG_PARAM_WOW_MOD_ENABLE_BITMAP: 8084 cmd->value = dbglog->value; 8085 memcpy(tlv->value, module_id_bitmap, 8086 MAX_MODULE_ID_BITMAP_WORDS * sizeof(u32)); 8087 /* clear current config to be used for next user config */ 8088 memset(module_id_bitmap, 0, 8089 MAX_MODULE_ID_BITMAP_WORDS * sizeof(u32)); 8090 break; 8091 default: 8092 dev_kfree_skb(skb); 8093 return -EINVAL; 8094 } 8095 8096 ret = ath11k_wmi_cmd_send(wmi, skb, WMI_DBGLOG_CFG_CMDID); 8097 if (ret) { 8098 ath11k_warn(ar->ab, 8099 "failed to send WMI_DBGLOG_CFG_CMDID\n"); 8100 dev_kfree_skb(skb); 8101 } 8102 return ret; 8103 } 8104 8105 int ath11k_wmi_connect(struct ath11k_base *ab) 8106 { 8107 u32 i; 8108 u8 wmi_ep_count; 8109 8110 wmi_ep_count = ab->htc.wmi_ep_count; 8111 if (wmi_ep_count > ab->hw_params.max_radios) 8112 return -1; 8113 8114 for (i = 0; i < wmi_ep_count; i++) 8115 ath11k_connect_pdev_htc_service(ab, i); 8116 8117 return 0; 8118 } 8119 8120 static void ath11k_wmi_pdev_detach(struct ath11k_base *ab, u8 pdev_id) 8121 { 8122 if (WARN_ON(pdev_id >= MAX_RADIOS)) 8123 return; 8124 8125 /* TODO: Deinit any pdev specific wmi resource */ 8126 } 8127 8128 int ath11k_wmi_pdev_attach(struct ath11k_base *ab, 8129 u8 pdev_id) 8130 { 8131 struct ath11k_pdev_wmi *wmi_handle; 8132 8133 if (pdev_id >= ab->hw_params.max_radios) 8134 return -EINVAL; 8135 8136 wmi_handle = &ab->wmi_ab.wmi[pdev_id]; 8137 8138 wmi_handle->wmi_ab = &ab->wmi_ab; 8139 8140 ab->wmi_ab.ab = ab; 8141 /* TODO: Init remaining resource specific to pdev */ 8142 8143 return 0; 8144 } 8145 8146 int ath11k_wmi_attach(struct ath11k_base *ab) 8147 { 8148 int ret; 8149 8150 ret = ath11k_wmi_pdev_attach(ab, 0); 8151 if (ret) 8152 return ret; 8153 8154 ab->wmi_ab.ab = ab; 8155 ab->wmi_ab.preferred_hw_mode = WMI_HOST_HW_MODE_MAX; 8156 8157 /* It's overwritten when service_ext_ready is handled */ 8158 if (ab->hw_params.single_pdev_only) 8159 ab->wmi_ab.preferred_hw_mode = WMI_HOST_HW_MODE_SINGLE; 8160 8161 /* TODO: Init remaining wmi soc resources required */ 8162 init_completion(&ab->wmi_ab.service_ready); 8163 init_completion(&ab->wmi_ab.unified_ready); 8164 8165 return 0; 8166 } 8167 8168 void ath11k_wmi_detach(struct ath11k_base *ab) 8169 { 8170 int i; 8171 8172 /* TODO: Deinit wmi resource specific to SOC as required */ 8173 8174 for (i = 0; i < ab->htc.wmi_ep_count; i++) 8175 ath11k_wmi_pdev_detach(ab, i); 8176 8177 ath11k_wmi_free_dbring_caps(ab); 8178 } 8179 8180 int ath11k_wmi_wow_host_wakeup_ind(struct ath11k *ar) 8181 { 8182 struct wmi_wow_host_wakeup_ind *cmd; 8183 struct sk_buff *skb; 8184 size_t len; 8185 8186 len = sizeof(*cmd); 8187 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, len); 8188 if (!skb) 8189 return -ENOMEM; 8190 8191 cmd = (struct wmi_wow_host_wakeup_ind *)skb->data; 8192 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 8193 WMI_TAG_WOW_HOSTWAKEUP_FROM_SLEEP_CMD) | 8194 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 8195 8196 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, "wmi tlv wow host wakeup ind\n"); 8197 8198 return ath11k_wmi_cmd_send(ar->wmi, skb, WMI_WOW_HOSTWAKEUP_FROM_SLEEP_CMDID); 8199 } 8200 8201 int ath11k_wmi_wow_enable(struct ath11k *ar) 8202 { 8203 struct wmi_wow_enable_cmd *cmd; 8204 struct sk_buff *skb; 8205 int len; 8206 8207 len = sizeof(*cmd); 8208 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, len); 8209 if (!skb) 8210 return -ENOMEM; 8211 8212 cmd = (struct wmi_wow_enable_cmd *)skb->data; 8213 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_WOW_ENABLE_CMD) | 8214 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 8215 8216 cmd->enable = 1; 8217 cmd->pause_iface_config = WOW_IFACE_PAUSE_ENABLED; 8218 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, "wmi tlv wow enable\n"); 8219 8220 return ath11k_wmi_cmd_send(ar->wmi, skb, WMI_WOW_ENABLE_CMDID); 8221 } 8222 8223 int ath11k_wmi_scan_prob_req_oui(struct ath11k *ar, 8224 const u8 mac_addr[ETH_ALEN]) 8225 { 8226 struct sk_buff *skb; 8227 struct wmi_scan_prob_req_oui_cmd *cmd; 8228 u32 prob_req_oui; 8229 int len; 8230 8231 prob_req_oui = (((u32)mac_addr[0]) << 16) | 8232 (((u32)mac_addr[1]) << 8) | mac_addr[2]; 8233 8234 len = sizeof(*cmd); 8235 skb = ath11k_wmi_alloc_skb(ar->wmi->wmi_ab, len); 8236 if (!skb) 8237 return -ENOMEM; 8238 8239 cmd = (struct wmi_scan_prob_req_oui_cmd *)skb->data; 8240 cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, 8241 WMI_TAG_SCAN_PROB_REQ_OUI_CMD) | 8242 FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE); 8243 cmd->prob_req_oui = prob_req_oui; 8244 8245 ath11k_dbg(ar->ab, ATH11K_DBG_WMI, "wmi scan prob req oui %d\n", 8246 prob_req_oui); 8247 8248 return ath11k_wmi_cmd_send(ar->wmi, skb, WMI_SCAN_PROB_REQ_OUI_CMDID); 8249 } 8250