1 #ifndef __MAC80211_DRIVER_OPS 2 #define __MAC80211_DRIVER_OPS 3 4 #include <net/mac80211.h> 5 #include "ieee80211_i.h" 6 #include "trace.h" 7 8 static inline bool check_sdata_in_driver(struct ieee80211_sub_if_data *sdata) 9 { 10 return !WARN(!(sdata->flags & IEEE80211_SDATA_IN_DRIVER), 11 "%s: Failed check-sdata-in-driver check, flags: 0x%x\n", 12 sdata->dev ? sdata->dev->name : sdata->name, sdata->flags); 13 } 14 15 static inline struct ieee80211_sub_if_data * 16 get_bss_sdata(struct ieee80211_sub_if_data *sdata) 17 { 18 if (sdata->vif.type == NL80211_IFTYPE_AP_VLAN) 19 sdata = container_of(sdata->bss, struct ieee80211_sub_if_data, 20 u.ap); 21 22 return sdata; 23 } 24 25 static inline void drv_tx(struct ieee80211_local *local, 26 struct ieee80211_tx_control *control, 27 struct sk_buff *skb) 28 { 29 local->ops->tx(&local->hw, control, skb); 30 } 31 32 static inline void drv_get_et_strings(struct ieee80211_sub_if_data *sdata, 33 u32 sset, u8 *data) 34 { 35 struct ieee80211_local *local = sdata->local; 36 if (local->ops->get_et_strings) { 37 trace_drv_get_et_strings(local, sset); 38 local->ops->get_et_strings(&local->hw, &sdata->vif, sset, data); 39 trace_drv_return_void(local); 40 } 41 } 42 43 static inline void drv_get_et_stats(struct ieee80211_sub_if_data *sdata, 44 struct ethtool_stats *stats, 45 u64 *data) 46 { 47 struct ieee80211_local *local = sdata->local; 48 if (local->ops->get_et_stats) { 49 trace_drv_get_et_stats(local); 50 local->ops->get_et_stats(&local->hw, &sdata->vif, stats, data); 51 trace_drv_return_void(local); 52 } 53 } 54 55 static inline int drv_get_et_sset_count(struct ieee80211_sub_if_data *sdata, 56 int sset) 57 { 58 struct ieee80211_local *local = sdata->local; 59 int rv = 0; 60 if (local->ops->get_et_sset_count) { 61 trace_drv_get_et_sset_count(local, sset); 62 rv = local->ops->get_et_sset_count(&local->hw, &sdata->vif, 63 sset); 64 trace_drv_return_int(local, rv); 65 } 66 return rv; 67 } 68 69 static inline int drv_start(struct ieee80211_local *local) 70 { 71 int ret; 72 73 might_sleep(); 74 75 trace_drv_start(local); 76 local->started = true; 77 smp_mb(); 78 ret = local->ops->start(&local->hw); 79 trace_drv_return_int(local, ret); 80 return ret; 81 } 82 83 static inline void drv_stop(struct ieee80211_local *local) 84 { 85 might_sleep(); 86 87 trace_drv_stop(local); 88 local->ops->stop(&local->hw); 89 trace_drv_return_void(local); 90 91 /* sync away all work on the tasklet before clearing started */ 92 tasklet_disable(&local->tasklet); 93 tasklet_enable(&local->tasklet); 94 95 barrier(); 96 97 local->started = false; 98 } 99 100 #ifdef CONFIG_PM 101 static inline int drv_suspend(struct ieee80211_local *local, 102 struct cfg80211_wowlan *wowlan) 103 { 104 int ret; 105 106 might_sleep(); 107 108 trace_drv_suspend(local); 109 ret = local->ops->suspend(&local->hw, wowlan); 110 trace_drv_return_int(local, ret); 111 return ret; 112 } 113 114 static inline int drv_resume(struct ieee80211_local *local) 115 { 116 int ret; 117 118 might_sleep(); 119 120 trace_drv_resume(local); 121 ret = local->ops->resume(&local->hw); 122 trace_drv_return_int(local, ret); 123 return ret; 124 } 125 126 static inline void drv_set_wakeup(struct ieee80211_local *local, 127 bool enabled) 128 { 129 might_sleep(); 130 131 if (!local->ops->set_wakeup) 132 return; 133 134 trace_drv_set_wakeup(local, enabled); 135 local->ops->set_wakeup(&local->hw, enabled); 136 trace_drv_return_void(local); 137 } 138 #endif 139 140 static inline int drv_add_interface(struct ieee80211_local *local, 141 struct ieee80211_sub_if_data *sdata) 142 { 143 int ret; 144 145 might_sleep(); 146 147 if (WARN_ON(sdata->vif.type == NL80211_IFTYPE_AP_VLAN || 148 (sdata->vif.type == NL80211_IFTYPE_MONITOR && 149 !(local->hw.flags & IEEE80211_HW_WANT_MONITOR_VIF) && 150 !(sdata->u.mntr_flags & MONITOR_FLAG_ACTIVE)))) 151 return -EINVAL; 152 153 trace_drv_add_interface(local, sdata); 154 ret = local->ops->add_interface(&local->hw, &sdata->vif); 155 trace_drv_return_int(local, ret); 156 157 if (ret == 0) 158 sdata->flags |= IEEE80211_SDATA_IN_DRIVER; 159 160 return ret; 161 } 162 163 static inline int drv_change_interface(struct ieee80211_local *local, 164 struct ieee80211_sub_if_data *sdata, 165 enum nl80211_iftype type, bool p2p) 166 { 167 int ret; 168 169 might_sleep(); 170 171 if (!check_sdata_in_driver(sdata)) 172 return -EIO; 173 174 trace_drv_change_interface(local, sdata, type, p2p); 175 ret = local->ops->change_interface(&local->hw, &sdata->vif, type, p2p); 176 trace_drv_return_int(local, ret); 177 return ret; 178 } 179 180 static inline void drv_remove_interface(struct ieee80211_local *local, 181 struct ieee80211_sub_if_data *sdata) 182 { 183 might_sleep(); 184 185 if (!check_sdata_in_driver(sdata)) 186 return; 187 188 trace_drv_remove_interface(local, sdata); 189 local->ops->remove_interface(&local->hw, &sdata->vif); 190 sdata->flags &= ~IEEE80211_SDATA_IN_DRIVER; 191 trace_drv_return_void(local); 192 } 193 194 static inline int drv_config(struct ieee80211_local *local, u32 changed) 195 { 196 int ret; 197 198 might_sleep(); 199 200 trace_drv_config(local, changed); 201 ret = local->ops->config(&local->hw, changed); 202 trace_drv_return_int(local, ret); 203 return ret; 204 } 205 206 static inline void drv_bss_info_changed(struct ieee80211_local *local, 207 struct ieee80211_sub_if_data *sdata, 208 struct ieee80211_bss_conf *info, 209 u32 changed) 210 { 211 might_sleep(); 212 213 if (WARN_ON_ONCE(changed & (BSS_CHANGED_BEACON | 214 BSS_CHANGED_BEACON_ENABLED) && 215 sdata->vif.type != NL80211_IFTYPE_AP && 216 sdata->vif.type != NL80211_IFTYPE_ADHOC && 217 sdata->vif.type != NL80211_IFTYPE_MESH_POINT && 218 sdata->vif.type != NL80211_IFTYPE_OCB)) 219 return; 220 221 if (WARN_ON_ONCE(sdata->vif.type == NL80211_IFTYPE_P2P_DEVICE || 222 sdata->vif.type == NL80211_IFTYPE_MONITOR)) 223 return; 224 225 if (!check_sdata_in_driver(sdata)) 226 return; 227 228 trace_drv_bss_info_changed(local, sdata, info, changed); 229 if (local->ops->bss_info_changed) 230 local->ops->bss_info_changed(&local->hw, &sdata->vif, info, changed); 231 trace_drv_return_void(local); 232 } 233 234 static inline u64 drv_prepare_multicast(struct ieee80211_local *local, 235 struct netdev_hw_addr_list *mc_list) 236 { 237 u64 ret = 0; 238 239 trace_drv_prepare_multicast(local, mc_list->count); 240 241 if (local->ops->prepare_multicast) 242 ret = local->ops->prepare_multicast(&local->hw, mc_list); 243 244 trace_drv_return_u64(local, ret); 245 246 return ret; 247 } 248 249 static inline void drv_configure_filter(struct ieee80211_local *local, 250 unsigned int changed_flags, 251 unsigned int *total_flags, 252 u64 multicast) 253 { 254 might_sleep(); 255 256 trace_drv_configure_filter(local, changed_flags, total_flags, 257 multicast); 258 local->ops->configure_filter(&local->hw, changed_flags, total_flags, 259 multicast); 260 trace_drv_return_void(local); 261 } 262 263 static inline int drv_set_tim(struct ieee80211_local *local, 264 struct ieee80211_sta *sta, bool set) 265 { 266 int ret = 0; 267 trace_drv_set_tim(local, sta, set); 268 if (local->ops->set_tim) 269 ret = local->ops->set_tim(&local->hw, sta, set); 270 trace_drv_return_int(local, ret); 271 return ret; 272 } 273 274 static inline int drv_set_key(struct ieee80211_local *local, 275 enum set_key_cmd cmd, 276 struct ieee80211_sub_if_data *sdata, 277 struct ieee80211_sta *sta, 278 struct ieee80211_key_conf *key) 279 { 280 int ret; 281 282 might_sleep(); 283 284 sdata = get_bss_sdata(sdata); 285 if (!check_sdata_in_driver(sdata)) 286 return -EIO; 287 288 trace_drv_set_key(local, cmd, sdata, sta, key); 289 ret = local->ops->set_key(&local->hw, cmd, &sdata->vif, sta, key); 290 trace_drv_return_int(local, ret); 291 return ret; 292 } 293 294 static inline void drv_update_tkip_key(struct ieee80211_local *local, 295 struct ieee80211_sub_if_data *sdata, 296 struct ieee80211_key_conf *conf, 297 struct sta_info *sta, u32 iv32, 298 u16 *phase1key) 299 { 300 struct ieee80211_sta *ista = NULL; 301 302 if (sta) 303 ista = &sta->sta; 304 305 sdata = get_bss_sdata(sdata); 306 if (!check_sdata_in_driver(sdata)) 307 return; 308 309 trace_drv_update_tkip_key(local, sdata, conf, ista, iv32); 310 if (local->ops->update_tkip_key) 311 local->ops->update_tkip_key(&local->hw, &sdata->vif, conf, 312 ista, iv32, phase1key); 313 trace_drv_return_void(local); 314 } 315 316 static inline int drv_hw_scan(struct ieee80211_local *local, 317 struct ieee80211_sub_if_data *sdata, 318 struct ieee80211_scan_request *req) 319 { 320 int ret; 321 322 might_sleep(); 323 324 if (!check_sdata_in_driver(sdata)) 325 return -EIO; 326 327 trace_drv_hw_scan(local, sdata); 328 ret = local->ops->hw_scan(&local->hw, &sdata->vif, req); 329 trace_drv_return_int(local, ret); 330 return ret; 331 } 332 333 static inline void drv_cancel_hw_scan(struct ieee80211_local *local, 334 struct ieee80211_sub_if_data *sdata) 335 { 336 might_sleep(); 337 338 if (!check_sdata_in_driver(sdata)) 339 return; 340 341 trace_drv_cancel_hw_scan(local, sdata); 342 local->ops->cancel_hw_scan(&local->hw, &sdata->vif); 343 trace_drv_return_void(local); 344 } 345 346 static inline int 347 drv_sched_scan_start(struct ieee80211_local *local, 348 struct ieee80211_sub_if_data *sdata, 349 struct cfg80211_sched_scan_request *req, 350 struct ieee80211_scan_ies *ies) 351 { 352 int ret; 353 354 might_sleep(); 355 356 if (!check_sdata_in_driver(sdata)) 357 return -EIO; 358 359 trace_drv_sched_scan_start(local, sdata); 360 ret = local->ops->sched_scan_start(&local->hw, &sdata->vif, 361 req, ies); 362 trace_drv_return_int(local, ret); 363 return ret; 364 } 365 366 static inline int drv_sched_scan_stop(struct ieee80211_local *local, 367 struct ieee80211_sub_if_data *sdata) 368 { 369 int ret; 370 371 might_sleep(); 372 373 if (!check_sdata_in_driver(sdata)) 374 return -EIO; 375 376 trace_drv_sched_scan_stop(local, sdata); 377 ret = local->ops->sched_scan_stop(&local->hw, &sdata->vif); 378 trace_drv_return_int(local, ret); 379 380 return ret; 381 } 382 383 static inline void drv_sw_scan_start(struct ieee80211_local *local, 384 struct ieee80211_sub_if_data *sdata, 385 const u8 *mac_addr) 386 { 387 might_sleep(); 388 389 trace_drv_sw_scan_start(local, sdata, mac_addr); 390 if (local->ops->sw_scan_start) 391 local->ops->sw_scan_start(&local->hw, &sdata->vif, mac_addr); 392 trace_drv_return_void(local); 393 } 394 395 static inline void drv_sw_scan_complete(struct ieee80211_local *local, 396 struct ieee80211_sub_if_data *sdata) 397 { 398 might_sleep(); 399 400 trace_drv_sw_scan_complete(local, sdata); 401 if (local->ops->sw_scan_complete) 402 local->ops->sw_scan_complete(&local->hw, &sdata->vif); 403 trace_drv_return_void(local); 404 } 405 406 static inline int drv_get_stats(struct ieee80211_local *local, 407 struct ieee80211_low_level_stats *stats) 408 { 409 int ret = -EOPNOTSUPP; 410 411 might_sleep(); 412 413 if (local->ops->get_stats) 414 ret = local->ops->get_stats(&local->hw, stats); 415 trace_drv_get_stats(local, stats, ret); 416 417 return ret; 418 } 419 420 static inline void drv_get_tkip_seq(struct ieee80211_local *local, 421 u8 hw_key_idx, u32 *iv32, u16 *iv16) 422 { 423 if (local->ops->get_tkip_seq) 424 local->ops->get_tkip_seq(&local->hw, hw_key_idx, iv32, iv16); 425 trace_drv_get_tkip_seq(local, hw_key_idx, iv32, iv16); 426 } 427 428 static inline int drv_set_frag_threshold(struct ieee80211_local *local, 429 u32 value) 430 { 431 int ret = 0; 432 433 might_sleep(); 434 435 trace_drv_set_frag_threshold(local, value); 436 if (local->ops->set_frag_threshold) 437 ret = local->ops->set_frag_threshold(&local->hw, value); 438 trace_drv_return_int(local, ret); 439 return ret; 440 } 441 442 static inline int drv_set_rts_threshold(struct ieee80211_local *local, 443 u32 value) 444 { 445 int ret = 0; 446 447 might_sleep(); 448 449 trace_drv_set_rts_threshold(local, value); 450 if (local->ops->set_rts_threshold) 451 ret = local->ops->set_rts_threshold(&local->hw, value); 452 trace_drv_return_int(local, ret); 453 return ret; 454 } 455 456 static inline int drv_set_coverage_class(struct ieee80211_local *local, 457 s16 value) 458 { 459 int ret = 0; 460 might_sleep(); 461 462 trace_drv_set_coverage_class(local, value); 463 if (local->ops->set_coverage_class) 464 local->ops->set_coverage_class(&local->hw, value); 465 else 466 ret = -EOPNOTSUPP; 467 468 trace_drv_return_int(local, ret); 469 return ret; 470 } 471 472 static inline void drv_sta_notify(struct ieee80211_local *local, 473 struct ieee80211_sub_if_data *sdata, 474 enum sta_notify_cmd cmd, 475 struct ieee80211_sta *sta) 476 { 477 sdata = get_bss_sdata(sdata); 478 if (!check_sdata_in_driver(sdata)) 479 return; 480 481 trace_drv_sta_notify(local, sdata, cmd, sta); 482 if (local->ops->sta_notify) 483 local->ops->sta_notify(&local->hw, &sdata->vif, cmd, sta); 484 trace_drv_return_void(local); 485 } 486 487 static inline int drv_sta_add(struct ieee80211_local *local, 488 struct ieee80211_sub_if_data *sdata, 489 struct ieee80211_sta *sta) 490 { 491 int ret = 0; 492 493 might_sleep(); 494 495 sdata = get_bss_sdata(sdata); 496 if (!check_sdata_in_driver(sdata)) 497 return -EIO; 498 499 trace_drv_sta_add(local, sdata, sta); 500 if (local->ops->sta_add) 501 ret = local->ops->sta_add(&local->hw, &sdata->vif, sta); 502 503 trace_drv_return_int(local, ret); 504 505 return ret; 506 } 507 508 static inline void drv_sta_remove(struct ieee80211_local *local, 509 struct ieee80211_sub_if_data *sdata, 510 struct ieee80211_sta *sta) 511 { 512 might_sleep(); 513 514 sdata = get_bss_sdata(sdata); 515 if (!check_sdata_in_driver(sdata)) 516 return; 517 518 trace_drv_sta_remove(local, sdata, sta); 519 if (local->ops->sta_remove) 520 local->ops->sta_remove(&local->hw, &sdata->vif, sta); 521 522 trace_drv_return_void(local); 523 } 524 525 #ifdef CONFIG_MAC80211_DEBUGFS 526 static inline void drv_sta_add_debugfs(struct ieee80211_local *local, 527 struct ieee80211_sub_if_data *sdata, 528 struct ieee80211_sta *sta, 529 struct dentry *dir) 530 { 531 might_sleep(); 532 533 sdata = get_bss_sdata(sdata); 534 if (!check_sdata_in_driver(sdata)) 535 return; 536 537 if (local->ops->sta_add_debugfs) 538 local->ops->sta_add_debugfs(&local->hw, &sdata->vif, 539 sta, dir); 540 } 541 542 static inline void drv_sta_remove_debugfs(struct ieee80211_local *local, 543 struct ieee80211_sub_if_data *sdata, 544 struct ieee80211_sta *sta, 545 struct dentry *dir) 546 { 547 might_sleep(); 548 549 sdata = get_bss_sdata(sdata); 550 check_sdata_in_driver(sdata); 551 552 if (local->ops->sta_remove_debugfs) 553 local->ops->sta_remove_debugfs(&local->hw, &sdata->vif, 554 sta, dir); 555 } 556 #endif 557 558 static inline void drv_sta_pre_rcu_remove(struct ieee80211_local *local, 559 struct ieee80211_sub_if_data *sdata, 560 struct sta_info *sta) 561 { 562 might_sleep(); 563 564 sdata = get_bss_sdata(sdata); 565 if (!check_sdata_in_driver(sdata)) 566 return; 567 568 trace_drv_sta_pre_rcu_remove(local, sdata, &sta->sta); 569 if (local->ops->sta_pre_rcu_remove) 570 local->ops->sta_pre_rcu_remove(&local->hw, &sdata->vif, 571 &sta->sta); 572 trace_drv_return_void(local); 573 } 574 575 static inline __must_check 576 int drv_sta_state(struct ieee80211_local *local, 577 struct ieee80211_sub_if_data *sdata, 578 struct sta_info *sta, 579 enum ieee80211_sta_state old_state, 580 enum ieee80211_sta_state new_state) 581 { 582 int ret = 0; 583 584 might_sleep(); 585 586 sdata = get_bss_sdata(sdata); 587 if (!check_sdata_in_driver(sdata)) 588 return -EIO; 589 590 trace_drv_sta_state(local, sdata, &sta->sta, old_state, new_state); 591 if (local->ops->sta_state) { 592 ret = local->ops->sta_state(&local->hw, &sdata->vif, &sta->sta, 593 old_state, new_state); 594 } else if (old_state == IEEE80211_STA_AUTH && 595 new_state == IEEE80211_STA_ASSOC) { 596 ret = drv_sta_add(local, sdata, &sta->sta); 597 if (ret == 0) 598 sta->uploaded = true; 599 } else if (old_state == IEEE80211_STA_ASSOC && 600 new_state == IEEE80211_STA_AUTH) { 601 drv_sta_remove(local, sdata, &sta->sta); 602 } 603 trace_drv_return_int(local, ret); 604 return ret; 605 } 606 607 static inline void drv_sta_rc_update(struct ieee80211_local *local, 608 struct ieee80211_sub_if_data *sdata, 609 struct ieee80211_sta *sta, u32 changed) 610 { 611 sdata = get_bss_sdata(sdata); 612 if (!check_sdata_in_driver(sdata)) 613 return; 614 615 WARN_ON(changed & IEEE80211_RC_SUPP_RATES_CHANGED && 616 (sdata->vif.type != NL80211_IFTYPE_ADHOC && 617 sdata->vif.type != NL80211_IFTYPE_MESH_POINT)); 618 619 trace_drv_sta_rc_update(local, sdata, sta, changed); 620 if (local->ops->sta_rc_update) 621 local->ops->sta_rc_update(&local->hw, &sdata->vif, 622 sta, changed); 623 624 trace_drv_return_void(local); 625 } 626 627 static inline void drv_sta_rate_tbl_update(struct ieee80211_local *local, 628 struct ieee80211_sub_if_data *sdata, 629 struct ieee80211_sta *sta) 630 { 631 sdata = get_bss_sdata(sdata); 632 if (!check_sdata_in_driver(sdata)) 633 return; 634 635 trace_drv_sta_rate_tbl_update(local, sdata, sta); 636 if (local->ops->sta_rate_tbl_update) 637 local->ops->sta_rate_tbl_update(&local->hw, &sdata->vif, sta); 638 639 trace_drv_return_void(local); 640 } 641 642 static inline void drv_sta_statistics(struct ieee80211_local *local, 643 struct ieee80211_sub_if_data *sdata, 644 struct ieee80211_sta *sta, 645 struct station_info *sinfo) 646 { 647 sdata = get_bss_sdata(sdata); 648 if (!check_sdata_in_driver(sdata)) 649 return; 650 651 trace_drv_sta_statistics(local, sdata, sta); 652 if (local->ops->sta_statistics) 653 local->ops->sta_statistics(&local->hw, &sdata->vif, sta, sinfo); 654 trace_drv_return_void(local); 655 } 656 657 static inline int drv_conf_tx(struct ieee80211_local *local, 658 struct ieee80211_sub_if_data *sdata, u16 ac, 659 const struct ieee80211_tx_queue_params *params) 660 { 661 int ret = -EOPNOTSUPP; 662 663 might_sleep(); 664 665 if (!check_sdata_in_driver(sdata)) 666 return -EIO; 667 668 if (WARN_ONCE(params->cw_min == 0 || 669 params->cw_min > params->cw_max, 670 "%s: invalid CW_min/CW_max: %d/%d\n", 671 sdata->name, params->cw_min, params->cw_max)) 672 return -EINVAL; 673 674 trace_drv_conf_tx(local, sdata, ac, params); 675 if (local->ops->conf_tx) 676 ret = local->ops->conf_tx(&local->hw, &sdata->vif, 677 ac, params); 678 trace_drv_return_int(local, ret); 679 return ret; 680 } 681 682 static inline u64 drv_get_tsf(struct ieee80211_local *local, 683 struct ieee80211_sub_if_data *sdata) 684 { 685 u64 ret = -1ULL; 686 687 might_sleep(); 688 689 if (!check_sdata_in_driver(sdata)) 690 return ret; 691 692 trace_drv_get_tsf(local, sdata); 693 if (local->ops->get_tsf) 694 ret = local->ops->get_tsf(&local->hw, &sdata->vif); 695 trace_drv_return_u64(local, ret); 696 return ret; 697 } 698 699 static inline void drv_set_tsf(struct ieee80211_local *local, 700 struct ieee80211_sub_if_data *sdata, 701 u64 tsf) 702 { 703 might_sleep(); 704 705 if (!check_sdata_in_driver(sdata)) 706 return; 707 708 trace_drv_set_tsf(local, sdata, tsf); 709 if (local->ops->set_tsf) 710 local->ops->set_tsf(&local->hw, &sdata->vif, tsf); 711 trace_drv_return_void(local); 712 } 713 714 static inline void drv_reset_tsf(struct ieee80211_local *local, 715 struct ieee80211_sub_if_data *sdata) 716 { 717 might_sleep(); 718 719 if (!check_sdata_in_driver(sdata)) 720 return; 721 722 trace_drv_reset_tsf(local, sdata); 723 if (local->ops->reset_tsf) 724 local->ops->reset_tsf(&local->hw, &sdata->vif); 725 trace_drv_return_void(local); 726 } 727 728 static inline int drv_tx_last_beacon(struct ieee80211_local *local) 729 { 730 int ret = 0; /* default unsupported op for less congestion */ 731 732 might_sleep(); 733 734 trace_drv_tx_last_beacon(local); 735 if (local->ops->tx_last_beacon) 736 ret = local->ops->tx_last_beacon(&local->hw); 737 trace_drv_return_int(local, ret); 738 return ret; 739 } 740 741 static inline int drv_ampdu_action(struct ieee80211_local *local, 742 struct ieee80211_sub_if_data *sdata, 743 enum ieee80211_ampdu_mlme_action action, 744 struct ieee80211_sta *sta, u16 tid, 745 u16 *ssn, u8 buf_size) 746 { 747 int ret = -EOPNOTSUPP; 748 749 might_sleep(); 750 751 sdata = get_bss_sdata(sdata); 752 if (!check_sdata_in_driver(sdata)) 753 return -EIO; 754 755 trace_drv_ampdu_action(local, sdata, action, sta, tid, ssn, buf_size); 756 757 if (local->ops->ampdu_action) 758 ret = local->ops->ampdu_action(&local->hw, &sdata->vif, action, 759 sta, tid, ssn, buf_size); 760 761 trace_drv_return_int(local, ret); 762 763 return ret; 764 } 765 766 static inline int drv_get_survey(struct ieee80211_local *local, int idx, 767 struct survey_info *survey) 768 { 769 int ret = -EOPNOTSUPP; 770 771 trace_drv_get_survey(local, idx, survey); 772 773 if (local->ops->get_survey) 774 ret = local->ops->get_survey(&local->hw, idx, survey); 775 776 trace_drv_return_int(local, ret); 777 778 return ret; 779 } 780 781 static inline void drv_rfkill_poll(struct ieee80211_local *local) 782 { 783 might_sleep(); 784 785 if (local->ops->rfkill_poll) 786 local->ops->rfkill_poll(&local->hw); 787 } 788 789 static inline void drv_flush(struct ieee80211_local *local, 790 struct ieee80211_sub_if_data *sdata, 791 u32 queues, bool drop) 792 { 793 struct ieee80211_vif *vif = sdata ? &sdata->vif : NULL; 794 795 might_sleep(); 796 797 if (sdata && !check_sdata_in_driver(sdata)) 798 return; 799 800 trace_drv_flush(local, queues, drop); 801 if (local->ops->flush) 802 local->ops->flush(&local->hw, vif, queues, drop); 803 trace_drv_return_void(local); 804 } 805 806 static inline void drv_channel_switch(struct ieee80211_local *local, 807 struct ieee80211_sub_if_data *sdata, 808 struct ieee80211_channel_switch *ch_switch) 809 { 810 might_sleep(); 811 812 trace_drv_channel_switch(local, sdata, ch_switch); 813 local->ops->channel_switch(&local->hw, &sdata->vif, ch_switch); 814 trace_drv_return_void(local); 815 } 816 817 818 static inline int drv_set_antenna(struct ieee80211_local *local, 819 u32 tx_ant, u32 rx_ant) 820 { 821 int ret = -EOPNOTSUPP; 822 might_sleep(); 823 if (local->ops->set_antenna) 824 ret = local->ops->set_antenna(&local->hw, tx_ant, rx_ant); 825 trace_drv_set_antenna(local, tx_ant, rx_ant, ret); 826 return ret; 827 } 828 829 static inline int drv_get_antenna(struct ieee80211_local *local, 830 u32 *tx_ant, u32 *rx_ant) 831 { 832 int ret = -EOPNOTSUPP; 833 might_sleep(); 834 if (local->ops->get_antenna) 835 ret = local->ops->get_antenna(&local->hw, tx_ant, rx_ant); 836 trace_drv_get_antenna(local, *tx_ant, *rx_ant, ret); 837 return ret; 838 } 839 840 static inline int drv_remain_on_channel(struct ieee80211_local *local, 841 struct ieee80211_sub_if_data *sdata, 842 struct ieee80211_channel *chan, 843 unsigned int duration, 844 enum ieee80211_roc_type type) 845 { 846 int ret; 847 848 might_sleep(); 849 850 trace_drv_remain_on_channel(local, sdata, chan, duration, type); 851 ret = local->ops->remain_on_channel(&local->hw, &sdata->vif, 852 chan, duration, type); 853 trace_drv_return_int(local, ret); 854 855 return ret; 856 } 857 858 static inline int drv_cancel_remain_on_channel(struct ieee80211_local *local) 859 { 860 int ret; 861 862 might_sleep(); 863 864 trace_drv_cancel_remain_on_channel(local); 865 ret = local->ops->cancel_remain_on_channel(&local->hw); 866 trace_drv_return_int(local, ret); 867 868 return ret; 869 } 870 871 static inline int drv_set_ringparam(struct ieee80211_local *local, 872 u32 tx, u32 rx) 873 { 874 int ret = -ENOTSUPP; 875 876 might_sleep(); 877 878 trace_drv_set_ringparam(local, tx, rx); 879 if (local->ops->set_ringparam) 880 ret = local->ops->set_ringparam(&local->hw, tx, rx); 881 trace_drv_return_int(local, ret); 882 883 return ret; 884 } 885 886 static inline void drv_get_ringparam(struct ieee80211_local *local, 887 u32 *tx, u32 *tx_max, u32 *rx, u32 *rx_max) 888 { 889 might_sleep(); 890 891 trace_drv_get_ringparam(local, tx, tx_max, rx, rx_max); 892 if (local->ops->get_ringparam) 893 local->ops->get_ringparam(&local->hw, tx, tx_max, rx, rx_max); 894 trace_drv_return_void(local); 895 } 896 897 static inline bool drv_tx_frames_pending(struct ieee80211_local *local) 898 { 899 bool ret = false; 900 901 might_sleep(); 902 903 trace_drv_tx_frames_pending(local); 904 if (local->ops->tx_frames_pending) 905 ret = local->ops->tx_frames_pending(&local->hw); 906 trace_drv_return_bool(local, ret); 907 908 return ret; 909 } 910 911 static inline int drv_set_bitrate_mask(struct ieee80211_local *local, 912 struct ieee80211_sub_if_data *sdata, 913 const struct cfg80211_bitrate_mask *mask) 914 { 915 int ret = -EOPNOTSUPP; 916 917 might_sleep(); 918 919 if (!check_sdata_in_driver(sdata)) 920 return -EIO; 921 922 trace_drv_set_bitrate_mask(local, sdata, mask); 923 if (local->ops->set_bitrate_mask) 924 ret = local->ops->set_bitrate_mask(&local->hw, 925 &sdata->vif, mask); 926 trace_drv_return_int(local, ret); 927 928 return ret; 929 } 930 931 static inline void drv_set_rekey_data(struct ieee80211_local *local, 932 struct ieee80211_sub_if_data *sdata, 933 struct cfg80211_gtk_rekey_data *data) 934 { 935 if (!check_sdata_in_driver(sdata)) 936 return; 937 938 trace_drv_set_rekey_data(local, sdata, data); 939 if (local->ops->set_rekey_data) 940 local->ops->set_rekey_data(&local->hw, &sdata->vif, data); 941 trace_drv_return_void(local); 942 } 943 944 static inline void drv_rssi_callback(struct ieee80211_local *local, 945 struct ieee80211_sub_if_data *sdata, 946 const enum ieee80211_rssi_event event) 947 { 948 trace_drv_rssi_callback(local, sdata, event); 949 if (local->ops->rssi_callback) 950 local->ops->rssi_callback(&local->hw, &sdata->vif, event); 951 trace_drv_return_void(local); 952 } 953 954 static inline void 955 drv_release_buffered_frames(struct ieee80211_local *local, 956 struct sta_info *sta, u16 tids, int num_frames, 957 enum ieee80211_frame_release_type reason, 958 bool more_data) 959 { 960 trace_drv_release_buffered_frames(local, &sta->sta, tids, num_frames, 961 reason, more_data); 962 if (local->ops->release_buffered_frames) 963 local->ops->release_buffered_frames(&local->hw, &sta->sta, tids, 964 num_frames, reason, 965 more_data); 966 trace_drv_return_void(local); 967 } 968 969 static inline void 970 drv_allow_buffered_frames(struct ieee80211_local *local, 971 struct sta_info *sta, u16 tids, int num_frames, 972 enum ieee80211_frame_release_type reason, 973 bool more_data) 974 { 975 trace_drv_allow_buffered_frames(local, &sta->sta, tids, num_frames, 976 reason, more_data); 977 if (local->ops->allow_buffered_frames) 978 local->ops->allow_buffered_frames(&local->hw, &sta->sta, 979 tids, num_frames, reason, 980 more_data); 981 trace_drv_return_void(local); 982 } 983 984 static inline void drv_mgd_prepare_tx(struct ieee80211_local *local, 985 struct ieee80211_sub_if_data *sdata) 986 { 987 might_sleep(); 988 989 if (!check_sdata_in_driver(sdata)) 990 return; 991 WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION); 992 993 trace_drv_mgd_prepare_tx(local, sdata); 994 if (local->ops->mgd_prepare_tx) 995 local->ops->mgd_prepare_tx(&local->hw, &sdata->vif); 996 trace_drv_return_void(local); 997 } 998 999 static inline void 1000 drv_mgd_protect_tdls_discover(struct ieee80211_local *local, 1001 struct ieee80211_sub_if_data *sdata) 1002 { 1003 might_sleep(); 1004 1005 if (!check_sdata_in_driver(sdata)) 1006 return; 1007 WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION); 1008 1009 trace_drv_mgd_protect_tdls_discover(local, sdata); 1010 if (local->ops->mgd_protect_tdls_discover) 1011 local->ops->mgd_protect_tdls_discover(&local->hw, &sdata->vif); 1012 trace_drv_return_void(local); 1013 } 1014 1015 static inline int drv_add_chanctx(struct ieee80211_local *local, 1016 struct ieee80211_chanctx *ctx) 1017 { 1018 int ret = -EOPNOTSUPP; 1019 1020 trace_drv_add_chanctx(local, ctx); 1021 if (local->ops->add_chanctx) 1022 ret = local->ops->add_chanctx(&local->hw, &ctx->conf); 1023 trace_drv_return_int(local, ret); 1024 if (!ret) 1025 ctx->driver_present = true; 1026 1027 return ret; 1028 } 1029 1030 static inline void drv_remove_chanctx(struct ieee80211_local *local, 1031 struct ieee80211_chanctx *ctx) 1032 { 1033 if (WARN_ON(!ctx->driver_present)) 1034 return; 1035 1036 trace_drv_remove_chanctx(local, ctx); 1037 if (local->ops->remove_chanctx) 1038 local->ops->remove_chanctx(&local->hw, &ctx->conf); 1039 trace_drv_return_void(local); 1040 ctx->driver_present = false; 1041 } 1042 1043 static inline void drv_change_chanctx(struct ieee80211_local *local, 1044 struct ieee80211_chanctx *ctx, 1045 u32 changed) 1046 { 1047 trace_drv_change_chanctx(local, ctx, changed); 1048 if (local->ops->change_chanctx) { 1049 WARN_ON_ONCE(!ctx->driver_present); 1050 local->ops->change_chanctx(&local->hw, &ctx->conf, changed); 1051 } 1052 trace_drv_return_void(local); 1053 } 1054 1055 static inline int drv_assign_vif_chanctx(struct ieee80211_local *local, 1056 struct ieee80211_sub_if_data *sdata, 1057 struct ieee80211_chanctx *ctx) 1058 { 1059 int ret = 0; 1060 1061 if (!check_sdata_in_driver(sdata)) 1062 return -EIO; 1063 1064 trace_drv_assign_vif_chanctx(local, sdata, ctx); 1065 if (local->ops->assign_vif_chanctx) { 1066 WARN_ON_ONCE(!ctx->driver_present); 1067 ret = local->ops->assign_vif_chanctx(&local->hw, 1068 &sdata->vif, 1069 &ctx->conf); 1070 } 1071 trace_drv_return_int(local, ret); 1072 1073 return ret; 1074 } 1075 1076 static inline void drv_unassign_vif_chanctx(struct ieee80211_local *local, 1077 struct ieee80211_sub_if_data *sdata, 1078 struct ieee80211_chanctx *ctx) 1079 { 1080 if (!check_sdata_in_driver(sdata)) 1081 return; 1082 1083 trace_drv_unassign_vif_chanctx(local, sdata, ctx); 1084 if (local->ops->unassign_vif_chanctx) { 1085 WARN_ON_ONCE(!ctx->driver_present); 1086 local->ops->unassign_vif_chanctx(&local->hw, 1087 &sdata->vif, 1088 &ctx->conf); 1089 } 1090 trace_drv_return_void(local); 1091 } 1092 1093 static inline int 1094 drv_switch_vif_chanctx(struct ieee80211_local *local, 1095 struct ieee80211_vif_chanctx_switch *vifs, 1096 int n_vifs, 1097 enum ieee80211_chanctx_switch_mode mode) 1098 { 1099 int ret = 0; 1100 int i; 1101 1102 if (!local->ops->switch_vif_chanctx) 1103 return -EOPNOTSUPP; 1104 1105 for (i = 0; i < n_vifs; i++) { 1106 struct ieee80211_chanctx *new_ctx = 1107 container_of(vifs[i].new_ctx, 1108 struct ieee80211_chanctx, 1109 conf); 1110 struct ieee80211_chanctx *old_ctx = 1111 container_of(vifs[i].old_ctx, 1112 struct ieee80211_chanctx, 1113 conf); 1114 1115 WARN_ON_ONCE(!old_ctx->driver_present); 1116 WARN_ON_ONCE((mode == CHANCTX_SWMODE_SWAP_CONTEXTS && 1117 new_ctx->driver_present) || 1118 (mode == CHANCTX_SWMODE_REASSIGN_VIF && 1119 !new_ctx->driver_present)); 1120 } 1121 1122 trace_drv_switch_vif_chanctx(local, vifs, n_vifs, mode); 1123 ret = local->ops->switch_vif_chanctx(&local->hw, 1124 vifs, n_vifs, mode); 1125 trace_drv_return_int(local, ret); 1126 1127 if (!ret && mode == CHANCTX_SWMODE_SWAP_CONTEXTS) { 1128 for (i = 0; i < n_vifs; i++) { 1129 struct ieee80211_chanctx *new_ctx = 1130 container_of(vifs[i].new_ctx, 1131 struct ieee80211_chanctx, 1132 conf); 1133 struct ieee80211_chanctx *old_ctx = 1134 container_of(vifs[i].old_ctx, 1135 struct ieee80211_chanctx, 1136 conf); 1137 1138 new_ctx->driver_present = true; 1139 old_ctx->driver_present = false; 1140 } 1141 } 1142 1143 return ret; 1144 } 1145 1146 static inline int drv_start_ap(struct ieee80211_local *local, 1147 struct ieee80211_sub_if_data *sdata) 1148 { 1149 int ret = 0; 1150 1151 if (!check_sdata_in_driver(sdata)) 1152 return -EIO; 1153 1154 trace_drv_start_ap(local, sdata, &sdata->vif.bss_conf); 1155 if (local->ops->start_ap) 1156 ret = local->ops->start_ap(&local->hw, &sdata->vif); 1157 trace_drv_return_int(local, ret); 1158 return ret; 1159 } 1160 1161 static inline void drv_stop_ap(struct ieee80211_local *local, 1162 struct ieee80211_sub_if_data *sdata) 1163 { 1164 if (!check_sdata_in_driver(sdata)) 1165 return; 1166 1167 trace_drv_stop_ap(local, sdata); 1168 if (local->ops->stop_ap) 1169 local->ops->stop_ap(&local->hw, &sdata->vif); 1170 trace_drv_return_void(local); 1171 } 1172 1173 static inline void 1174 drv_reconfig_complete(struct ieee80211_local *local, 1175 enum ieee80211_reconfig_type reconfig_type) 1176 { 1177 might_sleep(); 1178 1179 trace_drv_reconfig_complete(local, reconfig_type); 1180 if (local->ops->reconfig_complete) 1181 local->ops->reconfig_complete(&local->hw, reconfig_type); 1182 trace_drv_return_void(local); 1183 } 1184 1185 static inline void 1186 drv_set_default_unicast_key(struct ieee80211_local *local, 1187 struct ieee80211_sub_if_data *sdata, 1188 int key_idx) 1189 { 1190 if (!check_sdata_in_driver(sdata)) 1191 return; 1192 1193 WARN_ON_ONCE(key_idx < -1 || key_idx > 3); 1194 1195 trace_drv_set_default_unicast_key(local, sdata, key_idx); 1196 if (local->ops->set_default_unicast_key) 1197 local->ops->set_default_unicast_key(&local->hw, &sdata->vif, 1198 key_idx); 1199 trace_drv_return_void(local); 1200 } 1201 1202 #if IS_ENABLED(CONFIG_IPV6) 1203 static inline void drv_ipv6_addr_change(struct ieee80211_local *local, 1204 struct ieee80211_sub_if_data *sdata, 1205 struct inet6_dev *idev) 1206 { 1207 trace_drv_ipv6_addr_change(local, sdata); 1208 if (local->ops->ipv6_addr_change) 1209 local->ops->ipv6_addr_change(&local->hw, &sdata->vif, idev); 1210 trace_drv_return_void(local); 1211 } 1212 #endif 1213 1214 static inline void 1215 drv_channel_switch_beacon(struct ieee80211_sub_if_data *sdata, 1216 struct cfg80211_chan_def *chandef) 1217 { 1218 struct ieee80211_local *local = sdata->local; 1219 1220 if (local->ops->channel_switch_beacon) { 1221 trace_drv_channel_switch_beacon(local, sdata, chandef); 1222 local->ops->channel_switch_beacon(&local->hw, &sdata->vif, 1223 chandef); 1224 } 1225 } 1226 1227 static inline int 1228 drv_pre_channel_switch(struct ieee80211_sub_if_data *sdata, 1229 struct ieee80211_channel_switch *ch_switch) 1230 { 1231 struct ieee80211_local *local = sdata->local; 1232 int ret = 0; 1233 1234 if (!check_sdata_in_driver(sdata)) 1235 return -EIO; 1236 1237 trace_drv_pre_channel_switch(local, sdata, ch_switch); 1238 if (local->ops->pre_channel_switch) 1239 ret = local->ops->pre_channel_switch(&local->hw, &sdata->vif, 1240 ch_switch); 1241 trace_drv_return_int(local, ret); 1242 return ret; 1243 } 1244 1245 static inline int 1246 drv_post_channel_switch(struct ieee80211_sub_if_data *sdata) 1247 { 1248 struct ieee80211_local *local = sdata->local; 1249 int ret = 0; 1250 1251 if (!check_sdata_in_driver(sdata)) 1252 return -EIO; 1253 1254 trace_drv_post_channel_switch(local, sdata); 1255 if (local->ops->post_channel_switch) 1256 ret = local->ops->post_channel_switch(&local->hw, &sdata->vif); 1257 trace_drv_return_int(local, ret); 1258 return ret; 1259 } 1260 1261 static inline int drv_join_ibss(struct ieee80211_local *local, 1262 struct ieee80211_sub_if_data *sdata) 1263 { 1264 int ret = 0; 1265 1266 might_sleep(); 1267 if (!check_sdata_in_driver(sdata)) 1268 return -EIO; 1269 1270 trace_drv_join_ibss(local, sdata, &sdata->vif.bss_conf); 1271 if (local->ops->join_ibss) 1272 ret = local->ops->join_ibss(&local->hw, &sdata->vif); 1273 trace_drv_return_int(local, ret); 1274 return ret; 1275 } 1276 1277 static inline void drv_leave_ibss(struct ieee80211_local *local, 1278 struct ieee80211_sub_if_data *sdata) 1279 { 1280 might_sleep(); 1281 if (!check_sdata_in_driver(sdata)) 1282 return; 1283 1284 trace_drv_leave_ibss(local, sdata); 1285 if (local->ops->leave_ibss) 1286 local->ops->leave_ibss(&local->hw, &sdata->vif); 1287 trace_drv_return_void(local); 1288 } 1289 1290 static inline u32 drv_get_expected_throughput(struct ieee80211_local *local, 1291 struct ieee80211_sta *sta) 1292 { 1293 u32 ret = 0; 1294 1295 trace_drv_get_expected_throughput(sta); 1296 if (local->ops->get_expected_throughput) 1297 ret = local->ops->get_expected_throughput(sta); 1298 trace_drv_return_u32(local, ret); 1299 1300 return ret; 1301 } 1302 1303 static inline int drv_get_txpower(struct ieee80211_local *local, 1304 struct ieee80211_sub_if_data *sdata, int *dbm) 1305 { 1306 int ret; 1307 1308 if (!local->ops->get_txpower) 1309 return -EOPNOTSUPP; 1310 1311 ret = local->ops->get_txpower(&local->hw, &sdata->vif, dbm); 1312 trace_drv_get_txpower(local, sdata, *dbm, ret); 1313 1314 return ret; 1315 } 1316 1317 static inline int 1318 drv_tdls_channel_switch(struct ieee80211_local *local, 1319 struct ieee80211_sub_if_data *sdata, 1320 struct ieee80211_sta *sta, u8 oper_class, 1321 struct cfg80211_chan_def *chandef, 1322 struct sk_buff *tmpl_skb, u32 ch_sw_tm_ie) 1323 { 1324 int ret; 1325 1326 might_sleep(); 1327 if (!check_sdata_in_driver(sdata)) 1328 return -EIO; 1329 1330 if (!local->ops->tdls_channel_switch) 1331 return -EOPNOTSUPP; 1332 1333 trace_drv_tdls_channel_switch(local, sdata, sta, oper_class, chandef); 1334 ret = local->ops->tdls_channel_switch(&local->hw, &sdata->vif, sta, 1335 oper_class, chandef, tmpl_skb, 1336 ch_sw_tm_ie); 1337 trace_drv_return_int(local, ret); 1338 return ret; 1339 } 1340 1341 static inline void 1342 drv_tdls_cancel_channel_switch(struct ieee80211_local *local, 1343 struct ieee80211_sub_if_data *sdata, 1344 struct ieee80211_sta *sta) 1345 { 1346 might_sleep(); 1347 if (!check_sdata_in_driver(sdata)) 1348 return; 1349 1350 if (!local->ops->tdls_cancel_channel_switch) 1351 return; 1352 1353 trace_drv_tdls_cancel_channel_switch(local, sdata, sta); 1354 local->ops->tdls_cancel_channel_switch(&local->hw, &sdata->vif, sta); 1355 trace_drv_return_void(local); 1356 } 1357 1358 static inline void 1359 drv_tdls_recv_channel_switch(struct ieee80211_local *local, 1360 struct ieee80211_sub_if_data *sdata, 1361 struct ieee80211_tdls_ch_sw_params *params) 1362 { 1363 trace_drv_tdls_recv_channel_switch(local, sdata, params); 1364 if (local->ops->tdls_recv_channel_switch) 1365 local->ops->tdls_recv_channel_switch(&local->hw, &sdata->vif, 1366 params); 1367 trace_drv_return_void(local); 1368 } 1369 1370 #endif /* __MAC80211_DRIVER_OPS */ 1371