diff options
Diffstat (limited to 'wilink_6_1/stad/src/Ctrl_Interface')
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/CmdDispatcher.c | 535 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/CmdDispatcher.h | 59 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/CmdHndlr.c | 495 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/CmdHndlr.h | 88 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/CmdInterpret.h | 55 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/DrvMain.c | 1772 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/DrvMain.h | 60 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/DrvMainModules.h | 86 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/EvHandler.c | 287 | ||||
-rw-r--r-- | wilink_6_1/stad/src/Ctrl_Interface/EvHandler.h | 77 |
10 files changed, 3514 insertions, 0 deletions
diff --git a/wilink_6_1/stad/src/Ctrl_Interface/CmdDispatcher.c b/wilink_6_1/stad/src/Ctrl_Interface/CmdDispatcher.c new file mode 100644 index 0000000..135c772 --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/CmdDispatcher.c @@ -0,0 +1,535 @@ +/* + * CmdDispatcher.c + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + + +/** \file CmdDispatcher.c + * \brief The CmdDispatcher module. Handles user commbands dispatching to the driver modules. + * + * \see CmdDispatcher.h + */ + +#define __FILE_ID__ FILE_ID_47 +#include "tidef.h" +#include "osApi.h" +#include "report.h" +#include "DrvMain.h" +#include "connApi.h" +#include "siteMgrApi.h" +#include "smeApi.h" +#include "SoftGeminiApi.h" +#include "roamingMngrApi.h" +#include "qosMngr_API.h" +#include "PowerMgr_API.h" +#include "ScanCncn.h" +#include "scanMngrApi.h" +#include "regulatoryDomainApi.h" +#include "measurementMgrApi.h" +#include "TWDriver.h" +#include "debug.h" +#include "DrvMainModules.h" +#include "CmdDispatcher.h" +#include "healthMonitor.h" +#include "currBssApi.h" +#ifdef XCC_MODULE_INCLUDED +#include "XCCMngr.h" +#endif + + +/* Set/get params function prototype */ +typedef TI_STATUS (*TParamFunc) (TI_HANDLE handle, paramInfo_t *pParam); + +typedef struct +{ + TParamFunc set; + TParamFunc get; + TI_HANDLE handle; + +} TParamAccess; + +/* The module's object */ +typedef struct +{ + /* Other modules handles */ + TI_HANDLE hOs; + TI_HANDLE hReport; + TI_HANDLE hAuth; + TI_HANDLE hAssoc; + TI_HANDLE hRxData; + TI_HANDLE hTxCtrl; + TI_HANDLE hCtrlData; + TI_HANDLE hSiteMgr; + TI_HANDLE hConn; + TI_HANDLE hRsn; + TI_HANDLE hSme; + TI_HANDLE hScanCncn; + TI_HANDLE hScanMngr; + TI_HANDLE hMlmeSm; + TI_HANDLE hRegulatoryDomain; + TI_HANDLE hMeasurementMgr; + TI_HANDLE hRoamingMngr; + TI_HANDLE hSoftGemini; + TI_HANDLE hQosMngr; + TI_HANDLE hPowerMgr; + TI_HANDLE hHealthMonitor; + TI_HANDLE hTWD; + TI_HANDLE hCurrBss; +#ifdef XCC_MODULE_INCLUDED + TI_HANDLE hXCCMngr; +#endif + + /* Table of params set/get functions */ + TParamAccess paramAccessTable[MAX_PARAM_MODULE_NUMBER]; + +#ifdef TI_DBG + TStadHandlesList *pStadHandles; /* Save modules list pointer just for the debug functions */ +#endif + +} TCmdDispatchObj; + + +/* Internal functions prototypes */ +static void cmdDispatch_ConfigParamsAccessTable (TCmdDispatchObj *pCmdDispatch); +static TI_STATUS cmdDispatch_SetTwdParam (TI_HANDLE hCmdDispatch, paramInfo_t *pParam); +static TI_STATUS cmdDispatch_GetTwdParam (TI_HANDLE hCmdDispatch, paramInfo_t *pParam); + +#ifdef TI_DBG +static TI_STATUS cmdDispatch_DebugFuncSet (TI_HANDLE hCmdDispatch, paramInfo_t *pParam); +static TI_STATUS cmdDispatch_DebugFuncGet (TI_HANDLE hCmdDispatch, paramInfo_t *pParam); /*yael - this function is not in use*/ +#endif + + + +/** + * \fn cmdDispatch_Create + * \brief Create the module + * + * Create the Command-Dispatcher module + * + * \note + * \param hOs - Handle to the Os Abstraction Layer + * \return Handle to the allocated module (NULL if failed) + * \sa + */ +TI_HANDLE cmdDispatch_Create (TI_HANDLE hOs) +{ + TCmdDispatchObj *pCmdDispatch; + + /* allocate CmdDispatcher module */ + pCmdDispatch = os_memoryAlloc (hOs, (sizeof(TCmdDispatchObj))); + + if (!pCmdDispatch) + { + WLAN_OS_REPORT(("Error allocating the CmdDispatcher Module\n")); + return NULL; + } + + /* Reset CmdDispatcher module */ + os_memoryZero (hOs, pCmdDispatch, (sizeof(TCmdDispatchObj))); + + pCmdDispatch->hOs = hOs; + + return (TI_HANDLE)pCmdDispatch; +} + + +/** + * \fn cmdDispatch_Init + * \brief Save modules handles and fill the configuration table + * + * Save other modules handles, and fill the configuration table + * with the Get/Set functions. + * + * \note + * \param pStadHandles - The driver modules handles + * \return void + * \sa + */ +void cmdDispatch_Init (TStadHandlesList *pStadHandles) +{ + TCmdDispatchObj *pCmdDispatch = (TCmdDispatchObj *)(pStadHandles->hCmdDispatch); + + /* Save modules handles */ + pCmdDispatch->hReport = pStadHandles->hReport; + pCmdDispatch->hAuth = pStadHandles->hAuth; + pCmdDispatch->hAssoc = pStadHandles->hAssoc; + pCmdDispatch->hRxData = pStadHandles->hRxData; + pCmdDispatch->hTxCtrl = pStadHandles->hTxCtrl; + pCmdDispatch->hCtrlData = pStadHandles->hCtrlData; + pCmdDispatch->hSiteMgr = pStadHandles->hSiteMgr; + pCmdDispatch->hConn = pStadHandles->hConn; + pCmdDispatch->hRsn = pStadHandles->hRsn; + pCmdDispatch->hSme = pStadHandles->hSme; + pCmdDispatch->hScanCncn = pStadHandles->hScanCncn; + pCmdDispatch->hScanMngr = pStadHandles->hScanMngr; + pCmdDispatch->hMlmeSm = pStadHandles->hMlmeSm; + pCmdDispatch->hRegulatoryDomain = pStadHandles->hRegulatoryDomain; + pCmdDispatch->hMeasurementMgr = pStadHandles->hMeasurementMgr; + pCmdDispatch->hRoamingMngr = pStadHandles->hRoamingMngr; + pCmdDispatch->hSoftGemini = pStadHandles->hSoftGemini; + pCmdDispatch->hQosMngr = pStadHandles->hQosMngr; + pCmdDispatch->hPowerMgr = pStadHandles->hPowerMgr; + pCmdDispatch->hHealthMonitor = pStadHandles->hHealthMonitor; + pCmdDispatch->hTWD = pStadHandles->hTWD; + pCmdDispatch->hCurrBss = pStadHandles->hCurrBss; +#ifdef XCC_MODULE_INCLUDED + pCmdDispatch->hXCCMngr = pStadHandles->hXCCMngr; +#endif + +#ifdef TI_DBG + pCmdDispatch->pStadHandles = pStadHandles; /* Save modules list pointer just for the debug functions */ +#endif + + /* Fill the configuration table with the Get/Set functions */ + cmdDispatch_ConfigParamsAccessTable (pCmdDispatch); +} + + +/** + * \fn cmdDispatch_Destroy + * \brief Destroy the module object + * + * Destroy the module object. + * + * \note + * \param hCmdDispatch - The object + * \return TI_OK - Unload succesfull, TI_NOK - Unload unsuccesfull + * \sa + */ +TI_STATUS cmdDispatch_Destroy (TI_HANDLE hCmdDispatch) +{ + TCmdDispatchObj *pCmdDispatch = (TCmdDispatchObj *)hCmdDispatch; + + /* Free the module object */ + os_memoryFree (pCmdDispatch->hOs, pCmdDispatch, sizeof(TCmdDispatchObj)); + + return TI_OK; +} + + +/** + * \fn cmdDispatch_ConfigParamsAccessTable + * \brief Fill the configuration table with the Get/Set functions + * + * Called in the configuration phase by the driver, performs the following: + * - for each module that supply a Get/Set services to his parameters, + * fill the corresponding entry in the params access table with the following: + * - Get function + * - Set function + * - Handle to the module + * This table is used when Getting/Setting a parameter from the OS abstraction layer. + * + * \note + * \param pCmdDispatch - The object + * \return void + * \sa + */ +static void cmdDispatch_ConfigParamsAccessTable (TCmdDispatchObj *pCmdDispatch) +{ + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(AUTH_MODULE_PARAM) - 1].set = auth_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(AUTH_MODULE_PARAM) - 1].get = auth_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(AUTH_MODULE_PARAM) - 1].handle = pCmdDispatch->hAuth; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(ASSOC_MODULE_PARAM) - 1].set = assoc_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(ASSOC_MODULE_PARAM) - 1].get = assoc_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(ASSOC_MODULE_PARAM) - 1].handle = pCmdDispatch->hAssoc; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(RX_DATA_MODULE_PARAM) - 1].set = rxData_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(RX_DATA_MODULE_PARAM) - 1].get = rxData_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(RX_DATA_MODULE_PARAM) - 1].handle = pCmdDispatch->hRxData; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(TX_CTRL_MODULE_PARAM) - 1].set = txCtrlParams_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(TX_CTRL_MODULE_PARAM) - 1].get = txCtrlParams_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(TX_CTRL_MODULE_PARAM) - 1].handle = pCmdDispatch->hTxCtrl; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CTRL_DATA_MODULE_PARAM) - 1].set = ctrlData_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CTRL_DATA_MODULE_PARAM) - 1].get = ctrlData_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CTRL_DATA_MODULE_PARAM) - 1].handle = pCmdDispatch->hCtrlData; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SITE_MGR_MODULE_PARAM) - 1].set = siteMgr_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SITE_MGR_MODULE_PARAM) - 1].get = siteMgr_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SITE_MGR_MODULE_PARAM) - 1].handle = pCmdDispatch->hSiteMgr; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CONN_MODULE_PARAM) - 1].set = conn_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CONN_MODULE_PARAM) - 1].get = conn_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CONN_MODULE_PARAM) - 1].handle = pCmdDispatch->hConn; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(RSN_MODULE_PARAM) - 1].set = (TParamFunc)rsn_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(RSN_MODULE_PARAM) - 1].get = (TParamFunc)rsn_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(RSN_MODULE_PARAM) - 1].handle = pCmdDispatch->hRsn; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(TWD_MODULE_PARAM) - 1].set = cmdDispatch_SetTwdParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(TWD_MODULE_PARAM) - 1].get = cmdDispatch_GetTwdParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(TWD_MODULE_PARAM) - 1].handle = (TI_HANDLE)pCmdDispatch; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(REPORT_MODULE_PARAM) - 1].set = (TParamFunc)report_SetParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(REPORT_MODULE_PARAM) - 1].get = (TParamFunc)report_GetParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(REPORT_MODULE_PARAM) - 1].handle = pCmdDispatch->hReport; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SME_MODULE_PARAM) - 1].set = sme_SetParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SME_MODULE_PARAM) - 1].get = sme_GetParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SME_MODULE_PARAM) - 1].handle = pCmdDispatch->hSme; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SCAN_CNCN_PARAM) - 1].set = scanCncnApp_SetParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SCAN_CNCN_PARAM) - 1].get = scanCncnApp_GetParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SCAN_CNCN_PARAM) - 1].handle = pCmdDispatch->hScanCncn; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SCAN_MNGR_PARAM) - 1].set = scanMngr_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SCAN_MNGR_PARAM) - 1].get = scanMngr_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SCAN_MNGR_PARAM) - 1].handle = pCmdDispatch->hScanMngr; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MLME_SM_MODULE_PARAM) - 1].set = mlme_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MLME_SM_MODULE_PARAM) - 1].get = mlme_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MLME_SM_MODULE_PARAM) - 1].handle = pCmdDispatch->hMlmeSm; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(REGULATORY_DOMAIN_MODULE_PARAM) - 1].set = regulatoryDomain_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(REGULATORY_DOMAIN_MODULE_PARAM) - 1].get = regulatoryDomain_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(REGULATORY_DOMAIN_MODULE_PARAM) - 1].handle = pCmdDispatch->hRegulatoryDomain; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MEASUREMENT_MODULE_PARAM) - 1].set = measurementMgr_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MEASUREMENT_MODULE_PARAM) - 1].get = measurementMgr_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MEASUREMENT_MODULE_PARAM) - 1].handle = pCmdDispatch->hMeasurementMgr; + +#ifdef XCC_MODULE_INCLUDED + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(XCC_MANAGER_MODULE_PARAM) - 1].set = XCCMngr_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(XCC_MANAGER_MODULE_PARAM) - 1].get = XCCMngr_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(XCC_MANAGER_MODULE_PARAM) - 1].handle = pCmdDispatch->hXCCMngr; +#endif + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(ROAMING_MANAGER_MODULE_PARAM) - 1].set = roamingMngr_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(ROAMING_MANAGER_MODULE_PARAM) - 1].get = roamingMngr_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(ROAMING_MANAGER_MODULE_PARAM) - 1].handle = pCmdDispatch->hRoamingMngr; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SOFT_GEMINI_PARAM) - 1].set = SoftGemini_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SOFT_GEMINI_PARAM) - 1].get = SoftGemini_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(SOFT_GEMINI_PARAM) - 1].handle = pCmdDispatch->hSoftGemini; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(QOS_MANAGER_PARAM) - 1].set = qosMngr_setParams; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(QOS_MANAGER_PARAM) - 1].get = qosMngr_getParams; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(QOS_MANAGER_PARAM) - 1].handle = pCmdDispatch->hQosMngr; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(POWER_MANAGER_PARAM) - 1].set = powerMgr_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(POWER_MANAGER_PARAM) - 1].get = powerMgr_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(POWER_MANAGER_PARAM) - 1].handle = pCmdDispatch->hPowerMgr; + +#ifdef TI_DBG + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MISC_MODULE_PARAM) - 1].set = cmdDispatch_DebugFuncSet; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MISC_MODULE_PARAM) - 1].get = cmdDispatch_DebugFuncGet; /*yael - this function is not in use*/ + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(MISC_MODULE_PARAM) - 1].handle = (TI_HANDLE)pCmdDispatch; +#endif + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(HEALTH_MONITOR_MODULE_PARAM) - 1].set = healthMonitor_SetParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(HEALTH_MONITOR_MODULE_PARAM) - 1].get = healthMonitor_GetParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(HEALTH_MONITOR_MODULE_PARAM) - 1].handle = pCmdDispatch->hHealthMonitor; + + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CURR_BSS_MODULE_PARAM) - 1].set = currBSS_setParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CURR_BSS_MODULE_PARAM) - 1].get = currBSS_getParam; + pCmdDispatch->paramAccessTable[GET_PARAM_MODULE_NUMBER(CURR_BSS_MODULE_PARAM) - 1].handle = pCmdDispatch->hCurrBss; +} + + +/** + * \fn cmdDispatch_SetParam + * \brief Set a driver parameter + * + * Called by the OS abstraction layer in order to set a parameter in the driver. + * If the parameter can not be set from outside the driver it returns a failure status. + * The parameters is set to the module that uses as its father in the system + * (refer to the file paramOut.h for more explanations). + * + * \note + * \param hCmdDispatch - The object + * \param param - The parameter information + * \return result of parameter setting + * \sa + */ +TI_STATUS cmdDispatch_SetParam (TI_HANDLE hCmdDispatch, void *param) +{ + TCmdDispatchObj *pCmdDispatch = (TCmdDispatchObj *)hCmdDispatch; + paramInfo_t *pParam = (paramInfo_t *)param; + TI_UINT32 moduleNumber; + + moduleNumber = GET_PARAM_MODULE_NUMBER(pParam->paramType); + + if (moduleNumber > MAX_PARAM_MODULE_NUMBER) + { + return PARAM_MODULE_NUMBER_INVALID; + } + + if ((pCmdDispatch->paramAccessTable[moduleNumber - 1].set == 0) || + (pCmdDispatch->paramAccessTable[moduleNumber - 1].get == 0) || + (pCmdDispatch->paramAccessTable[moduleNumber - 1].handle == 0)) + { + WLAN_OS_REPORT(("cmdDispatch_SetParam(): NULL pointers!!!, return, ParamType=0x%x\n", pParam->paramType)); + return TI_NOK; + } + + TRACE2(pCmdDispatch->hReport, REPORT_SEVERITY_INFORMATION , "cmdDispatch_SetParam(): ParamType=0x%x, ModuleNumber=0x%x\n", pParam->paramType, moduleNumber); + + return pCmdDispatch->paramAccessTable[moduleNumber - 1].set(pCmdDispatch->paramAccessTable[moduleNumber - 1].handle, pParam); +} + + +/** + * \fn cmdDispatch_GetParam + * \brief Get a driver parameter + * + * Called by the OS abstraction layer in order to get a parameter the driver. + * If the parameter can not be get from outside the driver it returns a failure status. + * The parameter is get from the module that uses as its father in the system + * (refer to the file paramOut.h for more explanations). + * + * \note + * \param hCmdDispatch - The object + * \param param - The parameter information + * \return result of parameter getting + * \sa + */ +TI_STATUS cmdDispatch_GetParam (TI_HANDLE hCmdDispatch, void *param) +{ + TCmdDispatchObj *pCmdDispatch = (TCmdDispatchObj *) hCmdDispatch; + paramInfo_t *pParam = (paramInfo_t *) param; + TI_UINT32 moduleNumber; + TI_STATUS status; + + moduleNumber = GET_PARAM_MODULE_NUMBER(pParam->paramType); + + if (moduleNumber > MAX_PARAM_MODULE_NUMBER) + { + return PARAM_MODULE_NUMBER_INVALID; + } + + if ((pCmdDispatch->paramAccessTable[moduleNumber - 1].set == 0) || + (pCmdDispatch->paramAccessTable[moduleNumber - 1].get == 0) || + (pCmdDispatch->paramAccessTable[moduleNumber - 1].handle == 0)) + { + WLAN_OS_REPORT(("cmdDispatch_GetParam(): NULL pointers!!!, return, ParamType=0x%x\n", pParam->paramType)); + return TI_NOK; + } + + TRACE2(pCmdDispatch->hReport, REPORT_SEVERITY_INFORMATION , "cmdDispatch_GetParam(): ParamType=0x%x, ModuleNumber=0x%x\n", pParam->paramType, moduleNumber); + + status = pCmdDispatch->paramAccessTable[moduleNumber - 1].get(pCmdDispatch->paramAccessTable[moduleNumber - 1].handle, pParam); + + return status; +} + + +/** + * \fn cmdDispatch_SetTwdParam / cmdDispatch_GetParam + * \brief Set/Get a TWD parameter + * + * Set/Get a TWD parameter. + * + * \note + * \param hCmdDispatch - The object + * \param param - The parameter information + * \return parameter set/get result + * \sa + */ +static TI_STATUS cmdDispatch_SetTwdParam (TI_HANDLE hCmdDispatch, paramInfo_t *pParam) +{ + TCmdDispatchObj *pCmdDispatch = (TCmdDispatchObj *)hCmdDispatch; + + pParam->paramType &= ~(SET_BIT | GET_BIT | TWD_MODULE_PARAM | ASYNC_PARAM | ALLOC_NEEDED_PARAM); + + return TWD_SetParam (pCmdDispatch->hTWD, (TTwdParamInfo *)pParam); +} + +static TI_STATUS cmdDispatch_GetTwdParam (TI_HANDLE hCmdDispatch, paramInfo_t *pParam) +{ + TCmdDispatchObj *pCmdDispatch = (TCmdDispatchObj *)hCmdDispatch; + + pParam->paramType &= ~(SET_BIT | GET_BIT | TWD_MODULE_PARAM | ASYNC_PARAM | ALLOC_NEEDED_PARAM); + + return TWD_GetParam (pCmdDispatch->hTWD, (TTwdParamInfo *)pParam); +} + + + + +/** + * \fn cmdDispatch_DebugFuncSet / cmdDispatch_DebugFuncGet + * \brief Set/Get a debug function parameter + * + * Set/Get a debug function parameter. + * + * \note + * \param hCmdDispatch - The object + * \param param - The parameter information + * \return parameter set/get result + * \sa + */ + +#ifdef TI_DBG + +static TI_STATUS cmdDispatch_DebugFuncSet (TI_HANDLE hCmdDispatch, paramInfo_t *pParam) +{ + TCmdDispatchObj *pCmdDispatch = (TCmdDispatchObj *)hCmdDispatch; + + if (hCmdDispatch == NULL || pParam == NULL) + { + return TI_NOK; + } + + switch (pParam->paramType) + { + case DEBUG_ACTIVATE_FUNCTION: + debugFunction (pCmdDispatch->pStadHandles, + *(TI_UINT32*)&pParam->content, + (void*)((TI_UINT32*)&pParam->content + 1)); + break; + default: +TRACE1(pCmdDispatch->hReport, REPORT_SEVERITY_ERROR, "cmdDispatch_DebugFuncSet bad param=%X\n", pParam->paramType); + break; + } + return TI_OK; +} + + + +/*yael - this function is not in use*/ +static TI_STATUS cmdDispatch_DebugFuncGet (TI_HANDLE hCmdDispatch, paramInfo_t *pParam) +{ + if (hCmdDispatch == NULL || pParam == NULL) + { + return TI_NOK; + } + + /*yael - no use for that function */ + + return TI_OK; +} + +#endif /* TI_DBG */ + + diff --git a/wilink_6_1/stad/src/Ctrl_Interface/CmdDispatcher.h b/wilink_6_1/stad/src/Ctrl_Interface/CmdDispatcher.h new file mode 100644 index 0000000..6d0c1dd --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/CmdDispatcher.h @@ -0,0 +1,59 @@ +/* + * CmdDispatcher.h + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + + +/** \file CmdDispatcher.h + * \brief CmdDispatcher module header file. + * + * \see CmdDispatcher.c + */ + +#ifndef _CMD_DISPATCHER_H_ +#define _CMD_DISPATCHER_H_ + +#include "DrvMainModules.h" + + +/* Public Functions Prototypes */ +/* =========================== */ + +TI_HANDLE cmdDispatch_Create (TI_HANDLE hOs); +void cmdDispatch_Init (TStadHandlesList *pStadHandles); +TI_STATUS cmdDispatch_Destroy (TI_HANDLE hCmdDispatch); +TI_STATUS cmdDispatch_SetParam (TI_HANDLE hCmdDispatch, void *param); +TI_STATUS cmdDispatch_GetParam (TI_HANDLE hCmdDispatch, void *param); + + +#endif /* _CMD_DISPATCHER_H_ */ + + diff --git a/wilink_6_1/stad/src/Ctrl_Interface/CmdHndlr.c b/wilink_6_1/stad/src/Ctrl_Interface/CmdHndlr.c new file mode 100644 index 0000000..b60fa34 --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/CmdHndlr.c @@ -0,0 +1,495 @@ +/* + * CmdHndlr.c + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + + +/** \file CmdHndlr.c + * \brief The Command-Hnadler module. + * + * \see CmdHndlr.h + */ + +#define __FILE_ID__ FILE_ID_48 +#include "tidef.h" +#include "commonTypes.h" +#include "osApi.h" +#include "report.h" +#include "queue.h" +#include "context.h" +#include "CmdHndlr.h" +#include "CmdInterpret.h" +#include "DrvMainModules.h" + + +/* The queue may contain only one command per configuration application so 8 is more than enough */ +#define COMMANDS_QUE_SIZE 8 + +/* Command module internal data */ +typedef struct +{ + TI_HANDLE hOs; + TI_HANDLE hReport; + TI_HANDLE hContext; + TI_HANDLE hCmdInterpret; + + TI_HANDLE hCmdQueue; /* Handle to the commands queue */ + TI_BOOL bProcessingCmds; /* Indicates if currently processing commands */ + TI_UINT32 uContextId; /* ID allocated to this module on registration to context module */ + TConfigCommand *pCurrCmd; /* Pointer to the command currently being processed */ +} TCmdHndlrObj; + +/* External functions prototypes */ +extern void wlanDrvIf_CommandDone (TI_HANDLE hOs, void *pSignalObject, TI_UINT8 *CmdResp_p); + +/** + * \fn cmdHndlr_Create + * \brief Create the module + * + * Create the module object + * + * \note + * \param hOs - Handle to the Os Abstraction Layer + * \return Handle to the allocated module (NULL if failed) + * \sa + */ +TI_HANDLE cmdHndlr_Create (TI_HANDLE hOs, TI_HANDLE hEvHandler) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *) os_memoryAlloc (hOs, sizeof(TCmdHndlrObj)); + + if (pCmdHndlr == NULL) + { + return NULL; + } + + os_memoryZero (hOs, (void *)pCmdHndlr, sizeof(TCmdHndlrObj)); + + pCmdHndlr->hOs = hOs; + + pCmdHndlr->hCmdInterpret = cmdInterpret_Create (hOs); + + if (pCmdHndlr->hCmdInterpret == NULL) + { + cmdHndlr_Destroy ((TI_HANDLE) pCmdHndlr, (TI_HANDLE) hEvHandler); + return NULL; + } + + return (TI_HANDLE) pCmdHndlr; +} + + +/** + * \fn cmdHndlr_Destroy + * \brief Destroy the module object + * + * Destroy the module object. + * + * \note + * \param hCmdHndlr - The object + * \return TI_OK + * \sa + */ +TI_STATUS cmdHndlr_Destroy (TI_HANDLE hCmdHndlr, TI_HANDLE hEvHandler) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)hCmdHndlr; + + if (pCmdHndlr->hCmdInterpret) + { + cmdInterpret_Destroy (pCmdHndlr->hCmdInterpret, hEvHandler); + } + + cmdHndlr_ClearQueue (hCmdHndlr); + + if (pCmdHndlr->hCmdQueue) + { + que_Destroy (pCmdHndlr->hCmdQueue); + } + + os_memoryFree (pCmdHndlr->hOs, hCmdHndlr, sizeof(TCmdHndlrObj)); + + return TI_OK; +} + + +/** + * \fn cmdHndlr_ClearQueue + * \brief Clear commands queue + * + * Dequeue and free all queued commands. + * + * \note + * \param hCmdHndlr - The object + * \return void + * \sa + */ +void cmdHndlr_ClearQueue (TI_HANDLE hCmdHndlr) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)hCmdHndlr; + TConfigCommand *pCurrCmd; + + /* Dequeue and free all queued commands */ + do { + context_EnterCriticalSection (pCmdHndlr->hContext); + pCurrCmd = (TConfigCommand *)que_Dequeue(pCmdHndlr->hCmdQueue); + context_LeaveCriticalSection (pCmdHndlr->hContext); + if (pCurrCmd != NULL) { + /* Just release the semaphore. The command is freed subsequently. */ + os_SignalObjectSet (pCmdHndlr->hOs, pCurrCmd->pSignalObject); + } + } while (pCurrCmd != NULL); +} + + +/** + * \fn cmdHndlr_Init + * \brief Init required handles and registries + * + * Init required handles and module variables, create the commands-queue and + * register as the context-engine client. + * + * \note + * \param pStadHandles - The driver modules handles + * \return void + * \sa + */ +void cmdHndlr_Init (TStadHandlesList *pStadHandles) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)(pStadHandles->hCmdHndlr); + TI_UINT32 uNodeHeaderOffset; + + pCmdHndlr->hReport = pStadHandles->hReport; + pCmdHndlr->hContext = pStadHandles->hContext; + + cmdInterpret_Init (pCmdHndlr->hCmdInterpret, pStadHandles); + + /* The offset of the queue-node-header from the commands structure entry is needed by the queue */ + uNodeHeaderOffset = TI_FIELD_OFFSET(TConfigCommand, tQueNodeHdr); + + /* Create and initialize the commands queue */ + pCmdHndlr->hCmdQueue = que_Create (pCmdHndlr->hOs, pCmdHndlr->hReport, COMMANDS_QUE_SIZE, uNodeHeaderOffset); + + /* Register to the context engine and get the client ID */ + pCmdHndlr->uContextId = context_RegisterClient (pCmdHndlr->hContext, + cmdHndlr_HandleCommands, + (TI_HANDLE)pCmdHndlr, + TI_FALSE, + "COMMAND", + sizeof("COMMAND")); + + if(pCmdHndlr->hReport != NULL) + { + os_setDebugOutputToLogger(TI_FALSE); + } +} + + +/** + * \fn cmdHndlr_InsertCommand + * \brief Insert a new command to the driver + * + * Insert a new command to the commands queue from user context. + * If commands are not beeing processed set a request to start processing in the driver context. + * Wait on the current command's signal until its processing is completed. + * Note that this prevents the user application from sending further commands before completion. + * + * \note + * \param hCmdHndlr - The module object + * \param cmd - User request + * \param others - The command flags, data and params + * \return TI_OK if command processed successfully, TI_NOK if failed in processing or memory allocation. + * \sa cmdHndlr_HandleCommands, cmdHndlr_Complete + */ +TI_STATUS cmdHndlr_InsertCommand (TI_HANDLE hCmdHndlr, + TI_UINT32 cmd, + TI_UINT32 flags, + void *buffer1, + TI_UINT32 buffer1_len, + void *buffer2, + TI_UINT32 buffer2_len, + TI_UINT32 *param3, + TI_UINT32 *param4) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)hCmdHndlr; + TConfigCommand *pNewCmd; + TI_STATUS eStatus; + + /* Allocated command structure */ + pNewCmd = os_memoryAlloc (pCmdHndlr->hOs, sizeof (TConfigCommand)); + if (pNewCmd == NULL) + { + return TI_NOK; + } + + /* Copy user request into local structure */ + pNewCmd->cmd = cmd; + pNewCmd->flags = flags; + pNewCmd->buffer1 = buffer1; + pNewCmd->buffer1_len = buffer1_len; + pNewCmd->buffer2 = buffer2; + pNewCmd->buffer2_len = buffer2_len; + pNewCmd->param3 = param3; + pNewCmd->param4 = param4; + pNewCmd->pSignalObject = os_SignalObjectCreate (pCmdHndlr->hOs); /* initialize "complete-flag" */ + + /* If creating the signal object failed */ + if (pNewCmd->pSignalObject == NULL) + { + os_printf("cmdPerform: Failed to create signalling object\n"); + /* free allocated memory and return error */ + os_memoryFree (pCmdHndlr->hOs, pNewCmd, sizeof (TConfigCommand)); + return TI_NOK; + } + + /* Indicate the start of command process, from adding it to the queue until get return status form it */ + pNewCmd->bWaitFlag = TI_TRUE; + + /* Enter critical section to protect queue access */ + context_EnterCriticalSection (pCmdHndlr->hContext); + + /* Enqueue the command (if failed, release memory and return NOK) */ + eStatus = que_Enqueue (pCmdHndlr->hCmdQueue, (TI_HANDLE)pNewCmd); + if (eStatus != TI_OK) + { + context_LeaveCriticalSection (pCmdHndlr->hContext); /* Leave critical section */ + os_printf("cmdPerform: Failed to enqueue new command\n"); + os_SignalObjectFree (pCmdHndlr->hOs, pNewCmd->pSignalObject); + os_memoryFree (pCmdHndlr->hOs, pNewCmd, sizeof (TConfigCommand)); + return TI_NOK; + } + + /* + * Note: The bProcessingCmds flag is used for indicating if we are already processing + * the queued commands, so the context-engine shouldn't invoke cmdHndlr_HandleCommands. + * This is important because if we make this decision according to the queue being empty, + * there may be a command under processing (already dequeued) while the queue is empty. + * Note that although we are blocking the current command's originator, there may be another + * application that will issue a command. + */ + + if (pCmdHndlr->bProcessingCmds) + { + /* No need to schedule the driver (already handling commands) so just leave critical section */ + context_LeaveCriticalSection (pCmdHndlr->hContext); + } + else + { + /* Indicate that we are handling queued commands (before leaving critical section!) */ + pCmdHndlr->bProcessingCmds = TI_TRUE; + + /* Leave critical section */ + context_LeaveCriticalSection (pCmdHndlr->hContext); + + /* Request driver task schedule for command handling (after we left critical section!) */ + context_RequestSchedule (pCmdHndlr->hContext, pCmdHndlr->uContextId); + } + + /* Wait until the command is executed */ + os_SignalObjectWait (pCmdHndlr->hOs, pNewCmd->pSignalObject); + + /* After "wait" - the command has already been processed by the drivers' context */ + /* Indicate the end of command process, from adding it to the queue until get return status form it */ + pNewCmd->bWaitFlag = TI_FALSE; + + /* Copy the return code */ + eStatus = pNewCmd->return_code; + + /* Free signalling object and command structure */ + os_SignalObjectFree (pCmdHndlr->hOs, pNewCmd->pSignalObject); + + /* If command not completed in this context (Async) don't free the command memory */ + if(COMMAND_PENDING != pNewCmd->eCmdStatus) + { + os_memoryFree (pCmdHndlr->hOs, pNewCmd, sizeof (TConfigCommand)); + } + + /* Return to calling process with command return code */ + return eStatus; +} + + + +/** + * \fn cmdHndlr_HandleCommands + * \brief Handle queued commands + * + * While there are queued commands, dequeue a command and call the + * commands interpreter (OID or WEXT selected at compile time). + * If the command processing is not completed in this context (pending), we exit and + * this function is called again upon commnad completion, so it can continue processing + * further queued commands (if any). + * + * \note + * \param hCmdHndlr - The module object + * \return void + * \sa cmdHndlr_InsertCommand, cmdHndlr_Complete + */ +void cmdHndlr_HandleCommands (TI_HANDLE hCmdHndlr) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)hCmdHndlr; + + while (1) + { + /* Enter critical section to protect queue access */ + context_EnterCriticalSection (pCmdHndlr->hContext); + + /* Dequeue a command */ + pCmdHndlr->pCurrCmd = (TConfigCommand *) que_Dequeue (pCmdHndlr->hCmdQueue); + + /* If we have got a command */ + if (pCmdHndlr->pCurrCmd) + { + /* Leave critical section */ + context_LeaveCriticalSection (pCmdHndlr->hContext); + + /* Convert to driver structure and execute command */ + pCmdHndlr->pCurrCmd->eCmdStatus = cmdInterpret_convertAndExecute (pCmdHndlr->hCmdInterpret, pCmdHndlr->pCurrCmd); + + /* + * If command not completed in this context (Async), return. + * (we'll be called back upon command completion) + */ + if(COMMAND_PENDING == pCmdHndlr->pCurrCmd->eCmdStatus) + { + return; + } + + /* Command was completed so free the wait signal and continue to next command */ + wlanDrvIf_CommandDone(pCmdHndlr->hOs, pCmdHndlr->pCurrCmd->pSignalObject, pCmdHndlr->pCurrCmd->CmdRespBuffer); + + pCmdHndlr->pCurrCmd = NULL; + + } + + /* Else, we don't have commands to handle */ + else + { + /* Indicate that we are not handling commands (before leaving critical section!) */ + pCmdHndlr->bProcessingCmds = TI_FALSE; + + /* Leave critical section */ + context_LeaveCriticalSection (pCmdHndlr->hContext); + + /* Exit (no more work) */ + return; + } + } +} + + +/** + * \fn cmdHndlr_Complete + * \brief called whenever a command has finished executing + * + * This routine is called whenever a command has finished executing. + * Either called by the cmdHndlr_HandleCommands if completed in the same context, + * or by the CmdInterpreter module when tcompleted in a later context (Async). + * + * \note + * \param hCmdHndlr - The module object + * \return void + * \sa cmdHndlr_InsertCommand, cmdHndlr_HandleCommands + */ +void cmdHndlr_Complete (TI_HANDLE hCmdHndlr) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)hCmdHndlr; + TI_BOOL bLocalWaitFlag; + + if (pCmdHndlr->pCurrCmd) + { + /* set Status to COMPLETE */ + pCmdHndlr->pCurrCmd->eCmdStatus = TI_OK; + + /* save the wait flag before free semaphore */ + bLocalWaitFlag = pCmdHndlr->pCurrCmd->bWaitFlag; + + wlanDrvIf_CommandDone(pCmdHndlr->hOs, pCmdHndlr->pCurrCmd->pSignalObject, pCmdHndlr->pCurrCmd->CmdRespBuffer); + + /* if cmdHndlr_InsertCommand() not wait to cmd complete? */ + if (TI_FALSE == bLocalWaitFlag) + { + /* no wait, free the command memory */ + os_memoryFree (pCmdHndlr->hOs, pCmdHndlr->pCurrCmd, sizeof (TConfigCommand)); + } + + pCmdHndlr->pCurrCmd = NULL; + + return; + } + + TRACE0(pCmdHndlr->hReport, REPORT_SEVERITY_ERROR, "cmdHndlr_Complete(): pCurrCmd is NULL!\n"); +} + + +/** + * \fn cmdHndlr_GetStat + * \brief Get driver statistics + * + * Get the driver statistics (Tx, Rx, signal quality). + * + * \note + * \param hCmdHndlr - The object + * \return The driver statistics pointer + * \sa + */ +void * cmdHndlr_GetStat (TI_HANDLE hCmdHndlr) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)hCmdHndlr; + + return cmdInterpret_GetStat (pCmdHndlr->hCmdInterpret); +} + + +/** + * \fn cmdHndlr_Enable & cmdHndlr_Disable + * \brief Enable/Disable invoking CmdHndlr module from driver-task + * + * Called by the Driver-Main Init SM to enable/disable external inputs processing. + * Calls the context-engine enable/disable function accordingly. + * + * \note + * \param hCmdHndlr - The object + * \return void + * \sa + */ +void cmdHndlr_Enable (TI_HANDLE hCmdHndlr) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)hCmdHndlr; + + context_EnableClient (pCmdHndlr->hContext, pCmdHndlr->uContextId); +} + +void cmdHndlr_Disable (TI_HANDLE hCmdHndlr) +{ + TCmdHndlrObj *pCmdHndlr = (TCmdHndlrObj *)hCmdHndlr; + + context_DisableClient (pCmdHndlr->hContext, pCmdHndlr->uContextId); +} + diff --git a/wilink_6_1/stad/src/Ctrl_Interface/CmdHndlr.h b/wilink_6_1/stad/src/Ctrl_Interface/CmdHndlr.h new file mode 100644 index 0000000..886e7fe --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/CmdHndlr.h @@ -0,0 +1,88 @@ +/* + * CmdHndlr.h + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + + +#ifndef CMD_H +#define CMD_H + +#include "queue.h" +#include "DrvMainModules.h" +#include "WlanDrvIf.h" + +/* The configuration commands structure */ +typedef struct +{ + TQueNodeHdr tQueNodeHdr; /* The header used for queueing the command */ + TI_UINT32 cmd; + TI_UINT32 flags; + void *buffer1; + TI_UINT32 buffer1_len; + void *buffer2; + TI_UINT32 buffer2_len; + TI_UINT32 *param3; + TI_UINT32 *param4; + void *pSignalObject; /* use to save handle to complete mechanism per OS */ + void *local_buffer; + TI_UINT32 local_buffer_len; + TI_UINT32 return_code; + TI_STATUS eCmdStatus; /* (PEND / COMPLETE) */ + TI_BOOL bWaitFlag; /* (TRUE / FALSE) */ + /* + * TCmdRespUnion is defined for each OS: + * For Linx and WM that defined is empty. + * For OSE the new typedef includes all "Done" typedefs in union from EMP code (H files). + */ + TI_UINT8 CmdRespBuffer[sizeof(TCmdRespUnion)]; +} TConfigCommand; + + +TI_HANDLE cmdHndlr_Create (TI_HANDLE hOs, TI_HANDLE hEvHandler); +TI_STATUS cmdHndlr_Destroy (TI_HANDLE hCmdHndlr, TI_HANDLE hEvHandler); +void cmdHndlr_ClearQueue (TI_HANDLE hCmdHndlr); +void cmdHndlr_Init (TStadHandlesList *pStadHandles); +TI_STATUS cmdHndlr_InsertCommand (TI_HANDLE hCmdHndlr, + TI_UINT32 cmd, + TI_UINT32 flags, + void *buffer1, + TI_UINT32 buffer1_len, + void *buffer2, + TI_UINT32 buffer2_len, + TI_UINT32 *param3, + TI_UINT32 *param4); +void cmdHndlr_HandleCommands (TI_HANDLE hCmdHndlr); +void cmdHndlr_Complete (TI_HANDLE hCmdHndlr); +void *cmdHndlr_GetStat (TI_HANDLE hCmdHndlr); +void cmdHndlr_Enable (TI_HANDLE hCmdHndlr); +void cmdHndlr_Disable (TI_HANDLE hCmdHndlr); + +#endif diff --git a/wilink_6_1/stad/src/Ctrl_Interface/CmdInterpret.h b/wilink_6_1/stad/src/Ctrl_Interface/CmdInterpret.h new file mode 100644 index 0000000..80b2a36 --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/CmdInterpret.h @@ -0,0 +1,55 @@ +/* + * CmdInterpret.h + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + + + +#ifndef CMDINTERPRET_H +#define CMDINTERPRET_H + +/* Command interpreter header file */ + +TI_HANDLE cmdInterpret_Create (TI_HANDLE hOs); + +TI_STATUS cmdInterpret_Destroy (TI_HANDLE hCmdInterpret, TI_HANDLE hEvHandler); + +void cmdInterpret_Init (TI_HANDLE hCmdInterpret, TStadHandlesList *pStadHandles); + +int cmdInterpret_convertAndExecute (TI_HANDLE hCmdInterpret, TConfigCommand *cmdObj); + +int cmdInterpret_ServiceCompleteCB (TI_HANDLE hCmdInterpret, int status, void *buffer); + +void cmdInterpret_convertToOs (TI_HANDLE hCmdInterpret, TConfigCommand *cmdPtr); + +void *cmdInterpret_GetStat (TI_HANDLE hCmdInterpret); + +#endif diff --git a/wilink_6_1/stad/src/Ctrl_Interface/DrvMain.c b/wilink_6_1/stad/src/Ctrl_Interface/DrvMain.c new file mode 100644 index 0000000..9e55fa6 --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/DrvMain.c @@ -0,0 +1,1772 @@ +/* + * DrvMain.c + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + + +/** \file DrvMain.c + * \brief The DrvMain module. Handles driver init, stop and recovery processes. + * + * \see DrvMain.h + */ + +#define __FILE_ID__ FILE_ID_49 +#include "tidef.h" +#include "osApi.h" +#include "report.h" +#include "context.h" +#include "timer.h" +#include "CmdHndlr.h" +#include "DrvMain.h" +#include "scrApi.h" +#include "EvHandler.h" +#include "connApi.h" +#include "siteMgrApi.h" +#include "sme.h" +#include "SoftGeminiApi.h" +#include "roamingMngrApi.h" +#include "qosMngr_API.h" +#include "TrafficMonitor.h" +#include "PowerMgr_API.h" +#include "EvHandler.h" +#include "apConn.h" +#include "currBss.h" +#include "SwitchChannelApi.h" +#include "ScanCncn.h" +#include "healthMonitor.h" +#include "scanMngrApi.h" +#include "regulatoryDomainApi.h" +#include "measurementMgrApi.h" +#ifdef XCC_MODULE_INCLUDED +#include "XCCMngr.h" +#endif +#include "TxnQueue.h" +#include "TWDriver.h" +#include "debug.h" +#include "host_platform.h" +#include "StaCap.h" +#include "WlanDrvCommon.h" +#include "DrvMainModules.h" +#include "CmdDispatcher.h" + + +#define SM_WATCHDOG_TIME_MS 20000 /* SM processes timeout is 20 sec. */ + +#define SDIO_CONNECT_THRESHOLD 8 + + +/* Handle failure status from the SM callbacks by triggering the SM with FAILURE event */ +#define HANDLE_CALLBACKS_FAILURE_STATUS(hDrvMain, eStatus) \ + if (eStatus != TI_OK) { drvMain_SmEvent (hDrvMain, SM_EVENT_FAILURE); return; } + +/* The DrvMain SM states */ +typedef enum +{ + /* 0 */ SM_STATE_IDLE, + /* 1 */ SM_STATE_WAIT_INI_FILE, + /* 2 */ SM_STATE_WAIT_NVS_FILE, + /* 3 */ SM_STATE_HW_INIT, + /* 4 */ SM_STATE_DOWNLOAD_FW_FILE, + /* 5 */ SM_STATE_WAIT_FW_FILE, + /* 6 */ SM_STATE_FW_INIT, + /* 7 */ SM_STATE_FW_CONFIG, + /* 8 */ SM_STATE_OPERATIONAL, + /* 9 */ SM_STATE_DISCONNECTING, + /* 10 */ SM_STATE_STOPPING, + /* 11 */ SM_STATE_STOPPED, + /* 12 */ SM_STATE_STOPPING_ON_FAIL, + /* 13 */ SM_STATE_FAILED + +} ESmState; + +/* The DrvMain SM events */ +typedef enum +{ + /* 0 */ SM_EVENT_START, + /* 1 */ SM_EVENT_INI_FILE_READY, + /* 2 */ SM_EVENT_NVS_FILE_READY, + /* 3 */ SM_EVENT_HW_INIT_COMPLETE, + /* 4 */ SM_EVENT_FW_FILE_READY, + /* 5 */ SM_EVENT_FW_INIT_COMPLETE, + /* 6 */ SM_EVENT_FW_CONFIG_COMPLETE, + /* 7 */ SM_EVENT_STOP, + /* 8 */ SM_EVENT_RECOVERY, + /* 9 */ SM_EVENT_DISCONNECTED, + /* 10 */ SM_EVENT_STOP_COMPLETE, + /* 11 */ SM_EVENT_FAILURE + +} ESmEvent; + +/* The module's object */ +typedef struct +{ + TStadHandlesList tStadHandles; /* All STAD modules handles (distributed in driver init process) */ + TI_BOOL bRecovery; /* Indicates if we are during recovery process */ + ESmState eSmState; /* The DrvMain SM state. */ + ESmEvent ePendingEvent;/* A pending event issued when the SM is busy */ + TI_UINT32 uPendingEventsCount; /* Counts the number of events pending for SM execution */ + TFileInfo tFileInfo; /* Information of last file retrieved by os_GetFile() */ + TI_UINT32 uContextId; /* ID allocated to this module on registration to context module */ + EActionType eAction; /* The last action (start/stop) inserted to the driver */ + void *hSignalObj; /* The signal object used for waiting for action completion */ + TI_HANDLE hWatchdogTimer;/* SM Watchdog timer - expires upon deadlock in Start/Stop/Recovery processes. */ + TBusDrvCfg tBusDrvCfg; /* A union (struc per each supported bus type) for the bus driver configuration */ + +} TDrvMain; + + +static void drvMain_Init (TI_HANDLE hDrvMain); +static void drvMain_InitHwCb (TI_HANDLE hDrvMain, TI_STATUS eStatus); +static void drvMain_InitFwCb (TI_HANDLE hDrvMain, TI_STATUS eStatus); +static void drvMain_ConfigFwCb (TI_HANDLE hDrvMain, TI_STATUS eStatus); +static void drvMain_TwdStopCb (TI_HANDLE hDrvMain, TI_STATUS eStatus); +static void drvMain_InitFailCb (TI_HANDLE hDrvMain, TI_STATUS eStatus); +static void drvMain_InitLocals (TDrvMain *pDrvMain); +/* static void drvMain_SmWatchdogTimeout (TI_HANDLE hDrvMain); */ +static void drvMain_SmEvent (TI_HANDLE hDrvMain, ESmEvent eEvent); +static void drvMain_Sm (TI_HANDLE hDrvMain, ESmEvent eEvent); + +/* External functions prototypes */ + +/** \brief WLAN Driver I/F Get file + * + * \param hOs - OS module object handle + * \param pFileInfo - Pointer to output file information + * \return TI_OK on success or TI_NOK on failure + * + * \par Description + * This function provides access to a requested init file: + * It provides the requested file information and call the requester callback. + * Note that in Linux the files were previously loaded to driver memory by the loader + * + * \sa + */ +extern int wlanDrvIf_GetFile (TI_HANDLE hOs, TFileInfo *pFileInfo); +/** \brief WLAN Driver I/F Update Driver State + * + * \param hOs - OS module object handle + * \param eDriverState - New Driver State + * \return void + * + * \par Description + * This function Update the driver state (Idle | Running | Stopped |Failed): + * + * \sa + */ +extern void wlanDrvIf_UpdateDriverState (TI_HANDLE hOs, EDriverSteadyState eDriverState); +/** \brief WLAN Driver I/F Set MAC Address + * + * \param hOs - OS module object handle + * \param pMacAddr - Pointer to MAC address to set + * \return void + * + * \par Description + * This function Update the driver MAC address by copy it to the network interface structure + * + * \sa + */ +extern void wlanDrvIf_SetMacAddress (TI_HANDLE hOs, TI_UINT8 *pMacAddr); +/** \brief OS Init Table INI File + * + * \param hOs - OS module object handle + * \param InitTable - Pointer to initialization table + * \param file_buf - Pointer to Input buffer from INI file + * \param file_length - Length of input buffer from INI file + * \return void + * + * \par Description + * This function perform Initializing of init table accrding to data from INI file and driver defaults + * + * \sa + */ +extern int osInitTable_IniFile (TI_HANDLE hOs, TInitTable *InitTable, char *file_buf, int file_length); + + + +/* + * \fn drvMain_Create + * \brief Create the driver modules + * + * Create all STAD and TWD modules. + * Then call all modules init functions which initializes their handles and variables. + * + * \note + * \param hOs - Handle to the Os Abstraction Layer + * \param pDrvMainHndl - Pointer for returning the DrvMain handle. + * \param pCmdHndlr - Pointer for returning the CmdHndlr handle. + * \param pContext - Pointer for returning the Context handle. + * \param pTxDataQ - Pointer for returning the TxDataQ handle. + * \param pTxMgmtQ - Pointer for returning the TxMgmtQ handle. + * \param pTxCtrl - Pointer for returning the TxCtrl handle. + * \param pTwd - Pointer for returning the TWD handle. + * \param pEvHandler - Pointer for returning the EvHndler handle. + * \return Handle to the DrvMain module (NULL if failed) + * \sa + */ +TI_STATUS drvMain_Create (TI_HANDLE hOs, + TI_HANDLE *pDrvMainHndl, + TI_HANDLE *pCmdHndlr, + TI_HANDLE *pContext, + TI_HANDLE *pTxDataQ, + TI_HANDLE *pTxMgmtQ, + TI_HANDLE *pTxCtrl, + TI_HANDLE *pTwd, + TI_HANDLE *pEvHandler) +{ + /* Create the DrvMain module object. */ + TDrvMain *pDrvMain = (TDrvMain *) os_memoryAlloc (hOs, sizeof(TDrvMain)); + + if (pDrvMain == NULL) + { + return TI_NOK; + } + + os_memoryZero (hOs, (void *)pDrvMain, sizeof(TDrvMain)); + + pDrvMain->tStadHandles.hDrvMain = (TI_HANDLE)pDrvMain; + pDrvMain->tStadHandles.hOs = hOs; + + /* Create watchdog timer to detect deadlocks in the DrvMain SM processes. */ + /* return thr timer later on */ + /*pDrvMain->hWatchdogTimer = os_timerCreate (hOs, drvMain_SmWatchdogTimeout, (TI_HANDLE)pDrvMain); + if (pDrvMain->hWatchdogTimer == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + }*/ + +/* + * Create all driver modules + * ========================= + */ + + pDrvMain->tStadHandles.hContext = context_Create (hOs); + if (pDrvMain->tStadHandles.hContext == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hTimer = tmr_Create (hOs); + if (pDrvMain->tStadHandles.hTimer == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hSCR = scr_create (hOs); + if (pDrvMain->tStadHandles.hSCR == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hTxnQ = txnQ_Create (hOs); + if (pDrvMain->tStadHandles.hTxnQ == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hEvHandler = EvHandler_Create (hOs); + if (pDrvMain->tStadHandles.hEvHandler == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hReport = report_Create (hOs); + if (pDrvMain->tStadHandles.hReport == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hConn = conn_create (hOs); + if (pDrvMain->tStadHandles.hConn == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hScanCncn = scanCncn_Create (hOs); + if (pDrvMain->tStadHandles.hScanCncn == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hSme = sme_Create (hOs); + if (pDrvMain->tStadHandles.hSme == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hSiteMgr = siteMgr_create (hOs); + if (pDrvMain->tStadHandles.hSiteMgr == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hMlmeSm = mlme_create (hOs); + if (pDrvMain->tStadHandles.hMlmeSm == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hAuth = auth_create (hOs); + if (pDrvMain->tStadHandles.hAuth == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hAssoc = assoc_create (hOs); + if (pDrvMain->tStadHandles.hAssoc == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hRxData = rxData_create (hOs); + if (pDrvMain->tStadHandles.hRxData == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hTxCtrl = txCtrl_Create (hOs); + if (pDrvMain->tStadHandles.hTxCtrl == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hTxDataQ = txDataQ_Create(hOs); + if (pDrvMain->tStadHandles.hTxDataQ == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hTxMgmtQ = txMgmtQ_Create(hOs); + if (pDrvMain->tStadHandles.hTxMgmtQ == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hTxPort = txPort_create (hOs); + if (pDrvMain->tStadHandles.hTxPort == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hCtrlData = ctrlData_create (hOs); + if (pDrvMain->tStadHandles.hCtrlData == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hTrafficMon = TrafficMonitor_create (hOs); + if (pDrvMain->tStadHandles.hTrafficMon == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hRsn = rsn_create (hOs); + if (pDrvMain->tStadHandles.hRsn == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hRegulatoryDomain = regulatoryDomain_create (hOs); + if (pDrvMain->tStadHandles.hRegulatoryDomain == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hMeasurementMgr = measurementMgr_create (hOs); + if (pDrvMain->tStadHandles.hMeasurementMgr == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hSoftGemini = SoftGemini_create (hOs); + if (pDrvMain->tStadHandles.hSoftGemini == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + +#ifdef XCC_MODULE_INCLUDED + pDrvMain->tStadHandles.hXCCMngr = XCCMngr_create (hOs); + if (pDrvMain->tStadHandles.hXCCMngr == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } +#else + pDrvMain->tStadHandles.hXCCMngr = NULL; +#endif + + pDrvMain->tStadHandles.hRoamingMngr = roamingMngr_create (hOs); + if (pDrvMain->tStadHandles.hRoamingMngr == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hAPConnection = apConn_create (hOs); + if (pDrvMain->tStadHandles.hAPConnection == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hCurrBss = currBSS_create (hOs); + if (pDrvMain->tStadHandles.hCurrBss == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hQosMngr = qosMngr_create (hOs); + if (pDrvMain->tStadHandles.hQosMngr == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hPowerMgr = PowerMgr_create (hOs); + if (pDrvMain->tStadHandles.hPowerMgr == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hSwitchChannel = switchChannel_create (hOs); + if (pDrvMain->tStadHandles.hSwitchChannel == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hScanMngr = scanMngr_create (hOs); + if (NULL == pDrvMain->tStadHandles.hScanMngr) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hHealthMonitor = healthMonitor_create (hOs); + if (NULL == pDrvMain->tStadHandles.hHealthMonitor) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hTWD = TWD_Create (hOs); + if (pDrvMain->tStadHandles.hTWD == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hCmdHndlr = cmdHndlr_Create (hOs, pDrvMain->tStadHandles.hEvHandler); + if (pDrvMain->tStadHandles.hCmdHndlr == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hCmdDispatch = cmdDispatch_Create (hOs); + if (pDrvMain->tStadHandles.hCmdDispatch == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + pDrvMain->tStadHandles.hStaCap = StaCap_Create (hOs); + if (pDrvMain->tStadHandles.hStaCap == NULL) + { + drvMain_Destroy (pDrvMain); + return TI_NOK; + } + + /* Bind all modules handles */ + drvMain_Init ((TI_HANDLE)pDrvMain); + + + /* Provide required handles to the OAL */ + *pDrvMainHndl = (TI_HANDLE)pDrvMain; + *pCmdHndlr = pDrvMain->tStadHandles.hCmdHndlr; + *pContext = pDrvMain->tStadHandles.hContext; + *pTxDataQ = pDrvMain->tStadHandles.hTxDataQ; + *pTxMgmtQ = pDrvMain->tStadHandles.hTxMgmtQ; + *pTxCtrl = pDrvMain->tStadHandles.hTxCtrl; + *pTwd = pDrvMain->tStadHandles.hTWD; + *pEvHandler = pDrvMain->tStadHandles.hEvHandler; + + WLAN_INIT_REPORT (("drvMain_Create: success\n")); + + return TI_OK; +} + +/* + * \fn drvMain_Destroy + * \brief Destroy driver + * + * Destroy all STAD and TWD modules and resources. + * + * \note + * \param hDrvMain - The DrvMain object + * \return TI_OK if succeeded, TI_NOK if failed. + * \sa drvMain_Create + */ +TI_STATUS drvMain_Destroy (TI_HANDLE hDrvMain) +{ + TDrvMain *pDrvMain = (TDrvMain *)hDrvMain; + + hPlatform_Wlan_Hardware_DeInit (); + + if (pDrvMain == NULL) + { + return TI_NOK; + } + + if (pDrvMain->tStadHandles.hScanMngr != NULL) + { + scanMngr_unload (pDrvMain->tStadHandles.hScanMngr); + } + + if (pDrvMain->tStadHandles.hSiteMgr != NULL) + { + siteMgr_unLoad (pDrvMain->tStadHandles.hSiteMgr); + } + + if (pDrvMain->tStadHandles.hSme != NULL) + { + sme_Destroy (pDrvMain->tStadHandles.hSme); + } + + if (pDrvMain->tStadHandles.hConn != NULL) + { + conn_unLoad (pDrvMain->tStadHandles.hConn); + } + + if (pDrvMain->tStadHandles.hTWD != NULL) + { + TWD_Destroy (pDrvMain->tStadHandles.hTWD); + } + + if (pDrvMain->tStadHandles.hScanCncn != NULL) + { + scanCncn_Destroy (pDrvMain->tStadHandles.hScanCncn); + } + + if (pDrvMain->tStadHandles.hTrafficMon != NULL) + { + TrafficMonitor_Destroy (pDrvMain->tStadHandles.hTrafficMon); + } + + if (pDrvMain->tStadHandles.hCtrlData != NULL) + { + ctrlData_unLoad (pDrvMain->tStadHandles.hCtrlData); + } + + if (pDrvMain->tStadHandles.hTxCtrl != NULL) + { + txCtrl_Unload (pDrvMain->tStadHandles.hTxCtrl); + } + + if (pDrvMain->tStadHandles.hTxDataQ != NULL) + { + txDataQ_Destroy (pDrvMain->tStadHandles.hTxDataQ); + } + + if (pDrvMain->tStadHandles.hTxMgmtQ != NULL) + { + txMgmtQ_Destroy (pDrvMain->tStadHandles.hTxMgmtQ); + } + + if (pDrvMain->tStadHandles.hTxPort != NULL) + { + txPort_unLoad (pDrvMain->tStadHandles.hTxPort); + } + + if (pDrvMain->tStadHandles.hRxData != NULL) + { + rxData_unLoad (pDrvMain->tStadHandles.hRxData); + } + + if (pDrvMain->tStadHandles.hAssoc != NULL) + { + assoc_unload (pDrvMain->tStadHandles.hAssoc); + } + + if (pDrvMain->tStadHandles.hAuth != NULL) + { + auth_unload (pDrvMain->tStadHandles.hAuth); + } + + if (pDrvMain->tStadHandles.hMlmeSm != NULL) + { + mlme_unload (pDrvMain->tStadHandles.hMlmeSm); + } + + if (pDrvMain->tStadHandles.hSCR != NULL) + { + scr_release (pDrvMain->tStadHandles.hSCR); + } + + if (pDrvMain->tStadHandles.hTxnQ != NULL) + { + txnQ_Destroy (pDrvMain->tStadHandles.hTxnQ); + } + + if (pDrvMain->tStadHandles.hRsn != NULL) + { + rsn_unload (pDrvMain->tStadHandles.hRsn); + } + + if (pDrvMain->tStadHandles.hRegulatoryDomain != NULL) + { + regulatoryDomain_destroy (pDrvMain->tStadHandles.hRegulatoryDomain); + } + + if (pDrvMain->tStadHandles.hMeasurementMgr != NULL) + { + measurementMgr_destroy (pDrvMain->tStadHandles.hMeasurementMgr); + } + + if (pDrvMain->tStadHandles.hSoftGemini != NULL) + { + SoftGemini_destroy (pDrvMain->tStadHandles.hSoftGemini); + } + +#ifdef XCC_MODULE_INCLUDED + if (pDrvMain->tStadHandles.hXCCMngr != NULL) + { + XCCMngr_unload (pDrvMain->tStadHandles.hXCCMngr); + } +#endif + + if (pDrvMain->tStadHandles.hRoamingMngr != NULL) + { + roamingMngr_unload (pDrvMain->tStadHandles.hRoamingMngr); + } + + if (pDrvMain->tStadHandles.hQosMngr != NULL) + { + qosMngr_destroy (pDrvMain->tStadHandles.hQosMngr); + } + + if (pDrvMain->tStadHandles.hPowerMgr != NULL) + { + PowerMgr_destroy (pDrvMain->tStadHandles.hPowerMgr); + } + + if (pDrvMain->tStadHandles.hAPConnection != NULL) + { + apConn_unload (pDrvMain->tStadHandles.hAPConnection); + } + + if (pDrvMain->tStadHandles.hCurrBss != NULL) + { + currBSS_unload (pDrvMain->tStadHandles.hCurrBss); + } + + if (pDrvMain->tStadHandles.hSwitchChannel != NULL) + { + switchChannel_unload (pDrvMain->tStadHandles.hSwitchChannel); + } + + if (pDrvMain->tStadHandles.hHealthMonitor != NULL) + { + healthMonitor_unload (pDrvMain->tStadHandles.hHealthMonitor); + } + + if (pDrvMain->tStadHandles.hCmdHndlr && pDrvMain->tStadHandles.hEvHandler) + { + cmdHndlr_Destroy (pDrvMain->tStadHandles.hCmdHndlr, pDrvMain->tStadHandles.hEvHandler); + } + + if (pDrvMain->tStadHandles.hEvHandler != NULL) + { + EvHandlerUnload (pDrvMain->tStadHandles.hEvHandler); + } + + if (pDrvMain->tStadHandles.hCmdDispatch) + { + cmdDispatch_Destroy (pDrvMain->tStadHandles.hCmdDispatch); + } + + /* Note: The Timer module must be destroyed last, so all created timers are already destroyed!! */ + if (pDrvMain->tStadHandles.hTimer != NULL) + { + tmr_Destroy (pDrvMain->tStadHandles.hTimer); + } + + /* Destroy the SM watchdog timer */ + if (pDrvMain->hWatchdogTimer != NULL) + { + os_timerDestroy (pDrvMain->tStadHandles.hOs, pDrvMain->hWatchdogTimer); + } + + /* Note: Moved after timers for locks */ + if (pDrvMain->tStadHandles.hContext != NULL) + { + context_Destroy (pDrvMain->tStadHandles.hContext); + } + + if (pDrvMain->tStadHandles.hStaCap != NULL) + { + StaCap_Destroy (pDrvMain->tStadHandles.hStaCap); + } + + if (pDrvMain->tStadHandles.hReport != NULL) + { + report_Unload (pDrvMain->tStadHandles.hReport); + } + + /* Destroy the DrvMain object */ + os_memoryFree (pDrvMain->tStadHandles.hOs, hDrvMain, sizeof(TDrvMain)); + + return TI_OK; +} + +void drvMain_SmeStop (TI_HANDLE hDrvMain) +{ + drvMain_SmEvent (hDrvMain, SM_EVENT_DISCONNECTED); +} + + +/* + * \fn drvMain_Init + * \brief Init driver modules + * + * Called from OS context following the driver creation. + * Calls all STAD and TWD modules Init functions, which are saving other modules handles, + * registering to other modules and initializing their variables. + * + * \note + * \param hDrvMain - The DrvMain object + * \return void + * \sa drvMain_Create + */ +static void drvMain_Init (TI_HANDLE hDrvMain) +{ + TDrvMain *pDrvMain = (TDrvMain *) hDrvMain; + TStadHandlesList *pModules = &pDrvMain->tStadHandles; /* The STAD modules handles list */ + + /* + * Init all modules handles, variables and registries + */ + context_Init (pModules->hContext, pModules->hOs, pModules->hReport); + tmr_Init (pModules->hTimer, pModules->hOs, pModules->hReport, pModules->hContext); + txnQ_Init (pModules->hTxnQ, pModules->hOs, pModules->hReport, pModules->hContext); + scr_init (pModules); + conn_init (pModules); + ctrlData_init (pModules, + #ifdef XCC_MODULE_INCLUDED + XCCMngr_LinkTestRetriesUpdate, pModules->hXCCMngr); + #else + NULL, NULL); + #endif + siteMgr_init (pModules); + regulatoryDomain_init (pModules); + scanCncn_Init (pModules); + auth_init (pModules); + mlme_init (pModules); + assoc_init (pModules); + rxData_init (pModules); + txCtrl_Init (pModules); + txDataQ_Init (pModules); + txMgmtQ_Init (pModules); + txPort_init (pModules); + TrafficMonitor_Init (pModules, 1000 /* pInitTable->trafficMonitorMinIntervalPercentage */); + sme_Init (pModules); + rsn_init (pModules); + measurementMgr_init (pModules); +#ifdef XCC_MODULE_INCLUDED + XCCMngr_init (pModules); +#endif + scanMngr_init (pModules); + currBSS_init (pModules); + apConn_init (pModules); + roamingMngr_init (pModules); + qosMngr_init (pModules); + switchChannel_init (pModules); + healthMonitor_init (pModules); + PowerMgr_init (pModules); + SoftGemini_init (pModules); + cmdDispatch_Init (pModules); + StaCap_Init (pModules); + cmdHndlr_Init (pModules); + + /* Init TWD component (handles, variables and registries) and provide callbacks for next steps */ + TWD_Init (pModules->hTWD, + pModules->hReport, + pModules->hDrvMain, + pModules->hTimer, + pModules->hContext, + pModules->hTxnQ, + (TTwdCallback)drvMain_InitHwCb, + (TTwdCallback)drvMain_InitFwCb, + (TTwdCallback)drvMain_ConfigFwCb, + (TTwdCallback)drvMain_TwdStopCb, + (TTwdCallback)drvMain_InitFailCb); + + /* Init DrvMain module local variables */ + drvMain_InitLocals (pDrvMain); +} + + +/* + * \fn drvMain_SetDefaults + * \brief Set driver default configuration + * + * Configure all STAD and TWD modules with their default settings from the ini-file. + * Timers creation is also done at this stage. + * + * \note + * \param hDrvMain - The DrvMain object + * \param pBuf - The ini-file data. + * \param uLength - The ini-file length. + * \return TI_OK if succeeded, TI_NOK if failed. + * \sa drvMain_Init + */ +static TI_STATUS drvMain_SetDefaults (TI_HANDLE hDrvMain, TI_UINT8 *pBuf, TI_UINT32 uLength) +{ + TDrvMain *pDrvMain = (TDrvMain *) hDrvMain; + TInitTable *pInitTable; + TI_STATUS eStatus; + + pInitTable = os_memoryAlloc (pDrvMain->tStadHandles.hOs, sizeof(TInitTable)); + + /* Parse defaults */ + eStatus = osInitTable_IniFile (pDrvMain->tStadHandles.hOs, pInitTable, (char*)pBuf, (int)uLength); + + /* + * Configure modules with their default settings + */ + report_SetDefaults (pDrvMain->tStadHandles.hReport, &pInitTable->tReport); + context_SetDefaults (pDrvMain->tStadHandles.hContext, &pInitTable->tContextInitParams); + TWD_SetDefaults (pDrvMain->tStadHandles.hTWD, &pInitTable->twdInitParams); + conn_SetDefaults (pDrvMain->tStadHandles.hConn, &pInitTable->connInitParams); + ctrlData_SetDefaults (pDrvMain->tStadHandles.hCtrlData, &pInitTable->ctrlDataInitParams); + siteMgr_SetDefaults (pDrvMain->tStadHandles.hSiteMgr, &pInitTable->siteMgrInitParams); + regulatoryDomain_SetDefaults (pDrvMain->tStadHandles.hRegulatoryDomain, &pInitTable->regulatoryDomainInitParams); + scanCncn_SetDefaults (pDrvMain->tStadHandles.hScanCncn, &pInitTable->tScanCncnInitParams); + auth_SetDefaults (pDrvMain->tStadHandles.hAuth, &pInitTable->authInitParams); + assoc_SetDefaults (pDrvMain->tStadHandles.hAssoc, &pInitTable->assocInitParams); + rxData_SetDefaults (pDrvMain->tStadHandles.hRxData, &pInitTable->rxDataInitParams); + sme_SetDefaults (pDrvMain->tStadHandles.hSme, &pInitTable->tSmeModifiedInitParams, &pInitTable->tSmeInitParams); + rsn_SetDefaults (pDrvMain->tStadHandles.hRsn, &pInitTable->rsnInitParams); + measurementMgr_SetDefaults (pDrvMain->tStadHandles.hMeasurementMgr, &pInitTable->measurementInitParams); +#ifdef XCC_MODULE_INCLUDED + XCCMngr_SetDefaults (pDrvMain->tStadHandles.hXCCMngr, &pInitTable->XCCMngrParams); +#endif /*XCC_MODULE_INCLUDED*/ + apConn_SetDefaults (pDrvMain->tStadHandles.hAPConnection, &pInitTable->apConnParams); + qosMngr_SetDefaults (pDrvMain->tStadHandles.hQosMngr, &pInitTable->qosMngrInitParams); + switchChannel_SetDefaults (pDrvMain->tStadHandles.hSwitchChannel, &pInitTable->SwitchChannelInitParams); + healthMonitor_SetDefaults (pDrvMain->tStadHandles.hHealthMonitor, &pInitTable->healthMonitorInitParams); + PowerMgr_SetDefaults (pDrvMain->tStadHandles.hPowerMgr, &pInitTable->PowerMgrInitParams); + SoftGemini_SetDefaults (pDrvMain->tStadHandles.hSoftGemini, &pInitTable->SoftGeminiInitParams); + txDataQ_SetDefaults (pDrvMain->tStadHandles.hTxDataQ, &pInitTable->txDataInitParams); + txCtrl_SetDefaults (pDrvMain->tStadHandles.hTxCtrl, &pInitTable->txDataInitParams); + currBSS_SetDefaults (pDrvMain->tStadHandles.hCurrBss, &pInitTable->tCurrBssInitParams); + mlme_SetDefaults (pDrvMain->tStadHandles.hMlmeSm, &pInitTable->tMlmeInitParams); + + scanMngr_SetDefaults(pDrvMain->tStadHandles.hScanMngr, &pInitTable->tRoamScanMngrInitParams); + roamingMngr_setDefaults(pDrvMain->tStadHandles.hRoamingMngr, &pInitTable->tRoamScanMngrInitParams); + + /* Set DrvMain local defaults */ + pDrvMain->tBusDrvCfg.tSdioCfg.uBlkSizeShift = pInitTable->tDrvMainParams.uSdioBlkSizeShift; + pDrvMain->tBusDrvCfg.tSdioCfg.uBusDrvThreadPriority = pInitTable->tDrvMainParams.uBusDrvThreadPriority; + os_SetDrvThreadPriority (pDrvMain->tStadHandles.hOs, pInitTable->tDrvMainParams.uWlanDrvThreadPriority); + + /* Release the init table memory */ + os_memoryFree (pDrvMain->tStadHandles.hOs, pInitTable, sizeof(TInitTable)); + + return eStatus; +} + + +/* + * \fn drvMain_xxx...Cb + * \brief Callback functions for the init/stop stages completion + * + * The following callback functions are called from other modules (most from TWD) + * when the current init/stop step is completed. + * Note that the callbacks are called anyway, either in the original context (if completed), or + * in another context if pending. + * The first case (same context) may lead to a recursion of the SM, so a special handling is added + * to the SM to prevent recursion (see drvMain_Sm). + * + * drvMain_InitHwCb - HW init completion callback + * drvMain_InitFwCb - FW init (mainly download) completion callback + * drvMain_ConfigFwCb - FW configuration completion callback + * drvMain_TwdStopCb - TWD stopping completion callback + * drvMain_InitFailCb - FW init faulty completion callback + * drvMain_SmeStopCb - SME stopping completion callback + * drvMain_GetFileCb - Getting-file completion callback + * + * \note + * \param hDrvMain - The DrvMain object + * \param eStatus - The process result (TI_OK if succeeded, TI_NOK if failed) + * \return void + * \sa drvMain_Create + */ +static void drvMain_InitHwCb (TI_HANDLE hDrvMain, TI_STATUS eStatus) +{ + HANDLE_CALLBACKS_FAILURE_STATUS(hDrvMain, eStatus); + drvMain_SmEvent (hDrvMain, SM_EVENT_HW_INIT_COMPLETE); +} + +static void drvMain_InitFwCb (TI_HANDLE hDrvMain, TI_STATUS eStatus) +{ + HANDLE_CALLBACKS_FAILURE_STATUS(hDrvMain, eStatus); + drvMain_SmEvent (hDrvMain, SM_EVENT_FW_INIT_COMPLETE); +} + +static void drvMain_ConfigFwCb (TI_HANDLE hDrvMain, TI_STATUS eStatus) +{ + HANDLE_CALLBACKS_FAILURE_STATUS(hDrvMain, eStatus); + drvMain_SmEvent (hDrvMain, SM_EVENT_FW_CONFIG_COMPLETE); +} + +static void drvMain_TwdStopCb (TI_HANDLE hDrvMain, TI_STATUS eStatus) +{ + HANDLE_CALLBACKS_FAILURE_STATUS(hDrvMain, eStatus); + drvMain_SmEvent (hDrvMain, SM_EVENT_STOP_COMPLETE); +} + +static void drvMain_InitFailCb (TI_HANDLE hDrvMain, TI_STATUS eStatus) +{ + drvMain_SmEvent (hDrvMain, SM_EVENT_FAILURE); + /* + * Note that this call will pass the SM to the FAILED state, since this event + * is not handled by any state. + */ +} + +static void drvMain_InvokeAction (TI_HANDLE hDrvMain) +{ + TDrvMain *pDrvMain = (TDrvMain *)hDrvMain; + + switch (pDrvMain->eAction) + { + case ACTION_TYPE_START: + drvMain_SmEvent (hDrvMain, SM_EVENT_START); + break; + case ACTION_TYPE_STOP: + drvMain_SmEvent (hDrvMain, SM_EVENT_STOP); + break; + default: + TRACE1(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR , "drvMain_InvokeAction(): Action=%d\n", pDrvMain->eAction); + } +} + +static void drvMain_GetFileCb (TI_HANDLE hDrvMain) +{ + TDrvMain *pDrvMain = (TDrvMain *)hDrvMain; + ESmEvent eSmEvent; + + switch (pDrvMain->tFileInfo.eFileType) + { + case FILE_TYPE_INI: eSmEvent = SM_EVENT_INI_FILE_READY; break; + case FILE_TYPE_NVS: eSmEvent = SM_EVENT_NVS_FILE_READY; break; + case FILE_TYPE_FW: eSmEvent = SM_EVENT_FW_FILE_READY; break; + case FILE_TYPE_FW_NEXT: eSmEvent = SM_EVENT_FW_FILE_READY; break; + default: + TRACE1(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR , "drvMain_GetFileCb(): Unknown eFileType=%d\n", pDrvMain->tFileInfo.eFileType); + return; + } + drvMain_SmEvent (hDrvMain, eSmEvent); +} + + +/* + * \fn drvMain_InitLocals + * \brief Init DrvMain module + * + * Init the DrvMain variables, register to other modules and set device power to off. + * + * \note + * \param pDrvMain - The DrvMain object + * \return void + * \sa drvMain_Init + */ +static void drvMain_InitLocals (TDrvMain *pDrvMain) +{ + /* Initialize the module's local varniables to default values */ + pDrvMain->tFileInfo.eFileType = FILE_TYPE_INI; + pDrvMain->tFileInfo.fCbFunc = drvMain_GetFileCb; + pDrvMain->tFileInfo.hCbHndl = (TI_HANDLE)pDrvMain; + pDrvMain->eSmState = SM_STATE_IDLE; + pDrvMain->uPendingEventsCount = 0; + pDrvMain->bRecovery = TI_FALSE; + pDrvMain->eAction = ACTION_TYPE_NONE; + + /* Register the Action callback to the context engine and get the client ID */ + pDrvMain->uContextId = context_RegisterClient (pDrvMain->tStadHandles.hContext, + drvMain_InvokeAction, + (TI_HANDLE)pDrvMain, + TI_TRUE, + "ACTION", + sizeof("ACTION")); + + /* Platform specific HW preparations */ + hPlatform_Wlan_Hardware_Init(pDrvMain->tStadHandles.hOs); + + /* Insure that device power is off (expected to be) */ + hPlatform_DevicePowerOff (); +} + + +/* + * \fn drvMain_InitHw & drvMain_InitFw + * \brief Init HW and Init FW sequences + * + * drvMain_InitHw - HW init sequence which writes and reads some HW registers + * that are needed prior to FW download. + * drvMain_InitFw - FW init sequence which downloads the FW image and waits for + * FW init-complete indication. + * + * \note + * \param hDrvMain - The DrvMain object + * \param pBuf - The file data (NVS for HW-init, FW-Image for FW-init). + * \param uLength - The file length. + * \return TI_OK if succeeded, TI_NOK if failed. + * \sa + */ +static TI_STATUS drvMain_InitHw (TI_HANDLE hDrvMain, TI_UINT8 *pbuf, TI_UINT32 uLength) +{ + TDrvMain *pDrvMain = (TDrvMain *) hDrvMain; + + return TWD_InitHw (pDrvMain->tStadHandles.hTWD, pbuf, uLength); +} + +static TI_STATUS drvMain_InitFw (TI_HANDLE hDrvMain, TFileInfo *pFileInfo) +{ + TDrvMain *pDrvMain = (TDrvMain *) hDrvMain; + + return TWD_InitFw (pDrvMain->tStadHandles.hTWD, pFileInfo); +} + + +/* + * \fn drvMain_ConfigFw + * \brief Configure the FW + * + * The step that follows the FW Init (mainly FW download). + * The Command-Mailbox interface is enabled here and the FW is configured. + * + * \note + * \param pDrvMain - The DrvMain object + * \return TI_OK + * \sa drvMain_Init + */ +static TI_STATUS drvMain_ConfigFw (TI_HANDLE hDrvMain) +{ + TDrvMain *pDrvMain = (TDrvMain *) hDrvMain; + + /* get pointer to FW static info (already in driver memory) */ + TFwInfo *pFwInfo = TWD_GetFWInfo (pDrvMain->tStadHandles.hTWD); + TI_UINT8 *pMacAddr = (TI_UINT8 *)pFwInfo->macAddress; /* STA MAC address */ + + /* Update driver's MAC address */ + wlanDrvIf_SetMacAddress (pDrvMain->tStadHandles.hOs, pMacAddr); + + /* + * Exit from init mode should be before smeSM starts. this enable us to send + * command to the MboxQueue(that store the command) while the interrupts are masked. + * the interrupt would be enable at the end of the init process. + */ + TWD_ExitFromInitMode (pDrvMain->tStadHandles.hTWD); + + /* Configure the FW from the TWD DB */ + TWD_ConfigFw (pDrvMain->tStadHandles.hTWD); + + TRACE0(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_INIT , "EXIT FROM INIT\n"); + + /* Print the driver and firmware version and the mac address */ + os_printf("\n"); + os_printf("-----------------------------------------------------\n"); + os_printf("Driver Version : %s\n", SW_VERSION_STR); + os_printf("Firmware Version: %s\n", pFwInfo->fwVer); + os_printf("Station ID : %02X-%02X-%02X-%02X-%02X-%02X\n", + pMacAddr[0], pMacAddr[1], pMacAddr[2], pMacAddr[3], pMacAddr[4], pMacAddr[5]); + os_printf("-----------------------------------------------------\n"); + os_printf("\n"); + + return TI_OK; +} + + +/* + * \fn drvMain_StopActivities + * \brief Freeze driver activities + * + * Freeze all driver activities due to stop command or recovery process. + * + * \note + * \param pDrvMain - The DrvMain object + * \return TI_OK if succeeded, TI_NOK if failed. + * \sa drvMain_EnableActivities + */ +static TI_STATUS drvMain_StopActivities (TDrvMain *pDrvMain) +{ + txPort_suspendTx (pDrvMain->tStadHandles.hTxPort); + + /* Disable External Inputs (IRQs and commands) */ + TWD_DisableInterrupts(pDrvMain->tStadHandles.hTWD); + cmdHndlr_Disable (pDrvMain->tStadHandles.hCmdHndlr); + + /* Initiate TWD Restart */ + return TWD_Stop (pDrvMain->tStadHandles.hTWD); +} + + +/* + * \fn drvMain_EnableActivities + * \brief Enable driver activities + * + * Enable driver activities after init or recovery process completion. + * + * \note + * \param pDrvMain - The DrvMain object + * \return void + * \sa drvMain_StopActivities + */ +static void drvMain_EnableActivities (TDrvMain *pDrvMain) +{ + txPort_resumeTx (pDrvMain->tStadHandles.hTxPort); + + /* Enable External Inputs (IRQ is enabled elsewhere) */ + cmdHndlr_Enable (pDrvMain->tStadHandles.hCmdHndlr); + + /* Enable external events from FW */ + TWD_EnableExternalEvents (pDrvMain->tStadHandles.hTWD); + + +} + + +/* + * \fn drvMain_ClearQueuedEvents + * \brief Enable driver activities + * + * Clear all external events queues (Tx, commands and timers) upon driver stop. + * + * \note + * \param pDrvMain - The DrvMain object + * \return void + * \sa + */ +static void drvMain_ClearQueuedEvents (TDrvMain *pDrvMain) +{ + txDataQ_ClearQueues (pDrvMain->tStadHandles.hTxDataQ); + txMgmtQ_ClearQueues (pDrvMain->tStadHandles.hTxMgmtQ); + cmdHndlr_ClearQueue (pDrvMain->tStadHandles.hCmdHndlr); + tmr_ClearOperQueue (pDrvMain->tStadHandles.hTimer); +} + + +/* + * \fn drvMain_InsertAction + * \brief Get start/stop action and trigger handling + * + * Get start or stop action command from OAL, save it and trigger driver task + * for handling it. + * Wait on a signal object until the requested process is completed. + * + * \note + * \param hDrvMain - The DrvMain object + * \param eAction - The requested action + * \return void + * \sa + */ +TI_STATUS drvMain_InsertAction (TI_HANDLE hDrvMain, EActionType eAction) +{ + TDrvMain *pDrvMain = (TDrvMain *) hDrvMain; + + context_EnterCriticalSection(pDrvMain->tStadHandles.hContext); + if (pDrvMain->eAction == eAction) + { + context_LeaveCriticalSection(pDrvMain->tStadHandles.hContext); + TRACE0(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_CONSOLE, "Action is identical to last action!\n"); + WLAN_OS_REPORT(("Action %d is identical to last action!\n", eAction)); + return TI_NOK; + } + + /* Save the requested action */ + pDrvMain->eAction = eAction; + context_LeaveCriticalSection(pDrvMain->tStadHandles.hContext); + + /* Create signal object */ + /* + * Notice that we must create the signal object before asking for ReSchedule, + * because we might receive it immidiatly, and then we will be in a different context + * with null signal object. + */ + pDrvMain->hSignalObj = os_SignalObjectCreate (pDrvMain->tStadHandles.hOs); + if (pDrvMain->hSignalObj == NULL) + { + TRACE0(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR , "drvMain_InsertAction(): Couldn't allocate signal object!\n"); + return TI_NOK; + } + + /* Request driver task schedule for action handling */ + context_RequestSchedule (pDrvMain->tStadHandles.hContext, pDrvMain->uContextId); + + /* Wait for the action processing completion */ + os_SignalObjectWait (pDrvMain->tStadHandles.hOs, pDrvMain->hSignalObj); + + /* After "wait" - the action has already been processed in the driver's context */ + + /* Free signalling object */ + os_SignalObjectFree (pDrvMain->tStadHandles.hOs, pDrvMain->hSignalObj); + pDrvMain->hSignalObj = NULL; + + if (pDrvMain->eSmState == SM_STATE_FAILED) + return TI_NOK; + + return TI_OK; +} + + +/* + * \fn drvMain_Recovery + * \brief Initiate recovery process + * + * Initiate recovery process upon HW/FW error detection (in the Health-Monitor). + * + * \note + * \param hDrvMain - The DrvMain object + * \return TI_OK if started recovery, TI_NOK if recovery is already in progress. + * \sa + */ +TI_STATUS drvMain_Recovery (TI_HANDLE hDrvMain) +{ + TDrvMain *pDrvMain = (TDrvMain *) hDrvMain; + + if (!pDrvMain->bRecovery) + { + TRACE1(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_CONSOLE,".....drvMain_Recovery, ts=%d\n", os_timeStampMs(pDrvMain->tStadHandles.hOs)); +#ifdef REPORT_LOG + WLAN_OS_REPORT((".....drvMain_Recovery, ts=%d\n", os_timeStampMs(pDrvMain->tStadHandles.hOs))); +#else + printk("%s\n",__func__); +#endif + pDrvMain->bRecovery = TI_TRUE; + drvMain_SmEvent (hDrvMain, SM_EVENT_RECOVERY); + return TI_OK; + } + else + { + TRACE0(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR, "drvMain_Recovery: **** Recovery already in progress! ****\n"); + return TI_NOK; + } +} + + +/* + * \fn drvMain_RecoveryNotify + * \brief Notify STAD modules about recovery + * + * Notify the relevant STAD modules that recovery took place (after completed). + * + * \note + * \param pDrvMain - The DrvMain object + * \return void + * \sa + */ +static void drvMain_RecoveryNotify (TDrvMain *pDrvMain) +{ + txCtrl_NotifyFwReset (pDrvMain->tStadHandles.hTxCtrl); + scr_notifyFWReset (pDrvMain->tStadHandles.hSCR); + PowerMgr_notifyFWReset (pDrvMain->tStadHandles.hPowerMgr); + + TRACE1(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_CONSOLE, ".....drvMain_RecoveryNotify: End Of Recovery, ts=%d\n", os_timeStampMs(pDrvMain->tStadHandles.hOs)); + WLAN_OS_REPORT((".....drvMain_RecoveryNotify: End Of Recovery, ts=%d\n", os_timeStampMs(pDrvMain->tStadHandles.hOs))); +} + + +/* + * \fn drvMain_SmWatchdogTimeout + * \brief SM watchdog timer expiry handler + * + * This is the callback function called upon expiartion of the watchdog timer. + * It is called by the OS-API in timer expiry context, and it issues a failure event to the SM. + * Note that we can't switch to the driver task as for other timers, since we are using + * this timer to protect the init processes, and anyway we just need to stop the driver. + * + * \note + * \param hDrvMain - The DrvMain object + * \return void + * \sa + */ + +#if 0 +static void drvMain_SmWatchdogTimeout (TI_HANDLE hDrvMain) +{ + TDrvMain *pDrvMain = (TDrvMain *)hDrvMain; + + TRACE1(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR , "drvMain_SmWatchdogTimeout(): State = %d\n", pDrvMain->eSmState); + + /* Send failure event directly to the SM (so the drvMain_SmEvent won't block it). */ + + drvMain_Sm ((TI_HANDLE)pDrvMain, SM_EVENT_FAILURE); +} +#endif + +/* + * \fn drvMain_SmEvent + * \brief Issue DrvMain SM event + * + * Each event that is handled by the DrvMain state machine, is introduced through this function. + * To prevent SM recursion, the SM is invoeked only if it's not already handling the + * previous event. + * If the SM is busy, the current event is saved until the previous handling is completed. + * + * \note Recursion may happen because some SM activities generate SM events in the same context. + * \param hDrvMain - The DrvMain object + * \param eEvent - The event issued to the SM + * \return void + * \sa + */ +static void drvMain_SmEvent (TI_HANDLE hDrvMain, ESmEvent eEvent) +{ + TDrvMain *pDrvMain = (TDrvMain *)hDrvMain; + + /* Increment pending events counter and save last event. */ + pDrvMain->uPendingEventsCount++; + pDrvMain->ePendingEvent = eEvent; + + /* If the SM is busy, save event and exit (will be handled when current event is finished) */ + if (pDrvMain->uPendingEventsCount > 1) + { + /* Only one pending event is expected (in addition to the handled one, so two together). */ + if (pDrvMain->uPendingEventsCount > 2) + { + TRACE3(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR , "drvMain_SmEvent(): Multiple pending events (%d), State = %d, Event = %d\n", pDrvMain->uPendingEventsCount, pDrvMain->eSmState, eEvent); + } + + /* Exit. The current event will be handled by the following while loop of the first instance. */ + return; + } + + /* Invoke the SM with the current event and further events issued by the last SM invocation. */ + while (pDrvMain->uPendingEventsCount > 0) + { + drvMain_Sm (hDrvMain, pDrvMain->ePendingEvent); + + /* + * Note: The SM may issue another event by calling this function and incrementing + * the counter. + * In this case, only the upper part of this function is run, and the pending + * event is hanlded in the next while loo[. + */ + + pDrvMain->uPendingEventsCount--; + } +} + + +/* + * \fn drvMain_Sm + * \brief The DrvMain state machine + * + * The DrvMain state machine, which handles all driver init, recovery and stop processes. + * + * \note Since the SM may be called back from its own context, recursion is prevented + * by postponing the last event. + * \param hDrvMain - The DrvMain object + * \param eEvent - The event that triggers the SM + * \return void + * \sa + */ +static void drvMain_Sm (TI_HANDLE hDrvMain, ESmEvent eEvent) +{ + TDrvMain *pDrvMain = (TDrvMain *)hDrvMain; + TI_STATUS eStatus = TI_NOK; + TI_HANDLE hOs = pDrvMain->tStadHandles.hOs; + TI_UINT32 uSdioConIndex = 0; + + TRACE2(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_INFORMATION , "drvMain_Sm(): State = %d, Event = %d\n", pDrvMain->eSmState, eEvent); + + /* + * General explenations: + * ===================== + * 1) This SM calls some functions that may complete their processing in another context. + * All of these functions (wlanDrvIf_GetFile, drvMain_InitHw, drvMain_InitFw, drvMain_ConfigFw, + * drvMain_StopActivities, smeSm_start, smeSm_stop) are provided with a callback which + * they always call upon completion, even if they are completed in the original (SM) context. + * Since these callbacks are calling the SM, a simple mechanism is added to prevent + * recursion, by postponing the last event if the SM is still in the previous event's context. + * 2) In any case of unexpected event, the eStatus remains TI_NOK, leading to the FAILED state! + * FAILED state is also reached if any of the functions listed in note 1 returns TI_NOK. + * Note that if these functions detect a failure in another context, they may call their callback + * with the eStatus parameter set to TI_NOK, or call the drvMain_InitFailCb callback. + * All these cases lead to FAILED state which terminates all driver activities and wait for destroy. + * 3) Note that the wlanDrvIf_GetFile is always completed in the original context, and the + * option of completion in a later context is only for future use. + * 4) All processes (Start, Stop, Relcovery) are protected by a watchdog timer to let + * the user free the driver in case of deadlock during the process. + */ + + switch (pDrvMain->eSmState) + { + case SM_STATE_IDLE: + /* + * We get a START action after all modules are created and linked. + * Disable further actions, start watchdog timer and request for the ini-file. + */ + if (eEvent == SM_EVENT_START) + { + /* return thr timer later on */ + /*os_timerStart (hOs, pDrvMain->hWatchdogTimer, SM_WATCHDOG_TIME_MS);*/ + pDrvMain->eSmState = SM_STATE_WAIT_INI_FILE; + context_DisableClient (pDrvMain->tStadHandles.hContext, pDrvMain->uContextId); + pDrvMain->tFileInfo.eFileType = FILE_TYPE_INI; + eStatus = wlanDrvIf_GetFile (hOs, &pDrvMain->tFileInfo); + } + break; + case SM_STATE_WAIT_INI_FILE: + /* + * We've got the ini-file. + * Set STAD and TWD modules defaults according to the ini-file, + * turn on the device and request for the NVS file. + */ + if (eEvent == SM_EVENT_INI_FILE_READY) + { + pDrvMain->eSmState = SM_STATE_WAIT_NVS_FILE; + drvMain_SetDefaults (hDrvMain, pDrvMain->tFileInfo.pBuffer, pDrvMain->tFileInfo.uLength); + hPlatform_DevicePowerOn (); + + pDrvMain->tFileInfo.eFileType = FILE_TYPE_NVS; + eStatus = wlanDrvIf_GetFile (hOs, &pDrvMain->tFileInfo); + } + break; + + case SM_STATE_WAIT_NVS_FILE: + + /* SDBus Connect connection validation */ + for(uSdioConIndex=0; (uSdioConIndex < SDIO_CONNECT_THRESHOLD) && (eStatus != TI_OK); uSdioConIndex++) + { + /* : We should split the call to txnQ_ConnectBus to other state in order to support Async bus connection */ + eStatus = txnQ_ConnectBus(pDrvMain->tStadHandles.hTxnQ, &pDrvMain->tBusDrvCfg, NULL, NULL); + + if((eStatus != TI_OK) && + (uSdioConIndex < (SDIO_CONNECT_THRESHOLD - 1))) + { + TRACE0(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_WARNING , "SDBus Connect Failed\n"); + WLAN_OS_REPORT(("Try to SDBus Connect again...\n")); + if (uSdioConIndex > 1) + hPlatform_DevicePowerOffSetLongerDelay(); + else + hPlatform_DevicePowerOff(); + hPlatform_DevicePowerOn(); + } + } + + if(eStatus != TI_OK) + { + WLAN_OS_REPORT(("SDBus Connect Failed, Set Object Event !!\r\n")); + TRACE0(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR , "SDBus Connect Failed, Set Object Event !!\r\n"); + if (!pDrvMain->bRecovery) + { + os_SignalObjectSet(hOs, pDrvMain->hSignalObj); + } + else + { + /* in case recovery fails, stop the sme which will send disassociation event to os */ + sme_Stop(pDrvMain->tStadHandles.hSme); + } + } + else /* SDBus Connect success */ + { + /* + * We've got the NVS file. + * Start HW-Init process providing the NVS file. + */ + if (eEvent == SM_EVENT_NVS_FILE_READY) + { + pDrvMain->eSmState = SM_STATE_HW_INIT; + eStatus = drvMain_InitHw (hDrvMain, pDrvMain->tFileInfo.pBuffer, pDrvMain->tFileInfo.uLength); + } + } + break; + case SM_STATE_HW_INIT: + /* + * HW-Init process is completed. + * Request for the FW image file. + */ + if (eEvent == SM_EVENT_HW_INIT_COMPLETE) + { + pDrvMain->tFileInfo.eFileType = FILE_TYPE_FW; + pDrvMain->eSmState = SM_STATE_DOWNLOAD_FW_FILE; + eStatus = wlanDrvIf_GetFile (hOs, &pDrvMain->tFileInfo); + } + break; + case SM_STATE_DOWNLOAD_FW_FILE: + if (eEvent == SM_EVENT_FW_FILE_READY) + { + pDrvMain->tFileInfo.eFileType = FILE_TYPE_FW_NEXT; + if (pDrvMain->tFileInfo.bLast == TI_TRUE) + { + pDrvMain->eSmState = SM_STATE_FW_INIT; + } + else + { + pDrvMain->eSmState = SM_STATE_WAIT_FW_FILE; + } + /* + * We've got the FW image file. + * Start FW-Init process (mainly FW image download) providing the FW image file. + */ + eStatus = drvMain_InitFw (hDrvMain, &pDrvMain->tFileInfo); + } + break; + case SM_STATE_WAIT_FW_FILE: + if (eEvent == SM_EVENT_FW_INIT_COMPLETE) + { + pDrvMain->eSmState = SM_STATE_DOWNLOAD_FW_FILE; + eStatus = wlanDrvIf_GetFile (hOs, &pDrvMain->tFileInfo); + } + break; + case SM_STATE_FW_INIT: + /* + * FW-Init process is completed. + * Free the semaphore of the START action to enable the OS interface. + * Enable interrupts (or polling for debug). + * Start FW-Configuration process, and free the semaphore of the START action. + * + * Note that in some OSs, the semaphore must be released in order to enable the + * interrupts, and the interrupts are needed for the configuration process! + */ + if (eEvent == SM_EVENT_FW_INIT_COMPLETE) + { + pDrvMain->eSmState = SM_STATE_FW_CONFIG; + TWD_EnableInterrupts(pDrvMain->tStadHandles.hTWD); + #ifdef PRIODIC_INTERRUPT + /* Start periodic interrupts. It means that every period of time the FwEvent SM will be called */ + os_periodicIntrTimerStart (hOs); + #endif + eStatus = drvMain_ConfigFw (hDrvMain); + } + break; + case SM_STATE_FW_CONFIG: + /* + * FW-configuration process is completed. + * Stop watchdog timer. + * For recovery, notify the relevant STAD modules. + * For regular start, start the SME which handles the connection process. + * Update timer and OAL about entering OPERATIONAL state (OAL ignores recovery) + * Enable driver activities and external events. + * Enable STOP action + * We are now in OPERATIONAL state, i.e. the driver is fully operational! + */ + + if (eEvent == SM_EVENT_FW_CONFIG_COMPLETE) + { + pDrvMain->eSmState = SM_STATE_OPERATIONAL; + /* return thr timer later on */ + /*os_timerStop (hOs, pDrvMain->hWatchdogTimer);*/ + if (pDrvMain->bRecovery) + { + drvMain_RecoveryNotify (pDrvMain); + pDrvMain->bRecovery = TI_FALSE; + } + else + { + sme_Start (pDrvMain->tStadHandles.hSme); + wlanDrvIf_UpdateDriverState (hOs, DRV_STATE_RUNNING); + } + tmr_UpdateDriverState (pDrvMain->tStadHandles.hTimer, TI_TRUE); + drvMain_EnableActivities (pDrvMain); + context_EnableClient (pDrvMain->tStadHandles.hContext, pDrvMain->uContextId); + eStatus = TI_OK; + + } + if (!pDrvMain->bRecovery) + { + os_SignalObjectSet(hOs, pDrvMain->hSignalObj); + } + break; + case SM_STATE_OPERATIONAL: + /* + * Disable start/stop commands and start watchdog timer. + * Update timer and OAL about exiting OPERATIONAL state (OAL ignores recovery). + * For STOP, stop SME (handle disconnection) and move to DISCONNECTING state. + * For recovery, stop driver activities and move to STOPPING state. + * Note that driver-stop process may be Async if we are during Async bus transaction. + */ + + context_DisableClient (pDrvMain->tStadHandles.hContext, pDrvMain->uContextId); + /* return thr timer later on */ + /*os_timerStart (hOs, pDrvMain->hWatchdogTimer, SM_WATCHDOG_TIME_MS);*/ + tmr_UpdateDriverState (pDrvMain->tStadHandles.hTimer, TI_FALSE); + if (eEvent == SM_EVENT_STOP) + { + pDrvMain->eSmState = SM_STATE_DISCONNECTING; + wlanDrvIf_UpdateDriverState (hOs, DRV_STATE_STOPING); + sme_Stop (pDrvMain->tStadHandles.hSme); + eStatus = TI_OK; + } + else if (eEvent == SM_EVENT_RECOVERY) + { + pDrvMain->eSmState = SM_STATE_STOPPING; + eStatus = drvMain_StopActivities (pDrvMain); + } + + break; + case SM_STATE_DISCONNECTING: + /* + * Note that this state is not relevant for recovery. + * SME stop is completed + * Stop driver activities and move to STOPPING state. + * Note that driver stop process may be Async if we are during Async bus transaction. + */ + + if (eEvent == SM_EVENT_DISCONNECTED) + { + pDrvMain->eSmState = SM_STATE_STOPPING; + eStatus = drvMain_StopActivities (pDrvMain); + } + break; + case SM_STATE_STOPPING: + /* + * Driver stopping process is done. + * Turn device power off. + * For recovery, turn device power back on, request NVS file and continue with + * the init process (recover back all the way to OPERATIONAL state). + * For STOP process, the driver is now fully stopped (STOPPED state), so stop watchdog timer, + * clear all events queues, free the semaphore of the STOP action and enable START action. + */ + + if (eEvent == SM_EVENT_STOP_COMPLETE) + { + txnQ_DisconnectBus (pDrvMain->tStadHandles.hTxnQ); + hPlatform_DevicePowerOff (); + if (pDrvMain->bRecovery) + { + hPlatform_DevicePowerOn (); + pDrvMain->eSmState = SM_STATE_WAIT_NVS_FILE; + pDrvMain->tFileInfo.eFileType = FILE_TYPE_NVS; + eStatus = wlanDrvIf_GetFile (hOs, &pDrvMain->tFileInfo); + } + else + { + pDrvMain->eSmState = SM_STATE_STOPPED; + /* return thr timer later on */ + /*os_timerStop (hOs, pDrvMain->hWatchdogTimer);*/ + drvMain_ClearQueuedEvents (pDrvMain); + scr_notifyFWReset(pDrvMain->tStadHandles.hSCR); + os_SignalObjectSet (hOs, pDrvMain->hSignalObj); + context_EnableClient (pDrvMain->tStadHandles.hContext, pDrvMain->uContextId); + wlanDrvIf_UpdateDriverState (hOs, DRV_STATE_STOPPED); + eStatus = TI_OK; + } + } + + break; + case SM_STATE_STOPPED: + /* + * A START action command was inserted, so we go through the init process. + * Disable further actions, start watchdog timer, turn on device and request NVS file. + */ + + context_DisableClient (pDrvMain->tStadHandles.hContext, pDrvMain->uContextId); + /* return thr timer later on */ + /*os_timerStart (hOs, pDrvMain->hWatchdogTimer, SM_WATCHDOG_TIME_MS);*/ + if (eEvent == SM_EVENT_START) + { + hPlatform_DevicePowerOn (); + pDrvMain->eSmState = SM_STATE_WAIT_NVS_FILE; + pDrvMain->tFileInfo.eFileType = FILE_TYPE_NVS; + eStatus = wlanDrvIf_GetFile (hOs, &pDrvMain->tFileInfo); + } + break; + case SM_STATE_STOPPING_ON_FAIL: + /* + * Driver stopping process upon failure is completed. + * Turn off the device and move to FAILED state. + */ + + pDrvMain->eSmState = SM_STATE_FAILED; + txnQ_DisconnectBus (pDrvMain->tStadHandles.hTxnQ); + hPlatform_DevicePowerOff (); + WLAN_OS_REPORT(("[WLAN] Exit application\n")); + if (!pDrvMain->bRecovery) + { + os_SignalObjectSet (hOs, pDrvMain->hSignalObj); + } + break; + case SM_STATE_FAILED: + /* Nothing to do except waiting for Destroy */ + break; + default: + TRACE2(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR , "drvMain_Sm: Unknown state, eEvent=%u at state=%u\n", eEvent, pDrvMain->eSmState); + /* Note: Handled below as a failure since the status remains TI_NOK */ + break; + } + + /* Handle failures (status = NOK) if not handled yet */ + if ((eStatus == TI_NOK) && + (pDrvMain->eSmState != SM_STATE_FAILED) && + (pDrvMain->eSmState != SM_STATE_STOPPING_ON_FAIL)) + { + TRACE3(pDrvMain->tStadHandles.hReport, REPORT_SEVERITY_ERROR , "drvMain_Sm: eEvent=%u at state=%u, status=%d\n", eEvent, pDrvMain->eSmState, eStatus); + pDrvMain->eSmState = SM_STATE_STOPPING_ON_FAIL; + wlanDrvIf_UpdateDriverState (hOs, DRV_STATE_FAILED); + + /* + * Stop all activities. This may be completed in a different context if + * we should wait for an Async bus transaction completion. + * The drvMain_TwdStopCb is called from the TWD in any case to pass + * us to the SM_STATE_FAILED state (where we wait for Destroy). + */ + eStatus = drvMain_StopActivities (pDrvMain); + } +} diff --git a/wilink_6_1/stad/src/Ctrl_Interface/DrvMain.h b/wilink_6_1/stad/src/Ctrl_Interface/DrvMain.h new file mode 100644 index 0000000..f4e7175 --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/DrvMain.h @@ -0,0 +1,60 @@ +/* + * DrvMain.h + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + + + +#ifndef DRVMAIN_H +#define DRVMAIN_H + + +#include "paramOut.h" +#include "WlanDrvCommon.h" + + +/* Driver-Main module external functions */ + +TI_STATUS drvMain_Create (TI_HANDLE hOs, + TI_HANDLE *pDrvMainHndl, + TI_HANDLE *pCmdHndlr, + TI_HANDLE *pContext, + TI_HANDLE *pTxDataQ, + TI_HANDLE *pTxMgmtQ, + TI_HANDLE *pTxCtrl, + TI_HANDLE *pTwd, + TI_HANDLE *pEvHandler); +TI_STATUS drvMain_Destroy (TI_HANDLE hDrvMain); +TI_STATUS drvMain_InsertAction (TI_HANDLE hDrvMain, EActionType eAction); +TI_STATUS drvMain_Recovery (TI_HANDLE hDrvMain); +void drvMain_SmeStop (TI_HANDLE hDrvMain); + +#endif diff --git a/wilink_6_1/stad/src/Ctrl_Interface/DrvMainModules.h b/wilink_6_1/stad/src/Ctrl_Interface/DrvMainModules.h new file mode 100644 index 0000000..67aecd2 --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/DrvMainModules.h @@ -0,0 +1,86 @@ +/* + * DrvMainModules.h + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef DRVMAIN_MODULES_H +#define DRVMAIN_MODULES_H + +#include "tidef.h" + +/* STAD Modules Handles List */ +typedef struct +{ + TI_HANDLE hDrvMain; + TI_HANDLE hOs; + TI_HANDLE hReport; + TI_HANDLE hContext; + TI_HANDLE hTimer; + TI_HANDLE hTWD; + TI_HANDLE hCmdHndlr; + TI_HANDLE hSme; + TI_HANDLE hSiteMgr; + TI_HANDLE hConn; + TI_HANDLE hMlmeSm; + TI_HANDLE hAuth; + TI_HANDLE hAssoc; + TI_HANDLE hRxData; + TI_HANDLE hTxCtrl; + TI_HANDLE hTxPort; + TI_HANDLE hTxDataQ; + TI_HANDLE hTxMgmtQ; + TI_HANDLE hCtrlData; + TI_HANDLE hTrafficMon; + TI_HANDLE hRsn; + TI_HANDLE hRegulatoryDomain; + TI_HANDLE hMeasurementMgr; + TI_HANDLE hSoftGemini; + TI_HANDLE hXCCMngr; + TI_HANDLE hRoamingMngr; + TI_HANDLE hQosMngr; + TI_HANDLE hPowerMgr; + TI_HANDLE hPowerSrv; + TI_HANDLE hEvHandler; + TI_HANDLE hAPConnection; + TI_HANDLE hCurrBss; + TI_HANDLE hSwitchChannel; + TI_HANDLE hSCR; + TI_HANDLE hScanCncn; + TI_HANDLE hScanMngr; + TI_HANDLE hHealthMonitor; + TI_HANDLE hCmdDispatch; + TI_HANDLE hStaCap; + TI_HANDLE hTxnQ; + +} TStadHandlesList; + + +#endif /* DRVMAIN_MODULES_H */ diff --git a/wilink_6_1/stad/src/Ctrl_Interface/EvHandler.c b/wilink_6_1/stad/src/Ctrl_Interface/EvHandler.c new file mode 100644 index 0000000..99205b4 --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/EvHandler.c @@ -0,0 +1,287 @@ +/* + * EvHandler.c + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#define __FILE_ID__ FILE_ID_50 +#include "IPCKernelApi.h" +#include "EvHandler.h" +#include "osApi.h" +#include "osDebug.h" + +#ifndef _WINDOWS +#include "windows_types.h" +#else +#include <windows.h> +#endif /*_WINDOWS*/ + +#ifdef EV_HANDLER_DEBUG +TI_HANDLE ghEvHandler; /* for debug, remove later*/ +#endif + +/* ************************** Upper Interface **********************************/ + +TI_HANDLE EvHandler_Create (TI_HANDLE hOs) +{ + TEvHandlerObj *pEvHandler; + + PRINT(DBG_INIT_LOUD, (" EvHandlerInit\n")); + pEvHandler = os_memoryAlloc(hOs,sizeof(TEvHandlerObj)); + os_memoryZero(hOs,pEvHandler,sizeof(TEvHandlerObj)); + + #ifdef EV_HANDLER_DEBUG + ghEvHandler= pEvHandler; + PRINTF(DBG_INIT_VERY_LOUD, ("EvHandlerInit: ghEvHandler set to %08X\n", ghEvHandler)); + #endif + + pEvHandler->hOs = hOs; + + pEvHandler->LastUMEventType = 0xFFFFFFFF; + + return (TI_HANDLE) pEvHandler; +} + +TI_UINT32 EvHandlerUnload (TI_HANDLE hEvHandler) +{ + + TEvHandlerObj *pEvHandler; + + PRINT(DBG_INIT_LOUD, (" ev_handler_unLoad\n")); + pEvHandler = (TEvHandlerObj *)hEvHandler; + + os_memoryFree(pEvHandler->hOs,pEvHandler,sizeof(TEvHandlerObj)); + + return TI_OK; +} + + +TI_UINT32 EvHandlerRegisterEvent(TI_HANDLE hEvHandler, TI_UINT8* pData, TI_UINT32 Length) +{ + TEvHandlerObj *pEvHandler; + IPC_EVENT_PARAMS *pEvParams; + TI_UINT32 ModuleIndex; + + if( (hEvHandler==NULL) || (pData == NULL)){ + PRINT(DBG_INIT_ERROR, "EvHandler:EvHandlerRegisterEvent Bad Handle passed \n"); + return TI_NOK; + } + +#ifdef EV_HANDLER_DEBUG + if (ghEvHandler != hEvHandler) + { + return TI_NOK; + } +#endif + + pEvHandler = (TEvHandlerObj *)hEvHandler; + pEvParams = (IPC_EVENT_PARAMS *)pData; + + PRINTF(DBG_INIT_LOUD, (" EvHandlerRegisterEvent EventType = %d \n",pEvParams->uEventType)); + + /* used to be: if ( sizeof(IPC_EVENT_PARAMS) != Length) + relaxed size checking (okay if output buffer is larger) */ + if (sizeof(IPC_EVENT_PARAMS) > Length) + { + PRINTF(DBG_INIT_ERROR, (" EvHandlerRegisterEvent Error sizeof(IPC_EVENT_PARAMS) != Length," + "%d != %d \n",sizeof(IPC_EVENT_PARAMS), (int)Length)); + return (TI_UINT32)STATUS_INVALID_PARAMETER; + } + + if (pEvParams->uEventType >= IPC_EVENT_MAX){ + PRINTF(DBG_INIT_ERROR, (" EvHandlerRegisterEvent Error - Invalid Event Type = %d \n", + pEvParams->uEventType)); + return (TI_UINT32)STATUS_INVALID_PARAMETER; + } + + ModuleIndex = 0; + + while ((ModuleIndex < MAX_REGISTERED_MODULES) && + (pEvHandler->RegistrationArray[pEvParams->uEventType][ModuleIndex].uEventID != NULL)) + { + ModuleIndex++; + } + + if (ModuleIndex == MAX_REGISTERED_MODULES) + { + PRINTF(DBG_INIT_WARNING, (" EvHandlerRegisterEvent %d " + "Registration queue full or event already registered!\n", + pEvParams->uEventType)); + return (TI_UINT32)STATUS_INVALID_PARAMETER; + } + + os_memoryCopy(pEvHandler->hOs,(TI_UINT8*)&pEvHandler->RegistrationArray[pEvParams->uEventType][ModuleIndex], + (TI_UINT8*)pEvParams,Length); + + pEvParams->uEventID = (TI_HANDLE)&pEvHandler->RegistrationArray[pEvParams->uEventType][ModuleIndex]; + + pEvHandler->RegistrationArray[pEvParams->uEventType][ModuleIndex].uEventID = pEvParams->uEventID; + + PRINT(DBG_INIT_LOUD, " EvHandlerRegisterEvent Out \n"); + return STATUS_SUCCESS; + +} + + +TI_UINT32 EvHandlerUnRegisterEvent(TI_HANDLE hEvHandler, TI_HANDLE uEventID) +{ + TEvHandlerObj *pEvHandler; + IPC_EVENT_PARAMS *pEvParams; + TI_UINT32 ModuleIndex; + +#ifdef EV_HANDLER_DEBUG + if (ghEvHandler != hEvHandler ) + { + return TI_NOK; + } +#endif + + if (uEventID == NULL) + { + return TI_NOK; + } + + pEvHandler = (TEvHandlerObj *)hEvHandler; + pEvParams = (IPC_EVENT_PARAMS *)uEventID; + + PRINTF(DBG_INIT_LOUD, (" EvHandlerUnRegisterEvent EventType = %d \n",pEvParams->uEventType)); + + if( pEvParams->uEventType >= IPC_EVENT_MAX){ + PRINTF(DBG_INIT_ERROR, (" EvHandlerRegisterEvent Error Event Type = %d \n", + pEvParams->uEventType)); + return (TI_UINT32)STATUS_INVALID_PARAMETER; + } + + ModuleIndex = 0; + + while ((ModuleIndex < MAX_REGISTERED_MODULES) && + (pEvHandler->RegistrationArray[pEvParams->uEventType][ModuleIndex].uEventID != pEvParams->uEventID)) + { + ModuleIndex++; + } + + if (ModuleIndex == MAX_REGISTERED_MODULES) + { + PRINTF(DBG_INIT_ERROR, (" EvHandlerUnRegisterEvent %d " + "Registration queue doesn't hold this event!\n", + pEvParams->uEventType )); + return (TI_UINT32)STATUS_INVALID_PARAMETER; + } + pEvHandler->RegistrationArray[pEvParams->uEventType][ModuleIndex].uEventID = NULL; + + return STATUS_SUCCESS; +} + +/* ************************** Upper Interface End*********************************/ + +/* ************************** Bottom Interface **********************************/ + +TI_UINT32 EvHandlerSendEvent(TI_HANDLE hEvHandler, TI_UINT32 EvType, TI_UINT8* pData, TI_UINT32 Length) +{ + TEvHandlerObj *pEvHandler; + IPC_EV_DATA* pNewEvent; + TI_UINT32 TailIndex=0; + TI_UINT32 ModuleIndex=0; + + PRINTF(DBG_INIT_LOUD, (" EvHandlerSendEvent %d \n", EvType)); + + if(hEvHandler == NULL){ + PRINT(DBG_INIT_ERROR, "EvHandlerSendEvent Bad Handle passed \n"); + return TI_NOK; + } + +#ifdef EV_HANDLER_DEBUG + if (ghEvHandler != hEvHandler) + { + return TI_NOK; + } +#endif + + pEvHandler = (TEvHandlerObj *)hEvHandler; + + TailIndex = pEvHandler->SendEventArray.TailIndex; + + while ((ModuleIndex < MAX_REGISTERED_MODULES) && (EvType <= IPC_EVENT_MAX)) + { + if (pEvHandler->RegistrationArray[EvType][ModuleIndex].uEventID != NULL ) + { + if(pEvHandler->SendEventArray.Counter == MAX_SEND_EVENTS) + { + PRINT(DBG_INIT_ERROR, " EvHandlerSendEvent Array Full u Fool! \n"); + return TI_NOK; + } + + pNewEvent = &pEvHandler->SendEventArray.Array[TailIndex]; + + /* copy the event parameters and data to the events queue*/ + os_memoryCopy(pEvHandler->hOs,(TI_UINT8*)&pNewEvent->EvParams, + (TI_UINT8*)&pEvHandler->RegistrationArray[EvType][ModuleIndex], + sizeof(IPC_EVENT_PARAMS)); + + os_memoryZero(pEvHandler->hOs,(TI_UINT8*)pNewEvent->uBuffer, sizeof(pNewEvent->uBuffer)); + + os_memoryCopy(pEvHandler->hOs, + (TI_UINT8*)pNewEvent->uBuffer, + (TI_UINT8*)pData, + Length); + + pNewEvent->uBufferSize = Length; + + if(pNewEvent->EvParams.uDeliveryType == DELIVERY_PUSH) + { + PRINTF(DBG_INIT_LOUD, (" EvHandlerSendEvent %d to OS \n", EvType)); + PRINTF(DBG_INIT_LOUD, ("EvHandlerSendEvent Matching OS Registered event found at EvType = %d," + "ModuleIndex = %d \n", EvType, ModuleIndex)); + IPC_EventSend (pEvHandler->hOs,(TI_UINT8*)pNewEvent,sizeof(IPC_EV_DATA)); + } + else { + + pEvHandler->LastUMEventType = EvType; + pEvHandler->SendEventArray.TailIndex = (TailIndex+1) % MAX_SEND_EVENTS; + pEvHandler->SendEventArray.Counter++; + TailIndex = pEvHandler->SendEventArray.TailIndex; + PRINTF(DBG_INIT_LOUD, (" EvHandlerSendEvent %d to User Mode \n", EvType)); + PRINTF(DBG_INIT_LOUD, ("EvHandlerSendEvent Matching User Mode Registered event found at EvType = %d," + "ModuleIndex = %d \n", EvType, ModuleIndex)); + if (pEvHandler->SendEventArray.Counter == 1) + { + IPC_EventSend (pEvHandler->hOs,NULL,0); + } + } + } /* end if*/ + + ModuleIndex++; + + } /* end of while*/ + + return TI_OK; +} + + /* ************************** Bottom Interface End **********************************/ diff --git a/wilink_6_1/stad/src/Ctrl_Interface/EvHandler.h b/wilink_6_1/stad/src/Ctrl_Interface/EvHandler.h new file mode 100644 index 0000000..9da8d21 --- /dev/null +++ b/wilink_6_1/stad/src/Ctrl_Interface/EvHandler.h @@ -0,0 +1,77 @@ +/* + * EvHandler.h + * + * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name Texas Instruments nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef _EVHANDLER_H_ +#define _EVHANDLER_H_ + + +#include "TI_IPC_Api.h" + + +typedef struct +{ + IPC_EV_DATA Array[MAX_SEND_EVENTS]; + TI_UINT32 TailIndex; /* Points to the next free node*/ + TI_UINT32 HeadIndex; /* Points to the first occupied node*/ + TI_UINT32 Counter; +}EV_CYCL_ARRAY, *PEV_CYCL_ARRAY; + +typedef struct +{ + TI_HANDLE hOs; + IPC_EVENT_PARAMS RegistrationArray[IPC_EVENT_MAX][MAX_REGISTERED_MODULES]; + EV_CYCL_ARRAY SendEventArray; + TI_UINT32 LastUMEventType; + +}TEvHandlerObj; + +/* Upper Interface*/ +TI_HANDLE EvHandler_Create (TI_HANDLE hOs); + +TI_UINT32 EvHandlerUnload (TI_HANDLE hEvHandler); + +TI_UINT32 EvHandlerRegisterEvent (TI_HANDLE hEvHandler, TI_UINT8* pData, TI_UINT32 Length); + +TI_UINT32 EvHandlerUnRegisterEvent (TI_HANDLE hEvHandler, TI_HANDLE uEventID); + +TI_UINT32 EvHandlerMaskEvent (TI_HANDLE hEvHandler, TI_UINT32 uEventID); + +TI_UINT32 EvHandlerUnMaskEvent (TI_HANDLE hEvHandler, TI_UINT32 uEventID); + +TI_UINT32 EvHandlerGetEventData (TI_HANDLE hEvHandler, TI_UINT8* pData, TI_UINT32* pLength); +/* Bottom Interface*/ + +TI_UINT32 EvHandlerSendEvent (TI_HANDLE hEvHandler, TI_UINT32 EvType, TI_UINT8* pData, TI_UINT32 Length); + + +#endif |