Home | History | Annotate | Download | only in Sta_Management
      1 /*
      2  * assocSM.c
      3  *
      4  * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved.
      5  * All rights reserved.
      6  *
      7  * Redistribution and use in source and binary forms, with or without
      8  * modification, are permitted provided that the following conditions
      9  * are met:
     10  *
     11  *  * Redistributions of source code must retain the above copyright
     12  *    notice, this list of conditions and the following disclaimer.
     13  *  * Redistributions in binary form must reproduce the above copyright
     14  *    notice, this list of conditions and the following disclaimer in
     15  *    the documentation and/or other materials provided with the
     16  *    distribution.
     17  *  * Neither the name Texas Instruments nor the names of its
     18  *    contributors may be used to endorse or promote products derived
     19  *    from this software without specific prior written permission.
     20  *
     21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     22  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     24  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     25  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     26  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     27  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     28  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     29  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     30  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     31  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     32  */
     33 
     34 /** \file assocSM.c
     35  *  \brief 802.11 association SM source
     36  *
     37  *  \see assocSM.h
     38  */
     39 
     40 
     41 /***************************************************************************/
     42 /*                                                                         */
     43 /*      MODULE: assocSM.c                                                  */
     44 /*    PURPOSE:  802.11 association SM source                               */
     45 /*                                                                         */
     46 /***************************************************************************/
     47 
     48 #define __FILE_ID__  FILE_ID_63
     49 #include "osApi.h"
     50 #include "paramOut.h"
     51 #include "rate.h"
     52 #include "timer.h"
     53 #include "fsm.h"
     54 #include "report.h"
     55 #include "DataCtrl_Api.h"
     56 #include "siteMgrApi.h"
     57 #include "rsnApi.h"
     58 #include "regulatoryDomainApi.h"
     59 #include "mlmeBuilder.h"
     60 #include "mlmeApi.h"
     61 #include "AssocSM.h"
     62 #include "qosMngr_API.h"
     63 #ifdef XCC_MODULE_INCLUDED
     64 #include "XCCRMMngr.h"
     65 #include "XCCMngr.h"
     66 #endif
     67 #include "apConn.h"
     68 #include "TWDriver.h"
     69 #include "DrvMainModules.h"
     70 #include "StaCap.h"
     71 #include "smeApi.h"
     72 
     73 /* Constants */
     74 
     75 /** number of states in the state machine */
     76 #define ASSOC_SM_NUM_STATES     3
     77 
     78 /** number of events in the state machine */
     79 #define ASSOC_SM_NUM_EVENTS     6
     80 
     81 /* Enumerations */
     82 
     83 /* Typedefs */
     84 
     85 /* Structures */
     86 
     87 /* External data definitions */
     88 
     89 /* External functions definitions */
     90 
     91 /* Global variables */
     92 
     93 /* Local function prototypes */
     94 
     95 /* functions */
     96 
     97 
     98 /* state machine functions */
     99 
    100 
    101 TI_STATUS assoc_smEvent(assoc_t *pAssoc, TI_UINT8 event, void *pData);
    102 
    103 void assoc_smTimeout(TI_HANDLE hAssoc, TI_BOOL bTwdInitOccured);
    104 
    105 TI_STATUS assoc_smStartIdle(assoc_t *pAssoc);
    106 TI_STATUS assoc_smStopWait(assoc_t *pAssoc);
    107 TI_STATUS assoc_smSuccessWait(assoc_t *pAssoc);
    108 TI_STATUS assoc_smFailureWait(assoc_t *pAssoc);
    109 TI_STATUS assoc_smTimeoutWait(assoc_t *pAssoc);
    110 TI_STATUS assoc_smMaxRetryWait(assoc_t *pAssoc);
    111 TI_STATUS assoc_smStopAssoc(assoc_t *pAssoc);
    112 TI_STATUS assoc_smActionUnexpected(assoc_t *pAssoc);
    113 
    114 TI_STATUS assoc_smResetRetry(assoc_t *pAssoc);
    115 TI_STATUS assoc_smIncRetry(assoc_t *pAssoc);
    116 TI_STATUS assoc_smReportSuccess(assoc_t *pAssoc);
    117 TI_STATUS assoc_smReportFailure(assoc_t *pAssoc, TI_UINT16 uStatusCode);
    118 TI_STATUS assoc_smSendAssocReq(assoc_t *pAssoc);
    119 TI_STATUS assoc_smStartTimer(assoc_t *pAssoc);
    120 TI_STATUS assoc_smStopTimer(assoc_t *pAssoc);
    121 
    122 TI_STATUS assoc_smCapBuild(assoc_t *pCtx, TI_UINT16 *cap);
    123 TI_STATUS assoc_smSSIDBuild(assoc_t *pCtx, TI_UINT8 *pSSID, TI_UINT32 *ssidLen);
    124 TI_STATUS assoc_smRatesBuild(assoc_t *pCtx, TI_UINT8 *pRates, TI_UINT32 *ratesLen);
    125 TI_STATUS assoc_smRequestBuild(assoc_t *pCtx, TI_UINT8* reqBuf, TI_UINT32* reqLen);
    126 
    127 TI_STATUS assoc_saveAssocReqMessage(assoc_t *pAssocSm, TI_UINT8 *pAssocBuffer, TI_UINT32 length);
    128 TI_STATUS assoc_sendDisAssoc(assoc_t *pAssocSm, mgmtStatus_e reason);
    129 
    130 /**
    131 *
    132 * assoc_create - allocate memory for association SM
    133 *
    134 * \b Description:
    135 *
    136 * Allocate memory for association SM. \n
    137 *       Allocates memory for Association context. \n
    138 *       Allocates memory for association SM matrix. \n
    139 *
    140 * \b ARGS:
    141 *
    142 *  I   - hOs - OS context  \n
    143 *
    144 * \b RETURNS:
    145 *
    146 *  TI_OK if successful, TI_NOK otherwise.
    147 *
    148 * \sa rsn_mainSecSmKeysOnlyStop()
    149 */
    150 TI_HANDLE assoc_create(TI_HANDLE hOs)
    151 {
    152     assoc_t     *pHandle;
    153     TI_STATUS       status;
    154 
    155     /* allocate association context memory */
    156     pHandle = (assoc_t*)os_memoryAlloc(hOs, sizeof(assoc_t));
    157     if (pHandle == NULL)
    158     {
    159         return NULL;
    160     }
    161 
    162     os_memoryZero(hOs, pHandle, sizeof(assoc_t));
    163 
    164     pHandle->hOs = hOs;
    165 
    166     /* allocate memory for association state machine */
    167     status = fsm_Create(hOs, &pHandle->pAssocSm, ASSOC_SM_NUM_STATES, ASSOC_SM_NUM_EVENTS);
    168     if (status != TI_OK)
    169     {
    170         os_memoryFree(hOs, pHandle, sizeof(assoc_t));
    171         return NULL;
    172     }
    173 
    174     return pHandle;
    175 }
    176 
    177 
    178 /**
    179 *
    180 * assocunload - unload association SM from memory
    181 *
    182 * \b Description:
    183 *
    184 * Unload association SM from memory
    185 *
    186 * \b ARGS:
    187 *
    188 *  I   - hAssoc - association SM context  \n
    189 *
    190 * \b RETURNS:
    191 *
    192 *  TI_OK if successful, TI_NOK otherwise.
    193 *
    194 * \sa rsn_mainSecSmKeysOnlyStop()
    195 */
    196 TI_STATUS assoc_unload(TI_HANDLE hAssoc)
    197 {
    198     TI_STATUS       status;
    199     assoc_t     *pHandle;
    200 
    201     pHandle = (assoc_t*)hAssoc;
    202 
    203     status = fsm_Unload(pHandle->hOs, pHandle->pAssocSm);
    204     if (status != TI_OK)
    205     {
    206         /* report failure but don't stop... */
    207         TRACE0(pHandle->hReport, REPORT_SEVERITY_ERROR, "ASSOC_SM: Error releasing FSM memory \n");
    208     }
    209 
    210 	if (pHandle->hAssocSmTimer)
    211 	{
    212 		tmr_DestroyTimer (pHandle->hAssocSmTimer);
    213 	}
    214 
    215     os_memoryFree(pHandle->hOs, hAssoc, sizeof(assoc_t));
    216 
    217     return TI_OK;
    218 }
    219 
    220 /**
    221 *
    222 * assoc_config - configure a new association SM
    223 *
    224 * \b Description:
    225 *
    226 * Configure a new association SM.
    227 *
    228 * \b RETURNS:
    229 *
    230 *  void
    231 *
    232 * \sa assoc_Create, assoc_Unload
    233 */
    234 void assoc_init (TStadHandlesList *pStadHandles)
    235 {
    236     assoc_t *pHandle = (assoc_t*)(pStadHandles->hAssoc);
    237 
    238     /** Main 802.1X State Machine matrix */
    239     fsm_actionCell_t    assoc_smMatrix[ASSOC_SM_NUM_STATES][ASSOC_SM_NUM_EVENTS] =
    240     {
    241         /* next state and actions for IDLE state */
    242         {{ASSOC_SM_STATE_WAIT, (fsm_Action_t)assoc_smStartIdle},
    243          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smActionUnexpected},
    244          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smActionUnexpected},
    245          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smActionUnexpected},
    246          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smActionUnexpected},
    247          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smActionUnexpected}
    248         },
    249         /* next state and actions for WAIT state */
    250         {{ASSOC_SM_STATE_WAIT, (fsm_Action_t)assoc_smActionUnexpected},
    251          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smStopWait},
    252          {ASSOC_SM_STATE_ASSOC, (fsm_Action_t)assoc_smSuccessWait},
    253          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smFailureWait},
    254          {ASSOC_SM_STATE_WAIT, (fsm_Action_t)assoc_smTimeoutWait},
    255          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smMaxRetryWait}
    256         },
    257         /* next state and actions for ASSOC state */
    258         {{ASSOC_SM_STATE_ASSOC, (fsm_Action_t)assoc_smActionUnexpected},
    259          {ASSOC_SM_STATE_IDLE, (fsm_Action_t)assoc_smStopAssoc},
    260          {ASSOC_SM_STATE_ASSOC, (fsm_Action_t)assoc_smActionUnexpected},
    261          {ASSOC_SM_STATE_ASSOC, (fsm_Action_t)assoc_smActionUnexpected},
    262          {ASSOC_SM_STATE_ASSOC, (fsm_Action_t)assoc_smActionUnexpected},
    263          {ASSOC_SM_STATE_ASSOC, (fsm_Action_t)assoc_smActionUnexpected}
    264         }};
    265 
    266     /* configure state machine */
    267     fsm_Config (pHandle->pAssocSm, &assoc_smMatrix[0][0], ASSOC_SM_NUM_STATES, ASSOC_SM_NUM_EVENTS, NULL, pStadHandles->hOs);
    268 
    269     pHandle->assocRejectCount = 0;
    270     pHandle->assocTimeoutCount = 0;
    271     pHandle->currentState = ASSOC_SM_STATE_IDLE;
    272 
    273     pHandle->hMlme             = pStadHandles->hMlmeSm;
    274     pHandle->hRegulatoryDomain = pStadHandles->hRegulatoryDomain;
    275     pHandle->hSiteMgr          = pStadHandles->hSiteMgr;
    276     pHandle->hCtrlData         = pStadHandles->hCtrlData;
    277     pHandle->hTWD              = pStadHandles->hTWD;
    278     pHandle->hRsn              = pStadHandles->hRsn;
    279     pHandle->hReport           = pStadHandles->hReport;
    280     pHandle->hOs               = pStadHandles->hOs;
    281     pHandle->hXCCMngr          = pStadHandles->hXCCMngr;
    282     pHandle->hQosMngr          = pStadHandles->hQosMngr;
    283     pHandle->hMeasurementMgr   = pStadHandles->hMeasurementMgr;
    284     pHandle->hApConn           = pStadHandles->hAPConnection;
    285     pHandle->hTimer            = pStadHandles->hTimer;
    286     pHandle->hStaCap = pStadHandles->hStaCap;
    287     pHandle->hSme              = pStadHandles->hSme;
    288 
    289 }
    290 
    291 
    292 TI_STATUS assoc_SetDefaults (TI_HANDLE hAssoc, assocInitParams_t *pAssocInitParams)
    293 {
    294     assoc_t *pHandle = (assoc_t*)hAssoc;
    295 
    296     pHandle->timeout = pAssocInitParams->assocResponseTimeout;
    297     pHandle->maxCount = pAssocInitParams->assocMaxRetryCount;
    298 
    299     /* allocate OS timer memory */
    300     pHandle->hAssocSmTimer = tmr_CreateTimer (pHandle->hTimer);
    301     if (pHandle->hAssocSmTimer == NULL)
    302     {
    303         TRACE0(pHandle->hReport, REPORT_SEVERITY_ERROR, "assoc_SetDefaults(): Failed to create hAssocSmTimer!\n");
    304         return TI_NOK;
    305     }
    306 
    307     return TI_OK;
    308 }
    309 
    310 
    311 /**
    312 *
    313 * assoc_start - Start event for the association SM
    314 *
    315 * \b Description:
    316 *
    317 * Start event for the association SM
    318 *
    319 * \b ARGS:
    320 *
    321 *  I   - hAssoc - Association SM context  \n
    322 *
    323 * \b RETURNS:
    324 *
    325 *  TI_OK if successful, TI_NOK otherwise.
    326 *
    327 * \sa assoc_Stop, assoc_Recv
    328 */
    329 TI_STATUS assoc_start(TI_HANDLE hAssoc)
    330 {
    331     TI_STATUS       status;
    332     assoc_t     *pHandle;
    333 
    334     pHandle = (assoc_t*)hAssoc;
    335 
    336     if (pHandle == NULL)
    337     {
    338         return TI_NOK;
    339     }
    340 
    341     pHandle->reAssoc = TI_FALSE;
    342 
    343     pHandle->disAssoc = TI_FALSE;
    344 
    345     status = assoc_smEvent(pHandle, ASSOC_SM_EVENT_START, hAssoc);
    346 
    347     return status;
    348 }
    349 
    350 
    351 /**
    352 *
    353 * assoc_start - Start event for the association SM
    354 *
    355 * \b Description:
    356 *
    357 * Start event for the association SM - for Re-assoc request
    358 *
    359 * \b ARGS:
    360 *
    361 *  I   - hAssoc - Association SM context  \n
    362 *
    363 * \b RETURNS:
    364 *
    365 *  TI_OK if successful, TI_NOK otherwise.
    366 *
    367 * \sa assoc_Stop, assoc_Recv
    368 */
    369 TI_STATUS reassoc_start(TI_HANDLE hAssoc)
    370 {
    371     TI_STATUS       status;
    372     assoc_t     *pHandle;
    373 
    374     pHandle = (assoc_t*)hAssoc;
    375 
    376     if (pHandle == NULL)
    377     {
    378         return TI_NOK;
    379     }
    380     pHandle->reAssoc = TI_TRUE;
    381 
    382     status = assoc_smEvent(pHandle, ASSOC_SM_EVENT_START, hAssoc);
    383 
    384     return status;
    385 }
    386 
    387 /**
    388 *
    389 * assoc_stop - Stop event for the association SM
    390 *
    391 * \b Description:
    392 *
    393 * Stop event for the association SM
    394 *
    395 * \b ARGS:
    396 *
    397 *  I   - hAssoc - Association SM context  \n
    398 *
    399 * \b RETURNS:
    400 *
    401 *  TI_OK if successful, TI_NOK otherwise.
    402 *
    403 * \sa assoc_Start, assoc_Recv
    404 */
    405 TI_STATUS assoc_stop(TI_HANDLE hAssoc)
    406 {
    407     TI_STATUS       status;
    408     assoc_t     *pHandle;
    409 
    410     pHandle = (assoc_t*)hAssoc;
    411 
    412     if (pHandle == NULL)
    413     {
    414         return TI_NOK;
    415     }
    416 
    417     status = assoc_smEvent(pHandle, ASSOC_SM_EVENT_STOP, hAssoc);
    418 
    419     return status;
    420 }
    421 
    422 
    423 TI_STATUS assoc_setDisAssocFlag(TI_HANDLE hAssoc, TI_BOOL disAsoccFlag)
    424 {
    425     assoc_t     *pHandle;
    426     pHandle = (assoc_t*)hAssoc;
    427 
    428     pHandle->disAssoc = disAsoccFlag;
    429 
    430     return TI_OK;
    431 }
    432 
    433 
    434 
    435 /**
    436 *
    437 * assoc_recv - Recive a message from the AP
    438 *
    439 * \b Description:
    440 *
    441 * Parse a message form the AP and perform the appropriate event.
    442 *
    443 * \b ARGS:
    444 *
    445 *  I   - hAssoc - Association SM context  \n
    446 *  I   - pFrame - Frame recieved  \n
    447 *
    448 * \b RETURNS:
    449 *
    450 *  TI_OK if successful, TI_NOK otherwise.
    451 *
    452 * \sa assoc_Start, assoc_Stop
    453 */
    454 TI_STATUS assoc_recv(TI_HANDLE hAssoc, mlmeFrameInfo_t *pFrame)
    455 {
    456     TI_STATUS       status;
    457     assoc_t         *pHandle = (assoc_t*)hAssoc;
    458     TTwdParamInfo   tTwdParam;
    459     TI_UINT16           rspStatus;
    460 
    461     if (pHandle == NULL)
    462     {
    463         return TI_NOK;
    464     }
    465 
    466     /* ensure that the SM is waiting for assoc response */
    467     if(pHandle->currentState != ASSOC_SM_STATE_WAIT)
    468         return TI_OK;
    469 
    470 
    471     if ((pFrame->subType != ASSOC_RESPONSE) && (pFrame->subType != RE_ASSOC_RESPONSE))
    472     {
    473         return TI_NOK;
    474     }
    475 
    476     /* check response status */
    477     rspStatus  = pFrame->content.assocRsp.status;
    478 
    479     if (rspStatus == 0)
    480     {
    481         TRsnData        rsnData;
    482         dot11_RSN_t *pRsnIe;
    483         TI_UINT8       curRsnData[255];
    484         TI_UINT8       rsnAssocIeLen;
    485         TI_UINT8        length = 0;
    486 
    487 
    488         TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG Success associating to AP \n");
    489 
    490         /* set AID to HAL */
    491         tTwdParam.paramType = TWD_AID_PARAM_ID;
    492         tTwdParam.content.halCtrlAid  = pFrame->content.assocRsp.aid;
    493         TWD_SetParam (pHandle->hTWD, &tTwdParam);
    494 
    495 
    496         /* Get the RSN IE data */
    497         pRsnIe = pFrame->content.assocRsp.pRsnIe;
    498         while (length < pFrame->content.assocRsp.rsnIeLen && (pFrame->content.assocRsp.rsnIeLen < 255))
    499         {
    500             curRsnData[0+length] = pRsnIe->hdr[0];
    501             curRsnData[1+length] = pRsnIe->hdr[1];
    502             os_memoryCopy(pHandle->hOs, &curRsnData[2+length], (void *)pRsnIe->rsnIeData, pRsnIe->hdr[1]);
    503             length += pRsnIe->hdr[1] + 2;
    504             pRsnIe += 1;
    505         }
    506 
    507         if (pFrame->content.assocRsp.rsnIeLen != 0)
    508         {
    509             rsnData.pIe = curRsnData;
    510             rsnData.ieLen = pFrame->content.assocRsp.rsnIeLen;
    511             rsnData.privacy =  ((pFrame->content.assocRsp.capabilities >> CAP_PRIVACY_SHIFT) & CAP_PRIVACY_MASK) ? TI_TRUE : TI_FALSE;
    512             rsn_setSite(pHandle->hRsn, &rsnData, NULL, &rsnAssocIeLen);
    513         }
    514 
    515         /* update siteMgr with capabilities and whether we are connected to Cisco AP */
    516         siteMgr_assocReport(pHandle->hSiteMgr,
    517                             pFrame->content.assocRsp.capabilities, pFrame->content.assocRsp.ciscoIEPresent);
    518 
    519         /* update QoS Manager - it the QOS active protocol is NONE, or no WME IE present, it will return TI_OK */
    520         /* if configured by AP, update MSDU lifetime */
    521         status = qosMngr_setSite(pHandle->hQosMngr, &pFrame->content.assocRsp);
    522 
    523         if(status != TI_OK)
    524         {
    525             TRACE0(pHandle->hReport, REPORT_SEVERITY_ERROR, "ASSOC_SM: DEBUG - Association failed : qosMngr_setSite error \n");
    526             /* in case we wanted to work with qosAP and failed to connect to qos AP we want to reassociated again
    527                to another one */
    528             status = assoc_smEvent(pHandle, ASSOC_SM_EVENT_FAIL, hAssoc);
    529         }
    530         else
    531         {
    532             status = assoc_smEvent(pHandle, ASSOC_SM_EVENT_SUCCESS, hAssoc);
    533         }
    534     }
    535     else
    536     {
    537         pHandle->assocRejectCount++;
    538 
    539         /* If there was attempt to renegotiate voice settings, update QoS Manager */
    540         qosMngr_checkTspecRenegResults(pHandle->hQosMngr, &pFrame->content.assocRsp);
    541 
    542         /* check failure reason */
    543         switch (rspStatus)
    544         {
    545         case 0:
    546             break;
    547         case 1:
    548             /* print debug message */
    549             TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG - Association denied: Unspecified error \n");
    550             break;
    551         case 10:
    552             /* print debug message */
    553             TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG - Association denied: Cannot support all requested capabilities in the Capability Information field \n");
    554             break;
    555         case 11:
    556             /* print debug message */
    557             TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG - Association denied: Reassociation denied due to inability to confirm that association exists \n");
    558             break;
    559         case 12:
    560             /* print debug message */
    561             TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG - Association denied: Association denied due to reason outside the scope of this standard \n");
    562             rsn_reportAuthFailure(pHandle->hRsn, RSN_AUTH_STATUS_INVALID_TYPE);
    563             break;
    564         case 13:
    565             TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG - Association denied: Association denied due to wrong authentication algorithm \n");
    566             rsn_reportAuthFailure(pHandle->hRsn, RSN_AUTH_STATUS_INVALID_TYPE);
    567             break;
    568         case 17:
    569             /* print debug message */
    570             TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG - Association denied: Association denied because AP is unable to handle additional associated stations \n");
    571             break;
    572         case 18:
    573             /* print debug message */
    574             TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG - Association denied: Association denied due to requesting station not supporting all of the data rates in the BSSBasicRateSet parameter \n");
    575             break;
    576         default:
    577             /* print error message on wrong error code for association response */
    578             TRACE1(pHandle->hReport, REPORT_SEVERITY_ERROR, "ASSOC_SM: ERROR - Association denied: error code (%d) irrelevant \n", rspStatus);
    579             break;
    580         }
    581 
    582         status = assoc_smEvent(pHandle, ASSOC_SM_EVENT_FAIL, hAssoc);
    583     }
    584 
    585     return status;
    586 }
    587 
    588 /**
    589 *
    590 * assoc_getParam - Get a specific parameter from the association SM
    591 *
    592 * \b Description:
    593 *
    594 * Get a specific parameter from the association SM.
    595 *
    596 * \b ARGS:
    597 *
    598 *  I   - hAssoc - Association SM context  \n
    599 *  I/O - pParam - Parameter \n
    600 *
    601 * \b RETURNS:
    602 *
    603 *  TI_OK if successful, TI_NOK otherwise.
    604 *
    605 * \sa assoc_Start, assoc_Stop
    606 */
    607 TI_STATUS assoc_getParam(TI_HANDLE hAssoc, paramInfo_t *pParam)
    608 {
    609     assoc_t *pHandle = (assoc_t *)hAssoc;
    610 
    611     if ((pHandle == NULL) || (pParam == NULL))
    612     {
    613         return TI_NOK;
    614     }
    615 
    616     /* serch parameter type */
    617     switch (pParam->paramType)
    618     {
    619     case ASSOC_RESPONSE_TIMEOUT_PARAM:
    620         pParam->content.assocResponseTimeout = pHandle->timeout;
    621         break;
    622 
    623     case ASSOC_COUNTERS_PARAM:
    624         pParam->content.siteMgrTiWlanCounters.AssocRejects = pHandle->assocRejectCount;
    625         pParam->content.siteMgrTiWlanCounters.AssocTimeouts = pHandle->assocTimeoutCount;
    626         break;
    627 
    628     case ASSOC_ASSOCIATION_REQ_PARAM:
    629         pParam->content.assocReqBuffer.buffer = pHandle->assocReqBuffer;
    630         pParam->content.assocReqBuffer.bufferSize = pHandle->assocReqLen;
    631 		pParam->content.assocReqBuffer.reAssoc = pHandle->reAssoc;
    632         break;
    633 
    634     case ASSOC_ASSOCIATION_RESP_PARAM:
    635         pParam->content.assocReqBuffer.buffer = pHandle->assocRespBuffer;
    636         pParam->content.assocReqBuffer.bufferSize = pHandle->assocRespLen;
    637 		pParam->content.assocReqBuffer.reAssoc = pHandle->reAssocResp;
    638         break;
    639 
    640     case ASSOC_ASSOCIATION_INFORMATION_PARAM:
    641        {
    642            TI_UINT8  reqBuffIEOffset, respBuffIEOffset;
    643            TI_UINT32 RequestIELength = 0;
    644            TI_UINT32 ResponseIELength = 0;
    645            paramInfo_t  *lParam;
    646            ScanBssType_enum bssType;
    647 
    648            TRACE0(pHandle->hReport, REPORT_SEVERITY_SM, "ASSOC_SM: DEBUG - Association Information Get:  \n");
    649            lParam = (paramInfo_t *)os_memoryAlloc(pHandle->hOs, sizeof(paramInfo_t));
    650            if (!lParam)
    651                return TI_NOK;
    652 
    653            /* Assoc exists only in Infrastructure */
    654            lParam->paramType = CTRL_DATA_CURRENT_BSS_TYPE_PARAM;
    655            ctrlData_getParam(pHandle->hCtrlData, lParam);
    656            bssType = lParam->content.ctrlDataCurrentBssType;
    657            os_memoryFree(pHandle->hOs, lParam, sizeof(paramInfo_t));
    658            if (bssType != BSS_INFRASTRUCTURE)
    659            {
    660                TRACE0(pHandle->hReport, REPORT_SEVERITY_ERROR, "Not in Infrastructure BSS, No ASSOC Info for GET ASSOC_ASSOCIATION_INFORMATION_PARAM\n");
    661                return TI_NOK;
    662            }
    663 
    664            /* Init the result buffer to 0 */
    665            os_memoryZero(pHandle->hOs ,&pParam->content, sizeof(OS_802_11_ASSOCIATION_INFORMATION));
    666 
    667            reqBuffIEOffset  = 4;  /* In Assoc request frame IEs are located from byte 4 */
    668            respBuffIEOffset = 6;  /* In Assoc response frame the IEs are located from byte 6 */
    669 
    670             /* If the last associate was re-associciation, the current AP MAC address */
    671             /* is placed before the IEs. Copy it to the result parameters.            */
    672             if (pHandle->reAssoc)
    673             {
    674                 MAC_COPY (pParam->content.assocAssociationInformation.RequestFixedIEs.CurrentAPAddress,
    675                           &pHandle->assocReqBuffer[reqBuffIEOffset]);
    676                 reqBuffIEOffset += MAC_ADDR_LEN;
    677             }
    678 
    679             /* Calculate length of Info elements in assoc request and response frames */
    680             if(pHandle->assocReqLen > reqBuffIEOffset)
    681                 RequestIELength = pHandle->assocReqLen - reqBuffIEOffset;
    682 
    683             if(pHandle->assocRespLen > respBuffIEOffset)
    684                 ResponseIELength = pHandle->assocRespLen - respBuffIEOffset;
    685 
    686             /* Copy the association request information */
    687             pParam->content.assocAssociationInformation.Length = sizeof(OS_802_11_ASSOCIATION_INFORMATION);
    688             pParam->content.assocAssociationInformation.AvailableRequestFixedIEs = OS_802_11_AI_REQFI_CAPABILITIES | OS_802_11_AI_REQFI_LISTENINTERVAL;
    689             pParam->content.assocAssociationInformation.RequestFixedIEs.Capabilities = *(TI_UINT16*)&(pHandle->assocReqBuffer[0]);
    690             pParam->content.assocAssociationInformation.RequestFixedIEs.ListenInterval = *(TI_UINT16*)(&pHandle->assocReqBuffer[2]);
    691 
    692             pParam->content.assocAssociationInformation.RequestIELength = RequestIELength;
    693             pParam->content.assocAssociationInformation.OffsetRequestIEs = 0;
    694             if (RequestIELength > 0)
    695             {
    696                 pParam->content.assocAssociationInformation.OffsetRequestIEs = (TI_UINT32)&pHandle->assocReqBuffer[reqBuffIEOffset];
    697             }
    698             /* Copy the association response information */
    699             pParam->content.assocAssociationInformation.AvailableResponseFixedIEs =
    700                 OS_802_11_AI_RESFI_CAPABILITIES | OS_802_11_AI_RESFI_STATUSCODE | OS_802_11_AI_RESFI_ASSOCIATIONID;
    701             pParam->content.assocAssociationInformation.ResponseFixedIEs.Capabilities = *(TI_UINT16*)&(pHandle->assocRespBuffer[0]);
    702             pParam->content.assocAssociationInformation.ResponseFixedIEs.StatusCode = *(TI_UINT16*)&(pHandle->assocRespBuffer[2]);
    703             pParam->content.assocAssociationInformation.ResponseFixedIEs.AssociationId = *(TI_UINT16*)&(pHandle->assocRespBuffer[4]);
    704             pParam->content.assocAssociationInformation.ResponseIELength = ResponseIELength;
    705             pParam->content.assocAssociationInformation.OffsetResponseIEs = 0;
    706             if (ResponseIELength > 0)
    707             {
    708                 pParam->content.assocAssociationInformation.OffsetResponseIEs = (TI_UINT32)&pHandle->assocRespBuffer[respBuffIEOffset];
    709             }
    710 
    711        }
    712         break;
    713     default:
    714         return TI_NOK;
    715     }
    716 
    717     return TI_OK;
    718 }
    719 
    720 /**
    721 *
    722 * assoc_setParam - Set a specific parameter to the association SM
    723 *
    724 * \b Description:
    725 *
    726 * Set a specific parameter to the association SM.
    727 *
    728 * \b ARGS:
    729 *
    730 *  I   - hAssoc - Association SM context  \n
    731 *  I/O - pParam - Parameter \n
    732 *
    733 * \b RETURNS:
    734 *
    735 *  TI_OK if successful, TI_NOK otherwise.
    736 *
    737 * \sa assoc_Start, assoc_Stop
    738 */
    739 TI_STATUS assoc_setParam(TI_HANDLE hAssoc, paramInfo_t *pParam)
    740 {
    741     assoc_t     *pHandle;
    742 
    743     pHandle = (assoc_t*)hAssoc;
    744 
    745     if ((pHandle == NULL) || (pParam == NULL))
    746     {
    747         return TI_NOK;
    748     }
    749 
    750     switch (pParam->paramType)
    751     {
    752     case ASSOC_RESPONSE_TIMEOUT_PARAM:
    753         /* check bounds */
    754         if ((pParam->content.assocResponseTimeout >= ASSOC_RESPONSE_TIMEOUT_MIN) &&
    755             (pParam->content.assocResponseTimeout <= ASSOC_RESPONSE_TIMEOUT_MAX))
    756         {
    757             pHandle->timeout = pParam->content.assocResponseTimeout;
    758         } else {
    759             return TI_NOK;
    760         }
    761         break;
    762     default:
    763         return TI_NOK;
    764     }
    765 
    766     return TI_OK;
    767 }
    768 
    769 /**
    770 *
    771 * assoc_smTimeout - Time out event activation function
    772 *
    773 * \b Description:
    774 *
    775 * Time out event activation function.
    776 *
    777 * \b ARGS:
    778 *
    779 *  I   - hAssoc - Association SM context  \n
    780 *
    781 * \b RETURNS:
    782 *
    783 *  TI_OK if successful, TI_NOK otherwise.
    784 *
    785 * \sa assoc_Start, assoc_Stop
    786 */
    787 void assoc_smTimeout(TI_HANDLE hAssoc, TI_BOOL bTwdInitOccured)
    788 {
    789     assoc_t     *pHandle;
    790 
    791     pHandle = (assoc_t*)hAssoc;
    792 
    793 
    794     if (pHandle == NULL)
    795     {
    796         return;
    797     }
    798 
    799     pHandle->assocTimeoutCount++;
    800 
    801     assoc_smEvent(pHandle, ASSOC_SM_EVENT_TIMEOUT, hAssoc);
    802 }
    803 
    804 /**
    805 *
    806 * assoc_smEvent - Perform an event on the association SM
    807 *
    808 * \b Description:
    809 *
    810 * Perform an event on the association SM.
    811 *
    812 * \b ARGS:
    813 *
    814 *  I   - pAssoc - Association SM context  \n
    815 *  I   - event - Current event \n
    816 *  I   - pData - event related data
    817 *
    818 * \b RETURNS:
    819 *
    820 *  TI_OK if successful, TI_NOK otherwise.
    821 *
    822 * \sa
    823 */
    824 TI_STATUS assoc_smEvent(assoc_t *pAssoc, TI_UINT8 event, void *pData)
    825 {
    826     TI_STATUS       status;
    827     TI_UINT8        nextState;
    828 
    829     status = fsm_GetNextState(pAssoc->pAssocSm, pAssoc->currentState, event, &nextState);
    830     if (status != TI_OK)
    831     {
    832         TRACE0(pAssoc->hReport, REPORT_SEVERITY_ERROR, "ASSOC_SM: ERROR - failed getting next state \n");
    833 
    834         return(TI_NOK);
    835     }
    836 
    837 	TRACE3( pAssoc->hReport, REPORT_SEVERITY_INFORMATION, "assoc_smEvent: <currentState = %d, event = %d> --> nextState = %d\n", pAssoc->currentState, event, nextState);
    838 
    839     status = fsm_Event(pAssoc->pAssocSm, &pAssoc->currentState, event, pData);
    840 
    841     return(status);
    842 }
    843 
    844 /* state machine functions */
    845 
    846 TI_STATUS assoc_smStartIdle(assoc_t *pAssoc)
    847 {
    848     TI_STATUS       status;
    849 
    850     status = assoc_smResetRetry(pAssoc);
    851     status = assoc_smSendAssocReq(pAssoc);
    852     status = assoc_smStartTimer(pAssoc);
    853     status = assoc_smIncRetry(pAssoc);
    854 
    855     return status;
    856 }
    857 
    858 TI_STATUS assoc_smStopWait(assoc_t *pAssoc)
    859 {
    860     TI_STATUS       status;
    861 
    862     status = assoc_smStopTimer(pAssoc);
    863 
    864     return status;
    865 }
    866 
    867 TI_STATUS assoc_smSuccessWait(assoc_t *pAssoc)
    868 {
    869     TI_STATUS       status;
    870 
    871     status = assoc_smStopTimer(pAssoc);
    872     status = assoc_smReportSuccess(pAssoc);
    873 
    874     return status;
    875 }
    876 
    877 TI_STATUS assoc_smFailureWait(assoc_t *pAssoc)
    878 {
    879     TI_STATUS       status;
    880     TI_UINT16           uRspStatus = *(TI_UINT16*)&(pAssoc->assocRespBuffer[2]);
    881 
    882     status = assoc_smStopTimer(pAssoc);
    883 
    884     /* Sanity check. If the Response status is indeed not 0 */
    885     if (uRspStatus)
    886     {
    887         status = assoc_smReportFailure(pAssoc, uRspStatus);
    888     }
    889     else    /* (uRspStatus == 0) how did we get here ? */
    890     {
    891         TRACE0(pAssoc->hReport, REPORT_SEVERITY_ERROR, "while Response status is OK (0) !!! \n");
    892 
    893         status = assoc_smReportFailure(pAssoc, (TI_UINT16)TI_NOK);
    894     }
    895     return status;
    896 }
    897 
    898 TI_STATUS assoc_smTimeoutWait(assoc_t *pAssoc)
    899 {
    900     TI_STATUS       status;
    901 
    902     status = assoc_smSendAssocReq(pAssoc);
    903     status = assoc_smStartTimer(pAssoc);
    904     status = assoc_smIncRetry(pAssoc);
    905 
    906     return status;
    907 }
    908 
    909 TI_STATUS assoc_smMaxRetryWait(assoc_t *pAssoc)
    910 {
    911     TI_STATUS       status;
    912 
    913     status = assoc_smStopTimer(pAssoc);
    914     status = assoc_smReportFailure(pAssoc, STATUS_PACKET_REJ_TIMEOUT);
    915 
    916     return status;
    917 }
    918 
    919 TI_STATUS assoc_smSendAssocReq(assoc_t *pAssoc)
    920 {
    921     TI_UINT8           *assocMsg;
    922     TI_UINT32           msgLen;
    923     TI_STATUS           status;
    924     dot11MgmtSubType_e  assocType=ASSOC_REQUEST;
    925 
    926     assocMsg = os_memoryAlloc(pAssoc->hOs, MAX_ASSOC_MSG_LENGTH);
    927     if (!assocMsg)
    928         return TI_NOK;
    929 
    930     if (pAssoc->reAssoc)
    931     {
    932         assocType = RE_ASSOC_REQUEST;
    933     }
    934     status = assoc_smRequestBuild(pAssoc, assocMsg, &msgLen);
    935     if (status == TI_OK) {
    936         /* Save the association request message */
    937         assoc_saveAssocReqMessage(pAssoc, assocMsg, msgLen);
    938         status = mlmeBuilder_sendFrame(pAssoc->hMlme, assocType, assocMsg, msgLen, 0);
    939     }
    940     os_memoryFree(pAssoc->hOs, assocMsg, MAX_ASSOC_MSG_LENGTH);
    941     return status;
    942 }
    943 
    944 TI_STATUS assoc_smStopAssoc(assoc_t *pAssoc)
    945 {
    946     if (pAssoc->disAssoc) {
    947         assoc_sendDisAssoc(pAssoc, STATUS_UNSPECIFIED);
    948     }
    949     return TI_OK;
    950 }
    951 
    952 TI_STATUS assoc_smActionUnexpected(assoc_t *pAssoc)
    953 {
    954     return TI_OK;
    955 }
    956 
    957 /* local functions */
    958 
    959 
    960 TI_STATUS assoc_smResetRetry(assoc_t *pAssoc)
    961 {
    962     if (pAssoc == NULL)
    963     {
    964         return TI_NOK;
    965     }
    966 
    967     pAssoc->retryCount = 0;
    968 
    969     return TI_OK;
    970 }
    971 
    972 TI_STATUS assoc_smIncRetry(assoc_t *pAssoc)
    973 {
    974     TI_STATUS       status;
    975 
    976     if (pAssoc == NULL)
    977     {
    978         return TI_NOK;
    979     }
    980 
    981     pAssoc->retryCount++;
    982 
    983     if (pAssoc->retryCount > pAssoc->maxCount)
    984     {
    985         status = assoc_smEvent(pAssoc, ASSOC_SM_EVENT_MAX_RETRY, pAssoc);
    986 
    987         return status;
    988     }
    989 
    990     return TI_OK;
    991 }
    992 
    993 TI_STATUS assoc_smReportSuccess(assoc_t *pAssoc)
    994 {
    995     TI_STATUS       status;
    996 
    997     if (pAssoc == NULL)
    998     {
    999         return TI_NOK;
   1000     }
   1001     status = mlme_reportAssocStatus(pAssoc->hMlme, (TI_UINT16)TI_OK);
   1002 
   1003     return status;
   1004 }
   1005 
   1006 TI_STATUS assoc_smReportFailure(assoc_t *pAssoc, TI_UINT16 uStatusCode)
   1007 {
   1008     TI_STATUS       status;
   1009 
   1010     if (pAssoc == NULL)
   1011     {
   1012         return TI_NOK;
   1013     }
   1014 
   1015     status = mlme_reportAssocStatus(pAssoc->hMlme, uStatusCode);
   1016 
   1017     return status;
   1018 }
   1019 
   1020 TI_STATUS assoc_smStartTimer(assoc_t *pAssoc)
   1021 {
   1022     if (pAssoc == NULL)
   1023     {
   1024         return TI_NOK;
   1025     }
   1026 
   1027     tmr_StartTimer (pAssoc->hAssocSmTimer,
   1028                     assoc_smTimeout,
   1029                     (TI_HANDLE)pAssoc,
   1030                     pAssoc->timeout,
   1031                     TI_FALSE);
   1032 
   1033     return TI_OK;
   1034 }
   1035 
   1036 TI_STATUS assoc_smStopTimer(assoc_t *pAssoc)
   1037 {
   1038     if (pAssoc == NULL)
   1039     {
   1040         return TI_NOK;
   1041     }
   1042 
   1043     tmr_StopTimer (pAssoc->hAssocSmTimer);
   1044 
   1045     return TI_OK;
   1046 }
   1047 
   1048 /*****************************************************************************
   1049 **
   1050 ** Association messages builder/Parser
   1051 **
   1052 *****************************************************************************/
   1053 
   1054 TI_STATUS assoc_smCapBuild(assoc_t *pCtx, TI_UINT16 *cap)
   1055 {
   1056     paramInfo_t         param;
   1057     TI_STATUS           status;
   1058     EDot11Mode          mode;
   1059     TI_UINT32           rateSuppMask, rateBasicMask;
   1060     TI_UINT8            ratesBuf[DOT11_MAX_SUPPORTED_RATES];
   1061     TI_UINT32           len = 0, ofdmIndex = 0;
   1062     TI_BOOL             b11nEnable, bWmeEnable;
   1063 
   1064     *cap = 0;
   1065 
   1066     /* Bss type */
   1067     param.paramType = CTRL_DATA_CURRENT_BSS_TYPE_PARAM;
   1068     status =  ctrlData_getParam(pCtx->hCtrlData, &param);
   1069     if (status == TI_OK)
   1070     {
   1071         if (param.content.ctrlDataCurrentBssType == BSS_INFRASTRUCTURE)
   1072         {
   1073             *cap |= DOT11_CAPS_ESS;
   1074         } else {
   1075             *cap |= DOT11_CAPS_IBSS;
   1076         }
   1077     } else {
   1078         return TI_NOK;
   1079     }
   1080 
   1081     /* Privacy */
   1082     param.paramType = RSN_ENCRYPTION_STATUS_PARAM;
   1083     status =  rsn_getParam(pCtx->hRsn, &param);
   1084     if (status == TI_OK)
   1085     {
   1086         if (param.content.rsnEncryptionStatus != TWD_CIPHER_NONE)
   1087         {
   1088             *cap |= DOT11_CAPS_PRIVACY;
   1089         }
   1090     } else {
   1091         return TI_NOK;
   1092     }
   1093 
   1094     /* Preamble */
   1095     param.paramType = SITE_MGR_DESIRED_PREAMBLE_TYPE_PARAM;
   1096     status =  siteMgr_getParam(pCtx->hSiteMgr, &param);
   1097     if (status == TI_OK)
   1098     {
   1099         if (param.content.siteMgrCurrentPreambleType == PREAMBLE_SHORT)
   1100             *cap |= DOT11_CAPS_SHORT_PREAMBLE;
   1101     } else {
   1102         return TI_NOK;
   1103     }
   1104 
   1105     /* Pbcc */
   1106     param.paramType = SITE_MGR_CURRENT_RATE_PAIR_PARAM;
   1107     status =  siteMgr_getParam(pCtx->hSiteMgr, &param);
   1108     if (status == TI_OK)
   1109     {
   1110         if(param.content.siteMgrCurrentRateMask.supportedRateMask & DRV_RATE_MASK_22_PBCC)
   1111             *cap |= DOT11_CAPS_PBCC;
   1112     } else {
   1113         return TI_NOK;
   1114     }
   1115 
   1116 
   1117     /* Checking if the station supports Spectrum Management (802.11h) */
   1118     param.paramType = REGULATORY_DOMAIN_MANAGEMENT_CAPABILITY_ENABLED_PARAM;
   1119     status =  regulatoryDomain_getParam(pCtx->hRegulatoryDomain, &param);
   1120     if (status == TI_OK )
   1121     {
   1122         if( param.content.spectrumManagementEnabled)
   1123             *cap |= DOT11_SPECTRUM_MANAGEMENT;
   1124     }
   1125     else
   1126     {
   1127         return TI_NOK;
   1128     }
   1129 
   1130     /* slot time */
   1131     param.paramType = SITE_MGR_OPERATIONAL_MODE_PARAM;
   1132     status = siteMgr_getParam(pCtx->hSiteMgr, &param);
   1133     if(status == TI_OK)
   1134     {
   1135         mode = param.content.siteMgrDot11OperationalMode;
   1136     }
   1137     else
   1138         return TI_NOK;
   1139 
   1140     if(mode == DOT11_G_MODE)
   1141     {
   1142         /* new requirement: the short slot time should be set only
   1143            if the AP's modulation is OFDM (highest rate) */
   1144 
   1145         /* get Rates */
   1146         param.paramType = SITE_MGR_CURRENT_RATE_PAIR_PARAM;
   1147         status =  siteMgr_getParam(pCtx->hSiteMgr, &param);
   1148         if (status == TI_OK)
   1149         {
   1150             rateBasicMask = param.content.siteMgrCurrentRateMask.basicRateMask;
   1151             rateSuppMask  = param.content.siteMgrCurrentRateMask.supportedRateMask;
   1152         } else {
   1153             return TI_NOK;
   1154         }
   1155 
   1156         /* convert the bit map to the rates array */
   1157         rate_DrvBitmapToNetStr (rateSuppMask, rateBasicMask, ratesBuf, &len, &ofdmIndex);
   1158 
   1159         if(ofdmIndex < len)
   1160             *cap |= DOT11_CAPS_SHORT_SLOT_TIME;
   1161 
   1162 /*
   1163         param.paramType = SITE_MGR_CURRENT_MODULATION_TYPE_PARAM;
   1164         status = siteMgr_getParam(pCtx->hSiteMgr, &param);
   1165         if(param.content.siteMgrCurrentModulationType == DRV_MODULATION_OFDM)
   1166             *cap |= DOT11_CAPS_SHORT_SLOT_TIME;
   1167 */
   1168     }
   1169 
   1170     /* Immediate Block Ack subfield - (is WME on?) AND (is HT Enable?) */
   1171     /* verify 11n_Enable and Chip type */
   1172     StaCap_IsHtEnable (pCtx->hStaCap, &b11nEnable);
   1173     /* verify that WME flag enable */
   1174     qosMngr_GetWmeEnableFlag (pCtx->hQosMngr, &bWmeEnable);
   1175 
   1176     if ((b11nEnable != TI_FALSE) && (bWmeEnable != TI_FALSE))
   1177     {
   1178         *cap |= DOT11_CAPS_IMMEDIATE_BA;
   1179       }
   1180 
   1181     return TI_OK;
   1182 }
   1183 
   1184 
   1185 TI_STATUS assoc_smSSIDBuild(assoc_t *pCtx, TI_UINT8 *pSSID, TI_UINT32 *ssidLen)
   1186 {
   1187     paramInfo_t         param;
   1188     TI_STATUS               status;
   1189     dot11_SSID_t        *pDot11Ssid;
   1190 
   1191     pDot11Ssid = (dot11_SSID_t*)pSSID;
   1192     /* set SSID element id */
   1193     pDot11Ssid->hdr[0] = SSID_IE_ID;
   1194 
   1195     /* get SSID */
   1196     param.paramType = SME_DESIRED_SSID_ACT_PARAM;
   1197     status =  sme_GetParam(pCtx->hSme, &param);
   1198     if (status != TI_OK)
   1199     {
   1200         return status;
   1201     }
   1202 
   1203     /* check for ANY ssid */
   1204     if (param.content.smeDesiredSSID.len != 0)
   1205     {
   1206         pDot11Ssid->hdr[1] = param.content.smeDesiredSSID.len;
   1207         os_memoryCopy(pCtx->hOs,
   1208                       (void *)pDot11Ssid->serviceSetId,
   1209                       (void *)param.content.smeDesiredSSID.str,
   1210                       param.content.smeDesiredSSID.len);
   1211 
   1212     } else {
   1213         /* if ANY ssid is configured, use the current SSID */
   1214         param.paramType = SITE_MGR_CURRENT_SSID_PARAM;
   1215         status =  siteMgr_getParam(pCtx->hSiteMgr, &param);
   1216         if (status != TI_OK)
   1217         {
   1218             return status;
   1219         }
   1220         pDot11Ssid->hdr[1] = param.content.siteMgrCurrentSSID.len;
   1221         os_memoryCopy(pCtx->hOs,
   1222                       (void *)pDot11Ssid->serviceSetId,
   1223                       (void *)param.content.siteMgrCurrentSSID.str,
   1224                       param.content.siteMgrCurrentSSID.len);
   1225 
   1226     }
   1227 
   1228     *ssidLen = pDot11Ssid->hdr[1] + sizeof(dot11_eleHdr_t);
   1229 
   1230     return TI_OK;
   1231 }
   1232 
   1233 TI_STATUS assoc_smRatesBuild(assoc_t *pCtx, TI_UINT8 *pRates, TI_UINT32 *ratesLen)
   1234 {
   1235     paramInfo_t         param;
   1236     TI_STATUS           status;
   1237     TI_UINT32           rateSuppMask, rateBasicMask;
   1238     dot11_RATES_t       *pDot11Rates;
   1239     TI_UINT32           len = 0, ofdmIndex = 0;
   1240     TI_UINT8            ratesBuf[DOT11_MAX_SUPPORTED_RATES];
   1241     EDot11Mode          mode;
   1242     TI_UINT32           suppRatesLen, extSuppRatesLen, i;
   1243     pDot11Rates = (dot11_RATES_t*)pRates;
   1244 
   1245 
   1246     /* get Rates */
   1247     param.paramType = SITE_MGR_CURRENT_RATE_PAIR_PARAM;
   1248     status =  siteMgr_getParam(pCtx->hSiteMgr, &param);
   1249     if (status == TI_OK)
   1250     {
   1251         rateBasicMask = param.content.siteMgrCurrentRateMask.basicRateMask;
   1252         rateSuppMask  = param.content.siteMgrCurrentRateMask.supportedRateMask;
   1253     }
   1254     else
   1255     {
   1256         return TI_NOK;
   1257     }
   1258 
   1259     /* get operational mode */
   1260     param.paramType = SITE_MGR_OPERATIONAL_MODE_PARAM;
   1261     status = siteMgr_getParam(pCtx->hSiteMgr, &param);
   1262     if(status == TI_OK)
   1263         mode = param.content.siteMgrDot11OperationalMode;
   1264     else
   1265         return TI_NOK;
   1266 
   1267     /* convert the bit map to the rates array */
   1268     /* remove MCS rates from Extended Supported Rates IE */
   1269     rateSuppMask &= ~(DRV_RATE_MASK_MCS_0_OFDM |
   1270                       DRV_RATE_MASK_MCS_1_OFDM |
   1271                       DRV_RATE_MASK_MCS_2_OFDM |
   1272                       DRV_RATE_MASK_MCS_3_OFDM |
   1273                       DRV_RATE_MASK_MCS_4_OFDM |
   1274                       DRV_RATE_MASK_MCS_5_OFDM |
   1275                       DRV_RATE_MASK_MCS_6_OFDM |
   1276                       DRV_RATE_MASK_MCS_7_OFDM );
   1277 
   1278     rate_DrvBitmapToNetStr (rateSuppMask, rateBasicMask, ratesBuf, &len, &ofdmIndex);
   1279 
   1280     if(mode != DOT11_G_MODE || ofdmIndex == len )
   1281     {
   1282         pDot11Rates->hdr[0] = SUPPORTED_RATES_IE_ID;
   1283         pDot11Rates->hdr[1] = len;
   1284         os_memoryCopy(NULL, (void *)pDot11Rates->rates, ratesBuf, len);
   1285         *ratesLen = pDot11Rates->hdr[1] + sizeof(dot11_eleHdr_t);
   1286     }
   1287     else
   1288     {
   1289         /* fill in the supported rates */
   1290         pDot11Rates->hdr[0] = SUPPORTED_RATES_IE_ID;
   1291         pDot11Rates->hdr[1] = ofdmIndex;
   1292         os_memoryCopy(NULL, (void *)pDot11Rates->rates, ratesBuf, pDot11Rates->hdr[1]);
   1293         suppRatesLen = pDot11Rates->hdr[1] + sizeof(dot11_eleHdr_t);
   1294         /* fill in the extended supported rates */
   1295         pDot11Rates = (dot11_RATES_t*)(pRates + suppRatesLen);
   1296         pDot11Rates->hdr[0] = EXT_SUPPORTED_RATES_IE_ID;
   1297         pDot11Rates->hdr[1] = len - ofdmIndex;
   1298         os_memoryCopy(NULL, (void *)pDot11Rates->rates, &ratesBuf[ofdmIndex], pDot11Rates->hdr[1]);
   1299         extSuppRatesLen = pDot11Rates->hdr[1] + sizeof(dot11_eleHdr_t);
   1300         *ratesLen = suppRatesLen + extSuppRatesLen;
   1301     }
   1302 
   1303     TRACE3(pCtx->hReport, REPORT_SEVERITY_INFORMATION, "ASSOC_SM: ASSOC_REQ - bitmapSupp= 0x%X,bitMapBasic = 0x%X, len = %d\n", rateSuppMask,rateBasicMask,len);
   1304     for(i=0; i<len; i++)
   1305     {
   1306         TRACE2(pCtx->hReport, REPORT_SEVERITY_INFORMATION, "ASSOC_SM: ASSOC_REQ - ratesBuf[%d] = 0x%X\n", i, ratesBuf[i]);
   1307     }
   1308 
   1309     return TI_OK;
   1310 }
   1311 
   1312 TI_STATUS assoc_powerCapabilityBuild(assoc_t *pCtx, TI_UINT8 *pPowerCapability, TI_UINT32 *powerCapabilityLen)
   1313 {
   1314     paramInfo_t         param;
   1315     TI_STATUS               status;
   1316     dot11_CAPABILITY_t      *pDot11PowerCapability;
   1317 
   1318     pDot11PowerCapability = (dot11_CAPABILITY_t*)pPowerCapability;
   1319 
   1320     /* set Power Capability element id */
   1321     pDot11PowerCapability->hdr[0] = DOT11_CAPABILITY_ELE_ID;
   1322     pDot11PowerCapability->hdr[1] = DOT11_CAPABILITY_ELE_LEN;
   1323 
   1324     /* get power capability */
   1325     param.paramType = REGULATORY_DOMAIN_POWER_CAPABILITY_PARAM;
   1326     status =  regulatoryDomain_getParam(pCtx->hRegulatoryDomain, &param);
   1327 
   1328     if (status == TI_OK)
   1329     {
   1330         pDot11PowerCapability->minTxPower = param.content.powerCapability.minTxPower;
   1331         pDot11PowerCapability->maxTxPower = param.content.powerCapability.maxTxPower;
   1332         *powerCapabilityLen = pDot11PowerCapability->hdr[1] + sizeof(dot11_eleHdr_t);
   1333     }
   1334     else
   1335         *powerCapabilityLen = 0;
   1336 
   1337     return TI_OK;
   1338 }
   1339 
   1340 TI_STATUS assoc_smRequestBuild(assoc_t *pCtx, TI_UINT8* reqBuf, TI_UINT32* reqLen)
   1341 {
   1342     TI_STATUS       status;
   1343     TI_UINT8        *pRequest;
   1344     TI_UINT32       len;
   1345     paramInfo_t     param;
   1346     TTwdParamInfo   tTwdParam;
   1347     TI_UINT16       capabilities;
   1348 
   1349     pRequest = reqBuf;
   1350     *reqLen = 0;
   1351 
   1352     /* insert capabilities */
   1353     status = assoc_smCapBuild(pCtx, &capabilities);
   1354     if (status == TI_OK)
   1355     {
   1356         *(TI_UINT16*)pRequest = capabilities;
   1357     }
   1358     else
   1359         return TI_NOK;
   1360 
   1361     pRequest += 2;
   1362     *reqLen += 2;
   1363 
   1364     /* insert listen interval */
   1365     tTwdParam.paramType = TWD_LISTEN_INTERVAL_PARAM_ID;
   1366     status =  TWD_GetParam (pCtx->hTWD, &tTwdParam);
   1367     if (status == TI_OK)
   1368     {
   1369         *(TI_UINT16*)pRequest = ENDIAN_HANDLE_WORD((TI_UINT16)tTwdParam.content.halCtrlListenInterval);
   1370     } else {
   1371         return TI_NOK;
   1372     }
   1373 
   1374     pRequest += 2;
   1375     *reqLen += 2;
   1376     if (pCtx->reAssoc)
   1377     {   /* Insert currentAPAddress element only in reassoc request*/
   1378         param.paramType = SITE_MGR_PREV_SITE_BSSID_PARAM;
   1379         status = siteMgr_getParam(pCtx->hSiteMgr, &param);
   1380         if (status == TI_OK)
   1381         {
   1382             MAC_COPY (pRequest, param.content.siteMgrDesiredBSSID);
   1383             TRACE6(pCtx->hReport, REPORT_SEVERITY_INFORMATION, "ASSOC_SM: ASSOC_REQ - prev AP = %x-%x-%x-%x-%x-%x\n", param.content.siteMgrDesiredBSSID[0], param.content.siteMgrDesiredBSSID[1], param.content.siteMgrDesiredBSSID[2], param.content.siteMgrDesiredBSSID[3], param.content.siteMgrDesiredBSSID[4], param.content.siteMgrDesiredBSSID[5]);
   1384 
   1385 
   1386             pRequest += MAC_ADDR_LEN;
   1387             *reqLen += MAC_ADDR_LEN;
   1388         }
   1389         else
   1390         {
   1391             TRACE0(pCtx->hReport, REPORT_SEVERITY_ERROR, "ASSOC_SM: ASSOC_REQ - No prev AP \n");
   1392             return status;
   1393 
   1394         }
   1395     }
   1396 
   1397     /* insert SSID element */
   1398     status = assoc_smSSIDBuild(pCtx, pRequest, &len);
   1399     if (status != TI_OK)
   1400     {
   1401         return TI_NOK;
   1402     }
   1403 
   1404     pRequest += len;
   1405     *reqLen += len;
   1406 
   1407     /* insert Rates element */
   1408     status = assoc_smRatesBuild(pCtx, pRequest, &len);
   1409     if (status != TI_OK)
   1410     {
   1411         return TI_NOK;
   1412     }
   1413     pRequest += len;
   1414     *reqLen += len;
   1415 
   1416     /* Checking if the station supports Spectrum Management (802.11h) */
   1417     param.paramType = REGULATORY_DOMAIN_MANAGEMENT_CAPABILITY_ENABLED_PARAM;
   1418     status = regulatoryDomain_getParam(pCtx->hRegulatoryDomain,&param);
   1419     if( (status == TI_OK) && param.content.spectrumManagementEnabled)
   1420     {
   1421         /* Checking the selected AP capablities */
   1422         param.paramType = SITE_MGR_SITE_CAPABILITY_PARAM;
   1423         status =  siteMgr_getParam(pCtx->hSiteMgr,&param);
   1424         if(status == TI_OK && ((param.content.siteMgrSiteCapability & DOT11_SPECTRUM_MANAGEMENT) != 0))
   1425         {
   1426             /* insert Power capability element */
   1427             status = assoc_powerCapabilityBuild(pCtx, pRequest, &len);
   1428             if (status != TI_OK)
   1429             {
   1430                 return TI_NOK;
   1431             }
   1432             pRequest += len;
   1433             *reqLen += len;
   1434 #if 0
   1435             /* insert Supported Channels element */
   1436             status = assoc_supportedChannelBuild(pCtx, pRequest, &len);
   1437             if (status != TI_OK)
   1438             {
   1439                 return TI_NOK;
   1440             }
   1441             pRequest += len;
   1442             *reqLen += len;
   1443 #endif
   1444         }
   1445 
   1446 
   1447     }
   1448 
   1449     status = qosMngr_getQosCapabiltyInfeElement(pCtx->hQosMngr,pRequest,&len);
   1450     if (status != TI_OK)
   1451     {
   1452         return TI_NOK;
   1453     }
   1454     pRequest += len;
   1455     *reqLen += len;
   1456 
   1457 
   1458 #ifdef XCC_MODULE_INCLUDED
   1459     status = rsn_getXCCExtendedInfoElement(pCtx->hRsn, pRequest, (TI_UINT8*)&len);
   1460     if (status != TI_OK)
   1461     {
   1462         return TI_NOK;
   1463     }
   1464     pRequest += len;
   1465     *reqLen += len;
   1466 
   1467     if (pCtx->reAssoc)
   1468     {   /* insert CCKM information element only in reassoc */
   1469         status = XCCMngr_getCckmInfoElement(pCtx->hXCCMngr, pRequest, (TI_UINT8*)&len);
   1470 
   1471         if (status != TI_OK)
   1472         {
   1473             return TI_NOK;
   1474         }
   1475         pRequest += len;
   1476         *reqLen += len;
   1477     }
   1478     status = XCCMngr_getXCCVersionInfoElement(pCtx->hXCCMngr, pRequest, (TI_UINT8*)&len);
   1479     if (status != TI_OK)
   1480     {
   1481         return TI_NOK;
   1482     }
   1483     pRequest += len;
   1484     *reqLen += len;
   1485 
   1486     /* Insert Radio Mngt Capability IE */
   1487     status = measurementMgr_radioMngtCapabilityBuild(pCtx->hMeasurementMgr, pRequest, (TI_UINT8*)&len);
   1488     if (status != TI_OK)
   1489     {
   1490         return TI_NOK;
   1491     }
   1492     pRequest += len;
   1493     *reqLen += len;
   1494 #endif
   1495 
   1496      /* Get Simple-Config state */
   1497     param.paramType = SITE_MGR_SIMPLE_CONFIG_MODE;
   1498     status = siteMgr_getParam(pCtx->hSiteMgr, &param);
   1499 
   1500    if (param.content.siteMgrWSCMode.WSCMode == TIWLN_SIMPLE_CONFIG_OFF)
   1501    {
   1502     /* insert RSN information elements */
   1503     status = rsn_getInfoElement(pCtx->hRsn, pRequest, &len);
   1504 
   1505 	if (status != TI_OK)
   1506 	{
   1507 		return TI_NOK;
   1508 	}
   1509 	pRequest += len;
   1510 	*reqLen += len;
   1511   }
   1512 
   1513     /* Primary Site support HT ? */
   1514     param.paramType = SITE_MGR_PRIMARY_SITE_HT_SUPPORT;
   1515     siteMgr_getParam(pCtx->hSiteMgr, &param);
   1516 
   1517     if(TI_TRUE == param.content.bPrimarySiteHtSupport)
   1518     {
   1519         status = StaCap_GetHtCapabilitiesIe (pCtx->hStaCap, pRequest, &len);
   1520     	if (status != TI_OK)
   1521     	{
   1522     		return TI_NOK;
   1523     	}
   1524     	pRequest += len;
   1525     	*reqLen += len;
   1526     }
   1527 
   1528 	status = qosMngr_assocReqBuild(pCtx->hQosMngr,pRequest,&len);
   1529 	if (status != TI_OK)
   1530 	{
   1531 		return TI_NOK;
   1532 	}
   1533 	pRequest += len;
   1534 	*reqLen += len;
   1535 
   1536 	status = apConn_getVendorSpecificIE(pCtx->hApConn, pRequest, &len);
   1537 	if (status != TI_OK)
   1538 	{
   1539 		return TI_NOK;
   1540 	}
   1541 	pRequest += len;
   1542 	*reqLen += len;
   1543 
   1544     if (*reqLen>=MAX_ASSOC_MSG_LENGTH)
   1545     {
   1546         return TI_NOK;
   1547     }
   1548 
   1549     return TI_OK;
   1550 }
   1551 
   1552 
   1553 
   1554 TI_STATUS assoc_saveAssocRespMessage(assoc_t *pAssocSm, TI_UINT8 *pAssocBuffer, TI_UINT32 length)
   1555 {
   1556     if ((pAssocSm==NULL) || (pAssocBuffer==NULL) || (length>=MAX_ASSOC_MSG_LENGTH))
   1557     {
   1558         return TI_NOK;
   1559     }
   1560     os_memoryCopy(pAssocSm->hOs, pAssocSm->assocRespBuffer, pAssocBuffer, length);
   1561     pAssocSm->assocRespLen = length;
   1562 
   1563     TRACE1(pAssocSm->hReport, REPORT_SEVERITY_INFORMATION, "assoc_saveAssocRespMessage: length=%ld \n",length);
   1564     return TI_OK;
   1565 }
   1566 
   1567 TI_STATUS assoc_saveAssocReqMessage(assoc_t *pAssocSm, TI_UINT8 *pAssocBuffer, TI_UINT32 length)
   1568 {
   1569 
   1570     if ((pAssocSm==NULL) || (pAssocBuffer==NULL) || (length>=MAX_ASSOC_MSG_LENGTH))
   1571     {
   1572         return TI_NOK;
   1573     }
   1574 
   1575     os_memoryCopy(pAssocSm->hOs, pAssocSm->assocReqBuffer, pAssocBuffer, length);
   1576     pAssocSm->assocReqLen = length;
   1577 
   1578     TRACE1(pAssocSm->hReport, REPORT_SEVERITY_INFORMATION, "assoc_saveAssocReqMessage: length=%ld \n",length);
   1579     return TI_OK;
   1580 }
   1581 
   1582 
   1583 TI_STATUS assoc_sendDisAssoc(assoc_t *pAssocSm, mgmtStatus_e reason)
   1584 {
   1585     TI_STATUS       status;
   1586     disAssoc_t      disAssoc;
   1587 
   1588     if (reason == STATUS_SUCCESSFUL)
   1589     {
   1590         disAssoc.reason = ENDIAN_HANDLE_WORD(STATUS_UNSPECIFIED);
   1591     } else {
   1592         disAssoc.reason = ENDIAN_HANDLE_WORD(reason);
   1593     }
   1594 
   1595     status = mlmeBuilder_sendFrame(pAssocSm->hMlme, DIS_ASSOC, (TI_UINT8*)&disAssoc, sizeof(disAssoc_t), 0);
   1596 
   1597     return status;
   1598 }
   1599 
   1600 
   1601