blob: c7d82281fb971cee4c2331c9f24d6c0c82ceb53d [file] [log] [blame]
/*
* Copyright (c) 2012-2014, 2017 The Linux Foundation. All rights reserved.
*
* Previously licensed under the ISC license by Qualcomm Atheros, Inc.
*
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
* above copyright notice and this permission notice appear in all
* copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
* WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
* AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
* DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
* PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
* TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
* PERFORMANCE OF THIS SOFTWARE.
*/
/*
* This file was originally distributed by Qualcomm Atheros, Inc.
* under proprietary terms before Copyright ownership was assigned
* to the Linux Foundation.
*/
/*===========================================================================
b t a m p F s m . C
OVERVIEW:
This software unit holds the implementation of the Finite State Machine that
controls the operation of each individual AMP Physical link.
(Currently, this is limited to ONE link.)
The btampFsm() routine provided by this module is called by the rest of
the BT-AMP PAL module whenever a control plane operation occurs that requires a
major state transition.
DEPENDENCIES:
Are listed for each API below.
===========================================================================*/
/*===========================================================================
EDIT HISTORY FOR FILE
This section contains comments describing changes made to the module.
Notice that changes are listed in reverse chronological order.
$Header: /prj/qct/asw/engbuilds/scl/users02/jzmuda/gb-bluez/vendor/qcom/proprietary/wlan/libra/CORE/BAP/src/btampFsm.c,v 1.11 2011/03/30 21:52:10 jzmuda Exp jzmuda $
when who what, where, why
---------- --- --------------------------------------------------------
2008-10-16 jez Created module
===========================================================================*/
/* This file is generated from btampFsm.cdd - do not edit manually*/
/* Generated on: Thu Oct 16 15:40:39 PDT 2008 / version 1.2 Beta 1 */
/*----------------------------------------------------------------------------
* Include Files
* -------------------------------------------------------------------------*/
#include "fsmDefs.h"
//#include "btampFsm.h"
#include "bapInternal.h"
#include "btampFsm_ext.h"
// Pick up the BTAMP Timer API definitions
#include "bapApiTimer.h"
// Pick up the BTAMP RSN definitions
#include "bapRsn8021xFsm.h"
#include "bapRsn8021xAuthFsm.h"
// Pick up the SME API definitions
#include "sme_Api.h"
// Pick up the PMC API definitions
#include "pmcApi.h"
// Pick up the BTAMP API defintions for interfacing to External subsystems
#include "bapApiExt.h"
#include "wlan_nlink_common.h"
#include "wlan_btc_svc.h"
// Pick up the DOT11 Frames compiler
// I just need these one "opaque" type definition in order to use the "frames" code
typedef struct sAniSirGlobal *tpAniSirGlobal;
#include "dot11f.h"
#if 0
/*
* Event-related Defines.
* - Ultimately, these events will be values
* - from an enumeration. That are set by some
* - of the following events.
*/
#define eWLAN_BAP_MAC_START_BSS_SUCCESS /* bapRoamCompleteCallback with eCSR_ROAM_RESULT_WDS_STARTED */
#define eWLAN_BAP_MAC_START_FAILS /* bapRoamCompleteCallback with eCSR_ROAM_RESULT_FAILURE or eCSR_ROAM_RESULT_NOT_ASSOCIATED */
#define eWLAN_BAP_MAC_SCAN_COMPLETE /* bapScanCompleteCallback */
#define eWLAN_BAP_CHANNEL_NOT_SELECTED /* No existing Infra assoc - e.g., use HAL to access the STA LIST and find nothing */
#define eWLAN_BAP_MAC_CONNECT_COMPLETED /* bapRoamCompleteCallback with eCSR_ROAM_RESULT_WDS_ASSOCIATED */
#define eWLAN_BAP_MAC_CONNECT_FAILED /* bapRoamCompleteCallback with eCSR_ROAM_RESULT_FAILURE or eCSR_ROAM_RESULT_NOT_ASSOCIATED */
#define eWLAN_BAP_MAC_CONNECT_INDICATION /* bapRoamCompleteCallback with eCSR_ROAM_RESULT_WDS_ASSOCIATION_IND */
#define eWLAN_BAP_RSN_SUCCESS /* setKey IOCTL from the Auth/Supp App */
#define eWLAN_BAP_RSN_FAILURE /* deAuth IOCTL from the Auth/Supp App */
#define eWLAN_BAP_MAC_KEY_SET_SUCCESS /* bapRoamCompleteCallback with eCSR_ROAM_RESULT_KEY_SET */
#define eWLAN_BAP_MAC_INDICATES_MEDIA_DISCONNECTION /* bapRoamCompleteCallback with eCSR_ROAM_RESULT_WDS_DISASSOC_IND */
#define eWLAN_BAP_MAC_READY_FOR_CONNECTIONS /* bapRoamCompleteCallback with eCSR_ROAM_RESULT_WDS_STOPPED */
#define eWLAN_BAP_CHANNEL_SELECTION_FAILED /* ??? */
#endif /* 0 */
/*Min and max channel values in 2.4GHz band for operational channel validation
on connect*/
#define WLAN_BAP_MIN_24G_CH 1
#define WLAN_BAP_MAX_24G_CH 14
/* The HCI Disconnect Logical Link Complete Event signalling routine*/
VOS_STATUS
signalHCIDiscLogLinkCompEvent
(
ptBtampContext btampContext, /* btampContext value */
v_U8_t status, /* the BT-AMP status */
v_U16_t log_link_handle, /* The Logical Link that disconnected*/
v_U8_t reason /* the BT-AMP reason code */
);
/* Stubs - TODO : Remove once the functions are available */
int
bapSuppDisconnect(tBtampContext *ctx)
{
// Disconnect function is called internally
// TODO : Need to find, if it disconnect will be issued from bap for supplicant
return ANI_OK;
}
int
bapAuthDisconnect(tBtampContext *ctx)
{
// Disconnect function is called internally
// TODO : Need to find, if it disconnect will be issued from bap for supplicant
return ANI_OK;
}
VOS_STATUS
bapSetKey( v_PVOID_t pvosGCtx, tCsrRoamSetKey *pSetKeyInfo )
{
tWLAN_BAPEvent bapEvent; /* State machine event */
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
ptBtampContext btampContext; /* use btampContext value */
v_U8_t status; /* return the BT-AMP status here */
eHalStatus halStatus;
v_U32_t roamId = 0xFF;
tHalHandle hHal = NULL;
v_U8_t groupMac[ANI_MAC_ADDR_SIZE] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
/* Validate params */
if ((pvosGCtx == NULL) || (pSetKeyInfo == NULL))
{
return VOS_STATUS_E_FAULT;
}
btampContext = VOS_GET_BAP_CB(pvosGCtx);
/* Validate params */
if ( btampContext == NULL)
{
return VOS_STATUS_E_FAULT;
}
hHal = VOS_GET_HAL_CB(btampContext->pvosGCtx);
if (NULL == hHal)
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"hHal is NULL in %s", __func__);
return VOS_STATUS_E_FAULT;
}
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "%s: btampContext value: %pK", __func__, btampContext);
/* Fill in the event structure */
bapEvent.event = eWLAN_BAP_RSN_SUCCESS;
bapEvent.params = NULL;
/* Signal the successful RSN auth and key exchange event */
/* (You have to signal BEFORE calling sme_RoamSetKey) */
vosStatus = btampFsm(btampContext, &bapEvent, &status);
/* Set the Pairwise Key */
halStatus = sme_RoamSetKey(
hHal,
btampContext->sessionId,
pSetKeyInfo,
&roamId );
if ( halStatus != eHAL_STATUS_SUCCESS )
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"[%4d] sme_RoamSetKey returned ERROR status= %d", __LINE__, halStatus );
return VOS_STATUS_E_FAULT;
}
/* Set the Group Key */
vos_mem_copy( pSetKeyInfo->peerMac, groupMac, sizeof( tAniMacAddr ) );
halStatus = sme_RoamSetKey(
hHal,
btampContext->sessionId,
pSetKeyInfo,
&roamId );
if ( halStatus != eHAL_STATUS_SUCCESS )
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"[%4d] sme_RoamSetKey returned ERROR status= %d", __LINE__, halStatus );
return VOS_STATUS_E_FAULT;
}
return vosStatus;
}
/*
* Debug-related Defines.
* - Ultimately, these events will be values
* - from an enumeration. That are set by some
* - of the following events.
*/
#define DUMPLOG_ON
#if defined DUMPLOG_ON
#define DUMPLOG(n, name1, name2, aStr, size) do { \
int i; \
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "%d. %s: %s = \n", n, name1, name2); \
for (i = 0; i < size; i++) \
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "%2.2x%s", ((unsigned char *)aStr)[i], i % 16 == 15 ? "\n" : " "); \
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "\n"); \
} while (0)
#else
#define DUMPLOG(n, name1, name2, aStr, size)
#endif
/*
* State transition procedures
*/
VOS_STATUS
gotoS1
(
ptBtampContext btampContext, /* btampContext value */
ptWLAN_BAPEvent bapEvent, /* State machine event */
tWLAN_BAPRole BAPDeviceRole,
v_U8_t *status /* return the BT-AMP status here */
)
{
tBtampTLVHCI_Create_Physical_Link_Cmd *pBapHCIPhysLinkCreate
= (tBtampTLVHCI_Create_Physical_Link_Cmd *) bapEvent->params;
tBtampTLVHCI_Accept_Physical_Link_Cmd *pBapHCIPhysLinkAccept
= (tBtampTLVHCI_Accept_Physical_Link_Cmd *) bapEvent->params;
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
v_U32_t conAcceptTOInterval;
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
/* Remember role */
btampContext->BAPDeviceRole = BAPDeviceRole;
switch(BAPDeviceRole)
{
case BT_INITIATOR:
/* Copy down the phy_link_handle value */
btampContext->phy_link_handle = pBapHCIPhysLinkCreate->phy_link_handle;
/* Copy out the key material from the HCI command */
btampContext->key_type = pBapHCIPhysLinkCreate->key_type;
btampContext->key_length = pBapHCIPhysLinkCreate->key_length;
vos_mem_copy(
btampContext->key_material,
pBapHCIPhysLinkCreate->key_material,
32); /* Need a key size define */
break;
case BT_RESPONDER:
/* Copy down the phy_link_handle value */
btampContext->phy_link_handle = pBapHCIPhysLinkAccept->phy_link_handle;
/* Copy out the key material from the HCI command */
btampContext->key_type = pBapHCIPhysLinkAccept->key_type;
btampContext->key_length = pBapHCIPhysLinkAccept->key_length;
vos_mem_copy(
btampContext->key_material,
pBapHCIPhysLinkAccept->key_material,
32); /* Need a key size define */
break;
default:
*status = WLANBAP_ERROR_HOST_REJ_RESOURCES; /* return the BT-AMP status here */
return VOS_STATUS_E_RESOURCES;
}
conAcceptTOInterval = (btampContext->bapConnectionAcceptTimerInterval * 5)/ 8;
/* Start the Connection Accept Timer */
vosStatus = WLANBAP_StartConnectionAcceptTimer (
btampContext,
conAcceptTOInterval);
*status = WLANBAP_STATUS_SUCCESS; /* return the BT-AMP status here */
return VOS_STATUS_SUCCESS;
} //gotoS1
VOS_STATUS
gotoScanning
(
ptBtampContext btampContext, /* btampContext value */
tWLAN_BAPRole BAPDeviceRole,
v_U8_t *status /* return the BT-AMP status here */
)
{
/* Initiate a SCAN request */
//csrScanRequest();
*status = WLANBAP_STATUS_SUCCESS; /* return the BT-AMP status here */
return VOS_STATUS_SUCCESS;
}
#if 0
/*==========================================================================
FUNCTION: convertRoleToBssType
DESCRIPTION: Return one of the following values:
eCSR_BSS_TYPE_INFRASTRUCTURE,
eCSR_BSS_TYPE_IBSS, // an IBSS network we will NOT start
eCSR_BSS_TYPE_START_IBSS, // an IBSS network we will start if no partners detected.
eCSR_BSS_TYPE_WDS_AP, // BT-AMP AP
eCSR_BSS_TYPE_WDS_STA, // BT-AMP station
eCSR_BSS_TYPE_ANY,
============================================================================*/
#endif
eCsrRoamBssType
convertRoleToBssType
(
tWLAN_BAPRole bapRole /* BT-AMP role */
)
{
switch (bapRole)
{
case BT_RESPONDER:
// an WDS network we will join
return eCSR_BSS_TYPE_WDS_STA;
//return eCSR_BSS_TYPE_INFRASTRUCTURE;
//return eCSR_BSS_TYPE_IBSS; // Initial testing with IBSS on both ends makes more sense
case BT_INITIATOR:
// an WDS network we will start if no partners detected.
return eCSR_BSS_TYPE_WDS_AP;
//return eCSR_BSS_TYPE_START_IBSS; // I really should try IBSS on both ends
default:
return eCSR_BSS_TYPE_INFRASTRUCTURE;
}
} // convertRoleToBssType
char hexValue[] = {'0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'a', 'b', 'c', 'd', 'e', 'f'
};
#define BAP_MIN(x, y) ((x) < (y) ? (x) : (y))
#define MAX_BYTES 8
// Each byte will be converted to hex digits followed by a
// punctuation (which is specified in the "delimiter" param.) Thus
// allocate three times the storage.
v_U8_t *
bapBin2Hex(const v_U8_t *bytes, v_U32_t len, char delimiter)
{
static v_U8_t buf[MAX_BYTES*(2+1)];
v_U32_t i;
v_U8_t *ptr;
len = BAP_MIN(len, MAX_BYTES);
for (i = 0, ptr = buf; i < len; i++)
{
*ptr++ = hexValue[ (bytes[i] >> 4) & 0x0f];
*ptr++ = hexValue[ bytes[i] & 0x0f];
*ptr++ = delimiter;
//sprintf(ptr, "%.2x%c", bytes[i], delimiter);
//ptr += 3;
}
// Delete the extra punctuation and null terminate the string
if (len > 0)
ptr--;
*ptr = '\0';
return buf;
}// bapBin2Hex
char bapSsidPrefixValue[] = {'A', 'M', 'P', '-'};
v_U8_t *
convertBSSIDToSSID
(
v_U8_t *bssid /* BSSID value */
)
{
static v_U8_t ssId[32];
vos_mem_copy(
ssId,
bapSsidPrefixValue,
4);
vos_mem_copy(
&ssId[4],
bapBin2Hex(bssid, 6, '-'),
17);
return ssId;
} // convertBSSIDToSSID
VOS_STATUS
convertToCsrProfile
(
ptBtampContext btampContext, /* btampContext value */
eCsrRoamBssType bssType,
tCsrRoamProfile *pProfile /* return the profile info here */
)
{
static v_U8_t btampRSNIE[] = {0x30, 0x14, 0x01, 0x00, 0x00, 0x0f, 0xac, 0x04, 0x01, 0x00,
0x00, 0x0f, 0xac, 0x04, 0x01, 0x00, 0x00, 0x0f, 0xac, 0x02, 0x00, 0x00
};
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
v_S7_t sessionid = -1;
tHalHandle hHal = NULL;
v_U32_t triplet;
v_U8_t regulatoryClass;
v_U8_t firstChannel;
v_U8_t numChannels;
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
if (NULL == btampContext)
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"btampContext is NULL in %s", __func__);
return VOS_STATUS_E_FAULT;
}
hHal = VOS_GET_HAL_CB(btampContext->pvosGCtx);
if (NULL == hHal)
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"hHal is NULL in %s", __func__);
return VOS_STATUS_E_FAULT;
}
//Zero out entire roamProfile structure to avoid problems in uninitialized pointers as the structure expands */
//vos_mem_zero(pProfile,sizeof(tCsrRoamProfile));
//Set the BSS Type
//pProfile->BSSType = convertRoleToBssType(btampContext->BAPDeviceRole );
pProfile->BSSType = bssType;
//pProfile->BSSType = eCSR_BSS_TYPE_INFRASTRUCTURE;
//Set the SSID
if ( bssType == eCSR_BSS_TYPE_WDS_STA)
{
pProfile->SSIDs.numOfSSIDs = 2;
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "%s: bssType = %s, SSID specified = %s\n", __func__, "eCSR_BSS_TYPE_WDS_STA", convertBSSIDToSSID(btampContext->btamp_Remote_AMP_Assoc.HC_mac_addr));
vos_mem_zero(pProfile->SSIDs.SSIDList[0].SSID.ssId,
sizeof(pProfile->SSIDs.SSIDList[0].SSID.ssId));
vos_mem_copy(pProfile->SSIDs.SSIDList[0].SSID.ssId,
convertBSSIDToSSID(btampContext->btamp_Remote_AMP_Assoc.HC_mac_addr),
21); // Length of BTAMP SSID is 21 bytes
pProfile->SSIDs.SSIDList[0].SSID.length = 21;
vos_mem_zero(pProfile->SSIDs.SSIDList[1].SSID.ssId,
sizeof(pProfile->SSIDs.SSIDList[1].SSID.ssId));
vos_mem_copy(pProfile->SSIDs.SSIDList[1].SSID.ssId,
convertBSSIDToSSID(btampContext->self_mac_addr),
21); // Length of BTAMP SSID is 21 bytes
pProfile->SSIDs.SSIDList[1].SSID.length = 21;
//Set the BSSID to the Remote AP
pProfile->BSSIDs.numOfBSSIDs = 1;
vos_mem_copy(pProfile->BSSIDs.bssid,
btampContext->btamp_Remote_AMP_Assoc.HC_mac_addr,
sizeof( tCsrBssid ) );
}
else if ( bssType == eCSR_BSS_TYPE_WDS_AP)
{
pProfile->SSIDs.numOfSSIDs = 1;
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "%s: bssType = %s, SSID specified = %s\n", __func__, "eCSR_BSS_TYPE_WDS_AP", convertBSSIDToSSID(btampContext->self_mac_addr));
vos_mem_zero(pProfile->SSIDs.SSIDList[0].SSID.ssId,
sizeof(pProfile->SSIDs.SSIDList[0].SSID.ssId));
vos_mem_copy(pProfile->SSIDs.SSIDList[0].SSID.ssId,
convertBSSIDToSSID(btampContext->self_mac_addr),
21); // Length of BTAMP SSID is 21 bytes
pProfile->SSIDs.SSIDList[0].SSID.length = 21;
#if 0
//In case you are an AP, don't set the BSSID
pProfile->BSSIDs.numOfBSSIDs = 0;
#endif //0
//Set the BSSID to your "self MAC Addr"
pProfile->BSSIDs.numOfBSSIDs = 1;
vos_mem_copy(pProfile->BSSIDs.bssid,
btampContext->self_mac_addr,
sizeof( tCsrBssid ) );
}
else
// Handle everything else as bssType eCSR_BSS_TYPE_INFRASTRUCTURE
{
pProfile->SSIDs.numOfSSIDs = 1;
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "%s: bssType = %s, SSID specified = %s\n", __func__, "eCSR_BSS_TYPE_WDS_STA", convertBSSIDToSSID(btampContext->btamp_Remote_AMP_Assoc.HC_mac_addr));
vos_mem_zero(pProfile->SSIDs.SSIDList[0].SSID.ssId,
sizeof(pProfile->SSIDs.SSIDList[0].SSID.ssId));
vos_mem_copy(pProfile->SSIDs.SSIDList[0].SSID.ssId,
convertBSSIDToSSID(btampContext->btamp_Remote_AMP_Assoc.HC_mac_addr),
21); // Length of BTAMP SSID is 21 bytes
pProfile->SSIDs.SSIDList[0].SSID.length = 21;
//Set the BSSID to the Remote AP
pProfile->BSSIDs.numOfBSSIDs = 1;
vos_mem_copy(pProfile->BSSIDs.bssid,
btampContext->btamp_Remote_AMP_Assoc.HC_mac_addr,
sizeof( tCsrBssid ) );
}
//Always set the Auth Type
//pProfile->negotiatedAuthType = eCSR_AUTH_TYPE_RSN_PSK;
//pProfile->negotiatedAuthType = eCSR_AUTH_TYPE_NONE;
//pProfile->negotiatedAuthType = eCSR_AUTH_TYPE_OPEN_SYSTEM;
pProfile->AuthType.numEntries = 1;
//pProfile->AuthType.authType[0] = eCSR_AUTH_TYPE_OPEN_SYSTEM;
pProfile->AuthType.authType[0] = eCSR_AUTH_TYPE_RSN_PSK;
//Always set the Encryption Type
//pProfile->negotiatedUCEncryptionType = eCSR_ENCRYPT_TYPE_AES;
//pProfile->negotiatedUCEncryptionType = eCSR_ENCRYPT_TYPE_NONE;
pProfile->EncryptionType.numEntries = 1;
//pProfile->EncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_NONE;
pProfile->EncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_AES;
pProfile->mcEncryptionType.numEntries = 1;
//pProfile->mcEncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_NONE;
pProfile->mcEncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_AES;
//set the RSN IE
//This is weird, but it works
pProfile->pRSNReqIE = &btampRSNIE[0];
pProfile->nRSNReqIELength = 0x16; //TODO
//pProfile->pRSNReqIE = NULL;
/** We don't use the WPAIE.But NULL it to avoid being used **/
pProfile->pWPAReqIE = NULL;
pProfile->nWPAReqIELength = 0;
// Identify the operation channel
/* Choose the operation channel from the preferred channel list */
pProfile->operationChannel = 0;
regulatoryClass = 0;
for (triplet = 0; triplet < btampContext->btamp_Remote_AMP_Assoc.HC_pref_num_triplets; triplet++)
{
firstChannel = 0;
numChannels = 0;
/* is this a regulatory class triplet? */
if (btampContext->btamp_Remote_AMP_Assoc.HC_pref_triplets[triplet][0] == 201)
{
/* identify supported 2.4GHz regulatory classes */
switch (btampContext->btamp_Remote_AMP_Assoc.HC_pref_triplets[triplet][1])
{
case 254:
{
/* class 254 is special regulatory class defined by BT HS+3.0 spec that
is valid only for unknown/'mobile' country */
if ((btampContext->btamp_Remote_AMP_Assoc.HC_pref_country[0] == 'X') &&
(btampContext->btamp_Remote_AMP_Assoc.HC_pref_country[1] == 'X'))
{
regulatoryClass = 254;
firstChannel = 1;
numChannels = 11;
}
break;
}
case 12:
{
/* class 12 in the US regulatory domain is 2.4GHz channels 1-11 */
if ((btampContext->btamp_Remote_AMP_Assoc.HC_pref_country[0] == 'U') &&
(btampContext->btamp_Remote_AMP_Assoc.HC_pref_country[1] == 'S'))
{
regulatoryClass = 12;
firstChannel = 1;
numChannels = 11;
}
break;
}
case 4:
{
/* class 4 in the Europe regulatory domain is 2.4GHz channels 1-13 */
if ((btampContext->btamp_Remote_AMP_Assoc.HC_pref_country[0] == 'G') &&
(btampContext->btamp_Remote_AMP_Assoc.HC_pref_country[1] == 'B'))
{
regulatoryClass = 4;
firstChannel = 1;
numChannels = 13;
}
break;
}
case 30:
{
/* class 30 in the Japan regulatory domain is 2.4GHz channels 1-13 */
if ((btampContext->btamp_Remote_AMP_Assoc.HC_pref_country[0] == 'J') &&
(btampContext->btamp_Remote_AMP_Assoc.HC_pref_country[1] == 'P'))
{
regulatoryClass = 30;
firstChannel = 1;
numChannels = 13;
}
break;
}
default:
{
break;
}
}
/* if the next triplet is not another regulatory class triplet then it must be a sub-band
triplet. Skip processing the default channels for this regulatory class triplet and let
the sub-band triplet restrict the available channels */
if (((triplet+1) < btampContext->btamp_Remote_AMP_Assoc.HC_pref_num_triplets) &&
(btampContext->btamp_Remote_AMP_Assoc.HC_pref_triplets[triplet+1][0] != 201))
{
continue;
}
}
else
{
/* if the regulatory class is valid then this is a sub-band triplet */
if (regulatoryClass)
{
firstChannel = btampContext->btamp_Remote_AMP_Assoc.HC_pref_triplets[triplet][0];
numChannels = btampContext->btamp_Remote_AMP_Assoc.HC_pref_triplets[triplet][1];
}
}
if (firstChannel && numChannels)
{
if (!btampContext->btamp_AMP_Assoc.HC_pref_num_triplets)
{
pProfile->operationChannel = firstChannel;
break;
}
else if (((btampContext->btamp_AMP_Assoc.HC_pref_triplets[1][0] + btampContext->btamp_AMP_Assoc.HC_pref_triplets[1][1]) <= firstChannel) ||
((firstChannel + numChannels ) <= btampContext->btamp_AMP_Assoc.HC_pref_triplets[1][0]))
{
continue;
}
else if ((btampContext->btamp_AMP_Assoc.HC_pref_triplets[1][0] + btampContext->btamp_AMP_Assoc.HC_pref_triplets[1][1]) > firstChannel)
{
pProfile->operationChannel = firstChannel;
break;
}
else if ((firstChannel + numChannels) > btampContext->btamp_AMP_Assoc.HC_pref_triplets[1][0])
{
pProfile->operationChannel = btampContext->btamp_AMP_Assoc.HC_pref_triplets[1][0];
break;
}
}
}
if (!pProfile->operationChannel)
{
return VOS_STATUS_E_INVAL;
}
/*Set the selected channel */
sessionid = sme_GetInfraSessionId(hHal);
/*if there is infra session up already, use that channel only for BT AMP
connection, else we can use the user preferred one*/
if(-1 != sessionid)
{
pProfile->operationChannel =
sme_GetInfraOperationChannel(hHal,
sessionid);
}
if(sme_IsChannelValid(hHal, pProfile->operationChannel))
{
btampContext->channel = pProfile->operationChannel;
}
else
{
//no valid channel, not proceeding with connection
return VOS_STATUS_E_INVAL;
}
if ( BT_INITIATOR == btampContext->BAPDeviceRole )
{
pProfile->ChannelInfo.numOfChannels = 1;
pProfile->ChannelInfo.ChannelList = &pProfile->operationChannel;
}
else
{
pProfile->ChannelInfo.numOfChannels = 1;
pProfile->ChannelInfo.ChannelList = &pProfile->operationChannel;
}
// Turn off CB mode
pProfile->CBMode = eCSR_CB_OFF;
//set the phyMode to accept anything
//Taurus means everything because it covers all the things we support
pProfile->phyMode = eCSR_DOT11_MODE_11n; //eCSR_DOT11_MODE_TAURUS; //eCSR_DOT11_MODE_AUTO; /*eCSR_DOT11_MODE_BEST;*/
//set the mode in CFG as well
sme_CfgSetInt(hHal, WNI_CFG_DOT11_MODE, WNI_CFG_DOT11_MODE_11N, NULL, eANI_BOOLEAN_FALSE);
pProfile->bWPSAssociation = eANI_BOOLEAN_FALSE;
//Make sure we DON'T request UAPSD
pProfile->uapsd_mask = 0;
//return the vosStatus
return vosStatus;
} //convertToCsrProfile
VOS_STATUS
gotoStarting
(
ptBtampContext btampContext, /* btampContext value */
ptWLAN_BAPEvent bapEvent, /* State machine event */
eCsrRoamBssType bssType,
v_U8_t *status /* return the BT-AMP status here */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
eHalStatus halStatus;
v_U32_t parseStatus;
/* tHalHandle */
tHalHandle hHal;
tBtampTLVHCI_Write_Remote_AMP_ASSOC_Cmd *pBapHCIWriteRemoteAMPAssoc
= (tBtampTLVHCI_Write_Remote_AMP_ASSOC_Cmd *) bapEvent->params;
tBtampAMP_ASSOC btamp_ASSOC;
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
if (NULL == btampContext)
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"btampContext is NULL in %s", __func__);
return VOS_STATUS_E_FAULT;
}
hHal = VOS_GET_HAL_CB(btampContext->pvosGCtx);
if (NULL == hHal)
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"hHal is NULL in %s", __func__);
return VOS_STATUS_E_FAULT;
}
//If we are a BT-Responder, we are assuming we are a BT "slave" and we HAVE
//to "squelch" the slaves frequent (every 1.25ms) polls.
if (eCSR_BSS_TYPE_WDS_STA == bssType)
{
/* Sleep for 300(200) milliseconds - to allow BT through */
vos_sleep( 200 );
/* Signal BT Coexistence code in firmware to prefer WLAN */
WLANBAP_NeedBTCoexPriority ( btampContext, 1);
}
//Tell PMC to exit BMPS;
halStatus = pmcRequestFullPower(
hHal,
WLANBAP_pmcFullPwrReqCB,
btampContext,
eSME_REASON_OTHER);
// JEZ081210: This has to wait until we sync down from
// /main/latest as of 12/4. We are currently at 12/3.
//eSME_FULL_PWR_NEEDED_BY_BAP);
//Need to check the result...because Host may have been told by
//OS to go to standby (D2) device state. In that case, I have to
//fail the HCI Create Physical Link
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH,
"In %s, amp_assoc_remaining_length = %d", __func__,
pBapHCIWriteRemoteAMPAssoc->amp_assoc_remaining_length);
#if 0
DUMPLOG(1, __func__, "amp_assoc_fragment",
pBapHCIWriteRemoteAMPAssoc->amp_assoc_fragment,
64);
#endif //0
//What about parsing the AMP Assoc structure?
parseStatus = btampUnpackAMP_ASSOC(
hHal,
pBapHCIWriteRemoteAMPAssoc->amp_assoc_fragment,
pBapHCIWriteRemoteAMPAssoc->amp_assoc_remaining_length,
&btamp_ASSOC);
/* Unknown or Reserved TLVs are allowed in the write AMP assoc fragment */
if ((BTAMP_PARSE_SUCCESS != parseStatus ) && (BTAMP_UNKNOWN_TLVS != parseStatus))
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, parseStatus = %d", __func__, parseStatus);
*status = WLANBAP_ERROR_INVALID_HCI_CMND_PARAM;
return VOS_STATUS_E_BADMSG;
}
//What about writing the peer MAC address, and other info to the BTAMP
//context for this physical link?
if (btamp_ASSOC.AMP_Assoc_MAC_Addr.present == 1)
{
/* Save the peer MAC address */
vos_mem_copy(
btampContext->btamp_Remote_AMP_Assoc.HC_mac_addr,
btamp_ASSOC.AMP_Assoc_MAC_Addr.mac_addr,
sizeof(btampContext->btamp_Remote_AMP_Assoc.HC_mac_addr));
/* Save it in the peer MAC address field */
vos_mem_copy(
btampContext->peer_mac_addr,
btamp_ASSOC.AMP_Assoc_MAC_Addr.mac_addr,
sizeof(btampContext->peer_mac_addr));
}
if (btamp_ASSOC.AMP_Assoc_Preferred_Channel_List.present == 1)
{
/* Save the peer Preferred Channel List */
vos_mem_copy(
btampContext->btamp_Remote_AMP_Assoc.HC_pref_country,
btamp_ASSOC.AMP_Assoc_Preferred_Channel_List.country,
sizeof(btampContext->btamp_Remote_AMP_Assoc.HC_pref_country));
/* Save the peer Preferred Channel List */
btampContext->btamp_Remote_AMP_Assoc.HC_pref_num_triplets =
btamp_ASSOC.AMP_Assoc_Preferred_Channel_List.num_triplets;
if(WLANBAP_MAX_NUM_TRIPLETS <
btampContext->btamp_Remote_AMP_Assoc.HC_pref_num_triplets)
{
btampContext->btamp_Remote_AMP_Assoc.HC_pref_num_triplets =
WLANBAP_MAX_NUM_TRIPLETS;
}
vos_mem_copy(
btampContext->btamp_Remote_AMP_Assoc.HC_pref_triplets,
btamp_ASSOC.AMP_Assoc_Preferred_Channel_List.triplets,
sizeof(btampContext->btamp_Remote_AMP_Assoc.HC_pref_triplets[0]) *
btampContext->btamp_Remote_AMP_Assoc.HC_pref_num_triplets
);
}
if (btamp_ASSOC.AMP_Assoc_Connected_Channel.present == 1)
{
/* Save the peer Connected Channel */
vos_mem_copy(
btampContext->btamp_Remote_AMP_Assoc.HC_cnct_country,
btamp_ASSOC.AMP_Assoc_Connected_Channel.country,
sizeof(btampContext->btamp_Remote_AMP_Assoc.HC_cnct_country));
/* Save the peer Connected Channel */
btampContext->btamp_Remote_AMP_Assoc.HC_cnct_num_triplets =
btamp_ASSOC.AMP_Assoc_Connected_Channel.num_triplets;
if(WLANBAP_MAX_NUM_TRIPLETS <
btampContext->btamp_Remote_AMP_Assoc.HC_cnct_num_triplets)
{
btampContext->btamp_Remote_AMP_Assoc.HC_cnct_num_triplets =
WLANBAP_MAX_NUM_TRIPLETS;
}
vos_mem_copy(
btampContext->btamp_Remote_AMP_Assoc.HC_cnct_triplets,
btamp_ASSOC.AMP_Assoc_Connected_Channel.triplets,
sizeof(btampContext->btamp_Remote_AMP_Assoc.HC_cnct_triplets[0]) *
btampContext->btamp_Remote_AMP_Assoc.HC_cnct_num_triplets
);
}
if (btamp_ASSOC.AMP_Assoc_PAL_Capabilities.present == 1)
{
/* Save the peer PAL Capabilities */
btampContext->btamp_Remote_AMP_Assoc.HC_pal_capabilities
= btamp_ASSOC.AMP_Assoc_PAL_Capabilities.pal_capabilities;
}
if (btamp_ASSOC.AMP_Assoc_PAL_Version.present == 1)
{
/* Save the peer PAL Version */
btampContext->btamp_Remote_AMP_Assoc.HC_pal_version
= btamp_ASSOC.AMP_Assoc_PAL_Version.pal_version;
btampContext->btamp_Remote_AMP_Assoc.HC_pal_CompanyID
= btamp_ASSOC.AMP_Assoc_PAL_Version.pal_CompanyID;
btampContext->btamp_Remote_AMP_Assoc.HC_pal_subversion
= btamp_ASSOC.AMP_Assoc_PAL_Version.pal_subversion;
}
//Set Connection Accept Timeout;
/* Already done in gotoS1() */
//Set gNeedPhysLinkCompEvent;
//JEZ081114: This needs to happen earlier. In gotoS1. Right at HCI Create Physical Link
btampContext->gNeedPhysLinkCompEvent = VOS_TRUE;
//Clear gDiscRequested;
btampContext->gDiscRequested = VOS_FALSE;
//Set gPhysLinkStatus to 0 (no error);
btampContext->gPhysLinkStatus = WLANBAP_STATUS_SUCCESS;
//Set gDiscReason to 0 (no reason);
btampContext->gDiscReason = WLANBAP_STATUS_SUCCESS;
/* Initiate the link as either START or JOIN */
//halStatus = csrRoamOpenSession(&newSession);
/*Added by Luiza:*/
if (btampContext->isBapSessionOpen == FALSE)
{
halStatus = sme_OpenSession(hHal,
WLANBAP_RoamCallback,
btampContext,
// <=== JEZ081210: FIXME
//(tANI_U8 *) btampContext->self_mac_addr,
btampContext->self_mac_addr,
&btampContext->sessionId);
if(eHAL_STATUS_SUCCESS == halStatus)
{
btampContext->isBapSessionOpen = TRUE;
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"sme_OpenSession failed in %s", __func__);
*status = WLANBAP_ERROR_NO_CNCT;
return VOS_STATUS_E_FAILURE;
}
}
/* Update the SME Session info for this Phys Link (i.e., for this Phys State Machine instance) */
//bapUpdateSMESessionForThisPhysLink(newSession, PhysLinkHandle);
// Taken care of, above
//halStatus = csrRoamConnect(newSession, bssType);
// Final
vosStatus = convertToCsrProfile (
btampContext, /* btampContext value */
bssType,
&btampContext->csrRoamProfile); /* return the profile info here */
if(VOS_STATUS_E_INVAL == vosStatus)
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"Incorrect channel to create AMP link %s", __func__);
*status = WLANBAP_ERROR_NO_SUITABLE_CHANNEL;
return VOS_STATUS_E_INVAL;
}
#if 0
halStatus = sme_RoamConnect(VOS_GET_HAL_CB(btampContext->pvosGCtx),
&btampContext->csrRoamProfile,
NULL, /* tScanResultHandle hBssListIn, */
&btampContext->csrRoamId);
#endif //0
//#if 0
halStatus = sme_RoamConnect(hHal,
btampContext->sessionId,
&btampContext->csrRoamProfile,
&btampContext->csrRoamId);
//#endif //0
//Map the halStatus into a vosStatus
return vosStatus;
} //gotoStarting
VOS_STATUS
gotoConnecting(
ptBtampContext btampContext /* btampContext value */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
/* No longer needed. This call has been made in gotoStarting(). */
/* Signal BT Coexistence code in firmware to prefer WLAN */
WLANBAP_NeedBTCoexPriority ( btampContext, 1);
return vosStatus;
} //gotoConnecting
VOS_STATUS
gotoAuthenticating(
ptBtampContext btampContext /* btampContext value */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
/* Signal BT Coexistence code in firmware to prefer WLAN */
WLANBAP_NeedBTCoexPriority ( btampContext, 1);
return vosStatus;
} //gotoAuthenticating
#if 0
VOID initRsnSupplicant()
{
/* This is a NO-OP. The Supplicant waits for MSG 1 */
}
#endif /* 0 */
VOS_STATUS
initRsnSupplicant
(
ptBtampContext btampContext, /* btampContext value */
tWLAN_BAPRole BAPDeviceRole
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
/* This is a NO-OP. The Supplicant waits for MSG 1 */
/* Init RSN FSM */
if (!(suppRsnFsmCreate(btampContext)))
{
/* Send Start Event */
/* RSN_FSM_AUTH_START */
}
else
{
/* RSN Init Failed */
vosStatus = VOS_STATUS_E_FAILURE;
}
/* This is a NO-OP. The Supplicant waits for MSG 1 */
return vosStatus;
}
#if 0
VOID initRsnAuthenticator()
{
/* Signal the Authenticator/Supplicant App that we are associated. */
/* Use an IOCTL? That the app is hanging a read on? Or use a "special" data packet. Again, that the app is waiting on a receive for. */
}
#endif /* 0 */
VOS_STATUS
initRsnAuthenticator
(
ptBtampContext btampContext, /* btampContext value */
tWLAN_BAPRole BAPDeviceRole
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
/* Init RSN FSM */
if (!(authRsnFsmCreate(btampContext)))
{
/* Send Start Event */
}
else
{
/* RSN Init Failed */
vosStatus = VOS_STATUS_E_FAILURE;
}
return vosStatus;
/* Signal the Authenticator/Supplicant App that we are associated. */
/* Use an IOCTL? That the app is hanging a read on? Or use a "special" data packet. Again, that the app is waiting on a receive for. */
}
/* We have to register our STA with TL */
VOS_STATUS
regStaWithTl
(
ptBtampContext btampContext, /* btampContext value */
tWLAN_BAPRole BAPDeviceRole,
tCsrRoamInfo *pCsrRoamInfo
)
{
VOS_STATUS vosStatus;
WLAN_STADescType staDesc;
tANI_S8 rssi = 0;
vos_mem_zero(&staDesc, sizeof(WLAN_STADescType));
/* Fill in everything I know about the STA */
btampContext->ucSTAId = staDesc.ucSTAId = pCsrRoamInfo->staId;
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "BAP register TL ucSTAId=%d\n",
staDesc.ucSTAId );
/* Fill in the peer MAC address */
vos_mem_copy(
staDesc.vSTAMACAddress.bytes,
btampContext->peer_mac_addr,
sizeof(btampContext->peer_mac_addr));
/* Fill in the self MAC address */
vos_mem_copy(
staDesc.vSelfMACAddress.bytes,
btampContext->self_mac_addr,
sizeof(btampContext->peer_mac_addr));
/* Set the STA Type */
staDesc.wSTAType = WLAN_STA_BT_AMP;
// Set the QoS field appropriately, if the info available
if( pCsrRoamInfo->u.pConnectedProfile)
{
btampContext->bapQosCfg.bWmmIsEnabled = //1;
pCsrRoamInfo->u.pConnectedProfile->qosConnection;
}
else
{
btampContext->bapQosCfg.bWmmIsEnabled = 0;
}
// set the QoS field appropriately
if( btampContext->bapQosCfg.bWmmIsEnabled )
{
staDesc.ucQosEnabled = 1;
}
else
{
staDesc.ucQosEnabled = 0;
}
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "BAP register TL QoS_enabled=%d\n",
staDesc.ucQosEnabled );
// UMA is ready we inform TL not to do frame
// translation for WinMob 6.1
//*** Not to enabled UMA.
/* Enable UMA for TX translation only when there is no concurrent session active */
staDesc.ucSwFrameTXXlation = 1;
staDesc.ucSwFrameRXXlation = 1;
staDesc.ucAddRmvLLC = 0;
if ( btampContext->ucSecEnabled )
{
staDesc.ucProtectedFrame = 1;
}
else
{
staDesc.ucProtectedFrame = 0;
}
staDesc.ucUcastSig = pCsrRoamInfo->ucastSig;
staDesc.ucBcastSig = pCsrRoamInfo->bcastSig;
staDesc.ucInitState = ( btampContext->ucSecEnabled)?
WLANTL_STA_CONNECTED:WLANTL_STA_AUTHENTICATED;
staDesc.ucIsReplayCheckValid = VOS_FALSE;
if(NULL != pCsrRoamInfo->pBssDesc)
{
rssi = pCsrRoamInfo->pBssDesc->rssi;
}
/* register our STA with TL */
vosStatus = WLANTL_RegisterSTAClient
(
btampContext->pvosGCtx,
WLANBAP_STARxCB,
WLANBAP_TxCompCB,
(WLANTL_STAFetchPktCBType)WLANBAP_STAFetchPktCB,
&staDesc ,
rssi);
if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"%s: WLANTL_RegisterSTAClient() failed to register. Status= %d [0x%08X]",
__func__, vosStatus, vosStatus );
}
if ( ! btampContext->ucSecEnabled )
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_MED,
"open/shared auth StaId= %d. Changing TL state to AUTHENTICATED at Join time", btampContext->ucSTAId);
// Connections that do not need Upper layer auth, transition TL directly
// to 'Authenticated' state.
vosStatus = WLANTL_ChangeSTAState( btampContext->pvosGCtx, staDesc.ucSTAId,
WLANTL_STA_AUTHENTICATED );
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_MED,
"ULA auth StaId= %d. Changing TL state to CONNECTED at Join time", btampContext->ucSTAId );
vosStatus = WLANTL_ChangeSTAState( btampContext->pvosGCtx, staDesc.ucSTAId,
WLANTL_STA_CONNECTED );
}
return VOS_STATUS_SUCCESS;
} /* regStaWithTl */
#if 0
/*==========================================================================
FUNCTION: determineChan
DESCRIPTION: Return the current channel we are to operate on
============================================================================*/
#endif
VOS_STATUS
determineChan
(
ptBtampContext btampContext, /* btampContext value */
tWLAN_BAPRole BAPDeviceRole,
v_U32_t *channel, /* Current channel */
v_U8_t *status /* return the BT-AMP status here */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
v_U32_t activeFlag; /* Channel active flag */
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
switch(BAPDeviceRole)
{
case BT_INITIATOR:
/* if an Infra assoc already exists, return that channel. */
/* or use the results from the Scan to determine the least busy channel. How? */
/* For now, just do this. */
vosStatus = WLANBAP_GetCurrentChannel (btampContext, channel, &activeFlag);
break;
case BT_RESPONDER:
/* return the value obtained from the Preferred Channels field of the AMP Assoc structure from the BT-AMP peer (device A) */
/* No! I don't have that yet. */
/* For now, just do this. */
vosStatus = WLANBAP_GetCurrentChannel (btampContext, channel, &activeFlag);
break;
default:
*status = WLANBAP_ERROR_HOST_REJ_RESOURCES; /* return the BT-AMP status here */
return VOS_STATUS_E_RESOURCES;
}
*status = WLANBAP_STATUS_SUCCESS; /* return the BT-AMP status here */
return vosStatus;
} // determineChan
VOS_STATUS
gotoDisconnected
(
ptBtampContext btampContext /* btampContext value */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
//Is it legitimate to always make this call?
//What if pmcRequestFullPower wasn't called?
//Tell PMC to resume BMPS; /* Whatever the previous BMPS "state" was */
//Comment this out until such time as we have PMC support
//halStatus = pmcResumePower ( hHal);
/* Signal BT Coexistence code in firmware to no longer prefer WLAN */
WLANBAP_NeedBTCoexPriority ( btampContext, 0);
//Map the halStatus into a vosStatus
return vosStatus;
} // gotoDisconnected
VOS_STATUS
gotoDisconnecting
(
ptBtampContext btampContext, /* btampContext value */
v_U8_t needPhysLinkCompEvent,
v_U8_t physLinkStatus, /* BT-AMP disconnecting status */
// v_U8_t statusPresent, /* BT-AMP disconnecting status present */
v_U8_t discRequested,
v_U8_t discReason /* BT-AMP disconnecting reason */
)
{
// gNeedPhysLinkCompEvent
btampContext->gNeedPhysLinkCompEvent = needPhysLinkCompEvent;
// gPhysLinkStatus
btampContext->gPhysLinkStatus = physLinkStatus; /* BT-AMP disconnecting status */
// gDiscRequested
btampContext->gDiscRequested = discRequested;
// gDiscReason
btampContext->gDiscReason = discReason; /* BT-AMP disconnecting reason */
//WLANBAP_DeInitLinkSupervision( btampHandle);
//WLANBAP_StopLinkSupervisionTimer(btampContext);
/* Inform user space that no AMP channel is in use, for AFH purposes */
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_LOW,
"Calling send_btc_nlink_msg() with AMP channel = 0");
send_btc_nlink_msg(WLAN_AMP_ASSOC_DONE_IND, 0);
return VOS_STATUS_SUCCESS;
} //gotoDisconnecting
VOS_STATUS
gotoConnected
(
ptBtampContext btampContext /* btampContext value */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
ptBtampHandle btampHandle = ( ptBtampHandle)btampContext;
//#if 0
/* Stop the Connection Accept Timer */
vosStatus = WLANBAP_StopConnectionAcceptTimer (btampContext);
//#endif
///*De-initialize the timer */
//vosStatus = WLANBAP_DeinitConnectionAcceptTimer(btampContext);
/* Signal BT Coex in firmware to now honor only priority BT requests */
WLANBAP_NeedBTCoexPriority ( btampContext, 2);
// If required after successful Upper layer auth, transition TL
// to 'Authenticated' state.
if ( btampContext->ucSecEnabled )
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_MED,
"open/shared auth StaId= %d. Changing TL state to AUTHENTICATED at Join time", btampContext->ucSTAId);
vosStatus = WLANTL_ChangeSTAState(
btampContext->pvosGCtx,
btampContext->ucSTAId,
WLANTL_STA_AUTHENTICATED );
}
btampContext->dataPktPending = VOS_FALSE;
vosStatus = WLANBAP_InitLinkSupervision( btampHandle);
/* Inform user space of the AMP channel selected, for AFH purposes */
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_LOW,
"Calling send_btc_nlink_msg() with AMP channel %d", btampContext->channel);
send_btc_nlink_msg(WLAN_AMP_ASSOC_DONE_IND, btampContext->channel);
return vosStatus;
} //gotoConnected
/* the HCI Event signalling routine*/
VOS_STATUS
signalHCIPhysLinkCompEvent
(
ptBtampContext btampContext, /* btampContext value */
v_U8_t status /* the BT-AMP status */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
tBtampHCI_Event bapHCIEvent; /* This now encodes ALL event types */
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
/* Format the Physical Link Complete event to return... */
bapHCIEvent.bapHCIEventCode = BTAMP_TLV_HCI_PHYSICAL_LINK_COMPLETE_EVENT;
bapHCIEvent.u.btampPhysicalLinkCompleteEvent.present = 1;
bapHCIEvent.u.btampPhysicalLinkCompleteEvent.status = status;
bapHCIEvent.u.btampPhysicalLinkCompleteEvent.phy_link_handle
= btampContext->phy_link_handle;
bapHCIEvent.u.btampPhysicalLinkCompleteEvent.ch_number
= btampContext->channel;
if(WLANBAP_STATUS_SUCCESS == status)
{
/* Start the Tx packet monitoring timer */
WLANBAP_StartTxPacketMonitorTimer(btampContext);
}
else
{ //reset the PL handle
btampContext->phy_link_handle = 0;
}
vosStatus = (*btampContext->pBapHCIEventCB)
(
btampContext->pHddHdl, /* this refers the BSL per application context */
&bapHCIEvent, /* This now encodes ALL event types */
VOS_TRUE /* Flag to indicate assoc-specific event */
);
return vosStatus;
} /* signalHCIPhysLinkCompEvent */
/* the HCI Disconnect Complete Event signalling routine*/
VOS_STATUS
signalHCIPhysLinkDiscEvent
(
ptBtampContext btampContext, /* btampContext value */
v_U8_t status, /* the BT-AMP status */
v_U8_t reason /* the BT-AMP reason code */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
tBtampHCI_Event bapHCIEvent; /* This now encodes ALL event types */
v_U8_t i;
tpBtampLogLinkCtx pLogLinkContext = NULL;
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
#ifdef BAP_DEBUG
/* Trace the tBtampCtx being passed in. */
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH,
"WLAN BAP Context Monitor: btampContext value = %pK in %s:%d", btampContext, __func__, __LINE__ );
#endif //BAP_DEBUG
/* Loop disconnecting all Logical Links on this Physical Link */
for (i = 0 ; i < WLANBAP_MAX_LOG_LINKS; i++)
{
pLogLinkContext = &(btampContext->btampLogLinkCtx[i]);
if (pLogLinkContext->present == VOS_TRUE)
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"WLAN BAP: Deleting logical link entry %d in %s", i,
__func__);
/* Mark this Logical Link index value as free */
pLogLinkContext->present = VOS_FALSE;
// signalHCIDiscLogLink(status = SUCCESS, reason = CONNECTION_TERM_BY_REMOTE_HOST);
signalHCIDiscLogLinkCompEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
i, // logical link
// I don't know how to signal CONNECTION_TERM_BY_REMOTE_HOST
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
}
}
/*Reset current_log_link_index and total_log_link_index values*/
btampContext->current_log_link_index = 0;
btampContext->total_log_link_index = 0;
/* Format the Physical Link Disconnect Complete event to return... */
bapHCIEvent.bapHCIEventCode = BTAMP_TLV_HCI_DISCONNECT_PHYSICAL_LINK_COMPLETE_EVENT;
bapHCIEvent.u.btampDisconnectPhysicalLinkCompleteEvent.present = 1;
bapHCIEvent.u.btampDisconnectPhysicalLinkCompleteEvent.status = status;
bapHCIEvent.u.btampDisconnectPhysicalLinkCompleteEvent.reason = reason;//uncommented to debug
bapHCIEvent.u.btampDisconnectPhysicalLinkCompleteEvent.phy_link_handle
= btampContext->phy_link_handle;
/* Stop the Tx packet monitoring timer */
WLANBAP_StopTxPacketMonitorTimer(btampContext);
/*Need to clean up the phy link handle as we are disconnected at this
point
?? - do we need to do any more cleanup on this*/
btampContext->phy_link_handle = 0;
vosStatus = (*btampContext->pBapHCIEventCB)
(
btampContext->pHddHdl, /* this refers the BSL per application context */
&bapHCIEvent, /* This now encodes ALL event types */
VOS_TRUE /* Flag to indicate assoc-specific event */
);
return vosStatus;
} /* signalHCIPhysLinkDiscEvent */
/* the HCI Channel Select Event signalling routine*/
VOS_STATUS
signalHCIChanSelEvent
(
ptBtampContext btampContext /* btampContext value */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
tBtampHCI_Event bapHCIEvent; /* This now encodes ALL event types */
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
/* Format the Physical Link Disconnect Complete event to return... */
bapHCIEvent.bapHCIEventCode = BTAMP_TLV_HCI_CHANNEL_SELECTED_EVENT;
bapHCIEvent.u.btampChannelSelectedEvent.present = 1;
bapHCIEvent.u.btampChannelSelectedEvent.phy_link_handle
= btampContext->phy_link_handle;
vosStatus = (*btampContext->pBapHCIEventCB)
(
btampContext->pHddHdl, /* this refers the BSL per application context */
&bapHCIEvent, /* This now encodes ALL event types */
VOS_TRUE /* Flag to indicate assoc-specific event */
);
return vosStatus;
} /* signalHCIChanSelEvent */
/* the HCI Disconnect Logical Link Complete Event signalling routine*/
VOS_STATUS
signalHCIDiscLogLinkCompEvent
(
ptBtampContext btampContext, /* btampContext value */
v_U8_t status, /* the BT-AMP status */
v_U16_t log_link_handle, /* The Logical Link that disconnected*/
v_U8_t reason /* the BT-AMP reason code */
)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
tBtampHCI_Event bapHCIEvent; /* This now encodes ALL event types */
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
/* Format the Logical Link Disconnect Complete event to return... */
bapHCIEvent.bapHCIEventCode = BTAMP_TLV_HCI_DISCONNECT_LOGICAL_LINK_COMPLETE_EVENT;
bapHCIEvent.u.btampDisconnectLogicalLinkCompleteEvent.present = 1;
bapHCIEvent.u.btampDisconnectLogicalLinkCompleteEvent.status = status;
bapHCIEvent.u.btampDisconnectLogicalLinkCompleteEvent.reason = reason;
bapHCIEvent.u.btampDisconnectLogicalLinkCompleteEvent.log_link_handle
= (log_link_handle << 8) + btampContext->phy_link_handle;
vosStatus = (*btampContext->pBapHCIEventCB)
(
btampContext->pHddHdl, /* this refers the BSL per application context */
&bapHCIEvent, /* This now encodes ALL event types */
VOS_TRUE /* Flag to indicate assoc-specific event */
);
return vosStatus;
} /* signalHCIDiscLogLinkCompEvent */
// These are needed to recognize RSN suite types
#define WLANBAP_RSN_OUI_SIZE 4
tANI_U8 pRSNOui00[ WLANBAP_RSN_OUI_SIZE ] = { 0x00, 0x0F, 0xAC, 0x00 }; // group cipher
tANI_U8 pRSNOui01[ WLANBAP_RSN_OUI_SIZE ] = { 0x00, 0x0F, 0xAC, 0x01 }; // WEP-40 or RSN
tANI_U8 pRSNOui02[ WLANBAP_RSN_OUI_SIZE ] = { 0x00, 0x0F, 0xAC, 0x02 }; // TKIP or RSN-PSK
tANI_U8 pRSNOui03[ WLANBAP_RSN_OUI_SIZE ] = { 0x00, 0x0F, 0xAC, 0x03 }; // Reserved
tANI_U8 pRSNOui04[ WLANBAP_RSN_OUI_SIZE ] = { 0x00, 0x0F, 0xAC, 0x04 }; // AES-CCMP
tANI_U8 pRSNOui05[ WLANBAP_RSN_OUI_SIZE ] = { 0x00, 0x0F, 0xAC, 0x05 }; // WEP-104
/* Incoming Association indication validation predicate */
v_U32_t
validAssocInd
(
ptBtampContext btampContext, /* btampContext value */
tCsrRoamInfo *pRoamInfo
)
{
/* tHalHandle */
tHalHandle hHal = VOS_GET_HAL_CB(btampContext->pvosGCtx);
v_U32_t ieLen;
/* For now, always return true */
return VOS_TRUE;
/* Check for a valid peer MAC address */
/* For an incoming Assoc Indication, the peer MAC address
* should match the value that the BlueTooth AMP
* configured us with.
*/
if ( !vos_mem_compare( btampContext->peer_mac_addr,
pRoamInfo->peerMac,
sizeof(btampContext->peer_mac_addr) ))
{
/* Return not valid */
return VOS_FALSE;
}
/* JEZ081115: For now, ignore the RSN IE */
/* Otherwise, it is valid */
return VOS_TRUE;
/* Check for a trivial case: IEs missing */
if( pRoamInfo->prsnIE == NULL )
{
//btampContext->ieFields = NULL;
//btampContext->ieLen = 0;
/* Return not valid */
return VOS_FALSE;
}
//btampContext->ieLen = GET_IE_LEN_IN_BSS( pBssDesc->length );
//ieLen = GET_IE_LEN_IN_BSS( pBssDesc->length );
ieLen = pRoamInfo->rsnIELen;
/* Check for a trivial case: IEs zero length */
//if( btampContext->ieLen == 0 )
if( ieLen == 0 )
{
//btampContext->ieFields = NULL;
//btampContext->ieLen = 0;
/* Return not valid */
return VOS_FALSE;
}
{
// --- Start of block ---
tDot11fBeaconIEs dot11BeaconIEs;
tDot11fIESSID *pDot11SSID;
tDot11fIERSN *pDot11RSN;
// JEZ081215: This really needs to be updated to just validate the RSN IE.
// Validating the SSID can be done directly from...
// "Unpack" really wants tpAniSirGlobal (pMac) as its first param.
// But since it isn't used, I just pass in some arbitrary "context" pointer.
// So hHalHandle will make it happy.
dot11fUnpackBeaconIEs((tpAniSirGlobal) hHal,
(tANI_U8 *) pRoamInfo->prsnIE,
ieLen,
&dot11BeaconIEs);
//DUMPLOG(9, __func__, "dot11BeaconIEs", &dot11BeaconIEs, 64);
pDot11SSID = &dot11BeaconIEs.SSID;
// Assume there wasn't an SSID in the Assoc Request
btampContext->assocSsidLen = 0;
if (pDot11SSID->present )
{
//DUMPLOG(10, __func__, "pDot11SSID present", pDot11SSID, 64);
btampContext->assocSsidLen = pDot11SSID->num_ssid;
vos_mem_copy(btampContext->assocSsid,
pDot11SSID->ssid,
btampContext->assocSsidLen );
}
else
return VOS_FALSE;
// Check the validity of the SSID against our SSID value
if ( !vos_mem_compare( btampContext->ownSsid,
pDot11SSID->ssid,
btampContext->ownSsidLen ))
{
/* Return not valid */
return VOS_FALSE;
}
pDot11RSN = &dot11BeaconIEs.RSN;
// Assume there wasn't an RSN IE in the Assoc Request
//btampContext->assocRsnIeLen = 0;
if (pDot11RSN->present )
{
//DUMPLOG(10, __func__, "pDot11RSN present", pDot11RSN, 64);
//The 802.11 BT-AMP PAL only supports WPA2-PSK
if (!vos_mem_compare(pRSNOui02,// RSN-PSK
pDot11RSN->akm_suite[0],
WLANBAP_RSN_OUI_SIZE))
return VOS_FALSE;
//The 802.11 BT-AMP PAL only supports AES-CCMP Unicast
if (!vos_mem_compare(pRSNOui04, // AES-CCMP
pDot11RSN->pwise_cipher_suites[0],
WLANBAP_RSN_OUI_SIZE))
return VOS_FALSE;
}
else
return VOS_FALSE;
} // --- End of block ---
/* Otherwise, it is valid */
return VOS_TRUE;
} /* validAssocInd */
/* the change state function*/
void
btampfsmChangeToState
(
BTAMPFSM_INSTANCEDATA_T *instance,
BTAMPFSM_STATES_T state
)
{
instance->stateVar = state;
//BTAMPFSM_ENTRY_FLAG_T disconnectedEntry;
}
/* Physical Link state machine function */
//int
VOS_STATUS
btampFsm
(
//BTAMPFSM_INSTANCEDATA_T *instanceVar
ptBtampContext btampContext, /* btampContext value */
// tBtampSessCtx *tpBtampSessCtx, /* btampContext value */
ptWLAN_BAPEvent bapEvent, /* State machine event */
v_U8_t *status /* return the BT-AMP status here */
)
{
/* Retrieve the phy link state machine structure
* from the btampContext value
*/
BTAMPFSM_INSTANCEDATA_T *instanceVar;
v_U32_t msg = bapEvent->event; /* State machine input event message */
v_U32_t channel; /* Current channel */
v_U32_t activeFlag; /* Channel active flag */
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
ptBtampHandle btampHandle = ( ptBtampHandle)btampContext;
v_U8_t ucSTAId; /* The StaId (used by TL, PE, and HAL) */
v_PVOID_t pHddHdl; /* Handle to return BSL context in */
tHalHandle hHal = NULL;
/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
/* Validate params */
if (btampHandle == NULL)
{
return VOS_STATUS_E_FAULT;
}
instanceVar = &(btampContext->bapPhysLinkMachine);
hHal = VOS_GET_HAL_CB(btampContext->pvosGCtx);
if (NULL == hHal)
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,
"hHal is NULL in %s", __func__);
return VOS_STATUS_E_FAULT;
}
#define CHANNEL_NOT_SELECTED (WLANBAP_GetCurrentChannel (btampContext, &channel, &activeFlag) != VOS_STATUS_SUCCESS)
/*Initialize BTAMP PAL status code being returned to the btampFsm caller */
*status = WLANBAP_STATUS_SUCCESS;
switch(instanceVar->stateVar)
{
case DISCONNECTED:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_CREATE))
{
/*Transition from DISCONNECTED to S1 (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "DISCONNECTED", "S1");
#if 0
/* This will have issues in multisession. Need not close the session */
/* TODO : Need to have better handling */
if(btampContext->isBapSessionOpen == TRUE)//We want to close only BT-AMP Session
{
sme_CloseSession(VOS_GET_HAL_CB(btampContext->pvosGCtx),
btampContext->sessionId);
/*Added by Luiza:*/
btampContext->isBapSessionOpen = FALSE;
}
#endif
/* Set BAP device role */
vosStatus = gotoS1( btampContext, bapEvent, BT_INITIATOR, status);
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, cmd status is %d", __func__, *status);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,S1);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_ACCEPT))
{
/*Transition from DISCONNECTED to S1 (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "DISCONNECTED", "S1");
#if 0
if(btampContext->isBapSessionOpen == TRUE)
{
sme_CloseSession(VOS_GET_HAL_CB(btampContext->pvosGCtx),
btampContext->sessionId);
/*Added by Luiza:*/
btampContext->isBapSessionOpen = FALSE;
}
/*Action code for transition */
#endif
/* Set BAP device role */
vosStatus = gotoS1(btampContext, bapEvent, BT_RESPONDER, status);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,S1);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "DISCONNECTED", msg);
/* Intentionally left blank */
}
break;
case S1:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_WRITE_REMOTE_AMP_ASSOC
) && (btampContext->BAPDeviceRole == BT_INITIATOR && !(CHANNEL_NOT_SELECTED)))
{
/*Transition from S1 to STARTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "S1", "STARTING");
/*Action code for transition */
vosStatus = determineChan(btampContext, BT_INITIATOR, &channel, status);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,STARTING);
// This has to be commented out until I get the BT-AMP SME/CSR changes
vosStatus = gotoStarting( btampContext, bapEvent, eCSR_BSS_TYPE_WDS_AP, status);
if (VOS_STATUS_SUCCESS != vosStatus)
{
btampfsmChangeToState(instanceVar, S1);
}
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_TIMER_CONNECT_ACCEPT_TIMEOUT))
{
/*Transition from S1 to DISCONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "S1", "DISCONNECTED");
/*Action code for transition */
/* Set everything back as dis-connected */
gotoDisconnected( btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTED);
/*Signal the disconnect */
signalHCIPhysLinkCompEvent( btampContext, WLANBAP_ERROR_HOST_TIMEOUT);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_DISCONNECT))
{
/*Transition from S1 to DISCONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "S1", "DISCONNECTED");
/*Action code for transition */
gotoDisconnected(btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTED);
/*Signal the successful physical link disconnect */
signalHCIPhysLinkDiscEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
/*Signal the unsuccessful physical link creation */
signalHCIPhysLinkCompEvent( btampContext, WLANBAP_ERROR_NO_CNCT );
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_WRITE_REMOTE_AMP_ASSOC
) && (btampContext->BAPDeviceRole == BT_RESPONDER))
{
/*Transition from S1 to STARTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "S1", "STARTING");
/*Action code for transition */
//determineChan(BT_RESPONDER);
vosStatus = determineChan(btampContext, BT_RESPONDER, &channel, status);
btampfsmChangeToState(instanceVar,STARTING);//Moved to here to debug
// This has to be commented out until I get the BT-AMP SME/CSR changes
/*Advance outer statevar */
// btampfsmChangeToState(instanceVar,STARTING);
vosStatus = gotoStarting( btampContext, bapEvent, eCSR_BSS_TYPE_WDS_STA, status);
if (VOS_STATUS_SUCCESS != vosStatus)
{
btampfsmChangeToState(instanceVar, S1);
}
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_WRITE_REMOTE_AMP_ASSOC
) && (btampContext->BAPDeviceRole == BT_INITIATOR && CHANNEL_NOT_SELECTED))
{
/*Transition from S1 to SCANNING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "S1", "SCANNING");
/*Action code for transition */
gotoScanning(btampContext, BT_RESPONDER, status);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,SCANNING);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "S1", msg);
/* Intentionally left blank */
}
break;
case STARTING:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_START_BSS_SUCCESS
) && (btampContext->BAPDeviceRole == BT_INITIATOR))
{
/*Transition from STARTING to CONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "STARTING", "CONNECTING");
btampfsmChangeToState(instanceVar,CONNECTING);//Moved to debug
/*Set the selected channel */
/*should have been already set */
btampContext->channel = ( 0 == btampContext->channel )?1:btampContext->channel;
/*Action code for transition */
signalHCIChanSelEvent(btampContext);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_DISCONNECT))
{
/*Transition from STARTING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "STARTING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
// Danlin, where are the richer reason codes?
// I want to be able to convey everything 802.11 supports...
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_NO_CNCT,
//VOS_TRUE, // Should be VOS_FALSE !!!
VOS_FALSE,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
// It is NOT clear that we need to send the Phy Link Disconnect
// Complete Event here.
signalHCIPhysLinkDiscEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_CHANNEL_SELECTION_FAILED))
{
/*Transition from STARTING to DISCONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "STARTING", "DISCONNECTED");
gotoDisconnected(btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTED);
/*Action code for transition */
signalHCIPhysLinkCompEvent( btampContext, WLANBAP_ERROR_HOST_REJ_RESOURCES );
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_START_BSS_SUCCESS
) && (btampContext->BAPDeviceRole == BT_RESPONDER))
{
/*Transition from STARTING to CONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "STARTING", "CONNECTING");
/* Set the selected channel */
/*should have been already set */
btampContext->channel = ( 0 == btampContext->channel )?1:btampContext->channel;
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,CONNECTING);
/*Action code for transition */
gotoConnecting(btampContext);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_TIMER_CONNECT_ACCEPT_TIMEOUT))
{
/*Transition from STARTING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "STARTING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_HOST_TIMEOUT,
VOS_FALSE,
0);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_START_FAILS))
{
/*Transition from STARTING to DISCONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "STARTING", "DISCONNECTED");
/*Action code for transition */
gotoDisconnected(btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTED);
signalHCIPhysLinkCompEvent( btampContext, WLANBAP_ERROR_MAX_NUM_CNCTS );
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "STARTING", msg);
/* Intentionally left blank */
}
break;
case CONNECTING:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_CONNECT_COMPLETED
) && (btampContext->BAPDeviceRole == BT_RESPONDER))
{
/*Transition from CONNECTING to AUTHENTICATING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "AUTHENTICATING");
//VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "CONNECTED");
gotoAuthenticating(btampContext);
/*Action code for transition */
initRsnSupplicant(btampContext, BT_RESPONDER);
#if 1
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,AUTHENTICATING);
#else
/*Action code for transition */
signalHCIPhysLinkCompEvent(btampContext, WLANBAP_STATUS_SUCCESS);
gotoConnected(btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,CONNECTED);
#endif
/* register our STA with TL */
regStaWithTl (
btampContext, /* btampContext value */
BT_RESPONDER,
(tCsrRoamInfo *)bapEvent->params);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_DISCONNECT))
{
/*Transition from CONNECTING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_NO_CNCT,
//VOS_TRUE, // Should be VOS_FALSE !!!
VOS_FALSE,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
// It is NOT clear that we need to send the Phy Link Disconnect
// Complete Event here.
signalHCIPhysLinkDiscEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_CONNECT_INDICATION
//) && (bssDesc indicates an invalid peer MAC Addr or SecParam)){
) && !validAssocInd(btampContext, (tCsrRoamInfo *)bapEvent->params))
{
/*Transition from CONNECTING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect(DEAUTH);
//JEZ081120: Danlin points out that I could just ignore this
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_DEAUTH);
//eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_AUTHENT_FAILURE,
VOS_FALSE,
0);
/*Set the status code being returned to the btampFsm caller */
*status = WLANBAP_ERROR_AUTHENT_FAILURE;
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_CONNECT_INDICATION
//) && (bssDesc indicates a valid MAC Addr and SecParam)){
) && validAssocInd(btampContext, (tCsrRoamInfo *)bapEvent->params))
{
/*Transition from CONNECTING to VALIDATED (both without substates)*/
//VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "VALIDATED");
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "AUTHENTICATING");
//VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "CONNECTED");
/*Action code for transition */
// JEZ081027: This one is a pain. Since we are responding in the
// callback itself. This messes up my state machine.
//csrRoamAccept();
// No! This is fine.
/*Set the status code being returned to the btampFsm caller */
*status = WLANBAP_STATUS_SUCCESS;
/* JEZ081215: N.B.: Currently, I don't get the
* eCSR_ROAM_RESULT_WDS_ASSOCIATED as an AP.
* So, I have to register with TL, here. This
* seems weird.
*/
/* register our STA with TL */
regStaWithTl (
btampContext, /* btampContext value */
BT_INITIATOR,
(tCsrRoamInfo *)bapEvent->params );
gotoAuthenticating(btampContext);
/*Action code for transition */
initRsnAuthenticator(btampContext, BT_INITIATOR);
#if 1
/*Advance outer statevar */
//btampfsmChangeToState(instanceVar,VALIDATED);
btampfsmChangeToState(instanceVar,AUTHENTICATING);
#else
/*Action code for transition */
signalHCIPhysLinkCompEvent(btampContext, WLANBAP_STATUS_SUCCESS);
gotoConnected(btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,CONNECTED);
#endif
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_CONNECT_FAILED))
{
/*Transition from CONNECTING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "DISCONNECTING");
/*Action code for transition */
sme_RoamDisconnect(hHal,
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
/* Section 3.1.8 and section 3.1.9 have contradictory semantics for 0x16.
* 3.1.8 is "connection terminated by local host". 3.1.9 is "failed connection".
*/
//gotoDisconnecting(FAILED_CONNECTION);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST, //FAILED_CONNECTION
VOS_FALSE,
0);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_TIMER_CONNECT_ACCEPT_TIMEOUT))
{
/*Transition from CONNECTING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_HOST_TIMEOUT,
VOS_FALSE,
0);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "CONNECTING", msg);
/* Intentionally left blank */
}
break;
case AUTHENTICATING:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_RSN_SUCCESS
) && (btampContext->BAPDeviceRole == BT_RESPONDER))
{
/*Transition from AUTHENTICATING to KEYING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "AUTHENTICATING", "KEYING");
/*Action code for transition */
//sme_RoamSetContext();
#if 0
sme_RoamSetKey(
VOS_GET_HAL_CB(btampContext->pvosGCtx),
btampContext->sessionId,
tSirMacAddr peerBssId,
eCsrEncryptionType encryptType,
tANI_U16 keyLength,
tANI_U8 *pKey,
VOS_TRUE, // TRUE
tANI_U8 paeRole);
#endif //0
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,KEYING);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_RSN_SUCCESS
) && (btampContext->BAPDeviceRole == BT_INITIATOR))
{
/*Transition from AUTHENTICATING to KEYING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "AUTHENTICATING", "KEYING");
/*Action code for transition */
//sme_RoamSetContext();
#if 0
sme_RoamSetKey(
VOS_GET_HAL_CB(btampContext->pvosGCtx),
btampContext->sessionId,
tSirMacAddr peerBssId,
eCsrEncryptionType encryptType,
tANI_U16 keyLength,
tANI_U8 *pKey,
VOS_TRUE, // TRUE
tANI_U8 paeRole);
#endif //0
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,KEYING);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_TIMER_CONNECT_ACCEPT_TIMEOUT))
{
/*Transition from AUTHENTICATING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s ConnectAcceptTimeout", __func__, "AUTHENTICATING", "DISCONNECTING");
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_HOST_TIMEOUT,
VOS_FALSE,
0);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
/*Action code for transition */
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_DISCONNECT))
{
/*Transition from AUTHENTICATING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s Physicallink Disconnect", __func__, "AUTHENTICATING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_NO_CNCT,
//VOS_TRUE, // Should be VOS_FALSE !!!
VOS_FALSE,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
// It is NOT clear that we need to send the Phy Link Disconnect
// Complete Event here.
signalHCIPhysLinkDiscEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_RSN_FAILURE))
{
/*Transition from AUTHENTICATING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s RSN Failure", __func__, "AUTHENTICATING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect(DEAUTH);
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_DEAUTH);
//eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_AUTHENT_FAILURE,
VOS_FALSE,
0);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "AUTHENTICATING", msg);
/* Intentionally left blank */
}
break;
case CONNECTED:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_DISCONNECT))
{
/*Transition from CONNECTED to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTED", "DISCONNECTING");
gotoDisconnecting(
btampContext,
VOS_FALSE,
0,
VOS_TRUE,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
WLANBAP_DeInitLinkSupervision(( ptBtampHandle)btampContext);
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_INDICATES_MEDIA_DISCONNECTION))
{
/*Transition from CONNECTED to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "CONNECTED", "DISCONNECTING");
WLANBAP_DeInitLinkSupervision(( ptBtampHandle)btampContext);
gotoDisconnecting(
btampContext,
VOS_FALSE,
0,
VOS_TRUE,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
/*Action code for transition */
sme_RoamDisconnect(hHal,
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "CONNECTED", msg);
/* Intentionally left blank */
}
break;
/* JEZ081107: This will only work if I have already signalled the disconnect complete
* event in every case where a physical link complete event is required. And a
* disconnect was requested.
* - - -
* And only if I check for gNeedPhysLinkCompEvent BEFORE I check gDiscRequested.
* Naw! Not necessary.
*/
case DISCONNECTING:
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, Entered DISCONNECTING:", __func__);//Debug statement
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_READY_FOR_CONNECTIONS
) && (btampContext->gDiscRequested == VOS_TRUE))
{
/*Transition from DISCONNECTING to DISCONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "DISCONNECTING", "DISCONNECTED");
//Clear gDiscRequested;
btampContext->gDiscRequested = VOS_FALSE;
if(btampContext->BAPDeviceRole == BT_INITIATOR)
{
if(!VOS_IS_STATUS_SUCCESS(vos_lock_acquire(&btampContext->bapLock)))
{
VOS_TRACE(VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,"btampFsm, Get LOCK Fail");
}
authRsnFsmFree(btampContext);
if(!VOS_IS_STATUS_SUCCESS(vos_lock_release(&btampContext->bapLock)))
{
VOS_TRACE(VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,"btampFsm, Release LOCK Fail");
}
}
else if(btampContext->BAPDeviceRole == BT_RESPONDER)
{
suppRsnFsmFree(btampContext);
}
/* Lookup the StaId using the phy_link_handle and the BAP context */
vosStatus = WLANBAP_GetStaIdFromLinkCtx (
btampHandle, /* btampHandle value in */
btampContext->phy_link_handle, /* phy_link_handle value in */
&ucSTAId, /* The StaId (used by TL, PE, and HAL) */
&pHddHdl); /* Handle to return BSL context */
if ( VOS_STATUS_SUCCESS != vosStatus )
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO,
"Unable to retrieve STA Id from BAP context and phy_link_handle in %s", __func__);
return VOS_STATUS_E_FAULT;
}
WLANTL_ClearSTAClient(btampContext->pvosGCtx, ucSTAId);
// gotoDisconnected(btampContext);
// VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "%s:In DISCONNECTING-changing outer state var to DISCONNECTED", __func__);
/*Advance outer statevar */
// btampfsmChangeToState(instanceVar,DISCONNECTED);
signalHCIPhysLinkDiscEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
btampContext->gDiscReason);
/*sme_CloseSession(VOS_GET_HAL_CB(btampContext->pvosGCtx),
btampContext->sessionId);*/
/*Action code for transition */
gotoDisconnected(btampContext);
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "%s:In DISCONNECTING-changing outer state var to DISCONNECTED", __func__);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTED);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_READY_FOR_CONNECTIONS
) && (btampContext->gNeedPhysLinkCompEvent == VOS_TRUE))
{
/*Transition from DISCONNECTING to DISCONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s gNeedPhysLinkComp TRUE", __func__, "DISCONNECTING", "DISCONNECTED");
if(btampContext->BAPDeviceRole == BT_INITIATOR)
{
if(!VOS_IS_STATUS_SUCCESS(vos_lock_acquire(&btampContext->bapLock)))
{
VOS_TRACE(VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,"btampFsm, Get LOCK Fail");
}
authRsnFsmFree(btampContext);
if(!VOS_IS_STATUS_SUCCESS(vos_lock_release(&btampContext->bapLock)))
{
VOS_TRACE(VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR,"btampFsm, Release LOCK Fail");
}
}
else if(btampContext->BAPDeviceRole == BT_RESPONDER)
{
suppRsnFsmFree(btampContext);
}
/* Lookup the StaId using the phy_link_handle and the BAP context */
vosStatus = WLANBAP_GetStaIdFromLinkCtx (
btampHandle, /* btampHandle value in */
btampContext->phy_link_handle, /* phy_link_handle value in */
&ucSTAId, /* The StaId (used by TL, PE, and HAL) */
&pHddHdl); /* Handle to return BSL context */
if ( VOS_STATUS_SUCCESS != vosStatus )
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO,
"Unable to retrieve STA Id from BAP context and phy_link_handle in %s", __func__);
return VOS_STATUS_E_FAULT;
}
WLANTL_ClearSTAClient(btampContext->pvosGCtx, ucSTAId);
/*Action code for transition */
// signalHCIPhysLinkCompEvent(btampContext, WLANBAP_ERROR_NO_CNCT/*btampContext->gPhysLinkStatus*/);
signalHCIPhysLinkCompEvent(btampContext, btampContext->gPhysLinkStatus);
gotoDisconnected(btampContext);
/*sme_CloseSession(VOS_GET_HAL_CB(btampContext->pvosGCtx),
btampContext->sessionId);*/
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTED);
// signalHCIPhysLinkCompEvent(btampContext, btampContext->gPhysLinkStatus);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "DISCONNECTING", msg);
/* Intentionally left blank */
}
break;
case KEYING:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_TIMER_CONNECT_ACCEPT_TIMEOUT))
{
/*Transition from KEYING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "KEYING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_HOST_TIMEOUT,
VOS_FALSE,
0);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_DISCONNECT))
{
/*Transition from KEYING to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "KEYING", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_NO_CNCT,
//VOS_TRUE, // Should be VOS_FALSE !!!
VOS_FALSE,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
// It is NOT clear that we need to send the Phy Link Disconnect
// Complete Event here.
signalHCIPhysLinkDiscEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_KEY_SET_SUCCESS))
{
/*Transition from KEYING to CONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "KEYING", "CONNECTED");
/*Action code for transition */
gotoConnected(btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,CONNECTED);
signalHCIPhysLinkCompEvent(btampContext, WLANBAP_STATUS_SUCCESS);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "KEYING", msg);
/* Intentionally left blank */
}
break;
case SCANNING:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_SCAN_COMPLETE))
{
/*Transition from SCANNING to STARTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "SCANNING", "STARTING");
/*Action code for transition */
vosStatus = determineChan(btampContext, BT_INITIATOR, &channel, status);
// This has to be commented out until I get the BT-AMP SME/CSR changes
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,STARTING);
vosStatus = gotoStarting( btampContext, bapEvent, eCSR_BSS_TYPE_WDS_AP, status);
if (VOS_STATUS_SUCCESS != vosStatus)
{
btampfsmChangeToState(instanceVar, SCANNING);
}
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_TIMER_CONNECT_ACCEPT_TIMEOUT))
{
/*Transition from SCANNING to DISCONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "SCANNING", "DISCONNECTED");
/*Action code for transition */
gotoDisconnected(btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTED);
signalHCIPhysLinkCompEvent( btampContext, WLANBAP_ERROR_HOST_TIMEOUT);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_DISCONNECT))
{
/*Transition from SCANNING to DISCONNECTED (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "SCANNING", "DISCONNECTED");
/*Action code for transition */
gotoDisconnected(btampContext);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTED);
signalHCIPhysLinkDiscEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
signalHCIPhysLinkCompEvent( btampContext, WLANBAP_ERROR_NO_CNCT);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "SCANNING", msg);
/* Intentionally left blank */
}
break;
case VALIDATED:
if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_MAC_CONNECT_COMPLETED
) && (btampContext->BAPDeviceRole == BT_INITIATOR))
{
/*Transition from VALIDATED to AUTHENTICATING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "VALIDATED", "AUTHENTICATING");
gotoAuthenticating(btampContext);
/*Action code for transition */
initRsnAuthenticator(btampContext, BT_INITIATOR);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,AUTHENTICATING);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_TIMER_CONNECT_ACCEPT_TIMEOUT))
{
/*Transition from VALIDATED to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "VALIDATED", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_HOST_TIMEOUT,
VOS_FALSE,
0);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
}
else if((msg==(BTAMPFSM_EVENT_T)eWLAN_BAP_HCI_PHYSICAL_LINK_DISCONNECT))
{
/*Transition from VALIDATED to DISCONNECTING (both without substates)*/
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, from state %s => %s", __func__, "VALIDATED", "DISCONNECTING");
/*Action code for transition */
//csrRoamDisconnect();
sme_RoamDisconnect(hHal,
//JEZ081115: Fixme
btampContext->sessionId,
eCSR_DISCONNECT_REASON_UNSPECIFIED);
gotoDisconnecting(
btampContext,
VOS_TRUE,
WLANBAP_ERROR_NO_CNCT,
//VOS_TRUE, // Should be VOS_FALSE !!!
VOS_FALSE,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
/*Advance outer statevar */
btampfsmChangeToState(instanceVar,DISCONNECTING);
// It is NOT clear that we need to send the Phy Link Disconnect
// Complete Event here.
signalHCIPhysLinkDiscEvent
( btampContext,
WLANBAP_STATUS_SUCCESS,
WLANBAP_ERROR_TERM_BY_LOCAL_HOST);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, in state %s, invalid event msg %d", __func__, "VALIDATED", msg);
/* Intentionally left blank */
}
break;
default:
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_INFO_HIGH, "In %s, invalid state %d", __func__, instanceVar->stateVar);
/*Intentionally left blank*/
break;
}
return vosStatus;
}
VOS_STATUS btampEstablishLogLink(ptBtampContext btampContext)
{
VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
vos_msg_t msg;
tAniBtAmpLogLinkReq *pMsg;
pMsg = vos_mem_malloc(sizeof(tAniBtAmpLogLinkReq));
if ( NULL == pMsg )
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR, "In %s, failed to allocate mem for req", __func__);
return VOS_STATUS_E_NOMEM;
}
pMsg->msgType = pal_cpu_to_be16((tANI_U16)eWNI_SME_BTAMP_LOG_LINK_IND);
pMsg->msgLen = (tANI_U16)sizeof(tAniBtAmpLogLinkReq);
pMsg->sessionId = btampContext->sessionId;
pMsg->btampHandle = btampContext;
msg.type = eWNI_SME_BTAMP_LOG_LINK_IND;
msg.bodyptr = pMsg;
msg.reserved = 0;
if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MQ_ID_SME, &msg))
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR, "In %s, failed to post msg to self", __func__);
vos_mem_free(pMsg);
vosStatus = VOS_STATUS_E_FAILURE;
}
return vosStatus;
}
void btampEstablishLogLinkHdlr(void* pMsg)
{
tAniBtAmpLogLinkReq *pBtAmpLogLinkReq = (tAniBtAmpLogLinkReq*)pMsg;
ptBtampContext btampContext;
if(pBtAmpLogLinkReq)
{
btampContext = (ptBtampContext)pBtAmpLogLinkReq->btampHandle;
if(NULL != btampContext)
{
vos_sleep( 200 );
WLAN_BAPEstablishLogicalLink(btampContext);
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR, "In %s, btampContext is NULL", __func__);
return;
}
}
else
{
VOS_TRACE( VOS_MODULE_ID_BAP, VOS_TRACE_LEVEL_ERROR, "In %s, pBtAmpLogLinkReq is NULL", __func__);
}
return;
}