1 /* 2 * Copyright (c) 2019-2021 The Linux Foundation. All rights reserved. 3 * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. 4 * 5 * Permission to use, copy, modify, and/or distribute this software for 6 * any purpose with or without fee is hereby granted, provided that the 7 * above copyright notice and this permission notice appear in all 8 * copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL 11 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED 12 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE 13 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL 14 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR 15 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER 16 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 17 * PERFORMANCE OF THIS SOFTWARE. 18 */ 19 20 #include <wlan_cfr_ucfg_api.h> 21 #include "cfr_defs_i.h" 22 #include <wlan_cfr_utils_api.h> 23 #include <wlan_cfr_tgt_api.h> 24 #include <wlan_objmgr_peer_obj.h> 25 #include <wlan_objmgr_pdev_obj.h> 26 #include <qdf_module.h> 27 #ifdef WLAN_ENH_CFR_ENABLE 28 #include "cdp_txrx_ctrl.h" 29 #endif 30 31 #ifdef WLAN_ENH_CFR_ENABLE 32 static bool cfr_is_filter_enabled(struct cfr_rcc_param *rcc_param) 33 { 34 if (rcc_param->m_directed_ftm || 35 rcc_param->m_all_ftm_ack || 36 rcc_param->m_ndpa_ndp_directed || 37 rcc_param->m_ndpa_ndp_all || 38 rcc_param->m_ta_ra_filter || 39 rcc_param->m_all_packet) 40 return true; 41 else 42 return false; 43 } 44 45 static bool cfr_is_rcc_enabled(struct pdev_cfr *pa) 46 { 47 if (pa->is_cfr_rcc_capable && 48 cfr_is_filter_enabled(&pa->rcc_param)) 49 return true; 50 else 51 return false; 52 } 53 #else 54 static bool cfr_is_rcc_enabled(struct pdev_cfr *pa) 55 { 56 return false; 57 } 58 #endif 59 int ucfg_cfr_start_capture(struct wlan_objmgr_pdev *pdev, 60 struct wlan_objmgr_peer *peer, 61 struct cfr_capture_params *params) 62 { 63 int status; 64 struct pdev_cfr *pa; 65 struct peer_cfr *pe; 66 struct wlan_objmgr_psoc *psoc; 67 68 pa = wlan_objmgr_pdev_get_comp_private_obj(pdev, WLAN_UMAC_COMP_CFR); 69 if (NULL == pa) { 70 cfr_err("PDEV cfr object is NULL!"); 71 return -EINVAL; 72 } 73 74 if (!(pa->is_cfr_capable)) { 75 cfr_err("cfr is not supported on this chip"); 76 return -EINVAL; 77 } 78 79 /* Get peer private object */ 80 pe = wlan_objmgr_peer_get_comp_private_obj(peer, WLAN_UMAC_COMP_CFR); 81 if (NULL == pe) { 82 cfr_err("PEER cfr object is NULL!"); 83 return -EINVAL; 84 } 85 86 psoc = wlan_pdev_get_psoc(pdev); 87 if (!psoc) { 88 cfr_err("psoc is null!"); 89 return -EINVAL; 90 } 91 92 if (!(tgt_cfr_validate_period(psoc, params->period))) 93 return -EINVAL; 94 95 if (!(params->period) && (pa->cfr_timer_enable)) { 96 cfr_err("Single shot capture is not allowed during periodic capture"); 97 return -EINVAL; 98 } 99 100 if ((params->period) && !(pa->cfr_timer_enable)) { 101 cfr_err("Global periodic timer is not enabled, configure global cfr timer"); 102 } 103 104 if (params->period) { 105 if (pa->cfr_current_sta_count == pa->cfr_max_sta_count) { 106 cfr_err("max periodic cfr clients reached"); 107 return -EINVAL; 108 } 109 if (!(pe->request)) 110 pa->cfr_current_sta_count++; 111 } 112 113 if (cfr_is_rcc_enabled(pa)) { 114 cfr_err("This is not allowed since RCC is enabled"); 115 pa->cfr_timer_enable = 0; 116 return -EINVAL; 117 } 118 119 status = tgt_cfr_start_capture(pdev, peer, params); 120 121 if (status == 0) { 122 pe->bandwidth = params->bandwidth; 123 pe->period = params->period; 124 pe->capture_method = params->method; 125 pe->request = PEER_CFR_CAPTURE_ENABLE; 126 } else 127 pa->cfr_current_sta_count--; 128 129 return status; 130 } 131 132 int ucfg_cfr_start_capture_probe_req(struct wlan_objmgr_pdev *pdev, 133 struct qdf_mac_addr *unassoc_mac, 134 struct cfr_capture_params *params) 135 { 136 int idx, idx_to_insert = -1; 137 struct pdev_cfr *pa; 138 139 pa = wlan_objmgr_pdev_get_comp_private_obj(pdev, WLAN_UMAC_COMP_CFR); 140 if (!pa) { 141 cfr_err("Pdev cfr object is null!"); 142 return -EINVAL; 143 } 144 145 if (!(pa->is_cfr_capable)) { 146 cfr_err("CFR is not supported on this chip"); 147 return -EINVAL; 148 } 149 150 if (pa->cfr_current_sta_count == pa->cfr_max_sta_count) { 151 cfr_err("max cfr cleint reached"); 152 return -EINVAL; 153 } 154 155 for (idx = 0; idx < MAX_CFR_ENABLED_CLIENTS; idx++) { 156 /* Store first invalid entry's index, to add mac entry if not 157 * already present. 158 */ 159 if (idx_to_insert < 0) { 160 if (pa->unassoc_pool[idx].is_valid != true) 161 idx_to_insert = idx; 162 } 163 164 /* Add new mac entry only if it is not present. If already 165 * present, update the capture parameters 166 */ 167 if (qdf_mem_cmp(&pa->unassoc_pool[idx].mac, unassoc_mac, 168 sizeof(struct qdf_mac_addr)) == 0) { 169 cfr_info("Node already present. Updating params"); 170 qdf_mem_copy(&pa->unassoc_pool[idx].cfr_params, 171 params, 172 sizeof(struct cfr_capture_params)); 173 pa->unassoc_pool[idx].is_valid = true; 174 return 0; 175 } 176 } 177 178 if (idx_to_insert < 0) { 179 /* All the entries in the table are valid. So we have reached 180 * max client capacity. To add a new client, capture on one of 181 * the clients in table has to be stopped. 182 */ 183 cfr_err("Maximum client capacity reached"); 184 return -EINVAL; 185 } 186 187 /* If control reaches here, we did not find mac in the table 188 * and we have atleast one free entry in table. 189 * Add the entry at index = idx_to_insert 190 */ 191 qdf_mem_copy(&pa->unassoc_pool[idx_to_insert].mac, 192 unassoc_mac, sizeof(struct qdf_mac_addr)); 193 qdf_mem_copy(&pa->unassoc_pool[idx_to_insert].cfr_params, 194 params, sizeof(struct cfr_capture_params)); 195 pa->unassoc_pool[idx_to_insert].is_valid = true; 196 pa->cfr_current_sta_count++; 197 198 return 0; 199 } 200 201 int ucfg_cfr_stop_capture_probe_req(struct wlan_objmgr_pdev *pdev, 202 struct qdf_mac_addr *unassoc_mac) 203 { 204 struct pdev_cfr *pa; 205 int idx; 206 207 pa = wlan_objmgr_pdev_get_comp_private_obj(pdev, WLAN_UMAC_COMP_CFR); 208 if (!pa) { 209 cfr_err("Pdev cfr object is NULL!"); 210 return -EINVAL; 211 } 212 213 if (!(pa->is_cfr_capable)) { 214 cfr_err("CFR is not supported on this chip"); 215 return -EINVAL; 216 } 217 218 for (idx = 0; idx < MAX_CFR_ENABLED_CLIENTS; idx++) { 219 /* Remove mac only if it is present */ 220 if (qdf_mem_cmp(&pa->unassoc_pool[idx].mac, unassoc_mac, 221 sizeof(struct qdf_mac_addr)) == 0) { 222 qdf_mem_zero(&pa->unassoc_pool[idx], 223 sizeof(struct unassoc_pool_entry)); 224 pa->cfr_current_sta_count--; 225 return 0; 226 } 227 } 228 229 /* If mac was present in pool it would have been deleted in the 230 * above loop and returned from there. 231 * If control reached here, mac was not found. So, ignore the request. 232 */ 233 cfr_err("Trying to delete mac not present in pool. Ignoring request."); 234 return 0; 235 } 236 237 int ucfg_cfr_set_timer(struct wlan_objmgr_pdev *pdev, uint32_t value) 238 { 239 struct pdev_cfr *pa; 240 241 if (wlan_cfr_is_feature_disabled(pdev)) { 242 cfr_err("cfr is disabled"); 243 return QDF_STATUS_E_NOSUPPORT; 244 } 245 246 pa = wlan_objmgr_pdev_get_comp_private_obj(pdev, WLAN_UMAC_COMP_CFR); 247 if (pa == NULL) { 248 cfr_err("PDEV cfr object is NULL!"); 249 return -EINVAL; 250 } 251 252 if (!(pa->is_cfr_capable)) { 253 cfr_err("cfr is not supported on this chip"); 254 return -EINVAL; 255 } 256 257 return tgt_cfr_enable_cfr_timer(pdev, value); 258 } 259 qdf_export_symbol(ucfg_cfr_set_timer); 260 261 int ucfg_cfr_get_timer(struct wlan_objmgr_pdev *pdev) 262 { 263 struct pdev_cfr *pa; 264 265 if (wlan_cfr_is_feature_disabled(pdev)) { 266 cfr_err("cfr is disabled"); 267 return QDF_STATUS_E_NOSUPPORT; 268 } 269 270 pa = wlan_objmgr_pdev_get_comp_private_obj(pdev, WLAN_UMAC_COMP_CFR); 271 if (pa == NULL) { 272 cfr_err("PDEV cfr object is NULL!"); 273 return -EINVAL; 274 } 275 276 if (!(pa->is_cfr_capable)) { 277 cfr_err("cfr is not supported on this chip"); 278 return -EINVAL; 279 } 280 281 return pa->cfr_timer_enable; 282 } 283 qdf_export_symbol(ucfg_cfr_get_timer); 284 285 static void cfr_iter_peer_handler(struct wlan_objmgr_pdev *pdev, 286 void *object, void *arg) 287 { 288 struct wlan_objmgr_peer *peer = (struct wlan_objmgr_peer *)object; 289 struct peer_cfr *pe; 290 int *cfr_capt_status = (int *)arg; 291 292 if (*cfr_capt_status == PEER_CFR_CAPTURE_ENABLE) 293 return; 294 295 if (!peer || !pdev) { 296 cfr_err("peer or pdev object is NULL"); 297 return; 298 } 299 300 if (wlan_vdev_get_selfpeer(peer->peer_objmgr.vdev) == peer) 301 return; 302 303 pe = wlan_objmgr_peer_get_comp_private_obj(peer, WLAN_UMAC_COMP_CFR); 304 if (!pe) { 305 cfr_err("PEER cfr object is NULL!"); 306 return; 307 } 308 309 if (pe->period && (pe->request == PEER_CFR_CAPTURE_ENABLE)) { 310 *cfr_capt_status = pe->request; 311 cfr_debug("CFR capture running for peer " 312 QDF_MAC_ADDR_FMT, 313 QDF_MAC_ADDR_REF(peer->macaddr)); 314 } 315 } 316 317 void ucfg_cfr_get_capture_status(struct wlan_objmgr_pdev *pdev, 318 enum cfr_capt_status *status) 319 { 320 *status = PEER_CFR_CAPTURE_DISABLE; 321 322 wlan_objmgr_pdev_iterate_obj_list(pdev, WLAN_PEER_OP, 323 cfr_iter_peer_handler, 324 status, 1, WLAN_CFR_ID); 325 } 326 qdf_export_symbol(ucfg_cfr_get_capture_status); 327 328 int ucfg_cfr_stop_capture(struct wlan_objmgr_pdev *pdev, 329 struct wlan_objmgr_peer *peer) 330 { 331 int status; 332 struct peer_cfr *pe; 333 struct pdev_cfr *pa; 334 335 pa = wlan_objmgr_pdev_get_comp_private_obj(pdev, WLAN_UMAC_COMP_CFR); 336 if (pa == NULL) { 337 cfr_err("PDEV cfr object is NULL!"); 338 return -EINVAL; 339 } 340 341 if (!(pa->is_cfr_capable)) { 342 cfr_err("cfr is not supported on this chip"); 343 return -EINVAL; 344 } 345 346 pe = wlan_objmgr_peer_get_comp_private_obj(peer, WLAN_UMAC_COMP_CFR); 347 if (pe == NULL) { 348 cfr_err("PEER cfr object is NULL!"); 349 return -EINVAL; 350 } 351 352 if ((pe->period) && (pe->request)) 353 status = tgt_cfr_stop_capture(pdev, peer); 354 else { 355 cfr_err("periodic cfr not started for the client"); 356 return -EINVAL; 357 } 358 359 if (status == 0) { 360 pe->request = PEER_CFR_CAPTURE_DISABLE; 361 pa->cfr_current_sta_count--; 362 } 363 364 return status; 365 } 366 367 int ucfg_cfr_list_peers(struct wlan_objmgr_pdev *pdev) 368 { 369 return 0; 370 } 371 372 QDF_STATUS ucfg_cfr_stop_indication(struct wlan_objmgr_vdev *vdev) 373 { 374 if (!vdev) { 375 cfr_err("null vdev"); 376 return QDF_STATUS_E_INVAL; 377 } 378 379 return cfr_stop_indication(vdev); 380 } 381 382 #ifdef WLAN_CFR_ADRASTEA 383 void ucfg_cfr_capture_data(struct wlan_objmgr_psoc *psoc, uint32_t vdev_id, 384 struct csi_cfr_header *hdr, uint32_t mem_index) 385 { 386 struct wlan_objmgr_vdev *vdev; 387 struct wlan_objmgr_pdev *pdev; 388 struct pdev_cfr *pcfr; 389 uint32_t end_magic_num = 0xBEAFDEAD; 390 void *vaddr, *payload; 391 u32 *rindex, *windex, payload_len; 392 QDF_STATUS status = QDF_STATUS_SUCCESS; 393 394 vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id, 395 WLAN_CFR_ID); 396 if (!vdev) { 397 cfr_err("vdev is NULL"); 398 return; 399 } 400 401 pdev = wlan_vdev_get_pdev(vdev); 402 if (!pdev) { 403 cfr_err("pdev is NULL"); 404 wlan_objmgr_vdev_release_ref(vdev, WLAN_CFR_ID); 405 return; 406 } 407 408 status = wlan_objmgr_pdev_try_get_ref(pdev, WLAN_CFR_ID); 409 if (status != QDF_STATUS_SUCCESS) { 410 cfr_err("Failed to get pdev reference"); 411 wlan_objmgr_vdev_release_ref(vdev, WLAN_CFR_ID); 412 return; 413 } 414 415 pcfr = wlan_objmgr_pdev_get_comp_private_obj(pdev, 416 WLAN_UMAC_COMP_CFR); 417 if (!pcfr) { 418 cfr_err("pdev is NULL"); 419 goto exit; 420 } 421 422 if (!pcfr->is_cfr_capable) { 423 cfr_err("CFR not supported on this chip"); 424 goto exit; 425 } 426 427 hdr->cmn.vendorid = CFR_VENDOR_ID; 428 hdr->cmn.cfr_metadata_version = CFR_META_VERSION_1; 429 hdr->cmn.cfr_data_version = CFR_DATA_VERSION_1; 430 hdr->cmn.chip_type = CFR_CAPTURE_RADIO_ADRASTEA; 431 hdr->cmn.pltform_type = CFR_PLATFORM_TYPE_ARM; 432 hdr->cmn.cfr_metadata_len = CFR_META_DATA_LEN; 433 434 vaddr = pcfr->cfr_mem_chunk.vaddr; 435 rindex = (u32 *)vaddr; 436 windex = rindex + 1; 437 438 /* 439 * mem_index is having the index of the address where CFR dump wrriten, 440 * find data pointer from mem index and start address of memory. 441 */ 442 payload = vaddr + mem_index; 443 payload_len = hdr->u.meta_legacy.length; 444 445 /* Write data into streamfs */ 446 tgt_cfr_info_send(pdev, hdr, sizeof(struct csi_cfr_header), 447 payload, payload_len, &end_magic_num, 448 sizeof(uint32_t)); 449 450 /* 451 * Updating the read index to the number of bytes read by host, it will 452 * help in writing next capture. 453 * ignoring 4 byte for FW magic number from the actual allocated memory 454 * length to avoid corruption in magic number. This memory is circular 455 * so after complation of one round, Skipping the first 8 byte as they 456 * are for read index and write index. 457 */ 458 if (((*rindex) + payload_len) <= (pcfr->cfr_mem_chunk.len - 4)) 459 (*rindex) += payload_len; 460 else if (((*rindex) + payload_len) > (pcfr->cfr_mem_chunk.len - 4)) 461 (*rindex) = (payload_len + 8); 462 463 exit: 464 wlan_objmgr_vdev_release_ref(vdev, WLAN_CFR_ID); 465 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 466 } 467 #endif 468 469 #ifdef WLAN_ENH_CFR_ENABLE 470 471 static 472 QDF_STATUS dev_sanity_check(struct wlan_objmgr_vdev *vdev, 473 struct wlan_objmgr_pdev **ppdev, 474 struct pdev_cfr **ppcfr) 475 { 476 QDF_STATUS status = QDF_STATUS_SUCCESS; 477 478 if (!vdev) { 479 cfr_err("vdev is NULL"); 480 return QDF_STATUS_E_NULL_VALUE; 481 } 482 483 *ppdev = wlan_vdev_get_pdev(vdev); 484 485 if (!*ppdev) { 486 cfr_err("pdev is NULL"); 487 return QDF_STATUS_E_NULL_VALUE; 488 } 489 490 status = wlan_objmgr_pdev_try_get_ref(*ppdev, WLAN_CFR_ID); 491 if (status != QDF_STATUS_SUCCESS) { 492 cfr_err("Failed to get pdev reference"); 493 return status; 494 } 495 496 *ppcfr = wlan_objmgr_pdev_get_comp_private_obj(*ppdev, 497 WLAN_UMAC_COMP_CFR); 498 499 if (!(*ppcfr)) { 500 cfr_err("pdev object for CFR is null"); 501 wlan_objmgr_pdev_release_ref(*ppdev, WLAN_CFR_ID); 502 return QDF_STATUS_E_NULL_VALUE; 503 } 504 505 if (!(*ppcfr)->is_cfr_rcc_capable) { 506 cfr_err("cfr is not supported on this chip"); 507 wlan_objmgr_pdev_release_ref(*ppdev, WLAN_CFR_ID); 508 return QDF_STATUS_E_NOSUPPORT; 509 } 510 511 return status; 512 } 513 514 /* 515 * This is needed only in case of m_ta_ra_filter mode. 516 * If user wants to reset the group configurations to default values, 517 * then this handler will come into action. 518 * 519 * If user wants to reset the configurations of 0th, 1st and 3rd group, 520 * then the input should be : 521 * 522 * wlanconfig ath0 cfr reset_cfg 0xb 523 * 524 */ 525 526 QDF_STATUS ucfg_cfr_set_reset_bitmap(struct wlan_objmgr_vdev *vdev, 527 struct cfr_wlanconfig_param *params) 528 { 529 struct pdev_cfr *pcfr = NULL; 530 struct wlan_objmgr_pdev *pdev = NULL; 531 QDF_STATUS status = QDF_STATUS_SUCCESS; 532 533 status = dev_sanity_check(vdev, &pdev, &pcfr); 534 if (status != QDF_STATUS_SUCCESS) 535 return status; 536 537 pcfr->rcc_param.modified_in_curr_session |= params->reset_cfg; 538 tgt_cfr_default_ta_ra_cfg(pdev, &pcfr->rcc_param, 539 true, params->reset_cfg); 540 541 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 542 543 return status; 544 } 545 546 #ifdef WLAN_ENH_CFR_ENABLE 547 /* 548 * This is needed only in case of m_ta_ra_filter mode. 549 * After providing all the group configurations, user should provide 550 * the information about which groups need to be enabled. 551 * Based on that FW will enable the configurations for CFR groups. 552 * If user has to enable only 0th group, then input should be : 553 * 554 * wlanconfig ath0 cfr en_cfg 0x1 555 * 556 * Enable the bitmap from user provided configuration into cfr_rcc_param. 557 */ 558 559 QDF_STATUS ucfg_cfr_set_en_bitmap(struct wlan_objmgr_vdev *vdev, 560 struct cfr_wlanconfig_param *params) 561 { 562 struct pdev_cfr *pcfr = NULL; 563 struct wlan_objmgr_pdev *pdev = NULL; 564 QDF_STATUS status = QDF_STATUS_SUCCESS; 565 566 status = dev_sanity_check(vdev, &pdev, &pcfr); 567 if (status != QDF_STATUS_SUCCESS) 568 return status; 569 570 pcfr->rcc_param.filter_group_bitmap = params->en_cfg; 571 572 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 573 574 return status; 575 } 576 #endif 577 578 /* 579 * Copy user provided input for ul_mu_user_mask into cfr_rcc_param. 580 */ 581 582 QDF_STATUS 583 ucfg_cfr_set_ul_mu_user_mask(struct wlan_objmgr_vdev *vdev, 584 struct cfr_wlanconfig_param *params) 585 { 586 struct pdev_cfr *pcfr = NULL; 587 struct wlan_objmgr_pdev *pdev = NULL; 588 QDF_STATUS status = QDF_STATUS_SUCCESS; 589 590 status = dev_sanity_check(vdev, &pdev, &pcfr); 591 if (status != QDF_STATUS_SUCCESS) 592 return status; 593 594 pcfr->rcc_param.ul_mu_user_mask_lower = params->ul_mu_user_mask_lower; 595 pcfr->rcc_param.ul_mu_user_mask_upper = params->ul_mu_user_mask_upper; 596 597 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 598 599 return status; 600 } 601 602 /* 603 * FREEZE_TLV_DELAY_CNT_* registers are used for FREEZE TLV timeout mechanism 604 * in MAC side. In case MAC send FREEZE TLV to PHY too late due to 605 * long AST delay, PHY ucode may not handle it well or it will impact 606 * next frame’s normal processing, then MAC needs to drop FREEZE TLV 607 * sending process after reaching the threshold. 608 * 609 * This handler will copy user provided input for freeze_tlv_delay_cnt 610 * into cfr_rcc_param. 611 */ 612 613 QDF_STATUS 614 ucfg_cfr_set_freeze_tlv_delay_cnt(struct wlan_objmgr_vdev *vdev, 615 struct cfr_wlanconfig_param *params) 616 { 617 struct pdev_cfr *pcfr = NULL; 618 struct wlan_objmgr_pdev *pdev = NULL; 619 QDF_STATUS status = QDF_STATUS_SUCCESS; 620 621 status = dev_sanity_check(vdev, &pdev, &pcfr); 622 if (status != QDF_STATUS_SUCCESS) 623 return status; 624 625 pcfr->rcc_param.freeze_tlv_delay_cnt_en = 626 params->freeze_tlv_delay_cnt_en; 627 628 pcfr->rcc_param.freeze_tlv_delay_cnt_thr = 629 params->freeze_tlv_delay_cnt_thr; 630 631 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 632 633 return status; 634 } 635 636 /* 637 * Configure ta_ra_filter_in_as_fp from the provided configuration into 638 * cfr_rcc_param. All fixed parameters needed to be stored into cfr_rcc_param. 639 */ 640 QDF_STATUS 641 ucfg_cfr_set_tara_filterin_as_fp(struct wlan_objmgr_vdev *vdev, 642 struct cfr_wlanconfig_param *params) 643 { 644 struct pdev_cfr *pcfr = NULL; 645 struct wlan_objmgr_pdev *pdev = NULL; 646 QDF_STATUS status = QDF_STATUS_SUCCESS; 647 648 status = dev_sanity_check(vdev, &pdev, &pcfr); 649 if (status != QDF_STATUS_SUCCESS) 650 return status; 651 652 if (!pcfr->is_mo_marking_support) { 653 cfr_err("MO marking support not available to filter as FP/MO"); 654 status = QDF_STATUS_E_NOSUPPORT; 655 } else { 656 pcfr->rcc_param.en_ta_ra_filter_in_as_fp = 657 params->en_ta_ra_filter_in_as_fp; 658 } 659 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 660 661 return status; 662 } 663 664 /* 665 * Set the capture count from the provided configuration into cfr_rcc_param. 666 * All fixed parameters are needed to be stored into cfr_rcc_param. 667 */ 668 QDF_STATUS 669 ucfg_cfr_set_capture_count(struct wlan_objmgr_vdev *vdev, 670 struct cfr_wlanconfig_param *params) 671 { 672 struct pdev_cfr *pcfr = NULL; 673 struct wlan_objmgr_pdev *pdev = NULL; 674 QDF_STATUS status = QDF_STATUS_SUCCESS; 675 676 status = dev_sanity_check(vdev, &pdev, &pcfr); 677 if (status != QDF_STATUS_SUCCESS) 678 return status; 679 680 if (!pcfr->is_cap_interval_mode_sel_support) { 681 cfr_err("Capture count support not enabled"); 682 status = QDF_STATUS_E_NOSUPPORT; 683 } else { 684 pcfr->rcc_param.capture_count = params->cap_count; 685 } 686 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 687 688 return status; 689 } 690 691 /* 692 * Set interval mode sel nob from the provided configuration into cfr_rcc_param. 693 * All fixed parameters are needed to be stored into cfr_rcc_param 694 */ 695 QDF_STATUS 696 ucfg_cfr_set_capture_interval_mode_sel(struct wlan_objmgr_vdev *vdev, 697 struct cfr_wlanconfig_param *params) 698 { 699 struct pdev_cfr *pcfr = NULL; 700 struct wlan_objmgr_pdev *pdev = NULL; 701 QDF_STATUS status = QDF_STATUS_SUCCESS; 702 703 status = dev_sanity_check(vdev, &pdev, &pcfr); 704 if (status != QDF_STATUS_SUCCESS) 705 return status; 706 707 if (!pcfr->is_cap_interval_mode_sel_support) { 708 cfr_err("Capture count support not enabled"); 709 status = QDF_STATUS_E_NOSUPPORT; 710 } else { 711 pcfr->rcc_param.capture_intval_mode_sel = 712 params->cap_intval_mode_sel; 713 } 714 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 715 716 return status; 717 } 718 719 /* 720 * Set capture interval from the provided configuration into cfr_rcc_param. 721 * All fixed parameters are needed to be stored into cfr_rcc_param. 722 */ 723 724 QDF_STATUS 725 ucfg_cfr_set_capture_interval(struct wlan_objmgr_vdev *vdev, 726 struct cfr_wlanconfig_param *params) 727 { 728 struct pdev_cfr *pcfr = NULL; 729 struct wlan_objmgr_pdev *pdev = NULL; 730 QDF_STATUS status = QDF_STATUS_SUCCESS; 731 732 status = dev_sanity_check(vdev, &pdev, &pcfr); 733 if (status != QDF_STATUS_SUCCESS) 734 return status; 735 736 if (pcfr->rcc_param.capture_duration > params->cap_intvl) { 737 cfr_err("Capture interval should be more than capture duration"); 738 status = QDF_STATUS_E_INVAL; 739 } else { 740 pcfr->rcc_param.capture_interval = params->cap_intvl; 741 } 742 743 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 744 745 return status; 746 } 747 748 /* 749 * Set capture duration from the provided configuration into cfr_rcc_param. 750 * All fixed parameters are needed to be stored into cfr_rcc_param. 751 */ 752 753 QDF_STATUS 754 ucfg_cfr_set_capture_duration(struct wlan_objmgr_vdev *vdev, 755 struct cfr_wlanconfig_param *params) 756 { 757 struct pdev_cfr *pcfr = NULL; 758 struct wlan_objmgr_pdev *pdev = NULL; 759 QDF_STATUS status = QDF_STATUS_SUCCESS; 760 761 status = dev_sanity_check(vdev, &pdev, &pcfr); 762 if (status != QDF_STATUS_SUCCESS) 763 return status; 764 765 if (pcfr->rcc_param.capture_interval && 766 (params->cap_dur > pcfr->rcc_param.capture_interval)) { 767 cfr_err("Capture duration is exceeding capture interval"); 768 status = QDF_STATUS_E_INVAL; 769 } else { 770 pcfr->rcc_param.capture_duration = params->cap_dur; 771 } 772 773 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 774 775 return status; 776 } 777 778 /* 779 * Copy user provided group parameters( type/ subtype of mgmt, ctrl, data ) 780 * into curr_cfg instance of ta_ra_cfr_cfg. 781 * Set valid mask for the provided configuration. 782 * Set modified_in_curr_session for the particular group. 783 */ 784 785 QDF_STATUS 786 ucfg_cfr_set_frame_type_subtype(struct wlan_objmgr_vdev *vdev, 787 struct cfr_wlanconfig_param *params) 788 { 789 struct pdev_cfr *pcfr = NULL; 790 struct wlan_objmgr_pdev *pdev = NULL; 791 struct ta_ra_cfr_cfg *curr_cfg = NULL; 792 QDF_STATUS status = QDF_STATUS_SUCCESS; 793 794 status = dev_sanity_check(vdev, &pdev, &pcfr); 795 if (status != QDF_STATUS_SUCCESS) 796 return status; 797 798 /* Populating current config based on user's input */ 799 curr_cfg = &pcfr->rcc_param.curr[params->grp_id]; 800 curr_cfg->mgmt_subtype_filter = params->expected_mgmt_subtype; 801 curr_cfg->ctrl_subtype_filter = params->expected_ctrl_subtype; 802 curr_cfg->data_subtype_filter = params->expected_data_subtype; 803 804 curr_cfg->valid_mgmt_subtype = 1; 805 curr_cfg->valid_ctrl_subtype = 1; 806 curr_cfg->valid_data_subtype = 1; 807 808 qdf_set_bit(params->grp_id, 809 &pcfr->rcc_param.modified_in_curr_session); 810 811 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 812 813 return status; 814 } 815 816 /* 817 * Copy user provided group parameters( BW and NSS ) 818 * into curr_cfg instance of ta_ra_cfr_cfg. 819 * Set valid mask for the provided configuration. 820 * Set modified_in_curr_session for the particular group. 821 */ 822 823 QDF_STATUS ucfg_cfr_set_bw_nss(struct wlan_objmgr_vdev *vdev, 824 struct cfr_wlanconfig_param *params) 825 { 826 struct pdev_cfr *pcfr = NULL; 827 struct wlan_objmgr_pdev *pdev = NULL; 828 struct ta_ra_cfr_cfg *curr_cfg = NULL; 829 QDF_STATUS status = QDF_STATUS_SUCCESS; 830 831 status = dev_sanity_check(vdev, &pdev, &pcfr); 832 if (status != QDF_STATUS_SUCCESS) 833 return status; 834 835 /* Populating current config based on user's input */ 836 curr_cfg = &pcfr->rcc_param.curr[params->grp_id]; 837 curr_cfg->bw = params->bw; 838 curr_cfg->nss = params->nss; 839 840 curr_cfg->valid_bw_mask = 1; 841 curr_cfg->valid_nss_mask = 1; 842 843 qdf_set_bit(params->grp_id, 844 &pcfr->rcc_param.modified_in_curr_session); 845 846 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 847 848 return status; 849 } 850 851 /* 852 * Copy user provided group parameters( TA, RA, TA_MASK, RA_MASK ) 853 * into curr_cfg instance of ta_ra_cfr_cfg. 854 * Set valid mask for the provided configuration. 855 * Set modified_in_curr_session for the particular group. 856 */ 857 858 QDF_STATUS ucfg_cfr_set_tara_config(struct wlan_objmgr_vdev *vdev, 859 struct cfr_wlanconfig_param *params) 860 { 861 struct pdev_cfr *pcfr = NULL; 862 struct wlan_objmgr_pdev *pdev = NULL; 863 struct ta_ra_cfr_cfg *curr_cfg = NULL; 864 QDF_STATUS status = QDF_STATUS_SUCCESS; 865 866 status = dev_sanity_check(vdev, &pdev, &pcfr); 867 if (status != QDF_STATUS_SUCCESS) 868 return status; 869 870 curr_cfg = &pcfr->rcc_param.curr[params->grp_id]; 871 qdf_mem_copy(curr_cfg->tx_addr, params->ta, QDF_MAC_ADDR_SIZE); 872 qdf_mem_copy(curr_cfg->rx_addr, params->ra, QDF_MAC_ADDR_SIZE); 873 qdf_mem_copy(curr_cfg->tx_addr_mask, 874 params->ta_mask, QDF_MAC_ADDR_SIZE); 875 qdf_mem_copy(curr_cfg->rx_addr_mask, 876 params->ra_mask, QDF_MAC_ADDR_SIZE); 877 878 curr_cfg->valid_ta = 1; 879 curr_cfg->valid_ta_mask = 1; 880 curr_cfg->valid_ra = 1; 881 curr_cfg->valid_ra_mask = 1; 882 883 qdf_set_bit(params->grp_id, 884 &pcfr->rcc_param.modified_in_curr_session); 885 886 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 887 888 return status; 889 } 890 891 QDF_STATUS ucfg_cfr_get_cfg(struct wlan_objmgr_vdev *vdev) 892 { 893 struct pdev_cfr *pcfr = NULL; 894 struct wlan_objmgr_pdev *pdev = NULL; 895 struct ta_ra_cfr_cfg *glbl_cfg = NULL; 896 QDF_STATUS status = QDF_STATUS_SUCCESS; 897 uint8_t grp_id; 898 899 status = dev_sanity_check(vdev, &pdev, &pcfr); 900 if (status != QDF_STATUS_SUCCESS) 901 return status; 902 if (!cfr_is_filter_enabled(&pcfr->rcc_param)) { 903 cfr_err(" All RCC modes are disabled"); 904 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 905 return status; 906 } 907 908 cfr_err("CAPTURE MODE:\n"); 909 910 cfr_err("m_directed_ftm is : %s\n", 911 pcfr->rcc_param.m_directed_ftm ? 912 "enabled" : "disabled"); 913 cfr_err("m_all_ftm_ack is : %s\n", 914 pcfr->rcc_param.m_all_ftm_ack ? 915 "enabled" : "disabled"); 916 cfr_err("m_ndpa_ndp_directed is: %s\n", 917 pcfr->rcc_param.m_ndpa_ndp_directed ? 918 "enabled" : "disabled"); 919 cfr_err("m_ndpa_ndp_all is : %s\n", 920 pcfr->rcc_param.m_ndpa_ndp_all ? 921 "enabled" : "disabled"); 922 cfr_err("m_ta_ra_filter is : %s\n", 923 pcfr->rcc_param.m_ta_ra_filter ? 924 "enabled" : "disabled"); 925 cfr_err("m_all_packet is : %s\n", 926 pcfr->rcc_param.m_all_packet ? 927 "enabled" : "disabled"); 928 929 cfr_err("capture duration : %u usec\n", 930 pcfr->rcc_param.capture_duration); 931 cfr_err("capture interval : %u usec\n", 932 pcfr->rcc_param.capture_interval); 933 cfr_err("capture count : %u\n", 934 pcfr->rcc_param.capture_count); 935 cfr_err("capture interval mode sel : %u\n", 936 pcfr->rcc_param.capture_intval_mode_sel); 937 cfr_err("UL MU User mask lower : %u\n", 938 pcfr->rcc_param.ul_mu_user_mask_lower); 939 cfr_err("UL MU User mask upper : %u\n", 940 pcfr->rcc_param.ul_mu_user_mask_upper); 941 cfr_err("Freeze TLV delay count is : %s\n", 942 pcfr->rcc_param.freeze_tlv_delay_cnt_en ? 943 "enabled" : "disabled"); 944 cfr_err("Freeze TLV delay count threshold : %u\n", 945 pcfr->rcc_param.freeze_tlv_delay_cnt_thr); 946 cfr_err("Enabled CFG id bitmap : 0x%x\n", 947 pcfr->rcc_param.filter_group_bitmap); 948 cfr_err(" Modified cfg id bitmap : %lu\n", 949 pcfr->rcc_param.modified_in_curr_session); 950 951 cfr_err("TARA_CONFIG details:\n"); 952 953 for (grp_id = 0; grp_id < MAX_TA_RA_ENTRIES; grp_id++) { 954 glbl_cfg = &pcfr->global[grp_id]; 955 956 cfr_err("Config ID: %d\n", grp_id); 957 cfr_err("Bandwidth :0x%x\n", glbl_cfg->bw); 958 cfr_err("NSS : 0x%x\n", glbl_cfg->nss); 959 cfr_err("valid_ta: %d\n", glbl_cfg->valid_ta); 960 cfr_err("valid_ta_mask: %d\n", glbl_cfg->valid_ta_mask); 961 cfr_err("valid_ra: %d\n", glbl_cfg->valid_ra); 962 cfr_err("valid_ra_mask: %d\n", glbl_cfg->valid_ra_mask); 963 cfr_err("valid_bw_mask: %d\n", glbl_cfg->valid_bw_mask); 964 cfr_err("valid_nss_mask: %d\n", glbl_cfg->valid_nss_mask); 965 cfr_err("valid_mgmt_subtype: %d\n", 966 glbl_cfg->valid_mgmt_subtype); 967 cfr_err("valid_ctrl_subtype: %d\n", 968 glbl_cfg->valid_ctrl_subtype); 969 cfr_err("valid_data_subtype: %d\n", 970 glbl_cfg->valid_data_subtype); 971 cfr_err("Mgmt subtype : 0x%x\n", 972 glbl_cfg->mgmt_subtype_filter); 973 cfr_err("CTRL subtype : 0x%x\n", 974 glbl_cfg->ctrl_subtype_filter); 975 cfr_err("Data subtype : 0x%x\n", 976 glbl_cfg->data_subtype_filter); 977 cfr_err("TX Addr: " QDF_MAC_ADDR_FMT, 978 QDF_MAC_ADDR_REF(glbl_cfg->tx_addr)); 979 cfr_err("TX Addr Mask: " QDF_FULL_MAC_FMT, 980 QDF_FULL_MAC_REF(glbl_cfg->tx_addr_mask)); 981 cfr_err("RX Addr: " QDF_MAC_ADDR_FMT, 982 QDF_MAC_ADDR_REF(glbl_cfg->rx_addr)); 983 cfr_err("RX Addr Mask: " QDF_FULL_MAC_FMT, 984 QDF_FULL_MAC_REF(glbl_cfg->rx_addr_mask)); 985 } 986 987 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 988 989 return status; 990 } 991 992 static const char *chan_capture_status_to_str(enum chan_capture_status type) 993 { 994 switch (type) { 995 case CAPTURE_IDLE: 996 return "CAPTURE_IDLE"; 997 case CAPTURE_BUSY: 998 return "CAPTURE_BUSY"; 999 case CAPTURE_ACTIVE: 1000 return "CAPTURE_ACTIVE"; 1001 case CAPTURE_NO_BUFFER: 1002 return "CAPTURE_NO_BUFFER"; 1003 default: 1004 return "INVALID"; 1005 } 1006 } 1007 1008 static const 1009 char *mac_freeze_reason_to_str(enum mac_freeze_capture_reason type) 1010 { 1011 switch (type) { 1012 case FREEZE_REASON_TM: 1013 return "FREEZE_REASON_TM"; 1014 case FREEZE_REASON_FTM: 1015 return "FREEZE_REASON_FTM"; 1016 case FREEZE_REASON_ACK_RESP_TO_TM_FTM: 1017 return "FREEZE_REASON_ACK_RESP_TO_TM_FTM"; 1018 case FREEZE_REASON_TA_RA_TYPE_FILTER: 1019 return "FREEZE_REASON_TA_RA_TYPE_FILTER"; 1020 case FREEZE_REASON_NDPA_NDP: 1021 return "FREEZE_REASON_NDPA_NDP"; 1022 case FREEZE_REASON_ALL_PACKET: 1023 return "FREEZE_REASON_ALL_PACKET"; 1024 default: 1025 return "INVALID"; 1026 } 1027 } 1028 1029 QDF_STATUS ucfg_cfr_rcc_dump_dbg_counters(struct wlan_objmgr_vdev *vdev) 1030 { 1031 struct pdev_cfr *pcfr = NULL; 1032 struct wlan_objmgr_pdev *pdev = NULL; 1033 struct wlan_objmgr_psoc *psoc = NULL; 1034 struct cdp_cfr_rcc_stats *cfr_rcc_stats = NULL; 1035 uint8_t stats_cnt; 1036 QDF_STATUS status = QDF_STATUS_SUCCESS; 1037 1038 status = dev_sanity_check(vdev, &pdev, &pcfr); 1039 if (status != QDF_STATUS_SUCCESS) 1040 return status; 1041 1042 psoc = wlan_pdev_get_psoc(pdev); 1043 if (!psoc) { 1044 cfr_err("psoc is null!"); 1045 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1046 return QDF_STATUS_E_NULL_VALUE; 1047 } 1048 1049 cfr_err("total_tx_evt_cnt = %llu\n", 1050 pcfr->total_tx_evt_cnt); 1051 cfr_err("dbr_evt_cnt = %llu\n", 1052 pcfr->dbr_evt_cnt); 1053 cfr_err("rx_tlv_evt_cnt = %llu\n", 1054 pcfr->rx_tlv_evt_cnt); 1055 cfr_err("release_cnt = %llu\n", 1056 pcfr->release_cnt); 1057 cfr_err("Error cnt:\n"); 1058 cfr_err("flush_dbr_cnt = %llu\n", 1059 pcfr->flush_dbr_cnt); 1060 cfr_err("invalid_dma_length_cnt = %llu\n", 1061 pcfr->invalid_dma_length_cnt); 1062 cfr_err("flush_timeout_dbr_cnt = %llu\n", 1063 pcfr->flush_timeout_dbr_cnt); 1064 cfr_err("tx_peer_status_cfr_fail = %llu\n", 1065 pcfr->tx_peer_status_cfr_fail); 1066 cfr_err("tx_evt_status_cfr_fail = %llu\n", 1067 pcfr->tx_evt_status_cfr_fail); 1068 cfr_err("tx_dbr_cookie_lookup_fail = %llu\n", 1069 pcfr->tx_dbr_cookie_lookup_fail); 1070 cfr_err("PPDU id mismatch for same cookie:\n"); 1071 cfr_err("clear_txrx_event = %llu\n", 1072 pcfr->clear_txrx_event); 1073 cfr_err("cfr_dma_aborts = %llu\n", 1074 pcfr->cfr_dma_aborts); 1075 1076 cfr_rcc_stats = qdf_mem_malloc(sizeof(struct cdp_cfr_rcc_stats)); 1077 if (!cfr_rcc_stats) { 1078 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1079 return QDF_STATUS_E_NOMEM; 1080 } 1081 1082 cdp_get_cfr_dbg_stats(wlan_psoc_get_dp_handle(psoc), 1083 wlan_objmgr_pdev_get_pdev_id(pdev), 1084 cfr_rcc_stats); 1085 1086 cfr_err("bb_captured_channel_cnt: %llu\n", 1087 cfr_rcc_stats->bb_captured_channel_cnt); 1088 cfr_err("bb_captured_timeout_cnt: %llu\n", 1089 cfr_rcc_stats->bb_captured_timeout_cnt); 1090 cfr_err("rx_loc_info_valid_cnt: %llu\n", 1091 cfr_rcc_stats->rx_loc_info_valid_cnt); 1092 1093 cfr_err("Channel capture status:\n"); 1094 for (stats_cnt = 0; stats_cnt < CAPTURE_MAX; stats_cnt++) { 1095 cfr_err("%s = %llu\n", 1096 chan_capture_status_to_str(stats_cnt), 1097 cfr_rcc_stats->chan_capture_status[stats_cnt]); 1098 } 1099 1100 cfr_err("Freeze reason:\n"); 1101 for (stats_cnt = 0; stats_cnt < FREEZE_REASON_MAX; stats_cnt++) { 1102 cfr_err("%s = %llu\n", 1103 mac_freeze_reason_to_str(stats_cnt), 1104 cfr_rcc_stats->reason_cnt[stats_cnt]); 1105 } 1106 1107 qdf_mem_free(cfr_rcc_stats); 1108 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1109 1110 return status; 1111 } 1112 1113 QDF_STATUS ucfg_cfr_rcc_clr_dbg_counters(struct wlan_objmgr_vdev *vdev) 1114 { 1115 struct pdev_cfr *pcfr = NULL; 1116 struct wlan_objmgr_pdev *pdev = NULL; 1117 struct wlan_objmgr_psoc *psoc = NULL; 1118 QDF_STATUS status = QDF_STATUS_SUCCESS; 1119 1120 status = dev_sanity_check(vdev, &pdev, &pcfr); 1121 if (status != QDF_STATUS_SUCCESS) 1122 return status; 1123 1124 psoc = wlan_pdev_get_psoc(pdev); 1125 if (!psoc) { 1126 cfr_err("psoc is null!"); 1127 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1128 return QDF_STATUS_E_NULL_VALUE; 1129 } 1130 cdp_cfr_clr_dbg_stats(wlan_psoc_get_dp_handle(psoc), 1131 wlan_objmgr_pdev_get_pdev_id(pdev)); 1132 1133 pcfr->dbr_evt_cnt = 0; 1134 pcfr->release_cnt = 0; 1135 pcfr->total_tx_evt_cnt = 0; 1136 pcfr->rx_tlv_evt_cnt = 0; 1137 pcfr->flush_dbr_cnt = 0; 1138 pcfr->flush_timeout_dbr_cnt = 0; 1139 pcfr->invalid_dma_length_cnt = 0; 1140 pcfr->clear_txrx_event = 0; 1141 pcfr->cfr_dma_aborts = 0; 1142 pcfr->tx_peer_status_cfr_fail = 0; 1143 pcfr->tx_evt_status_cfr_fail = 0; 1144 pcfr->tx_dbr_cookie_lookup_fail = 0; 1145 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1146 1147 return status; 1148 } 1149 1150 QDF_STATUS ucfg_cfr_rcc_dump_lut(struct wlan_objmgr_vdev *vdev) 1151 { 1152 struct wlan_objmgr_pdev *pdev = NULL; 1153 QDF_STATUS status = QDF_STATUS_SUCCESS; 1154 1155 if (!vdev) { 1156 cfr_err("vdev is NULL"); 1157 return QDF_STATUS_E_INVAL; 1158 } 1159 1160 pdev = wlan_vdev_get_pdev(vdev); 1161 if (!pdev) { 1162 cfr_err("pdev is NULL"); 1163 return QDF_STATUS_E_INVAL; 1164 } 1165 1166 if (wlan_objmgr_pdev_try_get_ref(pdev, WLAN_CFR_ID) != 1167 QDF_STATUS_SUCCESS) { 1168 return QDF_STATUS_E_INVAL; 1169 } 1170 1171 cfr_err("LUT table:"); 1172 tgt_cfr_dump_lut_enh(pdev); 1173 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1174 1175 return status; 1176 } 1177 1178 static void cfr_set_filter(struct wlan_objmgr_pdev *pdev, bool enable, 1179 struct cdp_monitor_filter *filter_val) 1180 { 1181 struct wlan_objmgr_psoc *psoc = wlan_pdev_get_psoc(pdev); 1182 1183 cfr_info("pdev_id=%d\n", wlan_objmgr_pdev_get_pdev_id(pdev)); 1184 1185 cdp_cfr_filter(wlan_psoc_get_dp_handle(psoc), 1186 wlan_objmgr_pdev_get_pdev_id(pdev), 1187 enable, 1188 filter_val); 1189 } 1190 1191 #ifdef WLAN_ENH_CFR_ENABLE 1192 /* 1193 * With the initiation of commit command, this handler will be triggered. 1194 * 1195 * Starts the procedure of forming the TLVs. 1196 * If Host succeeds to send WMI command to FW, after TLV processing, then it 1197 * will save the previous CFR configurations into one instance ta_ra_cfr_cfg, 1198 * called glbl_cfg and update the current config to default state for the 1199 * next commit session. 1200 * 1201 * Finally, reset the counter (modified_in_curr_session) to 0 before moving to 1202 * next commit session. 1203 * 1204 */ 1205 1206 QDF_STATUS ucfg_cfr_committed_rcc_config(struct wlan_objmgr_vdev *vdev) 1207 { 1208 struct pdev_cfr *pcfr = NULL; 1209 struct wlan_objmgr_pdev *pdev = NULL; 1210 struct wlan_objmgr_psoc *psoc = NULL; 1211 QDF_STATUS status = QDF_STATUS_SUCCESS; 1212 struct cdp_monitor_filter filter_val = {0}; 1213 1214 status = dev_sanity_check(vdev, &pdev, &pcfr); 1215 if (status != QDF_STATUS_SUCCESS) 1216 return status; 1217 1218 psoc = wlan_pdev_get_psoc(pdev); 1219 1220 if (!psoc) { 1221 cfr_err("psoc is null!"); 1222 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1223 return QDF_STATUS_E_NULL_VALUE; 1224 } 1225 1226 pcfr->rcc_param.vdev_id = wlan_vdev_get_id(vdev); 1227 1228 /* 1229 * If capture mode is valid, then Host: 1230 * Subscribes for PPDU status TLVs in monitor status ring. 1231 * Sets filter type to either FP or MO, based on the capture mode. 1232 * Starts the LUT_AGE_TIMER of 1sec. 1233 * 1234 * If capture mode is disabled, then Host: 1235 * unsubscribes for PPDU status TLVs in monitor status ring. 1236 * Sets filter type to 0. 1237 * Stops the LUT_AGE_TIMER. 1238 * 1239 */ 1240 1241 if (cfr_is_filter_enabled(&pcfr->rcc_param)) { 1242 if (pcfr->cfr_timer_enable) { 1243 cfr_err("Not allowed: Periodic capture is enabled.\n"); 1244 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1245 return QDF_STATUS_E_NOSUPPORT; 1246 } 1247 1248 if (pcfr->rcc_param.m_all_ftm_ack) { 1249 filter_val.mode |= MON_FILTER_PASS | 1250 MON_FILTER_OTHER; 1251 filter_val.fp_mgmt |= FILTER_MGMT_ACTION; 1252 filter_val.mo_mgmt |= FILTER_MGMT_ACTION; 1253 } 1254 1255 if (pcfr->rcc_param.m_ndpa_ndp_all) { 1256 filter_val.mode |= MON_FILTER_PASS | 1257 MON_FILTER_OTHER; 1258 filter_val.fp_ctrl |= FILTER_CTRL_VHT_NDP; 1259 filter_val.mo_ctrl |= FILTER_CTRL_VHT_NDP; 1260 } 1261 1262 if (pcfr->rcc_param.m_all_packet) { 1263 filter_val.mode |= MON_FILTER_PASS | 1264 MON_FILTER_OTHER; 1265 filter_val.fp_mgmt |= FILTER_MGMT_ALL; 1266 filter_val.mo_mgmt |= FILTER_MGMT_ALL; 1267 filter_val.fp_ctrl |= FILTER_CTRL_ALL; 1268 filter_val.mo_ctrl |= FILTER_CTRL_ALL; 1269 filter_val.fp_data |= FILTER_DATA_ALL; 1270 filter_val.mo_data |= FILTER_DATA_ALL; 1271 } 1272 1273 /* 1274 * M_TA_RA in monitor other is as intensive as M_ALL pkt 1275 * Support only FP in M_TA_RA mode 1276 */ 1277 if (pcfr->rcc_param.m_ta_ra_filter) { 1278 filter_val.mode |= MON_FILTER_PASS | 1279 MON_FILTER_OTHER; 1280 filter_val.fp_mgmt |= FILTER_MGMT_ALL; 1281 filter_val.mo_mgmt |= FILTER_MGMT_ALL; 1282 filter_val.fp_ctrl |= FILTER_CTRL_ALL; 1283 filter_val.mo_ctrl |= FILTER_CTRL_ALL; 1284 filter_val.fp_data |= FILTER_DATA_ALL; 1285 filter_val.mo_data |= FILTER_DATA_ALL; 1286 } 1287 1288 if (pcfr->rcc_param.m_directed_ftm) { 1289 filter_val.mode |= MON_FILTER_PASS; 1290 filter_val.fp_mgmt |= FILTER_MGMT_ACTION; 1291 } 1292 1293 if (pcfr->rcc_param.m_ndpa_ndp_directed) { 1294 filter_val.mode |= MON_FILTER_PASS; 1295 filter_val.fp_ctrl |= FILTER_CTRL_VHT_NDP; 1296 } 1297 1298 if (!cdp_get_cfr_rcc(wlan_psoc_get_dp_handle(psoc), 1299 wlan_objmgr_pdev_get_pdev_id(pdev))) 1300 tgt_cfr_start_lut_age_timer(pdev); 1301 cfr_set_filter(pdev, 1, &filter_val); 1302 } else { 1303 if (cdp_get_cfr_rcc(wlan_psoc_get_dp_handle(psoc), 1304 wlan_objmgr_pdev_get_pdev_id(pdev))) 1305 tgt_cfr_stop_lut_age_timer(pdev); 1306 cfr_set_filter(pdev, 0, &filter_val); 1307 } 1308 1309 /* Trigger wmi to start the TLV processing. */ 1310 status = tgt_cfr_config_rcc(pdev, &pcfr->rcc_param); 1311 if (status == QDF_STATUS_SUCCESS) { 1312 cfr_info("CFR commit done\n"); 1313 /* Update global config */ 1314 tgt_cfr_update_global_cfg(pdev); 1315 1316 /* Bring curr_cfg to default state for next commit session */ 1317 tgt_cfr_default_ta_ra_cfg(pdev, &pcfr->rcc_param, 1318 false, MAX_RESET_CFG_ENTRY); 1319 } else { 1320 cfr_err("CFR commit failed"); 1321 } 1322 1323 pcfr->rcc_param.num_grp_tlvs = 0; 1324 pcfr->rcc_param.modified_in_curr_session = 0; 1325 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1326 1327 return status; 1328 } 1329 1330 #ifdef WLAN_CFR_PM 1331 QDF_STATUS ucfg_cfr_suspend(struct wlan_objmgr_pdev *pdev) 1332 { 1333 struct pdev_cfr *pcfr; 1334 1335 pcfr = wlan_objmgr_pdev_get_comp_private_obj( 1336 pdev, WLAN_UMAC_COMP_CFR); 1337 1338 if (!pcfr) { 1339 cfr_err("null pcfr"); 1340 return QDF_STATUS_E_INVAL; 1341 } 1342 1343 return cfr_allow_suspend(pcfr); 1344 } 1345 1346 QDF_STATUS ucfg_cfr_resume(struct wlan_objmgr_pdev *pdev) 1347 { 1348 struct pdev_cfr *pcfr; 1349 1350 pcfr = wlan_objmgr_pdev_get_comp_private_obj( 1351 pdev, WLAN_UMAC_COMP_CFR); 1352 1353 if (!pcfr) { 1354 cfr_err("null pcfr"); 1355 return QDF_STATUS_E_INVAL; 1356 } 1357 1358 return cfr_prevent_suspend(pcfr); 1359 } 1360 #endif 1361 /* 1362 * This handler is used to enable / disable the capture mode. 1363 * 1364 */ 1365 QDF_STATUS ucfg_cfr_set_rcc_mode(struct wlan_objmgr_vdev *vdev, 1366 enum capture_type mode, uint8_t value) 1367 { 1368 struct pdev_cfr *pcfr = NULL; 1369 struct wlan_objmgr_pdev *pdev = NULL; 1370 QDF_STATUS status = QDF_STATUS_SUCCESS; 1371 1372 status = dev_sanity_check(vdev, &pdev, &pcfr); 1373 if (status != QDF_STATUS_SUCCESS) 1374 return status; 1375 1376 switch (mode) { 1377 case RCC_DIRECTED_FTM_FILTER: 1378 pcfr->rcc_param.m_directed_ftm = value; 1379 break; 1380 case RCC_ALL_FTM_ACK_FILTER: 1381 pcfr->rcc_param.m_all_ftm_ack = value; 1382 break; 1383 case RCC_DIRECTED_NDPA_NDP_FILTER: 1384 pcfr->rcc_param.m_ndpa_ndp_directed = value; 1385 break; 1386 case RCC_NDPA_NDP_ALL_FILTER: 1387 pcfr->rcc_param.m_ndpa_ndp_all = value; 1388 break; 1389 case RCC_TA_RA_FILTER: 1390 pcfr->rcc_param.m_ta_ra_filter = value; 1391 break; 1392 case RCC_ALL_PACKET_FILTER: 1393 pcfr->rcc_param.m_all_packet = value; 1394 break; 1395 case RCC_DIS_ALL_MODE: 1396 pcfr->rcc_param.m_directed_ftm = value; 1397 pcfr->rcc_param.m_all_ftm_ack = value; 1398 pcfr->rcc_param.m_ndpa_ndp_directed = value; 1399 pcfr->rcc_param.m_ndpa_ndp_all = value; 1400 pcfr->rcc_param.m_ta_ra_filter = value; 1401 pcfr->rcc_param.m_all_packet = value; 1402 break; 1403 1404 default: 1405 break; 1406 } 1407 1408 cfr_debug("<CFR_UMAC> Capture mode set by user: 0x%x\n", value); 1409 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1410 1411 return status; 1412 } 1413 #endif 1414 1415 bool ucfg_cfr_get_rcc_enabled(struct wlan_objmgr_vdev *vdev) 1416 { 1417 struct pdev_cfr *pcfr = NULL; 1418 struct wlan_objmgr_pdev *pdev = NULL; 1419 QDF_STATUS status = QDF_STATUS_SUCCESS; 1420 bool rcc_enabled = false; 1421 1422 status = dev_sanity_check(vdev, &pdev, &pcfr); 1423 if (status != QDF_STATUS_SUCCESS) 1424 return false; 1425 1426 rcc_enabled = cfr_is_filter_enabled(&pcfr->rcc_param); 1427 wlan_objmgr_pdev_release_ref(pdev, WLAN_CFR_ID); 1428 1429 return rcc_enabled; 1430 } 1431 1432 #ifdef WLAN_ENH_CFR_ENABLE 1433 QDF_STATUS ucfg_cfr_subscribe_ppdu_desc(struct wlan_objmgr_pdev *pdev, 1434 bool is_subscribe) 1435 { 1436 return tgt_cfr_subscribe_ppdu_desc(pdev, is_subscribe); 1437 } 1438 #endif 1439 #endif 1440