1 /* 2 * Copyright (c) 2017-2018 The Linux Foundation. All rights reserved. 3 * 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 * @file wlan_reg_services_api.c 22 * @brief contains regulatory service functions 23 */ 24 25 26 #include <qdf_status.h> 27 #include <qdf_types.h> 28 #include <wlan_reg_services_api.h> 29 #include "../../core/src/reg_services.h" 30 #include "../../core/src/reg_priv.h" 31 #include "../../core/src/reg_db_parser.h" 32 33 /** 34 * wlan_reg_get_channel_list_with_power() - Provide the channel list with power 35 * @ch_list: pointer to the channel list. 36 * 37 * Return: QDF_STATUS 38 */ 39 QDF_STATUS wlan_reg_get_channel_list_with_power(struct wlan_objmgr_pdev *pdev, 40 struct channel_power *ch_list, 41 uint8_t *num_chan) 42 { 43 /* 44 * Update the channel list with channel information with power. 45 */ 46 return reg_get_channel_list_with_power(pdev, ch_list, num_chan); 47 } 48 49 /** 50 * wlan_reg_read_default_country() - Read the default country for the regdomain 51 * @country: pointer to the country code. 52 * 53 * Return: None 54 */ 55 QDF_STATUS wlan_reg_read_default_country(struct wlan_objmgr_psoc *psoc, 56 uint8_t *country) 57 { 58 /* 59 * Get the default country information 60 */ 61 return reg_read_default_country(psoc, country); 62 } 63 64 QDF_STATUS wlan_reg_read_current_country(struct wlan_objmgr_psoc *psoc, 65 uint8_t *country) 66 { 67 /* 68 * Get the current country information 69 */ 70 return reg_read_current_country(psoc, country); 71 } 72 73 /** 74 * wlan_reg_get_channel_state() - Get channel state from regulatory 75 * @ch: channel number. 76 * 77 * Return: channel state 78 */ 79 enum channel_state wlan_reg_get_channel_state(struct wlan_objmgr_pdev *pdev, 80 uint32_t ch) 81 { 82 /* 83 * Get channel state from regulatory 84 */ 85 return reg_get_channel_state(pdev, ch); 86 } 87 88 bool 89 wlan_reg_chan_has_dfs_attribute(struct wlan_objmgr_pdev *pdev, uint32_t ch) 90 { 91 return reg_chan_has_dfs_attribute(pdev, ch); 92 } 93 94 /** 95 * wlan_reg_get_5g_bonded_channel_state() - Get 5G bonded channel state 96 * @ch: channel number. 97 * @bw: channel band width 98 * 99 * Return: channel state 100 */ 101 enum channel_state wlan_reg_get_5g_bonded_channel_state( 102 struct wlan_objmgr_pdev *pdev, uint8_t ch, 103 enum phy_ch_width bw) 104 { 105 /* 106 * Get channel state from regulatory 107 */ 108 return reg_get_5g_bonded_channel_state(pdev, ch, bw); 109 } 110 111 /** 112 * wlan_reg_get_2g_bonded_channel_state() - Get 2G bonded channel state 113 * @ch: channel number. 114 * @bw: channel band width 115 * 116 * Return: channel state 117 */ 118 enum channel_state wlan_reg_get_2g_bonded_channel_state( 119 struct wlan_objmgr_pdev *pdev, uint8_t ch, 120 uint8_t sec_ch, enum phy_ch_width bw) 121 { 122 /* 123 * Get channel state from regulatory 124 */ 125 return reg_get_2g_bonded_channel_state(pdev, ch, sec_ch, bw); 126 } 127 128 /** 129 * wlan_reg_set_channel_params() - Sets channel parameteres for given bandwidth 130 * @ch: channel number. 131 * @ch_params: pointer to the channel parameters. 132 * 133 * Return: None 134 */ 135 void wlan_reg_set_channel_params(struct wlan_objmgr_pdev *pdev, uint8_t ch, 136 uint8_t sec_ch_2g, 137 struct ch_params *ch_params) 138 { 139 /* 140 * Set channel parameters like center frequency for a bonded channel 141 * state. Also return the maximum bandwidth supported by the channel. 142 */ 143 reg_set_channel_params(pdev, ch, sec_ch_2g, ch_params); 144 } 145 146 /** 147 * wlan_reg_get_dfs_region () - Get the current dfs region 148 * @dfs_reg: pointer to dfs region 149 * 150 * Return: Status 151 */ 152 QDF_STATUS wlan_reg_get_dfs_region(struct wlan_objmgr_pdev *pdev, 153 enum dfs_reg *dfs_reg) 154 { 155 /* 156 * Get the current dfs region 157 */ 158 reg_get_current_dfs_region(pdev, dfs_reg); 159 160 return QDF_STATUS_SUCCESS; 161 } 162 163 uint32_t wlan_reg_get_channel_reg_power(struct wlan_objmgr_pdev *pdev, 164 uint32_t chan_num) 165 { 166 return reg_get_channel_reg_power(pdev, chan_num); 167 } 168 169 /** 170 * wlan_reg_get_channel_freq() - get regulatory power for channel 171 * @chan_num: channel number 172 * 173 * Return: int 174 */ 175 uint32_t wlan_reg_get_channel_freq(struct wlan_objmgr_pdev *pdev, 176 uint32_t chan_num) 177 { 178 return reg_get_channel_freq(pdev, chan_num); 179 } 180 181 QDF_STATUS wlan_reg_get_current_chan_list(struct wlan_objmgr_pdev *pdev, 182 struct regulatory_channel *chan_list) 183 { 184 return reg_get_current_chan_list(pdev, chan_list); 185 } 186 187 /** 188 * wlan_reg_get_bw_value() - give bandwidth value 189 * bw: bandwidth enum 190 * 191 * Return: uint16_t 192 */ 193 uint16_t wlan_reg_get_bw_value(enum phy_ch_width bw) 194 { 195 return reg_get_bw_value(bw); 196 } 197 198 /** 199 * wlan_reg_get_bonded_channel_state() - Get 2G bonded channel state 200 * @ch: channel number. 201 * @bw: channel band width 202 * 203 * Return: channel state 204 */ 205 enum channel_state wlan_reg_get_bonded_channel_state( 206 struct wlan_objmgr_pdev *pdev, uint8_t ch, 207 enum phy_ch_width bw, uint8_t sec_ch) 208 { 209 if (WLAN_REG_IS_24GHZ_CH(ch)) 210 return reg_get_2g_bonded_channel_state(pdev, ch, 211 sec_ch, bw); 212 else 213 return reg_get_5g_bonded_channel_state(pdev, ch, 214 bw); 215 } 216 217 /** 218 * wlan_reg_set_dfs_region () - Get the current dfs region 219 * @dfs_reg: pointer to dfs region 220 * 221 * Return: None 222 */ 223 void wlan_reg_set_dfs_region(struct wlan_objmgr_pdev *pdev, 224 enum dfs_reg dfs_reg) 225 { 226 reg_set_dfs_region(pdev, dfs_reg); 227 } 228 229 QDF_STATUS wlan_reg_get_domain_from_country_code(v_REGDOMAIN_t *reg_domain_ptr, 230 const uint8_t *country_alpha2, enum country_src source) 231 { 232 233 return reg_get_domain_from_country_code(reg_domain_ptr, 234 country_alpha2, source); 235 } 236 237 238 uint16_t wlan_reg_dmn_get_opclass_from_channel(uint8_t *country, 239 uint8_t channel, 240 uint8_t offset) 241 { 242 return reg_dmn_get_opclass_from_channel(country, channel, 243 offset); 244 } 245 246 uint16_t wlan_reg_dmn_get_chanwidth_from_opclass(uint8_t *country, 247 uint8_t channel, 248 uint8_t opclass) 249 { 250 return reg_dmn_get_chanwidth_from_opclass(country, channel, 251 opclass); 252 } 253 254 uint16_t wlan_reg_dmn_set_curr_opclasses(uint8_t num_classes, 255 uint8_t *class) 256 { 257 return reg_dmn_set_curr_opclasses(num_classes, class); 258 } 259 260 uint16_t wlan_reg_dmn_get_curr_opclasses(uint8_t *num_classes, 261 uint8_t *class) 262 { 263 return reg_dmn_get_curr_opclasses(num_classes, class); 264 } 265 266 QDF_STATUS wlan_regulatory_init(void) 267 { 268 QDF_STATUS status; 269 270 status = wlan_objmgr_register_psoc_create_handler( 271 WLAN_UMAC_COMP_REGULATORY, 272 wlan_regulatory_psoc_obj_created_notification, NULL); 273 if (status != QDF_STATUS_SUCCESS) { 274 reg_err("failed to register reg psoc obj create handler"); 275 return status; 276 } 277 278 status = wlan_objmgr_register_psoc_destroy_handler( 279 WLAN_UMAC_COMP_REGULATORY, 280 wlan_regulatory_psoc_obj_destroyed_notification, NULL); 281 if (status != QDF_STATUS_SUCCESS) { 282 reg_err("failed to register reg psoc obj create handler"); 283 goto unreg_psoc_create; 284 } 285 286 status = wlan_objmgr_register_pdev_create_handler( 287 WLAN_UMAC_COMP_REGULATORY, 288 wlan_regulatory_pdev_obj_created_notification, NULL); 289 if (status != QDF_STATUS_SUCCESS) { 290 reg_err("failed to register reg psoc obj create handler"); 291 goto unreg_psoc_destroy; 292 } 293 294 status = wlan_objmgr_register_pdev_destroy_handler( 295 WLAN_UMAC_COMP_REGULATORY, 296 wlan_regulatory_pdev_obj_destroyed_notification, NULL); 297 if (status != QDF_STATUS_SUCCESS) { 298 reg_err("failed to register reg psoc obj create handler"); 299 goto unreg_pdev_create; 300 } 301 302 reg_debug("regulatory handlers registered with obj mgr"); 303 304 return status; 305 306 unreg_pdev_create: 307 status = wlan_objmgr_unregister_pdev_create_handler( 308 WLAN_UMAC_COMP_REGULATORY, 309 wlan_regulatory_pdev_obj_created_notification, 310 NULL); 311 312 unreg_psoc_destroy: 313 status = wlan_objmgr_unregister_psoc_destroy_handler( 314 WLAN_UMAC_COMP_REGULATORY, 315 wlan_regulatory_psoc_obj_destroyed_notification, 316 NULL); 317 318 unreg_psoc_create: 319 status = wlan_objmgr_unregister_psoc_create_handler( 320 WLAN_UMAC_COMP_REGULATORY, 321 wlan_regulatory_psoc_obj_created_notification, 322 NULL); 323 324 return QDF_STATUS_E_FAILURE; 325 } 326 327 QDF_STATUS wlan_regulatory_deinit(void) 328 { 329 QDF_STATUS status, ret_status = QDF_STATUS_SUCCESS; 330 331 status = wlan_objmgr_unregister_pdev_destroy_handler( 332 WLAN_UMAC_COMP_REGULATORY, 333 wlan_regulatory_pdev_obj_destroyed_notification, NULL); 334 if (status != QDF_STATUS_SUCCESS) { 335 reg_err("failed to unregister reg pdev obj destroy handler"); 336 ret_status = status; 337 } 338 339 status = wlan_objmgr_unregister_pdev_create_handler( 340 WLAN_UMAC_COMP_REGULATORY, 341 wlan_regulatory_pdev_obj_created_notification, NULL); 342 if (status != QDF_STATUS_SUCCESS) { 343 reg_err("failed to unregister reg pdev obj create handler"); 344 ret_status = status; 345 } 346 347 status = wlan_objmgr_unregister_psoc_destroy_handler( 348 WLAN_UMAC_COMP_REGULATORY, 349 wlan_regulatory_psoc_obj_destroyed_notification, NULL); 350 if (status != QDF_STATUS_SUCCESS) { 351 reg_err("failed to unregister reg psoc obj destroy handler"); 352 ret_status = status; 353 } 354 355 status = wlan_objmgr_unregister_psoc_create_handler( 356 WLAN_UMAC_COMP_REGULATORY, 357 wlan_regulatory_psoc_obj_created_notification, NULL); 358 if (status != QDF_STATUS_SUCCESS) { 359 reg_err("failed to unregister reg psoc obj create handler"); 360 ret_status = status; 361 } 362 363 reg_debug("deregistered callbacks with obj mgr"); 364 365 return ret_status; 366 } 367 368 QDF_STATUS regulatory_psoc_open(struct wlan_objmgr_psoc *psoc) 369 { 370 struct wlan_lmac_if_reg_tx_ops *tx_ops; 371 372 tx_ops = reg_get_psoc_tx_ops(psoc); 373 if (tx_ops->register_master_handler) 374 tx_ops->register_master_handler(psoc, NULL); 375 if (tx_ops->register_11d_new_cc_handler) 376 tx_ops->register_11d_new_cc_handler(psoc, NULL); 377 if (tx_ops->register_ch_avoid_event_handler) 378 tx_ops->register_ch_avoid_event_handler(psoc, NULL); 379 380 return QDF_STATUS_SUCCESS; 381 } 382 383 QDF_STATUS regulatory_psoc_close(struct wlan_objmgr_psoc *psoc) 384 { 385 struct wlan_lmac_if_reg_tx_ops *tx_ops; 386 struct wlan_regulatory_psoc_priv_obj *soc_reg; 387 uint8_t i; 388 389 tx_ops = reg_get_psoc_tx_ops(psoc); 390 if (tx_ops->unregister_11d_new_cc_handler) 391 tx_ops->unregister_11d_new_cc_handler(psoc, NULL); 392 if (tx_ops->unregister_master_handler) 393 tx_ops->unregister_master_handler(psoc, NULL); 394 if (tx_ops->unregister_ch_avoid_event_handler) 395 tx_ops->unregister_ch_avoid_event_handler(psoc, NULL); 396 397 soc_reg = reg_get_psoc_obj(psoc); 398 399 if (!soc_reg) { 400 reg_err("reg psoc private obj is NULL"); 401 return QDF_STATUS_E_FAULT; 402 } 403 for (i = 0; i < PSOC_MAX_PHY_REG_CAP; i++) 404 reg_reset_reg_rules(&soc_reg->mas_chan_params[i].reg_rules); 405 406 return QDF_STATUS_SUCCESS; 407 } 408 409 QDF_STATUS regulatory_pdev_open(struct wlan_objmgr_pdev *pdev) 410 { 411 struct wlan_objmgr_psoc *parent_psoc; 412 QDF_STATUS status; 413 414 parent_psoc = wlan_pdev_get_psoc(pdev); 415 416 status = reg_send_scheduler_msg_sb(parent_psoc, pdev); 417 418 if (QDF_IS_STATUS_ERROR(status)) 419 reg_err("scheduler send msg failed"); 420 421 return status; 422 } 423 424 QDF_STATUS regulatory_pdev_close(struct wlan_objmgr_pdev *pdev) 425 { 426 struct wlan_objmgr_psoc *psoc; 427 struct wlan_regulatory_psoc_priv_obj *soc_reg; 428 429 psoc = wlan_pdev_get_psoc(pdev); 430 soc_reg = reg_get_psoc_obj(psoc); 431 if (!soc_reg) { 432 reg_err("reg psoc private obj is NULL"); 433 return QDF_STATUS_E_FAULT; 434 } 435 436 reg_reset_ctry_pending_hints(soc_reg); 437 438 return QDF_STATUS_SUCCESS; 439 } 440 441 void wlan_reg_update_nol_ch(struct wlan_objmgr_pdev *pdev, uint8_t *ch_list, 442 uint8_t num_ch, bool nol_ch) 443 { 444 reg_update_nol_ch(pdev, ch_list, num_ch, nol_ch); 445 } 446 447 void wlan_reg_update_nol_history_ch(struct wlan_objmgr_pdev *pdev, 448 uint8_t *ch_list, uint8_t num_ch, 449 bool nol_history_ch) 450 { 451 reg_update_nol_history_ch(pdev, ch_list, num_ch, nol_history_ch); 452 } 453 454 bool wlan_reg_is_dfs_ch(struct wlan_objmgr_pdev *pdev, 455 uint32_t chan) 456 { 457 return reg_is_dfs_ch(pdev, chan); 458 } 459 460 bool wlan_reg_is_passive_or_disable_ch(struct wlan_objmgr_pdev *pdev, 461 uint32_t chan) 462 { 463 return reg_is_passive_or_disable_ch(pdev, chan); 464 } 465 466 bool wlan_reg_is_disable_ch(struct wlan_objmgr_pdev *pdev, 467 uint32_t chan) 468 { 469 return reg_is_disable_ch(pdev, chan); 470 } 471 472 uint32_t wlan_reg_freq_to_chan(struct wlan_objmgr_pdev *pdev, 473 uint32_t freq) 474 { 475 return reg_freq_to_chan(pdev, freq); 476 } 477 478 uint32_t wlan_reg_chan_to_freq(struct wlan_objmgr_pdev *pdev, 479 uint32_t chan_num) 480 { 481 return reg_chan_to_freq(pdev, chan_num); 482 } 483 484 bool wlan_reg_chan_is_49ghz(struct wlan_objmgr_pdev *pdev, 485 uint8_t chan_num) 486 { 487 return reg_chan_is_49ghz(pdev, chan_num); 488 } 489 490 QDF_STATUS wlan_reg_set_country(struct wlan_objmgr_pdev *pdev, 491 uint8_t *country) 492 { 493 return reg_set_country(pdev, country); 494 } 495 496 QDF_STATUS wlan_reg_set_11d_country(struct wlan_objmgr_pdev *pdev, 497 uint8_t *country) 498 { 499 return reg_set_11d_country(pdev, country); 500 } 501 502 bool wlan_reg_is_world(uint8_t *country) 503 { 504 return reg_is_world_alpha2(country); 505 } 506 507 bool wlan_reg_is_us(uint8_t *country) 508 { 509 return reg_is_us_alpha2(country); 510 } 511 512 void wlan_reg_register_chan_change_callback(struct wlan_objmgr_psoc *psoc, 513 reg_chan_change_callback cbk, 514 void *arg) 515 { 516 reg_register_chan_change_callback(psoc, cbk, arg); 517 518 } 519 520 void wlan_reg_unregister_chan_change_callback(struct wlan_objmgr_psoc *psoc, 521 reg_chan_change_callback cbk) 522 { 523 reg_unregister_chan_change_callback(psoc, cbk); 524 } 525 526 bool wlan_reg_is_11d_offloaded(struct wlan_objmgr_psoc *psoc) 527 { 528 return reg_is_11d_offloaded(psoc); 529 } 530 531 bool wlan_reg_11d_enabled_on_host(struct wlan_objmgr_psoc *psoc) 532 { 533 return reg_11d_enabled_on_host(psoc); 534 } 535 536 bool wlan_reg_is_dsrc_chan(struct wlan_objmgr_pdev *pdev, uint8_t chan_num) 537 { 538 return reg_is_dsrc_chan(pdev, chan_num); 539 } 540 541 bool wlan_reg_is_etsi13_srd_chan(struct wlan_objmgr_pdev *pdev, 542 uint8_t chan_num) 543 { 544 return reg_is_etsi13_srd_chan(pdev, chan_num); 545 } 546 547 bool wlan_reg_is_etsi13_regdmn(struct wlan_objmgr_pdev *pdev) 548 { 549 return reg_is_etsi13_regdmn(pdev); 550 } 551 552 bool wlan_reg_is_etsi13_srd_chan_allowed_master_mode(struct wlan_objmgr_pdev 553 *pdev) 554 { 555 return reg_is_etsi13_srd_chan_allowed_master_mode(pdev); 556 } 557 558 QDF_STATUS wlan_reg_get_chip_mode(struct wlan_objmgr_pdev *pdev, 559 uint32_t *chip_mode) 560 { 561 struct wlan_regulatory_pdev_priv_obj *pdev_priv_obj; 562 563 pdev_priv_obj = wlan_objmgr_pdev_get_comp_private_obj(pdev, 564 WLAN_UMAC_COMP_REGULATORY); 565 566 if (NULL == pdev_priv_obj) { 567 reg_err("reg pdev private obj is NULL"); 568 return QDF_STATUS_E_FAULT; 569 } 570 571 *chip_mode = pdev_priv_obj->wireless_modes; 572 573 return QDF_STATUS_SUCCESS; 574 } 575 576 bool wlan_reg_is_11d_scan_inprogress(struct wlan_objmgr_psoc *psoc) 577 { 578 return reg_is_11d_scan_inprogress(psoc); 579 } 580 581 QDF_STATUS wlan_reg_get_freq_range(struct wlan_objmgr_pdev *pdev, 582 uint32_t *low_2g, 583 uint32_t *high_2g, 584 uint32_t *low_5g, 585 uint32_t *high_5g) 586 { 587 struct wlan_regulatory_pdev_priv_obj *pdev_priv_obj; 588 589 pdev_priv_obj = wlan_objmgr_pdev_get_comp_private_obj(pdev, 590 WLAN_UMAC_COMP_REGULATORY); 591 592 if (NULL == pdev_priv_obj) { 593 reg_err("reg pdev private obj is NULL"); 594 return QDF_STATUS_E_FAULT; 595 } 596 597 *low_2g = pdev_priv_obj->range_2g_low; 598 *high_2g = pdev_priv_obj->range_2g_high; 599 *low_5g = pdev_priv_obj->range_5g_low; 600 *high_5g = pdev_priv_obj->range_5g_high; 601 602 return QDF_STATUS_SUCCESS; 603 } 604 605 struct wlan_lmac_if_reg_tx_ops * 606 wlan_reg_get_tx_ops(struct wlan_objmgr_psoc *psoc) 607 { 608 return reg_get_psoc_tx_ops(psoc); 609 } 610 611 QDF_STATUS wlan_reg_get_curr_regdomain(struct wlan_objmgr_pdev *pdev, 612 struct cur_regdmn_info *cur_regdmn) 613 { 614 return reg_get_curr_regdomain(pdev, cur_regdmn); 615 } 616