1 /* 2 * Copyright (c) 2016-2021 The Linux Foundation. All rights reserved. 3 * Copyright (c) 2023-2024 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: cdp_txrx_peer_ops.h 22 * Define the host data path peer API functions 23 * called by the host control SW and the OS interface module 24 */ 25 #ifndef _CDP_TXRX_PEER_H_ 26 #define _CDP_TXRX_PEER_H_ 27 #include <cdp_txrx_ops.h> 28 #include "cdp_txrx_handle.h" 29 30 /** 31 * cdp_peer_register() - Register peer into physical device 32 * @soc: data path soc handle 33 * @pdev_id: data path device instance id 34 * @sta_desc: peer description 35 * 36 * Register peer into physical device 37 * 38 * Return: QDF_STATUS_SUCCESS registration success 39 * QDF_STATUS_E_NOSUPPORT not support this feature 40 */ 41 static inline QDF_STATUS 42 cdp_peer_register(ol_txrx_soc_handle soc, uint8_t pdev_id, 43 struct ol_txrx_desc_type *sta_desc) 44 { 45 if (!soc || !soc->ops || !soc->ops->peer_ops) { 46 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 47 "%s invalid instance", __func__); 48 return QDF_STATUS_E_INVAL; 49 } 50 51 if (soc->ops->peer_ops->register_peer) 52 return soc->ops->peer_ops->register_peer(soc, pdev_id, 53 sta_desc); 54 55 return QDF_STATUS_E_NOSUPPORT; 56 } 57 58 /** 59 * cdp_clear_peer() - remove peer from physical device 60 * @soc: data path soc handle 61 * @pdev_id: data path device instance id 62 * @peer_addr: peer mac address 63 * 64 * remove peer from physical device 65 * 66 * Return: QDF_STATUS_SUCCESS registration success 67 * QDF_STATUS_E_NOSUPPORT not support this feature 68 */ 69 static inline QDF_STATUS 70 cdp_clear_peer(ol_txrx_soc_handle soc, uint8_t pdev_id, 71 struct qdf_mac_addr peer_addr) 72 { 73 if (!soc || !soc->ops || !soc->ops->peer_ops) { 74 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 75 "%s invalid instance", __func__); 76 return QDF_STATUS_E_INVAL; 77 } 78 79 if (soc->ops->peer_ops->clear_peer) 80 return soc->ops->peer_ops->clear_peer(soc, pdev_id, peer_addr); 81 82 return QDF_STATUS_E_NOSUPPORT; 83 } 84 85 /** 86 * cdp_peer_register_ocb_peer() - register ocb peer from physical device 87 * @soc: data path soc handle 88 * @mac_addr: mac address for ocb self peer 89 * 90 * register ocb peer from physical device 91 * 92 * Return: QDF_STATUS_SUCCESS registration success 93 * QDF_STATUS_E_NOSUPPORT not support this feature 94 */ 95 static inline QDF_STATUS 96 cdp_peer_register_ocb_peer(ol_txrx_soc_handle soc, 97 uint8_t *mac_addr) 98 { 99 if (!soc || !soc->ops || !soc->ops->peer_ops) { 100 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 101 "%s invalid instance", __func__); 102 return QDF_STATUS_E_INVAL; 103 } 104 105 if (soc->ops->peer_ops->register_ocb_peer) 106 return soc->ops->peer_ops->register_ocb_peer(mac_addr); 107 108 return QDF_STATUS_E_NOSUPPORT; 109 } 110 111 /** 112 * cdp_find_peer_exist - Find if peer already exists 113 * @soc: data path soc handle 114 * @pdev_id: data path device instance id 115 * @peer_addr: peer mac address 116 * 117 * Return: true or false 118 */ 119 static inline bool 120 cdp_find_peer_exist(ol_txrx_soc_handle soc, uint8_t pdev_id, 121 uint8_t *peer_addr) 122 { 123 if (!soc || !soc->ops || !soc->ops->peer_ops) { 124 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 125 "%s invalid instance", __func__); 126 return false; 127 } 128 129 if (soc->ops->peer_ops->find_peer_exist) 130 return soc->ops->peer_ops->find_peer_exist(soc, pdev_id, 131 peer_addr); 132 133 return false; 134 } 135 136 /** 137 * cdp_find_peer_exist_on_vdev - Find if duplicate peer exists 138 * on the given vdev 139 * @soc: data path soc handle 140 * @vdev_id: data path virtual interface id 141 * @peer_addr: peer mac address 142 * 143 * Return: true or false 144 */ 145 static inline bool 146 cdp_find_peer_exist_on_vdev(ol_txrx_soc_handle soc, uint8_t vdev_id, 147 uint8_t *peer_addr) 148 { 149 if (!soc || !soc->ops || !soc->ops->peer_ops) { 150 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 151 "%s invalid instance", __func__); 152 return false; 153 } 154 155 if (soc->ops->peer_ops->find_peer_exist_on_vdev) 156 return soc->ops->peer_ops->find_peer_exist_on_vdev(soc, vdev_id, 157 peer_addr); 158 159 return false; 160 } 161 162 /** 163 * cdp_find_peer_exist_on_other_vdev - Find if duplicate peer exists 164 * on other than the given vdev 165 * @soc: data path soc handle 166 * @vdev_id: data path virtual interface id 167 * @peer_addr: peer mac address 168 * @max_bssid: max number of bssids 169 * 170 * Return: true or false 171 */ 172 static inline bool 173 cdp_find_peer_exist_on_other_vdev(ol_txrx_soc_handle soc, uint8_t vdev_id, 174 uint8_t *peer_addr, uint16_t max_bssid) 175 { 176 if (!soc || !soc->ops || !soc->ops->peer_ops) { 177 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 178 "%s invalid instance", __func__); 179 return false; 180 } 181 182 if (soc->ops->peer_ops->find_peer_exist_on_other_vdev) 183 return soc->ops->peer_ops->find_peer_exist_on_other_vdev( 184 soc, vdev_id, 185 peer_addr, 186 max_bssid); 187 188 return false; 189 } 190 191 /** 192 * cdp_peer_state_update() - update peer local state 193 * @soc: data path soc handle 194 * @peer_addr: peer mac address 195 * @state: new peer local state 196 * 197 * update peer local state 198 * 199 * Return: QDF_STATUS_SUCCESS registration success 200 * QDF_STATUS_E_NOSUPPORT not support this feature 201 */ 202 static inline QDF_STATUS 203 cdp_peer_state_update(ol_txrx_soc_handle soc, uint8_t *peer_addr, 204 enum ol_txrx_peer_state state) 205 { 206 if (!soc || !soc->ops || !soc->ops->peer_ops) { 207 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 208 "%s invalid instance", __func__); 209 return QDF_STATUS_E_INVAL; 210 } 211 212 if (soc->ops->peer_ops->peer_state_update) 213 return soc->ops->peer_ops->peer_state_update(soc, peer_addr, 214 state); 215 216 return QDF_STATUS_E_NOSUPPORT; 217 } 218 219 /** 220 * cdp_peer_state_get() - Get local peer state 221 * @soc: data path soc handle 222 * @vdev_id: virtual interface id 223 * @peer_mac: peer mac addr 224 * @slowpath: call from slow path or not 225 * 226 * Get local peer state 227 * 228 * Return: peer status 229 */ 230 static inline int 231 cdp_peer_state_get(ol_txrx_soc_handle soc, uint8_t vdev_id, uint8_t *peer_mac, bool slowpath) 232 { 233 if (!soc || !soc->ops || !soc->ops->peer_ops) { 234 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 235 "%s invalid instance", __func__); 236 return 0; 237 } 238 239 if (soc->ops->peer_ops->get_peer_state) 240 return soc->ops->peer_ops->get_peer_state(soc, vdev_id, 241 peer_mac, 242 slowpath); 243 244 return 0; 245 } 246 247 /** 248 * cdp_peer_get_vdevid() - Get virtual interface id which peer registered 249 * @soc: data path soc handle 250 * @peer_mac: peer mac address 251 * @vdev_id: virtual interface id which peer registered 252 * 253 * Get virtual interface id which peer registered 254 * 255 * Return: QDF_STATUS_SUCCESS registration success 256 * QDF_STATUS_E_NOSUPPORT not support this feature 257 */ 258 static inline QDF_STATUS 259 cdp_peer_get_vdevid(ol_txrx_soc_handle soc, 260 uint8_t *peer_mac, uint8_t *vdev_id) 261 { 262 if (!soc || !soc->ops || !soc->ops->peer_ops) { 263 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 264 "%s invalid instance", __func__); 265 return QDF_STATUS_E_INVAL; 266 } 267 268 if (soc->ops->peer_ops->get_vdevid) 269 return soc->ops->peer_ops->get_vdevid(soc, peer_mac, vdev_id); 270 271 return QDF_STATUS_E_NOSUPPORT; 272 } 273 274 /** 275 * cdp_peer_get_vdev_by_peer_addr() - Get vdev instance by local peer address 276 * @soc: data path soc handle 277 * @pdev: data path device instance 278 * @peer_addr: peer mac address 279 * 280 * Get virtual interface id by local peer id 281 * 282 * Return: Virtual interface instance 283 * NULL in case cannot find 284 */ 285 static inline struct cdp_vdev 286 *cdp_peer_get_vdev_by_peer_addr(ol_txrx_soc_handle soc, struct cdp_pdev *pdev, 287 struct qdf_mac_addr peer_addr) 288 { 289 if (!soc || !soc->ops || !soc->ops->peer_ops) { 290 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 291 "%s invalid instance", __func__); 292 return NULL; 293 } 294 295 if (soc->ops->peer_ops->get_vdev_by_peer_addr) 296 return soc->ops->peer_ops->get_vdev_by_peer_addr(pdev, 297 peer_addr); 298 299 return NULL; 300 } 301 302 /** 303 * cdp_peer_get_peer_mac_addr() - Get peer mac address 304 * @soc: data path soc handle 305 * @peer: peer instance 306 * 307 * Get peer mac address 308 * 309 * Return: peer mac address pointer 310 * NULL in case cannot find 311 */ 312 static inline uint8_t 313 *cdp_peer_get_peer_mac_addr(ol_txrx_soc_handle soc, void *peer) 314 { 315 if (!soc || !soc->ops || !soc->ops->peer_ops) { 316 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 317 "%s invalid instance", __func__); 318 return NULL; 319 } 320 321 if (soc->ops->peer_ops->peer_get_peer_mac_addr) 322 return soc->ops->peer_ops->peer_get_peer_mac_addr(peer); 323 324 return NULL; 325 } 326 327 /** 328 * cdp_peer_update_ibss_add_peer_num_of_vdev() - update number of peer 329 * @soc: data path soc handle 330 * @vdev_id: virtual interface instance id 331 * @peer_num_delta: number of peer should be updated 332 * 333 * update number of peer 334 * 335 * Return: updated number of peer 336 * 0 fail 337 */ 338 static inline int16_t 339 cdp_peer_update_ibss_add_peer_num_of_vdev(ol_txrx_soc_handle soc, 340 uint8_t vdev_id, 341 int16_t peer_num_delta) 342 { 343 if (!soc || !soc->ops || !soc->ops->peer_ops) { 344 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 345 "%s invalid instance", __func__); 346 return 0; 347 } 348 349 if (soc->ops->peer_ops->update_ibss_add_peer_num_of_vdev) 350 return soc->ops->peer_ops->update_ibss_add_peer_num_of_vdev( 351 soc, vdev_id, 352 peer_num_delta); 353 354 return 0; 355 } 356 357 /** 358 * cdp_peer_copy_mac_addr_raw() - copy peer mac address 359 * @soc: data path soc handle 360 * @vdev_id: virtual interface instance id 361 * @bss_addr: mac address should be copied 362 * 363 * copy peer mac address 364 * 365 * Return: none 366 */ 367 static inline void 368 cdp_peer_copy_mac_addr_raw(ol_txrx_soc_handle soc, 369 uint8_t vdev_id, uint8_t *bss_addr) 370 { 371 if (!soc || !soc->ops || !soc->ops->peer_ops) { 372 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 373 "%s invalid instance", __func__); 374 return; 375 } 376 377 if (soc->ops->peer_ops->copy_mac_addr_raw) 378 return soc->ops->peer_ops->copy_mac_addr_raw(soc, vdev_id, 379 bss_addr); 380 381 return; 382 } 383 384 /** 385 * cdp_peer_add_last_real_peer() - Add peer with last peer marking 386 * @soc: data path soc handle 387 * @pdev_id: data path device instance id 388 * @vdev_id: virtual interface instance id 389 * 390 * copy peer mac address 391 * 392 * Return: none 393 */ 394 static inline void 395 cdp_peer_add_last_real_peer(ol_txrx_soc_handle soc, uint8_t pdev_id, 396 uint8_t vdev_id) 397 { 398 if (!soc || !soc->ops || !soc->ops->peer_ops) { 399 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 400 "%s invalid instance", __func__); 401 return; 402 } 403 404 if (soc->ops->peer_ops->add_last_real_peer) 405 return soc->ops->peer_ops->add_last_real_peer(soc, pdev_id, 406 vdev_id); 407 return; 408 } 409 410 /** 411 * cdp_peer_is_vdev_restore_last_peer() - restore last peer 412 * @soc: data path soc handle 413 * @vdev_id: virtual interface id 414 * @peer_mac: peer mac address 415 * 416 * restore last peer 417 * 418 * Return: true, restore success 419 * false, restore fail 420 */ 421 static inline bool 422 cdp_peer_is_vdev_restore_last_peer(ol_txrx_soc_handle soc, uint8_t vdev_id, 423 uint8_t *peer_mac) 424 { 425 if (!soc || !soc->ops || !soc->ops->peer_ops) { 426 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 427 "%s invalid instance", __func__); 428 return false; 429 } 430 431 if (soc->ops->peer_ops->is_vdev_restore_last_peer) 432 return soc->ops->peer_ops->is_vdev_restore_last_peer(soc, 433 vdev_id, 434 peer_mac); 435 436 return false; 437 } 438 439 /** 440 * cdp_peer_update_last_real_peer() - update last real peer 441 * @soc: data path soc handle 442 * @pdev_id: data path device instance id 443 * @vdev_id: virtual interface id 444 * @restore_last_peer: restore last peer or not 445 * 446 * update last real peer 447 * 448 * Return: none 449 */ 450 static inline void 451 cdp_peer_update_last_real_peer(ol_txrx_soc_handle soc, uint8_t pdev_id, 452 uint8_t vdev_id, bool restore_last_peer) 453 { 454 if (!soc || !soc->ops || !soc->ops->peer_ops) { 455 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 456 "%s invalid instance", __func__); 457 return; 458 } 459 460 if (soc->ops->peer_ops->update_last_real_peer) 461 return soc->ops->peer_ops->update_last_real_peer( 462 soc, pdev_id, vdev_id, 463 restore_last_peer); 464 465 return; 466 } 467 468 /** 469 * cdp_peer_detach_force_delete() - Detach and delete a peer's data object 470 * @soc: data path soc handle 471 * @vdev_id: data path virtual interface id 472 * @peer_mac: peer mac address 473 * 474 * Detach a peer and force the peer object to be removed. It is called during 475 * roaming scenario when the firmware has already deleted a peer. 476 * Peer object is freed immediately to avoid duplicate peers during roam sync 477 * indication processing. 478 * 479 * Return: None 480 */ 481 static inline void cdp_peer_detach_force_delete(ol_txrx_soc_handle soc, 482 uint8_t vdev_id, 483 uint8_t *peer_mac) 484 { 485 if (!soc || !soc->ops || !soc->ops->peer_ops) { 486 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 487 "%s invalid instance", __func__); 488 return; 489 } 490 491 if (soc->ops->peer_ops->peer_detach_force_delete) 492 return soc->ops->peer_ops->peer_detach_force_delete(soc, 493 vdev_id, 494 peer_mac); 495 496 return; 497 } 498 499 /** 500 * is_cdp_peer_detach_force_delete_supported() - To check if force delete 501 * operation is supported 502 * @soc: pointer to SOC handle 503 * 504 * Some of the platforms support force delete operation and some of them 505 * don't. This API returns true if API which handles force delete operation 506 * is registered and false otherwise. 507 * 508 * Return: true if API which handles force delete operation is registered 509 * false in all other cases 510 */ 511 static inline bool 512 is_cdp_peer_detach_force_delete_supported(ol_txrx_soc_handle soc) 513 { 514 if (!soc || !soc->ops || !soc->ops->peer_ops) { 515 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 516 "%s invalid instance", __func__); 517 return false; 518 } 519 520 if (soc->ops->peer_ops->peer_detach_force_delete) 521 return true; 522 523 return false; 524 } 525 526 /** 527 * cdp_peer_set_peer_as_tdls() - To set peer as tdls peer 528 * @soc: pointer to SOC handle 529 * @vdev_id: virtual interface id 530 * @peer_mac: peer mac address 531 * @val: true or false 532 * 533 * Return: void 534 */ 535 static inline void 536 cdp_peer_set_peer_as_tdls(ol_txrx_soc_handle soc, uint8_t vdev_id, 537 uint8_t *peer_mac, bool val) 538 { 539 if (!soc || !soc->ops || !soc->ops->peer_ops) { 540 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 541 "%s invalid instance", __func__); 542 return; 543 } 544 545 if (soc->ops->peer_ops->set_peer_as_tdls_peer) 546 soc->ops->peer_ops->set_peer_as_tdls_peer(soc, vdev_id, 547 peer_mac, val); 548 } 549 550 /** 551 * cdp_peer_set_tdls_offchan_enabled() - Set tdls offchan operation as enabled 552 * @soc: pointer to SOC handle 553 * @vdev_id: virtual interface id 554 * @peer_mac: peer mac address 555 * @val: true or false 556 * 557 * update tdls_offchan_enabled 558 * 559 * Return: none 560 */ 561 static inline void 562 cdp_peer_set_tdls_offchan_enabled(ol_txrx_soc_handle soc, uint8_t vdev_id, 563 uint8_t *peer_mac, bool val) 564 { 565 if (!soc || !soc->ops || !soc->ops->peer_ops) { 566 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 567 "%s invalid instance", __func__); 568 return; 569 } 570 571 if (soc->ops->peer_ops->set_tdls_offchan_enabled) 572 soc->ops->peer_ops->set_tdls_offchan_enabled(soc, vdev_id, 573 peer_mac, val); 574 } 575 576 /** 577 * cdp_peer_flush_frags() - Flush frags on peer 578 * @soc: data path soc handle 579 * @vdev_id: virtual interface id 580 * @peer_mac: peer mac addr 581 * 582 * Return: None 583 */ 584 static inline void 585 cdp_peer_flush_frags(ol_txrx_soc_handle soc, uint8_t vdev_id, uint8_t *peer_mac) 586 { 587 if (!soc || !soc->ops || !soc->ops->peer_ops) { 588 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL, 589 "%s invalid instance", __func__); 590 return; 591 } 592 593 if (soc->ops->peer_ops->peer_flush_frags) 594 soc->ops->peer_ops->peer_flush_frags(soc, vdev_id, peer_mac); 595 } 596 #endif /* _CDP_TXRX_PEER_H_ */ 597