1 /* 2 * Copyright (c) 2017-2021 The Linux Foundation. All rights reserved. 3 * Copyright (c) 2022-2023 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 /** 21 * DOC: wlan_tdls_main.c 22 * 23 * TDLS core function definitions 24 */ 25 26 #include "wlan_tdls_main.h" 27 #include "wlan_tdls_peer.h" 28 #include "wlan_tdls_ct.h" 29 #include "wlan_tdls_mgmt.h" 30 #include "wlan_tdls_api.h" 31 #include "wlan_tdls_tgt_api.h" 32 #include "wlan_policy_mgr_public_struct.h" 33 #include "wlan_policy_mgr_api.h" 34 #include "wlan_scan_ucfg_api.h" 35 #include "wlan_tdls_ucfg_api.h" 36 #include "wlan_cm_roam_api.h" 37 #include "wlan_cfg80211_tdls.h" 38 #include "wlan_nan_api_i.h" 39 #include "wlan_mlme_vdev_mgr_interface.h" 40 41 /* Global tdls soc pvt object 42 * this is useful for some functions which does not receive either vdev or psoc 43 * objects. 44 */ 45 static struct tdls_soc_priv_obj *tdls_soc_global; 46 47 #ifdef WLAN_DEBUG 48 /** 49 * tdls_get_cmd_type_str() - parse cmd to string 50 * @cmd_type: tdls cmd type 51 * 52 * This function parse tdls cmd to string. 53 * 54 * Return: command string 55 */ 56 static char *tdls_get_cmd_type_str(enum tdls_command_type cmd_type) 57 { 58 switch (cmd_type) { 59 CASE_RETURN_STRING(TDLS_CMD_TX_ACTION); 60 CASE_RETURN_STRING(TDLS_CMD_ADD_STA); 61 CASE_RETURN_STRING(TDLS_CMD_CHANGE_STA); 62 CASE_RETURN_STRING(TDLS_CMD_ENABLE_LINK); 63 CASE_RETURN_STRING(TDLS_CMD_DISABLE_LINK); 64 CASE_RETURN_STRING(TDLS_CMD_CONFIG_FORCE_PEER); 65 CASE_RETURN_STRING(TDLS_CMD_REMOVE_FORCE_PEER); 66 CASE_RETURN_STRING(TDLS_CMD_STATS_UPDATE); 67 CASE_RETURN_STRING(TDLS_CMD_CONFIG_UPDATE); 68 CASE_RETURN_STRING(TDLS_CMD_SCAN_DONE); 69 CASE_RETURN_STRING(TDLS_CMD_SET_RESPONDER); 70 CASE_RETURN_STRING(TDLS_NOTIFY_STA_CONNECTION); 71 CASE_RETURN_STRING(TDLS_NOTIFY_STA_DISCONNECTION); 72 CASE_RETURN_STRING(TDLS_CMD_SET_TDLS_MODE); 73 CASE_RETURN_STRING(TDLS_CMD_SESSION_INCREMENT); 74 CASE_RETURN_STRING(TDLS_CMD_SESSION_DECREMENT); 75 CASE_RETURN_STRING(TDLS_CMD_TEARDOWN_LINKS); 76 CASE_RETURN_STRING(TDLS_NOTIFY_RESET_ADAPTERS); 77 CASE_RETURN_STRING(TDLS_CMD_ANTENNA_SWITCH); 78 CASE_RETURN_STRING(TDLS_CMD_SET_OFFCHANMODE); 79 CASE_RETURN_STRING(TDLS_CMD_SET_OFFCHANNEL); 80 CASE_RETURN_STRING(TDLS_CMD_SET_SECOFFCHANOFFSET); 81 CASE_RETURN_STRING(TDLS_DELETE_ALL_PEERS_INDICATION); 82 CASE_RETURN_STRING(TDLS_CMD_START_BSS); 83 CASE_RETURN_STRING(TDLS_CMD_SET_LINK_UNFORCE); 84 default: 85 return "Invalid TDLS command"; 86 } 87 } 88 89 /** 90 * tdls_get_event_type_str() - parase event to string 91 * @event_type: tdls event type 92 * 93 * This function parse tdls event to string. 94 * 95 * Return: event string 96 */ 97 static char *tdls_get_event_type_str(enum tdls_event_type event_type) 98 { 99 switch (event_type) { 100 case TDLS_SHOULD_DISCOVER: 101 return "TDLS_SHOULD_DISCOVER"; 102 case TDLS_SHOULD_TEARDOWN: 103 return "TDLS_SHOULD_TEARDOWN"; 104 case TDLS_PEER_DISCONNECTED: 105 return "TDLS_PEER_DISCONNECTED"; 106 case TDLS_CONNECTION_TRACKER_NOTIFY: 107 return "TDLS_CONNECTION_TRACKER_NOTIFY"; 108 109 default: 110 return "Invalid TDLS event"; 111 } 112 } 113 #else 114 static char *tdls_get_cmd_type_str(enum tdls_command_type cmd_type) 115 { 116 return ""; 117 } 118 119 static char *tdls_get_event_type_str(enum tdls_event_type event_type) 120 { 121 return ""; 122 } 123 #endif 124 125 QDF_STATUS tdls_psoc_obj_create_notification(struct wlan_objmgr_psoc *psoc, 126 void *arg_list) 127 { 128 QDF_STATUS status; 129 struct tdls_soc_priv_obj *tdls_soc_obj; 130 131 tdls_soc_obj = qdf_mem_malloc(sizeof(*tdls_soc_obj)); 132 if (!tdls_soc_obj) 133 return QDF_STATUS_E_NOMEM; 134 135 tdls_soc_obj->soc = psoc; 136 137 status = wlan_objmgr_psoc_component_obj_attach(psoc, 138 WLAN_UMAC_COMP_TDLS, 139 (void *)tdls_soc_obj, 140 QDF_STATUS_SUCCESS); 141 142 if (QDF_IS_STATUS_ERROR(status)) { 143 tdls_err("Failed to attach psoc tdls component"); 144 qdf_mem_free(tdls_soc_obj); 145 return status; 146 } 147 148 tdls_soc_global = tdls_soc_obj; 149 tdls_notice("TDLS obj attach to psoc successfully"); 150 151 return status; 152 } 153 154 QDF_STATUS tdls_psoc_obj_destroy_notification(struct wlan_objmgr_psoc *psoc, 155 void *arg_list) 156 { 157 QDF_STATUS status; 158 struct tdls_soc_priv_obj *tdls_soc_obj; 159 160 tdls_soc_obj = wlan_objmgr_psoc_get_comp_private_obj(psoc, 161 WLAN_UMAC_COMP_TDLS); 162 if (!tdls_soc_obj) { 163 tdls_err("Failed to get tdls obj in psoc"); 164 return QDF_STATUS_E_FAILURE; 165 } 166 167 status = wlan_objmgr_psoc_component_obj_detach(psoc, 168 WLAN_UMAC_COMP_TDLS, 169 tdls_soc_obj); 170 171 if (QDF_IS_STATUS_ERROR(status)) 172 tdls_err("Failed to detach psoc tdls component"); 173 qdf_mem_free(tdls_soc_obj); 174 175 return status; 176 } 177 178 static QDF_STATUS tdls_vdev_init(struct tdls_vdev_priv_obj *vdev_obj) 179 { 180 uint8_t i; 181 struct tdls_config_params *config; 182 struct tdls_user_config *user_config; 183 struct tdls_soc_priv_obj *soc_obj; 184 185 soc_obj = wlan_vdev_get_tdls_soc_obj(vdev_obj->vdev); 186 if (!soc_obj) { 187 tdls_err("tdls soc obj NULL"); 188 return QDF_STATUS_E_FAILURE; 189 } 190 191 config = &vdev_obj->threshold_config; 192 user_config = &soc_obj->tdls_configs; 193 config->tx_period_t = user_config->tdls_tx_states_period; 194 config->tx_packet_n = user_config->tdls_tx_pkt_threshold; 195 config->discovery_tries_n = user_config->tdls_max_discovery_attempt; 196 config->idle_timeout_t = user_config->tdls_idle_timeout; 197 config->idle_packet_n = user_config->tdls_idle_pkt_threshold; 198 config->rssi_trigger_threshold = 199 user_config->tdls_rssi_trigger_threshold; 200 config->rssi_teardown_threshold = 201 user_config->tdls_rssi_teardown_threshold; 202 config->rssi_delta = user_config->tdls_rssi_delta; 203 204 for (i = 0; i < WLAN_TDLS_PEER_LIST_SIZE; i++) { 205 qdf_list_create(&vdev_obj->peer_list[i], 206 WLAN_TDLS_PEER_SUB_LIST_SIZE); 207 } 208 qdf_mc_timer_init(&vdev_obj->peer_update_timer, QDF_TIMER_TYPE_SW, 209 tdls_ct_handler, vdev_obj->vdev); 210 qdf_mc_timer_init(&vdev_obj->peer_discovery_timer, QDF_TIMER_TYPE_SW, 211 tdls_discovery_timeout_peer_cb, vdev_obj->vdev); 212 213 return QDF_STATUS_SUCCESS; 214 } 215 216 static void tdls_vdev_deinit(struct tdls_vdev_priv_obj *vdev_obj) 217 { 218 qdf_mc_timer_stop_sync(&vdev_obj->peer_update_timer); 219 qdf_mc_timer_stop_sync(&vdev_obj->peer_discovery_timer); 220 221 qdf_mc_timer_destroy(&vdev_obj->peer_update_timer); 222 qdf_mc_timer_destroy(&vdev_obj->peer_discovery_timer); 223 224 tdls_peer_idle_timers_destroy(vdev_obj); 225 tdls_free_peer_list(vdev_obj); 226 } 227 228 QDF_STATUS tdls_vdev_obj_create_notification(struct wlan_objmgr_vdev *vdev, 229 void *arg) 230 { 231 QDF_STATUS status; 232 struct tdls_vdev_priv_obj *tdls_vdev_obj; 233 struct wlan_objmgr_pdev *pdev; 234 struct tdls_soc_priv_obj *tdls_soc_obj; 235 uint32_t tdls_feature_flags; 236 237 tdls_debug("tdls vdev mode %d", wlan_vdev_mlme_get_opmode(vdev)); 238 if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE && 239 wlan_vdev_mlme_get_opmode(vdev) != QDF_P2P_CLIENT_MODE) 240 return QDF_STATUS_SUCCESS; 241 242 tdls_soc_obj = wlan_vdev_get_tdls_soc_obj(vdev); 243 if (!tdls_soc_obj) { 244 tdls_err("get soc by vdev failed"); 245 return QDF_STATUS_E_NOMEM; 246 } 247 248 tdls_feature_flags = tdls_soc_obj->tdls_configs.tdls_feature_flags; 249 if (!TDLS_IS_ENABLED(tdls_feature_flags)) { 250 tdls_debug("disabled in ini"); 251 return QDF_STATUS_E_NOSUPPORT; 252 } 253 254 if (tdls_soc_obj->tdls_osif_init_cb) { 255 status = tdls_soc_obj->tdls_osif_init_cb(vdev); 256 if (QDF_IS_STATUS_ERROR(status)) 257 return status; 258 } 259 260 /* TODO: Add concurrency check */ 261 262 tdls_vdev_obj = qdf_mem_malloc(sizeof(*tdls_vdev_obj)); 263 if (!tdls_vdev_obj) { 264 status = QDF_STATUS_E_NOMEM; 265 goto err_attach; 266 } 267 268 status = wlan_objmgr_vdev_component_obj_attach(vdev, 269 WLAN_UMAC_COMP_TDLS, 270 (void *)tdls_vdev_obj, 271 QDF_STATUS_SUCCESS); 272 if (QDF_IS_STATUS_ERROR(status)) { 273 tdls_err("Failed to attach vdev tdls component"); 274 goto err_attach; 275 } 276 tdls_vdev_obj->vdev = vdev; 277 status = tdls_vdev_init(tdls_vdev_obj); 278 if (QDF_IS_STATUS_ERROR(status)) 279 goto err_vdev_init; 280 281 status = qdf_event_create(&tdls_vdev_obj->tdls_teardown_comp); 282 if (QDF_IS_STATUS_ERROR(status)) 283 goto err_event_create; 284 285 pdev = wlan_vdev_get_pdev(vdev); 286 287 status = ucfg_scan_register_event_handler(pdev, 288 tdls_scan_complete_event_handler, 289 tdls_soc_obj); 290 291 if (QDF_STATUS_SUCCESS != status) { 292 tdls_err("scan event register failed "); 293 goto err_register; 294 } 295 296 tdls_debug("tdls object attach to vdev successfully"); 297 return status; 298 299 err_register: 300 qdf_event_destroy(&tdls_vdev_obj->tdls_teardown_comp); 301 err_event_create: 302 tdls_vdev_deinit(tdls_vdev_obj); 303 err_vdev_init: 304 wlan_objmgr_vdev_component_obj_detach(vdev, 305 WLAN_UMAC_COMP_TDLS, 306 (void *)tdls_vdev_obj); 307 err_attach: 308 if (tdls_soc_obj->tdls_osif_deinit_cb) 309 tdls_soc_obj->tdls_osif_deinit_cb(vdev); 310 if (tdls_vdev_obj) { 311 qdf_mem_free(tdls_vdev_obj); 312 tdls_vdev_obj = NULL; 313 } 314 315 return status; 316 } 317 318 QDF_STATUS tdls_vdev_obj_destroy_notification(struct wlan_objmgr_vdev *vdev, 319 void *arg) 320 { 321 QDF_STATUS status; 322 struct tdls_vdev_priv_obj *tdls_vdev_obj; 323 struct tdls_soc_priv_obj *tdls_soc_obj; 324 uint32_t tdls_feature_flags; 325 326 tdls_debug("tdls vdev mode %d", wlan_vdev_mlme_get_opmode(vdev)); 327 if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE && 328 wlan_vdev_mlme_get_opmode(vdev) != QDF_P2P_CLIENT_MODE) 329 return QDF_STATUS_SUCCESS; 330 331 tdls_soc_obj = wlan_vdev_get_tdls_soc_obj(vdev); 332 if (!tdls_soc_obj) { 333 tdls_err("get soc by vdev failed"); 334 return QDF_STATUS_E_NOMEM; 335 } 336 337 tdls_feature_flags = tdls_soc_obj->tdls_configs.tdls_feature_flags; 338 if (!TDLS_IS_ENABLED(tdls_feature_flags)) { 339 tdls_debug("disabled in ini"); 340 return QDF_STATUS_E_NOSUPPORT; 341 } 342 343 tdls_vdev_obj = wlan_objmgr_vdev_get_comp_private_obj(vdev, 344 WLAN_UMAC_COMP_TDLS); 345 if (!tdls_vdev_obj) { 346 tdls_err("Failed to get tdls vdev object"); 347 return QDF_STATUS_E_FAILURE; 348 } 349 350 if (wlan_vdev_mlme_is_mlo_vdev(vdev)) { 351 if (QDF_TIMER_STATE_STOPPED != 352 qdf_mc_timer_get_current_state( 353 &tdls_vdev_obj->peer_discovery_timer)) 354 qdf_mc_timer_stop(&tdls_vdev_obj->peer_discovery_timer); 355 } 356 357 qdf_event_destroy(&tdls_vdev_obj->tdls_teardown_comp); 358 tdls_vdev_deinit(tdls_vdev_obj); 359 360 status = wlan_objmgr_vdev_component_obj_detach(vdev, 361 WLAN_UMAC_COMP_TDLS, 362 tdls_vdev_obj); 363 if (QDF_IS_STATUS_ERROR(status)) 364 tdls_err("Failed to detach vdev tdls component"); 365 366 if (tdls_soc_obj->tdls_osif_deinit_cb) 367 tdls_soc_obj->tdls_osif_deinit_cb(vdev); 368 qdf_mem_free(tdls_vdev_obj); 369 370 return status; 371 } 372 373 /** 374 * __tdls_get_all_peers_from_list() - get all the tdls peers from the list 375 * @get_tdls_peers: get_tdls_peers object 376 * 377 * Return: int 378 */ 379 static int __tdls_get_all_peers_from_list( 380 struct tdls_get_all_peers *get_tdls_peers) 381 { 382 int i; 383 int len, init_len; 384 qdf_list_t *head; 385 qdf_list_node_t *p_node; 386 struct tdls_peer *curr_peer; 387 char *buf; 388 int buf_len; 389 struct tdls_vdev_priv_obj *tdls_vdev; 390 QDF_STATUS status; 391 392 tdls_notice("Enter "); 393 394 buf = get_tdls_peers->buf; 395 buf_len = get_tdls_peers->buf_len; 396 397 if (wlan_vdev_is_up(get_tdls_peers->vdev) != QDF_STATUS_SUCCESS) { 398 len = qdf_scnprintf(buf, buf_len, 399 "\nSTA is not associated\n"); 400 return len; 401 } 402 403 tdls_vdev = wlan_vdev_get_tdls_vdev_obj(get_tdls_peers->vdev); 404 405 if (!tdls_vdev) { 406 len = qdf_scnprintf(buf, buf_len, "TDLS not enabled\n"); 407 return len; 408 } 409 410 init_len = buf_len; 411 len = qdf_scnprintf(buf, buf_len, 412 "\n%-18s%-3s%-4s%-3s%-5s\n", 413 "MAC", "Id", "cap", "up", "RSSI"); 414 buf += len; 415 buf_len -= len; 416 len = qdf_scnprintf(buf, buf_len, 417 "---------------------------------\n"); 418 buf += len; 419 buf_len -= len; 420 421 for (i = 0; i < WLAN_TDLS_PEER_LIST_SIZE; i++) { 422 head = &tdls_vdev->peer_list[i]; 423 status = qdf_list_peek_front(head, &p_node); 424 while (QDF_IS_STATUS_SUCCESS(status)) { 425 curr_peer = qdf_container_of(p_node, 426 struct tdls_peer, node); 427 if (buf_len < 32 + 1) 428 break; 429 len = qdf_scnprintf(buf, buf_len, 430 QDF_MAC_ADDR_FMT "%4s%3s%5d\n", 431 QDF_MAC_ADDR_REF(curr_peer->peer_mac.bytes), 432 (curr_peer->tdls_support == 433 TDLS_CAP_SUPPORTED) ? "Y" : "N", 434 TDLS_IS_LINK_CONNECTED(curr_peer) ? "Y" : 435 "N", curr_peer->rssi); 436 buf += len; 437 buf_len -= len; 438 status = qdf_list_peek_next(head, p_node, &p_node); 439 } 440 } 441 442 tdls_notice("Exit "); 443 return init_len - buf_len; 444 } 445 446 /** 447 * tdls_get_all_peers_from_list() - get all the tdls peers from the list 448 * @get_tdls_peers: get_tdls_peers object 449 * 450 * Return: None 451 */ 452 static void tdls_get_all_peers_from_list( 453 struct tdls_get_all_peers *get_tdls_peers) 454 { 455 int32_t len; 456 struct tdls_soc_priv_obj *tdls_soc_obj; 457 struct tdls_osif_indication indication; 458 459 if (!get_tdls_peers->vdev) { 460 qdf_mem_free(get_tdls_peers); 461 return; 462 } 463 len = __tdls_get_all_peers_from_list(get_tdls_peers); 464 465 indication.status = len; 466 indication.vdev = get_tdls_peers->vdev; 467 468 tdls_soc_obj = wlan_vdev_get_tdls_soc_obj(get_tdls_peers->vdev); 469 if (tdls_soc_obj && tdls_soc_obj->tdls_event_cb) 470 tdls_soc_obj->tdls_event_cb(tdls_soc_obj->tdls_evt_cb_data, 471 TDLS_EVENT_USER_CMD, &indication); 472 473 qdf_mem_free(get_tdls_peers); 474 } 475 476 /** 477 * tdls_process_reset_all_peers() - Reset all tdls peers 478 * @vdev: vdev object 479 * 480 * This function is called to reset all tdls peers and 481 * notify upper layers of teardown inidcation 482 * 483 * Return: QDF_STATUS 484 */ 485 486 static QDF_STATUS tdls_process_reset_all_peers(struct wlan_objmgr_vdev *vdev) 487 { 488 QDF_STATUS status = QDF_STATUS_SUCCESS; 489 uint8_t staidx; 490 struct tdls_peer *curr_peer = NULL; 491 struct tdls_vdev_priv_obj *tdls_vdev; 492 struct tdls_soc_priv_obj *tdls_soc; 493 uint8_t reset_session_id; 494 495 status = tdls_get_vdev_objects(vdev, &tdls_vdev, &tdls_soc); 496 if (QDF_STATUS_SUCCESS != status) { 497 tdls_err("tdls objects are NULL "); 498 return status; 499 } 500 501 reset_session_id = tdls_vdev->session_id; 502 for (staidx = 0; staidx < tdls_soc->max_num_tdls_sta; 503 staidx++) { 504 if (!tdls_soc->tdls_conn_info[staidx].valid_entry) 505 continue; 506 if (tdls_soc->tdls_conn_info[staidx].session_id != 507 reset_session_id) 508 continue; 509 510 curr_peer = 511 tdls_find_all_peer(tdls_soc, 512 tdls_soc->tdls_conn_info[staidx]. 513 peer_mac.bytes); 514 if (!curr_peer) 515 continue; 516 517 tdls_notice("indicate TDLS teardown "QDF_MAC_ADDR_FMT, 518 QDF_MAC_ADDR_REF(curr_peer->peer_mac.bytes)); 519 520 /* Indicate teardown to supplicant */ 521 tdls_indicate_teardown(tdls_vdev, 522 curr_peer, 523 TDLS_TEARDOWN_PEER_UNSPEC_REASON); 524 525 tdls_reset_peer(tdls_vdev, curr_peer->peer_mac.bytes); 526 527 tdls_decrement_peer_count(vdev, tdls_soc); 528 tdls_soc->tdls_conn_info[staidx].valid_entry = false; 529 tdls_soc->tdls_conn_info[staidx].session_id = 255; 530 tdls_soc->tdls_conn_info[staidx].index = 531 INVALID_TDLS_PEER_INDEX; 532 533 qdf_mem_zero(&tdls_soc->tdls_conn_info[staidx].peer_mac, 534 sizeof(struct qdf_mac_addr)); 535 } 536 return status; 537 } 538 539 /** 540 * tdls_reset_all_peers() - Reset all tdls peers 541 * @delete_all_peers_ind: Delete all peers indication 542 * 543 * This function is called to reset all tdls peers and 544 * notify upper layers of teardown inidcation 545 * 546 * Return: QDF_STATUS 547 */ 548 static QDF_STATUS tdls_reset_all_peers( 549 struct tdls_delete_all_peers_params *delete_all_peers_ind) 550 { 551 QDF_STATUS status; 552 553 if (!delete_all_peers_ind || !delete_all_peers_ind->vdev) { 554 tdls_err("invalid param"); 555 qdf_mem_free(delete_all_peers_ind); 556 return QDF_STATUS_E_INVAL; 557 } 558 559 status = tdls_process_reset_all_peers(delete_all_peers_ind->vdev); 560 561 wlan_objmgr_vdev_release_ref(delete_all_peers_ind->vdev, 562 WLAN_TDLS_SB_ID); 563 qdf_mem_free(delete_all_peers_ind); 564 565 return status; 566 } 567 568 #ifdef WLAN_FEATURE_TDLS_CONCURRENCIES 569 QDF_STATUS tdls_handle_start_bss(struct wlan_objmgr_psoc *psoc) 570 { 571 struct wlan_objmgr_vdev *tdls_vdev; 572 573 tdls_vdev = tdls_get_vdev(psoc, WLAN_TDLS_NB_ID); 574 if (!tdls_vdev) { 575 tdls_err("Unable get the tdls vdev"); 576 return QDF_STATUS_E_FAILURE; 577 } 578 579 tdls_set_tdls_offchannelmode(tdls_vdev, DISABLE_ACTIVE_CHANSWITCH); 580 wlan_objmgr_vdev_release_ref(tdls_vdev, WLAN_TDLS_NB_ID); 581 582 return QDF_STATUS_SUCCESS; 583 } 584 #endif 585 586 static void tdls_handle_link_unforce(struct wlan_objmgr_vdev *vdev) 587 { 588 struct tdls_action_frame_request req = {0}; 589 590 req.vdev = vdev; 591 req.tdls_mgmt.frame_type = TDLS_MAX_ACTION_CODE; 592 593 tdls_debug("set vdev %d unforce", wlan_vdev_get_id(vdev)); 594 tdls_set_link_mode(&req); 595 } 596 597 QDF_STATUS tdls_process_cmd(struct scheduler_msg *msg) 598 { 599 QDF_STATUS status = QDF_STATUS_SUCCESS; 600 601 if (!msg || !msg->bodyptr) { 602 tdls_err("msg: 0x%pK", msg); 603 QDF_ASSERT(0); 604 return QDF_STATUS_E_NULL_VALUE; 605 } 606 tdls_debug("TDLS process command: %s(%d)", 607 tdls_get_cmd_type_str(msg->type), msg->type); 608 609 switch (msg->type) { 610 case TDLS_CMD_TX_ACTION: 611 tdls_process_mgmt_req(msg->bodyptr); 612 break; 613 case TDLS_CMD_ADD_STA: 614 tdls_process_add_peer(msg->bodyptr); 615 break; 616 case TDLS_CMD_CHANGE_STA: 617 tdls_process_update_peer(msg->bodyptr); 618 break; 619 case TDLS_CMD_ENABLE_LINK: 620 tdls_process_enable_link(msg->bodyptr); 621 break; 622 case TDLS_CMD_DISABLE_LINK: 623 tdls_process_del_peer(msg->bodyptr); 624 break; 625 case TDLS_CMD_CONFIG_FORCE_PEER: 626 tdls_process_setup_peer(msg->bodyptr); 627 break; 628 case TDLS_CMD_REMOVE_FORCE_PEER: 629 tdls_process_remove_force_peer(msg->bodyptr); 630 break; 631 case TDLS_CMD_STATS_UPDATE: 632 break; 633 case TDLS_CMD_CONFIG_UPDATE: 634 break; 635 case TDLS_CMD_SET_RESPONDER: 636 tdls_set_responder(msg->bodyptr); 637 break; 638 case TDLS_CMD_SCAN_DONE: 639 tdls_scan_done_callback(msg->bodyptr); 640 break; 641 case TDLS_NOTIFY_STA_CONNECTION: 642 tdls_notify_sta_connect(msg->bodyptr); 643 break; 644 case TDLS_NOTIFY_STA_DISCONNECTION: 645 tdls_notify_sta_disconnect(msg->bodyptr); 646 break; 647 case TDLS_CMD_SET_TDLS_MODE: 648 tdls_set_operation_mode(msg->bodyptr); 649 break; 650 case TDLS_CMD_SESSION_DECREMENT: 651 tdls_process_decrement_active_session(msg->bodyptr); 652 break; 653 case TDLS_CMD_SESSION_INCREMENT: 654 tdls_process_policy_mgr_notification(msg->bodyptr); 655 break; 656 case TDLS_CMD_TEARDOWN_LINKS: 657 tdls_teardown_connections(msg->bodyptr); 658 break; 659 case TDLS_NOTIFY_RESET_ADAPTERS: 660 tdls_notify_reset_adapter(msg->bodyptr); 661 break; 662 case TDLS_CMD_ANTENNA_SWITCH: 663 tdls_process_antenna_switch(msg->bodyptr); 664 break; 665 case TDLS_CMD_GET_ALL_PEERS: 666 tdls_get_all_peers_from_list(msg->bodyptr); 667 break; 668 case TDLS_CMD_SET_OFFCHANNEL: 669 tdls_process_set_offchannel(msg->bodyptr); 670 break; 671 case TDLS_CMD_SET_OFFCHANMODE: 672 tdls_process_set_offchan_mode(msg->bodyptr); 673 break; 674 case TDLS_CMD_SET_SECOFFCHANOFFSET: 675 tdls_process_set_secoffchanneloffset(msg->bodyptr); 676 break; 677 case TDLS_DELETE_ALL_PEERS_INDICATION: 678 tdls_reset_all_peers(msg->bodyptr); 679 break; 680 case TDLS_CMD_START_BSS: 681 tdls_handle_start_bss(msg->bodyptr); 682 break; 683 case TDLS_CMD_SET_LINK_UNFORCE: 684 tdls_handle_link_unforce(msg->bodyptr); 685 break; 686 default: 687 break; 688 } 689 690 return status; 691 } 692 693 QDF_STATUS tdls_process_evt(struct scheduler_msg *msg) 694 { 695 struct wlan_objmgr_vdev *vdev; 696 struct tdls_event_notify *notify; 697 struct tdls_event_info *event; 698 699 if (!msg || !msg->bodyptr) { 700 tdls_err("msg is not valid: %pK", msg); 701 return QDF_STATUS_E_NULL_VALUE; 702 } 703 notify = msg->bodyptr; 704 vdev = notify->vdev; 705 if (!vdev) { 706 tdls_err("NULL vdev object"); 707 qdf_mem_free(notify); 708 return QDF_STATUS_E_NULL_VALUE; 709 } 710 event = ¬ify->event; 711 712 tdls_debug("evt type: %s(%d)", 713 tdls_get_event_type_str(event->message_type), 714 event->message_type); 715 716 switch (event->message_type) { 717 case TDLS_SHOULD_DISCOVER: 718 tdls_process_should_discover(vdev, event); 719 break; 720 case TDLS_SHOULD_TEARDOWN: 721 case TDLS_PEER_DISCONNECTED: 722 tdls_process_should_teardown(vdev, event); 723 break; 724 case TDLS_CONNECTION_TRACKER_NOTIFY: 725 tdls_process_connection_tracker_notify(vdev, event); 726 break; 727 default: 728 break; 729 } 730 731 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_SB_ID); 732 qdf_mem_free(notify); 733 734 return QDF_STATUS_SUCCESS; 735 } 736 737 void tdls_timer_restart(struct wlan_objmgr_vdev *vdev, 738 qdf_mc_timer_t *timer, 739 uint32_t expiration_time) 740 { 741 if (QDF_TIMER_STATE_RUNNING != 742 qdf_mc_timer_get_current_state(timer)) 743 qdf_mc_timer_start(timer, expiration_time); 744 } 745 746 /** 747 * tdls_monitor_timers_stop() - stop all monitoring timers 748 * @tdls_vdev: TDLS vdev object 749 * 750 * Return: none 751 */ 752 static void tdls_monitor_timers_stop(struct tdls_vdev_priv_obj *tdls_vdev) 753 { 754 if (!wlan_vdev_mlme_is_mlo_vdev(tdls_vdev->vdev)) 755 qdf_mc_timer_stop(&tdls_vdev->peer_discovery_timer); 756 } 757 758 /** 759 * tdls_peer_idle_timers_stop() - stop peer idle timers 760 * @tdls_vdev: TDLS vdev object 761 * 762 * Loop through the idle peer list and stop their timers 763 * 764 * Return: None 765 */ 766 static void tdls_peer_idle_timers_stop(struct tdls_vdev_priv_obj *tdls_vdev) 767 { 768 int i; 769 qdf_list_t *head; 770 qdf_list_node_t *p_node; 771 struct tdls_peer *curr_peer; 772 QDF_STATUS status; 773 774 tdls_vdev->discovery_peer_cnt = 0; 775 776 for (i = 0; i < WLAN_TDLS_PEER_LIST_SIZE; i++) { 777 head = &tdls_vdev->peer_list[i]; 778 status = qdf_list_peek_front(head, &p_node); 779 while (QDF_IS_STATUS_SUCCESS(status)) { 780 curr_peer = qdf_container_of(p_node, struct tdls_peer, 781 node); 782 if (curr_peer->is_peer_idle_timer_initialised) 783 qdf_mc_timer_stop(&curr_peer->peer_idle_timer); 784 status = qdf_list_peek_next(head, p_node, &p_node); 785 } 786 } 787 788 } 789 790 /** 791 * tdls_ct_timers_stop() - stop tdls connection tracker timers 792 * @tdls_vdev: TDLS vdev 793 * 794 * Return: None 795 */ 796 static void tdls_ct_timers_stop(struct tdls_vdev_priv_obj *tdls_vdev) 797 { 798 qdf_mc_timer_stop(&tdls_vdev->peer_update_timer); 799 tdls_peer_idle_timers_stop(tdls_vdev); 800 } 801 802 /** 803 * tdls_timers_stop() - stop all the tdls timers running 804 * @tdls_vdev: TDLS vdev 805 * 806 * Return: none 807 */ 808 void tdls_timers_stop(struct tdls_vdev_priv_obj *tdls_vdev) 809 { 810 tdls_monitor_timers_stop(tdls_vdev); 811 tdls_ct_timers_stop(tdls_vdev); 812 } 813 814 QDF_STATUS tdls_get_vdev_objects(struct wlan_objmgr_vdev *vdev, 815 struct tdls_vdev_priv_obj **tdls_vdev_obj, 816 struct tdls_soc_priv_obj **tdls_soc_obj) 817 { 818 enum QDF_OPMODE device_mode; 819 820 if (!vdev) 821 return QDF_STATUS_E_FAILURE; 822 823 *tdls_vdev_obj = wlan_vdev_get_tdls_vdev_obj(vdev); 824 if (NULL == (*tdls_vdev_obj)) 825 return QDF_STATUS_E_FAILURE; 826 827 *tdls_soc_obj = wlan_vdev_get_tdls_soc_obj(vdev); 828 if (NULL == (*tdls_soc_obj)) 829 return QDF_STATUS_E_FAILURE; 830 831 device_mode = wlan_vdev_mlme_get_opmode(vdev); 832 833 if (device_mode != QDF_STA_MODE && 834 device_mode != QDF_P2P_CLIENT_MODE) 835 return QDF_STATUS_E_FAILURE; 836 837 return QDF_STATUS_SUCCESS; 838 } 839 840 #ifdef WLAN_FEATURE_11AX 841 uint32_t tdls_get_6g_pwr_for_power_type(struct wlan_objmgr_vdev *vdev, 842 qdf_freq_t freq, 843 enum supported_6g_pwr_types pwr_typ) 844 { 845 struct wlan_objmgr_pdev *pdev = wlan_vdev_get_pdev(vdev); 846 struct regulatory_channel *chan; 847 uint8_t chn_idx, num_chan; 848 uint8_t band_mask = BIT(REG_BAND_6G); 849 uint32_t tx_power = 0; 850 851 if (!pdev) 852 return 0; 853 854 /* No power check is required for non 6 Ghz channel */ 855 if (!wlan_reg_is_6ghz_chan_freq(freq)) 856 return 0; 857 858 chan = qdf_mem_malloc(sizeof(struct regulatory_channel) * NUM_CHANNELS); 859 if (!chan) 860 return 0; 861 862 num_chan = wlan_reg_get_band_channel_list_for_pwrmode(pdev, 863 band_mask, 864 chan, 865 REG_CLI_DEF_VLP); 866 867 for (chn_idx = 0; chn_idx < num_chan; chn_idx++) { 868 if (chan[chn_idx].center_freq == freq) { 869 tdls_debug("VLP power for channel %d is %d", 870 chan[chn_idx].center_freq, 871 chan[chn_idx].tx_power); 872 tx_power = chan[chn_idx].tx_power; 873 } 874 } 875 876 qdf_mem_free(chan); 877 return tx_power; 878 } 879 880 bool tdls_is_6g_freq_allowed(struct wlan_objmgr_vdev *vdev, 881 qdf_freq_t freq) 882 { 883 struct wlan_objmgr_pdev *pdev = wlan_vdev_get_pdev(vdev); 884 struct regulatory_channel *chan; 885 bool is_allowed = false; 886 uint8_t country_code[REG_ALPHA2_LEN + 1]; 887 uint8_t chn_idx, num_chan = 0; 888 uint8_t band_mask = BIT(REG_BAND_6G); 889 890 /* Return if freq is not 6 Ghz freq */ 891 if (!wlan_reg_is_6ghz_chan_freq(freq)) 892 return false; 893 894 if (!wlan_cfg80211_tdls_is_fw_6ghz_capable(vdev)) 895 return false; 896 897 if (!pdev) 898 return false; 899 900 wlan_cm_get_country_code(pdev, wlan_vdev_get_id(vdev), country_code); 901 if (!wlan_reg_ctry_support_vlp(country_code)) 902 return false; 903 904 chan = qdf_mem_malloc(sizeof(struct regulatory_channel) * NUM_CHANNELS); 905 if (!chan) 906 return false; 907 908 num_chan = wlan_reg_get_band_channel_list_for_pwrmode(pdev, 909 band_mask, 910 chan, 911 REG_CLI_DEF_VLP); 912 tdls_debug("Country IE:%c%c freq %d num_chan %d", country_code[0], 913 country_code[1], freq, num_chan); 914 if (!num_chan) 915 goto error; 916 917 for (chn_idx = 0; chn_idx < num_chan; chn_idx++) { 918 if (chan[chn_idx].center_freq == freq) { 919 tdls_debug("TDLS 6ghz freq: %d supports VLP power", 920 chan[chn_idx].center_freq); 921 is_allowed = true; 922 break; 923 } 924 } 925 926 error: 927 qdf_mem_free(chan); 928 return is_allowed; 929 } 930 #else 931 bool tdls_is_6g_freq_allowed(struct wlan_objmgr_vdev *vdev, 932 qdf_freq_t freq) 933 { 934 return false; 935 } 936 937 uint32_t tdls_get_6g_pwr_for_power_type(struct wlan_objmgr_vdev *vdev, 938 qdf_freq_t freq, 939 enum supported_6g_pwr_types pwr_typ) 940 { 941 return 0; 942 } 943 #endif 944 945 bool tdls_check_is_user_tdls_enable(struct tdls_soc_priv_obj *tdls_soc_obj) 946 { 947 return tdls_soc_obj->is_user_tdls_enable; 948 } 949 950 bool tdls_check_is_tdls_allowed(struct wlan_objmgr_vdev *vdev) 951 { 952 struct tdls_vdev_priv_obj *tdls_vdev_obj; 953 struct tdls_soc_priv_obj *tdls_soc_obj; 954 bool state = false; 955 qdf_freq_t ch_freq; 956 QDF_STATUS status; 957 uint32_t connection_count; 958 uint8_t sta_count, p2p_cli_count; 959 960 status = wlan_objmgr_vdev_try_get_ref(vdev, WLAN_TDLS_NB_ID); 961 if (QDF_IS_STATUS_ERROR(status)) 962 return state; 963 964 status = tdls_get_vdev_objects(vdev, &tdls_vdev_obj, &tdls_soc_obj); 965 if (QDF_IS_STATUS_ERROR(status)) { 966 tdls_err("Failed to get TDLS objects"); 967 goto exit; 968 } 969 970 if (wlan_vdev_mlme_is_mlo_vdev(vdev) && 971 !wlan_tdls_is_fw_11be_mlo_capable(tdls_soc_obj->soc)) { 972 tdls_debug("TDLS not supported on MLO vdev"); 973 goto exit; 974 } 975 976 if (wlan_nan_is_disc_active(tdls_soc_obj->soc)) { 977 tdls_err("NAN active. NAN+TDLS not supported"); 978 goto exit; 979 } 980 981 if (!tdls_check_is_user_tdls_enable(tdls_soc_obj)) { 982 tdls_err("TDLS Disabled from userspace"); 983 goto exit; 984 } 985 986 connection_count = 987 policy_mgr_get_connection_count_with_mlo(tdls_soc_obj->soc); 988 sta_count = 989 policy_mgr_mode_specific_connection_count(tdls_soc_obj->soc, 990 PM_STA_MODE, NULL); 991 p2p_cli_count = 992 policy_mgr_mode_specific_connection_count(tdls_soc_obj->soc, 993 PM_P2P_CLIENT_MODE, 994 NULL); 995 if ((connection_count == 1 && (sta_count || p2p_cli_count)) || 996 (connection_count > 1 && 997 tdls_is_concurrency_allowed(tdls_soc_obj->soc))) { 998 state = true; 999 } else { 1000 tdls_warn("vdev:%d Concurrent sessions exist disable TDLS", 1001 wlan_vdev_get_id(vdev)); 1002 state = false; 1003 goto exit; 1004 } 1005 1006 if (wlan_vdev_mlme_get_opmode(vdev) == QDF_P2P_CLIENT_MODE && sta_count) { 1007 tdls_warn("vdev:%d Concurrent STA exists. TDLS not allowed for P2P vdev", 1008 wlan_vdev_get_id(vdev)); 1009 state = false; 1010 goto exit; 1011 } 1012 1013 ch_freq = wlan_get_operation_chan_freq(vdev); 1014 if (wlan_reg_is_6ghz_chan_freq(ch_freq) && 1015 !tdls_is_6g_freq_allowed(vdev, ch_freq)) { 1016 tdls_debug("6GHz freq:%d not allowed for TDLS", ch_freq); 1017 state = false; 1018 } 1019 1020 exit: 1021 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); 1022 1023 return state; 1024 } 1025 1026 #ifdef WLAN_FEATURE_TDLS_CONCURRENCIES 1027 bool tdls_is_concurrency_allowed(struct wlan_objmgr_psoc *psoc) 1028 { 1029 if (!wlan_psoc_nif_fw_ext2_cap_get(psoc, 1030 WLAN_TDLS_CONCURRENCIES_SUPPORT)) { 1031 tdls_debug("fw cap is not advertised"); 1032 return false; 1033 } 1034 1035 if (policy_mgr_get_connection_count_with_mlo(psoc) > 1036 WLAN_TDLS_MAX_CONCURRENT_VDEV_SUPPORTED) 1037 return false; 1038 1039 if (policy_mgr_mode_specific_connection_count(psoc, PM_STA_MODE, 1040 NULL) > 1) { 1041 tdls_debug("More than one STA exist. Don't allow TDLS"); 1042 return false; 1043 } 1044 1045 if (policy_mgr_is_mcc_on_any_sta_vdev(psoc)) { 1046 tdls_debug("Base channel MCC. Don't allow TDLS"); 1047 return false; 1048 } 1049 1050 /* 1051 * Don't enable TDLS for P2P_CLI in concurrency cases 1052 */ 1053 if (policy_mgr_get_connection_count_with_mlo(psoc) > 1 && 1054 !policy_mgr_mode_specific_connection_count(psoc, PM_STA_MODE, 1055 NULL)) 1056 return false; 1057 1058 return true; 1059 } 1060 #endif 1061 1062 void tdls_set_ct_mode(struct wlan_objmgr_psoc *psoc, 1063 struct wlan_objmgr_vdev *vdev) 1064 { 1065 struct tdls_soc_priv_obj *tdls_soc_obj; 1066 struct tdls_vdev_priv_obj *tdls_vdev_obj; 1067 uint32_t tdls_feature_flags = 0, sta_count, p2p_count; 1068 bool state = false; 1069 bool tdls_mlo; 1070 QDF_STATUS status; 1071 1072 if (!tdls_check_is_tdls_allowed(vdev)) 1073 return; 1074 1075 status = tdls_get_vdev_objects(vdev, &tdls_vdev_obj, &tdls_soc_obj); 1076 if (QDF_IS_STATUS_ERROR(status)) { 1077 tdls_err("Failed to get TDLS objects"); 1078 return; 1079 } 1080 1081 qdf_atomic_set(&tdls_soc_obj->timer_cnt, 0); 1082 tdls_feature_flags = tdls_soc_obj->tdls_configs.tdls_feature_flags; 1083 if (TDLS_SUPPORT_DISABLED == tdls_soc_obj->tdls_current_mode || 1084 TDLS_SUPPORT_SUSPENDED == tdls_soc_obj->tdls_current_mode || 1085 !TDLS_IS_IMPLICIT_TRIG_ENABLED(tdls_feature_flags)) { 1086 state = false; 1087 goto set_state; 1088 } 1089 1090 sta_count = policy_mgr_mode_specific_connection_count(psoc, PM_STA_MODE, 1091 NULL); 1092 p2p_count = 1093 policy_mgr_mode_specific_connection_count(psoc, 1094 PM_P2P_CLIENT_MODE, 1095 NULL); 1096 tdls_mlo = wlan_tdls_is_fw_11be_mlo_capable(psoc); 1097 if (sta_count == 1 || (sta_count >= 2 && tdls_mlo) || 1098 (policy_mgr_get_connection_count_with_mlo(psoc) == 1 && 1099 p2p_count == 1)) { 1100 state = true; 1101 /* 1102 * In case of TDLS external control, peer should be added 1103 * by the user space to start connection tracker. 1104 */ 1105 if (TDLS_IS_EXTERNAL_CONTROL_ENABLED(tdls_feature_flags) && 1106 !tdls_soc_obj->tdls_external_peer_count) 1107 state = false; 1108 1109 goto set_state; 1110 } 1111 1112 state = false; 1113 1114 set_state: 1115 tdls_soc_obj->enable_tdls_connection_tracker = state; 1116 if (tdls_soc_obj->enable_tdls_connection_tracker) 1117 tdls_implicit_enable(tdls_vdev_obj); 1118 else 1119 tdls_implicit_disable(tdls_vdev_obj); 1120 1121 tdls_debug("vdev:%d enable_tdls_connection_tracker %d current_mode:%d feature_flags:0x%x", 1122 wlan_vdev_get_id(vdev), 1123 tdls_soc_obj->enable_tdls_connection_tracker, 1124 tdls_soc_obj->tdls_current_mode, tdls_feature_flags); 1125 } 1126 1127 void tdls_set_user_tdls_enable(struct wlan_objmgr_vdev *vdev, 1128 bool is_user_tdls_enable) 1129 { 1130 QDF_STATUS status; 1131 struct tdls_vdev_priv_obj *tdls_vdev_obj; 1132 struct tdls_soc_priv_obj *tdls_soc_obj; 1133 1134 status = wlan_objmgr_vdev_try_get_ref(vdev, WLAN_TDLS_NB_ID); 1135 if (QDF_IS_STATUS_ERROR(status)) 1136 return; 1137 1138 status = tdls_get_vdev_objects(vdev, &tdls_vdev_obj, &tdls_soc_obj); 1139 if (QDF_IS_STATUS_ERROR(status)) { 1140 tdls_err("Failed to get TDLS objects"); 1141 goto exit; 1142 } 1143 1144 tdls_soc_obj->is_user_tdls_enable = is_user_tdls_enable; 1145 tdls_debug("TDLS enable:%d via userspace", 1146 tdls_soc_obj->is_user_tdls_enable); 1147 1148 exit: 1149 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); 1150 } 1151 1152 QDF_STATUS 1153 tdls_process_policy_mgr_notification(struct wlan_objmgr_psoc *psoc) 1154 { 1155 struct wlan_objmgr_vdev *tdls_vdev; 1156 struct tdls_vdev_priv_obj *tdls_priv_vdev; 1157 struct tdls_soc_priv_obj *tdls_priv_soc; 1158 QDF_STATUS status; 1159 1160 if (!psoc) { 1161 tdls_err("psoc is NULL"); 1162 return QDF_STATUS_E_NULL_VALUE; 1163 } 1164 1165 tdls_vdev = tdls_get_vdev(psoc, WLAN_TDLS_NB_ID); 1166 if (!tdls_vdev) { 1167 tdls_debug("No TDLS vdev"); 1168 return QDF_STATUS_E_NULL_VALUE; 1169 } 1170 1171 status = tdls_get_vdev_objects(tdls_vdev, &tdls_priv_vdev, 1172 &tdls_priv_soc); 1173 if (QDF_IS_STATUS_ERROR(status)) { 1174 tdls_debug("TDLS vdev objects NULL"); 1175 wlan_objmgr_vdev_release_ref(tdls_vdev, WLAN_TDLS_NB_ID); 1176 return QDF_STATUS_E_NULL_VALUE; 1177 } 1178 1179 if (!tdls_check_is_tdls_allowed(tdls_vdev)) { 1180 tdls_disable_offchan_and_teardown_links(tdls_vdev); 1181 tdls_debug("Disable the tdls in FW due to concurrency"); 1182 wlan_objmgr_vdev_release_ref(tdls_vdev, WLAN_TDLS_NB_ID); 1183 return QDF_STATUS_E_NULL_VALUE; 1184 } 1185 1186 tdls_debug("vdev:%d enter", wlan_vdev_get_id(tdls_vdev)); 1187 1188 tdls_set_tdls_offchannelmode(tdls_vdev, ENABLE_CHANSWITCH); 1189 tdls_set_ct_mode(psoc, tdls_vdev); 1190 1191 wlan_objmgr_vdev_release_ref(tdls_vdev, WLAN_TDLS_NB_ID); 1192 tdls_debug("exit "); 1193 1194 return QDF_STATUS_SUCCESS; 1195 } 1196 1197 QDF_STATUS 1198 tdls_process_decrement_active_session(struct wlan_objmgr_psoc *psoc) 1199 { 1200 struct tdls_soc_priv_obj *tdls_priv_soc; 1201 struct tdls_vdev_priv_obj *tdls_priv_vdev; 1202 struct wlan_objmgr_vdev *tdls_obj_vdev; 1203 uint8_t vdev_id; 1204 QDF_STATUS status; 1205 1206 tdls_debug("Enter"); 1207 if (!psoc) 1208 return QDF_STATUS_E_NULL_VALUE; 1209 1210 if(!policy_mgr_is_hw_dbs_2x2_capable(psoc) && 1211 !policy_mgr_is_hw_dbs_required_for_band(psoc, HW_MODE_MAC_BAND_2G) && 1212 policy_mgr_is_current_hwmode_dbs(psoc)) { 1213 tdls_debug("Current HW mode is 1*1 DBS. Wait for Opportunistic timer to expire to enable TDLS in FW"); 1214 return QDF_STATUS_SUCCESS; 1215 } 1216 1217 tdls_obj_vdev = tdls_get_vdev(psoc, WLAN_TDLS_NB_ID); 1218 if (!tdls_obj_vdev) 1219 return QDF_STATUS_E_FAILURE; 1220 1221 if (!tdls_check_is_tdls_allowed(tdls_obj_vdev)) 1222 goto release_ref; 1223 1224 /* 1225 * 2 Port MCC -> 1 port scenario or 1226 * 3 Port MCC -> 2 port SCC scenario or 1227 * 4 Port -> 3 Port SCC scenario 1228 * So enable TDLS in firmware 1229 */ 1230 tdls_debug("Enable TDLS in FW and host as active sta/p2p_cli interface is present"); 1231 vdev_id = wlan_vdev_get_id(tdls_obj_vdev); 1232 status = tdls_get_vdev_objects(tdls_obj_vdev, &tdls_priv_vdev, 1233 &tdls_priv_soc); 1234 if (QDF_IS_STATUS_ERROR(status)) 1235 goto release_ref; 1236 1237 tdls_send_update_to_fw(tdls_priv_vdev, tdls_priv_soc, 1238 mlme_get_tdls_prohibited(tdls_obj_vdev), 1239 mlme_get_tdls_chan_switch_prohibited(tdls_obj_vdev), 1240 true, vdev_id); 1241 if (tdls_priv_soc->connected_peer_count == 1) 1242 tdls_set_tdls_offchannelmode(tdls_obj_vdev, ENABLE_CHANSWITCH); 1243 1244 release_ref: 1245 wlan_objmgr_vdev_release_ref(tdls_obj_vdev, WLAN_TDLS_NB_ID); 1246 1247 return QDF_STATUS_SUCCESS; 1248 } 1249 1250 #ifdef WLAN_FEATURE_11BE_MLO 1251 struct wlan_objmgr_vdev *wlan_tdls_get_mlo_vdev(struct wlan_objmgr_vdev *vdev, 1252 uint8_t index, 1253 wlan_objmgr_ref_dbgid dbg_id) 1254 { 1255 struct wlan_mlo_dev_context *mlo_dev_ctx; 1256 struct wlan_objmgr_vdev *mlo_vdev; 1257 1258 if (!vdev) 1259 return NULL; 1260 1261 mlo_dev_ctx = vdev->mlo_dev_ctx; 1262 if (!mlo_dev_ctx) 1263 return NULL; 1264 1265 mlo_vdev = mlo_dev_ctx->wlan_vdev_list[index]; 1266 if (mlo_vdev && 1267 wlan_objmgr_vdev_try_get_ref(mlo_vdev, dbg_id) == 1268 QDF_STATUS_SUCCESS) 1269 return mlo_vdev; 1270 1271 return NULL; 1272 } 1273 1274 void wlan_tdls_release_mlo_vdev(struct wlan_objmgr_vdev *vdev, 1275 wlan_objmgr_ref_dbgid dbg_id) 1276 { 1277 if (!vdev) 1278 return; 1279 1280 wlan_objmgr_vdev_release_ref(vdev, dbg_id); 1281 } 1282 #else 1283 struct wlan_objmgr_vdev *wlan_tdls_get_mlo_vdev(struct wlan_objmgr_vdev *vdev, 1284 uint8_t index, 1285 wlan_objmgr_ref_dbgid dbg_id) 1286 { 1287 return NULL; 1288 } 1289 1290 void wlan_tdls_release_mlo_vdev(struct wlan_objmgr_vdev *vdev, 1291 wlan_objmgr_ref_dbgid dbg_id) 1292 { 1293 } 1294 #endif 1295 /** 1296 * tdls_get_vdev() - Get tdls specific vdev object manager 1297 * @psoc: wlan psoc object manager 1298 * @dbg_id: debug id 1299 * 1300 * If TDLS possible, return the corresponding vdev 1301 * to enable TDLS in the system. 1302 * 1303 * Return: vdev manager pointer or NULL. 1304 */ 1305 struct wlan_objmgr_vdev *tdls_get_vdev(struct wlan_objmgr_psoc *psoc, 1306 wlan_objmgr_ref_dbgid dbg_id) 1307 { 1308 uint32_t vdev_id; 1309 1310 vdev_id = policy_mgr_mode_specific_vdev_id(psoc, PM_STA_MODE); 1311 if (WLAN_INVALID_VDEV_ID != vdev_id) 1312 return wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id, 1313 dbg_id); 1314 /* 1315 * For P2P_Client mode, TDLS is not supported on concurrency 1316 * so return P2P_client vdev only if P2P client mode exists without 1317 * any concurreny 1318 */ 1319 vdev_id = policy_mgr_mode_specific_vdev_id(psoc, PM_P2P_CLIENT_MODE); 1320 if (WLAN_INVALID_VDEV_ID != vdev_id && 1321 policy_mgr_get_connection_count_with_mlo(psoc) == 1) 1322 return wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id, 1323 dbg_id); 1324 1325 return NULL; 1326 } 1327 1328 static QDF_STATUS tdls_post_msg_flush_cb(struct scheduler_msg *msg) 1329 { 1330 void *ptr = msg->bodyptr; 1331 struct wlan_objmgr_vdev *vdev = NULL; 1332 1333 switch (msg->type) { 1334 case TDLS_NOTIFY_STA_DISCONNECTION: 1335 vdev = ((struct tdls_sta_notify_params *)ptr)->vdev; 1336 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); 1337 qdf_mem_free(ptr); 1338 break; 1339 1340 case TDLS_DELETE_ALL_PEERS_INDICATION: 1341 vdev = ((struct tdls_delete_all_peers_params *)ptr)->vdev; 1342 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_SB_ID); 1343 qdf_mem_free(ptr); 1344 break; 1345 1346 case TDLS_CMD_SCAN_DONE: 1347 case TDLS_CMD_SESSION_INCREMENT: 1348 case TDLS_CMD_SESSION_DECREMENT: 1349 break; 1350 } 1351 1352 return QDF_STATUS_SUCCESS; 1353 } 1354 1355 /** 1356 * tdls_process_session_update() - update session count information 1357 * @psoc: soc object 1358 * @cmd_type: type of command 1359 * 1360 * update the session information in connection tracker 1361 * 1362 * Return: None 1363 */ 1364 static void tdls_process_session_update(struct wlan_objmgr_psoc *psoc, 1365 enum tdls_command_type cmd_type) 1366 { 1367 struct scheduler_msg msg = {0}; 1368 QDF_STATUS status; 1369 1370 msg.bodyptr = psoc; 1371 msg.callback = tdls_process_cmd; 1372 msg.flush_callback = tdls_post_msg_flush_cb; 1373 msg.type = (uint16_t)cmd_type; 1374 1375 status = scheduler_post_message(QDF_MODULE_ID_TDLS, 1376 QDF_MODULE_ID_TDLS, 1377 QDF_MODULE_ID_OS_IF, &msg); 1378 if (QDF_IS_STATUS_ERROR(status)) 1379 tdls_alert("message post failed "); 1380 } 1381 1382 void tdls_notify_increment_session(struct wlan_objmgr_psoc *psoc) 1383 { 1384 tdls_process_session_update(psoc, TDLS_CMD_SESSION_INCREMENT); 1385 } 1386 1387 void tdls_notify_decrement_session(struct wlan_objmgr_psoc *psoc) 1388 { 1389 tdls_process_session_update(psoc, TDLS_CMD_SESSION_DECREMENT); 1390 } 1391 1392 void tdls_send_update_to_fw(struct tdls_vdev_priv_obj *tdls_vdev_obj, 1393 struct tdls_soc_priv_obj *tdls_soc_obj, 1394 bool tdls_prohibited, 1395 bool tdls_chan_swit_prohibited, 1396 bool sta_connect_event, 1397 uint8_t session_id) 1398 { 1399 struct tdls_info *tdls_info_to_fw; 1400 struct tdls_config_params *threshold_params; 1401 uint32_t tdls_feature_flags; 1402 QDF_STATUS status; 1403 bool tdls_mlo; 1404 1405 tdls_feature_flags = tdls_soc_obj->tdls_configs.tdls_feature_flags; 1406 if (!TDLS_IS_ENABLED(tdls_feature_flags)) { 1407 tdls_debug("TDLS mode is not enabled"); 1408 return; 1409 } 1410 1411 tdls_mlo = wlan_tdls_is_fw_11be_mlo_capable(tdls_soc_obj->soc); 1412 1413 /* If AP or caller indicated TDLS Prohibited then disable tdls mode */ 1414 if (sta_connect_event) { 1415 if (tdls_prohibited) { 1416 tdls_soc_obj->tdls_current_mode = 1417 TDLS_SUPPORT_DISABLED; 1418 } else { 1419 if (!TDLS_IS_IMPLICIT_TRIG_ENABLED(tdls_feature_flags)) 1420 tdls_soc_obj->tdls_current_mode = 1421 TDLS_SUPPORT_EXP_TRIG_ONLY; 1422 else if (TDLS_IS_EXTERNAL_CONTROL_ENABLED( 1423 tdls_feature_flags)) 1424 tdls_soc_obj->tdls_current_mode = 1425 TDLS_SUPPORT_EXT_CONTROL; 1426 else 1427 tdls_soc_obj->tdls_current_mode = 1428 TDLS_SUPPORT_IMP_MODE; 1429 } 1430 } else { 1431 tdls_soc_obj->tdls_current_mode = 1432 TDLS_SUPPORT_DISABLED; 1433 } 1434 1435 tdls_info_to_fw = qdf_mem_malloc(sizeof(struct tdls_info)); 1436 if (!tdls_info_to_fw) 1437 return; 1438 1439 threshold_params = &tdls_vdev_obj->threshold_config; 1440 1441 tdls_info_to_fw->notification_interval_ms = 1442 threshold_params->tx_period_t; 1443 tdls_info_to_fw->tx_discovery_threshold = 1444 threshold_params->tx_packet_n; 1445 tdls_info_to_fw->tx_teardown_threshold = 1446 threshold_params->idle_packet_n; 1447 tdls_info_to_fw->rssi_teardown_threshold = 1448 threshold_params->rssi_teardown_threshold; 1449 tdls_info_to_fw->rssi_delta = threshold_params->rssi_delta; 1450 tdls_info_to_fw->vdev_id = session_id; 1451 1452 /* record the session id in vdev context */ 1453 tdls_vdev_obj->session_id = session_id; 1454 tdls_info_to_fw->tdls_state = tdls_soc_obj->tdls_current_mode; 1455 tdls_info_to_fw->tdls_options = 0; 1456 1457 /* 1458 * Do not enable TDLS offchannel, if AP prohibited TDLS 1459 * channel switch 1460 */ 1461 if (TDLS_IS_OFF_CHANNEL_ENABLED(tdls_feature_flags) && 1462 (!tdls_chan_swit_prohibited)) 1463 tdls_info_to_fw->tdls_options = ENA_TDLS_OFFCHAN; 1464 1465 if (TDLS_IS_BUFFER_STA_ENABLED(tdls_feature_flags)) 1466 tdls_info_to_fw->tdls_options |= ENA_TDLS_BUFFER_STA; 1467 if (TDLS_IS_SLEEP_STA_ENABLED(tdls_feature_flags)) 1468 tdls_info_to_fw->tdls_options |= ENA_TDLS_SLEEP_STA; 1469 1470 1471 tdls_info_to_fw->peer_traffic_ind_window = 1472 tdls_soc_obj->tdls_configs.tdls_uapsd_pti_window; 1473 tdls_info_to_fw->peer_traffic_response_timeout = 1474 tdls_soc_obj->tdls_configs.tdls_uapsd_ptr_timeout; 1475 tdls_info_to_fw->puapsd_mask = 1476 tdls_soc_obj->tdls_configs.tdls_uapsd_mask; 1477 tdls_info_to_fw->puapsd_inactivity_time = 1478 tdls_soc_obj->tdls_configs.tdls_uapsd_inactivity_time; 1479 tdls_info_to_fw->puapsd_rx_frame_threshold = 1480 tdls_soc_obj->tdls_configs.tdls_rx_pkt_threshold; 1481 tdls_info_to_fw->teardown_notification_ms = 1482 tdls_soc_obj->tdls_configs.tdls_idle_timeout; 1483 tdls_info_to_fw->tdls_peer_kickout_threshold = 1484 tdls_soc_obj->tdls_configs.tdls_peer_kickout_threshold; 1485 tdls_info_to_fw->tdls_discovery_wake_timeout = 1486 tdls_soc_obj->tdls_configs.tdls_discovery_wake_timeout; 1487 1488 status = tgt_tdls_set_fw_state(tdls_soc_obj->soc, tdls_info_to_fw); 1489 if (QDF_IS_STATUS_ERROR(status)) 1490 goto done; 1491 1492 if (sta_connect_event) { 1493 tdls_soc_obj->set_state_info.vdev_id = session_id; 1494 } 1495 1496 tdls_debug("FW tdls state sent for vdev id %d", session_id); 1497 done: 1498 qdf_mem_free(tdls_info_to_fw); 1499 return; 1500 } 1501 1502 void tdls_process_enable_for_vdev(struct wlan_objmgr_vdev *vdev) 1503 { 1504 struct wlan_objmgr_psoc *psoc; 1505 struct tdls_vdev_priv_obj *tdls_vdev_obj; 1506 struct tdls_soc_priv_obj *tdls_soc_obj; 1507 enum QDF_OPMODE opmode; 1508 QDF_STATUS status; 1509 uint8_t sta_count; 1510 1511 psoc = wlan_vdev_get_psoc(vdev); 1512 if (!psoc) 1513 return; 1514 1515 sta_count = policy_mgr_mode_specific_connection_count(psoc, PM_STA_MODE, 1516 NULL); 1517 opmode = wlan_vdev_mlme_get_opmode(vdev); 1518 if (opmode == QDF_P2P_CLIENT_MODE && sta_count) { 1519 tdls_debug("STA + P2P concurrency. Don't allow TDLS on P2P vdev:%d", 1520 wlan_vdev_get_id(vdev)); 1521 return; 1522 } 1523 1524 status = tdls_get_vdev_objects(vdev, &tdls_vdev_obj, &tdls_soc_obj); 1525 if (QDF_IS_STATUS_ERROR(status)) 1526 return; 1527 1528 tdls_send_update_to_fw(tdls_vdev_obj, tdls_soc_obj, 1529 mlme_get_tdls_prohibited(vdev), 1530 mlme_get_tdls_chan_switch_prohibited(vdev), 1531 true, wlan_vdev_get_id(vdev)); 1532 1533 /* check and set the connection tracker */ 1534 tdls_set_ct_mode(tdls_soc_obj->soc, vdev); 1535 } 1536 1537 static QDF_STATUS 1538 tdls_process_sta_connect(struct tdls_sta_notify_params *notify) 1539 { 1540 if (!tdls_check_is_tdls_allowed(notify->vdev)) 1541 return QDF_STATUS_E_NOSUPPORT; 1542 1543 tdls_process_enable_for_vdev(notify->vdev); 1544 1545 return QDF_STATUS_SUCCESS; 1546 } 1547 1548 QDF_STATUS tdls_notify_sta_connect(struct tdls_sta_notify_params *notify) 1549 { 1550 QDF_STATUS status; 1551 1552 if (!notify) { 1553 tdls_err("invalid param"); 1554 return QDF_STATUS_E_INVAL; 1555 } 1556 1557 if (!notify->vdev) { 1558 tdls_err("invalid param"); 1559 qdf_mem_free(notify); 1560 return QDF_STATUS_E_INVAL; 1561 } 1562 1563 status = tdls_process_sta_connect(notify); 1564 1565 wlan_objmgr_vdev_release_ref(notify->vdev, WLAN_TDLS_NB_ID); 1566 qdf_mem_free(notify); 1567 1568 return status; 1569 } 1570 1571 static QDF_STATUS 1572 tdls_process_sta_disconnect(struct tdls_sta_notify_params *notify) 1573 { 1574 struct tdls_vdev_priv_obj *tdls_vdev_obj; 1575 struct tdls_soc_priv_obj *tdls_soc_obj; 1576 struct wlan_objmgr_vdev *temp_vdev = NULL; 1577 uint8_t vdev_id; 1578 QDF_STATUS status; 1579 1580 status = tdls_get_vdev_objects(notify->vdev, &tdls_vdev_obj, 1581 &tdls_soc_obj); 1582 if (QDF_IS_STATUS_ERROR(status)) 1583 return status; 1584 1585 /* if the disconnect comes from user space, we have to delete all the 1586 * tdls peers before sending the set state cmd. 1587 */ 1588 if (notify->user_disconnect) 1589 return tdls_delete_all_tdls_peers(notify->vdev, tdls_soc_obj); 1590 1591 tdls_debug("Check and update TDLS state for vdev:%d", 1592 notify->session_id); 1593 1594 /* Disassociation event */ 1595 tdls_send_update_to_fw(tdls_vdev_obj, tdls_soc_obj, false, 1596 false, false, notify->session_id); 1597 1598 /* If concurrency is not marked, then we have to 1599 * check, whether TDLS could be enabled in the 1600 * system after this disassoc event. 1601 */ 1602 if (notify->lfr_roam) 1603 return status; 1604 1605 temp_vdev = tdls_get_vdev(tdls_soc_obj->soc, WLAN_TDLS_NB_ID); 1606 if (!temp_vdev) 1607 return status; 1608 1609 vdev_id = wlan_vdev_get_id(temp_vdev); 1610 status = tdls_get_vdev_objects(temp_vdev, &tdls_vdev_obj, 1611 &tdls_soc_obj); 1612 if (QDF_IS_STATUS_ERROR(status)) { 1613 wlan_objmgr_vdev_release_ref(temp_vdev, WLAN_TDLS_NB_ID); 1614 return status; 1615 } 1616 1617 tdls_send_update_to_fw(tdls_vdev_obj, tdls_soc_obj, 1618 mlme_get_tdls_prohibited(temp_vdev), 1619 mlme_get_tdls_chan_switch_prohibited(temp_vdev), 1620 true, vdev_id); 1621 1622 /* Check and set the connection tracker and implicit timers */ 1623 tdls_set_ct_mode(tdls_soc_obj->soc, temp_vdev); 1624 wlan_objmgr_vdev_release_ref(temp_vdev, WLAN_TDLS_NB_ID); 1625 1626 wlan_vdev_mlme_feat_ext2_cap_clear(notify->vdev, 1627 WLAN_VDEV_FEXT2_MLO_STA_TDLS); 1628 1629 return status; 1630 } 1631 1632 QDF_STATUS tdls_notify_sta_disconnect(struct tdls_sta_notify_params *notify) 1633 { 1634 QDF_STATUS status; 1635 struct wlan_objmgr_vdev *vdev; 1636 enum QDF_OPMODE opmode; 1637 struct wlan_objmgr_psoc *psoc; 1638 uint8_t sta_count; 1639 1640 if (!notify) { 1641 tdls_err("invalid param"); 1642 return QDF_STATUS_E_INVAL; 1643 } 1644 1645 vdev = notify->vdev; 1646 if (!vdev) { 1647 tdls_err("invalid param"); 1648 qdf_mem_free(notify); 1649 return QDF_STATUS_E_INVAL; 1650 } 1651 1652 psoc = wlan_vdev_get_psoc(vdev); 1653 if (!psoc) { 1654 wlan_objmgr_vdev_release_ref(notify->vdev, WLAN_TDLS_NB_ID); 1655 qdf_mem_free(notify); 1656 return QDF_STATUS_E_INVAL; 1657 } 1658 1659 opmode = wlan_vdev_mlme_get_opmode(vdev); 1660 sta_count = policy_mgr_mode_specific_connection_count(psoc, PM_STA_MODE, 1661 NULL); 1662 if (opmode == QDF_P2P_CLIENT_MODE && sta_count) { 1663 tdls_debug("STA + P2P concurrency. No action on P2P vdev"); 1664 wlan_objmgr_vdev_release_ref(notify->vdev, WLAN_TDLS_NB_ID); 1665 qdf_mem_free(notify); 1666 return QDF_STATUS_E_INVAL; 1667 } 1668 1669 status = tdls_process_sta_disconnect(notify); 1670 1671 wlan_objmgr_vdev_release_ref(notify->vdev, WLAN_TDLS_NB_ID); 1672 qdf_mem_free(notify); 1673 1674 return status; 1675 } 1676 1677 static void tdls_process_reset_adapter(struct wlan_objmgr_vdev *vdev) 1678 { 1679 struct tdls_vdev_priv_obj *tdls_vdev; 1680 1681 tdls_vdev = wlan_vdev_get_tdls_vdev_obj(vdev); 1682 if (!tdls_vdev) 1683 return; 1684 tdls_timers_stop(tdls_vdev); 1685 } 1686 1687 void tdls_notify_reset_adapter(struct wlan_objmgr_vdev *vdev) 1688 { 1689 if (!vdev) { 1690 QDF_ASSERT(0); 1691 return; 1692 } 1693 1694 if (QDF_STATUS_SUCCESS != wlan_objmgr_vdev_try_get_ref(vdev, 1695 WLAN_TDLS_NB_ID)) 1696 return; 1697 1698 tdls_process_reset_adapter(vdev); 1699 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); 1700 } 1701 1702 QDF_STATUS tdls_peers_deleted_notification(struct wlan_objmgr_psoc *psoc, 1703 uint8_t vdev_id) 1704 { 1705 struct scheduler_msg msg = {0, }; 1706 struct tdls_sta_notify_params *notify; 1707 QDF_STATUS status; 1708 struct wlan_objmgr_vdev *vdev; 1709 1710 notify = qdf_mem_malloc(sizeof(*notify)); 1711 if (!notify) 1712 return QDF_STATUS_E_NULL_VALUE; 1713 1714 vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, 1715 vdev_id, 1716 WLAN_TDLS_NB_ID); 1717 1718 if (!vdev) { 1719 tdls_err("vdev not exist for the vdev id %d", 1720 vdev_id); 1721 qdf_mem_free(notify); 1722 return QDF_STATUS_E_INVAL; 1723 } 1724 1725 notify->lfr_roam = true; 1726 notify->tdls_chan_swit_prohibited = false; 1727 notify->tdls_prohibited = false; 1728 notify->session_id = vdev_id; 1729 notify->vdev = vdev; 1730 notify->user_disconnect = false; 1731 1732 msg.bodyptr = notify; 1733 msg.callback = tdls_process_cmd; 1734 msg.flush_callback = tdls_post_msg_flush_cb; 1735 msg.type = TDLS_NOTIFY_STA_DISCONNECTION; 1736 1737 status = scheduler_post_message(QDF_MODULE_ID_TDLS, 1738 QDF_MODULE_ID_TDLS, 1739 QDF_MODULE_ID_OS_IF, &msg); 1740 if (QDF_IS_STATUS_ERROR(status)) { 1741 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); 1742 qdf_mem_free(notify); 1743 tdls_alert("message post failed "); 1744 1745 return QDF_STATUS_E_FAILURE; 1746 } 1747 1748 return QDF_STATUS_SUCCESS; 1749 } 1750 1751 static 1752 QDF_STATUS tdls_delete_all_peers_indication(struct wlan_objmgr_psoc *psoc, 1753 uint8_t vdev_id) 1754 { 1755 struct scheduler_msg msg = {0, }; 1756 struct tdls_delete_all_peers_params *indication; 1757 QDF_STATUS status; 1758 struct wlan_objmgr_vdev *vdev; 1759 1760 indication = qdf_mem_malloc(sizeof(*indication)); 1761 if (!indication) 1762 return QDF_STATUS_E_NULL_VALUE; 1763 1764 vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, vdev_id, 1765 WLAN_TDLS_SB_ID); 1766 if (!vdev) { 1767 tdls_err("vdev:%d does not exist", vdev_id); 1768 qdf_mem_free(indication); 1769 return QDF_STATUS_E_INVAL; 1770 } 1771 1772 indication->vdev = vdev; 1773 1774 msg.bodyptr = indication; 1775 msg.callback = tdls_process_cmd; 1776 msg.type = TDLS_DELETE_ALL_PEERS_INDICATION; 1777 msg.flush_callback = tdls_post_msg_flush_cb; 1778 1779 status = scheduler_post_message(QDF_MODULE_ID_TDLS, 1780 QDF_MODULE_ID_TDLS, 1781 QDF_MODULE_ID_OS_IF, &msg); 1782 if (QDF_IS_STATUS_ERROR(status)) { 1783 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_SB_ID); 1784 qdf_mem_free(indication); 1785 tdls_alert("message post failed "); 1786 return QDF_STATUS_E_FAILURE; 1787 } 1788 1789 return QDF_STATUS_SUCCESS; 1790 } 1791 1792 QDF_STATUS 1793 tdls_check_and_indicate_delete_all_peers(struct wlan_objmgr_psoc *psoc, 1794 uint8_t vdev_id) 1795 { 1796 struct wlan_objmgr_pdev *pdev; 1797 uint32_t pdev_id; 1798 enum QDF_OPMODE opmode; 1799 uint8_t sta_count = 1800 policy_mgr_mode_specific_connection_count(psoc, PM_STA_MODE, 1801 NULL); 1802 1803 pdev_id = wlan_get_pdev_id_from_vdev_id(psoc, vdev_id, WLAN_TDLS_SB_ID); 1804 if (pdev_id == WLAN_INVALID_PDEV_ID) { 1805 tdls_debug("Invalid pdev id"); 1806 return QDF_STATUS_E_INVAL; 1807 } 1808 1809 pdev = wlan_objmgr_get_pdev_by_id(psoc, pdev_id, WLAN_TDLS_SB_ID); 1810 if (!pdev) { 1811 tdls_debug("pdev is NULL"); 1812 return QDF_STATUS_E_INVAL; 1813 } 1814 1815 opmode = wlan_get_opmode_from_vdev_id(pdev, vdev_id); 1816 wlan_objmgr_pdev_release_ref(pdev, WLAN_TDLS_SB_ID); 1817 1818 if (opmode == QDF_P2P_CLIENT_MODE && sta_count) { 1819 tdls_debug("STA + P2P concurrency. No action on P2P vdev"); 1820 return QDF_STATUS_E_INVAL; 1821 } 1822 1823 return tdls_delete_all_peers_indication(psoc, vdev_id); 1824 } 1825 1826 /** 1827 * tdls_set_mode_in_vdev() - set TDLS mode 1828 * @tdls_vdev: tdls vdev object 1829 * @tdls_soc: tdls soc object 1830 * @tdls_mode: TDLS mode 1831 * @source: TDLS disable source enum values 1832 * 1833 * Return: Void 1834 */ 1835 static void tdls_set_mode_in_vdev(struct tdls_vdev_priv_obj *tdls_vdev, 1836 struct tdls_soc_priv_obj *tdls_soc, 1837 enum tdls_feature_mode tdls_mode, 1838 enum tdls_disable_sources source) 1839 { 1840 tdls_debug("set tdls mode: %d source:%d", tdls_mode, 1841 source); 1842 1843 switch (tdls_mode) { 1844 case TDLS_SUPPORT_IMP_MODE: 1845 fallthrough; 1846 case TDLS_SUPPORT_EXT_CONTROL: 1847 clear_bit((unsigned long)source, &tdls_soc->tdls_source_bitmap); 1848 /* 1849 * Check if any TDLS source bit is set and if 1850 * bitmap is not zero then we should not enable TDLS 1851 */ 1852 if (tdls_soc->tdls_source_bitmap) { 1853 tdls_notice("Don't enable TDLS, source bitmap: %lu", 1854 tdls_soc->tdls_source_bitmap); 1855 return; 1856 } 1857 tdls_implicit_enable(tdls_vdev); 1858 /* 1859 * tdls implicit mode is enabled, so enable the connection 1860 * tracker 1861 */ 1862 tdls_soc->enable_tdls_connection_tracker = true; 1863 1864 return; 1865 1866 case TDLS_SUPPORT_DISABLED: 1867 set_bit((unsigned long)source, 1868 &tdls_soc->tdls_source_bitmap); 1869 tdls_implicit_disable(tdls_vdev); 1870 /* If tdls implicit mode is disabled, then 1871 * stop the connection tracker. 1872 */ 1873 tdls_soc->enable_tdls_connection_tracker = false; 1874 1875 return; 1876 1877 case TDLS_SUPPORT_EXP_TRIG_ONLY: 1878 clear_bit((unsigned long)source, 1879 &tdls_soc->tdls_source_bitmap); 1880 tdls_implicit_disable(tdls_vdev); 1881 /* If tdls implicit mode is disabled, then 1882 * stop the connection tracker. 1883 */ 1884 tdls_soc->enable_tdls_connection_tracker = false; 1885 1886 /* 1887 * Check if any TDLS source bit is set and if 1888 * bitmap is not zero then we should not 1889 * enable TDLS 1890 */ 1891 if (tdls_soc->tdls_source_bitmap) 1892 return; 1893 1894 return; 1895 default: 1896 return; 1897 } 1898 } 1899 1900 /** 1901 * tdls_set_current_mode() - set TDLS mode 1902 * @tdls_soc: tdls soc object 1903 * @tdls_mode: TDLS mode 1904 * @update_last: indicate to record the last tdls mode 1905 * @source: TDLS disable source enum values 1906 * 1907 * Return: Void 1908 */ 1909 static void tdls_set_current_mode(struct tdls_soc_priv_obj *tdls_soc, 1910 enum tdls_feature_mode tdls_mode, 1911 bool update_last, 1912 enum tdls_disable_sources source) 1913 { 1914 struct wlan_objmgr_vdev *vdev; 1915 struct tdls_vdev_priv_obj *tdls_vdev; 1916 1917 if (!tdls_soc) 1918 return; 1919 1920 tdls_debug("mode %d", (int)tdls_mode); 1921 1922 if (update_last) 1923 tdls_soc->tdls_last_mode = tdls_mode; 1924 1925 if (tdls_soc->tdls_current_mode == tdls_mode) { 1926 tdls_debug("already in mode %d", tdls_mode); 1927 1928 switch (tdls_mode) { 1929 /* TDLS is already enabled hence clear source mask, return */ 1930 case TDLS_SUPPORT_IMP_MODE: 1931 case TDLS_SUPPORT_EXP_TRIG_ONLY: 1932 case TDLS_SUPPORT_EXT_CONTROL: 1933 clear_bit((unsigned long)source, 1934 &tdls_soc->tdls_source_bitmap); 1935 tdls_debug("clear source mask:%d", source); 1936 return; 1937 /* TDLS is already disabled hence set source mask, return */ 1938 case TDLS_SUPPORT_DISABLED: 1939 set_bit((unsigned long)source, 1940 &tdls_soc->tdls_source_bitmap); 1941 tdls_debug("set source mask:%d", source); 1942 return; 1943 default: 1944 return; 1945 } 1946 } 1947 1948 /* get sta vdev */ 1949 vdev = wlan_objmgr_get_vdev_by_opmode_from_psoc(tdls_soc->soc, 1950 QDF_STA_MODE, 1951 WLAN_TDLS_NB_ID); 1952 if (vdev) { 1953 tdls_debug("set mode in tdls STA vdev:%d", 1954 wlan_vdev_get_id(vdev)); 1955 tdls_vdev = wlan_vdev_get_tdls_vdev_obj(vdev); 1956 if (tdls_vdev) 1957 tdls_set_mode_in_vdev(tdls_vdev, tdls_soc, 1958 tdls_mode, source); 1959 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); 1960 1961 goto exit; 1962 } 1963 1964 /* get p2p client vdev */ 1965 vdev = wlan_objmgr_get_vdev_by_opmode_from_psoc(tdls_soc->soc, 1966 QDF_P2P_CLIENT_MODE, 1967 WLAN_TDLS_NB_ID); 1968 if (vdev) { 1969 tdls_debug("set mode in tdls P2P cli vdev:%d", 1970 wlan_vdev_get_id(vdev)); 1971 tdls_vdev = wlan_vdev_get_tdls_vdev_obj(vdev); 1972 if (tdls_vdev) 1973 tdls_set_mode_in_vdev(tdls_vdev, tdls_soc, 1974 tdls_mode, source); 1975 wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); 1976 } 1977 1978 exit: 1979 if (!update_last) 1980 tdls_soc->tdls_last_mode = tdls_soc->tdls_current_mode; 1981 1982 tdls_soc->tdls_current_mode = tdls_mode; 1983 } 1984 1985 QDF_STATUS tdls_set_operation_mode(struct tdls_set_mode_params *tdls_set_mode) 1986 { 1987 struct tdls_soc_priv_obj *tdls_soc; 1988 struct tdls_vdev_priv_obj *tdls_vdev; 1989 QDF_STATUS status; 1990 1991 if (!tdls_set_mode) 1992 return QDF_STATUS_E_INVAL; 1993 1994 if (!tdls_set_mode->vdev) { 1995 qdf_mem_free(tdls_set_mode); 1996 return QDF_STATUS_E_INVAL; 1997 } 1998 1999 status = tdls_get_vdev_objects(tdls_set_mode->vdev, 2000 &tdls_vdev, &tdls_soc); 2001 2002 if (QDF_IS_STATUS_ERROR(status)) 2003 goto release_mode_ref; 2004 2005 tdls_set_current_mode(tdls_soc, 2006 tdls_set_mode->tdls_mode, 2007 tdls_set_mode->update_last, 2008 tdls_set_mode->source); 2009 2010 release_mode_ref: 2011 wlan_objmgr_vdev_release_ref(tdls_set_mode->vdev, WLAN_TDLS_NB_ID); 2012 qdf_mem_free(tdls_set_mode); 2013 return status; 2014 } 2015 2016 /** 2017 * tdls_scan_done_callback() - callback for tdls scan done event 2018 * @tdls_soc: tdls soc object 2019 * 2020 * Return: Void 2021 */ 2022 void tdls_scan_done_callback(struct tdls_soc_priv_obj *tdls_soc) 2023 { 2024 if (!tdls_soc) 2025 return; 2026 2027 /* if tdls was enabled before scan, re-enable tdls mode */ 2028 if (TDLS_SUPPORT_IMP_MODE == tdls_soc->tdls_last_mode || 2029 TDLS_SUPPORT_EXT_CONTROL == tdls_soc->tdls_last_mode || 2030 TDLS_SUPPORT_EXP_TRIG_ONLY == tdls_soc->tdls_last_mode) 2031 tdls_set_current_mode(tdls_soc, tdls_soc->tdls_last_mode, 2032 false, TDLS_SET_MODE_SOURCE_SCAN); 2033 } 2034 2035 /** 2036 * tdls_post_scan_done_msg() - post scan done message to tdls cmd queue 2037 * @tdls_soc: tdls soc object 2038 * 2039 * Return: QDF_STATUS_SUCCESS or QDF_STATUS_E_NULL_VALUE 2040 */ 2041 static QDF_STATUS tdls_post_scan_done_msg(struct tdls_soc_priv_obj *tdls_soc) 2042 { 2043 struct scheduler_msg msg = {0, }; 2044 2045 if (!tdls_soc) { 2046 tdls_err("tdls_soc: %pK ", tdls_soc); 2047 return QDF_STATUS_E_NULL_VALUE; 2048 } 2049 2050 msg.bodyptr = tdls_soc; 2051 msg.callback = tdls_process_cmd; 2052 msg.flush_callback = tdls_post_msg_flush_cb; 2053 msg.type = TDLS_CMD_SCAN_DONE; 2054 2055 return scheduler_post_message(QDF_MODULE_ID_TDLS, 2056 QDF_MODULE_ID_TDLS, 2057 QDF_MODULE_ID_OS_IF, &msg); 2058 } 2059 2060 void tdls_scan_complete_event_handler(struct wlan_objmgr_vdev *vdev, 2061 struct scan_event *event, 2062 void *arg) 2063 { 2064 enum QDF_OPMODE device_mode; 2065 struct tdls_soc_priv_obj *tdls_soc; 2066 2067 if (!vdev || !event || !arg) 2068 return; 2069 2070 if (SCAN_EVENT_TYPE_COMPLETED != event->type) 2071 return; 2072 2073 device_mode = wlan_vdev_mlme_get_opmode(vdev); 2074 2075 tdls_soc = (struct tdls_soc_priv_obj *) arg; 2076 tdls_post_scan_done_msg(tdls_soc); 2077 } 2078 2079 void tdls_set_link_unforce(struct wlan_objmgr_vdev *vdev) 2080 { 2081 QDF_STATUS status; 2082 struct scheduler_msg msg = {0}; 2083 2084 msg.callback = tdls_process_cmd; 2085 msg.type = TDLS_CMD_SET_LINK_UNFORCE; 2086 msg.bodyptr = vdev; 2087 status = scheduler_post_message(QDF_MODULE_ID_TDLS, 2088 QDF_MODULE_ID_TDLS, 2089 QDF_MODULE_ID_OS_IF, &msg); 2090 if (QDF_IS_STATUS_ERROR(status)) 2091 tdls_err("failed to set tdls link mode"); 2092 } 2093 2094 /** 2095 * tdls_check_peer_buf_capable() - Check buffer sta capable of tdls peers 2096 * @tdls_vdev: TDLS vdev object 2097 * 2098 * Used in scheduler thread context, no lock needed. 2099 * 2100 * Return: false if there is connected peer and not support buffer sta. 2101 */ 2102 static bool tdls_check_peer_buf_capable(struct tdls_vdev_priv_obj *tdls_vdev) 2103 { 2104 uint16_t i; 2105 struct tdls_peer *peer; 2106 qdf_list_t *head; 2107 qdf_list_node_t *p_node; 2108 QDF_STATUS status; 2109 2110 if (!tdls_vdev) { 2111 tdls_err("invalid tdls vdev object"); 2112 return false; 2113 } 2114 2115 for (i = 0; i < WLAN_TDLS_PEER_LIST_SIZE; i++) { 2116 head = &tdls_vdev->peer_list[i]; 2117 2118 status = qdf_list_peek_front(head, &p_node); 2119 while (QDF_IS_STATUS_SUCCESS(status)) { 2120 peer = qdf_container_of(p_node, struct tdls_peer, node); 2121 2122 if (peer && 2123 (TDLS_LINK_CONNECTED == peer->link_status) && 2124 (!peer->buf_sta_capable)) 2125 return false; 2126 2127 status = qdf_list_peek_next(head, p_node, &p_node); 2128 } 2129 } 2130 2131 return true; 2132 } 2133 2134 QDF_STATUS tdls_scan_callback(struct tdls_soc_priv_obj *tdls_soc) 2135 { 2136 struct tdls_vdev_priv_obj *tdls_vdev; 2137 struct wlan_objmgr_vdev *vdev; 2138 uint16_t tdls_peer_count; 2139 uint32_t feature; 2140 bool peer_buf_capable; 2141 QDF_STATUS status = QDF_STATUS_SUCCESS; 2142 2143 /* if tdls is not enabled, then continue scan */ 2144 if (TDLS_SUPPORT_DISABLED == tdls_soc->tdls_current_mode) 2145 return status; 2146 2147 /* Get the vdev based on vdev operating mode*/ 2148 vdev = tdls_get_vdev(tdls_soc->soc, WLAN_TDLS_NB_ID); 2149 if (!vdev) 2150 return status; 2151 2152 tdls_vdev = wlan_vdev_get_tdls_vdev_obj(vdev); 2153 if (!tdls_vdev) 2154 goto return_success; 2155 2156 if (tdls_is_progress(tdls_vdev, NULL, 0)) { 2157 if (tdls_soc->scan_reject_count++ >= TDLS_SCAN_REJECT_MAX) { 2158 tdls_notice("Allow this scan req. as already max no of scan's are rejected"); 2159 tdls_soc->scan_reject_count = 0; 2160 status = QDF_STATUS_SUCCESS; 2161 2162 } else { 2163 tdls_warn("tdls in progress. scan rejected %d", 2164 tdls_soc->scan_reject_count); 2165 status = QDF_STATUS_E_BUSY; 2166 } 2167 } 2168 2169 tdls_peer_count = tdls_soc->connected_peer_count; 2170 if (!tdls_peer_count) 2171 goto disable_tdls; 2172 2173 feature = tdls_soc->tdls_configs.tdls_feature_flags; 2174 if (TDLS_IS_SCAN_ENABLED(feature)) { 2175 tdls_debug("TDLS Scan enabled, keep tdls link and allow scan, connected tdls peers: %d", 2176 tdls_peer_count); 2177 goto disable_tdls; 2178 } 2179 2180 if (TDLS_IS_BUFFER_STA_ENABLED(feature) && 2181 (tdls_peer_count <= TDLS_MAX_CONNECTED_PEERS_TO_ALLOW_SCAN)) { 2182 peer_buf_capable = tdls_check_peer_buf_capable(tdls_vdev); 2183 if (peer_buf_capable) { 2184 tdls_debug("All peers (num %d) bufSTAs, we can be sleep sta, so allow scan, tdls mode changed to %d", 2185 tdls_peer_count, 2186 tdls_soc->tdls_current_mode); 2187 goto disable_tdls; 2188 } 2189 } 2190 2191 tdls_disable_offchan_and_teardown_links(vdev); 2192 2193 disable_tdls: 2194 tdls_set_current_mode(tdls_soc, TDLS_SUPPORT_DISABLED, 2195 false, TDLS_SET_MODE_SOURCE_SCAN); 2196 2197 return_success: 2198 wlan_objmgr_vdev_release_ref(vdev, 2199 WLAN_TDLS_NB_ID); 2200 return status; 2201 } 2202 2203 void tdls_scan_serialization_comp_info_cb(struct wlan_objmgr_vdev *vdev, 2204 union wlan_serialization_rules_info *comp_info, 2205 struct wlan_serialization_command *cmd) 2206 { 2207 struct tdls_soc_priv_obj *tdls_soc; 2208 QDF_STATUS status; 2209 if (!comp_info) 2210 return; 2211 2212 tdls_soc = tdls_soc_global; 2213 comp_info->scan_info.is_tdls_in_progress = false; 2214 status = tdls_scan_callback(tdls_soc); 2215 if (QDF_STATUS_E_BUSY == status) 2216 comp_info->scan_info.is_tdls_in_progress = true; 2217 } 2218 2219 static uint8_t tdls_find_opclass_frm_freq(struct wlan_objmgr_vdev *vdev, 2220 qdf_freq_t ch_freq, uint8_t bw_offset, 2221 uint16_t behav_limit) 2222 { 2223 struct wlan_objmgr_pdev *pdev = wlan_vdev_get_pdev(vdev); 2224 uint8_t channel, opclass; 2225 2226 if (!pdev) { 2227 tdls_err("pdev is NULL"); 2228 return 0; 2229 } 2230 2231 wlan_reg_freq_width_to_chan_op_class(pdev, ch_freq, bw_offset, false, 2232 BIT(behav_limit), &opclass, 2233 &channel); 2234 2235 return opclass; 2236 } 2237 2238 uint8_t tdls_get_opclass_from_bandwidth(struct wlan_objmgr_vdev *vdev, 2239 qdf_freq_t freq, uint8_t bw_offset, 2240 uint8_t *reg_bw_offset) 2241 { 2242 uint8_t opclass; 2243 2244 if (bw_offset & (1 << BW_160_OFFSET_BIT)) { 2245 opclass = tdls_find_opclass_frm_freq(vdev, 2246 freq, BW_160_MHZ, 2247 BEHAV_NONE); 2248 *reg_bw_offset = BWALL; 2249 } else if (bw_offset & (1 << BW_80_OFFSET_BIT)) { 2250 opclass = tdls_find_opclass_frm_freq(vdev, 2251 freq, BW_80_MHZ, 2252 BEHAV_NONE); 2253 *reg_bw_offset = BW80; 2254 } else if (bw_offset & (1 << BW_40_OFFSET_BIT)) { 2255 opclass = tdls_find_opclass_frm_freq(vdev, 2256 freq, BW_40_MHZ, 2257 BEHAV_BW40_LOW_PRIMARY); 2258 *reg_bw_offset = BW40_LOW_PRIMARY; 2259 if (!opclass) { 2260 opclass = tdls_find_opclass_frm_freq(vdev, 2261 freq, 2262 BW_40_MHZ, 2263 BEHAV_BW40_HIGH_PRIMARY); 2264 *reg_bw_offset = BW40_HIGH_PRIMARY; 2265 } 2266 } else if (bw_offset & (1 << BW_20_OFFSET_BIT)) { 2267 opclass = tdls_find_opclass_frm_freq(vdev, 2268 freq, BW_20_MHZ, 2269 BEHAV_NONE); 2270 *reg_bw_offset = BW20; 2271 } else { 2272 opclass = tdls_find_opclass_frm_freq(vdev, 2273 freq, BW_160_MHZ, 2274 BEHAV_NONE); 2275 *reg_bw_offset = BWALL; 2276 } 2277 2278 return opclass; 2279 } 2280