1 /** \file regulatoryDomain.c 2 * \brief regulatoryDomain module interface 3 * 4 * \see regulatoryDomain.h 5 */ 6 /**************************************************************************** 7 **+-----------------------------------------------------------------------+** 8 **| |** 9 **| Copyright(c) 1998 - 2008 Texas Instruments. All rights reserved. |** 10 **| All rights reserved. |** 11 **| |** 12 **| Redistribution and use in source and binary forms, with or without |** 13 **| modification, are permitted provided that the following conditions |** 14 **| are met: |** 15 **| |** 16 **| * Redistributions of source code must retain the above copyright |** 17 **| notice, this list of conditions and the following disclaimer. |** 18 **| * Redistributions in binary form must reproduce the above copyright |** 19 **| notice, this list of conditions and the following disclaimer in |** 20 **| the documentation and/or other materials provided with the |** 21 **| distribution. |** 22 **| * Neither the name Texas Instruments nor the names of its |** 23 **| contributors may be used to endorse or promote products derived |** 24 **| from this software without specific prior written permission. |** 25 **| |** 26 **| THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |** 27 **| "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |** 28 **| LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |** 29 **| A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT |** 30 **| OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |** 31 **| SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |** 32 **| LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |** 33 **| DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |** 34 **| THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |** 35 **| (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |** 36 **| OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |** 37 **| |** 38 **+-----------------------------------------------------------------------+** 39 ****************************************************************************/ 40 41 /************************************************************************************************/ 42 /* */ 43 /* MODULE: regulatoryDomain.c */ 44 /* PURPOSE: regulatoryDomain module interface. */ 45 /* This module calculated the channel that should be scanned and that are */ 46 /* supported. Moreover, he set the transmit power level according to the */ 47 /* regulatory domain requirements and the supported channel. */ 48 /* */ 49 /************************************************************************************************/ 50 #include "report.h" 51 #include "osApi.h" 52 #include "paramOut.h" 53 #include "utils.h" 54 #include "regulatoryDomain.h" 55 #include "regulatoryDomainApi.h" 56 #include "whalCtrl_api.h" 57 #include "siteMgrApi.h" 58 #include "whalHwCtrl.h" 59 #include "SwitchChannelApi.h" 60 61 /* Mask for retrieving the TxPower from the Scan Control Table */ 62 #define MASK_TX_POWER (0x1f) /* bits 0-4 indicates MaxTxPower */ 63 #define MASK_ACTIVE_ALLOWED (0x40) /* bit 6 indiactes the channel is allowed for Active scan */ 64 #define MASK_FREQ_ALLOWED (0x80) /* bit 7 indicates the cahnnel is allowed*/ 65 66 #define CHANNEL_VALIDITY_TS_THRESHOLD 10000 /* 10 sec */ 67 68 #define INVALID_CHANNEL_165 165 69 70 /********************************************************************************/ 71 /* Internal functions prototypes. */ 72 /********************************************************************************/ 73 static TI_STATUS regulatoryDomain_updateCurrTxPower(regulatoryDomain_t *pRegulatoryDomain); 74 75 static void regulatoryDomain_setChannelValidity(regulatoryDomain_t *pRegulatoryDomain, 76 UINT16 channelNum, BOOL channelValidity); 77 78 static TI_STATUS setSupportedChannelsAccording2CountryIe(regulatoryDomain_t *pRegulatoryDomain, country_t* pCountry, BOOL band_2_4); 79 80 static void setSupportedChannelsAccording2ScanControlTable(regulatoryDomain_t *pRegulatoryDomain); 81 82 static TI_STATUS regulatoryDomain_getChannelCapability(regulatoryDomain_t *pRegulatoryDomain, 83 channelCapabilityReq_t channelCapabilityReq, 84 channelCapabilityRet_t *channelCapabilityRet); 85 86 static void regulatoryDomain_updateChannelsTs(regulatoryDomain_t *pRegulatoryDomain, UINT8 channel); 87 88 static void regulatoryDomain_buildDefaultListOfChannelsPerBand(regulatoryDomain_t *pRegulatoryDomain, radioBand_e band, UINT8 *listSize); 89 90 static void regulatoryDomain_checkCountryCodeExpiry(regulatoryDomain_t *pRegulatoryDomain); 91 92 static BOOL regulatoryDomain_isChannelSupprted(regulatoryDomain_t *pRegulatoryDomain, UINT8 channel); 93 94 static BOOL regulatoryDomain_isCountryFound(regulatoryDomain_t *pRegulatoryDomain, radioBand_e radioBand); 95 96 static void regulatoryDomain_getPowerLevelTableCB( TI_HANDLE hRegulatoryDomain, TI_STATUS status, 97 UINT8* CB_buf ); 98 99 static UINT8 regulatoryDomain_getMaxPowerAllowed(regulatoryDomain_t *pRegulatoryDomain, 100 UINT8 uChannel, 101 radioBand_e eBand, 102 BOOL bServingChannel); 103 104 /********************************************************************************/ 105 /* Interface functions Implementation. */ 106 /********************************************************************************/ 107 108 109 /************************************************************************ 110 * regulatoryDomain_create * 111 ************************************************************************ 112 DESCRIPTION: regulatoryDomain module creation function, called by the config mgr in creation phase 113 performs the following: 114 - Allocate the regulatoryDomain handle 115 116 INPUT: hOs - Handle to OS 117 118 119 OUTPUT: 120 121 RETURN: Handle to the regulatoryDomain module on success, NULL otherwise 122 123 ************************************************************************/ 124 TI_HANDLE regulatoryDomain_create(TI_HANDLE hOs) 125 { 126 regulatoryDomain_t *pRegulatoryDomain = NULL; 127 128 /* allocating the regulatoryDomain object */ 129 pRegulatoryDomain = os_memoryAlloc(hOs,sizeof(regulatoryDomain_t)); 130 131 if (pRegulatoryDomain == NULL) 132 return NULL; 133 134 return(pRegulatoryDomain); 135 } 136 137 /************************************************************************ 138 * regulatoryDomain_config * 139 ************************************************************************ 140 DESCRIPTION: regulatoryDomain module configuration function, called by the config mgr in configuration phase 141 performs the following: 142 - Reset & initializes local variables 143 - Init the handles to be used by the module 144 145 INPUT: hRegulatoryDomain - regulatoryDomain handle 146 List of handles to be used by the module 147 pRegulatoryDomainInitParams - Init table of the module. 148 149 150 OUTPUT: 151 152 RETURN: OK on success, NOK otherwise 153 154 ************************************************************************/ 155 TI_STATUS regulatoryDomain_config(TI_HANDLE hRegulatoryDomain, 156 TI_HANDLE hSiteMgr, 157 TI_HANDLE hHalCtrl, 158 TI_HANDLE hReport, 159 TI_HANDLE hOs, 160 TI_HANDLE hSwitchChannel, 161 regulatoryDomainInitParams_t *pRegulatoryDomainInitParams) 162 { 163 regulatoryDomain_t *pRegulatoryDomain = (regulatoryDomain_t *)hRegulatoryDomain; 164 whalParamInfo_t tWhalParam; 165 166 /* 167 *init variables - must be the 1st thing that is init! 168 */ 169 pRegulatoryDomain->country_2_4_WasFound = FALSE; 170 pRegulatoryDomain->country_5_WasFound = FALSE; 171 pRegulatoryDomain->uExternTxPowerPreferred = MAX_TX_POWER; /* i.e. no restriction */ 172 pRegulatoryDomain->uPowerConstraint = MIN_TX_POWER; /* i.e. no restriction */ 173 174 /* Init handlers */ 175 pRegulatoryDomain->hSiteMgr = hSiteMgr; 176 pRegulatoryDomain->hHalCtrl = hHalCtrl; 177 pRegulatoryDomain->hReport = hReport; 178 pRegulatoryDomain->hOs = hOs; 179 pRegulatoryDomain->hSwitchChannel = hSwitchChannel; 180 181 /* User max Tx power for all channels */ 182 pRegulatoryDomain->uUserMaxTxPower = pRegulatoryDomainInitParams->desiredTxPower; 183 /* Temporary Tx Power control to be used */ 184 pRegulatoryDomain->uDesiredTemporaryTxPower = pRegulatoryDomainInitParams->uTemporaryTxPower; 185 pRegulatoryDomain->uTemporaryTxPower = pRegulatoryDomainInitParams->uTemporaryTxPower; 186 187 /* 188 * Indicate the time in which the STA didn't receive any country code and was not connected, and therefore 189 * will delete its current country code 190 */ 191 pRegulatoryDomain->uTimeOutToResetCountryMs = pRegulatoryDomainInitParams->uTimeOutToResetCountryMs; 192 pRegulatoryDomain->uLastCountryReceivedTS = 0; 193 194 /* Get Power Translation Table from NVS. This table is retrieved only once */ 195 tWhalParam.paramType = HAL_CTRL_POWER_LEVEL_TABLE_PARAM; 196 tWhalParam.content.interogateCmdCBParams.CB_Func = (void *)regulatoryDomain_getPowerLevelTableCB; 197 tWhalParam.content.interogateCmdCBParams.CB_handle = hRegulatoryDomain; 198 tWhalParam.content.interogateCmdCBParams.CB_buf = (UINT8*)(&(pRegulatoryDomain->tPowerLevelTableInterrogate)); 199 whalCtrl_GetParam( pRegulatoryDomain->hHalCtrl, &tWhalParam ); 200 201 202 pRegulatoryDomain->regulatoryDomainEnabled = pRegulatoryDomainInitParams->multiRegulatoryDomainEnabled; 203 pRegulatoryDomain->spectrumManagementEnabled = pRegulatoryDomainInitParams->spectrumManagementEnabled; 204 if (pRegulatoryDomain->spectrumManagementEnabled == TRUE) 205 { 206 pRegulatoryDomain->regulatoryDomainEnabled = TRUE; 207 } 208 209 /* Getting the desired Control Table contents for 2.4 Ghz*/ 210 os_memoryCopy(pRegulatoryDomain->hOs, 211 (void *)pRegulatoryDomain->scanControlTable.ScanControlTable24.tableString, 212 (void *)pRegulatoryDomainInitParams->desiredScanControlTable.ScanControlTable24.tableString, 213 NUM_OF_CHANNELS_24 * sizeof(INT8)); 214 215 /* Getting the desired Control Table contents for 5 Ghz*/ 216 os_memoryCopy(pRegulatoryDomain->hOs, 217 (void *)pRegulatoryDomain->scanControlTable.ScanControlTable5.tableString, 218 (void *)pRegulatoryDomainInitParams->desiredScanControlTable.ScanControlTable5.tableString, 219 A_5G_BAND_NUM_CHANNELS * sizeof(INT8)); 220 221 setSupportedChannelsAccording2ScanControlTable(pRegulatoryDomain); 222 223 pRegulatoryDomain->minDFS_channelNum = A_5G_BAND_MIN_MIDDLE_BAND_DFS_CHANNEL; 224 pRegulatoryDomain->maxDFS_channelNum = A_5G_BAND_MAX_UPPER_BAND_DFS_CHANNEL; 225 226 WLAN_REPORT_INIT(hReport, REGULATORY_DOMAIN_MODULE_LOG, (".....Regulatory domain configured successfully\n")); 227 228 return OK; 229 } 230 231 232 /*********************************************************************** 233 * regulatoryDomain_setParam 234 *********************************************************************** 235 DESCRIPTION: Regulatory Domain set param function, called by the following: 236 - config mgr in order to set a parameter receiving from the OS abstraction layer. 237 - From inside the driver 238 239 INPUT: hRegulatoryDomain - Regulatory Domain handle. 240 pParam - Pointer to the parameter 241 242 OUTPUT: 243 244 RETURN: OK on success, NOK otherwise 245 246 ************************************************************************/ 247 TI_STATUS regulatoryDomain_setParam(TI_HANDLE hRegulatoryDomain, 248 paramInfo_t *pParam) 249 { 250 regulatoryDomain_t *pRegulatoryDomain = (regulatoryDomain_t *)hRegulatoryDomain; 251 252 253 switch(pParam->paramType) 254 { 255 case REGULATORY_DOMAIN_COUNTRY_PARAM: 256 { 257 BOOL bBand_2_4; 258 259 /* Sanity check */ 260 if (NULL == pParam->content.pCountry) 261 { 262 WLAN_REPORT_ERROR(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 263 ("regulatoryDomain_setParam, REGULATORY_DOMAIN_COUNTRY_PARAM is set with NULL pointer")); 264 265 return NOK; 266 } 267 else /* Update country code and supported channels */ 268 { 269 bBand_2_4 = siteMgr_isCurrentBand24(pRegulatoryDomain->hSiteMgr); 270 271 /* Setting the CountryIE for every Band */ 272 setSupportedChannelsAccording2CountryIe(pRegulatoryDomain, pParam->content.pCountry, bBand_2_4); 273 } 274 } 275 break; 276 277 case REGULATORY_DOMAIN_CHECK_COUNTRY_PARAM: 278 279 /* Check if Country code should be updated */ 280 regulatoryDomain_checkCountryCodeExpiry(pRegulatoryDomain); 281 282 break; 283 284 case REGULATORY_DOMAIN_SET_POWER_CONSTRAINT_PARAM: 285 286 /* Update only if 11h enabled */ 287 if (pRegulatoryDomain->spectrumManagementEnabled) 288 { 289 /* Convert to RegDomain units */ 290 UINT8 uNewPowerConstraint = DBM2DBMDIV10(pParam->content.powerConstraint); 291 292 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 293 ("SET_POWER_CONSTRAINT Old= %d New = %d (Only if bigger...)\n", 294 pRegulatoryDomain->uPowerConstraint, uNewPowerConstraint)); 295 296 /* Update powerConstraint */ 297 if ( pRegulatoryDomain->uPowerConstraint != uNewPowerConstraint ) 298 { 299 pRegulatoryDomain->uPowerConstraint = uNewPowerConstraint; 300 /* Set new Tx power to Hal - only if needed ! */ 301 regulatoryDomain_updateCurrTxPower(pRegulatoryDomain); 302 } 303 } 304 break; 305 306 case REGULATORY_DOMAIN_EXTERN_TX_POWER_PREFERRED: 307 /* ExternTxPowerPreferred is the TX Power Control (TPC) */ 308 { 309 /* Convert to RegDomain units */ 310 UINT8 uNewTPC = DBM2DBMDIV10(pParam->content.ExternTxPowerPreferred); 311 312 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 313 ("REGULATORY_DOMAIN_EXTERN_TX_POWER_PREFERRED Old= %d New = %d\n", 314 pRegulatoryDomain->uExternTxPowerPreferred, uNewTPC)); 315 316 if ( uNewTPC != pRegulatoryDomain->uExternTxPowerPreferred ) 317 { 318 pRegulatoryDomain->uExternTxPowerPreferred = uNewTPC; 319 /* Set new Tx power to Hal - only if needed ! */ 320 regulatoryDomain_updateCurrTxPower(pRegulatoryDomain); 321 } 322 } 323 break; 324 325 case REGULATORY_DOMAIN_SET_CHANNEL_VALIDITY: 326 /* Set channel as Valid or Invalid for Active SCAN only. 327 Mainly used by DFS when Switch Channel is active */ 328 regulatoryDomain_setChannelValidity(pRegulatoryDomain, pParam->content.channelValidity.channelNum, 329 pParam->content.channelValidity.channelValidity); 330 break; 331 332 case REGULATORY_DOMAIN_CURRENT_TX_POWER_IN_DBM_PARAM: 333 /* This case is called when the desired Tx Power Level in Dbm is changed by the user */ 334 if(pRegulatoryDomain->uUserMaxTxPower != pParam->content.desiredTxPower) 335 { 336 pRegulatoryDomain->uUserMaxTxPower = pParam->content.desiredTxPower; 337 /* Set new Tx power to Hal - only if needed ! */ 338 regulatoryDomain_updateCurrTxPower(pRegulatoryDomain); 339 } 340 341 break; 342 343 case REGULATORY_DOMAIN_TX_POWER_AFTER_SELECTION_PARAM: 344 /* Called after joining BSS, set Tx power to Hal */ 345 346 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 347 ("regulatoryDomain_setParam, REGULATORY_DOMAIN_TX_POWER_AFTER_SELECTION_PARAM \n")); 348 349 /* setting the Tx Power according to the selected channel */ 350 regulatoryDomain_updateCurrTxPower(pRegulatoryDomain); 351 352 break; 353 354 case REGULATORY_DOMAIN_DISCONNECT_PARAM: 355 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 356 ("regulatoryDomain_setParam, REGULATORY_DOMAIN_DISCONNECT_PARAM\n")); 357 358 pRegulatoryDomain->uExternTxPowerPreferred = MAX_TX_POWER; /* i.e. no restriction */ 359 pRegulatoryDomain->uPowerConstraint = MIN_TX_POWER; /* i.e. no restriction */ 360 361 /* Update the last time a country code was used. 362 After uTimeOutToResetCountryMs the country code will be deleted */ 363 if (pRegulatoryDomain->country_2_4_WasFound || pRegulatoryDomain->country_5_WasFound) 364 { 365 pRegulatoryDomain->uLastCountryReceivedTS = os_timeStampMs(pRegulatoryDomain->hOs); 366 } 367 break; 368 369 case REGULATORY_DOMAIN_UPDATE_CHANNEL_VALIDITY: 370 regulatoryDomain_updateChannelsTs(pRegulatoryDomain, pParam->content.channel); 371 break; 372 373 case REGULATORY_DOMAIN_TEMPORARY_TX_ATTENUATION_PARAM: 374 /* Temporary Tx Power control */ 375 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 376 (" temporary fix = %d, \n", pParam->content.bActivateTempPowerFix)); 377 378 /* Check if Temporary Tx Power control is enabled or disabled */ 379 if ( pParam->content.bActivateTempPowerFix ) 380 { /* setting the Temporary Tx Power directly to Hal */ 381 whalParamInfo_t whalParam; 382 383 whalParam.content.halCtrlTxPowerDbm = pRegulatoryDomain->uTemporaryTxPower; 384 whalParam.paramType = HAL_CTRL_TX_POWER_PARAM; 385 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 386 (" Setting actual temporary TX power = %d,Desired =%d \n", 387 pRegulatoryDomain->uTemporaryTxPower, 388 pRegulatoryDomain->uDesiredTemporaryTxPower)); 389 whalCtrl_SetParam(pRegulatoryDomain->hHalCtrl, &whalParam); 390 } 391 else 392 { /* Exit from Temporary Tx Power control- return to normal Tx Power */ 393 regulatoryDomain_updateCurrTxPower(pRegulatoryDomain); 394 } 395 396 break; 397 398 case REGULATORY_DOMAIN_ENABLE_DISABLE_802_11D: 399 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 400 ("regulatoryDomain_setParam, REGULATORY_DOMAIN_ENABLE_DISABLE_802_11D = %d, \n", pParam->content.enableDisable_802_11d)); 401 402 if ((pRegulatoryDomain->regulatoryDomainEnabled != pParam->content.enableDisable_802_11d) && 403 !pParam->content.enableDisable_802_11d && pRegulatoryDomain->spectrumManagementEnabled) 404 { /* Disable of 802_11d, is not allowed when 802_11h is enabled */ 405 WLAN_REPORT_ERROR(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 406 ("regulatoryDomain_setParam, Disable of 802_11d, is not allowed when 802_11h is enabled \n")); 407 return NOK; 408 409 } 410 pRegulatoryDomain->regulatoryDomainEnabled = pParam->content.enableDisable_802_11d; 411 412 /* Mark that no country was found - applies for both enabling and disabling of 11d */ 413 pRegulatoryDomain->country_2_4_WasFound = FALSE; 414 pRegulatoryDomain->country_5_WasFound = FALSE; 415 416 if (!pRegulatoryDomain->regulatoryDomainEnabled) 417 { /* Set regulatory Domain according to scan control table */ 418 setSupportedChannelsAccording2ScanControlTable(pRegulatoryDomain); 419 } 420 421 break; 422 423 case REGULATORY_DOMAIN_ENABLE_DISABLE_802_11H: 424 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 425 ("regulatoryDomain_setParam, REGULATORY_DOMAIN_ENABLE_DISABLE_802_11H = %d, \n", pParam->content.enableDisable_802_11h)); 426 427 pRegulatoryDomain->spectrumManagementEnabled = pParam->content.enableDisable_802_11h; 428 if (pParam->content.enableDisable_802_11h) 429 { /* If 802_11h is enabled, enable 802_11d as well */ 430 pRegulatoryDomain->regulatoryDomainEnabled = TRUE; 431 } 432 switchChannel_enableDisableSpectrumMngmt(pRegulatoryDomain->hSwitchChannel, pRegulatoryDomain->spectrumManagementEnabled); 433 break; 434 435 case REGULATORY_DOMAIN_COUNTRY_2_4_PARAM: 436 /* NOTE !!! use this feature carefully. */ 437 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 438 ("regulatoryDomain_setParam, REGULATORY_DOMAIN_COUNTRY_2_4_PARAM Len = %d, \n", pParam->paramLength)); 439 440 WLAN_REPORT_HEX_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, (UINT8*)pParam->content.pCountry, sizeof(country_t)); 441 442 return setSupportedChannelsAccording2CountryIe(pRegulatoryDomain, pParam->content.pCountry, TRUE); 443 444 case REGULATORY_DOMAIN_COUNTRY_5_PARAM: 445 /* NOTE !!! use this feature carefully */ 446 return setSupportedChannelsAccording2CountryIe(pRegulatoryDomain, pParam->content.pCountry, FALSE); 447 448 449 case REGULATORY_DOMAIN_DFS_CHANNELS_RANGE: 450 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 451 ("regulatoryDomain_setParam, DFS_CHANNELS_RANGE, min = %d, max = %d, \n", 452 pParam->content.DFS_ChannelRange.minDFS_channelNum, 453 pParam->content.DFS_ChannelRange.maxDFS_channelNum)); 454 if ((pParam->content.DFS_ChannelRange.minDFS_channelNum<A_5G_BAND_MIN_CHANNEL) || 455 (pParam->content.DFS_ChannelRange.maxDFS_channelNum>A_5G_BAND_MAX_CHANNEL) || 456 pParam->content.DFS_ChannelRange.minDFS_channelNum > pParam->content.DFS_ChannelRange.maxDFS_channelNum) 457 { 458 WLAN_REPORT_ERROR(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 459 ("regulatoryDomain_setParam, Bad DFS_CHANNELS_RANGE, min = %d, max = %d, \n", 460 pParam->content.DFS_ChannelRange.minDFS_channelNum, 461 pParam->content.DFS_ChannelRange.maxDFS_channelNum)); 462 return NOK; 463 } 464 pRegulatoryDomain->minDFS_channelNum = (UINT8)pParam->content.DFS_ChannelRange.minDFS_channelNum; 465 pRegulatoryDomain->maxDFS_channelNum = (UINT8)pParam->content.DFS_ChannelRange.maxDFS_channelNum; 466 467 break; 468 469 default: 470 WLAN_REPORT_ERROR(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, ("Set param, Params is not supported, %d\n\n", pParam->paramType)); 471 return PARAM_NOT_SUPPORTED; 472 } 473 474 return OK; 475 } 476 477 /*********************************************************************** 478 * regulatoryDomain_getParam 479 *********************************************************************** 480 DESCRIPTION: Regulatory Domain get param function, called by the following: 481 - config mgr in order to get a parameter from the OS abstraction layer. 482 - From inside the driver 483 484 INPUT: hRegulatoryDomain - Regulatory Domain handle. 485 pParam - Pointer to the parameter 486 487 OUTPUT: 488 489 RETURN: OK on success, NOK otherwise 490 491 ************************************************************************/ 492 TI_STATUS regulatoryDomain_getParam(TI_HANDLE hRegulatoryDomain, 493 paramInfo_t *pParam) 494 { 495 regulatoryDomain_t *pRegulatoryDomain = (regulatoryDomain_t *)hRegulatoryDomain; 496 497 switch(pParam->paramType) 498 { 499 500 case REGULATORY_DOMAIN_TX_POWER_LEVEL_TABLE_PARAM: 501 /* Copy power translation table */ 502 os_memoryCopy(pRegulatoryDomain->hOs, (void*)&pParam->content.powerLevelTable, 503 (void*)&(pRegulatoryDomain->tPowerLevelTableInterrogate.tTable), sizeof(powerLevelTable_t)); 504 505 break; 506 507 case REGULATORY_DOMAIN_MANAGEMENT_CAPABILITY_ENABLED_PARAM: 508 pParam->content.spectrumManagementEnabled = pRegulatoryDomain->spectrumManagementEnabled; 509 break; 510 511 case REGULATORY_DOMAIN_ENABLED_PARAM: 512 pParam->content.regulatoryDomainEnabled = pRegulatoryDomain->regulatoryDomainEnabled; 513 break; 514 515 case REGULATORY_DOMAIN_GET_SCAN_CAPABILITIES: 516 { 517 channelCapabilityReq_t channelCapabilityReq; 518 519 channelCapabilityReq.band = pParam->content.channelCapabilityReq.band; 520 channelCapabilityReq.channelNum = pParam->content.channelCapabilityReq.channelNum; 521 channelCapabilityReq.scanOption = pParam->content.channelCapabilityReq.scanOption; 522 523 regulatoryDomain_getChannelCapability(pRegulatoryDomain, channelCapabilityReq, &pParam->content.channelCapabilityRet); 524 } 525 break; 526 527 case REGULATORY_DOMAIN_POWER_CAPABILITY_PARAM: 528 /* power capability is only applicable when spectrum management is active (802.11h) */ 529 if(pRegulatoryDomain->spectrumManagementEnabled) 530 { 531 pParam->content.powerCapability.minTxPower = pRegulatoryDomain->uMinPowerDbm; 532 pParam->content.powerCapability.maxTxPower = pRegulatoryDomain->uMaxPowerDbm; 533 } 534 else 535 { 536 return NOK; 537 } 538 break; 539 540 case REGULATORY_DOMAIN_IS_CHANNEL_SUPPORTED: 541 /* checking if the channel is supported */ 542 pParam->content.bIsChannelSupprted = 543 regulatoryDomain_isChannelSupprted(pRegulatoryDomain, pParam->content.channel); 544 545 break; 546 547 case REGULATORY_DOMAIN_ALL_SUPPORTED_CHANNELS: 548 { 549 radioBand_e band = pParam->content.siteMgrRadioBand; 550 regulatoryDomain_buildDefaultListOfChannelsPerBand(pRegulatoryDomain, band, &pParam->content.supportedChannels.sizeOfList); 551 pParam->content.supportedChannels.listOfChannels = pRegulatoryDomain->pDefaultChannels; 552 } 553 break; 554 555 case REGULATORY_DOMAIN_CURRENT_TX_POWER_IN_DBM_PARAM: 556 557 { 558 whalParamInfo_t tWhalParam; 559 /* Get last configured Tx power from Hal */ 560 tWhalParam.paramType = HAL_CTRL_TX_POWER_PARAM; 561 whalCtrl_GetParam(pRegulatoryDomain->hHalCtrl, &tWhalParam); 562 563 pParam->content.desiredTxPower = tWhalParam.content.halCtrlTxPowerDbm; 564 565 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 566 ("regulatoryDomain_getParam, CURRENT_TX_POWER_IN_DBM = %d\n", 567 pParam->content.desiredTxPower)); 568 } 569 570 break; 571 572 case REGULATORY_DOMAIN_COUNTRY_PARAM: 573 { 574 /* This case is used as an inner function of the driver to retrieve the full IE of the country */ 575 576 BOOL bBand_2_4 = siteMgr_isCurrentBand24(pRegulatoryDomain->hSiteMgr); 577 578 /* Check if country code is still valid */ 579 regulatoryDomain_checkCountryCodeExpiry(pRegulatoryDomain); 580 581 if (bBand_2_4) 582 { 583 if (pRegulatoryDomain->country_2_4_WasFound) 584 { 585 pParam->content.pCountry = &pRegulatoryDomain->country24; 586 } 587 else /* Do not use the Inforamtion */ 588 { 589 pParam->content.pCountry = NULL; 590 } 591 } /* band 5.0 */ 592 else 593 { 594 if (pRegulatoryDomain->country_5_WasFound) 595 { 596 pParam->content.pCountry = &pRegulatoryDomain->country5; 597 } 598 else /* Do not use the Inforamtion */ 599 { 600 pParam->content.pCountry = NULL; 601 } 602 } 603 } 604 break; 605 606 case REGULATORY_DOMAIN_COUNTRY_2_4_PARAM: 607 /* Getting only country string */ 608 609 /* Check if country code is still valid */ 610 regulatoryDomain_checkCountryCodeExpiry(pRegulatoryDomain); 611 612 if (pRegulatoryDomain->country_2_4_WasFound) 613 { 614 os_memoryCopy(pRegulatoryDomain->hOs, (void*)pParam->content.pCountryString, (void*)pRegulatoryDomain->country24.countryIE.CountryString, COUNTRY_STRING_LEN); 615 } 616 else 617 { 618 pParam->content.pCountryString[0] = '\0'; 619 } 620 break; 621 622 case REGULATORY_DOMAIN_COUNTRY_5_PARAM: 623 /* Getting only country string */ 624 625 /* Check if country code is still valid */ 626 regulatoryDomain_checkCountryCodeExpiry(pRegulatoryDomain); 627 628 if (pRegulatoryDomain->country_5_WasFound) 629 { 630 os_memoryCopy(pRegulatoryDomain->hOs, (void*)pParam->content.pCountryString, (void*)pRegulatoryDomain->country5.countryIE.CountryString, COUNTRY_STRING_LEN); 631 } 632 else 633 { 634 pParam->content.pCountryString[0] = '\0'; 635 } 636 break; 637 638 case REGULATORY_DOMAIN_DFS_CHANNELS_RANGE: 639 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 640 ("regulatoryDomain_getParam, DFS_CHANNELS_RANGE, min = %d, max = %d, \n", 641 pRegulatoryDomain->minDFS_channelNum, 642 pRegulatoryDomain->maxDFS_channelNum)); 643 pParam->content.DFS_ChannelRange.minDFS_channelNum = pRegulatoryDomain->minDFS_channelNum; 644 pParam->content.DFS_ChannelRange.maxDFS_channelNum = pRegulatoryDomain->maxDFS_channelNum; 645 646 break; 647 648 case REGULATORY_DOMAIN_IS_COUNTRY_FOUND: 649 650 pParam->content.bIsCountryFound = 651 regulatoryDomain_isCountryFound(pRegulatoryDomain, pParam->content.eRadioBand); 652 653 break; 654 655 default: 656 WLAN_REPORT_ERROR(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, ("Get param, Params is not supported, %d\n\n", pParam->paramType)); 657 return PARAM_NOT_SUPPORTED; 658 } 659 660 return OK; 661 } 662 663 /************************************************************************ 664 * regulatoryDomain_destroy * 665 ************************************************************************ 666 DESCRIPTION: regulatoryDomain module destroy function, called by the config mgr in the destroy phase 667 performs the following: 668 - Free all memory allocated by the module 669 670 INPUT: hRegulatoryDomain - regulatoryDomain handle. 671 672 673 OUTPUT: 674 675 RETURN: OK on success, NOK otherwise 676 677 ************************************************************************/ 678 TI_STATUS regulatoryDomain_destroy(TI_HANDLE hRegulatoryDomain) 679 { 680 regulatoryDomain_t *pRegulatoryDomain = (regulatoryDomain_t *)hRegulatoryDomain; 681 682 if (pRegulatoryDomain == NULL) 683 return OK; 684 685 utils_nullMemoryFree(pRegulatoryDomain->hOs, pRegulatoryDomain, sizeof(regulatoryDomain_t)); 686 687 return OK; 688 } 689 690 /************************************************************************ 691 * regulatoryDomain_isCountryFound * 692 ************************************************************************ 693 DESCRIPTION: This function returns the validity of Country according to band 694 695 INPUT: hRegulatoryDomain - regulatoryDomain handle. 696 radioBand - the desired band 697 698 699 OUTPUT: 700 701 RETURN: TRUE - if country IE was found according to the band. 702 FALSE - otherwise. 703 704 ************************************************************************/ 705 BOOL regulatoryDomain_isCountryFound(regulatoryDomain_t *pRegulatoryDomain, radioBand_e radioBand) 706 { 707 708 if(radioBand == RADIO_BAND_2_4_GHZ) 709 { 710 return pRegulatoryDomain->country_2_4_WasFound; 711 } 712 else 713 { 714 return pRegulatoryDomain->country_5_WasFound; 715 } 716 717 } 718 719 /*********************************************************************** 720 * setSupportedChannelsAccording2CountryIe 721 *********************************************************************** 722 DESCRIPTION: Called when beacon/Probe Response with Country IE 723 is found. 724 The function sets the local countryIE per band with the CountryIE 725 that was detected in the last passive scan. 726 It is assumed that only one Country IE per band is allowed. 727 If Country is changed when the TNET is loaded, it should 728 be re-loaded in order to re-config the new Country domain. 729 730 INPUT: hRegulatoryDomain - RegulatoryDomain handle. 731 pCountry - pointer to the detected country IE. 732 733 OUTPUT: 734 735 RETURN: OK - New country code was set (or the same one was already configured) 736 NOK - The new country code could not be set 737 738 ************************************************************************/ 739 static TI_STATUS setSupportedChannelsAccording2CountryIe(regulatoryDomain_t *pRegulatoryDomain, country_t* pCountry, BOOL band_2_4) 740 { 741 channelCapability_t *pSupportedChannels; 742 UINT8 channelIndex; 743 UINT8 tripletChannelIndex, tripletChannelCnt; 744 UINT8 channelStep, numberOfChannels, minChannelNumber, maxChannelNumber; 745 746 747 if (!pRegulatoryDomain->regulatoryDomainEnabled) 748 { /* Ignore the Country IE if 802.11d is disabled */ 749 return NOK; 750 } 751 752 /* Check if the country code should be reset */ 753 regulatoryDomain_checkCountryCodeExpiry(pRegulatoryDomain); 754 755 if( band_2_4 == TRUE ) 756 { 757 if (pRegulatoryDomain->country_2_4_WasFound) 758 { /* Do not update new Country IE */ 759 if (os_memoryCompare(pRegulatoryDomain->hOs, (void *)&pCountry->countryIE, 760 (void *)&pRegulatoryDomain->country24.countryIE, sizeof(countryIE_t))) 761 { 762 WLAN_REPORT_WARNING(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 763 ("setSupportedChannelsAccording2CountryIe different Country, cur=%s, new=%s\n", 764 pRegulatoryDomain->country24.countryIE.CountryString, pCountry->countryIE.CountryString)); 765 return NOK; 766 } 767 else /* Same IE - just mark the TS and return OK */ 768 { 769 /* Mark the time of the received country IE */ 770 pRegulatoryDomain->uLastCountryReceivedTS = os_timeStampMs(pRegulatoryDomain->hOs); 771 return OK; 772 } 773 } 774 pRegulatoryDomain->country_2_4_WasFound = TRUE; 775 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_2_4; 776 channelStep = BG_24G_BAND_CHANNEL_HOPS; 777 maxChannelNumber = NUM_OF_CHANNELS_24; 778 minChannelNumber = BG_24G_BAND_MIN_CHANNEL; 779 numberOfChannels = NUM_OF_CHANNELS_24; 780 /* save the country IE */ 781 os_memoryCopy(pRegulatoryDomain->hOs, (void*)&pRegulatoryDomain->country24, (void *)pCountry, sizeof(country_t)); 782 783 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 784 ("Country 2.4 =%c%c%c\n",pRegulatoryDomain->country24.countryIE.CountryString[0], 785 pRegulatoryDomain->country24.countryIE.CountryString[1], 786 pRegulatoryDomain->country24.countryIE.CountryString[2])); 787 788 } 789 else /* band 5.0 */ 790 { 791 if (pRegulatoryDomain->country_5_WasFound) 792 { /* Do not update new Country IE if the IE is the same*/ 793 if (os_memoryCompare(pRegulatoryDomain->hOs, (void *)&pCountry->countryIE, 794 (void *)&pRegulatoryDomain->country5.countryIE, sizeof(countryIE_t))) 795 { 796 WLAN_REPORT_WARNING(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 797 ("setSupportedChannelsAccording2CountryIe different Country, cur=%s, new=%s\n", 798 pRegulatoryDomain->country5.countryIE.CountryString, pCountry->countryIE.CountryString)); 799 return NOK; 800 } 801 else /* Same IE - just mark the TS and return OK */ 802 { 803 /* Mark the time of the received country IE */ 804 pRegulatoryDomain->uLastCountryReceivedTS = os_timeStampMs(pRegulatoryDomain->hOs); 805 return OK; 806 } 807 } 808 pRegulatoryDomain->country_5_WasFound = TRUE; 809 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_5; 810 channelStep = A_5G_BAND_CHANNEL_HOPS; 811 maxChannelNumber = A_5G_BAND_MAX_CHANNEL; 812 minChannelNumber = A_5G_BAND_MIN_CHANNEL; 813 numberOfChannels = A_5G_BAND_NUM_CHANNELS; 814 /* save the country IE */ 815 os_memoryCopy(pRegulatoryDomain->hOs, (void*)&pRegulatoryDomain->country5, (void*)pCountry, sizeof(country_t)); 816 817 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 818 ("Country 5 =%c%c%c\n",pRegulatoryDomain->country5.countryIE.CountryString[0], 819 pRegulatoryDomain->country5.countryIE.CountryString[1], 820 pRegulatoryDomain->country5.countryIE.CountryString[2])); 821 } 822 823 /* 824 * New Country IE was saved. Now - update the last received TS and ScanControlTable 825 */ 826 827 /* Mark the time of the received country IE */ 828 pRegulatoryDomain->uLastCountryReceivedTS = os_timeStampMs(pRegulatoryDomain->hOs); 829 830 /* First clear the validity of all channels 831 Overwrite the ScanControlTable */ 832 for (channelIndex=0; channelIndex<numberOfChannels; channelIndex++) 833 { 834 pSupportedChannels[channelIndex].channelValidityActive = FALSE; 835 pSupportedChannels[channelIndex].channelValidityPassive = FALSE; 836 pSupportedChannels[channelIndex].bChanneInCountryIe = FALSE; 837 pSupportedChannels[channelIndex].uMaxTxPowerDomain = MIN_TX_POWER; 838 } 839 840 tripletChannelCnt = (pCountry->len - COUNTRY_STRING_LEN) / 3; 841 /* set validity of the channels according to the band (2.4 or 5) */ 842 for( tripletChannelIndex = 0; tripletChannelIndex < tripletChannelCnt ; tripletChannelIndex++) 843 { 844 UINT8 firstChannelNumInTriplet; 845 846 firstChannelNumInTriplet = pCountry->countryIE.tripletChannels[tripletChannelIndex].firstChannelNumber; 847 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 848 ("firstChannelNumInTriplet=%d,channelStep=%d\n", firstChannelNumInTriplet, channelStep)); 849 for (channelIndex=0; channelIndex<pCountry->countryIE.tripletChannels[tripletChannelIndex].numberOfChannels; channelIndex++) 850 { 851 UINT16 channelNumber; 852 853 channelNumber = firstChannelNumInTriplet+(channelIndex*channelStep); 854 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 855 ("setSupportedChannelsAccording2CountryIe of channel=%d\n", channelNumber)); 856 857 if ((channelNumber <= maxChannelNumber)&& (channelNumber !=INVALID_CHANNEL_165)) 858 { 859 UINT8 channelIndex4Band; 860 861 channelIndex4Band = (channelNumber-minChannelNumber); 862 pSupportedChannels[channelIndex4Band].bChanneInCountryIe = TRUE; 863 pSupportedChannels[channelIndex4Band].channelValidityPassive = TRUE; 864 pSupportedChannels[channelIndex4Band].channelValidityActive = TRUE; 865 866 /* set the TX power in DBM/10 units */ 867 pSupportedChannels[channelIndex4Band].uMaxTxPowerDomain = 868 DBM2DBMDIV10(pCountry->countryIE.tripletChannels[tripletChannelIndex].maxTxPowerLevel); 869 870 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 871 ("channel = %d uMaxTxPowerDomain=%d\n", 872 channelNumber, pSupportedChannels[channelIndex4Band].uMaxTxPowerDomain)); 873 } 874 } 875 } 876 877 return OK; 878 } 879 880 881 /*********************************************************************** 882 * regulatoryDomain_isChannelSupprted 883 *********************************************************************** 884 DESCRIPTION: The function checks if the input channel is supported. 885 886 INPUT: pRegulatoryDomain - RegulatoryDomain pointer. 887 channel - Channel number. 888 889 890 OUTPUT: 891 892 RETURN: OK if channel is supported, NOK otherwise. 893 894 ************************************************************************/ 895 static BOOL regulatoryDomain_isChannelSupprted(regulatoryDomain_t *pRegulatoryDomain, UINT8 channel) 896 { 897 UINT8 channelIndex; 898 channelCapability_t *pSupportedChannels; 899 900 if (pRegulatoryDomain==NULL) 901 { 902 return FALSE; 903 } 904 905 if ((channel<BG_24G_BAND_MIN_CHANNEL) || (channel>A_5G_BAND_MAX_CHANNEL)) 906 { 907 return FALSE; 908 } 909 if (channel>=A_5G_BAND_MIN_CHANNEL) 910 { 911 channelIndex = (channel-A_5G_BAND_MIN_CHANNEL); 912 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_5; 913 } 914 else 915 { 916 channelIndex = (channel-BG_24G_BAND_MIN_CHANNEL); 917 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_2_4; 918 } 919 if (pRegulatoryDomain->spectrumManagementEnabled 920 && (channel >= pRegulatoryDomain->minDFS_channelNum) 921 && (channel <= pRegulatoryDomain->maxDFS_channelNum) 922 && ((os_timeStampMs(pRegulatoryDomain->hOs)-pSupportedChannels[channelIndex].timestamp) >=CHANNEL_VALIDITY_TS_THRESHOLD )) 923 { /* If 802.11h is enabled, a DFS channel is valid only for 10 sec 924 from the last Beacon/ProbeResponse */ 925 pSupportedChannels[channelIndex].channelValidityActive = FALSE; 926 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 927 ("regulatoryDomain_isChannelSupprted(): CHANNEL_VALIDITY_TS_THRESHOLD !! Disable channel no %d, DFS channel\n", channel )); 928 929 } 930 931 return (pSupportedChannels[channelIndex].channelValidityActive); 932 933 } 934 935 /************************************************************************ 936 * regulatoryDomain_setChannelValidity * 937 ************************************************************************/ 938 /* 939 * 940 * 941 * \b Description: 942 * 943 * This function sets a channel as invalid or valid in the internal Regulatory Domain 944 * database. 945 * 946 * \b ARGS: 947 * 948 * I - pData - pointer to the regDoamin SM context \n 949 * I - channelNum - the invalid/valid channel number 950 * I - channelValidity - TRUE if channel is valid, FALSE channel is invalid 951 * 952 * \b RETURNS: 953 * 954 * None. 955 * 956 * 957 *************************************************************************/ 958 static void regulatoryDomain_setChannelValidity(regulatoryDomain_t *pRegulatoryDomain, 959 UINT16 channelNum, BOOL channelValidity) 960 { 961 channelCapability_t *pSupportedChannels; 962 UINT8 channelIndex; 963 964 965 if (pRegulatoryDomain == NULL) 966 { 967 return; 968 } 969 if ((channelNum==0 ) || (channelNum>A_5G_BAND_MAX_CHANNEL)) 970 { 971 WLAN_REPORT_ERROR(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 972 ("regulatoryDomain_setChannelValidity, invalid channelNum=%d \n", channelNum)); 973 return; 974 } 975 976 if (channelNum <= NUM_OF_CHANNELS_24) 977 { 978 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_2_4; 979 channelIndex = (channelNum-BG_24G_BAND_MIN_CHANNEL); 980 } 981 else 982 { 983 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_5; 984 channelIndex = (channelNum - A_5G_BAND_MIN_CHANNEL); 985 } 986 987 if(channelValidity == TRUE) 988 if((pSupportedChannels[channelIndex].bChanneInCountryIe == FALSE) && (pRegulatoryDomain->regulatoryDomainEnabled == TRUE)) 989 { 990 WLAN_REPORT_WARNING(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 991 ("regulatoryDomain_setChannelValidity: channelNum = %d isn't supported at the Country. wll not set to active!\n", channelNum)); 992 return; 993 } 994 995 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 996 ("regulatoryDomain_setChannelValidity: channelNum=%d, validity=%d \n", channelNum, channelValidity)); 997 998 999 pSupportedChannels[channelIndex].channelValidityActive = channelValidity; 1000 } 1001 1002 1003 /************************************************************************ 1004 * setSupportedChannelsAccording2ScanControlTable * 1005 ************************************************************************/ 1006 /** 1007 * 1008 * 1009 * \b Description: 1010 * 1011 * This function is called in config and sets the supported channels according to 1012 * the scan control table read from registry and reg domain read from the chip. 1013 * 1014 * \b ARGS: 1015 * 1016 * I - pRegulatoryDomain - pointer to the regDoamin SM context \n 1017 * 1018 * \b RETURNS: 1019 * 1020 * None. 1021 * 1022 * 1023 *************************************************************************/ 1024 static void setSupportedChannelsAccording2ScanControlTable(regulatoryDomain_t *pRegulatoryDomain) 1025 { 1026 UINT8 channelIndex; 1027 UINT8 channelMask; 1028 1029 if (pRegulatoryDomain==NULL) 1030 { 1031 return; 1032 } 1033 1034 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1035 ("setSupportedChannelsAccording2ScanControlTable \n")); 1036 1037 for (channelIndex=0; channelIndex<NUM_OF_CHANNELS_24; channelIndex++) 1038 { 1039 channelMask = pRegulatoryDomain->scanControlTable.ScanControlTable24.tableString[channelIndex]; 1040 pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].bChanneInCountryIe = FALSE; 1041 1042 /* Calculate Domain Tx Power - channelMask units are in Dbm. */ 1043 pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].uMaxTxPowerDomain = 1044 DBM2DBMDIV10(channelMask & MASK_TX_POWER); 1045 if (channelMask & (MASK_ACTIVE_ALLOWED | MASK_FREQ_ALLOWED)) 1046 { /* The channel is allowed for Active & Passive scans */ 1047 if (pRegulatoryDomain->regulatoryDomainEnabled) 1048 { /* All channels should be invalid for Active scan */ 1049 pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].channelValidityActive = FALSE; 1050 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1051 ("channelIndex=%d is invalid for Active \n", channelIndex+1)); 1052 } 1053 else 1054 { 1055 pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].channelValidityActive = TRUE; 1056 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1057 ("channelIndex=%d is Active valid \n", channelIndex+1)); 1058 } 1059 1060 } 1061 1062 if (channelMask & MASK_FREQ_ALLOWED) 1063 { /* The channel is allowed for Passive scan */ 1064 pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].channelValidityPassive = TRUE; 1065 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1066 ("channelIndex=%d is Passive valid \n", channelIndex+1)); 1067 } 1068 else 1069 { /* The channel is not allowed */ 1070 pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].channelValidityPassive = FALSE; 1071 pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].channelValidityActive = FALSE; 1072 } 1073 } 1074 1075 for (channelIndex=A_5G_BAND_MIN_CHANNEL; channelIndex<=A_5G_BAND_MAX_CHANNEL; channelIndex++) 1076 { 1077 UINT8 channelIndexInBand5; 1078 1079 channelIndexInBand5 = (channelIndex-A_5G_BAND_MIN_CHANNEL); 1080 channelMask = pRegulatoryDomain->scanControlTable.ScanControlTable5.tableString[channelIndexInBand5]; 1081 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1082 ("channelIndex=%d, channelIndexInBand5=%d channelMask=%d\n", channelIndex, channelIndexInBand5, channelMask)); 1083 1084 /* Calculate Domain Tx Power - channelMask units are in Dbm. */ 1085 pRegulatoryDomain->supportedChannels_band_5[channelIndexInBand5].uMaxTxPowerDomain = 1086 DBM2DBMDIV10(channelMask & MASK_TX_POWER); 1087 1088 pRegulatoryDomain->supportedChannels_band_5[channelIndexInBand5].bChanneInCountryIe = FALSE; 1089 if (channelMask & (MASK_ACTIVE_ALLOWED | MASK_FREQ_ALLOWED)) 1090 { /* The channel is allowed for Active & Passive scans */ 1091 if (pRegulatoryDomain->regulatoryDomainEnabled) 1092 { /* All channels should be invalid for Active scan */ 1093 pRegulatoryDomain->supportedChannels_band_5[channelIndexInBand5].channelValidityActive = FALSE; 1094 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1095 ("channelIndex=%d is invalid for Active \n", channelIndex)); 1096 } 1097 else 1098 { 1099 pRegulatoryDomain->supportedChannels_band_5[channelIndexInBand5].channelValidityActive = TRUE; 1100 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1101 ("channelIndex=%d, channelIndexInBand5=%d, is Active valid \n", channelIndex, channelIndexInBand5)); 1102 } 1103 } 1104 1105 if (channelMask & MASK_FREQ_ALLOWED) 1106 { /* The channel is allowed for Passive scan */ 1107 pRegulatoryDomain->supportedChannels_band_5[channelIndexInBand5].channelValidityPassive = TRUE; 1108 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1109 ("channelIndex=%d, channelIndexInBand5=%d, is Passive valid \n", channelIndex, channelIndexInBand5)); 1110 } 1111 else 1112 { /* The channel is not allowed */ 1113 pRegulatoryDomain->supportedChannels_band_5[channelIndexInBand5].channelValidityPassive = FALSE; 1114 pRegulatoryDomain->supportedChannels_band_5[channelIndexInBand5].channelValidityActive = FALSE; 1115 } 1116 1117 } 1118 } 1119 1120 1121 /*********************************************************************** 1122 * regulatoryDomain_getChannelCapability 1123 *********************************************************************** 1124 DESCRIPTION: This function returns the channel capability information 1125 1126 INPUT: pRegulatoryDomain - RegulatoryDomain pointer. 1127 channelCapabilityReq - Channels parameters 1128 1129 1130 OUTPUT: channelCapabilityRet - Channel capability information 1131 1132 RETURN: OK if information was retrieved, NOK otherwise. 1133 1134 ************************************************************************/ 1135 static TI_STATUS regulatoryDomain_getChannelCapability(regulatoryDomain_t *pRegulatoryDomain, 1136 channelCapabilityReq_t channelCapabilityReq, 1137 channelCapabilityRet_t *channelCapabilityRet) 1138 { 1139 channelCapability_t *pSupportedChannels; 1140 UINT8 channelIndex; 1141 BOOL bCountryWasFound, bServingChannel; 1142 paramInfo_t tParamInfo; 1143 1144 if ((pRegulatoryDomain == NULL) || (channelCapabilityRet == NULL)) 1145 { 1146 return NOK; 1147 } 1148 1149 channelCapabilityRet->channelValidity = FALSE; 1150 channelCapabilityRet->maxTxPowerDbm = 0; 1151 if ((channelCapabilityReq.channelNum==0 ) || (channelCapabilityReq.channelNum>A_5G_BAND_MAX_CHANNEL)) 1152 { 1153 WLAN_REPORT_ERROR(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1154 ("regulatoryDomain_getChannelCapability, invalid channelNum=%d \n", channelCapabilityReq.channelNum)); 1155 return NOK; 1156 } 1157 1158 if (channelCapabilityReq.band==RADIO_BAND_2_4_GHZ) 1159 { 1160 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_2_4; 1161 channelIndex = (channelCapabilityReq.channelNum-BG_24G_BAND_MIN_CHANNEL); 1162 bCountryWasFound = pRegulatoryDomain->country_2_4_WasFound; 1163 } 1164 else if (channelCapabilityReq.band==RADIO_BAND_5_0_GHZ) 1165 { 1166 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_5; 1167 channelIndex = (channelCapabilityReq.channelNum - A_5G_BAND_MIN_CHANNEL); 1168 bCountryWasFound = pRegulatoryDomain->country_5_WasFound; 1169 } 1170 else 1171 { 1172 WLAN_REPORT_ERROR(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1173 ("regulatoryDomain_getChannelCapability, invalid band=%d \n", channelCapabilityReq.band)); 1174 return NOK; 1175 } 1176 1177 1178 /* 1179 * Set channelValidity according to ScanTable and whether 11d is enabled 1180 */ 1181 if (channelCapabilityReq.scanOption == ACTIVE_SCANNING) 1182 { 1183 if ( ( pRegulatoryDomain->regulatoryDomainEnabled ) && ( !bCountryWasFound ) ) 1184 { /* 11d enabled and no country IE was found - set channel to invalid */ 1185 channelCapabilityRet->channelValidity = FALSE; 1186 } 1187 else 1188 { 1189 channelCapabilityRet->channelValidity = pSupportedChannels[channelIndex].channelValidityActive; 1190 /* 1191 * Set Maximum Tx power for the channel - only for active scanning 1192 */ 1193 1194 /* Get current channel and check if we are using the same one */ 1195 tParamInfo.paramType = SITE_MGR_CURRENT_CHANNEL_PARAM; 1196 siteMgr_getParam(pRegulatoryDomain->hSiteMgr, &tParamInfo); 1197 1198 bServingChannel = ( tParamInfo.content.siteMgrCurrentChannel == channelCapabilityReq.channelNum ? 1199 TRUE : FALSE ); 1200 1201 channelCapabilityRet->maxTxPowerDbm = regulatoryDomain_getMaxPowerAllowed(pRegulatoryDomain, 1202 channelCapabilityReq.channelNum, 1203 channelCapabilityReq.band, 1204 bServingChannel); 1205 } 1206 } 1207 else /* Passive scanning */ 1208 { 1209 if ( ( pRegulatoryDomain->regulatoryDomainEnabled ) && ( !bCountryWasFound ) ) 1210 { /* 11d enabled and no country IE was found - set channel to valid for passive scan */ 1211 channelCapabilityRet->channelValidity = TRUE; 1212 } 1213 else 1214 { 1215 channelCapabilityRet->channelValidity = pSupportedChannels[channelIndex].channelValidityPassive; 1216 } 1217 } 1218 1219 if (pRegulatoryDomain->spectrumManagementEnabled 1220 && (channelCapabilityReq.scanOption == ACTIVE_SCANNING) 1221 && (channelCapabilityReq.channelNum >= pRegulatoryDomain->minDFS_channelNum) 1222 && (channelCapabilityReq.channelNum <= pRegulatoryDomain->maxDFS_channelNum) 1223 && ((os_timeStampMs(pRegulatoryDomain->hOs)-pSupportedChannels[channelIndex].timestamp) >=CHANNEL_VALIDITY_TS_THRESHOLD )) 1224 { /* If 802.11h is enabled, a DFS channel is valid only for 10 sec 1225 from the last Beacon/ProbeResponse */ 1226 pSupportedChannels[channelIndex].channelValidityActive = FALSE; 1227 channelCapabilityRet->channelValidity = FALSE; 1228 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1229 ("regulatoryDomain_getChannelCapability(): CHANNEL_VALIDITY_TS_THRESHOLD !!! Disable channel no %d, DFS channel\n", channelCapabilityReq.channelNum )); 1230 } 1231 1232 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1233 (" Channel num= %d, scan option=%d validity = %d, TX power = %d \n", 1234 channelCapabilityReq.channelNum, 1235 channelCapabilityReq.scanOption, 1236 channelCapabilityRet->channelValidity, 1237 channelCapabilityRet->maxTxPowerDbm)); 1238 return OK; 1239 1240 } 1241 1242 1243 static void regulatoryDomain_updateChannelsTs(regulatoryDomain_t *pRegulatoryDomain, UINT8 channel) 1244 { 1245 UINT8 channelIndex; 1246 channelCapability_t *pSupportedChannels; 1247 1248 if (pRegulatoryDomain==NULL) 1249 { 1250 return; 1251 } 1252 1253 if ((channel<BG_24G_BAND_MIN_CHANNEL) || (channel>A_5G_BAND_MAX_CHANNEL)) 1254 { 1255 return; 1256 } 1257 1258 if (channel>=A_5G_BAND_MIN_CHANNEL) 1259 { 1260 channelIndex = (channel-A_5G_BAND_MIN_CHANNEL); 1261 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_5; 1262 } 1263 else 1264 { 1265 channelIndex = (channel-BG_24G_BAND_MIN_CHANNEL); 1266 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_2_4; 1267 } 1268 1269 if((pSupportedChannels[channelIndex].bChanneInCountryIe == FALSE) && (pRegulatoryDomain->regulatoryDomainEnabled == TRUE)) 1270 { 1271 WLAN_REPORT_WARNING(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1272 ("regulatoryDomain_updateChannelsTs: channelNum = %d isn't supported at the Country. wll not set to active!\n", channel)); 1273 return; 1274 } 1275 1276 pSupportedChannels[channelIndex].timestamp = os_timeStampMs(pRegulatoryDomain->hOs); 1277 pSupportedChannels[channelIndex].channelValidityActive = TRUE; 1278 1279 } 1280 1281 /*********************************************************************** 1282 * regulatoryDomain_updateCurrTxPower 1283 *********************************************************************** 1284 DESCRIPTION: Called when new Tx power should be calculated and configured. 1285 Check if we are already joined to BSS/IBSS, calculate 1286 new Tx power and configure it to Hal. 1287 1288 INPUT: pRegulatoryDomain - regulatoryDomain pointer. 1289 1290 RETURN: OK - New value was configured to Hal, NOK - Can't configure value 1291 TX_POWER_SET_SAME_VALUE - Same value was already configured. 1292 1293 ************************************************************************/ 1294 static TI_STATUS regulatoryDomain_updateCurrTxPower(regulatoryDomain_t *pRegulatoryDomain) 1295 { 1296 UINT8 uCurrChannel, uNewTxPower; 1297 whalParamInfo_t whalParam; 1298 paramInfo_t tParamInfo; 1299 TI_STATUS eStatus; 1300 1301 /* Get the current channel, and update HAL with the changed */ 1302 tParamInfo.paramType = SITE_MGR_CURRENT_CHANNEL_PARAM; 1303 eStatus = siteMgr_getParam(pRegulatoryDomain->hSiteMgr, &tParamInfo); 1304 1305 if ( eStatus != OK ) 1306 { 1307 /* We are not joined yet - no meaning for new Tx power */ 1308 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1309 ("regulatoryDomain_updateCurrTxPower, No site selected yet\n")); 1310 1311 return NOK; 1312 } 1313 /* Save current channel */ 1314 uCurrChannel = tParamInfo.content.siteMgrCurrentChannel; 1315 1316 /* Get the current channel, and update HAL with the changed */ 1317 tParamInfo.paramType = SITE_MGR_RADIO_BAND_PARAM; 1318 siteMgr_getParam(pRegulatoryDomain->hSiteMgr, &tParamInfo); 1319 1320 /* Calculate maximum Tx power for the serving channel */ 1321 uNewTxPower = regulatoryDomain_getMaxPowerAllowed(pRegulatoryDomain, uCurrChannel, 1322 tParamInfo.content.siteMgrRadioBand, TRUE); 1323 /* Verify that the Temporary TX Power Control doesn't violate the TX Power Constraint */ 1324 pRegulatoryDomain->uTemporaryTxPower = MIN(pRegulatoryDomain->uDesiredTemporaryTxPower, uNewTxPower); 1325 1326 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1327 ("regulatoryDomain_updateCurrTxPower, Write to Hal = %d \n", uNewTxPower)); 1328 1329 whalParam.paramType = HAL_CTRL_TX_POWER_PARAM; 1330 whalParam.content.halCtrlTxPowerDbm = uNewTxPower; 1331 return whalCtrl_SetParam(pRegulatoryDomain->hHalCtrl, &whalParam); 1332 } 1333 1334 /*********************************************************************** 1335 * regulatoryDomain_checkCountryCodeExpiry 1336 *********************************************************************** 1337 DESCRIPTION: Check & Reset the country code that was detected earlier. 1338 Reseting country code will be done when the STA was not connected for 1339 a certain amount of time, and no country code was received in that period (from the same country). 1340 This scenario might indicate that the STA has moved to a different country. 1341 1342 INPUT: pRegulatoryDomain - Regulatory Domain handle. 1343 1344 OUTPUT: updating country code if necessary. 1345 1346 RETURN: 1347 1348 ************************************************************************/ 1349 void regulatoryDomain_checkCountryCodeExpiry(regulatoryDomain_t *pRegulatoryDomain) 1350 { 1351 paramInfo_t param; 1352 TI_STATUS connStatus; 1353 UINT32 uCurrentTS = os_timeStampMs(pRegulatoryDomain->hOs); 1354 1355 if ((pRegulatoryDomain->country_2_4_WasFound) || (pRegulatoryDomain->country_5_WasFound)) 1356 { 1357 /* Get connection status */ 1358 param.paramType = SITE_MGR_CURRENT_SSID_PARAM; 1359 connStatus = siteMgr_getParam(pRegulatoryDomain->hSiteMgr, ¶m); 1360 1361 /* If (uTimeOutToResetCountryMs has elapsed && we are not connected) 1362 delete the last country code received */ 1363 if (((uCurrentTS - pRegulatoryDomain->uLastCountryReceivedTS) > pRegulatoryDomain->uTimeOutToResetCountryMs) && 1364 (connStatus == NO_SITE_SELECTED_YET)) 1365 { 1366 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1367 ("%s, Reset country code after %d Ms\n", 1368 __FUNCTION__,(uCurrentTS - pRegulatoryDomain->uLastCountryReceivedTS))); 1369 1370 /* Reset country codes */ 1371 pRegulatoryDomain->country_2_4_WasFound = FALSE; 1372 pRegulatoryDomain->country_5_WasFound = FALSE; 1373 1374 /* Restore default values of the scan control table */ 1375 setSupportedChannelsAccording2ScanControlTable(pRegulatoryDomain); 1376 } 1377 } 1378 } 1379 1380 /*********************************************************************** 1381 * regulatoryDomain_getMaxPowerAllowed 1382 *********************************************************************** 1383 DESCRIPTION: Get the maximum tx power allowed for the given channel. 1384 The final value is constructed by: 1385 1) User max value 1386 2) Domain restriction - 11d country code IE 1387 3) 11h power constraint - only on serving channel 1388 4) EXC TPC - only on serving channel 1389 1390 RETURN: Max power in Dbm/10 for the given channel 1391 1392 ************************************************************************/ 1393 static UINT8 regulatoryDomain_getMaxPowerAllowed(regulatoryDomain_t *pRegulatoryDomain, 1394 UINT8 uChannel, 1395 radioBand_e eBand, 1396 BOOL bServingChannel) 1397 { 1398 channelCapability_t *pSupportedChannels; 1399 UINT8 uChannelIndex, uTxPower; 1400 1401 if( eBand == RADIO_BAND_2_4_GHZ) 1402 { 1403 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_2_4; 1404 uChannelIndex = uChannel - BG_24G_BAND_MIN_CHANNEL; 1405 } 1406 else 1407 { 1408 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_5; 1409 uChannelIndex = uChannel - A_5G_BAND_MIN_CHANNEL; 1410 } 1411 1412 /* We'll start with the "Domain restriction - 11d country code IE" */ 1413 uTxPower = pSupportedChannels[uChannelIndex].uMaxTxPowerDomain; 1414 1415 if ( bServingChannel) 1416 { 1417 if (pRegulatoryDomain->uPowerConstraint < uTxPower) 1418 { 1419 /* When 802.11h is disabled, uPowerConstraint is 0 anyway */ 1420 uTxPower -= pRegulatoryDomain->uPowerConstraint; 1421 } 1422 1423 /* Take EXC limitation too */ 1424 uTxPower = MIN(uTxPower, pRegulatoryDomain->uExternTxPowerPreferred); 1425 1426 } 1427 1428 /* Now make sure we are not exceeding the user maximum */ 1429 uTxPower = MIN(uTxPower, pRegulatoryDomain->uUserMaxTxPower); 1430 1431 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1432 ("%s uChannel = %d bServingChannel = %d uTxPower = %d \n", 1433 __FUNCTION__, uChannel, bServingChannel, uTxPower)); 1434 1435 return uTxPower; 1436 } 1437 1438 1439 static void regulatoryDomain_buildDefaultListOfChannelsPerBand(regulatoryDomain_t *pRegulatoryDomain, radioBand_e band, UINT8 *listSize) 1440 { 1441 UINT8 channelIndex; 1442 UINT8 numberOfChannels, minChannelNumber; 1443 channelCapability_t *pSupportedChannels; 1444 UINT8 maxSupportedChannels=0; 1445 1446 if ( (pRegulatoryDomain==NULL) || (listSize==NULL)) 1447 { 1448 return; 1449 } 1450 1451 if( band == RADIO_BAND_2_4_GHZ) 1452 { 1453 minChannelNumber = BG_24G_BAND_MIN_CHANNEL; 1454 numberOfChannels = NUM_OF_CHANNELS_24; 1455 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_2_4; 1456 } 1457 else 1458 { 1459 minChannelNumber = A_5G_BAND_MIN_CHANNEL; 1460 numberOfChannels = A_5G_BAND_NUM_CHANNELS; 1461 pSupportedChannels = pRegulatoryDomain->supportedChannels_band_5; 1462 } 1463 1464 1465 for (channelIndex=0; channelIndex<numberOfChannels; channelIndex++) 1466 { 1467 if (pSupportedChannels[channelIndex].channelValidityPassive) 1468 { 1469 pRegulatoryDomain->pDefaultChannels[maxSupportedChannels] = channelIndex+minChannelNumber; 1470 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1471 ("Channel num %d is supported \n", pRegulatoryDomain->pDefaultChannels[maxSupportedChannels])); 1472 maxSupportedChannels++; 1473 } 1474 } 1475 1476 *listSize = maxSupportedChannels; 1477 1478 } 1479 1480 /*********************************************************************** 1481 * regulatoryDomain_getPowerLevelTableCB 1482 *********************************************************************** 1483 DESCRIPTION: CB for retrieving power level table from FW (NVS). 1484 The table is made of 4 power levels and 5 bands/sub-bands. For 1485 each power level there's a maximum value of Dbm to be used. 1486 1487 RETURN: void 1488 1489 ************************************************************************/ 1490 static void regulatoryDomain_getPowerLevelTableCB( TI_HANDLE hRegulatoryDomain, TI_STATUS status, 1491 UINT8* CB_buf ) 1492 { 1493 regulatoryDomain_t *pRegulatoryDomain = (regulatoryDomain_t *)hRegulatoryDomain; 1494 UINT8 i; 1495 1496 /* Calculate Min and Max values of the table */ 1497 pRegulatoryDomain->uMinPowerDbm = MAX_TX_POWER; 1498 pRegulatoryDomain->uMaxPowerDbm = MIN_TX_POWER; 1499 for ( i = 0 ; i < NUM_SUB_BANDS_FOR_POWER_TABLE ; i++ ) 1500 { 1501 WLAN_REPORT_INFORMATION(pRegulatoryDomain->hReport, REGULATORY_DOMAIN_MODULE_LOG, 1502 ("PowerTable sub-band %i : %d %d %d %d\n", i, 1503 pRegulatoryDomain->tPowerLevelTableInterrogate.tTable.uDbm[i][0], 1504 pRegulatoryDomain->tPowerLevelTableInterrogate.tTable.uDbm[i][1], 1505 pRegulatoryDomain->tPowerLevelTableInterrogate.tTable.uDbm[i][2], 1506 pRegulatoryDomain->tPowerLevelTableInterrogate.tTable.uDbm[i][3])); 1507 1508 pRegulatoryDomain->uMinPowerDbm = MIN(pRegulatoryDomain->uMinPowerDbm, 1509 pRegulatoryDomain->tPowerLevelTableInterrogate.tTable.uDbm[i][MIN_POWER_LEVEL]); 1510 pRegulatoryDomain->uMaxPowerDbm = MAX(pRegulatoryDomain->uMaxPowerDbm, 1511 pRegulatoryDomain->tPowerLevelTableInterrogate.tTable.uDbm[i][MAX_POWER_LEVEL]); 1512 1513 } 1514 } 1515 1516 /* for debug */ 1517 void regDomainPrintValidTables(TI_HANDLE hRegulatoryDomain) 1518 { 1519 regulatoryDomain_t *pRegulatoryDomain = (regulatoryDomain_t *)hRegulatoryDomain; 1520 UINT16 channelIndex; 1521 1522 for (channelIndex=0; channelIndex<NUM_OF_CHANNELS_24; channelIndex++) 1523 { 1524 if (pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].channelValidityPassive) 1525 WLAN_OS_REPORT(("channel num =%d is valid for passive \n", channelIndex+1)); 1526 if (pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].channelValidityActive) 1527 { 1528 WLAN_OS_REPORT(("channel =%d is valid for active TX power=%d\n", 1529 channelIndex+1, pRegulatoryDomain->supportedChannels_band_2_4[channelIndex].uMaxTxPowerDomain)); 1530 } 1531 } 1532 1533 for (channelIndex=0; channelIndex<A_5G_BAND_NUM_CHANNELS; channelIndex++) 1534 { 1535 UINT8 channelNum; 1536 channelNum = channelIndex+A_5G_BAND_MIN_CHANNEL; 1537 if (pRegulatoryDomain->supportedChannels_band_5[channelIndex].channelValidityPassive) 1538 WLAN_OS_REPORT(("channel =%d is valid for passive \n", channelNum)); 1539 if (pRegulatoryDomain->supportedChannels_band_5[channelIndex].channelValidityActive) 1540 { 1541 WLAN_OS_REPORT(("channel =%d is valid for active TX power=%d\n", 1542 channelNum,pRegulatoryDomain->supportedChannels_band_5[channelIndex].uMaxTxPowerDomain)); 1543 } 1544 } 1545 1546 WLAN_OS_REPORT(("11h PowerConstraint = %d, EXC TPC = %d, User = %d\n", 1547 pRegulatoryDomain->uPowerConstraint, pRegulatoryDomain->uExternTxPowerPreferred, 1548 pRegulatoryDomain->uUserMaxTxPower)); 1549 1550 } 1551