prima: WLAN Driver Release 3.1.7.9

This is the initial release of the Prima WLAN Driver
diff --git a/CORE/SME/inc/btcApi.h b/CORE/SME/inc/btcApi.h
new file mode 100644
index 0000000..9cd2466
--- /dev/null
+++ b/CORE/SME/inc/btcApi.h
@@ -0,0 +1,347 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/******************************************************************************
+*
+* Name:  btcApi.h
+*
+* Description: BTC Events Layer API definitions.
+*
+* Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+* Qualcomm Confidential and Proprietary.
+*
+******************************************************************************/
+
+#ifndef __BTC_API_H__
+#define __BTC_API_H__
+
+#include "vos_types.h"
+#include "vos_timer.h"
+
+#define BT_INVALID_CONN_HANDLE (0xFFFF)  /**< Invalid connection handle */
+
+/* ACL and Sync connection attempt results */
+#define BT_CONN_STATUS_FAIL      (0)         /**< Connection failed */
+#define BT_CONN_STATUS_SUCCESS   (1)         /**< Connection successful */
+#define BT_CONN_STATUS_MAX       (2)         /**< This and beyond are invalid values */
+
+/** ACL and Sync link types
+  These must match the Bluetooth Spec!
+*/
+#define BT_SCO                  (0)   /**< SCO Link */
+#define BT_ACL                  (1)   /**< ACL Link */
+#define BT_eSCO                 (2)   /**< eSCO Link */
+#define BT_LINK_TYPE_MAX        (3)   /**< This value and higher are invalid */
+
+/** ACL link modes
+    These must match the Bluetooth Spec!
+*/
+#define BT_ACL_ACTIVE           (0)   /**< Active mode */
+#define BT_ACL_HOLD             (1)   /**< Hold mode */
+#define BT_ACL_SNIFF            (2)   /**< Sniff mode */
+#define BT_ACL_PARK             (3)   /**< Park mode */
+#define BT_ACL_MODE_MAX         (4)   /**< This value and higher are invalid */
+
+/**
+ * A2DP BTC max no of BT sub intervals
+ *
+ * **/
+#define BTC_MAX_NUM_ACL_BT_SUB_INTS (7)
+
+/** BTC Executions Modes allowed to be set by user
+*/
+#define BTC_SMART_COEXISTENCE   (0) /** BTC Mapping Layer decides whats best */
+#define BTC_WLAN_ONLY           (1) /** WLAN takes all mode */
+#define BTC_PTA_ONLY            (2) /** Allow only 3 wire protocol in H/W */
+#define BTC_SMART_MAX_WLAN      (3) /** BTC Mapping Layer decides whats best, WLAN weighted */
+#define BTC_SMART_MAX_BT        (4) /** BTC Mapping Layer decides whats best, BT weighted */
+#define BTC_SMART_BT_A2DP       (5) /** BTC Mapping Layer decides whats best, balanced + BT A2DP weight */
+#define BT_EXEC_MODE_MAX        (6) /** This and beyond are invalid values */
+
+/** Enumeration of different kinds actions that BTC Mapping Layer
+    can do if PM indication (to AP) fails.
+*/
+#define BTC_RESTART_CURRENT     (0) /** Restart the interval we just failed to leave */
+#define BTC_START_NEXT          (1) /** Start the next interval even though the PM transition at the AP was unsuccessful */
+#define BTC_ACTION_TYPE_MAX     (2) /** This and beyond are invalid values */
+
+#define BTC_BT_INTERVAL_MODE1_DEFAULT       (120) /** BT Interval in Mode 1 */
+#define BTC_WLAN_INTERVAL_MODE1_DEFAULT     (30)  /** WLAN Interval in Mode 1 */
+
+/** Bitmaps used for maintaining various BT events that requires
+    enough time to complete such that it might require disbling of
+    heartbeat monitoring to avoid WLAN link loss with the AP
+*/
+#define BT_INQUIRY_STARTED                  (1<<0)
+#define BT_PAGE_STARTED                     (1<<1)
+#define BT_CREATE_ACL_CONNECTION_STARTED    (1<<2)
+#define BT_CREATE_SYNC_CONNECTION_STARTED   (1<<3)
+
+/** Maximum time duration in milliseconds between a specific BT start event and its
+    respective stop event, before it can be declared timed out on receiving the stop event.
+*/
+#define BT_MAX_EVENT_DONE_TIMEOUT   45000
+
+
+/*
+    To suppurt multiple SCO connections for BT+UAPSD work
+*/
+#define BT_MAX_SCO_SUPPORT  3
+#define BT_MAX_ACL_SUPPORT  3
+#define BT_MAX_DISCONN_SUPPORT (BT_MAX_SCO_SUPPORT+BT_MAX_ACL_SUPPORT)
+#define BT_MAX_NUM_EVENT_ACL_DEFERRED  4  //We may need to defer these many BT events for ACL
+#define BT_MAX_NUM_EVENT_SCO_DEFERRED  4  //We may need to defer these many BT events for SYNC
+
+
+/** Enumeration of all the different kinds of BT events
+*/
+typedef enum eSmeBtEventType
+{
+  BT_EVENT_DEVICE_SWITCHED_ON,
+  BT_EVENT_DEVICE_SWITCHED_OFF,
+  BT_EVENT_INQUIRY_STARTED,
+  BT_EVENT_INQUIRY_STOPPED,
+  BT_EVENT_INQUIRY_SCAN_STARTED,
+  BT_EVENT_INQUIRY_SCAN_STOPPED,
+  BT_EVENT_PAGE_STARTED,
+  BT_EVENT_PAGE_STOPPED,
+  BT_EVENT_PAGE_SCAN_STARTED,
+  BT_EVENT_PAGE_SCAN_STOPPED,
+  BT_EVENT_CREATE_ACL_CONNECTION,
+  BT_EVENT_ACL_CONNECTION_COMPLETE,
+  BT_EVENT_CREATE_SYNC_CONNECTION,
+  BT_EVENT_SYNC_CONNECTION_COMPLETE,
+  BT_EVENT_SYNC_CONNECTION_UPDATED,
+  BT_EVENT_DISCONNECTION_COMPLETE,
+  BT_EVENT_MODE_CHANGED,
+  BT_EVENT_A2DP_STREAM_START,
+  BT_EVENT_A2DP_STREAM_STOP,
+  BT_EVENT_TYPE_MAX,    //This and beyond are invalid values
+} tSmeBtEventType;
+
+/** BT-AMP events type
+*/
+typedef enum eSmeBtAmpEventType
+{
+  BTAMP_EVENT_CONNECTION_START,
+  BTAMP_EVENT_CONNECTION_STOP,
+  BTAMP_EVENT_CONNECTION_TERMINATED,
+  BTAMP_EVENT_TYPE_MAX, //This and beyond are invalid values
+} tSmeBtAmpEventType;
+
+
+/**Data structure that specifies the needed event parameters for
+    BT_EVENT_CREATE_ACL_CONNECTION and BT_EVENT_ACL_CONNECTION_COMPLETE
+*/
+typedef struct sSmeBtAclConnectionParam
+{
+   v_U8_t       bdAddr[6];
+   v_U16_t      connectionHandle;
+   v_U8_t       status;
+} tSmeBtAclConnectionParam, *tpSmeBtAclConnectionParam;
+
+/** Data structure that specifies the needed event parameters for
+    BT_EVENT_CREATE_SYNC_CONNECTION, BT_EVENT_SYNC_CONNECTION_COMPLETE
+    and BT_EVENT_SYNC_CONNECTION_UPDATED
+*/
+typedef struct sSmeBtSyncConnectionParam
+{
+   v_U8_t       bdAddr[6];
+   v_U16_t      connectionHandle;
+   v_U8_t       status;
+   v_U8_t       linkType;
+   v_U8_t       scoInterval; //units in number of 625us slots
+   v_U8_t       scoWindow;   //units in number of 625us slots
+   v_U8_t       retransmisisonWindow; //units in number of 625us slots
+} tSmeBtSyncConnectionParam, *tpSmeBtSyncConnectionParam;
+
+typedef struct sSmeBtSyncUpdateHist
+{
+    tSmeBtSyncConnectionParam btSyncConnection;
+    v_BOOL_t fValid;
+} tSmeBtSyncUpdateHist, *tpSmeBtSyncUpdateHist;
+
+/**Data structure that specifies the needed event parameters for
+    BT_EVENT_MODE_CHANGED
+*/
+typedef struct sSmeBtAclModeChangeParam
+{
+    v_U16_t     connectionHandle;
+    v_U8_t      mode;
+} tSmeBtAclModeChangeParam, *tpSmeBtAclModeChangeParam;
+
+/*Data structure that specifies the needed event parameters for
+    BT_EVENT_DISCONNECTION_COMPLETE
+*/
+typedef struct sSmeBtDisconnectParam
+{
+   v_U16_t connectionHandle;
+} tSmeBtDisconnectParam, *tpSmeBtDisconnectParam;
+
+/*Data structure that specifies the needed event parameters for
+    BT_EVENT_A2DP_STREAM_START
+    BT_EVENT_A2DP_STREAM_STOP
+*/
+typedef struct sSmeBtA2DPParam
+{
+   v_U8_t       bdAddr[6];
+} tSmeBtA2DPParam, *tpSmeBtA2DPParam;
+
+
+/** Generic Bluetooth Event structure for BTC
+*/
+typedef struct sSmeBtcBtEvent
+{
+   tSmeBtEventType btEventType;
+   union
+   {
+      v_U8_t                    bdAddr[6];    /**< For events with only a BT Addr in event_data */
+      tSmeBtAclConnectionParam  btAclConnection;
+      tSmeBtSyncConnectionParam btSyncConnection;
+      tSmeBtDisconnectParam     btDisconnect;
+      tSmeBtAclModeChangeParam  btAclModeChange;
+   }uEventParam;
+} tSmeBtEvent, *tpSmeBtEvent;
+
+
+/**
+    BT-AMP Event Structure
+*/
+typedef struct sSmeBtAmpEvent
+{
+  tSmeBtAmpEventType btAmpEventType;
+
+} tSmeBtAmpEvent, *tpSmeBtAmpEvent;
+
+
+/** Data structure that specifies the BTC Configuration parameters
+*/
+typedef struct sSmeBtcConfig
+{
+   v_U8_t       btcExecutionMode;
+   v_U8_t       btcConsBtSlotsToBlockDuringDhcp;
+   v_U8_t       btcA2DPBtSubIntervalsDuringDhcp;
+   v_U8_t       btcActionOnPmFail;
+   v_U8_t       btcBtIntervalMode1;
+   v_U8_t       btcWlanIntervalMode1;
+
+} tSmeBtcConfig, *tpSmeBtcConfig;
+
+
+typedef struct sSmeBtAclModeChangeEventHist
+{
+    tSmeBtAclModeChangeParam  btAclModeChange;
+    v_BOOL_t fValid;
+} tSmeBtAclModeChangeEventHist, *tpSmeBtAclModeChangeEventHist;
+
+typedef struct sSmeBtAclEventHist
+{
+    //At most, cached events are COMPLETION, DISCONNECT, CREATION, COMPLETION
+    tSmeBtEventType btEventType[BT_MAX_NUM_EVENT_ACL_DEFERRED];
+    tSmeBtAclConnectionParam  btAclConnection[BT_MAX_NUM_EVENT_ACL_DEFERRED];
+    //bNextEventIdx == 0 meaning no event cached here
+    tANI_U8 bNextEventIdx;
+} tSmeBtAclEventHist, *tpSmeBtAclEventHist;
+
+typedef struct sSmeBtSyncEventHist
+{
+    //At most, cached events are COMPLETION, DISCONNECT, CREATION, COMPLETION
+    tSmeBtEventType btEventType[BT_MAX_NUM_EVENT_SCO_DEFERRED];
+    tSmeBtSyncConnectionParam  btSyncConnection[BT_MAX_NUM_EVENT_SCO_DEFERRED];
+    //bNextEventIdx == 0 meaning no event cached here
+    tANI_U8 bNextEventIdx;
+} tSmeBtSyncEventHist, *tpSmeBtSyncEventHist;
+
+typedef struct sSmeBtDisconnectEventHist
+{
+    tSmeBtDisconnectParam btDisconnect;
+    v_BOOL_t fValid;
+} tSmeBtDisconnectEventHist, *tpSmeBtDisconnectEventHist;
+
+
+/*
+  Data structure for the history of BT events
+*/
+typedef struct sSmeBtcEventHist
+{
+   tSmeBtSyncEventHist btSyncConnectionEvent[BT_MAX_SCO_SUPPORT];
+   tSmeBtAclEventHist btAclConnectionEvent[BT_MAX_ACL_SUPPORT];
+   tSmeBtAclModeChangeEventHist btAclModeChangeEvent[BT_MAX_ACL_SUPPORT];
+   tSmeBtDisconnectEventHist btDisconnectEvent[BT_MAX_DISCONN_SUPPORT];
+   tSmeBtSyncUpdateHist btSyncUpdateEvent[BT_MAX_SCO_SUPPORT];
+   int nInquiryEvent;    //>0 for # of outstanding inquiriy starts
+                         //<0 for # of outstanding inquiry stops
+                         //0 == no inquiry event
+   int nPageEvent;  //>0 for # of outstanding page starts
+                    //<0 for # of outstanding page stops
+                    //0 == no page event
+   v_BOOL_t fA2DPStarted;
+   v_BOOL_t fA2DPStopped;
+} tSmeBtcEventHist, *tpSmeBtcEventHist;
+
+typedef struct sSmeBtcEventReplay
+{
+   tSmeBtcEventHist btcEventHist;
+   v_BOOL_t fBTSwitchOn;
+   v_BOOL_t fBTSwitchOff;
+   //This is not directly tied to BT event so leave it alone when processing BT events
+   v_BOOL_t fRestoreHBMonitor;
+} tSmeBtcEventReplay, *tpSmeBtcEventReplay;
+
+typedef struct sSmeBtcInfo
+{
+   tSmeBtcConfig btcConfig;
+   v_BOOL_t      btcReady;
+   v_U8_t        btcEventState;
+   v_U8_t        btcHBActive;    /* Is HB currently active */
+   v_U8_t        btcHBCount;     /* default HB count */
+   vos_timer_t   restoreHBTimer; /* Timer to restore heart beat */
+   tSmeBtcEventReplay btcEventReplay;
+   v_BOOL_t      fReplayBTEvents;
+   v_BOOL_t      btcUapsdOk;  /* Indicate whether BTC is ok with UAPSD */
+   v_BOOL_t      fA2DPTrafStop;/*flag to check A2DP_STOP event has come before MODE_CHANGED*/
+   v_U16_t       btcScoHandles[BT_MAX_SCO_SUPPORT];  /* Handles for SCO, if any*/
+   v_BOOL_t      fA2DPUp;        /*remember whether A2DP is in session*/
+} tSmeBtcInfo, *tpSmeBtcInfo;
+
+
+/** Routine definitions
+*/
+
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+VOS_STATUS btcOpen (tHalHandle hHal);
+VOS_STATUS btcClose (tHalHandle hHal);
+VOS_STATUS btcReady (tHalHandle hHal);
+VOS_STATUS btcSendCfgMsg(tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig);
+VOS_STATUS btcSignalBTEvent (tHalHandle hHal, tpSmeBtEvent pBtEvent);
+VOS_STATUS btcSetConfig (tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig);
+VOS_STATUS btcGetConfig (tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig);
+/*
+   Caller can check whether BTC's current event allows UAPSD. This doesn't affect
+   BMPS.
+   return:  VOS_TRUE -- BTC is ready for UAPSD
+            VOS_FALSE -- certain BT event is active, cannot enter UAPSD
+*/
+v_BOOL_t btcIsReadyForUapsd( tHalHandle hHal );
+eHalStatus btcHandleCoexInd(tHalHandle hHal, void* pMsg);
+#endif /* End of WLAN_MDM_CODE_REDUCTION_OPT */
+
+#endif
diff --git a/CORE/SME/inc/ccmApi.h b/CORE/SME/inc/ccmApi.h
new file mode 100644
index 0000000..5195459
--- /dev/null
+++ b/CORE/SME/inc/ccmApi.h
@@ -0,0 +1,116 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+    \file ccmApi.h
+  
+    \brief Exports and types for the Common Config Module (CCM)
+  
+    $Id$ 
+  
+  
+    Copyright (C) 2006 Airgo Networks, Incorporated
+
+    This file contains all the interfaces for thge Platform Abstration Layer
+    functions.  It is intended to be included in all modules that are using 
+    the PAL interfaces.
+  
+   ========================================================================== */
+#ifndef CCMAPI_H__
+#define CCMAPI_H__
+
+//#include "wniCfgAp.h" /* CFG_PARAM_MAX_NUM */
+#include "wniCfgSta.h"
+#include "halTypes.h"
+
+#define CCM_11B_CHANNEL_END             14
+
+#define CCM_IS_RESULT_SUCCESS(result)   (WNI_CFG_SUCCESS == (result) ||\
+                                         WNI_CFG_NEED_RESTART == (result) || \
+                                         WNI_CFG_NEED_RELOAD == (result))
+
+#define CCM_INTEGER_TYPE                0
+#define CCM_STRING_TYPE                 1
+
+typedef void (*tCcmCfgSetCallback)(tHalHandle hHal, tANI_S32 result) ;
+
+typedef enum {
+    eCCM_STOPPED,
+    eCCM_STARTED,
+    eCCM_REQ_SENT,
+    eCCM_REQ_QUEUED,
+    eCCM_REQ_DONE,
+} eCcmState ;
+
+/* We do not use Linux's list facility */
+typedef struct cfgreq {
+    struct cfgreq       *next ;
+    tANI_U16            cfgId ;
+    tANI_U8             type ;
+    tANI_U8             state : 7 ;
+    tANI_U8             toBeSaved : 1 ;
+    tANI_S32            length ;
+    void                *ccmPtr;
+    tANI_U32            ccmValue;
+    tCcmCfgSetCallback  callback;
+    void                *done ;
+} tCfgReq ;
+
+typedef struct {
+    tANI_U16            started : 1 ;
+    tANI_U16            in_progress : 1 ;
+    tANI_U16            reserved : 14 ;
+    tANI_S16            nr_param ;
+    tANI_U32            result ;
+    tCcmCfgSetCallback  callback ;
+    void                *done ;
+} tCfgReplay ;
+
+struct ccmlink {
+    tCfgReq *head;
+    tCfgReq *tail;
+} ;
+
+typedef struct {
+    struct ccmlink      reqQ ;
+    eCcmState           state ;
+    tCfgReq *           comp[CFG_PARAM_MAX_NUM] ;
+    tCfgReplay          replay ;
+    void                *lock;
+} tCcm ;
+
+void ccmCfgCnfMsgHandler(tHalHandle hHal, void *msg) ;
+eHalStatus ccmOpen(tHalHandle hHal) ;
+eHalStatus ccmClose(tHalHandle hHal) ;
+void ccmStart(tHalHandle hHal) ;
+void ccmStop(tHalHandle hHal) ;
+//If callback is NULL, the API is not serialized for the CFGs
+eHalStatus ccmCfgSetInt(tHalHandle hHal, tANI_U32 cfgId, tANI_U32 ccmValue, tCcmCfgSetCallback callback, eAniBoolean toBeSaved) ;
+//If callback is NULL, the API is not serialized for the CFGs
+eHalStatus ccmCfgSetStr(tHalHandle hHal, tANI_U32 cfgId, tANI_U8 *pStr, tANI_U32 length, tCcmCfgSetCallback callback, eAniBoolean toBeSaved) ;
+eHalStatus ccmCfgUpdate(tHalHandle hHal, tCcmCfgSetCallback callback) ;
+eHalStatus ccmCfgGetInt(tHalHandle hHal, tANI_U32 cfgId, tANI_U32 *pValue) ;
+eHalStatus ccmCfgGetStr(tHalHandle hHal, tANI_U32 cfgId, tANI_U8 *pBuf, tANI_U32 *pLength) ;
+
+void ccmDumpInit(tHalHandle hHal);
+
+#endif /*CCMAPI_H__*/
diff --git a/CORE/SME/inc/csrApi.h b/CORE/SME/inc/csrApi.h
new file mode 100644
index 0000000..60d9da9
--- /dev/null
+++ b/CORE/SME/inc/csrApi.h
@@ -0,0 +1,1385 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+    \file csrApi.h
+  
+    Exports and types for the Common Scan and Roaming Module interfaces.
+  
+    Copyright (C) 2006 Airgo Networks, Incorporated 
+   ========================================================================== */
+#ifndef CSRAPI_H__
+#define CSRAPI_H__
+
+#include "sirApi.h"
+#include "sirMacProtDef.h"
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halRfTypes.h"
+#endif
+#include "csrLinkList.h"
+
+typedef enum 
+{
+    eCSR_AUTH_TYPE_NONE,    //never used
+    // MAC layer authentication types
+    eCSR_AUTH_TYPE_OPEN_SYSTEM,
+    eCSR_AUTH_TYPE_SHARED_KEY,
+    eCSR_AUTH_TYPE_AUTOSWITCH,
+
+    // Upper layer authentication types
+    eCSR_AUTH_TYPE_WPA,
+    eCSR_AUTH_TYPE_WPA_PSK,
+    eCSR_AUTH_TYPE_WPA_NONE,
+
+    eCSR_AUTH_TYPE_RSN,
+    eCSR_AUTH_TYPE_RSN_PSK,
+#if defined WLAN_FEATURE_VOWIFI_11R
+    eCSR_AUTH_TYPE_FT_RSN,
+    eCSR_AUTH_TYPE_FT_RSN_PSK,
+#endif
+#ifdef FEATURE_WLAN_WAPI
+    eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE,
+    eCSR_AUTH_TYPE_WAPI_WAI_PSK,
+#endif /* FEATURE_WLAN_WAPI */
+#ifdef FEATURE_WLAN_CCX
+    eCSR_AUTH_TYPE_CCKM_WPA,
+    eCSR_AUTH_TYPE_CCKM_RSN,
+#endif /* FEATURE_WLAN_CCX */
+    eCSR_NUM_OF_SUPPORT_AUTH_TYPE,
+    eCSR_AUTH_TYPE_FAILED = 0xff,
+    eCSR_AUTH_TYPE_UNKNOWN = eCSR_AUTH_TYPE_FAILED,
+
+}eCsrAuthType;
+
+
+typedef enum 
+{
+    eCSR_ENCRYPT_TYPE_NONE,
+    eCSR_ENCRYPT_TYPE_WEP40_STATICKEY,
+    eCSR_ENCRYPT_TYPE_WEP104_STATICKEY,
+
+    eCSR_ENCRYPT_TYPE_WEP40,
+    eCSR_ENCRYPT_TYPE_WEP104,
+    eCSR_ENCRYPT_TYPE_TKIP,
+    eCSR_ENCRYPT_TYPE_AES,
+#ifdef FEATURE_WLAN_WAPI
+    eCSR_ENCRYPT_TYPE_WPI, //WAPI
+#endif /* FEATURE_WLAN_WAPI */
+#ifdef FEATURE_WLAN_CCX
+    eCSR_ENCRYPT_TYPE_KRK,
+#endif /* FEATURE_WLAN_CCX */
+#ifdef WLAN_FEATURE_11W
+    //11w BIP
+    eCSR_ENCRYPT_TYPE_AES_CMAC,
+#endif
+    eCSR_ENCRYPT_TYPE_ANY,
+    eCSR_NUM_OF_ENCRYPT_TYPE = eCSR_ENCRYPT_TYPE_ANY,
+
+    eCSR_ENCRYPT_TYPE_FAILED = 0xff,
+    eCSR_ENCRYPT_TYPE_UNKNOWN = eCSR_ENCRYPT_TYPE_FAILED,
+
+}eCsrEncryptionType;
+
+/*---------------------------------------------------------------------------
+   Enumeration of the various Security types
+---------------------------------------------------------------------------*/
+typedef enum
+{
+    eCSR_SECURITY_TYPE_WPA,
+    eCSR_SECURITY_TYPE_RSN,
+#ifdef FEATURE_WLAN_WAPI
+    eCSR_SECURITY_TYPE_WAPI,
+#endif /* FEATURE_WLAN_WAPI */
+    eCSR_SECURITY_TYPE_UNKNOWN,
+
+}eCsrSecurityType;
+
+typedef enum
+{
+    eCSR_DOT11_MODE_TAURUS = 0, //This mean everything because it covers all thing we support
+    eCSR_DOT11_MODE_abg = 0x0001,    //11a/b/g only, no HT, no proprietary
+    eCSR_DOT11_MODE_11a = 0x0002,
+    eCSR_DOT11_MODE_11b = 0x0004,
+    eCSR_DOT11_MODE_11g = 0x0008,
+    eCSR_DOT11_MODE_11n = 0x0010,
+    eCSR_DOT11_MODE_POLARIS = 0x0020,
+    eCSR_DOT11_MODE_TITAN = 0x0040,
+    eCSR_DOT11_MODE_11g_ONLY = 0x0080,
+    eCSR_DOT11_MODE_11n_ONLY = 0x0100,
+    eCSR_DOT11_MODE_TAURUS_ONLY = 0x0200,
+    eCSR_DOT11_MODE_11b_ONLY = 0x0400,
+    eCSR_DOT11_MODE_11a_ONLY = 0x0800,
+    //This is for WIFI test. It is same as eWNIAPI_MAC_PROTOCOL_ALL except when it starts IBSS in 11B of 2.4GHz
+    //It is for CSR internal use
+    eCSR_DOT11_MODE_AUTO = 0x1000,
+
+    eCSR_NUM_PHY_MODE = 16,     //specify the number of maximum bits for phyMode
+}eCsrPhyMode;
+
+
+typedef tANI_U8 tCsrBssid[WNI_CFG_BSSID_LEN];
+
+typedef enum
+{
+    eCSR_BSS_TYPE_INFRASTRUCTURE,
+#ifdef WLAN_SOFTAP_FEATURE
+    eCSR_BSS_TYPE_INFRA_AP,       // SoftAP AP
+#endif
+    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,            // any BSS type (IBSS or Infrastructure).
+}eCsrRoamBssType;
+
+
+
+typedef enum {
+    eCSR_SCAN_REQUEST_11D_SCAN = 1,
+    eCSR_SCAN_REQUEST_FULL_SCAN,
+    eCSR_SCAN_IDLE_MODE_SCAN,
+    eCSR_SCAN_HO_BG_SCAN, // bg scan request in NRT & RT Handoff sub-states
+    eCSR_SCAN_HO_PROBE_SCAN, // directed probe on an entry from the candidate list
+    eCSR_SCAN_HO_NT_BG_SCAN, // bg scan request in NT  sub-state
+    eCSR_SCAN_P2P_DISCOVERY,
+
+    eCSR_SCAN_SOFTAP_CHANNEL_RANGE,
+    eCSR_SCAN_P2P_FIND_PEER,
+}eCsrRequestType;
+
+typedef enum {
+    eCSR_SCAN_RESULT_GET = 0,
+    eCSR_SCAN_RESULT_FLUSH = 1,     //to delete all cached scan results
+}eCsrScanResultCmd;
+
+typedef enum
+{
+    eCSR_SCAN_SUCCESS,
+    eCSR_SCAN_FAILURE,
+    eCSR_SCAN_ABORT,
+   eCSR_SCAN_FOUND_PEER,    
+}eCsrScanStatus;
+
+#define CSR_SCAN_TIME_DEFAULT       0
+#define CSR_VALUE_IGNORED           0xFFFFFFFF
+#define CSR_RSN_PMKID_SIZE          16
+#define CSR_MAX_PMKID_ALLOWED       16
+#define CSR_WEP40_KEY_LEN       5
+#define CSR_WEP104_KEY_LEN      13
+#define CSR_TKIP_KEY_LEN        32
+#define CSR_AES_KEY_LEN         16
+#define CSR_MAX_TX_POWER        ( WNI_CFG_CURRENT_TX_POWER_LEVEL_STAMAX )
+#define CSR_MAX_RSC_LEN          16
+#ifdef FEATURE_WLAN_WAPI
+#define CSR_WAPI_BKID_SIZE          16
+#define CSR_MAX_BKID_ALLOWED        16
+#define CSR_WAPI_KEY_LEN        32
+#define CSR_MAX_KEY_LEN         ( CSR_WAPI_KEY_LEN )  //longest one is for WAPI
+#else
+#define CSR_MAX_KEY_LEN         ( CSR_TKIP_KEY_LEN )  //longest one is for TKIP
+#endif /* FEATURE_WLAN_WAPI */
+#ifdef FEATURE_WLAN_CCX
+#define CSR_KRK_KEY_LEN 16
+#endif
+
+
+
+typedef struct tagCsrChannelInfo
+{
+    tANI_U8 numOfChannels;
+    tANI_U8 *ChannelList;   //it will be an array of channels
+}tCsrChannelInfo;
+
+typedef struct tagCsrSSIDInfo
+{
+   tSirMacSSid     SSID;   
+   tANI_BOOLEAN    handoffPermitted;
+   tANI_BOOLEAN    ssidHidden;
+}tCsrSSIDInfo;
+
+typedef struct tagCsrSSIDs
+{
+    tANI_U32 numOfSSIDs;
+    tCsrSSIDInfo *SSIDList;   //To be allocated for array of SSIDs
+}tCsrSSIDs;
+
+typedef struct tagCsrBSSIDs
+{
+    tANI_U32 numOfBSSIDs;
+    tCsrBssid *bssid;
+}tCsrBSSIDs;
+
+
+typedef struct tagCsrScanRequest 
+{
+    tSirScanType scanType;
+    tCsrBssid bssid;
+    eCsrRoamBssType BSSType;
+    tCsrSSIDs SSIDs;   
+    tCsrChannelInfo ChannelInfo;
+    tANI_U32 minChnTime;    //in units of milliseconds
+    tANI_U32 maxChnTime;    //in units of milliseconds
+    tANI_U32 restTime;      //in units of milliseconds  //ignored when not connected
+    tANI_U32 uIEFieldLen;
+    tANI_U8 *pIEField;
+    eCsrRequestType requestType;    //11d scan or full scan
+#ifdef WLAN_FEATURE_P2P
+    tANI_BOOLEAN p2pSearch;
+#endif
+}tCsrScanRequest;
+
+typedef struct tagCsrBGScanRequest
+{
+    tSirScanType scanType;
+    tSirMacSSid SSID;
+    tCsrChannelInfo ChannelInfo;
+    tANI_U32 scanInterval;  //in units of milliseconds
+    tANI_U32 minChnTime;    //in units of milliseconds
+    tANI_U32 maxChnTime;    //in units of milliseconds
+    tANI_U32 restTime;      //in units of milliseconds  //ignored when not connected
+    tANI_U32 throughputImpact;      //specify whether BG scan cares about impacting throughput  //ignored when not connected
+    tCsrBssid bssid;    //how to use it?? Apple
+}tCsrBGScanRequest;
+
+
+typedef struct tagCsrScanResultInfo
+{
+    //Carry the IEs for the current BSSDescription. A pointer to tDot11fBeaconIEs. Maybe NULL for start BSS.
+    void *pvIes;
+    tAniSSID ssId;
+    v_TIME_t timer; // timer is variable which is used for hidden SSID's timer value
+    //This member must be the last in the structure because the end of tSirBssDescription is an
+    //    array with nonknown size at this time
+    tSirBssDescription BssDescriptor;
+}tCsrScanResultInfo;
+
+typedef struct tagCsrEncryptionList
+{
+
+    tANI_U32 numEntries;
+    eCsrEncryptionType encryptionType[eCSR_NUM_OF_ENCRYPT_TYPE];
+
+}tCsrEncryptionList, *tpCsrEncryptionList;
+
+typedef struct tagCsrAuthList
+{
+    tANI_U32 numEntries;
+    eCsrAuthType authType[eCSR_NUM_OF_SUPPORT_AUTH_TYPE];
+}tCsrAuthList, *tpCsrAuthList;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+typedef struct tagCsrMobilityDomainInfo
+{
+    tANI_U8 mdiePresent;
+    tANI_U16 mobilityDomain;
+} tCsrMobilityDomainInfo;
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+typedef struct tagCsrCcxCckmInfo
+{
+    tANI_U32       reassoc_req_num;
+    tANI_BOOLEAN   krk_plumbed;
+    tANI_U8        krk[CSR_KRK_KEY_LEN];
+} tCsrCcxCckmInfo;
+#endif
+
+
+typedef struct tagCsrScanResultFilter
+{
+    tCsrBSSIDs BSSIDs;    //each bssid has a length of WNI_CFG_BSSID_LEN (6)
+    tCsrSSIDs SSIDs;   
+    tCsrChannelInfo ChannelInfo;
+    tCsrAuthList authType;
+    tCsrEncryptionList EncryptionType;
+    //eCSR_ENCRYPT_TYPE_ANY cannot be set in multicast encryption type. If caller doesn't case, 
+    //put all supported encryption types in here
+    tCsrEncryptionList mcEncryptionType;
+    eCsrRoamBssType BSSType;   
+    //this is a bit mask of all the needed phy mode defined in eCsrPhyMode
+    tANI_U32 phyMode;   
+    //If countryCode[0] is not 0, countryCode is checked independent of fCheckUnknownCountryCode
+    tANI_U8 countryCode[WNI_CFG_COUNTRY_CODE_LEN]; 
+    tANI_U8 uapsd_mask; 
+    /*For WPS filtering if true => auth and ecryption should be ignored*/
+    tANI_BOOLEAN bWPSAssociation;
+#if defined WLAN_FEATURE_VOWIFI
+    /*For measurement reports --> if set, only SSID, BSSID and channel is considered for filtering.*/
+    tANI_BOOLEAN fMeasurement;
+#endif
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    tCsrMobilityDomainInfo MDID;
+#endif
+    tANI_BOOLEAN p2pResult;
+}tCsrScanResultFilter;
+
+
+typedef struct sCsrChnPower_
+{
+  tANI_U8 firstChannel;
+  tANI_U8 numChannels;
+  tANI_U8 maxtxPower;
+}sCsrChnPower;
+
+
+typedef struct sCsrChannel_
+{
+    tANI_U8 numChannels;
+    tANI_U8 channelList[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+}sCsrChannel;
+
+
+typedef struct tagCsr11dinfo
+{
+  sCsrChannel     Channels;
+  tANI_U8         countryCode[WNI_CFG_COUNTRY_CODE_LEN+1];
+  //max power channel list
+  sCsrChnPower    ChnPower[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+}tCsr11dinfo;
+
+
+typedef enum
+{
+    eCSR_ROAM_CANCELLED = 1,
+    //this mean error happens before association_start or roaming_start is called.
+    eCSR_ROAM_FAILED,   
+    //a CSR trigger roaming operation starts, callback may get a pointer to tCsrConnectedProfile
+    eCSR_ROAM_ROAMING_START,    
+    //a CSR trigger roaming operation is completed
+    eCSR_ROAM_ROAMING_COMPLETION,   
+    //Connection completed status.
+    eCSR_ROAM_CONNECT_COMPLETION, 
+    //an association or start_IBSS operation starts, 
+    //callback may get a pointer to tCsrRoamProfile and a pointer to tSirBssDescription 
+    eCSR_ROAM_ASSOCIATION_START,    
+    //a roaming operation is finish, see eCsrRoamResult for 
+    //possible data passed back
+    eCSR_ROAM_ASSOCIATION_COMPLETION,   
+    eCSR_ROAM_DISASSOCIATED,
+    eCSR_ROAM_ASSOCIATION_FAILURE,
+    //when callback with this flag. callback gets a pointer to the BSS desc.
+    eCSR_ROAM_SHOULD_ROAM,  
+    //A new candidate for PMKID is found
+    eCSR_ROAM_SCAN_FOUND_NEW_BSS,
+    //CSR is done lostlink roaming and still cannot reconnect
+    eCSR_ROAM_LOSTLINK,
+    //a link lost is detected. CSR starts roaming.
+    eCSR_ROAM_LOSTLINK_DETECTED,   
+    //TKIP MIC error detected, callback gets a pointer to tpSirSmeMicFailureInd
+    eCSR_ROAM_MIC_ERROR_IND,
+    eCSR_ROAM_IBSS_IND, //IBSS indications.
+    //Update the connection status, useful for IBSS: new peer added, network is active etc. 
+    eCSR_ROAM_CONNECT_STATUS_UPDATE,  
+    eCSR_ROAM_GEN_INFO,
+    eCSR_ROAM_SET_KEY_COMPLETE,
+    eCSR_ROAM_REMOVE_KEY_COMPLETE,
+    eCSR_ROAM_IBSS_LEAVE, //IBSS indications.
+    //BSS in WDS mode status indication
+    eCSR_ROAM_WDS_IND,
+#ifdef WLAN_SOFTAP_FEATURE
+    //BSS in SoftAP mode status indication
+    eCSR_ROAM_INFRA_IND,
+    eCSR_ROAM_WPS_PBC_PROBE_REQ_IND,
+#endif
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    eCSR_ROAM_FT_RESPONSE,
+#endif
+    eCSR_ROAM_FT_START,
+    eCSR_ROAM_INDICATE_MGMT_FRAME,
+    eCSR_ROAM_REMAIN_CHAN_READY,
+    eCSR_ROAM_SEND_ACTION_CNF,
+    //this mean error happens before association_start or roaming_start is called.
+    eCSR_ROAM_SESSION_OPENED,
+    eCSR_ROAM_FT_REASSOC_FAILED,
+}eRoamCmdStatus;
+
+
+//comment inside indicates what roaming callback gets
+typedef enum
+{
+    eCSR_ROAM_RESULT_NONE,
+    //this means no more action in CSR
+    //If roamStatus is eCSR_ROAM_ASSOCIATION_COMPLETION, tCsrRoamInfo's pBssDesc may pass back
+    eCSR_ROAM_RESULT_FAILURE,   
+    //Pass back pointer to tCsrRoamInfo
+    eCSR_ROAM_RESULT_ASSOCIATED,    
+    eCSR_ROAM_RESULT_NOT_ASSOCIATED,
+    eCSR_ROAM_RESULT_MIC_FAILURE,
+    eCSR_ROAM_RESULT_FORCED,
+    eCSR_ROAM_RESULT_DISASSOC_IND,
+    eCSR_ROAM_RESULT_DEAUTH_IND,
+    eCSR_ROAM_RESULT_CAP_CHANGED,
+    //This means we starts an IBSS
+    //tCsrRoamInfo's pBssDesc may pass back
+    eCSR_ROAM_RESULT_IBSS_STARTED,  
+    //START_BSS failed
+    //tCsrRoamInfo's pBssDesc may pass back
+    eCSR_ROAM_RESULT_IBSS_START_FAILED, 
+    eCSR_ROAM_RESULT_IBSS_JOIN_SUCCESS,
+    eCSR_ROAM_RESULT_IBSS_JOIN_FAILED, 
+    eCSR_ROAM_RESULT_IBSS_CONNECT,
+    eCSR_ROAM_RESULT_IBSS_INACTIVE,
+    //If roamStatus is eCSR_ROAM_ASSOCIATION_COMPLETION
+    //tCsrRoamInfo's pBssDesc may pass back. and the peer's MAC address in peerMacOrBssid 
+    //If roamStatus is eCSR_ROAM_IBSS_IND,  
+    //the peer's MAC address in peerMacOrBssid and a beacon frame of the IBSS in pbFrames
+    eCSR_ROAM_RESULT_IBSS_NEW_PEER, 
+    //Peer departed from IBSS, Callback may get a pointer tSmeIbssPeerInd in pIbssPeerInd
+    eCSR_ROAM_RESULT_IBSS_PEER_DEPARTED, 
+    //Coalescing in the IBSS network (joined an IBSS network)
+    //Callback pass a BSSID in peerMacOrBssid
+    eCSR_ROAM_RESULT_IBSS_COALESCED,    
+    //If roamStatus is eCSR_ROAM_ROAMING_START, callback may get a pointer to tCsrConnectedProfile used to connect.
+    eCSR_ROAM_RESULT_IBSS_STOP,  
+    eCSR_ROAM_RESULT_LOSTLINK, 
+    eCSR_ROAM_RESULT_MIC_ERROR_UNICAST,
+    eCSR_ROAM_RESULT_MIC_ERROR_GROUP,
+    eCSR_ROAM_RESULT_AUTHENTICATED,
+    eCSR_ROAM_RESULT_NEW_RSN_BSS,
+#ifdef FEATURE_WLAN_WAPI
+    eCSR_ROAM_RESULT_NEW_WAPI_BSS,
+#endif /* FEATURE_WLAN_WAPI */
+    // WDS started successfully
+    eCSR_ROAM_RESULT_WDS_STARTED,
+    // WDS start failed
+    eCSR_ROAM_RESULT_WDS_START_FAILED,
+    // WDS stopped
+    eCSR_ROAM_RESULT_WDS_STOPPED,
+    // WDS joined successfully in STA mode
+    eCSR_ROAM_RESULT_WDS_ASSOCIATED,
+    // A station joined WDS AP 
+    eCSR_ROAM_RESULT_WDS_ASSOCIATION_IND,
+    // WDS join failed in STA mode
+    eCSR_ROAM_RESULT_WDS_NOT_ASSOCIATED,
+    // WDS disassociated
+    eCSR_ROAM_RESULT_WDS_DISASSOCIATED,
+#ifdef WLAN_SOFTAP_FEATURE
+    // INFRA started successfully
+    eCSR_ROAM_RESULT_INFRA_STARTED,
+    // INFRA start failed
+    eCSR_ROAM_RESULT_INFRA_START_FAILED,
+    // INFRA stopped
+    eCSR_ROAM_RESULT_INFRA_STOPPED,
+    // A station joining INFRA AP
+    eCSR_ROAM_RESULT_INFRA_ASSOCIATION_IND,
+    // A station joined INFRA AP
+    eCSR_ROAM_RESULT_INFRA_ASSOCIATION_CNF,
+    // INFRA disassociated
+    eCSR_ROAM_RESULT_INFRA_DISASSOCIATED,
+    eCSR_ROAM_RESULT_WPS_PBC_PROBE_REQ_IND,
+#endif
+#ifdef WLAN_FEATURE_P2P
+    eCSR_ROAM_RESULT_SEND_ACTION_FAIL,
+#endif
+    // peer rejected assoc because max assoc limit reached. callback gets pointer to peer
+    eCSR_ROAM_RESULT_MAX_ASSOC_EXCEEDED,
+}eCsrRoamResult;
+
+
+
+/*----------------------------------------------------------------------------
+  List of link quality indications HDD can receive from SME
+-----------------------------------------------------------------------------*/
+typedef enum
+{
+ eCSR_ROAM_LINK_QUAL_MIN_IND     = -1,
+
+ eCSR_ROAM_LINK_QUAL_POOR_IND            =  0,   /* bad link                */
+ eCSR_ROAM_LINK_QUAL_GOOD_IND            =  1,   /* acceptable for voice    */
+ eCSR_ROAM_LINK_QUAL_VERY_GOOD_IND       =  2,   /* suitable for voice      */
+ eCSR_ROAM_LINK_QUAL_EXCELLENT_IND       =  3,   /* suitable for voice      */
+
+ eCSR_ROAM_LINK_QUAL_MAX_IND  /* invalid value */
+
+} eCsrRoamLinkQualityInd;
+
+typedef enum
+{
+    eCSR_DISCONNECT_REASON_UNSPECIFIED = 0,
+    eCSR_DISCONNECT_REASON_MIC_ERROR,
+    eCSR_DISCONNECT_REASON_DISASSOC,
+    eCSR_DISCONNECT_REASON_DEAUTH,
+    eCSR_DISCONNECT_REASON_HANDOFF,
+    eCSR_DISCONNECT_REASON_IBSS_JOIN_FAILURE,
+    eCSR_DISCONNECT_REASON_IBSS_LEAVE,
+}eCsrRoamDisconnectReason;
+
+typedef enum 
+{
+    // Not associated in Infra or participating in an IBSS / Ad-hoc network.
+    eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED,
+    // Associated in an Infrastructure network.
+    eCSR_ASSOC_STATE_TYPE_INFRA_ASSOCIATED,
+    // Participating in an IBSS network though disconnected (no partner stations
+    // in the IBSS).
+    eCSR_ASSOC_STATE_TYPE_IBSS_DISCONNECTED,
+    // Participating in an IBSS network with partner stations also present
+    eCSR_ASSOC_STATE_TYPE_IBSS_CONNECTED,
+    // Participating in a WDS network in AP or STA mode but not connected yet
+    eCSR_ASSOC_STATE_TYPE_WDS_DISCONNECTED,
+    // Participating in a WDS network and connected peer to peer
+    eCSR_ASSOC_STATE_TYPE_WDS_CONNECTED,
+#ifdef WLAN_SOFTAP_FEATURE
+    // Participating in a Infra network in AP not yet in connected state
+    eCSR_ASSOC_STATE_TYPE_INFRA_DISCONNECTED,
+    // Participating in a Infra network and connected to a peer
+    eCSR_ASSOC_STATE_TYPE_INFRA_CONNECTED,
+#endif
+
+}eCsrConnectState;
+
+
+// This parameter is no longer supported in the Profile.  Need to set this in the global properties
+// for the adapter.
+typedef enum eCSR_MEDIUM_ACCESS 
+{
+    eCSR_MEDIUM_ACCESS_AUTO = 0,
+    eCSR_MEDIUM_ACCESS_DCF,
+    eCSR_MEDIUM_ACCESS_eDCF,
+    eCSR_MEDIUM_ACCESS_HCF,
+
+    eCSR_MEDIUM_ACCESS_WMM_eDCF_802dot1p,
+    eCSR_MEDIUM_ACCESS_WMM_eDCF_DSCP,
+    eCSR_MEDIUM_ACCESS_WMM_eDCF_NoClassify,
+    eCSR_MEDIUM_ACCESS_11e_eDCF = eCSR_MEDIUM_ACCESS_eDCF,
+    eCSR_MEDIUM_ACCESS_11e_HCF  = eCSR_MEDIUM_ACCESS_HCF,
+}eCsrMediaAccessType;
+
+typedef enum 
+{
+    eCSR_TX_RATE_AUTO = 0,   // use rate adaption to determine Tx rate.
+
+    eCSR_TX_RATE_1Mbps   = 0x00000001,
+    eCSR_TX_RATE_2Mbps   = 0x00000002,
+    eCSR_TX_RATE_5_5Mbps = 0x00000004,
+    eCSR_TX_RATE_6Mbps   = 0x00000008,
+    eCSR_TX_RATE_9Mbps   = 0x00000010,
+    eCSR_TX_RATE_11Mbps  = 0x00000020,
+    eCSR_TX_RATE_12Mbps  = 0x00000040,
+    eCSR_TX_RATE_18Mbps  = 0x00000080,
+    eCSR_TX_RATE_24Mbps  = 0x00000100,
+    eCSR_TX_RATE_36Mbps  = 0x00000200,
+    eCSR_TX_RATE_42Mbps  = 0x00000400,
+    eCSR_TX_RATE_48Mbps  = 0x00000800,
+    eCSR_TX_RATE_54Mbps  = 0x00001000,
+    eCSR_TX_RATE_72Mbps  = 0x00002000,
+    eCSR_TX_RATE_84Mbps  = 0x00004000,
+    eCSR_TX_RATE_96Mbps  = 0x00008000,
+    eCSR_TX_RATE_108Mbps = 0x00010000,
+    eCSR_TX_RATE_126Mbps = 0x00020000,
+    eCSR_TX_RATE_144Mbps = 0x00040000,
+    eCSR_TX_RATE_168Mbps = 0x00080000,
+    eCSR_TX_RATE_192Mbps = 0x00100000,
+    eCSR_TX_RATE_216Mbps = 0x00200000,
+    eCSR_TX_RATE_240Mbps = 0x00400000,
+
+}eCsrExposedTxRate;
+
+typedef enum 
+{
+    eCSR_OPERATING_CHANNEL_ALL  = 0,
+    eCSR_OPERATING_CHANNEL_AUTO = eCSR_OPERATING_CHANNEL_ALL,
+    eCSR_OPERATING_CHANNEL_ANY  = eCSR_OPERATING_CHANNEL_ALL,
+}eOperationChannel;
+
+typedef enum 
+{
+    eCSR_DOT11_FRAG_THRESH_AUTO            = -1,
+    eCSR_DOT11_FRAG_THRESH_MIN             = 256,
+    eCSR_DOT11_FRAG_THRESH_MAX             = 2346,
+    eCSR_DOT11_FRAG_THRESH_DEFAULT         = 2000
+}eCsrDot11FragThresh;
+
+
+//for channel bonding for ibss
+typedef enum 
+{
+    eCSR_CB_OFF = 0,
+    eCSR_CB_AUTO = 1,
+    eCSR_CB_DOWN = 2,
+    eCSR_CB_UP = 3,
+}eCsrCBChoice;
+
+//For channel bonding, the channel number gap is 4, either up or down. For both 11a and 11g mode.
+#define CSR_CB_CHANNEL_GAP 4
+#define CSR_CB_CENTER_CHANNEL_OFFSET    2
+#define CSR_MAX_24GHz_CHANNEL_NUMBER ( SIR_11B_CHANNEL_END )
+
+// WEP keysize (in bits)...
+typedef enum  
+{
+    eCSR_SECURITY_WEP_KEYSIZE_40  =  40,   // 40 bit key + 24bit IV = 64bit WEP
+    eCSR_SECURITY_WEP_KEYSIZE_104 = 104,   // 104bit key + 24bit IV = 128bit WEP
+
+    eCSR_SECURITY_WEP_KEYSIZE_MIN = eCSR_SECURITY_WEP_KEYSIZE_40,
+    eCSR_SECURITY_WEP_KEYSIZE_MAX = eCSR_SECURITY_WEP_KEYSIZE_104,
+    eCSR_SECURITY_WEP_KEYSIZE_MAX_BYTES = ( eCSR_SECURITY_WEP_KEYSIZE_MAX / 8 ),
+}eCsrWEPKeySize;
+
+
+// Possible values for the WEP static key ID...
+typedef enum
+{
+
+    eCSR_SECURITY_WEP_STATIC_KEY_ID_MIN       =  0,
+    eCSR_SECURITY_WEP_STATIC_KEY_ID_MAX       =  3,
+    eCSR_SECURITY_WEP_STATIC_KEY_ID_DEFAULT   =  0,
+
+    eCSR_SECURITY_WEP_STATIC_KEY_ID_INVALID   = -1,
+
+}eCsrWEPStaticKeyID;
+
+#define CSR_MAX_NUM_KEY     (eCSR_SECURITY_WEP_STATIC_KEY_ID_MAX + 1)
+
+typedef enum 
+{
+    eCSR_SECURITY_SET_KEY_ACTION_NO_CHANGE,
+    eCSR_SECURITY_SET_KEY_ACTION_SET_KEY,
+    eCSR_SECURITY_SET_KEY_ACTION_DELETE_KEY,
+}eCsrSetKeyAction;
+
+typedef enum
+{
+    eCSR_BAND_ALL,
+    eCSR_BAND_24,
+    eCSR_BAND_5G,
+    eCSR_BAND_MAX,
+}eCsrBand;
+
+
+typedef enum 
+{
+   // Roaming because HDD requested for reassoc by changing one of the fields in 
+   // tCsrRoamModifyProfileFields. OR
+   // Roaming because SME requested for reassoc by changing one of the fields in 
+   // tCsrRoamModifyProfileFields.
+   eCsrRoamReasonStaCapabilityChanged,
+   // Roaming because SME requested for reassoc to a different AP, as part of 
+   // inter AP handoff.
+   eCsrRoamReasonBetterAP,
+   // Roaming because SME requested it as the link is lost - placeholder, will 
+   // clean it up once handoff code gets in
+   eCsrRoamReasonSmeIssuedForLostLink,
+
+}eCsrRoamReasonCodes;
+
+typedef enum
+{
+   eCsrRoamWmmAuto = 0,
+   eCsrRoamWmmQbssOnly = 1,
+   eCsrRoamWmmNoQos = 2,
+
+} eCsrRoamWmmUserModeType;
+
+typedef enum
+{
+   eCSR_REQUESTER_MIN = 0,
+   eCSR_DIAG,
+   eCSR_UMA_GAN,
+   eCSR_HDD
+} eCsrStatsRequesterType;
+
+typedef struct tagPmkidCandidateInfo
+{
+    tCsrBssid BSSID;
+    tANI_BOOLEAN preAuthSupported;
+}tPmkidCandidateInfo;
+
+typedef struct tagPmkidCacheInfo
+{
+    tCsrBssid BSSID;
+    tANI_U8 PMKID[CSR_RSN_PMKID_SIZE];
+}tPmkidCacheInfo;
+
+#ifdef FEATURE_WLAN_WAPI
+typedef struct tagBkidCandidateInfo
+{
+    tCsrBssid BSSID;
+    tANI_BOOLEAN preAuthSupported;
+}tBkidCandidateInfo;
+
+typedef struct tagBkidCacheInfo
+{
+    tCsrBssid BSSID;
+    tANI_U8 BKID[CSR_WAPI_BKID_SIZE];
+}tBkidCacheInfo;
+#endif /* FEATURE_WLAN_WAPI */
+
+typedef struct tagCsrKeys
+{
+    tANI_U8 KeyLength[ CSR_MAX_NUM_KEY ];   //Also use to indicate whether the key index is set
+    tANI_U8 KeyMaterial[ CSR_MAX_NUM_KEY ][ CSR_MAX_KEY_LEN ];
+    tANI_U8 defaultIndex;
+}tCsrKeys;
+
+/* Following are fields which are part of tCsrRoamConnectedProfile might need 
+   modification dynamically once STA is up & running and this could trigger
+   reassoc */
+typedef struct tagCsrRoamModifyProfileFields
+{
+   // during connect this specifies ACs U-APSD is to be setup 
+   //   for (Bit0:VO; Bit1:VI; Bit2:BK; Bit3:BE all other bits are ignored).
+   //  During assoc response this COULD carry confirmation of what ACs U-APSD 
+   // got setup for. Later if an APP looking for APSD, SME-QoS might need to
+   // modify this field
+   tANI_U8     uapsd_mask;
+   // HDD might ask to modify this field
+   tANI_U16    listen_interval;
+}tCsrRoamModifyProfileFields;
+
+typedef struct tagCsrRoamProfile
+{
+    //For eCSR_BSS_TYPE_WDS_AP. There must be one SSID in SSIDs.
+    //For eCSR_BSS_TYPE_WDS_STA. There must be two SSIDs. Index 0 is the SSID of the WDS-AP
+    //that we need to join. Index 1 is the SSID for self BSS.
+    tCsrSSIDs SSIDs;
+    tCsrBSSIDs BSSIDs;
+    tANI_U32 phyMode;   //this is a bit mask of all the needed phy mode defined in eCsrPhyMode
+    eCsrRoamBssType BSSType;
+
+    tCsrAuthList AuthType;
+    eCsrAuthType negotiatedAuthType;
+
+    tCsrEncryptionList EncryptionType;
+    //This field is for output only, not for input
+    eCsrEncryptionType negotiatedUCEncryptionType;
+
+    //eCSR_ENCRYPT_TYPE_ANY cannot be set in multicast encryption type. If caller doesn't case, 
+    //put all supported encryption types in here
+    tCsrEncryptionList mcEncryptionType;
+    //This field is for output only, not for input
+    eCsrEncryptionType negotiatedMCEncryptionType;  
+
+    tCsrKeys Keys;
+    eCsrCBChoice CBMode; //up, down or auto
+    tCsrChannelInfo ChannelInfo;
+    tANI_U8 operationChannel;   
+    tANI_U16 beaconInterval;    //If this is 0, SME will fill in for caller.
+    // during connect this specifies ACs U-APSD is to be setup 
+    //   for (Bit0:VO; Bit1:VI; Bit2:BK; Bit3:BE all other bits are ignored).
+    //  During assoc response this COULD carry confirmation of what ACs U-APSD got setup for
+    tANI_U8 uapsd_mask; 
+    tANI_U32 nWPAReqIELength;   //The byte count in the pWPAReqIE
+    tANI_U8 *pWPAReqIE;   //If not null, it has the IE byte stream for WPA
+    tANI_U32 nRSNReqIELength;  //The byte count in the pRSNReqIE
+    tANI_U8 *pRSNReqIE;     //If not null, it has the IE byte stream for RSN
+#ifdef FEATURE_WLAN_WAPI
+    tANI_U32 nWAPIReqIELength;   //The byte count in the pWAPIReqIE
+    tANI_U8 *pWAPIReqIE;   //If not null, it has the IE byte stream for WAPI
+#endif /* FEATURE_WLAN_WAPI */
+
+    tANI_U32 nAddIEScanLength;   //The byte count in the pAddIE for scan (at the time of join)
+    tANI_U8 *pAddIEScan;       //If not null, it has the IE byte stream for additional IE, which can be WSC IE and/or P2P IE
+    tANI_U32 nAddIEAssocLength;   //The byte count in the pAddIE for assoc 
+    tANI_U8 *pAddIEAssoc;       //If not null, it has the IE byte stream for additional IE, which can be WSC IE and/or P2P IE
+
+    tANI_U8 countryCode[WNI_CFG_COUNTRY_CODE_LEN];  //it is ignored if [0] is 0.
+    /*WPS Association if true => auth and ecryption should be ignored*/
+    tANI_BOOLEAN bWPSAssociation;
+    tANI_U32 nWSCReqIELength;   //The byte count in the pWSCReqIE
+    tANI_U8 *pWSCReqIE;   //If not null, it has the IE byte stream for WSC
+
+#ifdef WLAN_SOFTAP_FEATURE
+    tANI_U8 ieee80211d;
+    tANI_U8 privacy;
+    tANI_BOOLEAN fwdWPSPBCProbeReq;
+    tAniAuthType csr80211AuthType;
+    tANI_U32 dtimPeriod;
+    tANI_BOOLEAN ApUapsdEnable;
+    tANI_BOOLEAN protEnabled;
+    tANI_BOOLEAN obssProtEnabled;
+    tANI_U16 cfg_protection;
+    tANI_U8 wps_state;
+#endif
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    tCsrMobilityDomainInfo MDID;
+#endif
+    tVOS_CON_MODE csrPersona;
+
+}tCsrRoamProfile;
+
+
+typedef struct tagCsrRoamConnectedProfile
+{
+    tSirMacSSid SSID;
+    tANI_BOOLEAN    handoffPermitted;
+    tANI_BOOLEAN    ssidHidden;
+    tCsrBssid bssid;
+    eCsrRoamBssType BSSType;
+    eCsrAuthType AuthType;
+    tCsrAuthList AuthInfo;
+    eCsrEncryptionType EncryptionType;
+    tCsrEncryptionList EncryptionInfo;
+    eCsrEncryptionType mcEncryptionType;
+    tCsrEncryptionList mcEncryptionInfo;
+    eCsrCBChoice CBMode; //up, down or auto
+    tANI_U8 operationChannel;
+    tCsrKeys Keys;
+    // meaningless on connect. It's an OUT param from CSR's point of view
+    // During assoc response carries the ACM bit-mask i.e. what
+    // ACs have ACM=1 (if any), 
+    // (Bit0:VO; Bit1:VI; Bit2:BK; Bit3:BE all other bits are ignored)
+    tANI_U8  acm_mask;
+    tCsrRoamModifyProfileFields modifyProfileFields;
+    tSirBssDescription *pBssDesc;   
+    tANI_BOOLEAN   qap; //AP supports QoS
+    tANI_BOOLEAN   qosConnection; //A connection is QoS enabled
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    tCsrMobilityDomainInfo MDID;
+#endif
+    
+#ifdef FEATURE_WLAN_CCX
+    tCsrCcxCckmInfo ccxCckmInfo;
+    tANI_BOOLEAN    isCCXAssoc; 
+#endif
+}tCsrRoamConnectedProfile;
+
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+typedef struct tagCsr11rConfigParams
+{
+    tANI_BOOLEAN   IsFTResourceReqSupported;
+} tCsr11rConfigParams;
+#endif
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+typedef struct tagCsrNeighborRoamConfigParams
+{
+
+    tANI_U32       nNeighborScanTimerPeriod;
+    tANI_U8        nNeighborLookupRssiThreshold;
+    tANI_U8        nNeighborReassocRssiThreshold;
+    tANI_U16       nNeighborScanMinChanTime;
+    tANI_U16       nNeighborScanMaxChanTime;
+    sCsrChannel    neighborScanChanList;
+    tANI_U8        nMaxNeighborRetries;
+    tANI_U16       nNeighborResultsRefreshPeriod;
+}tCsrNeighborRoamConfigParams;
+#endif
+
+typedef struct tagCsrConfigParam
+{
+    tANI_U32 FragmentationThreshold;
+    tANI_U32 channelBondingMode24GHz;
+    tANI_U32 channelBondingMode5GHz;
+    eCsrPhyMode phyMode;
+    eCsrBand eBand;
+    tANI_U32 RTSThreshold;
+    tANI_U32 HeartbeatThresh50;
+    tANI_U32 HeartbeatThresh24;
+    eCsrCBChoice cbChoice;
+    eCsrBand bandCapability;     //indicate hw capability
+    tANI_U32 bgScanInterval;
+    tANI_U16 TxRate;
+    eCsrRoamWmmUserModeType WMMSupportMode;
+    tANI_BOOLEAN Is11eSupportEnabled;
+    tANI_BOOLEAN Is11dSupportEnabled;
+    tANI_BOOLEAN Is11dSupportEnabledOriginal;
+    tANI_BOOLEAN Is11hSupportEnabled;
+    tANI_BOOLEAN shortSlotTime;
+    tANI_BOOLEAN ProprietaryRatesEnabled;
+    tANI_U8 AdHocChannel24;
+    tANI_U8 AdHocChannel5G;
+    tANI_U32 impsSleepTime;     //in units of seconds
+    tANI_U32 nScanResultAgeCount;   //this number minus one is the number of times a scan doesn't find it before it is removed
+    tANI_U32 scanAgeTimeNCNPS;  //scan result aging time threshold when Not-Connect-No-Power-Save, in seconds
+    tANI_U32 scanAgeTimeNCPS;   //scan result aging time threshold when Not-Connect-Power-Save, in seconds
+    tANI_U32 scanAgeTimeCNPS;   //scan result aging time threshold when Connect-No-Power-Save, in seconds,
+    tANI_U32 scanAgeTimeCPS;   //scan result aging time threshold when Connect-Power-Savein seconds
+    tANI_U32 nRoamingTime;  //In seconds, CSR will try this long before gives up. 0 means no roaming
+    tANI_U8 bCatRssiOffset;     //to set the RSSI difference for each category
+    tANI_U8 fEnableMCCMode; //to set MCC Enable/Disable mode
+
+    tCsr11dinfo  Csr11dinfo;
+    //Whether to limit the channels to the ones set in Csr11dInfo. If true, the opertaional
+    //channels are limited to the default channel list. It is an "AND" operation between the 
+    //default channels and the channels in the 802.11d IE.
+    tANI_BOOLEAN fEnforce11dChannels;  
+    //Country Code Priority
+    //0 = 802.11D > Country IOCTL > NV 
+    //1 = Country IOCTL > 802.11D > NV
+    tANI_BOOLEAN fSupplicantCountryCodeHasPriority;
+    //When true, AP with unknown country code won't be see. 
+    //"Unknown country code" means either Ap doesn't have 11d IE or we cannot 
+    //find a domain for the country code in its 11d IE. 
+    tANI_BOOLEAN fEnforceCountryCodeMatch;  
+    //When true, only APs in the default domain can be seen. If the Ap has "unknown country
+    //code", or the domain of the country code doesn't match the default domain, the Ap is
+    //not acceptable.
+    tANI_BOOLEAN fEnforceDefaultDomain;     
+
+    tANI_U16 vccRssiThreshold;
+    tANI_U32 vccUlMacLossThreshold;
+
+    tANI_U32  nPassiveMinChnTime;    //in units of milliseconds
+    tANI_U32  nPassiveMaxChnTime;    //in units of milliseconds
+    tANI_U32  nActiveMinChnTime;     //in units of milliseconds
+    tANI_U32  nActiveMaxChnTime;     //in units of milliseconds
+
+    tANI_BOOLEAN IsIdleScanEnabled;
+    //in dBm, the maximum TX power
+    //The actual TX power is the lesser of this value and 11d. 
+    //If 11d is disable, the lesser of this and default setting.
+    tANI_U8 nTxPowerCap;     
+    tANI_U32  statsReqPeriodicity;  //stats request frequency from PE while in full power
+    tANI_U32  statsReqPeriodicityInPS;//stats request frequency from PE while in power save
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    tCsr11rConfigParams  csr11rConfig;
+#endif
+#ifdef FEATURE_WLAN_CCX
+    tANI_U8   isCcxIniFeatureEnabled;
+#endif
+
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+    tANI_U8   isFastTransitionEnabled;
+#endif
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+    tCsrNeighborRoamConfigParams    neighborRoamConfig;
+#endif
+
+    /* Instead of Reassoc, send ADDTS/DELTS even when ACM is off for that AC 
+     * This is mandated by WMM-AC certification */
+    tANI_BOOLEAN addTSWhenACMIsOff;
+
+    
+    /*channelPowerInfoList24 has been seen corrupted. Set this flag to true trying to 
+    * detect when it happens. Adding this into code because we can't reproduce it easily.
+    * We don't know when it happens. */
+    tANI_BOOLEAN fValidateList;
+
+    /*Customer wants to start with an active scan based on the default country code.
+    * This optimization will minimize the driver load to association time.
+    * Based on this flag we will bypass the initial passive scan needed for 11d
+    * to determine the country code & domain */
+    tANI_BOOLEAN fEnableBypass11d;
+
+    /*Customer wants to optimize the scan time. Avoiding scans(passive) on DFS 
+    * channels while swipping through both bands can save some time 
+    * (apprx 1.3 sec) */
+    tANI_BOOLEAN fEnableDFSChnlScan;
+
+    //To enable/disable scanning 2.4Ghz channels twice on a single scan request from HDD
+    tANI_BOOLEAN fScanTwice;
+
+}tCsrConfigParam;   
+
+//Tush
+typedef struct tagCsrUpdateConfigParam
+{
+   tCsr11dinfo  Csr11dinfo;
+}tCsrUpdateConfigParam;
+
+typedef struct tagCsrRoamInfo
+{
+    tCsrRoamProfile *pProfile;  //may be NULL
+    tSirBssDescription *pBssDesc;  //May be NULL
+    tANI_U32 nBeaconLength; //the length, in bytes, of the beacon frame, can be 0
+    tANI_U32 nAssocReqLength;   //the length, in bytes, of the assoc req frame, can be 0
+    tANI_U32 nAssocRspLength;   //The length, in bytes, of the assoc rsp frame, can be 0
+    tANI_U32 nFrameLength;
+    tANI_U8  frameType;
+    tANI_U8 *pbFrames;  //Point to a buffer contain the beacon, assoc req, assoc rsp frame, in that order
+                        //user needs to use nBeaconLength, nAssocReqLength, nAssocRspLength to desice where
+                        //each frame starts and ends.
+    tANI_BOOLEAN fReassocReq;   //set to true if for re-association
+    tANI_BOOLEAN fReassocRsp;   //set to true if for re-association
+    tCsrBssid bssid;
+    //Only valid in IBSS 
+    //this is the peers MAC address for eCSR_ROAM_RESULT_IBSS_NEW_PEER or PEER_DEPARTED
+    tCsrBssid peerMac;  
+    tSirResultCodes statusCode;
+    tANI_U32 reasonCode;    //this could be our own defined or sent from the other BSS(per 802.11 spec)
+    tANI_U8  staId;         // Peer stationId when connected
+    /*The DPU signatures will be sent eventually to TL to help it determine the 
+      association to which a packet belongs to*/
+    /*Unicast DPU signature*/
+    tANI_U8            ucastSig;
+
+    /*Broadcast DPU signature*/
+    tANI_U8            bcastSig;
+
+    tANI_BOOLEAN fAuthRequired;   //FALSE means auth needed from supplicant. TRUE means authenticated(static WEP, open)
+    tANI_U8 sessionId;
+    tANI_U8 rsnIELen;
+    tANI_U8 *prsnIE;
+
+    tANI_U8 addIELen;
+    tANI_U8 *paddIE;
+    
+    union
+    {
+        tSirMicFailureInfo *pMICFailureInfo;
+        tCsrRoamConnectedProfile *pConnectedProfile;
+#ifdef WLAN_SOFTAP_FEATURE
+        tSirWPSPBCProbeReq *pWPSPBCProbeReq;
+#endif
+    } u;
+
+#ifdef WLAN_SOFTAP_FEATURE
+    tANI_BOOLEAN wmmEnabledSta;   //set to true if WMM enabled STA
+    tANI_U32 dtimPeriod;
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+    tANI_BOOLEAN isCCXAssoc;
+#endif
+#ifdef WLAN_FEATURE_P2P
+    void* pRemainCtx; 
+    tANI_U32 rxChan;
+#endif
+
+    // Required for indicating the frames to upper layer
+    tANI_U32 beaconLength;
+    tANI_U8* beaconPtr;
+    tANI_U32 assocReqLength;
+    tANI_U8* assocReqPtr;    
+}tCsrRoamInfo;
+
+
+
+
+
+typedef struct tagCsrFreqScanInfo
+{
+    tANI_U32 nStartFreq;    //in unit of MHz
+    tANI_U32 nEndFreq;      //in unit of MHz
+    tSirScanType scanType;
+}tCsrFreqScanInfo;
+
+
+#ifdef WLAN_SOFTAP_FEATURE
+typedef struct sSirSmeAssocIndToUpperLayerCnf
+{
+    tANI_U16             messageType; // eWNI_SME_ASSOC_CNF
+    tANI_U16             length;
+    tANI_U8              sessionId;
+    tSirResultCodes      statusCode;
+    tSirMacAddr          bssId;      // Self BSSID
+    tSirMacAddr          peerMacAddr;
+    tANI_U16             aid;
+    tSirMacAddr          alternateBssId;
+    tANI_U8              alternateChannelId;
+    tANI_U8              wmmEnabledSta;   //set to true if WMM enabled STA
+    tSirRSNie            rsnIE;           // RSN IE received from peer
+    tSirAddie            addIE;           // Additional IE received from peer, which can be WSC and/or P2P IE
+    tANI_U8              reassocReq;      //set to true if reassoc
+} tSirSmeAssocIndToUpperLayerCnf, *tpSirSmeAssocIndToUpperLayerCnf;
+#endif
+
+typedef struct tagCsrSummaryStatsInfo
+{
+   tANI_U32 retry_cnt[4];
+   tANI_U32 multiple_retry_cnt[4];
+   tANI_U32 tx_frm_cnt[4];
+   //tANI_U32 num_rx_frm_crc_err; same as rx_error_cnt
+   //tANI_U32 num_rx_frm_crc_ok; same as rx_frm_cnt
+   tANI_U32 rx_frm_cnt;
+   tANI_U32 frm_dup_cnt;
+   tANI_U32 fail_cnt[4];
+   tANI_U32 rts_fail_cnt;
+   tANI_U32 ack_fail_cnt;
+   tANI_U32 rts_succ_cnt;
+   tANI_U32 rx_discard_cnt;
+   tANI_U32 rx_error_cnt;
+   tANI_U32 tx_byte_cnt;
+
+}tCsrSummaryStatsInfo;
+
+typedef struct tagCsrGlobalClassAStatsInfo
+{
+   tANI_U32 rx_frag_cnt;
+   tANI_U32 promiscuous_rx_frag_cnt;
+   //tANI_U32 rx_fcs_err;
+   tANI_U32 rx_input_sensitivity;
+   tANI_U32 max_pwr;
+   //tANI_U32 default_pwr;
+   tANI_U32 sync_fail_cnt;
+   tANI_U32 tx_rate;
+   //mcs index for HT20 and HT40 rates
+   tANI_U32  mcs_index;
+   //to defferentiate between HT20 and HT40 rates;short and long guard interval
+   tANI_U32  tx_rate_flags;
+
+}tCsrGlobalClassAStatsInfo;
+
+typedef struct tagCsrGlobalClassBStatsInfo
+{
+   tANI_U32 uc_rx_wep_unencrypted_frm_cnt;
+   tANI_U32 uc_rx_mic_fail_cnt;
+   tANI_U32 uc_tkip_icv_err;
+   tANI_U32 uc_aes_ccmp_format_err;
+   tANI_U32 uc_aes_ccmp_replay_cnt;
+   tANI_U32 uc_aes_ccmp_decrpt_err;
+   tANI_U32 uc_wep_undecryptable_cnt;
+   tANI_U32 uc_wep_icv_err;
+   tANI_U32 uc_rx_decrypt_succ_cnt;
+   tANI_U32 uc_rx_decrypt_fail_cnt;
+   tANI_U32 mcbc_rx_wep_unencrypted_frm_cnt;
+   tANI_U32 mcbc_rx_mic_fail_cnt;
+   tANI_U32 mcbc_tkip_icv_err;
+   tANI_U32 mcbc_aes_ccmp_format_err;
+   tANI_U32 mcbc_aes_ccmp_replay_cnt;
+   tANI_U32 mcbc_aes_ccmp_decrpt_err;
+   tANI_U32 mcbc_wep_undecryptable_cnt;
+   tANI_U32 mcbc_wep_icv_err;
+   tANI_U32 mcbc_rx_decrypt_succ_cnt;
+   tANI_U32 mcbc_rx_decrypt_fail_cnt;
+
+}tCsrGlobalClassBStatsInfo;
+
+typedef struct tagCsrGlobalClassCStatsInfo
+{
+   tANI_U32 rx_amsdu_cnt;
+   tANI_U32 rx_ampdu_cnt;
+   tANI_U32 tx_20_frm_cnt;
+   tANI_U32 rx_20_frm_cnt;
+   tANI_U32 rx_mpdu_in_ampdu_cnt;
+   tANI_U32 ampdu_delimiter_crc_err;
+
+}tCsrGlobalClassCStatsInfo;
+
+typedef struct tagCsrGlobalClassDStatsInfo
+{
+   tANI_U32 tx_uc_frm_cnt;
+   tANI_U32 tx_mc_frm_cnt;
+   tANI_U32 tx_bc_frm_cnt;
+   tANI_U32 rx_uc_frm_cnt;
+   tANI_U32 rx_mc_frm_cnt;
+   tANI_U32 rx_bc_frm_cnt;
+   tANI_U32 tx_uc_byte_cnt[4];
+   tANI_U32 tx_mc_byte_cnt;
+   tANI_U32 tx_bc_byte_cnt;
+   tANI_U32 rx_uc_byte_cnt[4];
+   tANI_U32 rx_mc_byte_cnt;
+   tANI_U32 rx_bc_byte_cnt;
+   tANI_U32 rx_byte_cnt;
+   tANI_U32 num_rx_bytes_crc_ok;
+   tANI_U32 rx_rate;
+
+}tCsrGlobalClassDStatsInfo;
+
+typedef struct tagCsrPerStaStatsInfo
+{
+   tANI_U32 tx_frag_cnt[4];
+   tANI_U32 tx_ampdu_cnt;
+   tANI_U32 tx_mpdu_in_ampdu_cnt;
+} tCsrPerStaStatsInfo;
+
+typedef struct tagCsrRoamSetKey
+{
+    eCsrEncryptionType encType;
+    tAniKeyDirection keyDirection;    //Tx, Rx or Tx-and-Rx
+    tCsrBssid peerMac;   //Peers MAC address. ALL 1's for group key
+    tANI_U8 paeRole;      //0 for supplicant
+    tANI_U8 keyId;  // Kye index
+    tANI_U16 keyLength;  //Number of bytes containing the key in pKey
+    tANI_U8 Key[CSR_MAX_KEY_LEN];
+    tANI_U8 keyRsc[CSR_MAX_RSC_LEN];
+} tCsrRoamSetKey;
+
+typedef struct tagCsrRoamRemoveKey
+{
+    eCsrEncryptionType encType;
+    tCsrBssid peerMac;   //Peers MAC address. ALL 1's for group key
+    tANI_U8 keyId;  //key index
+} tCsrRoamRemoveKey;
+
+
+typedef void * tScanResultHandle;
+
+#define CSR_INVALID_SCANRESULT_HANDLE       (NULL)
+
+
+
+////////////////////////////////////////////Common SCAN starts
+
+//void *p2 -- the second context pass in for the caller
+//***what if callback is called before requester gets the scanId??
+typedef eHalStatus (*csrScanCompleteCallback)(tHalHandle, void *p2, tANI_U32 scanID, eCsrScanStatus status);   
+
+
+
+///////////////////////////////////////////Common Roam starts
+
+//pContext is the pContext passed in with the roam request
+//pParam is a pointer to a tCsrRoamInfo, see definition of eRoamCmdStatus and
+//   eRoamCmdResult for detail valid members. It may be NULL
+//roamId is to identify the callback related roam request. 0 means unsolicit
+//roamStatus is a flag indicating the status of the callback
+//roamResult is the result
+typedef eHalStatus (*csrRoamCompleteCallback)(void *pContext, tCsrRoamInfo *pParam, tANI_U32 roamId, 
+                                              eRoamCmdStatus roamStatus, eCsrRoamResult roamResult);
+
+typedef eHalStatus (*csrRoamSessionCloseCallback)(void *pContext);   
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetNumPMKIDCache
+    \brief return number of PMKID cache entries
+    \return tANI_U32 - the number of PMKID cache entries
+  -------------------------------------------------------------------------------*/
+//tANI_U32 csrRoamGetNumPMKIDCache(tHalHandle hHal);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetPMKIDCache
+    \brief return PMKID cache from CSR
+    \param pNum - caller allocated memory that has the space of the number of pBuf tPmkidCacheInfo as input. Upon returned, *pNum has the 
+    needed or actually number in tPmkidCacheInfo.
+    \param pPmkidCache - Caller allocated memory that contains PMKID cache, if any, upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not big enough
+  -------------------------------------------------------------------------------*/
+//eHalStatus csrRoamGetPMKIDCache(tHalHandle hHal, tANI_U32 *pNum, tPmkidCacheInfo *pPmkidCache);
+
+//pProfile - pointer to tCsrRoamProfile
+#define CSR_IS_START_IBSS(pProfile) (eCSR_BSS_TYPE_START_IBSS == (pProfile)->BSSType)
+#define CSR_IS_JOIN_TO_IBSS(pProfile) (eCSR_BSS_TYPE_IBSS == (pProfile)->BSSType)
+#define CSR_IS_IBSS(pProfile) ( CSR_IS_START_IBSS(pProfile) || CSR_IS_JOIN_TO_IBSS(pProfile) )
+#define CSR_IS_INFRASTRUCTURE(pProfile) (eCSR_BSS_TYPE_INFRASTRUCTURE == (pProfile)->BSSType)
+#define CSR_IS_ANY_BSS_TYPE(pProfile) (eCSR_BSS_TYPE_ANY == (pProfile)->BSSType)
+#define CSR_IS_WDS_AP( pProfile )  ( eCSR_BSS_TYPE_WDS_AP == (pProfile)->BSSType )
+#define CSR_IS_WDS_STA( pProfile ) ( eCSR_BSS_TYPE_WDS_STA == (pProfile)->BSSType )
+#define CSR_IS_WDS( pProfile )  ( CSR_IS_WDS_AP( pProfile ) || CSR_IS_WDS_STA( pProfile ) )
+#ifdef WLAN_SOFTAP_FEATURE
+#define CSR_IS_INFRA_AP( pProfile )  ( eCSR_BSS_TYPE_INFRA_AP == (pProfile)->BSSType )
+#endif
+
+//pProfile - pointer to tCsrRoamConnectedProfile
+#ifdef WLAN_SOFTAP_FEATURE
+#define CSR_IS_CONN_INFRA_AP( pProfile )  ( eCSR_BSS_TYPE_INFRA_AP == (pProfile)->BSSType )
+#endif
+#define CSR_IS_CONN_WDS_AP( pProfile )  ( eCSR_BSS_TYPE_WDS_AP == (pProfile)->BSSType )
+#define CSR_IS_CONN_WDS_STA( pProfile ) ( eCSR_BSS_TYPE_WDS_STA == (pProfile)->BSSType )
+#define CSR_IS_CONN_WDS( pProfile )  ( CSR_IS_WDS_AP( pProfile ) || CSR_IS_WDS_STA( pProfile ) )
+
+
+
+///////////////////////////////////////////Common Roam ends
+
+
+
+#ifdef WLAN_SOFTAP_FEATURE
+/* ---------------------------------------------------------------------------
+    \fn csrSetChannels
+    \brief HDD calls this function to change some global settings. 
+    caller must set the all fields or call csrGetConfigParam to prefill the fields.
+    \param pParam - caller allocated memory
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+
+eHalStatus csrSetChannels(tHalHandle hHal,  tCsrConfigParam *pParam  );
+
+eHalStatus csrSetRegInfo(tHalHandle hHal,  tANI_U8 *apCntryCode);
+#endif
+
+
+//enum to string conversion for debug output
+const char * get_eRoamCmdStatus_str(eRoamCmdStatus val);
+const char * get_eCsrRoamResult_str(eCsrRoamResult val);
+/* ---------------------------------------------------------------------------
+    \fn csrSetPhyMode
+    \brief HDD calls this function to set the phyMode.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    CSR.
+    \param phyMode - indicate the phyMode needs to set to. The value has to be either 0, or some bits set. 
+    See eCsrPhyMode for definition
+    \param eBand - specify the operational band (2.4, 5 or both)
+    \param pfRestartNeeded - pointer to a caller allocated space. Upon successful return, it indicates whether 
+    a restart is needed to apply the change
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrSetPhyMode(tHalHandle hHal, tANI_U32 phyMode, eCsrBand eBand, tANI_BOOLEAN *pfRestartNeeded);
+
+void csrDumpInit(tHalHandle hHal);
+
+
+/*---------------------------------------------------------------------------
+  This is the type for a link quality callback to be registered with SME
+  for indications
+  Once the link quality has been indicated, subsequently, link indications are 
+  posted each time there is a CHANGE in link quality.
+  *** If there is no change in link, there will be no indication ***
+
+  The indications may be based on one or more criteria internal to SME
+  such as RSSI and PER.
+
+  \param ind - Indication being posted
+  \param pContext - any user data given at callback registration.  
+  \return None
+  
+---------------------------------------------------------------------------*/
+typedef void (* csrRoamLinkQualityIndCallback)
+             (eCsrRoamLinkQualityInd  ind, void *pContext);
+
+
+/*---------------------------------------------------------------------------
+  This is the type for a statistics callback to be registered with SME
+  for stats reporting
+
+  Since the client requesting for the stats already know which class/type of 
+  stats it asked for, the callback will carry them in the rsp buffer 
+  (void * stats) whose size will be same as the size of requested stats & 
+  will be exactly in the same order requested in the stats mask from LSB to MSB
+
+  \param stats - stats rsp buffer sent back with the report
+  \param pContext - any user data given at callback registration.  
+  \return None
+  
+---------------------------------------------------------------------------*/
+typedef void ( *tCsrStatsCallback) (void * stats, void *pContext);
+
+/*---------------------------------------------------------------------------
+  This is the type for a rssi callback to be registered with SME
+  for getting rssi
+
+  \param rssi - rssi
+  \param pContext - any user data given at callback registration.  
+  \return None
+  
+---------------------------------------------------------------------------*/
+
+typedef void ( *tCsrRssiCallback) (v_S7_t rssi, tANI_U32 staId, void *pContext);
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+eHalStatus csrRoamIssueFTPreauthReq(tHalHandle hHal, tANI_U32 sessionId, tpSirBssDescription pBssDescription);
+#endif
+
+/*---------------------------------------------------------------------------
+  This is the function to change the Band configuraiton (ALL/2.4 GHZ/5 GHZ) 
+
+  \param hHal - handle to Hal context 
+  \param eBand - band value
+  \return  eHalStatus
+  
+---------------------------------------------------------------------------*/
+eHalStatus csrSetBand(tHalHandle hHal, eCsrBand eBand);
+
+/*---------------------------------------------------------------------------
+  This is the function to get the current operating band value
+  \param hHal - handl to Hal context
+  \return eCsrband - band value
+  
+---------------------------------------------------------------------------*/
+eCsrBand csrGetCurrentBand (tHalHandle hHal);
+
+#endif
+
diff --git a/CORE/SME/inc/csrInternal.h b/CORE/SME/inc/csrInternal.h
new file mode 100644
index 0000000..9fc423d
--- /dev/null
+++ b/CORE/SME/inc/csrInternal.h
@@ -0,0 +1,1177 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+
+  
+    \file csrInternal.h
+  
+    Define internal data structure for MAC.
+  
+    Copyright (C) 2006 Airgo Networks, Incorporated 
+   ========================================================================== */
+#ifndef CSRINTERNAL_H__
+#define CSRINTERNAL_H__
+
+#if defined(VOSS_ENABLED)
+#include "vos_status.h"
+#include "vos_lock.h"
+#endif //#if defined(VOSS_ENABLED)
+
+#include "palTimer.h"
+#include "csrSupport.h"
+#include "vos_nvitem.h"
+#include "wlan_qct_tl.h"
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+#include "csrNeighborRoam.h"
+#endif
+
+#define CSR_MAX_STA (HAL_NUM_STA)
+
+#define CSR_SME_SCAN_FLAGS_DELETE_CACHE     0x80
+
+#define CSR_TITAN_MAX_RATE_MIMO_CB 240
+#define CSR_TITAN_MAX_RATE_MIMO    126
+
+//define scan return criteria. LIM should use these define as well
+#define CSR_SCAN_RETURN_AFTER_ALL_CHANNELS          (    0 )
+#define CSR_SCAN_RETURN_AFTER_FIRST_MATCH           ( 0x01 )
+#define CSR_SCAN_RETURN_AFTER_5_BAND_11d_FOUND      ( 0x80 )
+#define CSR_SCAN_RETURN_AFTER_24_BAND_11d_FOUND     ( 0x40 )
+#define CSR_SCAN_RETURN_AFTER_EITHER_BAND_11d_FOUND ( CSR_SCAN_RETURN_AFTER_5_BAND_11d_FOUND | CSR_SCAN_RETURN_AFTER_24_BAND_11d_FOUND )
+#define CSR_NUM_RSSI_CAT        5
+#define CSR_MAX_STATISTICS_REQ        10
+
+//Support for multiple session
+#define CSR_SESSION_ID_INVALID    0xFF   // session ID invalid
+#define CSR_ROAM_SESSION_MAX      5   // No of sessions to be supported, and a
+                                      // session is for Infra, IBSS or BT-AMP
+
+#define CSR_IS_SESSION_VALID( pMac, sessionId ) ( ( (sessionId) < CSR_ROAM_SESSION_MAX ) \
+                                                  && ( (pMac)->roam.roamSession[(sessionId)].sessionActive ) )
+#define CSR_GET_SESSION( pMac, sessionId ) \
+( \
+    (sessionId < CSR_ROAM_SESSION_MAX) ? \
+     (&(pMac)->roam.roamSession[(sessionId)]) :\
+     NULL \
+)
+
+
+
+typedef enum
+{
+    //eCSR_CFG_DOT11_MODE_BEST = 0,
+    eCSR_CFG_DOT11_MODE_TAURUS = 0,
+    eCSR_CFG_DOT11_MODE_ABG,    
+    eCSR_CFG_DOT11_MODE_11A,    
+    eCSR_CFG_DOT11_MODE_11B,    
+    eCSR_CFG_DOT11_MODE_11G,    
+    eCSR_CFG_DOT11_MODE_11N,   
+    eCSR_CFG_DOT11_MODE_POLARIS,    
+    eCSR_CFG_DOT11_MODE_TITAN,    
+#ifdef WLAN_SOFTAP_FEATURE
+    eCSR_CFG_DOT11_MODE_11G_ONLY,    
+    eCSR_CFG_DOT11_MODE_11N_ONLY,   
+#endif 
+    //This value can never set to CFG. It is for CSR's internal use
+    eCSR_CFG_DOT11_MODE_AUTO,
+}eCsrCfgDot11Mode;  //Used to determine what to set to the WNI_CFG_DOT11_MODE
+
+typedef enum etCsrRoamCommands 
+{
+    eCsrRoamNoCommand,                 
+    eCsrRoamCommandScan,
+    eCsrRoamCommandRoam, 
+    eCsrRoamCommandWmStatusChange, 
+    eCsrRoamCommandSetKey,
+    eCsrRoamCommandRemoveKey,
+
+} eCsrRoamCommands;
+
+typedef enum  
+{
+    eCsrScanOther = 1,
+    eCsrScanLostLink1,
+    eCsrScanLostLink2,
+    eCsrScanLostLink3,
+    eCsrScanLostLink4,
+    eCsrScan11d1,  //First 11d scan
+    eCsrScan11d2,  //First 11d scan has failed
+    eCsrScan11dDone,  //11d scan succeeded, try the rest of the channel
+    eCsrScanUserRequest,
+    eCsrScanGetResult,
+    eCsrScanSetBGScanParam, //used for HO too - bg scan request in NT Handoff sub-state
+    eCsrScanForSsid,
+    eCsrScanForCapsChange,
+    eCsrScanBGScanAbort,
+    eCsrScanBGScanEnable,
+    eCsrScanIdleScan,
+    eCsrScanGetScanChnInfo,     //To get the list of channels scanned
+
+    eCsrScanBgScan, // bg scan request in NRT & RT Handoff sub-states
+    eCsrScanProbeBss, // directed probe on an entry from the candidate list - HO
+    eCsrScanAbortBgScan,    //aborting a BG scan (meaning the scan is triggered by LIM timer)
+    eCsrScanAbortNormalScan, //aborting a normal scan (the scan is trigger by eWNI_SME_SCAN_REQ)
+    eCsrScanP2PFindPeer    
+}eCsrScanReason;
+
+typedef enum 
+{
+    eCsrNoConnection,          // Roaming because we have not established the initial connection.
+    eCsrCapsChange,            // roaming because LIM reported a Capability change in the associated AP.
+    eCsrForcedDisassoc,        // roaming becuase someone asked us to Disassoc and stay disassociated.
+    eCsrHddIssued,             // roaming because an 802.11 request was issued to the driver.
+    eCsrLostLink1,             // roaming because we lost link to an associated AP
+    eCsrLostLink2, 
+    eCsrLostLink3,
+    eCsrForcedDisassocMICFailure, // roaming because we need to force a Disassoc due to MIC failure
+    eCsrHddIssuedReassocToSameAP,
+    eCsrSmeIssuedReassocToSameAP,
+    eCsrSmeIssuedReassocToDiffAP,
+    eCsrForcedDeauth,        // roaming becuase someone asked us to deauth and stay disassociated.
+    eCsrSmeIssuedDisassocForHandoff, // will be issued by Handoff logic to disconect from current AP
+    eCsrSmeIssuedAssocToSimilarAP, // will be issued by Handoff logic to join a new AP with same profile
+    eCsrSmeIssuedIbssJoinFailure, // ibss join timer fired before any perr showed up, so shut down the network
+    eCsrForcedIbssLeave,
+    eCsrStopBss,
+    eCsrSmeIssuedFTReassoc,
+    eCsrForcedDisassocSta,
+    eCsrForcedDeauthSta,
+    
+}eCsrRoamReason;
+
+typedef enum
+{
+    eCSR_ROAM_SUBSTATE_NONE = 0,                 
+    eCSR_ROAM_SUBSTATE_START_BSS_REQ,            
+    eCSR_ROAM_SUBSTATE_JOIN_REQ,                 
+    eCSR_ROAM_SUBSTATE_REASSOC_REQ,              
+    eCSR_ROAM_SUBSTATE_DISASSOC_REQ,             
+    eCSR_ROAM_SUBSTATE_STOP_BSS_REQ,             
+    eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING,   //Continue the current roam command after disconnect            
+    eCSR_ROAM_SUBSTATE_AUTH_REQ,                 
+    eCSR_ROAM_SUBSTATE_CONFIG,                   
+    eCSR_ROAM_SUBSTATE_DEAUTH_REQ,               
+    eCSR_ROAM_SUBSTATE_DISASSOC_NOTHING_TO_JOIN, 
+    eCSR_ROAM_SUBSTATE_DISASSOC_REASSOC_FAILURE, 
+    eCSR_ROAM_SUBSTATE_DISASSOC_FORCED,          
+    eCSR_ROAM_SUBSTATE_WAIT_FOR_KEY,
+    eCSR_ROAM_SUBSTATE_DISASSOC_HANDOFF,
+    eCSR_ROAM_SUBSTATE_JOINED_NO_TRAFFIC,
+    eCSR_ROAM_SUBSTATE_JOINED_NON_REALTIME_TRAFFIC,
+    eCSR_ROAM_SUBSTATE_JOINED_REALTIME_TRAFFIC,
+//  max is 15 unless the bitfield is expanded...
+} eCsrRoamSubState;
+
+
+typedef enum 
+{
+  eCSR_ROAMING_STATE_STOP = 0,
+  eCSR_ROAMING_STATE_IDLE,
+  eCSR_ROAMING_STATE_SCANNING,
+  eCSR_ROAMING_STATE_JOINING,
+  eCSR_ROAMING_STATE_JOINED,
+}eCsrRoamState;
+
+
+typedef enum 
+{
+    eCsrContinueRoaming,
+    eCsrStopRoaming,
+    eCsrStartIbss,
+    eCsrStartIbssSameIbss,
+    eCsrReassocToSelfNoCapChange,
+    
+}eCsrJoinState;
+
+typedef enum
+{
+    eCsrNotRoaming,
+    eCsrLostlinkRoamingDisassoc,
+    eCsrLostlinkRoamingDeauth,
+    eCsrDynamicRoaming,
+   eCsrReassocRoaming,
+}eCsrRoamingReason;
+
+typedef enum 
+{
+    eCsrDisassociated,
+    eCsrDeauthenticated
+
+}eCsrRoamWmStatusChangeTypes;
+
+typedef enum
+{
+   eCsrSummaryStats = 0,
+   eCsrGlobalClassAStats,
+   eCsrGlobalClassBStats,
+   eCsrGlobalClassCStats,
+   eCsrGlobalClassDStats,
+   eCsrPerStaStats,
+   eCsrMaxStats
+}eCsrRoamStatsClassTypes;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+typedef enum
+{
+   eCSR_WLAN_STATUS_CONNECT =0,
+   eCSR_WLAN_STATUS_DISCONNECT
+
+}eCsrDiagWlanStatusEventSubtype;
+
+typedef enum
+{
+   eCSR_REASON_UNSPECIFIED = 0,
+   eCSR_REASON_USER_REQUESTED,
+   eCSR_REASON_MIC_ERROR,
+   eCSR_REASON_DISASSOC,
+   eCSR_REASON_DEAUTH,
+   eCSR_REASON_HANDOFF,
+
+}eCsrDiagWlanStatusEventReason;
+
+typedef enum
+{
+   eCSR_WLAN_HANDOFF_EVENT =0,
+
+}eCsrDiagWlanHandoffEventSubtype;
+
+typedef enum
+{
+   eCSR_WLAN_VCC_EVENT =0,
+
+}eCsrDiagWlanVccEventSubtype;
+
+#endif //FEATURE_WLAN_DIAG_SUPPORT
+
+typedef struct tagCsrChannel
+{
+    tANI_U8 numChannels;
+    tANI_U8 channelList[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+}tCsrChannel;
+
+typedef struct tagScanProfile
+{
+    tANI_U32 minChnTime;
+    tANI_U32 maxChnTime;
+    tANI_U32 restTime;  //This is ignored if not associated
+    tANI_U32 numOfChannels;
+    tANI_U8 *pChannelList;
+    tSirScanType scanType;  //active or passive
+    eCsrRoamBssType bssType;    //BSS or IBSS
+    tANI_U8 ssid[WNI_CFG_SSID_LEN];
+    tANI_U8 bReturnAfter1stMatch;
+    tANI_U8 fUniqueResult;
+    tANI_U8 freshScan;
+    tCsrBssid bssid;
+}tScanProfile;
+
+typedef struct tagBssConfigParam
+{
+    eCsrMediaAccessType qosType;
+    tSirMacSSid SSID;
+    tANI_U32 uRTSThresh;
+    tANI_U32 uDeferThresh;  //
+    eCsrCfgDot11Mode uCfgDot11Mode;
+    eCsrBand eBand;
+    tANI_U8 standardRate[CSR_DOT11_SUPPORTED_RATES_MAX];
+    tANI_U8 extendedRate[CSR_DOT11_EXTENDED_SUPPORTED_RATES_MAX];
+    eCsrExposedTxRate txRate;
+    tAniAuthType authType;
+    eCsrEncryptionType encType;
+    tANI_U32 uShortSlotTime;
+    tANI_U32 uHTSupport;    //High throughput
+    tANI_U32 uPowerLimit;
+    tANI_U32 uHeartBeatThresh;
+    tANI_U32 uJoinTimeOut;
+    tSirMacCapabilityInfo BssCap;
+    tANI_BOOLEAN f11hSupport;
+    tAniCBSecondaryMode cbMode;
+}tBssConfigParam;
+
+
+typedef struct tagCsrRoamStartBssParams
+{
+    tSirMacSSid         ssId;
+    tCsrBssid           bssid;    //this is the BSSID for the party we want to join (only use for IBSS or WDS)
+    tSirNwType          sirNwType;
+    tAniCBSecondaryMode cbMode;
+    tSirMacRateSet      operationalRateSet;
+    tSirMacRateSet      extendedRateSet;
+    tANI_U8             operationChn;
+    eCsrCfgDot11Mode    uCfgDot11Mode;
+#ifdef WLAN_SOFTAP_FEATURE
+    tANI_U8             privacy;
+    tANI_BOOLEAN        fwdWPSPBCProbeReq;
+    tANI_BOOLEAN        protEnabled;
+    tANI_BOOLEAN        obssProtEnabled;
+    tAniAuthType        authType;
+    tANI_U16            beaconInterval;    //If this is 0, SME will fill in for caller.
+    tANI_U16            ht_protection;
+    tANI_U32            dtimPeriod;
+    tANI_U8             ApUapsdEnable;
+    tANI_U8             ssidHidden;
+    tANI_U8             wps_state;
+#endif
+    tVOS_CON_MODE       bssPersona;
+    tANI_U16            nRSNIELength;  //The byte count in the pRSNIE, if 0, pRSNIE is ignored.
+    tANI_U8             *pRSNIE;     //If not null, it has the IE byte stream for RSN
+}tCsrRoamStartBssParams;
+
+
+typedef struct tagScanCmd
+{
+    tANI_U32                scanID;
+    csrScanCompleteCallback callback;
+    void                    *pContext;
+    eCsrScanReason          reason;
+    eCsrRoamState           lastRoamState[CSR_ROAM_SESSION_MAX];
+    tCsrRoamProfile         *pToRoamProfile;
+    tANI_U32                roamId;    //this is the ID related to the pToRoamProfile
+    union
+    {
+        tCsrScanRequest   scanRequest;
+        tCsrBGScanRequest bgScanRequest;
+    }u;
+}tScanCmd;
+
+typedef struct tagRoamCmd 
+{
+    tANI_U32 roamId;
+    eCsrRoamReason roamReason;
+    tCsrRoamProfile roamProfile;
+    tScanResultHandle hBSSList;     //BSS list fits the profile
+    tListElem *pRoamBssEntry;  //point to the current BSS in the list that is roaming. It starts from head to tail        
+    tSirBssDescription *pLastRoamBss;   //the last BSS we try and failed
+    tANI_BOOLEAN fReleaseBssList;  //whether to free hBSSList 
+    tANI_BOOLEAN fReleaseProfile;  //whether to free roamProfile
+    tANI_BOOLEAN fReassoc;  //whether this command is for reassociation
+    tANI_BOOLEAN fUpdateCurRoamProfile;     //whether pMac->roam.pCurRoamProfile needs to be updated
+    //this is for CSR internal used only. And it should not be assigned when creating the command
+    //This causes the roam command not to do anything.
+    tANI_BOOLEAN fReassocToSelfNoCapChange;    
+
+    tANI_BOOLEAN fStopWds;
+    tSirMacAddr peerMac;
+    tSirMacReasonCodes reason;
+}tRoamCmd;
+
+typedef struct tagSetKeyCmd
+{
+    tANI_U32 roamId;
+    eCsrEncryptionType encType;
+    eCsrAuthType authType;
+    tAniKeyDirection keyDirection;    //Tx, Rx or Tx-and-Rx
+    tSirMacAddr peerMac;   //Peer's MAC address. ALL 1's for group key
+    tANI_U8 paeRole;      //0 for supplicant
+    tANI_U8 keyId;  // Kye index
+    tANI_U8 keyLength;  //Number of bytes containing the key in pKey
+    tANI_U8 Key[CSR_MAX_KEY_LEN];
+    tANI_U8 keyRsc[CSR_MAX_RSC_LEN];
+} tSetKeyCmd;
+
+typedef struct tahRemoveKeyCmd
+{
+    tANI_U32 roamId;
+    eCsrEncryptionType encType;
+    eCsrAuthType authType;
+    tSirMacAddr peerMac;   //Peer's MAC address. ALL 1's for group key
+    tANI_U8 keyId;  //key index
+} tRemoveKeyCmd;
+
+typedef struct tagWmStatusChangeCmd 
+{
+    eCsrRoamWmStatusChangeTypes Type;
+    union 
+    {    
+        tSirSmeDeauthInd   DeauthIndMsg;
+        tSirSmeDisassocInd DisassocIndMsg;
+    }u;    
+
+}tWmStatusChangeCmd;
+
+typedef struct tagAddStaForSessionCmd
+{
+   //Session self mac addr
+   tSirMacAddr selfMacAddr;
+}tAddStaForSessionCmd;
+
+typedef struct tagDelStaForSessionCmd
+{
+   //Session self mac addr
+   tSirMacAddr selfMacAddr;
+   csrRoamSessionCloseCallback callback;
+   void *pContext;
+}tDelStaForSessionCmd;
+
+//This structure represents one scan request
+typedef struct tagCsrCmd
+{
+    tListElem Link;
+    eCsrRoamCommands command;
+    tANI_U8 sessionId;              // Session ID for this command
+    union
+    {
+        tScanCmd scanCmd;
+        tRoamCmd roamCmd;
+        tWmStatusChangeCmd wmStatusChangeCmd;
+        tSetKeyCmd setKeyCmd;
+        tRemoveKeyCmd removeKeyCmd;
+        tAddStaForSessionCmd addStaSessionCmd;
+        tDelStaForSessionCmd delStaSessionCmd;
+    }u;
+}tCsrCmd;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+typedef struct tagCsr11rConfig
+{
+    tANI_BOOLEAN   IsFTResourceReqSupported;
+} tCsr11rConfig;
+#endif
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+typedef struct tagCsrNeighborRoamConfig
+{
+    tANI_U32       nNeighborScanTimerPeriod;
+    tANI_U8        nNeighborLookupRssiThreshold;
+    tANI_U8        nNeighborReassocRssiThreshold;
+    tANI_U16       nNeighborScanMinChanTime;
+    tANI_U16       nNeighborScanMaxChanTime;
+    sCsrChannel    neighborScanChanList;
+    tANI_U8        nMaxNeighborRetries;
+    tANI_U16       nNeighborResultsRefreshPeriod;
+}tCsrNeighborRoamConfig;
+#endif
+
+typedef struct tagCsrConfig
+{
+    tANI_U32 agingCount;
+    tANI_U32 FragmentationThreshold;
+    tANI_U32 channelBondingMode24GHz;
+    tANI_U32 channelBondingMode5GHz;
+    tANI_U32 RTSThreshold;
+    eCsrPhyMode phyMode;
+    eCsrCfgDot11Mode uCfgDot11Mode;
+    eCsrBand eBand;
+    tANI_U32 HeartbeatThresh50;
+    tANI_U32 HeartbeatThresh24;
+    tANI_U32 bgScanInterval;
+    eCsrCBChoice cbChoice;
+    eCsrBand bandCapability;     //indicate hw capability
+    eCsrRoamWmmUserModeType WMMSupportMode;
+    tANI_BOOLEAN Is11eSupportEnabled;
+    tANI_BOOLEAN Is11dSupportEnabled;
+    tANI_BOOLEAN Is11dSupportEnabledOriginal;
+    tANI_BOOLEAN Is11hSupportEnabled;
+    tANI_BOOLEAN shortSlotTime;
+    tANI_BOOLEAN ProprietaryRatesEnabled;
+    tANI_BOOLEAN  fenableMCCMode;
+    tANI_U16 TxRate;
+    tANI_U8 AdHocChannel24;
+    tANI_U8 AdHocChannel5G;
+    tANI_U32 impsSleepTime;     //in units of microseconds
+    tANI_U32 scanAgeTimeNCNPS;  //scan result aging time threshold when Not-Connect-No-Power-Save, in seconds
+    tANI_U32 scanAgeTimeNCPS;   //scan result aging time threshold when Not-Connect-Power-Save, in seconds
+    tANI_U32 scanAgeTimeCNPS;   //scan result aging time threshold when Connect-No-Power-Save, in seconds,
+    tANI_U32 scanAgeTimeCPS;   //scan result aging time threshold when Connect-Power-Savein seconds
+    tANI_U32 BssPreferValue[CSR_NUM_RSSI_CAT];  //each RSSI category has one value
+    int RSSICat[CSR_NUM_RSSI_CAT];
+    tANI_U8 bCatRssiOffset;     //to set the RSSI difference for each category
+    tANI_U32 nRoamingTime;  //In seconds, CSR will try this long before gives up, 0 means no roaming
+    //Whether to limit the channels to the ones set in Csr11dInfo. If true, the opertaional
+    //channels are limited to the default channel list. It is an "AND" operation between the 
+    //default channels and the channels in the 802.11d IE.
+    tANI_BOOLEAN fEnforce11dChannels;   
+    //Country Code Priority
+    //0 = 802.11D > Configured Country > NV 
+    //1 = Configured Country > 802.11D > NV
+    tANI_BOOLEAN fSupplicantCountryCodeHasPriority;
+    //When true, AP with unknown country code won't be see. 
+    //"Unknown country code" means either Ap doesn't have 11d IE or we cannot 
+    //find a domain for the country code in its 11d IE.
+    tANI_BOOLEAN fEnforceCountryCodeMatch;  
+    //When true, only APs in the default domain can be seen. If the Ap has "unknown country
+    //code", or the doamin of the country code doesn't match the default domain, the Ap is
+    //not acceptable.
+    tANI_BOOLEAN fEnforceDefaultDomain;     
+
+    tANI_U16 vccRssiThreshold;
+    tANI_U32 vccUlMacLossThreshold;
+
+    tANI_U32  nPassiveMinChnTime;    //in units of milliseconds
+    tANI_U32  nPassiveMaxChnTime;    //in units of milliseconds
+    tANI_U32  nActiveMinChnTime;     //in units of milliseconds
+    tANI_U32  nActiveMaxChnTime;     //in units of milliseconds
+
+    tANI_BOOLEAN IsIdleScanEnabled;
+    //in dBm, the maximum TX power
+    //The actual TX power is the lesser of this value and 11d. 
+    //If 11d is disable, the lesser of this and default setting.
+    tANI_U8 nTxPowerCap;
+    tANI_U32  statsReqPeriodicity;  //stats request frequency from PE while in full power
+    tANI_U32  statsReqPeriodicityInPS;//stats request frequency from PE while in power save
+#ifdef WLAN_SOFTAP_FEATURE
+    tANI_U32 dtimPeriod;
+    tANI_BOOLEAN    ssidHidden;
+#endif
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    tCsr11rConfig csr11rConfig;
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+    tANI_U8   isCcxIniFeatureEnabled;
+#endif
+
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+    tANI_U8   isFastTransitionEnabled;
+#endif
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+    tCsrNeighborRoamConfig neighborRoamConfig;
+#endif
+
+    /* Instead of Reassoc, send ADDTS/DELTS even when ACM is off for that AC 
+     * This is mandated by WMM-AC certification */
+    tANI_BOOLEAN addTSWhenACMIsOff;
+
+    tANI_BOOLEAN fValidateList;
+    tANI_BOOLEAN concurrencyEnabled;
+
+    //To enable/disable scanning 2.4Ghz channels twice on a single scan request from HDD
+    tANI_BOOLEAN fScanTwice;
+
+}tCsrConfig;
+
+typedef struct tagCsrChannelPowerInfo 
+{
+    tListElem link;
+    tANI_U8 firstChannel;
+    tANI_U8 numChannels;
+    tANI_U8 txPower;
+    tANI_U8 interChannelOffset;
+}tCsrChannelPowerInfo;
+
+typedef struct tagRoamJoinStatus
+{
+    tSirResultCodes statusCode;
+    //this is set to unspecified if statusCode indicates timeout. Or it is the failed reason from the other BSS(per 802.11 spec)
+    tANI_U32 reasonCode;    
+}tCsrRoamJoinStatus;
+
+typedef struct tagCsrOsChannelMask
+{
+    tANI_U8 numChannels;
+    tANI_BOOLEAN scanEnabled[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+    tANI_U8 channelList[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+}tCsrOsChannelMask;
+
+
+typedef struct tagCsrScanStruct
+{
+    tScanProfile scanProfile;
+    tANI_U32 nextScanID;
+    tDblLinkList scanResultList;
+    tDblLinkList tempScanResults;
+    tANI_BOOLEAN fScanEnable;
+    tANI_BOOLEAN fFullScanIssued;
+    tPalTimerHandle hTimerGetResult;
+#ifdef WLAN_AP_STA_CONCURRENCY
+    tPalTimerHandle hTimerStaApConcTimer;
+#endif
+    tPalTimerHandle hTimerIdleScan;
+    tPalTimerHandle hTimerResultAging;
+    tPalTimerHandle hTimerBgScan;
+    //changes on every scan, it is used as a flag for whether 11d info is found on every scan
+    tANI_U8 channelOf11dInfo;   
+    //changes on every scan, a flag to tell whether conflict 11d info found on each BSS
+    tANI_BOOLEAN fAmbiguous11dInfoFound;    
+    //Tush: changes on every scan, a flag to tell whether the applied 11d info present in one of the scan results
+    tANI_BOOLEAN fCurrent11dInfoMatch;    
+    tANI_BOOLEAN f11dInfoReset;     //to indicate whether the 11d info in CFG is reset to default
+    tSirScanType curScanType;
+    tCsrChannel baseChannels;   //This are all the supported channels AND(&) to the current eBand
+    tCsrChannel channels11d;
+    tChannelListWithPower defaultPowerTable[WNI_CFG_VALID_CHANNEL_LIST_LEN]; //From NV
+    tChannelListWithPower defaultPowerTable40MHz[WNI_CFG_VALID_CHANNEL_LIST_LEN]; //From NV
+    tANI_U32 numChannelsDefault; //total channels of NV
+    tCsrChannel base20MHzChannels;   //The channel base to work on
+    tCsrChannel base40MHzChannels;   //center channels for 40MHz channels
+    tDblLinkList channelPowerInfoList24;
+    tDblLinkList channelPowerInfoList5G;
+    tANI_U32 nLastAgeTimeOut;
+    tANI_U32 nAgingCountDown;
+    tANI_U8 countryCodeDefault[WNI_CFG_COUNTRY_CODE_LEN+1];     //The country code from NV
+    tANI_U8 countryCodeCurrent[WNI_CFG_COUNTRY_CODE_LEN+1];
+    tANI_U8 countryCode11d[WNI_CFG_COUNTRY_CODE_LEN+1];
+    v_REGDOMAIN_t domainIdDefault;  //default regulatory domain
+    v_REGDOMAIN_t domainIdCurrent;  //current regulatory domain
+    tANI_BOOLEAN f11dInfoApplied;
+    tANI_BOOLEAN fCancelIdleScan;
+#ifdef FEATURE_WLAN_WAPI
+//    tANI_U16 NumBkidCandidate;
+//    tBkidCandidateInfo BkidCandidateInfo[CSR_MAX_BKID_ALLOWED]; /* Move this as part of SessionEntry */
+#endif /* FEATURE_WLAN_WAPI */
+    tANI_U8 numBGScanChannel;   //number of valid channels in the bgScanChannelList
+    tANI_U8 bgScanChannelList[WNI_CFG_BG_SCAN_CHANNEL_LIST_LEN];
+    //the ChannelInfo member is not used in this structure.
+    //numBGScanChannel and bgScanChannelList are used for the BG scan channel info
+    tCsrBGScanRequest bgScanParams;  
+    tANI_BOOLEAN fRestartIdleScan;
+    tANI_U32 nIdleScanTimeGap;  //the time since last trying to trigger idle scan
+    tCsrOsChannelMask osScanChannelMask;//keep a track of channels to be scnned while in traffic condition
+    tANI_U16 nBssLimit; //the maximum number of BSS in scan cache
+    /*channelPowerInfoList24 has been seen corrupted. Set this flag to true trying to 
+    * detect when it happens. Adding this into code because we can't reproduce it easily.
+    * We don't know when it happens. */
+    tANI_BOOLEAN fValidateList;
+    /*Customer wants to start with an active scan based on the default country code.
+    * This optimization will minimize the driver load to association time.
+    * Based on this flag we will bypass the initial passive scan needed for 11d
+    * to determine the country code & domain */
+    tANI_BOOLEAN fEnableBypass11d;
+
+    /*Customer wants to optimize the scan time. Avoiding scans(passive) on DFS 
+    * channels while swipping through both bands can save some time 
+    * (apprx 1.3 sec) */
+    tANI_BOOLEAN fEnableDFSChnlScan;
+
+    tANI_BOOLEAN fDropScanCmd; //true means we don't accept scan commands
+
+#ifdef WLAN_AP_STA_CONCURRENCY
+    tDblLinkList scanCmdPendingList;
+#endif    
+}tCsrScanStruct;
+
+
+//Save the connected information. This structure + connectedProfile
+//should contain all information about the connection
+typedef struct tagRoamCsrConnectedInfo
+{
+    tANI_U32 nBeaconLength; //the length, in bytes, of the beacon frame, can be 0
+    tANI_U32 nAssocReqLength;   //the length, in bytes, of the assoc req frame, can be 0
+    tANI_U32 nAssocRspLength;   //The length, in bytes, of the assoc rsp frame, can be 0
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    tANI_U32 nRICRspLength; //Length of the parsed RIC response IEs received in reassoc response
+#endif    
+#ifdef FEATURE_WLAN_CCX
+    tANI_U32 nTspecIeLength;
+#endif    
+    tANI_U8 *pbFrames;  //Point to a buffer contain the beacon, assoc req, assoc rsp frame, in that order
+                        //user needs to use nBeaconLength, nAssocReqLength, nAssocRspLength to desice where
+                        //each frame starts and ends.
+    tANI_U8 staId;
+}tCsrRoamConnectedInfo;
+
+
+typedef struct tagCsrLinkQualityIndInfo
+{   
+   csrRoamLinkQualityIndCallback  callback;
+   void                          *context;
+}tCsrLinkQualityIndInfo;
+
+typedef struct tagCsrPeStatsReqInfo
+{
+   tListElem              link;  /* list links */
+   tANI_U32               statsMask;
+   tANI_U32               periodicity;
+   tANI_BOOLEAN           rspPending;
+   vos_timer_t            hPeStatsTimer;
+   tANI_BOOLEAN           timerRunning;
+   tANI_U8                staId;
+   tANI_U8                numClient;
+   tpAniSirGlobal         pMac;
+   /* To remember if the peStats timer is stopped successfully or not */   
+   tANI_BOOLEAN           timerStopFailed;
+
+}tCsrPeStatsReqInfo;
+
+typedef struct tagCsrStatsClientReqInfo
+{
+   tListElem              link;  /* list links */
+   eCsrStatsRequesterType requesterId;
+   tCsrStatsCallback      callback;
+   tANI_U32               periodicity;
+   void                  *pContext;
+   tANI_U32               statsMask;
+   tCsrPeStatsReqInfo    *pPeStaEntry;
+   tANI_U8                staId;
+   vos_timer_t            timer;
+   tANI_BOOLEAN           timerExpired;
+   tpAniSirGlobal         pMac; // TODO: Confirm this change BTAMP
+}tCsrStatsClientReqInfo;
+
+typedef struct tagCsrTlStatsReqInfo
+{
+   tANI_U32               periodicity;
+   tANI_BOOLEAN           timerRunning;
+   tPalTimerHandle        hTlStatsTimer;
+   tANI_U8                numClient;
+}tCsrTlStatsReqInfo;
+
+typedef struct tagCsrRoamSession
+{
+    tANI_U8 sessionId;             // Session ID
+    tANI_BOOLEAN sessionActive;      // TRUE if it is used
+    tCsrBssid selfMacAddr;           // For BT-AMP station, this serve as BSSID for self-BSS.
+    csrRoamCompleteCallback callback;
+    void *pContext;
+    eCsrConnectState connectState;
+    tCsrRoamConnectedProfile connectedProfile;
+    tCsrRoamConnectedInfo connectedInfo;
+    tCsrRoamProfile *pCurRoamProfile;   
+    tSirBssDescription *pConnectBssDesc;
+    tANI_U16 NumPmkidCache;
+    tPmkidCacheInfo PmkidCacheInfo[CSR_MAX_PMKID_ALLOWED];
+    tANI_U8 cJoinAttemps;
+    //This may or may not have the up-to-date valid channel list
+    //It is used to get WNI_CFG_VALID_CHANNEL_LIST and not allocate memory all the time
+    tSirMacChanNum validChannelList[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+    tANI_S32 sPendingCommands;    //0 means CSR is ok to low power
+#ifdef FEATURE_WLAN_WAPI
+    tANI_U16 NumBkidCache;
+    tBkidCacheInfo BkidCacheInfo[CSR_MAX_BKID_ALLOWED];
+#endif /* FEATURE_WLAN_WAPI */
+    tANI_BOOLEAN fRoaming;  //indicate whether CSR is roaming (either via lostlink or dynamic roaming)
+    //to remember some parameters needed for START_BSS.
+    //All member must be set every time we try to join or start an IBSS or BT-AMP
+    tCsrRoamStartBssParams bssParams;   
+    tANI_U32 nWpaRsnReqIeLength;   //the byte count of pWpaRsnIE;
+    tANI_U8 *pWpaRsnReqIE; //this contain the WPA/RSN IE in assoc request or the one sent in beacon (IBSS)
+    tANI_U32 nWpaRsnRspIeLength;    //the byte count for pWpaRsnRspIE
+    tANI_U8 *pWpaRsnRspIE;  //this contain the WPA/RSN IE in beacon/probe rsp
+#ifdef FEATURE_WLAN_WAPI
+    tANI_U32 nWapiReqIeLength;   //the byte count of pWapiReqIE;
+    tANI_U8 *pWapiReqIE; //this contain the WAPI IE in assoc request or the one sent in beacon (IBSS)
+    tANI_U32 nWapiRspIeLength;    //the byte count for pWapiRspIE
+    tANI_U8 *pWapiRspIE;  //this contain the WAPI IE in beacon/probe rsp
+#endif /* FEATURE_WLAN_WAPI */
+    tANI_U32 nAddIEScanLength;  //the byte count of pAddIeScanIE;
+    tANI_U8 *pAddIEScan; //this contains the additional IE in (unicast) probe request at the time of join
+    tANI_U32 nAddIEAssocLength;      //the byte count for pAddIeAssocIE
+    tANI_U8 *pAddIEAssoc; //this contains the additional IE in (re) assoc request
+
+    tANI_TIMESTAMP roamingStartTime;    //in units of 10ms
+    tCsrTimerInfo roamingTimerInfo;
+    eCsrRoamingReason roamingReason;
+    tANI_BOOLEAN fCancelRoaming;
+    tPalTimerHandle hTimerRoaming;
+    tPalTimerHandle hTimerIbssJoining;
+    tCsrTimerInfo ibssJoinTimerInfo;
+    tANI_BOOLEAN ibss_join_pending;
+    eCsrRoamResult roamResult;  //the roamResult that is used when the roaming timer fires
+    tCsrRoamJoinStatus joinFailStatusCode;    //This is the reason code for join(assoc) failure
+    //The status code returned from PE for deauth or disassoc (in case of lostlink), or our own dynamic roaming
+    tANI_U32 roamingStatusCode;     
+    tANI_U16 NumPmkidCandidate;
+    tPmkidCandidateInfo PmkidCandidateInfo[CSR_MAX_PMKID_ALLOWED];
+ #ifdef FEATURE_WLAN_WAPI
+    tANI_U16 NumBkidCandidate;
+    tBkidCandidateInfo BkidCandidateInfo[CSR_MAX_BKID_ALLOWED]; 
+#endif
+    tANI_BOOLEAN fWMMConnection;
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+    //To retry a join later when it fails if so desired
+    tPalTimerHandle hTimerJoinRetry;
+    tCsrTimerInfo joinRetryTimerInfo;
+    tANI_U32 maxRetryCount;
+#endif
+#ifdef FEATURE_WLAN_CCX
+    tCsrCcxCckmInfo ccxCckmInfo;
+    tANI_BOOLEAN isPrevApInfoValid;
+    tSirMacSSid prevApSSID;
+    tCsrBssid prevApBssid;
+    tANI_U8 prevOpChannel;
+    tANI_U16 clientDissSecs;
+    tANI_U32 roamTS1;
+#endif
+    tANI_U8 bRefAssocStartCnt;   //Tracking assoc start indication
+} tCsrRoamSession;
+
+typedef struct tagCsrRoamStruct
+{
+    tANI_U32 nextRoamId;
+    tDblLinkList roamCmdPendingList;
+    tDblLinkList channelList5G;
+    tDblLinkList channelList24;
+    tCsrConfig configParam;
+    tANI_U32 numChannelsEeprom; //total channels of eeprom
+    tCsrChannel base20MHzChannels;   //The channel base to work on              
+    tCsrChannel base40MHzChannels;   //center channels for 40MHz channels      
+    eCsrRoamState curState[CSR_ROAM_SESSION_MAX];  
+    eCsrRoamSubState curSubState[CSR_ROAM_SESSION_MAX];
+    //This may or may not have the up-to-date valid channel list
+    //It is used to get WNI_CFG_VALID_CHANNEL_LIST and not allocate memory all the time
+    tSirMacChanNum validChannelList[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+    tANI_U32 numValidChannels; //total number of channels in CFG
+    
+    tANI_S32 sPendingCommands;
+    tChannelListWithPower   *powerTableFromEeprom;
+    tChannelListWithPower   *powerTableFromEeprom40MHz;
+    tPalTimerHandle hTimerWaitForKey;  //To support timeout for WaitForKey state
+    tCsrSummaryStatsInfo       summaryStatsInfo;
+    tCsrGlobalClassAStatsInfo  classAStatsInfo;
+    tCsrGlobalClassBStatsInfo  classBStatsInfo;
+    tCsrGlobalClassCStatsInfo  classCStatsInfo;
+    tCsrGlobalClassDStatsInfo  classDStatsInfo;
+    tCsrPerStaStatsInfo        perStaStatsInfo[CSR_MAX_STA];
+    tDblLinkList  statsClientReqList;
+    tDblLinkList  peStatsReqList;
+    tCsrTlStatsReqInfo  tlStatsReqInfo;
+    eCsrRoamLinkQualityInd vccLinkQuality;
+    tCsrLinkQualityIndInfo linkQualityIndInfo;
+    v_CONTEXT_t gVosContext; //used for interaction with TL
+    //To specify whether an association or a IBSS is WMM enabled
+    //This parameter is only valid during a join or start BSS command is being executed
+    //tANI_BOOLEAN fWMMConnection;      /* Moving it to be part of roamsession */
+    v_U8_t ucACWeights[WLANTL_MAX_AC];
+    /* TODO : Upto here */
+    tCsrTimerInfo WaitForKeyTimerInfo;
+    tCsrRoamSession   *roamSession;
+    tANI_U32 transactionId;        // Current transaction ID for internal use. 
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING    
+    tCsrNeighborRoamControlInfo neighborRoamInfo;
+#endif
+#ifdef FEATURE_WLAN_CCX
+    tANI_U8   isCcxIniFeatureEnabled;
+#endif
+}tCsrRoamStruct;
+
+
+#define GET_NEXT_ROAM_ID(pRoamStruct)  (((pRoamStruct)->nextRoamId + 1 == 0) ? 1 : (pRoamStruct)->nextRoamId)
+#define CSR_IS_ROAM_STATE(pMac, state, sessionId)  ( (state) == (pMac)->roam.curState[sessionId] )
+
+#define CSR_IS_ROAM_STOP(pMac, sessionId) CSR_IS_ROAM_STATE( (pMac), eCSR_ROAMING_STATE_STOP, sessionId ) 
+#define CSR_IS_ROAM_INIT(pMac, sessionId)  CSR_IS_ROAM_STATE( (pMac), eCSR_ROAMING_STATE_INIT, sessionId ) 
+#define CSR_IS_ROAM_SCANNING(pMac, sessionId)  CSR_IS_ROAM_STATE( pMac, eCSR_ROAMING_STATE_SCANNING, sessionId )
+#define CSR_IS_ROAM_JOINING(pMac, sessionId)   CSR_IS_ROAM_STATE( pMac, eCSR_ROAMING_STATE_JOINING, sessionId )
+#define CSR_IS_ROAM_IDLE(pMac, sessionId) CSR_IS_ROAM_STATE( pMac, eCSR_ROAMING_STATE_IDLE, sessionId ) 
+#define CSR_IS_ROAM_JOINED(pMac, sessionId)    CSR_IS_ROAM_STATE( pMac, eCSR_ROAMING_STATE_JOINED, sessionId )
+
+#define CSR_IS_ROAM_SUBSTATE(pMac, subState, sessionId)   ((subState) == (pMac)->roam.curSubState[sessionId])
+#define CSR_IS_ROAM_SUBSTATE_JOIN_REQ(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_JOIN_REQ, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_AUTH_REQ(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_AUTH_REQ, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_REASSOC_REQ(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_REASSOC_REQ, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_DISASSOC_REQ(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_DISASSOC_REQ, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_DISASSOC_NO_JOIN(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_DISASSOC_NOTHING_TO_JOIN, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_REASSOC_FAIL(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_DISASSOC_REASSOC_FAILURE, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_DISASSOC_FORCED(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_DISASSOC_FORCED, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_DEAUTH_REQ(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_DEAUTH_REQ, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_START_BSS_REQ(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_START_BSS_REQ, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_STOP_BSS_REQ(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_STOP_BSS_REQ, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_DISCONNECT_CONTINUE(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_CONFIG(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_CONFIG, sessionId)
+#define CSR_IS_ROAM_SUBSTATE_WAITFORKEY(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_WAIT_FOR_KEY, sessionId)
+#define CSR_IS_ROAM_SUBSTATE_DISASSOC_HO(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_DISASSOC_HANDOFF, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_HO_NT(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_JOINED_NO_TRAFFIC, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_HO_NRT(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_JOINED_NON_REALTIME_TRAFFIC, sessionId) 
+#define CSR_IS_ROAM_SUBSTATE_HO_RT(pMac, sessionId)    CSR_IS_ROAM_SUBSTATE((pMac), eCSR_ROAM_SUBSTATE_JOINED_REALTIME_TRAFFIC, sessionId) 
+
+#define CSR_IS_PHY_MODE_B_ONLY(pMac) \
+        ((eCSR_DOT11_MODE_11b == (pMac)->roam.configParam.phyMode) ||\
+        (eCSR_DOT11_MODE_11b_ONLY == (pMac)->roam.configParam.phyMode))
+        
+#define CSR_IS_PHY_MODE_G_ONLY(pMac) \
+        (eCSR_DOT11_MODE_11g == (pMac)->roam.configParam.phyMode || eCSR_DOT11_MODE_11g_ONLY == (pMac)->roam.configParam.phyMode)        
+        
+#define CSR_IS_PHY_MODE_A_ONLY(pMac) \
+        ((eCSR_DOT11_MODE_11a == (pMac)->roam.configParam.phyMode) ||\
+        (eCSR_DOT11_MODE_11a_ONLY == (pMac)->roam.configParam.phyMode))
+        
+#define CSR_IS_PHY_MODE_DUAL_BAND(phyMode) \
+        ((eCSR_DOT11_MODE_abg & (phyMode)) || (eCSR_DOT11_MODE_11n & (phyMode)) || \
+        (eCSR_DOT11_MODE_TAURUS & (phyMode)) || \
+        (eCSR_DOT11_MODE_AUTO & (phyMode)))
+
+// this function returns TRUE if the NIC is operating exclusively in the 2.4 GHz band, meaning
+// it is NOT operating in the 5.0 GHz band.
+#define CSR_IS_24_BAND_ONLY(pMac) \
+        (eCSR_BAND_24 == (pMac)->roam.configParam.eBand)
+
+#define CSR_IS_5G_BAND_ONLY(pMac) \
+        (eCSR_BAND_5G == (pMac)->roam.configParam.eBand)
+
+#define CSR_IS_RADIO_DUAL_BAND(pMac) \
+        (eCSR_BAND_ALL == (pMac)->roam.configParam.bandCapability)
+
+#define CSR_IS_RADIO_BG_ONLY(pMac) \
+        (eCSR_BAND_24 == (pMac)->roam.configParam.bandCapability)
+
+// this function returns TRUE if the NIC is operating exclusively in the 5.0 GHz band, meaning
+// it is NOT operating in the 2.4 GHz band
+#define CSR_IS_RADIO_A_ONLY(pMac) \
+        (eCSR_BAND_5G == (pMac)->roam.configParam.bandCapability)
+
+// this function returns TRUE if the NIC is operating in both bands.
+#define CSR_IS_OPEARTING_DUAL_BAND(pMac) \
+        ((eCSR_BAND_ALL == (pMac)->roam.configParam.bandCapability) && (eCSR_BAND_ALL == (pMac)->roam.configParam.eBand))
+
+// this function returns TRUE if the NIC can operate in the 5.0 GHz band (could operate in the
+// 2.4 GHz band also).
+#define CSR_IS_OPERATING_A_BAND(pMac) \
+        (CSR_IS_OPEARTING_DUAL_BAND((pMac)) || CSR_IS_RADIO_A_ONLY((pMac)) || CSR_IS_5G_BAND_ONLY((pMac)))
+
+// this function returns TRUE if the NIC can operate in the 2.4 GHz band (could operate in the
+// 5.0 GHz band also).
+#define CSR_IS_OPERATING_BG_BAND(pMac) \
+        (CSR_IS_OPEARTING_DUAL_BAND((pMac)) || CSR_IS_RADIO_BG_ONLY((pMac)) || CSR_IS_24_BAND_ONLY((pMac)))
+
+#define CSR_IS_CHANNEL_5GHZ(chnNum) \
+        ((chnNum) > CSR_MAX_24GHz_CHANNEL_NUMBER)
+
+#define CSR_IS_CHANNEL_24GHZ(chnNum) \
+        (((chnNum) > 0) && ((chnNum) <= CSR_MAX_24GHz_CHANNEL_NUMBER))
+        
+#define CSR_IS_SAME_BAND_CHANNELS(ch1, ch2) (CSR_IS_CHANNEL_5GHZ(ch1) == CSR_IS_CHANNEL_5GHZ(ch2))
+
+
+#define CSR_IS_11D_INFO_FOUND(pMac) \
+        (0 != (pMac)->scan.channelOf11dInfo)
+// DEAUTHIND
+#define CSR_IS_ROAMING(pSession) ((CSR_IS_LOSTLINK_ROAMING((pSession)->roamingReason)) || \
+                              (eCsrDynamicRoaming == (pSession)->roamingReason)  || \
+                              (eCsrReassocRoaming == (pSession)->roamingReason))   
+
+
+#define CSR_IS_SET_KEY_COMMAND( pCommand )    ( eSmeCommandSetKey == (pCommand)->command )
+
+#define CSR_IS_ADDTS_WHEN_ACMOFF_SUPPORTED(pMac) (pMac->roam.configParam.addTSWhenACMIsOff)
+// DEAUTHIND
+#define CSR_IS_LOSTLINK_ROAMING(reason)  ((eCsrLostlinkRoamingDisassoc == (reason)) || (eCsrLostlinkRoamingDeauth == (reason)))
+
+//Stop CSR from asking for IMPS, This function doesn't disable IMPS from CSR
+void csrScanSuspendIMPS( tpAniSirGlobal pMac );
+//Start CSR from asking for IMPS. This function doesn't trigger CSR to request entering IMPS
+//because IMPS maybe disabled.
+void csrScanResumeIMPS( tpAniSirGlobal pMac );
+
+eHalStatus csrInitGetChannels(tpAniSirGlobal pMac);
+
+eHalStatus csrSetModifyProfileFields(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                     tCsrRoamModifyProfileFields *pModifyProfileFields);
+/* ---------------------------------------------------------------------------
+    \fn csrGetModifyProfileFields
+    \brief HDD or SME - QOS calls this function to get the current values of 
+    connected profile fields changing which can cause reassoc.
+    This function must be called after CFG is downloaded and STA is in connected
+    state.
+    \param pModifyProfileFields - pointer to the connected profile fields 
+    changing which can cause reassoc
+
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrGetModifyProfileFields(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                     tCsrRoamModifyProfileFields * pModifyProfileFields);
+void csrSetGlobalCfgs( tpAniSirGlobal pMac );
+void csrSetDefaultDot11Mode( tpAniSirGlobal pMac );
+void csrScanSetChannelMask(tpAniSirGlobal pMac, tCsrChannelInfo *pChannelInfo);
+tANI_BOOLEAN csrIsConnStateDisconnected(tpAniSirGlobal pMac, tANI_U32 sessionId);
+tANI_BOOLEAN csrIsConnStateConnectedIbss( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsConnStateDisconnectedIbss( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsConnStateConnectedInfra( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsConnStateConnected( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsConnStateInfra( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsConnStateIbss( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsConnStateWds( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsConnStateConnectedWds( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsConnStateDisconnectedWds( tpAniSirGlobal pMac, tANI_U32 sessionId );
+tANI_BOOLEAN csrIsAnySessionInConnectState( tpAniSirGlobal pMac );
+tANI_BOOLEAN csrIsAllSessionDisconnected( tpAniSirGlobal pMac );
+tANI_BOOLEAN csrIsInfraConnected( tpAniSirGlobal pMac );
+tANI_BOOLEAN csrIsConcurrentInfraConnected( tpAniSirGlobal pMac );
+tANI_BOOLEAN csrIsIBSSStarted( tpAniSirGlobal pMac );
+tANI_BOOLEAN csrIsBTAMPStarted( tpAniSirGlobal pMac );
+tANI_BOOLEAN csrIsBTAMP( tpAniSirGlobal pMac, tANI_U32 sessionId );
+eHalStatus csrIsBTAMPAllowed( tpAniSirGlobal pMac, tANI_U32 chnId );
+tANI_BOOLEAN csrIsValidMcConcurrentSession(tpAniSirGlobal pMac, tANI_U32 sessionId);
+#ifdef WLAN_SOFTAP_FEATURE
+tANI_BOOLEAN csrIsConnStateConnectedInfraAp( tpAniSirGlobal pMac, tANI_U32 sessionId );
+#endif
+/*----------------------------------------------------------------------------
+  \fn csrRoamRegisterLinkQualityIndCallback
+
+  \brief
+  a CSR function to allow HDD to register a callback handler with CSR for 
+  link quality indications. 
+
+  Only one callback may be registered at any time.
+  In order to deregister the callback, a NULL cback may be provided.
+
+  Registration happens in the task context of the caller.
+
+  \param callback - Call back being registered
+  \param pContext - user data
+  
+  DEPENDENCIES: After CSR open
+
+  \return eHalStatus  
+-----------------------------------------------------------------------------*/
+eHalStatus csrRoamRegisterLinkQualityIndCallback(tpAniSirGlobal pMac,
+                                                 csrRoamLinkQualityIndCallback   callback,  
+                                                 void                           *pContext);
+/* ---------------------------------------------------------------------------
+    \fn csrGetStatistics
+    \brief csr function that client calls to register a callback to get 
+    different PHY level statistics from CSR. 
+    
+    \param requesterId - different client requesting for statistics, HDD, UMA/GAN etc
+    \param statsMask - The different category/categories of stats requester is looking for
+    \param callback - SME sends back the requested stats using the callback
+    \param periodicity - If requester needs periodic update, 0 means it's an one 
+                         time request
+    \param cache - If requester is happy with cached stats
+    \param staId - The station ID for which the stats is requested for
+    \param pContext - user context to be passed back along with the callback
+
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus csrGetStatistics(tpAniSirGlobal pMac, eCsrStatsRequesterType requesterId, 
+                            tANI_U32 statsMask, 
+                            tCsrStatsCallback callback, 
+                            tANI_U32 periodicity, tANI_BOOLEAN cache, 
+                            tANI_U8 staId, void *pContext);
+
+
+eHalStatus csrGetRssi(tpAniSirGlobal pMac,tCsrRssiCallback callback,tANI_U8 staId,tCsrBssid bssId,void * pContext,void * pVosContext);
+eHalStatus csrRoamRegisterCallback(tpAniSirGlobal pMac, csrRoamCompleteCallback callback, void *pContext);
+/* ---------------------------------------------------------------------------
+    \fn csrGetConfigParam
+    \brief HDD calls this function to get the global settings currently maintained by CSR. 
+    \param pParam - caller allocated memory
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrGetConfigParam(tpAniSirGlobal pMac, tCsrConfigParam *pParam);
+
+/* ---------------------------------------------------------------------------
+    \fn csrMsgProcessor
+    \brief HDD calls this function to change some global settings. 
+    caller must set the all fields or call csrGetConfigParam to prefill the fields.
+    \param pParam - caller allocated memory
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrChangeDefaultConfigParam(tpAniSirGlobal pMac, tCsrConfigParam *pParam);
+
+
+/* ---------------------------------------------------------------------------
+    \fn csrMsgProcessor
+    \brief HDD calls this function for the messages that are handled by CSR.
+    \param pMsgBuf - a pointer to a buffer that maps to various structures base on the message type.
+    The beginning of the buffer can always map to tSirSmeRsp.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrMsgProcessor( tpAniSirGlobal pMac,  void *pMsgBuf );
+
+/* ---------------------------------------------------------------------------
+    \fn csrOpen
+    \brief This function must be called before any API call to CSR. 
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrOpen(tpAniSirGlobal pMac);
+/* ---------------------------------------------------------------------------
+    \fn csrClose
+    \brief To close down CSR module. There should not be any API call into CSR after calling this function.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrClose(tpAniSirGlobal pMac);
+/* ---------------------------------------------------------------------------
+    \fn csrStart
+    \brief To start CSR.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrStart(tpAniSirGlobal pMac);
+/* ---------------------------------------------------------------------------
+    \fn csrStop
+    \brief To stop CSR. CSR still keeps its current setting.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrStop(tpAniSirGlobal pMac);
+/* ---------------------------------------------------------------------------
+    \fn csrReady
+    \brief To let CSR is ready to operate
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrReady(tpAniSirGlobal pMac);
+
+#ifdef FEATURE_WLAN_WAPI
+eHalStatus csrRoamGetBKIDCache(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pNum,
+                                tBkidCacheInfo *pBkidCache);
+
+
+eHalStatus csrScanGetBKIDCandidateList(tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                       tBkidCandidateInfo *pBkidList, tANI_U32 *pNumItems );
+tANI_U32 csrRoamGetNumBKIDCache(tpAniSirGlobal pMac, tANI_U32 sessionId);
+eHalStatus csrRoamSetBKIDCache( tpAniSirGlobal pMac, tANI_U32 sessionId, tBkidCacheInfo *pBKIDCache,
+                                 tANI_U32 numItems );
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetWapiReqIE
+    \brief return the WAPI IE CSR passes to PE to JOIN request or START_BSS request
+    \param pLen - caller allocated memory that has the length of pBuf as input. Upon returned, *pLen has the 
+    needed or IE length in pBuf.
+    \param pBuf - Caller allocated memory that contain the IE field, if any, upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not big enough
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamGetWapiReqIE(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pLen, tANI_U8 *pBuf);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetWapiRspIE
+    \brief return the WAPI IE from the beacon or probe rsp if connected
+    \param pLen - caller allocated memory that has the length of pBuf as input. Upon returned, *pLen has the 
+    needed or IE length in pBuf.
+    \param pBuf - Caller allocated memory that contain the IE field, if any, upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not big enough
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamGetWapiRspIE(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pLen, tANI_U8 *pBuf);
+tANI_U8 csrConstructWapiIe( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                            tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes, tCsrWapiIe *pWapiIe );
+#endif /* FEATURE_WLAN_WAPI */
+
+#ifdef WLAN_SOFTAP_FEATURE
+eHalStatus csrRoamUpdateAPWPSIE( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirAPWPSIEs *pAPWPSIES );
+eHalStatus csrRoamUpdateWPARSNIEs( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirRSNie * pAPSirRSNie);
+#endif
+void csrSetCfgPrivacy( tpAniSirGlobal pMac, tCsrRoamProfile *pProfile, tANI_BOOLEAN fPrivacy );
+tANI_S8 csrGetInfraSessionId( tpAniSirGlobal pMac );
+tANI_U8 csrGetInfraOperationChannel( tpAniSirGlobal pMac, tANI_U8 sessionId);
+tANI_U8 csrGetConcurrentOperationChannel( tpAniSirGlobal pMac );
+
+eHalStatus csrRoamCopyConnectProfile(tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                               tCsrRoamConnectedProfile *pProfile);
+tANI_BOOLEAN csrIsSetKeyAllowed(tpAniSirGlobal pMac, tANI_U32 sessionId);
+
+void csrSetOppositeBandChannelInfo( tpAniSirGlobal pMac );
+void csrConstructCurrentValidChannelList( tpAniSirGlobal pMac, tDblLinkList *pChannelSetList, 
+                                            tANI_U8 *pChannelList, tANI_U8 bSize, tANI_U8 *pNumChannels );
+
+#endif
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+//Returns whether the current association is a 11r assoc or not
+tANI_BOOLEAN csrRoamIs11rAssoc(tpAniSirGlobal pMac);
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+//Returns whether the current association is a CCX assoc or not
+tANI_BOOLEAN csrRoamIsCCXAssoc(tpAniSirGlobal pMac);
+#endif
+
+void csrDisconnectAllActiveSessions(tpAniSirGlobal pMac);
diff --git a/CORE/SME/inc/csrLinkList.h b/CORE/SME/inc/csrLinkList.h
new file mode 100644
index 0000000..569ca14
--- /dev/null
+++ b/CORE/SME/inc/csrLinkList.h
@@ -0,0 +1,112 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+    \file csrLinkList.h
+  
+    Exports and types for the Common link list interfaces.
+  
+   Copyright (C) 2006 Airgo Networks, Incorporated
+ 
+   ========================================================================== */
+#ifndef CSR_LINK_LIST_H__
+#define CSR_LINK_LIST_H__
+
+#include "vos_lock.h"
+
+
+#define LL_ACCESS_LOCK          eANI_BOOLEAN_TRUE
+#define LL_ACCESS_NOLOCK        eANI_BOOLEAN_FALSE
+
+typedef struct tagListElem
+{
+    struct tagListElem *last;
+    struct tagListElem *next;
+}tListElem;
+
+typedef enum
+{
+    LIST_FLAG_CLOSE = 0,
+    LIST_FLAG_OPEN = 0xa1b2c4d7,
+}tListFlag;
+
+//This is a circular double link list
+typedef struct tagDblLinkList
+{
+  tListElem ListHead;
+  vos_lock_t Lock;
+  tANI_U32  Count;
+  tHddHandle hHdd;
+  tListFlag Flag;
+}tDblLinkList;
+
+//To get the address of an object of (type) base on the (address) of one of its (field)
+#define GET_BASE_ADDR(address, type, field) ((type *)( \
+                                                  (tANI_U8 *)(address) - \
+                                                  (tANI_U8 *)(&((type *)0)->field)))
+                                     
+//To get the offset of (field) inside structure (type)                                                  
+#define GET_FIELD_OFFSET(type, field)  ((tANI_U32_OR_PTR)(&(((type *)0)->field)))
+
+#define GET_ROUND_UP( _Field, _Boundary ) (((_Field) + ((_Boundary) - 1))  & ~((_Boundary) - 1))
+#define BITS_ON(  _Field, _Bitmask ) ( (_Field) |=  (_Bitmask) )
+#define BITS_OFF( _Field, _Bitmask ) ( (_Field) &= ~(_Bitmask) )
+
+#define CSR_MAX(a, b)  ((a) > (b) ? (a) : (b))
+#define CSR_MIN(a, b)  ((a) < (b) ? (a) : (b))
+
+                                                  
+#define csrIsListEmpty(pHead) ((pHead)->next == (pHead))
+
+tANI_U32 csrLLCount( tDblLinkList *pList );
+
+eHalStatus csrLLOpen( tHddHandle hHdd, tDblLinkList  *pList );
+void csrLLClose( tDblLinkList *pList );
+
+void csrLLLock( tDblLinkList *pList );
+void csrLLUnlock( tDblLinkList *pList );
+
+tANI_BOOLEAN csrLLIsListEmpty( tDblLinkList *pList, tANI_BOOLEAN fInterlocked );
+
+void csrLLInsertHead( tDblLinkList *pList, tListElem *pEntry, tANI_BOOLEAN fInterlocked );
+void csrLLInsertTail( tDblLinkList *pList, tListElem *pEntry, tANI_BOOLEAN fInterlocked );
+//This function put pNewEntry before pEntry. Caller should have found pEntry
+void csrLLInsertEntry( tDblLinkList *pList, tListElem *pEntry, tListElem *pNewEntry, tANI_BOOLEAN fInterlocked );
+
+tListElem *csrLLPeekHead( tDblLinkList *pList, tANI_BOOLEAN fInterlocked );
+tListElem *csrLLPeekTail( tDblLinkList *pList, tANI_BOOLEAN fInterlocked );
+
+tListElem *csrLLRemoveHead( tDblLinkList *pList, tANI_BOOLEAN fInterlocked );
+tListElem *csrLLRemoveTail( tDblLinkList *pList, tANI_BOOLEAN fInterlocked );
+tANI_BOOLEAN  csrLLRemoveEntry( tDblLinkList *pList, tListElem *pEntryToRemove, tANI_BOOLEAN fInterlocked );
+void csrLLPurge( tDblLinkList *pList, tANI_BOOLEAN fInterlocked );
+
+//csrLLNext return NULL if reaching the end or list is empty
+tListElem *csrLLNext( tDblLinkList *pList, tListElem *pEntry, tANI_BOOLEAN fInterlocked );
+
+tListElem *csrLLPrevious( tDblLinkList *pList, tListElem *pEntry, tANI_BOOLEAN fInterlocked );
+
+tANI_BOOLEAN csrLLFindEntry( tDblLinkList *pList, tListElem *pEntryToFind );
+
+
+#endif
+
diff --git a/CORE/SME/inc/csrNeighborRoam.h b/CORE/SME/inc/csrNeighborRoam.h
new file mode 100644
index 0000000..b5f535b
--- /dev/null
+++ b/CORE/SME/inc/csrNeighborRoam.h
@@ -0,0 +1,186 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+
+  
+    \file csrNeighborRoam.h
+  
+    Exports and types for the neighbor roaming algorithm which is sepcifically 
+    designed for Android.
+  
+   Copyright (C) 2006 Airgo Networks, Incorporated
+   
+========================================================================== */
+#ifndef CSR_NEIGHBOR_ROAM_H
+#define CSR_NEIGHBOR_ROAM_H
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+
+/* Enumeration of various states in neighbor roam algorithm */
+typedef enum
+{
+    eCSR_NEIGHBOR_ROAM_STATE_CLOSED,
+    eCSR_NEIGHBOR_ROAM_STATE_INIT,
+    eCSR_NEIGHBOR_ROAM_STATE_CONNECTED,
+    eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN,
+    eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING,
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY,
+    eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN,
+    eCSR_NEIGHBOR_ROAM_STATE_PREAUTHENTICATING,
+    eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE,
+#endif /* WLAN_FEATURE_VOWIFI_11R */    
+    eNEIGHBOR_STATE_MAX
+} eCsrNeighborRoamState;
+
+/* Parameters that are obtained from CFG */
+typedef struct sCsrNeighborRoamCfgParams
+{
+    tANI_U8         maxNeighborRetries;
+    tANI_U32        neighborScanPeriod;
+    tCsrChannelInfo channelInfo;
+    tANI_U8         neighborLookupThreshold;
+    tANI_U8         neighborReassocThreshold;
+    tANI_U32        minChannelScanTime;
+    tANI_U32        maxChannelScanTime;
+    tANI_U16        neighborResultsRefreshPeriod;
+} tCsrNeighborRoamCfgParams, *tpCsrNeighborRoamCfgParams;
+
+#define CSR_NEIGHBOR_ROAM_INVALID_CHANNEL_INDEX    255
+typedef struct sCsrNeighborRoamChannelInfo
+{
+    tANI_BOOLEAN    IAPPNeighborListReceived; // Flag to mark reception of IAPP Neighbor list
+    tANI_BOOLEAN    chanListScanInProgress;
+    tANI_U8         currentChanIndex;       //Current channel index that is being scanned
+    tCsrChannelInfo currentChannelListInfo; //Max number of channels in channel list and the list of channels
+} tCsrNeighborRoamChannelInfo, *tpCsrNeighborRoamChannelInfo;
+
+typedef struct sCsrNeighborRoamBSSInfo
+{
+    tListElem           List;
+    tANI_U8             apPreferenceVal;
+//    tCsrScanResultInfo  *scanResultInfo;
+    tpSirBssDescription pBssDescription;
+} tCsrNeighborRoamBSSInfo, *tpCsrNeighborRoamBSSInfo;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+#define CSR_NEIGHBOR_ROAM_REPORT_QUERY_TIMEOUT  1000    //in milliseconds
+#define CSR_NEIGHBOR_ROAM_PREAUTH_RSP_WAIT_MULTIPLIER   5     //in milliseconds
+#define MAX_NUM_PREAUTH_FAIL_LIST_ADDRESS       10 //Max number of MAC addresses with which the pre-auth was failed
+#define MAX_BSS_IN_NEIGHBOR_RPT                 4
+#define CSR_NEIGHBOR_ROAM_MAX_NUM_PREAUTH_RETRIES 3
+
+/* Black listed APs. List of MAC Addresses with which the Preauthentication was failed. */
+typedef struct sCsrPreauthFailListInfo
+{
+    tANI_U8     numMACAddress;
+    tSirMacAddr macAddress[MAX_NUM_PREAUTH_FAIL_LIST_ADDRESS];
+} tCsrPreauthFailListInfo, *tpCsrPreauthFailListInfo;
+
+typedef struct sCsrNeighborReportBssInfo
+{
+    tANI_U8 channelNum;
+    tANI_U8 neighborScore;
+    tSirMacAddr neighborBssId;
+} tCsrNeighborReportBssInfo, *tpCsrNeighborReportBssInfo;
+
+typedef struct sCsr11rAssocNeighborInfo
+{
+    tANI_BOOLEAN                preauthRspPending;
+    tANI_BOOLEAN                neighborRptPending;
+    tANI_U8                     currentNeighborRptRetryNum;
+    tPalTimerHandle             preAuthRspWaitTimer; //This timer is used for preauth response
+    tCsrTimerInfo               preAuthRspWaitTimerInfo;
+    tCsrPreauthFailListInfo     preAuthFailList;
+    tANI_U32                    neighborReportTimeout;
+    tANI_U32                    PEPreauthRespTimeout;
+    tANI_U8                     numPreAuthRetries;
+    tDblLinkList                preAuthDoneList;    /* Linked list which consists or preauthenticated nodes */
+    tANI_U8                     numBssFromNeighborReport;
+    tCsrNeighborReportBssInfo   neighboReportBssInfo[MAX_BSS_IN_NEIGHBOR_RPT];  //Contains info needed during REPORT_SCAN State
+} tCsr11rAssocNeighborInfo, *tpCsr11rAssocNeighborInfo;
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+
+/* Below macros are used to increase the registered neighbor Lookup threshold with TL when 
+ * we dont see any AP during back ground scanning. The values are incremented from neighborLookupThreshold 
+ * from CFG, incremented by 5,10,15...50(LOOKUP_THRESHOLD_INCREMENT_MULTIPLIER_MAX * 
+ * NEIGHBOR_LOOKUP_THRESHOLD_INCREMENT_CONSTANT) */
+#define NEIGHBOR_LOOKUP_THRESHOLD_INCREMENT_CONSTANT    5
+#define LOOKUP_THRESHOLD_INCREMENT_MULTIPLIER_MAX       4
+
+/* Complete control information for neighbor roam algorithm */
+typedef struct sCsrNeighborRoamControlInfo
+{
+    eCsrNeighborRoamState       neighborRoamState;
+    eCsrNeighborRoamState       prevNeighborRoamState;
+    tCsrNeighborRoamCfgParams   cfgParams;
+    tCsrBssid                   currAPbssid; // current assoc AP
+    tANI_U8                     currAPoperationChannel; // current assoc AP
+    tPalTimerHandle             neighborScanTimer;
+    tPalTimerHandle             neighborResultsRefreshTimer;
+    tCsrTimerInfo               neighborScanTimerInfo;
+    tCsrNeighborRoamChannelInfo roamChannelInfo;
+    tANI_U8                     currentNeighborLookupThreshold;
+    tANI_U8                     currentLookupIncrementMultiplier;
+    tANI_BOOLEAN                scanRspPending;
+    tANI_TIMESTAMP              scanRequestTimeStamp;
+    tDblLinkList                roamableAPList;    // List of current FT candidates
+    tANI_U32                    csrSessionId;
+    tCsrRoamProfile             csrNeighborRoamProfile;
+#ifdef WLAN_FEATURE_VOWIFI_11R    
+    tANI_BOOLEAN                is11rAssoc;
+    tCsr11rAssocNeighborInfo    FTRoamInfo;
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+#ifdef FEATURE_WLAN_CCX    
+    tANI_BOOLEAN                isCCXAssoc;
+    tANI_BOOLEAN                isVOAdmitted;
+    tANI_U32                    MinQBssLoadRequired;
+#endif
+} tCsrNeighborRoamControlInfo, *tpCsrNeighborRoamControlInfo;
+
+
+/* All the necessary Function declarations are here */
+eHalStatus csrNeighborRoamIndicateConnect(tpAniSirGlobal pMac,tANI_U8 sessionId, VOS_STATUS status);
+eHalStatus csrNeighborRoamIndicateDisconnect(tpAniSirGlobal pMac,tANI_U8 sessionId);
+tANI_BOOLEAN csrNeighborRoamIsHandoffInProgress(tpAniSirGlobal pMac);
+void csrNeighborRoamRequestHandoff(tpAniSirGlobal pMac);
+eHalStatus csrNeighborRoamInit(tpAniSirGlobal pMac);
+void csrNeighborRoamClose(tpAniSirGlobal pMac);
+void csrNeighborRoamPurgePreauthFailedList(tpAniSirGlobal pMac);
+VOS_STATUS csrNeighborRoamTransitToCFGChanScan(tpAniSirGlobal pMac);
+VOS_STATUS csrNeighborRoamTransitionToPreauthDone(tpAniSirGlobal pMac);
+eHalStatus csrNeighborRoamPrepareScanProfileFilter(tpAniSirGlobal pMac, tCsrScanResultFilter *pScanFilter);
+void csrNeighborRoamGetHandoffAPInfo(tpAniSirGlobal pMac, tpCsrNeighborRoamBSSInfo pHandoffNode);
+void csrNeighborRoamPreauthRspHandler(tpAniSirGlobal pMac, VOS_STATUS vosStatus);
+#ifdef WLAN_FEATURE_VOWIFI_11R
+tANI_BOOLEAN csrNeighborRoamIs11rAssoc(tpAniSirGlobal pMac);
+#endif
+VOS_STATUS csrNeighborRoamCreateChanListFromNeighborReport(tpAniSirGlobal pMac);
+void csrNeighborRoamTranistionPreauthDoneToDisconnected(tpAniSirGlobal pMac);
+tANI_BOOLEAN csrNeighborRoamStatePreauthDone(tpAniSirGlobal pMac);
+
+
+
+#endif /* WLAN_FEATURE_NEIGHBOR_ROAMING */
+
+#endif /* CSR_NEIGHBOR_ROAM_H */
diff --git a/CORE/SME/inc/csrSupport.h b/CORE/SME/inc/csrSupport.h
new file mode 100644
index 0000000..d7257e7
--- /dev/null
+++ b/CORE/SME/inc/csrSupport.h
@@ -0,0 +1,813 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+
+  
+    \file csrSupport.h
+  
+    Exports and types for the Common Scan and Roaming supporting interfaces.
+  
+   Copyright (C) 2006 Airgo Networks, Incorporated
+ 
+   ========================================================================== */
+#ifndef CSR_SUPPORT_H__
+#define CSR_SUPPORT_H__
+
+#include "csrLinkList.h"
+#include "csrApi.h"
+#include "vos_nvitem.h"
+
+#ifdef FEATURE_WLAN_WAPI
+#define CSR_WAPI_OUI_SIZE              ( 4 )
+#define CSR_WAPI_VERSION_SUPPORTED     ( 1 )
+#define CSR_WAPI_MAX_AUTH_SUITES       ( 2 )
+#define CSR_WAPI_MAX_CYPHERS           ( 5 )
+#define CSR_WAPI_MAX_UNICAST_CYPHERS   ( 5 )
+#define CSR_WAPI_MAX_MULTICAST_CYPHERS ( 1 )
+#endif /* FEATURE_WLAN_WAPI */
+
+#define CSR_RSN_OUI_SIZE              ( 4 )
+#define CSR_RSN_VERSION_SUPPORTED     ( 1 )
+#define CSR_RSN_MAX_AUTH_SUITES       ( 2 )
+#define CSR_RSN_MAX_CYPHERS           ( 5 )
+#define CSR_RSN_MAX_UNICAST_CYPHERS   ( 5 )
+#define CSR_RSN_MAX_MULTICAST_CYPHERS ( 1 )
+
+#define CSR_WPA_OUI_SIZE              ( 4 )
+#define CSR_WPA_VERSION_SUPPORTED     ( 1 )
+#define CSR_WME_OUI_SIZE ( 4 )
+#define CSR_WPA_MAX_AUTH_SUITES       ( 2 )
+#define CSR_WPA_MAX_CYPHERS           ( 5 )
+#define CSR_WPA_MAX_UNICAST_CYPHERS   ( 5 )
+#define CSR_WPA_MAX_MULTICAST_CYPHERS ( 1 )
+#define CSR_WPA_IE_MIN_SIZE           ( 6 )   // minimum size of the IE->length is the size of the Oui + Version.
+#define CSR_WPA_IE_MIN_SIZE_W_MULTICAST ( HDD_WPA_IE_MIN_SIZE + HDD_WPA_OUI_SIZE )
+#define CSR_WPA_IE_MIN_SIZE_W_UNICAST   ( HDD_WPA_IE_MIN_SIZE + HDD_WPA_OUI_SIZE + sizeof( pWpaIe->cUnicastCyphers ) )
+
+#define CSR_DOT11_SUPPORTED_RATES_MAX ( 12 )
+#define CSR_DOT11_EXTENDED_SUPPORTED_RATES_MAX ( 8 )
+
+#define CSR_DOT11_MAX_NUM_SUPPORTED_11B_RATES ( 4 )
+#define CSR_DOT11_MAX_NUM_SUPPORTED_11A_RATES ( 8 )
+#define CSR_DOT11_BASIC_RATE_MASK ( 0x80 )
+
+#define CSR_WME_INFO_IE_VERSION_SUPPORTED ( 1 )
+#define CSR_WME_PARM_IE_VERSION_SUPPORTED ( 1 )
+
+#define CSR_PASSIVE_SCAN_STARTING_CHANNEL ( 52)
+#define CSR_PASSIVE_SCAN_ENDING_CHANNEL ( 140)
+
+#define CSR_DOT11_MAX_11A_RATE ( 54 * 2 )
+#define CSR_DOT11_MIN_11A_RATE (  6 * 2 )
+#define CSR_DOT11_MAX_11B_RATE ( 11 * 2 )
+#define CSR_DOT11_MIN_11B_RATE (  1 * 2 )
+#define CSR_DOT11_MAX_11G_RATE ( 54 * 2 )
+#define CSR_DOT11_MIN_11G_RATE (  6 * 2 )
+
+//Define the frequency ranges that need to be passive scan, MHz
+#define CSR_PASSIVE_SCAN_CAT1_LOW       5250 
+#define CSR_PASSIVE_SCAN_CAT1_HIGH      5350
+#define CSR_PASSIVE_SCAN_CAT2_LOW       5470 
+#define CSR_PASSIVE_SCAN_CAT2_HIGH      5725
+#define CSR_PASSIVE_SCAN_CAT3_LOW       5500 
+#define CSR_PASSIVE_SCAN_CAT3_HIGH      5560
+
+#define CSR_OUI_USE_GROUP_CIPHER_INDEX 0x00
+#define CSR_OUI_WEP40_OR_1X_INDEX      0x01
+#define CSR_OUI_TKIP_OR_PSK_INDEX      0x02
+#define CSR_OUI_RESERVED_INDEX         0x03
+#define CSR_OUI_AES_INDEX              0x04
+#define CSR_OUI_WEP104_INDEX           0x05
+
+#ifdef FEATURE_WLAN_WAPI
+#define CSR_OUI_WAPI_RESERVED_INDEX    0x00
+#define CSR_OUI_WAPI_WAI_CERT_OR_SMS4_INDEX    0x01
+#define CSR_OUI_WAPI_WAI_PSK_INDEX     0x02
+#endif /* FEATURE_WLAN_WAPI */
+
+
+typedef enum 
+{
+    // 11b rates
+    eCsrSuppRate_1Mbps   =   1 * 2,
+    eCsrSuppRate_2Mbps   =   2 * 2,
+    eCsrSuppRate_5_5Mbps =  11,      // 5.5 * 2
+    eCsrSuppRate_11Mbps  =  11 * 2,
+
+    // 11a / 11g rates
+    eCsrSuppRate_6Mbps   =   6 * 2,
+    eCsrSuppRate_9Mbps   =   9 * 2,
+    eCsrSuppRate_12Mbps  =  12 * 2,
+    eCsrSuppRate_18Mbps  =  18 * 2,
+    eCsrSuppRate_24Mbps  =  24 * 2,
+    eCsrSuppRate_36Mbps  =  36 * 2,
+    eCsrSuppRate_48Mbps  =  48 * 2,
+    eCsrSuppRate_54Mbps  =  54 * 2,
+
+    // airgo proprietary rates
+    eCsrSuppRate_10Mbps  =  10 * 2,
+    eCsrSuppRate_10_5Mbps=  21,     // 10.5 * 2
+    eCsrSuppRate_20Mbps  =  20 * 2,
+    eCsrSuppRate_21Mbps  =  21 * 2,
+    eCsrSuppRate_40Mbps  =  40 * 2,
+    eCsrSuppRate_42Mbps  =  42 * 2,
+    eCsrSuppRate_60Mbps  =  60 * 2,
+    eCsrSuppRate_63Mbps  =  63 * 2,
+    eCsrSuppRate_72Mbps  =  72 * 2,
+    eCsrSuppRate_80Mbps  =  80 * 2,
+    eCsrSuppRate_84Mbps  =  84 * 2,
+    eCsrSuppRate_96Mbps  =  96 * 2,
+    eCsrSuppRate_108Mbps = 108 * 2,
+    eCsrSuppRate_120Mbps = 120 * 2,
+    eCsrSuppRate_126Mbps = 126 * 2,
+    eCsrSuppRate_144Mbps = 144 * 2,
+    eCsrSuppRate_160Mbps = 160 * 2,
+    eCsrSuppRate_168Mbps = 168 * 2,
+    eCsrSuppRate_192Mbps = 192 * 2,
+    eCsrSuppRate_216Mbps = 216 * 2,
+    eCsrSuppRate_240Mbps = 240 * 2
+}eCsrSupportedRates;
+
+typedef enum
+{
+    eCsrPassiveScanNot,     //can be scanned actively on the whole 5GHz band
+    eCsrPassiveScanCat1,    //always passive scan from 5250 to 5350MHz
+    eCsrPassiveScanCat2,    //always passive scan from 5250 to 5350MHz, and from 5470 to 5725MHz
+    eCsrPassiveScanCat3,    //always passive scan from 5250 to 5350MHz, from 5470 to 5725MHz, and from 5500 to 5560MHz
+}eCsrPassiveScanCat;
+
+
+//Please donot insert in the middle of the enum here because they tie to the indiex
+typedef enum
+{
+    eCSR_COUNTRY_INDEX_US = 0,  //Always set US as index 0
+    eCSR_COUNTRY_INDEX_ANDORRA,
+    eCSR_COUNTRY_INDEX_UAE,     //United Arab Emirates
+    eCSR_COUNTRY_INDEX_AFGHANISTAN,
+    eCSR_COUNTRY_INDEX_ANTIGUA_AND_BARBUDA,
+    eCSR_COUNTRY_INDEX_ANGUILLA,
+    eCSR_COUNTRY_INDEX_ALBANIA,
+    eCSR_COUNTRY_INDEX_ARMENIA,
+    eCSR_COUNTRY_INDEX_NETHERLANDS_ANTILLES,
+    eCSR_COUNTRY_INDEX_ANGOLA,
+    eCSR_COUNTRY_INDEX_ANTARCTICA,
+    eCSR_COUNTRY_INDEX_ARGENTINA,
+    eCSR_COUNTRY_INDEX_AMERICAN_SAMOA,
+    eCSR_COUNTRY_INDEX_AUSTRIA,
+    eCSR_COUNTRY_INDEX_AUSTRALIA,
+    eCSR_COUNTRY_INDEX_ARUBA,
+    eCSR_COUNTRY_INDEX_ALAND_ISLANDS,
+    eCSR_COUNTRY_INDEX_AZERBAIJAN,
+    eCSR_COUNTRY_INDEX_BOSNIA_AND_HERZEGOVINA,
+    eCSR_COUNTRY_INDEX_BARBADOS,
+    eCSR_COUNTRY_INDEX_BANGLADESH,
+    eCSR_COUNTRY_INDEX_BELGIUM,
+    eCSR_COUNTRY_INDEX_BURKINA_FASO,
+    eCSR_COUNTRY_INDEX_BULGARIA,
+    eCSR_COUNTRY_INDEX_BAHRAIN,
+    eCSR_COUNTRY_INDEX_BURUNDI,
+    eCSR_COUNTRY_INDEX_BENIN,
+    eCSR_COUNTRY_INDEX_SAINT_BARTHELEMY,
+    eCSR_COUNTRY_INDEX_BERMUDA,
+    eCSR_COUNTRY_INDEX_BRUNEI_DARUSSALAM,
+    eCSR_COUNTRY_INDEX_BOLVIA,
+    eCSR_COUNTRY_INDEX_BRAZIL,
+    eCSR_COUNTRY_INDEX_BAHAMAS,
+    eCSR_COUNTRY_INDEX_BHUTAN,
+    eCSR_COUNTRY_INDEX_BOUVET_ISLAND,
+    eCSR_COUNTRY_INDEX_BOTSWANA,
+    eCSR_COUNTRY_INDEX_BELARUS,
+    eCSR_COUNTRY_INDEX_BELIZE,
+    eCSR_COUNTRY_INDEX_CANADA,      
+    eCSR_COUNTRY_INDEX_COCOS_KEELING_ISLANDS,
+    eCSR_COUNTRY_INDEX_CONGO_REP,
+    eCSR_COUNTRY_INDEX_CENTRAL_AFRICAN,
+    eCSR_COUNTRY_INDEX_CONGO,
+    eCSR_COUNTRY_INDEX_SWITZERLAND,
+    eCSR_COUNTRY_INDEX_COTE_DIVOIRE,
+    eCSR_COUNTRY_INDEX_COOK_ISLANDS,
+    eCSR_COUNTRY_INDEX_CHILE,
+    eCSR_COUNTRY_INDEX_CAMEROON,
+    eCSR_COUNTRY_INDEX_CHINA,
+    eCSR_COUNTRY_INDEX_COLUMBIA,
+    eCSR_COUNTRY_INDEX_COSTA_RICA,
+    eCSR_COUNTRY_INDEX_CUBA,
+    eCSR_COUNTRY_INDEX_CAPE_VERDE,
+    eCSR_COUNTRY_INDEX_CHRISTMAS_ISLAND,
+    eCSR_COUNTRY_INDEX_CYPRUS,
+    eCSR_COUNTRY_INDEX_CZECH,
+    eCSR_COUNTRY_INDEX_GERMANY,
+    eCSR_COUNTRY_INDEX_DJIBOUTI,
+    eCSR_COUNTRY_INDEX_DENMARK,
+    eCSR_COUNTRY_INDEX_DOMINICA,
+    eCSR_COUNTRY_INDEX_DOMINICAN_REP,
+    eCSR_COUNTRY_INDEX_ALGERIA,
+    eCSR_COUNTRY_INDEX_ECUADOR,
+    eCSR_COUNTRY_INDEX_ESTONIA,
+    eCSR_COUNTRY_INDEX_EGYPT,
+    eCSR_COUNTRY_INDEX_WESTERN_SAHARA,
+    eCSR_COUNTRY_INDEX_ERITREA,
+    eCSR_COUNTRY_INDEX_SPAIN,
+    eCSR_COUNTRY_INDEX_ETHIOPIA,
+    eCSR_COUNTRY_INDEX_FINLAND,
+    eCSR_COUNTRY_INDEX_FIJI,
+    eCSR_COUNTRY_INDEX_FALKLAND_ISLANDS,
+    eCSR_COUNTRY_INDEX_MICRONESIA,
+    eCSR_COUNTRY_INDEX_FAROE_ISLANDS,
+    eCSR_COUNTRY_INDEX_FRANCE,
+    eCSR_COUNTRY_INDEX_GABON,
+    eCSR_COUNTRY_INDEX_UNITED_KINGDOM,
+    eCSR_COUNTRY_INDEX_GRENADA,
+    eCSR_COUNTRY_INDEX_GEORGIA,
+    eCSR_COUNTRY_INDEX_FRENCH_GUIANA,
+    eCSR_COUNTRY_INDEX_GUERNSEY,
+    eCSR_COUNTRY_INDEX_GHANA,
+    eCSR_COUNTRY_INDEX_GIBRALTAR,
+    eCSR_COUNTRY_INDEX_GREENLAND,
+    eCSR_COUNTRY_INDEX_GAMBIA,
+    eCSR_COUNTRY_INDEX_GUINEA,
+    eCSR_COUNTRY_INDEX_GUADELOUPE,
+    eCSR_COUNTRY_INDEX_EQUATORIAL_GUINEA,
+    eCSR_COUNTRY_INDEX_GREECE,
+    eCSR_COUNTRY_INDEX_SOUTH_GEORGIA,
+    eCSR_COUNTRY_INDEX_GUATEMALA,
+    eCSR_COUNTRY_INDEX_GUAM,
+    eCSR_COUNTRY_INDEX_GUINEA_BISSAU,
+    eCSR_COUNTRY_INDEX_GUYANA,
+    eCSR_COUNTRY_INDEX_HONGKONG,
+    eCSR_COUNTRY_INDEX_HEARD_ISLAND,
+    eCSR_COUNTRY_INDEX_HONDURAS,
+    eCSR_COUNTRY_INDEX_CROATIA,
+    eCSR_COUNTRY_INDEX_HAITI,
+    eCSR_COUNTRY_INDEX_HUNGARY,
+    eCSR_COUNTRY_INDEX_INDONESIA,
+    eCSR_COUNTRY_INDEX_IRELAND,
+    eCSR_COUNTRY_INDEX_ISRAEL,
+    eCSR_COUNTRY_INDEX_ISLE_OF_MAN,
+    eCSR_COUNTRY_INDEX_INDIA,
+    eCSR_COUNTRY_INDEX_BRITISH_INDIAN,
+    eCSR_COUNTRY_INDEX_IRAQ,
+    eCSR_COUNTRY_INDEX_IRAN,
+    eCSR_COUNTRY_INDEX_ICELAND,
+    eCSR_COUNTRY_INDEX_ITALY,
+    eCSR_COUNTRY_INDEX_JERSEY,
+    eCSR_COUNTRY_INDEX_JAMAICA,
+    eCSR_COUNTRY_INDEX_JORDAN,
+    eCSR_COUNTRY_INDEX_JAPAN,
+    eCSR_COUNTRY_INDEX_KENYA,
+    eCSR_COUNTRY_INDEX_KYRGYZSTAN,
+    eCSR_COUNTRY_INDEX_CAMBODIA,
+    eCSR_COUNTRY_INDEX_KIRIBATI,
+    eCSR_COUNTRY_INDEX_COMOROS,
+    eCSR_COUNTRY_INDEX_SAINT_KITTS_AND_NEVIS,
+    eCSR_COUNTRY_INDEX_KOREA_NORTH,
+    eCSR_COUNTRY_INDEX_KOREA_SOUTH,
+    eCSR_COUNTRY_INDEX_KUWAIT,
+    eCSR_COUNTRY_INDEX_CAYMAN_ISLANDS,
+    eCSR_COUNTRY_INDEX_KAZAKHSTAN,
+    eCSR_COUNTRY_INDEX_LAO,
+    eCSR_COUNTRY_INDEX_LEBANON,
+    eCSR_COUNTRY_INDEX_SAINT_LUCIA,
+    eCSR_COUNTRY_INDEX_LIECHTENSTEIN,
+    eCSR_COUNTRY_INDEX_SRI_LANKA,
+    eCSR_COUNTRY_INDEX_LIBERIA,
+    eCSR_COUNTRY_INDEX_LESOTHO,
+    eCSR_COUNTRY_INDEX_LITHUANIA,
+    eCSR_COUNTRY_INDEX_LUXEMBOURG,
+    eCSR_COUNTRY_INDEX_LATVIA,
+    eCSR_COUNTRY_INDEX_LIBYAN_ARAB_JAMAHIRIYA,
+    eCSR_COUNTRY_INDEX_MOROCCO,
+    eCSR_COUNTRY_INDEX_MONACO,
+    eCSR_COUNTRY_INDEX_MOLDOVA,
+    eCSR_COUNTRY_INDEX_MONTENEGRO,
+    eCSR_COUNTRY_INDEX_MADAGASCAR,
+    eCSR_COUNTRY_INDEX_MARSHALL_ISLANDS,
+    eCSR_COUNTRY_INDEX_MACEDONIA,
+    eCSR_COUNTRY_INDEX_MALI,
+    eCSR_COUNTRY_INDEX_MYANMAR,
+    eCSR_COUNTRY_INDEX_MONGOLIA,
+    eCSR_COUNTRY_INDEX_MACAO,
+    eCSR_COUNTRY_INDEX_NORTHERN_MARIANA_ISLANDS,
+    eCSR_COUNTRY_INDEX_MARTINIQUE,
+    eCSR_COUNTRY_INDEX_MAURITANIA,
+    eCSR_COUNTRY_INDEX_MONTSERRAT,
+    eCSR_COUNTRY_INDEX_MALTA,
+    eCSR_COUNTRY_INDEX_MAURITIUS,
+    eCSR_COUNTRY_INDEX_MALDIVES,
+    eCSR_COUNTRY_INDEX_MALAWI,
+    eCSR_COUNTRY_INDEX_MEXICO,
+    eCSR_COUNTRY_INDEX_MALAYSIA,
+    eCSR_COUNTRY_INDEX_MOZAMBIQUE,
+    eCSR_COUNTRY_INDEX_NAMIBIA,
+    eCSR_COUNTRY_INDEX_NEW_CALENDONIA,
+    eCSR_COUNTRY_INDEX_NIGER,
+    eCSR_COUNTRY_INDEX_NORFOLK_ISLAND,
+    eCSR_COUNTRY_INDEX_NIGERIA,
+    eCSR_COUNTRY_INDEX_NICARAGUA,
+    eCSR_COUNTRY_INDEX_NETHERLANDS,
+    eCSR_COUNTRY_INDEX_NORWAY,
+    eCSR_COUNTRY_INDEX_NEPAL,
+    eCSR_COUNTRY_INDEX_NAURU,
+    eCSR_COUNTRY_INDEX_NIUE,
+    eCSR_COUNTRY_INDEX_NEW_ZEALAND,
+    eCSR_COUNTRY_INDEX_OMAN,
+    eCSR_COUNTRY_INDEX_PANAMA,
+    eCSR_COUNTRY_INDEX_PERU,
+    eCSR_COUNTRY_INDEX_FRENCH_POLYNESIA,
+    eCSR_COUNTRY_INDEX_PAPUA_NEW_HUINEA,
+    eCSR_COUNTRY_INDEX_PHILIPPINES,
+    eCSR_COUNTRY_INDEX_PAKISTAN,
+    eCSR_COUNTRY_INDEX_POLAND,
+    eCSR_COUNTRY_INDEX_SAINT_PIERRE_AND_MIQUELON,
+    eCSR_COUNTRY_INDEX_PITCAIRN,
+    eCSR_COUNTRY_INDEX_PUERTO_RICO,
+    eCSR_COUNTRY_INDEX_PALESTINIAN_TERRITOTY_OCCUPIED,
+    eCSR_COUNTRY_INDEX_PORTUGAL,
+    eCSR_COUNTRY_INDEX_PALAU,
+    eCSR_COUNTRY_INDEX_PARAGUAY,
+    eCSR_COUNTRY_INDEX_QATAR,
+    eCSR_COUNTRY_INDEX_REUNION,
+    eCSR_COUNTRY_INDEX_ROMANIA,
+    eCSR_COUNTRY_INDEX_SERBIA,
+    eCSR_COUNTRY_INDEX_RUSSIAN,
+    eCSR_COUNTRY_INDEX_RWANDA,
+    eCSR_COUNTRY_INDEX_SAUDI_ARABIA,
+    eCSR_COUNTRY_INDEX_SOLOMON_ISLANDS,
+    eCSR_COUNTRY_INDEX_SEYCHELLES,
+    eCSR_COUNTRY_INDEX_SUDAN,
+    eCSR_COUNTRY_INDEX_SWEDEN,
+    eCSR_COUNTRY_INDEX_SINGAPORE,
+    eCSR_COUNTRY_INDEX_SAINT_HELENA,
+    eCSR_COUNTRY_INDEX_SLOVENIA,
+    eCSR_COUNTRY_INDEX_SVALBARD_AND_JAN_MAYEN,
+    eCSR_COUNTRY_INDEX_SLOVAKIA,
+    eCSR_COUNTRY_INDEX_SIERRA_LEONE,
+    eCSR_COUNTRY_INDEX_SAN_MARINO,
+    eCSR_COUNTRY_INDEX_SENEGAL,
+    eCSR_COUNTRY_INDEX_SOMOLIA,
+    eCSR_COUNTRY_INDEX_SURINAME,
+    eCSR_COUNTRY_INDEX_SAO_TOME_AND_PRINCIPE,
+    eCSR_COUNTRY_INDEX_EL_SALVADOR,
+    eCSR_COUNTRY_INDEX_SYRIAN_REP,
+    eCSR_COUNTRY_INDEX_SWAZILAND,
+    eCSR_COUNTRY_INDEX_TURKS_AND_CAICOS_ISLANDS,
+    eCSR_COUNTRY_INDEX_CHAD,
+    eCSR_COUNTRY_INDEX_FRENCH_SOUTHERN_TERRRTORY,
+    eCSR_COUNTRY_INDEX_TOGO,
+    eCSR_COUNTRY_INDEX_THAILAND,
+    eCSR_COUNTRY_INDEX_TAJIKSTAN,
+    eCSR_COUNTRY_INDEX_TOKELAU,
+    eCSR_COUNTRY_INDEX_TIMOR_LESTE,
+    eCSR_COUNTRY_INDEX_TURKMENISTAN,
+    eCSR_COUNTRY_INDEX_TUNISIA,
+    eCSR_COUNTRY_INDEX_TONGA,
+    eCSR_COUNTRY_INDEX_TURKEY,
+    eCSR_COUNTRY_INDEX_TRINIDAD_AND_TOBAGO,
+    eCSR_COUNTRY_INDEX_TUVALU,
+    eCSR_COUNTRY_INDEX_TAIWAN,
+    eCSR_COUNTRY_INDEX_TANZANIA,
+    eCSR_COUNTRY_INDEX_UKRAINE,
+    eCSR_COUNTRY_INDEX_UGANDA,
+    eCSR_COUNTRY_INDEX_US_MINOR_OUTLYING_ISLANDS,
+    eCSR_COUNTRY_INDEX_URUGUAY,
+    eCSR_COUNTRY_INDEX_UZBEKISTAN,
+    eCSR_COUNTRY_INDEX_HOLY_SEE,
+    eCSR_COUNTRY_INDEX_SAINT_VINCENT_AND_THE_GRENADINES,
+    eCSR_COUNTRY_INDEX_VENESUELA,
+    eCSR_COUNTRY_INDEX_VIRGIN_ISLANDS_BRITISH,
+    eCSR_COUNTRY_INDEX_VIRGIN_ISLANDS_US,
+    eCSR_COUNTRY_INDEX_VIET_NAM,
+    eCSR_COUNTRY_INDEX_VANUATU,
+    eCSR_COUNTRY_INDEX_WALLIS_AND_FUTUNA,
+    eCSR_COUNTRY_INDEX_SAMOA,
+    eCSR_COUNTRY_INDEX_YEMEN,
+    eCSR_COUNTRY_INDEX_MAYOTTE,
+    eCSR_COUNTRY_INDEX_SOTHER_AFRICA,
+    eCSR_COUNTRY_INDEX_ZAMBIA,
+    eCSR_COUNTRY_INDEX_ZIMBABWE,
+
+    eCSR_COUNTRY_INDEX_KOREA_1,
+    eCSR_COUNTRY_INDEX_KOREA_2,
+    eCSR_COUNTRY_INDEX_KOREA_3,
+    eCSR_COUNTRY_INDEX_KOREA_4,
+
+    eCSR_NUM_COUNTRY_INDEX,     
+}eCsrCountryIndex;
+//Please donot insert in the middle of the enum above because they tie to the indiex
+
+
+typedef struct tagCsrSirMBMsgHdr 
+{
+    tANI_U16 type;
+    tANI_U16 msgLen;
+
+}tCsrSirMBMsgHdr;
+
+typedef struct tagCsrCfgMsgTlvHdr 
+{
+    tANI_U32 type;
+    tANI_U32 length;    
+
+}tCsrCfgMsgTlvHdr;
+
+
+
+typedef struct tagCsrCfgMsgTlv
+{
+    tCsrCfgMsgTlvHdr Hdr;
+    tANI_U32 variable[ 1 ];    // placeholder for the data
+    
+}tCsrCfgMsgTlv;
+
+typedef struct tagCsrCfgGetRsp 
+{
+  tCsrSirMBMsgHdr hdr;
+  tANI_U32    respStatus;
+  tANI_U32    paramId;
+  tANI_U32    attribLen;
+  tANI_U32    attribVal[1];
+}tCsrCfgGetRsp;
+
+typedef struct tagCsrCfgSetRsp 
+{
+  
+  tCsrSirMBMsgHdr hdr;
+  tANI_U32    respStatus;
+  tANI_U32    paramId;
+}tCsrCfgSetRsp;
+
+
+typedef struct tagCsrDomainChnScanInfo
+{
+    tANI_U8 chnId;
+    tSirScanType scanType;  //whether this channel must be scan passively
+}tCsrDomainChnScanInfo;
+
+
+#if defined(__ANI_COMPILER_PRAGMA_PACK_STACK)
+#pragma pack( push )
+#pragma pack( 1 )
+#elif defined(__ANI_COMPILER_PRAGMA_PACK)
+#pragma pack( 1 )
+#endif
+
+// Generic Information Element Structure
+typedef __ani_attr_pre_packed struct sDot11IEHeader 
+{
+    tANI_U8 ElementID;
+    tANI_U8 Length;
+}__ani_attr_packed tDot11IEHeader;
+
+typedef __ani_attr_pre_packed struct tagCsrWmeInfoIe
+{
+    tDot11IEHeader IeHeader;
+    tANI_U8    Oui[ CSR_WME_OUI_SIZE ];  // includes the 3 byte OUI + 1 byte Type
+    tANI_U8    Subtype;
+    tANI_U8    Version;
+    tANI_U8    QoSInfo;
+    
+} __ani_attr_packed tCsrWmeInfoIe;
+
+typedef __ani_attr_pre_packed struct tagCsrWmeAcParms
+{
+    tANI_U8  AciAifsn;
+    tANI_U8  EcwMinEcwMax;
+    tANI_U16 TxOpLimit;
+    
+} __ani_attr_packed tCsrWmeAcParms;
+
+typedef __ani_attr_pre_packed struct tagCsrWmeParmIe
+{
+    tDot11IEHeader IeHeader;
+    tANI_U8    Oui[ CSR_WME_OUI_SIZE ];  // includes the 3 byte OUI + 1 byte Type
+    tANI_U8    Subtype;
+    tANI_U8    Version;
+    tANI_U8    QoSInfo;
+    tANI_U8    Reserved;
+    tCsrWmeAcParms   BestEffort;
+    tCsrWmeAcParms   Background;
+    tCsrWmeAcParms   Video;
+    tCsrWmeAcParms   Voice;
+        
+} __ani_attr_packed tCsrWmeParmIe;
+
+typedef __ani_attr_pre_packed struct tagCsrWpaIe 
+{
+    tDot11IEHeader IeHeader;
+    tANI_U8    Oui[ CSR_WPA_OUI_SIZE ];
+    tANI_U16   Version;
+    tANI_U8    MulticastOui[ CSR_WPA_OUI_SIZE ];
+    tANI_U16   cUnicastCyphers;
+    
+    __ani_attr_pre_packed struct {
+    
+        tANI_U8 Oui[ CSR_WPA_OUI_SIZE ];
+        
+    } __ani_attr_packed UnicastOui[ 1 ];
+    
+} __ani_attr_packed tCsrWpaIe;
+
+typedef __ani_attr_pre_packed struct tagCsrWpaAuthIe 
+{
+
+    tANI_U16 cAuthenticationSuites;
+    
+    __ani_attr_pre_packed struct {
+    
+        tANI_U8 Oui[ CSR_WPA_OUI_SIZE ];
+    
+    } __ani_attr_packed AuthOui[ 1 ];
+
+} __ani_attr_packed tCsrWpaAuthIe;
+
+
+typedef __ani_attr_pre_packed struct tagCsrRSNIe 
+{
+    tDot11IEHeader IeHeader;
+    tANI_U16   Version;
+    tANI_U8    MulticastOui[ CSR_RSN_OUI_SIZE ];
+    tANI_U16   cUnicastCyphers;
+    
+    __ani_attr_pre_packed struct {
+    
+        tANI_U8 Oui[ CSR_RSN_OUI_SIZE ];
+        
+    } __ani_attr_packed UnicastOui[ 1 ];
+    
+} __ani_attr_packed tCsrRSNIe;
+
+typedef __ani_attr_pre_packed struct tagCsrRSNAuthIe 
+{
+    tANI_U16 cAuthenticationSuites;
+    __ani_attr_pre_packed struct {
+    
+        tANI_U8 Oui[ CSR_RSN_OUI_SIZE ];
+    
+    } __ani_attr_packed AuthOui[ 1 ];
+
+} __ani_attr_packed tCsrRSNAuthIe;
+
+typedef __ani_attr_pre_packed struct tagCsrRSNCapabilities 
+{
+    tANI_U16 PreAuthSupported:1;
+    tANI_U16 NoPairwise:1;
+    tANI_U16 PTKSAReplayCounter:2;
+    tANI_U16 GTKSAReplayCounter:2;
+    tANI_U16 Reserved:10;
+} __ani_attr_packed tCsrRSNCapabilities;
+
+typedef __ani_attr_pre_packed struct tagCsrRSNPMKIe 
+{
+    tANI_U16 cPMKIDs;
+    
+    __ani_attr_pre_packed struct {
+    
+        tANI_U8 PMKID[ CSR_RSN_PMKID_SIZE ];
+    
+    } __ani_attr_packed PMKIDList[ 1 ];
+
+
+} __ani_attr_packed tCsrRSNPMKIe;
+
+typedef __ani_attr_pre_packed struct tCsrIELenInfo
+{
+    tANI_U8 min;
+    tANI_U8 max;
+} __ani_attr_packed tCsrIELenInfo;
+
+#ifdef FEATURE_WLAN_WAPI
+typedef __ani_attr_pre_packed struct tagCsrWapiIe 
+{
+    tDot11IEHeader IeHeader;
+    tANI_U16   Version;
+
+    tANI_U16 cAuthenticationSuites;
+    __ani_attr_pre_packed struct {
+
+        tANI_U8 Oui[ CSR_WAPI_OUI_SIZE ];
+
+    } __ani_attr_packed AuthOui[ 1 ];
+
+    tANI_U16   cUnicastCyphers;
+    __ani_attr_pre_packed struct {
+
+        tANI_U8 Oui[ CSR_WAPI_OUI_SIZE ];
+
+    } __ani_attr_packed UnicastOui[ 1 ];
+
+    tANI_U8    MulticastOui[ CSR_WAPI_OUI_SIZE ];    
+
+    __ani_attr_pre_packed struct {
+       tANI_U16 PreAuthSupported:1;
+       tANI_U16 Reserved:15;
+    } __ani_attr_packed tCsrWapiCapabilities;
+
+
+} __ani_attr_packed tCsrWapiIe;
+
+typedef __ani_attr_pre_packed struct tagCsrWAPIBKIe 
+{
+    tANI_U16 cBKIDs;
+    __ani_attr_pre_packed struct {
+
+        tANI_U8 BKID[ CSR_WAPI_BKID_SIZE ];
+
+    } __ani_attr_packed BKIDList[ 1 ];
+
+
+} __ani_attr_packed tCsrWAPIBKIe;
+#endif /* FEATURE_WLAN_WAPI */
+
+#if defined(__ANI_COMPILER_PRAGMA_PACK_STACK)
+#pragma pack( pop )
+#endif
+
+// Structure used to describe a group of continuous channels and hook it into the 
+// corresponding channel list
+typedef struct tagCsrChannelSet 
+{
+  tListElem      channelListLink;
+  tANI_U8   firstChannel;
+  tANI_U8   interChannelOffset;
+  tANI_U8   numChannels;
+  tANI_U8   txPower;
+}tCsrChannelSet;
+
+
+typedef struct sDot11InfoIBSSParmSet 
+{
+    tDot11IEHeader dot11IEHeader;
+    tANI_U8 ATIMWindow;
+}tDot11InfoIBSSParmSet;
+
+
+typedef struct sDot11IECountry 
+{
+    tDot11IEHeader dot11IEHeader;
+    tANI_U8 countryString[3];
+    tSirMacChanInfo chanInfo[1];
+}tDot11IECountry;
+
+
+typedef struct sDot11IEExtenedSupportedRates 
+{
+    tDot11IEHeader dot11IEHeader;
+    tANI_U8 ExtendedSupportedRates[ CSR_DOT11_EXTENDED_SUPPORTED_RATES_MAX ];
+}tDot11IEExtenedSupportedRates;
+
+#define CSR_DOT11_AP_NAME_MAX_LENGTH ( 32 )
+
+typedef struct tagDot11IEAPName
+{
+    tDot11IEHeader dot11IEHeader;
+    tANI_U8 ApName[ CSR_DOT11_AP_NAME_MAX_LENGTH ];
+}tDot11IEAPName;
+
+typedef struct tagDot11IE11HLocalPowerConstraint
+{
+    tDot11IEHeader dot11IEHeader;
+    tANI_U8 localPowerConstraint;
+
+}tDot11IE11HLocalPowerConstraint;
+
+typedef struct tagRoamingTimerInfo
+{
+    tpAniSirGlobal pMac;
+    tANI_U8 sessionId;
+} tCsrTimerInfo;
+
+
+#define CSR_IS_11A_BSS(pBssDesc)    ( eSIR_11A_NW_TYPE == (pBssDesc)->nwType )
+#define CSR_IS_BASIC_RATE(rate)     ((rate) & CSR_DOT11_BASIC_RATE_MASK)
+#define CSR_IS_QOS_BSS(pIes)  ( (pIes)->WMMParams.present || (pIes)->WMMInfoAp.present )
+
+#define CSR_IS_UAPSD_BSS(pIes) \
+    ( ((pIes)->WMMParams.present && ((pIes)->WMMParams.qosInfo & SME_QOS_AP_SUPPORTS_APSD)) || \
+               ((pIes)->WMMInfoAp.present && (pIes)->WMMInfoAp.uapsd) )
+
+//This macro returns the total length needed of Tlv with with len bytes of data
+#define GET_TLV_MSG_LEN(len)    GET_ROUND_UP((sizeof(tCsrCfgMsgTlvHdr) + (len)), sizeof(tANI_U32))
+
+tANI_BOOLEAN csrGetBssIdBssDesc( tHalHandle hHal, tSirBssDescription *pSirBssDesc, tCsrBssid *pBssId ); 
+tANI_BOOLEAN csrIsBssIdEqual( tHalHandle hHal, tSirBssDescription *pSirBssDesc1, tSirBssDescription *pSirBssDesc2 );
+
+eCsrMediaAccessType csrGetQoSFromBssDesc( tHalHandle hHal, tSirBssDescription *pSirBssDesc,
+                                          tDot11fBeaconIEs *pIes);
+tANI_BOOLEAN csrIsNULLSSID( tANI_U8 *pBssSsid, tANI_U8 len );
+tANI_BOOLEAN csrIsInfraBssDesc( tSirBssDescription *pSirBssDesc ); 
+tANI_BOOLEAN csrIsIbssBssDesc( tSirBssDescription *pSirBssDesc ); 
+tANI_BOOLEAN csrIsPrivacy( tSirBssDescription *pSirBssDesc );
+tSirResultCodes csrGetDisassocRspStatusCode( tSirSmeDisassocRsp *pSmeDisassocRsp );
+tSirResultCodes csrGetDeAuthRspStatusCode( tSirSmeDeauthRsp *pSmeRsp );
+tANI_U32 csrGetFragThresh( tHalHandle hHal );
+tANI_U32 csrGetRTSThresh( tHalHandle hHal );
+eCsrPhyMode csrGetPhyModeFromBssDesc( tSirBssDescription *pSirBssDesc );
+tANI_U32 csrGet11hPowerConstraint( tHalHandle hHal, tDot11fIEPowerConstraints *pPowerConstraint );
+tANI_U8 csrConstructRSNIe( tHalHandle hHal, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                            tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes, tCsrRSNIe *pRSNIe );
+tANI_U8 csrConstructWpaIe( tHalHandle hHal, tCsrRoamProfile *pProfile, tSirBssDescription *pSirBssDesc, 
+                           tDot11fBeaconIEs *pIes, tCsrWpaIe *pWpaIe );
+#ifdef FEATURE_WLAN_WAPI
+
+tANI_BOOLEAN csrIsProfileWapi( tCsrRoamProfile *pProfile );
+#endif /* FEATURE_WLAN_WAPI */
+//If a WPAIE exists in the profile, just use it. Or else construct one from the BSS
+//Caller allocated memory for pWpaIe and guarrantee it can contain a max length WPA IE
+tANI_U8 csrRetrieveWpaIe( tHalHandle hHal, tCsrRoamProfile *pProfile, tSirBssDescription *pSirBssDesc, 
+                          tDot11fBeaconIEs *pIes, tCsrWpaIe *pWpaIe );
+tANI_BOOLEAN csrIsSsidEqual( tHalHandle hHal, tSirBssDescription *pSirBssDesc1, 
+                             tSirBssDescription *pSirBssDesc2, tDot11fBeaconIEs *pIes2 );
+//Null ssid means match
+tANI_BOOLEAN csrIsSsidInList( tHalHandle hHal, tSirMacSSid *pSsid, tCsrSSIDs *pSsidList );
+tANI_BOOLEAN csrIsProfileWpa( tCsrRoamProfile *pProfile );
+tANI_BOOLEAN csrIsProfileRSN( tCsrRoamProfile *pProfile );
+//This function returns the raw byte array of WPA and/or RSN IE
+tANI_BOOLEAN csrGetWpaRsnIe( tHalHandle hHal, tANI_U8 *pIes, tANI_U32 len,
+                             tANI_U8 *pWpaIe, tANI_U8 *pcbWpaIe, tANI_U8 *pRSNIe, tANI_U8 *pcbRSNIe);
+//If a RSNIE exists in the profile, just use it. Or else construct one from the BSS
+//Caller allocated memory for pWpaIe and guarrantee it can contain a max length WPA IE
+tANI_U8 csrRetrieveRsnIe( tHalHandle hHal, tANI_U32 sessionId, tCsrRoamProfile *pProfile, tSirBssDescription *pSirBssDesc, 
+                          tDot11fBeaconIEs *pIes, tCsrRSNIe *pRsnIe );
+#ifdef FEATURE_WLAN_WAPI
+//If a WAPI IE exists in the profile, just use it. Or else construct one from the BSS
+//Caller allocated memory for pWapiIe and guarrantee it can contain a max length WAPI IE
+tANI_U8 csrRetrieveWapiIe( tHalHandle hHal, tANI_U32 sessionId, tCsrRoamProfile *pProfile, tSirBssDescription *pSirBssDesc, 
+                          tDot11fBeaconIEs *pIes, tCsrWapiIe *pWapiIe );
+#endif /* FEATURE_WLAN_WAPI */
+tANI_BOOLEAN csrSearchChannelListForTxPower(tHalHandle hHal, tSirBssDescription *pBssDescription, tCsrChannelSet *returnChannelGroup);
+tANI_BOOLEAN csrRatesIsDot11Rate11bSupportedRate( tANI_U8 dot11Rate );
+tANI_BOOLEAN csrRatesIsDot11Rate11aSupportedRate( tANI_U8 dot11Rate );
+tAniEdType csrTranslateEncryptTypeToEdType( eCsrEncryptionType EncryptType ); 
+//pIes shall contain IEs from pSirBssDesc. It shall be returned from function csrGetParsedBssDescriptionIEs 
+tANI_BOOLEAN csrIsSecurityMatch( tHalHandle hHal, tCsrAuthList *authType, tCsrEncryptionList *pUCEncryptionType, tCsrEncryptionList *pMCEncryptionType,
+                                 tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes, 
+                                 eCsrAuthType *negotiatedAuthtype, eCsrEncryptionType *negotiatedUCCipher, eCsrEncryptionType *negotiatedMCCipher );
+tANI_BOOLEAN csrIsBSSTypeMatch(eCsrRoamBssType bssType1, eCsrRoamBssType bssType2);
+tANI_BOOLEAN csrIsBssTypeIBSS(eCsrRoamBssType bssType);
+tANI_BOOLEAN csrIsBssTypeWDS(eCsrRoamBssType bssType);
+//ppIes can be NULL. If caller want to get the *ppIes allocated by this function, pass in *ppIes = NULL
+//Caller needs to free the memory in this case
+tANI_BOOLEAN csrMatchBSS( tHalHandle hHal, tSirBssDescription *pBssDesc, tCsrScanResultFilter *pFilter, 
+                          eCsrAuthType *pNegAuth, eCsrEncryptionType *pNegUc, eCsrEncryptionType *pNegMc,
+                          tDot11fBeaconIEs **ppIes);
+
+tANI_BOOLEAN csrIsBssidMatch( tHalHandle hHal, tCsrBssid *pProfBssid, tCsrBssid *BssBssid );
+tANI_BOOLEAN csrMatchBSSToConnectProfile( tHalHandle hHal, tCsrRoamConnectedProfile *pProfile,
+                                          tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes );
+tANI_BOOLEAN csrRatesIsDot11RateSupported( tHalHandle hHal, tANI_U8 rate );
+tANI_U16 csrRatesFindBestRate( tSirMacRateSet *pSuppRates, tSirMacRateSet *pExtRates, tSirMacPropRateSet *pPropRates );
+tSirBssType csrTranslateBsstypeToMacType(eCsrRoamBssType csrtype);
+                            
+//Caller allocates memory for pIEStruct
+eHalStatus csrParseBssDescriptionIEs(tHalHandle hHal, tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIEStruct);
+//This function will allocate memory for the parsed IEs to the caller. Caller must free the memory
+//after it is done with the data only if this function succeeds
+eHalStatus csrGetParsedBssDescriptionIEs(tHalHandle hHal, tSirBssDescription *pBssDesc, tDot11fBeaconIEs **ppIEStruct);
+
+tANI_BOOLEAN csrValidateCountryString( tHalHandle hHal, tANI_U8 *pCountryString );
+tSirScanType csrGetScanType(tpAniSirGlobal pMac, tANI_U8 chnId);
+
+tANI_U8 csrToUpper( tANI_U8 ch );
+eHalStatus csrGetPhyModeFromBss(tpAniSirGlobal pMac, tSirBssDescription *pBSSDescription, 
+                                eCsrPhyMode *pPhyMode, tDot11fBeaconIEs *pIes);
+
+//fForce -- force reassoc regardless of whether there is any change
+//The reason is that for UAPSD-bypass, the code underneath this call determine whether
+//to allow UAPSD. The information in pModProfileFields reflects what the user wants.
+//There may be discrepency in it. UAPSD-bypass logic should decide if it needs to reassoc
+eHalStatus csrReassoc(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                      tCsrRoamModifyProfileFields *pModProfileFields,
+                      tANI_U32 *pRoamId, v_BOOL_t fForce);
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+tANI_BOOLEAN csrIsProfile11r( tCsrRoamProfile *pProfile );
+tANI_BOOLEAN csrIsAuthType11r( eCsrAuthType AuthType );
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+tANI_BOOLEAN csrIsAuthTypeCCX( eCsrAuthType AuthType );
+tANI_BOOLEAN csrIsProfileCCX( tCsrRoamProfile *pProfile );
+#endif
+
+#endif
+
diff --git a/CORE/SME/inc/measApi.h b/CORE/SME/inc/measApi.h
new file mode 100644
index 0000000..1e9b029
--- /dev/null
+++ b/CORE/SME/inc/measApi.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
diff --git a/CORE/SME/inc/measInternal.h b/CORE/SME/inc/measInternal.h
new file mode 100644
index 0000000..1e9b029
--- /dev/null
+++ b/CORE/SME/inc/measInternal.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
diff --git a/CORE/SME/inc/p2p_Api.h b/CORE/SME/inc/p2p_Api.h
new file mode 100644
index 0000000..13276de
--- /dev/null
+++ b/CORE/SME/inc/p2p_Api.h
@@ -0,0 +1,527 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/******************************************************************************
+*
+* Name:  p2p_Api.h
+*
+* Description: P2P FSM defines.
+*
+* Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+* Qualcomm Confidential and Proprietary.
+*
+******************************************************************************/
+
+#ifndef __P2P_API_H__
+#define __P2P_API_H__
+
+#include "vos_types.h"
+#include "halTypes.h"
+#include "palTimer.h"
+#include "vos_lock.h"
+
+typedef struct sP2pPsConfig{
+  tANI_U8   opp_ps;
+  tANI_U32  ctWindow;
+  tANI_U8   count; 
+  tANI_U32  duration;
+  tANI_U32  interval;
+  tANI_U32  single_noa_duration;
+  tANI_U8   psSelection;
+  tANI_U8   sessionid;   
+}tP2pPsConfig,*tpP2pPsConfig;
+
+typedef eHalStatus (*remainOnChanCallback)( tHalHandle, void* context, 
+                                            eHalStatus status );
+
+typedef struct sRemainOnChn{
+    tANI_U8 chn;
+    tANI_U32 duration;
+    remainOnChanCallback callback;
+  void *pCBContext;
+}tRemainOnChn, tpRemainOnChn;
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+
+#define MAX_SOCIAL_CHANNELS 3
+#define P2P_OPERATING_CHANNEL 6
+#define P2P_MAX_GROUP_LIMIT 5
+#define P2P_MAC_ADDRESS_LEN 6
+#define MAX_LISTEN_SEARCH_CYCLE 3
+#define P2P_LISTEN_TIMEOUT_AUTO    500 //0.5 sec
+#define P2P_LISTEN_TIMEOUT_HIGH    200 //0.4 sec
+#define P2P_LISTEN_TIMEOUT         1000  //1 sec
+#define P2P_REMAIN_ON_CHAN_TIMEOUT 300
+#define P2P_REMAIN_ON_CHAN_TIMEOUT_HIGH 1000
+#define P2P_REMAIN_ON_CHAN_TIMEOUT_LOW 100
+#define ACTION_FRAME_RETRY_TIMEOUT 50
+#define P2P_COUNTRY_CODE_LEN 3
+
+#define P2P_CLEAR_POWERSAVE 0
+#define P2P_OPPORTUNISTIC_PS 1
+#define P2P_PERIODIC_NOA 2
+#define P2P_SINGLE_NOA 4
+
+
+/* Wi-Fi Direct Device Discovery Type */
+typedef enum ep2pDiscoverType {
+   /** Driver must perform device discovery only using the scan phase*/
+   WFD_DISCOVER_TYPE_SCAN_ONLY = 1,
+   /** Driver must perform device discovery only using the find phase*/
+   WFD_DISCOVER_TYPE_FIND_ONLY = 2,
+   /** Driver can use either use scan phase or find phase to discovery 
+   P2P devices. In our case Driver uses scan phase */
+   WFD_DISCOVER_TYPE_AUTO = 3,
+   /*Scan only social channel*/
+   WFD_DISCOVER_SCAN_ONLY_SOCIAL_CHN,
+   /** If it is set, driver must perform a complete discovery, 
+   If it is false, it can do partial discovery.*/
+   WFD_DISCOVER_TYPE_FORCED = 0x80000000
+} ep2pDiscoverType, *ePp2pDiscoverType;
+
+//bit mask for what to discover
+#define QCWLAN_P2P_DISCOVER_DEVICE     0x1
+#define QCWLAN_P2P_DISCOVER_GO         0x2
+#define QCWLAN_P2P_DISCOVER_ANY        0x8
+
+#define P2P_DISCOVER_SCAN_ONLY(t) ( (WFD_DISCOVER_TYPE_SCAN_ONLY == (t)) \
+                                    || (WFD_DISCOVER_SCAN_ONLY_SOCIAL_CHN == (t)) )
+
+/* Scan Type */
+typedef enum ep2pScanType {
+   P2P_SCAN_TYPE_ACTIVE = 1,  /**  device should perform active scans for the scan phase of device discovery */
+   P2P_SCAN_TYPE_PASSIVE = 2, /** device should perform passive scanning for the scan phase of device discovery  */
+   P2P_SCAN_TYPE_AUTO = 3     /** The selection of the scan type is upto the driver */
+} ep2pScanType, * ePp2pScanType;
+
+/** Listen State Discoverability */
+typedef enum ep2pListenStateDiscoverability {
+   P2P_DEVICE_NOT_DISCOVERABLE, /**  Wi-Fi Direct Device Port must not make itself discoverable */
+   P2P_DEVICE_AUTO_AVAILABILITY, /** Wi-Fi Direct Device Port must periodically put itself in the listen state to become discoverable*/
+   P2P_DEVICE_HIGH_AVAILABILITY  /** Wi-Fi Direct Device Port must be frequently put itself in the listen state 
+                                 to increase the speed and reliability of remote devices discovering it */
+} ep2pListenStateDiscoverability, * ePp2pListenStateDiscoverability;
+
+typedef enum ep2pOperatingMode {
+   OPERATION_MODE_INVALID,
+   OPERATION_MODE_P2P_DEVICE,
+   OPERATION_MODE_P2P_GROUP_OWNER,
+   OPERATION_MODE_P2P_CLIENT
+}ep2pOperatingMode;
+
+typedef struct _tp2pDiscoverDeviceFilter{ 
+   tSirMacAddr DeviceID; 
+   v_UCHAR_t ucBitmask; 
+   tSirMacSSid GroupSSID; 
+} tp2pDiscoverDeviceFilter;
+
+typedef struct _tp2pDiscoverRequest {
+   ep2pDiscoverType discoverType;
+   ep2pScanType scanType;
+   tANI_U32 uDiscoverTimeout;
+   tANI_U32 uNumDeviceFilters;
+   tp2pDiscoverDeviceFilter *pDeviceFilters;
+   tANI_BOOLEAN bForceScanLegacyNetworks;
+   tANI_U32 uNumOfLegacySSIDs;
+   tANI_U8  *pLegacySSIDs;
+   tANI_U32 uIELen;
+   tANI_U8 *pIEField;
+} tP2PDiscoverRequest;
+
+typedef enum _eP2PDiscoverStatus {
+   eP2P_DISCOVER_SUCCESS,
+   eP2P_DISCOVER_FAILURE,
+   eP2P_DISCOVER_ABORT,
+   eP2P_DIRECTED_DISCOVER
+} eP2PDiscoverStatus;
+
+typedef eHalStatus (*p2pDiscoverCompleteCallback)(tHalHandle hHal, void *pContext, eP2PDiscoverStatus discoverStatus);
+
+typedef struct sP2PGroupId {
+    tANI_U8 present;
+    tANI_U8 deviceAddress[6];
+    tANI_U8 num_ssid;
+    tANI_U8 ssid[32];
+} tP2PGroupId;
+
+typedef struct sP2PGroupBssid {
+    tANI_U8 present;
+    tANI_U8 P2PGroupBssid[6];
+} tP2PGroupBssid;
+
+typedef struct sP2PChannel {
+   tANI_U8 present;
+   tANI_U8 countryString[P2P_COUNTRY_CODE_LEN];
+   tANI_U8 regulatoryClass;
+   tANI_U8 channel;
+} tP2P_OperatingChannel, tP2P_ListenChannel;
+
+/** Structure contains parameters required for Wi-Fi Direct Device functionality such as device discovery, Group Owner Negotiation */
+typedef enum P2PFrameType {
+   eP2P_INVALID_FRM,
+   eP2P_PROBE_REQ,
+   eP2P_PROBE_RSP,
+   eP2P_GONEGO_REQ,
+   eP2P_GONEGO_RES,
+   eP2P_GONEGO_CNF,
+   eP2P_PROVISION_DISCOVERY_REQUEST,
+   eP2P_PROVISION_DISCOVERY_RESPONSE,
+   eP2P_BEACON,
+   eP2P_GROUP_ID,
+   eP2P_ASSOC_REQ,
+   eP2P_INVITATION_REQ,
+   eP2P_INVITATION_RSP,
+   eP2P_DEVICE_DISCOVERY_REQ,
+   eP2P_DEVICE_DISCOVERY_RSP,
+} eP2PFrameType;
+
+typedef enum P2PRequest {
+   eWFD_DISCOVER_REQUEST,
+   eWFD_DEVICE_ID,
+   eWFD_DEVICE_CAPABILITY,
+   eWFD_GROUP_OWNER_CAPABILITY,
+   eWFD_DEVICE_INFO,
+   eWFD_SECONDARY_DEVICE_TYPE_LIST,
+   eWFD_ADDITIONAL_IE,
+   eWFD_GROUP_ID,
+   eWFD_SEND_GO_NEGOTIATION_REQUEST,
+   eWFD_SEND_GO_NEGOTIATION_RESPONSE,
+   eWFD_SEND_GO_NEGOTIATION_CONFIRMATION,
+   eWFD_SEND_PROVISION_DISCOVERY_REQUEST,
+   eWFD_SEND_PROVISION_DISCOVERY_RESPONSE,
+   eWFD_SEND_INVITATION_REQUEST,
+   eWFD_SEND_INVITATION_RESPONSE,
+   eWFD_OPERATING_CHANNEL,
+   eWFD_LISTEN_CHANNEL
+} eP2PRequest;
+
+typedef struct _p2p_device_capability_config {
+   tANI_BOOLEAN bServiceDiscoveryEnabled;
+   tANI_BOOLEAN bClientDiscoverabilityEnabled;
+   tANI_BOOLEAN bConcurrentOperationSupported;
+   tANI_BOOLEAN bInfrastructureManagementEnabled;
+   tANI_BOOLEAN bDeviceLimitReached;
+   tANI_BOOLEAN bInvitationProcedureEnabled;
+   tANI_U32 WPSVersionsEnabled;
+} tp2p_device_capability_config;
+
+typedef struct _p2p_group_owner_capability_config {
+   tANI_BOOLEAN bPersistentGroupEnabled;
+   tANI_BOOLEAN bIntraBSSDistributionSupported;
+   tANI_BOOLEAN bCrossConnectionSupported;
+   tANI_BOOLEAN bPersistentReconnectSupported;
+   tANI_BOOLEAN bGroupFormationEnabled;
+   tANI_U32 uMaximumGroupLimit;
+} tp2p_group_owner_capability_config;
+
+typedef struct _tP2P_ProvDiscoveryReq {
+   tANI_U8     dialogToken;
+   tANI_U8  PeerDeviceAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U32 uSendTimeout;
+   tANI_U8  GroupCapability;
+   tP2PGroupId GroupId;
+   tANI_BOOLEAN bUseGroupID;
+   tANI_U32 uIELength;
+   tANI_U8 *IEdata;
+} tP2P_ProvDiscoveryReq;
+
+typedef struct _tP2P_ProvDiscoveryRes {
+   tANI_U8  dialogToken;
+   tANI_U8  ReceiverDeviceAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U32 uSendTimeout;
+   tANI_U32 uIELength;
+   tANI_U8 *IEdata;
+} tP2P_ProvDiscoveryRes;
+
+typedef struct p2p_go_request {
+   tANI_U8     dialogToken;
+   tANI_U8    peerDeviceAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U32 uSendTimeout;
+   tANI_U8 GoIntent;
+   tANI_U32 GoTimeout;
+   tANI_U32 ClientTimeout;
+   tANI_U8    IntendedInterfaceAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U8 GroupCapability;
+   tANI_U32 uIELength;
+   tANI_U8 *IEdata;
+} tP2P_go_request;
+
+typedef struct p2p_go_confirm {
+   tANI_U8    peerDeviceAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U8    dialog_token;
+   tANI_U32 uSendTimeout;
+   tANI_U8    status;
+   tANI_U8 GroupCapability;
+   tP2PGroupId GroupId;
+   tANI_BOOLEAN bUsedGroupId;
+   tANI_U32 uIELength;
+   tANI_U8 *IEdata;
+} tP2P_go_confirm;
+
+typedef struct p2p_go_response {
+   tANI_U8    peerDeviceAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U8    dialog_token;
+   tANI_U32 uSendTimeout;
+   tANI_U8    status;
+   tANI_U8 GoIntent;
+   tANI_U32 GoTimeout;
+   tANI_U32 ClientTimeout;
+   tANI_U8    IntendedInterfaceAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U8 GroupCapability;
+   tP2PGroupId GroupId;
+   tANI_BOOLEAN bUsedGroupId;
+   tANI_U32 uIELength;
+   tANI_U8 *IEdata;
+} tP2P_go_response;
+
+//Invitation Req parameters
+typedef struct p2p_invitation_request {
+    tANI_U8 DialogToken;
+    tANI_U8 PeerDeviceAddress[P2P_MAC_ADDRESS_LEN];
+    tANI_U32 uSendTimeout;
+    tANI_U32 GoTimeout;
+    tANI_U32 ClientTimeout; 
+    tANI_U8 InvitationFlags;
+    tP2PGroupBssid GroupBSSID;
+    tP2P_OperatingChannel OperatingChannel;
+    tP2PGroupId GroupID;
+    tANI_U32 uIELength;
+    tANI_U8 *IEdata;
+} tP2P_invitation_request;
+
+
+//Invitation Response parameters
+typedef struct p2p_invitation_response {
+    tANI_U8 ReceiverDeviceAddress[P2P_MAC_ADDRESS_LEN];
+    tANI_U8 DialogToken;
+    void* RequestContext;
+    tANI_U32 uSendTimeout;
+    tANI_U8     status;
+    tANI_U32 GoTimeout;
+    tANI_U32 ClientTimeout; 
+    tP2PGroupBssid GroupBSSID;
+    tP2P_OperatingChannel OperatingChannel;
+    tANI_U32 uIELength;
+    tANI_U8 *IEdata;
+} tP2P_invitation_response;
+
+typedef enum eOUISubType {
+   eOUI_P2P_GONEGO_REQ,
+   eOUI_P2P_GONEGO_RES,
+   eOUI_P2P_GONEGO_CNF,
+   eOUI_P2P_INVITATION_REQ,
+   eOUI_P2P_INVITATION_RES,
+   eOUI_P2P_DEVICE_DISCOVERABILITY_REQ,
+   eOUI_P2P_DEVICE_DISCOVERABILITY_RES,
+   eOUI_P2P_PROVISION_DISCOVERY_REQ,
+   eOUI_P2P_PROVISION_DISCOVERY_RES,
+   eOUI_P2P_INVALID
+}eOUISubType;
+
+typedef enum _eP2PPort {
+   eP2PPortDevice,
+   eP2PPortGroupOwner,
+   eP2PPortClient
+} eP2PPort;
+
+typedef enum eListenDiscoverableState {
+   eStateDisabled,
+   eStateEnabled,
+
+}eListenDiscoverableState;
+
+typedef enum P2PRemainOnChnReason
+{
+   eP2PRemainOnChnReasonUnknown,
+   eP2PRemainOnChnReasonDiscovery, //Part of the discovery (search and listen)
+   eP2PRemainOnChnReasonSendFrame, //Found peer and before sending request frame
+   eP2PRemainOnChnReasonListen,    //In listen-only mode
+}eP2PRemainOnChnReason;
+
+typedef struct sGroupFormationReq {
+   tCsrBssid deviceAddress;
+   tANI_U8 targetListenChannel;
+   tANI_U8 persistent_group;
+   tANI_U8 group_limit; /* may be internal */
+   tANI_U8 GO_config_timeout;
+   tANI_U8 CL_config_timeout;
+   tANI_U8 GO_intent;
+   tANI_U16 devicePasswdId;
+   tSirMacAddr groupBssid;
+   tSirMacSSid groupSsid;
+}tGroupFormationReq;
+
+typedef struct tP2PConfigParam
+{
+   v_U32_t P2POperatingChannel;
+   v_U32_t P2PListenChannel;
+   v_U32_t P2PPSSelection;
+   v_U32_t P2POpPSCTWindow;
+   v_U32_t P2PNoADuration;
+   v_U32_t P2PNoACount;
+   v_U32_t P2PNoAInterval;
+}tP2PConfigParam;
+
+#endif
+
+typedef struct sp2pContext
+{
+   v_CONTEXT_t vosContext;
+   tHalHandle hHal;
+   tANI_U8 sessionId; //Session id corresponding to P2P. On windows it is same as HDD sessionid not sme sessionid.
+   tANI_U8 SMEsessionId;
+   tANI_U8 probeReqForwarding;
+   tANI_U8 *probeRspIe;
+   tANI_U32 probeRspIeLength;
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+   tANI_U8 numClients;
+   tANI_U32 maxGroupLimit;
+   ep2pOperatingMode operatingmode;
+   tANI_U8 state;
+   tANI_U8 socialChannel[MAX_SOCIAL_CHANNELS];
+   tANI_U8 currentSearchIndex;
+   tANI_U8 listenIndex;
+   tANI_U8 dialogToken;
+   tANI_U8 receivedDialogToken;
+   eOUISubType actionFrameOUI;
+   eP2PFrameType actionFrameType;
+   tANI_BOOLEAN actionFrameTimeout;
+   tANI_U8 *pSentActionFrame;
+   tANI_U32 ActionFrameLen;
+   tANI_U32 ActionFrameSendTimeout;
+   eListenDiscoverableState listenDiscoverableState;
+   tPalTimerHandle listenTimerHandler;
+   tPalTimerHandle WPSRegistrarCheckTimerHandler;
+   tANI_U32 WPSRegistrarSet;
+   tANI_U8 bWaitForWPSReady;
+   tANI_U8 bInGroupFormation;
+   tPalTimerHandle discoverTimer;
+   tPalTimerHandle retryActionFrameTimer;
+   tPalTimerHandle actionFrameTimer;
+   tPalTimerHandle nextActionFrameTimer;
+   tANI_U8 peerMacAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U8 selfMacAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U8 ReceiverDeviceAddress[P2P_MAC_ADDRESS_LEN];
+   tANI_U8 listen_search_cycle;
+   ep2pDiscoverType discoverType;
+   ep2pScanType scanType;
+   tANI_U32 uDiscoverTimeout;
+   tp2pDiscoverDeviceFilter *directedDiscoveryFilter;
+   tANI_U32 uNumDeviceFilters;
+   //Number of deviceFilter directedDiscoveryFilter holds
+   tANI_U32 uNumDeviceFilterAllocated; 
+   tGroupFormationReq formationReq;
+   tANI_U8 GroupFormationPending;
+   tANI_BOOLEAN PeerFound;
+   tANI_BOOLEAN directedDiscovery;
+   tANI_U32 listenDuration;
+   tANI_U32 expire_time;
+   p2pDiscoverCompleteCallback p2pDiscoverCBFunc;
+   void *pContext;
+   tANI_BOOLEAN bForceScanLegacyNetworks;
+   tANI_U8 *DiscoverReqIeField;
+   tANI_U32 DiscoverReqIeLength;
+   tANI_U8 *GoNegoReqIeField;
+   tANI_U32 GoNegoReqIeLength;
+   tANI_U8 *GoNegoResIeField;
+   tANI_U32 GoNegoResIeLength;
+   tANI_U8 *GoNegoCnfIeField;
+   tANI_U32 GoNegoCnfIeLength;
+   tANI_U8 *ProvDiscReqIeField;
+   tANI_U32 ProvDiscReqIeLength;
+   tANI_U8 *ProvDiscResIeField;
+   tANI_U32 ProvDiscResIeLength;
+   tANI_U8 *InvitationReqIeField;
+   tANI_U32 InvitationReqIeLength;
+   tANI_U8 *InvitationResIeField;
+   tANI_U32 InvitationResIeLength;
+   tANI_U32 DiscoverableCfg;
+   vos_spin_lock_t lState;
+   tANI_U8 *pNextActionFrm;
+   tANI_U32 nNextFrmLen;
+   tANI_U32 nNextFrameTimeOut;
+   eP2PFrameType NextActionFrameType;
+   tANI_U8 ssid[32];
+   v_U32_t P2PListenChannel;
+   v_U32_t P2POperatingChannel;
+   tP2pPsConfig pNoA;
+   tANI_U8 OriginalGroupCapability;
+#endif
+} tp2pContext, *tPp2pContext;
+
+
+eHalStatus sme_RemainOnChannel( tHalHandle hHal, tANI_U8 sessionId,
+                                tANI_U8 channel, tANI_U32 duration,
+                                remainOnChanCallback callback, 
+                                void *pContext );
+eHalStatus sme_ReportProbeReq( tHalHandle hHal, tANI_U8 flag );
+eHalStatus sme_updateP2pIe( tHalHandle hHal, void *p2pIe, 
+                            tANI_U32 p2pIeLength );
+eHalStatus sme_sendAction( tHalHandle hHal, tANI_U8 sessionId,
+                           const tANI_U8 *pBuf, tANI_U32 len );
+eHalStatus sme_CancelRemainOnChannel( tHalHandle hHal, tANI_U8 sessionId );
+eHalStatus sme_p2pOpen( tHalHandle hHal );
+eHalStatus p2pStop( tHalHandle hHal );
+eHalStatus sme_p2pClose( tHalHandle hHal );
+eHalStatus sme_p2pSetPs( tHalHandle hHal, tP2pPsConfig * data );
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+eHalStatus p2pRemainOnChannel( tHalHandle hHal, tANI_U8 sessionId,
+                               tANI_U8 channel, tANI_U32 duration,
+                               remainOnChanCallback callback, void *pContext,
+                               eP2PRemainOnChnReason reason);
+#else
+eHalStatus p2pRemainOnChannel( tHalHandle hHal, tANI_U8 sessionId,
+                               tANI_U8 channel, tANI_U32 duration,
+                               remainOnChanCallback callback, void *pContext);
+#endif
+eHalStatus p2pSendAction( tHalHandle hHal, tANI_U8 sessionId,
+                          const tANI_U8 *pBuf, tANI_U32 len );
+eHalStatus p2pCancelRemainOnChannel( tHalHandle hHal, tANI_U8 sessionId );
+eHalStatus p2pSetPs( tHalHandle hHal, tP2pPsConfig *pNoA );
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+eHalStatus p2pRemainOnChannelCallback(tHalHandle halHandle, void *pContext, eHalStatus scan_status);
+eHalStatus P2P_DiscoverRequest(tHalHandle hHal, tANI_U8 SessionID, tP2PDiscoverRequest *pDiscoverRequest, 
+                               p2pDiscoverCompleteCallback callback, void *pContext);
+tANI_U8 p2pGetDialogToken(tHalHandle hHal, tANI_U8 SessionID, eP2PFrameType actionFrameType);
+eHalStatus P2P_ListenStateDiscoverable(tHalHandle hHal, tANI_U8 sessionId, ep2pListenStateDiscoverability listenState);
+eHalStatus p2pCreateSendActionFrame(tHalHandle hHal, tANI_U8 SessionID, 
+      void *p2pactionframe, eP2PFrameType actionFrameType, tANI_U32 timeout);
+eHalStatus p2pScanRequest(tp2pContext *p2pContext, p2pDiscoverCompleteCallback callback, void *pContext);
+void p2pActionFrameTimerHandler(void *pContext);
+void p2pListenDiscoverTimerHandler(void *pContext);
+void p2pDiscoverTimerHandler(void *pContext);
+void p2pRetryActionFrameTimerHandler(void *pContext);
+eHalStatus p2pGrpFormationRemainOnChanRspCallback(tHalHandle halHandle, void *pContext, tANI_U32 scanId, eCsrScanStatus scan_status);
+eHalStatus p2pChangeDefaultConfigParam(tHalHandle hHal, tP2PConfigParam *pParam);
+eHalStatus p2pGetConfigParam(tHalHandle hHal, tP2PConfigParam *pParam);
+eHalStatus p2pPS(tHalHandle hHal, tANI_U8 sessionId);
+eHalStatus p2pCloseSession(tHalHandle hHal, tANI_U8 SessionID);
+eHalStatus p2pSetSessionId(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 SmeSessionId);
+tANI_BOOLEAN p2pIsOperatingChannEqualListenChann(tHalHandle hHal, tANI_U8 SessionID);
+eHalStatus p2pGetListenChannel(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 *channel);
+eHalStatus p2pSetListenChannel(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 channel);
+eHalStatus p2pStopDiscovery(tHalHandle hHal, tANI_U8 SessionID);
+tANI_U8 getP2PSessionIdFromSMESessionId(tHalHandle hHal, tANI_U8 SessionID);
+void p2pCallDiscoverCallback(tp2pContext *p2pContext, eP2PDiscoverStatus statusCode);
+eHalStatus p2pGetResultFilter(tp2pContext *pP2pContext,
+                              tCsrScanResultFilter *pFilter);
+#endif//INTERNAL
+#endif //__P2P_API_H__
diff --git a/CORE/SME/inc/pmc.h b/CORE/SME/inc/pmc.h
new file mode 100644
index 0000000..e2e3c7f
--- /dev/null
+++ b/CORE/SME/inc/pmc.h
@@ -0,0 +1,251 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/******************************************************************************
+*
+* Name:  pmc.h
+*
+* Description: Power Management Control (PMC) internal definitions.
+*
+* Copyright 2008 (c) Qualcomm, Incorporated.  
+  All Rights Reserved.
+* Qualcomm Confidential and Proprietary.
+*
+******************************************************************************/
+
+#ifndef __PMC_H__
+#define __PMC_H__
+
+
+#include "palTimer.h"
+#include "csrLinkList.h"
+#include "pmcApi.h"
+#include "smeInternal.h"
+
+
+//Change PMC_ABORT to no-op for now. We need to define it as VOS_ASSERT(0) once we 
+//cleanup the usage.
+#define PMC_ABORT  
+
+/* Host power sources. */
+typedef enum ePowerSource
+{
+    AC_POWER,  /* host is operating from AC power */
+    BATTERY_POWER  /* host is operating from battery power */
+} tPowerSource;
+
+
+/* Power save check routine list entry. */
+typedef struct sPowerSaveCheckEntry
+{
+    tListElem link;  /* list links */
+    tANI_BOOLEAN (*checkRoutine) (void *checkContext);  /* power save check routine */
+    void *checkContext;  /* value to be passed as parameter to routine specified above */
+} tPowerSaveCheckEntry, *tpPowerSaveCheckEntry;
+
+
+/* Device Power State update indication list entry. */
+typedef struct sDeviceStateUpdateIndEntry
+{
+    tListElem link;  /* list links */
+    void (*callbackRoutine) (void *callbackContext, tPmcState pmcState); /* Callback routine to be invoked when pmc changes device state */
+    void *callbackContext;  /* value to be passed as parameter to routine specified above */
+} tDeviceStateUpdateIndEntry, *tpDeviceStateUpdateIndEntry;
+
+/* Request full power callback routine list entry. */
+typedef struct sRequestFullPowerEntry
+{
+    tListElem link;  /* list links */
+    void (*callbackRoutine) (void *callbackContext, eHalStatus status);  /* routine to call when full power is restored */
+    void *callbackContext;  /* value to be passed as parameter to routine specified above */
+} tRequestFullPowerEntry, *tpRequestFullPowerEntry;
+
+
+/* Request BMPS callback routine list entry. */
+typedef struct sRequestBmpsEntry
+{
+   tListElem link;  /* list links */
+
+   /* routine to call when BMPS request succeeded/failed */
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status);
+
+   /* value to be passed as parameter to routine specified above */
+   void *callbackContext;  
+
+} tRequestBmpsEntry, *tpRequestBmpsEntry;
+
+
+/* Start U-APSD callback routine list entry. */
+typedef struct sStartUapsdEntry
+{
+   tListElem link;  /* list links */
+
+   /* routine to call when Uapsd Start succeeded/failed*/
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status);
+
+   /* value to be passed as parameter to routine specified above */
+   void *callbackContext;  
+
+} tStartUapsdEntry, *tpStartUapsdEntry;
+
+typedef struct sPmcDeferredMsg
+{
+    tListElem link;
+    tpAniSirGlobal pMac;
+    tANI_U16 messageType;
+    tANI_U16 size;  //number of bytes in u.data
+    union
+    {
+        tSirPowerSaveCfg powerSaveConfig;
+        tSirWowlAddBcastPtrn wowlAddPattern;
+        tSirWowlDelBcastPtrn wowlDelPattern;
+        tANI_U8 data[1];    //a place holder
+    }u;
+} tPmcDeferredMsg;
+
+
+
+/* Current PMC information for a particular device. */
+typedef struct sPmcInfo
+{
+    tPowerSource powerSource;  /* host power source */
+    tPmcSwitchState hwWlanSwitchState;  /* Hardware WLAN Switch state */
+    tPmcSwitchState swWlanSwitchState;  /* Software WLAN Switch state */
+    tPmcState pmcState;  /* PMC state */
+    tANI_BOOLEAN requestFullPowerPending;  /* TRUE if a request for full power is pending */
+    tRequestFullPowerReason requestFullPowerReason; /* reason for requesting full power */
+    tPmcImpsConfigParams impsConfig;  /* IMPS configuration */
+    tPmcBmpsConfigParams bmpsConfig;  /* BMPS configuration */
+    tPmcSmpsConfigParams smpsConfig;  /* SMPS configuration */
+    tANI_BOOLEAN impsEnabled;  /* TRUE if IMPS is enabled */
+    tANI_BOOLEAN bmpsEnabled;  /* TRUE if BMPS is enabled */
+    tANI_BOOLEAN autoBmpsEntryEnabled;  /* TRUE if auto BMPS entry is enabled. If set to TRUE, PMC will
+                                           attempt to put the device into BMPS on entry into full Power */
+    tANI_BOOLEAN bmpsRequestedByHdd; /*TRUE if BMPS mode has been requested by HDD */
+    tANI_BOOLEAN bmpsRequestQueued; /*If a enter BMPS request is queued*/
+    tANI_BOOLEAN smpsEnabled;  /* TRUE if SMPS is enabled */
+    tANI_BOOLEAN remainInPowerActiveTillDHCP;  /* Remain in Power active till DHCP completes */
+    tANI_U32 remainInPowerActiveThreshold;  /*Remain in Power active till DHCP threshold*/
+    tANI_U32 impsPeriod;  /* amount of time to remain in IMPS */
+    void (*impsCallbackRoutine) (void *callbackContext, eHalStatus status);  /* routine to call when IMPS period
+                                                                                has finished */ 
+    void *impsCallbackContext;  /* value to be passed as parameter to routine specified above */
+    tPalTimerHandle hImpsTimer;  /* timer to use with IMPS */
+    vos_timer_t hTrafficTimer;  /* timer to measure traffic for BMPS */
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    tPalTimerHandle hDiagEvtTimer;  /* timer to report PMC state through DIAG event */
+#endif
+    tPalTimerHandle hExitPowerSaveTimer;  /* timer for deferred exiting of power save mode */
+    tDblLinkList powerSaveCheckList; /* power save check routine list */
+    tDblLinkList requestFullPowerList; /* request full power callback routine list */
+    tANI_U32 cLastTxUnicastFrames;  /* transmit unicast frame count at last BMPS traffic timer expiration */
+    tANI_U32 cLastRxUnicastFrames;  /* receive unicast frame count at last BMPS traffic timer expiration */
+
+
+    tANI_BOOLEAN uapsdEnabled;  /* TRUE if UAPSD is enabled */
+    tANI_BOOLEAN uapsdSessionRequired; /* TRUE if device should go to UAPSD on entering BMPS*/
+    tDblLinkList requestBmpsList; /* request Bmps callback routine list */
+    tDblLinkList requestStartUapsdList; /* request start Uapsd callback routine list */
+    tANI_BOOLEAN standbyEnabled;  /* TRUE if Standby is enabled */
+    void (*standbyCallbackRoutine) (void *callbackContext, eHalStatus status); /* routine to call for standby request */ 
+    void *standbyCallbackContext;/* value to be passed as parameter to routine specified above */
+    tDblLinkList deviceStateUpdateIndList; /*update device state indication list */
+    tANI_BOOLEAN pmcReady; /*whether eWNI_SME_SYS_READY_IND has been sent to PE or not */
+    tANI_BOOLEAN wowlEnabled;  /* TRUE if WoWL is enabled */
+    tANI_BOOLEAN wowlModeRequired; /* TRUE if device should go to WOWL on entering BMPS */
+    void (*enterWowlCallbackRoutine) (void *callbackContext, eHalStatus status); /* routine to call for wowl request */ 
+    void *enterWowlCallbackContext;/* value to be passed as parameter to routine specified above */
+    tSirSmeWowlEnterParams wowlEnterParams; /* WOWL mode configuration */
+    tDblLinkList deferredMsgList;   //The message in here are deferred and DONOT expect response from PE
+    tANI_BOOLEAN rfSuppliesVotedOff;  //Whether RF supplies are voted off or not.
+#ifdef FEATURE_WLAN_SCAN_PNO
+    preferredNetworkFoundIndCallback  prefNetwFoundCB; /* routine to call for Preferred Network Found Indication */ 
+    void *preferredNetworkFoundIndCallbackContext;/* value to be passed as parameter to routine specified above */
+#endif // FEATURE_WLAN_SCAN_PNO
+#ifdef WLAN_FEATURE_PACKET_FILTERING
+    FilterMatchCountCallback  FilterMatchCountCB; /* routine to call for Packet Coalescing Filter Match Count */ 
+    void *FilterMatchCountCBContext;/* value to be passed as parameter to routine specified above */
+#endif // WLAN_FEATURE_PACKET_FILTERING
+#ifdef WLAN_FEATURE_GTK_OFFLOAD
+    GTKOffloadGetInfoCallback  GtkOffloadGetInfoCB; /* routine to call for GTK Offload Information */ 
+    void *GtkOffloadGetInfoCBContext;        /* value to be passed as parameter to routine specified above */
+#endif // WLAN_FEATURE_GTK_OFFLOAD
+
+#ifdef WLAN_WAKEUP_EVENTS
+    void (*wakeReasonIndCB) (void *callbackContext, tpSirWakeReasonInd pWakeReasonInd);  /* routine to call for Wake Reason Indication */ 
+    void *wakeReasonIndCBContext;  /* value to be passed as parameter to routine specified above */
+#endif // WLAN_WAKEUP_EVENTS
+} tPmcInfo, *tpPmcInfo;
+
+
+//MACRO
+#define PMC_IS_READY(pMac)  ( ((pMac)->pmc.pmcReady) && (STOPPED != (pMac)->pmc.pmcState) )
+
+
+/* Routine definitions. */
+extern eHalStatus pmcEnterLowPowerState (tHalHandle hHal);
+extern eHalStatus pmcExitLowPowerState (tHalHandle hHal);
+extern eHalStatus pmcEnterFullPowerState (tHalHandle hHal);
+extern eHalStatus pmcEnterRequestFullPowerState (tHalHandle hHal, tRequestFullPowerReason fullPowerReason);
+extern eHalStatus pmcEnterRequestImpsState (tHalHandle hHal);
+extern eHalStatus pmcEnterImpsState (tHalHandle hHal);
+extern eHalStatus pmcEnterRequestBmpsState (tHalHandle hHal);
+extern eHalStatus pmcEnterBmpsState (tHalHandle hHal);
+extern eHalStatus pmcEnterRequestStartUapsdState (tHalHandle hHal);
+extern eHalStatus pmcEnterUapsdState (tHalHandle hHal);
+extern eHalStatus pmcEnterRequestStopUapsdState (tHalHandle hHal);
+extern eHalStatus pmcEnterRequestStandbyState (tHalHandle hHal);
+extern eHalStatus pmcEnterStandbyState (tHalHandle hHal);
+extern tANI_BOOLEAN pmcPowerSaveCheck (tHalHandle hHal);
+extern eHalStatus pmcSendPowerSaveConfigMessage (tHalHandle hHal);
+extern eHalStatus pmcSendMessage (tpAniSirGlobal pMac, tANI_U16 messageType, void *pMessageData, tANI_U32 messageSize);
+extern void pmcDoCallbacks (tHalHandle hHal, eHalStatus callbackStatus);
+extern void pmcDoBmpsCallbacks (tHalHandle hHal, eHalStatus callbackStatus);
+extern void pmcDoStartUapsdCallbacks (tHalHandle hHal, eHalStatus callbackStatus);
+extern void pmcDoStandbyCallbacks (tHalHandle hHal, eHalStatus callbackStatus);
+extern eHalStatus pmcStartTrafficTimer (tHalHandle hHal, tANI_U32 expirationTime);
+extern void pmcStopTrafficTimer (tHalHandle hHal);
+extern void pmcImpsTimerExpired (tHalHandle hHal);
+extern void pmcTrafficTimerExpired (tHalHandle hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+extern eHalStatus pmcStartDiagEvtTimer (tHalHandle hHal);
+extern void pmcStopDiagEvtTimer (tHalHandle hHal);
+extern void pmcDiagEvtTimerExpired (tHalHandle hHal);
+#endif
+
+extern void pmcExitPowerSaveTimerExpired (tHalHandle hHal);
+extern tPmcState pmcGetPmcState (tHalHandle hHal);
+extern const char* pmcGetPmcStateStr(tPmcState state);
+extern void pmcDoDeviceStateUpdateCallbacks (tHalHandle hHal, tPmcState state);
+extern eHalStatus pmcRequestEnterWowlState(tHalHandle hHal, tpSirSmeWowlEnterParams wowlEnterParams);
+extern eHalStatus pmcEnterWowlState (tHalHandle hHal);
+extern eHalStatus pmcRequestExitWowlState(tHalHandle hHal);
+extern void pmcDoEnterWowlCallbacks (tHalHandle hHal, eHalStatus callbackStatus);
+//The function will request for full power as well in addition to defer the message
+extern eHalStatus pmcDeferMsg( tpAniSirGlobal pMac, tANI_U16 messageType, 
+                                               void *pData, tANI_U32 size);
+extern eHalStatus pmcIssueCommand( tpAniSirGlobal pMac, eSmeCommandType cmdType, void *pvParam, 
+                                   tANI_U32 size, tANI_BOOLEAN fPutToListHead );
+extern eHalStatus pmcEnterImpsCheck( tpAniSirGlobal pMac );
+extern eHalStatus pmcEnterBmpsCheck( tpAniSirGlobal pMac );
+extern tANI_BOOLEAN pmcShouldBmpsTimerRun( tpAniSirGlobal pMac );
+#endif
diff --git a/CORE/SME/inc/pmcApi.h b/CORE/SME/inc/pmcApi.h
new file mode 100644
index 0000000..05a7fff
--- /dev/null
+++ b/CORE/SME/inc/pmcApi.h
@@ -0,0 +1,484 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/******************************************************************************
+
+*
+
+* Name:  pmcApi.h
+
+*
+
+* Description: Power Management Control (PMC) API definitions.
+
+* Copyright 2008 (c) Qualcomm, Incorporated.  
+
+* All Rights Reserved.
+
+* Qualcomm Confidential and Proprietary.
+
+*
+
+******************************************************************************/
+
+
+#ifndef __PMC_API_H__
+
+#define __PMC_API_H__
+
+//This timer value determines the default periodicity at which BMPS retries will happen
+//This default value is overwritten typicaly by OS specific registry/INI values. 
+#define BMPS_TRAFFIC_TIMER_DEFAULT 5000  //unit = ms
+#define DHCP_REMAIN_POWER_ACTIVE_THRESHOLD 12 // (12 * 5) sec = 60 seconds = 1 min
+
+//This timer value is used when starting the timer right after association. This value
+//should be large enough to allow the auth, DHCP handshake to complete
+#define BMPS_TRAFFIC_TIMER_ALLOW_SECURITY_DHCP 8000  //unit = ms
+
+#define PMC_IS_CHIP_ACCESSIBLE(pmcState) ( (IMPS != (pmcState)) && (REQUEST_IMPS != (pmcState)) && \
+       (STANDBY != (pmcState)) && (REQUEST_STANDBY != (pmcState)) )
+
+
+
+/* Power events that are signaled to PMC. */
+
+typedef enum ePmcPowerEvent
+
+{
+
+    ePMC_SYSTEM_HIBERNATE,  /* host is entering hibernation */
+
+    ePMC_SYSTEM_RESUME,  /* host is resuming after hibernation */
+
+    ePMC_HW_WLAN_SWITCH_OFF,  /* Hardware WLAN Switch has been turned off */
+
+    ePMC_HW_WLAN_SWITCH_ON,  /* Hardware WLAN Switch has been turned on */
+
+    ePMC_SW_WLAN_SWITCH_OFF,  /* Software WLAN Switch has been turned off */
+
+    ePMC_SW_WLAN_SWITCH_ON,  /* Software WLAN Switch has been turned on */
+
+    ePMC_BATTERY_OPERATION,  /* host is now operating on battery power */
+
+    ePMC_AC_OPERATION  /* host is now operating on AC power */
+
+} tPmcPowerEvent;
+
+
+
+
+/* Power saving modes. */
+
+typedef enum ePmcPowerSavingMode
+
+{
+
+    ePMC_IDLE_MODE_POWER_SAVE,  /* Idle Mode Power Save (IMPS) */
+
+    ePMC_BEACON_MODE_POWER_SAVE,  /* Beacon Mode Power Save (BMPS) */
+
+    ePMC_SPATIAL_MULTIPLEX_POWER_SAVE,  /* Spatial Multiplexing Power Save (SMPS) */
+
+    ePMC_UAPSD_MODE_POWER_SAVE,  /* Unscheduled Automatic Power Save Delivery Mode */
+
+    ePMC_STANDBY_MODE_POWER_SAVE,  /* Standby Power Save Mode */
+
+    ePMC_WOWL_MODE_POWER_SAVE  /* Wake-on-Wireless LAN Power Save Mode */
+
+} tPmcPowerSavingMode;
+
+
+
+
+/* Switch states. */
+
+typedef enum ePmcSwitchState
+
+{
+
+    ePMC_SWITCH_OFF,  /* switch off */
+
+    ePMC_SWITCH_ON  /* switch on */
+
+} tPmcSwitchState;
+
+
+
+
+/* Device power states. */
+
+typedef enum ePmcPowerState
+
+{
+
+    ePMC_FULL_POWER,  /* full power */
+
+    ePMC_LOW_POWER,  /* low power */
+
+} tPmcPowerState;
+
+ 
+
+/* PMC states. */
+
+typedef enum ePmcState
+
+{
+
+    STOPPED, /* PMC is stopped */
+
+    FULL_POWER, /* full power */
+
+    LOW_POWER, /* low power */
+
+    REQUEST_IMPS,  /* requesting IMPS */
+
+    IMPS,  /* in IMPS */
+
+    REQUEST_BMPS,  /* requesting BMPS */
+
+    BMPS,  /* in BMPS */
+
+    REQUEST_FULL_POWER,  /* requesting full power */
+
+    REQUEST_START_UAPSD,  /* requesting Start UAPSD */
+
+    REQUEST_STOP_UAPSD,  /* requesting Stop UAPSD */
+
+    UAPSD,           /* in UAPSD */
+
+    REQUEST_STANDBY,  /* requesting standby mode */
+
+    STANDBY,  /* in standby mode */
+
+    REQUEST_ENTER_WOWL, /* requesting enter WOWL */
+
+    REQUEST_EXIT_WOWL,  /* requesting exit WOWL */
+
+    WOWL                /* Chip in WOWL mode */
+
+} tPmcState;
+
+
+/* Which beacons should be forwarded to the host. */
+
+typedef enum ePmcBeaconsToForward
+
+{
+
+    ePMC_NO_BEACONS,  /* none */
+
+    ePMC_BEACONS_WITH_TIM_SET,  /* with TIM set */
+
+    ePMC_BEACONS_WITH_DTIM_SET,  /* with DTIM set */
+
+    ePMC_NTH_BEACON,  /* every Nth beacon */
+
+    ePMC_ALL_BEACONS  /* all beacons */
+
+} tPmcBeaconsToForward;
+
+
+
+
+/* The Spatial Mulitplexing Power Save modes. */
+
+typedef enum ePmcSmpsMode
+
+{
+
+    ePMC_DYNAMIC_SMPS,  /* dynamic SMPS */
+
+    ePMC_STATIC_SMPS  /* static SMPS */
+
+} tPmcSmpsMode;
+
+
+
+
+/* Configuration parameters for Idle Mode Power Save (IMPS). */
+
+typedef struct sPmcImpsConfigParams
+
+{
+
+    tANI_BOOLEAN enterOnAc;  /* FALSE if device should enter IMPS only when host operating
+
+                                on battery power, TRUE if device should enter always */
+
+} tPmcImpsConfigParams, *tpPmcImpsConfigParams;
+
+
+
+
+/* Configuration parameters for Beacon Mode Power Save (BMPS). */
+
+typedef struct sPmcBmpsConfigParams
+
+{
+
+    tANI_BOOLEAN enterOnAc;  /* FALSE if device should enter BMPS only when host operating on
+
+                                battery power, TRUE if device should enter always */
+
+    tANI_U32 txThreshold;  /* transmit rate under which BMPS should be entered (frames / traffic measurement period) */
+
+    tANI_U32 rxThreshold;  /* receive rate under which BMPS should be entered (frames / traffic measurement period) */
+
+    tANI_U32 trafficMeasurePeriod; /* period for BMPS traffic measurement (milliseconds) */
+
+    tANI_U32 bmpsPeriod;  /* amount of time in low power (beacon intervals) */
+
+    tPmcBeaconsToForward forwardBeacons;  /* which beacons should be forwarded to the host */
+
+    tANI_U32 valueOfN;  /* the value of N when forwardBeacons is set to ePMC_NTH_BEACON */
+
+    tANI_BOOLEAN usePsPoll;  /* TRUE if PS-POLL should be used to retrieve frames from AP, FALSE if a
+
+                                null data frame with the PM bit reset should be used */
+
+    tANI_BOOLEAN setPmOnLastFrame; /* TRUE to keep device in BMPS as much as possible, FALSE otherwise, TRUE means:
+
+                                      1) PM bit should be set on last pending transmit data frame
+
+                                      2) null frame with PM bit set should be transmitted after last pending receive
+
+                                         frame has been processed */
+
+    tANI_BOOLEAN enableBeaconEarlyTermination; /* if TRUE, BET feature in RIVA 
+                                      will be enabled, FALSE otherwise, TRUE means:
+                                      RXP will read the beacon header for the 
+                                      TIM bit & discard the rest if set to 0, 
+                                      while in BMPS              */
+    tANI_U8      bcnEarlyTermWakeInterval; /* This specifies how often in terms 
+                                      of LI we will disable BET in order to sync 
+                                      up TSF*/
+
+} tPmcBmpsConfigParams, *tpPmcBmpsConfigParams;
+
+
+
+
+/* Configuration parameters for Spatial Mulitplexing Power Save (SMPS). */
+
+typedef struct sPmcSmpsConfigParams
+
+{
+
+    tPmcSmpsMode mode;  /* mode to use */
+
+    tANI_BOOLEAN enterOnAc;  /* FALSE if device should enter SMPS only when host operating on
+
+                                battery power, TRUE if device should enter always */
+
+} tPmcSmpsConfigParams, *tpPmcSmpsConfigParams;
+
+
+/* Routine definitions. */
+
+extern eHalStatus pmcOpen (tHalHandle hHal);
+
+extern eHalStatus pmcStart (tHalHandle hHal);
+
+extern eHalStatus pmcStop (tHalHandle hHal);
+
+extern eHalStatus pmcClose (tHalHandle hHal );
+
+extern eHalStatus pmcSignalPowerEvent (tHalHandle hHal, tPmcPowerEvent event);
+
+extern eHalStatus pmcSetConfigPowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode, void *pConfigParams);
+
+extern eHalStatus pmcGetConfigPowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode, void *pConfigParams);
+
+extern eHalStatus pmcEnablePowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode);
+
+extern eHalStatus pmcStartAutoBmpsTimer (tHalHandle hHal);
+
+extern eHalStatus pmcStopAutoBmpsTimer (tHalHandle hHal);
+
+extern eHalStatus pmcDisablePowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode);
+
+extern eHalStatus pmcQueryPowerState (tHalHandle hHal, tPmcPowerState *pPowerState, tPmcSwitchState *pHwWlanSwitchState,
+
+                                      tPmcSwitchState *pSwWlanSwitchState);
+
+extern tANI_BOOLEAN pmcIsPowerSaveEnabled (tHalHandle hHal, tPmcPowerSavingMode psMode);
+
+extern eHalStatus pmcRequestFullPower (tHalHandle hHal, void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+
+                                       void *callbackContext, tRequestFullPowerReason fullPowerReason);
+
+extern eHalStatus pmcRequestImps (tHalHandle hHal, tANI_U32 impsPeriod,
+
+                                  void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+
+                                  void *callbackContext);
+
+extern eHalStatus pmcRegisterPowerSaveCheck (tHalHandle hHal, tANI_BOOLEAN (*checkRoutine) (void *checkContext),
+
+                                             void *checkContext);
+
+extern eHalStatus pmcDeregisterPowerSaveCheck (tHalHandle hHal, tANI_BOOLEAN (*checkRoutine) (void *checkContext));
+
+extern void pmcMessageProcessor (tHalHandle hHal, tSirSmeRsp *pMsg);
+
+
+extern eHalStatus pmcRequestBmps (
+
+   tHalHandle hHal,
+
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+
+   void *callbackContext);
+
+
+extern eHalStatus pmcStartUapsd (
+
+   tHalHandle hHal,
+
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+
+   void *callbackContext);
+
+
+extern eHalStatus pmcStopUapsd (tHalHandle hHal);
+
+
+extern eHalStatus pmcRequestStandby (
+
+   tHalHandle hHal,
+
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+
+   void *callbackContext);
+
+
+extern eHalStatus pmcRegisterDeviceStateUpdateInd (tHalHandle hHal, 
+
+   void (*callbackRoutine) (void *callbackContext, tPmcState pmcState),
+
+   void *callbackContext);
+
+
+extern eHalStatus pmcDeregisterDeviceStateUpdateInd (tHalHandle hHal, 
+
+   void (*callbackRoutine) (void *callbackContext, tPmcState pmcState));
+
+
+extern eHalStatus pmcReady(tHalHandle hHal);
+
+
+void pmcDumpInit(tHalHandle hHal);
+
+
+extern eHalStatus pmcWowlAddBcastPattern (
+
+   tHalHandle hHal, 
+
+   tpSirWowlAddBcastPtrn pattern);
+
+
+extern eHalStatus pmcWowlDelBcastPattern (
+
+   tHalHandle hHal, 
+
+   tpSirWowlDelBcastPtrn pattern);
+
+
+extern eHalStatus pmcEnterWowl ( 
+
+    tHalHandle hHal, 
+
+    void (*enterWowlCallbackRoutine) (void *callbackContext, eHalStatus status),
+
+    void *enterWowlCallbackContext,
+#ifdef WLAN_WAKEUP_EVENTS
+    void (*wakeReasonIndCB) (void *callbackContext, tpSirWakeReasonInd pWakeReasonInd),
+
+    void *wakeReasonIndCBContext,
+#endif // WLAN_WAKEUP_EVENTS
+    tpSirSmeWowlEnterParams wowlEnterParams);
+
+extern eHalStatus pmcExitWowl (tHalHandle hHal);
+
+
+extern eHalStatus pmcSetHostOffload (tHalHandle hHal, tpSirHostOffloadReq pRequest);
+
+/* ---------------------------------------------------------------------------
+    \fn pmcSetKeepAlive
+    \brief  Set the Keep Alive feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest - Pointer to the Keep Alive.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the keepalive.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+extern eHalStatus pmcSetKeepAlive (tHalHandle hHal, tpSirKeepAliveReq pRequest);
+
+extern tANI_BOOLEAN pmcValidateConnectState( tHalHandle hHal );
+
+extern tANI_BOOLEAN pmcAllowImps( tHalHandle hHal );
+
+
+#ifdef FEATURE_WLAN_SCAN_PNO
+/*Pref netw found Cb declaration*/
+typedef void(*preferredNetworkFoundIndCallback)(void *callbackContext, tpSirPrefNetworkFoundInd pPrefNetworkFoundInd);
+
+extern eHalStatus pmcSetPreferredNetworkList(tHalHandle hHal, tpSirPNOScanReq pRequest, tANI_U8 sessionId, preferredNetworkFoundIndCallback callbackRoutine, void *callbackContext);
+extern eHalStatus pmcSetRssiFilter(tHalHandle hHal, v_U8_t rssiThreshold);
+#endif // FEATURE_WLAN_SCAN_PNO
+
+#ifdef WLAN_FEATURE_PACKET_FILTERING
+// Packet Coalescing Filter Match Count Callback declaration
+typedef void(*FilterMatchCountCallback)(void *callbackContext,
+                                        tpSirRcvFltPktMatchRsp pRcvFltPktMatchRsp);
+extern eHalStatus pmcGetFilterMatchCount(tHalHandle hHal, FilterMatchCountCallback callbackRoutine, void *callbackContext);
+#endif // WLAN_FEATURE_PACKET_FILTERING
+
+#ifdef WLAN_FEATURE_GTK_OFFLOAD
+// GTK Offload Information Callback declaration
+typedef void(*GTKOffloadGetInfoCallback)(void *callbackContext, tpSirGtkOffloadGetInfoRspParams pGtkOffloadGetInfoRsp);
+
+/* ---------------------------------------------------------------------------
+    \fn pmcSetGTKOffload
+    \brief  Set GTK offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pGtkOffload - Pointer to the GTK offload request.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the offload.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+extern eHalStatus pmcSetGTKOffload (tHalHandle hHal, tpSirGtkOffloadParams pGtkOffload);
+
+/* ---------------------------------------------------------------------------
+    \fn pmcGetGTKOffload
+    \brief  Get GTK offload information.
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine - Pointer to the GTK Offload Get Info response callback routine.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the offload.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+extern eHalStatus pmcGetGTKOffload (tHalHandle hHal, GTKOffloadGetInfoCallback callbackRoutine, void *callbackContext);
+#endif // WLAN_FEATURE_GTK_OFFLOAD
+
+#endif
+
diff --git a/CORE/SME/inc/smeInside.h b/CORE/SME/inc/smeInside.h
new file mode 100644
index 0000000..742ac7d
--- /dev/null
+++ b/CORE/SME/inc/smeInside.h
@@ -0,0 +1,195 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+#if !defined( __SMEINSIDE_H )
+#define __SMEINSIDE_H
+
+
+/**=========================================================================
+  
+  \file  smeInside.h
+  
+  \brief prototype for SME structures and APIs used insside SME
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+
+/* $Header$ */
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#include "vos_status.h"
+#include "vos_lock.h"
+#include "vos_trace.h"
+#include "vos_memory.h"
+#include "vos_types.h"
+#include "sirApi.h"
+#include "csrInternal.h"
+#include "sme_QosApi.h"
+#include "smeQosInternal.h"
+
+
+
+#if defined WLAN_FEATURE_VOWIFI
+#include "sme_RrmApi.h"
+#endif
+
+
+/*-------------------------------------------------------------------------- 
+  Type declarations
+  ------------------------------------------------------------------------*/
+
+#define SME_TOTAL_COMMAND  20
+
+
+typedef struct sGenericPmcCmd
+{
+    tANI_U32 size;  //sizeof the data in the union, if any
+    tRequestFullPowerReason fullPowerReason;
+    tANI_BOOLEAN fReleaseWhenDone; //if TRUE, the command shall not put back to the queue, free te memory instead.
+    union
+    {
+        tExitBmpsInfo exitBmpsInfo;
+        tSirSmeWowlEnterParams enterWowlInfo;
+    }u;
+} tGenericPmcCmd;
+
+
+typedef struct sGenericQosCmd
+{
+    sme_QosWmmTspecInfo tspecInfo;
+    sme_QosEdcaAcType ac;
+    v_U8_t tspec_mask;
+} tGenericQosCmd;
+
+#ifdef WLAN_FEATURE_P2P
+typedef struct sRemainChlCmd
+{
+    tANI_U8 chn;
+    tANI_U8 phyMode;
+    tANI_U32 duration;
+    void* callback;
+    void* callbackCtx;
+}tRemainChlCmd;
+
+typedef struct sNoACmd
+{
+    tP2pPsConfig NoA;
+} tNoACmd;
+#endif
+
+typedef struct tagSmeCmd
+{
+    tListElem Link;
+    eSmeCommandType command;
+    tANI_U32 sessionId;
+    union
+    {
+        tScanCmd scanCmd;
+        tRoamCmd roamCmd;
+        tWmStatusChangeCmd wmStatusChangeCmd;
+        tSetKeyCmd setKeyCmd;
+        tRemoveKeyCmd removeKeyCmd;
+        tGenericPmcCmd pmcCmd;
+        tGenericQosCmd qosCmd;
+#ifdef WLAN_FEATURE_P2P
+        tRemainChlCmd remainChlCmd;
+        tNoACmd NoACmd;
+#endif
+        tAddStaForSessionCmd addStaSessionCmd;
+        tDelStaForSessionCmd delStaSessionCmd;
+    }u;
+}tSmeCmd;
+
+
+
+/*-------------------------------------------------------------------------- 
+                         Internal to SME
+  ------------------------------------------------------------------------*/
+
+//To get a command buffer
+//Return: NULL if there no more command buffer left
+tSmeCmd *smeGetCommandBuffer( tpAniSirGlobal pMac );
+void smePushCommand( tpAniSirGlobal pMac, tSmeCmd *pCmd, tANI_BOOLEAN fHighPriority );
+void smeProcessPendingQueue( tpAniSirGlobal pMac );
+void smeReleaseCommand(tpAniSirGlobal pMac, tSmeCmd *pCmd);
+void purgeSmeSessionCmdList(tpAniSirGlobal pMac, tANI_U32 sessionId);
+tANI_BOOLEAN smeCommandPending(tpAniSirGlobal pMac);
+tANI_BOOLEAN pmcProcessCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+//this function is used to abort a command where the normal processing of the command
+//is terminated without going through the normal path. it is here to take care of callbacks for
+//the command, if applicable.
+void pmcAbortCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fStopping );
+tANI_BOOLEAN qosProcessCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+
+eHalStatus csrProcessScanCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+eHalStatus csrRoamProcessCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+void csrRoamProcessWmStatusChangeCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+void csrReinitRoamCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand); 
+void csrReinitWmStatusChangeCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+void csrReinitSetKeyCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+void csrReinitRemoveKeyCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+eHalStatus csrRoamProcessSetKeyCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+eHalStatus csrRoamProcessRemoveKeyCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+void csrReleaseCommandSetKey(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+void csrReleaseCommandRemoveKey(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+//eHalStatus csrRoamIssueSetKeyCommand( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamSetKey *pSetKey, tANI_U32 roamId );
+eHalStatus csrRoamIssueRemoveKeyCommand( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                         tCsrRoamRemoveKey *pRemoveKey, tANI_U32 roamId );
+eHalStatus csrIsFullPowerNeeded( tpAniSirGlobal pMac, tSmeCmd *pCommand, tRequestFullPowerReason *pReason,
+                                 tANI_BOOLEAN *pfNeedPower);
+void csrAbortCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fStopping );
+
+eHalStatus sme_AcquireGlobalLock( tSmeStruct *psSme);
+eHalStatus sme_ReleaseGlobalLock( tSmeStruct *psSme);
+
+
+eHalStatus csrProcessAddStaSessionCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+eHalStatus csrProcessAddStaSessionRsp( tpAniSirGlobal pMac, tANI_U8 *pMsg);
+eHalStatus csrProcessDelStaSessionCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+eHalStatus csrProcessDelStaSessionRsp( tpAniSirGlobal pMac, tANI_U8 *pMsg);
+
+#ifdef WLAN_NS_OFFLOAD
+/* ---------------------------------------------------------------------------
+    \fn pmcSetNSOffload
+    \brief  Set the host offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest - Pointer to the offload request.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the offload.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcSetNSOffload (tHalHandle hHal, tpSirHostOffloadReq pRequest);
+#endif //WLAN_NS_OFFLOAD
+
+#ifdef FEATURE_WLAN_SCAN_PNO
+eHalStatus pmcSetPreferredNetworkList(tHalHandle hHal, tpSirPNOScanReq pRequest, tANI_U8 sessionId, preferredNetworkFoundIndCallback callbackRoutine,  void *callbackContext);
+eHalStatus pmcUpdateScanParams(tHalHandle hHal, tCsrConfig *pRequest, tCsrChannel *pChannelList, tANI_U8 b11dResolved);
+eHalStatus pmcSetRssiFilter(tHalHandle hHal,   v_U8_t        rssiThreshold);
+#endif // FEATURE_WLAN_SCAN_PNO
+eHalStatus pmcSetPowerParams(tHalHandle hHal,   tSirSetPowerParamsReq*  pwParams);
+
+tANI_BOOLEAN csrRoamGetConcurrencyConnectStatusForBmps(tpAniSirGlobal pMac);
+#endif //#if !defined( __SMEINSIDE_H )
diff --git a/CORE/SME/inc/smeInternal.h b/CORE/SME/inc/smeInternal.h
new file mode 100644
index 0000000..3d27d9b
--- /dev/null
+++ b/CORE/SME/inc/smeInternal.h
@@ -0,0 +1,116 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+#if !defined( __SMEINTERNAL_H )
+#define __SMEINTERNAL_H
+
+
+/**=========================================================================
+  
+  \file  smeInternal.h
+  
+  \brief prototype for SME internal structures and APIs used for SME and MAC
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+
+/* $Header$ */
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#include "vos_status.h"
+#include "vos_lock.h"
+#include "vos_trace.h"
+#include "vos_memory.h"
+#include "vos_types.h"
+#include "csrLinkList.h"
+
+/*-------------------------------------------------------------------------- 
+  Type declarations
+  ------------------------------------------------------------------------*/
+
+// Mask can be only have one bit set
+typedef enum eSmeCommandType 
+{
+    eSmeNoCommand = 0, 
+    eSmeDropCommand,
+    //CSR
+    eSmeCsrCommandMask = 0x10000,   //this is not a command, it is to identify this is a CSR command
+    eSmeCommandScan,
+    eSmeCommandRoam, 
+    eSmeCommandWmStatusChange, 
+    eSmeCommandSetKey,
+    eSmeCommandRemoveKey,
+    eSmeCommandAddStaSession,
+    eSmeCommandDelStaSession,
+    //PMC
+    eSmePmcCommandMask = 0x20000, //To identify PMC commands
+    eSmeCommandEnterImps,
+    eSmeCommandExitImps,
+    eSmeCommandEnterBmps,
+    eSmeCommandExitBmps,
+    eSmeCommandEnterUapsd,
+    eSmeCommandExitUapsd,
+    eSmeCommandEnterWowl,
+    eSmeCommandExitWowl,
+    eSmeCommandEnterStandby,
+    //QOS
+    eSmeQosCommandMask = 0x40000,  //To identify Qos commands
+    eSmeCommandAddTs,
+    eSmeCommandDelTs,
+#ifdef WLAN_FEATURE_P2P
+    eSmeCommandRemainOnChannel,
+    eSmeCommandNoAUpdate,
+#endif
+} eSmeCommandType;
+
+
+typedef enum eSmeState
+{
+    SME_STATE_STOP,
+    SME_STATE_START,
+    SME_STATE_READY,
+} eSmeState;
+
+
+#define SME_IS_START(pMac)  (SME_STATE_STOP != (pMac)->sme.state)
+#define SME_IS_READY(pMac)  (SME_STATE_READY == (pMac)->sme.state)
+
+
+typedef struct tagSmeStruct
+{
+    eSmeState state;
+    vos_lock_t lkSmeGlobalLock;
+    tANI_U32 totalSmeCmd;
+    void *pSmeCmdBufAddr;
+    tDblLinkList smeCmdActiveList;
+    tDblLinkList smeCmdPendingList;
+    tDblLinkList smeCmdFreeList;   //preallocated roam cmd list
+    void (*pTxPerHitCallback) (void *pCallbackContext); /* callback for Tx PER hit to HDD */ 
+    void *pTxPerHitCbContext;
+} tSmeStruct, *tpSmeStruct;
+
+
+#endif //#if !defined( __SMEINTERNAL_H )
diff --git a/CORE/SME/inc/smeQosInternal.h b/CORE/SME/inc/smeQosInternal.h
new file mode 100644
index 0000000..f318af1
--- /dev/null
+++ b/CORE/SME/inc/smeQosInternal.h
@@ -0,0 +1,249 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+
+#if !defined( __SMEQOSINTERNAL_H )
+#define __SMEQOSINTERNAL_H
+
+
+/**=========================================================================
+  
+  \file  smeQosInternal.h
+  
+  \brief prototype for SME QoS APIs
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+
+/* $Header$ */
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#include "vos_lock.h"
+#include "vos_trace.h"
+#include "vos_memory.h"
+#include "vos_types.h"
+#include "aniGlobal.h"
+#include "sirApi.h"
+#include "sme_QosApi.h"
+#include "smeInternal.h"
+
+/*-------------------------------------------------------------------------- 
+  Type declarations
+  ------------------------------------------------------------------------*/
+#define SME_QOS_AP_SUPPORTS_APSD         0x80
+
+/*---------------------------------------------------------------------------
+   Enumeration of the various EDCA Access Categories:
+   Based on AC to ACI mapping in 802.11e spec (identical to WMM)
+---------------------------------------------------------------------------*/
+typedef enum
+{
+   SME_QOS_EDCA_AC_BE = 0,  /* Best effort access category             */
+   SME_QOS_EDCA_AC_BK = 1,  /* Background access category              */
+   SME_QOS_EDCA_AC_VI = 2,  /* Video access category                   */
+   SME_QOS_EDCA_AC_VO = 3,  /* Voice access category                   */
+  
+   SME_QOS_EDCA_AC_MAX
+} sme_QosEdcaAcType;
+
+
+/*---------------------------------------------------------------------------
+   Enumeration of the various CSR event indication types that would be reported 
+   by CSR
+---------------------------------------------------------------------------*/
+typedef enum
+{
+   SME_QOS_CSR_JOIN_REQ = 0,
+   SME_QOS_CSR_ASSOC_COMPLETE,
+   SME_QOS_CSR_REASSOC_REQ,
+   SME_QOS_CSR_REASSOC_COMPLETE,
+   SME_QOS_CSR_REASSOC_FAILURE,
+   SME_QOS_CSR_DISCONNECT_REQ,
+   SME_QOS_CSR_DISCONNECT_IND,
+   SME_QOS_CSR_HANDOFF_ASSOC_REQ,
+   SME_QOS_CSR_HANDOFF_COMPLETE,
+   SME_QOS_CSR_HANDOFF_FAILURE,
+#ifdef WLAN_FEATURE_VOWIFI_11R
+   SME_QOS_CSR_PREAUTH_SUCCESS_IND,
+   SME_QOS_CSR_SET_KEY_SUCCESS_IND,
+#endif
+}sme_QosCsrEventIndType;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+typedef enum
+{
+   SME_QOS_DIAG_ADDTS_REQ = 0,
+   SME_QOS_DIAG_ADDTS_RSP,
+   SME_QOS_DIAG_DELTS
+
+}sme_QosDiagQosEventSubtype;
+
+typedef enum
+{
+   SME_QOS_DIAG_ADDTS_ADMISSION_ACCEPTED = 0,
+   SME_QOS_DIAG_ADDTS_INVALID_PARAMS,
+   SME_QOS_DIAG_ADDTS_RESERVED,
+   SME_QOS_DIAG_ADDTS_REFUSED,
+   SME_QOS_DIAG_USER_REQUESTED,
+   SME_QOS_DIAG_DELTS_IND_FROM_AP,
+
+}sme_QosDiagQosEventReasonCode;
+
+#endif //FEATURE_WLAN_DIAG_SUPPORT
+/*---------------------------------------------------------------------------
+    The association information structure to be passed by CSR after assoc or 
+    reassoc is done
+---------------------------------------------------------------------------*/
+typedef struct
+{ 
+   tSirBssDescription            *pBssDesc;
+   tCsrRoamProfile               *pProfile;
+} sme_QosAssocInfo;
+
+/*-------------------------------------------------------------------------- 
+                         External APIs for CSR - Internal to SME
+  ------------------------------------------------------------------------*/
+
+/* --------------------------------------------------------------------------
+    \brief sme_QosOpen() - This function must be called before any API call to 
+    SME QoS module.
+
+    \param pMac - Pointer to the global MAC parameter structure.
+    
+    \return eHalStatus     
+----------------------------------------------------------------------------*/
+eHalStatus sme_QosOpen(tpAniSirGlobal pMac);
+
+/* --------------------------------------------------------------------------
+    \brief sme_QosClose() - To close down SME QoS module. There should not be 
+    any API call into this module after calling this function until another
+    call of sme_QosOpen.
+
+    \param pMac - Pointer to the global MAC parameter structure.
+    
+    \return eHalStatus     
+----------------------------------------------------------------------------*/
+eHalStatus sme_QosClose(tpAniSirGlobal pMac);
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosSetParams() - This function is used by HDD to provide the 
+   default TSPEC params to SME.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info per AC as defined above, provided by HDD
+  
+  \return eHAL_STATUS_SUCCESS - Setparam is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosSetParams(tpAniSirGlobal pMac, sme_QosWmmTspecInfo * pQoSInfo);
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosMsgProcessor() - sme_ProcessMsg() calls this function for the 
+  messages that are handled by SME QoS module.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param msg_type - the type of msg passed by PE as defined in wniApi.h
+  \param pMsgBuf - a pointer to a buffer that maps to various structures base 
+                   on the message type.
+                   The beginning of the buffer can always map to tSirSmeRsp.
+  
+  \return eHalStatus.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosMsgProcessor( tpAniSirGlobal pMac,  v_U16_t msg_type, 
+                                void *pMsgBuf);
+
+/*-------------------------------------------------------------------------- 
+                         Internal APIs for CSR
+  ------------------------------------------------------------------------*/
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosValidateParams() - The SME QoS API exposed to CSR to validate AP 
+  capabilities regarding QoS support & any other QoS parameter validation.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pBssDesc - Pointer to the BSS Descriptor information passed down by 
+                    CSR to PE while issuing the Join request
+  
+  \return eHAL_STATUS_SUCCESS - Validation is successful
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosValidateParams(tpAniSirGlobal pMac, 
+                                 tSirBssDescription *pBssDesc);
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosCsrEventInd() - The QoS sub-module in SME expects notifications 
+  from CSR when certain events occur as mentioned in sme_QosCsrEventIndType.
+
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param ind - The event occurred of type sme_QosCsrEventIndType.
+  \param pEvent_info - Information related to the event
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosCsrEventInd(tpAniSirGlobal pMac,
+                              v_U8_t sessionId,
+                              sme_QosCsrEventIndType ind, 
+                              void *pEvent_info);
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosGetACMMask() - The QoS sub-module API to find out on which ACs
+  AP mandates Admission Control (ACM = 1)
+
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pSirBssDesc - The event occurred of type sme_QosCsrEventIndType.
+  \param pIes - the parsed IE for pSirBssDesc. This can be NULL.
+
+  
+  \return a bit mask indicating for which ACs AP has ACM set to 1
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+v_U8_t sme_QosGetACMMask(tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes);
+
+/*
+  sme_QosTriggerUapsdChange
+        It trigger a change on UAPSD (either disable/enable UAPSD) on current QoS flows
+*/
+sme_QosStatusType sme_QosTriggerUapsdChange( tpAniSirGlobal pMac );
+
+#ifdef FEATURE_WLAN_CCX
+v_U8_t sme_QosCCxRetrieveTspecInfo(tpAniSirGlobal pMac, v_U8_t sessionId, tTspecInfo *pTspecInfo);
+
+#endif
+
+#endif //#if !defined( __SMEQOSINTERNAL_H )
diff --git a/CORE/SME/inc/smeRrmInternal.h b/CORE/SME/inc/smeRrmInternal.h
new file mode 100644
index 0000000..072a5e0
--- /dev/null
+++ b/CORE/SME/inc/smeRrmInternal.h
@@ -0,0 +1,109 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/*
+ * */
+#if !defined( __SMERRMINTERNAL_H )
+#define __SMERRMINTERNAL_H
+
+
+/**=========================================================================
+  
+  \file  smeRrmInternal.h
+  
+  \brief prototype for SME RRM APIs
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+
+/* $Header$ */
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#include "vos_lock.h"
+#include "vos_trace.h"
+#include "vos_memory.h"
+#include "vos_types.h"
+#include "palTimer.h"
+#include "rrmGlobal.h"
+
+/*-------------------------------------------------------------------------- 
+  Type declarations
+  ------------------------------------------------------------------------*/
+typedef struct sRrmConfigParam
+{
+   tANI_U8 rrmEnabled;
+   tANI_U8 maxRandnInterval;
+}tRrmConfigParam, *tpRrmConfigParam;
+
+typedef struct sRrmNeighborReportDesc
+{
+   tListElem    List;
+   tSirNeighborBssDescription   *pNeighborBssDescription;
+   tANI_U32                     roamScore;
+} tRrmNeighborReportDesc, *tpRrmNeighborReportDesc;
+
+
+typedef void (*NeighborReportRspCallback) (void *context, VOS_STATUS vosStatus);
+
+typedef struct sRrmNeighborRspCallbackInfo
+{
+    tANI_U32                  timeout;  //in ms.. min value is 10 (10ms)
+    NeighborReportRspCallback neighborRspCallback;
+    void                      *neighborRspCallbackContext;
+} tRrmNeighborRspCallbackInfo, *tpRrmNeighborRspCallbackInfo;
+
+typedef struct sRrmNeighborRequestControlInfo
+{
+    tANI_BOOLEAN    isNeighborRspPending;   //To check whether a neighbor req is already sent and response pending
+    vos_timer_t     neighborRspWaitTimer;
+    tRrmNeighborRspCallbackInfo neighborRspCallbackInfo;
+} tRrmNeighborRequestControlInfo, *tpRrmNeighborRequestControlInfo;
+
+typedef struct sRrmSMEContext
+{
+   tANI_U16 token;
+   tCsrBssid sessionBssId;
+   tANI_U8 regClass;
+   tCsrChannelInfo channelList; //list of all channels to be measured.
+   tANI_U8 currentIndex;
+   tAniSSID ssId;  //SSID used in the measuring beacon report.
+   tSirMacAddr bssId; //bssid used for beacon report measurement.
+   tANI_U16 randnIntvl; //Randomization interval to be used in subsequent measurements.
+   tANI_U16 duration;
+   tANI_U16 measMode;
+   tRrmConfigParam rrmConfig;
+   vos_timer_t IterMeasTimer;
+   tDblLinkList neighborReportCache;
+   tRrmNeighborRequestControlInfo neighborReqControlInfo;
+}tRrmSMEContext, *tpRrmSMEContext; 
+
+typedef struct sRrmNeighborReq
+{
+   tANI_U8 no_ssid;
+   tSirMacSSid ssid;
+}tRrmNeighborReq, *tpRrmNeighborReq;
+
+#endif //#if !defined( __SMERRMINTERNAL_H )
diff --git a/CORE/SME/inc/sme_Api.h b/CORE/SME/inc/sme_Api.h
new file mode 100644
index 0000000..c14d3f9
--- /dev/null
+++ b/CORE/SME/inc/sme_Api.h
@@ -0,0 +1,2089 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+#if !defined( __SME_API_H )
+#define __SME_API_H
+
+
+/**=========================================================================
+  
+  \file  smeApi.h
+  
+  \brief prototype for SME APIs
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+
+/* $Header$ */
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#include "ccmApi.h"
+#include "csrApi.h"
+#include "pmcApi.h"
+#include "vos_mq.h"
+#include "vos_lock.h"
+#include "halTypes.h"
+#include "sirApi.h"
+#include "btcApi.h"
+#include "vos_nvitem.h"
+#include "p2p_Api.h"
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halFw.h"
+#endif
+
+
+#if defined WLAN_FEATURE_VOWIFI
+#include "smeRrmInternal.h"
+#endif
+
+/*-------------------------------------------------------------------------- 
+  Preprocessor definitions and constants
+  ------------------------------------------------------------------------*/
+
+#define SME_SUMMARY_STATS         1
+#define SME_GLOBAL_CLASSA_STATS   2
+#define SME_GLOBAL_CLASSB_STATS   4
+#define SME_GLOBAL_CLASSC_STATS   8
+#define SME_GLOBAL_CLASSD_STATS  16
+#define SME_PER_STA_STATS        32
+
+#define SME_INVALID_COUNTRY_CODE "XX"
+
+/*-------------------------------------------------------------------------- 
+  Type declarations
+  ------------------------------------------------------------------------*/
+typedef struct _smeConfigParams
+{
+   tCsrConfigParam  csrConfig;
+#if defined WLAN_FEATURE_VOWIFI
+   tRrmConfigParam  rrmConfig;
+#endif
+#if defined FEATURE_WLAN_CCX
+    tANI_U8   isCcxIniFeatureEnabled;
+#endif
+#if defined WLAN_FEATURE_P2P_INTERNAL
+   tP2PConfigParam  p2pConfig;
+#endif
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+    tANI_U8   isFastTransitionEnabled;
+#endif
+} tSmeConfigParams, *tpSmeConfigParams;
+
+
+/*------------------------------------------------------------------------- 
+  Function declarations and documenation
+  ------------------------------------------------------------------------*/
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_Open() - Initialze all SME modules and put them at idle state
+  
+  The function initializes each module inside SME, PMC, CCM, CSR, etc. . Upon 
+  successfully return, all modules are at idle state ready to start.
+
+  smeOpen must be called before any other SME APIs can be involved. 
+  smeOpen must be called after macOpen.
+  
+  \param hHal - The handle returned by macOpen.
+  
+  \return eHAL_STATUS_SUCCESS - SME is successfully initialized.
+  
+          Other status means SME is failed to be initialized     
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_Open(tHalHandle hHal);
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_Close() - Release all SME modules and their resources.
+  
+  The function release each module in SME, PMC, CCM, CSR, etc. . Upon 
+  return, all modules are at closed state.
+
+  No SME APIs can be involved after sme_Close except sme_Open. 
+  sme_Close must be called before macClose.
+  
+  \param hHal - The handle returned by macOpen.
+  
+  \return eHAL_STATUS_SUCCESS - SME is successfully close.
+  
+          Other status means SME is failed to be closed but caller still cannot
+          call any other SME functions except smeOpen.
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_Close(tHalHandle hHal);
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_Start() - Put all SME modules at ready state.
+  
+  The function starts each module in SME, PMC, CCM, CSR, etc. . Upon 
+  successfully return, all modules are ready to run.
+
+  \param hHal - The handle returned by macOpen.
+  
+  \return eHAL_STATUS_SUCCESS - SME is ready.
+  
+          Other status means SME is failed to start.     
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_Start(tHalHandle hHal);
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_Stop() - Stop all SME modules and put them at idle state
+  
+  The function stops each module in SME, PMC, CCM, CSR, etc. . Upon 
+  return, all modules are at idle state ready to start.
+
+  
+  \param hHal - The handle returned by macOpen.
+
+  \param pmcFlag - The flag tells SME if we want to stop PMC or not
+  
+  \return eHAL_STATUS_SUCCESS - SME is stopped.
+  
+          Other status means SME is failed to stop but caller should still consider 
+          SME is stopped.
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_Stop(tHalHandle hHal, tANI_BOOLEAN pmcFlag);
+
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_OpenSession() - Open a session for scan/roam operation. 
+  
+  This is a synchronous API.
+
+  
+  \param hHal - The handle returned by macOpen.
+  \param callback - A pointer to the function caller specifies for roam/connect status indication
+  \param pContext - The context passed with callback
+  \param pSelfMacAddr - Caller allocated memory filled with self MAC address (6 bytes)
+  \param pbSessionId - pointer to a caller allocated buffer for returned session ID
+  
+  \return eHAL_STATUS_SUCCESS - session is opened. sessionId returned.
+  
+          Other status means SME is failed to open the session.  
+          eHAL_STATUS_RESOURCES - no more session available.
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_OpenSession(tHalHandle hHal, csrRoamCompleteCallback callback, void *pContext, 
+                           tANI_U8 *pSelfMacAddr, tANI_U8 *pbSessionId);
+
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_CloseSession() - Open a session for scan/roam operation. 
+  
+  This is a synchronous API.
+
+  
+  \param hHal - The handle returned by macOpen.
+
+  \param sessionId - A previous opened session's ID.
+  
+  \return eHAL_STATUS_SUCCESS - session is closed. 
+  
+          Other status means SME is failed to open the session.  
+          eHAL_STATUS_INVALID_PARAMETER - session is not opened. 
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_CloseSession(tHalHandle hHal, tANI_U8 sessionId,
+                         csrRoamSessionCloseCallback callback, void *pContext);
+
+
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_UpdateConfig() - Change configurations for all SME moduels
+  
+  The function updates some configuration for modules in SME, CCM, CSR, etc
+  during SMEs close -> open sequence.
+   
+  Modules inside SME apply the new configuration at the next transaction.
+
+  
+  \param hHal - The handle returned by macOpen.
+  \Param pSmeConfigParams - a pointer to a caller allocated object of 
+  typedef struct _smeConfigParams.
+  
+  \return eHAL_STATUS_SUCCESS - SME update the config parameters successfully.
+  
+          Other status means SME is failed to update the config parameters.
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_UpdateConfig(tHalHandle hHal, tpSmeConfigParams pSmeConfigParams);
+
+#ifdef FEATURE_WLAN_SCAN_PNO
+/*--------------------------------------------------------------------------
+
+  \brief sme_UpdateChannelConfig() - Update channel configuration in RIVA.
+ 
+  It is used at driver start up to inform RIVA of the default channel 
+  configuration. 
+
+  This is a synchronuous call
+
+  \param hHal - The handle returned by macOpen.
+  
+  \return eHAL_STATUS_SUCCESS - SME update the channel config successfully.
+
+          Other status means SME is failed to update the channel config.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_UpdateChannelConfig(tHalHandle hHal);
+
+#endif // FEATURE_WLAN_SCAN_PNLO
+#ifdef WLAN_SOFTAP_FEATURE
+/*--------------------------------------------------------------------------
+  
+  \brief sme_set11dinfo() - Set the 11d information about valid channels
+   and there power using information from nvRAM 
+   This function is called only for AP.
+
+  This is a synchronuous call
+
+  \param hHal - The handle returned by macOpen.
+  \Param pSmeConfigParams - a pointer to a caller allocated object of
+  typedef struct _smeConfigParams.
+
+  \return eHAL_STATUS_SUCCESS - SME update the config parameters successfully.
+
+          Other status means SME is failed to update the config parameters.
+  \sa
+--------------------------------------------------------------------------*/
+
+eHalStatus sme_set11dinfo(tHalHandle hHal,  tpSmeConfigParams pSmeConfigParams);
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_getSoftApDomain() - Get the current regulatory domain of softAp.
+
+  This is a synchronuous call
+
+  \param hHal - The handle returned by HostapdAdapter.
+  \Param v_REGDOMAIN_t - The current Regulatory Domain requested for SoftAp.
+
+  \return eHAL_STATUS_SUCCESS - SME successfully completed the request.
+
+          Other status means, failed to get the current regulatory domain.
+  \sa
+--------------------------------------------------------------------------*/
+
+eHalStatus sme_getSoftApDomain(tHalHandle hHal,  v_REGDOMAIN_t *domainIdSoftAp);
+
+eHalStatus sme_setRegInfo(tHalHandle hHal,  tANI_U8 *apCntryCode);
+
+#endif
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ChangeConfigParams
+    \brief The SME API exposed for HDD to provide config params to SME during 
+    SMEs stop -> start sequence. 
+    
+    If HDD changed the domain that will cause a reset. This function will 
+    provide the new set of 11d information for the new domain. Currrently this
+    API provides info regarding 11d only at reset but we can extend this for
+    other params (PMC, QoS) which needs to be initialized again at reset.
+
+    This is a synchronuous call
+    
+    \param hHal - The handle returned by macOpen.
+
+    \Param
+    pUpdateConfigParam - a pointer to a structure (tCsrUpdateConfigParam) that 
+                currently provides 11d related information like Country code, 
+                Regulatory domain, valid channel list, Tx power per channel, a 
+                list with active/passive scan allowed per valid channel. 
+
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ChangeConfigParams(tHalHandle hHal, 
+                                 tCsrUpdateConfigParam *pUpdateConfigParam);
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_HDDReadyInd() - SME sends eWNI_SME_SYS_READY_IND to PE to inform that the NIC
+  is ready tio run.
+  
+  The function is called by HDD at the end of initialization stage so PE/HAL can enable the NIC 
+  to running state. 
+  
+  
+  \param hHal - The handle returned by macOpen.
+  
+  \return eHAL_STATUS_SUCCESS - eWNI_SME_SYS_READY_IND is sent to PE successfully.
+  
+          Other status means SME failed to send the message to PE.
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_HDDReadyInd(tHalHandle hHal);
+
+
+/*--------------------------------------------------------------------------
+  
+  \brief sme_ProcessMsg() - The main message processor for SME.
+  
+  The function is called by a message dispatcher when to process a message 
+  targeted for SME. 
+  
+  
+  \param hHal - The handle returned by macOpen.
+  \param pMsg - A pointer to a caller allocated object of tSirMsgQ.
+  
+  \return eHAL_STATUS_SUCCESS - SME successfully process the message.
+  
+          Other status means SME failed to process the message.
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_ProcessMsg(tHalHandle hHal, vos_msg_t* pMsg);
+
+v_VOID_t sme_FreeMsg( tHalHandle hHal, vos_msg_t* pMsg );
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanRequest
+    \brief a wrapper function to Request a 11d or full scan from CSR.
+    \param pScanRequestID - pointer to an object to get back the request ID
+    \param callback - a callback function that scan calls upon finish, will not 
+                      be called if csrScanRequest returns error
+    \param pContext - a pointer passed in for the callback
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanRequest(tHalHandle hHal, tANI_U8 sessionId, tCsrScanRequest *, 
+                           tANI_U32 *pScanRequestID, 
+                           csrScanCompleteCallback callback, void *pContext);
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanSetBGScanparams
+    \brief a wrapper function to request CSR to set BG scan params in PE
+    \param pScanReq - BG scan request structure
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanSetBGScanparams(tHalHandle hHal, tANI_U8 sessionId, tCsrBGScanRequest *pScanReq);
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanGetResult
+    \brief a wrapper function to request scan results from CSR.
+    \param pFilter - If pFilter is NULL, all cached results are returned
+    \param phResult - an object for the result.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanGetResult(tHalHandle hHal, tANI_U8 sessionId, tCsrScanResultFilter *pFilter, 
+                            tScanResultHandle *phResult);
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanFlushResult
+    \brief a wrapper function to request CSR to clear scan results.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanFlushResult(tHalHandle hHal, tANI_U8 sessionId);
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanResultGetFirst
+    \brief a wrapper function to request CSR to returns the first element of 
+           scan result.
+    \param hScanResult - returned from csrScanGetResult
+    \return tCsrScanResultInfo * - NULL if no result     
+  ---------------------------------------------------------------------------*/
+tCsrScanResultInfo *sme_ScanResultGetFirst(tHalHandle, 
+                                          tScanResultHandle hScanResult);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanResultGetNext
+    \brief a wrapper function to request CSR to returns the next element of 
+           scan result. It can be called without calling csrScanResultGetFirst 
+           first
+    \param hScanResult - returned from csrScanGetResult
+    \return Null if no result or reach the end     
+  ---------------------------------------------------------------------------*/
+tCsrScanResultInfo *sme_ScanResultGetNext(tHalHandle, 
+                                          tScanResultHandle hScanResult);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanResultPurge
+    \brief a wrapper function to request CSR to remove all items(tCsrScanResult) 
+           in the list and free memory for each item
+    \param hScanResult - returned from csrScanGetResult. hScanResult is 
+                         considered gone by 
+    calling this function and even before this function reutrns.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanResultPurge(tHalHandle hHal, tScanResultHandle hScanResult);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanGetPMKIDCandidateList
+    \brief a wrapper function to return the PMKID candidate list
+    \param pPmkidList - caller allocated buffer point to an array of 
+                        tPmkidCandidateInfo
+    \param pNumItems - pointer to a variable that has the number of 
+                       tPmkidCandidateInfo allocated when retruning, this is 
+                       either the number needed or number of items put into 
+                       pPmkidList
+    \return eHalStatus - when fail, it usually means the buffer allocated is not 
+                         big enough and pNumItems
+    has the number of tPmkidCandidateInfo.
+    \Note: pNumItems is a number of tPmkidCandidateInfo, 
+           not sizeof(tPmkidCandidateInfo) * something
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanGetPMKIDCandidateList(tHalHandle hHal, tANI_U8 sessionId,
+                                        tPmkidCandidateInfo *pPmkidList, 
+                                        tANI_U32 *pNumItems );
+
+
+/*----------------------------------------------------------------------------
+  \fn sme_RoamRegisterLinkQualityIndCallback
+
+  \brief
+  a wrapper function to allow HDD to register a callback handler with CSR for 
+  link quality indications. 
+
+  Only one callback may be registered at any time.
+  In order to deregister the callback, a NULL cback may be provided.
+
+  Registration happens in the task context of the caller.
+
+  \param callback - Call back being registered
+  \param pContext - user data
+  
+  DEPENDENCIES: After CSR open
+
+  \return eHalStatus  
+-----------------------------------------------------------------------------*/
+eHalStatus sme_RoamRegisterLinkQualityIndCallback(tHalHandle hHal, tANI_U8 sessionId,
+                                                  csrRoamLinkQualityIndCallback   callback,  
+                                                  void                           *pContext);
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamConnect
+    \brief a wrapper function to request CSR to inititiate an association
+    \param sessionId - the sessionId returned by sme_OpenSession.
+    \param pProfile - can be NULL to join to any open ones
+    \param pRoamId - to get back the request ID
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamConnect(tHalHandle hHal, tANI_U8 sessionId, tCsrRoamProfile *pProfile, 
+                           tANI_U32 *pRoamId);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamReassoc
+    \brief a wrapper function to request CSR to inititiate a re-association
+    \param pProfile - can be NULL to join the currently connected AP. In that 
+    case modProfileFields should carry the modified field(s) which could trigger
+    reassoc  
+    \param modProfileFields - fields which are part of tCsrRoamConnectedProfile 
+    that might need modification dynamically once STA is up & running and this 
+    could trigger a reassoc
+    \param pRoamId - to get back the request ID
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamReassoc(tHalHandle hHal, tANI_U8 sessionId, tCsrRoamProfile *pProfile,
+                          tCsrRoamModifyProfileFields modProfileFields,
+                          tANI_U32 *pRoamId);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamConnectToLastProfile
+    \brief a wrapper function to request CSR to disconnect and reconnect with 
+           the same profile
+    \return eHalStatus. It returns fail if currently connected     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamConnectToLastProfile(tHalHandle hHal, tANI_U8 sessionId);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamDisconnect
+    \brief a wrapper function to request CSR to disconnect from a network
+    \param reason -- To indicate the reason for disconnecting. Currently, only 
+                     eCSR_DISCONNECT_REASON_MIC_ERROR is meanful.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamDisconnect(tHalHandle hHal, tANI_U8 sessionId, eCsrRoamDisconnectReason reason);
+
+#ifdef WLAN_SOFTAP_FEATURE
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamStopBss
+    \brief a wrapper function to request CSR to stop bss
+    \param sessionId    - sessionId of SoftAP
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamStopBss(tHalHandle hHal, tANI_U8 sessionId);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetAssociatedStas
+    \brief To probe the list of associated stations from various modules of CORE stack.
+    \This is an asynchronous API.
+    \param sessionId    - sessionId of SoftAP
+    \param modId        - Module from whom list of associtated stations is to be probed.
+                          If an invalid module is passed then by default VOS_MODULE_ID_PE will be probed
+    \param pUsrContext  - Opaque HDD context
+    \param pfnSapEventCallback  - Sap event callback in HDD
+    \param pAssocBuf    - Caller allocated memory to be filled with associatd stations info
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetAssociatedStas(tHalHandle hHal, tANI_U8 sessionId,
+                                        VOS_MODULE_ID modId, void *pUsrContext,
+                                        void *pfnSapEventCallback, tANI_U8 *pAssocStasBuf);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamDisconnectSta
+    \brief To disassociate a station. This is an asynchronous API.
+    \param pPeerMacAddr - Caller allocated memory filled with peer MAC address (6 bytes)
+    \return eHalStatus  SUCCESS  Roam callback will be called to indicate actual results
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamDisconnectSta(tHalHandle hHal, tANI_U8 sessionId, tANI_U8 *pPeerMacAddr);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamDeauthSta
+    \brief To disassociate a station. This is an asynchronous API.
+    \param hHal - Global structure
+    \param sessionId - sessionId of SoftAP
+    \param pPeerMacAddr - Caller allocated memory filled with peer MAC address (6 bytes)
+    \return eHalStatus  SUCCESS  Roam callback will be called to indicate actual results    
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamDeauthSta(tHalHandle hHal, tANI_U8 sessionId,
+                                tANI_U8 *pPeerMacAddr);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamTKIPCounterMeasures
+    \brief To start or stop TKIP counter measures. This is an asynchronous API.
+    \param sessionId - sessionId of SoftAP
+    \param bEnable - Flag to start/stop TKIP countermeasures
+    \return eHalStatus  SUCCESS  Roam callback will be called to indicate actual results    
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamTKIPCounterMeasures(tHalHandle hHal, tANI_U8 sessionId, tANI_BOOLEAN bEnable);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetWpsSessionOverlap
+    \brief To get the WPS PBC session overlap information.
+    \This is an asynchronous API.
+    \param sessionId    - sessionId of SoftAP
+    \param pUsrContext  - Opaque HDD context
+    \param pfnSapEventCallback  - Sap event callback in HDD
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetWpsSessionOverlap(tHalHandle hHal, tANI_U8 sessionId,
+                                        void *pUsrContext, void *pfnSapEventCallback,
+                                        v_MACADDR_t pRemoveMac);
+#endif
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetConnectState
+    \brief a wrapper function to request CSR to return the current connect state 
+           of Roaming
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetConnectState(tHalHandle hHal, tANI_U8 sessionId, eCsrConnectState *pState);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetConnectProfile
+    \brief a wrapper function to request CSR to return the current connect 
+           profile. Caller must call csrRoamFreeConnectProfile after it is done 
+           and before reuse for another csrRoamGetConnectProfile call.
+    \param pProfile - pointer to a caller allocated structure 
+                      tCsrRoamConnectedProfile
+    \return eHalStatus. Failure if not connected     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetConnectProfile(tHalHandle hHal, tANI_U8 sessionId,
+                                     tCsrRoamConnectedProfile *pProfile);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamFreeConnectProfile
+    \brief a wrapper function to request CSR to free and reinitialize the 
+           profile returned previously by csrRoamGetConnectProfile.
+    \param pProfile - pointer to a caller allocated structure 
+                      tCsrRoamConnectedProfile
+    \return eHalStatus.      
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamFreeConnectProfile(tHalHandle hHal, 
+                                      tCsrRoamConnectedProfile *pProfile);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamSetPMKIDCache
+    \brief a wrapper function to request CSR to return the PMKID candidate list
+    \param pPMKIDCache - caller allocated buffer point to an array of 
+                         tPmkidCacheInfo
+    \param numItems - a variable that has the number of tPmkidCacheInfo 
+                      allocated when retruning, this is either the number needed 
+                      or number of items put into pPMKIDCache
+    \return eHalStatus - when fail, it usually means the buffer allocated is not 
+                         big enough and pNumItems has the number of 
+                         tPmkidCacheInfo.
+    \Note: pNumItems is a number of tPmkidCacheInfo, 
+           not sizeof(tPmkidCacheInfo) * something
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamSetPMKIDCache( tHalHandle hHal, tANI_U8 sessionId, tPmkidCacheInfo *pPMKIDCache, 
+                                  tANI_U32 numItems );
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetSecurityReqIE
+    \brief a wrapper function to request CSR to return the WPA or RSN or WAPI IE CSR
+           passes to PE to JOIN request or START_BSS request
+    This is a synchronuous call.
+    \param sessionId - returned by sme_OpenSession.
+    \param pLen - caller allocated memory that has the length of pBuf as input. 
+                  Upon returned, *pLen has the needed or IE length in pBuf.
+    \param pBuf - Caller allocated memory that contain the IE field, if any, 
+                  upon return
+    \param secType - Specifies whether looking for WPA/WPA2/WAPI IE                  
+    \return eHalStatus - when fail, it usually means the buffer allocated is not 
+                         big enough
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetSecurityReqIE(tHalHandle hHal, tANI_U8 sessionId, tANI_U32 *pLen,
+                                  tANI_U8 *pBuf, eCsrSecurityType secType);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetSecurityRspIE
+    \brief a wrapper function to request CSR to return the WPA or RSN or WAPI IE from 
+           the beacon or probe rsp if connected
+    \param sessionId - returned by sme_OpenSession.
+    \param pLen - caller allocated memory that has the length of pBuf as input. 
+                  Upon returned, *pLen has the needed or IE length in pBuf.
+    \param pBuf - Caller allocated memory that contain the IE field, if any, 
+                  upon return
+    \param secType - Specifies whether looking for WPA/WPA2/WAPI IE                                       
+    \return eHalStatus - when fail, it usually means the buffer allocated is not 
+                         big enough
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetSecurityRspIE(tHalHandle hHal, tANI_U8 sessionId, tANI_U32 *pLen,
+                                  tANI_U8 *pBuf, eCsrSecurityType secType);
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetNumPMKIDCache
+    \brief a wrapper function to request CSR to return number of PMKID cache 
+           entries
+    \return tANI_U32 - the number of PMKID cache entries
+  ---------------------------------------------------------------------------*/
+tANI_U32 sme_RoamGetNumPMKIDCache(tHalHandle hHal, tANI_U8 sessionId);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetPMKIDCache
+    \brief a wrapper function to request CSR to return PMKID cache from CSR
+    \param pNum - caller allocated memory that has the space of the number of 
+                  pBuf tPmkidCacheInfo as input. Upon returned, *pNum has the 
+                  needed or actually number in tPmkidCacheInfo.
+    \param pPmkidCache - Caller allocated memory that contains PMKID cache, if 
+                         any, upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not 
+                         big enough
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetPMKIDCache(tHalHandle hHal, tANI_U8 sessionId, tANI_U32 *pNum, 
+                                 tPmkidCacheInfo *pPmkidCache);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetConfigParam
+    \brief a wrapper function that HDD calls to get the global settings 
+           currently maintained by CSR. 
+    \param pParam - caller allocated memory
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetConfigParam(tHalHandle hHal, tSmeConfigParams *pParam);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetStatistics
+    \brief a wrapper function that client calls to register a callback to get 
+    different PHY level statistics from CSR. 
+    
+    \param requesterId - different client requesting for statistics, HDD, UMA/GAN etc
+    \param statsMask - The different category/categories of stats requester is looking for
+    The order in which you set the bits in the statsMask for requesting 
+    different type of stats is:
+
+      eCsrSummaryStats = bit 0
+      eCsrGlobalClassAStats = bit 1
+      eCsrGlobalClassBStats = bit 2
+      eCsrGlobalClassCStats = bit 3
+      eCsrGlobalClassDStats = bit 4
+      eCsrPerStaStats = bit 5
+
+    \param callback - SME sends back the requested stats using the callback
+    \param periodicity - If requester needs periodic update, 0 means it's an one 
+                         time request
+    \param cache - If requester is happy with cached stats
+    \param staId - The station ID for which the stats is requested for
+    \param pContext - user context to be passed back along with the callback
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetStatistics(tHalHandle hHal, eCsrStatsRequesterType requesterId, 
+                             tANI_U32 statsMask, 
+                             tCsrStatsCallback callback, 
+                             tANI_U32 periodicity, tANI_BOOLEAN cache, 
+                             tANI_U8 staId, void *pContext);
+
+eHalStatus sme_GetRssi(tHalHandle hHal, 
+                             tCsrRssiCallback callback, 
+                             tANI_U8 staId, tCsrBssid bssId, void *pContext, void* pVosContext);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_CfgSetInt
+    \brief a wrapper function that HDD calls to set parameters in CFG. 
+    \param cfgId - Configuration Parameter ID (type) for STA. 
+    \param ccmValue - The information related to Configuration Parameter ID
+                      which needs to be saved in CFG
+    \param callback - To be registered by CSR with CCM. Once the CFG done with 
+                      saving the information in the database, it notifies CCM & 
+                      then the callback will be invoked to notify. 
+    \param toBeSaved - To save the request for future reference
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_CfgSetInt(tHalHandle hHal, tANI_U32 cfgId, tANI_U32 ccmValue, 
+                         tCcmCfgSetCallback callback, eAniBoolean toBeSaved) ;
+
+/* ---------------------------------------------------------------------------
+    \fn sme_CfgSetStr
+    \brief a wrapper function that HDD calls to set parameters in CFG. 
+    \param cfgId - Configuration Parameter ID (type) for STA. 
+    \param pStr - Pointer to the byte array which carries the information needs 
+                  to be saved in CFG
+    \param length - Length of the data to be saved                  
+    \param callback - To be registered by CSR with CCM. Once the CFG done with 
+                      saving the information in the database, it notifies CCM & 
+                      then the callback will be invoked to notify. 
+    \param toBeSaved - To save the request for future reference
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_CfgSetStr(tHalHandle hHal, tANI_U32 cfgId, tANI_U8 *pStr, 
+                         tANI_U32 length, tCcmCfgSetCallback callback, 
+                         eAniBoolean toBeSaved) ;
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetModifyProfileFields
+    \brief HDD or SME - QOS calls this function to get the current values of 
+    connected profile fields, changing which can cause reassoc.
+    This function must be called after CFG is downloaded and STA is in connected
+    state. Also, make sure to call this function to get the current profile
+    fields before calling the reassoc. So that pModifyProfileFields will have
+    all the latest values plus the one(s) has been updated as part of reassoc
+    request.
+    \param pModifyProfileFields - pointer to the connected profile fields 
+    changing which can cause reassoc
+
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetModifyProfileFields(tHalHandle hHal, tANI_U8 sessionId, 
+                                     tCsrRoamModifyProfileFields * pModifyProfileFields);
+
+
+/*--------------------------------------------------------------------------
+    \fn sme_SetConfigPowerSave
+    \brief  Wrapper fn to change power save configuration in SME (PMC) module.
+            For BMPS related configuration, this function also updates the CFG
+            and sends a message to FW to pick up the new values. Note: Calling
+            this function only updates the configuration and does not enable 
+            the specified power save mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  psMode - Power Saving mode being modified
+    \param  pConfigParams - a pointer to a caller allocated object of type
+            tPmcSmpsConfigParams or tPmcBmpsConfigParams or tPmcImpsConfigParams 
+    \return eHalStatus   
+  --------------------------------------------------------------------------*/
+eHalStatus sme_SetConfigPowerSave(tHalHandle hHal, tPmcPowerSavingMode psMode,
+                                  void *pConfigParams);
+
+/*--------------------------------------------------------------------------
+    \fn sme_GetConfigPowerSave
+    \brief  Wrapper fn to retireve power save configuration in SME (PMC) module
+    \param  hHal - The handle returned by macOpen.
+    \param  psMode - Power Saving mode
+    \param  pConfigParams - a pointer to a caller allocated object of type
+            tPmcSmpsConfigParams or tPmcBmpsConfigParams or tPmcImpsConfigParams 
+    \return eHalStatus   
+  --------------------------------------------------------------------------*/
+eHalStatus sme_GetConfigPowerSave(tHalHandle hHal, tPmcPowerSavingMode psMode,
+                                  void *pConfigParams);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SignalPowerEvent
+    \brief  Signals to PMC that a power event has occurred. Used for putting
+            the chip into deep sleep mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  event - the event that has occurred
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_SignalPowerEvent (
+   tHalHandle hHal,
+   tPmcPowerEvent event);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_EnablePowerSave
+    \brief  Enables one of the power saving modes. This API does not cause a
+            device state change. This is purely a configuration API.
+    \param  hHal - The handle returned by macOpen.
+    \param  psMode - The power saving mode to enable.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_EnablePowerSave (
+   tHalHandle hHal,
+   tPmcPowerSavingMode psMode);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_DisablePowerSave
+    \brief   Disables one of the power saving modes.Disabling does not imply
+             that device will be brought out of the current PS mode. This is 
+             purely a configuration API.
+    \param  hHal - The handle returned by macOpen.
+    \param  psMode - The power saving mode to disable. 
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_DisablePowerSave (
+   tHalHandle hHal,
+   tPmcPowerSavingMode psMode);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_StartAutoBmpsTimer
+    \brief  Starts a timer that periodically polls all the registered
+            module for entry into Bmps mode. This timer is started only if BMPS is
+            enabled and whenever the device is in full power.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_StartAutoBmpsTimer ( tHalHandle hHal);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_StopAutoBmpsTimer
+    \brief  Stops the Auto BMPS Timer that was started using sme_startAutoBmpsTimer
+            Stopping the timer does not cause a device state change. Only the timer
+            is stopped. If "Full Power" is desired, use the sme_RequestFullPower API
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_StopAutoBmpsTimer ( tHalHandle hHal);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_QueryPowerState
+    \brief  Returns the current power state of the device.
+    \param  hHal - The handle returned by macOpen.
+    \param pPowerState - pointer to location to return power state
+    \param pSwWlanSwitchState - ptr to location to return SW WLAN Switch state
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_QueryPowerState (
+   tHalHandle hHal,
+   tPmcPowerState *pPowerState,
+   tPmcSwitchState *pSwWlanSwitchState);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_IsPowerSaveEnabled
+    \brief  Checks if the device is able to enter a particular power save mode
+            This does not imply that the device is in a particular PS mode
+    \param  hHal - The handle returned by macOpen.
+    \param psMode - the power saving mode
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+extern tANI_BOOLEAN sme_IsPowerSaveEnabled(
+   tHalHandle hHal,
+   tPmcPowerSavingMode psMode);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RequestFullPower
+    \brief  Request that the device be brought to full power state.
+            Note 1: If "fullPowerReason" specificied in this API is set to
+            eSME_FULL_PWR_NEEDED_BY_HDD, PMC will clear any "buffered wowl" requests
+            and also clear any "buffered BMPS requests by HDD". Assumption is that since
+            HDD is requesting full power, we need to undo any previous HDD requests for 
+            BMPS (using sme_RequestBmps) or WoWL (using sme_EnterWoWL). If the reason is
+            specified anything other than above, the buffered requests for BMPS and WoWL
+            will not be cleared.
+            Note 2: Requesting full power (no matter what the fullPowerReason is) doesn't
+            disable the "auto bmps timer" (if it is enabled) or clear any "buffered uapsd
+            request".
+            Note 3: When the device finally enters Full Power PMC will start a timer 
+            if any of the following holds true:
+            - Auto BMPS mode is enabled
+            - Uapsd request is pending
+            - HDD's request for BMPS is pending
+            - HDD's request for WoWL is pending
+            On timer expiry PMC will attempt to put the device in BMPS mode if following 
+            (in addition to those listed above) holds true:
+            - Polling of all modules through the Power Save Check routine passes
+            - STA is associated to an access point
+    \param  hHal - The handle returned by macOpen.
+    \param  - callbackRoutine Callback routine invoked in case of success/failure
+    \param  - callbackContext -  Cookie to be passed back during callback
+    \param  - fullPowerReason - Reason why this API is being invoked. SME needs to
+              distinguish between BAP and HDD requests
+    \return eHalStatus - status 
+     eHAL_STATUS_SUCCESS - device brought to full power state
+     eHAL_STATUS_FAILURE - device cannot be brought to full power state
+     eHAL_STATUS_PMC_PENDING - device is being brought to full power state,
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_RequestFullPower (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext,
+   tRequestFullPowerReason fullPowerReason);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RequestBmps
+    \brief  Request that the device be put in BMPS state. Request will be 
+            accepted only if BMPS mode is enabled and power save check routine
+            passes. Only HDD should invoke this API.
+    \param  hHal - The handle returned by macOpen.
+    \param  - callbackRoutine Callback routine invoked in case of success/failure
+    \param  - callbackContext -  Cookie to be passed back during callback
+    \return eHalStatus
+      eHAL_STATUS_SUCCESS - device is in BMPS state
+      eHAL_STATUS_FAILURE - device cannot be brought to BMPS state
+      eHAL_STATUS_PMC_PENDING - device is being brought to BMPS state
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_RequestBmps (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext);
+
+/* ---------------------------------------------------------------------------
+    \fn  sme_SetDHCPTillPowerActiveFlag
+    \brief  Sets/Clears DHCP related flag in PMC to disable/enable auto BMPS 
+            entry by PMC
+    \param  hHal - The handle returned by macOpen.
+  ---------------------------------------------------------------------------*/
+void  sme_SetDHCPTillPowerActiveFlag(tHalHandle hHal, tANI_U8 flag);
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_StartUapsd
+    \brief  Request that the device be put in UAPSD state. If the device is in
+            Full Power it will be put in BMPS mode first and then into UAPSD
+            mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  - callbackRoutine Callback routine invoked in case of success/failure
+    \param  - callbackContext -  Cookie to be passed back during callback
+      eHAL_STATUS_SUCCESS - device is in UAPSD state
+      eHAL_STATUS_FAILURE - device cannot be brought to UAPSD state
+      eHAL_STATUS_PMC_PENDING - device is being brought to UAPSD state
+      eHAL_STATUS_PMC_DISABLED - UAPSD is disabled or BMPS mode is disabled
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_StartUapsd (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_StopUapsd
+    \brief  Request that the device be put out of UAPSD state. Device will be
+            put in in BMPS state after stop UAPSD completes. Buffered requests for
+            UAPSD will be cleared after this.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus  
+      eHAL_STATUS_SUCCESS - device is put out of UAPSD and back in BMPS state
+      eHAL_STATUS_FAILURE - device cannot be brought out of UAPSD state
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_StopUapsd (tHalHandle hHal);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RequestStandby
+    \brief  Request that the device be put in standby. It is HDD's responsibility
+            to bring the chip to full power and do a discconnect before calling
+            this API. Request for standby will be rejected if STA is associated
+            to an AP.
+    \param  hHal - The handle returned by macOpen.
+    \param  - callbackRoutine Callback routine invoked in case of success/failure
+    \param  - callbackContext -  Cookie to be passed back during callback
+    \return eHalStatus  
+      eHAL_STATUS_SUCCESS - device is in Standby mode
+      eHAL_STATUS_FAILURE - device cannot be put in standby mode
+      eHAL_STATUS_PMC_PENDING - device is being put in standby mode
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_RequestStandby (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RegisterPowerSaveCheck
+    \brief  Register a power save check routine that is called whenever
+            the device is about to enter one of the power save modes.
+    \param  hHal - The handle returned by macOpen.
+    \param  checkRoutine -  Power save check routine to be registered
+    \param  callbackContext -  Cookie to be passed back during callback
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully registered
+            eHAL_STATUS_FAILURE - not successfully registered  
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_RegisterPowerSaveCheck (
+   tHalHandle hHal, 
+   tANI_BOOLEAN (*checkRoutine) (void *checkContext), void *checkContext);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_DeregisterPowerSaveCheck
+    \brief  Deregister a power save check routine
+    \param  hHal - The handle returned by macOpen.
+    \param  checkRoutine -  Power save check routine to be deregistered
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully deregistered
+            eHAL_STATUS_FAILURE - not successfully deregistered  
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_DeregisterPowerSaveCheck (
+   tHalHandle hHal, 
+   tANI_BOOLEAN (*checkRoutine) (void *checkContext));
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RegisterDeviceStateUpdateInd
+    \brief  Register a callback routine that is called whenever
+            the device enters a new device state (Full Power, BMPS, UAPSD)
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine -  Callback routine to be registered
+    \param  callbackContext -  Cookie to be passed back during callback
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully registered
+            eHAL_STATUS_FAILURE - not successfully registered  
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_RegisterDeviceStateUpdateInd (
+   tHalHandle hHal, 
+   void (*callbackRoutine) (void *callbackContext, tPmcState pmcState),
+   void *callbackContext);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_DeregisterDeviceStateUpdateInd
+    \brief  Deregister a routine that was registered for device state changes
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine -  Callback routine to be deregistered
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully deregistered
+            eHAL_STATUS_FAILURE - not successfully deregistered  
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_DeregisterDeviceStateUpdateInd (
+   tHalHandle hHal, 
+   void (*callbackRoutine) (void *callbackContext, tPmcState pmcState));
+
+/* ---------------------------------------------------------------------------
+    \fn sme_WowlAddBcastPattern
+    \brief  Add a pattern for Pattern Byte Matching in Wowl mode. Firmware will
+            do a pattern match on these patterns when Wowl is enabled during BMPS
+            mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  pattern -  Pattern to be added
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot add pattern
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_WowlAddBcastPattern (
+   tHalHandle hHal, 
+   tpSirWowlAddBcastPtrn pattern);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_WowlDelBcastPattern
+    \brief  Delete a pattern that was added for Pattern Byte Matching.
+    \param  hHal - The handle returned by macOpen.
+    \param  pattern -  Pattern to be deleted
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot delete pattern
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_WowlDelBcastPattern (
+   tHalHandle hHal, 
+   tpSirWowlDelBcastPtrn pattern);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_EnterWowl
+    \brief  This is the API to request entry into WOWL mode. 
+            WoWLAN works on top of BMPS mode. If the device is not in BMPS mode, 
+            SME will will cache the information that WOWL has been requested and
+            attempt to put the device in BMPS first. On entry into BMPS, SME will
+            enter the WOWL mode.
+            Note 1: After WoWL request is accepted, If module other than HDD requests
+            full power BEFORE WoWL request is completed, PMC will buffer the WoWL request
+            and attempt to put the chip into BMPS+WOWL based on a timer.
+            Note 2: Buffered request for WoWL will be cleared immedisately AFTER "enter Wowl"
+            completes or if HDD requests full power or if sme_ExitWoWL API is invoked.
+            Note 3: Both UAPSD and WOWL work on top of BMPS. On entry into BMPS, SME
+            will give priority to UAPSD and enable only UAPSD if both UAPSD and WOWL
+            are required. Currently there is no requirement or use case to support UAPSD
+            and WOWL at the same time.
+            Note 4. Request for WoWL is rejected if there is a pending UAPSD request.
+            Note 5. Request for WoWL is rejected if BMPS is disabled.
+            
+    \param  hHal - The handle returned by macOpen.
+    \param  enterWowlCallbackRoutine -  Callback routine provided by HDD.
+                               Used for success/failure notification by SME
+    \param  enterWowlCallbackContext - A cookie passed by HDD, that is passed back to HDD
+                              at the time of callback.
+    \param  wakeReasonIndCB -  Callback routine provided by HDD.
+                               Used for Wake Reason Indication by SME
+    \param  wakeReasonIndCBContext - A cookie passed by HDD, that is passed back to HDD
+                              at the time of callback.
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS  Device is already in WoWLAN mode
+            eHAL_STATUS_FAILURE  Device cannot enter WoWLAN mode.
+            eHAL_STATUS_PMC_PENDING  Request accepted. SME will enable WOWL when BMPS
+                                      mode is entered.
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_EnterWowl (
+    tHalHandle hHal,
+    void (*enterWowlCallbackRoutine) (void *callbackContext, eHalStatus status),
+    void *enterWowlCallbackContext,
+#ifdef WLAN_WAKEUP_EVENTS
+    void (*wakeReasonIndCB) (void *callbackContext, tpSirWakeReasonInd pWakeReasonInd),
+    void *wakeReasonIndCBContext,
+#endif // WLAN_WAKEUP_EVENTS
+    tpSirSmeWowlEnterParams wowlEnterParams);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ExitWowl
+    \brief  This is the SME API exposed to HDD to request exit from WoWLAN mode. 
+            SME will initiate exit from WoWLAN mode and device will be put in BMPS 
+            mode. Any Buffered request for WoWL will be cleared after this API.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Device cannot exit WoWLAN mode. This can happen
+                                  only if the previous "Enter WOWL" transaction has
+                                  not even completed.
+            eHAL_STATUS_SUCCESS  Request accepted to exit WoWLAN mode. 
+  ---------------------------------------------------------------------------*/
+extern eHalStatus sme_ExitWowl (tHalHandle hHal);
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RoamSetKey
+
+    \brief To set encryption key. This function should be called only when connected
+    This is an asynchronous API.
+
+    \param pSetKeyInfo - pointer to a caller allocated object of tCsrSetContextInfo
+
+    \param pRoamId  Upon success return, this is the id caller can use to identify the request in roamcallback
+
+    \return eHalStatus  SUCCESS  Roam callback will be called indicate actually results
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamSetKey(tHalHandle, tANI_U8 sessionId, tCsrRoamSetKey *pSetKey, tANI_U32 *pRoamId);
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RoamRemoveKey
+
+    \brief To set encryption key. This is an asynchronous API.
+
+    \param pRemoveKey - pointer to a caller allocated object of tCsrRoamRemoveKey
+
+    \param pRoamId  Upon success return, this is the id caller can use to identify the request in roamcallback
+
+    \return eHalStatus  SUCCESS  Roam callback will be called indicate actually results
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamRemoveKey(tHalHandle, tANI_U8 sessionId, tCsrRoamRemoveKey *pRemoveKey, tANI_U32 *pRoamId);
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetCountryCode
+
+    \brief To return the current country code. If no country code is applied, default country code is 
+    used to fill the buffer.
+    If 11d supported is turned off, an error is return and the last applied/default country code is used.
+    This is a synchronous API.
+
+    \param pBuf - pointer to a caller allocated buffer for returned country code.
+
+    \param pbLen  For input, this parameter indicates how big is the buffer.
+                   Upon return, this parameter has the number of bytes for country. If pBuf
+                   doesn't have enough space, this function returns
+                   fail status and this parameter contains the number that is needed.
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetCountryCode(tHalHandle hHal, tANI_U8 *pBuf, tANI_U8 *pbLen);
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_SetCountryCode
+
+    \brief To change the current/default country code. 
+    If 11d supported is turned off, an error is return.
+    This is a synchronous API.
+
+    \param pCountry - pointer to a caller allocated buffer for the country code.
+
+    \param pfRestartNeeded  A pointer to caller allocated memory, upon successful return, it indicates
+    whether a reset is required.
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_SetCountryCode(tHalHandle hHal, tANI_U8 *pCountry, tANI_BOOLEAN *pfRestartNeeded);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ResetCountryCodeInformation
+    \brief this function is to reset the country code current being used back to EEPROM default
+    this includes channel list and power setting. This is a synchronous API.
+    \param pfRestartNeeded - pointer to a caller allocated space. Upon successful return, it indicates whether 
+    a restart is needed to apply the change
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_ResetCountryCodeInformation(tHalHandle hHal, tANI_BOOLEAN *pfRestartNeeded);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetSupportedCountryCode
+    \brief this function is to get a list of the country code current being supported
+    \param pBuf - Caller allocated buffer with at least 3 bytes, upon success return, 
+    this has the country code list. 3 bytes for each country code. This may be NULL if
+    caller wants to know the needed byte count.
+    \param pbLen - Caller allocated, as input, it indicates the length of pBuf. Upon success return,
+    this contains the length of the data in pBuf. If pbuf is NULL, as input, *pbLen should be 0.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetSupportedCountryCode(tHalHandle hHal, tANI_U8 *pBuf, tANI_U32 *pbLen);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetCurrentRegulatoryDomain
+    \brief this function is to get the current regulatory domain. This is a synchronous API.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    SME. The function fails if 11d support is turned off.
+    \param pDomain - Caller allocated buffer to return the current domain.
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.     
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetCurrentRegulatoryDomain(tHalHandle hHal, v_REGDOMAIN_t *pDomain);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetRegulatoryDomain
+    \brief this function is to set the current regulatory domain.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    SME. This is a synchronous API.
+    \param domainId - indicate the domain (defined in the driver) needs to set to.  
+    See v_REGDOMAIN_t for definition
+    \param pfRestartNeeded - pointer to a caller allocated space. Upon successful return, it indicates whether 
+    a restart is needed to apply the change
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_SetRegulatoryDomain(tHalHandle hHal, v_REGDOMAIN_t domainId, tANI_BOOLEAN *pfRestartNeeded);
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetRegulatoryDomainForCountry
+
+    \brief To return a regulatory domain base on a country code. This is a synchronous API.
+
+    \param pCountry - pointer to a caller allocated buffer for input country code.
+
+    \param pDomainId  Upon successful return, it is the domain that country belongs to.
+    If it is NULL, returning success means that the country code is known.
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetRegulatoryDomainForCountry(tHalHandle hHal, tANI_U8 *pCountry, v_REGDOMAIN_t *pDomainId);
+
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetSupportedRegulatoryDomains
+
+    \brief To return a list of supported regulatory domains. This is a synchronous API.
+
+    \param pDomains - pointer to a caller allocated buffer for returned regulatory domains.
+
+    \param pNumDomains  For input, this parameter indicates howm many domains pDomains can hold.
+                         Upon return, this parameter has the number for supported domains. If pDomains
+                         doesn't have enough space for all the supported domains, this function returns
+                         fail status and this parameter contains the number that is needed.
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetSupportedRegulatoryDomains(tHalHandle hHal, v_REGDOMAIN_t *pDomains, tANI_U32 *pNumDomains);
+
+//some support functions
+tANI_BOOLEAN sme_Is11dSupported(tHalHandle hHal);
+tANI_BOOLEAN sme_Is11hSupported(tHalHandle hHal);
+tANI_BOOLEAN sme_IsWmmSupported(tHalHandle hHal); 
+//Upper layer to get the list of the base channels to scan for passively 11d info from csr
+eHalStatus sme_ScanGetBaseChannels( tHalHandle hHal, tCsrChannelInfo * pChannelInfo );
+
+typedef void ( *tSmeChangeCountryCallback)(void *pContext);
+/* ---------------------------------------------------------------------------
+
+    \fn sme_ChangeCountryCode
+
+    \brief Change Country code from upperlayer during WLAN driver operation.
+           This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+
+    \param pCountry New Country Code String
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_ChangeCountryCode( tHalHandle hHal,
+                                  tSmeChangeCountryCallback callback,
+                                  tANI_U8 *pCountry,
+                                  void *pContext,
+                                  void* pVosContext );
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_BtcSignalBtEvent
+    \brief  API to signal Bluetooth (BT) event to the WLAN driver. Based on the
+            BT event type and the current operating mode of Libra (full power,
+            BMPS, UAPSD etc), appropriate Bluetooth Coexistence (BTC) strategy
+            would be employed.
+    \param  hHal - The handle returned by macOpen.
+    \param  pBtcBtEvent -  Pointer to a caller allocated object of type tSmeBtEvent
+                           Caller owns the memory and is responsible for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  BT Event not passed to HAL. This can happen
+                                   if driver has not yet been initialized or if BTC 
+                                   Events Layer has been disabled.
+            VOS_STATUS_SUCCESS    BT Event passed to HAL 
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_BtcSignalBtEvent (tHalHandle hHal, tpSmeBtEvent pBtcBtEvent);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_BtcSetConfig
+    \brief  API to change the current Bluetooth Coexistence (BTC) configuration
+            This function should be invoked only after CFG download has completed.
+            Calling it after sme_HDDReadyInd is recommended.
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type
+                            tSmeBtcConfig. Caller owns the memory and is responsible
+                            for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  Config not passed to HAL. 
+            VOS_STATUS_SUCCESS  Config passed to HAL 
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_BtcSetConfig (tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_BtcGetConfig
+    \brief  API to retrieve the current Bluetooth Coexistence (BTC) configuration
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type tSmeBtcConfig.
+                            Caller owns the memory and is responsible for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_BtcGetConfig (tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetCfgPrivacy
+    \brief  API to set configure privacy parameters
+    \param  hHal - The handle returned by macOpen.
+    \param  pProfile - Pointer CSR Roam profile.
+    \param  fPrivacy - This parameter indicates status of privacy 
+                            
+    \return void
+  ---------------------------------------------------------------------------*/
+void sme_SetCfgPrivacy(tHalHandle hHal, tCsrRoamProfile *pProfile, tANI_BOOLEAN fPrivacy);
+
+#if defined WLAN_FEATURE_VOWIFI
+/* ---------------------------------------------------------------------------
+    \fn sme_NeighborReportRequest
+    \brief  API to request neighbor report.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRrmNeighborReq - Pointer to a caller allocated object of type
+                            tRrmNeighborReq. Caller owns the memory and is responsible
+                            for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_NeighborReportRequest (tHalHandle hHal, tANI_U8 sessionId, 
+                tpRrmNeighborReq pRrmNeighborReq, tpRrmNeighborRspCallbackInfo callbackInfo);
+#endif
+
+//The following are debug APIs to support direct read/write register/memory
+//They are placed in SME because HW cannot be access when in LOW_POWER state
+//AND not connected. The knowledge and synchronization is done in SME
+
+//sme_DbgReadRegister
+//Caller needs to validate the input values
+VOS_STATUS sme_DbgReadRegister(tHalHandle hHal, v_U32_t regAddr, v_U32_t *pRegValue);
+
+//sme_DbgWriteRegister
+//Caller needs to validate the input values
+VOS_STATUS sme_DbgWriteRegister(tHalHandle hHal, v_U32_t regAddr, v_U32_t regValue);
+
+//sme_DbgReadMemory
+//Caller needs to validate the input values
+//pBuf caller allocated buffer has the length of nLen
+VOS_STATUS sme_DbgReadMemory(tHalHandle hHal, v_U32_t memAddr, v_U8_t *pBuf, v_U32_t nLen);
+
+//sme_DbgWriteMemory
+//Caller needs to validate the input values
+VOS_STATUS sme_DbgWriteMemory(tHalHandle hHal, v_U32_t memAddr, v_U8_t *pBuf, v_U32_t nLen);
+
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+//sme_GetFwVersion
+VOS_STATUS sme_GetFwVersion (tHalHandle hHal,FwVersionInfo *pVersion);
+#endif
+#ifdef FEATURE_WLAN_INTEGRATED_SOC
+VOS_STATUS sme_GetWcnssWlanCompiledVersion(tHalHandle hHal,
+                                           tSirVersionType *pVersion);
+VOS_STATUS sme_GetWcnssWlanReportedVersion(tHalHandle hHal,
+                                           tSirVersionType *pVersion);
+VOS_STATUS sme_GetWcnssSoftwareVersion(tHalHandle hHal,
+                                       tANI_U8 *pVersion,
+                                       tANI_U32 versionBufferSize);
+VOS_STATUS sme_GetWcnssHardwareVersion(tHalHandle hHal,
+                                       tANI_U8 *pVersion,
+                                       tANI_U32 versionBufferSize);
+#endif
+eHalStatus sme_RoamRegisterCallback(tHalHandle hHal,
+                                    csrRoamCompleteCallback callback,
+                                    void *pContext);
+
+#ifdef FEATURE_WLAN_WAPI
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamSetBKIDCache
+    \brief The SME API exposed to HDD to allow HDD to provde SME the BKID 
+    candidate list.
+    \param hHal - Handle to the HAL. The HAL handle is returned by the HAL after 
+    it is opened (by calling halOpen).
+    \param pBKIDCache - caller allocated buffer point to an array of tBkidCacheInfo
+    \param numItems - a variable that has the number of tBkidCacheInfo allocated 
+    when retruning, this is the number of items put into pBKIDCache
+    \return eHalStatus - when fail, it usually means the buffer allocated is not 
+    big enough and pNumItems has the number of tBkidCacheInfo.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamSetBKIDCache( tHalHandle hHal, tANI_U32 sessionId, tBkidCacheInfo *pBKIDCache,
+                                 tANI_U32 numItems );
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetBKIDCache
+    \brief The SME API exposed to HDD to allow HDD to request SME to return its 
+    BKID cache.
+    \param hHal - Handle to the HAL. The HAL handle is returned by the HAL after 
+    it is opened (by calling halOpen).
+    \param pNum - caller allocated memory that has the space of the number of 
+    tBkidCacheInfo as input. Upon returned, *pNum has the needed number of entries 
+    in SME cache.
+    \param pBkidCache - Caller allocated memory that contains BKID cache, if any, 
+    upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not 
+    big enough.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetBKIDCache(tHalHandle hHal, tANI_U32 *pNum,
+                                tBkidCacheInfo *pBkidCache);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetNumBKIDCache
+    \brief The SME API exposed to HDD to allow HDD to request SME to return the 
+    number of BKID cache entries.
+    \param hHal - Handle to the HAL. The HAL handle is returned by the HAL after 
+    it is opened (by calling halOpen).
+    \return tANI_U32 - the number of BKID cache entries.
+  ---------------------------------------------------------------------------*/
+tANI_U32 sme_RoamGetNumBKIDCache(tHalHandle hHal, tANI_U32 sessionId);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanGetBKIDCandidateList
+    \brief a wrapper function to return the BKID candidate list
+    \param pBkidList - caller allocated buffer point to an array of 
+                        tBkidCandidateInfo
+    \param pNumItems - pointer to a variable that has the number of 
+                       tBkidCandidateInfo allocated when retruning, this is 
+                       either the number needed or number of items put into 
+                       pPmkidList
+    \return eHalStatus - when fail, it usually means the buffer allocated is not 
+                         big enough and pNumItems
+    has the number of tBkidCandidateInfo.
+    \Note: pNumItems is a number of tBkidCandidateInfo, 
+           not sizeof(tBkidCandidateInfo) * something
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanGetBKIDCandidateList(tHalHandle hHal, tANI_U32 sessionId,
+                                        tBkidCandidateInfo *pBkidList, 
+                                        tANI_U32 *pNumItems );
+#endif /* FEATURE_WLAN_WAPI */
+
+
+
+#ifdef WLAN_SOFTAP_FEATURE
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RoamUpdateAPWPSIE
+
+    \brief To update AP's WPS IE. This function should be called after SME AP session is created
+    This is an asynchronous API.
+
+    \param pAPWPSIES - pointer to a caller allocated object of tCsrRoamAPWPSIES
+
+    \return eHalStatus – SUCCESS – Roam callback will be called indicate actually results
+
+                         FAILURE or RESOURCES – The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+
+eHalStatus sme_RoamUpdateAPWPSIE(tHalHandle, tANI_U8 sessionId, tSirAPWPSIEs *pAPWPSIES);
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RoamUpdateAPWPARSNIEs
+
+    \brief To update AP's WPA/RSN IEs. This function should be called after SME AP session is created
+    This is an asynchronous API.
+
+    \param pAPSirRSNie - pointer to a caller allocated object of tSirRSNie with WPS/RSN IEs
+
+    \return eHalStatus – SUCCESS – 
+
+                         FAILURE or RESOURCES – The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamUpdateAPWPARSNIEs(tHalHandle hHal, tANI_U8 sessionId, tSirRSNie * pAPSirRSNie);
+
+#endif
+
+/* ---------------------------------------------------------------------------
+  \fn sme_sendBTAmpEvent
+  \brief API to send the btAMPstate to FW
+  \param  hHal - The handle returned by macOpen.
+  \param  btAmpEvent -- btAMP event
+  \return eHalStatus – SUCCESS –
+
+                         FAILURE or RESOURCES – The API finished and failed.
+
+--------------------------------------------------------------------------- */
+
+eHalStatus sme_sendBTAmpEvent(tHalHandle hHal, tSmeBtAmpEvent btAmpEvent);
+
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetHostOffload
+    \brief  API to set the host offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the offload request.
+    \return eHalStatus
+   ---------------------------------------------------------------------------*/
+eHalStatus sme_SetHostOffload (tHalHandle hHal, tpSirHostOffloadReq pRequest);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetKeepAlive
+    \brief  API to set the Keep Alive feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the Keep Alive request.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetKeepAlive (tHalHandle hHal, tpSirKeepAliveReq pRequest);
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_AbortMacScan
+    \brief  API to cancel MAC scan.
+    \param  hHal - The handle returned by macOpen.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_AbortMacScan(tHalHandle hHal);
+
+/* ----------------------------------------------------------------------------
+   \fn sme_GetOperationChannel
+   \brief API to get current channel on which STA is parked
+   this function gives channel information only of infra station or IBSS station.
+   \param hHal and poiter to memory location 
+   \returns eHAL_STATUS_SUCCESS
+            eHAL_STATUS_FAILURE
+-------------------------------------------------------------------------------*/
+eHalStatus sme_GetOperationChannel(tHalHandle hHal, tANI_U32 *pChannel);
+
+#ifdef WLAN_FEATURE_P2P
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RegisterMgtFrame
+
+    \brief To register managment frame of specified type and subtype. 
+    \param frameType - type of the frame that needs to be passed to HDD.
+    \param matchData - data which needs to be matched before passing frame 
+                       to HDD. 
+    \param matchDataLen - Length of matched data.
+    \return eHalStatus 
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RegisterMgmtFrame(tHalHandle hHal, tANI_U8 sessionId, 
+                     tANI_U16 frameType, tANI_U8* matchData, tANI_U16 matchLen);
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_DeregisterMgtFrame
+
+    \brief To De-register managment frame of specified type and subtype. 
+    \param frameType - type of the frame that needs to be passed to HDD.
+    \param matchData - data which needs to be matched before passing frame 
+                       to HDD. 
+    \param matchDataLen - Length of matched data.
+    \return eHalStatus 
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_DeregisterMgmtFrame(tHalHandle hHal, tANI_U8 sessionId, 
+                     tANI_U16 frameType, tANI_U8* matchData, tANI_U16 matchLen);
+#endif
+
+/* ---------------------------------------------------------------------------
+
+  \fn    sme_ConfigureRxpFilter
+
+  \brief 
+    SME will pass this request to lower mac to set/reset the filter on RXP for
+    multicast & broadcast traffic.
+
+  \param 
+
+    hHal - The handle returned by macOpen. 
+ 
+    filterMask- Currently the API takes a 1 or 0 (set or reset) as filter.
+    Basically to enable/disable the filter (to filter "all" mcbc traffic) based
+    on this param. In future we can use this as a mask to set various types of
+    filters as suggested below:
+    FILTER_ALL_MULTICAST:
+    FILTER_ALL_BROADCAST:
+    FILTER_ALL_MULTICAST_BROADCAST:
+
+   
+  \return eHalStatus    
+  
+  
+--------------------------------------------------------------------------- */
+eHalStatus sme_ConfigureRxpFilter( tHalHandle hHal, 
+                              tpSirWlanSetRxpFilters  wlanRxpFilterParam);
+
+/* ---------------------------------------------------------------------------
+
+  \fn    sme_ConfigureAppsCpuWakeupState
+
+  \brief 
+    SME will pass this request to lower mac to dynamically adjusts the listen
+    interval based on the WLAN/MSM activity. This feature is named as
+    Telescopic Beacon wakeup feature.
+
+  \param 
+
+    hHal - The handle returned by macOpen. 
+ 
+    isAppsAwake- Depicts the state of the Apps CPU
+
+   
+  \return eHalStatus    
+  
+  
+--------------------------------------------------------------------------- */
+eHalStatus sme_ConfigureAppsCpuWakeupState( tHalHandle hHal, tANI_BOOLEAN  isAppsAwake);
+
+#ifdef FEATURE_WLAN_INTEGRATED_SOC
+/* ---------------------------------------------------------------------------
+
+  \fn    sme_ConfigureSuspendInd
+
+  \brief 
+    SME will pass this request to lower mac to Indicate that the wlan needs to 
+    be suspended
+
+  \param 
+
+    hHal - The handle returned by macOpen. 
+ 
+    wlanSuspendParam- Depicts the wlan suspend params
+
+   
+  \return eHalStatus    
+  
+  
+--------------------------------------------------------------------------- */
+eHalStatus sme_ConfigureSuspendInd( tHalHandle hHal, 
+                             tpSirWlanSuspendParam  wlanSuspendParam);
+
+/* ---------------------------------------------------------------------------
+
+  \fn    sme_ConfigureResumeReq
+
+  \brief 
+    SME will pass this request to lower mac to Indicate that the wlan needs to 
+    be Resumed
+
+  \param 
+
+    hHal - The handle returned by macOpen. 
+ 
+    wlanResumeParam- Depicts the wlan resume params
+
+   
+  \return eHalStatus    
+  
+  
+--------------------------------------------------------------------------- */
+eHalStatus sme_ConfigureResumeReq( tHalHandle hHal, 
+                             tpSirWlanResumeParam  wlanResumeParam);
+
+#endif
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetInfraSessionId
+
+    \brief To get the session ID for infra session, if connected
+    This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+
+    \return sessionid, -1 if infra session is not connected
+
+  -------------------------------------------------------------------------------*/
+tANI_S8 sme_GetInfraSessionId(tHalHandle hHal);
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetInfraOperationChannel
+
+    \brief To get the operating channel for infra session, if connected
+    This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+    \param sessionId - the sessionId returned by sme_OpenSession.
+
+    \return operating channel, 0 if infra session is not connected
+
+  -------------------------------------------------------------------------------*/
+tANI_U8 sme_GetInfraOperationChannel( tHalHandle hHal, tANI_U8 sessionId);
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetConcurrentOperationChannel
+
+    \brief To get the operating channel for other concurrent sessions, if connected
+    This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+    \param currentPersona - persona that is trying to come up.
+
+    \return operating channel, 0 if infra session is not connected
+
+  -------------------------------------------------------------------------------*/
+tANI_U8 sme_GetConcurrentOperationChannel( tHalHandle hHal );
+
+/* ---------------------------------------------------------------------------
+    \fn sme_AbortMacScan
+    \brief  API to cancel MAC scan.
+    \param  hHal - The handle returned by macOpen.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_AbortMacScan(tHalHandle hHal);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetCfgValidChannels
+    \brief  API to get valid channel list
+    \param  hHal - The handle returned by macOpen.
+    \param  aValidChannels -  Pointer to the valid channel list
+    \param  len -  valid channel list length
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetCfgValidChannels(tHalHandle hHal, tANI_U8 *aValidChannels, tANI_U32 *len);
+
+#ifdef FEATURE_WLAN_SCAN_PNO
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetPreferredNetworkList
+    \brief  API to set the Preferred Network List Offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the offload request.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetPreferredNetworkList (tHalHandle hHal, tpSirPNOScanReq pRequest, tANI_U8 sessionId, preferredNetworkFoundIndCallback callbackRoutine, void *callbackContext );
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetRSSIFilter
+    \brief  API to set RSSI Filter feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the offload request.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetRSSIFilter(tHalHandle hHal, v_U8_t rssiThreshold);
+
+/******************************************************************************
+*
+* Name: sme_PreferredNetworkFoundInd
+*
+* Description:
+*    Invoke Preferred Network Found Indication 
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    pMsg - found network description
+* 
+* Returns: eHalStatus
+*
+******************************************************************************/
+eHalStatus sme_PreferredNetworkFoundInd (tHalHandle hHal, void* pMsg);
+#endif // FEATURE_WLAN_SCAN_PNO
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetPowerParams
+    \brief  API to set Power Parameters 
+    \param  hHal - The handle returned by macOpen.
+    \param  pwParams -  Pointer to the power parameters requested.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetPowerParams(tHalHandle hHal, tSirSetPowerParamsReq* pwParams);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetTxPerTracking
+    \brief  Set Tx PER tracking configuration parameters
+    \param  hHal - The handle returned by macOpen.
+    \param  pTxPerTrackingParam - Tx PER configuration parameters
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetTxPerTracking (
+   tHalHandle hHal,
+   void (*pCallbackfn) (void *pCallbackContext),
+   void *pCallbackContext,
+   tpSirTxPerTrackingParam pTxPerTrackingParam);
+
+#ifdef WLAN_FEATURE_PACKET_FILTERING
+/* ---------------------------------------------------------------------------
+    \fn sme_ReceiveFilterSetFilter
+    \brief  API to set 8023 Multicast Address List
+    \param  hHal - The handle returned by macOpen.
+    \param  pMulticastAddrs - Pointer to the Multicast Address List
+    \return eHalStatus   
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_8023MulticastList(tHalHandle hHal, tpSirRcvFltMcAddrList pMulticastAddrs);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ReceiveFilterSetFilter
+    \brief  API to set Receive Packet Filter
+    \param  hHal - The handle returned by macOpen.
+    \param  pRcvPktFilterCfg - Receive Packet Filter parameter
+    \return eHalStatus   
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ReceiveFilterSetFilter(tHalHandle hHal, tpSirRcvPktFilterCfgType pRcvPktFilterCfg);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetFilterMatchCount
+    \brief  API to get D0 PC Filter Match Count
+    \param  hHal - The handle returned by macOpen 
+    \param  callbackRoutine - Callback routine invoked to receive Packet Coalescing Filter Match Count
+    \param  callbackContext - Cookie to be passed back during callback 
+    \return eHalStatus   
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetFilterMatchCount(tHalHandle hHal, 
+                                   FilterMatchCountCallback callbackRoutine, 
+                                   void *callbackContext );
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ReceiveFilterClearFilter
+    \brief  API to clear Receive Packet Filter
+    \param  hHal - The handle returned by macOpen.
+    \param  pRcvFltPktClearParam - Receive Packet Filter Clear parameter
+    \return eHalStatus   
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ReceiveFilterClearFilter(tHalHandle hHal,
+                                        tpSirRcvFltPktClearParam pRcvFltPktClearParam);
+#endif // WLAN_FEATURE_PACKET_FILTERING
+/* ---------------------------------------------------------------------------
+
+    \fn sme_IsChannelValid
+    \brief To check if the channel is valid for currently established domain
+    This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+    \param channel - channel to verify
+
+    \return TRUE/FALSE, TRUE if channel is valid
+
+  -------------------------------------------------------------------------------*/
+tANI_BOOLEAN sme_IsChannelValid(tHalHandle hHal, tANI_U8 channel);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetFreqBand
+    \brief  Used to set frequency band.
+    \param  hHal
+    \eBand  band value to be configured
+    \- return eHalStatus
+    -------------------------------------------------------------------------*/
+eHalStatus sme_SetFreqBand(tHalHandle hHal, eCsrBand eBand);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetFreqBand
+    \brief  Used to get the current band settings.
+    \param  hHal
+    \pBand  pointer to hold the current band value
+    \- return eHalStatus
+    -------------------------------------------------------------------------*/
+eHalStatus sme_GetFreqBand(tHalHandle hHal, eCsrBand *pBand);
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_SetTxPerTracking
+    \brief  Set Tx PER tracking configuration parameters
+    \param  hHal - The handle returned by macOpen.
+    \param  pTxPerTrackingParam - Tx PER configuration parameters
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetTxPerTracking (
+   tHalHandle hHal,
+   void (*pCallbackfn) (void *pCallbackContext),
+   void *pCallbackContext,
+   tpSirTxPerTrackingParam pTxPerTrackingParam);
+
+#ifdef WLAN_FEATURE_GTK_OFFLOAD
+/* ---------------------------------------------------------------------------
+    \fn sme_SetGTKOffload
+    \brief  API to set GTK offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the GTK offload request.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetGTKOffload (tHalHandle hHal, tpSirGtkOffloadParams pRequest);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetGTKOffload
+    \brief  API to get GTK offload information.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the GTK offload response.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetGTKOffload (tHalHandle hHal, GTKOffloadGetInfoCallback callbackRoutine, void *callbackContext );
+#endif // WLAN_FEATURE_GTK_OFFLOAD
+
+#ifdef WLAN_WAKEUP_EVENTS
+eHalStatus sme_WakeReasonIndCallback (tHalHandle hHal, void* pMsg);
+#endif // WLAN_WAKEUP_EVENTS
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetTxPerTracking
+    \brief  Set Tx PER tracking configuration parameters
+    \param  hHal - The handle returned by macOpen.
+    \param  pTxPerTrackingParam - Tx PER configuration parameters
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetTxPerTracking (
+   tHalHandle hHal,
+   void (*pCallbackfn) (void *pCallbackContext),
+   void *pCallbackContext,
+   tpSirTxPerTrackingParam pTxPerTrackingParam);
+
+
+//return frequency for a particular channel
+tANI_U16 sme_ChnToFreq(tANI_U8 chanNum);
+
+tANI_BOOLEAN sme_IsChannelValid(tHalHandle hHal, tANI_U8 channel);
+
+#if defined WLAN_FEATURE_P2P_INTERNAL
+
+eHalStatus sme_p2pResetSession(tHalHandle hHal, tANI_U8 HDDSessionId);
+
+/* ---------------------------------------------------------------------------
+    \fn sme_p2pFlushDeviceList
+    \brief  Remove cached P2P result from scan results
+    \param  hHal - The handle returned by macOpen.
+    \param  HDDSessionId - HDD's sessionId. Currently unused.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_p2pFlushDeviceList(tHalHandle hHal, tANI_U8 HDDSessionId);
+
+eHalStatus sme_p2pGetResultFilter(tHalHandle hHal, tANI_U8 HDDSessionId,
+                              tCsrScanResultFilter *pFilter);
+
+#endif //#if defined WLAN_FEATURE_P2P_INTERNAL
+   
+/* ---------------------------------------------------------------------------
+    \fn sme_SetMaxTxPower
+    \brief  Used to set the Maximum Transmit Power dynamically. Note: this
+    setting will not persist over reboots
+    \param  hHal
+    \param pBssid  BSSID to set the power cap for
+    \param pBssid  pSelfMacAddress self MAC Address
+    \param pBssid  power to set in dB
+    \- return eHalStatus
+    -------------------------------------------------------------------------*/
+eHalStatus sme_SetMaxTxPower(tHalHandle hHal, tSirMacAddr pBssid, 
+                             tSirMacAddr pSelfMacAddress, v_S7_t dB);
+
+#ifdef WLAN_SOFTAP_FEATURE
+/* ---------------------------------------------------------------------------
+
+    \fn sme_HideSSID
+
+    \brief Enable/Disables hidden SSID dynamically. Note: this setting will
+    not persist over reboots.
+
+    \param hHal
+    \param sessionId 
+    \param ssidHidden 0 - Broadcast SSID, 1 - Disable broadcast SSID
+    \- return eHalStatus
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_HideSSID(tHalHandle hHal, v_U8_t sessionId, v_U8_t ssidHidden);
+#endif
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_SetTmLevel
+    \brief  Set Thermal Mitigation Level to RIVA
+    \param  hHal - The handle returned by macOpen.
+    \param  newTMLevel - new Thermal Mitigation Level
+    \param  tmMode - Thermal Mitigation handle mode, default 0
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetTmLevel(tHalHandle hHal, v_U16_t newTMLevel, v_U16_t tmMode);
+
+/*---------------------------------------------------------------------------
+
+  \brief sme_featureCapsExchange() - SME interface to exchange capabilities between
+  Host and FW.
+
+  \param  hHal - HAL handle for device
+
+  \return NONE
+
+---------------------------------------------------------------------------*/
+void sme_featureCapsExchange(tHalHandle hHal);
+
+#endif //#if !defined( __SME_API_H )
diff --git a/CORE/SME/inc/sme_FTApi.h b/CORE/SME/inc/sme_FTApi.h
new file mode 100644
index 0000000..30465c6
--- /dev/null
+++ b/CORE/SME/inc/sme_FTApi.h
@@ -0,0 +1,84 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+#if !defined( __SME_FTAPI_H )
+#define __SME_FTAPI_H
+
+#include <limFTDefs.h>
+#include <palTimer.h>
+
+/**=========================================================================
+  
+  \brief macros and prototype for SME APIs
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+typedef enum eFTIEState
+{
+    eFT_START_READY,                // Start before and after 11r assoc
+    eFT_AUTH_REQ_READY,             // When we have recvd the 1st or nth auth req
+    eFT_WAIT_AUTH2,                 // Sent auth1 and waiting auth2
+    eFT_AUTH_COMPLETE,              // We are now ready for FT phase, send auth1, recd auth2
+    eFT_REASSOC_REQ_WAIT,           // Now we have sent Auth Rsp to the supplicant and waiting
+                                    // Reassoc Req from the supplicant.
+    eFT_SET_KEY_WAIT,               // We have received the Reassoc request from 
+                                    // supplicant. Waiting for the keys.
+} tFTIEStates;
+
+
+typedef struct sFTSMEContext
+{
+    tANI_U8           *auth_ft_ies;
+    tANI_U32          auth_ft_ies_length;
+
+    tANI_U8           *reassoc_ft_ies;
+    tANI_U16          reassoc_ft_ies_length;
+
+    // Pre-Auth info
+    tFTIEStates       FTState;               // The state of FT in the current 11rAssoc
+    tSirMacAddr       preAuthbssId;          // BSSID to preauth to
+    tANI_U32          smeSessionId;
+
+    // Saved pFTPreAuthRsp
+    tpSirFTPreAuthRsp psavedFTPreAuthRsp;
+
+    // Time to trigger reassoc once pre-auth is successful
+    tPalTimerHandle   preAuthReassocIntvlTimer;
+
+} tftSMEContext, *tpftSMEContext;
+
+/*--------------------------------------------------------------------------
+  Prototype functions
+  ------------------------------------------------------------------------*/
+void sme_FTOpen(tHalHandle hHal);
+void sme_FTClose(tHalHandle hHal);
+void sme_SetFTIEs( tHalHandle hHal, tANI_U8 sessionId, tANI_U8 *ft_ies, tANI_U16 ft_ies_length );
+eHalStatus sme_FTUpdateKey( tHalHandle hHal, tCsrRoamSetKey * pFTKeyInfo );
+void csrFTPreAuthRspProcessor( tHalHandle hHal, tpSirFTPreAuthRsp pFTPreAuthRsp );
+void sme_GetFTPreAuthResponse( tHalHandle hHal, tANI_U8 *ft_ies, tANI_U32 ft_ies_ip_len, tANI_U16 *ft_ies_length );
+void sme_GetRICIEs( tHalHandle hHal, tANI_U8 *ric_ies, tANI_U32 ric_ies_ip_len, tANI_U32 *ric_ies_length );
+void sme_PreauthReassocIntvlTimerCallback(void *context);
+
+
+#endif //#if !defined( __SME_FTAPI_H )
diff --git a/CORE/SME/inc/sme_QosApi.h b/CORE/SME/inc/sme_QosApi.h
new file mode 100644
index 0000000..d6614fd
--- /dev/null
+++ b/CORE/SME/inc/sme_QosApi.h
@@ -0,0 +1,356 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+
+#if !defined( __SME_QOSAPI_H )
+#define __SME_QOSAPI_H
+
+
+/**=========================================================================
+  
+  \file  sme_QosApi.h
+  
+  \brief prototype for SME QoS APIs
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+
+/* $Header$ */
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#include "vos_lock.h"
+#include "vos_trace.h"
+#include "vos_memory.h"
+#include "vos_types.h"
+#include "aniGlobal.h"
+#include "sirApi.h"
+
+/*-------------------------------------------------------------------------- 
+  Type declarations
+  ------------------------------------------------------------------------*/
+
+/*---------------------------------------------------------------------------
+   Enumeration of the various QoS status types that would be reported to HDD
+---------------------------------------------------------------------------*/
+typedef enum
+{
+   //async: once PE notifies successful TSPEC negotiation, or CSR notifies for
+   //successful reassoc, notifies HDD with current QoS Params
+   SME_QOS_STATUS_SETUP_SUCCESS_IND = 0, 
+   //sync: only when App asked for APSD & it's already set with ACM = 0
+   SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY,
+   //both: sync or async: in case of async notifies HDD with current QoS Params
+   SME_QOS_STATUS_SETUP_FAILURE_RSP, 
+   //sync
+   SME_QOS_STATUS_SETUP_INVALID_PARAMS_RSP, 
+   //sync: AP doesn't support QoS (WMM)
+   SME_QOS_STATUS_SETUP_NOT_QOS_AP_RSP, 
+   //sync: either req has been sent down to PE or just buffered in SME
+   SME_QOS_STATUS_SETUP_REQ_PENDING_RSP, 
+   //async: in case of flow aggregation, if the new TSPEC negotiation is 
+   //successful, OR, 
+   //notify existing flows that TSPEC is modified with current QoS Params
+   SME_QOS_STATUS_SETUP_MODIFIED_IND,
+   //sync: no APSD asked for & ACM = 0
+   SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP, 
+   //async: In case of UAPSD, once PE notifies successful TSPEC negotiation, or 
+   //CSR notifies for successful reassoc to SME-QoS, notify HDD if PMC can't
+   //put the module in UAPSD mode right away (eHAL_STATUS_PMC_PENDING)
+   SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_PENDING, 
+   //async: In case of UAPSD, once PE notifies successful TSPEC negotiation, or 
+   //CSR notifies for successful reassoc to SME-QoS, notify HDD if PMC can't
+   //put the module in UAPSD mode at all (eHAL_STATUS_FAILURE)
+   SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_SET_FAILED, 
+
+   //sync: req has been sent down to PE in case of delts or addts for remain 
+   // flows, OR if the AC doesn't have APSD or ACM
+   //async: once the downgrade req for QoS params is successful
+   SME_QOS_STATUS_RELEASE_SUCCESS_RSP = 100,
+   //both: sync or async: in case of async notifies HDD with current QoS Params
+   SME_QOS_STATUS_RELEASE_FAILURE_RSP,
+   //async: AP sent DELTS indication
+   SME_QOS_STATUS_RELEASE_QOS_LOST_IND,
+   //sync: an addts req has been sent down to PE to downgrade the QoS params or 
+   // just buffered in SME
+   SME_QOS_STATUS_RELEASE_REQ_PENDING_RSP, 
+   //sync
+   SME_QOS_STATUS_RELEASE_INVALID_PARAMS_RSP, 
+
+   //async: for QoS modify request if modification is successful, notifies HDD 
+   // with current QoS Params
+   SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND = 200,
+   //sync: only when App asked for APSD & it's already set with ACM = 0
+   SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_APSD_SET_ALREADY,
+   //both: sync or async: in case of async notifies HDD with current QoS Params
+   SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP,
+   //sync: either req has been sent down to PE or just buffered in SME
+   SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP,
+   //sync: no APSD asked for & ACM = 0
+   SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP, 
+   //sync
+   SME_QOS_STATUS_MODIFY_SETUP_INVALID_PARAMS_RSP, 
+   //async: In case of UAPSD, once PE notifies successful TSPEC negotiation, or 
+   //CSR notifies for successful reassoc to SME-QoS, notify HDD if PMC can't
+   //put the module in UAPSD mode right away (eHAL_STATUS_PMC_PENDING)
+   SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND_APSD_PENDING, 
+   //async: In case of UAPSD, once PE notifies successful TSPEC negotiation, or 
+   //CSR notifies for successful reassoc to SME-QoS, notify HDD if PMC can't
+   //put the module in UAPSD mode at all (eHAL_STATUS_FAILURE)
+   SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND_APSD_SET_FAILED,
+   //sync: STA is handing off to a new AP
+   SME_QOS_STATUS_HANDING_OFF = 300,
+   //async:powersave mode changed by PMC from UAPSD to Full power
+   SME_QOS_STATUS_OUT_OF_APSD_POWER_MODE_IND = 400,
+   //async:powersave mode changed by PMC from Full power to UAPSD
+   SME_QOS_STATUS_INTO_APSD_POWER_MODE_IND,
+   
+}sme_QosStatusType;
+
+/*---------------------------------------------------------------------------
+   Enumeration of the various User priority (UP) types
+   
+   From 802.1D/802.11e/WMM specifications (all refer to same table)
+---------------------------------------------------------------------------*/
+typedef enum
+{
+   SME_QOS_WMM_UP_BE      = 0,
+   SME_QOS_WMM_UP_BK      = 1,
+   SME_QOS_WMM_UP_RESV    = 2,    /* Reserved                              */
+   SME_QOS_WMM_UP_EE      = 3,
+   SME_QOS_WMM_UP_CL      = 4,
+   SME_QOS_WMM_UP_VI      = 5,
+   SME_QOS_WMM_UP_VO      = 6,
+   SME_QOS_WMM_UP_NC      = 7,
+
+   SME_QOS_WMM_UP_MAX
+
+}sme_QosWmmUpType;
+
+/*---------------------------------------------------------------------------
+   Enumeration of the various TSPEC directions
+   
+   From 802.11e/WMM specifications
+---------------------------------------------------------------------------*/
+
+typedef enum
+{
+   SME_QOS_WMM_TS_DIR_UPLINK   = 0,
+   SME_QOS_WMM_TS_DIR_DOWNLINK = 1,
+   SME_QOS_WMM_TS_DIR_RESV     = 2,   /* Reserved                          */
+   SME_QOS_WMM_TS_DIR_BOTH     = 3,
+
+}sme_QosWmmDirType;
+
+/*---------------------------------------------------------------------------
+   Enumeration of the various TSPEC ack policies.
+   
+   From 802.11 WMM specification
+---------------------------------------------------------------------------*/
+
+typedef enum
+{
+   SME_QOS_WMM_TS_ACK_POLICY_NORMAL_ACK   = 0,
+   SME_QOS_WMM_TS_ACK_POLICY_RESV1 = 1,
+   SME_QOS_WMM_TS_ACK_POLICY_RESV2     = 2,   /* Reserved                          */
+   SME_QOS_WMM_TS_ACK_POLICY_HT_IMMEDIATE_BLOCK_ACK     = 3,
+
+}sme_QosWmmAckPolicyType;
+
+/*---------------------------------------------------------------------------
+   TS Info field in the WMM TSPEC
+   
+   See suggestive values above
+---------------------------------------------------------------------------*/
+typedef struct
+{
+   v_U8_t              burst_size_defn;
+   sme_QosWmmAckPolicyType    ack_policy;
+   sme_QosWmmUpType    up;        /* User priority                    */
+   v_U8_t              psb;       /* power-save bit                   */
+   sme_QosWmmDirType   direction; /* Direction                        */
+   v_U8_t              tid;       /* TID : To be filled up by SME-QoS */
+} sme_QosWmmTsInfoType;
+
+/*---------------------------------------------------------------------------
+    The WMM TSPEC Element (from the WMM spec)
+---------------------------------------------------------------------------*/
+typedef struct
+{ 
+  sme_QosWmmTsInfoType            ts_info;
+  v_U16_t                         nominal_msdu_size;
+  v_U16_t                         maximum_msdu_size;
+  v_U32_t                         min_service_interval;
+  v_U32_t                         max_service_interval;
+  v_U32_t                         inactivity_interval;
+  v_U32_t                         suspension_interval;
+  v_U32_t                         svc_start_time;
+  v_U32_t                         min_data_rate;
+  v_U32_t                         mean_data_rate;
+  v_U32_t                         peak_data_rate;
+  v_U32_t                         max_burst_size;
+  v_U32_t                         delay_bound;
+  v_U32_t                         min_phy_rate;
+  v_U16_t                         surplus_bw_allowance;
+  v_U16_t                         medium_time;
+} sme_QosWmmTspecInfo;
+
+
+/*-------------------------------------------------------------------------- 
+                         External APIs
+  ------------------------------------------------------------------------*/
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosCallback() - This is a callback function which is registered 
+   per flow while HDD is requesting for QoS. Used for any notification for the 
+   flow (i.e. setup success/failure/release) which needs to be sent to HDD. HDD
+   will notify the application in turn, if needed.
+  
+  \param hHal - The handle returned by macOpen.
+  \param HDDcontext - A cookie passed by HDD during QoS setup, to be used by SME 
+                      during any QoS notification (through the callabck) to HDD 
+  \param pCurrentQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM 
+                           TSPEC related info as defined above, fed back to HDD
+  \param status - The status of the flow running on an AC. It could be of 
+                  sme_QosStatusType
+  
+  \return eHAL_STATUS_SUCCESS - Callback invoke successful.
+  
+
+  \sa
+  
+  --------------------------------------------------------------------------*/
+typedef eHalStatus (*sme_QosCallback)(tHalHandle hHal, void * HDDcontext, 
+                                      sme_QosWmmTspecInfo * pCurrentQoSInfo, 
+                                      sme_QosStatusType status,
+                                      v_U32_t QosFlowID);   
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosSetupReq() - The SME QoS API exposed to HDD to request for QoS 
+  on a particular AC. This function should be called after a link has been 
+  established, i.e. STA is associated with an AP etc. If the request involves 
+  admission control on the requested AC, HDD needs to provide the necessary 
+  Traffic Specification (TSPEC) parameters otherwise SME is going to use the
+  default params.
+  
+  \param hHal - The handle returned by macOpen.
+  \param sessionId - sessionId returned by sme_OpenSession. Current QOS code doesn't 
+                     support multiple session. This function returns failure when different
+                     sessionId is passed in before calling sme_QosReleaseReq.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info as defined above, provided by HDD
+  \param QoSCallback - The callback which is registered per flow while 
+                       requesting for QoS. Used for any notification for the 
+                       flow (i.e. setup success/failure/release) which needs to 
+                       be sent to HDD
+  \param HDDcontext - A cookie passed by HDD to be used by SME during any QoS 
+                      notification (through the callabck) to HDD 
+  \param UPType - Useful only if HDD or any other upper layer module (BAP etc.)
+                  looking for implicit QoS setup, in that 
+                  case, the pQoSInfo will be NULL & SME will know about the AC
+                  (from the UP provided in this param) QoS is requested on
+  \param pQosFlowID - Identification per flow running on each AC generated by 
+                      SME. 
+                     It is only meaningful if the QoS setup for the flow is 
+                     successful
+                  
+  \return SME_QOS_STATUS_SETUP_SUCCESS - Setup request processed successfully.
+  
+          Other status means Setup request failed     
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosSetupReq(tHalHandle hHal, tANI_U32 sessionId,
+                                  sme_QosWmmTspecInfo * pQoSInfo,
+                                  sme_QosCallback QoSCallback, void * HDDcontext,
+                                  sme_QosWmmUpType UPType, v_U32_t * pQosFlowID);
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosModifyReq() - The SME QoS API exposed to HDD to request for 
+  modification of certain QoS params on a flow running on a particular AC. 
+  This function should be called after a link has been established, i.e. STA is 
+  associated with an AP etc. & a QoS setup has been succesful for that flow. 
+  If the request involves admission control on the requested AC, HDD needs to 
+  provide the necessary Traffic Specification (TSPEC) parameters & SME might
+  start the renegotiation process through ADDTS.
+  
+  \param hHal - The handle returned by macOpen.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info as defined above, provided by HDD
+  \param QosFlowID - Identification per flow running on each AC generated by 
+                      SME. 
+                     It is only meaningful if the QoS setup for the flow has 
+                     been successful already
+                  
+  \return SME_QOS_STATUS_SETUP_SUCCESS - Modification request processed 
+                                         successfully.
+  
+          Other status means request failed     
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosModifyReq(tHalHandle hHal, 
+                                   sme_QosWmmTspecInfo * pQoSInfo,
+                                   v_U32_t QosFlowID);
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosReleaseReq() - The SME QoS API exposed to HDD to request for 
+  releasing a QoS flow running on a particular AC. This function should be 
+  called only if a QoS is set up with a valid FlowID. HDD sould invoke this 
+  API only if an explicit request for QoS release has come from Application 
+  
+  \param hHal - The handle returned by macOpen.
+  \param QosFlowID - Identification per flow running on each AC generated by SME 
+                     It is only meaningful if the QoS setup for the flow is 
+                     successful
+  
+  \return SME_QOS_STATUS_RELEASE_SUCCESS - Release request processed 
+                                           successfully.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosReleaseReq(tHalHandle hHal, v_U32_t QosFlowID);
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosIsTSInfoAckPolicyValid() - The SME QoS API exposed to HDD to 
+  check if TS info ack policy field can be set to "HT-immediate block acknowledgement" 
+  
+  \param pMac - The handle returned by macOpen.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info, provided by HDD
+  \param sessionId - sessionId returned by sme_OpenSession.
+  
+  \return VOS_TRUE - Current Association is HT association and so TS info ack policy
+                     can be set to "HT-immediate block acknowledgement"
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+v_BOOL_t sme_QosIsTSInfoAckPolicyValid(tpAniSirGlobal pMac,
+    sme_QosWmmTspecInfo * pQoSInfo,
+    v_U8_t sessionId);
+
+#endif //#if !defined( __SME_QOSAPI_H )
diff --git a/CORE/SME/inc/sme_RrmApi.h b/CORE/SME/inc/sme_RrmApi.h
new file mode 100644
index 0000000..9b105b2
--- /dev/null
+++ b/CORE/SME/inc/sme_RrmApi.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+
+#if !defined( __SMERRMAPI_H )
+#define __SMERRMAPI_H
+
+
+/**=========================================================================
+  
+  \file  sme_RrmApi.h
+  
+  \brief prototype for SME RRM APIs
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+
+/* $Header$ */
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#include "vos_lock.h"
+#include "vos_trace.h"
+#include "vos_memory.h"
+#include "vos_types.h"
+#include "aniGlobal.h"
+#include "sirApi.h"
+#include "smeInternal.h"
+#include "smeRrmInternal.h"
+
+
+//APIs
+eHalStatus sme_RrmMsgProcessor( tpAniSirGlobal pMac,  v_U16_t msg_type, 
+                                void *pMsgBuf);
+
+VOS_STATUS rrmClose (tpAniSirGlobal pMac);
+VOS_STATUS rrmReady (tpAniSirGlobal pMac);
+VOS_STATUS rrmOpen (tpAniSirGlobal pMac);
+VOS_STATUS rrmChangeDefaultConfigParam(tpAniSirGlobal pMac, tpRrmConfigParam pRrmConfig);
+VOS_STATUS sme_RrmNeighborReportRequest(tpAniSirGlobal pMac, tANI_U8 sessionId, tpRrmNeighborReq pNeighborReq, tpRrmNeighborRspCallbackInfo callbackInfo);
+
+tRrmNeighborReportDesc* smeRrmGetFirstBssEntryFromNeighborCache( tpAniSirGlobal pMac);
+tRrmNeighborReportDesc* smeRrmGetNextBssEntryFromNeighborCache( tpAniSirGlobal pMac, tpRrmNeighborReportDesc pBssEntry);
+
+
+#endif
diff --git a/CORE/SME/inc/smsDebug.h b/CORE/SME/inc/smsDebug.h
new file mode 100644
index 0000000..9d91493
--- /dev/null
+++ b/CORE/SME/inc/smsDebug.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+
+  
+    \file cssDebug.h
+  
+    Define debug log interface for SMS.
+  
+   Copyright (C) 2006 Airgo Networks, Incorporated
+ 
+   ========================================================================== */
+   
+#ifndef SMS_DEBUG_H__
+#define SMS_DEBUG_H__
+
+//#include <stdio.h>
+//#include <stdarg.h>
+
+#include "utilsApi.h"
+#include "sirDebug.h"
+
+void smsLog(tpAniSirGlobal pMac, tANI_U32 loglevel, const char *pString,...); 
+
+#endif // __HAL_DEBUG_H__
diff --git a/CORE/SME/inc/wlan_ps_wow_diag.h b/CORE/SME/inc/wlan_ps_wow_diag.h
new file mode 100644
index 0000000..0291923
--- /dev/null
+++ b/CORE/SME/inc/wlan_ps_wow_diag.h
@@ -0,0 +1,140 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+#ifndef _WLAN_PS_WOW_DIAG_H_
+#define _WLAN_PS_WOW_DIAG_H_
+
+
+#include "vos_diag_core_event.h"
+#include "vos_diag_core_log.h"
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT 
+
+typedef enum
+{
+   WLAN_BMPS_ENTER_REQ =0,
+   WLAN_UAPSD_START_REQ =1,
+   WLAN_UAPSD_STOP_REQ =2,
+   WLAN_ENTER_STANDBY_REQ =3,
+   WLAN_ENTER_DEEP_SLEEP_REQ =4,
+   WLAN_START_BMPS_AUTO_TIMER_REQ =5,
+   WLAN_STOP_BMPS_AUTO_TIMER_REQ =6,
+   WLAN_IMPS_ENTER_REQ =7,
+   WLAN_ENTER_FULL_POWER_REQ =8,
+   WLAN_PMC_CURRENT_STATE =9,
+   WLAN_PS_MODE_ENABLE_REQ =10,
+   WLAN_PS_MODE_DISABLE_REQ =11,
+   WLAN_WINMOB_D_POWER_STATE =12,
+   WLAN_BMPS_DTIM_PERIOD =13,
+   WLAN_BMPS_FINAL_LI =14,
+   WLAN_BMPS_SET_CONFIG =15,
+
+} wlan_ps_evt_subtype_t;
+
+// maps directly to eRequestFullPowerReason
+typedef enum
+{
+   WLAN_MISSED_BEACON_IND_RCVD,    /* PE received a MAX_MISSED_BEACON_IND */
+   WLAN_BMPS_STATUS_IND_RCVD,      /* PE received a SIR_HAL_BMPS_STATUS_IND */
+   WLAN_BMPS_MODE_DISABLED,        /* BMPS mode was disabled by HDD in SME */
+   WLAN_LINK_DISCONNECTED_BY_HDD,  /* Link has been disconnected requested by HDD */
+   WLAN_LINK_DISCONNECTED_BY_OTHER,/* Disconnect due to linklost or requested by peer */
+   WLAN_FULL_PWR_NEEDED_BY_HDD,    /* HDD request full power for some reason */
+   WLAN_FULL_PWR_NEEDED_BY_BAP,    /* BAP request full power for BT_AMP */
+   WLAN_FULL_PWR_NEEDED_BY_CSR,    /* CSR requests full power */
+   WLAN_FULL_PWR_NEEDED_BY_QOS,    /* QOS requests full power */
+   WLAN_REASON_OTHER               /* No specific reason. General reason code */ 
+
+} wlan_ps_full_power_request_reason_t;
+
+// maps directly to ePmcState
+typedef enum 
+{
+   WLAN_PMC_STOPPED, /* PMC is stopped */
+   WLAN_PMC_FULL_POWER, /* full power */
+   WLAN_PMC_LOW_POWER, /* low power */
+   WLAN_PMC_REQUEST_IMPS,  /* requesting IMPS */
+   WLAN_PMC_IMPS,  /* in IMPS */
+   WLAN_PMC_REQUEST_BMPS,  /* requesting BMPS */
+   WLAN_PMC_BMPS,  /* in BMPS */
+   WLAN_PMC_REQUEST_FULL_POWER,  /* requesting full power */
+   WLAN_PMC_REQUEST_START_UAPSD,  /* requesting Start UAPSD */
+   WLAN_PMC_REQUEST_STOP_UAPSD,  /* requesting Stop UAPSD */
+   WLAN_PMC_UAPSD,           /* in UAPSD */
+   WLAN_PMC_REQUEST_STANDBY,  /* requesting standby mode */
+   WLAN_PMC_STANDBY,  /* in standby mode */
+   WLAN_PMC_REQUEST_ENTER_WOWL, /* requesting enter WOWL */
+   WLAN_PMC_REQUEST_EXIT_WOWL,  /* requesting exit WOWL */
+   WLAN_PMC_WOWL                /* Chip in WOWL mode */
+
+} wlan_ps_pmc_current_state_t;
+
+// maps directly to ePmcPowerSavingMode
+typedef enum
+{
+   WLAN_IDLE_MODE_POWER_SAVE,  /* Idle Mode Power Save (IMPS) */
+   WLAN_BEACON_MODE_POWER_SAVE,  /* Beacon Mode Power Save (BMPS) */
+   WLAN_SPATIAL_MULTIPLEX_POWER_SAVE,  /* Spatial Multiplexing Power Save (SMPS) */
+   WLAN_UAPSD_MODE_POWER_SAVE,  /* Unscheduled Automatic Power Save Delivery Mode */
+   WLAN_STANDBY_MODE_POWER_SAVE,  /* Standby Power Save Mode */
+   WLAN_WOWL_MODE_POWER_SAVE  /* Wake-on-Wireless LAN Power Save Mode */
+
+} wlan_ps_enable_disable_ps_mode_t;
+
+typedef enum
+{
+   WLAN_D0,
+   WLAN_D1,
+   WLAN_D2,
+   WLAN_D3,
+   WLAN_D4
+
+} wlan_ps_winmob_d_power_state_t;
+
+typedef enum
+{
+   WLAN_WOW_ENTER_REQ =0,
+   WLAN_WOW_EXIT_REQ =1,
+   WLAN_WOW_DEL_PTRN_REQ =2,
+   WLAN_WOW_WAKEUP = 3
+
+} wlan_ps_wow_evt_subtype_t;
+
+typedef enum
+{
+   WLAN_WOW_TYPE_NONE,
+   WLAN_WOW_TYPE_MAGIC_PKT_ONLY,
+   WLAN_WOW_TYPE_PTRN_BYTE_MATCH_ONLY,
+   WLAN_WOW_TYPE_MAGIC_PKT_PTRN_BYTE_MATCH,
+
+} wlan_ps_wow_type_t;
+
+typedef enum
+{
+   WLAN_WOW_MAGIC_PKT_MATCH,
+   WLAN_WOW_PTRN_BYTE_MATCH
+
+} wlan_ps_wos_wakeup_cause_t;
+
+#endif // FEATURE_WLAN_DIAG_SUPPORT
+
+#endif // _WLAN_PS_WOW_DIAG_H_
+
diff --git a/CORE/SME/src/QoS/sme_Qos.c b/CORE/SME/src/QoS/sme_Qos.c
new file mode 100644
index 0000000..7729594
--- /dev/null
+++ b/CORE/SME/src/QoS/sme_Qos.c
@@ -0,0 +1,7890 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/**=========================================================================
+  
+  \file  sme_Qos.c
+  
+  \brief implementation for SME QoS APIs
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+/* $Header$ */
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halInternal.h" //Check if the below include of aniGobal.h is sufficient for Volans too.
+#endif
+
+#ifdef FEATURE_WLAN_INTEGRATED_SOC
+#include "aniGlobal.h"
+#endif
+
+#include "smeInside.h"
+#include "vos_diag_core_event.h"
+#include "vos_diag_core_log.h"
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+#include "smsDebug.h"
+#include "utilsParser.h"
+#endif
+#ifdef FEATURE_WLAN_CCX
+#include <csrCcx.h>
+#endif
+
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+/* TODO : 6Mbps as Cisco APs seem to like only this value; analysis req.   */
+#define SME_QOS_MIN_PHY_RATE         0x5B8D80    
+#define SME_QOS_SURPLUS_BW_ALLOWANCE  0x2000     /* Ratio of 1.0           */
+/*---------------------------------------------------------------------------
+  Max values to bound tspec params against and avoid rollover
+---------------------------------------------------------------------------*/
+#define SME_QOS_32BIT_MAX  0xFFFFFFFF
+#define SME_QOS_16BIT_MAX  0xFFFF
+#define SME_QOS_16BIT_MSB  0x8000
+/*---------------------------------------------------------------------------
+  Adds y to x, but saturates at 32-bit max to avoid rollover
+---------------------------------------------------------------------------*/
+#define SME_QOS_BOUNDED_U32_ADD_Y_TO_X( _x, _y )                            \
+  do                                                                        \
+  {                                                                         \
+    (_x) = ( (SME_QOS_32BIT_MAX-(_x))<(_y) ) ?                              \
+    (SME_QOS_32BIT_MAX) : (_x)+(_y);                                        \
+  } while(0)
+/*---------------------------------------------------------------------------
+  As per WMM spec there could be max 2 TSPEC running on the same AC with 
+  different direction. We will refer each TSPEC with an index
+---------------------------------------------------------------------------*/
+#define SME_QOS_TSPEC_INDEX_0            0
+#define SME_QOS_TSPEC_INDEX_1            1
+#define SME_QOS_TSPEC_INDEX_MAX          2
+#define SME_QOS_TSPEC_MASK_BIT_1_SET     1
+#define SME_QOS_TSPEC_MASK_BIT_2_SET     2
+#define SME_QOS_TSPEC_MASK_BIT_1_2_SET   3
+#define SME_QOS_TSPEC_MASK_CLEAR         0
+
+//which key to search on, in the flowlist (1 = flowID, 2 = AC, 4 = reason)
+#define SME_QOS_SEARCH_KEY_INDEX_1       1
+#define SME_QOS_SEARCH_KEY_INDEX_2       2
+#define SME_QOS_SEARCH_KEY_INDEX_3       4
+#define SME_QOS_SEARCH_KEY_INDEX_4       8  // ac + direction
+#define SME_QOS_SEARCH_KEY_INDEX_5       0x10  // ac + tspec_mask
+//special value for searching any Session Id
+#define SME_QOS_SEARCH_SESSION_ID_ANY    CSR_ROAM_SESSION_MAX
+#define SME_QOS_ACCESS_POLICY_EDCA       1
+#define SME_QOS_MAX_TID                  255
+#define SME_QOS_TSPEC_IE_LENGTH          61
+#define SME_QOS_TSPEC_IE_TYPE            2
+#define SME_QOS_MIN_FLOW_ID              1
+#define SME_QOS_MAX_FLOW_ID              0xFFFFFFFE
+#define SME_QOS_INVALID_FLOW_ID          0xFFFFFFFF
+// per the WMM Specification v1.2 Section 2.2.10
+// The Dialog Token field shall be set [...] to a non-zero value
+#define SME_QOS_MIN_DIALOG_TOKEN         1
+#define SME_QOS_MAX_DIALOG_TOKEN         0xFF
+/*-------------------------------------------------------------------------- 
+  Type declarations
+  ------------------------------------------------------------------------*/
+/*---------------------------------------------------------------------------
+   Enumeration of the various states in the QoS state m/c
+---------------------------------------------------------------------------*/
+typedef enum
+{
+   SME_QOS_CLOSED = 0,
+   SME_QOS_INIT,
+   SME_QOS_LINK_UP,
+   SME_QOS_REQUESTED,
+   SME_QOS_QOS_ON,
+   SME_QOS_HANDOFF,
+   
+}sme_QosStates;
+/*---------------------------------------------------------------------------
+   Enumeration of the various QoS cmds 
+---------------------------------------------------------------------------*/
+typedef enum
+{
+   SME_QOS_SETUP_REQ = 0,
+   SME_QOS_RELEASE_REQ,
+   SME_QOS_MODIFY_REQ,
+   SME_QOS_RESEND_REQ,
+   SME_QOS_CMD_MAX
+}sme_QosCmdType;
+/*---------------------------------------------------------------------------
+   Enumeration of the various QoS reason codes to be used in the Flow list 
+---------------------------------------------------------------------------*/
+typedef enum
+{
+   SME_QOS_REASON_SETUP = 0,
+   SME_QOS_REASON_RELEASE,
+   SME_QOS_REASON_MODIFY,
+   SME_QOS_REASON_MODIFY_PENDING,
+   SME_QOS_REASON_REQ_SUCCESS,
+   SME_QOS_REASON_MAX
+}sme_QosReasonType;
+
+/*---------------------------------------------------------------------------
+  Table to map user priority passed in as an argument to appropriate Access 
+  Category as specified in 802.11e/WMM
+---------------------------------------------------------------------------*/
+sme_QosEdcaAcType sme_QosUPtoACMap[SME_QOS_WMM_UP_MAX] = 
+{
+   SME_QOS_EDCA_AC_BE, /* User Priority 0 */
+   SME_QOS_EDCA_AC_BK, /* User Priority 1 */
+   SME_QOS_EDCA_AC_BK, /* User Priority 2 */
+   SME_QOS_EDCA_AC_BE, /* User Priority 3 */
+   SME_QOS_EDCA_AC_VI, /* User Priority 4 */
+   SME_QOS_EDCA_AC_VI, /* User Priority 5 */
+   SME_QOS_EDCA_AC_VO, /* User Priority 6 */
+   SME_QOS_EDCA_AC_VO  /* User Priority 7 */
+};
+
+/*---------------------------------------------------------------------------
+  Table to map access category (AC) to appropriate user priority as specified
+  in 802.11e/WMM
+  Note: there is a quantization loss here because 4 ACs are mapped to 8 UPs
+  Mapping is done for consistency
+---------------------------------------------------------------------------*/
+sme_QosWmmUpType sme_QosACtoUPMap[SME_QOS_EDCA_AC_MAX] = 
+{
+   SME_QOS_WMM_UP_BE,   /* AC BE */
+   SME_QOS_WMM_UP_BK,   /* AC BK */
+   SME_QOS_WMM_UP_VI,   /* AC VI */
+   SME_QOS_WMM_UP_VO    /* AC VO */
+};
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's FLOW Link List structure. This list can hold information per 
+  flow/request, like TSPEC params requested, which AC it is running on 
+---------------------------------------------------------------------------*/
+typedef struct sme_QosFlowInfoEntry_s
+{
+    tListElem             link;  /* list links */
+    v_U8_t                sessionId;
+    v_U8_t                tspec_mask;
+    sme_QosReasonType     reason;
+    v_U32_t               QosFlowID;
+    sme_QosEdcaAcType     ac_type;
+    sme_QosWmmTspecInfo   QoSInfo;
+    void                * HDDcontext;
+    sme_QosCallback       QoSCallback;
+    v_BOOL_t              hoRenewal;//set to TRUE while re-negotiating flows after
+                                     //handoff, will set to FALSE once done with
+                                     //the process. Helps SME to decide if at all 
+                                     //to notify HDD/LIS for flow renewal after HO
+} sme_QosFlowInfoEntry;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's setup request cmd related information structure. 
+---------------------------------------------------------------------------*/
+typedef struct sme_QosSetupCmdInfo_s
+{
+    v_U32_t               QosFlowID;
+    sme_QosWmmTspecInfo   QoSInfo;
+    void                 *HDDcontext;
+    sme_QosCallback       QoSCallback;
+    sme_QosWmmUpType      UPType;
+    v_BOOL_t              hoRenewal;//set to TRUE while re-negotiating flows after
+                                     //handoff, will set to FALSE once done with
+                                     //the process. Helps SME to decide if at all 
+                                     //to notify HDD/LIS for flow renewal after HO
+} sme_QosSetupCmdInfo;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's modify cmd related information structure. 
+---------------------------------------------------------------------------*/
+typedef struct sme_QosModifyCmdInfo_s
+{
+    v_U32_t               QosFlowID;
+    sme_QosEdcaAcType     ac;
+    sme_QosWmmTspecInfo   QoSInfo;
+} sme_QosModifyCmdInfo;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's resend cmd related information structure. 
+---------------------------------------------------------------------------*/
+typedef struct sme_QosResendCmdInfo_s
+{
+    v_U8_t                tspecMask;
+    sme_QosEdcaAcType     ac;
+    sme_QosWmmTspecInfo   QoSInfo;
+} sme_QosResendCmdInfo;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's release cmd related information structure. 
+---------------------------------------------------------------------------*/
+typedef struct sme_QosReleaseCmdInfo_s
+{
+    v_U32_t               QosFlowID;
+} sme_QosReleaseCmdInfo;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's buffered cmd related information structure. 
+---------------------------------------------------------------------------*/
+typedef struct sme_QosCmdInfo_s
+{
+    sme_QosCmdType        command;
+    tpAniSirGlobal        pMac;
+    v_U8_t                sessionId;
+    union
+    {
+       sme_QosSetupCmdInfo    setupCmdInfo;
+       sme_QosModifyCmdInfo   modifyCmdInfo;
+       sme_QosResendCmdInfo   resendCmdInfo;
+       sme_QosReleaseCmdInfo  releaseCmdInfo;
+    }u;
+} sme_QosCmdInfo;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's buffered cmd List structure. This list can hold information 
+  related to any pending cmd from HDD
+---------------------------------------------------------------------------*/
+typedef struct sme_QosCmdInfoEntry_s
+{
+    tListElem             link;  /* list links */
+    sme_QosCmdInfo        cmdInfo;
+} sme_QosCmdInfoEntry;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's Per AC information structure. This can hold information on
+  how many flows running on the AC, the current, previous states the AC is in 
+---------------------------------------------------------------------------*/
+typedef struct sme_QosACInfo_s
+{
+   v_U8_t                 num_flows[SME_QOS_TSPEC_INDEX_MAX];
+   sme_QosStates          curr_state;
+   sme_QosStates          prev_state;
+   sme_QosWmmTspecInfo    curr_QoSInfo[SME_QOS_TSPEC_INDEX_MAX];
+   sme_QosWmmTspecInfo    requested_QoSInfo[SME_QOS_TSPEC_INDEX_MAX];
+   v_BOOL_t               reassoc_pending;//reassoc requested for APSD
+   //As per WMM spec there could be max 2 TSPEC running on the same AC with 
+   //different direction. We will refer each TSPEC with an index
+   v_U8_t                 tspec_mask_status; //status showing if both the indices are in use
+   v_U8_t                 tspec_pending;//tspec negotiation going on for which index
+   v_BOOL_t               hoRenewal;//set to TRUE while re-negotiating flows after
+                                    //handoff, will set to FALSE once done with
+                                    //the process. Helps SME to decide if at all 
+                                    //to notify HDD/LIS for flow renewal after HO
+#ifdef WLAN_FEATURE_VOWIFI_11R
+   v_U8_t                 ricIdentifier[SME_QOS_TSPEC_INDEX_MAX];
+   /* stores the ADD TS response for each AC. The ADD TS response is formed by
+   parsing the RIC received in the the reassoc response */
+   tSirAddtsRsp           addTsRsp[SME_QOS_TSPEC_INDEX_MAX];
+#endif
+
+} sme_QosACInfo;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's Per session information structure. This can hold information
+  on the state of the session
+---------------------------------------------------------------------------*/
+typedef struct sme_QosSessionInfo_s
+{
+   // what is this entry's session id
+   v_U8_t                 sessionId;
+   // is the session currently active
+   v_BOOL_t               sessionActive;
+   // All AC info for this session
+   sme_QosACInfo          ac_info[SME_QOS_EDCA_AC_MAX];
+   // Bitmask of the ACs with APSD on 
+   // Bit0:VO; Bit1:VI; Bit2:BK; Bit3:BE all other bits are ignored
+   v_U8_t                 apsdMask;
+   // association information for this session
+   sme_QosAssocInfo       assocInfo;
+   // ID assigned to our reassoc request
+   v_U32_t                roamID;
+   // maintaining a powersave status in QoS module, to be fed back to PMC at 
+   // times through the sme_QosPmcCheckRoutine
+   v_BOOL_t               readyForPowerSave;
+   // are we in the process of handing off to a different AP
+   v_BOOL_t               handoffRequested;
+   // following reassoc or AddTS has UAPSD already been requested from PMC
+   v_BOOL_t               uapsdAlreadyRequested;
+   // commands that are being buffered for this session
+   tDblLinkList           bufferedCommandList;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+   v_BOOL_t               ftHandoffInProgress;
+#endif
+
+} sme_QosSessionInfo;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  Search key union. We can use the flowID, ac type, or reason to find an entry 
+  in the flow list
+---------------------------------------------------------------------------*/
+typedef union sme_QosSearchKey_s
+{
+   v_U32_t               QosFlowID;
+   sme_QosEdcaAcType     ac_type;
+   sme_QosReasonType     reason;
+}sme_QosSearchKey;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  We can either use the flowID or the ac type to find an entry in the flow list.
+  The index is a bitmap telling us which key to use. Starting from LSB,
+  bit 0 - Flow ID
+  bit 1 - AC type
+---------------------------------------------------------------------------*/
+typedef struct sme_QosSearchInfo_s
+{
+   v_U8_t           sessionId;
+   v_U8_t           index;
+   sme_QosSearchKey key;
+   sme_QosWmmDirType   direction;
+   v_U8_t              tspec_mask;
+}sme_QosSearchInfo;
+/*---------------------------------------------------------------------------
+DESCRIPTION
+  SME QoS module's internal control block.
+---------------------------------------------------------------------------*/
+struct sme_QosCb_s
+{
+   //global Mac pointer
+   tpAniSirGlobal   pMac;
+   //All Session Info
+   sme_QosSessionInfo     sessionInfo[CSR_ROAM_SESSION_MAX];
+   //All FLOW info
+   tDblLinkList           flow_list;
+   //default TSPEC params
+   sme_QosWmmTspecInfo    def_QoSInfo[SME_QOS_EDCA_AC_MAX];
+   //counter for assigning Flow IDs
+   v_U32_t                nextFlowId;
+   //counter for assigning Dialog Tokens
+   v_U8_t                nextDialogToken;
+}sme_QosCb;
+typedef eHalStatus (*sme_QosProcessSearchEntry)(tpAniSirGlobal pMac, tListElem *pEntry);
+/*-------------------------------------------------------------------------- 
+                         Internal function declarations
+  ------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosInternalSetupReq(tpAniSirGlobal pMac, 
+                                          v_U8_t sessionId,
+                                          sme_QosWmmTspecInfo * pQoSInfo,
+                                          sme_QosCallback QoSCallback, 
+                                          void * HDDcontext,
+                                          sme_QosWmmUpType UPType, 
+                                          v_U32_t QosFlowID,
+                                          v_BOOL_t buffered_cmd,
+                                          v_BOOL_t hoRenewal);
+sme_QosStatusType sme_QosInternalModifyReq(tpAniSirGlobal pMac, 
+                                           sme_QosWmmTspecInfo * pQoSInfo,
+                                           v_U32_t QosFlowID,
+                                           v_BOOL_t buffered_cmd);
+sme_QosStatusType sme_QosInternalReleaseReq(tpAniSirGlobal pMac, 
+                                            v_U32_t QosFlowID,
+                                            v_BOOL_t buffered_cmd);
+sme_QosStatusType sme_QosSetup(tpAniSirGlobal pMac,
+                               v_U8_t sessionId,
+                               sme_QosWmmTspecInfo *pTspec_Info, 
+                               sme_QosEdcaAcType ac);
+eHalStatus sme_QosAddTsReq(tpAniSirGlobal pMac,
+                           v_U8_t sessionId,
+                           sme_QosWmmTspecInfo * pTspec_Info,
+                           sme_QosEdcaAcType ac);
+eHalStatus sme_QosDelTsReq(tpAniSirGlobal pMac,
+                           v_U8_t sessionId,
+                           sme_QosEdcaAcType ac,
+                           v_U8_t tspec_mask);
+eHalStatus sme_QosProcessAddTsRsp(tpAniSirGlobal pMac, void *pMsgBuf);
+eHalStatus sme_QosProcessDelTsInd(tpAniSirGlobal pMac, void *pMsgBuf);
+eHalStatus sme_QosProcessDelTsRsp(tpAniSirGlobal pMac, void *pMsgBuf);
+eHalStatus sme_QosProcessAssocCompleteEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessReassocReqEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessReassocSuccessEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessReassocFailureEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessDisconnectEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessJoinReqEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessHandoffAssocReqEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessHandoffSuccessEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessHandoffFailureEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+#ifdef WLAN_FEATURE_VOWIFI_11R
+eHalStatus sme_QosProcessPreauthSuccessInd(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessSetKeySuccessInd(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info);
+eHalStatus sme_QosProcessAggrQosRsp(tpAniSirGlobal pMac, void *pMsgBuf);
+eHalStatus sme_QosFTAggrQosReq( tpAniSirGlobal pMac, v_U8_t sessionId );
+#endif
+eHalStatus sme_QosProcessAddTsSuccessRsp(tpAniSirGlobal pMac, 
+                                         v_U8_t sessionId,
+                                         tSirAddtsRspInfo * pRsp);
+eHalStatus sme_QosProcessAddTsFailureRsp(tpAniSirGlobal pMac, 
+                                         v_U8_t sessionId,
+                                         tSirAddtsRspInfo * pRsp);
+eHalStatus sme_QosAggregateParams(
+   sme_QosWmmTspecInfo * pInput_Tspec_Info,
+   sme_QosWmmTspecInfo * pCurrent_Tspec_Info,
+   sme_QosWmmTspecInfo * pUpdated_Tspec_Info);
+static eHalStatus sme_QosUpdateParams(v_U8_t sessionId,
+                                      sme_QosEdcaAcType ac,
+                                      v_U8_t tspec_mask, 
+                                      sme_QosWmmTspecInfo * pTspec_Info);
+sme_QosWmmUpType sme_QosAcToUp(sme_QosEdcaAcType ac);
+sme_QosEdcaAcType sme_QosUpToAc(sme_QosWmmUpType up);
+v_BOOL_t sme_QosIsACM(tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc, 
+                      sme_QosEdcaAcType ac, tDot11fBeaconIEs *pIes);
+tListElem *sme_QosFindInFlowList(sme_QosSearchInfo search_key);
+eHalStatus sme_QosFindAllInFlowList(tpAniSirGlobal pMac,
+                                    sme_QosSearchInfo search_key, 
+                                    sme_QosProcessSearchEntry fnp);
+static void sme_QosStateTransition(v_U8_t sessionId,
+                                   sme_QosEdcaAcType ac,
+                                   sme_QosStates new_state);
+eHalStatus sme_QosBufferCmd(sme_QosCmdInfo *pcmd, v_BOOL_t insert_head);
+static eHalStatus sme_QosProcessBufferedCmd(v_U8_t sessionId);
+eHalStatus sme_QosSaveAssocInfo(sme_QosSessionInfo *pSession, sme_QosAssocInfo *pAssoc_info);
+eHalStatus sme_QosSetupFnp(tpAniSirGlobal pMac, tListElem *pEntry);
+eHalStatus sme_QosModificationNotifyFnp(tpAniSirGlobal pMac, tListElem *pEntry);
+eHalStatus sme_QosModifyFnp(tpAniSirGlobal pMac, tListElem *pEntry);
+eHalStatus sme_QosDelTsIndFnp(tpAniSirGlobal pMac, tListElem *pEntry);
+eHalStatus sme_QosReassocSuccessEvFnp(tpAniSirGlobal pMac, tListElem *pEntry);
+eHalStatus sme_QosAddTsFailureFnp(tpAniSirGlobal pMac, tListElem *pEntry);
+eHalStatus sme_QosAddTsSuccessFnp(tpAniSirGlobal pMac, tListElem *pEntry);
+static v_BOOL_t sme_QosIsRspPending(v_U8_t sessionId, sme_QosEdcaAcType ac);
+static v_BOOL_t sme_QosIsUapsdActive(void);
+void sme_QosPmcFullPowerCallback(void *callbackContext, eHalStatus status);
+void sme_QosPmcStartUapsdCallback(void *callbackContext, eHalStatus status);
+v_BOOL_t sme_QosPmcCheckRoutine(void *callbackContext);
+void sme_QosPmcDeviceStateUpdateInd(void *callbackContext, tPmcState pmcState);
+eHalStatus sme_QosProcessOutOfUapsdMode(tpAniSirGlobal pMac);
+eHalStatus sme_QosProcessIntoUapsdMode(tpAniSirGlobal pMac);
+static eHalStatus sme_QosBufferExistingFlows(tpAniSirGlobal pMac,
+                                             v_U8_t sessionId);
+static eHalStatus sme_QosDeleteExistingFlows(tpAniSirGlobal pMac,
+                                             v_U8_t sessionId);
+static void sme_QosCleanupCtrlBlkForHandoff(tpAniSirGlobal pMac,
+                                            v_U8_t sessionId);
+static eHalStatus sme_QosDeleteBufferedRequests(tpAniSirGlobal pMac,
+                                                v_U8_t sessionId);
+v_BOOL_t sme_QosValidateRequestedParams(tpAniSirGlobal pMac,
+    sme_QosWmmTspecInfo * pQoSInfo,
+    v_U8_t sessionId);
+
+extern eHalStatus sme_AcquireGlobalLock( tSmeStruct *psSme);
+extern eHalStatus sme_ReleaseGlobalLock( tSmeStruct *psSme);
+static eHalStatus qosIssueCommand( tpAniSirGlobal pMac, v_U8_t sessionId,
+                                   eSmeCommandType cmdType, sme_QosWmmTspecInfo * pQoSInfo,
+                                   sme_QosEdcaAcType ac, v_U8_t tspec_mask );
+/*
+    sme_QosReRequestAddTS to re-send AddTS for the combined QoS request
+*/
+static sme_QosStatusType sme_QosReRequestAddTS(tpAniSirGlobal pMac,
+                                               v_U8_t sessionId,
+                                               sme_QosWmmTspecInfo * pQoSInfo,
+                                               sme_QosEdcaAcType ac,
+                                               v_U8_t tspecMask);
+static void sme_QosInitACs(tpAniSirGlobal pMac, v_U8_t sessionId);
+static eHalStatus sme_QosRequestReassoc(tpAniSirGlobal pMac, tANI_U8 sessionId,
+                                        tCsrRoamModifyProfileFields *pModFields,
+                                        v_BOOL_t fForce );
+static v_U32_t sme_QosAssignFlowId(void);
+static v_U8_t sme_QosAssignDialogToken(void);
+static eHalStatus sme_QosUpdateTspecMask(v_U8_t sessionId,
+                                      sme_QosSearchInfo search_key,
+                                      v_U8_t new_tspec_mask);
+/*-------------------------------------------------------------------------- 
+                         External APIs definitions
+  ------------------------------------------------------------------------*/
+/* --------------------------------------------------------------------------
+    \brief sme_QosOpen() - This function must be called before any API call to 
+    SME QoS module.
+    \param pMac - Pointer to the global MAC parameter structure.
+    
+    \return eHalStatus     
+----------------------------------------------------------------------------*/
+eHalStatus sme_QosOpen(tpAniSirGlobal pMac)
+{
+   sme_QosSessionInfo *pSession;
+   v_U8_t sessionId;
+   eHalStatus status;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: initializing SME-QoS module",
+             __FUNCTION__, __LINE__);
+   //init the control block
+   //(note that this will make all sessions invalid)
+   vos_mem_zero(&sme_QosCb, sizeof(sme_QosCb));
+   sme_QosCb.pMac = pMac;
+   sme_QosCb.nextFlowId = SME_QOS_MIN_FLOW_ID;
+   sme_QosCb.nextDialogToken = SME_QOS_MIN_DIALOG_TOKEN;
+   //init flow list
+   status = csrLLOpen(pMac->hHdd, &sme_QosCb.flow_list);
+   if (!HAL_STATUS_SUCCESS(status))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,
+                "%s: %d: cannot initialize Flow List",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   
+   for (sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; ++sessionId)
+   {
+      pSession = &sme_QosCb.sessionInfo[sessionId];
+      pSession->sessionId = sessionId;
+      // initialize the session's per-AC information
+      sme_QosInitACs(pMac, sessionId);
+      // initialize the session's buffered command list
+      status = csrLLOpen(pMac->hHdd, &pSession->bufferedCommandList);
+      if (!HAL_STATUS_SUCCESS(status))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,
+                   "%s: %d: cannot initialize cmd list for session %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId);
+         return eHAL_STATUS_FAILURE;
+      }
+      pSession->readyForPowerSave = VOS_TRUE;
+   }
+   //the routine registered here gets called by PMC whenever the device is about 
+   //to enter one of the power save modes. PMC runs a poll with all the 
+   //registered modules if device can enter powersave mode or remain full power
+   if(!HAL_STATUS_SUCCESS(
+      pmcRegisterPowerSaveCheck(pMac, sme_QosPmcCheckRoutine, pMac)))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,
+                "%s: %d: cannot register with pmcRegisterPowerSaveCheck()",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   //the routine registered here gets called by PMC whenever there is a device 
+   // state change. PMC might go to full power because of many reasons and this 
+   // is the way for PMC to inform all the other registered modules so that 
+   // everyone is in sync.
+   if(!HAL_STATUS_SUCCESS(
+      pmcRegisterDeviceStateUpdateInd(pMac, sme_QosPmcDeviceStateUpdateInd, pMac)))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,
+                "%s: %d: cannot register with pmcRegisterDeviceStateUpdateInd()",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: done initializing SME-QoS module",
+             __FUNCTION__, __LINE__);
+   return eHAL_STATUS_SUCCESS;
+}
+/* --------------------------------------------------------------------------
+    \brief sme_QosClose() - To close down SME QoS module. There should not be 
+    any API call into this module after calling this function until another
+    call of sme_QosOpen.
+    \param pMac - Pointer to the global MAC parameter structure.
+    
+    \return eHalStatus     
+----------------------------------------------------------------------------*/
+eHalStatus sme_QosClose(tpAniSirGlobal pMac)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosEdcaAcType ac;
+   v_U8_t sessionId;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: closing down SME-QoS",
+             __FUNCTION__, __LINE__);
+   // deregister with PMC
+   if(!HAL_STATUS_SUCCESS(
+      pmcDeregisterDeviceStateUpdateInd(pMac, sme_QosPmcDeviceStateUpdateInd)))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,
+                "%s: %d: cannot deregister with pmcDeregisterDeviceStateUpdateInd()",
+                __FUNCTION__, __LINE__);
+   }
+   if(!HAL_STATUS_SUCCESS(
+      pmcDeregisterPowerSaveCheck(pMac, sme_QosPmcCheckRoutine)))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,
+                "%s: %d: cannot deregister with pmcDeregisterPowerSaveCheck()",
+                __FUNCTION__, __LINE__);
+   }
+   //cleanup control block
+   //close the flow list
+   csrLLClose(&sme_QosCb.flow_list);
+   // shut down all of the sessions
+   for(sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; ++sessionId)
+   {
+      pSession = &sme_QosCb.sessionInfo[sessionId];
+      if (pSession == NULL)
+            continue;
+
+       sme_QosInitACs(pMac, sessionId);
+       // this session doesn't require UAPSD
+       pSession->apsdMask = 0;
+
+       pSession->uapsdAlreadyRequested = VOS_FALSE;
+       pSession->handoffRequested = VOS_FALSE;
+       pSession->readyForPowerSave = VOS_TRUE;
+       pSession->roamID = 0;
+       //need to clean up buffered req
+       sme_QosDeleteBufferedRequests(pMac, sessionId);
+       //need to clean up flows
+       sme_QosDeleteExistingFlows(pMac, sessionId);
+
+       // Clean up the assoc info if already allocated
+       if (pSession->assocInfo.pBssDesc) {
+          vos_mem_free(pSession->assocInfo.pBssDesc);
+          pSession->assocInfo.pBssDesc = NULL;
+       }
+
+      // close the session's buffered command list
+      csrLLClose(&pSession->bufferedCommandList);
+      for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+      {
+         sme_QosStateTransition(sessionId, ac, SME_QOS_CLOSED);
+      }
+      pSession->sessionActive = VOS_FALSE;
+      pSession->readyForPowerSave = VOS_TRUE;
+   }
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: closed down QoS",
+             __FUNCTION__, __LINE__);
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosSetupReq() - The SME QoS API exposed to HDD to request for QoS 
+  on a particular AC. This function should be called after a link has been 
+  established, i.e. STA is associated with an AP etc. If the request involves 
+  admission control on the requested AC, HDD needs to provide the necessary 
+  Traffic Specification (TSPEC) parameters otherwise SME is going to use the
+  default params.
+  
+  \param hHal - The handle returned by macOpen.
+  \param sessionId - sessionId returned by sme_OpenSession.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info as defined above, provided by HDD
+  \param QoSCallback - The callback which is registered per flow while 
+                       requesting for QoS. Used for any notification for the 
+                       flow (i.e. setup success/failure/release) which needs to 
+                       be sent to HDD
+  \param HDDcontext - A cookie passed by HDD to be used by SME during any QoS 
+                      notification (through the callabck) to HDD 
+  \param UPType - Useful only if HDD or any other upper layer module (BAP etc.)
+                  looking for implicit QoS setup, in that 
+                  case, the pQoSInfo will be NULL & SME will know about the AC
+                  (from the UP provided in this param) QoS is requested on
+  \param pQosFlowID - Identification per flow running on each AC generated by 
+                      SME. 
+                     It is only meaningful if the QoS setup for the flow is 
+                     successful
+                  
+  \return eHAL_STATUS_SUCCESS - Setup is successful.
+  
+          Other status means Setup request failed     
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosSetupReq(tHalHandle hHal, tANI_U32 sessionId,
+                                  sme_QosWmmTspecInfo * pQoSInfo,
+                                  sme_QosCallback QoSCallback,
+                                  void * HDDcontext,
+                                  sme_QosWmmUpType UPType, v_U32_t * pQosFlowID)
+{
+   sme_QosSessionInfo *pSession;
+   eHalStatus lock_status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   sme_QosStatusType status;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: QoS Setup requested by client on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   lock_status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( !HAL_STATUS_SUCCESS( lock_status ) )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Unable to obtain lock",
+                __FUNCTION__, __LINE__);
+      return SME_QOS_STATUS_SETUP_FAILURE_RSP;
+   }
+   //Make sure the session is valid
+   if (!CSR_IS_SESSION_VALID( pMac, sessionId ))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Supplied Session ID %d is invalid",
+                __FUNCTION__, __LINE__,
+                sessionId);
+      status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+   }
+   else
+   {
+      //Make sure the session is active
+      pSession = &sme_QosCb.sessionInfo[sessionId];
+      if (!pSession->sessionActive)
+      { 
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: Supplied Session ID %d is inactive",
+                   __FUNCTION__, __LINE__,
+                   sessionId);
+         status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+      }
+      else
+      {
+         //Assign a Flow ID
+         *pQosFlowID = sme_QosAssignFlowId();
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: QoS request on session %d assigned Flow ID %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId, *pQosFlowID);
+         //Call the internal function for QoS setup,
+         // adding a layer of abstraction
+         status = sme_QosInternalSetupReq(pMac, (v_U8_t)sessionId, pQoSInfo,
+                                          QoSCallback, HDDcontext, UPType,
+                                          *pQosFlowID, VOS_FALSE, VOS_FALSE);
+      }
+   }
+   sme_ReleaseGlobalLock( &pMac->sme );
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: QoS setup return status on session %d is %d",
+             __FUNCTION__, __LINE__,
+             sessionId, status);
+   return status;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosModifyReq() - The SME QoS API exposed to HDD to request for 
+  modification of certain QoS params on a flow running on a particular AC. 
+  This function should be called after a link has been established, i.e. STA is 
+  associated with an AP etc. & a QoS setup has been succesful for that flow. 
+  If the request involves admission control on the requested AC, HDD needs to 
+  provide the necessary Traffic Specification (TSPEC) parameters & SME might
+  start the renegotiation process through ADDTS.
+  
+  \param hHal - The handle returned by macOpen.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info as defined above, provided by HDD
+  \param QosFlowID - Identification per flow running on each AC generated by 
+                      SME. 
+                     It is only meaningful if the QoS setup for the flow has 
+                     been successful already
+                  
+  \return SME_QOS_STATUS_SETUP_SUCCESS_RSP - Modification is successful.
+  
+          Other status means request failed     
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosModifyReq(tHalHandle hHal, 
+                                   sme_QosWmmTspecInfo * pQoSInfo,
+                                   v_U32_t QosFlowID)
+{
+   eHalStatus lock_status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   sme_QosStatusType status;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: QoS Modify requested by client for Flow %d",
+             __FUNCTION__, __LINE__,
+             QosFlowID);
+   lock_status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( !HAL_STATUS_SUCCESS( lock_status ) )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Unable to obtain lock",
+                __FUNCTION__, __LINE__);
+      return SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+   }
+   //Call the internal function for QoS modify, adding a layer of abstraction
+   status = sme_QosInternalModifyReq(pMac, pQoSInfo, QosFlowID, VOS_FALSE);
+   sme_ReleaseGlobalLock( &pMac->sme );
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: QoS Modify return status on Flow %d is %d",
+             __FUNCTION__, __LINE__,
+             QosFlowID, status);
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosReleaseReq() - The SME QoS API exposed to HDD to request for 
+  releasing a QoS flow running on a particular AC. This function should be 
+  called only if a QoS is set up with a valid FlowID. HDD sould invoke this 
+  API only if an explicit request for QoS release has come from Application 
+  
+  \param hHal - The handle returned by macOpen.
+  \param QosFlowID - Identification per flow running on each AC generated by SME
+                     It is only meaningful if the QoS setup for the flow is 
+                     successful
+  
+  \return eHAL_STATUS_SUCCESS - Release is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosReleaseReq(tHalHandle hHal, v_U32_t QosFlowID)
+{
+   eHalStatus lock_status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   sme_QosStatusType status;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: QoS Release requested by client for Flow %d",
+             __FUNCTION__, __LINE__,
+             QosFlowID);
+   lock_status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( !HAL_STATUS_SUCCESS( lock_status ) )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Unable to obtain lock",
+                __FUNCTION__, __LINE__);
+      return SME_QOS_STATUS_RELEASE_FAILURE_RSP;
+   }
+   //Call the internal function for QoS release, adding a layer of abstraction
+   status = sme_QosInternalReleaseReq(pMac, QosFlowID, VOS_FALSE);
+   sme_ReleaseGlobalLock( &pMac->sme );
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: QoS Release return status on Flow %d is %d",
+             __FUNCTION__, __LINE__,
+             QosFlowID, status);
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosSetParams() - This function is used by HDD to provide the 
+   default TSPEC params to SME.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info per AC as defined above, provided by HDD
+  
+  \return eHAL_STATUS_SUCCESS - Setparam is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosSetParams(tpAniSirGlobal pMac, sme_QosWmmTspecInfo * pQoSInfo)
+{
+   sme_QosEdcaAcType ac;
+   // find the AC
+   ac = sme_QosUpToAc(pQoSInfo->ts_info.up);
+   if(SME_QOS_EDCA_AC_MAX == ac)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Invalid AC %d (via UP %d)",
+                __FUNCTION__, __LINE__,
+                ac, pQoSInfo->ts_info.up );
+      return eHAL_STATUS_FAILURE;
+   }
+   //copy over the default params for this AC
+   sme_QosCb.def_QoSInfo[ac] = *pQoSInfo;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: QoS default params set for AC %d (via UP %d)",
+             __FUNCTION__, __LINE__,
+             ac, pQoSInfo->ts_info.up );
+   return eHAL_STATUS_SUCCESS;
+}
+
+void qosReleaseCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+   vos_mem_zero( &pCommand->u.qosCmd, sizeof( tGenericQosCmd ) );
+   smeReleaseCommand( pMac, pCommand );
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosMsgProcessor() - sme_ProcessMsg() calls this function for the 
+  messages that are handled by SME QoS module.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param msg_type - the type of msg passed by PE as defined in wniApi.h
+  \param pMsgBuf - a pointer to a buffer that maps to various structures base 
+                   on the message type.
+                   The beginning of the buffer can always map to tSirSmeRsp.
+  
+  \return eHAL_STATUS_SUCCESS - Validation is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosMsgProcessor( tpAniSirGlobal pMac,  v_U16_t msg_type, 
+                                void *pMsgBuf)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tListElem *pEntry;
+   tSmeCmd *pCommand;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: msg = %d for QoS",
+             __FUNCTION__, __LINE__, msg_type);
+   //switch on the msg type & make the state transition accordingly
+   switch(msg_type)
+   {
+      case eWNI_SME_ADDTS_RSP:
+         pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+         if( pEntry )
+         {
+             pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+             if( eSmeCommandAddTs == pCommand->command )
+             {
+                status = sme_QosProcessAddTsRsp(pMac, pMsgBuf);
+                if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+                {
+                   qosReleaseCommand( pMac, pCommand );
+                }
+                smeProcessPendingQueue( pMac );
+             }
+         }
+         break;
+      case eWNI_SME_DELTS_RSP:
+         pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+         if( pEntry )
+         {
+             pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+             if( eSmeCommandDelTs == pCommand->command )
+             {
+                status = sme_QosProcessDelTsRsp(pMac, pMsgBuf);
+                if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+                {
+                   qosReleaseCommand( pMac, pCommand );
+                }
+                smeProcessPendingQueue( pMac );
+             }
+         }
+         break;
+      case eWNI_SME_DELTS_IND:
+         status = sme_QosProcessDelTsInd(pMac, pMsgBuf);
+         break;
+#ifdef WLAN_FEATURE_VOWIFI_11R
+      case eWNI_SME_FT_AGGR_QOS_RSP:
+         status = sme_QosProcessAggrQosRsp(pMac, pMsgBuf);
+         break;
+#endif
+
+      default:
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: unknown msg type = %d",
+                   __FUNCTION__, __LINE__, msg_type);
+         break;
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosValidateParams() - The SME QoS API exposed to CSR to validate AP
+  capabilities regarding QoS support & any other QoS parameter validation.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pBssDesc - Pointer to the BSS Descriptor information passed down by 
+                    CSR to PE while issuing the Join request
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosValidateParams(tpAniSirGlobal pMac, 
+                                 tSirBssDescription *pBssDesc)
+{
+   tDot11fBeaconIEs *pIes = NULL;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+             "%s: %d: validation for QAP & APSD",
+             __FUNCTION__, __LINE__);
+   do
+   {
+      if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIes)))
+      {
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: csrGetParsedBssDescriptionIEs() failed",
+                   __FUNCTION__, __LINE__);
+         break;
+      }
+      //check if the AP is QAP & it supports APSD
+      if( !CSR_IS_QOS_BSS(pIes) )
+      {
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: AP doesn't support QoS",
+                   __FUNCTION__, __LINE__);
+         
+         break;
+      }
+      if(!(pIes->WMMParams.qosInfo & SME_QOS_AP_SUPPORTS_APSD) &&
+         !(pIes->WMMInfoAp.uapsd))
+      {
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: AP doesn't support APSD",
+                   __FUNCTION__, __LINE__);
+         break;
+      }
+      status = eHAL_STATUS_SUCCESS;
+   }while(0);
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: validated with status = %d",
+             __FUNCTION__, __LINE__, status);
+   if(pIes)
+   {
+      vos_mem_free(pIes);
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosCsrEventInd() - The QoS sub-module in SME expects notifications 
+  from CSR when certain events occur as mentioned in sme_QosCsrEventIndType.
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param ind - The event occurred of type sme_QosCsrEventIndType.
+  \param pEvent_info - Information related to the event
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosCsrEventInd(tpAniSirGlobal pMac,
+                              v_U8_t sessionId,
+                              sme_QosCsrEventIndType ind, 
+                              void *pEvent_info)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: On Session %d Event %d received from CSR",
+             __FUNCTION__, __LINE__,
+             sessionId, ind );
+   switch(ind)
+   {
+      case SME_QOS_CSR_ASSOC_COMPLETE:
+         //expecting assoc info in pEvent_info
+         status = sme_QosProcessAssocCompleteEv(pMac, sessionId, pEvent_info);
+         break;
+      case SME_QOS_CSR_REASSOC_REQ:
+         //nothing expected in pEvent_info
+         status = sme_QosProcessReassocReqEv(pMac, sessionId, pEvent_info);
+         break;
+      case SME_QOS_CSR_REASSOC_COMPLETE:
+         //expecting assoc info in pEvent_info
+         status = sme_QosProcessReassocSuccessEv(pMac, sessionId, pEvent_info);
+         break;
+      case SME_QOS_CSR_REASSOC_FAILURE:
+         //nothing expected in pEvent_info
+         status = sme_QosProcessReassocFailureEv(pMac, sessionId, pEvent_info);
+         break;
+      case SME_QOS_CSR_DISCONNECT_REQ:
+      case SME_QOS_CSR_DISCONNECT_IND:
+         //nothing expected in pEvent_info
+         status = sme_QosProcessDisconnectEv(pMac, sessionId, pEvent_info);
+         break;
+      case SME_QOS_CSR_JOIN_REQ:
+         //nothing expected in pEvent_info
+         status = sme_QosProcessJoinReqEv(pMac, sessionId, pEvent_info);
+         break;
+      case SME_QOS_CSR_HANDOFF_ASSOC_REQ:
+         //nothing expected in pEvent_info
+         status = sme_QosProcessHandoffAssocReqEv(pMac, sessionId, pEvent_info);
+         break;
+      case SME_QOS_CSR_HANDOFF_COMPLETE:
+         //nothing expected in pEvent_info
+         status = sme_QosProcessHandoffSuccessEv(pMac, sessionId, pEvent_info);
+         break;
+      case SME_QOS_CSR_HANDOFF_FAILURE:
+         //nothing expected in pEvent_info
+         status = sme_QosProcessHandoffFailureEv(pMac, sessionId, pEvent_info);
+         break;
+#ifdef WLAN_FEATURE_VOWIFI_11R
+      case SME_QOS_CSR_PREAUTH_SUCCESS_IND:
+         status = sme_QosProcessPreauthSuccessInd(pMac, sessionId, pEvent_info);
+         break;
+#ifdef FEATURE_WLAN_CCX
+      case SME_QOS_CSR_SET_KEY_SUCCESS_IND:
+         status = sme_QosProcessSetKeySuccessInd(pMac, sessionId, pEvent_info);
+         break;
+#endif
+#endif
+      default:
+         //Err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: On Session %d Unknown Event %d received from CSR",
+                   __FUNCTION__, __LINE__,
+                   sessionId, ind );
+         break;
+   }
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: On Session %d processed Event %d with status %d",
+             __FUNCTION__, __LINE__,
+             sessionId, ind, status );
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosGetACMMask() - The QoS sub-module API to find out on which ACs
+  AP mandates Admission Control (ACM = 1)
+  (Bit0:VO; Bit1:VI; Bit2:BK; Bit3:BE all other bits are ignored)
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pSirBssDesc - The event occurred of type sme_QosCsrEventIndType.
+
+  \return a bit mask indicating for which ACs AP has ACM set to 1
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+v_U8_t sme_QosGetACMMask(tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes)
+{
+   sme_QosEdcaAcType ac;
+   v_U8_t acm_mask = 0;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked",
+             __FUNCTION__, __LINE__);
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++)
+   {
+      if(sme_QosIsACM(pMac, pSirBssDesc, ac, pIes))
+      {
+         acm_mask = acm_mask | (1 << (SME_QOS_EDCA_AC_VO - ac));
+      }
+      
+   }
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: mask is %d",
+             __FUNCTION__, __LINE__, acm_mask);
+   return acm_mask;
+}
+/*-------------------------------------------------------------------------- 
+                         Internal function definitions
+  ------------------------------------------------------------------------*/
+/*--------------------------------------------------------------------------
+  \brief sme_QosInternalSetupReq() - The SME QoS internal setup request handling
+  function.
+  If the request involves admission control on the requested AC, HDD needs to 
+  provide the necessary Traffic Specification (TSPEC) parameters otherwise SME 
+  is going to use the default params.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info as defined above, provided by HDD
+  \param QoSCallback - The callback which is registered per flow while 
+                       requesting for QoS. Used for any notification for the 
+                       flow (i.e. setup success/failure/release) which needs to 
+                       be sent to HDD
+  \param HDDcontext - A cookie passed by HDD to be used by SME during any QoS 
+                      notification (through the callabck) to HDD 
+  \param UPType - Useful only if HDD or any other upper layer module (BAP etc.)
+                  looking for implicit QoS setup, in that 
+                  case, the pQoSInfo will be NULL & SME will know about the AC
+                  (from the UP provided in this param) QoS is requested on
+  \param QosFlowID - Identification per flow running on each AC generated by 
+                      SME. 
+                     It is only meaningful if the QoS setup for the flow is 
+                     successful
+  \param buffered_cmd - tells us if the cmd was a buffered one or fresh from 
+                        client
+                  
+  \return eHAL_STATUS_SUCCESS - Setup is successful.
+  
+          Other status means Setup request failed     
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosInternalSetupReq(tpAniSirGlobal pMac, 
+                                          v_U8_t sessionId,
+                                          sme_QosWmmTspecInfo * pQoSInfo,
+                                          sme_QosCallback QoSCallback, 
+                                          void * HDDcontext,
+                                          sme_QosWmmUpType UPType, 
+                                          v_U32_t QosFlowID,
+                                          v_BOOL_t buffered_cmd,
+                                          v_BOOL_t hoRenewal)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosEdcaAcType ac;
+   sme_QosWmmTspecInfo Tspec_Info;
+   sme_QosStates new_state = SME_QOS_CLOSED;
+   sme_QosFlowInfoEntry *pentry = NULL;
+   sme_QosCmdInfo  cmd;
+   sme_QosStatusType status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+   v_U8_t tmask = 0;
+   v_U8_t new_tmask = 0;
+   sme_QosSearchInfo search_key;
+   v_BOOL_t bufferCommand;
+   eHalStatus hstatus;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d for flow %d",
+             __FUNCTION__, __LINE__,
+             sessionId, QosFlowID);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   // if caller sent an empty TSPEC, fill up with the default one
+   if(!pQoSInfo)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, 
+                "%s: %d: caller sent an empty QoS param list, using defaults",
+                __FUNCTION__, __LINE__);
+      // find the AC with UPType passed in
+      ac = sme_QosUpToAc(UPType);
+      if(SME_QOS_EDCA_AC_MAX == ac)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: invalid AC %d from UP %d",
+                   __FUNCTION__, __LINE__,
+                   ac, UPType);
+         
+         return SME_QOS_STATUS_SETUP_INVALID_PARAMS_RSP;
+      }
+      Tspec_Info = sme_QosCb.def_QoSInfo[ac];
+   }
+   else
+   {
+      // find the AC
+      ac = sme_QosUpToAc(pQoSInfo->ts_info.up);
+      if(SME_QOS_EDCA_AC_MAX == ac)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: invalid AC %d from UP %d",
+                   __FUNCTION__, __LINE__,
+                   ac, pQoSInfo->ts_info.up);
+         
+         return SME_QOS_STATUS_SETUP_INVALID_PARAMS_RSP;
+      }
+      //validate QoS params
+      if(!sme_QosValidateRequestedParams(pMac, pQoSInfo, sessionId))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: invalid params",
+                   __FUNCTION__, __LINE__);
+         return SME_QOS_STATUS_SETUP_INVALID_PARAMS_RSP;
+      }
+      Tspec_Info = *pQoSInfo;
+   }
+   pACInfo = &pSession->ac_info[ac];
+   // need to vote off powersave for the duration of this request
+   pSession->readyForPowerSave = VOS_FALSE;
+   // assume we won't have to (re)buffer the command
+   bufferCommand = VOS_FALSE;
+   //check to consider the following flowing scenario
+   //Addts request is pending on one AC, while APSD requested on another which 
+   //needs a reassoc. Will buffer a request if Addts is pending on any AC, 
+   //which will safegaurd the above scenario, & also won't confuse PE with back 
+   //to back Addts or Addts followed by Reassoc
+   if(sme_QosIsRspPending(sessionId, ac))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                "%s: %d: buffering the setup request for flow %d in state %d "
+                "since another request is pending",
+                __FUNCTION__, __LINE__, 
+                QosFlowID, pACInfo->curr_state );
+      bufferCommand = VOS_TRUE;
+   }
+   else
+   {
+      // make sure we are in full power so that we can issue
+      // an AddTS or reassoc if necessary
+      hstatus = pmcRequestFullPower(pMac, sme_QosPmcFullPowerCallback,
+                                    pSession, eSME_REASON_OTHER);
+      if( eHAL_STATUS_PMC_PENDING == hstatus )
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                   "%s: %d: buffering the setup request for flow %d in state %d, "
+                   "waiting for full power",
+                   __FUNCTION__, __LINE__, 
+                   QosFlowID, pACInfo->curr_state );
+         bufferCommand = VOS_TRUE;
+      }
+   }
+   if (bufferCommand)
+   {
+      // we need to buffer the command
+      cmd.command = SME_QOS_SETUP_REQ;
+      cmd.pMac = pMac;
+      cmd.sessionId = sessionId;
+      cmd.u.setupCmdInfo.HDDcontext = HDDcontext;
+      cmd.u.setupCmdInfo.QoSInfo = Tspec_Info;
+      cmd.u.setupCmdInfo.QoSCallback = QoSCallback;
+      cmd.u.setupCmdInfo.UPType = UPType;
+      cmd.u.setupCmdInfo.hoRenewal = hoRenewal;
+      cmd.u.setupCmdInfo.QosFlowID = QosFlowID;
+      hstatus = sme_QosBufferCmd(&cmd, buffered_cmd);
+      if(!HAL_STATUS_SUCCESS(hstatus))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: couldn't buffer the setup request in state = %d",
+                   __FUNCTION__, __LINE__,
+                   pACInfo->curr_state );
+         // unable to buffer the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_SETUP_FAILURE_RSP;
+      }
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Buffered setup request for flow = %d",
+                __FUNCTION__, __LINE__,
+                QosFlowID);
+      return SME_QOS_STATUS_SETUP_REQ_PENDING_RSP;
+   }
+
+   //get into the state m/c to see if the request can be granted
+   switch(pACInfo->curr_state)
+   {
+   case SME_QOS_LINK_UP:
+      //call the internal qos setup logic to decide on if the
+      // request is NOP, or need reassoc for APSD and/or need to send out ADDTS
+      status = sme_QosSetup(pMac, sessionId, &Tspec_Info, ac);
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: On session %d with AC %d in state SME_QOS_LINK_UP "
+                "sme_QosSetup returned with status %d",
+                __FUNCTION__, __LINE__,
+                sessionId, ac, status);
+      if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP != status)
+      {
+         // we aren't waiting for a response from the AP
+         // so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+      }
+      if((SME_QOS_STATUS_SETUP_REQ_PENDING_RSP == status)||
+         (SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status) ||
+         (SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status))
+      {
+         // we received an expected "good" status
+         //create an entry in the flow list
+         pentry = vos_mem_malloc(sizeof(*pentry));
+         if (!pentry)
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                      "%s: %d: couldn't allocate memory for the new "
+                      "entry in the Flow List",
+                      __FUNCTION__, __LINE__);
+            return SME_QOS_STATUS_SETUP_FAILURE_RSP;
+         }
+         pentry->ac_type = ac;
+         pentry->HDDcontext = HDDcontext;
+         pentry->QoSCallback = QoSCallback;
+         pentry->hoRenewal = hoRenewal;
+         pentry->QosFlowID = QosFlowID;
+         pentry->sessionId = sessionId;
+         // since we are in state SME_QOS_LINK_UP this must be the
+         // first TSPEC on this AC, so use index 0 (mask bit 1)
+         pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0] = Tspec_Info;
+         if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP == status)
+         {
+            if(pACInfo->tspec_mask_status &&
+               !pACInfo->reassoc_pending)
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: On session %d with AC %d in state "
+                            "SME_QOS_LINK_UP tspec_mask_status is %d "
+                         "but should not be set yet",
+                         __FUNCTION__, __LINE__,
+                         sessionId, ac, pACInfo->tspec_mask_status);
+               //ASSERT
+               VOS_ASSERT(0);
+               vos_mem_free(pentry);
+               return SME_QOS_STATUS_SETUP_FAILURE_RSP;
+            }
+            pACInfo->tspec_mask_status = SME_QOS_TSPEC_MASK_BIT_1_SET;
+            if(!pACInfo->reassoc_pending)
+            {
+               // we didn't request for reassoc, it must be a tspec negotiation
+               pACInfo->tspec_pending = 1;
+            }
+             
+            pentry->reason = SME_QOS_REASON_SETUP;
+            new_state = SME_QOS_REQUESTED;
+         }
+         else
+         {
+            // SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP or
+            // SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY
+            pentry->reason = SME_QOS_REASON_REQ_SUCCESS;
+            new_state = SME_QOS_QOS_ON;
+            pACInfo->tspec_mask_status = SME_QOS_TSPEC_MASK_BIT_1_SET;
+            pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0] = Tspec_Info;
+            if(buffered_cmd && !pentry->hoRenewal)
+            {
+               QoSCallback(pMac, HDDcontext, 
+                           &pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0],
+                           status,
+                           pentry->QosFlowID);
+            }
+            pentry->hoRenewal = VOS_FALSE;
+         }
+         pACInfo->num_flows[SME_QOS_TSPEC_INDEX_0]++;
+
+         //indicate on which index the flow entry belongs to & add it to the 
+         //Flow List at the end
+         pentry->tspec_mask = pACInfo->tspec_mask_status;
+         pentry->QoSInfo = Tspec_Info;
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: Creating entry on session %d at %p with flowID %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId, pentry, QosFlowID);
+         csrLLInsertTail(&sme_QosCb.flow_list, &pentry->link, VOS_TRUE);
+      }
+      else
+      {
+         // unexpected status returned by sme_QosSetup()
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: On session %d unexpected status %d "
+                   "returned by sme_QosSetup",
+                   __FUNCTION__, __LINE__,
+                   sessionId, status);
+         new_state = pACInfo->curr_state;
+         if(buffered_cmd && hoRenewal)
+         {
+            QoSCallback(pMac, HDDcontext, 
+                        &pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0],
+                        SME_QOS_STATUS_RELEASE_QOS_LOST_IND,
+                        QosFlowID);
+         }
+      }
+      break;
+   case SME_QOS_HANDOFF:
+   case SME_QOS_REQUESTED:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                "%s: %d: Buffering setup request for flow %d in state = %d",
+                __FUNCTION__, __LINE__,
+                QosFlowID, pACInfo->curr_state );
+      //buffer cmd
+      cmd.command = SME_QOS_SETUP_REQ;
+      cmd.pMac = pMac;
+      cmd.sessionId = sessionId;
+      cmd.u.setupCmdInfo.HDDcontext = HDDcontext;
+      cmd.u.setupCmdInfo.QoSInfo = Tspec_Info;
+      cmd.u.setupCmdInfo.QoSCallback = QoSCallback;
+      cmd.u.setupCmdInfo.UPType = UPType;
+      cmd.u.setupCmdInfo.hoRenewal = hoRenewal;
+      cmd.u.setupCmdInfo.QosFlowID = QosFlowID;
+      hstatus = sme_QosBufferCmd(&cmd, buffered_cmd);
+      if(!HAL_STATUS_SUCCESS(hstatus))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: On session %d couldn't buffer the setup "
+                   "request for flow %d in state = %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId, QosFlowID, pACInfo->curr_state );
+         // unable to buffer the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_SETUP_FAILURE_RSP;
+      }
+      status = SME_QOS_STATUS_SETUP_REQ_PENDING_RSP;
+      new_state = pACInfo->curr_state;
+      break;
+   case SME_QOS_QOS_ON:
+      
+      //check if multiple flows running on the ac
+      if((pACInfo->num_flows[SME_QOS_TSPEC_INDEX_0] > 0)||
+         (pACInfo->num_flows[SME_QOS_TSPEC_INDEX_1] > 0))
+      {
+         //do we need to care about the case where APSD needed on ACM = 0 below?
+         if(CSR_IS_ADDTS_WHEN_ACMOFF_SUPPORTED(pMac) ||
+            sme_QosIsACM(pMac, pSession->assocInfo.pBssDesc, ac, NULL))
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                      "%s: %d: tspec_mask_status = %d for AC = %d",
+                      __FUNCTION__, __LINE__,
+                      pACInfo->tspec_mask_status, ac);
+            if(!pACInfo->tspec_mask_status)
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: tspec_mask_status can't be 0 for ac = %d in "
+                         "state = %d",
+                         __FUNCTION__, __LINE__,
+                         ac, pACInfo->curr_state);
+               //ASSERT
+               VOS_ASSERT(0);
+               // unable to service the request
+               // nothing is pending so vote powersave back on
+               pSession->readyForPowerSave = VOS_TRUE;
+               return status;
+            }
+            /* Flow aggregation */
+            if(SME_QOS_TSPEC_MASK_BIT_1_2_SET != pACInfo->tspec_mask_status)
+            {
+              /* Either of upstream, downstream or bidirectional flows are present */
+              /* If either of new stream or current stream is for bidirecional, aggregate 
+               * the new stream with the current streams present and send out aggregated Tspec.*/
+              if((Tspec_Info.ts_info.direction == SME_QOS_WMM_TS_DIR_BOTH) ||
+                 (pACInfo->curr_QoSInfo[pACInfo->tspec_mask_status - 1].
+                      ts_info.direction == SME_QOS_WMM_TS_DIR_BOTH))
+              {
+                // Aggregate the new stream with the current stream(s).
+                tmask = pACInfo->tspec_mask_status;
+              }
+              /* None of new stream or current (aggregated) streams are for bidirectional.
+               * Check if the new stream direction matches the current stream direction. */
+              else if(pACInfo->curr_QoSInfo[pACInfo->tspec_mask_status - 1].
+                  ts_info.direction == Tspec_Info.ts_info.direction)
+              {
+                // Aggregate the new stream with the current stream(s).
+                tmask = pACInfo->tspec_mask_status;
+              }
+              /* New stream is in different direction. */
+              else
+              {
+                // No Aggregation. Mark the 2nd tpsec index also as active.
+                tmask = SME_QOS_TSPEC_MASK_CLEAR;
+                new_tmask = SME_QOS_TSPEC_MASK_BIT_1_2_SET & ~pACInfo->tspec_mask_status;
+                pACInfo->tspec_mask_status = SME_QOS_TSPEC_MASK_BIT_1_2_SET;
+              }
+            }
+            else
+            {
+              /* Both uplink and downlink streams are present. */
+              /* If new stream is bidirectional, aggregate new stream with all existing
+               * upstreams and downstreams. Send out new aggregated tpsec. */
+              if(Tspec_Info.ts_info.direction == SME_QOS_WMM_TS_DIR_BOTH)
+              {
+                // Only one tspec index (0) will be in use after this aggregation.
+                tmask = SME_QOS_TSPEC_MASK_BIT_1_2_SET;
+                pACInfo->tspec_mask_status = SME_QOS_TSPEC_MASK_BIT_1_SET;
+              }
+              /* New stream is also uni-directional
+               * Find out the tsepc index with which it needs to be aggregated */
+              else if(pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0].ts_info.direction != 
+                   Tspec_Info.ts_info.direction)
+              {
+                // Aggregate with 2nd tspec index
+                tmask = SME_QOS_TSPEC_MASK_BIT_2_SET;
+              }
+              else
+              {
+                // Aggregate with 1st tspec index
+                tmask = SME_QOS_TSPEC_MASK_BIT_1_SET;
+              }
+            }
+         }
+         else
+         {
+            //ACM = 0
+            // We won't be sending a TSPEC to the AP but we still need
+            // to aggregate to calculate trigger frame parameters
+            tmask = SME_QOS_TSPEC_MASK_BIT_1_SET;
+         }
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED,
+                   "%s: %d: tmask = %d, new_tmask = %d in state = %d",
+                   __FUNCTION__, __LINE__,
+                   tmask, new_tmask, pACInfo->curr_state );
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED,
+                   "%s: %d: tspec_mask_status = %d for AC = %d",
+                   __FUNCTION__, __LINE__,
+                   pACInfo->tspec_mask_status, ac);
+         if(tmask)
+         {
+            // create the aggregate TSPEC
+            if(tmask != SME_QOS_TSPEC_MASK_BIT_1_2_SET)
+            {
+              hstatus = sme_QosAggregateParams(&Tspec_Info, 
+                                               &pACInfo->curr_QoSInfo[tmask - 1],
+                                               &pACInfo->requested_QoSInfo[tmask - 1]);
+            }
+            else
+            {
+              /* Aggregate the new bidirectional stream with the existing upstreams and 
+               * downstreams in tspec indices 0 and 1. */
+              tmask = SME_QOS_TSPEC_MASK_BIT_1_SET;
+
+              if((hstatus = sme_QosAggregateParams(&Tspec_Info, 
+                                                   &pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0],
+                                                   &pACInfo->requested_QoSInfo[tmask - 1]))
+                          == eHAL_STATUS_SUCCESS)
+              {
+                hstatus = sme_QosAggregateParams(&pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_1], 
+                                                 &pACInfo->requested_QoSInfo[tmask - 1],
+                                                 NULL);
+              }
+            }
+
+            if(!HAL_STATUS_SUCCESS(hstatus))
+            {
+               //err msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: failed to aggregate params",
+                         __FUNCTION__, __LINE__);
+               // unable to service the request
+               // nothing is pending so vote powersave back on
+               pSession->readyForPowerSave = VOS_TRUE;
+               return SME_QOS_STATUS_SETUP_FAILURE_RSP;
+            }
+         }
+         else
+         {
+            tmask = new_tmask;
+         }
+      }
+      else
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: no flows running for ac = %d while in state = %d",
+                   __FUNCTION__, __LINE__,
+                   ac, pACInfo->curr_state );
+         //ASSERT
+         VOS_ASSERT(0);
+         // unable to service the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return status;
+      }
+      //although aggregating, make sure to request on the correct UP
+      pACInfo->requested_QoSInfo[tmask - 1].ts_info.up = Tspec_Info.ts_info.up;
+      status = sme_QosSetup(pMac, sessionId,
+                            &pACInfo->requested_QoSInfo[tmask - 1], ac);
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: On session %d with AC %d in state SME_QOS_QOS_ON "
+                "sme_QosSetup returned with status %d",
+                __FUNCTION__, __LINE__,
+                sessionId, ac, status);
+      if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP != status)
+      {
+         // we aren't waiting for a response from the AP
+         // so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+      }
+      if((SME_QOS_STATUS_SETUP_REQ_PENDING_RSP == status)||
+         (SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status) ||
+         (SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status))
+      {
+         // we received an expected "good" status
+         //create an entry in the flow list
+         pentry = (sme_QosFlowInfoEntry *) vos_mem_malloc(sizeof(*pentry));
+         if (!pentry)
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                      "%s: %d: couldn't allocate memory for the new "
+                      "entry in the Flow List",
+                      __FUNCTION__, __LINE__);
+            return SME_QOS_STATUS_SETUP_FAILURE_RSP;
+         }
+         pentry->ac_type = ac;
+         pentry->HDDcontext = HDDcontext;
+         pentry->QoSCallback = QoSCallback;
+         pentry->hoRenewal = hoRenewal;
+         pentry->QosFlowID = QosFlowID;
+         pentry->sessionId = sessionId;
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: Creating flow %d",
+                   __FUNCTION__, __LINE__,
+                   QosFlowID);
+         if((SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status)||
+            (SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status))
+         {
+            new_state = pACInfo->curr_state;
+            pentry->reason = SME_QOS_REASON_REQ_SUCCESS;
+            pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0] = 
+               pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0];
+            if(buffered_cmd && !pentry->hoRenewal)
+            {
+               QoSCallback(pMac, HDDcontext, 
+                           &pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0],
+                           status,
+                           pentry->QosFlowID);
+            }
+            if(SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status)
+            {
+               // if we are not in handoff, then notify all flows on
+               // this AC that the aggregate TSPEC may have changed
+               if(!pentry->hoRenewal)
+               {
+                  vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+                  search_key.key.ac_type = ac;
+                  search_key.index = SME_QOS_SEARCH_KEY_INDEX_2;
+                  search_key.sessionId = sessionId;
+                  hstatus = sme_QosFindAllInFlowList(pMac, search_key,
+                                                     sme_QosSetupFnp);
+                  if(!HAL_STATUS_SUCCESS(hstatus))
+                  {
+                     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                               "%s: %d: couldn't notify other "
+                               "entries on this AC =%d",
+                               __FUNCTION__, __LINE__, ac);
+                  }
+               }
+            }
+            pentry->hoRenewal = VOS_FALSE;
+         }
+         else
+         {
+            // SME_QOS_STATUS_SETUP_REQ_PENDING_RSP
+            new_state = SME_QOS_REQUESTED;
+            pentry->reason = SME_QOS_REASON_SETUP;
+            //Need this info when addts comes back from PE to know on
+            //which index of the AC the request was from
+            pACInfo->tspec_pending = tmask;
+         }
+         pACInfo->num_flows[tmask - 1]++;
+         //indicate on which index the flow entry belongs to & add it to the 
+         //Flow List at the end
+         pentry->tspec_mask = tmask;
+         pentry->QoSInfo = Tspec_Info;
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: On session %d creating entry at %p with flowID %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId, pentry, QosFlowID);
+         csrLLInsertTail(&sme_QosCb.flow_list, &pentry->link, VOS_TRUE);
+      }
+      else
+      {
+         // unexpected status returned by sme_QosSetup()
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: On session %d unexpected status %d "
+                   "returned by sme_QosSetup",
+                   __FUNCTION__, __LINE__,
+                   sessionId, status);
+         new_state = pACInfo->curr_state;
+      }
+      break;
+   case SME_QOS_CLOSED:
+   case SME_QOS_INIT:
+   default:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: setup requested in unexpected state = %d",
+                __FUNCTION__, __LINE__,
+                pACInfo->curr_state);
+      // unable to service the request
+      // nothing is pending so vote powersave back on
+      pSession->readyForPowerSave = VOS_TRUE;
+      VOS_ASSERT(0);
+      new_state = pACInfo->curr_state;
+   }
+   /* if current state is same as previous no need for transistion,
+      if we are doing reassoc & we are already in handoff state, no need to move
+      to requested state. But make sure to set the previous state as requested
+      state
+   */
+   if((new_state != pACInfo->curr_state)&&
+      (!(pACInfo->reassoc_pending && 
+         (SME_QOS_HANDOFF == pACInfo->curr_state))))
+   {
+      sme_QosStateTransition(sessionId, ac, new_state);
+   }
+   
+   if(pACInfo->reassoc_pending && 
+      (SME_QOS_HANDOFF == pACInfo->curr_state))
+   {
+      pACInfo->prev_state = SME_QOS_REQUESTED;
+   }
+   if((SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status) ||
+      (SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status)) 
+   {
+      (void)sme_QosProcessBufferedCmd(sessionId);
+   }
+   return status;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosInternalModifyReq() - The SME QoS internal function to request 
+  for modification of certain QoS params on a flow running on a particular AC. 
+  If the request involves admission control on the requested AC, HDD needs to 
+  provide the necessary Traffic Specification (TSPEC) parameters & SME might
+  start the renegotiation process through ADDTS.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info as defined above, provided by HDD
+  \param QosFlowID - Identification per flow running on each AC generated by 
+                      SME. 
+                     It is only meaningful if the QoS setup for the flow has 
+                     been successful already
+                  
+  \return SME_QOS_STATUS_SETUP_SUCCESS_RSP - Modification is successful.
+  
+          Other status means request failed     
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosInternalModifyReq(tpAniSirGlobal pMac, 
+                                           sme_QosWmmTspecInfo * pQoSInfo,
+                                           v_U32_t QosFlowID,
+                                           v_BOOL_t buffered_cmd)
+{
+   tListElem *pEntry= NULL;
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *pNewEntry= NULL;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosEdcaAcType ac;
+   sme_QosStates new_state = SME_QOS_CLOSED;
+   sme_QosStatusType status = SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+   sme_QosWmmTspecInfo Aggr_Tspec_Info;
+   sme_QosSearchInfo search_key;
+   sme_QosCmdInfo  cmd;
+   v_U8_t sessionId;
+   v_BOOL_t bufferCommand;
+   eHalStatus hstatus;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked for flow %d",
+             __FUNCTION__, __LINE__,
+             QosFlowID);
+
+   vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+   //set the key type & the key to be searched in the Flow List
+   search_key.key.QosFlowID = QosFlowID;
+   search_key.index = SME_QOS_SEARCH_KEY_INDEX_1;
+   search_key.sessionId = SME_QOS_SEARCH_SESSION_ID_ANY;
+   //go through the link list to find out the details on the flow
+   pEntry = sme_QosFindInFlowList(search_key);
+   if(!pEntry)
+   {
+      //Err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: no match found for flowID = %d",
+                __FUNCTION__, __LINE__,
+                QosFlowID);
+      return SME_QOS_STATUS_MODIFY_SETUP_INVALID_PARAMS_RSP;
+   }
+   // find the AC
+   flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+   ac = flow_info->ac_type;
+
+   sessionId = flow_info->sessionId;
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pACInfo = &pSession->ac_info[ac];
+
+   //validate QoS params
+   if(!sme_QosValidateRequestedParams(pMac, pQoSInfo, sessionId))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: invalid params",
+                __FUNCTION__, __LINE__);
+      return SME_QOS_STATUS_MODIFY_SETUP_INVALID_PARAMS_RSP;
+   }
+   // For modify, make sure that direction, TID and UP are not being altered
+   if((pQoSInfo->ts_info.direction != flow_info->QoSInfo.ts_info.direction) ||
+      (pQoSInfo->ts_info.up != flow_info->QoSInfo.ts_info.up) ||
+      (pQoSInfo->ts_info.tid != flow_info->QoSInfo.ts_info.tid))
+   {
+     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+               "%s: %d: Modification of direction/tid/up is not allowed",
+               __FUNCTION__, __LINE__);
+
+     return SME_QOS_STATUS_MODIFY_SETUP_INVALID_PARAMS_RSP;
+   }
+   // need to vote off powersave for the duration of this request
+   pSession->readyForPowerSave = VOS_FALSE;
+   // assume we won't have to (re)buffer the command
+   bufferCommand = VOS_FALSE;
+   //check to consider the following flowing scenario
+   //Addts request is pending on one AC, while APSD requested on another which 
+   //needs a reassoc. Will buffer a request if Addts is pending on any AC, 
+   //which will safegaurd the above scenario, & also won't confuse PE with back 
+   //to back Addts or Addts followed by Reassoc
+   if(sme_QosIsRspPending(sessionId, ac))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                "%s: %d: buffering the modify request for flow %d in state %d "
+                "since another request is pending",
+                __FUNCTION__, __LINE__, 
+                QosFlowID, pACInfo->curr_state );
+      bufferCommand = VOS_TRUE;
+   }
+   else
+   {
+      // make sure we are in full power so that we can issue
+      // an AddTS or reassoc if necessary
+      hstatus = pmcRequestFullPower(pMac, sme_QosPmcFullPowerCallback,
+                                    pSession, eSME_REASON_OTHER);
+      if( eHAL_STATUS_PMC_PENDING == hstatus )
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                   "%s: %d: buffering the modify request for flow %d in state %d, "
+                   "waiting for full power",
+                   __FUNCTION__, __LINE__, 
+                   QosFlowID, pACInfo->curr_state );
+         bufferCommand = VOS_TRUE;
+      }
+   }
+   if (bufferCommand)
+   {
+      // we need to buffer the command
+      cmd.command = SME_QOS_MODIFY_REQ;
+      cmd.pMac = pMac;
+      cmd.sessionId = sessionId;
+      cmd.u.modifyCmdInfo.QosFlowID = QosFlowID;
+      cmd.u.modifyCmdInfo.QoSInfo = *pQoSInfo;
+      hstatus = sme_QosBufferCmd(&cmd, buffered_cmd);
+      if(!HAL_STATUS_SUCCESS(hstatus))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: couldn't buffer the modify request in state = %d",
+                   __FUNCTION__, __LINE__,
+                   pACInfo->curr_state );
+         // unable to buffer the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+      }
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Buffered modify request for flow = %d",
+                __FUNCTION__, __LINE__,
+                QosFlowID);
+      return SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP;
+   }
+   //get into the stat m/c to see if the request can be granted
+   switch(pACInfo->curr_state)
+   {
+   case SME_QOS_QOS_ON:
+      //save the new params adding a new (duplicate) entry in the Flow List
+      //Once we have decided on OTA exchange needed or not we can delete the
+      //original one from the List
+      pNewEntry = (sme_QosFlowInfoEntry *) vos_mem_malloc(sizeof(*pNewEntry));
+      if (!pNewEntry)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                   "%s: %d: couldn't allocate memory for the new "
+                   "entry in the Flow List",
+                   __FUNCTION__, __LINE__);
+         // unable to service the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+      }
+      pNewEntry->ac_type = ac;
+      pNewEntry->sessionId = sessionId;
+      pNewEntry->HDDcontext = flow_info->HDDcontext;
+      pNewEntry->QoSCallback = flow_info->QoSCallback;
+      pNewEntry->QosFlowID = flow_info->QosFlowID;
+      pNewEntry->reason = SME_QOS_REASON_MODIFY_PENDING;
+      //since it is a modify request, use the same index on which the flow
+      //entry originally was running & add it to the Flow List at the end
+      pNewEntry->tspec_mask = flow_info->tspec_mask;
+      pNewEntry->QoSInfo = *pQoSInfo;
+      //update the entry from Flow List which needed to be modified
+      flow_info->reason = SME_QOS_REASON_MODIFY;
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: On session %d creating modified "
+                "entry at %p with flowID %d",
+                __FUNCTION__, __LINE__,
+                sessionId, pNewEntry, pNewEntry->QosFlowID);
+      //add the new entry under construction to the Flow List
+      csrLLInsertTail(&sme_QosCb.flow_list, &pNewEntry->link, VOS_TRUE);
+      //update TSPEC with the new param set
+      hstatus = sme_QosUpdateParams(sessionId,
+                                    ac, pNewEntry->tspec_mask, 
+                                    &Aggr_Tspec_Info);
+      if(HAL_STATUS_SUCCESS(hstatus))
+      {
+         pACInfo->requested_QoSInfo[pNewEntry->tspec_mask -1] = Aggr_Tspec_Info;
+         //if ACM, send out a new ADDTS
+         status = sme_QosSetup(pMac, sessionId,
+                               &pACInfo->requested_QoSInfo[pNewEntry->tspec_mask -1],
+                               ac);
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: On session %d with AC %d in state SME_QOS_QOS_ON "
+                   "sme_QosSetup returned with status %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId, ac, status);
+         if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP != status)
+         {
+            // we aren't waiting for a response from the AP
+            // so vote powersave back on
+            pSession->readyForPowerSave = VOS_TRUE;
+         }
+         if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP == status) 
+         {
+            new_state = SME_QOS_REQUESTED;
+            status = SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP;
+            pACInfo->tspec_pending = pNewEntry->tspec_mask;
+         }
+         else if((SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status) ||
+                 (SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status))
+         {
+            new_state = SME_QOS_QOS_ON;
+
+            vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+            //delete the original entry in FLOW list which got modified
+            search_key.key.ac_type = ac;
+            search_key.index = SME_QOS_SEARCH_KEY_INDEX_2;
+            search_key.sessionId = sessionId;
+            hstatus = sme_QosFindAllInFlowList(pMac, search_key,
+                                               sme_QosModifyFnp);
+            if(!HAL_STATUS_SUCCESS(hstatus))
+            {
+               status = SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+            }
+            if(SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP != status)
+            {
+               pACInfo->curr_QoSInfo[pNewEntry->tspec_mask -1] = 
+                  pACInfo->requested_QoSInfo[pNewEntry->tspec_mask -1];
+               if(SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status)
+               {
+                  status = SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_APSD_SET_ALREADY;
+                  vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+                  search_key.key.ac_type = ac;
+                  search_key.index = SME_QOS_SEARCH_KEY_INDEX_2;
+                  search_key.sessionId = sessionId;
+                  hstatus = sme_QosFindAllInFlowList(pMac, search_key, 
+                                                     sme_QosModificationNotifyFnp);
+                  if(!HAL_STATUS_SUCCESS(hstatus))
+                  {
+                     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                               "%s: %d: couldn't notify other "
+                               "entries on this AC =%d",
+                               __FUNCTION__, __LINE__, ac);
+                  }
+               }
+               else if(SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status)
+               {
+                  status = SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP;
+               }
+            }
+            if(buffered_cmd)
+            {
+               flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                      &pACInfo->curr_QoSInfo[pNewEntry->tspec_mask -1],
+                                      status,
+                                      flow_info->QosFlowID);
+            }
+            
+         }
+         else
+         {
+            // unexpected status returned by sme_QosSetup()
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: On session %d unexpected status %d "
+                      "returned by sme_QosSetup",
+                      __FUNCTION__, __LINE__,
+                      sessionId, status);
+            new_state = SME_QOS_QOS_ON;
+         }
+      }
+      else
+      {
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: sme_QosUpdateParams() failed",
+                   __FUNCTION__, __LINE__);
+         // unable to service the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         new_state = SME_QOS_LINK_UP;
+      }
+      /* if we are doing reassoc & we are already in handoff state, no need
+         to move to requested state. But make sure to set the previous state
+         as requested state
+      */
+      if(!(pACInfo->reassoc_pending && 
+           (SME_QOS_HANDOFF == pACInfo->curr_state)))
+      {
+         sme_QosStateTransition(sessionId, ac, new_state);
+      }
+      else
+      {
+         pACInfo->prev_state = SME_QOS_REQUESTED;
+      }
+      break;
+   case SME_QOS_HANDOFF:
+   case SME_QOS_REQUESTED:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                "%s: %d: Buffering modify request for flow %d in state = %d",
+                __FUNCTION__, __LINE__,
+                QosFlowID, pACInfo->curr_state );
+      //buffer cmd
+      cmd.command = SME_QOS_MODIFY_REQ;
+      cmd.pMac = pMac;
+      cmd.sessionId = sessionId;
+      cmd.u.modifyCmdInfo.QosFlowID = QosFlowID;
+      cmd.u.modifyCmdInfo.QoSInfo = *pQoSInfo;
+      hstatus = sme_QosBufferCmd(&cmd, buffered_cmd);
+      if(!HAL_STATUS_SUCCESS(hstatus))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: couldn't buffer the modify request in state = %d",
+                   __FUNCTION__, __LINE__,
+                   pACInfo->curr_state );
+         // unable to buffer the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+      }
+      status = SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP;
+      break;
+   case SME_QOS_CLOSED:
+   case SME_QOS_INIT:
+   case SME_QOS_LINK_UP:
+   default:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: modify requested in unexpected state = %d",
+                __FUNCTION__, __LINE__,
+                pACInfo->curr_state);
+      // unable to service the request
+      // nothing is pending so vote powersave back on
+      pSession->readyForPowerSave = VOS_TRUE;
+      break;
+   }
+   if((SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status) ||
+      (SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_APSD_SET_ALREADY == status)) 
+   {
+      (void)sme_QosProcessBufferedCmd(sessionId);
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosInternalReleaseReq() - The SME QoS internal function to request 
+  for releasing a QoS flow running on a particular AC. 
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param QosFlowID - Identification per flow running on each AC generated by SME 
+                     It is only meaningful if the QoS setup for the flow is 
+                     successful
+  
+  \return eHAL_STATUS_SUCCESS - Release is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosInternalReleaseReq(tpAniSirGlobal pMac, 
+                                            v_U32_t QosFlowID,
+                                            v_BOOL_t buffered_cmd)
+{
+   tListElem *pEntry= NULL;
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosFlowInfoEntry *pDeletedFlow = NULL;
+   sme_QosEdcaAcType ac;
+   sme_QosStates new_state = SME_QOS_CLOSED;
+   sme_QosStatusType status = SME_QOS_STATUS_RELEASE_FAILURE_RSP;
+   sme_QosWmmTspecInfo Aggr_Tspec_Info;
+   sme_QosSearchInfo search_key;
+   sme_QosCmdInfo  cmd;
+   tCsrRoamModifyProfileFields modifyProfileFields;
+   v_BOOL_t  deltsIssued = VOS_FALSE;
+   v_U8_t sessionId;
+   v_BOOL_t bufferCommand;
+   eHalStatus hstatus;
+   v_BOOL_t biDirectionalFlowsPresent = VOS_FALSE;
+   v_BOOL_t uplinkFlowsPresent = VOS_FALSE;
+   v_BOOL_t downlinkFlowsPresent = VOS_FALSE;
+   tListElem *pResult= NULL;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked for flow %d",
+             __FUNCTION__, __LINE__,
+             QosFlowID);
+
+   vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+   //set the key type & the key to be searched in the Flow List
+   search_key.key.QosFlowID = QosFlowID;
+   search_key.index = SME_QOS_SEARCH_KEY_INDEX_1;
+   search_key.sessionId = SME_QOS_SEARCH_SESSION_ID_ANY;
+   //go through the link list to find out the details on the flow
+   pEntry = sme_QosFindInFlowList(search_key);
+   
+   if(!pEntry)
+   {
+      //Err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: no match found for flowID = %d",
+                __FUNCTION__, __LINE__,
+                QosFlowID);
+      return SME_QOS_STATUS_RELEASE_INVALID_PARAMS_RSP;
+   }
+   // find the AC
+   flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+   ac = flow_info->ac_type;
+   sessionId = flow_info->sessionId;
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   // need to vote off powersave for the duration of this request
+   pSession->readyForPowerSave = VOS_FALSE;
+   // assume we won't have to (re)buffer the command
+   bufferCommand = VOS_FALSE;
+   //check to consider the following flowing scenario
+   //Addts request is pending on one AC, while APSD requested on another which 
+   //needs a reassoc. Will buffer a request if Addts is pending on any AC, 
+   //which will safegaurd the above scenario, & also won't confuse PE with back 
+   //to back Addts or Addts followed by Reassoc
+   if(sme_QosIsRspPending(sessionId, ac))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                "%s: %d: buffering the release request for flow %d in state %d "
+                "since another request is pending",
+                __FUNCTION__, __LINE__, 
+                QosFlowID, pACInfo->curr_state );
+      bufferCommand = VOS_TRUE;
+   }
+   else
+   {
+      // make sure we are in full power so that we can issue
+      // a DelTS or reassoc if necessary
+      hstatus = pmcRequestFullPower(pMac, sme_QosPmcFullPowerCallback,
+                                    pSession, eSME_REASON_OTHER);
+      if( eHAL_STATUS_PMC_PENDING == hstatus )
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                   "%s: %d: buffering the release request for flow %d in state %d, "
+                   "waiting for full power",
+                   __FUNCTION__, __LINE__, 
+                   QosFlowID, pACInfo->curr_state );
+         bufferCommand = VOS_TRUE;
+      }
+   }
+   if (bufferCommand)
+   {
+      // we need to buffer the command
+      cmd.command = SME_QOS_RELEASE_REQ;
+      cmd.pMac = pMac;
+      cmd.sessionId = sessionId;
+      cmd.u.releaseCmdInfo.QosFlowID = QosFlowID;
+      hstatus = sme_QosBufferCmd(&cmd, buffered_cmd);
+      if(!HAL_STATUS_SUCCESS(hstatus))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: couldn't buffer the release request in state = %d",
+                   __FUNCTION__, __LINE__,
+                   pACInfo->curr_state );
+         // unable to buffer the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_RELEASE_FAILURE_RSP;
+      }
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Buffered release request for flow = %d",
+                __FUNCTION__, __LINE__,
+                QosFlowID);
+      return SME_QOS_STATUS_RELEASE_REQ_PENDING_RSP;
+   }
+   //get into the stat m/c to see if the request can be granted
+   switch(pACInfo->curr_state)
+   {
+   case SME_QOS_QOS_ON:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                "%s: %d: tspec_mask_status = %d for AC = %d with "
+                "entry tspec_mask = %d",
+                __FUNCTION__, __LINE__, 
+                pACInfo->tspec_mask_status, ac, flow_info->tspec_mask);
+
+      //check if multiple flows running on the ac
+      if(pACInfo->num_flows[flow_info->tspec_mask - 1] > 1)
+      {
+         //don't want to include the flow in the new TSPEC on which release 
+         //is requested
+         flow_info->reason = SME_QOS_REASON_RELEASE;
+
+         /* Check if the flow being released is for bi-diretional.
+          * Following flows may present in the system. 
+          * a) bi-directional flows
+          * b) uplink flows
+          * c) downlink flows. 
+          * If the flow being released is for bidirectional, splitting of existing 
+          * streams into two tspec indices is required in case ff (b), (c) are present 
+          * and not (a).
+          * In case if split occurs, all upstreams are aggregated into tspec index 0, 
+          * downstreams are aggregaed into tspec index 1 and two tspec requests for 
+          * (aggregated) upstream(s) followed by (aggregated) downstream(s) is sent
+          * to AP. */
+         if(flow_info->QoSInfo.ts_info.direction == SME_QOS_WMM_TS_DIR_BOTH)
+         {
+           vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+           //set the key type & the key to be searched in the Flow List
+           search_key.key.ac_type = ac;
+           search_key.index = SME_QOS_SEARCH_KEY_INDEX_4;
+           search_key.sessionId = sessionId;
+           search_key.direction = SME_QOS_WMM_TS_DIR_BOTH;
+           pResult = sme_QosFindInFlowList(search_key);
+           if(pResult)
+             biDirectionalFlowsPresent = VOS_TRUE;
+
+           if(!biDirectionalFlowsPresent)
+           {
+             // The only existing bidirectional flow is being released
+
+             // Check if uplink flows exist
+             search_key.direction = SME_QOS_WMM_TS_DIR_UPLINK;
+             pResult = sme_QosFindInFlowList(search_key);
+             if(pResult)
+               uplinkFlowsPresent = VOS_TRUE;
+
+             // Check if downlink flows exist
+             search_key.direction = SME_QOS_WMM_TS_DIR_DOWNLINK;
+             pResult = sme_QosFindInFlowList(search_key);
+             if(pResult)
+               downlinkFlowsPresent = VOS_TRUE;
+
+             if(uplinkFlowsPresent && downlinkFlowsPresent)
+             {
+               // Need to split the uni-directional flows into SME_QOS_TSPEC_INDEX_0 and SME_QOS_TSPEC_INDEX_1
+
+               vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+               // Mark all downstream flows as using tspec index 1
+               search_key.key.ac_type = ac;
+               search_key.index = SME_QOS_SEARCH_KEY_INDEX_4;
+               search_key.sessionId = sessionId;
+               search_key.direction = SME_QOS_WMM_TS_DIR_DOWNLINK;
+               sme_QosUpdateTspecMask(sessionId, search_key, SME_QOS_TSPEC_MASK_BIT_2_SET);
+
+               // Aggregate all downstream flows
+               hstatus = sme_QosUpdateParams(sessionId,
+                                             ac, SME_QOS_TSPEC_MASK_BIT_2_SET,
+                                             &Aggr_Tspec_Info);
+
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                         "%s: %d: On session %d buffering the AddTS request "
+                            "for AC %d in state %d as Addts is pending "
+                         "on other Tspec index of this AC",
+                         __FUNCTION__, __LINE__,
+                         sessionId, ac, pACInfo->curr_state);
+
+               // Buffer the (aggregated) tspec request for downstream flows.
+               // Please note that the (aggregated) tspec for upstream flows is sent 
+               // out by the susequent logic.
+               cmd.command = SME_QOS_RESEND_REQ;
+               cmd.pMac = pMac;
+               cmd.sessionId = sessionId;
+               cmd.u.resendCmdInfo.ac = ac;
+               cmd.u.resendCmdInfo.tspecMask = SME_QOS_TSPEC_MASK_BIT_2_SET;
+               cmd.u.resendCmdInfo.QoSInfo = Aggr_Tspec_Info;
+               pACInfo->requested_QoSInfo[SME_QOS_TSPEC_MASK_BIT_2_SET - 1] = Aggr_Tspec_Info;
+               if(!HAL_STATUS_SUCCESS(sme_QosBufferCmd(&cmd, VOS_FALSE)))
+               {
+                  VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                            "%s: %d: On session %d unable to buffer the AddTS "
+                            "request for AC %d TSPEC %d in state %d",
+                            __FUNCTION__, __LINE__,
+                            sessionId, ac, SME_QOS_TSPEC_MASK_BIT_2_SET, pACInfo->curr_state);
+
+                  // unable to buffer the request
+                  // nothing is pending so vote powersave back on
+                  pSession->readyForPowerSave = VOS_TRUE;
+
+                  return SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+               }
+               pACInfo->tspec_mask_status = SME_QOS_TSPEC_MASK_BIT_1_2_SET;
+
+             }
+           }
+         }
+
+         /* In case of splitting of existing streams,
+          * tspec_mask will be pointing to tspec index 0 and 
+          * aggregated tspec for upstream(s) is sent out here. */
+         hstatus = sme_QosUpdateParams(sessionId,
+                                       ac, flow_info->tspec_mask,
+                                       &Aggr_Tspec_Info);
+         if(HAL_STATUS_SUCCESS(hstatus))
+         {
+            pACInfo->requested_QoSInfo[flow_info->tspec_mask - 1] = Aggr_Tspec_Info;
+            //if ACM, send out a new ADDTS
+            status = sme_QosSetup(pMac, sessionId,
+                                  &pACInfo->requested_QoSInfo[flow_info->tspec_mask - 1], ac);
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                      "%s: %d: On session %d with AC %d in state SME_QOS_QOS_ON "
+                      "sme_QosSetup returned with status %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac, status);
+            if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP != status)
+            {
+               // we aren't waiting for a response from the AP
+               // so vote powersave back on
+               pSession->readyForPowerSave = VOS_TRUE;
+            }
+            if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP == status) 
+            {
+               new_state = SME_QOS_REQUESTED;
+               status = SME_QOS_STATUS_RELEASE_REQ_PENDING_RSP;
+               pACInfo->tspec_pending = flow_info->tspec_mask;
+            }
+            else if((SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status) ||
+                    (SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status))
+            {
+               new_state = SME_QOS_QOS_ON;
+               pACInfo->num_flows[flow_info->tspec_mask - 1]--;
+               pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1] =
+                  pACInfo->requested_QoSInfo[flow_info->tspec_mask - 1];
+               //delete the entry from Flow List
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: Deleting entry at %p with flowID %d",
+                         __FUNCTION__, __LINE__,
+                         flow_info, QosFlowID);
+               csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+               pDeletedFlow = flow_info;
+               if(SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status)
+               {
+                  vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+                  search_key.key.ac_type = ac;
+                  search_key.index = SME_QOS_SEARCH_KEY_INDEX_2;
+                  search_key.sessionId = sessionId;
+                  hstatus = sme_QosFindAllInFlowList(pMac, search_key, 
+                                                     sme_QosSetupFnp);
+                  if(!HAL_STATUS_SUCCESS(hstatus))
+                  {
+                     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                               "%s: %d: couldn't notify other "
+                               "entries on this AC =%d",
+                               __FUNCTION__, __LINE__, ac);
+                  }
+               }
+               status = SME_QOS_STATUS_RELEASE_SUCCESS_RSP;
+               if(buffered_cmd)
+               {
+                  flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                         &pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1],
+                                         status,
+                                         flow_info->QosFlowID);
+               }
+            }
+            else
+            {
+               // unexpected status returned by sme_QosSetup()
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: On session %d unexpected status %d "
+                         "returned by sme_QosSetup",
+                         __FUNCTION__, __LINE__,
+                         sessionId, status);
+               new_state = SME_QOS_LINK_UP;
+               pACInfo->num_flows[flow_info->tspec_mask - 1]--;
+               pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1] =
+                  pACInfo->requested_QoSInfo[flow_info->tspec_mask - 1];
+               //delete the entry from Flow List
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: On session %d deleting entry at "
+                         "%p with flowID %d",
+                         __FUNCTION__, __LINE__,
+                         sessionId, flow_info, QosFlowID);
+               csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+               pDeletedFlow = flow_info;
+               if(buffered_cmd)
+               {
+                  flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                         &pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1],
+                                         status,
+                                         flow_info->QosFlowID);
+               }
+            }
+         }
+         else
+         {
+            //err msg
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: sme_QosUpdateParams() failed",
+                      __FUNCTION__, __LINE__);
+            // unable to service the request
+            // nothing is pending so vote powersave back on
+            pSession->readyForPowerSave = VOS_TRUE;
+            new_state = SME_QOS_LINK_UP;
+            if(buffered_cmd)
+            {
+               flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                      &pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1],
+                                      status,
+                                      flow_info->QosFlowID);
+            }
+         }
+      }
+      else
+      {
+         // this is the only flow aggregated in this TSPEC
+         status = SME_QOS_STATUS_RELEASE_SUCCESS_RSP;
+#ifdef FEATURE_WLAN_CCX
+         if (ac == SME_QOS_EDCA_AC_VO)
+         {
+            // Indicate to neighbor roam logic of the new required VO
+            // ac bandwidth requirement.
+            csrNeighborRoamIndicateVoiceBW( pMac, pACInfo->curr_QoSInfo[0].peak_data_rate, FALSE );
+         }
+#endif
+         //check if delts needs to be sent
+         if(CSR_IS_ADDTS_WHEN_ACMOFF_SUPPORTED(pMac) ||
+            sme_QosIsACM(pMac, pSession->assocInfo.pBssDesc, ac, NULL))
+         {
+            //check if other TSPEC for this AC is also in use
+            if(SME_QOS_TSPEC_MASK_BIT_1_2_SET != pACInfo->tspec_mask_status)
+            {
+               // this is the only TSPEC active on this AC
+               // so indicate that we no longer require APSD
+               pSession->apsdMask &= ~(1 << (SME_QOS_EDCA_AC_VO - ac));
+               //Also update modifyProfileFields.uapsd_mask in CSR for consistency
+               csrGetModifyProfileFields(pMac, flow_info->sessionId, &modifyProfileFields);
+               modifyProfileFields.uapsd_mask = pSession->apsdMask; 
+               csrSetModifyProfileFields(pMac, flow_info->sessionId, &modifyProfileFields);
+               if(!pSession->apsdMask)
+               {
+                  // this session no longer needs UAPSD
+                  // do any sessions still require UAPSD?
+                  if (!sme_QosIsUapsdActive())
+                  {
+                     // No sessions require UAPSD so turn it off
+                     // (really don't care when PMC stops it)
+                     (void)pmcStopUapsd(pMac);
+                  }
+               }
+            }
+            //send delts
+            hstatus = qosIssueCommand(pMac, sessionId, eSmeCommandDelTs,
+                                      NULL, ac, flow_info->tspec_mask);
+            if(!HAL_STATUS_SUCCESS(hstatus))
+            {
+               //err msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: sme_QosDelTsReq() failed",
+                         __FUNCTION__, __LINE__);
+               status = SME_QOS_STATUS_RELEASE_FAILURE_RSP;
+               // we won't be waiting for a response from the AP
+               // so vote powersave back on
+               pSession->readyForPowerSave = VOS_TRUE;
+            }
+            else
+            {
+               pACInfo->tspec_mask_status &= SME_QOS_TSPEC_MASK_BIT_1_2_SET & 
+                  (~flow_info->tspec_mask);
+               deltsIssued = VOS_TRUE;
+            }
+         }
+         else if(pSession->apsdMask & (1 << (SME_QOS_EDCA_AC_VO - ac)))
+         {
+            //reassoc logic
+            csrGetModifyProfileFields(pMac, sessionId, &modifyProfileFields);
+            modifyProfileFields.uapsd_mask |= pSession->apsdMask;
+            modifyProfileFields.uapsd_mask &= ~(1 << (SME_QOS_EDCA_AC_VO - ac));
+            pSession->apsdMask &= ~(1 << (SME_QOS_EDCA_AC_VO - ac));
+            if(!pSession->apsdMask)
+            {
+               // this session no longer needs UAPSD
+               // do any sessions still require UAPSD?
+               if (!sme_QosIsUapsdActive())
+               {
+                  // No sessions require UAPSD so turn it off
+                  // (really don't care when PMC stops it)
+                  (void)pmcStopUapsd(pMac);
+               }
+            }
+            hstatus = sme_QosRequestReassoc(pMac, sessionId,
+                                            &modifyProfileFields, VOS_FALSE);
+            if(!HAL_STATUS_SUCCESS(hstatus))
+            {
+               //err msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: Reassoc failed",
+                         __FUNCTION__, __LINE__);
+               status = SME_QOS_STATUS_RELEASE_FAILURE_RSP;
+               // we won't be waiting for a response from the AP
+               // so vote powersave back on
+               pSession->readyForPowerSave = VOS_TRUE;
+            }
+            else
+            {
+               pACInfo->reassoc_pending = VOS_FALSE;//no need to wait
+               pACInfo->prev_state = SME_QOS_LINK_UP;
+               pACInfo->tspec_pending = 0;
+            }
+         }
+         else
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                      "%s: %d: nothing to do for AC = %d",
+                      __FUNCTION__, __LINE__, ac);
+            // we won't be waiting for a response from the AP
+            // so vote powersave back on
+            pSession->readyForPowerSave = VOS_TRUE;
+         }
+         if(buffered_cmd)
+         {
+            flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                   NULL,
+                                   status,
+                                   flow_info->QosFlowID);
+         }
+         if(SME_QOS_STATUS_RELEASE_FAILURE_RSP == status)
+         {
+            break;
+         }
+
+         if(((SME_QOS_TSPEC_MASK_BIT_1_2_SET & ~flow_info->tspec_mask) > 0) &&
+            ((SME_QOS_TSPEC_MASK_BIT_1_2_SET & ~flow_info->tspec_mask) <= 
+                SME_QOS_TSPEC_INDEX_MAX))
+         {
+            if(pACInfo->num_flows[(SME_QOS_TSPEC_MASK_BIT_1_2_SET & 
+                                    ~flow_info->tspec_mask) - 1] > 0)
+            {
+               new_state = SME_QOS_QOS_ON;
+            }
+            else
+            {
+               new_state = SME_QOS_LINK_UP;
+            }         
+         }
+         else
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                      "%s: %d: Exceeded the array bounds of pACInfo->num_flows",
+                      __FUNCTION__, __LINE__);
+            VOS_ASSERT (0);
+            return SME_QOS_STATUS_RELEASE_INVALID_PARAMS_RSP;
+         }
+
+         if(VOS_FALSE == deltsIssued)
+         {
+            vos_mem_zero(&pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1], 
+                      sizeof(sme_QosWmmTspecInfo));
+         }
+         vos_mem_zero(&pACInfo->requested_QoSInfo[flow_info->tspec_mask - 1], 
+                      sizeof(sme_QosWmmTspecInfo));
+         pACInfo->num_flows[flow_info->tspec_mask - 1]--;
+         //delete the entry from Flow List
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: On session %d deleting entry at %p with flowID %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId, flow_info, QosFlowID);
+         csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+         pDeletedFlow = flow_info;
+      }
+      /* if we are doing reassoc & we are already in handoff state, no need
+         to move to requested state. But make sure to set the previous state
+         as requested state
+      */
+      if(SME_QOS_HANDOFF != pACInfo->curr_state)
+      {
+         sme_QosStateTransition(sessionId, ac, new_state);
+      }
+      if(pACInfo->reassoc_pending)
+      {
+         pACInfo->prev_state = SME_QOS_REQUESTED;
+      }
+      break;
+   case SME_QOS_HANDOFF:
+   case SME_QOS_REQUESTED:
+      //buffer cmd
+      cmd.command = SME_QOS_RELEASE_REQ;
+      cmd.pMac = pMac;
+      cmd.sessionId = sessionId;
+      cmd.u.releaseCmdInfo.QosFlowID = QosFlowID;
+      hstatus = sme_QosBufferCmd(&cmd, buffered_cmd);
+      if(!HAL_STATUS_SUCCESS(hstatus))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: couldn't buffer the release request in state = %d",
+                   __FUNCTION__, __LINE__,
+                   pACInfo->curr_state );
+         // unable to service the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_RELEASE_FAILURE_RSP;
+      }
+      status = SME_QOS_STATUS_RELEASE_REQ_PENDING_RSP;
+      break;
+   case SME_QOS_CLOSED:
+   case SME_QOS_INIT:
+   case SME_QOS_LINK_UP:
+   default:
+      //print error msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: release request in unexpected state = %d",
+                __FUNCTION__, __LINE__,
+                pACInfo->curr_state );
+      //ASSERT
+      VOS_ASSERT(0);
+      // unable to service the request
+      // nothing is pending so vote powersave back on
+      pSession->readyForPowerSave = VOS_TRUE;
+      break;
+   }
+   // if we deleted a flow, reclaim the memory
+   if (pDeletedFlow)
+   {
+      vos_mem_free(pDeletedFlow);
+   }
+   if((SME_QOS_STATUS_RELEASE_SUCCESS_RSP == status)) 
+   {
+      (void)sme_QosProcessBufferedCmd(sessionId);
+   }
+   return status;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosSetup() - The internal qos setup function which has the 
+  intelligence if the request is NOP, or for APSD and/or need to send out ADDTS.
+  It also does the sanity check for QAP, AP supports APSD etc.
+  \param pMac - Pointer to the global MAC parameter structure.   
+  \param sessionId - Session upon which setup is being performed
+  \param pTspec_Info - Pointer to sme_QosWmmTspecInfo which contains the WMM 
+                       TSPEC related info as defined above
+  \param ac - Enumeration of the various EDCA Access Categories.
+  
+  \return SME_QOS_STATUS_SETUP_SUCCESS_RSP if the setup is successful
+  The logic used in the code might be confusing. Trying to cover all the cases 
+  here.
+  AP supports  App wants   ACM = 1  Already set APSD   Result
+  |    0     |    0     |     0   |       0          |  NO ACM NO APSD
+  |    0     |    0     |     0   |       1          |  NO ACM NO APSD/INVALID
+  |    0     |    0     |     1   |       0          |  ADDTS
+  |    0     |    0     |     1   |       1          |  ADDTS
+  |    0     |    1     |     0   |       0          |  FAILURE
+  |    0     |    1     |     0   |       1          |  INVALID
+  |    0     |    1     |     1   |       0          |  ADDTS
+  |    0     |    1     |     1   |       1          |  ADDTS
+  |    1     |    0     |     0   |       0          |  NO ACM NO APSD
+  |    1     |    0     |     0   |       1          |  NO ACM NO APSD
+  |    1     |    0     |     1   |       0          |  ADDTS
+  |    1     |    0     |     1   |       1          |  ADDTS
+  |    1     |    1     |     0   |       0          |  REASSOC
+  |    1     |    1     |     0   |       1          |  NOP: APSD SET ALREADY
+  |    1     |    1     |     1   |       0          |  ADDTS
+  |    1     |    1     |     1   |       1          |  ADDTS
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosStatusType sme_QosSetup(tpAniSirGlobal pMac,
+                               v_U8_t sessionId,
+                               sme_QosWmmTspecInfo *pTspec_Info, 
+                               sme_QosEdcaAcType ac)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosStatusType status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+   tDot11fBeaconIEs *pIes = NULL;
+   tCsrRoamModifyProfileFields modifyProfileFields;
+   eHalStatus hstatus;
+   if( !CSR_IS_SESSION_VALID( pMac, sessionId ) )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Session Id %d is invalid",
+                __FUNCTION__, __LINE__,
+                sessionId);
+      return status;
+   }
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   if( !pSession->sessionActive )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Session %d is inactive",
+                __FUNCTION__, __LINE__,
+                sessionId);
+      return status;
+   }
+   if(!pSession->assocInfo.pBssDesc)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Session %d has an Invalid BSS Descriptor",
+                __FUNCTION__, __LINE__,
+                sessionId, ac);
+      return status;
+   }
+   hstatus = csrGetParsedBssDescriptionIEs(pMac,
+                                           pSession->assocInfo.pBssDesc,
+                                           &pIes);
+   if(!HAL_STATUS_SUCCESS(hstatus))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                "%s: %d: On session %d unable to parse BSS IEs",
+                __FUNCTION__, __LINE__,
+                sessionId, ac);
+      return status;
+   }
+
+   /* success so pIes was allocated */
+
+   if( !CSR_IS_QOS_BSS(pIes) )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: On session %d AP doesn't support QoS",
+                __FUNCTION__, __LINE__,
+                sessionId);
+      vos_mem_free(pIes);
+      //notify HDD through the synchronous status msg
+      return SME_QOS_STATUS_SETUP_NOT_QOS_AP_RSP;
+   }
+   if(pTspec_Info->max_service_interval || pTspec_Info->min_service_interval)
+   {
+      pTspec_Info->ts_info.psb = 1;
+   }
+   else
+   {
+      pTspec_Info->ts_info.psb = 0;
+   }
+
+   pACInfo = &pSession->ac_info[ac];
+   do
+   {
+      // is ACM enabled for this AC?
+      if(CSR_IS_ADDTS_WHEN_ACMOFF_SUPPORTED(pMac) ||
+         sme_QosIsACM(pMac, pSession->assocInfo.pBssDesc, ac, NULL))
+      {
+         // ACM is enabled for this AC so we must send an AddTS
+         if(pTspec_Info->ts_info.psb && 
+            (!pMac->pmc.uapsdEnabled ))
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                      "%s: %d: Request is looking for APSD but PMC doesn't "
+                      "have support for APSD",
+                      __FUNCTION__, __LINE__);
+            break;
+         }
+         if(SME_QOS_MAX_TID == pTspec_Info->ts_info.tid)
+         {
+            //App didn't set TID, generate one
+            pTspec_Info->ts_info.tid =
+               (v_U8_t)(SME_QOS_WMM_UP_NC - pTspec_Info->ts_info.up);
+         }
+         //addts logic
+         hstatus = qosIssueCommand(pMac, sessionId, eSmeCommandAddTs,
+                                   pTspec_Info, ac, 0);
+         if(!HAL_STATUS_SUCCESS(hstatus))
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: sme_QosAddTsReq() failed",
+                      __FUNCTION__, __LINE__);
+            break;
+         }
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                   "%s: %d: On session %d AddTS on AC %d is pending",
+                   __FUNCTION__, __LINE__,
+                   sessionId, ac);
+         status = SME_QOS_STATUS_SETUP_REQ_PENDING_RSP;
+         break;
+      }
+      // ACM is not enabled for this AC
+      // Is the application looking for APSD?
+      if(0 == pTspec_Info->ts_info.psb)
+      {
+         //no, we don't need APSD
+         //but check the case, if the setup is called as a result of a release 
+         // or modify which boils down to the fact that APSD was set on this AC
+         // but no longer needed - so we need a reassoc for the above case to 
+         // let the AP know
+         if(pSession->apsdMask & (1 << (SME_QOS_EDCA_AC_VO - ac)))
+         {
+            // APSD was formerly enabled on this AC but is no longer required
+            // so we must reassociate
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                      "%s: %d: On session %d reassoc needed "
+                      "to disable APSD on AC %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac);
+            csrGetModifyProfileFields(pMac, sessionId, &modifyProfileFields);
+            modifyProfileFields.uapsd_mask |= pSession->apsdMask;
+            modifyProfileFields.uapsd_mask &= ~(1 << (SME_QOS_EDCA_AC_VO - ac));
+            hstatus = sme_QosRequestReassoc(pMac, sessionId,
+                                            &modifyProfileFields, VOS_FALSE);
+            if(!HAL_STATUS_SUCCESS(hstatus))
+            {
+               //err msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: Unable to request reassociation",
+                         __FUNCTION__, __LINE__);
+               break;
+            }
+            else
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                         "%s: %d: On session %d reassociation to enable "
+                         "APSD on AC %d is pending",
+                         __FUNCTION__, __LINE__,
+                         sessionId, ac);
+               status = SME_QOS_STATUS_SETUP_REQ_PENDING_RSP;
+               pACInfo->reassoc_pending = VOS_TRUE;
+            }
+         }
+         else
+         {
+            // we don't need APSD on this AC
+            // and we don't currently have APSD on this AC
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                      "%s: %d: Request is not looking for APSD & Admission "
+                      "Control isn't mandatory for the AC",
+                      __FUNCTION__, __LINE__);
+            //return success right away
+            status = SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP;
+         }
+         break;
+      }
+      else if(!(pIes->WMMParams.qosInfo & SME_QOS_AP_SUPPORTS_APSD) &&
+              !(pIes->WMMInfoAp.uapsd))
+      {
+         // application is looking for APSD but AP doesn't support it
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: On session %d AP doesn't support APSD",
+                   __FUNCTION__, __LINE__,
+                   sessionId);
+         break;
+      }
+      else if(pSession->apsdMask & (1 << (SME_QOS_EDCA_AC_VO - ac)))
+      {
+         // application is looking for APSD
+         // and it is already enabled on this AC
+         status = SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY;
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: Request is looking for APSD and it is already "
+                   "set for the AC",
+                   __FUNCTION__, __LINE__);
+         break;
+      }
+      else
+      {
+         // application is looking for APSD
+         // but it is not enabled on this AC
+         // so we need to reassociate
+         if(pMac->pmc.uapsdEnabled)
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                      "%s: %d: On session %d reassoc needed "
+                      "to enable APSD on AC %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac);
+            //reassoc logic
+            // update the UAPSD mask to include the new 
+            // AC on which APSD is requested
+            csrGetModifyProfileFields(pMac, sessionId, &modifyProfileFields);
+            modifyProfileFields.uapsd_mask |= pSession->apsdMask;
+            modifyProfileFields.uapsd_mask |= 1 << (SME_QOS_EDCA_AC_VO - ac);
+            hstatus = sme_QosRequestReassoc(pMac, sessionId,
+                                            &modifyProfileFields, VOS_FALSE);
+            if(!HAL_STATUS_SUCCESS(hstatus))
+            {
+               //err msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: Unable to request reassociation",
+                         __FUNCTION__, __LINE__);
+               break;
+            }
+            else
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                         "%s: %d: On session %d reassociation to enable "
+                         "APSD on AC %d is pending",
+                         __FUNCTION__, __LINE__,
+                         sessionId, ac);
+               status = SME_QOS_STATUS_SETUP_REQ_PENDING_RSP;
+               pACInfo->reassoc_pending = VOS_TRUE;
+            }
+         }
+         else
+         {
+            //err msg: no support for APSD from PMC
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: no support for APSD or BMPS from PMC",
+                      __FUNCTION__, __LINE__);
+         }
+      }
+   }while(0);
+
+   vos_mem_free(pIes);
+   return status;
+}
+
+#ifdef FEATURE_WLAN_CCX
+/* This is a dummy function now. But the purpose of me adding this was to 
+ * delay the TSPEC processing till SET_KEY completes. This function can be 
+ * used to do any SME_QOS processing after the SET_KEY. As of now, it is 
+ * not required as we are ok with tspec getting programmed before set_key 
+ * as the roam timings are measured without tspec in reassoc!
+ */
+eHalStatus sme_QosProcessSetKeySuccessInd(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, 
+            "########### CCX Set Key Complete #############");
+    return eHAL_STATUS_SUCCESS;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosCCXSaveTspecResponse() - This function saves the TSPEC
+         parameters that came along in the TSPEC IE in the reassoc response
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param sessionId - SME session ID 
+  \param pTspec - Pointer to the TSPEC IE from the reassoc rsp
+  \param ac - Access Category for which this TSPEC rsp is received
+  \param tspecIndex - flow/direction
+  
+  \return eHAL_STATUS_SUCCESS - Release is successful.
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosCCXSaveTspecResponse(tpAniSirGlobal pMac, v_U8_t sessionId, tDot11fIEWMMTSPEC *pTspec, v_U8_t ac, v_U8_t tspecIndex)
+{
+    tpSirAddtsRsp pAddtsRsp = &sme_QosCb.sessionInfo[sessionId].ac_info[ac].addTsRsp[tspecIndex];
+
+    ac = sme_QosUPtoACMap[pTspec->user_priority];
+
+    vos_mem_zero(pAddtsRsp, sizeof(tSirAddtsRsp));
+
+    pAddtsRsp->messageType = eWNI_SME_ADDTS_RSP;
+    pAddtsRsp->length = sizeof(tSirAddtsRsp);
+    pAddtsRsp->rc = eSIR_SUCCESS;
+    pAddtsRsp->sessionId = sessionId;
+    pAddtsRsp->rsp.dialogToken = 0;
+    pAddtsRsp->rsp.status = eSIR_SUCCESS;
+    pAddtsRsp->rsp.wmeTspecPresent = pTspec->present;
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+            "%s: Copy Tspec to local data structure ac=%d, tspecIdx=%d", 
+            __FUNCTION__, ac, tspecIndex);
+
+    if (pAddtsRsp->rsp.wmeTspecPresent)
+    {
+        //Copy TSPEC params received in assoc response to addts response
+        ConvertWMMTSPEC(pMac, &pAddtsRsp->rsp.tspec, pTspec);
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosCCXProcessReassocTspecRsp() - This function processes the
+         WMM TSPEC IE in the reassoc response. Reassoc triggered as part of 
+         CCX roaming to another CCX capable AP. If the TSPEC was added before 
+         reassoc, as part of Call Admission Control, the reasso req from the
+         STA would carry the TSPEC parameters which were already negotiated
+         with the older AP.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param sessionId - SME session ID 
+  \param pEven_info - Pointer to the smeJoinRsp structure
+  
+  \return eHAL_STATUS_SUCCESS - Release is successful.
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosCCXProcessReassocTspecRsp(tpAniSirGlobal pMac, v_U8_t sessionId, void* pEvent_info)
+{
+    sme_QosSessionInfo *pSession;
+    sme_QosACInfo *pACInfo;
+    tDot11fIEWMMTSPEC *pTspecIE = NULL;
+    tCsrRoamSession *pCsrSession = CSR_GET_SESSION( pMac, sessionId );
+    tCsrRoamConnectedInfo *pCsrConnectedInfo = &pCsrSession->connectedInfo;
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    v_U8_t ac, numTspec, cnt;
+    v_U8_t tspec_flow_index, tspec_mask_status;
+    v_U32_t tspecIeLen;
+
+    pSession = &sme_QosCb.sessionInfo[sessionId];
+
+    // Get the TSPEC IEs which came along with the reassoc response 
+    // from the pbFrames pointer
+    pTspecIE = (tDot11fIEWMMTSPEC *)(pCsrConnectedInfo->pbFrames + pCsrConnectedInfo->nBeaconLength +
+        pCsrConnectedInfo->nAssocReqLength + pCsrConnectedInfo->nAssocRspLength + pCsrConnectedInfo->nRICRspLength);
+
+    // Get the number of tspecs Ies in the frame, the min length
+    // should be atleast equal to the one TSPEC IE 
+    tspecIeLen = pCsrConnectedInfo->nTspecIeLength;
+    if (tspecIeLen < sizeof(tDot11fIEWMMTSPEC)) {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                FL("CCX Tspec IE len %d less than min %d"), 
+                tspecIeLen, sizeof(tDot11fIEWMMTSPEC));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN,
+             "TspecLen = %d, pbFrames = %p, pTspecIE = %p\n", 
+             tspecIeLen, pCsrConnectedInfo->pbFrames, pTspecIE);
+
+    numTspec = (tspecIeLen)/sizeof(tDot11fIEWMMTSPEC);
+    for(cnt=0; cnt<numTspec; cnt++) {
+        ac = sme_QosUpToAc(pTspecIE->user_priority);
+        pACInfo = &pSession->ac_info[ac];
+        tspec_mask_status = pACInfo->tspec_mask_status;
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, 
+                FL("UP=%d, ac=%d, tspec_mask_status=%x"), 
+                pTspecIE->user_priority, ac,  tspec_mask_status );
+
+            for (tspec_flow_index = 0; tspec_flow_index < SME_QOS_TSPEC_INDEX_MAX; tspec_flow_index++) {
+                if (tspec_mask_status & (1 << tspec_flow_index)) {
+                VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, 
+                FL("Found Tspec entry flow = %d AC = %d"),tspec_flow_index, ac);
+                    sme_QosCCXSaveTspecResponse(pMac, sessionId, pTspecIE, ac, tspec_flow_index);
+                } else {
+                VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, 
+                FL("Not found Tspec entry flow = %d AC = %d"),tspec_flow_index, ac);
+                }
+            }
+        // Increment the pointer to point it to the next TSPEC IE
+        pTspecIE++;
+    }
+
+    /* Send the Aggregated QoS request to HAL */
+    status = sme_QosFTAggrQosReq(pMac,sessionId);
+
+    return status;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosCopyTspecInfo() - This function copies the existing TSPEC 
+         parameters from the source structure to the destination structure.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pTspec_Info - source structure
+  \param pTspec - destination structure
+  
+  \return void 
+  --------------------------------------------------------------------------*/
+static void sme_QosCopyTspecInfo(tpAniSirGlobal pMac, sme_QosWmmTspecInfo *pTspec_Info, tSirMacTspecIE* pTspec)
+{
+    /* As per WMM_AC_testplan_v0.39 Minimum Service Interval, Maximum Service
+     * Interval, Service Start Time, Suspension Interval and Delay Bound are
+     * all intended for HCCA operation and therefore must be set to zero*/
+    pTspec->delayBound        = pTspec_Info->delay_bound;
+    pTspec->inactInterval     = pTspec_Info->inactivity_interval;
+    pTspec->length            = SME_QOS_TSPEC_IE_LENGTH;
+    pTspec->maxBurstSz        = pTspec_Info->max_burst_size;
+    pTspec->maxMsduSz         = pTspec_Info->maximum_msdu_size;
+    pTspec->maxSvcInterval    = pTspec_Info->max_service_interval;
+    pTspec->meanDataRate      = pTspec_Info->mean_data_rate;
+    pTspec->mediumTime        = pTspec_Info->medium_time;
+    pTspec->minDataRate       = pTspec_Info->min_data_rate;
+    pTspec->minPhyRate        = pTspec_Info->min_phy_rate;
+    pTspec->minSvcInterval    = pTspec_Info->min_service_interval;
+    pTspec->nomMsduSz         = pTspec_Info->nominal_msdu_size;
+    pTspec->peakDataRate      = pTspec_Info->peak_data_rate;
+    pTspec->surplusBw         = pTspec_Info->surplus_bw_allowance;
+    pTspec->suspendInterval   = pTspec_Info->suspension_interval;
+    pTspec->svcStartTime      = pTspec_Info->svc_start_time;
+    pTspec->tsinfo.traffic.direction = pTspec_Info->ts_info.direction;
+
+    //Make sure UAPSD is allowed. BTC may want to disable UAPSD while keep QoS setup
+    if (pTspec_Info->ts_info.psb && btcIsReadyForUapsd(pMac)) {
+        pTspec->tsinfo.traffic.psb = pTspec_Info->ts_info.psb;
+    } else {
+        pTspec->tsinfo.traffic.psb = 0;
+        pTspec_Info->ts_info.psb = 0;
+    }
+    pTspec->tsinfo.traffic.tsid           = pTspec_Info->ts_info.tid;
+    pTspec->tsinfo.traffic.userPrio       = pTspec_Info->ts_info.up;
+    pTspec->tsinfo.traffic.accessPolicy   = SME_QOS_ACCESS_POLICY_EDCA;
+    pTspec->tsinfo.traffic.burstSizeDefn  = pTspec_Info->ts_info.burst_size_defn;
+    pTspec->tsinfo.traffic.ackPolicy      = pTspec_Info->ts_info.ack_policy;
+    pTspec->type                          = SME_QOS_TSPEC_IE_TYPE;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+            "%s: %d: up = %d, tid = %d",
+            __FUNCTION__, __LINE__,
+            pTspec_Info->ts_info.up,
+            pTspec_Info->ts_info.tid);
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosCCxRetrieveTspecInfo() - This function is called by CSR
+         when try to create reassoc request message to PE - csrSendSmeReassocReqMsg
+         This functions get the existing tspec parameters to be included
+         in the reassoc request.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param sessionId - SME session ID 
+  \param pTspecInfo - Pointer to the structure to carry back the TSPEC parameters
+  
+  \return v_U8_t - number of existing negotiated TSPECs
+  --------------------------------------------------------------------------*/
+v_U8_t sme_QosCCxRetrieveTspecInfo(tpAniSirGlobal pMac, v_U8_t sessionId, tTspecInfo *pTspecInfo)
+{
+    sme_QosSessionInfo *pSession;
+    sme_QosACInfo *pACInfo;
+    v_U8_t tspec_mask_status = 0;
+    v_U8_t tspec_pending_status = 0;
+    v_U8_t ac, numTspecs = 0;
+    tTspecInfo *pDstTspec = pTspecInfo;
+
+    //TODO: Check if TSPEC has already been established, if not return
+
+    pSession = &sme_QosCb.sessionInfo[sessionId];    
+
+    for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) {
+        volatile v_U8_t tspec_index = 0;
+
+        pACInfo = &pSession->ac_info[ac];
+        tspec_pending_status = pACInfo->tspec_pending;
+        tspec_mask_status = pACInfo->tspec_mask_status;
+
+        do {
+            if (tspec_mask_status & SME_QOS_TSPEC_MASK_BIT_1_SET) {
+                /* If a tspec status is pending, take requested_QoSInfo for RIC request, else use curr_QoSInfo
+                   for the RIC request */
+                if (tspec_pending_status & SME_QOS_TSPEC_MASK_BIT_1_SET) {
+                    sme_QosCopyTspecInfo(pMac, &pACInfo->requested_QoSInfo[tspec_index], &pDstTspec->tspec);
+                } else {
+                    sme_QosCopyTspecInfo(pMac, &pACInfo->curr_QoSInfo[tspec_index], &pDstTspec->tspec);
+                }
+                pDstTspec->valid = TRUE;
+                numTspecs++;
+                pDstTspec++;
+            }
+            tspec_mask_status >>= 1;
+            tspec_pending_status >>= 1;
+            tspec_index++;
+        } while (tspec_mask_status);
+    }
+
+    return numTspecs;
+}
+
+#endif
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+
+eHalStatus sme_QosCreateTspecRICIE(tpAniSirGlobal pMac, sme_QosWmmTspecInfo *pTspec_Info,
+                                                       v_U8_t *pRICBuffer, v_U32_t *pRICLength, v_U8_t *pRICIdentifier)
+{
+    tDot11fIERICDataDesc    ricIE;
+    tANI_U32                nStatus;
+
+    VOS_ASSERT(NULL != pRICBuffer);
+    VOS_ASSERT(NULL != pRICLength);
+    VOS_ASSERT(NULL != pRICIdentifier);
+
+    vos_mem_zero(&ricIE, sizeof(tDot11fIERICDataDesc));
+
+    ricIE.present = 1;
+    ricIE.RICData.present = 1;
+    ricIE.RICData.resourceDescCount = 1;
+    ricIE.RICData.statusCode = 0;
+    ricIE.RICData.Identifier = sme_QosAssignDialogToken();
+#ifndef USE_80211_WMMTSPEC_FOR_RIC
+    ricIE.TSPEC.present = 1;
+    ricIE.TSPEC.delay_bound = pTspec_Info->delay_bound;
+    ricIE.TSPEC.inactivity_int = pTspec_Info->inactivity_interval;
+    ricIE.TSPEC.burst_size = pTspec_Info->max_burst_size;
+    ricIE.TSPEC.max_msdu_size = pTspec_Info->maximum_msdu_size;
+    ricIE.TSPEC.max_service_int = pTspec_Info->max_service_interval;
+    ricIE.TSPEC.mean_data_rate = pTspec_Info->mean_data_rate;
+    ricIE.TSPEC.medium_time = pTspec_Info->medium_time;
+    ricIE.TSPEC.min_data_rate = pTspec_Info->min_data_rate;
+    ricIE.TSPEC.min_phy_rate = pTspec_Info->min_phy_rate;
+    ricIE.TSPEC.min_service_int = pTspec_Info->min_service_interval;
+    ricIE.TSPEC.size = pTspec_Info->nominal_msdu_size;
+    ricIE.TSPEC.peak_data_rate = pTspec_Info->peak_data_rate;
+    ricIE.TSPEC.surplus_bw_allowance = pTspec_Info->surplus_bw_allowance;
+    ricIE.TSPEC.suspension_int = pTspec_Info->suspension_interval;
+    ricIE.TSPEC.service_start_time = pTspec_Info->svc_start_time;
+    ricIE.TSPEC.direction = pTspec_Info->ts_info.direction;
+    //Make sure UAPSD is allowed. BTC may want to disable UAPSD while keep QoS setup
+    if( pTspec_Info->ts_info.psb && btcIsReadyForUapsd(pMac) )
+    {
+       ricIE.TSPEC.psb = pTspec_Info->ts_info.psb;
+    }
+    else
+    {
+       ricIE.TSPEC.psb = 0;
+    }
+    ricIE.TSPEC.tsid = pTspec_Info->ts_info.tid;
+    ricIE.TSPEC.user_priority = pTspec_Info->ts_info.up;
+    ricIE.TSPEC.access_policy = SME_QOS_ACCESS_POLICY_EDCA;
+
+    *pRICIdentifier = ricIE.RICData.Identifier;
+    
+    nStatus = dot11fPackIeRICDataDesc(pMac, &ricIE, pRICBuffer, sizeof(ricIE), pRICLength);
+    if (DOT11F_FAILED(nStatus))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                FL("Packing of RIC Data of length %d failed with status %d"), 
+                                        *pRICLength, nStatus);
+    }
+#else // WMM TSPEC
+    /*As per WMM_AC_testplan_v0.39 Minimum Service Interval, Maximum Service 
+      Interval, Service Start Time, Suspension Interval and Delay Bound are 
+      all intended for HCCA operation and therefore must be set to zero*/
+    ricIE.WMMTSPEC.present = 1;
+    ricIE.WMMTSPEC.version = 1;
+    ricIE.WMMTSPEC.delay_bound = pTspec_Info->delay_bound;
+    ricIE.WMMTSPEC.inactivity_int = pTspec_Info->inactivity_interval;
+    ricIE.WMMTSPEC.burst_size = pTspec_Info->max_burst_size;
+    ricIE.WMMTSPEC.max_msdu_size = pTspec_Info->maximum_msdu_size;
+    ricIE.WMMTSPEC.max_service_int = pTspec_Info->max_service_interval;
+    ricIE.WMMTSPEC.mean_data_rate = pTspec_Info->mean_data_rate;
+    ricIE.WMMTSPEC.medium_time = pTspec_Info->medium_time;
+    ricIE.WMMTSPEC.min_data_rate = pTspec_Info->min_data_rate;
+    ricIE.WMMTSPEC.min_phy_rate = pTspec_Info->min_phy_rate;
+    ricIE.WMMTSPEC.min_service_int = pTspec_Info->min_service_interval;
+    ricIE.WMMTSPEC.size = pTspec_Info->nominal_msdu_size;
+    ricIE.WMMTSPEC.peak_data_rate = pTspec_Info->peak_data_rate;
+    ricIE.WMMTSPEC.surplus_bw_allowance = pTspec_Info->surplus_bw_allowance;
+    ricIE.WMMTSPEC.suspension_int = pTspec_Info->suspension_interval;
+    ricIE.WMMTSPEC.service_start_time = pTspec_Info->svc_start_time;
+    ricIE.WMMTSPEC.direction = pTspec_Info->ts_info.direction;
+    //Make sure UAPSD is allowed. BTC may want to disable UAPSD while keep QoS setup
+    if( pTspec_Info->ts_info.psb && btcIsReadyForUapsd(pMac) )
+    {
+       ricIE.WMMTSPEC.psb = pTspec_Info->ts_info.psb;
+    }
+    else
+    {
+       ricIE.WMMTSPEC.psb = 0;
+    }
+    ricIE.WMMTSPEC.tsid = pTspec_Info->ts_info.tid;
+    ricIE.WMMTSPEC.user_priority = pTspec_Info->ts_info.up;
+    ricIE.WMMTSPEC.access_policy = SME_QOS_ACCESS_POLICY_EDCA;
+
+    
+    nStatus = dot11fPackIeRICDataDesc(pMac, &ricIE, pRICBuffer, sizeof(ricIE), pRICLength);
+    if (DOT11F_FAILED(nStatus))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                FL("Packing of RIC Data of length %d failed with status %d"), 
+                                        *pRICLength, nStatus);
+    }
+#endif /* 80211_TSPEC */
+    *pRICIdentifier = ricIE.RICData.Identifier;
+    return nStatus;
+}
+
+eHalStatus sme_QosProcessFTReassocReqEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+    sme_QosSessionInfo *pSession;
+    sme_QosACInfo *pACInfo;
+    v_U8_t ac, qos_requested = FALSE;
+    v_U8_t tspec_flow_index;
+    sme_QosFlowInfoEntry *flow_info = NULL;
+    tListElem *pEntry= NULL;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+            FL("Invoked on session %d"), sessionId);
+
+    pSession = &sme_QosCb.sessionInfo[sessionId];
+
+    for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++)
+    {
+        pACInfo = &pSession->ac_info[ac];
+        qos_requested = FALSE;
+
+        for (tspec_flow_index = 0; tspec_flow_index < SME_QOS_TSPEC_INDEX_MAX; tspec_flow_index++)
+        {
+            /* Only in the below case, copy the AC's curr QoS Info to requested QoS info */
+            if ((pACInfo->ricIdentifier[tspec_flow_index] && !pACInfo->tspec_pending) ||
+                    (pACInfo->tspec_mask_status & (1<<tspec_flow_index)))
+            {
+                VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                        FL("Copying the currentQos to requestedQos for AC=%d, flow=%d\n"),
+                        ac, tspec_flow_index );
+
+                pACInfo->requested_QoSInfo[tspec_flow_index] = pACInfo->curr_QoSInfo[tspec_flow_index];
+                vos_mem_zero(&pACInfo->curr_QoSInfo[tspec_flow_index], sizeof(sme_QosWmmTspecInfo));
+                qos_requested = TRUE;
+            }
+        }
+
+        // Only if the tspec is required, transition the state to 
+        // SME_QOS_REQUESTED for this AC
+        if (qos_requested) 
+        {
+            switch(pACInfo->curr_state)
+            {
+                case SME_QOS_HANDOFF:
+                    sme_QosStateTransition(sessionId, ac, SME_QOS_REQUESTED);
+                    break;
+                default:
+                    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                            FL("FT Reassoc req event in unexpected state %d"), pACInfo->curr_state);
+                    VOS_ASSERT(0);
+            }
+        }
+
+    }
+
+    /* At this point of time, we are disconnected from the old AP, so it is safe
+     *             to reset all these session variables */
+    pSession->apsdMask = 0;
+    pSession->uapsdAlreadyRequested = 0;
+    pSession->readyForPowerSave = 0;
+
+    /* Now change reason and HO renewal of all the flow in this session only */
+    pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_FALSE );
+    if(!pEntry)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN,
+                "%s: %d: Flow List empty, nothing to update",
+                __FUNCTION__, __LINE__);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    do
+    {
+        flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+        if(sessionId == flow_info->sessionId)
+        {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                    "%s: %d: Changing FlowID %d reason to SETUP and HO renewal to FALSE",
+                    __FUNCTION__, __LINE__,
+                    flow_info->QosFlowID);
+            flow_info->reason = SME_QOS_REASON_SETUP;
+            flow_info->hoRenewal = eANI_BOOLEAN_TRUE;
+        }
+        pEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_FALSE );
+    } while( pEntry );
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+eHalStatus sme_QosFTAggrQosReq( tpAniSirGlobal pMac, v_U8_t sessionId )
+{
+    tSirAggrQosReq *pMsg = NULL;
+    sme_QosSessionInfo *pSession;
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    int i, j = 0;
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+            "%s: %d: invoked on session %d", __FUNCTION__, __LINE__,
+            sessionId);
+
+    pSession = &sme_QosCb.sessionInfo[sessionId];
+
+    pMsg = (tSirAggrQosReq *)vos_mem_malloc(sizeof(tSirAggrQosReq));
+
+    if (!pMsg)
+    {
+        //err msg
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                "%s: %d: couldn't allocate memory for the msg buffer",
+                __FUNCTION__, __LINE__);
+
+        return eHAL_STATUS_FAILURE;
+      }
+
+    vos_mem_zero(pMsg, sizeof(tSirAggrQosReq));
+
+    pMsg->messageType = pal_cpu_to_be16((v_U16_t)eWNI_SME_FT_AGGR_QOS_REQ);
+    pMsg->length = sizeof(tSirAggrQosReq);
+    pMsg->sessionId = sessionId;
+    pMsg->timeout = 0;
+    pMsg->rspReqd = VOS_TRUE;
+    vos_mem_copy( &pMsg->bssId[ 0 ],
+            &pSession->assocInfo.pBssDesc->bssId[ 0 ],
+            sizeof(tCsrBssid) );
+
+    for( i = 0; i < SME_QOS_EDCA_AC_MAX; i++ )
+    {
+        for( j = 0; j < SME_QOS_TSPEC_INDEX_MAX; j++ )
+        {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+                    FL("ac=%d, tspec_mask_staus=%x, tspec_index=%d\n"), 
+                    i, pSession->ac_info[i].tspec_mask_status, j);
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                    FL("direction = %d\n"), pSession->ac_info[i].addTsRsp[j].rsp.tspec.tsinfo.traffic.direction);
+            // Check if any flow is active on this AC
+            if ((pSession->ac_info[i].tspec_mask_status) & (1 << j))
+            {
+                tANI_U8 direction = pSession->ac_info[i].addTsRsp[j].rsp.tspec.tsinfo.traffic.direction;
+                if ((direction == SME_QOS_WMM_TS_DIR_UPLINK) ||
+                        (direction == SME_QOS_WMM_TS_DIR_BOTH))
+                {
+                    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, 
+                            FL("Found tspec entry AC=%d, flow=%d, direction = %d\n"), i, j, direction);
+                    pMsg->aggrInfo.aggrAddTsInfo[i].dialogToken =
+                        sme_QosAssignDialogToken();
+                    pMsg->aggrInfo.aggrAddTsInfo[i].lleTspecPresent =
+                        pSession->ac_info[i].addTsRsp[j].rsp.lleTspecPresent;
+                    pMsg->aggrInfo.aggrAddTsInfo[i].numTclas =
+                        pSession->ac_info[i].addTsRsp[j].rsp.numTclas;
+                    vos_mem_copy( pMsg->aggrInfo.aggrAddTsInfo[i].tclasInfo,
+                            pSession->ac_info[i].addTsRsp[j].rsp.tclasInfo,
+                            SIR_MAC_TCLASIE_MAXNUM );
+                    pMsg->aggrInfo.aggrAddTsInfo[i].tclasProc =
+                        pSession->ac_info[i].addTsRsp[j].rsp.tclasProc;
+                    pMsg->aggrInfo.aggrAddTsInfo[i].tclasProcPresent =
+                        pSession->ac_info[i].addTsRsp[j].rsp.tclasProcPresent;
+                    pMsg->aggrInfo.aggrAddTsInfo[i].tspec =
+                        pSession->ac_info[i].addTsRsp[j].rsp.tspec;
+                    pMsg->aggrInfo.aggrAddTsInfo[i].wmeTspecPresent =
+                        pSession->ac_info[i].addTsRsp[j].rsp.wmeTspecPresent;
+                    pMsg->aggrInfo.aggrAddTsInfo[i].wsmTspecPresent =
+                        pSession->ac_info[i].addTsRsp[j].rsp.wsmTspecPresent;
+                    pMsg->aggrInfo.tspecIdx |= ( 1 << i );
+
+                    // Mark the index for this AC as pending for response, which would be 
+                    // used to validate the AddTS response from HAL->PE->SME
+                    pSession->ac_info[i].tspec_pending = (1<<j);
+                }
+            }
+        }
+    }
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+            "Sending aggregated message to HAL 0x%x\n", pMsg->aggrInfo.tspecIdx);
+
+    if(HAL_STATUS_SUCCESS(palSendMBMessage(pMac->hHdd, pMsg)))
+    {
+        status = eHAL_STATUS_SUCCESS;
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                "%s: %d: sent down a AGGR QoS req to PE",
+                __FUNCTION__, __LINE__);
+    }
+
+    return status;
+}
+
+eHalStatus sme_QosProcessFTRICResponse(tpAniSirGlobal pMac, v_U8_t sessionId, tDot11fIERICDataDesc *pRicDataDesc, v_U8_t ac, v_U8_t tspecIndex)
+{
+    tANI_U8        i = 0;
+    tpSirAddtsRsp   pAddtsRsp
+        = &sme_QosCb.sessionInfo[sessionId].ac_info[ac].addTsRsp[tspecIndex];
+
+    vos_mem_zero(pAddtsRsp, sizeof(tSirAddtsRsp));
+
+    pAddtsRsp->messageType = eWNI_SME_ADDTS_RSP;
+    pAddtsRsp->length = sizeof(tSirAddtsRsp);
+    pAddtsRsp->rc = pRicDataDesc->RICData.statusCode;
+    pAddtsRsp->sessionId = sessionId;
+    pAddtsRsp->rsp.dialogToken = pRicDataDesc->RICData.Identifier;
+    pAddtsRsp->rsp.status = pRicDataDesc->RICData.statusCode;
+    pAddtsRsp->rsp.wmeTspecPresent = pRicDataDesc->TSPEC.present;
+    if (pAddtsRsp->rsp.wmeTspecPresent)
+    {
+        //Copy TSPEC params received in RIC response to addts response
+        ConvertTSPEC(pMac, &pAddtsRsp->rsp.tspec, &pRicDataDesc->TSPEC);
+    }
+
+    pAddtsRsp->rsp.numTclas = pRicDataDesc->num_TCLAS;
+    if (pAddtsRsp->rsp.numTclas)
+    {
+        for (i = 0; i < pAddtsRsp->rsp.numTclas; i++)
+        {
+            //Copy TCLAS info per index to the addts response
+            ConvertTCLAS(pMac, &pAddtsRsp->rsp.tclasInfo[i], &pRicDataDesc->TCLAS[i]);
+        }
+    }
+
+    pAddtsRsp->rsp.tclasProcPresent = pRicDataDesc->TCLASSPROC.present;
+    if (pAddtsRsp->rsp.tclasProcPresent)
+        pAddtsRsp->rsp.tclasProc = pRicDataDesc->TCLASSPROC.processing;
+
+
+    pAddtsRsp->rsp.schedulePresent = pRicDataDesc->Schedule.present;
+    if (pAddtsRsp->rsp.schedulePresent)
+   {
+        //Copy Schedule IE params to addts response
+        ConvertSchedule(pMac, &pAddtsRsp->rsp.schedule, &pRicDataDesc->Schedule);
+    }
+
+    //Need to check the below portion is a part of WMM TSPEC
+    //Process Delay element
+    if (pRicDataDesc->TSDelay.present)
+        ConvertTSDelay(pMac, &pAddtsRsp->rsp.delay, &pRicDataDesc->TSDelay);
+    //return sme_QosProcessAddTsRsp(pMac, &addtsRsp);
+    return eHAL_STATUS_SUCCESS;
+   }
+eHalStatus sme_QosProcessAggrQosRsp(tpAniSirGlobal pMac, void *pMsgBuf)
+{
+    tpSirAggrQosRsp pAggrRsp = (tpSirAggrQosRsp)pMsgBuf;
+    tSirAddtsRsp   addtsRsp;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    int i, j = 0;
+    tANI_U8 sessionId = pAggrRsp->sessionId;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+            FL("Received AGGR_QOS resp from LIM"));
+
+    /* Copy over the updated response information for TSPEC of all the ACs */
+    for( i = 0; i < SIR_QOS_NUM_AC_MAX; i++ )
+    {
+        tANI_U8 tspec_mask_status = sme_QosCb.sessionInfo[sessionId].ac_info[i].tspec_mask_status;
+        for( j = 0; j < SME_QOS_TSPEC_INDEX_MAX; j++ ) 
+        {
+            tANI_U8 direction = sme_QosCb.sessionInfo[sessionId].ac_info[i].
+                addTsRsp[j].rsp.tspec.tsinfo.traffic.direction;
+
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+                    FL("Addts rsp from LIM AC=%d, flow=%d dir=%d, tspecIdx=%x\n"),
+                    i, j, direction, pAggrRsp->aggrInfo.tspecIdx);
+            // Check if the direction is Uplink or bi-directional
+            if( ((1<<i) & pAggrRsp->aggrInfo.tspecIdx) &&
+                    ((tspec_mask_status) & (1<<j)) &&
+                    ((direction == SME_QOS_WMM_TS_DIR_UPLINK) ||
+                     (direction == SME_QOS_WMM_TS_DIR_BOTH)))
+            {
+                addtsRsp = sme_QosCb.sessionInfo[sessionId].ac_info[i].addTsRsp[j];
+                addtsRsp.rc = pAggrRsp->aggrInfo.aggrRsp[i].status;
+                addtsRsp.rsp.status = pAggrRsp->aggrInfo.aggrRsp[i].status;
+                addtsRsp.rsp.tspec = pAggrRsp->aggrInfo.aggrRsp[i].tspec;
+
+                VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+                        FL("%s: Processing Addts rsp from LIM AC=%d, flow=%d\n"), i, j);
+                /* post ADD TS response for each */
+                if (sme_QosProcessAddTsRsp(pMac, &addtsRsp) != eHAL_STATUS_SUCCESS)
+                {
+                    status = eHAL_STATUS_FAILURE;
+                }
+            }
+        }
+    }
+   return status;
+}
+
+
+eHalStatus sme_QosProcessFTReassocRspEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+    sme_QosSessionInfo *pSession;
+    sme_QosACInfo *pACInfo;
+    v_U8_t ac;
+    v_U8_t tspec_flow_index;
+    tDot11fIERICDataDesc *pRicDataDesc = NULL;
+    eHalStatus            status = eHAL_STATUS_SUCCESS;
+    tCsrRoamSession *pCsrSession = CSR_GET_SESSION( pMac, sessionId );
+    tCsrRoamConnectedInfo *pCsrConnectedInfo = &pCsrSession->connectedInfo;
+    tANI_U32    ricRspLen = pCsrConnectedInfo->nRICRspLength;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+            "%s: %d: invoked on session %d",
+            __FUNCTION__, __LINE__,
+            sessionId);
+
+    pSession = &sme_QosCb.sessionInfo[sessionId];
+
+    pRicDataDesc = (tDot11fIERICDataDesc *)pCsrConnectedInfo->pbFrames + pCsrConnectedInfo->nBeaconLength +
+        pCsrConnectedInfo->nAssocReqLength + pCsrConnectedInfo->nAssocRspLength;
+
+    for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++)
+    {
+        pACInfo = &pSession->ac_info[ac];
+
+        for (tspec_flow_index = 0; tspec_flow_index < SME_QOS_TSPEC_INDEX_MAX; tspec_flow_index++)
+        {
+            /* Only in the below case, copy the AC's curr QoS Info to requested QoS info */
+            if (pACInfo->ricIdentifier[tspec_flow_index])
+            {
+
+                if (!ricRspLen)
+                {
+                    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                            FL("RIC Response not received for AC %d on TSPEC Index %d, RIC Req Identifier = %d"),
+                            ac, tspec_flow_index, pACInfo->ricIdentifier[tspec_flow_index]);
+                    VOS_ASSERT(0);
+                }
+                else
+                {
+                    /* Now we got response for this identifier. Process it. */
+                    if (pRicDataDesc->present)
+                    {
+                        if (pRicDataDesc->RICData.present)
+                        {
+                            if (pRicDataDesc->RICData.Identifier != pACInfo->ricIdentifier[tspec_flow_index])
+                            {
+                                VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                                        FL("RIC response order not same as request sent. Request ID = %d, Response ID = %d"),
+                                        pACInfo->ricIdentifier[tspec_flow_index], pRicDataDesc->RICData.Identifier);
+                                VOS_ASSERT(0);
+                            }
+                            else
+                            {
+                                VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                                        FL("Processing RIC Response for AC %d, TSPEC Flow index %d with RIC ID %d \n"),
+                                        ac, tspec_flow_index, pRicDataDesc->RICData.Identifier);
+                                status = sme_QosProcessFTRICResponse(pMac, sessionId, pRicDataDesc, ac, tspec_flow_index);
+                                if (eHAL_STATUS_SUCCESS != status)
+                                {
+                                    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                                            FL("Failed with status %d for AC %d in TSPEC Flow index = %d\n"),
+                                            status, ac, tspec_flow_index);
+                                }
+                            }
+                            pRicDataDesc++;
+                            ricRspLen -= sizeof(tDot11fIERICDataDesc);
+                        }
+                    }
+                }
+            }
+
+        }
+    }
+
+    if (ricRspLen)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                FL("RIC Response still follows despite traversing through all ACs. Remaining len = %d\n"), ricRspLen);
+        VOS_ASSERT(0);
+    }
+
+    /* Send the Aggregated QoS request to HAL */
+    status = sme_QosFTAggrQosReq(pMac,sessionId);
+
+    return status;
+}
+
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+
+
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosAddTsReq() - To send down the ADDTS request with TSPEC params
+  to PE 
+  
+ 
+  \param pMac - Pointer to the global MAC parameter structure.  
+  \param sessionId - Session upon which the TSPEC should be added
+  \param pTspec_Info - Pointer to sme_QosWmmTspecInfo which contains the WMM 
+                       TSPEC related info as defined above
+  \param ac - Enumeration of the various EDCA Access Categories.
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosAddTsReq(tpAniSirGlobal pMac,
+                           v_U8_t sessionId,
+                           sme_QosWmmTspecInfo * pTspec_Info,
+                           sme_QosEdcaAcType ac)
+{
+   tSirAddtsReq *pMsg = NULL;
+   sme_QosSessionInfo *pSession;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+#ifdef FEATURE_WLAN_CCX
+   tCsrRoamSession *pCsrSession = CSR_GET_SESSION( pMac, sessionId );
+#endif
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+   WLAN_VOS_DIAG_EVENT_DEF(qos, vos_event_wlan_qos_payload_type);
+#endif
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d for AC %d",
+             __FUNCTION__, __LINE__,
+             sessionId, ac);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pMsg = (tSirAddtsReq *)vos_mem_malloc(sizeof(tSirAddtsReq));
+   if (!pMsg)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: couldn't allocate memory for the msg buffer",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   vos_mem_zero(pMsg, sizeof(tSirAddtsReq));
+   pMsg->messageType = pal_cpu_to_be16((v_U16_t)eWNI_SME_ADDTS_REQ);
+   pMsg->length = sizeof(tSirAddtsReq);
+   pMsg->sessionId = sessionId;
+   pMsg->timeout = 0;
+   pMsg->rspReqd = VOS_TRUE;
+   pMsg->req.dialogToken = sme_QosAssignDialogToken();
+   /*As per WMM_AC_testplan_v0.39 Minimum Service Interval, Maximum Service 
+     Interval, Service Start Time, Suspension Interval and Delay Bound are 
+     all intended for HCCA operation and therefore must be set to zero*/
+   pMsg->req.tspec.delayBound = 0;
+   pMsg->req.tspec.inactInterval = pTspec_Info->inactivity_interval;
+   pMsg->req.tspec.length = SME_QOS_TSPEC_IE_LENGTH;
+   pMsg->req.tspec.maxBurstSz = pTspec_Info->max_burst_size;
+   pMsg->req.tspec.maxMsduSz = pTspec_Info->maximum_msdu_size;
+   pMsg->req.tspec.maxSvcInterval = pTspec_Info->max_service_interval;
+   pMsg->req.tspec.meanDataRate = pTspec_Info->mean_data_rate;
+   pMsg->req.tspec.mediumTime = pTspec_Info->medium_time;
+   pMsg->req.tspec.minDataRate = pTspec_Info->min_data_rate;
+   pMsg->req.tspec.minPhyRate = pTspec_Info->min_phy_rate;
+   pMsg->req.tspec.minSvcInterval = pTspec_Info->min_service_interval;
+   pMsg->req.tspec.nomMsduSz = pTspec_Info->nominal_msdu_size;
+   pMsg->req.tspec.peakDataRate = pTspec_Info->peak_data_rate;
+   pMsg->req.tspec.surplusBw = pTspec_Info->surplus_bw_allowance;
+   pMsg->req.tspec.suspendInterval = pTspec_Info->suspension_interval;
+   pMsg->req.tspec.svcStartTime = 0;
+   pMsg->req.tspec.tsinfo.traffic.direction = pTspec_Info->ts_info.direction;
+   //Make sure UAPSD is allowed. BTC may want to disable UAPSD while keep QoS setup
+   if( pTspec_Info->ts_info.psb 
+         && btcIsReadyForUapsd(pMac) 
+     )
+   {
+      pMsg->req.tspec.tsinfo.traffic.psb = pTspec_Info->ts_info.psb;
+   }
+   else
+   {
+      pMsg->req.tspec.tsinfo.traffic.psb = 0;
+      pTspec_Info->ts_info.psb = 0;
+   }
+   pMsg->req.tspec.tsinfo.traffic.tsid = pTspec_Info->ts_info.tid;
+   pMsg->req.tspec.tsinfo.traffic.userPrio = pTspec_Info->ts_info.up;
+   pMsg->req.tspec.tsinfo.traffic.accessPolicy = SME_QOS_ACCESS_POLICY_EDCA;
+   pMsg->req.tspec.tsinfo.traffic.burstSizeDefn = pTspec_Info->ts_info.burst_size_defn;
+   pMsg->req.tspec.tsinfo.traffic.ackPolicy = pTspec_Info->ts_info.ack_policy;
+   pMsg->req.tspec.type = SME_QOS_TSPEC_IE_TYPE;
+   /*Fill the BSSID pMsg->req.bssId*/
+   if (NULL == pSession->assocInfo.pBssDesc)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: BSS descriptor is NULL so we don't send requst to PE",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   vos_mem_copy( &pMsg->bssId[ 0 ], 
+                 &pSession->assocInfo.pBssDesc->bssId[ 0 ], 
+                 sizeof(tCsrBssid) );
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: up = %d, tid = %d",
+             __FUNCTION__, __LINE__, 
+             pTspec_Info->ts_info.up,
+             pTspec_Info->ts_info.tid);
+#ifdef FEATURE_WLAN_CCX
+   if(pCsrSession->connectedProfile.isCCXAssoc)
+   {
+      pMsg->req.tsrsIE.tsid = pTspec_Info->ts_info.up;
+      pMsg->req.tsrsPresent = 1;
+   }
+#endif
+   if(HAL_STATUS_SUCCESS(palSendMBMessage(pMac->hHdd, pMsg)))
+   {
+      status = eHAL_STATUS_SUCCESS;
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: sent down a ADDTS req to PE",
+                __FUNCTION__, __LINE__);
+      //event: EVENT_WLAN_QOS
+#ifdef FEATURE_WLAN_DIAG_SUPPORT          
+      qos.eventId = SME_QOS_DIAG_ADDTS_REQ;
+      qos.reasonCode = SME_QOS_DIAG_USER_REQUESTED;
+      WLAN_VOS_DIAG_EVENT_REPORT(&qos, EVENT_WLAN_QOS);
+#endif //FEATURE_WLAN_DIAG_SUPPORT
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosDelTsReq() - To send down the DELTS request with TSPEC params
+  to PE 
+  
+ 
+  \param pMac - Pointer to the global MAC parameter structure.  
+  \param sessionId - Session from which the TSPEC should be deleted
+  \param ac - Enumeration of the various EDCA Access Categories.
+  \param tspec_mask - on which tspec per AC, the delts is requested
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosDelTsReq(tpAniSirGlobal pMac,
+                           v_U8_t sessionId,
+                           sme_QosEdcaAcType ac,
+                           v_U8_t tspec_mask)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   tSirDeltsReq *pMsg;
+   sme_QosWmmTspecInfo *pTspecInfo;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+   WLAN_VOS_DIAG_EVENT_DEF(qos, vos_event_wlan_qos_payload_type);
+#endif
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d for AC %d",
+             __FUNCTION__, __LINE__,
+             sessionId, ac);
+   pMsg = (tSirDeltsReq *)vos_mem_malloc(sizeof(tSirDeltsReq));
+   if (!pMsg)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: couldn't allocate memory for the msg buffer",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   vos_mem_zero(pMsg, sizeof(tSirDeltsReq));
+   // get pointer to the TSPEC being deleted
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   pTspecInfo = &pACInfo->curr_QoSInfo[tspec_mask - 1];
+   pMsg->messageType = pal_cpu_to_be16((v_U16_t)eWNI_SME_DELTS_REQ);
+   pMsg->length = sizeof(tSirDeltsReq);
+   pMsg->sessionId = sessionId;
+   pMsg->rspReqd = VOS_TRUE;
+   pMsg->req.tspec.delayBound = pTspecInfo->delay_bound;
+   pMsg->req.tspec.inactInterval = pTspecInfo->inactivity_interval;
+   pMsg->req.tspec.length = SME_QOS_TSPEC_IE_LENGTH;
+   pMsg->req.tspec.maxBurstSz = pTspecInfo->max_burst_size;
+   pMsg->req.tspec.maxMsduSz = pTspecInfo->maximum_msdu_size;
+   pMsg->req.tspec.maxSvcInterval = pTspecInfo->max_service_interval;
+   pMsg->req.tspec.meanDataRate = pTspecInfo->mean_data_rate;
+   pMsg->req.tspec.mediumTime = pTspecInfo->medium_time;
+   pMsg->req.tspec.minDataRate = pTspecInfo->min_data_rate;
+   pMsg->req.tspec.minPhyRate = pTspecInfo->min_phy_rate;
+   pMsg->req.tspec.minSvcInterval = pTspecInfo->min_service_interval;
+   pMsg->req.tspec.nomMsduSz = pTspecInfo->nominal_msdu_size;
+   pMsg->req.tspec.peakDataRate = pTspecInfo->peak_data_rate;
+   pMsg->req.tspec.surplusBw = pTspecInfo->surplus_bw_allowance;
+   pMsg->req.tspec.suspendInterval = pTspecInfo->suspension_interval;
+   pMsg->req.tspec.svcStartTime = pTspecInfo->svc_start_time;
+   pMsg->req.tspec.tsinfo.traffic.direction = pTspecInfo->ts_info.direction;
+   pMsg->req.tspec.tsinfo.traffic.psb = pTspecInfo->ts_info.psb;
+   pMsg->req.tspec.tsinfo.traffic.tsid = pTspecInfo->ts_info.tid;
+   pMsg->req.tspec.tsinfo.traffic.userPrio = pTspecInfo->ts_info.up;
+   pMsg->req.tspec.tsinfo.traffic.accessPolicy = SME_QOS_ACCESS_POLICY_EDCA;
+   pMsg->req.tspec.tsinfo.traffic.burstSizeDefn = pTspecInfo->ts_info.burst_size_defn;
+   pMsg->req.tspec.tsinfo.traffic.ackPolicy = pTspecInfo->ts_info.ack_policy;
+   pMsg->req.tspec.type = SME_QOS_TSPEC_IE_TYPE;
+   /*Fill the BSSID pMsg->req.bssId*/
+   if (NULL == pSession->assocInfo.pBssDesc)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: BSS descriptor is NULL so we don't send request to PE",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   vos_mem_copy( &pMsg->bssId[ 0 ], 
+                 &pSession->assocInfo.pBssDesc->bssId[ 0 ], 
+                 sizeof(tCsrBssid) );
+
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: up = %d, tid = %d",
+             __FUNCTION__, __LINE__, 
+             pTspecInfo->ts_info.up,
+             pTspecInfo->ts_info.tid);
+   vos_mem_zero(&pACInfo->curr_QoSInfo[tspec_mask - 1], 
+                sizeof(sme_QosWmmTspecInfo));
+   if(HAL_STATUS_SUCCESS(palSendMBMessage(pMac->hHdd, pMsg)))
+   {
+      status = eHAL_STATUS_SUCCESS;
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: sme_QosDelTsReq:Test: sent down a DELTS req to PE",
+                __FUNCTION__, __LINE__);
+      //event: EVENT_WLAN_QOS
+#ifdef FEATURE_WLAN_DIAG_SUPPORT          
+      qos.eventId = SME_QOS_DIAG_DELTS;
+      qos.reasonCode = SME_QOS_DIAG_USER_REQUESTED;
+      WLAN_VOS_DIAG_EVENT_REPORT(&qos, EVENT_WLAN_QOS);
+#endif //FEATURE_WLAN_DIAG_SUPPORT
+   }
+
+   return status;
+}
+
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessAddTsRsp() - Function to process the
+  eWNI_SME_ADDTS_RSP came from PE 
+  
+  \param pMac - Pointer to the global MAC parameter structure.  
+  \param pMsgBuf - Pointer to the msg buffer came from PE.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessAddTsRsp(tpAniSirGlobal pMac, void *pMsgBuf)
+{
+   tpSirAddtsRsp paddts_rsp = (tpSirAddtsRsp)pMsgBuf;
+   sme_QosSessionInfo *pSession;
+   v_U8_t sessionId = paddts_rsp->sessionId;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    sme_QosWmmUpType up = (sme_QosWmmUpType)paddts_rsp->rsp.tspec.tsinfo.traffic.userPrio;
+    sme_QosACInfo *pACInfo;
+    sme_QosEdcaAcType ac;
+#endif
+
+    pSession = &sme_QosCb.sessionInfo[sessionId];
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+            "%s: %d: invoked on session %d for UP %d",
+            __FUNCTION__, __LINE__,
+            sessionId, up);
+
+    ac = sme_QosUpToAc(up);
+    if(SME_QOS_EDCA_AC_MAX == ac)
+    {
+        //err msg
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: invalid AC %d from UP %d",
+                __FUNCTION__, __LINE__, ac, up);
+
+        return eHAL_STATUS_FAILURE;
+    }
+    pACInfo = &pSession->ac_info[ac];   
+    if (SME_QOS_HANDOFF == pACInfo->curr_state)
+    {
+        smsLog(pMac, LOG1, FL("ADDTS Response received for AC %d in HANDOFF State.. Dropping"), ac);
+        pSession->readyForPowerSave = VOS_TRUE;
+        return eHAL_STATUS_SUCCESS;
+    }
+#endif
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+   WLAN_VOS_DIAG_EVENT_DEF(qos, vos_event_wlan_qos_payload_type);
+#endif
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: Invoked on session %d with return code %d",
+             __FUNCTION__, __LINE__,
+             sessionId, paddts_rsp->rc);
+   // our outstanding request has been serviced
+   // we can go into powersave
+   pSession->readyForPowerSave = VOS_TRUE;
+   if(paddts_rsp->rc)
+   {
+      //event: EVENT_WLAN_QOS
+#ifdef FEATURE_WLAN_DIAG_SUPPORT          
+      qos.eventId = SME_QOS_DIAG_ADDTS_RSP;
+      qos.reasonCode = SME_QOS_DIAG_ADDTS_REFUSED;
+      WLAN_VOS_DIAG_EVENT_REPORT(&qos, EVENT_WLAN_QOS);
+#endif //FEATURE_WLAN_DIAG_SUPPORT
+      status = sme_QosProcessAddTsFailureRsp(pMac, sessionId, &paddts_rsp->rsp);
+   }
+   else
+   {
+      status = sme_QosProcessAddTsSuccessRsp(pMac, sessionId, &paddts_rsp->rsp);
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessDelTsRsp() - Function to process the
+  eWNI_SME_DELTS_RSP came from PE 
+  
+  \param pMac - Pointer to the global MAC parameter structure.  
+  \param pMsgBuf - Pointer to the msg buffer came from PE.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessDelTsRsp(tpAniSirGlobal pMac, void *pMsgBuf)
+{
+   tpSirDeltsRsp pDeltsRsp = (tpSirDeltsRsp)pMsgBuf;
+   sme_QosSessionInfo *pSession;
+   v_U8_t sessionId = pDeltsRsp->sessionId;
+   // msg
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: Invoked on session %d with return code %d",
+             __FUNCTION__, __LINE__,
+             sessionId, pDeltsRsp->rc);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   // our outstanding request has been serviced
+   // we can go into powersave
+   pSession->readyForPowerSave = VOS_TRUE;
+   (void)sme_QosProcessBufferedCmd(sessionId);
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessDelTsInd() - Function to process the
+  eWNI_SME_DELTS_IND came from PE 
+  
+  Since it's a DELTS indication from AP, will notify all the flows running on 
+  this AC about QoS release
+  \param pMac - Pointer to the global MAC parameter structure.  
+  \param pMsgBuf - Pointer to the msg buffer came from PE.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessDelTsInd(tpAniSirGlobal pMac, void *pMsgBuf)
+{
+   tpSirDeltsRsp pdeltsind = (tpSirDeltsRsp)pMsgBuf;
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   v_U8_t sessionId = pdeltsind->sessionId;
+   sme_QosEdcaAcType ac;
+   sme_QosSearchInfo search_key;
+   sme_QosWmmUpType up = (sme_QosWmmUpType)pdeltsind->rsp.tspec.tsinfo.traffic.userPrio;
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+   WLAN_VOS_DIAG_EVENT_DEF(qos, vos_event_wlan_qos_payload_type);
+#endif
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: Invoked on session %d for UP %d",
+             __FUNCTION__, __LINE__,
+             sessionId, up);
+   ac = sme_QosUpToAc(up);
+   if(SME_QOS_EDCA_AC_MAX == ac)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: invalid AC %d from UP %d",
+                __FUNCTION__, __LINE__,
+                ac, up);
+      return eHAL_STATUS_FAILURE;
+   }
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pACInfo = &pSession->ac_info[ac];
+
+   vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+   //set the key type & the key to be searched in the Flow List
+   search_key.key.ac_type = ac;
+   search_key.index = SME_QOS_SEARCH_KEY_INDEX_2;
+   search_key.sessionId = sessionId;
+   //find all Flows on the perticular AC & delete them, also send HDD indication
+   // through the callback it registered per request
+   if(!HAL_STATUS_SUCCESS(sme_QosFindAllInFlowList(pMac, search_key, sme_QosDelTsIndFnp)))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: no match found for ac = %d",
+                __FUNCTION__, __LINE__, 
+                search_key.key.ac_type);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   //clean up the CB
+   vos_mem_zero(&pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0], 
+                sizeof(sme_QosWmmTspecInfo));
+   vos_mem_zero(&pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0], 
+                sizeof(sme_QosWmmTspecInfo));
+   vos_mem_zero(&pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_1], 
+                sizeof(sme_QosWmmTspecInfo));
+   vos_mem_zero(&pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_1], 
+                sizeof(sme_QosWmmTspecInfo));
+   pACInfo->tspec_mask_status = SME_QOS_TSPEC_MASK_CLEAR;
+   pACInfo->tspec_pending = 0;
+   //event: EVENT_WLAN_QOS
+#ifdef FEATURE_WLAN_DIAG_SUPPORT          
+   qos.eventId = SME_QOS_DIAG_DELTS;
+   qos.reasonCode = SME_QOS_DIAG_DELTS_IND_FROM_AP;
+   WLAN_VOS_DIAG_EVENT_REPORT(&qos, EVENT_WLAN_QOS);
+#endif //FEATURE_WLAN_DIAG_SUPPORT
+
+   sme_QosStateTransition(sessionId, ac, SME_QOS_LINK_UP);
+   (void)sme_QosProcessBufferedCmd(sessionId);
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessAssocCompleteEv() - Function to process the
+  SME_QOS_CSR_ASSOC_COMPLETE event indication from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessAssocCompleteEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   sme_QosEdcaAcType ac = SME_QOS_EDCA_AC_BE;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   if(((SME_QOS_INIT == pSession->ac_info[SME_QOS_EDCA_AC_BE].curr_state)&&
+       (SME_QOS_INIT == pSession->ac_info[SME_QOS_EDCA_AC_BK].curr_state)&&
+       (SME_QOS_INIT == pSession->ac_info[SME_QOS_EDCA_AC_VI].curr_state)&&
+       (SME_QOS_INIT == pSession->ac_info[SME_QOS_EDCA_AC_VO].curr_state)) ||
+       (pSession->handoffRequested))
+   {
+      //get the association info
+      if(!pEvent_info)
+      {
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: pEvent_info is NULL",
+                   __FUNCTION__, __LINE__);
+         return status;
+      }
+      if(!((sme_QosAssocInfo *)pEvent_info)->pBssDesc)
+      {
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: pBssDesc is NULL",
+                   __FUNCTION__, __LINE__);
+         return status;
+      }
+      if((pSession->assocInfo.pBssDesc) &&
+         (csrIsBssidMatch(pMac, (tCsrBssid *)&pSession->assocInfo.pBssDesc->bssId, 
+                          (tCsrBssid *) &(((sme_QosAssocInfo *)pEvent_info)->pBssDesc->bssId))))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: assoc with the same BSS, no update needed",
+                   __FUNCTION__, __LINE__);
+      }
+      else
+      {
+         status = sme_QosSaveAssocInfo(pSession, pEvent_info);
+      }
+   }
+   else
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: wrong state: BE %d, BK %d, VI %d, VO %d",
+                __FUNCTION__, __LINE__,
+                pSession->ac_info[SME_QOS_EDCA_AC_BE].curr_state,
+                pSession->ac_info[SME_QOS_EDCA_AC_BK].curr_state,
+                pSession->ac_info[SME_QOS_EDCA_AC_VI].curr_state,
+                pSession->ac_info[SME_QOS_EDCA_AC_VO].curr_state);
+      //ASSERT
+      VOS_ASSERT(0);
+      return status;
+   }
+   // the session is active
+   pSession->sessionActive = VOS_TRUE;
+   if(pSession->handoffRequested)
+   {
+      pSession->handoffRequested = VOS_FALSE;
+      //renew all flows
+      (void)sme_QosProcessBufferedCmd(sessionId);
+      status = eHAL_STATUS_SUCCESS;
+   }
+   else
+   {
+      for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+      {
+         pACInfo = &pSession->ac_info[ac];
+         switch(pACInfo->curr_state)
+         {
+            case SME_QOS_INIT:
+               sme_QosStateTransition(sessionId, ac, SME_QOS_LINK_UP);
+               break;
+            case SME_QOS_LINK_UP:
+            case SME_QOS_REQUESTED:
+            case SME_QOS_QOS_ON:
+            case SME_QOS_HANDOFF:
+            case SME_QOS_CLOSED:
+            default:
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: On session %d AC %d is in wrong state %d",
+                         __FUNCTION__, __LINE__,
+                         sessionId, ac, pACInfo->curr_state);
+               //ASSERT
+               VOS_ASSERT(0);
+               break;
+         }
+      }
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessReassocReqEv() - Function to process the
+  SME_QOS_CSR_REASSOC_REQ event indication from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessReassocReqEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosEdcaAcType ac;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+   if(pSession->ftHandoffInProgress)
+   {
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+               "%s: %d: no need for state transition, should "
+               "already be in handoff state",
+               __FUNCTION__, __LINE__);
+       VOS_ASSERT(pSession->ac_info[0].curr_state == SME_QOS_HANDOFF);
+       VOS_ASSERT(pSession->ac_info[1].curr_state == SME_QOS_HANDOFF);
+       VOS_ASSERT(pSession->ac_info[2].curr_state == SME_QOS_HANDOFF);
+       VOS_ASSERT(pSession->ac_info[3].curr_state == SME_QOS_HANDOFF);
+       sme_QosProcessFTReassocReqEv(pMac, sessionId, pEvent_info);
+       return eHAL_STATUS_SUCCESS;
+   }
+#endif
+
+   if(pSession->handoffRequested)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: no need for state transition, should "
+                "already be in handoff state",
+                __FUNCTION__, __LINE__);
+      VOS_ASSERT(pSession->ac_info[0].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[1].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[2].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[3].curr_state == SME_QOS_HANDOFF);
+
+      //buffer the existing flows to be renewed after handoff is done
+      sme_QosBufferExistingFlows(pMac, sessionId);
+      //clean up the control block partially for handoff
+      sme_QosCleanupCtrlBlkForHandoff(pMac, sessionId);
+      return eHAL_STATUS_SUCCESS;
+   }
+//TBH: Assuming both handoff algo & 11r willn't be enabled at the same time
+#ifdef WLAN_FEATURE_VOWIFI_11R
+   if(pSession->ftHandoffInProgress)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: no need for state transition, should "
+                "already be in handoff state",
+                __FUNCTION__, __LINE__);
+      VOS_ASSERT(pSession->ac_info[0].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[1].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[2].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[3].curr_state == SME_QOS_HANDOFF);
+
+      sme_QosProcessFTReassocReqEv(pMac, sessionId, pEvent_info);
+      return eHAL_STATUS_SUCCESS;
+   }
+#endif
+
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      pACInfo = &pSession->ac_info[ac];
+      switch(pACInfo->curr_state)
+      {
+         case SME_QOS_LINK_UP:
+         case SME_QOS_REQUESTED:
+         case SME_QOS_QOS_ON:
+            sme_QosStateTransition(sessionId, ac, SME_QOS_HANDOFF);
+            break;
+         case SME_QOS_HANDOFF:
+            //This is normal because sme_QosRequestReassoc may already change the state
+            break;
+         case SME_QOS_CLOSED:
+         case SME_QOS_INIT:
+         default:
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: On session %d AC %d is in wrong state %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac, pACInfo->curr_state);
+            //ASSERT
+            VOS_ASSERT(0);
+            break;
+      }
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessReassocSuccessEv() - Function to process the
+  SME_QOS_CSR_REASSOC_COMPLETE event indication from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessReassocSuccessEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   tpSirSmeJoinRsp pSmeJoinRsp = (tpSirSmeJoinRsp) pEvent_info;
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosEdcaAcType ac, ac_index;
+   sme_QosSearchInfo search_key;
+   sme_QosSearchInfo search_key1;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tListElem *pEntry= NULL;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   // our pending reassociation has completed
+   // we can allow powersave
+   pSession->readyForPowerSave = VOS_TRUE;
+   //get the association info
+   if(!pEvent_info)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: pEvent_info is NULL",
+                __FUNCTION__, __LINE__);
+      return status;
+   }
+   if(!((sme_QosAssocInfo *)pEvent_info)->pBssDesc)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: pBssDesc is NULL",
+                __FUNCTION__, __LINE__);
+      return status;
+   }
+   status = sme_QosSaveAssocInfo(pSession, pEvent_info);
+   if(status)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: sme_QosSaveAssocInfo() failed",
+                __FUNCTION__, __LINE__);
+   }
+//TBH: Assuming both handoff algo & 11r willn't be enabled at the same time   
+   if(pSession->handoffRequested)
+   {
+      pSession->handoffRequested = VOS_FALSE;
+      //renew all flows
+      (void)sme_QosProcessBufferedCmd(sessionId);
+      return eHAL_STATUS_SUCCESS;
+   }
+#ifdef WLAN_FEATURE_VOWIFI_11R
+   if (pSession->ftHandoffInProgress)
+   {
+       if (csrRoamIs11rAssoc(pMac)) {
+           if (pSmeJoinRsp->parsedRicRspLen) {
+               status = sme_QosProcessFTReassocRspEv(pMac, sessionId, pEvent_info);
+           }
+       }
+#ifdef FEATURE_WLAN_CCX
+       // If CCX association check for TSPEC IEs in the reassoc rsp frame
+       if (csrRoamIsCCXAssoc(pMac)) {
+           if (pSmeJoinRsp->tspecIeLen) {
+               status = sme_QosCCXProcessReassocTspecRsp(pMac, sessionId, pEvent_info);
+           }
+       }
+#endif
+       pSession->ftHandoffInProgress = VOS_FALSE;
+       pSession->handoffRequested = VOS_FALSE;
+       return status;
+   }
+#endif
+
+   pSession->sessionActive = VOS_TRUE;
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      pACInfo = &pSession->ac_info[ac];
+      switch(pACInfo->curr_state)
+      {
+         case SME_QOS_HANDOFF:
+            // return to our previous state
+            sme_QosStateTransition(sessionId, ac, pACInfo->prev_state);
+            //for which ac APSD (hence the reassoc) is requested
+            if(pACInfo->reassoc_pending)
+            {
+               //update the apsd mask in CB - make sure to take care of the case
+               //where we are resetting the bit in apsd_mask
+               if(pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0].ts_info.psb)
+               {
+                  pSession->apsdMask |= 1 << (SME_QOS_EDCA_AC_VO - ac);
+               }
+               else
+               {
+                  pSession->apsdMask &= ~(1 << (SME_QOS_EDCA_AC_VO - ac));
+               }
+               pACInfo->reassoc_pending = VOS_FALSE;
+               //during setup it gets set as addts & reassoc both gets a pending flag
+               //pACInfo->tspec_pending = 0;
+               sme_QosStateTransition(sessionId, ac, SME_QOS_QOS_ON);
+               // notify HDD with new Service Interval
+               pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0] = 
+                  pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0];
+               vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+               //set the key type & the key to be searched in the Flow List
+               search_key.key.ac_type = ac;
+               search_key.index = SME_QOS_SEARCH_KEY_INDEX_2;
+               search_key.sessionId = sessionId;
+               //notify PMC that reassoc is done for APSD on certain AC??
+
+               vos_mem_zero(&search_key1, sizeof(sme_QosSearchInfo));
+               //set the hoRenewal field in control block if needed
+               search_key1.index = SME_QOS_SEARCH_KEY_INDEX_3;
+               search_key1.key.reason = SME_QOS_REASON_SETUP;
+               search_key1.sessionId = sessionId;
+               for(ac_index = SME_QOS_EDCA_AC_BE; ac_index < SME_QOS_EDCA_AC_MAX; ac_index++)
+               {
+                  pEntry = sme_QosFindInFlowList(search_key1);
+                  if(pEntry)
+                  {
+                     flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+                     if(flow_info->ac_type == ac)
+                     {
+                        pACInfo->hoRenewal = flow_info->hoRenewal;
+                        break;
+                     }
+                  }
+               }
+               //notify HDD the success for the requested flow 
+               //notify all the other flows running on the AC that QoS got modified
+               if(!HAL_STATUS_SUCCESS(sme_QosFindAllInFlowList(pMac, search_key, sme_QosReassocSuccessEvFnp)))
+               {
+                  VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                            "%s: %d: no match found for ac = %d",
+                            __FUNCTION__, __LINE__,
+                            search_key.key.ac_type);
+                  //ASSERT
+                  VOS_ASSERT(0);
+                  return eHAL_STATUS_FAILURE;
+               }
+               pACInfo->hoRenewal = VOS_FALSE;
+               vos_mem_zero(&pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0], 
+                            sizeof(sme_QosWmmTspecInfo));
+            }
+            status = eHAL_STATUS_SUCCESS;
+            break;
+         case SME_QOS_INIT:
+         case SME_QOS_CLOSED:
+            //NOP
+            status = eHAL_STATUS_SUCCESS;
+            break;
+         case SME_QOS_LINK_UP:
+         case SME_QOS_REQUESTED:
+         case SME_QOS_QOS_ON:
+         default:
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: On session %d AC %d is in wrong state %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac, pACInfo->curr_state);
+            //ASSERT
+            VOS_ASSERT(0);
+            break;
+      }
+   }
+   (void)sme_QosProcessBufferedCmd(sessionId);
+   return status;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessReassocFailureEv() - Function to process the
+  SME_QOS_CSR_REASSOC_FAILURE event indication from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessReassocFailureEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosEdcaAcType ac;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   // our pending reassociation has completed
+   // we can allow powersave
+   pSession->readyForPowerSave = VOS_TRUE;
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      pACInfo = &pSession->ac_info[ac];
+      switch(pACInfo->curr_state)
+      {
+         case SME_QOS_HANDOFF:
+            sme_QosStateTransition(sessionId, ac, SME_QOS_INIT);
+            if(pACInfo->reassoc_pending)
+            {
+               pACInfo->reassoc_pending = VOS_FALSE;
+            }
+            vos_mem_zero(&pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0], 
+                         sizeof(sme_QosWmmTspecInfo));
+            vos_mem_zero(&pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0], 
+                         sizeof(sme_QosWmmTspecInfo));
+            vos_mem_zero(&pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_1], 
+                         sizeof(sme_QosWmmTspecInfo));
+            vos_mem_zero(&pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_1], 
+                         sizeof(sme_QosWmmTspecInfo));
+            pACInfo->tspec_mask_status = SME_QOS_TSPEC_MASK_CLEAR;
+            pACInfo->tspec_pending = 0;
+            pACInfo->num_flows[SME_QOS_TSPEC_INDEX_0] = 0;
+            pACInfo->num_flows[SME_QOS_TSPEC_INDEX_1] = 0;
+            break;
+         case SME_QOS_INIT:
+         case SME_QOS_CLOSED:
+            //NOP
+            break;
+         case SME_QOS_LINK_UP:
+         case SME_QOS_REQUESTED:
+         case SME_QOS_QOS_ON:
+         default:
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: On session %d AC %d is in wrong state %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac, pACInfo->curr_state);
+            //ASSERT
+            VOS_ASSERT(0);
+            break;
+      }
+   }
+   //need to clean up flows
+   sme_QosDeleteExistingFlows(pMac, sessionId);
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessHandoffAssocReqEv() - Function to process the
+  SME_QOS_CSR_HANDOFF_ASSOC_REQ event indication from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessHandoffAssocReqEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   v_U8_t ac;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      pACInfo = &pSession->ac_info[ac];
+      switch(pACInfo->curr_state)
+      {
+         case SME_QOS_LINK_UP:
+         case SME_QOS_REQUESTED:
+         case SME_QOS_QOS_ON:
+            sme_QosStateTransition(sessionId, ac, SME_QOS_HANDOFF);
+            break;
+         case SME_QOS_HANDOFF:
+            //print error msg
+#ifdef WLAN_FEATURE_VOWIFI_11R
+            if(pSession->ftHandoffInProgress)
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: SME_QOS_CSR_HANDOFF_ASSOC_REQ received in "
+                         "SME_QOS_HANDOFF state with FT in progress"
+                         , __FUNCTION__, __LINE__); 
+               break; 
+            }
+#endif            
+
+         case SME_QOS_CLOSED:
+         case SME_QOS_INIT:
+         default:
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: On session %d AC %d is in wrong state %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac, pACInfo->curr_state);
+            //ASSERT
+            VOS_ASSERT(0);
+            break;
+      }
+   }
+   // If FT handoff is in progress, legacy handoff need not be enabled
+   if (!pSession->ftHandoffInProgress) {
+       pSession->handoffRequested = VOS_TRUE;
+   }
+   // this session no longer needs UAPSD
+   pSession->apsdMask = 0;
+   // do any sessions still require UAPSD?
+   if (!sme_QosIsUapsdActive())
+   {
+      // No sessions require UAPSD so turn it off
+      // (really don't care when PMC stops it)
+      (void)pmcStopUapsd(pMac);
+   }
+   pSession->uapsdAlreadyRequested = VOS_FALSE;
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessHandoffSuccessEv() - Function to process the
+  SME_QOS_CSR_HANDOFF_COMPLETE event indication from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessHandoffSuccessEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   v_U8_t ac;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   //go back to original state before handoff
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      pACInfo = &pSession->ac_info[ac];
+      switch(pACInfo->curr_state)
+      {
+         case SME_QOS_HANDOFF:
+            sme_QosStateTransition(sessionId, ac, pACInfo->prev_state);
+            //we will retry for the requested flow(s) with the new AP
+            if(SME_QOS_REQUESTED == pACInfo->curr_state)
+            {
+               pACInfo->curr_state = SME_QOS_LINK_UP;
+            }
+            status = eHAL_STATUS_SUCCESS;
+            break;
+         // FT logic, has already moved it to QOS_REQUESTED state during the 
+         // reassoc request event, which would include the Qos (TSPEC) params
+         // in the reassoc req frame
+         case SME_QOS_REQUESTED:
+            break;
+         case SME_QOS_INIT:
+         case SME_QOS_CLOSED:
+         case SME_QOS_LINK_UP:
+         case SME_QOS_QOS_ON:
+         default:
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/* In case of 11r - RIC, we request QoS and Hand-off at the same time hence the
+   state may be SME_QOS_REQUESTED */
+            if( pSession->ftHandoffInProgress )
+               break;
+#endif
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: On session %d AC %d is in wrong state %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac, pACInfo->curr_state);
+            //ASSERT
+            VOS_ASSERT(0);
+            break;
+      }
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessHandoffFailureEv() - Function to process the
+  SME_QOS_CSR_HANDOFF_FAILURE event indication from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessHandoffFailureEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   v_U8_t ac;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      pACInfo = &pSession->ac_info[ac];
+      switch(pACInfo->curr_state)
+      {
+         case SME_QOS_HANDOFF:
+            sme_QosStateTransition(sessionId, ac, SME_QOS_INIT);
+            //need to clean up flows: TODO
+            vos_mem_zero(&pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0], 
+                         sizeof(sme_QosWmmTspecInfo));
+            vos_mem_zero(&pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0], 
+                         sizeof(sme_QosWmmTspecInfo));
+            vos_mem_zero(&pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_1], 
+                         sizeof(sme_QosWmmTspecInfo));
+            vos_mem_zero(&pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_1], 
+                         sizeof(sme_QosWmmTspecInfo));
+            pACInfo->tspec_mask_status = SME_QOS_TSPEC_MASK_CLEAR;
+            pACInfo->tspec_pending = 0;
+            pACInfo->num_flows[SME_QOS_TSPEC_INDEX_0] = 0;
+            pACInfo->num_flows[SME_QOS_TSPEC_INDEX_1] = 0;
+            break;
+         case SME_QOS_INIT:
+         case SME_QOS_CLOSED:
+         case SME_QOS_LINK_UP:
+         case SME_QOS_REQUESTED:
+         case SME_QOS_QOS_ON:
+         default:
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: On session %d AC %d is in wrong state %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId, ac, pACInfo->curr_state);
+            //ASSERT
+            VOS_ASSERT(0);
+            break;
+      }
+   }
+   //no longer in handoff
+   pSession->handoffRequested = VOS_FALSE;
+   //clean up the assoc info
+   if(pSession->assocInfo.pBssDesc)
+   {
+      vos_mem_free(pSession->assocInfo.pBssDesc);
+      pSession->assocInfo.pBssDesc = NULL;
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessDisconnectEv() - Function to process the
+  SME_QOS_CSR_DISCONNECT_REQ or  SME_QOS_CSR_DISCONNECT_IND event indication 
+  from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessDisconnectEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   sme_QosSessionInfo *pSession;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   if((pSession->handoffRequested)
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/* In case of 11r - RIC, we request QoS and Hand-off at the same time hence the
+   state may be SME_QOS_REQUESTED */
+      && !pSession->ftHandoffInProgress
+#endif
+      )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: no need for state transition, should "
+                "already be in handoff state",
+                __FUNCTION__, __LINE__);
+      VOS_ASSERT(pSession->ac_info[0].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[1].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[2].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[3].curr_state == SME_QOS_HANDOFF);
+      return eHAL_STATUS_SUCCESS;
+   }
+   sme_QosInitACs(pMac, sessionId);
+   // this session doesn't require UAPSD
+   pSession->apsdMask = 0;
+   // do any sessions still require UAPSD?
+   if (!sme_QosIsUapsdActive())
+   {
+      // No sessions require UAPSD so turn it off
+      // (really don't care when PMC stops it)
+      (void)pmcStopUapsd(pMac);
+   }
+   pSession->uapsdAlreadyRequested = VOS_FALSE;
+   pSession->handoffRequested = VOS_FALSE;
+   pSession->readyForPowerSave = VOS_TRUE;
+   pSession->roamID = 0;
+   //need to clean up buffered req
+   sme_QosDeleteBufferedRequests(pMac, sessionId);
+   //need to clean up flows
+   sme_QosDeleteExistingFlows(pMac, sessionId);
+   //clean up the assoc info
+   if(pSession->assocInfo.pBssDesc)
+   {
+      vos_mem_free(pSession->assocInfo.pBssDesc);
+      pSession->assocInfo.pBssDesc = NULL;
+   }
+   sme_QosCb.sessionInfo[sessionId].sessionActive = VOS_FALSE;
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessJoinReqEv() - Function to process the
+  SME_QOS_CSR_JOIN_REQ event indication from CSR
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessJoinReqEv(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosEdcaAcType ac;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   if(pSession->handoffRequested)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: no need for state transition, should "
+                "already be in handoff state",
+                __FUNCTION__, __LINE__);
+      VOS_ASSERT(pSession->ac_info[0].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[1].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[2].curr_state == SME_QOS_HANDOFF);
+      VOS_ASSERT(pSession->ac_info[3].curr_state == SME_QOS_HANDOFF);
+      //buffer the existing flows to be renewed after handoff is done
+      sme_QosBufferExistingFlows(pMac, sessionId);
+      //clean up the control block partially for handoff
+      sme_QosCleanupCtrlBlkForHandoff(pMac, sessionId);
+      return eHAL_STATUS_SUCCESS;
+   }
+
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      sme_QosStateTransition(sessionId, ac, SME_QOS_INIT);
+   }
+   //clean up the assoc info if already set
+   if(pSession->assocInfo.pBssDesc)
+   {
+      vos_mem_free(pSession->assocInfo.pBssDesc);
+      pSession->assocInfo.pBssDesc = NULL;
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessPreauthSuccessInd() - Function to process the
+  SME_QOS_CSR_PREAUTH_SUCCESS_IND event indication from CSR
+
+  \param pEvent_info - Pointer to relevant info from CSR.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessPreauthSuccessInd(tpAniSirGlobal pMac, v_U8_t sessionId, void * pEvent_info)
+{
+    sme_QosSessionInfo *pSession;
+    sme_QosACInfo *pACInfo;
+    v_U8_t ac;
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+            "%s: %d: invoked on session %d",
+            __FUNCTION__, __LINE__,
+            sessionId);
+
+    pSession = &sme_QosCb.sessionInfo[sessionId];
+
+    for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++)
+    {
+        pACInfo = &pSession->ac_info[ac];
+
+        switch(pACInfo->curr_state)
+        {
+            case SME_QOS_LINK_UP:
+            case SME_QOS_REQUESTED:
+            case SME_QOS_QOS_ON:
+                sme_QosStateTransition(sessionId, ac, SME_QOS_HANDOFF);
+                break;
+            case SME_QOS_HANDOFF:
+                //print error msg
+            case SME_QOS_CLOSED:
+            case SME_QOS_INIT:
+            default:
+                VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                        "%s: %d: On session %d AC %d is in wrong state %d",
+                        __FUNCTION__, __LINE__,
+                        sessionId, ac, pACInfo->curr_state);
+                //ASSERT
+                VOS_ASSERT(0);
+                break;
+        }
+    }
+
+    pSession->ftHandoffInProgress = VOS_TRUE;
+
+    // Check if its a 11R roaming before preparing the RIC IEs
+    if (csrRoamIs11rAssoc(pMac)) 
+    {
+        v_U16_t ricOffset = 0;
+        v_U32_t ricIELength = 0;
+        v_U8_t  *ricIE;
+        v_U8_t  tspec_mask_status = 0;
+        v_U8_t  tspec_pending_status = 0;
+
+        /* Any Block Ack info there, should have been already filled by PE and present in this buffer
+           and the ric_ies_length should contain the length of the whole RIC IEs. Filling of TSPEC info
+           should start from this length */
+        ricIE = pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ric_ies;
+        ricOffset = pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ric_ies_length;
+
+        /* Now we have to process the currentTspeInfo inside this session and create the RIC IEs */
+        for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++)
+        {
+            volatile v_U8_t   tspec_index = 0;
+
+            pACInfo = &pSession->ac_info[ac];
+            tspec_pending_status = pACInfo->tspec_pending;
+            tspec_mask_status = pACInfo->tspec_mask_status;
+            vos_mem_zero(pACInfo->ricIdentifier, SME_QOS_TSPEC_INDEX_MAX);
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                    FL("AC %d ==> TSPEC status = %d, tspec pending = %d"), 
+                    ac, tspec_mask_status, tspec_pending_status);
+
+            do
+            {
+                if (tspec_mask_status & 0x1)
+                {
+                    /* If a tspec status is pending, take requested_QoSInfo for RIC request, else use curr_QoSInfo
+                       for the RIC request */
+                    if (tspec_pending_status & 0x1)
+                    {
+                        status = sme_QosCreateTspecRICIE(pMac, &pACInfo->requested_QoSInfo[tspec_index],
+                                ricIE + ricOffset, &ricIELength, &pACInfo->ricIdentifier[tspec_index]);
+                    }
+                    else
+                    {
+                        status = sme_QosCreateTspecRICIE(pMac, &pACInfo->curr_QoSInfo[tspec_index],
+                                ricIE + ricOffset, &ricIELength, &pACInfo->ricIdentifier[tspec_index]);
+                    }
+                }
+                ricOffset += ricIELength;
+                pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ric_ies_length += ricIELength;
+
+                tspec_mask_status >>= 1;
+                tspec_pending_status >>= 1;
+                tspec_index++;
+            } while (tspec_mask_status);
+        }
+    }
+    return status;
+}
+
+#endif
+
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessAddTsFailureRsp() - Function to process the
+  Addts request failure response came from PE 
+  
+  We will notify HDD only for the requested Flow, other Flows running on the AC 
+  stay intact
+  
+  \param pMac - Pointer to the global MAC parameter structure.  
+  \param pRsp - Pointer to the addts response structure came from PE.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessAddTsFailureRsp(tpAniSirGlobal pMac, 
+                                         v_U8_t sessionId,
+                                         tSirAddtsRspInfo * pRsp)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosEdcaAcType ac;
+   sme_QosSearchInfo search_key;
+   v_U8_t tspec_pending;
+   sme_QosWmmUpType up = (sme_QosWmmUpType)pRsp->tspec.tsinfo.traffic.userPrio;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d for UP %d",
+             __FUNCTION__, __LINE__,
+             sessionId, up);
+   ac = sme_QosUpToAc(up);
+   if(SME_QOS_EDCA_AC_MAX == ac)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: invalid AC %d from UP %d",
+                __FUNCTION__, __LINE__, ac, up);
+      return eHAL_STATUS_FAILURE;
+   }
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   // is there a TSPEC request pending on this AC?
+   tspec_pending = pACInfo->tspec_pending;
+   if(!tspec_pending)
+   {
+      //ASSERT
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: On session %d an AddTS is not pending on AC %d",
+                __FUNCTION__, __LINE__,
+                sessionId, ac);
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+   //set the key type & the key to be searched in the Flow List
+   search_key.key.ac_type = ac;
+   search_key.index = SME_QOS_SEARCH_KEY_INDEX_2;
+   search_key.sessionId = sessionId;
+   if(!HAL_STATUS_SUCCESS(sme_QosFindAllInFlowList(pMac, search_key, sme_QosAddTsFailureFnp)))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: On session %d no match found for ac = %d",
+                __FUNCTION__, __LINE__,
+                sessionId, search_key.key.ac_type);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   vos_mem_zero(&pACInfo->requested_QoSInfo[tspec_pending - 1], 
+                sizeof(sme_QosWmmTspecInfo));
+
+   if((!pACInfo->num_flows[0])&&
+      (!pACInfo->num_flows[1]))
+   {
+      pACInfo->tspec_mask_status &= SME_QOS_TSPEC_MASK_BIT_1_2_SET & 
+         (~pACInfo->tspec_pending);
+      sme_QosStateTransition(sessionId, ac, SME_QOS_LINK_UP);
+   }
+   else
+   {
+      sme_QosStateTransition(sessionId, ac, SME_QOS_QOS_ON);
+   }
+   pACInfo->tspec_pending = 0;
+
+   (void)sme_QosProcessBufferedCmd(sessionId);
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosUpdateTspecMask() - Utiltity function to update the tspec.
+  Typical usage while aggregating unidirectional flows into a bi-directional
+  flow on AC which is running multiple flows
+  
+  \param sessionId - Session upon which the TSPEC is being updated
+  \param ac - Enumeration of the various EDCA Access Categories.
+  \param old_tspec_mask - on which tspec per AC, the update is requested
+  \param new_tspec_mask - tspec to be set for this AC
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static eHalStatus sme_QosUpdateTspecMask(v_U8_t sessionId,
+                                      sme_QosSearchInfo search_key,
+                                      v_U8_t new_tspec_mask)
+{
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d for AC %d TSPEC %d",
+             __FUNCTION__, __LINE__,
+             sessionId, search_key.key.ac_type, new_tspec_mask);
+
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   
+   if (search_key.key.ac_type < SME_QOS_EDCA_AC_MAX)
+   {
+   pACInfo = &pSession->ac_info[search_key.key.ac_type];
+   }
+   else
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Exceeded the array bounds of pSession->ac_info",
+                __FUNCTION__, __LINE__);
+      VOS_ASSERT (0);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_FALSE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Flow List empty, nothing to update",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_FALSE );
+      flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+
+      if(search_key.sessionId == flow_info->sessionId)
+      {
+         if(search_key.index & SME_QOS_SEARCH_KEY_INDEX_4)
+         {
+            if((search_key.key.ac_type == flow_info->ac_type) &&
+               (search_key.direction == flow_info->QoSInfo.ts_info.direction))
+            {
+               //msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: Flow %d matches",
+                         __FUNCTION__, __LINE__,
+                         flow_info->QosFlowID);
+               pACInfo->num_flows[flow_info->tspec_mask - 1]--;
+               pACInfo->num_flows[new_tspec_mask - 1]++;
+               flow_info->tspec_mask = new_tspec_mask;
+            }
+         }
+         else if(search_key.index & SME_QOS_SEARCH_KEY_INDEX_5)
+         {
+            if((search_key.key.ac_type == flow_info->ac_type) &&
+               (search_key.tspec_mask == flow_info->tspec_mask))
+            {
+               //msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: Flow %d matches",
+                         __FUNCTION__, __LINE__,
+                         flow_info->QosFlowID);
+               pACInfo->num_flows[flow_info->tspec_mask - 1]--;
+               pACInfo->num_flows[new_tspec_mask - 1]++;
+               flow_info->tspec_mask = new_tspec_mask;
+            }
+         }
+      }
+
+      pEntry = pNextEntry;
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessAddTsSuccessRsp() - Function to process the
+  Addts request success response came from PE 
+  
+  We will notify HDD with addts success for the requested Flow, & for other 
+  Flows running on the AC we will send an addts modify status 
+  
+  
+  \param pMac - Pointer to the global MAC parameter structure.  
+  \param pRsp - Pointer to the addts response structure came from PE.   
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessAddTsSuccessRsp(tpAniSirGlobal pMac, 
+                                         v_U8_t sessionId,
+                                         tSirAddtsRspInfo * pRsp)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosEdcaAcType ac, ac_index;
+   sme_QosSearchInfo search_key;
+   sme_QosSearchInfo search_key1;
+   v_U8_t tspec_pending;
+   tListElem *pEntry= NULL;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosWmmUpType up = (sme_QosWmmUpType)pRsp->tspec.tsinfo.traffic.userPrio;
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+   WLAN_VOS_DIAG_EVENT_DEF(qos, vos_event_wlan_qos_payload_type);
+   vos_log_qos_tspec_pkt_type *log_ptr = NULL;
+#endif //FEATURE_WLAN_DIAG_SUPPORT
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d for UP %d",
+             __FUNCTION__, __LINE__,
+             sessionId, up);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   ac = sme_QosUpToAc(up);
+   if(SME_QOS_EDCA_AC_MAX == ac)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: invalid AC %d from UP %d",
+                __FUNCTION__, __LINE__, ac, up);
+      return eHAL_STATUS_FAILURE;
+   }
+   pACInfo = &pSession->ac_info[ac];
+   // is there a TSPEC request pending on this AC?
+   tspec_pending = pACInfo->tspec_pending;
+   if(!tspec_pending)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: On session %d an AddTS is not pending on AC %d",
+                __FUNCTION__, __LINE__,
+                sessionId, ac);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   //App is looking for APSD or the App which was looking for APSD has been 
+   //released, so STA re-negotiated with AP
+   if(pACInfo->requested_QoSInfo[tspec_pending - 1].ts_info.psb)
+   {
+      //update the session's apsd mask
+      pSession->apsdMask |= 1 << (SME_QOS_EDCA_AC_VO - ac);
+   }
+   else
+   {
+      if(((SME_QOS_TSPEC_MASK_BIT_1_2_SET & ~tspec_pending) > 0) &&
+         ((SME_QOS_TSPEC_MASK_BIT_1_2_SET & ~tspec_pending) <= 
+            SME_QOS_TSPEC_INDEX_MAX))
+      {
+      if(!pACInfo->requested_QoSInfo
+         [(SME_QOS_TSPEC_MASK_BIT_1_2_SET & ~tspec_pending) - 1].ts_info.psb)
+      {
+         //update the session's apsd mask
+         pSession->apsdMask &= ~(1 << (SME_QOS_EDCA_AC_VO - ac));
+      }
+   }
+      else
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: Exceeded the array bounds of pACInfo->requested_QosInfo",
+                   __FUNCTION__, __LINE__);
+         VOS_ASSERT (0);
+         return eHAL_STATUS_FAILURE;
+      }
+   }
+   pACInfo->curr_QoSInfo[tspec_pending - 1] = 
+      pACInfo->requested_QoSInfo[tspec_pending - 1];
+   /* Check if the current flow is for bi-directional. If so, update the number of flows
+    * to reflect that all flows are aggregated into tspec index 0. */
+   if((pACInfo->curr_QoSInfo[pACInfo->tspec_pending - 1].ts_info.direction == SME_QOS_WMM_TS_DIR_BOTH) &&
+      (pACInfo->num_flows[SME_QOS_TSPEC_INDEX_1] > 0))
+   {
+     vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+     /* update tspec_mask for all the flows having SME_QOS_TSPEC_MASK_BIT_2_SET to SME_QOS_TSPEC_MASK_BIT_1_SET */
+     search_key.key.ac_type = ac;
+     search_key.index = SME_QOS_SEARCH_KEY_INDEX_5;
+     search_key.sessionId = sessionId;
+     search_key.tspec_mask = SME_QOS_TSPEC_MASK_BIT_2_SET;
+     sme_QosUpdateTspecMask(sessionId, search_key, SME_QOS_TSPEC_MASK_BIT_1_SET);
+   }
+
+   vos_mem_zero(&search_key1, sizeof(sme_QosSearchInfo));
+   //set the horenewal field in control block if needed
+   search_key1.index = SME_QOS_SEARCH_KEY_INDEX_3;
+   search_key1.key.reason = SME_QOS_REASON_SETUP;
+   search_key1.sessionId = sessionId;
+   for(ac_index = SME_QOS_EDCA_AC_BE; ac_index < SME_QOS_EDCA_AC_MAX; ac_index++)
+   {
+      pEntry = sme_QosFindInFlowList(search_key1);
+      if(pEntry)
+      {
+         flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+         if(flow_info->ac_type == ac)
+         {
+            pACInfo->hoRenewal = flow_info->hoRenewal;
+            break;
+         }
+      }
+   }
+   vos_mem_zero(&search_key, sizeof(sme_QosSearchInfo));
+   //set the key type & the key to be searched in the Flow List
+   search_key.key.ac_type = ac;
+   search_key.index = SME_QOS_SEARCH_KEY_INDEX_2;
+   search_key.sessionId = sessionId;
+   //notify HDD the success for the requested flow 
+   //notify all the other flows running on the AC that QoS got modified
+   if(!HAL_STATUS_SUCCESS(sme_QosFindAllInFlowList(pMac, search_key, sme_QosAddTsSuccessFnp)))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: On session %d no match found for ac %d",
+                __FUNCTION__, __LINE__,
+                sessionId, search_key.key.ac_type);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   pACInfo->hoRenewal = VOS_FALSE;
+   vos_mem_zero(&pACInfo->requested_QoSInfo[tspec_pending - 1], 
+                sizeof(sme_QosWmmTspecInfo));
+   //event: EVENT_WLAN_QOS
+#ifdef FEATURE_WLAN_DIAG_SUPPORT          
+   qos.eventId = SME_QOS_DIAG_ADDTS_RSP;
+   qos.reasonCode = SME_QOS_DIAG_ADDTS_ADMISSION_ACCEPTED;
+   WLAN_VOS_DIAG_EVENT_REPORT(&qos, EVENT_WLAN_QOS);
+   WLAN_VOS_DIAG_LOG_ALLOC(log_ptr, vos_log_qos_tspec_pkt_type, LOG_WLAN_QOS_TSPEC_C);
+   if(log_ptr)
+   {
+      log_ptr->delay_bound = pACInfo->curr_QoSInfo[tspec_pending - 1].delay_bound;
+      log_ptr->inactivity_interval = pACInfo->curr_QoSInfo[tspec_pending - 1].inactivity_interval;
+      log_ptr->max_burst_size = pACInfo->curr_QoSInfo[tspec_pending - 1].max_burst_size;
+      log_ptr->max_service_interval = pACInfo->curr_QoSInfo[tspec_pending - 1].max_service_interval;
+      log_ptr->maximum_msdu_size = pACInfo->curr_QoSInfo[tspec_pending - 1].maximum_msdu_size;
+      log_ptr->mean_data_rate = pACInfo->curr_QoSInfo[tspec_pending - 1].mean_data_rate;
+      log_ptr->medium_time = pACInfo->curr_QoSInfo[tspec_pending - 1].medium_time;
+      log_ptr->min_data_rate = pACInfo->curr_QoSInfo[tspec_pending - 1].min_data_rate;
+      log_ptr->min_phy_rate = pACInfo->curr_QoSInfo[tspec_pending - 1].min_phy_rate;
+      log_ptr->min_service_interval = pACInfo->curr_QoSInfo[tspec_pending - 1].min_service_interval;
+      log_ptr->nominal_msdu_size = pACInfo->curr_QoSInfo[tspec_pending - 1].nominal_msdu_size;
+      log_ptr->peak_data_rate = pACInfo->curr_QoSInfo[tspec_pending - 1].peak_data_rate;
+      log_ptr->surplus_bw_allowance = pACInfo->curr_QoSInfo[tspec_pending - 1].surplus_bw_allowance;
+      log_ptr->suspension_interval = pACInfo->curr_QoSInfo[tspec_pending - 1].surplus_bw_allowance;
+      log_ptr->suspension_interval = pACInfo->curr_QoSInfo[tspec_pending - 1].suspension_interval;
+      log_ptr->svc_start_time = pACInfo->curr_QoSInfo[tspec_pending - 1].svc_start_time;
+      log_ptr->tsinfo[0] = pACInfo->curr_QoSInfo[tspec_pending - 1].ts_info.direction << 5 |
+         pACInfo->curr_QoSInfo[tspec_pending - 1].ts_info.tid << 1;
+      log_ptr->tsinfo[1] = pACInfo->curr_QoSInfo[tspec_pending - 1].ts_info.up << 11 |
+         pACInfo->curr_QoSInfo[tspec_pending - 1].ts_info.psb << 10;
+      log_ptr->tsinfo[2] = 0;
+   }
+   WLAN_VOS_DIAG_LOG_REPORT(log_ptr);
+#endif //FEATURE_WLAN_DIAG_SUPPORT
+#ifdef FEATURE_WLAN_CCX
+   if (ac == SME_QOS_EDCA_AC_VO)
+   {
+      // Indicate to neighbor roam logic of the new required VO
+      // ac bandwidth requirement.
+      csrNeighborRoamIndicateVoiceBW( pMac, pACInfo->curr_QoSInfo[tspec_pending - 1].peak_data_rate, TRUE );
+   }
+#endif
+   pACInfo->tspec_pending = 0;
+
+   sme_QosStateTransition(sessionId, ac, SME_QOS_QOS_ON);
+
+
+   (void)sme_QosProcessBufferedCmd(sessionId);
+   return eHAL_STATUS_SUCCESS;
+   
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosAggregateParams() - Utiltity function to increament the TSPEC 
+  params per AC. Typical usage while using flow aggregation or deletion of flows
+  
+  \param pInput_Tspec_Info - Pointer to sme_QosWmmTspecInfo which contains the 
+  WMM TSPEC related info with which pCurrent_Tspec_Info will be updated
+  \param pCurrent_Tspec_Info - Pointer to sme_QosWmmTspecInfo which contains 
+  current the WMM TSPEC related info
+
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosAggregateParams(
+   sme_QosWmmTspecInfo * pInput_Tspec_Info,
+   sme_QosWmmTspecInfo * pCurrent_Tspec_Info,
+   sme_QosWmmTspecInfo * pUpdated_Tspec_Info)
+{
+   sme_QosWmmTspecInfo TspecInfo;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked",
+             __FUNCTION__, __LINE__);
+   if(!pInput_Tspec_Info)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: input is NULL, nothing to aggregate",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   if(!pCurrent_Tspec_Info)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Current is NULL, can't aggregate",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   vos_mem_copy(&TspecInfo, pCurrent_Tspec_Info, 
+                sizeof(sme_QosWmmTspecInfo));
+   /*-------------------------------------------------------------------------
+     APSD preference is only meaningful if service interval was set by app
+   -------------------------------------------------------------------------*/
+   if(pCurrent_Tspec_Info->min_service_interval && pInput_Tspec_Info->min_service_interval)
+   {
+      TspecInfo.min_service_interval = VOS_MIN(
+         pCurrent_Tspec_Info->min_service_interval,
+         pInput_Tspec_Info->min_service_interval);
+   }
+   else if(pInput_Tspec_Info->min_service_interval)
+   {
+      TspecInfo.min_service_interval = pInput_Tspec_Info->min_service_interval;
+   }
+   if(pCurrent_Tspec_Info->max_service_interval)
+   {
+      TspecInfo.max_service_interval = VOS_MIN(
+         pCurrent_Tspec_Info->max_service_interval,
+         pInput_Tspec_Info->max_service_interval);
+   }
+   else
+   {
+      TspecInfo.max_service_interval = pInput_Tspec_Info->max_service_interval;
+   }
+   /*-------------------------------------------------------------------------
+     If directions don't match, it must necessarily be both uplink and
+     downlink
+   -------------------------------------------------------------------------*/
+   if(pCurrent_Tspec_Info->ts_info.direction != 
+      pInput_Tspec_Info->ts_info.direction)
+   {
+      TspecInfo.ts_info.direction = SME_QOS_WMM_TS_DIR_BOTH;
+   }
+   /*-------------------------------------------------------------------------
+     Max MSDU size : these sizes are `maxed'
+   -------------------------------------------------------------------------*/
+   TspecInfo.maximum_msdu_size = VOS_MAX(pCurrent_Tspec_Info->maximum_msdu_size,
+                                         pInput_Tspec_Info->maximum_msdu_size);
+
+   /*-------------------------------------------------------------------------
+     Inactivity interval : these sizes are `maxed'
+   -------------------------------------------------------------------------*/
+   TspecInfo.inactivity_interval = VOS_MAX(pCurrent_Tspec_Info->inactivity_interval,
+                                         pInput_Tspec_Info->inactivity_interval);
+
+   /*-------------------------------------------------------------------------
+     Delay bounds: min of all values
+     Check on 0: if 0, it means initial value since delay can never be 0!!
+   -------------------------------------------------------------------------*/
+   if(pCurrent_Tspec_Info->delay_bound)
+   {
+      TspecInfo.delay_bound = VOS_MIN(pCurrent_Tspec_Info->delay_bound,
+                                      pInput_Tspec_Info->delay_bound);
+   }
+   else
+   {
+      TspecInfo.delay_bound = pInput_Tspec_Info->delay_bound;
+   }
+   TspecInfo.max_burst_size = VOS_MAX(pCurrent_Tspec_Info->max_burst_size,
+                                      pInput_Tspec_Info->max_burst_size);
+
+   /*-------------------------------------------------------------------------
+     Nominal MSDU size also has a fixed bit that needs to be `handled' before
+     aggregation
+     This can be handled only if previous size is the same as new or both have
+     the fixed bit set
+     These sizes are not added: but `maxed'
+   -------------------------------------------------------------------------*/
+   TspecInfo.nominal_msdu_size = VOS_MAX(
+      pCurrent_Tspec_Info->nominal_msdu_size & ~SME_QOS_16BIT_MSB,
+      pInput_Tspec_Info->nominal_msdu_size & ~SME_QOS_16BIT_MSB);
+
+   if( ((pCurrent_Tspec_Info->nominal_msdu_size == 0) ||
+        (pCurrent_Tspec_Info->nominal_msdu_size & SME_QOS_16BIT_MSB)) &&
+       ((pInput_Tspec_Info->nominal_msdu_size == 0) ||
+        (pInput_Tspec_Info->nominal_msdu_size & SME_QOS_16BIT_MSB)))
+   {
+     TspecInfo.nominal_msdu_size |= SME_QOS_16BIT_MSB;
+   }
+
+   /*-------------------------------------------------------------------------
+     Data rates: 
+     Add up the rates for aggregation
+   -------------------------------------------------------------------------*/
+   SME_QOS_BOUNDED_U32_ADD_Y_TO_X( TspecInfo.peak_data_rate,
+                                   pInput_Tspec_Info->peak_data_rate );
+   SME_QOS_BOUNDED_U32_ADD_Y_TO_X( TspecInfo.min_data_rate,
+                                   pInput_Tspec_Info->min_data_rate );
+   /* mean data rate = peak data rate: aggregate to be flexible on apps  */
+   SME_QOS_BOUNDED_U32_ADD_Y_TO_X( TspecInfo.mean_data_rate,
+                                   pInput_Tspec_Info->mean_data_rate );
+
+   /*-------------------------------------------------------------------------
+     Suspension interval : this is set to the inactivity interval since per
+     spec it is less than or equal to inactivity interval
+     This is not provided by app since we currently don't support the HCCA
+     mode of operation
+     Currently set it to 0 to avoid confusion: Cisco CCX needs ~0; spec 
+     requires inactivity interval to be > suspension interval: this could
+     be tricky!
+   -------------------------------------------------------------------------*/
+   TspecInfo.suspension_interval = 0;
+   /*-------------------------------------------------------------------------
+     Remaining parameters do not come from app as they are very WLAN
+     air interface specific
+     Set meaningful values here
+   -------------------------------------------------------------------------*/
+   TspecInfo.medium_time = 0;               /* per WMM spec                 */
+   TspecInfo.min_phy_rate = SME_QOS_MIN_PHY_RATE;
+   TspecInfo.svc_start_time = 0;           /* arbitrary                  */
+   TspecInfo.surplus_bw_allowance += pInput_Tspec_Info->surplus_bw_allowance;
+   if(TspecInfo.surplus_bw_allowance > SME_QOS_SURPLUS_BW_ALLOWANCE)
+   {
+      TspecInfo.surplus_bw_allowance = SME_QOS_SURPLUS_BW_ALLOWANCE;
+   }
+   /* Set ack_policy to block ack even if one stream requests block ack policy */
+   if((pInput_Tspec_Info->ts_info.ack_policy == SME_QOS_WMM_TS_ACK_POLICY_HT_IMMEDIATE_BLOCK_ACK) ||
+      (pCurrent_Tspec_Info->ts_info.ack_policy == SME_QOS_WMM_TS_ACK_POLICY_HT_IMMEDIATE_BLOCK_ACK))
+   {
+     TspecInfo.ts_info.ack_policy = SME_QOS_WMM_TS_ACK_POLICY_HT_IMMEDIATE_BLOCK_ACK;
+   }
+
+   if(pInput_Tspec_Info->ts_info.burst_size_defn || pCurrent_Tspec_Info->ts_info.burst_size_defn )
+   {
+     TspecInfo.ts_info.burst_size_defn = 1;
+   }
+   if(pUpdated_Tspec_Info)
+   {
+      vos_mem_copy(pUpdated_Tspec_Info, &TspecInfo, 
+                   sizeof(sme_QosWmmTspecInfo));
+   }
+   else
+   {
+      vos_mem_copy(pCurrent_Tspec_Info, &TspecInfo, 
+                   sizeof(sme_QosWmmTspecInfo));
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosUpdateParams() - Utiltity function to update the TSPEC 
+  params per AC. Typical usage while deleting flows on AC which is running
+  multiple flows
+  
+  \param sessionId - Session upon which the TSPEC is being updated
+  \param ac - Enumeration of the various EDCA Access Categories.
+  \param tspec_mask - on which tspec per AC, the update is requested
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static eHalStatus sme_QosUpdateParams(v_U8_t sessionId,
+                                      sme_QosEdcaAcType ac,
+                                      v_U8_t tspec_mask, 
+                                      sme_QosWmmTspecInfo * pTspec_Info)
+{
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosWmmTspecInfo Tspec_Info;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: invoked on session %d for AC %d TSPEC %d",
+             __FUNCTION__, __LINE__,
+             sessionId, ac, tspec_mask);
+   if(!pTspec_Info)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: output is NULL, can't aggregate",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   vos_mem_zero(&Tspec_Info, sizeof(sme_QosWmmTspecInfo));
+   pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_FALSE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Flow List empty, nothing to update",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   //init the TS info field
+   Tspec_Info.ts_info.up  = pACInfo->curr_QoSInfo[tspec_mask - 1].ts_info.up;
+   Tspec_Info.ts_info.psb = pACInfo->curr_QoSInfo[tspec_mask - 1].ts_info.psb;
+   Tspec_Info.ts_info.tid = pACInfo->curr_QoSInfo[tspec_mask - 1].ts_info.tid;
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_FALSE );
+      flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+      if((sessionId == flow_info->sessionId) &&
+         (ac == flow_info->ac_type) &&
+         (tspec_mask == flow_info->tspec_mask))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: Flow %d matches",
+                   __FUNCTION__, __LINE__,
+                   flow_info->QosFlowID);
+         
+         if((SME_QOS_REASON_RELEASE == flow_info->reason ) ||
+            (SME_QOS_REASON_MODIFY == flow_info->reason))
+         {
+            //msg
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                      "%s: %d: Skipping Flow %d as it is marked "
+                      "for release/modify",
+                      __FUNCTION__, __LINE__,
+                      flow_info->QosFlowID);
+         }
+         else if(!HAL_STATUS_SUCCESS(sme_QosAggregateParams(&flow_info->QoSInfo, 
+                                                            &Tspec_Info,
+                                                            NULL)))
+         {
+            //err msg
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: sme_QosAggregateParams() failed",
+                      __FUNCTION__, __LINE__);
+         }
+      }
+      pEntry = pNextEntry;
+   }
+   // return the aggregate
+   *pTspec_Info = Tspec_Info;
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosAcToUp() - Utiltity function to map an AC to UP
+  Note: there is a quantization loss here because 4 ACs are mapped to 8 UPs
+  Mapping is done for consistency
+  \param ac - Enumeration of the various EDCA Access Categories.
+  \return an User Priority
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosWmmUpType sme_QosAcToUp(sme_QosEdcaAcType ac)
+{
+   sme_QosWmmUpType up = SME_QOS_WMM_UP_MAX;
+   if(ac >= 0 && ac < SME_QOS_EDCA_AC_MAX)
+   {
+      up = sme_QosACtoUPMap[ac];
+   }
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+             "%s: %d: ac = %d up = %d returned",
+             __FUNCTION__, __LINE__, ac, up);
+   return up;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosUpToAc() - Utiltity function to map an UP to AC
+  \param up - Enumeration of the various User priorities (UP).
+  \return an Access Category
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+sme_QosEdcaAcType sme_QosUpToAc(sme_QosWmmUpType up)
+{
+   sme_QosEdcaAcType ac = SME_QOS_EDCA_AC_MAX;
+   if(up >= 0 && up < SME_QOS_WMM_UP_MAX)
+   {
+      ac = sme_QosUPtoACMap[up];
+   }
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+             "%s: %d: up = %d ac = %d returned",
+             __FUNCTION__, __LINE__, up, ac);
+   return ac;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosStateTransition() - The state transition function per AC. We
+  save the previous state also.
+  \param sessionId - Session upon which the state machine is running
+  \param ac - Enumeration of the various EDCA Access Categories.
+  \param new_state - The state FSM is moving to.
+  
+  \return None
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static void sme_QosStateTransition(v_U8_t sessionId,
+                                   sme_QosEdcaAcType ac,
+                                   sme_QosStates new_state)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   pACInfo->prev_state = pACInfo->curr_state;
+   pACInfo->curr_state = new_state;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+             "%s: %d: On session %d new state=%d, old state=%d, for AC=%d",
+             __FUNCTION__, __LINE__, 
+             sessionId, pACInfo->curr_state, pACInfo->prev_state, ac );
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosFindInFlowList() - Utility function to find an flow entry from
+  the flow_list.
+  \param search_key -  We can either use the flowID or the ac type to find the 
+  entry in the flow list.
+  A bitmap in sme_QosSearchInfo tells which key to use. Starting from LSB,
+  bit 0 - Flow ID
+  bit 1 - AC type
+  \return the pointer to the entry in the link list
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+tListElem *sme_QosFindInFlowList(sme_QosSearchInfo search_key)
+{
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_FALSE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Flow List empty, can't search",
+                __FUNCTION__, __LINE__);
+      return NULL;
+   }
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_FALSE );
+      flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+      if((search_key.sessionId == flow_info->sessionId) ||
+         (search_key.sessionId == SME_QOS_SEARCH_SESSION_ID_ANY))
+      {
+         if(search_key.index & SME_QOS_SEARCH_KEY_INDEX_1)
+         {
+            if(search_key.key.QosFlowID == flow_info->QosFlowID)
+            {
+               //msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: match found on flowID, ending search",
+                         __FUNCTION__, __LINE__);
+               break;
+            }
+         }
+         else if(search_key.index & SME_QOS_SEARCH_KEY_INDEX_2)
+         {
+            if(search_key.key.ac_type == flow_info->ac_type)
+            {
+               //msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: match found on ac, ending search",
+                         __FUNCTION__, __LINE__);
+               break;
+            }
+         }
+         else if(search_key.index & SME_QOS_SEARCH_KEY_INDEX_3)
+         {
+            if(search_key.key.reason == flow_info->reason)
+            {
+               //msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: match found on reason, ending search",
+                         __FUNCTION__, __LINE__);
+               break;
+            }
+         }
+         else if(search_key.index & SME_QOS_SEARCH_KEY_INDEX_4)
+         {
+            if((search_key.key.ac_type == flow_info->ac_type) && 
+               (search_key.direction == flow_info->QoSInfo.ts_info.direction))
+            {
+               //msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: match found on reason, ending search",
+                         __FUNCTION__, __LINE__);
+
+               break;
+            }
+         }
+      }
+      pEntry = pNextEntry;
+   }
+   return pEntry;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosFindAllInFlowList() - Utility function to find an flow entry 
+  from the flow_list & act on it.
+  \param search_key -  We can either use the flowID or the ac type to find the 
+  entry in the flow list.
+  A bitmap in sme_QosSearchInfo tells which key to use. Starting from LSB,
+  bit 0 - Flow ID
+  bit 1 - AC type
+  \param fnp - function pointer specifying the action type for the entry found
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosFindAllInFlowList(tpAniSirGlobal pMac,
+                                    sme_QosSearchInfo search_key, 
+                                    sme_QosProcessSearchEntry fnp)
+{
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   sme_QosSessionInfo *pSession;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_FALSE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Flow List empty, can't search",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_FALSE );
+      flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+      pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+      if((search_key.sessionId == flow_info->sessionId) ||
+         (search_key.sessionId == SME_QOS_SEARCH_SESSION_ID_ANY))
+      {
+         if(search_key.index & SME_QOS_SEARCH_KEY_INDEX_1)
+         {
+            if(search_key.key.QosFlowID == flow_info->QosFlowID)
+            {
+               //msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: match found on flowID, ending search",
+                         __FUNCTION__, __LINE__);
+               status = fnp(pMac, pEntry);
+               if(eHAL_STATUS_FAILURE == status)
+               {
+                  VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                            "%s: %d: Failed to process entry",
+                            __FUNCTION__, __LINE__);
+                  break;
+               }
+            }
+         }
+         else if(search_key.index & SME_QOS_SEARCH_KEY_INDEX_2)
+         {
+            if(search_key.key.ac_type == flow_info->ac_type)
+            {
+               //msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: match found on ac, ending search",
+                         __FUNCTION__, __LINE__);
+               flow_info->hoRenewal = pSession->ac_info[flow_info->ac_type].hoRenewal;
+               status = fnp(pMac, pEntry);
+               if(eHAL_STATUS_FAILURE == status)
+               {
+                  VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                            "%s: %d: Failed to process entry",
+                            __FUNCTION__, __LINE__);
+                  break;
+               }
+            }
+         }
+      }
+      pEntry = pNextEntry;
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosIsACM() - Utility function to check if a particular AC
+  mandates Admission Control.
+  \param ac - Enumeration of the various EDCA Access Categories.
+  
+  \return VOS_TRUE if the AC mandates Admission Control
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+v_BOOL_t sme_QosIsACM(tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc, 
+                      sme_QosEdcaAcType ac, tDot11fBeaconIEs *pIes)
+{
+   v_BOOL_t ret_val = VOS_FALSE;
+   tDot11fBeaconIEs *pIesLocal;
+   if(!pSirBssDesc)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: pSirBssDesc is NULL",
+                __FUNCTION__, __LINE__);
+      return VOS_FALSE;
+   }
+
+   if (NULL != pIes)
+   {
+      /* IEs were provided so use them locally */
+      pIesLocal = pIes;
+   }
+   else
+   {
+      /* IEs were not provided so parse them ourselves */
+      if (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc, &pIesLocal)))
+      {
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: csrGetParsedBssDescriptionIEs() failed",
+                   __FUNCTION__, __LINE__);
+         return VOS_FALSE;
+      }
+
+      /* if success then pIesLocal was allocated */
+   }
+
+   if(CSR_IS_QOS_BSS(pIesLocal))
+   {
+       switch(ac)
+       {
+          case SME_QOS_EDCA_AC_BE:
+             if(pIesLocal->WMMParams.acbe_acm) ret_val = VOS_TRUE;
+             break;
+          case SME_QOS_EDCA_AC_BK:
+             if(pIesLocal->WMMParams.acbk_acm) ret_val = VOS_TRUE;
+             break;
+          case SME_QOS_EDCA_AC_VI:
+             if(pIesLocal->WMMParams.acvi_acm) ret_val = VOS_TRUE;
+             break;
+          case SME_QOS_EDCA_AC_VO:
+             if(pIesLocal->WMMParams.acvo_acm) ret_val = VOS_TRUE;
+             break;
+          default:
+             VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                       "%s: %d: unknown AC = %d",
+                       __FUNCTION__, __LINE__, ac);
+             //Assert
+             VOS_ASSERT(0);
+             break;
+       }
+   }//IS_QOS_BSS
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: ACM = %d for AC = %d",
+             __FUNCTION__, __LINE__, ret_val, ac );
+   if (NULL == pIes)
+   {
+      /* IEs were allocated locally so free them */
+      vos_mem_free(pIesLocal);
+   }
+   return ret_val;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosBufferExistingFlows() - Utility function to buffer the existing
+  flows in flow_list, so that we can renew them after handoff is done.
+
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static eHalStatus sme_QosBufferExistingFlows(tpAniSirGlobal pMac,
+                                             v_U8_t sessionId)
+{
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   sme_QosSessionInfo *pSession;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosCmdInfo  cmd;
+   pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_FALSE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Flow List empty, nothing to buffer",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_FALSE );
+      flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+      if (flow_info->sessionId == sessionId)
+      {
+         if((SME_QOS_REASON_REQ_SUCCESS == flow_info->reason )||
+            (SME_QOS_REASON_SETUP == flow_info->reason ))
+         {
+            cmd.command = SME_QOS_SETUP_REQ;
+            cmd.pMac = pMac;
+            cmd.sessionId = sessionId;
+            cmd.u.setupCmdInfo.HDDcontext = flow_info->HDDcontext;
+            cmd.u.setupCmdInfo.QoSInfo = flow_info->QoSInfo;
+            cmd.u.setupCmdInfo.QoSCallback = flow_info->QoSCallback;
+            cmd.u.setupCmdInfo.UPType = SME_QOS_WMM_UP_MAX;//shouldn't be needed
+            cmd.u.setupCmdInfo.QosFlowID = flow_info->QosFlowID;
+            if(SME_QOS_REASON_SETUP == flow_info->reason )
+            {
+               cmd.u.setupCmdInfo.hoRenewal = VOS_FALSE;
+            }
+            else
+            {
+               cmd.u.setupCmdInfo.hoRenewal = VOS_TRUE;//TODO: might need this for modify
+            }
+            if(!HAL_STATUS_SUCCESS(sme_QosBufferCmd(&cmd, VOS_TRUE)))
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: couldn't buffer the setup request for "
+                         "flow %d in handoff state",
+                         __FUNCTION__, __LINE__,
+                         flow_info->QosFlowID);
+            }
+            else
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: buffered a setup request for "
+                         "flow %d in handoff state",
+                         __FUNCTION__, __LINE__,
+                         flow_info->QosFlowID);
+            }
+         }
+         else if(SME_QOS_REASON_RELEASE == flow_info->reason ) 
+         {
+            cmd.command = SME_QOS_RELEASE_REQ;
+            cmd.pMac = pMac;
+            cmd.sessionId = sessionId;
+            cmd.u.releaseCmdInfo.QosFlowID = flow_info->QosFlowID;
+            if(!HAL_STATUS_SUCCESS(sme_QosBufferCmd(&cmd, VOS_TRUE)))
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: couldn't buffer the release request for "
+                         "flow %d in handoff state",
+                         __FUNCTION__, __LINE__,
+                         flow_info->QosFlowID);
+            }
+            else
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: buffered a release request for "
+                         "flow %d in handoff state",
+                         __FUNCTION__, __LINE__,
+                         flow_info->QosFlowID);
+            }
+         }
+         else if(SME_QOS_REASON_MODIFY_PENDING == flow_info->reason)
+         {
+            cmd.command = SME_QOS_MODIFY_REQ;
+            cmd.pMac = pMac;
+            cmd.sessionId = sessionId;
+            cmd.u.modifyCmdInfo.QosFlowID = flow_info->QosFlowID;
+            cmd.u.modifyCmdInfo.QoSInfo = flow_info->QoSInfo;
+            if(!HAL_STATUS_SUCCESS(sme_QosBufferCmd(&cmd, VOS_TRUE)))
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                         "%s: %d: couldn't buffer the modify request for "
+                         "flow %d in handoff state",
+                         __FUNCTION__, __LINE__,
+                         flow_info->QosFlowID);
+            }
+            else
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                         "%s: %d: buffered a modify request for "
+                         "flow %d in handoff state",
+                         __FUNCTION__, __LINE__,
+                         flow_info->QosFlowID);
+            }
+         }
+         //delete the entry from Flow List
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                   "%s: %d: Deleting original entry at %p with flowID %d",
+                   __FUNCTION__, __LINE__,
+                   flow_info, flow_info->QosFlowID);
+         csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+         vos_mem_free(flow_info);
+      }
+      pEntry = pNextEntry;
+   }
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pSession->uapsdAlreadyRequested = VOS_FALSE;
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosDeleteExistingFlows() - Utility function to Delete the existing
+  flows in flow_list, if we lost connectivity.
+
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static eHalStatus sme_QosDeleteExistingFlows(tpAniSirGlobal pMac,
+                                             v_U8_t sessionId)
+{
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_TRUE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                "%s: %d: Flow List empty, nothing to delete",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_TRUE );
+      flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+      if (flow_info->sessionId == sessionId)
+      {
+         if((SME_QOS_REASON_REQ_SUCCESS == flow_info->reason )||
+            (SME_QOS_REASON_SETUP == flow_info->reason )||
+            (SME_QOS_REASON_RELEASE == flow_info->reason )||
+            (SME_QOS_REASON_MODIFY == flow_info->reason ))
+         {
+            flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                   NULL,
+                                   SME_QOS_STATUS_RELEASE_QOS_LOST_IND,
+                                   flow_info->QosFlowID);
+         }
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                   "%s: %d: Deleting entry at %p with flowID %d",
+                   __FUNCTION__, __LINE__,
+                   flow_info, flow_info->QosFlowID);
+         //delete the entry from Flow List
+         csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+         vos_mem_free(flow_info);
+      }
+      pEntry = pNextEntry;
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosBufferCmd() - Utility function to buffer a request (setup/modify/
+  release) from client while processing another one on the same AC.
+  \param pcmd - a pointer to the cmd structure to be saved inside the buffered
+                cmd link list
+                
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosBufferCmd(sme_QosCmdInfo *pcmd, v_BOOL_t insert_head)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosCmdInfoEntry * pentry = NULL;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: Invoked",
+             __FUNCTION__, __LINE__);
+   pentry = (sme_QosCmdInfoEntry *) vos_mem_malloc(sizeof(sme_QosCmdInfoEntry));
+   if (!pentry)
+   {
+      //err msg
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Memory allocation failure",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   // copy the entire CmdInfo
+   pentry->cmdInfo = *pcmd;
+ 
+   pSession = &sme_QosCb.sessionInfo[pcmd->sessionId];
+   if(insert_head) 
+   {
+      csrLLInsertHead(&pSession->bufferedCommandList, &pentry->link, VOS_TRUE);
+   }
+   else
+   {
+      csrLLInsertTail(&pSession->bufferedCommandList, &pentry->link, VOS_TRUE);
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessBufferedCmd() - Utility function to process a buffered 
+  request (setup/modify/release) initially came from the client.
+
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static eHalStatus sme_QosProcessBufferedCmd(v_U8_t sessionId)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosCmdInfoEntry *pcmd = NULL;
+   tListElem *pEntry= NULL;
+   sme_QosStatusType hdd_status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+   eHalStatus halStatus = eHAL_STATUS_SUCCESS;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: Invoked on session %d",
+             __FUNCTION__, __LINE__,
+             sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   if(!csrLLIsListEmpty( &pSession->bufferedCommandList, VOS_FALSE ))
+   {
+      pEntry = csrLLRemoveHead( &pSession->bufferedCommandList, VOS_TRUE );
+      if(!pEntry)
+      {
+         //Err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: no more buffered commands on session %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId);
+         pSession->readyForPowerSave = VOS_TRUE;
+         return eHAL_STATUS_FAILURE;
+      }
+      pcmd = GET_BASE_ADDR( pEntry, sme_QosCmdInfoEntry, link );
+      switch(pcmd->cmdInfo.command)
+      {
+      case SME_QOS_SETUP_REQ:
+         hdd_status = sme_QosInternalSetupReq(pcmd->cmdInfo.pMac, 
+                                              pcmd->cmdInfo.sessionId,
+                                              &pcmd->cmdInfo.u.setupCmdInfo.QoSInfo,
+                                              pcmd->cmdInfo.u.setupCmdInfo.QoSCallback, 
+                                              pcmd->cmdInfo.u.setupCmdInfo.HDDcontext, 
+                                              pcmd->cmdInfo.u.setupCmdInfo.UPType, 
+                                              pcmd->cmdInfo.u.setupCmdInfo.QosFlowID, 
+                                              VOS_TRUE,
+                                              pcmd->cmdInfo.u.setupCmdInfo.hoRenewal);
+         if(SME_QOS_STATUS_SETUP_FAILURE_RSP == hdd_status)
+         {
+            //Err msg
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: sme_QosInternalSetupReq failed on session %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId);
+            halStatus = eHAL_STATUS_FAILURE;
+         }
+         break;
+      case SME_QOS_RELEASE_REQ:
+         hdd_status = sme_QosInternalReleaseReq(pcmd->cmdInfo.pMac, 
+                                                pcmd->cmdInfo.u.releaseCmdInfo.QosFlowID,
+                                                VOS_TRUE);
+         if(SME_QOS_STATUS_RELEASE_FAILURE_RSP == hdd_status)
+         {
+            //Err msg
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: sme_QosInternalReleaseReq failed on session %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId);
+            halStatus = eHAL_STATUS_FAILURE;
+         }
+         break;
+      case SME_QOS_MODIFY_REQ:
+         hdd_status = sme_QosInternalModifyReq(pcmd->cmdInfo.pMac, 
+                                               &pcmd->cmdInfo.u.modifyCmdInfo.QoSInfo,
+                                               pcmd->cmdInfo.u.modifyCmdInfo.QosFlowID,
+                                               VOS_TRUE);
+         if(SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP == hdd_status)
+         {
+            //Err msg
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: sme_QosInternalModifyReq failed on session %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId);
+            halStatus = eHAL_STATUS_FAILURE;
+         }
+         break;
+      case SME_QOS_RESEND_REQ:
+         hdd_status = sme_QosReRequestAddTS(pcmd->cmdInfo.pMac, 
+                                            pcmd->cmdInfo.sessionId,
+                                            &pcmd->cmdInfo.u.resendCmdInfo.QoSInfo,
+                                            pcmd->cmdInfo.u.resendCmdInfo.ac,
+                                            pcmd->cmdInfo.u.resendCmdInfo.tspecMask);
+         if(SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP == hdd_status)
+         {
+            //Err msg
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: sme_QosReRequestAddTS failed on session %d",
+                      __FUNCTION__, __LINE__,
+                      sessionId);
+            halStatus = eHAL_STATUS_FAILURE;
+         }
+         break;
+      default:
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: On session %d unknown cmd = %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId, pcmd->cmdInfo.command);
+         //ASSERT
+         VOS_ASSERT(0);
+         break;
+      }
+      // buffered command has been processed, reclaim the memory
+      vos_mem_free(pcmd);
+   }
+   else
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: cmd buffer empty",
+                __FUNCTION__, __LINE__);
+      pSession->readyForPowerSave = VOS_TRUE;
+   }
+   return halStatus;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosDeleteBufferedRequests() - Utility function to Delete the buffered
+  requests in the buffered_cmd_list, if we lost connectivity.
+
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static eHalStatus sme_QosDeleteBufferedRequests(tpAniSirGlobal pMac,
+                                                v_U8_t sessionId)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosCmdInfoEntry *pcmd = NULL;
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: Invoked on session %d",
+             __FUNCTION__, __LINE__, sessionId);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pEntry = csrLLPeekHead( &pSession->bufferedCommandList, VOS_TRUE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Buffered List empty, nothing to delete on session %d",
+                __FUNCTION__, __LINE__,
+                sessionId);
+      return eHAL_STATUS_FAILURE;
+   }
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &pSession->bufferedCommandList, pEntry, VOS_TRUE );
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: deleting entry from buffered List",
+                __FUNCTION__, __LINE__);
+      //delete the entry from Flow List
+      csrLLRemoveEntry(&pSession->bufferedCommandList, pEntry, VOS_TRUE );
+      // reclaim the memory
+      pcmd = GET_BASE_ADDR( pEntry, sme_QosCmdInfoEntry, link );
+      vos_mem_free(pcmd);
+      pEntry = pNextEntry;
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosSaveAssocInfo() - Utility function to save the assoc info in the
+  CB like BSS descritor of the AP, the profile that HDD sent down with the 
+  connect request, while CSR notifies for assoc/reassoc success.
+  \param pAssoc_info - pointer to the assoc structure to store the BSS descritor 
+                       of the AP, the profile that HDD sent down with the 
+                       connect request
+                       
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosSaveAssocInfo(sme_QosSessionInfo *pSession, sme_QosAssocInfo *pAssoc_info)
+{
+   tSirBssDescription    *pBssDesc = NULL;
+   v_U32_t                bssLen = 0;
+   if(NULL == pAssoc_info)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: pAssoc_info is NULL",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   //clean up the assoc info if already set
+   if(pSession->assocInfo.pBssDesc)
+   {
+      vos_mem_free(pSession->assocInfo.pBssDesc);
+      pSession->assocInfo.pBssDesc = NULL;
+   }
+   bssLen = pAssoc_info->pBssDesc->length + 
+      sizeof(pAssoc_info->pBssDesc->length);
+   //save the bss Descriptor
+   pBssDesc = (tSirBssDescription *)vos_mem_malloc(bssLen);
+   if (!pBssDesc)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: couldn't allocate memory for the bss Descriptor",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   vos_mem_copy(pBssDesc, pAssoc_info->pBssDesc, bssLen);
+   pSession->assocInfo.pBssDesc = pBssDesc;
+   //save the apsd info from assoc
+   if(pAssoc_info->pProfile)
+   {
+       pSession->apsdMask |= pAssoc_info->pProfile->uapsd_mask;
+   }
+   // [TODO] Do we need to update the global APSD bitmap?
+   return eHAL_STATUS_SUCCESS;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosSetupFnp() - Utility function (pointer) to notify other entries 
+  in FLOW list on the same AC that qos params got modified
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pEntry - Pointer to an entry in the flow_list(i.e. tListElem structure)
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosSetupFnp(tpAniSirGlobal pMac, tListElem *pEntry)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosStatusType hdd_status = SME_QOS_STATUS_SETUP_MODIFIED_IND;
+   sme_QosEdcaAcType ac;
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Entry is NULL",
+                __FUNCTION__, __LINE__);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+   ac = flow_info->ac_type;
+   pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   if(SME_QOS_REASON_REQ_SUCCESS == flow_info->reason)
+   {
+      //notify HDD, only the other Flows running on the AC 
+      flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                             &pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1],
+                             hdd_status,
+                             flow_info->QosFlowID);
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Entry with flowID = %d getting notified",
+                __FUNCTION__, __LINE__,
+                flow_info->QosFlowID);
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosModificationNotifyFnp() - Utility function (pointer) to notify 
+  other entries in FLOW list on the same AC that qos params got modified
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pEntry - Pointer to an entry in the flow_list(i.e. tListElem structure)
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosModificationNotifyFnp(tpAniSirGlobal pMac, tListElem *pEntry)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosStatusType hdd_status = SME_QOS_STATUS_SETUP_MODIFIED_IND;
+   sme_QosEdcaAcType ac;
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Entry is NULL",
+                __FUNCTION__, __LINE__);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+   ac = flow_info->ac_type;
+   pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   if(SME_QOS_REASON_REQ_SUCCESS == flow_info->reason)
+   {
+      //notify HDD, only the other Flows running on the AC 
+      flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                             &pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1],
+                             hdd_status,
+                             flow_info->QosFlowID);
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Entry with flowID = %d getting notified",
+                __FUNCTION__, __LINE__,
+                flow_info->QosFlowID);
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosModifyFnp() - Utility function (pointer) to delete the origianl 
+  entry in FLOW list & add the modified one
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pEntry - Pointer to an entry in the flow_list(i.e. tListElem structure)
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosModifyFnp(tpAniSirGlobal pMac, tListElem *pEntry)
+{
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Entry is NULL",
+                __FUNCTION__, __LINE__);
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+   switch(flow_info->reason)
+   {
+   case SME_QOS_REASON_MODIFY_PENDING:
+      //set the proper reason code for the new (with modified params) entry
+      flow_info->reason = SME_QOS_REASON_REQ_SUCCESS;
+      break;
+   case SME_QOS_REASON_MODIFY:
+      //delete the original entry from Flow List
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Deleting original entry at %p with flowID %d",
+                __FUNCTION__, __LINE__,
+                flow_info, flow_info->QosFlowID);
+      csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+      // reclaim the memory
+      vos_mem_free(flow_info);
+      break;
+   default:
+      break;
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosDelTsIndFnp() - Utility function (pointer) to find all Flows on 
+  the perticular AC & delete them, also send HDD indication through the callback 
+  it registered per request
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pEntry - Pointer to an entry in the flow_list(i.e. tListElem structure)
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosDelTsIndFnp(tpAniSirGlobal pMac, tListElem *pEntry)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   sme_QosEdcaAcType ac;
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Entry is NULL",
+                __FUNCTION__, __LINE__);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   //delete the entry from Flow List
+   flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+   ac = flow_info->ac_type;
+   pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                          &pACInfo->curr_QoSInfo[flow_info->tspec_mask - 1],
+                          SME_QOS_STATUS_RELEASE_QOS_LOST_IND,
+                          flow_info->QosFlowID);
+   pACInfo->num_flows[flow_info->tspec_mask - 1]--;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+             "%s: %d: Deleting entry at %p with flowID %d",
+             __FUNCTION__, __LINE__,
+             flow_info, flow_info->QosFlowID);
+   csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+   // reclaim the memory
+   vos_mem_free(flow_info);
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosReassocSuccessEvFnp() - Utility function (pointer) to notify HDD 
+  the success for the requested flow & notify all the other flows running on the 
+  same AC that QoS params got modified
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pEntry - Pointer to an entry in the flow_list(i.e. tListElem structure)
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosReassocSuccessEvFnp(tpAniSirGlobal pMac, tListElem *pEntry)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   v_BOOL_t delete_entry = VOS_FALSE;
+   sme_QosStatusType hdd_status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+   sme_QosEdcaAcType ac;
+   eHalStatus pmc_status = eHAL_STATUS_FAILURE;
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Entry is NULL",
+                __FUNCTION__, __LINE__);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   flow_info = GET_BASE_ADDR(pEntry, sme_QosFlowInfoEntry, link);
+   ac = flow_info->ac_type;
+   pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   switch(flow_info->reason)
+   {
+   case SME_QOS_REASON_SETUP:
+      hdd_status = SME_QOS_STATUS_SETUP_SUCCESS_IND;
+      delete_entry = VOS_FALSE;
+      flow_info->reason = SME_QOS_REASON_REQ_SUCCESS;
+      //check for the case where we had to do reassoc to reset the apsd bit
+      //for the ac - release or modify scenario
+      if(pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0].ts_info.psb)
+      {
+         // notify PMC as App is looking for APSD. If we already requested
+         // then we don't need to do anything.
+         if(!pSession->uapsdAlreadyRequested)
+         {
+            // this is the first flow to detect we need PMC in UAPSD mode
+   
+            pmc_status = pmcStartUapsd(pMac,
+                                       sme_QosPmcStartUapsdCallback,
+                                       pSession);
+            // if PMC doesn't return success right away means it is yet to put
+            // the module in BMPS state & later to UAPSD state
+         
+            if(eHAL_STATUS_FAILURE == pmc_status)
+            {
+               hdd_status = SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_SET_FAILED;
+               //we need to always notify this case
+               flow_info->hoRenewal = VOS_FALSE;
+            }
+            else if(eHAL_STATUS_PMC_PENDING == pmc_status)
+            {
+               // let other flows know PMC has been notified
+               pSession->uapsdAlreadyRequested = VOS_TRUE;
+            }
+            // for any other pmc status we declare success
+         }
+      }
+      break;
+   case SME_QOS_REASON_RELEASE:
+      pACInfo->num_flows[SME_QOS_TSPEC_INDEX_0]--;
+      // fall through
+   case SME_QOS_REASON_MODIFY:
+      delete_entry = VOS_TRUE;
+      break;
+   case SME_QOS_REASON_MODIFY_PENDING:
+      hdd_status = SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND;
+      delete_entry = VOS_FALSE;
+      flow_info->reason = SME_QOS_REASON_REQ_SUCCESS;
+      if(pACInfo->requested_QoSInfo[SME_QOS_TSPEC_INDEX_0].ts_info.psb)
+      {
+   
+         if(!pSession->uapsdAlreadyRequested)
+         {
+            // this is the first flow to detect we need PMC in UAPSD mode
+            pmc_status = pmcStartUapsd(pMac,
+                                       sme_QosPmcStartUapsdCallback,
+                                       pSession);
+         
+            // if PMC doesn't return success right away means it is yet to put
+            // the module in BMPS state & later to UAPSD state
+            if(eHAL_STATUS_FAILURE == pmc_status)
+            {
+               hdd_status = SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND_APSD_SET_FAILED;
+               // we need to always notify this case
+               flow_info->hoRenewal = VOS_FALSE;
+            }
+            else if(eHAL_STATUS_PMC_PENDING == pmc_status)
+            {
+               pSession->uapsdAlreadyRequested = VOS_TRUE;
+            }
+            // for any other pmc status we declare success
+         }
+      }
+      break;
+   case SME_QOS_REASON_REQ_SUCCESS:
+      hdd_status = SME_QOS_STATUS_SETUP_MODIFIED_IND;
+      // fall through
+   default:
+      delete_entry = VOS_FALSE;
+      break;
+   }
+   if(!delete_entry)
+   {
+      if(!flow_info->hoRenewal)
+      {
+         flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                &pACInfo->curr_QoSInfo[SME_QOS_TSPEC_INDEX_0],
+                                hdd_status,
+                                flow_info->QosFlowID);
+      }
+      else
+      {
+         flow_info->hoRenewal = VOS_FALSE;
+      }
+   }
+   else
+   {
+      //delete the entry from Flow List
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Deleting entry at %p with flowID %d",
+                __FUNCTION__, __LINE__,
+                flow_info, flow_info->QosFlowID);
+      csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+      // reclaim the memory
+      vos_mem_free(flow_info);
+   }
+   
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosAddTsFailureFnp() - Utility function (pointer), 
+  if the Addts request was for for an flow setup request, delete the entry from 
+  Flow list & notify HDD 
+  if the Addts request was for downgrading of QoS params because of an flow 
+  release requested on the AC, delete the entry from Flow list & notify HDD 
+  if the Addts request was for change of QoS params because of an flow 
+  modification requested on the AC, delete the new entry from Flow list & notify 
+  HDD 
+
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pEntry - Pointer to an entry in the flow_list(i.e. tListElem structure)
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosAddTsFailureFnp(tpAniSirGlobal pMac, tListElem *pEntry)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   v_BOOL_t inform_hdd = VOS_FALSE;
+   sme_QosStatusType hdd_status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+   sme_QosEdcaAcType ac;
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Entry is NULL",
+                __FUNCTION__, __LINE__);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+   ac = flow_info->ac_type;
+   pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   switch(flow_info->reason)
+   {
+   case SME_QOS_REASON_SETUP:
+      hdd_status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+      pACInfo->num_flows[pACInfo->tspec_pending - 1]--;
+      inform_hdd = VOS_TRUE;
+      break;
+   case SME_QOS_REASON_RELEASE:
+      hdd_status = SME_QOS_STATUS_RELEASE_FAILURE_RSP;
+      pACInfo->num_flows[pACInfo->tspec_pending - 1]--;
+      inform_hdd = VOS_TRUE;
+      break;
+   case SME_QOS_REASON_MODIFY_PENDING:
+      hdd_status = SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+      inform_hdd = VOS_TRUE;
+      break;
+   case SME_QOS_REASON_MODIFY:
+      flow_info->reason = SME_QOS_REASON_REQ_SUCCESS;
+   case SME_QOS_REASON_REQ_SUCCESS:
+   default:
+      inform_hdd = VOS_FALSE;
+      break;
+   }
+   if(inform_hdd)
+   {
+      //notify HDD, only the requested Flow, other Flows running on the AC stay 
+      // intact
+      if(!flow_info->hoRenewal)
+      {
+         flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                &pACInfo->curr_QoSInfo[pACInfo->tspec_pending - 1],
+                                hdd_status,
+                                flow_info->QosFlowID);
+      }
+      else
+      {
+         flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                &pACInfo->curr_QoSInfo[pACInfo->tspec_pending - 1],
+                                SME_QOS_STATUS_RELEASE_QOS_LOST_IND,
+                                flow_info->QosFlowID);
+      }
+      //delete the entry from Flow List
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Deleting entry at %p with flowID %d",
+                __FUNCTION__, __LINE__,
+                flow_info, flow_info->QosFlowID);
+      csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+      // reclaim the memory
+      vos_mem_free(flow_info);
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosAddTsSuccessFnp() - Utility function (pointer), 
+  if the Addts request was for for an flow setup request, notify HDD for success
+  for the flow & notify all the other flows running on the same AC that QoS 
+  params got modified
+  if the Addts request was for downgrading of QoS params because of an flow 
+  release requested on the AC, delete the entry from Flow list & notify HDD 
+  if the Addts request was for change of QoS params because of an flow 
+  modification requested on the AC, delete the old entry from Flow list & notify 
+  HDD for success for the flow & notify all the other flows running on the same 
+  AC that QoS params got modified
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param pEntry - Pointer to an entry in the flow_list(i.e. tListElem structure)
+  
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosAddTsSuccessFnp(tpAniSirGlobal pMac, tListElem *pEntry)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   v_BOOL_t inform_hdd = VOS_FALSE;
+   v_BOOL_t delete_entry = VOS_FALSE;
+   sme_QosStatusType hdd_status = SME_QOS_STATUS_SETUP_FAILURE_RSP;
+   sme_QosEdcaAcType ac;
+   eHalStatus pmc_status = eHAL_STATUS_FAILURE;
+   tCsrRoamModifyProfileFields modifyProfileFields;
+
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Entry is NULL",
+                __FUNCTION__, __LINE__);
+      //ASSERT
+      VOS_ASSERT(0);
+      return eHAL_STATUS_FAILURE;
+   }
+   flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+   ac = flow_info->ac_type;
+   pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   if(flow_info->tspec_mask != pACInfo->tspec_pending)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: No need to notify the HDD, the ADDTS "
+                "success is not for index = %d of the AC = %d",
+                __FUNCTION__, __LINE__,
+                flow_info->tspec_mask, ac);
+      return eHAL_STATUS_SUCCESS;
+   }
+   switch(flow_info->reason)
+   {
+   case SME_QOS_REASON_SETUP:
+      hdd_status = SME_QOS_STATUS_SETUP_SUCCESS_IND;
+      flow_info->reason = SME_QOS_REASON_REQ_SUCCESS;
+      delete_entry = VOS_FALSE;
+      inform_hdd = VOS_TRUE;
+      // check if App is looking for APSD
+      if(pACInfo->requested_QoSInfo[pACInfo->tspec_pending - 1].ts_info.psb)
+      {
+         // notify PMC as App is looking for APSD. If we already requested
+         // then we don't need to do anything
+         if(!pSession->uapsdAlreadyRequested)
+         {
+            // this is the first flow to detect we need PMC in UAPSD mode
+            pmc_status = pmcStartUapsd(pMac,
+                                       sme_QosPmcStartUapsdCallback,
+                                       pSession);
+            // if PMC doesn't return success right away means it is yet to put
+            // the module in BMPS state & later to UAPSD state
+            if(eHAL_STATUS_FAILURE == pmc_status)
+            {
+               hdd_status = SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_SET_FAILED;
+               // we need to always notify this case
+               flow_info->hoRenewal = VOS_FALSE;
+            }
+            else if(eHAL_STATUS_PMC_PENDING == pmc_status)
+            {
+               // let other flows know PMC has been notified
+               pSession->uapsdAlreadyRequested = VOS_TRUE;
+            }
+            // for any other pmc status we declare success
+         }
+      }
+      break;
+   case SME_QOS_REASON_RELEASE:
+      pACInfo->num_flows[pACInfo->tspec_pending - 1]--;
+      hdd_status = SME_QOS_STATUS_RELEASE_SUCCESS_RSP;
+      inform_hdd = VOS_TRUE;
+      delete_entry = VOS_TRUE;
+      break;
+   case SME_QOS_REASON_MODIFY:
+      delete_entry = VOS_TRUE;
+      inform_hdd = VOS_FALSE;
+      break;
+   case SME_QOS_REASON_MODIFY_PENDING:
+      hdd_status = SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND;
+      delete_entry = VOS_FALSE;
+      flow_info->reason = SME_QOS_REASON_REQ_SUCCESS;
+      inform_hdd = VOS_TRUE;
+      //notify PMC if App is looking for APSD
+      if(pACInfo->requested_QoSInfo[pACInfo->tspec_pending - 1].ts_info.psb)
+      {
+         // notify PMC as App is looking for APSD. If we already requested
+         // then we don't need to do anything.
+         if(!pSession->uapsdAlreadyRequested)
+         {
+            // this is the first flow to detect we need PMC in UAPSD mode
+            pmc_status = pmcStartUapsd(pMac,
+                                       sme_QosPmcStartUapsdCallback,
+                                       pSession);
+            // if PMC doesn't return success right away means it is yet to put
+            // the module in BMPS state & later to UAPSD state
+            if(eHAL_STATUS_FAILURE == pmc_status)
+            {
+               hdd_status = SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_IND_APSD_SET_FAILED;
+               // we need to always notify this case
+               flow_info->hoRenewal = VOS_FALSE;
+            }
+            else if(eHAL_STATUS_PMC_PENDING == pmc_status)
+            {
+               // let other flows know PMC has been notified
+               pSession->uapsdAlreadyRequested = VOS_TRUE;
+            }
+            // for any other pmc status we declare success
+         }
+      }
+      else
+      {
+        if((pACInfo->num_flows[flow_info->tspec_mask - 1] == 1) && 
+           (SME_QOS_TSPEC_MASK_BIT_1_2_SET != pACInfo->tspec_mask_status))
+        {
+          // this is the only TSPEC active on this AC
+          // so indicate that we no longer require APSD
+          pSession->apsdMask &= ~(1 << (SME_QOS_EDCA_AC_VO - ac));
+          //Also update modifyProfileFields.uapsd_mask in CSR for consistency
+          csrGetModifyProfileFields(pMac, flow_info->sessionId, &modifyProfileFields);
+          modifyProfileFields.uapsd_mask = pSession->apsdMask; 
+          csrSetModifyProfileFields(pMac, flow_info->sessionId, &modifyProfileFields);
+          if(!pSession->apsdMask)
+          {
+             // this session no longer needs UAPSD
+             // do any sessions still require UAPSD?
+             if (!sme_QosIsUapsdActive())
+             {
+                // No sessions require UAPSD so turn it off
+                // (really don't care when PMC stops it)
+                (void)pmcStopUapsd(pMac);
+             }
+          }
+        }
+      }
+      break;
+   case SME_QOS_REASON_REQ_SUCCESS:
+      hdd_status = SME_QOS_STATUS_SETUP_MODIFIED_IND;
+      inform_hdd = VOS_TRUE;
+   default:
+      delete_entry = VOS_FALSE;
+      break;
+   }
+   if(inform_hdd)
+   {
+      if(!flow_info->hoRenewal)
+      {
+      
+         flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                &pACInfo->curr_QoSInfo[pACInfo->tspec_pending - 1],
+                                hdd_status,
+                                flow_info->QosFlowID);
+      }
+      else
+      {
+         flow_info->hoRenewal = VOS_FALSE;
+      }
+   }
+   if(delete_entry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+                "%s: %d: Deleting entry at %p with flowID %d",
+                __FUNCTION__, __LINE__,
+                flow_info, flow_info->QosFlowID);
+      //delete the entry from Flow List
+      csrLLRemoveEntry(&sme_QosCb.flow_list, pEntry, VOS_TRUE );
+      // reclaim the memory
+      vos_mem_free(flow_info);
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosIsRspPending() - Utility function to check if we are waiting 
+  for an AddTS or reassoc response on some AC other than the given AC
+  
+  \param sessionId - Session we are interted in
+  \param ac - Enumeration of the various EDCA Access Categories.
+  
+  \return boolean
+  TRUE - Response is pending on an AC
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static v_BOOL_t sme_QosIsRspPending(v_U8_t sessionId, sme_QosEdcaAcType ac)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosEdcaAcType acIndex;
+   v_BOOL_t status = VOS_FALSE;
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   for(acIndex = SME_QOS_EDCA_AC_BE; acIndex < SME_QOS_EDCA_AC_MAX; acIndex++) 
+   {
+      if(acIndex == ac)
+      {
+         continue;
+      }
+      pACInfo = &pSession->ac_info[acIndex];
+      if((pACInfo->tspec_pending) || (pACInfo->reassoc_pending))
+      {
+         status = VOS_TRUE;
+         break;
+      }
+   }
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosIsUapsdActive() - Function which can be called to determine
+  if any sessions require PMC to be in U-APSD mode.
+  \return boolean
+  
+  Returns true if at least one session required PMC to be in U-APSD mode
+  Returns false if no sessions require PMC to be in U-APSD mode
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+static v_BOOL_t sme_QosIsUapsdActive(void)
+{
+   sme_QosSessionInfo *pSession;
+   v_U8_t sessionId;
+   for (sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; ++sessionId)
+   {
+      pSession = &sme_QosCb.sessionInfo[sessionId];
+      if ((pSession->sessionActive) && (pSession->apsdMask))
+      {
+         return VOS_TRUE;
+      }
+   }
+   // no active sessions have U-APSD active
+   return VOS_FALSE;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosPmcFullPowerCallback() - Callback function registered with PMC 
+  to notify SME-QoS when it puts the chip into full power
+  
+  \param callbackContext - The context passed to PMC during pmcRequestFullPower
+  call.
+  \param status - eHalStatus returned by PMC.
+  
+  \return None
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+void sme_QosPmcFullPowerCallback(void *callbackContext, eHalStatus status)
+{
+   sme_QosSessionInfo *pSession = callbackContext;
+   if(HAL_STATUS_SUCCESS(status))
+   {
+      (void)sme_QosProcessBufferedCmd(pSession->sessionId);
+   }
+   else
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: PMC failed to put the chip in Full power",
+                __FUNCTION__, __LINE__);
+      //ASSERT
+      VOS_ASSERT(0);
+   }
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosPmcStartUAPSDCallback() - Callback function registered with PMC 
+  to notify SME-QoS when it puts the chip into UAPSD mode
+  
+  \param callbackContext - The context passed to PMC during pmcStartUapsd call.
+  \param status - eHalStatus returned by PMC.
+  
+  \return None
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+void sme_QosPmcStartUapsdCallback(void *callbackContext, eHalStatus status)
+{
+   sme_QosSessionInfo *pSession = callbackContext;
+   // NOTE WELL
+   //
+   // In the orignal QoS design the TL module was responsible for
+   // the generation of trigger frames.  When that design was in
+   // use, we had to queue up any flows which were waiting for PMC
+   // since we didn't want to notify HDD until PMC had changed to
+   // UAPSD state.  Otherwise HDD would provide TL with the trigger
+   // frame parameters, and TL would start trigger frame generation
+   // before PMC was ready.  The flows were queued in various places
+   // throughout this module, and they were dequeued here following
+   // a successful transition to the UAPSD state by PMC.
+   //
+   // In the current QoS design the Firmware is responsible for the
+   // generation of trigger frames, but the parameters are still
+   // provided by TL via HDD.  The Firmware will be notified of the
+   // change to UAPSD state directly by PMC, at which time it will be
+   // responsible for the generation of trigger frames. Therefore
+   // where we used to queue up flows waiting for PMC to transition
+   // to the UAPSD state, we now always transition directly to the
+   // "success" state so that HDD will immediately provide the trigger
+   // frame parameters to TL, who will in turn plumb them down to the
+   // Firmware.  That way the Firmware will have the trigger frame
+   // parameters when it needs them
+   // just note that there is no longer an outstanding request
+   pSession->uapsdAlreadyRequested = VOS_FALSE;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosPmcCheckRoutine() - Function registered with PMC to check with 
+  SME-QoS whenever the device is about to enter one of the power 
+  save modes. PMC runs a poll with all the registered modules if device can 
+  enter powersave mode or remain in full power  
+  
+  \param callbackContext - The context passed to PMC during registration through
+  pmcRegisterPowerSaveCheck.
+  \return boolean
+  
+  SME-QOS returns PMC true or false respectively if it wants to vote for 
+  entering power save or not
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+v_BOOL_t sme_QosPmcCheckRoutine(void *callbackContext)
+{
+   sme_QosSessionInfo *pSession;
+   v_U8_t sessionId;
+   for (sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; ++sessionId)
+   {
+      pSession = &sme_QosCb.sessionInfo[sessionId];
+      if ((pSession->sessionActive) &&
+          (!pSession->readyForPowerSave))
+      {
+         return VOS_FALSE;
+      }
+   }
+   // all active sessions have voted for powersave
+   return VOS_TRUE;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosPmcDeviceStateUpdateInd() - Callback function registered with 
+  PMC to notify SME-QoS when it changes the power state
+  
+  \param callbackContext - The context passed to PMC during registration 
+  through pmcRegisterDeviceStateUpdateInd.
+  \param pmcState - Current power state that PMC moved into.
+  
+  \return None
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+void sme_QosPmcDeviceStateUpdateInd(void *callbackContext, tPmcState pmcState)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( callbackContext );
+   //check all the entries in Flow list for non-zero service interval, which will
+   //tell us if we need to notify HDD when PMC is out of UAPSD mode or going 
+   // back to UAPSD mode
+   switch(pmcState)
+   {
+   case FULL_POWER:
+      status = sme_QosProcessOutOfUapsdMode(pMac);
+      break;
+   case UAPSD:
+      status = sme_QosProcessIntoUapsdMode(pMac);
+      break;
+   default:
+      status = eHAL_STATUS_SUCCESS;
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: nothing to process in PMC state %d",
+                __FUNCTION__, __LINE__,
+                pmcState);
+   }
+   if(!HAL_STATUS_SUCCESS(status))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: ignoring Device(PMC) state change to %d",
+                __FUNCTION__, __LINE__,
+                pmcState);
+   }
+
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessOutOfUapsdMode() - Function to notify HDD when PMC 
+  notifies SME-QoS that it moved out of UAPSD mode to FULL power
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessOutOfUapsdMode(tpAniSirGlobal pMac)
+{
+   sme_QosSessionInfo *pSession;
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+   
+   pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_FALSE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Flow List empty, can't search",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_FALSE );
+      flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+      pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+      //only notify the flows which already successfully setup UAPSD
+      if((flow_info->QoSInfo.max_service_interval ||
+          flow_info->QoSInfo.min_service_interval) &&
+         (SME_QOS_REASON_REQ_SUCCESS == flow_info->reason))
+      {
+         flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                &pSession->ac_info[flow_info->ac_type].curr_QoSInfo[flow_info->tspec_mask - 1],
+                                SME_QOS_STATUS_OUT_OF_APSD_POWER_MODE_IND,
+                                flow_info->QosFlowID);
+      }
+      pEntry = pNextEntry;
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_QosProcessIntoUapsdMode() - Function to notify HDD when PMC 
+  notifies SME-QoS that it is moving into UAPSD mode 
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \return eHalStatus
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_QosProcessIntoUapsdMode(tpAniSirGlobal pMac)
+{
+   sme_QosSessionInfo *pSession;
+   tListElem *pEntry= NULL, *pNextEntry = NULL;
+   sme_QosFlowInfoEntry *flow_info = NULL;
+
+   pEntry = csrLLPeekHead( &sme_QosCb.flow_list, VOS_FALSE );
+   if(!pEntry)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Flow List empty, can't search",
+                __FUNCTION__, __LINE__);
+      return eHAL_STATUS_FAILURE;
+   }
+   while( pEntry )
+   {
+      pNextEntry = csrLLNext( &sme_QosCb.flow_list, pEntry, VOS_FALSE );
+      flow_info = GET_BASE_ADDR( pEntry, sme_QosFlowInfoEntry, link );
+      pSession = &sme_QosCb.sessionInfo[flow_info->sessionId];
+      //only notify the flows which already successfully setup UAPSD
+      if((flow_info->QoSInfo.max_service_interval ||
+          flow_info->QoSInfo.min_service_interval) &&
+         (SME_QOS_REASON_REQ_SUCCESS == flow_info->reason))
+      {
+         flow_info->QoSCallback(pMac, flow_info->HDDcontext, 
+                                &pSession->ac_info[flow_info->ac_type].curr_QoSInfo[flow_info->tspec_mask - 1],
+                                SME_QOS_STATUS_INTO_APSD_POWER_MODE_IND,
+                                flow_info->QosFlowID);
+      }
+      pEntry = pNextEntry;
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+
+void sme_QosCleanupCtrlBlkForHandoff(tpAniSirGlobal pMac, v_U8_t sessionId)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosEdcaAcType ac;
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      pACInfo = &pSession->ac_info[ac];
+      vos_mem_zero(pACInfo->curr_QoSInfo, 
+                   sizeof(sme_QosWmmTspecInfo) * SME_QOS_TSPEC_INDEX_MAX);
+      vos_mem_zero(pACInfo->requested_QoSInfo, 
+                   sizeof(sme_QosWmmTspecInfo) * SME_QOS_TSPEC_INDEX_MAX);
+      pACInfo->num_flows[0] = 0;
+      pACInfo->num_flows[1] = 0;
+      pACInfo->reassoc_pending = VOS_FALSE;
+      pACInfo->tspec_mask_status = 0;
+      pACInfo->tspec_pending = VOS_FALSE;
+      pACInfo->hoRenewal = VOS_FALSE;
+      pACInfo->prev_state = SME_QOS_LINK_UP;
+   }
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_QosIsTSInfoAckPolicyValid() - The SME QoS API exposed to HDD to 
+  check if TS info ack policy field can be set to "HT-immediate block acknowledgement" 
+  
+  \param pMac - The handle returned by macOpen.
+  \param pQoSInfo - Pointer to sme_QosWmmTspecInfo which contains the WMM TSPEC
+                    related info, provided by HDD
+  \param sessionId - sessionId returned by sme_OpenSession.
+  
+  \return VOS_TRUE - Current Association is HT association and so TS info ack policy
+                     can be set to "HT-immediate block acknowledgement"
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+v_BOOL_t sme_QosIsTSInfoAckPolicyValid(tpAniSirGlobal pMac,
+    sme_QosWmmTspecInfo * pQoSInfo,
+    v_U8_t sessionId)
+{
+  tDot11fBeaconIEs *pIes = NULL;
+  sme_QosSessionInfo *pSession;
+  eHalStatus hstatus;
+  if( !CSR_IS_SESSION_VALID( pMac, sessionId ) )
+  {
+     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+               "%s: %d: Session Id %d is invalid",
+               __FUNCTION__, __LINE__,
+               sessionId);
+     return VOS_FALSE;
+  }
+
+  pSession = &sme_QosCb.sessionInfo[sessionId];
+
+  if( !pSession->sessionActive )
+  {
+     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+               "%s: %d: Session %d is inactive",
+               __FUNCTION__, __LINE__,
+               sessionId);
+     return VOS_FALSE;
+  }
+
+  if(!pSession->assocInfo.pBssDesc)
+  {
+     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+               "%s: %d: Session %d has an Invalid BSS Descriptor",
+               __FUNCTION__, __LINE__,
+               sessionId);
+     return VOS_FALSE;
+  }
+
+  hstatus = csrGetParsedBssDescriptionIEs(pMac,
+                                          pSession->assocInfo.pBssDesc,
+                                          &pIes);
+  if(!HAL_STATUS_SUCCESS(hstatus))
+  {
+     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+               "%s: %d: On session %d unable to parse BSS IEs",
+               __FUNCTION__, __LINE__,
+               sessionId);
+     return VOS_FALSE;
+  }
+
+  /* success means pIes was allocated */
+
+  if(!pIes->HTCaps.present &&
+     pQoSInfo->ts_info.ack_policy == SME_QOS_WMM_TS_ACK_POLICY_HT_IMMEDIATE_BLOCK_ACK)
+  {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: On session %d HT Caps aren't present but application set ack policy to HT ",
+                __FUNCTION__, __LINE__,
+                sessionId);
+      
+      vos_mem_free(pIes);
+      return VOS_FALSE;
+  }
+
+  vos_mem_free(pIes);
+  return VOS_TRUE;
+}
+
+v_BOOL_t sme_QosValidateRequestedParams(tpAniSirGlobal pMac,
+    sme_QosWmmTspecInfo * pQoSInfo,
+    v_U8_t sessionId)
+{
+   v_BOOL_t rc = VOS_FALSE;
+
+   do
+   {
+      if(SME_QOS_WMM_TS_DIR_RESV == pQoSInfo->ts_info.direction) break;
+      if(!sme_QosIsTSInfoAckPolicyValid(pMac, pQoSInfo, sessionId)) break;
+
+      rc = VOS_TRUE;
+   }while(0);
+   return rc;
+}
+
+static eHalStatus qosIssueCommand( tpAniSirGlobal pMac, v_U8_t sessionId,
+                                   eSmeCommandType cmdType, sme_QosWmmTspecInfo * pQoSInfo,
+                                   sme_QosEdcaAcType ac, v_U8_t tspec_mask )
+{
+    eHalStatus status = eHAL_STATUS_RESOURCES;
+    tSmeCmd *pCommand = NULL;
+    do
+    {
+        pCommand = smeGetCommandBuffer( pMac );
+        if ( !pCommand )
+        {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                         "%s: %d: fail to get command buffer for command %d",
+                         __FUNCTION__, __LINE__, cmdType);
+            break;
+        }
+        pCommand->command = cmdType;
+        pCommand->sessionId = sessionId;
+        switch ( cmdType )
+        {
+        case eSmeCommandAddTs:
+            if( pQoSInfo )
+            {
+                status = eHAL_STATUS_SUCCESS;
+                pCommand->u.qosCmd.tspecInfo = *pQoSInfo;
+                pCommand->u.qosCmd.ac = ac;
+            }
+            else
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                         "%s: %d: NULL pointer passed",
+                         __FUNCTION__, __LINE__);
+               status = eHAL_STATUS_INVALID_PARAMETER;
+            }
+            break;
+        case eSmeCommandDelTs:
+            status = eHAL_STATUS_SUCCESS;
+            pCommand->u.qosCmd.ac = ac;
+            pCommand->u.qosCmd.tspec_mask = tspec_mask;
+            break;
+        default:
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                      "%s: %d: invalid command type %d",
+                      __FUNCTION__, __LINE__, cmdType );
+            status = eHAL_STATUS_INVALID_PARAMETER;
+            break;
+        }
+    } while( 0 );
+    if( HAL_STATUS_SUCCESS( status ) && pCommand )
+    {
+        smePushCommand( pMac, pCommand, eANI_BOOLEAN_FALSE );
+    }
+    else if( pCommand )
+    {
+        qosReleaseCommand( pMac, pCommand );
+    }
+    return( status );
+}
+tANI_BOOLEAN qosProcessCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_BOOLEAN fRemoveCmd = eANI_BOOLEAN_TRUE;
+    do
+    {
+        switch ( pCommand->command )
+        {
+        case eSmeCommandAddTs:
+            status = sme_QosAddTsReq( pMac, (v_U8_t)pCommand->sessionId, &pCommand->u.qosCmd.tspecInfo, pCommand->u.qosCmd.ac);
+            if( HAL_STATUS_SUCCESS( status ) )
+            {
+                fRemoveCmd = eANI_BOOLEAN_FALSE;
+                status = SME_QOS_STATUS_SETUP_REQ_PENDING_RSP;
+            }
+            break;
+        case eSmeCommandDelTs:
+            status = sme_QosDelTsReq( pMac, (v_U8_t)pCommand->sessionId, pCommand->u.qosCmd.ac, pCommand->u.qosCmd.tspec_mask );
+            if( HAL_STATUS_SUCCESS( status ) )
+            {
+                fRemoveCmd = eANI_BOOLEAN_FALSE;
+            }
+            break;
+        default:
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                      "%s: %d: invalid command type %d",
+                      __FUNCTION__, __LINE__, pCommand->command );
+            break;
+        }//switch
+    } while(0);
+    return( fRemoveCmd );
+}
+
+/*
+  sme_QosTriggerUapsdChange
+  Invoked by BTC when UAPSD bypass is enabled or disabled
+  We, in turn, must disable or enable UAPSD on all flows as appropriate
+  That may require us to re-add TSPECs or to reassociate
+*/
+sme_QosStatusType sme_QosTriggerUapsdChange( tpAniSirGlobal pMac )
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   v_U8_t ac, tspec1 = 0, tspec2 = 0; 
+   v_U8_t uapsd_mask;
+   tDot11fBeaconIEs *pIesLocal;
+   v_U8_t acm_mask;
+   v_BOOL_t fIsUapsdNeeded;
+   v_U8_t sessionId;
+   v_BOOL_t addtsWhenACMNotSet = CSR_IS_ADDTS_WHEN_ACMOFF_SUPPORTED(pMac);
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+             "%s: %d: Invoked",
+             __FUNCTION__, __LINE__);
+   for (sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; ++sessionId)
+   {
+      pSession = &sme_QosCb.sessionInfo[sessionId];
+      if( !pSession->sessionActive )
+      {
+         continue;
+      }
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                "%s: %d: Session %d is active",
+                __FUNCTION__, __LINE__,
+                sessionId);
+      if( HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSession->assocInfo.pBssDesc, &pIesLocal)) )
+      {
+         // get the ACM mask
+         acm_mask = sme_QosGetACMMask(pMac, pSession->assocInfo.pBssDesc, pIesLocal);
+         vos_mem_free(pIesLocal);
+         // get the uapsd mask for this session
+         uapsd_mask = pSession->apsdMask;
+         // unmask the bits with ACM on to avoid reassoc on them 
+         uapsd_mask &= ~acm_mask;
+         // iterate through the ACs to determine if we need to re-add any TSPECs
+         for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++)
+         {
+            pACInfo = &pSession->ac_info[ac];
+            // Does this AC have QoS active?
+            if( SME_QOS_QOS_ON == pACInfo->curr_state )
+            {
+               // Yes, QoS is active on this AC
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                         "%s: %d: On session %d AC %d has QoS active",
+                         __FUNCTION__, __LINE__,
+                         sessionId, ac);
+               // Does this AC require ACM?
+               if(( acm_mask & (1 << (SME_QOS_EDCA_AC_VO - ac)) ) || addtsWhenACMNotSet )
+               {
+                  // Yes, so we need to re-add any TSPECS
+                  VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                            "%s: %d: On session %d AC %d has ACM enabled",
+                            __FUNCTION__, __LINE__,
+                            sessionId, ac);
+                  // Are any TSPECs active?
+                  if( pACInfo->tspec_mask_status )
+                  {
+                     // Yes, at least 1 TSPEC is active.  Are they both active?
+                     if( SME_QOS_TSPEC_MASK_BIT_1_2_SET == pACInfo->tspec_mask_status )
+                     {
+                        //both TSPECS are active
+                        tspec1 = SME_QOS_TSPEC_MASK_BIT_1_SET;
+                        tspec2 = SME_QOS_TSPEC_MASK_BIT_2_SET;
+                     }
+                     else
+                     {
+                        // only one TSPEC is active, get its mask
+                        tspec1 = SME_QOS_TSPEC_MASK_BIT_1_2_SET & pACInfo->tspec_mask_status;
+                     }
+                     // Does TSPEC 1 really require UAPSD?
+                     fIsUapsdNeeded = (v_BOOL_t)(pACInfo->curr_QoSInfo[tspec1 - 1].max_service_interval || 
+                                                 pACInfo->curr_QoSInfo[tspec1 - 1].min_service_interval);
+                     //double check whether we need to do anything
+                     if( fIsUapsdNeeded )
+                     {
+                        pACInfo->requested_QoSInfo[tspec1 - 1] = 
+                           pACInfo->curr_QoSInfo[tspec1 - 1];
+                        sme_QosReRequestAddTS( pMac, sessionId,
+                                               &pACInfo->requested_QoSInfo[tspec1 - 1],
+                                               ac,
+                                               tspec1 );
+                     }
+                     // Is TSPEC 2 active?
+                     if( tspec2 )
+                     {
+                        // Does TSPEC 2 really require UAPSD?
+                        fIsUapsdNeeded = (v_BOOL_t)(pACInfo->curr_QoSInfo[tspec2 - 1].max_service_interval || 
+                                                    pACInfo->curr_QoSInfo[tspec2 - 1].min_service_interval);
+                        if( fIsUapsdNeeded )
+                        {
+                           //No need to inform HDD
+                           //pACInfo->hoRenewal = VOS_TRUE;
+                           pACInfo->requested_QoSInfo[tspec2 - 1] = 
+                              pACInfo->curr_QoSInfo[tspec2 - 1];
+                           sme_QosReRequestAddTS( pMac, sessionId,
+                                                  &pACInfo->requested_QoSInfo[tspec2 - 1],
+                                                  ac,
+                                                  tspec2);
+                        }
+                     }
+                  }
+                  else
+                  {
+                     // QoS is set, ACM is on, but no TSPECs -- inconsistent state
+                     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                               "%s: %d: On session %d AC %d has QoS enabled and ACM is set, but no TSPEC",
+                               __FUNCTION__, __LINE__,
+                               sessionId, ac);
+                     VOS_ASSERT(0);
+                  }
+               }
+               else
+               {
+                  //Since ACM bit is not set, there should be only one QoS information for both directions.
+                  fIsUapsdNeeded = (v_BOOL_t)(pACInfo->curr_QoSInfo[0].max_service_interval || 
+                                              pACInfo->curr_QoSInfo[0].min_service_interval);
+                  if(fIsUapsdNeeded)
+                  {
+                     // we need UAPSD on this AC (and we may not currently have it)
+                     uapsd_mask |= 1 << (SME_QOS_EDCA_AC_VO - ac);
+                     VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                               "%s: %d: On session %d AC %d has ACM disabled, uapsd mask now 0x%X",
+                               __FUNCTION__, __LINE__,
+                               sessionId, ac, uapsd_mask);
+                  }
+               }
+            }
+         }
+         // do we need to reassociate?
+         if(uapsd_mask)
+         {
+            tCsrRoamModifyProfileFields modifyProfileFields;
+            //we need to do a reassoc on these AC 
+            csrGetModifyProfileFields(pMac, sessionId, &modifyProfileFields);
+            if( btcIsReadyForUapsd(pMac) )
+            {
+               modifyProfileFields.uapsd_mask = uapsd_mask;
+            }
+            else
+            {  
+               modifyProfileFields.uapsd_mask = 0;
+            }
+            //Do we need to inform HDD?
+            if(!HAL_STATUS_SUCCESS(sme_QosRequestReassoc(pMac, sessionId, &modifyProfileFields, VOS_TRUE)))
+            {
+               //err msg
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                         "%s: %d: On Session %d Reassoc failed",
+                         __FUNCTION__, __LINE__,
+                         sessionId);
+            }
+         }
+      }
+      else
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                   "%s: %d: On Session %d failed to parse IEs",
+                   __FUNCTION__, __LINE__,
+                   sessionId);
+      }
+   }
+   // return status is ignored by BTC
+   return SME_QOS_STATUS_SETUP_SUCCESS_IND;
+}
+
+/*
+    sme_QosReRequestAddTS to re-send AddTS for the combined QoS request
+*/
+static sme_QosStatusType sme_QosReRequestAddTS(tpAniSirGlobal pMac,
+                                               v_U8_t sessionId,
+                                               sme_QosWmmTspecInfo * pQoSInfo,
+                                               sme_QosEdcaAcType ac,
+                                               v_U8_t tspecMask)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   sme_QosStatusType status = SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+   sme_QosCmdInfo  cmd;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+             "%s: %d: Invoked on session %d for AC %d TSPEC %d",
+             __FUNCTION__, __LINE__,
+             sessionId, ac, tspecMask);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   pACInfo = &pSession->ac_info[ac];
+   // need to vote off powersave for the duration of this request
+   pSession->readyForPowerSave = VOS_FALSE;
+   //call PMC's request for power function
+   // AND
+   //another check is added considering the flowing scenario
+   //Addts reqest is pending on one AC, while APSD requested on another which 
+   //needs a reassoc. Will buffer a request if Addts is pending on any AC, 
+   //which will safegaurd the above scenario, & also won't confuse PE with back 
+   //to back Addts or Addts followed by Reassoc
+   if(sme_QosIsRspPending(sessionId, ac) || 
+      ( eHAL_STATUS_PMC_PENDING == pmcRequestFullPower(pMac, sme_QosPmcFullPowerCallback, pSession, eSME_REASON_OTHER)))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                "%s: %d: On session %d buffering the AddTS request "
+                   "for AC %d in state %d as Addts is pending "
+                "on other AC or waiting for full power",
+                __FUNCTION__, __LINE__,
+                sessionId, ac, pACInfo->curr_state);
+      //buffer cmd
+      cmd.command = SME_QOS_RESEND_REQ;
+      cmd.pMac = pMac;
+      cmd.sessionId = sessionId;
+      cmd.u.resendCmdInfo.ac = ac;
+      cmd.u.resendCmdInfo.tspecMask = tspecMask;
+      cmd.u.resendCmdInfo.QoSInfo = *pQoSInfo;
+      if(!HAL_STATUS_SUCCESS(sme_QosBufferCmd(&cmd, VOS_FALSE)))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                   "%s: %d: On session %d unable to buffer the AddTS "
+                   "request for AC %d TSPEC %d in state %d",
+                   __FUNCTION__, __LINE__,
+                   sessionId, ac, tspecMask, pACInfo->curr_state);
+         // unable to buffer the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+      }
+      return SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP;
+   }
+   //get into the stat m/c to see if the request can be granted
+   switch(pACInfo->curr_state)
+   {
+   case SME_QOS_QOS_ON:
+      {
+         //if ACM, send out a new ADDTS
+         pACInfo->hoRenewal = VOS_TRUE;
+         status = sme_QosSetup(pMac, sessionId, pQoSInfo, ac);
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+                   "%s: %d: sme_QosSetup returned in SME_QOS_QOS_ON state on "
+                   "AC %d with status =%d",
+                   __FUNCTION__, __LINE__,
+                   ac, status);
+         if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP != status)
+         {
+            // we aren't waiting for a response from the AP
+            // so vote powersave back on
+            pSession->readyForPowerSave = VOS_TRUE;
+         }
+         if(SME_QOS_STATUS_SETUP_REQ_PENDING_RSP == status) 
+         {
+            status = SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP;
+            pACInfo->tspec_pending = tspecMask;
+         }
+         else if((SME_QOS_STATUS_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status) ||
+                 (SME_QOS_STATUS_SETUP_SUCCESS_APSD_SET_ALREADY == status) ||
+                 (SME_QOS_STATUS_SETUP_SUCCESS_IND_APSD_PENDING == status))
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: UAPSD is setup already status = %d "
+                      "returned by sme_QosSetup",
+                      __FUNCTION__, __LINE__,
+                      status);  
+         }
+         else
+         {
+            //err msg
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                      "%s: %d: unexpected status = %d returned by sme_QosSetup",
+                      __FUNCTION__, __LINE__,
+                      status);
+         }
+      }
+      break;
+   case SME_QOS_HANDOFF:
+   case SME_QOS_REQUESTED:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: Re-Add request in state = %d  buffer the request",
+                __FUNCTION__, __LINE__,
+                pACInfo->curr_state);
+      cmd.command = SME_QOS_RESEND_REQ;
+      cmd.pMac = pMac;
+      cmd.sessionId = sessionId;
+      cmd.u.resendCmdInfo.ac = ac;
+      cmd.u.resendCmdInfo.tspecMask = tspecMask;
+      cmd.u.resendCmdInfo.QoSInfo = *pQoSInfo;
+      if(!HAL_STATUS_SUCCESS(sme_QosBufferCmd(&cmd, VOS_FALSE)))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "%s: %d: couldn't buffer the readd request in state = %d",
+                   __FUNCTION__, __LINE__,
+                   pACInfo->curr_state );
+         // unable to buffer the request
+         // nothing is pending so vote powersave back on
+         pSession->readyForPowerSave = VOS_TRUE;
+         return SME_QOS_STATUS_MODIFY_SETUP_FAILURE_RSP;
+      }
+      status = SME_QOS_STATUS_MODIFY_SETUP_PENDING_RSP;
+      break;
+   case SME_QOS_CLOSED:
+   case SME_QOS_INIT:
+   case SME_QOS_LINK_UP:
+   default:
+      //print error msg, 
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                "%s: %d: ReAdd request in unexpected state = %d",
+                __FUNCTION__, __LINE__,
+                pACInfo->curr_state );
+      // unable to service the request
+      // nothing is pending so vote powersave back on
+      pSession->readyForPowerSave = VOS_TRUE;
+      // ASSERT?
+      break;
+   }
+   if((SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_NO_ACM_NO_APSD_RSP == status) ||
+      (SME_QOS_STATUS_MODIFY_SETUP_SUCCESS_APSD_SET_ALREADY == status)) 
+   {
+      (void)sme_QosProcessBufferedCmd(sessionId);
+   }
+   return (status);
+}
+
+static void sme_QosInitACs(tpAniSirGlobal pMac, v_U8_t sessionId)
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosEdcaAcType ac;
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+   {
+      vos_mem_zero(&pSession->ac_info[ac], sizeof(sme_QosACInfo));
+      sme_QosStateTransition(sessionId, ac, SME_QOS_INIT);
+   }
+}
+static eHalStatus sme_QosRequestReassoc(tpAniSirGlobal pMac, tANI_U8 sessionId,
+                                        tCsrRoamModifyProfileFields *pModFields,
+                                        v_BOOL_t fForce )
+{
+   sme_QosSessionInfo *pSession;
+   sme_QosACInfo *pACInfo;
+   eHalStatus status;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
+             "%s: %d: Invoked on session %d with UAPSD mask 0x%X",
+             __FUNCTION__, __LINE__,
+             sessionId, pModFields->uapsd_mask);
+   pSession = &sme_QosCb.sessionInfo[sessionId];
+   status = csrReassoc(pMac, sessionId, pModFields, &pSession->roamID, fForce);
+   if(HAL_STATUS_SUCCESS(status))
+   {
+      //Update the state to Handoff so subsequent requests are queued until
+      // this one is finished
+      sme_QosEdcaAcType ac;
+      for(ac = SME_QOS_EDCA_AC_BE; ac < SME_QOS_EDCA_AC_MAX; ac++) 
+      {
+         pACInfo = &pSession->ac_info[ac];
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                   "%s: %d: AC[%d] is in state [%d]",
+                   __FUNCTION__, __LINE__,
+                   ac, pACInfo->curr_state );
+         // If it is already in HANDOFF state, don't do anything since we
+         // MUST preserve the previous state and sme_QosStateTransition
+         // will change the previous state
+         if(SME_QOS_HANDOFF != pACInfo->curr_state)
+         {
+            sme_QosStateTransition(sessionId, ac, SME_QOS_HANDOFF);
+         }
+      }
+   }
+   return status;
+}
+static v_U32_t sme_QosAssignFlowId(void)
+{
+   v_U32_t flowId;
+   flowId = sme_QosCb.nextFlowId;
+   if (SME_QOS_MAX_FLOW_ID == flowId)
+   {
+      // The Flow ID wrapped.  This is obviously not a real life scenario
+      // but handle it to keep the software test folks happy
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, 
+                "%s: %d: Software Test made the flow counter wrap, "
+                "QoS may no longer be functional",
+                __FUNCTION__, __LINE__);
+      sme_QosCb.nextFlowId = SME_QOS_MIN_FLOW_ID;
+   }
+   else
+   {
+      sme_QosCb.nextFlowId++;
+   }
+   return flowId;
+}
+
+static v_U8_t sme_QosAssignDialogToken(void)
+{
+   v_U8_t token;
+   token = sme_QosCb.nextDialogToken;
+   if (SME_QOS_MAX_DIALOG_TOKEN == token)
+   {
+      // wrap is ok
+      sme_QosCb.nextDialogToken = SME_QOS_MIN_DIALOG_TOKEN;
+   }
+   else
+   {
+      sme_QosCb.nextDialogToken++;
+   }
+   return token;
+}
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT */
diff --git a/CORE/SME/src/btc/btcApi.c b/CORE/SME/src/btc/btcApi.c
new file mode 100644
index 0000000..36d1fbe
--- /dev/null
+++ b/CORE/SME/src/btc/btcApi.c
@@ -0,0 +1,1941 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/******************************************************************************
+*
+* Name:  btcApi.c
+*
+* Description: Routines that make up the BTC API.
+*
+* Copyright 2008 (c) Qualcomm, Incorporated. All Rights Reserved.
+* Qualcomm Confidential and Proprietary.
+*
+******************************************************************************/
+#include "wlan_qct_wda.h"
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+#include "aniGlobal.h"
+#include "smsDebug.h"
+#include "btcApi.h"
+#include "cfgApi.h"
+#include "pmc.h"
+#include "smeQosInternal.h"
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+#include "vos_diag_core_event.h"
+#include "vos_diag_core_log.h"
+#endif /* FEATURE_WLAN_DIAG_SUPPORT */
+static void btcLogEvent (tHalHandle hHal, tpSmeBtEvent pBtEvent);
+static void btcRestoreHeartBeatMonitoringHandle(void* hHal);
+static void btcUapsdCheck( tpAniSirGlobal pMac, tpSmeBtEvent pBtEvent );
+VOS_STATUS btcCheckHeartBeatMonitoring(tHalHandle hHal, tpSmeBtEvent pBtEvent);
+static void btcPowerStateCB( v_PVOID_t pContext, tPmcState pmcState );
+static VOS_STATUS btcDeferEvent( tpAniSirGlobal pMac, tpSmeBtEvent pEvent );
+static VOS_STATUS btcDeferDisconnEvent( tpAniSirGlobal pMac, tpSmeBtEvent pEvent );
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+static void btcDiagEventLog (tHalHandle hHal, tpSmeBtEvent pBtEvent);
+#endif /* FEATURE_WLAN_DIAG_SUPPORT */
+/* ---------------------------------------------------------------------------
+    \fn btcOpen
+    \brief  API to init the BTC Events Layer
+    \param  hHal - The handle returned by macOpen.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  success
+            VOS_STATUS_SUCCESS  failure
+  ---------------------------------------------------------------------------*/
+VOS_STATUS btcOpen (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   VOS_STATUS vosStatus;
+   /* Initialize BTC configuartion. */
+   pMac->btc.btcConfig.btcExecutionMode = BTC_SMART_COEXISTENCE;
+   pMac->btc.btcConfig.btcConsBtSlotsToBlockDuringDhcp = 0;
+   pMac->btc.btcConfig.btcA2DPBtSubIntervalsDuringDhcp = BTC_MAX_NUM_ACL_BT_SUB_INTS;
+   pMac->btc.btcConfig.btcBtIntervalMode1 = BTC_BT_INTERVAL_MODE1_DEFAULT;
+   pMac->btc.btcConfig.btcWlanIntervalMode1 = BTC_WLAN_INTERVAL_MODE1_DEFAULT;
+   pMac->btc.btcConfig.btcActionOnPmFail = BTC_START_NEXT;
+   pMac->btc.btcReady = VOS_FALSE;
+   pMac->btc.btcEventState = 0;
+   pMac->btc.btcHBActive = VOS_TRUE;
+
+   vosStatus = vos_timer_init( &pMac->btc.restoreHBTimer,
+                      VOS_TIMER_TYPE_SW,
+                      btcRestoreHeartBeatMonitoringHandle,
+                      (void*) hHal);
+   if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcOpen: Fail to init timer");
+       return VOS_STATUS_E_FAILURE;
+   }
+   if( !HAL_STATUS_SUCCESS(pmcRegisterDeviceStateUpdateInd( pMac, btcPowerStateCB, pMac )) )
+   {
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcOpen: Fail to register PMC callback\n");
+       return VOS_STATUS_E_FAILURE;
+   }
+   return VOS_STATUS_SUCCESS;
+}
+/* ---------------------------------------------------------------------------
+    \fn btcClose
+    \brief  API to exit the BTC Events Layer
+    \param  hHal - The handle returned by macOpen.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  success
+            VOS_STATUS_SUCCESS  failure
+  ---------------------------------------------------------------------------*/
+VOS_STATUS btcClose (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   VOS_STATUS vosStatus;
+   pMac->btc.btcReady = VOS_FALSE;
+   pMac->btc.btcUapsdOk = VOS_FALSE;
+   vos_timer_stop(&pMac->btc.restoreHBTimer);
+   vosStatus = vos_timer_destroy(&pMac->btc.restoreHBTimer);
+   if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcClose: Fail to destroy timer");
+       return VOS_STATUS_E_FAILURE;
+   }
+   if(!HAL_STATUS_SUCCESS(
+      pmcDeregisterDeviceStateUpdateInd(pMac, btcPowerStateCB)))
+   {
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,
+         "%s: %d: cannot deregister with pmcDeregisterDeviceStateUpdateInd()",
+                __FUNCTION__, __LINE__);
+   }
+
+   return VOS_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn btcReady
+    \brief  fn to inform BTC that eWNI_SME_SYS_READY_IND has been sent to PE.
+            This acts as a trigger to send a message to HAL to update the BTC
+            related conig to FW. Note that if HDD configures any power BTC
+            related stuff before this API is invoked, BTC will buffer all the
+            configutaion.
+    \param  hHal - The handle returned by macOpen.
+    \return VOS_STATUS
+  ---------------------------------------------------------------------------*/
+VOS_STATUS btcReady (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    v_U32_t cfgVal = 0;
+    v_U8_t i;
+    pMac->btc.btcReady = VOS_TRUE;
+    pMac->btc.btcUapsdOk = VOS_TRUE;
+    for(i=0; i < BT_MAX_SCO_SUPPORT; i++)
+    {
+        pMac->btc.btcScoHandles[i] = BT_INVALID_CONN_HANDLE;
+    }
+
+    // Read heartbeat threshold CFG and save it.
+    ccmCfgGetInt(pMac, WNI_CFG_HEART_BEAT_THRESHOLD, &cfgVal);
+    pMac->btc.btcHBCount = (v_U8_t)cfgVal;
+    if (btcSendCfgMsg(hHal, &(pMac->btc.btcConfig)) != VOS_STATUS_SUCCESS)
+    {
+        return VOS_STATUS_E_FAILURE;
+    }
+    return VOS_STATUS_SUCCESS;
+}
+
+static VOS_STATUS btcSendBTEvent(tpAniSirGlobal pMac, tpSmeBtEvent pBtEvent)
+{
+   vos_msg_t msg;
+   tpSmeBtEvent ptrSmeBtEvent = NULL;
+   switch(pBtEvent->btEventType)
+   {
+      case BT_EVENT_CREATE_SYNC_CONNECTION:
+      case BT_EVENT_SYNC_CONNECTION_UPDATED:
+         if(pBtEvent->uEventParam.btSyncConnection.linkType != BT_SCO &&
+            pBtEvent->uEventParam.btSyncConnection.linkType != BT_eSCO)
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+               "Invalid link type %d for Sync Connection. BT event will be dropped ",
+               __FUNCTION__, pBtEvent->uEventParam.btSyncConnection.linkType);
+            return VOS_STATUS_E_FAILURE;
+         }
+         break;
+      case BT_EVENT_SYNC_CONNECTION_COMPLETE:
+         if((pBtEvent->uEventParam.btSyncConnection.status == BT_CONN_STATUS_SUCCESS) &&
+            ((pBtEvent->uEventParam.btSyncConnection.linkType != BT_SCO && pBtEvent->uEventParam.btSyncConnection.linkType != BT_eSCO) ||
+             (pBtEvent->uEventParam.btSyncConnection.connectionHandle == BT_INVALID_CONN_HANDLE)))
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+               "Invalid connection handle %d or link type %d for Sync Connection. BT event will be dropped ",
+               __FUNCTION__,
+               pBtEvent->uEventParam.btSyncConnection.connectionHandle,
+               pBtEvent->uEventParam.btSyncConnection.linkType);
+            return VOS_STATUS_E_FAILURE;
+         }
+         break;
+      case BT_EVENT_MODE_CHANGED:
+         if(pBtEvent->uEventParam.btAclModeChange.mode >= BT_ACL_MODE_MAX)
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+               "Invalid mode %d for ACL Connection. BT event will be dropped ",
+               __FUNCTION__,
+               pBtEvent->uEventParam.btAclModeChange.mode);
+            return VOS_STATUS_E_FAILURE;
+         }
+         break;
+     case BT_EVENT_DEVICE_SWITCHED_OFF:
+         pMac->btc.btcEventState = 0;
+         break;
+      default:
+         break;
+   }
+   ptrSmeBtEvent = vos_mem_malloc(sizeof(tSmeBtEvent));
+   if (NULL == ptrSmeBtEvent)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+         "Not able to allocate memory for BT event", __FUNCTION__);
+      return VOS_STATUS_E_FAILURE;
+   }
+   btcLogEvent(pMac, pBtEvent);
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+   btcDiagEventLog(pMac, pBtEvent);
+#endif
+   vos_mem_copy(ptrSmeBtEvent, pBtEvent, sizeof(tSmeBtEvent));
+   msg.type = WDA_SIGNAL_BT_EVENT;
+   msg.reserved = 0;
+   msg.bodyptr = ptrSmeBtEvent;
+   if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+         "Not able to post WDA_SIGNAL_BT_EVENT message to WDA", __FUNCTION__);
+      vos_mem_free( ptrSmeBtEvent );
+      return VOS_STATUS_E_FAILURE;
+   }
+   // After successfully posting the message, check if heart beat
+   // monitoring needs to be turned off
+   (void)btcCheckHeartBeatMonitoring(pMac, pBtEvent);
+   //Check whether BTC and UAPSD can co-exist
+   btcUapsdCheck( pMac, pBtEvent );
+   return VOS_STATUS_SUCCESS;
+   }
+
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+/* ---------------------------------------------------------------------------
+    \fn btcSignalBTEvent
+    \brief  API to signal Bluetooth (BT) event to the WLAN driver. Based on the
+            BT event type and the current operating mode of Libra (full power,
+            BMPS, UAPSD etc), appropriate Bluetooth Coexistence (BTC) strategy
+            would be employed.
+    \param  hHal - The handle returned by macOpen.
+    \param  pBtEvent -  Pointer to a caller allocated object of type tSmeBtEvent.
+                        Caller owns the memory and is responsible for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE – BT Event not passed to HAL. This can happen
+                                   if driver has not yet been initialized or if BTC
+                                   Events Layer has been disabled.
+            VOS_STATUS_SUCCESS   – BT Event passed to HAL
+  ---------------------------------------------------------------------------*/
+VOS_STATUS btcSignalBTEvent (tHalHandle hHal, tpSmeBtEvent pBtEvent)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   VOS_STATUS vosStatus;
+   if( NULL == pBtEvent )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+         "Null pointer for SME BT Event", __FUNCTION__);
+      return VOS_STATUS_E_FAILURE;
+   }
+   if(( BTC_WLAN_ONLY == pMac->btc.btcConfig.btcExecutionMode ) ||
+      ( BTC_PTA_ONLY == pMac->btc.btcConfig.btcExecutionMode ))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+         "BTC execution mode not set to BTC_SMART_COEXISTENCE. BT event will be dropped", __FUNCTION__);
+      return VOS_STATUS_E_FAILURE;
+   }
+   if( pBtEvent->btEventType < 0 || pBtEvent->btEventType >= BT_EVENT_TYPE_MAX )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+         "Invalid BT event %d being passed. BT event will be dropped",
+          __FUNCTION__, pBtEvent->btEventType);
+      return VOS_STATUS_E_FAILURE;
+   }
+   //Check PMC state to make sure whether we need to defer
+   //If we already have deferred events, defer the new one as well, in case PMC is in transition state
+   if( pMac->btc.fReplayBTEvents || !PMC_IS_CHIP_ACCESSIBLE(pmcGetPmcState( pMac )) )
+   {
+       //We need to defer the event
+       vosStatus = btcDeferEvent(pMac, pBtEvent);
+       if( VOS_IS_STATUS_SUCCESS(vosStatus) )
+       {
+           pMac->btc.fReplayBTEvents = VOS_TRUE;
+           return VOS_STATUS_SUCCESS;
+       }
+       else
+       {
+           return vosStatus;
+       }
+   }
+    btcSendBTEvent(pMac, pBtEvent);
+   return VOS_STATUS_SUCCESS;
+}
+#endif
+/* ---------------------------------------------------------------------------
+    \fn btcCheckHeartBeatMonitoring
+    \brief  API to check whether heartbeat monitoring is required to be disabled
+            for specific BT start events which takes significant time to complete
+            during which WLAN misses beacons. To avoid WLAN-MAC from disconnecting
+            for the not enough beacons received we stop the heartbeat timer during
+            this start BT event till the stop of that BT event.
+    \param  hHal - The handle returned by macOpen.
+    \param  pBtEvent -  Pointer to a caller allocated object of type tSmeBtEvent.
+                        Caller owns the memory and is responsible for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  Config not passed to HAL.
+            VOS_STATUS_SUCCESS  Config passed to HAL
+  ---------------------------------------------------------------------------*/
+VOS_STATUS btcCheckHeartBeatMonitoring(tHalHandle hHal, tpSmeBtEvent pBtEvent)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   VOS_STATUS vosStatus;
+   switch(pBtEvent->btEventType)
+   {
+      // Start events which requires heartbeat monitoring be disabled.
+      case BT_EVENT_INQUIRY_STARTED:
+          pMac->btc.btcEventState |= BT_INQUIRY_STARTED;
+          break;
+      case BT_EVENT_PAGE_STARTED:
+          pMac->btc.btcEventState |= BT_PAGE_STARTED;
+          break;
+      case BT_EVENT_CREATE_ACL_CONNECTION:
+          pMac->btc.btcEventState |= BT_CREATE_ACL_CONNECTION_STARTED;
+          break;
+      case BT_EVENT_CREATE_SYNC_CONNECTION:
+          pMac->btc.btcEventState |= BT_CREATE_SYNC_CONNECTION_STARTED;
+          break;
+      // Stop/done events which indicates heartbeat monitoring can be enabled
+      case BT_EVENT_INQUIRY_STOPPED:
+          pMac->btc.btcEventState &= ~(BT_INQUIRY_STARTED);
+          break;
+      case BT_EVENT_PAGE_STOPPED:
+          pMac->btc.btcEventState &= ~(BT_PAGE_STARTED);
+          break;
+      case BT_EVENT_ACL_CONNECTION_COMPLETE:
+          pMac->btc.btcEventState &= ~(BT_CREATE_ACL_CONNECTION_STARTED);
+          break;
+      case BT_EVENT_SYNC_CONNECTION_COMPLETE:
+          pMac->btc.btcEventState &= ~(BT_CREATE_SYNC_CONNECTION_STARTED);
+          break;
+      default:
+          // Ignore other events
+          return VOS_STATUS_SUCCESS;
+   }
+   // Check if any of the BT start events are active
+   if (pMac->btc.btcEventState) {
+       if (pMac->btc.btcHBActive) {
+           // set heartbeat threshold CFG to zero
+           ccmCfgSetInt(pMac, WNI_CFG_HEART_BEAT_THRESHOLD, 0, NULL, eANI_BOOLEAN_FALSE);
+           pMac->btc.btcHBActive = VOS_FALSE;
+       }
+       // Deactivate and active the restore HB timer
+       vos_timer_stop( &pMac->btc.restoreHBTimer);
+       vosStatus= vos_timer_start( &pMac->btc.restoreHBTimer, BT_MAX_EVENT_DONE_TIMEOUT );
+       if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
+           VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcCheckHeartBeatMonitoring: Fail to start timer");
+           return VOS_STATUS_E_FAILURE;
+       }
+   } else {
+       // Restore CFG back to the original value only if it was disabled
+       if (!pMac->btc.btcHBActive) {
+           ccmCfgSetInt(pMac, WNI_CFG_HEART_BEAT_THRESHOLD, pMac->btc.btcHBCount, NULL, eANI_BOOLEAN_FALSE);
+           pMac->btc.btcHBActive = VOS_TRUE;
+       }
+       // Deactivate the timer
+       vosStatus = vos_timer_stop( &pMac->btc.restoreHBTimer);
+       if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
+           VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcCheckHeartBeatMonitoring: Fail to stop timer");
+           return VOS_STATUS_E_FAILURE;
+       }
+   }
+   return VOS_STATUS_SUCCESS;
+}
+/* ---------------------------------------------------------------------------
+    \fn btcRestoreHeartBeatMonitoringHandle
+    \brief  Timer handler to handlet the timeout condition when a specific BT
+            stop event does not come back, in which case to restore back the
+            heartbeat timer.
+    \param  hHal - The handle returned by macOpen.
+    \return VOID
+  ---------------------------------------------------------------------------*/
+void btcRestoreHeartBeatMonitoringHandle(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    if( !pMac->btc.btcHBActive )
+    {
+        tPmcState pmcState;
+        //Check PMC state to make sure whether we need to defer
+        pmcState = pmcGetPmcState( pMac );
+        if( PMC_IS_CHIP_ACCESSIBLE(pmcState) )
+        {
+            // Restore CFG back to the original value
+            ccmCfgSetInt(pMac, WNI_CFG_HEART_BEAT_THRESHOLD, pMac->btc.btcHBCount, NULL, eANI_BOOLEAN_FALSE);
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "BT event timeout, restoring back HeartBeat timer");
+        }
+        else
+        {
+            //defer it
+            pMac->btc.btcEventReplay.fRestoreHBMonitor = VOS_TRUE;
+        }
+    }
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn btcSetConfig
+    \brief  API to change the current Bluetooth Coexistence (BTC) configuration
+            This function should be invoked only after CFG download has completed.
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type
+                            tSmeBtcConfig. Caller owns the memory and is responsible
+                            for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  Config not passed to HAL.
+            VOS_STATUS_SUCCESS  Config passed to HAL
+  ---------------------------------------------------------------------------*/
+VOS_STATUS btcSetConfig (tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   //Save a copy in the global BTC config
+   vos_mem_copy(&(pMac->btc.btcConfig), pSmeBtcConfig, sizeof(tSmeBtcConfig));
+   //Send the config down only if SME_HddReady has been invoked. If not ready,
+   //BTC config will plumbed down when btcReady is eventually invoked.
+   if(pMac->btc.btcReady)
+   {
+      if(VOS_STATUS_SUCCESS != btcSendCfgMsg(hHal, pSmeBtcConfig))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, 
+            "Failure to send BTC config down");
+         return VOS_STATUS_E_FAILURE;
+      }
+   }
+   return VOS_STATUS_SUCCESS;
+}
+/* ---------------------------------------------------------------------------
+    \fn btcPostBtcCfgMsg
+    \brief  Private API to post BTC config message to HAL
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type
+                            tSmeBtcConfig. Caller owns the memory and is responsible
+                            for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  Config not passed to HAL.
+            VOS_STATUS_SUCCESS  Config passed to HAL
+  ---------------------------------------------------------------------------*/
+VOS_STATUS btcSendCfgMsg(tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig)
+{
+   tpSmeBtcConfig ptrSmeBtcConfig = NULL;
+   vos_msg_t msg;
+   if( NULL == pSmeBtcConfig )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcSendCfgMsg: "
+         "Null pointer for BTC Config");
+      return VOS_STATUS_E_FAILURE;
+   }
+   if( pSmeBtcConfig->btcExecutionMode >= BT_EXEC_MODE_MAX )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcSendCfgMsg: "
+         "Invalid BT execution mode %d being set",
+          pSmeBtcConfig->btcExecutionMode);
+      return VOS_STATUS_E_FAILURE;
+   }
+   ptrSmeBtcConfig = vos_mem_malloc(sizeof(tSmeBtcConfig));
+   if (NULL == ptrSmeBtcConfig)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcSendCfgMsg: "
+         "Not able to allocate memory for SME BTC Config");
+      return VOS_STATUS_E_FAILURE;
+   }
+   vos_mem_copy(ptrSmeBtcConfig, pSmeBtcConfig, sizeof(tSmeBtcConfig));
+   msg.type = WDA_BTC_SET_CFG;
+   msg.reserved = 0;
+   msg.bodyptr = ptrSmeBtcConfig;
+   if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcSendCfgMsg: "
+         "Not able to post WDA_BTC_SET_CFG message to WDA");
+      vos_mem_free( ptrSmeBtcConfig );
+      return VOS_STATUS_E_FAILURE;
+   }
+   return VOS_STATUS_SUCCESS;
+}
+/* ---------------------------------------------------------------------------
+    \fn btcGetConfig
+    \brief  API to retrieve the current Bluetooth Coexistence (BTC) configuration
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type
+                            tSmeBtcConfig. Caller owns the memory and is responsible
+                            for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS btcGetConfig (tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   if( NULL == pSmeBtcConfig )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "btcGetConfig: "
+         "Null pointer for BTC Config");
+      return VOS_STATUS_E_FAILURE;
+   }
+   vos_mem_copy(pSmeBtcConfig, &(pMac->btc.btcConfig), sizeof(tSmeBtcConfig));
+   return VOS_STATUS_SUCCESS;
+}
+/*
+    btcFindAclEventHist find a suited ACL event buffer
+    Param: bdAddr - NULL meaning not care.
+                    pointer to caller alocated buffer containing the BD address to find a match
+           handle - BT_INVALID_CONN_HANDLE == not care
+                    otherwise, a handle to match
+    NOPTE: Either bdAddr or handle can be valid, if both of them are valid, use bdAddr only. If neither 
+           bdAddr nor handle is valid, return the next free slot.
+*/
+static tpSmeBtAclEventHist btcFindAclEventHist( tpAniSirGlobal pMac, v_U8_t *bdAddr, v_U16_t handle )
+{
+    int i, j;
+    tpSmeBtAclEventHist pRet = NULL;
+    tSmeBtcEventReplay *pReplay = &pMac->btc.btcEventReplay;
+    for( i = 0; (i < BT_MAX_ACL_SUPPORT) && (NULL == pRet); i++ )
+    {
+        if( NULL != bdAddr )
+        {
+            //try to match addr
+            if( pReplay->btcEventHist.btAclConnectionEvent[i].bNextEventIdx )
+            {
+                for(j = 0; j < pReplay->btcEventHist.btAclConnectionEvent[i].bNextEventIdx; j++)
+                {
+                    if( vos_mem_compare(pReplay->btcEventHist.btAclConnectionEvent[i].btAclConnection[j].bdAddr,
+                        bdAddr, 6) )
+                    {
+                        //found it
+                        pRet = &pReplay->btcEventHist.btAclConnectionEvent[i];
+                        break;
+                    }
+                }
+            }
+        }
+        else if( BT_INVALID_CONN_HANDLE != handle )
+        {
+            //try to match handle
+            if( pReplay->btcEventHist.btAclConnectionEvent[i].bNextEventIdx )
+            {
+                for(j = 0; j < pReplay->btcEventHist.btAclConnectionEvent[i].bNextEventIdx; j++)
+                {
+                    if( pReplay->btcEventHist.btAclConnectionEvent[i].btAclConnection[j].connectionHandle ==
+                        handle )
+                    {
+                        //found it
+                        pRet = &pReplay->btcEventHist.btAclConnectionEvent[i];
+                        break;
+                    }
+                }
+            }
+        }
+        else if( 0 == pReplay->btcEventHist.btAclConnectionEvent[i].bNextEventIdx )
+        {
+            pRet = &pReplay->btcEventHist.btAclConnectionEvent[i];
+            break;
+        }
+    }
+    return (pRet);
+}
+
+/*
+    btcFindSyncEventHist find a suited SYNC event buffer
+    Param: bdAddr - NULL meaning not care.
+                    pointer to caller alocated buffer containing the BD address to find a match
+           handle - BT_INVALID_CONN_HANDLE == not care
+                    otherwise, a handle to match
+    NOPTE: Either bdAddr or handle can be valid, if both of them are valid, use bdAddr only. If neither 
+           bdAddr nor handle is valid, return the next free slot.
+*/
+static tpSmeBtSyncEventHist btcFindSyncEventHist( tpAniSirGlobal pMac, v_U8_t *bdAddr, v_U16_t handle )
+{
+    int i, j;
+    tpSmeBtSyncEventHist pRet = NULL;
+    tSmeBtcEventReplay *pReplay = &pMac->btc.btcEventReplay;
+    for( i = 0; (i < BT_MAX_SCO_SUPPORT) && (NULL == pRet); i++ )
+    {
+        if( NULL != bdAddr )
+        {
+            //try to match addr
+            if( pReplay->btcEventHist.btSyncConnectionEvent[i].bNextEventIdx )
+            {
+                for(j = 0; j < pReplay->btcEventHist.btAclConnectionEvent[i].bNextEventIdx; j++)
+                {
+                    if( vos_mem_compare(pReplay->btcEventHist.btSyncConnectionEvent[i].btSyncConnection[j].bdAddr,
+                        bdAddr, 6) )
+                    {
+                        //found it
+                        pRet = &pReplay->btcEventHist.btSyncConnectionEvent[i];
+                        break;
+                    }
+                }
+            }
+        }
+        else if( BT_INVALID_CONN_HANDLE != handle )
+        {
+            //try to match handle
+            if( pReplay->btcEventHist.btSyncConnectionEvent[i].bNextEventIdx )
+            {
+                for(j = 0; j < pReplay->btcEventHist.btAclConnectionEvent[i].bNextEventIdx; j++)
+                {
+                    if( pReplay->btcEventHist.btSyncConnectionEvent[i].btSyncConnection[j].connectionHandle ==
+                        handle )
+                    {
+                        //found it
+                        pRet = &pReplay->btcEventHist.btSyncConnectionEvent[i];
+                        break;
+                    }
+                }
+            }
+        }
+        else if( !pReplay->btcEventHist.btSyncConnectionEvent[i].bNextEventIdx )
+        {
+            pRet = &pReplay->btcEventHist.btSyncConnectionEvent[i];
+            break;
+        }
+    }
+    return (pRet);
+}
+
+/*
+    btcFindDisconnEventHist find a slot for the deferred disconnect event
+    If handle is invlid, it returns a free slot, if any. 
+    If handle is valid, it tries to find a match first in case same disconnect event comes down again.
+*/
+static tpSmeBtDisconnectEventHist btcFindDisconnEventHist( tpAniSirGlobal pMac, v_U16_t handle )
+{
+    tpSmeBtDisconnectEventHist pRet = NULL;
+    tSmeBtcEventReplay *pReplay = &pMac->btc.btcEventReplay;
+    int i;
+    if( BT_INVALID_CONN_HANDLE != handle )
+    {
+        for(i = 0; i < BT_MAX_DISCONN_SUPPORT; i++)
+        {
+            if( pReplay->btcEventHist.btDisconnectEvent[i].fValid &&
+                (handle == pReplay->btcEventHist.btDisconnectEvent[i].btDisconnect.connectionHandle) )
+            {
+                pRet = &pReplay->btcEventHist.btDisconnectEvent[i];
+                break;
+            }
+        }
+    }
+    if( NULL == pRet )
+    {
+        //Find a free slot
+        for(i = 0; i < BT_MAX_DISCONN_SUPPORT; i++)
+        {
+            if( !pReplay->btcEventHist.btDisconnectEvent[i].fValid )
+            {
+                pRet = &pReplay->btcEventHist.btDisconnectEvent[i];
+                break;
+            }
+        }
+    }
+    return (pRet);
+}
+
+/*
+    btcFindModeChangeEventHist find a slot for the deferred mopde change event
+    If handle is invalid, it returns a free slot, if any. 
+    If handle is valid, it tries to find a match first in case same disconnect event comes down again.
+*/
+tpSmeBtAclModeChangeEventHist btcFindModeChangeEventHist( tpAniSirGlobal pMac, v_U16_t handle )
+{
+    tpSmeBtAclModeChangeEventHist pRet = NULL;
+    tSmeBtcEventReplay *pReplay = &pMac->btc.btcEventReplay;
+    int i;
+    if( BT_INVALID_CONN_HANDLE != handle )
+    {
+        for(i = 0; i < BT_MAX_ACL_SUPPORT; i++)
+        {
+            if( pReplay->btcEventHist.btAclModeChangeEvent[i].fValid &&
+                (handle == pReplay->btcEventHist.btAclModeChangeEvent[i].btAclModeChange.connectionHandle) )
+            {
+                pRet = &pReplay->btcEventHist.btAclModeChangeEvent[i];
+                break;
+            }
+        }
+    }
+    if( NULL == pRet )
+    {
+        //Find a free slot
+        for(i = 0; i < BT_MAX_ACL_SUPPORT; i++)
+        {
+            if( !pReplay->btcEventHist.btAclModeChangeEvent[i].fValid )
+            {
+                pRet = &pReplay->btcEventHist.btAclModeChangeEvent[i];
+                break;
+            }
+        }
+    }
+    return (pRet);
+}
+
+/*
+    btcFindSyncUpdateEventHist find a slot for the deferred SYNC_UPDATE event
+    If handle is invalid, it returns a free slot, if any. 
+    If handle is valid, it tries to find a match first in case same disconnect event comes down again.
+*/
+tpSmeBtSyncUpdateHist btcFindSyncUpdateEventHist( tpAniSirGlobal pMac, v_U16_t handle )
+{
+    tpSmeBtSyncUpdateHist pRet = NULL;
+    tSmeBtcEventReplay *pReplay = &pMac->btc.btcEventReplay;
+    int i;
+    if( BT_INVALID_CONN_HANDLE != handle )
+    {
+        for(i = 0; i < BT_MAX_SCO_SUPPORT; i++)
+        {
+            if( pReplay->btcEventHist.btSyncUpdateEvent[i].fValid &&
+                (handle == pReplay->btcEventHist.btSyncUpdateEvent[i].btSyncConnection.connectionHandle) )
+            {
+                pRet = &pReplay->btcEventHist.btSyncUpdateEvent[i];
+                break;
+            }
+        }
+    }
+    if( NULL == pRet )
+    {
+        //Find a free slot
+        for(i = 0; i < BT_MAX_SCO_SUPPORT; i++)
+        {
+            if( !pReplay->btcEventHist.btSyncUpdateEvent[i].fValid )
+            {
+                pRet = &pReplay->btcEventHist.btSyncUpdateEvent[i];
+                break;
+            }
+        }
+    }
+    return (pRet);
+}
+
+/*
+    Call must validate pAclEventHist
+*/
+static void btcReleaseAclEventHist( tpAniSirGlobal pMac, tpSmeBtAclEventHist pAclEventHist )
+{
+    vos_mem_zero( pAclEventHist, sizeof(tSmeBtAclEventHist) );
+}
+
+/*
+    Call must validate pSyncEventHist
+*/
+static void btcReleaseSyncEventHist( tpAniSirGlobal pMac, tpSmeBtSyncEventHist pSyncEventHist )
+{
+    vos_mem_zero( pSyncEventHist, sizeof(tSmeBtSyncEventHist) );
+}
+
+/*To defer a ACL creation event
+    We only support one ACL per BD address.
+    If the last cached event another ACL create event, replace that event with the new event
+    If a completion event with success status code, and the new ACL creation 
+    on same address, defer a new disconnect event(fake one), then cache this ACL creation event.
+    Otherwise, save this create event.
+*/
+static VOS_STATUS btcDeferAclCreate( tpAniSirGlobal pMac, tpSmeBtEvent pEvent )
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpSmeBtAclEventHist pAclEventHist;
+    tSmeBtAclConnectionParam *pAclEvent;
+    do
+    {
+        //Find a match
+        pAclEventHist = btcFindAclEventHist( pMac, pEvent->uEventParam.btAclConnection.bdAddr, 
+                                    BT_INVALID_CONN_HANDLE );
+        if( NULL == pAclEventHist )
+        {
+            //No cached ACL event on this address
+            //Find a free slot and save it
+            pAclEventHist = btcFindAclEventHist( pMac, NULL, BT_INVALID_CONN_HANDLE );
+            if( NULL != pAclEventHist )
+            {
+                vos_mem_copy(&pAclEventHist->btAclConnection[0], &pEvent->uEventParam.btAclConnection, 
+                                sizeof(tSmeBtAclConnectionParam));
+                pAclEventHist->btEventType[0] = BT_EVENT_CREATE_ACL_CONNECTION;
+                pAclEventHist->bNextEventIdx = 1;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" failed to find ACL event slot\n"));
+                status = VOS_STATUS_E_RESOURCES;
+            }
+            //done
+            break;
+        }
+        else
+        {
+            //There is history on this BD address
+            VOS_ASSERT(pAclEventHist->bNextEventIdx > 0);
+            pAclEvent = &pAclEventHist->btAclConnection[pAclEventHist->bNextEventIdx - 1];
+            if(BT_EVENT_CREATE_ACL_CONNECTION == pAclEventHist->btEventType[pAclEventHist->bNextEventIdx - 1])
+            {
+                //The last cached event is creation, replace it with the new one
+                vos_mem_copy(pAclEvent, 
+                                &pEvent->uEventParam.btAclConnection, 
+                                sizeof(tSmeBtAclConnectionParam));
+                //done
+                break;
+            }
+            else if(BT_EVENT_ACL_CONNECTION_COMPLETE == 
+                        pAclEventHist->btEventType[pAclEventHist->bNextEventIdx - 1])
+            {
+                //The last cached event is completion, check the status.
+                if(BT_CONN_STATUS_SUCCESS == pAclEvent->status)
+                {
+                    tSmeBtEvent btEvent;
+                    //The last event we have is success completion event. 
+                    //Should not get a creation event before creation.
+                    smsLog(pMac, LOGE, FL("  Missing disconnect event on handle %d\n"), pAclEvent->connectionHandle);
+                    //Fake a disconnect event
+                    btEvent.btEventType = BT_EVENT_DISCONNECTION_COMPLETE;
+                    btEvent.uEventParam.btDisconnect.connectionHandle = pAclEvent->connectionHandle;
+                    btcDeferDisconnEvent(pMac, &btEvent);
+                }
+            }
+            //Need to save the new event
+            if(pAclEventHist->bNextEventIdx < BT_MAX_NUM_EVENT_ACL_DEFERRED)
+            {
+                pAclEventHist->btEventType[pAclEventHist->bNextEventIdx] = BT_EVENT_CREATE_ACL_CONNECTION;
+                vos_mem_copy(&pAclEventHist->btAclConnection[pAclEventHist->bNextEventIdx], 
+                                &pEvent->uEventParam.btAclConnection, 
+                                sizeof(tSmeBtAclConnectionParam));
+                pAclEventHist->bNextEventIdx++;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" ACL event overflow\n"));
+                VOS_ASSERT(0);
+            }
+        }
+    }while(0);
+    return status;
+}
+
+/*Defer a ACL completion event
+  If there is cached event on this BD address, check completion status.
+  If status is fail and last cached event is creation, remove the creation event and drop
+  this completion event. Otherwise, cache this completion event as the latest one.
+*/
+static VOS_STATUS btcDeferAclComplete( tpAniSirGlobal pMac, tpSmeBtEvent pEvent )
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpSmeBtAclEventHist pAclEventHist;
+    do
+    {
+        //Find a match
+        pAclEventHist = btcFindAclEventHist( pMac, pEvent->uEventParam.btAclConnection.bdAddr, 
+                                    BT_INVALID_CONN_HANDLE );
+        if(pAclEventHist)
+        {
+            VOS_ASSERT(pAclEventHist->bNextEventIdx >0);
+            //Found one
+            if(BT_CONN_STATUS_SUCCESS != pEvent->uEventParam.btAclConnection.status)
+            {
+                //If completion fails, and the last one is creation, remove the creation event
+                if(BT_EVENT_CREATE_ACL_CONNECTION == pAclEventHist->btEventType[pAclEventHist->bNextEventIdx-1])
+                {
+                    vos_mem_zero(&pAclEventHist->btAclConnection[pAclEventHist->bNextEventIdx-1], 
+                                    sizeof(tSmeBtAclConnectionParam));
+                    pAclEventHist->bNextEventIdx--;
+                    //Done with this event
+                    break;
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, FL(" ACL completion fail but last event(%d) not creation\n"),
+                        pAclEventHist->btEventType[pAclEventHist->bNextEventIdx-1]);
+                }
+            }
+        }
+        if( NULL == pAclEventHist )
+        {
+            pAclEventHist = btcFindAclEventHist( pMac, NULL, BT_INVALID_CONN_HANDLE );
+        }
+        if(pAclEventHist)
+        {
+            if(pAclEventHist->bNextEventIdx < BT_MAX_NUM_EVENT_ACL_DEFERRED)
+            {
+                //Save this event
+                pAclEventHist->btEventType[pAclEventHist->bNextEventIdx] = BT_EVENT_ACL_CONNECTION_COMPLETE;
+                vos_mem_copy(&pAclEventHist->btAclConnection[pAclEventHist->bNextEventIdx], 
+                                &pEvent->uEventParam.btAclConnection, 
+                                sizeof(tSmeBtAclConnectionParam));
+                pAclEventHist->bNextEventIdx++;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" ACL event overflow\n"));
+                VOS_ASSERT(0);
+            }
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL(" cannot find match for failed BT_EVENT_ACL_CONNECTION_COMPLETE of bdAddr (%02X-%02X-%02X-%02X-%02X-%02X)\n"),
+                pEvent->uEventParam.btAclConnection.bdAddr[0],
+                pEvent->uEventParam.btAclConnection.bdAddr[1],
+                pEvent->uEventParam.btAclConnection.bdAddr[2],
+                pEvent->uEventParam.btAclConnection.bdAddr[3],
+                pEvent->uEventParam.btAclConnection.bdAddr[4],
+                pEvent->uEventParam.btAclConnection.bdAddr[5]);
+            status = VOS_STATUS_E_EMPTY;
+        }
+    }while(0);
+    return (status);
+}
+
+/*To defer a SYNC creation event
+    If the last cached event is another SYNC create event, replace 
+    that event with the new event.
+    If there is a completion event with success status code, cache a new 
+    disconnect event(fake) first, then cache this SYNC creation event.
+    Otherwise, cache this create event.
+*/
+static VOS_STATUS btcDeferSyncCreate( tpAniSirGlobal pMac, tpSmeBtEvent pEvent )
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpSmeBtSyncEventHist pSyncEventHist;
+    tSmeBtSyncConnectionParam *pSyncEvent;
+    do
+    {
+        //Find a match
+        pSyncEventHist = btcFindSyncEventHist( pMac, pEvent->uEventParam.btSyncConnection.bdAddr, 
+                                    BT_INVALID_CONN_HANDLE );
+        if( NULL == pSyncEventHist )
+        {
+            //No cached ACL event on this address
+            //Find a free slot and save it
+            pSyncEventHist = btcFindSyncEventHist( pMac, NULL, BT_INVALID_CONN_HANDLE );
+            if( NULL != pSyncEventHist )
+            {
+                vos_mem_copy(&pSyncEventHist->btSyncConnection[0], &pEvent->uEventParam.btSyncConnection, 
+                                sizeof(tSmeBtSyncConnectionParam));
+                pSyncEventHist->btEventType[0] = BT_EVENT_CREATE_SYNC_CONNECTION;
+                pSyncEventHist->bNextEventIdx = 1;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" failed to find SYNC event slot\n"));
+                status = VOS_STATUS_E_RESOURCES;
+            }
+            //done
+            break;
+        }
+        else
+        {
+            //There is history on this BD address
+            VOS_ASSERT(pSyncEventHist->bNextEventIdx > 0);
+            pSyncEvent = &pSyncEventHist->btSyncConnection[pSyncEventHist->bNextEventIdx - 1];
+            if(BT_EVENT_CREATE_SYNC_CONNECTION == 
+                pSyncEventHist->btEventType[pSyncEventHist->bNextEventIdx - 1])
+            {
+                //The last cached event is creation, replace it with the new one
+                vos_mem_copy(pSyncEvent, 
+                                &pEvent->uEventParam.btSyncConnection, 
+                                sizeof(tSmeBtSyncConnectionParam));
+                //done
+                break;
+            }
+            else if(BT_EVENT_SYNC_CONNECTION_COMPLETE == 
+                        pSyncEventHist->btEventType[pSyncEventHist->bNextEventIdx - 1])
+            {
+                //The last cached event is completion, check the status.
+                if(BT_CONN_STATUS_SUCCESS == pSyncEvent->status)
+                {
+                    tSmeBtEvent btEvent;
+                    //The last event we have is success completion event. 
+                    //Should not get a creation event before creation.
+                    smsLog(pMac, LOGE, FL("  Missing disconnect event on handle %d\n"), pSyncEvent->connectionHandle);
+                    //Fake a disconnect event
+                    btEvent.btEventType = BT_EVENT_DISCONNECTION_COMPLETE;
+                    btEvent.uEventParam.btDisconnect.connectionHandle = pSyncEvent->connectionHandle;
+                    btcDeferDisconnEvent(pMac, &btEvent);
+                }
+            }
+            //Need to save the new event
+            if(pSyncEventHist->bNextEventIdx < BT_MAX_NUM_EVENT_SCO_DEFERRED)
+            {
+                pSyncEventHist->btEventType[pSyncEventHist->bNextEventIdx] = BT_EVENT_CREATE_SYNC_CONNECTION;
+                vos_mem_copy(&pSyncEventHist->btSyncConnection[pSyncEventHist->bNextEventIdx], 
+                                &pEvent->uEventParam.btSyncConnection, 
+                                sizeof(tSmeBtSyncConnectionParam));
+                pSyncEventHist->bNextEventIdx++;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" SYNC event overflow\n"));
+            }
+        }
+    }while(0);
+    return status;
+}
+
+/*Defer a SYNC completion event
+  If there is cached event on this BD address, check completion status.
+  If status is fail and last cached event is creation, remove te creation event and drop
+  this completion event. 
+  Otherwise, cache this completion event as the latest one.
+*/
+static VOS_STATUS btcDeferSyncComplete( tpAniSirGlobal pMac, tpSmeBtEvent pEvent )
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpSmeBtSyncEventHist pSyncEventHist;
+    do
+    {
+        //Find a match
+        pSyncEventHist = btcFindSyncEventHist( pMac, pEvent->uEventParam.btSyncConnection.bdAddr, 
+                                    BT_INVALID_CONN_HANDLE );
+        if(pSyncEventHist)
+        {
+            VOS_ASSERT(pSyncEventHist->bNextEventIdx >0);
+            //Found one
+            if(BT_CONN_STATUS_SUCCESS != pEvent->uEventParam.btSyncConnection.status)
+            {
+                //If completion fails, and the last one is creation, remove the creation event
+                if(BT_EVENT_CREATE_SYNC_CONNECTION == pSyncEventHist->btEventType[pSyncEventHist->bNextEventIdx-1])
+                {
+                    vos_mem_zero(&pSyncEventHist->btSyncConnection[pSyncEventHist->bNextEventIdx-1], 
+                                    sizeof(tSmeBtSyncConnectionParam));
+                    pSyncEventHist->bNextEventIdx--;
+                    //Done with this event
+                    break;
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, FL(" SYNC completion fail but last event(%d) not creation\n"),
+                        pSyncEventHist->btEventType[pSyncEventHist->bNextEventIdx-1]);
+                }
+            }
+        }
+        if(NULL == pSyncEventHist)
+        {
+            //In case we don't defer the creation event
+            pSyncEventHist = btcFindSyncEventHist( pMac, NULL, BT_INVALID_CONN_HANDLE );
+        }
+        if(pSyncEventHist)
+        {
+            if(pSyncEventHist->bNextEventIdx < BT_MAX_NUM_EVENT_ACL_DEFERRED)
+            {
+                //Save this event
+                pSyncEventHist->btEventType[pSyncEventHist->bNextEventIdx] = BT_EVENT_SYNC_CONNECTION_COMPLETE;
+                vos_mem_copy(&pSyncEventHist->btSyncConnection[pSyncEventHist->bNextEventIdx], 
+                                &pEvent->uEventParam.btSyncConnection, 
+                                sizeof(tSmeBtSyncConnectionParam));
+                pSyncEventHist->bNextEventIdx++;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" SYNC event overflow\n"));
+            }
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL(" cannot find match for BT_EVENT_SYNC_CONNECTION_COMPLETE of bdAddr (%02X-%02X-%02X-%02X-%02X-%02X)\n"),
+                pEvent->uEventParam.btSyncConnection.bdAddr[0],
+                pEvent->uEventParam.btSyncConnection.bdAddr[1],
+                pEvent->uEventParam.btSyncConnection.bdAddr[2],
+                pEvent->uEventParam.btSyncConnection.bdAddr[3],
+                pEvent->uEventParam.btSyncConnection.bdAddr[4],
+                pEvent->uEventParam.btSyncConnection.bdAddr[5]);
+            status = VOS_STATUS_E_EMPTY;
+        }
+    }while(0);
+    return (status);
+}
+
+//return VOS_STATUS_E_EXISTS if the event handle cannot be found
+//VOS_STATUS_SUCCESS if the event is processed
+//Other error status meaning it cannot continue due to other errors
+/*
+  Defer a disconnect event for ACL
+  Check if any history on this event handle.
+  If both ACL_CREATION and ACL_COMPLETION is cached, remove both those events and drop
+  this disconnect event.
+  Otherwise save disconnect event in this ACL's bin.
+  If not ACL match on this handle, not to do anything.
+  Either way, remove any cached MODE_CHANGE event matches this disconnect event's handle.
+*/
+static VOS_STATUS btcDeferDisconnectEventForACL( tpAniSirGlobal pMac, tpSmeBtEvent pEvent )
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpSmeBtAclEventHist pAclEventHist;
+    tpSmeBtAclModeChangeEventHist pModeChangeEventHist;
+    v_BOOL_t fDone = VOS_FALSE;
+    int i;
+    pAclEventHist = btcFindAclEventHist( pMac, NULL, 
+                                pEvent->uEventParam.btDisconnect.connectionHandle );
+    if(pAclEventHist)
+    {
+        if( pAclEventHist->bNextEventIdx > BT_MAX_NUM_EVENT_ACL_DEFERRED)
+        {
+            smsLog(pMac, LOGE, FL(" ACL event history index:%d overflow, resetting to BT_MAX_NUM_EVENT_ACL_DEFERRED\n"), pAclEventHist->bNextEventIdx);
+            pAclEventHist->bNextEventIdx = BT_MAX_NUM_EVENT_ACL_DEFERRED;
+        }
+        //Looking backwords
+        for(i = pAclEventHist->bNextEventIdx - 1; i >= 0; i--)
+        {
+            if( BT_EVENT_ACL_CONNECTION_COMPLETE == pAclEventHist->btEventType[i] )
+            {
+                //make sure we can cancel the link
+                if( (i > 0) && (BT_EVENT_CREATE_ACL_CONNECTION == pAclEventHist->btEventType[i - 1]) )
+                {
+                    fDone = VOS_TRUE;
+                    if(i == 1)
+                    {
+                        //All events can be wiped off
+                        btcReleaseAclEventHist(pMac, pAclEventHist);
+                        break;
+                    }
+                    //we have both ACL creation and completion, wipe out all of them
+                    pAclEventHist->bNextEventIdx = (tANI_U8)(i - 1);
+                    vos_mem_zero(&pAclEventHist->btAclConnection[i-1], sizeof(tSmeBtAclConnectionParam));
+                    vos_mem_zero(&pAclEventHist->btAclConnection[i], sizeof(tSmeBtAclConnectionParam));
+                    break;
+                }
+            }
+        }//for loop
+        if(!fDone)
+        {
+            //Save this disconnect event
+            if(pAclEventHist->bNextEventIdx < BT_MAX_NUM_EVENT_ACL_DEFERRED)
+            {
+                pAclEventHist->btEventType[pAclEventHist->bNextEventIdx] = 
+                    BT_EVENT_DISCONNECTION_COMPLETE;
+                pAclEventHist->btAclConnection[pAclEventHist->bNextEventIdx].connectionHandle =
+                    pEvent->uEventParam.btDisconnect.connectionHandle;
+                pAclEventHist->bNextEventIdx++;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" ACL event overflow\n"));
+                status = VOS_STATUS_E_FAILURE;
+            }
+        }
+    }
+    else
+    {
+        status = VOS_STATUS_E_EXISTS;
+    }
+    //Wipe out the related mode change event if it is there
+    pModeChangeEventHist = btcFindModeChangeEventHist( pMac,  
+                            pEvent->uEventParam.btDisconnect.connectionHandle );
+    if( pModeChangeEventHist && pModeChangeEventHist->fValid )
+    {
+        pModeChangeEventHist->fValid = VOS_FALSE;
+    }
+    return status;
+}
+
+//This function works the same as btcDeferDisconnectEventForACL except it hanldes SYNC events
+//return VOS_STATUS_E_EXISTS if the event handle cannot be found
+//VOS_STATUS_SUCCESS if the event is processed
+//Other error status meaning it cannot continue due to other errors
+/*
+  Defer a disconnect event for SYNC
+  Check if any SYNC history on this event handle.
+  If yes and if both SYNC_CREATION and SYNC_COMPLETION is cached, remove both those events and drop
+  this disconnect event.
+  Otherwise save disconnect event in this SYNC's bin.
+  If no match found, not to save this event here.
+  Either way, remove any cached SYNC_UPDATE event matches this disconnect event's handle.
+*/
+static VOS_STATUS btcDeferDisconnectEventForSync( tpAniSirGlobal pMac, tpSmeBtEvent pEvent )
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpSmeBtSyncEventHist pSyncEventHist;
+    tpSmeBtSyncUpdateHist pSyncUpdateHist;
+    v_BOOL_t fDone = VOS_FALSE;
+    int i;
+    pSyncEventHist = btcFindSyncEventHist( pMac, NULL, 
+                                pEvent->uEventParam.btDisconnect.connectionHandle );
+    if(pSyncEventHist)
+    {
+        if( pSyncEventHist->bNextEventIdx > BT_MAX_NUM_EVENT_SCO_DEFERRED)
+        {
+            smsLog(pMac, LOGE, FL(" SYNC event history index:%d overflow, resetting to BT_MAX_NUM_EVENT_SCO_DEFERRED\n"), pSyncEventHist->bNextEventIdx);
+            pSyncEventHist->bNextEventIdx = BT_MAX_NUM_EVENT_SCO_DEFERRED;
+        }
+        //Looking backwords
+        for(i = pSyncEventHist->bNextEventIdx - 1; i >= 0; i--)
+        {
+            //if a mode change event exists, drop it
+            if( BT_EVENT_SYNC_CONNECTION_COMPLETE == pSyncEventHist->btEventType[i] )
+            {
+                //make sure we can cancel the link
+                if( (i > 0) && (BT_EVENT_CREATE_SYNC_CONNECTION == pSyncEventHist->btEventType[i - 1]) )
+                {
+                    fDone = VOS_TRUE;
+                    if(i == 1)
+                    {
+                        //All events can be wiped off
+                        btcReleaseSyncEventHist(pMac, pSyncEventHist);
+                        break;
+                    }
+                    //we have both ACL creation and completion, wipe out all of them
+                    pSyncEventHist->bNextEventIdx = (tANI_U8)(i - 1);
+                    vos_mem_zero(&pSyncEventHist->btSyncConnection[i-1], sizeof(tSmeBtSyncConnectionParam));
+                    vos_mem_zero(&pSyncEventHist->btSyncConnection[i], sizeof(tSmeBtSyncConnectionParam));
+                    break;
+                }
+            }
+        }//for loop
+        if(!fDone)
+        {
+            //Save this disconnect event
+            if(pSyncEventHist->bNextEventIdx < BT_MAX_NUM_EVENT_SCO_DEFERRED)
+            {
+                pSyncEventHist->btEventType[pSyncEventHist->bNextEventIdx] = 
+                    BT_EVENT_DISCONNECTION_COMPLETE;
+                pSyncEventHist->btSyncConnection[pSyncEventHist->bNextEventIdx].connectionHandle =
+                    pEvent->uEventParam.btDisconnect.connectionHandle;
+                pSyncEventHist->bNextEventIdx++;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" SYNC event overflow\n"));
+                status = VOS_STATUS_E_FAILURE;
+            }
+        }
+    }
+    else
+    {
+        status = VOS_STATUS_E_EXISTS;
+    }
+    //Wipe out the related mode change event if it is there
+    pSyncUpdateHist = btcFindSyncUpdateEventHist( pMac,  
+                            pEvent->uEventParam.btDisconnect.connectionHandle );
+    if( pSyncUpdateHist && pSyncUpdateHist->fValid )
+    {
+        pSyncUpdateHist->fValid = VOS_FALSE;
+    }
+    return status;
+}
+
+/*
+  Defer a disconnect event.
+  Try to defer it as part of the ACL event first. 
+  If no match is found, try SYNC. 
+  If still no match found, defer it at DISCONNECT event bin.
+*/
+static VOS_STATUS btcDeferDisconnEvent( tpAniSirGlobal pMac, tpSmeBtEvent pEvent )
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpSmeBtDisconnectEventHist pDisconnEventHist;
+    if( BT_INVALID_CONN_HANDLE == pEvent->uEventParam.btDisconnect.connectionHandle )
+    {
+        smsLog( pMac, LOGE, FL(" invalid handle\n") );
+        return (VOS_STATUS_E_INVAL);
+    }
+    //Check ACL first
+    status = btcDeferDisconnectEventForACL(pMac, pEvent);
+    if(!VOS_IS_STATUS_SUCCESS(status))
+    {
+        status = btcDeferDisconnectEventForSync(pMac, pEvent);
+    }
+    if( !VOS_IS_STATUS_SUCCESS(status) )
+    {
+        //Save the disconnect event
+        pDisconnEventHist = btcFindDisconnEventHist( pMac, 
+            pEvent->uEventParam.btDisconnect.connectionHandle );
+        if( pDisconnEventHist )
+        {
+            pDisconnEventHist->fValid = VOS_TRUE;
+            vos_mem_copy( &pDisconnEventHist->btDisconnect, &pEvent->uEventParam.btDisconnect,
+                sizeof(tSmeBtDisconnectParam) );
+            status = VOS_STATUS_SUCCESS;
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL(" cannot find match for BT_EVENT_DISCONNECTION_COMPLETE of handle (%d)\n"),
+                pEvent->uEventParam.btDisconnect.connectionHandle);
+            status = VOS_STATUS_E_EMPTY;
+        }
+    }
+    return (status);
+}
+
+/*
+    btcDeferEvent save the event for possible replay when chip can be accessed
+    This function is called only when in IMPS/Standby state
+*/
+static VOS_STATUS btcDeferEvent( tpAniSirGlobal pMac, tpSmeBtEvent pEvent )
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpSmeBtSyncUpdateHist pSyncUpdateHist;
+    tpSmeBtAclModeChangeEventHist pModeChangeEventHist;
+    tSmeBtcEventReplay *pReplay = &pMac->btc.btcEventReplay;
+    switch(pEvent->btEventType)
+    {
+    case BT_EVENT_DEVICE_SWITCHED_ON:
+        //Clear all events first
+        vos_mem_zero( &pReplay->btcEventHist, sizeof(tSmeBtcEventHist) );
+        pReplay->fBTSwitchOn = VOS_TRUE;
+        pReplay->fBTSwitchOff = VOS_FALSE;
+        break;
+    case BT_EVENT_DEVICE_SWITCHED_OFF:
+        //Clear all events first
+        vos_mem_zero( &pReplay->btcEventHist, sizeof(tSmeBtcEventHist) );
+        pReplay->fBTSwitchOff = VOS_TRUE;
+        pReplay->fBTSwitchOn = VOS_FALSE;
+        break;
+    case BT_EVENT_INQUIRY_STARTED:
+        pReplay->btcEventHist.nInquiryEvent++;
+        break;
+    case BT_EVENT_INQUIRY_STOPPED:
+        pReplay->btcEventHist.nInquiryEvent--;
+        break;
+    case BT_EVENT_PAGE_STARTED:
+        pReplay->btcEventHist.nPageEvent++;
+        break;
+    case BT_EVENT_PAGE_STOPPED:
+        pReplay->btcEventHist.nPageEvent--;
+        break;
+    case BT_EVENT_CREATE_ACL_CONNECTION:
+        status = btcDeferAclCreate(pMac, pEvent);
+        break;
+    case BT_EVENT_ACL_CONNECTION_COMPLETE:
+        status = btcDeferAclComplete( pMac, pEvent );
+        break;
+    case BT_EVENT_CREATE_SYNC_CONNECTION:
+        status = btcDeferSyncCreate(pMac, pEvent);
+        break;
+    case BT_EVENT_SYNC_CONNECTION_COMPLETE:
+        status = btcDeferSyncComplete( pMac, pEvent );
+        break;
+    case BT_EVENT_SYNC_CONNECTION_UPDATED:
+        if( BT_INVALID_CONN_HANDLE == pEvent->uEventParam.btDisconnect.connectionHandle )
+        {
+            smsLog( pMac, LOGE, FL(" invalid handle\n") );
+            status = VOS_STATUS_E_INVAL;
+            break;
+        }
+        //Find a match on handle. If not found, get a free slot.
+        pSyncUpdateHist = btcFindSyncUpdateEventHist( pMac,  
+                                    pEvent->uEventParam.btSyncConnection.connectionHandle );
+        if(pSyncUpdateHist)
+        {
+            pSyncUpdateHist->fValid = VOS_TRUE;
+            vos_mem_copy(&pSyncUpdateHist->btSyncConnection, &pEvent->uEventParam.btSyncConnection, 
+                            sizeof(tSmeBtSyncConnectionParam));
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL(" cannot find match for BT_EVENT_SYNC_CONNECTION_UPDATED of handle (%d)\n"),
+                pEvent->uEventParam.btSyncConnection.connectionHandle );
+            status = VOS_STATUS_E_EMPTY;
+        }
+        break;
+    case BT_EVENT_DISCONNECTION_COMPLETE:
+        status = btcDeferDisconnEvent( pMac, pEvent );
+        break;
+    case BT_EVENT_MODE_CHANGED:
+        if( BT_INVALID_CONN_HANDLE == pEvent->uEventParam.btDisconnect.connectionHandle )
+        {
+            smsLog( pMac, LOGE, FL(" invalid handle\n") );
+            status = VOS_STATUS_E_INVAL;
+            break;
+        }
+        //Find a match on handle, If not found, return a free slot
+        pModeChangeEventHist = btcFindModeChangeEventHist( pMac,  
+                                    pEvent->uEventParam.btAclModeChange.connectionHandle );
+        if(pModeChangeEventHist)
+        {
+            pModeChangeEventHist->fValid = VOS_TRUE;
+            vos_mem_copy( &pModeChangeEventHist->btAclModeChange,
+                            &pEvent->uEventParam.btAclModeChange, sizeof(tSmeBtAclModeChangeParam) );
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL(" cannot find match for BT_EVENT_MODE_CHANGED of handle (%d)\n"),
+                pEvent->uEventParam.btAclModeChange.connectionHandle);
+            status = VOS_STATUS_E_EMPTY;
+        }
+        break;
+    case BT_EVENT_A2DP_STREAM_START:
+        pReplay->btcEventHist.fA2DPStarted = VOS_TRUE;
+        pReplay->btcEventHist.fA2DPStopped = VOS_FALSE;
+        break;
+    case BT_EVENT_A2DP_STREAM_STOP:
+        pReplay->btcEventHist.fA2DPStopped = VOS_TRUE;
+        pReplay->btcEventHist.fA2DPStarted = VOS_FALSE;
+        break;
+    default:
+        smsLog( pMac, LOGE, FL(" event (%d) is not deferred\n"), pEvent->btEventType );
+        status = VOS_STATUS_E_NOSUPPORT;
+        break;
+    }
+    return (status);
+}
+
+/*
+    Replay all cached events in the following order
+    1. If BT_SWITCH_OFF event, send it.
+    2. Send INQUIRY event (START or STOP),if available
+    3. Send PAGE event (START or STOP), if available
+    4. Send DISCONNECT events, these DISCONNECT events are not tied to 
+        any ACL/SYNC event that we have cached
+    5. Send ACL events (possible events, CREATION, COMPLETION, DISCONNECT)
+    6. Send MODE_CHANGE events, if available
+    7. Send A2DP event(START or STOP), if available
+    8. Send SYNC events (possible events, CREATION, COMPLETION, DISCONNECT)
+    9. Send SYNC_UPDATE events, if available
+*/
+static void btcReplayEvents( tpAniSirGlobal pMac )
+{
+    int i, j;
+    tSmeBtEvent btEvent;
+    tpSmeBtAclEventHist pAclHist;
+    tpSmeBtSyncEventHist pSyncHist;
+    tSmeBtcEventReplay *pReplay = &pMac->btc.btcEventReplay;
+    //Always turn on HB monitor first. 
+    //It is independent of BT events even though BT event causes this
+    if( pReplay->fRestoreHBMonitor )
+    {
+        pReplay->fRestoreHBMonitor = VOS_FALSE;
+        //Only do it when needed
+        if( !pMac->btc.btcHBActive ) 
+        {
+            ccmCfgSetInt(pMac, WNI_CFG_HEART_BEAT_THRESHOLD, pMac->btc.btcHBCount, NULL, eANI_BOOLEAN_FALSE);
+            pMac->btc.btcHBActive = VOS_TRUE;
+        }
+    }
+    if( pMac->btc.fReplayBTEvents )
+    {
+        /*Set the flag to false here so btcSignalBTEvent won't defer any further.
+          This works because SME has it global lock*/
+        pMac->btc.fReplayBTEvents = VOS_FALSE;
+        if( pReplay->fBTSwitchOff )
+        {
+            vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+            btEvent.btEventType = BT_EVENT_DEVICE_SWITCHED_OFF;
+            btcSendBTEvent( pMac, &btEvent );
+            pReplay->fBTSwitchOff = VOS_FALSE;
+        }
+        else if( pReplay->fBTSwitchOn )
+        {
+            vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+            btEvent.btEventType = BT_EVENT_DEVICE_SWITCHED_ON;
+            btcSendBTEvent( pMac, &btEvent );
+            pReplay->fBTSwitchOn = VOS_FALSE;
+        }
+        //Do inquire first
+        if( pReplay->btcEventHist.nInquiryEvent > 0 )
+        {
+            vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+            btEvent.btEventType = BT_EVENT_INQUIRY_STARTED;
+            i = pReplay->btcEventHist.nInquiryEvent;
+            while(i--)
+            {
+                btcSendBTEvent( pMac, &btEvent );
+            }
+        }
+        else if( pReplay->btcEventHist.nInquiryEvent < 0 )
+        {
+            vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+            btEvent.btEventType = BT_EVENT_INQUIRY_STOPPED;
+            i = pReplay->btcEventHist.nInquiryEvent;
+            while(i++)
+            {
+                btcSendBTEvent( pMac, &btEvent );
+            }
+        }
+        //Page
+        if( pReplay->btcEventHist.nPageEvent > 0 )
+        {
+            vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+            btEvent.btEventType = BT_EVENT_PAGE_STARTED;
+            i = pReplay->btcEventHist.nPageEvent;
+            while(i--)
+            {
+                btcSendBTEvent( pMac, &btEvent );
+            }
+        }
+        else if( pReplay->btcEventHist.nPageEvent < 0 )
+        {
+            vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+            btEvent.btEventType = BT_EVENT_PAGE_STOPPED;
+            i = pReplay->btcEventHist.nPageEvent;
+            while(i++)
+            {
+                btcSendBTEvent( pMac, &btEvent );
+            }
+        }
+        //Replay non-completion disconnect events first
+        //Disconnect
+        for( i = 0; i < BT_MAX_DISCONN_SUPPORT; i++ )
+        {
+            if( pReplay->btcEventHist.btDisconnectEvent[i].fValid )
+            {
+                vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+                btEvent.btEventType = BT_EVENT_DISCONNECTION_COMPLETE;
+                vos_mem_copy( &btEvent.uEventParam.btDisconnect, 
+                    &pReplay->btcEventHist.btDisconnectEvent[i].btDisconnect, sizeof(tSmeBtDisconnectParam) );
+                btcSendBTEvent( pMac, &btEvent );
+            }
+        }
+        //ACL
+        for( i = 0; i < BT_MAX_ACL_SUPPORT; i++ )
+        {
+            if( pReplay->btcEventHist.btAclConnectionEvent[i].bNextEventIdx )
+            {
+                pAclHist = &pReplay->btcEventHist.btAclConnectionEvent[i];
+                //Replay all ACL events for this BD address/handle
+                for(j = 0; j < pAclHist->bNextEventIdx; j++)
+                {
+                    vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+                    vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+                    btEvent.btEventType = pAclHist->btEventType[j];
+                    if(BT_EVENT_DISCONNECTION_COMPLETE != btEvent.btEventType)
+                    {
+                        //It must be CREATE or CONNECTION_COMPLETE
+                       vos_mem_copy( &btEvent.uEventParam.btAclConnection, 
+                                     &pAclHist->btAclConnection[j], sizeof(tSmeBtAclConnectionParam) );
+                    }
+                    else
+                    {
+                       btEvent.uEventParam.btDisconnect.connectionHandle = pAclHist->btAclConnection[j].connectionHandle;
+                    }
+                    btcSendBTEvent( pMac, &btEvent );
+                }
+            }
+        }
+        //Mode change
+        for( i = 0; i < BT_MAX_ACL_SUPPORT; i++ )
+        {
+            if( pReplay->btcEventHist.btAclModeChangeEvent[i].fValid )
+            {
+                vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+                btEvent.btEventType = BT_EVENT_MODE_CHANGED;
+                vos_mem_copy( &btEvent.uEventParam.btAclModeChange, 
+                    &pReplay->btcEventHist.btAclModeChangeEvent[i].btAclModeChange, sizeof(tSmeBtAclModeChangeParam) );
+                btcSendBTEvent( pMac, &btEvent );
+            }
+        }
+       //A2DP
+        if( pReplay->btcEventHist.fA2DPStarted )
+        {
+            vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+            btEvent.btEventType = BT_EVENT_A2DP_STREAM_START;
+            btcSendBTEvent( pMac, &btEvent );
+        }
+        else if( pReplay->btcEventHist.fA2DPStopped )
+        {
+            vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+            btEvent.btEventType = BT_EVENT_A2DP_STREAM_STOP;
+            btcSendBTEvent( pMac, &btEvent );
+        }
+        //SCO
+        for( i = 0; i < BT_MAX_SCO_SUPPORT; i++ )
+        {
+            if( pReplay->btcEventHist.btSyncConnectionEvent[i].bNextEventIdx )
+            {
+                pSyncHist = &pReplay->btcEventHist.btSyncConnectionEvent[i];
+                //Replay all SYNC events for this BD address/handle
+                for(j = 0; j < pSyncHist->bNextEventIdx; j++)
+                {
+                    vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+                    vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+                    btEvent.btEventType = pSyncHist->btEventType[j];
+                    if(BT_EVENT_DISCONNECTION_COMPLETE != btEvent.btEventType)
+                    {
+                        //Must be CREATION or CONNECTION_COMPLETE
+                       vos_mem_copy( &btEvent.uEventParam.btSyncConnection, 
+                                     &pSyncHist->btSyncConnection[j], sizeof(tSmeBtSyncConnectionParam) );
+                    }
+                    else
+                    {
+                        btEvent.uEventParam.btDisconnect.connectionHandle = pSyncHist->btSyncConnection[j].connectionHandle;
+                    }
+                    btcSendBTEvent( pMac, &btEvent );
+                }
+            }
+        }
+        //SYNC update
+        for( i = 0; i < BT_MAX_SCO_SUPPORT; i++ )
+        {
+            if( pReplay->btcEventHist.btSyncUpdateEvent[i].fValid )
+            {
+                vos_mem_zero( &btEvent, sizeof(tSmeBtEvent) );
+                btEvent.btEventType = BT_EVENT_SYNC_CONNECTION_UPDATED;
+                vos_mem_copy( &btEvent.uEventParam.btSyncConnection, 
+                            &pReplay->btcEventHist.btSyncUpdateEvent[i].btSyncConnection, 
+                            sizeof(tSmeBtSyncConnectionParam) );
+                btcSendBTEvent( pMac, &btEvent );
+            }
+        }
+        //Clear all events
+        vos_mem_zero( &pReplay->btcEventHist, sizeof(tSmeBtcEventHist) );
+    }
+}
+
+static void btcPowerStateCB( v_PVOID_t pContext, tPmcState pmcState )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(pContext);
+    if( FULL_POWER == pmcState )
+    {
+        btcReplayEvents( pMac );
+    }
+}
+
+/* ---------------------------------------------------------------------------
+    \fn btcLogEvent
+    \brief  API to log the the current Bluetooth event
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type
+                            tSmeBtEvent. Caller owns the memory and is responsible
+                            for freeing it.
+    \return None
+  ---------------------------------------------------------------------------*/
+static void btcLogEvent (tHalHandle hHal, tpSmeBtEvent pBtEvent)
+{
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+               "Bluetooth Event %d received", __FUNCTION__, pBtEvent->btEventType);
+   switch(pBtEvent->btEventType)
+   {
+      case BT_EVENT_CREATE_SYNC_CONNECTION:
+      case BT_EVENT_SYNC_CONNECTION_COMPLETE:
+      case BT_EVENT_SYNC_CONNECTION_UPDATED:
+          VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "SCO Connection: "
+               "connectionHandle = %d status = %d linkType %d "
+               "scoInterval %d scoWindow %d retransmisisonWindow = %d ",
+               pBtEvent->uEventParam.btSyncConnection.connectionHandle,
+               pBtEvent->uEventParam.btSyncConnection.status,
+               pBtEvent->uEventParam.btSyncConnection.linkType,
+               pBtEvent->uEventParam.btSyncConnection.scoInterval,
+               pBtEvent->uEventParam.btSyncConnection.scoWindow,
+               pBtEvent->uEventParam.btSyncConnection.retransmisisonWindow);
+          VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "BD ADDR = "
+               "0x%x 0x%x 0x%x 0x%x 0x%x 0x%x",
+               pBtEvent->uEventParam.btSyncConnection.bdAddr[5],
+               pBtEvent->uEventParam.btSyncConnection.bdAddr[4],
+               pBtEvent->uEventParam.btSyncConnection.bdAddr[3],
+               pBtEvent->uEventParam.btSyncConnection.bdAddr[2],
+               pBtEvent->uEventParam.btSyncConnection.bdAddr[1],
+               pBtEvent->uEventParam.btSyncConnection.bdAddr[0]);
+          break;
+      case BT_EVENT_CREATE_ACL_CONNECTION:
+      case BT_EVENT_ACL_CONNECTION_COMPLETE:
+          VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "ACL Connection: "
+               "connectionHandle = %d status = %d ",
+               pBtEvent->uEventParam.btAclConnection.connectionHandle,
+               pBtEvent->uEventParam.btAclConnection.status);
+          VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "BD ADDR = "
+               "0x%x 0x%x 0x%x 0x%x 0x%x 0x%x",
+               pBtEvent->uEventParam.btAclConnection.bdAddr[5],
+               pBtEvent->uEventParam.btAclConnection.bdAddr[4],
+               pBtEvent->uEventParam.btAclConnection.bdAddr[3],
+               pBtEvent->uEventParam.btAclConnection.bdAddr[2],
+               pBtEvent->uEventParam.btAclConnection.bdAddr[1],
+               pBtEvent->uEventParam.btAclConnection.bdAddr[0]);
+          break;
+      case BT_EVENT_MODE_CHANGED:
+          VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "ACL Mode change : "
+               "connectionHandle %d mode %d ",
+               pBtEvent->uEventParam.btAclModeChange.connectionHandle,
+               pBtEvent->uEventParam.btAclModeChange.mode);
+          break;
+      case BT_EVENT_DISCONNECTION_COMPLETE:
+          VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "Disconnect Event : "
+               "connectionHandle %d ", pBtEvent->uEventParam.btAclModeChange.connectionHandle);
+          break;
+      default:
+         break;
+   }
+ }
+
+/*
+   Caller can check whether BTC's current event allows UAPSD. This doesn't affect
+   BMPS.
+   return:  VOS_TRUE -- BTC is ready for UAPSD
+            VOS_FALSE -- certain BT event is active, cannot enter UAPSD
+*/
+v_BOOL_t btcIsReadyForUapsd( tHalHandle hHal )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    return( pMac->btc.btcUapsdOk );
+}
+
+/*
+    Base on the BT event, this function sets the flag on whether to allow UAPSD
+    At this time, we are only interested in SCO and A2DP.
+    A2DP tracking is through BT_EVENT_A2DP_STREAM_START and BT_EVENT_A2DP_STREAM_STOP
+    SCO is through BT_EVENT_SYNC_CONNECTION_COMPLETE and BT_EVENT_DISCONNECTION_COMPLETE
+    BT_EVENT_DEVICE_SWITCHED_OFF overwrites them all
+*/
+void btcUapsdCheck( tpAniSirGlobal pMac, tpSmeBtEvent pBtEvent )
+{
+   v_U8_t i;
+   v_BOOL_t fLastUapsdState = pMac->btc.btcUapsdOk, fMoreSCO = VOS_FALSE;
+   switch( pBtEvent->btEventType )
+   {
+   case BT_EVENT_DISCONNECTION_COMPLETE:
+       if( (VOS_FALSE == pMac->btc.btcUapsdOk) && 
+           BT_INVALID_CONN_HANDLE != pBtEvent->uEventParam.btDisconnect.connectionHandle )
+       {
+           //Check whether all SCO connections are gone
+           for(i=0; i < BT_MAX_SCO_SUPPORT; i++)
+           {
+               if( (BT_INVALID_CONN_HANDLE != pMac->btc.btcScoHandles[i]) &&
+                   (pMac->btc.btcScoHandles[i] != pBtEvent->uEventParam.btDisconnect.connectionHandle) )
+               {
+                   //We still have outstanding SCO connection
+                   fMoreSCO = VOS_TRUE;
+               }
+               else if( pMac->btc.btcScoHandles[i] == pBtEvent->uEventParam.btDisconnect.connectionHandle )
+               {
+                   pMac->btc.btcScoHandles[i] = BT_INVALID_CONN_HANDLE;
+               }
+           }
+           if( !fMoreSCO && !pMac->btc.fA2DPUp )
+           {
+               //All SCO is disconnected
+               pMac->btc.btcUapsdOk = VOS_TRUE;
+               smsLog( pMac, LOGE, "BT event (DISCONNECTION) happens, UAPSD-allowed flag (%d) change to TRUE \n", 
+                        pBtEvent->btEventType, pMac->btc.btcUapsdOk );
+           }
+       }
+       break;
+   case BT_EVENT_DEVICE_SWITCHED_OFF:
+       smsLog( pMac, LOGE, "BT event (DEVICE_OFF) happens, UAPSD-allowed flag (%d) change to TRUE \n", 
+                        pBtEvent->btEventType, pMac->btc.btcUapsdOk );
+       //Clean up SCO
+       for(i=0; i < BT_MAX_SCO_SUPPORT; i++)
+       {
+           pMac->btc.btcScoHandles[i] = BT_INVALID_CONN_HANDLE;
+       }
+       pMac->btc.fA2DPUp = VOS_FALSE;
+       pMac->btc.btcUapsdOk = VOS_TRUE;
+       break;
+   case BT_EVENT_A2DP_STREAM_STOP:
+       smsLog( pMac, LOGE, "BT event  (A2DP_STREAM_STOP) happens, UAPSD-allowed flag (%d) \n", 
+            pMac->btc.btcUapsdOk );
+       pMac->btc.fA2DPUp = VOS_FALSE;
+       //Check whether SCO is on
+       for(i=0; i < BT_MAX_SCO_SUPPORT; i++)
+       {
+           if(pMac->btc.btcScoHandles[i] != BT_INVALID_CONN_HANDLE)
+           {
+              break;
+           }
+       }
+       if( BT_MAX_SCO_SUPPORT == i )
+       {
+            pMac->btc.fA2DPTrafStop = VOS_TRUE;
+           smsLog( pMac, LOGE, "BT_EVENT_A2DP_STREAM_STOP: UAPSD-allowed flag is now %d\n",
+                   pMac->btc.btcUapsdOk );
+       }
+       break;
+
+   case BT_EVENT_MODE_CHANGED:
+       smsLog( pMac, LOGE, "BT event (BT_EVENT_MODE_CHANGED) happens, Mode (%d) UAPSD-allowed flag (%d)\n",
+               pBtEvent->uEventParam.btAclModeChange.mode, pMac->btc.btcUapsdOk );
+       if(pBtEvent->uEventParam.btAclModeChange.mode == BT_ACL_SNIFF)
+       {
+           //Check whether SCO is on
+           for(i=0; i < BT_MAX_SCO_SUPPORT; i++)
+           {
+               if(pMac->btc.btcScoHandles[i] != BT_INVALID_CONN_HANDLE)
+               {
+                   break;
+               }
+           }
+           if( BT_MAX_SCO_SUPPORT == i )
+           {
+               if(VOS_TRUE == pMac->btc.fA2DPTrafStop)
+               {
+                   pMac->btc.btcUapsdOk = VOS_TRUE;
+                   pMac->btc.fA2DPTrafStop = VOS_FALSE;
+               }
+               smsLog( pMac, LOGE, "BT_EVENT_MODE_CHANGED with Mode:%d UAPSD-allowed flag is now %d\n",
+                       pBtEvent->uEventParam.btAclModeChange.mode,pMac->btc.btcUapsdOk );
+           }
+       }
+       break;
+   case BT_EVENT_CREATE_SYNC_CONNECTION:
+       {
+           pMac->btc.btcUapsdOk = VOS_FALSE;
+           smsLog( pMac, LOGE, "BT_EVENT_CREATE_SYNC_CONNECTION (%d) happens, UAPSD-allowed flag (%d) change to FALSE \n", 
+                   pBtEvent->btEventType, pMac->btc.btcUapsdOk );
+       }
+       break;
+   case BT_EVENT_SYNC_CONNECTION_COMPLETE:
+       //Make sure it is a success
+       if( BT_CONN_STATUS_FAIL != pBtEvent->uEventParam.btSyncConnection.status )
+       {
+           //Save te handle for later use
+           for( i = 0; i < BT_MAX_SCO_SUPPORT; i++)
+           {
+               VOS_ASSERT(BT_INVALID_CONN_HANDLE != pBtEvent->uEventParam.btSyncConnection.connectionHandle);
+               if( (BT_INVALID_CONN_HANDLE == pMac->btc.btcScoHandles[i]) &&
+                   (BT_INVALID_CONN_HANDLE != pBtEvent->uEventParam.btSyncConnection.connectionHandle))
+               {
+                   pMac->btc.btcScoHandles[i] = pBtEvent->uEventParam.btSyncConnection.connectionHandle;
+                   break;
+               }
+           }
+
+           if( i >= BT_MAX_SCO_SUPPORT )
+           {
+               smsLog(pMac, LOGE, FL("Too many SCO, ignore this one\n"));
+           }
+       }
+       else
+       {
+            //Check whether SCO is on
+           for(i=0; i < BT_MAX_SCO_SUPPORT; i++)
+           {
+               if(pMac->btc.btcScoHandles[i] != BT_INVALID_CONN_HANDLE)
+               {
+                   break;
+               }
+       }
+           /*If No Other Sco/A2DP is ON reenable UAPSD*/
+           if( (BT_MAX_SCO_SUPPORT == i)  && !pMac->btc.fA2DPUp)           
+           {
+               pMac->btc.btcUapsdOk = VOS_TRUE;
+           }
+           smsLog(pMac, LOGE, FL("TSYNC complete failed\n"));
+       }
+       break;
+   case BT_EVENT_A2DP_STREAM_START:
+       smsLog( pMac, LOGE, "BT_EVENT_A2DP_STREAM_START (%d) happens, UAPSD-allowed flag (%d) change to FALSE \n", 
+                pBtEvent->btEventType, pMac->btc.btcUapsdOk );
+       pMac->btc.fA2DPTrafStop = VOS_FALSE;
+       pMac->btc.btcUapsdOk = VOS_FALSE;
+       pMac->btc.fA2DPUp = VOS_TRUE;
+       break;
+   default:
+       //No change for these events
+       smsLog( pMac, LOGE, "BT event (%d) happens, UAPSD-allowed flag (%d) no change \n", 
+                    pBtEvent->btEventType, pMac->btc.btcUapsdOk );
+       break;
+   }
+   if(fLastUapsdState != pMac->btc.btcUapsdOk)
+   {
+      sme_QosTriggerUapsdChange( pMac );
+   }
+}
+
+/* ---------------------------------------------------------------------------
+    \fn btcHandleCoexInd
+    \brief  API to handle Coex indication from WDI
+    \param  pMac - The handle returned by macOpen.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  success
+            eHAL_STATUS_SUCCESS  failure
+  ---------------------------------------------------------------------------*/
+eHalStatus btcHandleCoexInd(tHalHandle hHal, void* pMsg)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tSirSmeCoexInd *pSmeCoexInd = (tSirSmeCoexInd *)pMsg;
+
+   if (NULL == pMsg)
+   {
+      smsLog(pMac, LOGE, "in %s msg ptr is NULL\n", __FUNCTION__);
+      status = eHAL_STATUS_FAILURE;
+   }
+   else
+   {
+      // DEBUG
+      smsLog(pMac, LOG1, "Coex indication in %s(), type %d",
+             __FUNCTION__, pSmeCoexInd->coexIndType);
+
+     // suspend heartbeat monitoring
+     if (pSmeCoexInd->coexIndType == SIR_COEX_IND_TYPE_DISABLE_HB_MONITOR)
+     {
+        // set heartbeat threshold CFG to zero
+        ccmCfgSetInt(pMac, WNI_CFG_HEART_BEAT_THRESHOLD, 0, NULL, eANI_BOOLEAN_FALSE);
+        pMac->btc.btcHBActive = VOS_FALSE;
+     }
+
+     // resume heartbeat monitoring
+     else if (pSmeCoexInd->coexIndType == SIR_COEX_IND_TYPE_ENABLE_HB_MONITOR)
+     {
+        if (!pMac->btc.btcHBActive) 
+        {
+           ccmCfgSetInt(pMac, WNI_CFG_HEART_BEAT_THRESHOLD, pMac->btc.btcHBCount, NULL, eANI_BOOLEAN_FALSE);
+           pMac->btc.btcHBActive = VOS_TRUE;
+        }
+     }
+
+     // unknown indication type
+     else
+     {
+        smsLog(pMac, LOGE, "unknown Coex indication type in %s()", __FUNCTION__);
+     }
+   }
+
+   return(status);
+}
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+/* ---------------------------------------------------------------------------
+    \fn btcDiagEventLog
+    \brief  API to log the the current Bluetooth event
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type
+                            tSmeBtEvent. Caller owns the memory and is responsible
+                            for freeing it.
+    \return None
+  ---------------------------------------------------------------------------*/
+static void btcDiagEventLog (tHalHandle hHal, tpSmeBtEvent pBtEvent)
+{
+   //vos_event_wlan_btc_type *log_ptr = NULL;
+   WLAN_VOS_DIAG_EVENT_DEF(btDiagEvent, vos_event_wlan_btc_type);
+   {
+       btDiagEvent.eventId = pBtEvent->btEventType;
+       switch(pBtEvent->btEventType)
+       {
+            case BT_EVENT_CREATE_SYNC_CONNECTION:
+            case BT_EVENT_SYNC_CONNECTION_COMPLETE:
+            case BT_EVENT_SYNC_CONNECTION_UPDATED:
+                btDiagEvent.connHandle = pBtEvent->uEventParam.btSyncConnection.connectionHandle;
+                btDiagEvent.connStatus = pBtEvent->uEventParam.btSyncConnection.status;
+                btDiagEvent.linkType   = pBtEvent->uEventParam.btSyncConnection.linkType;
+                btDiagEvent.scoInterval = pBtEvent->uEventParam.btSyncConnection.scoInterval;
+                btDiagEvent.scoWindow  = pBtEvent->uEventParam.btSyncConnection.scoWindow;
+                btDiagEvent.retransWindow = pBtEvent->uEventParam.btSyncConnection.retransmisisonWindow;
+                vos_mem_copy(btDiagEvent.btAddr, pBtEvent->uEventParam.btSyncConnection.bdAddr,
+                              sizeof(btDiagEvent.btAddr));
+                break;
+            case BT_EVENT_CREATE_ACL_CONNECTION:
+            case BT_EVENT_ACL_CONNECTION_COMPLETE:
+                btDiagEvent.connHandle = pBtEvent->uEventParam.btAclConnection.connectionHandle;
+                btDiagEvent.connStatus = pBtEvent->uEventParam.btAclConnection.status;
+                vos_mem_copy(btDiagEvent.btAddr, pBtEvent->uEventParam.btAclConnection.bdAddr,
+                             sizeof(btDiagEvent.btAddr));
+                break;
+            case BT_EVENT_MODE_CHANGED:
+                btDiagEvent.connHandle = pBtEvent->uEventParam.btAclModeChange.connectionHandle;
+                btDiagEvent.mode = pBtEvent->uEventParam.btAclModeChange.mode;
+                break;
+            case BT_EVENT_DISCONNECTION_COMPLETE:
+                btDiagEvent.connHandle = pBtEvent->uEventParam.btAclModeChange.connectionHandle;
+                break;
+            default:
+                break;
+       }
+   }
+   WLAN_VOS_DIAG_EVENT_REPORT(&btDiagEvent, EVENT_WLAN_BTC);
+}
+#endif /* FEATURE_WLAN_DIAG_SUPPORT */
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
diff --git a/CORE/SME/src/ccm/ccmApi.c b/CORE/SME/src/ccm/ccmApi.c
new file mode 100644
index 0000000..ac50aff
--- /dev/null
+++ b/CORE/SME/src/ccm/ccmApi.c
@@ -0,0 +1,1124 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+#include "palTypes.h"
+#include "wniApi.h"     /* WNI_CFG_SET_REQ */
+#include "sirParams.h"  /* tSirMbMsg */
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halHddApis.h" /* palAllocateMemory */
+#endif
+#include "smsDebug.h"   /* smsLog */
+#include "cfgApi.h"
+#include "ccmApi.h"
+#include "logDump.h"
+
+//#define CCM_DEBUG
+#undef CCM_DEBUG
+
+#define CCM_DEBUG2
+//#undef CCM_DEBUG2
+
+#define CFGOBJ_ALIGNTO          4
+#define CFGOBJ_ALIGN(len)       ( ((len)+CFGOBJ_ALIGNTO-1) & ~(CFGOBJ_ALIGNTO-1) )
+
+#define CFGOBJ_ID_SIZE                  4       /* 4 bytes for cfgId */
+#define CFGOBJ_LEN_SIZE                 4       /* 4 bytes for length */
+#define CFGOBJ_INTEGER_VALUE_SIZE       4       /* 4 bytes for integer value */
+
+#define CFG_UPDATE_MAGIC_DWORD     0xabab
+
+#define halHandle2HddHandle(hHal)  ( (NULL == (hHal)) ? 0 : ((tpAniSirGlobal)(hHal))->hHdd )
+
+static void ccmComplete(tHddHandle hHdd, void *done)
+{
+    if (done)
+    {
+        (void)palSemaphoreGive(hHdd, done);
+    }
+}
+
+static void ccmWaitForCompletion(tHddHandle hHdd, void *done)
+{
+    if (done)
+    {
+        (void)palSemaphoreTake(hHdd, done);
+    }
+}
+
+static tANI_U32 * encodeCfgReq(tHddHandle hHdd, tANI_U32 *pl, tANI_U32 cfgId, tANI_S32 length, void *pBuf, tANI_U32 value, tANI_U32 type)
+{
+    *pl++ = pal_cpu_to_be32(cfgId) ;
+    *pl++ = pal_cpu_to_be32(length) ;
+    if (type == CCM_INTEGER_TYPE)
+    {
+        *pl++ = pal_cpu_to_be32(value) ;
+    }
+    else
+    {
+        palCopyMemory(hHdd, (void *)pl, (void *)pBuf, length);
+        pl += (CFGOBJ_ALIGN(length) / CFGOBJ_ALIGNTO);
+    }
+    return pl ;
+}
+
+/*
+ * CCM_STRING_TYPE                       CCM_INTEGER_TYPE
+ * |<--------  4   ----->|               |<--------  4   ----->|                          
+ * +----------+            <-- msg  -->  +----------+                                 
+ * |type      |                          |type      |           
+ * +----------+                          +----------+           
+ * |msgLen=24 |                          |msgLen=16 |           
+ * +----------+----------+               +----------+----------+
+ * | cfgId               |               | cfgId               |  
+ * +---------------------+               +---------------------+
+ * | length=11           |               | length=4            |  
+ * +---------------------+               +---------------------+
+ * |                     |               | value               |  
+ * |                     |               +---------------------+  
+ * |                     |
+ * |                +----+
+ * |                |////| <- padding to 4-byte boundary
+ * +----------------+----+
+ */
+static eHalStatus sendCfg(tpAniSirGlobal pMac, tHddHandle hHdd, tCfgReq *req, tANI_BOOLEAN fRsp)
+{
+    tSirMbMsg *msg;
+    eHalStatus status;
+    tANI_S16 msgLen = (tANI_U16)(4 +    /* 4 bytes for msg header */
+                                 CFGOBJ_ID_SIZE +
+                                 CFGOBJ_LEN_SIZE +
+                                 CFGOBJ_ALIGN(req->length)) ;
+
+    status = palAllocateMemory(hHdd, (void **)&msg, msgLen);
+    if (status == eHAL_STATUS_SUCCESS)
+    {
+        if( fRsp )
+        {
+            msg->type = pal_cpu_to_be16(WNI_CFG_SET_REQ);
+        }
+        else
+        {
+            msg->type = pal_cpu_to_be16(WNI_CFG_SET_REQ_NO_RSP);
+        }
+        msg->msgLen = pal_cpu_to_be16(msgLen);
+        (void)encodeCfgReq(hHdd, msg->data, req->cfgId, req->length, req->ccmPtr, req->ccmValue, req->type) ;
+
+        status = palSendMBMessage(hHdd, msg) ;
+        if (status != eHAL_STATUS_SUCCESS)
+        {
+            smsLog( pMac, LOGW, FL("palSendMBMessage() failed\n"));
+            //No need to free msg. palSendMBMessage frees it.
+            status = eHAL_STATUS_FAILURE ;
+        }
+    }
+    else
+    {
+        smsLog( pMac, LOGW, FL("palAllocateMemory(len=%d)\n"), msgLen );
+    }
+
+    return status ;
+}
+
+static tCfgReq * allocateCfgReq(tHddHandle hHdd, tANI_U32 type, tANI_S32 length)
+{
+    tCfgReq *req ;
+    tANI_S32 alloc_len = sizeof(tCfgReq) ;
+
+    if (type == CCM_STRING_TYPE)
+    {
+        alloc_len += length ;
+    }
+
+    if (palAllocateMemory(hHdd, (void **)&req, alloc_len) != eHAL_STATUS_SUCCESS)
+    {
+        return NULL ;
+    }
+
+    req->ccmPtr = (req+1);
+
+    return req ;
+}
+
+static void freeCfgReq(tHddHandle hHdd, tCfgReq *req)
+{
+    palFreeMemory(hHdd, (void*)req) ;
+}
+
+static void add_req_tail(tCfgReq *req, struct ccmlink *q)
+{
+    if (q->tail)
+    {
+        q->tail->next = req;
+        q->tail = req ;
+    }
+    else
+    {
+        q->head = q->tail = req ;
+    }
+}
+
+static void del_req(tCfgReq *req, struct ccmlink *q)
+{
+    q->head = req->next ;
+    req->next = NULL ;
+    if (q->head == NULL)
+    {
+        q->tail = NULL ;
+    }
+}
+
+static void purgeReqQ(tHalHandle hHal)
+{
+    tHddHandle hHdd = halHandle2HddHandle(hHal);
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tCfgReq *req, *tmp ;
+
+    for (req = pMac->ccm.reqQ.head; req; req = tmp)
+    {
+        /* loop thru reqQ and invoke callback to return failure */
+        smsLog(pMac, LOGW, FL("deleting cfgReq, cfgid=%d\n"), (int)req->cfgId);
+
+        tmp = req->next ;
+
+        if (req->callback)
+        {
+            req->callback(hHal, eHAL_STATUS_FAILURE);
+        }
+        palSpinLockTake(hHdd, pMac->ccm.lock);
+        del_req(req, &pMac->ccm.reqQ);
+        palSpinLockGive(hHdd, pMac->ccm.lock);
+        freeCfgReq(hHdd, req);
+    }
+    return ;
+}
+
+static void sendQueuedReqToMacSw(tpAniSirGlobal pMac, tHddHandle hHdd)
+{
+    tCfgReq *req ;
+
+    /* Send the head req */
+    req = pMac->ccm.reqQ.head ;
+    if (req)
+    {
+        if (req->state == eCCM_REQ_QUEUED)
+        {
+            /* Send WNI_CFG_SET_REQ */
+            req->state = eCCM_REQ_SENT;
+            if (sendCfg(pMac, hHdd, req, eANI_BOOLEAN_TRUE) != eHAL_STATUS_SUCCESS)
+            {
+                smsLog( pMac, LOGW, FL("sendCfg() failed\n"));
+                palSpinLockTake(hHdd, pMac->ccm.lock);
+                del_req(req, &pMac->ccm.reqQ) ;
+                palSpinLockGive(hHdd, pMac->ccm.lock);
+                if (req->callback)
+                {
+                    req->callback((tHalHandle)pMac, WNI_CFG_OTHER_ERROR) ;
+                }
+
+#ifdef CCM_DEBUG
+                smsLog(pMac, LOGW, FL("ccmComplete(%p)\n"), req->done);
+#endif
+                ccmComplete(hHdd, req->done);
+
+                freeCfgReq(hHdd, req);
+            }
+        }
+        else
+        {
+            smsLog( pMac, LOGW, FL("reqState is not eCCM_REQ_QUEUED, is %d\n"), req->state );
+        }
+    }
+
+    return ;
+}
+
+static eHalStatus cfgSetSub(tpAniSirGlobal pMac, tHddHandle hHdd, tANI_U32 cfgId, tANI_U32 type, 
+                            tANI_S32 length, void *ccmPtr, tANI_U32 ccmValue, 
+                            tCcmCfgSetCallback callback, eAniBoolean toBeSaved, void *sem, tCfgReq **r)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCfgReq *req ;
+
+    do
+    {
+        *r = NULL ;
+
+        if (pMac->ccm.state == eCCM_STOPPED)
+        {
+            status = eHAL_STATUS_FAILURE ;
+            break ;
+        }
+
+        req = allocateCfgReq(hHdd, type, length);
+        if (req == NULL)
+        {
+            status = eHAL_STATUS_FAILED_ALLOC ;
+            break ;
+        }
+
+        req->next       = NULL ;
+        req->cfgId      = (tANI_U16)cfgId ;
+        req->type       = (tANI_U8)type ;
+        req->state      = eCCM_REQ_QUEUED ;
+        req->toBeSaved  = !!toBeSaved ;
+        req->length     = length ;
+        req->done       = sem ;
+        req->callback   = callback ;
+        if (type == CCM_INTEGER_TYPE)
+        {
+            req->ccmValue = ccmValue ;
+        }
+        else
+        {
+            palCopyMemory(hHdd, (void*)req->ccmPtr, (void*)ccmPtr, length); 
+        }
+
+        palSpinLockTake(hHdd, pMac->ccm.lock);
+
+        add_req_tail(req, &pMac->ccm.reqQ);
+        /* If this is the first req on the queue, send it to MAC SW */
+        if ((pMac->ccm.replay.started == 0) && (pMac->ccm.reqQ.head == req))
+        {
+            /* Send WNI_CFG_SET_REQ */
+            req->state = eCCM_REQ_SENT;
+            palSpinLockGive(hHdd, pMac->ccm.lock);
+            status = sendCfg(pMac, hHdd, req, eANI_BOOLEAN_TRUE) ;
+            if (status != eHAL_STATUS_SUCCESS)
+            {
+                smsLog( pMac, LOGW, FL("sendCfg() failed\n"));
+                palSpinLockTake(hHdd, pMac->ccm.lock);
+                del_req(req, &pMac->ccm.reqQ);
+                palSpinLockGive(hHdd, pMac->ccm.lock);
+                freeCfgReq(hHdd, req);
+                break ;
+            }
+            else
+            {
+                palSpinLockTake(hHdd, pMac->ccm.lock);
+                if(req != pMac->ccm.reqQ.head)
+                {
+                    //We send the request and it must be done already
+                    req = NULL;
+                }
+                palSpinLockGive(hHdd, pMac->ccm.lock);
+            }
+        }
+        else
+        {
+            palSpinLockGive(hHdd, pMac->ccm.lock);
+        }
+        *r = req ;
+
+    } while(0) ;
+
+    return status;
+}
+
+static eHalStatus cfgSet(tHalHandle hHal, tANI_U32 cfgId, tANI_U32 type, tANI_S32 length, void * ccmPtr, tANI_U32 ccmValue, tCcmCfgSetCallback callback, eAniBoolean toBeSaved)
+{
+    tHddHandle hHdd = halHandle2HddHandle(hHal);
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+    tCfgReq *req ;
+
+    if (pal_in_interrupt())
+    {
+#ifdef CCM_DEBUG2
+        smsLog(pMac, LOGE, FL("WNI_CFG_%s (%d 0x%x), in_interrupt()=TRUE\n"), gCfgParamName[cfgId], (int)cfgId, (int)cfgId);
+#endif
+        status = cfgSetSub(pMac, hHdd, cfgId, type, length, ccmPtr, ccmValue, callback, toBeSaved, NULL, &req);
+    }
+    else
+    {
+        void *sem ;
+
+#ifdef CCM_DEBUG2
+        smsLog(pMac, LOGE, FL("WNI_CFG_%s (%d 0x%x), in_interrupt()=FALSE\n"), gCfgParamName[cfgId], (int)cfgId, (int)cfgId);
+#endif
+        pal_local_bh_disable() ;
+
+        status = palMutexAllocLocked( hHdd, &sem ) ;
+        if (status != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("mutex alloc failed\n"));
+            sem = NULL;
+        }
+        else
+        {
+            status = cfgSetSub(pMac, hHdd, cfgId, type, length, ccmPtr, ccmValue, callback, toBeSaved, sem, &req);
+            if ((status != eHAL_STATUS_SUCCESS) || (req == NULL))
+            {
+                //Either it fails to send or the req is finished already
+                palSemaphoreFree( hHdd, sem );
+                sem = NULL;
+            }
+        }
+
+        pal_local_bh_enable() ;
+
+        if ((status == eHAL_STATUS_SUCCESS) && (sem != NULL))
+        {
+#ifdef CCM_DEBUG
+            smsLog(pMac, LOGW, FL("ccmWaitForCompletion(%p)\n"), req->done);
+#endif
+            ccmWaitForCompletion(hHdd, sem);
+
+#ifdef CCM_DEBUG
+            smsLog(pMac, LOGW, FL("free(%p)\n"), req->done);
+#endif
+            palSemaphoreFree( hHdd, sem ) ;
+        }
+    }
+
+    return status ;
+}
+
+eHalStatus ccmOpen(tHalHandle hHal)
+{
+    tHddHandle hHdd = halHandle2HddHandle(hHal);
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    (void)palZeroMemory(hHdd, &pMac->ccm, sizeof(tCcm)) ;
+    return palSpinLockAlloc(hHdd, &pMac->ccm.lock);
+}
+
+eHalStatus ccmClose(tHalHandle hHal)
+{
+    tHddHandle hHdd = halHandle2HddHandle(hHal);
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_U32 i ; 
+    tCfgReq *req ;
+
+    ccmStop(hHal);
+
+    /* Go thru comp[] to free all saved requests */
+    for (i = 0 ; i < CFG_PARAM_MAX_NUM ; ++i)
+    {
+        if ((req = pMac->ccm.comp[i]) != NULL)
+        {
+            freeCfgReq(hHdd, req);
+        }
+    }
+
+    return palSpinLockFree(hHdd, pMac->ccm.lock);
+}
+
+/* This function executes in (Linux) softirq context */
+void ccmCfgCnfMsgHandler(tHalHandle hHal, void *m)
+{
+    tHddHandle hHdd = halHandle2HddHandle(hHal);
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tSirMbMsg *msg = (tSirMbMsg *)m ;
+    tANI_U32 result, cfgId ;
+    tCfgReq *req, *old ;
+
+#if 0
+    if (pMac->ccm.state != eCCM_STARTED)
+    {
+        return ;
+    }
+#endif
+
+    result  = pal_be32_to_cpu(msg->data[0]);
+    cfgId   = pal_be32_to_cpu(msg->data[1]);
+
+    if (pMac->ccm.replay.started && cfgId == CFG_UPDATE_MAGIC_DWORD)
+    {
+        pMac->ccm.replay.in_progress = 1 ;
+        return ;
+    }
+
+    if (pMac->ccm.replay.in_progress)
+    {
+        /* save error code */
+        if (!CCM_IS_RESULT_SUCCESS(result))
+        {
+            pMac->ccm.replay.result = result ;
+        }
+
+        if (--pMac->ccm.replay.nr_param == 0)
+        {
+            pMac->ccm.replay.in_progress = 0 ;
+
+            if (pMac->ccm.replay.callback)
+            {
+                pMac->ccm.replay.callback(hHal, pMac->ccm.replay.result);
+            }
+
+            pMac->ccm.replay.started = 0 ;
+
+            /* Wake up the sleeping process */
+#ifdef CCM_DEBUG
+            smsLog(pMac, LOGW, FL("ccmComplete(%p)\n"), pMac->ccm.replay.done);
+#endif
+            ccmComplete(hHdd, pMac->ccm.replay.done);
+            //Let go with the rest of the set CFGs waiting.
+            sendQueuedReqToMacSw(pMac, hHdd);
+        }
+    }
+    else
+    {
+        /*
+         * Try to match this response with the request.
+         * What if i could not find the req entry ???
+         */
+        req = pMac->ccm.reqQ.head ;
+        if (req)
+        {
+
+            if (req->cfgId == cfgId && req->state == eCCM_REQ_SENT)
+            {
+                palSpinLockTake(hHdd, pMac->ccm.lock);
+                del_req(req, &pMac->ccm.reqQ);
+                palSpinLockGive(hHdd, pMac->ccm.lock);
+                req->state = eCCM_REQ_DONE ;
+
+                if (result == WNI_CFG_NEED_RESTART ||
+                    result == WNI_CFG_NEED_RELOAD)
+                {
+#ifdef CCM_DEBUG
+                    smsLog(pMac, LOGW, FL("need restart/reload, cfgId=%d\n"), req->cfgId) ;
+#endif
+                    //purgeReqQ(hHal);
+                }
+
+                /* invoke callback */
+                if (req->callback)
+                {
+#ifdef CCM_DEBUG
+                    req->callback(hHal, cfgId) ;
+#else
+                    req->callback(hHal, result) ;
+#endif
+                }
+
+                /* Wake up the sleeping process */
+#ifdef CCM_DEBUG
+                smsLog(pMac, LOGW, FL("cfgId=%ld, calling ccmComplete(%p)\n"), cfgId, req->done);
+#endif
+                ccmComplete(hHdd, req->done);
+
+                /* move the completed req from reqQ to comp[] */
+                if (req->toBeSaved && (CCM_IS_RESULT_SUCCESS(result)))
+                {
+                    if ((old = pMac->ccm.comp[cfgId]) != NULL)
+                    {
+                        freeCfgReq(hHdd, old) ;
+                    }
+                    pMac->ccm.comp[cfgId] = req ;
+                }
+                else
+                {
+                    freeCfgReq(hHdd, req) ;
+                }
+                sendQueuedReqToMacSw(pMac, hHdd);
+            }
+            else
+            {
+                smsLog( pMac, LOGW, FL("can not match RSP with REQ, rspcfgid=%d result=%d reqcfgid=%d reqstate=%d\n"),
+                        (int)cfgId, (int)result, req->cfgId, req->state);
+
+#ifdef CCM_DEBUG
+                smsLog(pMac, LOGW, FL("ccmComplete(%p)\n"), req->done);
+#endif
+            }
+
+        }
+    }
+
+    return ;
+}
+
+void ccmStart(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    pMac->ccm.state = eCCM_STARTED ;
+
+#if defined(ANI_LOGDUMP)
+    ccmDumpInit(hHal);
+#endif //#if defined(ANI_LOGDUMP)
+
+    return ;
+}
+
+void ccmStop(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    pMac->ccm.state = eCCM_STOPPED ;
+
+    pal_local_bh_disable() ;
+    purgeReqQ(hHal);
+    pal_local_bh_enable() ;
+
+    return ;
+}
+
+eHalStatus ccmCfgSetInt(tHalHandle hHal, tANI_U32 cfgId, tANI_U32 ccmValue, tCcmCfgSetCallback callback, eAniBoolean toBeSaved)
+{
+    if( callback || toBeSaved)
+    {
+        //we need to sychronous this one
+        return cfgSet(hHal, cfgId, CCM_INTEGER_TYPE, sizeof(tANI_U32), NULL, ccmValue, callback, toBeSaved);
+    }
+    else
+    {
+        //Simply push to CFG and not waiting for the response
+        tCfgReq req;
+        tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+        req.callback = NULL;
+        req.next = NULL;
+        req.cfgId = ( tANI_U16 )cfgId;
+        req.length = sizeof( tANI_U32 );
+        req.type = CCM_INTEGER_TYPE;
+        req.ccmPtr = NULL;
+        req.ccmValue = ccmValue;
+        req.toBeSaved = toBeSaved;
+        req.state = eCCM_REQ_SENT;
+
+        return ( sendCfg( pMac, pMac->hHdd, &req, eANI_BOOLEAN_FALSE ) );
+    }
+}
+
+eHalStatus ccmCfgSetStr(tHalHandle hHal, tANI_U32 cfgId, tANI_U8 *pStr, tANI_U32 length, tCcmCfgSetCallback callback, eAniBoolean toBeSaved)
+{
+    if( callback || toBeSaved )
+    {
+        //we need to sychronous this one
+        return cfgSet(hHal, cfgId, CCM_STRING_TYPE, length, pStr, 0, callback, toBeSaved);
+    }
+    else
+    {
+        //Simply push to CFG and not waiting for the response
+        tCfgReq req;
+        tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+        req.callback = NULL;
+        req.next = NULL;
+        req.cfgId = ( tANI_U16 )cfgId;
+        req.length = length;
+        req.type = CCM_STRING_TYPE;
+        req.ccmPtr = pStr;
+        req.ccmValue = 0;
+        req.toBeSaved = toBeSaved;
+        req.state = eCCM_REQ_SENT;
+
+        return ( sendCfg( pMac, pMac->hHdd, &req, eANI_BOOLEAN_FALSE ) );
+    }
+}
+
+eHalStatus ccmCfgGetInt(tHalHandle hHal, tANI_U32 cfgId, tANI_U32 *pValue)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status = eHAL_STATUS_SUCCESS ;
+    tCfgReq *req = pMac->ccm.comp[cfgId] ;
+
+    if (req && req->state == eCCM_REQ_DONE)
+    {
+        *pValue = req->ccmValue ; 
+    }
+    else
+    {
+        if (wlan_cfgGetInt(pMac, (tANI_U16)cfgId, pValue) != eSIR_SUCCESS)
+            status = eHAL_STATUS_FAILURE;
+    }
+
+    return status ;
+}
+
+eHalStatus ccmCfgGetStr(tHalHandle hHal, tANI_U32 cfgId, tANI_U8 *pBuf, tANI_U32 *pLength)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tHddHandle hHdd = halHandle2HddHandle(hHal);
+    eHalStatus status = eHAL_STATUS_SUCCESS ;
+    tCfgReq *req = pMac->ccm.comp[cfgId] ;
+
+    if (req && req->state == eCCM_REQ_DONE && (tANI_U32)req->length <= *pLength)
+    {
+        *pLength = req->length ; 
+        palCopyMemory(hHdd, (void*)pBuf, (void*)req->ccmPtr, req->length); 
+    }
+    else
+    {
+        if (wlan_cfgGetStr(pMac, (tANI_U16)cfgId, pBuf, pLength) != eSIR_SUCCESS)
+            status = eHAL_STATUS_FAILURE;
+    }
+
+    return status ;
+}
+
+/*
+ * Loop thru comp[] and form an ANI message which contains all completed cfgIds.
+ * The message begins with an INTEGER parameter (cfgId=CFG_UPDATE_MAGIC_DWORD)     
+ * to mark the start of the message.
+ */ 
+static eHalStatus cfgUpdate(tpAniSirGlobal pMac, tHddHandle hHdd, tCcmCfgSetCallback callback)
+{
+    tANI_U32 i, *pl ;
+    tCfgReq *req ;
+    tSirMbMsg *msg ;
+    eHalStatus status ;
+    tANI_S16 msgLen = 4 +       /* 4 bytes for msg header */ 
+                                /* for CFG_UPDATE_MAGIC_DWORD */ 
+        CFGOBJ_ID_SIZE +
+        CFGOBJ_LEN_SIZE +
+        CFGOBJ_INTEGER_VALUE_SIZE ;
+
+    if (pMac->ccm.state == eCCM_STOPPED || pMac->ccm.replay.started)
+    {
+        status = eHAL_STATUS_FAILURE ;
+        goto end ;
+    }
+
+    palSpinLockTake(hHdd, pMac->ccm.lock);
+
+    pMac->ccm.replay.started    = 1 ;
+    pMac->ccm.replay.nr_param   = 0 ;
+
+    palSpinLockGive(hHdd, pMac->ccm.lock);
+
+    /* Calculate message length */
+    for (i = 0 ; i < CFG_PARAM_MAX_NUM ; ++i)
+    {
+        if ((req = pMac->ccm.comp[i]) != NULL)
+        {
+            msgLen += (tANI_S16)(CFGOBJ_ID_SIZE + CFGOBJ_LEN_SIZE + CFGOBJ_ALIGN(req->length)) ;
+            pMac->ccm.replay.nr_param += 1 ;
+#ifdef CCM_DEBUG
+            smsLog(pMac, LOGW, FL("cfgId=%d\n"), req->cfgId);
+#endif
+        }
+    }
+
+    if (pMac->ccm.replay.nr_param == 0)
+    {
+        if (callback)
+        {
+            callback((tHalHandle)pMac, WNI_CFG_SUCCESS) ;
+        }
+        status = eHAL_STATUS_SUCCESS ;
+        goto end ;
+    }
+
+    pMac->ccm.replay.in_progress = 0 ;
+    pMac->ccm.replay.result      = WNI_CFG_SUCCESS ;
+    pMac->ccm.replay.callback    = callback ;
+    pMac->ccm.replay.done        = NULL ;
+
+    status = palAllocateMemory(hHdd, (void **)&msg, msgLen) ;
+    if (status != eHAL_STATUS_SUCCESS)
+    {
+        pMac->ccm.replay.started = 0 ;
+        goto end ; 
+    }
+
+    msg->type   = pal_cpu_to_be16(WNI_CFG_SET_REQ);
+    msg->msgLen = pal_cpu_to_be16(msgLen);
+
+    /* Encode the starting cfgId */
+    pl = encodeCfgReq(hHdd, msg->data, CFG_UPDATE_MAGIC_DWORD, 4, NULL, 0, CCM_INTEGER_TYPE) ;
+
+    /* Encode the saved cfg requests */
+    for (i = 0 ; i < CFG_PARAM_MAX_NUM ; ++i)
+    {
+        if ((req = pMac->ccm.comp[i]) != NULL)
+        {
+            pl = encodeCfgReq(hHdd, pl, req->cfgId, req->length, req->ccmPtr, req->ccmValue, req->type) ;
+        }
+    }
+
+    status = palSendMBMessage(hHdd, msg) ;
+    if (status != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGW, FL("palSendMBMessage() failed. status=%d\n"), status);
+        pMac->ccm.replay.started = 0 ;
+        //No need to free msg. palSendMBMessage frees it.
+        goto end ;
+    }
+
+ end:
+    return status ;
+}
+
+eHalStatus ccmCfgUpdate(tHalHandle hHal, tCcmCfgSetCallback callback)
+{
+    tHddHandle hHdd = halHandle2HddHandle(hHal);
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status ;
+
+    pal_local_bh_disable() ;
+
+    status = cfgUpdate(pMac, hHdd, callback) ;
+    if (status == eHAL_STATUS_SUCCESS)
+    {
+        if (pMac->ccm.replay.nr_param == 0)
+        {
+            /* there is nothing saved at comp[], so we are done! */
+            pMac->ccm.replay.started = 0 ;
+        }
+        else
+        {
+            /* we have sent update message to MAC SW */
+            void *sem ;
+
+            status = palMutexAllocLocked( hHdd, &sem ) ;
+            if (status != eHAL_STATUS_SUCCESS)
+            {
+                smsLog(pMac, LOGE, FL("mutex alloc failed\n"));
+                pMac->ccm.replay.started = 0 ;
+            }
+            else
+            {
+                pMac->ccm.replay.done = sem ;
+            }
+        }
+    }
+
+    pal_local_bh_enable() ;
+
+    /* Waiting here ... */
+    if (status == eHAL_STATUS_SUCCESS && pMac->ccm.replay.done)
+    {
+#ifdef CCM_DEBUG
+        smsLog(pMac, LOGW, FL("ccmWaitForCompletion(%p)\n"), pMac->ccm.replay.done);
+#endif
+        ccmWaitForCompletion(hHdd, pMac->ccm.replay.done);
+
+#ifdef CCM_DEBUG
+        smsLog(pMac, LOGW, FL("free(%p)\n"), pMac->ccm.replay.done);
+#endif
+        palSemaphoreFree( hHdd, pMac->ccm.replay.done) ;
+    }
+
+    return status ;
+}
+
+#if 0
+///////////////////////////////////////////////////////////////////
+#include <linux/netdevice.h>
+#include <linux/delay.h>
+extern struct net_device * hdd_dev[];
+
+typedef struct pal_netdev_priv_s
+{
+    // pointer to the PCI device structure for this device
+    struct pci_dev  *pci_dev;
+
+    // TAURUS has three BAR registers
+
+    // BAR0 is a fixed window for the PIF registers
+    volatile void *win0_addr;
+    tANI_U32 win0_size;
+
+    // BAR1 is a movable window for all other registers
+    volatile void *win1_addr;
+    tANI_U32 win1_size;
+    tANI_U32 win1_current;
+
+    // BAR2 is a movable window for all other memory
+    volatile void *win2_addr;
+    tANI_U32 win2_size;
+    tANI_U32 win2_current;
+
+
+} pal_netdev_priv_t;
+
+typedef struct hdd_stats_s {
+    /* Stats on the MAC SW messages sent to applications */
+    ulong stats_mac_rx_mbx_tot_cnt;
+    ulong stats_mac_rx_mbx_success_cnt;
+    ulong stats_mac_rx_mbx_drop_cnt;
+
+    /* Stats on messages sent to the MAC SW messages from applications */
+    ulong stats_mac_tx_mbx_tot_cnt;
+    ulong stats_mac_tx_mbx_success_cnt;
+    ulong stats_mac_tx_mbx_drop_cnt;
+} hdd_stats_t;
+
+/* HDD Driver Private Data structure */
+typedef struct hdd_netdev_priv_s
+{
+    tANI_U32 magic_head;
+
+    // chipset-specific private data
+    pal_netdev_priv_t ANI_CHIPSET;
+
+    tHalHandle halHandle;
+
+#ifdef ANI_BUS_TYPE_PCI
+    struct pci_dev  *pci_dev;
+    struct pci_device_id * pPciDevId;
+#endif // ANI_BUS_TYPE_PCI
+
+    // Queued EAPOL frame destination.
+    tANI_U32 eapol_pid;
+
+    unsigned int num_xmit;
+
+    /*
+     * Various frequently used variables that pertain to this
+     * instance of the driver
+     */
+    tANI_U32 rx_buf_sz;           /* Based on MTU+extra headroom needed.*/
+    tANI_U32 td_enqueue_nested;
+
+    /*
+     * Flag set by MAC SW to indicate a TD ring is desired
+     */
+    int td_flush;
+
+    int selectiveFlush;
+
+    spinlock_t lock;
+
+    /* Stats */
+    struct net_device_stats stats;
+    int curr_acc_cat;
+#ifdef LX5280
+    unsigned short rtl_pvid; //VLAN id this Interface belongs to
+    int rtl_extPortNum; //ext port used in RTL865x driver
+    int rtl_linkId[16];//link ID of each interface for RTL865x driver
+    int rtl_wdsActive;
+#endif
+    tANI_U16 lport; /* switch logical port */
+
+    /* management and control */
+    tANI_U32 status;
+    tANI_U32 msg_enable;
+    tANI_U32 radio_id;                  /* Unit # of this device */
+
+    int ap_flag;                        /* 
+                                         * indicates if the Radio is in AP
+                                         *  or BP mode.
+                                         */
+
+    /* NAPI Polling suport */
+    struct timer_list oom_timer;    /* Out of memory timer.    */
+
+    struct timer_list reset_req_timer;/* 
+                                       * Timer started when a Reset
+                                       * request is sent to WSM. Cleared
+                                       * when a subsequent Radio Disable
+                                       * Request is received.
+                                       */
+
+    struct tasklet_struct *rx_tasklet;
+    struct tasklet_struct *tx_tasklet;
+       
+    tANI_U32 learn_mode_frame_cnt;      /*
+                                         * Data Frames forwarded to MAC SW
+                                         * when Polaris is in learn mode 
+                                         */
+
+    tANI_U32 mgmt_ctl_frames;           /* MGMT/CTL Frames forwarded to MAC SW */
+
+    tANI_U32 nir;                       /* total number of times the ISR has
+                                         * been invoked.*/
+    tANI_U32 stats_dummy_pkt_requeue_cnt;
+    tANI_U32 stats_rx_td_dummy_pkt_cnt;/* TD Dummy pkts that were after HIF loopback */
+    tANI_U32 stats_rx_tm_dummy_pkt_cnt;/* TM Dummy pkts that were after HIF loopback */
+    tANI_U32 stats_td_dummy_pkt_cnt;    /* Dummy pkts that were succesfully
+                                         * put on the TD ring and that
+                                         * were picked up by the HIF
+                                         */
+
+    tANI_U32 stats_mac_dummy_pkt_drop_cnt;/* Number of dummy pkts dropped by the HDD
+                                           * due to any reason
+                                           */
+    tANI_U32 stats_wns_l2update_cnt; 
+    tANI_U32 stats_app_hif_wr_pkt_cnt;
+    hdd_stats_t hdd_stats;
+
+    tANI_U32 stats_reset_req_timer_cnt; /*
+                                         * Number of times the 
+                                         * Reset Req Timer expired
+                                         */
+
+#ifdef TCP_PROFILE
+    unsigned int pv_current_ip_proto;
+    unsigned int pv_current_ip_byte;
+    unsigned int pv_current_ack_seq;
+    unsigned int pv_current_seq;
+    unsigned int pv_rtt;
+    unsigned int pv_sent_seq;
+    unsigned int pv_p_ts;
+    unsigned int pv_tfpl_ts;
+#endif
+    tANI_U32 stats_mac_reset_cnt;         /* MAC SW Reset Requests */
+    tANI_U32 stats_mac_reset_eof_sof;
+    tANI_U32 stats_mac_reset_bmu;
+    tANI_U32 stats_mac_reset_pdu_low;
+    tANI_U32 stats_mac_reset_user;
+    tANI_U32 stats_mac_reset_wd_timeout;
+    tANI_U32 stats_mac_reset_unspecified;
+
+    tANI_U32 stats_wd_timeout_cnt;
+    tANI_U32 stats_radio_enable_cnt;
+    tANI_U32 stats_radio_disable_cnt;
+
+#ifdef PLM_EXTRA_STATS
+    tANI_U32 stats_tx_xmit_refilled;         /* Pkts xmit-filled */
+    tANI_U32 stats_tx_queue_stop;
+    tANI_U32 stats_tx_queue_start;
+
+    tANI_U32 stats_alloc_fail;
+    tANI_U32 stats_poll_starts;
+    tANI_U32 stats_poll_pkts;
+    tANI_U32 stats_poll_exit_done;
+    tANI_U32 stats_poll_exit_not_done;
+    tANI_U32 stats_poll_exit_oom;
+    tANI_U32 stats_poll_exit_done_rx_pending;
+    tANI_U32 stats_poll_zero_rx;
+
+#ifdef CONFIG_PROC_FS
+#ifdef ANI_USE_TASKLET
+    struct proc_dir_entry *proc_driver_dir; // for /proc/net/drivers
+#endif
+    struct proc_dir_entry *proc_ent_dir;    // for the directory itself
+
+    struct proc_dir_entry *proc_ent_stats;
+    struct proc_dir_entry *proc_ent_np_dump;
+    struct proc_dir_entry *proc_ent_ring;
+    char proc_fname_stats[32];
+    char proc_fname_np_dump[32];
+    char proc_fname_ring[32];
+
+    /* Setting Debug levels */
+    struct proc_dir_entry * proc_ent_dbg;
+    char proc_fname_dbg[32];
+
+    /* For bypass flags */
+    struct proc_dir_entry * proc_ent_bypass;
+    char proc_fname_bypass[32];
+
+    int sir_dump_cmd;   // Dump SIR command
+    int sir_dump_arg1;  // Dump SIR argument 1
+    int sir_dump_arg2;  // Dump SIR argument 2
+    int sir_dump_arg3;  // Dump SIR argument 3
+    int sir_dump_arg4;  // Dump SIR argument 4
+    struct proc_dir_entry * proc_ent_sir_dump;
+    char proc_fname_sir_dump[32];
+
+    eHalStatus status ;
+    struct proc_dir_entry * proc_ent_eeprom_info;
+    char proc_fname_eeprom_info[32];
+
+#endif  /* ifdef CONFIG_PROC_FS */
+
+    tANI_U32 rx_small_skb_failure;
+
+    unsigned long open_time; /* jiffies for last open */
+#endif /* PLM_EXTRA_STATS */
+
+    int mac_down;
+    tANI_U32 rx_mac_msg_cnt;
+    tANI_U32 tx_mac_msg_cnt;
+
+    int mbx_sent;
+
+    tANI_U32 bypass;                    // Used to various types of bypasses
+                                        // in the driver
+
+    /* 
+     * this table is initialized once for all by poldrv and so is not in 
+     * mac_param struct 
+     */
+    t_mac_block_table * mac_block_table;
+    struct sk_buff_head mac_list;
+#if  defined(ASICDXE_PROFILE) && defined(LX5280)
+    tANI_U32 num_of_reg_switches;
+#endif
+    tANI_U32 magic_tail;
+} hdd_netdev_priv_t;
+
+static void ccm_callback(tHalHandle hHal, tANI_S32 cfgId)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    smsLog(pMac, LOGW, FL("cfgId = %d\n"), cfgId);
+}
+
+static void ccm_callback2(tHalHandle hHal, tANI_S32 result)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    smsLog(pMac, LOGW, FL("result = %d\n"), result);
+}
+
+void ccm_test(void)
+{
+    tHalHandle hHal ;
+    tpAniSirGlobal pMac;
+    eHalStatus status ;
+    struct net_device *dev;
+    hdd_netdev_priv_t *np;
+    char str[80] = {1} ;
+
+    dev  = hdd_dev[0];
+    np = (hdd_netdev_priv_t *)dev->priv;
+    hHal = np->halHandle ;
+    pMac = PMAC_STRUCT( hHal );
+
+    smsLog(pMac, LOGW, "ccmStart()\n");
+    ccmStart(hHal) ;
+
+    status = ccmCfgUpdate(hHal, ccm_callback2) ;
+    smsLog(pMac, LOGW, "ccmCfgUpdate(): status=%d\n", status);
+
+    status = ccmCfgSetInt(hHal, WNI_CFG_FRAGMENTATION_THRESHOLD, 100, ccm_callback, 1) ;
+    smsLog(pMac, LOGW, "ccmCfgSetInt(WNI_CFG_FRAGMENTATION_THRESHOLD = %d): status=%d\n",
+           WNI_CFG_FRAGMENTATION_THRESHOLD, status);
+
+    status = ccmCfgSetInt(hHal, WNI_CFG_RTS_THRESHOLD, 100, ccm_callback, 1) ;
+    smsLog(pMac, LOGW, "ccmCfgSetInt(WNI_CFG_RTS_THRESHOLD = %d): status=%d\n",
+           WNI_CFG_RTS_THRESHOLD, status);
+
+    /* this cfgid causes reload */
+    status = ccmCfgSetInt(hHal, WNI_CFG_MIMO_ENABLED, 1, ccm_callback, 1) ;
+    smsLog(pMac, LOGW, "ccmCfgSetInt(WNI_CFG_MIMO_ENABLED = %d): status=%d\n",
+           WNI_CFG_MIMO_ENABLED, status);
+
+    status = ccmCfgSetInt(hHal, WNI_CFG_SHORT_RETRY_LIMIT, 100, ccm_callback, 1) ;
+    smsLog(pMac, LOGW, "ccmCfgSetInt(WNI_CFG_SHORT_RETRY_LIMIT = %d): status=%d\n",
+           WNI_CFG_SHORT_RETRY_LIMIT, status);
+
+    status = ccmCfgSetInt(hHal, WNI_CFG_LONG_RETRY_LIMIT, 100, ccm_callback, 1) ;
+    smsLog(pMac, LOGW, "ccmCfgSetInt(WNI_CFG_LONG_RETRY_LIMIT = %d): status=%d\n",
+           WNI_CFG_LONG_RETRY_LIMIT, status);
+
+    /* this cfgid causes restart */
+    status = ccmCfgSetStr(hHal, WNI_CFG_EDCA_WME_ACVI, str, sizeof(str), ccm_callback, 1) ;
+    smsLog(pMac, LOGW, "ccmCfgSetStr(WNI_CFG_EDCA_WME_ACVI = %d): status=%d\n",
+           WNI_CFG_EDCA_WME_ACVI, status);
+
+    mdelay(100);
+
+    smsLog(pMac, LOGW, "ccmStop()\n");
+    ccmStop(hHal);
+    status = ccmCfgUpdate(hHal, ccm_callback2) ;
+    smsLog(pMac, LOGW, "ccmCfgUpdate(): status=%d\n", status);
+
+    smsLog(pMac, LOGW, "ccmStart()\n");
+    ccmStart(hHal) ;
+    status = ccmCfgUpdate(hHal, ccm_callback2) ;
+    smsLog(pMac, LOGW, "ccmCfgUpdate(): status=%d\n", status);
+}
+#endif
diff --git a/CORE/SME/src/ccm/ccmLogDump.c b/CORE/SME/src/ccm/ccmLogDump.c
new file mode 100644
index 0000000..975bf68
--- /dev/null
+++ b/CORE/SME/src/ccm/ccmLogDump.c
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/*============================================================================
+ccmLogDump.c
+
+Implements the dump commands specific to the ccm module. 
+
+Copyright (c) 2007 QUALCOMM Incorporated.
+All Rights Reserved.
+Qualcomm Confidential and Proprietary
+ ============================================================================*/
+
+
+#include "aniGlobal.h"
+#include "logDump.h"
+
+#if defined(ANI_LOGDUMP)
+
+static tDumpFuncEntry ccmMenuDumpTable[] = {
+
+   {0,     "CCM (861-870)",                               NULL},
+    //{861,   "CCM: CCM testing ",                         dump_ccm}
+
+};
+
+void ccmDumpInit(tHalHandle hHal)
+{
+   logDumpRegisterTable( (tpAniSirGlobal) hHal, &ccmMenuDumpTable[0], 
+                         sizeof(ccmMenuDumpTable)/sizeof(ccmMenuDumpTable[0]) );
+}
+
+#endif //#if defined(ANI_LOGDUMP)
+
diff --git a/CORE/SME/src/csr/csrApiRoam.c b/CORE/SME/src/csr/csrApiRoam.c
new file mode 100644
index 0000000..e1c81a0
--- /dev/null
+++ b/CORE/SME/src/csr/csrApiRoam.c
@@ -0,0 +1,15084 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+
+  
+    \file csrApiRoam.c
+  
+    Implementation for the Common Roaming interfaces.
+  
+    Copyright (C) 2008 Qualcomm, Incorporated
+  
+ 
+   ========================================================================== */
+
+/*===========================================================================
+
+                      EDIT HISTORY FOR FILE
+
+
+  This section contains comments describing changes made to the module.
+  Notice that changes are listed in reverse chronological order.
+
+
+
+  when            who                 what, where, why
+----------       ---                --------------------------------------------------------
+06/03/10     js                     Added support to hostapd driven 
+ *                                  deauth/disassoc/mic failure
+
+===========================================================================*/
+
+#include "aniGlobal.h" //for tpAniSirGlobal
+#include "wlan_qct_wda.h"
+
+#ifdef FEATURE_WLAN_INTEGRATED_SOC
+#include "halMsgApi.h" //for HAL_STA_INVALID_IDX.
+#endif
+
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halPhyApi.h"
+#include "halInternal.h"
+#endif
+
+#include "palApi.h"
+#include "csrInsideApi.h"
+#include "smsDebug.h"
+#include "logDump.h"
+#include "smeQosInternal.h"
+#include "wlan_qct_tl.h"
+#include "smeInside.h"
+#include "vos_diag_core_event.h"
+#include "vos_diag_core_log.h"
+#include "csrApi.h"
+#include "pmc.h"
+#include "vos_nvitem.h"
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+#include "csrNeighborRoam.h"
+#endif /* WLAN_FEATURE_NEIGHBOR_ROAMING */
+
+#ifdef FEATURE_WLAN_CCX
+#include "csrCcx.h"
+#endif /* FEATURE_WLAN_CCX */
+
+#define CSR_NUM_IBSS_START_CHANNELS_50      4
+#define CSR_NUM_IBSS_START_CHANNELS_24      3
+#define CSR_DEF_IBSS_START_CHANNEL_50       36
+#define CSR_DEF_IBSS_START_CHANNEL_24       1
+#define CSR_IBSS_JOIN_TIMEOUT_PERIOD        ( 1 *  PAL_TIMER_TO_SEC_UNIT )  // 1 second
+#define CSR_WAIT_FOR_KEY_TIMEOUT_PERIOD         ( 50 * PAL_TIMER_TO_SEC_UNIT )  // 50 seconds, for WPA, WPA2, CCKM
+#define CSR_WAIT_FOR_WPS_KEY_TIMEOUT_PERIOD         ( 120 * PAL_TIMER_TO_SEC_UNIT )  // 120 seconds, for WPS
+/*---------------------------------------------------------------------------
+  OBIWAN recommends [8 10]% : pick 9% 
+---------------------------------------------------------------------------*/
+#define CSR_VCC_UL_MAC_LOSS_THRESHOLD 9
+
+/*---------------------------------------------------------------------------
+  OBIWAN recommends -85dBm 
+---------------------------------------------------------------------------*/
+#define CSR_VCC_RSSI_THRESHOLD 80
+#define CSR_MIN_GLOBAL_STAT_QUERY_PERIOD   500 //ms
+#define CSR_MIN_GLOBAL_STAT_QUERY_PERIOD_IN_BMPS 2000 //ms
+#define CSR_MIN_TL_STAT_QUERY_PERIOD       500 //ms
+#define CSR_DIAG_LOG_STAT_PERIOD           3000 //ms
+
+//We use constatnt 4 here
+//This macro returns true when higher AC parameter is bigger than lower AC for a difference
+//The bigger the number, the less chance of TX
+//It must put lower AC as the first parameter.
+#define SME_DETECT_AC_WEIGHT_DIFF(loAC, hiAC)   (v_BOOL_t)(((hiAC) > (loAC)) ? (((hiAC)-(loAC)) > 4) : 0)
+
+//Flag to send/do not send disassoc frame over the air
+#define CSR_DONT_SEND_DISASSOC_OVER_THE_AIR 1
+
+#define RSSI_HACK_BMPS (-40)
+/*-------------------------------------------------------------------------- 
+  Static Type declarations
+  ------------------------------------------------------------------------*/
+static tChannelListWithPower csrRoamPowerTableFromEeprom[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+static tChannelListWithPower csrRoamPowerTableFromEeprom40MHz[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+static tCsrRoamSession       csrRoamRoamSession[CSR_ROAM_SESSION_MAX];
+
+/*-------------------------------------------------------------------------- 
+  Type declarations
+  ------------------------------------------------------------------------*/
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+int diagAuthTypeFromCSRType(eCsrAuthType authType)
+{
+    int n = AUTH_OPEN;
+
+    switch(authType)
+    {
+    case eCSR_AUTH_TYPE_SHARED_KEY:
+        n = AUTH_SHARED;
+        break;
+
+    case eCSR_AUTH_TYPE_WPA:
+        n = AUTH_WPA_EAP;
+        break;
+
+    case eCSR_AUTH_TYPE_WPA_PSK:
+        n = AUTH_WPA_PSK;
+        break;
+
+    case eCSR_AUTH_TYPE_RSN:
+        n = AUTH_WPA2_EAP;
+        break;
+
+    case eCSR_AUTH_TYPE_RSN_PSK:
+        n = AUTH_WPA2_PSK;
+        break;
+#ifdef FEATURE_WLAN_WAPI
+    case eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE:
+        n = AUTH_WAPI_CERT;
+        break;
+
+    case eCSR_AUTH_TYPE_WAPI_WAI_PSK:
+        n = AUTH_WAPI_PSK;
+        break;
+#endif /* FEATURE_WLAN_WAPI */
+
+    default:
+        break;
+    }
+
+    return (n);
+}
+
+int diagEncTypeFromCSRType(eCsrEncryptionType encType)
+{
+    int n = ENC_MODE_OPEN;
+
+    switch(encType)
+    {
+    case eCSR_ENCRYPT_TYPE_WEP40_STATICKEY:
+    case eCSR_ENCRYPT_TYPE_WEP40:
+        n = ENC_MODE_WEP40;
+        break;
+
+    case eCSR_ENCRYPT_TYPE_WEP104_STATICKEY:
+    case eCSR_ENCRYPT_TYPE_WEP104:
+        n = ENC_MODE_WEP104;
+        break;
+
+    case eCSR_ENCRYPT_TYPE_TKIP:
+        n = ENC_MODE_TKIP;
+        break;
+
+    case eCSR_ENCRYPT_TYPE_AES:
+        n = ENC_MODE_AES;
+        break;
+
+#ifdef FEATURE_WLAN_WAPI
+    case eCSR_ENCRYPT_TYPE_WPI:
+        n = ENC_MODE_SMS4;
+        break;
+#endif /* FEATURE_WLAN_WAPI */
+    default:
+        break;
+    }
+
+    return (n);
+}
+
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+static const tANI_U8 csrStartIbssChannels50[ CSR_NUM_IBSS_START_CHANNELS_50 ] = { 36, 40,  44,  48}; 
+static const tANI_U8 csrStartIbssChannels24[ CSR_NUM_IBSS_START_CHANNELS_24 ] = { 1, 6, 11 };
+
+static void initConfigParam(tpAniSirGlobal pMac);
+static tANI_BOOLEAN csrRoamProcessResults( tpAniSirGlobal pMac, tSmeCmd *pCommand,
+                                       eCsrRoamCompleteResult Result, void *Context );
+static eHalStatus csrRoamStartIbss( tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                    tCsrRoamProfile *pProfile, 
+                                    tANI_BOOLEAN *pfSameIbss );
+static void csrRoamUpdateConnectedProfileFromNewBss( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirSmeNewBssInfo *pNewBss );
+static void csrRoamPrepareBssParams(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                                     tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes);
+static tAniCBSecondaryMode csrGetCBModeFromIes(tpAniSirGlobal pMac, tANI_U8 primaryChn, tDot11fBeaconIEs *pIes);
+eHalStatus csrInitGetChannels(tpAniSirGlobal pMac);
+static void csrRoamingStateConfigCnfProcessor( tpAniSirGlobal pMac, tANI_U32 result );
+eHalStatus csrRoamOpen(tpAniSirGlobal pMac);
+eHalStatus csrRoamClose(tpAniSirGlobal pMac);
+void csrRoamMICErrorTimerHandler(void *pv);
+void csrRoamTKIPCounterMeasureTimerHandler(void *pv);
+tANI_BOOLEAN csrRoamIsSameProfileKeys(tpAniSirGlobal pMac, tCsrRoamConnectedProfile *pConnProfile, tCsrRoamProfile *pProfile2);
+ 
+static eHalStatus csrRoamStartRoamingTimer(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 interval);
+static eHalStatus csrRoamStopRoamingTimer(tpAniSirGlobal pMac, tANI_U32 sessionId);
+static void csrRoamRoamingTimerHandler(void *pv);
+eHalStatus csrRoamStartIbssJoinTimer(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 interval);
+eHalStatus csrRoamStopIbssJoinTimer(tpAniSirGlobal pMac, tANI_U32 sessionId);
+static void csrRoamIbssJoinTimerHandler(void *pv);
+eHalStatus csrRoamStartWaitForKeyTimer(tpAniSirGlobal pMac, tANI_U32 interval);
+eHalStatus csrRoamStopWaitForKeyTimer(tpAniSirGlobal pMac);
+static void csrRoamWaitForKeyTimeOutHandler(void *pv);
+ 
+static eHalStatus CsrInit11dInfo(tpAniSirGlobal pMac, tCsr11dinfo *ps11dinfo);
+static eHalStatus csrRoamFreeConnectedInfo( tpAniSirGlobal pMac, tCsrRoamConnectedInfo *pConnectedInfo );
+eHalStatus csrSendMBSetContextReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, 
+           tSirMacAddr peerMacAddr, tANI_U8 numKeys, tAniEdType edType, 
+           tANI_BOOLEAN fUnicast, tAniKeyDirection aniKeyDirection,
+           tANI_U8 keyId, tANI_U8 keyLength, tANI_U8 *pKey, tANI_U8 paeRole, 
+           tANI_U8 *pKeyRsc );
+static eHalStatus csrRoamIssueReassociate( tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                    tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes, 
+                                    tCsrRoamProfile *pProfile );
+void csrRoamStatisticsTimerHandler(void *pv);
+void csrRoamStatsGlobalClassDTimerHandler(void *pv);
+
+static void csrRoamLinkUp(tpAniSirGlobal pMac, tCsrBssid bssid);
+VOS_STATUS csrRoamVccTriggerRssiIndCallback(tHalHandle hHal, 
+                                            v_U8_t  rssiNotification, 
+                                            void * context);
+static void csrRoamLinkDown(tpAniSirGlobal pMac, tANI_U32 sessionId);
+void csrRoamVccTrigger(tpAniSirGlobal pMac);
+eHalStatus csrSendMBStatsReqMsg( tpAniSirGlobal pMac, tANI_U32 statsMask, tANI_U8 staId);
+/*
+    pStaEntry is no longer invalid upon the return of this function.
+*/
+static void csrRoamRemoveStatListEntry(tpAniSirGlobal pMac, tListElem *pEntry);
+
+#ifdef WLAN_SOFTAP_FEATURE
+static eCsrCfgDot11Mode csrRoamGetPhyModeBandForBss( tpAniSirGlobal pMac, tCsrRoamProfile *pProfile,tANI_U8 operationChn, eCsrBand *pBand );
+#else
+static eCsrCfgDot11Mode csrRoamGetPhyModeBandForBss( tpAniSirGlobal pMac, eCsrPhyMode phyModeIn, tANI_U8 operationChn, eCsrBand *pBand );
+#endif
+static eHalStatus csrRoamGetQosInfoFromBss(tpAniSirGlobal pMac, tSirBssDescription *pBssDesc);
+
+
+tCsrStatsClientReqInfo * csrRoamInsertEntryIntoList( tpAniSirGlobal pMac,
+                                                     tDblLinkList *pStaList,
+                                                     tCsrStatsClientReqInfo *pStaEntry);
+void csrRoamStatsClientTimerHandler(void *pv);
+tCsrPeStatsReqInfo *  csrRoamCheckPeStatsReqList(tpAniSirGlobal pMac, tANI_U32  statsMask, 
+                                                 tANI_U32 periodicity, tANI_BOOLEAN *pFound, tANI_U8 staId);
+void csrRoamReportStatistics(tpAniSirGlobal pMac, tANI_U32 statsMask, 
+                             tCsrStatsCallback callback, tANI_U8 staId, void *pContext);
+void csrRoamSaveStatsFromTl(tpAniSirGlobal pMac, WLANTL_TRANSFER_STA_TYPE tlStats);
+void csrRoamTlStatsTimerHandler(void *pv);
+void csrRoamPeStatsTimerHandler(void *pv);
+tListElem * csrRoamCheckClientReqList(tpAniSirGlobal pMac, tANI_U32 statsMask);
+void csrRoamRemoveEntryFromPeStatsReqList(tpAniSirGlobal pMac, tCsrPeStatsReqInfo *pPeStaEntry);
+tListElem * csrRoamFindInPeStatsReqList(tpAniSirGlobal pMac, tANI_U32  statsMask);
+eHalStatus csrRoamDeregStatisticsReq(tpAniSirGlobal pMac);
+static tANI_U32 csrFindIbssSession( tpAniSirGlobal pMac );
+static eHalStatus csrRoamStartWds( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, tSirBssDescription *pBssDesc );
+static void csrInitSession( tpAniSirGlobal pMac, tANI_U32 sessionId );
+static eHalStatus csrRoamIssueSetKeyCommand( tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                             tCsrRoamSetKey *pSetKey, tANI_U32 roamId );
+//static eHalStatus csrRoamProcessStopBss( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+static eHalStatus csrRoamGetQosInfoFromBss(tpAniSirGlobal pMac, tSirBssDescription *pBssDesc);
+void csrRoamReissueRoamCommand(tpAniSirGlobal pMac);
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+void csrRoamJoinRetryTimerHandler(void *pv);
+#endif
+extern void SysProcessMmhMsg(tpAniSirGlobal pMac, tSirMsgQ* pMsg);
+
+extern void btampEstablishLogLinkHdlr(void* pMsg);
+
+static void csrSerDesUnpackDiassocRsp(tANI_U8 *pBuf, tSirSmeDisassocRsp *pRsp);
+
+//Initialize global variables
+static void csrRoamInitGlobals(tpAniSirGlobal pMac)
+{
+    if(pMac)
+    {
+        pMac->roam.powerTableFromEeprom      = csrRoamPowerTableFromEeprom;
+        pMac->roam.powerTableFromEeprom40MHz = csrRoamPowerTableFromEeprom40MHz;
+        pMac->roam.roamSession               = csrRoamRoamSession;
+    }
+    return;
+}
+
+
+static void csrRoamDeInitGlobals(tpAniSirGlobal pMac)
+{
+    if(pMac)
+    {
+        pMac->roam.powerTableFromEeprom      = NULL;
+        pMac->roam.powerTableFromEeprom40MHz = NULL;
+        pMac->roam.roamSession               = NULL;
+    }
+    return;
+}
+
+eHalStatus csrOpen(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    static uNvTables nvTables;
+    VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
+
+    v_REGDOMAIN_t regId;
+    tANI_U32 i;
+    
+    do
+    {
+        /* Initialize CSR Roam Globals */
+        csrRoamInitGlobals(pMac);
+
+        for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+           csrRoamStateChange( pMac, eCSR_ROAMING_STATE_STOP, i);
+
+        initConfigParam(pMac);
+        if(!HAL_STATUS_SUCCESS((status = csrScanOpen(pMac))))
+            break;
+        if(!HAL_STATUS_SUCCESS((status = csrRoamOpen(pMac))))
+            break;
+        pMac->roam.nextRoamId = 1;  //Must not be 0
+        if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &pMac->roam.statsClientReqList)))
+           break;
+        if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &pMac->roam.peStatsReqList)))
+           break;
+        if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &pMac->roam.roamCmdPendingList)))
+           break;
+
+        vosStatus = vos_nv_readDefaultCountryTable( &nvTables );
+        if ( VOS_IS_STATUS_SUCCESS(vosStatus) )
+        {
+            palCopyMemory( pMac->hHdd, pMac->scan.countryCodeDefault, 
+                    nvTables.defaultCountryTable.countryCode, WNI_CFG_COUNTRY_CODE_LEN );
+            status = eHAL_STATUS_SUCCESS;
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL("  fail to get NV_FIELD_IMAGE\n") );
+            //hardcoded for now
+            pMac->scan.countryCodeDefault[0] = 'U';
+            pMac->scan.countryCodeDefault[1] = 'S';
+            pMac->scan.countryCodeDefault[2] = 'I';
+            //status = eHAL_STATUS_SUCCESS;
+        }
+        smsLog( pMac, LOGE, FL(" country Code from nvRam %s\n"), pMac->scan.countryCodeDefault );
+
+        csrGetRegulatoryDomainForCountry(pMac, pMac->scan.countryCodeDefault, &regId);
+
+        WDA_SetRegDomain(pMac, regId);
+        pMac->scan.domainIdDefault = regId;
+        pMac->scan.domainIdCurrent = pMac->scan.domainIdDefault;
+
+        status = palCopyMemory(pMac->hHdd, pMac->scan.countryCodeCurrent, 
+                         pMac->scan.countryCodeDefault, WNI_CFG_COUNTRY_CODE_LEN);
+        status = csrInitGetChannels( pMac );
+
+    }while(0);
+    
+    return (status);
+}
+
+
+#ifdef WLAN_SOFTAP_FEATURE
+eHalStatus csrSetRegInfo(tHalHandle hHal,  tANI_U8 *apCntryCode)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    v_REGDOMAIN_t regId;
+    v_U8_t        cntryCodeLength;
+
+    if(NULL == apCntryCode)
+    {
+       smsLog( pMac, LOGW, FL(" Invalid country Code Pointer\n") );
+       return eHAL_STATUS_FAILURE;
+    }
+
+    smsLog( pMac, LOGW, FL(" country Code %s\n"), apCntryCode );
+
+    /* To get correct Regulatory domain from NV table 
+     * 2 character Country code should be used
+     * 3rd charater is optional for indoor/outdoor setting */
+    cntryCodeLength = strlen(apCntryCode);
+
+    status = csrGetRegulatoryDomainForCountry(pMac, apCntryCode, &regId);
+    if (status != eHAL_STATUS_SUCCESS)
+    {
+        smsLog( pMac, LOGE, FL("  fail to get regId for country Code %s\n"), apCntryCode );
+        return status;
+    }
+
+    status = WDA_SetRegDomain(hHal, regId);
+    if (status != eHAL_STATUS_SUCCESS)
+    {
+        smsLog( pMac, LOGE, FL("  fail to get regId for country Code %s\n"), apCntryCode );
+        return status;
+    }
+
+    pMac->scan.domainIdDefault = regId;
+    pMac->scan.domainIdCurrent = pMac->scan.domainIdDefault;
+
+    /* Clear CC field */
+    palFillMemory( pMac->hHdd,
+                   pMac->scan.countryCodeDefault,
+                   WNI_CFG_COUNTRY_CODE_LEN,
+                   0 );
+    /* Copy 2 or 3 bytes country code */
+    palCopyMemory( pMac->hHdd, pMac->scan.countryCodeDefault, 
+                apCntryCode, cntryCodeLength );
+
+    /* If 2 bytes country code, 3rd byte must be filled with space */
+    if((WNI_CFG_COUNTRY_CODE_LEN - 1) == cntryCodeLength)
+    {
+       palFillMemory( pMac->hHdd,
+                      pMac->scan.countryCodeDefault + 2,
+                      1,
+                      0x20 );
+    }
+
+    status = palCopyMemory(pMac->hHdd, pMac->scan.countryCodeCurrent, 
+                               pMac->scan.countryCodeDefault, WNI_CFG_COUNTRY_CODE_LEN);
+    status = csrInitGetChannels( pMac );
+
+    return status;
+}
+
+eHalStatus csrSetChannels(tHalHandle hHal,  tCsrConfigParam *pParam  )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_U8   index = 0;
+
+    palCopyMemory( pMac->hHdd, pParam->Csr11dinfo.countryCode, 
+                   pMac->scan.countryCodeCurrent, WNI_CFG_COUNTRY_CODE_LEN );
+
+    for ( index = 0; index < pMac->scan.base20MHzChannels.numChannels ; index++)
+    {
+        pParam->Csr11dinfo.Channels.channelList[index] = pMac->scan.base20MHzChannels.channelList[ index ];
+        pParam->Csr11dinfo.ChnPower[index].firstChannel = pMac->scan.base20MHzChannels.channelList[ index ];
+        pParam->Csr11dinfo.ChnPower[index].numChannels = 1;
+        pParam->Csr11dinfo.ChnPower[index].maxtxPower = pMac->scan.defaultPowerTable[index].pwr;
+    }
+    pParam->Csr11dinfo.Channels.numChannels = pMac->scan.base20MHzChannels.numChannels;
+    
+    return status;
+}
+#endif
+
+eHalStatus csrClose(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    
+    csrStop(pMac);
+    csrRoamClose(pMac);
+    csrScanClose(pMac);
+    csrLLClose(&pMac->roam.statsClientReqList);
+    csrLLClose(&pMac->roam.peStatsReqList);
+    csrLLClose(&pMac->roam.roamCmdPendingList);
+
+    /* DeInit Globals */
+    csrRoamDeInitGlobals(pMac);
+
+    return (status);
+} 
+
+eHalStatus csrStart(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 i;
+ 
+    do
+    {
+       //save the global vos context
+        pMac->roam.gVosContext = vos_get_global_context(VOS_MODULE_ID_SME, pMac);
+        for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+           csrRoamStateChange( pMac, eCSR_ROAMING_STATE_IDLE, i );
+
+        status = csrRoamStart(pMac);
+        if(!HAL_STATUS_SUCCESS(status)) break;
+        pMac->scan.f11dInfoApplied = eANI_BOOLEAN_FALSE;
+        status = pmcRegisterPowerSaveCheck(pMac, csrCheckPSReady, pMac);
+        if(!HAL_STATUS_SUCCESS(status)) break;
+        pMac->roam.sPendingCommands = 0;
+        csrScanEnable(pMac);
+#if   defined WLAN_FEATURE_NEIGHBOR_ROAMING
+        status = csrNeighborRoamInit(pMac);
+#endif /* WLAN_FEATURE_NEIGHBOR_ROAMING */
+        pMac->roam.tlStatsReqInfo.numClient = 0;
+        pMac->roam.tlStatsReqInfo.periodicity = 0;
+        pMac->roam.tlStatsReqInfo.timerRunning = FALSE;
+        //init the link quality indication also
+        pMac->roam.vccLinkQuality = eCSR_ROAM_LINK_QUAL_MIN_IND;
+        if(!HAL_STATUS_SUCCESS(status)) 
+        {
+           smsLog(pMac, LOGW, " csrStart: Couldn't Init HO control blk \n");
+           break;
+        }
+    }while(0);
+
+#if defined(ANI_LOGDUMP)
+    csrDumpInit(pMac);
+#endif //#if defined(ANI_LOGDUMP)
+
+    return (status);
+}
+
+
+eHalStatus csrStop(tpAniSirGlobal pMac)
+{
+    tANI_U32 sessionId;
+    tANI_U32 i;
+
+    for(sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; sessionId++)
+    {
+        csrRoamCloseSession(pMac, sessionId, TRUE, NULL, NULL);
+    }
+
+    csrScanDisable(pMac);
+    pMac->scan.fCancelIdleScan = eANI_BOOLEAN_FALSE;
+    pMac->scan.fRestartIdleScan = eANI_BOOLEAN_FALSE;
+
+    csrLLPurge( &pMac->roam.roamCmdPendingList, eANI_BOOLEAN_TRUE );
+    
+#if   defined WLAN_FEATURE_NEIGHBOR_ROAMING
+    csrNeighborRoamClose(pMac);
+#endif
+    csrScanFlushResult(pMac); //Do we want to do this?
+
+    // deregister from PMC since we register during csrStart()
+    // (ignore status since there is nothing we can do if it fails)
+    (void) pmcDeregisterPowerSaveCheck(pMac, csrCheckPSReady);
+
+    //Reset the domain back to the deault
+    pMac->scan.domainIdCurrent = pMac->scan.domainIdDefault;
+    csrResetCountryInformation(pMac, eANI_BOOLEAN_TRUE);
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+       csrRoamStateChange( pMac, eCSR_ROAMING_STATE_STOP ,i );
+       pMac->roam.curSubState[i] = eCSR_ROAM_SUBSTATE_NONE;
+    }
+
+    return (eHAL_STATUS_SUCCESS);
+}
+
+
+eHalStatus csrReady(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    csrScanGetSupportedChannels( pMac );
+    //WNI_CFG_VALID_CHANNEL_LIST should be set by this time
+    //use it to init the background scan list
+    csrInitBGScanChannelList(pMac);
+    /* HDD issues the init scan */
+    csrScanStartResultAgingTimer(pMac);
+
+    //Store the AC weights in TL for later use
+    WLANTL_GetACWeights(pMac->roam.gVosContext, pMac->roam.ucACWeights);
+
+    status = csrInitChannelList( pMac );
+    if ( ! HAL_STATUS_SUCCESS( status ) )
+    {
+       smsLog( pMac, LOGE, "csrInitChannelList failed during csrReady with status=%d\n",
+               status );
+    }
+
+    return (status);
+}
+
+void csrSetDefaultDot11Mode( tpAniSirGlobal pMac )
+{
+    v_U32_t wniDot11mode = 0;
+
+    wniDot11mode = csrTranslateToWNICfgDot11Mode(pMac,pMac->roam.configParam.uCfgDot11Mode);
+    ccmCfgSetInt(pMac, WNI_CFG_DOT11_MODE, wniDot11mode, NULL, eANI_BOOLEAN_FALSE);
+}
+
+void csrSetGlobalCfgs( tpAniSirGlobal pMac )
+{
+    ccmCfgSetInt(pMac, WNI_CFG_FRAGMENTATION_THRESHOLD, csrGetFragThresh(pMac), NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetInt(pMac, WNI_CFG_RTS_THRESHOLD, csrGetRTSThresh(pMac), NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetInt(pMac, WNI_CFG_11D_ENABLED,
+                        ((pMac->roam.configParam.Is11hSupportEnabled) ? pMac->roam.configParam.Is11dSupportEnabled : pMac->roam.configParam.Is11dSupportEnabled), 
+                        NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetInt(pMac, WNI_CFG_11H_ENABLED, pMac->roam.configParam.Is11hSupportEnabled, NULL, eANI_BOOLEAN_FALSE);
+    //Enable channel bonding at init; for 2.4 Ghz we will update this CFG at start BSS or join 
+    ccmCfgSetInt(pMac, WNI_CFG_CHANNEL_BONDING_MODE, WNI_CFG_CHANNEL_BONDING_MODE_ENABLE, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetInt(pMac, WNI_CFG_HEART_BEAT_THRESHOLD, pMac->roam.configParam.HeartbeatThresh24, NULL, eANI_BOOLEAN_FALSE);
+    
+    //Update the operating mode to configured value during initialization,
+    //So that client can advertise full capabilities in Probe request frame.
+    csrSetDefaultDot11Mode( pMac );    
+}
+
+
+eHalStatus csrRoamOpen(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 i;
+    tCsrRoamSession *pSession;
+
+    do
+    {
+        for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+        {
+            pSession = CSR_GET_SESSION( pMac, i );
+            pSession->roamingTimerInfo.pMac = pMac;
+            pSession->roamingTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+        }
+
+        pMac->roam.WaitForKeyTimerInfo.pMac = pMac;
+        pMac->roam.WaitForKeyTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+        status = palTimerAlloc(pMac->hHdd, &pMac->roam.hTimerWaitForKey, csrRoamWaitForKeyTimeOutHandler, 
+                                &pMac->roam.WaitForKeyTimerInfo);
+      if(!HAL_STATUS_SUCCESS(status))
+      {
+        smsLog(pMac, LOGE, FL("cannot allocate memory for WaitForKey time out timer\n"));
+        break;
+      }
+
+      status = palTimerAlloc(pMac->hHdd, &pMac->roam.tlStatsReqInfo.hTlStatsTimer, csrRoamTlStatsTimerHandler, pMac);
+      if(!HAL_STATUS_SUCCESS(status))
+      {
+         smsLog(pMac, LOGE, FL("cannot allocate memory for summary Statistics timer\n"));
+         return eHAL_STATUS_FAILURE;
+      }
+    }while (0);
+
+    return (status);
+}
+
+
+eHalStatus csrRoamClose(tpAniSirGlobal pMac)
+{
+    tANI_U32 sessionId;
+
+    for(sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; sessionId++)
+    {
+        csrRoamCloseSession(pMac, sessionId, TRUE, NULL, NULL);
+    }
+
+    palTimerStop(pMac->hHdd, pMac->roam.hTimerWaitForKey);
+    palTimerFree(pMac->hHdd, pMac->roam.hTimerWaitForKey);
+
+    palTimerStop(pMac->hHdd, pMac->roam.tlStatsReqInfo.hTlStatsTimer);
+    palTimerFree(pMac->hHdd, pMac->roam.tlStatsReqInfo.hTlStatsTimer);
+
+    return (eHAL_STATUS_SUCCESS);
+}
+
+
+eHalStatus csrRoamStart(tpAniSirGlobal pMac)
+{
+    (void)pMac;
+
+    return (eHAL_STATUS_SUCCESS);
+}
+
+
+void csrRoamStop(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+   csrRoamStopRoamingTimer(pMac, sessionId);
+   /* deregister the clients requesting stats from PE/TL & also stop the corresponding timers*/
+   csrRoamDeregStatisticsReq(pMac);
+}
+
+eHalStatus csrRoamGetConnectState(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrConnectState *pState)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+
+    if( pState )
+    {
+        status = eHAL_STATUS_SUCCESS;
+        *pState = pMac->roam.roamSession[sessionId].connectState;
+    }    
+    return (status);
+}
+
+
+
+eHalStatus csrRoamCopyConnectProfile(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamConnectedProfile *pProfile)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tANI_U32 size = 0;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    if(pProfile)
+    {
+        if(pSession->pConnectBssDesc)
+        {
+            do
+            {
+                size = pSession->pConnectBssDesc->length + sizeof(pSession->pConnectBssDesc->length);
+                if(size)
+                {
+                    status = palAllocateMemory(pMac->hHdd, (void **)&pProfile->pBssDesc, size);
+                    if(HAL_STATUS_SUCCESS(status))
+                    {
+                        palCopyMemory(pMac->hHdd, pProfile->pBssDesc, pSession->pConnectBssDesc, size);
+                    }
+                    else
+                        break;
+                }
+                else
+                {
+                    pProfile->pBssDesc = NULL;
+                }
+                pProfile->AuthType = pSession->connectedProfile.AuthType;
+                pProfile->EncryptionType = pSession->connectedProfile.EncryptionType;
+                pProfile->mcEncryptionType = pSession->connectedProfile.mcEncryptionType;
+                pProfile->BSSType = pSession->connectedProfile.BSSType;
+                pProfile->operationChannel = pSession->connectedProfile.operationChannel;
+                pProfile->CBMode = pSession->connectedProfile.CBMode;
+                palCopyMemory(pMac->hHdd, &pProfile->bssid, &pSession->connectedProfile.bssid, sizeof(tCsrBssid));
+                palCopyMemory(pMac->hHdd, &pProfile->SSID, &pSession->connectedProfile.SSID, sizeof(tSirMacSSid));
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                if (pSession->connectedProfile.MDID.mdiePresent)
+                {
+                    pProfile->MDID.mdiePresent = 1;
+                    pProfile->MDID.mobilityDomain = pSession->connectedProfile.MDID.mobilityDomain;
+                }
+                else
+                {
+                    pProfile->MDID.mdiePresent = 0;
+                    pProfile->MDID.mobilityDomain = 0;
+                }
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+                pProfile->isCCXAssoc = pSession->connectedProfile.isCCXAssoc;
+
+                if (csrIsAuthTypeCCX(pSession->connectedProfile.AuthType))
+                {
+                    palCopyMemory( pMac->hHdd, pProfile->ccxCckmInfo.krk, 
+                        pSession->connectedProfile.ccxCckmInfo.krk, CSR_KRK_KEY_LEN );
+                    pProfile->ccxCckmInfo.reassoc_req_num=
+                        pSession->connectedProfile.ccxCckmInfo.reassoc_req_num;
+                    pProfile->ccxCckmInfo.krk_plumbed = 
+                        pSession->connectedProfile.ccxCckmInfo.krk_plumbed;
+                }
+#endif
+            }while(0);
+        }
+    }
+    
+    return (status);
+}
+
+
+
+eHalStatus csrRoamGetConnectProfile(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamConnectedProfile *pProfile)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    
+    if(csrIsConnStateConnected(pMac, sessionId))
+    {
+        if(pProfile)
+        {
+            status = csrRoamCopyConnectProfile(pMac, sessionId, pProfile);
+        }
+    }
+
+    return (status);
+}
+
+eHalStatus csrRoamFreeConnectProfile(tpAniSirGlobal pMac, tCsrRoamConnectedProfile *pProfile)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    
+    if(pProfile->pBssDesc)
+    {
+        palFreeMemory(pMac->hHdd, pProfile->pBssDesc);
+    }
+    palZeroMemory(pMac->hHdd, pProfile, sizeof(tCsrRoamConnectedProfile));
+    pProfile->AuthType = eCSR_AUTH_TYPE_UNKNOWN;
+    return (status);
+}
+
+
+static eHalStatus csrRoamFreeConnectedInfo( tpAniSirGlobal pMac, tCsrRoamConnectedInfo *pConnectedInfo )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    if( pConnectedInfo->pbFrames )
+    {
+        palFreeMemory( pMac->hHdd, pConnectedInfo->pbFrames );
+        pConnectedInfo->pbFrames = NULL;
+    }
+    pConnectedInfo->nBeaconLength = 0;
+    pConnectedInfo->nAssocReqLength = 0;
+    pConnectedInfo->nAssocRspLength = 0;
+    pConnectedInfo->staId = 0;
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    pConnectedInfo->nRICRspLength = 0;
+#endif    
+#ifdef FEATURE_WLAN_CCX
+    pConnectedInfo->nTspecIeLength = 0;
+#endif    
+
+
+    return ( status );
+}
+
+
+    
+                
+void csrReleaseCommandRoam(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    csrReinitRoamCmd(pMac, pCommand);
+    csrReleaseCommand( pMac, pCommand );
+}
+
+
+void csrReleaseCommandScan(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    csrReinitScanCmd(pMac, pCommand);
+    csrReleaseCommand( pMac, pCommand );
+}
+
+
+void csrReleaseCommandWmStatusChange(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    csrReinitWmStatusChangeCmd(pMac, pCommand);
+    csrReleaseCommand( pMac, pCommand );
+}
+
+
+void csrReinitSetKeyCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    palZeroMemory(pMac->hHdd, &pCommand->u.setKeyCmd, sizeof(tSetKeyCmd));
+}
+
+
+void csrReinitRemoveKeyCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    palZeroMemory(pMac->hHdd, &pCommand->u.removeKeyCmd, sizeof(tRemoveKeyCmd));
+}
+
+
+void csrReleaseCommandSetKey(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    csrReinitSetKeyCmd(pMac, pCommand);
+    csrReleaseCommand( pMac, pCommand );
+}
+
+void csrReleaseCommandRemoveKey(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    csrReinitRemoveKeyCmd(pMac, pCommand);
+    csrReleaseCommand( pMac, pCommand );
+}
+
+void csrAbortCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fStopping )
+{
+
+    if( eSmeCsrCommandMask & pCommand->command )
+    {
+        switch (pCommand->command)
+        {
+        case eSmeCommandScan:
+            // We need to inform the requester before droping the scan command
+            smsLog( pMac, LOGW, "%s: Drop scan reason %d callback 0x%X\n", 
+                __FUNCTION__, pCommand->u.scanCmd.reason, (unsigned int)pCommand->u.scanCmd.callback);
+            if (NULL != pCommand->u.scanCmd.callback)
+            {
+                smsLog( pMac, LOGW, "%s callback scan requester\n", __FUNCTION__);
+                csrScanCallCallback(pMac, pCommand, eCSR_SCAN_ABORT);
+            }
+            csrReleaseCommandScan( pMac, pCommand );
+            break;
+
+        case eSmeCommandRoam:
+            csrReleaseCommandRoam( pMac, pCommand );
+            break;
+
+        case eSmeCommandWmStatusChange:
+            csrReleaseCommandWmStatusChange( pMac, pCommand );
+            break;
+
+        case eSmeCommandSetKey:
+            csrReleaseCommandSetKey( pMac, pCommand );
+            break;
+
+        case eSmeCommandRemoveKey:
+            csrReleaseCommandRemoveKey( pMac, pCommand );
+            break;
+
+    default:
+            smsLog( pMac, LOGW, " CSR abort standard command %d\n", pCommand->command );
+            csrReleaseCommand( pMac, pCommand );
+            break;
+        }
+    }
+}
+
+
+
+void csrRoamSubstateChange( tpAniSirGlobal pMac, eCsrRoamSubState NewSubstate, tANI_U32 sessionId)
+{
+    smsLog( pMac, LOG1, "   CSR RoamSubstate: [ %d <== %d ]\n", NewSubstate, pMac->roam.curSubState[sessionId]);
+
+
+    if(pMac->roam.curSubState[sessionId] == NewSubstate)
+    {
+       return;
+                }
+    pMac->roam.curSubState[sessionId] = NewSubstate;
+}
+
+
+eCsrRoamState csrRoamStateChange( tpAniSirGlobal pMac, eCsrRoamState NewRoamState, tANI_U8 sessionId)
+{
+    eCsrRoamState PreviousState;
+          
+    smsLog( pMac, LOG1, "CSR RoamState: [ %d <== %d ]\n", NewRoamState, pMac->roam.curState[sessionId]);
+
+    PreviousState = pMac->roam.curState[sessionId];
+    
+    if ( NewRoamState != pMac->roam.curState[sessionId] ) 
+    {
+        // Whenever we transition OUT of the Roaming state, clear the Roaming substate...
+        if ( CSR_IS_ROAM_JOINING(pMac, sessionId) ) 
+        {
+            csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId );
+        }
+
+        pMac->roam.curState[sessionId] = NewRoamState;
+    }
+    return( PreviousState );
+}
+
+
+void csrAssignRssiForCategory(tpAniSirGlobal pMac, tANI_U8 catOffset)
+{
+    int i;
+
+    if(catOffset)
+    {
+        pMac->roam.configParam.bCatRssiOffset = catOffset;
+        for(i = 0; i < CSR_NUM_RSSI_CAT; i++)
+        {
+            pMac->roam.configParam.RSSICat[CSR_NUM_RSSI_CAT - i - 1] = (int)CSR_BEST_RSSI_VALUE - (int)(i * catOffset);
+        }
+    }
+}
+
+
+static void initConfigParam(tpAniSirGlobal pMac)
+{
+    int i;
+
+    pMac->roam.configParam.agingCount = CSR_AGING_COUNT;
+    pMac->roam.configParam.channelBondingMode24GHz = WNI_CFG_CHANNEL_BONDING_MODE_DISABLE;
+    pMac->roam.configParam.channelBondingMode5GHz = WNI_CFG_CHANNEL_BONDING_MODE_ENABLE;
+    pMac->roam.configParam.phyMode = eCSR_DOT11_MODE_TAURUS;
+    pMac->roam.configParam.eBand = eCSR_BAND_ALL;
+    pMac->roam.configParam.uCfgDot11Mode = eCSR_CFG_DOT11_MODE_TAURUS;
+    pMac->roam.configParam.FragmentationThreshold = eCSR_DOT11_FRAG_THRESH_DEFAULT;
+    pMac->roam.configParam.HeartbeatThresh24 = 40;
+    pMac->roam.configParam.HeartbeatThresh50 = 40;
+    pMac->roam.configParam.Is11dSupportEnabled = eANI_BOOLEAN_FALSE;
+    pMac->roam.configParam.Is11dSupportEnabledOriginal = eANI_BOOLEAN_FALSE;
+    pMac->roam.configParam.Is11eSupportEnabled = eANI_BOOLEAN_TRUE;
+    pMac->roam.configParam.Is11hSupportEnabled = eANI_BOOLEAN_FALSE;
+    pMac->roam.configParam.RTSThreshold = 2346;
+    pMac->roam.configParam.shortSlotTime = eANI_BOOLEAN_TRUE;
+    pMac->roam.configParam.WMMSupportMode = eCsrRoamWmmAuto;
+    pMac->roam.configParam.ProprietaryRatesEnabled = eANI_BOOLEAN_TRUE;
+    pMac->roam.configParam.TxRate = eCSR_TX_RATE_AUTO;
+    pMac->roam.configParam.impsSleepTime = CSR_IDLE_SCAN_NO_PS_INTERVAL;
+    pMac->roam.configParam.scanAgeTimeNCNPS = CSR_SCAN_AGING_TIME_NOT_CONNECT_NO_PS;  
+    pMac->roam.configParam.scanAgeTimeNCPS = CSR_SCAN_AGING_TIME_NOT_CONNECT_W_PS;   
+    pMac->roam.configParam.scanAgeTimeCNPS = CSR_SCAN_AGING_TIME_CONNECT_NO_PS;   
+    pMac->roam.configParam.scanAgeTimeCPS = CSR_SCAN_AGING_TIME_CONNECT_W_PS;   
+    for(i = 0; i < CSR_NUM_RSSI_CAT; i++)
+    {
+        pMac->roam.configParam.BssPreferValue[i] = i;
+    }
+    csrAssignRssiForCategory(pMac, CSR_DEFAULT_RSSI_DB_GAP);
+    pMac->roam.configParam.nRoamingTime = CSR_DEFAULT_ROAMING_TIME;
+    pMac->roam.configParam.fEnforce11dChannels = eANI_BOOLEAN_FALSE;
+    pMac->roam.configParam.fSupplicantCountryCodeHasPriority = eANI_BOOLEAN_FALSE;
+
+    pMac->roam.configParam.fEnforceCountryCodeMatch = eANI_BOOLEAN_FALSE;
+    pMac->roam.configParam.fEnforceDefaultDomain = eANI_BOOLEAN_FALSE;
+    pMac->roam.configParam.nActiveMaxChnTime = CSR_ACTIVE_MAX_CHANNEL_TIME;
+    pMac->roam.configParam.nActiveMinChnTime = CSR_ACTIVE_MIN_CHANNEL_TIME;
+    pMac->roam.configParam.nPassiveMaxChnTime = CSR_PASSIVE_MAX_CHANNEL_TIME;
+    pMac->roam.configParam.nPassiveMinChnTime = CSR_PASSIVE_MIN_CHANNEL_TIME;
+
+    pMac->roam.configParam.IsIdleScanEnabled = TRUE; //enable the idle scan by default
+    pMac->roam.configParam.nTxPowerCap = CSR_MAX_TX_POWER;
+    pMac->roam.configParam.statsReqPeriodicity = CSR_MIN_GLOBAL_STAT_QUERY_PERIOD;
+    pMac->roam.configParam.statsReqPeriodicityInPS = CSR_MIN_GLOBAL_STAT_QUERY_PERIOD_IN_BMPS;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    pMac->roam.configParam.csr11rConfig.IsFTResourceReqSupported = 0;
+#endif
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+    pMac->roam.configParam.neighborRoamConfig.nMaxNeighborRetries = 3;
+    pMac->roam.configParam.neighborRoamConfig.nNeighborLookupRssiThreshold = 120;
+    pMac->roam.configParam.neighborRoamConfig.nNeighborReassocRssiThreshold = 125;
+    pMac->roam.configParam.neighborRoamConfig.nNeighborScanMinChanTime = 20;
+    pMac->roam.configParam.neighborRoamConfig.nNeighborScanMaxChanTime = 40;
+    pMac->roam.configParam.neighborRoamConfig.nNeighborScanTimerPeriod = 200;
+    pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels = 3;
+    pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.channelList[0] = 1;
+    pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.channelList[1] = 6;
+    pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.channelList[2] = 11;
+    pMac->roam.configParam.neighborRoamConfig.nNeighborResultsRefreshPeriod = 20000; //20 seconds
+#endif
+
+    pMac->roam.configParam.addTSWhenACMIsOff = 0;
+    pMac->roam.configParam.fScanTwice = eANI_BOOLEAN_FALSE;
+}
+
+eCsrBand csrGetCurrentBand(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    return pMac->roam.configParam.bandCapability;
+}
+
+eHalStatus csrSetBand(tHalHandle hHal, eCsrBand eBand)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    
+    if (CSR_IS_PHY_MODE_A_ONLY(pMac) &&
+            (eBand == eCSR_BAND_24))
+    {
+        /* DOT11 mode configured to 11a only and received 
+           request to change the band to 2.4 GHz */
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+            "failed to set band cfg80211 = %u, band = %u\n",  
+            pMac->roam.configParam.uCfgDot11Mode, eBand);
+        return eHAL_STATUS_INVALID_PARAMETER;
+    }
+
+    if ((CSR_IS_PHY_MODE_B_ONLY(pMac) ||
+                CSR_IS_PHY_MODE_G_ONLY(pMac)) &&
+            (eBand == eCSR_BAND_5G))
+    {
+        /* DOT11 mode configured to 11b/11g only and received 
+           request to change the band to 5 GHz */
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+            "failed to set band dot11mode = %u, band = %u\n",  
+            pMac->roam.configParam.uCfgDot11Mode, eBand);
+        return eHAL_STATUS_INVALID_PARAMETER;
+    }
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+            "Band changed to %u (0 - ALL, 1 - 2.4 GHZ, 2 - 5GHZ)\n", eBand);
+    pMac->roam.configParam.eBand = eBand; 
+    pMac->roam.configParam.bandCapability = eBand; 
+    csrScanGetSupportedChannels( pMac );
+    status = csrInitGetChannels( pMac );
+    if (eHAL_STATUS_SUCCESS == status)
+        csrInitChannelList( hHal );
+    return status;
+}
+
+eHalStatus csrChangeDefaultConfigParam(tpAniSirGlobal pMac, tCsrConfigParam *pParam)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    if(pParam)
+    {
+        pMac->roam.configParam.WMMSupportMode = pParam->WMMSupportMode;
+        pMac->roam.configParam.Is11eSupportEnabled = pParam->Is11eSupportEnabled;
+        pMac->roam.configParam.FragmentationThreshold = pParam->FragmentationThreshold;
+        pMac->roam.configParam.Is11dSupportEnabled = pParam->Is11dSupportEnabled;
+        pMac->roam.configParam.Is11dSupportEnabledOriginal = pParam->Is11dSupportEnabled;
+        pMac->roam.configParam.Is11hSupportEnabled = pParam->Is11hSupportEnabled;
+
+        pMac->roam.configParam.fenableMCCMode = pParam->fEnableMCCMode;
+        pMac->roam.configParam.channelBondingMode24GHz = pParam->channelBondingMode24GHz;
+        pMac->roam.configParam.channelBondingMode5GHz = pParam->channelBondingMode5GHz;
+        pMac->roam.configParam.RTSThreshold = pParam->RTSThreshold;
+        pMac->roam.configParam.phyMode = pParam->phyMode;
+        pMac->roam.configParam.shortSlotTime = pParam->shortSlotTime;
+        pMac->roam.configParam.HeartbeatThresh24 = pParam->HeartbeatThresh24;
+        pMac->roam.configParam.HeartbeatThresh50 = pParam->HeartbeatThresh50;
+        pMac->roam.configParam.ProprietaryRatesEnabled = pParam->ProprietaryRatesEnabled;
+        pMac->roam.configParam.TxRate = pParam->TxRate;
+        pMac->roam.configParam.AdHocChannel24 = pParam->AdHocChannel24;
+        pMac->roam.configParam.AdHocChannel5G = pParam->AdHocChannel5G;
+        pMac->roam.configParam.bandCapability = pParam->bandCapability;
+        pMac->roam.configParam.cbChoice = pParam->cbChoice;
+        pMac->roam.configParam.bgScanInterval = pParam->bgScanInterval;
+
+        //if HDD passed down non zero values then only update,
+        //otherwise keep using the defaults
+        if(pParam->nActiveMaxChnTime)
+        {
+            pMac->roam.configParam.nActiveMaxChnTime = pParam->nActiveMaxChnTime;
+        }
+        if(pParam->nActiveMinChnTime)
+        {
+            pMac->roam.configParam.nActiveMinChnTime = pParam->nActiveMinChnTime;
+        }
+        if(pParam->nPassiveMaxChnTime)
+        {
+            pMac->roam.configParam.nPassiveMaxChnTime = pParam->nPassiveMaxChnTime;
+        }
+        if(pParam->nPassiveMinChnTime)
+        {
+            pMac->roam.configParam.nPassiveMinChnTime = pParam->nPassiveMinChnTime;
+        }
+        //if upper layer wants to disable idle scan altogether set it to 0
+        if(pParam->impsSleepTime)
+        {
+            //Change the unit from second to microsecond
+            tANI_U32 impsSleepTime = pParam->impsSleepTime * PAL_TIMER_TO_SEC_UNIT;
+
+            if(CSR_IDLE_SCAN_NO_PS_INTERVAL_MIN <= impsSleepTime)
+            {
+                pMac->roam.configParam.impsSleepTime = impsSleepTime;
+            }
+        else
+        {
+            pMac->roam.configParam.impsSleepTime = CSR_IDLE_SCAN_NO_PS_INTERVAL;
+        }
+        }
+        else
+        {
+            pMac->roam.configParam.impsSleepTime = 0;
+        }
+        pMac->roam.configParam.eBand = pParam->eBand;
+#ifdef WLAN_SOFTAP_FEATURE
+        pMac->roam.configParam.uCfgDot11Mode = csrGetCfgDot11ModeFromCsrPhyMode(NULL, pMac->roam.configParam.phyMode, 
+                                                    pMac->roam.configParam.ProprietaryRatesEnabled);
+#else
+        pMac->roam.configParam.uCfgDot11Mode = csrGetCfgDot11ModeFromCsrPhyMode(pMac->roam.configParam.phyMode, 
+                                                    pMac->roam.configParam.ProprietaryRatesEnabled);
+#endif
+        //if HDD passed down non zero values for age params, then only update,
+        //otherwise keep using the defaults
+        if(pParam->nScanResultAgeCount)
+        {
+            pMac->roam.configParam.agingCount = pParam->nScanResultAgeCount;
+        }
+
+        if(pParam->scanAgeTimeNCNPS)
+        {
+            pMac->roam.configParam.scanAgeTimeNCNPS = pParam->scanAgeTimeNCNPS;  
+        }
+
+        if(pParam->scanAgeTimeNCPS)
+        {
+            pMac->roam.configParam.scanAgeTimeNCPS = pParam->scanAgeTimeNCPS;   
+        }
+
+        if(pParam->scanAgeTimeCNPS)
+        {
+            pMac->roam.configParam.scanAgeTimeCNPS = pParam->scanAgeTimeCNPS;   
+        }
+        if(pParam->scanAgeTimeCPS)
+        {
+            pMac->roam.configParam.scanAgeTimeCPS = pParam->scanAgeTimeCPS;   
+        }
+        
+        csrAssignRssiForCategory(pMac, pParam->bCatRssiOffset);
+        pMac->roam.configParam.nRoamingTime = pParam->nRoamingTime;
+        pMac->roam.configParam.fEnforce11dChannels = pParam->fEnforce11dChannels;
+        pMac->roam.configParam.fSupplicantCountryCodeHasPriority = pParam->fSupplicantCountryCodeHasPriority;
+        pMac->roam.configParam.fEnforceCountryCodeMatch = pParam->fEnforceCountryCodeMatch;
+        pMac->roam.configParam.fEnforceDefaultDomain = pParam->fEnforceDefaultDomain;
+
+        pMac->roam.configParam.vccRssiThreshold = pParam->vccRssiThreshold;
+        pMac->roam.configParam.vccUlMacLossThreshold = pParam->vccUlMacLossThreshold;
+
+        pMac->roam.configParam.IsIdleScanEnabled = pParam->IsIdleScanEnabled;
+        pMac->roam.configParam.statsReqPeriodicity = pParam->statsReqPeriodicity;
+        pMac->roam.configParam.statsReqPeriodicityInPS = pParam->statsReqPeriodicityInPS;
+        //Assign this before calling CsrInit11dInfo
+        pMac->roam.configParam.nTxPowerCap = pParam->nTxPowerCap;
+
+        if( csrIs11dSupported( pMac ) )
+        {
+            status = CsrInit11dInfo(pMac, &pParam->Csr11dinfo);
+        }
+        else
+        {
+            pMac->scan.curScanType = eSIR_ACTIVE_SCAN;
+        }
+#ifdef WLAN_FEATURE_VOWIFI_11R 
+        palCopyMemory( pMac->hHdd, &pMac->roam.configParam.csr11rConfig, &pParam->csr11rConfig, sizeof(tCsr11rConfigParams) );
+        smsLog( pMac, LOG1, "IsFTResourceReqSupp = %d\n", pMac->roam.configParam.csr11rConfig.IsFTResourceReqSupported); 
+#endif
+
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+        pMac->roam.configParam.isFastTransitionEnabled = pParam->isFastTransitionEnabled;
+#endif
+
+#ifdef FEATURE_WLAN_CCX 
+        pMac->roam.configParam.isCcxIniFeatureEnabled = pParam->isCcxIniFeatureEnabled;
+#endif
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+        palCopyMemory( pMac->hHdd, &pMac->roam.configParam.neighborRoamConfig, &pParam->neighborRoamConfig, sizeof(tCsrNeighborRoamConfigParams) );
+
+        smsLog( pMac, LOG1, "nNeighborScanTimerPerioid = %d\n", pMac->roam.configParam.neighborRoamConfig.nNeighborScanTimerPeriod);
+        smsLog( pMac, LOG1, "nNeighborReassocRssiThreshold = %d\n", pMac->roam.configParam.neighborRoamConfig.nNeighborReassocRssiThreshold);  
+        smsLog( pMac, LOG1, "nNeighborLookupRssiThreshold = %d\n", pMac->roam.configParam.neighborRoamConfig.nNeighborLookupRssiThreshold);  
+        smsLog( pMac, LOG1, "nNeighborScanMinChanTime = %d\n", pMac->roam.configParam.neighborRoamConfig.nNeighborScanMinChanTime); 
+        smsLog( pMac, LOG1, "nNeighborScanMaxChanTime = %d\n", pMac->roam.configParam.neighborRoamConfig.nNeighborScanMaxChanTime);
+        smsLog( pMac, LOG1, "nMaxNeighborRetries = %d\n", pMac->roam.configParam.neighborRoamConfig.nMaxNeighborRetries); 
+        smsLog( pMac, LOG1, "nNeighborResultsRefreshPeriod = %d\n", pMac->roam.configParam.neighborRoamConfig.nNeighborResultsRefreshPeriod); 
+
+        {
+           int i;
+           smsLog( pMac, LOG1, FL("Num of Channels in CFG Channel List: %d\n"), pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels); 
+
+           for( i=0; i< pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels; i++)
+           {
+              smsLog( pMac, LOG1, "%d ", pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.channelList[i] );
+           }
+           smsLog( pMac, LOG1, "\n");
+        }
+#endif
+
+        pMac->roam.configParam.addTSWhenACMIsOff = pParam->addTSWhenACMIsOff;
+        pMac->scan.fValidateList = pParam->fValidateList;
+        pMac->scan.fEnableBypass11d = pParam->fEnableBypass11d;
+        pMac->scan.fEnableDFSChnlScan = pParam->fEnableDFSChnlScan;
+        pMac->roam.configParam.fScanTwice = pParam->fScanTwice;
+    }
+    
+    return status;
+}
+
+
+eHalStatus csrGetConfigParam(tpAniSirGlobal pMac, tCsrConfigParam *pParam)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+
+    if(pParam)
+    {
+        pParam->WMMSupportMode = pMac->roam.configParam.WMMSupportMode;
+        pParam->Is11eSupportEnabled = pMac->roam.configParam.Is11eSupportEnabled;
+        pParam->FragmentationThreshold = pMac->roam.configParam.FragmentationThreshold;
+        pParam->Is11dSupportEnabled = pMac->roam.configParam.Is11dSupportEnabled;
+        pParam->Is11dSupportEnabledOriginal = pMac->roam.configParam.Is11dSupportEnabledOriginal;
+        pParam->Is11hSupportEnabled = pMac->roam.configParam.Is11hSupportEnabled;
+        pParam->channelBondingMode24GHz = pMac->roam.configParam.channelBondingMode24GHz;
+        pParam->channelBondingMode5GHz = pMac->roam.configParam.channelBondingMode5GHz;
+        pParam->RTSThreshold = pMac->roam.configParam.RTSThreshold;
+        pParam->phyMode = pMac->roam.configParam.phyMode;
+        pParam->shortSlotTime = pMac->roam.configParam.shortSlotTime;
+        pParam->HeartbeatThresh24 = pMac->roam.configParam.HeartbeatThresh24;
+        pParam->HeartbeatThresh50 = pMac->roam.configParam.HeartbeatThresh50;
+        pParam->ProprietaryRatesEnabled = pMac->roam.configParam.ProprietaryRatesEnabled;
+        pParam->TxRate = pMac->roam.configParam.TxRate;
+        pParam->AdHocChannel24 = pMac->roam.configParam.AdHocChannel24;
+        pParam->AdHocChannel5G = pMac->roam.configParam.AdHocChannel5G;
+        pParam->bandCapability = pMac->roam.configParam.bandCapability;
+        pParam->cbChoice = pMac->roam.configParam.cbChoice;
+        pParam->bgScanInterval = pMac->roam.configParam.bgScanInterval;
+
+        pParam->nActiveMaxChnTime = pMac->roam.configParam.nActiveMaxChnTime;
+        pParam->nActiveMinChnTime = pMac->roam.configParam.nActiveMinChnTime;
+        pParam->nPassiveMaxChnTime = pMac->roam.configParam.nPassiveMaxChnTime;
+        pParam->nPassiveMinChnTime = pMac->roam.configParam.nPassiveMinChnTime;
+
+        //Change the unit from microsecond to second
+        pParam->impsSleepTime = pMac->roam.configParam.impsSleepTime / PAL_TIMER_TO_SEC_UNIT;
+        pParam->eBand = pMac->roam.configParam.eBand;
+        pParam->nScanResultAgeCount = pMac->roam.configParam.agingCount;
+        pParam->scanAgeTimeNCNPS = pMac->roam.configParam.scanAgeTimeNCNPS;  
+        pParam->scanAgeTimeNCPS = pMac->roam.configParam.scanAgeTimeNCPS;   
+        pParam->scanAgeTimeCNPS = pMac->roam.configParam.scanAgeTimeCNPS;   
+        pParam->scanAgeTimeCPS = pMac->roam.configParam.scanAgeTimeCPS;   
+        pParam->bCatRssiOffset = pMac->roam.configParam.bCatRssiOffset;
+        pParam->nRoamingTime = pMac->roam.configParam.nRoamingTime;
+        pParam->fEnforce11dChannels = pMac->roam.configParam.fEnforce11dChannels;
+        pParam->fSupplicantCountryCodeHasPriority = pMac->roam.configParam.fSupplicantCountryCodeHasPriority;
+        pParam->fEnforceCountryCodeMatch = pMac->roam.configParam.fEnforceCountryCodeMatch;
+        pParam->fEnforceDefaultDomain = pMac->roam.configParam.fEnforceDefaultDomain;        
+        pParam->vccRssiThreshold = pMac->roam.configParam.vccRssiThreshold;
+        pParam->vccUlMacLossThreshold = pMac->roam.configParam.vccUlMacLossThreshold;
+
+        pParam->IsIdleScanEnabled = pMac->roam.configParam.IsIdleScanEnabled;
+        pParam->nTxPowerCap = pMac->roam.configParam.nTxPowerCap;
+        pParam->statsReqPeriodicity = pMac->roam.configParam.statsReqPeriodicity;
+        pParam->statsReqPeriodicityInPS = pMac->roam.configParam.statsReqPeriodicityInPS;
+
+        pParam->addTSWhenACMIsOff = pMac->roam.configParam.addTSWhenACMIsOff;
+        pParam->fValidateList = pMac->roam.configParam.fValidateList;
+        pParam->fEnableBypass11d = pMac->scan.fEnableBypass11d;
+        pParam->fEnableDFSChnlScan = pMac->scan.fEnableDFSChnlScan;
+        pParam->fScanTwice = pMac->roam.configParam.fScanTwice;
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+        palCopyMemory( pMac->hHdd, &pParam->neighborRoamConfig, &pMac->roam.configParam.neighborRoamConfig, sizeof(tCsrNeighborRoamConfigParams) );
+#endif
+
+        csrSetChannels(pMac, pParam);
+
+        status = eHAL_STATUS_SUCCESS;
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrSetPhyMode(tHalHandle hHal, tANI_U32 phyMode, eCsrBand eBand, tANI_BOOLEAN *pfRestartNeeded)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fRestartNeeded = eANI_BOOLEAN_FALSE;
+    eCsrPhyMode newPhyMode = eCSR_DOT11_MODE_AUTO;
+
+    do
+    {
+        if(eCSR_BAND_24 == eBand)
+        {
+            if(CSR_IS_RADIO_A_ONLY(pMac)) break;
+            if((eCSR_DOT11_MODE_11a & phyMode) || (eCSR_DOT11_MODE_11a_ONLY & phyMode)) break;
+        }
+        if(eCSR_BAND_5G == eBand)
+        {
+            if(CSR_IS_RADIO_BG_ONLY(pMac)) break;
+            if((eCSR_DOT11_MODE_11b & phyMode) || (eCSR_DOT11_MODE_11b_ONLY & phyMode) ||
+                (eCSR_DOT11_MODE_11g & phyMode) || (eCSR_DOT11_MODE_11g_ONLY & phyMode) 
+                ) 
+            {
+                break;
+            }
+        }
+        if((0 == phyMode) || (eCSR_DOT11_MODE_TAURUS & phyMode))
+        {
+            newPhyMode = eCSR_DOT11_MODE_TAURUS;
+        }
+        else if(eCSR_DOT11_MODE_AUTO & phyMode)
+        {
+            newPhyMode = eCSR_DOT11_MODE_AUTO;
+        }
+        else
+        {
+            //Check for dual band and higher capability first
+            if(eCSR_DOT11_MODE_11n_ONLY & phyMode)
+            {
+                if(eCSR_DOT11_MODE_11n_ONLY != phyMode) break;
+                newPhyMode = eCSR_DOT11_MODE_11n_ONLY;
+            }
+            else if(eCSR_DOT11_MODE_11a_ONLY & phyMode)
+            {
+                if(eCSR_DOT11_MODE_11a_ONLY != phyMode) break;
+                if(eCSR_BAND_24 == eBand) break;
+                newPhyMode = eCSR_DOT11_MODE_11a_ONLY;
+                eBand = eCSR_BAND_5G;
+            }
+            else if(eCSR_DOT11_MODE_11g_ONLY & phyMode)
+            {
+                if(eCSR_DOT11_MODE_11g_ONLY != phyMode) break;
+                if(eCSR_BAND_5G == eBand) break;
+                newPhyMode = eCSR_DOT11_MODE_11g_ONLY;
+                eBand = eCSR_BAND_24;
+            }
+            else if(eCSR_DOT11_MODE_11b_ONLY & phyMode)
+            {
+                if(eCSR_DOT11_MODE_11b_ONLY != phyMode) break;
+                if(eCSR_BAND_5G == eBand) break;
+                newPhyMode = eCSR_DOT11_MODE_11b_ONLY;
+                eBand = eCSR_BAND_24;
+            }
+            else if(eCSR_DOT11_MODE_11n & phyMode)
+            {
+                newPhyMode = eCSR_DOT11_MODE_11n;
+            }
+            else if(eCSR_DOT11_MODE_abg & phyMode)
+            {
+                newPhyMode = eCSR_DOT11_MODE_abg;
+            }
+            else if(eCSR_DOT11_MODE_11a & phyMode)
+            {
+                if((eCSR_DOT11_MODE_11g & phyMode) || (eCSR_DOT11_MODE_11b & phyMode))
+                {
+                    if(eCSR_BAND_ALL == eBand)
+                    {
+                        newPhyMode = eCSR_DOT11_MODE_abg;
+                    }
+                    else
+                    {
+                        //bad setting
+                        break;
+                    }
+                }
+                else
+                {
+                    newPhyMode = eCSR_DOT11_MODE_11a;
+                    eBand = eCSR_BAND_5G;
+                }
+            }
+            else if(eCSR_DOT11_MODE_11g & phyMode)
+            {
+                newPhyMode = eCSR_DOT11_MODE_11g;
+                eBand = eCSR_BAND_24;
+            }
+            else if(eCSR_DOT11_MODE_11b & phyMode)
+            {
+                newPhyMode = eCSR_DOT11_MODE_11b;
+                eBand = eCSR_BAND_24;
+            }
+            else
+            {
+                //We will never be here
+                smsLog( pMac, LOGE, FL(" cannot recognize the phy mode 0x%08X\n"), phyMode );
+                newPhyMode = eCSR_DOT11_MODE_AUTO;
+            }
+        }
+
+        //Done validating
+        status = eHAL_STATUS_SUCCESS;
+
+        //Now we need to check whether a restart is needed.
+        if(eBand != pMac->roam.configParam.eBand)
+        {
+            fRestartNeeded = eANI_BOOLEAN_TRUE;
+            break;
+        }
+        if(newPhyMode != pMac->roam.configParam.phyMode)
+        {
+            fRestartNeeded = eANI_BOOLEAN_TRUE;
+            break;
+        }
+
+    }while(0);
+
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        pMac->roam.configParam.eBand = eBand;
+        pMac->roam.configParam.phyMode = newPhyMode;
+        if(pfRestartNeeded)
+        {
+            *pfRestartNeeded = fRestartNeeded;
+        }
+    }
+
+    return (status);
+}
+    
+
+void csrPruneChannelListForMode( tpAniSirGlobal pMac, tCsrChannel *pChannelList )
+{
+    tANI_U8 Index;
+    tANI_U8 cChannels;
+
+    // for dual band NICs, don't need to trim the channel list....
+    if ( !CSR_IS_OPEARTING_DUAL_BAND( pMac ) )
+    {
+        // 2.4 GHz band operation requires the channel list to be trimmed to
+        // the 2.4 GHz channels only...
+        if ( CSR_IS_24_BAND_ONLY( pMac ) )
+        {
+            for( Index = 0, cChannels = 0; Index < pChannelList->numChannels;
+                 Index++ )
+            {
+                if ( CSR_IS_CHANNEL_24GHZ(pChannelList->channelList[ Index ]) )
+                {
+                    pChannelList->channelList[ cChannels ] = pChannelList->channelList[ Index ];
+                    cChannels++;
+                }
+            }
+
+            // Cleanup the rest of channels.   Note we only need to clean up the channels if we had
+            // to trim the list.  Calling palZeroMemory() with a 0 size is going to throw asserts on 
+            // the debug builds so let's be a bit smarter about that.  Zero out the reset of the channels
+            // only if we need to.
+            //
+            // The amount of memory to clear is the number of channesl that we trimmed 
+            // (pChannelList->numChannels - cChannels) times the size of a channel in the structure.
+           
+            if ( pChannelList->numChannels > cChannels )
+            {
+                palZeroMemory( pMac->hHdd, &pChannelList->channelList[ cChannels ],
+                               sizeof( pChannelList->channelList[ 0 ] ) * ( pChannelList->numChannels - cChannels ) );
+                
+            }
+            
+            pChannelList->numChannels = cChannels;
+        }
+        else if ( CSR_IS_5G_BAND_ONLY( pMac ) )
+        {
+            for ( Index = 0, cChannels = 0; Index < pChannelList->numChannels; Index++ )
+            {
+                if ( CSR_IS_CHANNEL_5GHZ(pChannelList->channelList[ Index ]) )
+                {
+                    pChannelList->channelList[ cChannels ] = pChannelList->channelList[ Index ];
+                    cChannels++;
+                }
+            }
+
+            // Cleanup the rest of channels.   Note we only need to clean up the channels if we had
+            // to trim the list.  Calling palZeroMemory() with a 0 size is going to throw asserts on 
+            // the debug builds so let's be a bit smarter about that.  Zero out the reset of the channels
+            // only if we need to.
+            //
+            // The amount of memory to clear is the number of channesl that we trimmed 
+            // (pChannelList->numChannels - cChannels) times the size of a channel in the structure.
+            if ( pChannelList->numChannels > cChannels )
+            {
+                palZeroMemory( pMac->hHdd, &pChannelList->channelList[ cChannels ],
+                               sizeof( pChannelList->channelList[ 0 ] ) * ( pChannelList->numChannels - cChannels ) );
+            }            
+                               
+            pChannelList->numChannels = cChannels;
+        }
+    }
+
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+#define INFRA_AP_DEFAULT_CHANNEL 6
+eHalStatus csrIsValidChannel(tpAniSirGlobal pMac, tANI_U8 chnNum)
+{
+    tANI_U8 index= 0;
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    for (index=0; index < pMac->scan.base20MHzChannels.numChannels ;index++)
+    {
+        if(pMac->scan.base20MHzChannels.channelList[ index ] == chnNum){
+            status = eHAL_STATUS_SUCCESS;
+            break;
+        }
+    }
+    return status;
+}
+#endif
+
+eHalStatus csrInitGetChannels(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U8 num20MHzChannelsFound = 0;
+    VOS_STATUS vosStatus;
+    tANI_U8 Index = 0;
+    tANI_U8 num40MHzChannelsFound = 0;
+
+    
+    //TODO: this interface changed to include the 40MHz channel list
+    // this needs to be tied into the adapter structure somehow and referenced appropriately for CB operation
+    // Read the scan channel list (including the power limit) from EEPROM
+    vosStatus = vos_nv_getChannelListWithPower( pMac->scan.defaultPowerTable, &num20MHzChannelsFound, 
+                        pMac->scan.defaultPowerTable40MHz, &num40MHzChannelsFound);
+    if ( (VOS_STATUS_SUCCESS != vosStatus) || (num20MHzChannelsFound == 0) )
+    {
+        smsLog( pMac, LOGE, FL("failed to get channels \n"));
+        status = eHAL_STATUS_FAILURE;
+    }
+    else
+    {
+        if ( num20MHzChannelsFound > WNI_CFG_VALID_CHANNEL_LIST_LEN )
+        {
+            num20MHzChannelsFound = WNI_CFG_VALID_CHANNEL_LIST_LEN;
+        }
+        pMac->scan.numChannelsDefault = num20MHzChannelsFound;
+        // Move the channel list to the global data
+        // structure -- this will be used as the scan list
+        for ( Index = 0; Index < num20MHzChannelsFound; Index++)
+        {
+#ifdef FEATURE_WLAN_INTEGRATED_SOC /* Need to fix this while dealing with NV item */
+            pMac->scan.base20MHzChannels.channelList[ Index ] = pMac->scan.defaultPowerTable[ Index ].chanId;
+#else
+           pMac->scan.base20MHzChannels.channelList[ Index ] = Index + 1;
+           pMac->scan.defaultPowerTable[Index].chanId = Index + 1;
+           pMac->scan.defaultPowerTable[Index].pwr = 25;
+#endif
+        }
+        pMac->scan.base20MHzChannels.numChannels = num20MHzChannelsFound;
+        if(num40MHzChannelsFound > WNI_CFG_VALID_CHANNEL_LIST_LEN)
+        {
+            num40MHzChannelsFound = WNI_CFG_VALID_CHANNEL_LIST_LEN;
+        }
+        for ( Index = 0; Index < num40MHzChannelsFound; Index++)
+        {
+            pMac->scan.base40MHzChannels.channelList[ Index ] = pMac->scan.defaultPowerTable40MHz[ Index ].chanId;
+        }
+        pMac->scan.base40MHzChannels.numChannels = num40MHzChannelsFound;
+    }
+
+    return (status);  
+}
+
+
+eHalStatus csrInitChannelList( tHalHandle hHal )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    csrPruneChannelListForMode(pMac, &pMac->scan.baseChannels);
+    csrPruneChannelListForMode(pMac, &pMac->scan.base20MHzChannels);
+    // Apply the base channel list, power info, and set the Country code...
+    csrApplyChannelPowerCountryInfo( pMac, &pMac->scan.base20MHzChannels, pMac->scan.countryCodeCurrent );
+ 
+    return (status);
+}
+
+
+eHalStatus csrChangeConfigParams(tpAniSirGlobal pMac, 
+                                 tCsrUpdateConfigParam *pUpdateConfigParam)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tCsr11dinfo *ps11dinfo = NULL;
+
+   ps11dinfo = &pUpdateConfigParam->Csr11dinfo;
+   status = CsrInit11dInfo(pMac, ps11dinfo);
+   return status;
+}
+
+
+static eHalStatus CsrInit11dInfo(tpAniSirGlobal pMac, tCsr11dinfo *ps11dinfo)
+{
+  eHalStatus status = eHAL_STATUS_FAILURE;
+  tANI_U8  index;
+  tANI_U32 count=0;
+  tSirMacChanInfo *pChanInfo;
+  tSirMacChanInfo *pChanInfoStart;
+  tANI_BOOLEAN applyConfig = TRUE;
+
+  if(!ps11dinfo)
+  {
+     return (status);
+  }
+
+  if ( ps11dinfo->Channels.numChannels && ( WNI_CFG_VALID_CHANNEL_LIST_LEN >= ps11dinfo->Channels.numChannels ) ) 
+  {
+    pMac->scan.base20MHzChannels.numChannels = ps11dinfo->Channels.numChannels;
+    status = palCopyMemory(pMac->hHdd, pMac->scan.base20MHzChannels.channelList, 
+                           ps11dinfo->Channels.channelList, ps11dinfo->Channels.numChannels);
+    if(!HAL_STATUS_SUCCESS(status)) return (status);
+  }
+  else
+  {
+     //No change
+     return (eHAL_STATUS_SUCCESS);
+  }
+
+  //legacy maintenance
+  status = palCopyMemory(pMac->hHdd, pMac->scan.countryCodeDefault, 
+                         ps11dinfo->countryCode, WNI_CFG_COUNTRY_CODE_LEN);
+  if(!HAL_STATUS_SUCCESS(status)) return (status);
+
+  //Tush: at csropen get this initialized with default, during csr reset if this 
+  // already set with some value no need initilaize with default again
+  if(0 == pMac->scan.countryCodeCurrent[0])
+  {
+     status = palCopyMemory(pMac->hHdd, pMac->scan.countryCodeCurrent, 
+                         ps11dinfo->countryCode, WNI_CFG_COUNTRY_CODE_LEN);
+     if(!HAL_STATUS_SUCCESS(status)) return (status);
+  }
+
+  // need to add the max power channel list
+  if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, (void **)&pChanInfo, sizeof(tSirMacChanInfo) * WNI_CFG_VALID_CHANNEL_LIST_LEN)))
+  {
+      palZeroMemory(pMac->hHdd, pChanInfo, sizeof(tSirMacChanInfo) * WNI_CFG_VALID_CHANNEL_LIST_LEN);
+      pChanInfoStart = pChanInfo;
+
+      for(index = 0; index < ps11dinfo->Channels.numChannels; index++)
+      {
+        pChanInfo->firstChanNum = ps11dinfo->ChnPower[index].firstChannel;
+        pChanInfo->numChannels  = ps11dinfo->ChnPower[index].numChannels;
+        pChanInfo->maxTxPower   = CSR_ROAM_MIN( ps11dinfo->ChnPower[index].maxtxPower, pMac->roam.configParam.nTxPowerCap );
+        pChanInfo++;
+        count++;
+      }
+      if(count)
+      {
+          csrSaveToChannelPower2G_5G( pMac, count * sizeof(tSirMacChanInfo), pChanInfoStart );
+      }
+      palFreeMemory(pMac->hHdd, pChanInfoStart);
+  }
+
+  //Only apply them to CFG when not in STOP state. Otherwise they will be applied later
+  if( HAL_STATUS_SUCCESS(status) )
+  {
+      for( index = 0; index < CSR_ROAM_SESSION_MAX; index++ )
+      {
+          if((CSR_IS_SESSION_VALID(pMac, index)) && CSR_IS_ROAM_STOP(pMac, index))
+          {
+              applyConfig = FALSE;
+          }
+    }
+
+    if(TRUE == applyConfig)
+    {
+        // Apply the base channel list, power info, and set the Country code...
+        csrApplyChannelPowerCountryInfo( pMac, &pMac->scan.base20MHzChannels, pMac->scan.countryCodeCurrent );
+    }
+
+  }
+
+  return (status);
+}
+
+//pCommand may be NULL
+//Pass in sessionId in case pCommand is NULL. sessionId is not used in case pCommand is not NULL.
+void csrRoamRemoveDuplicateCommand(tpAniSirGlobal pMac, tANI_U32 sessionId, tSmeCmd *pCommand, eCsrRoamReason eRoamReason)
+{
+    tListElem *pEntry, *pNextEntry;
+    tSmeCmd *pDupCommand;
+    tDblLinkList localList;
+
+    vos_mem_zero(&localList, sizeof(tDblLinkList));
+    if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &localList)))
+    {
+        smsLog(pMac, LOGE, FL(" failed to open list"));
+        return;
+    }
+    csrLLLock( &pMac->sme.smeCmdPendingList );
+    pEntry = csrLLPeekHead( &pMac->sme.smeCmdPendingList, LL_ACCESS_NOLOCK );
+    while( pEntry )
+    {
+        pNextEntry = csrLLNext( &pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_NOLOCK );
+        pDupCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+
+        // Remove the previous command if..
+        // - the new roam command is for the same RoamReason...
+        // - the new roam command is a NewProfileList.
+        // - the new roam command is a Forced Dissoc
+        // - the new roam command is from an 802.11 OID (OID_SSID or OID_BSSID).
+        if ( 
+            (pCommand && ( pCommand->sessionId == pDupCommand->sessionId ) &&
+                ((pCommand->command == pDupCommand->command) &&
+                 (pCommand->u.roamCmd.roamReason == pDupCommand->u.roamCmd.roamReason ||
+                    eCsrForcedDisassoc == pCommand->u.roamCmd.roamReason ||
+                    eCsrHddIssued == pCommand->u.roamCmd.roamReason))) 
+                ||
+            //below the pCommand is NULL
+            ( (sessionId == pDupCommand->sessionId) && (eCsrRoamCommandRoam == pDupCommand->command) &&
+                 ((eCsrForcedDisassoc == eRoamReason) ||
+                    (eCsrHddIssued == eRoamReason))
+               )
+           )
+        {
+            smsLog(pMac, LOGW, FL("   roamReason = %d\n"), pDupCommand->u.roamCmd.roamReason);
+            // Remove the 'stale' roam command from the pending list...
+            if(csrLLRemoveEntry( &pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_NOLOCK ))
+            {
+                csrLLInsertTail(&localList, pEntry, LL_ACCESS_NOLOCK);
+            }
+        }
+        pEntry = pNextEntry;
+    }
+    csrLLUnlock( &pMac->sme.smeCmdPendingList );
+
+    while( (pEntry = csrLLRemoveHead(&localList, LL_ACCESS_NOLOCK)) )
+    {
+        pDupCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        //Tell caller that the command is cancelled
+        csrRoamCallCallback(pMac, pDupCommand->sessionId, NULL, pDupCommand->u.roamCmd.roamId,
+                                            eCSR_ROAM_CANCELLED, eCSR_ROAM_RESULT_NONE);
+        csrReleaseCommandRoam(pMac, pDupCommand);
+    }
+    csrLLClose(&localList);
+}
+
+eHalStatus csrRoamCallCallback(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamInfo *pRoamInfo, 
+                               tANI_U32 roamId, eRoamCmdStatus u1, eCsrRoamResult u2)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+    WLAN_VOS_DIAG_EVENT_DEF(connectionStatus, vos_event_wlan_status_payload_type);
+#endif
+    tCsrRoamSession *pSession;
+
+    if( CSR_IS_SESSION_VALID( pMac, sessionId) )
+    {
+        pSession = CSR_GET_SESSION( pMac, sessionId );
+    }
+    else
+    {
+       smsLog(pMac, LOGE, "Session ID:%d is not valid\n", sessionId);
+       VOS_ASSERT(0);
+       return eHAL_STATUS_FAILURE;
+    }
+
+    if(eCSR_ROAM_ASSOCIATION_COMPLETION == u1 && pRoamInfo)
+    {
+        smsLog(pMac, LOGW, " Assoc complete result = %d statusCode = %d reasonCode = %d\n", u2, pRoamInfo->statusCode, pRoamInfo->reasonCode);
+    }
+
+    if ( (pSession == NULL) ||
+        (eANI_BOOLEAN_FALSE == pSession->sessionActive) )
+    {
+        smsLog(pMac, LOG1, "Session ID is not valid\n");
+        return eHAL_STATUS_FAILURE;
+    }
+
+    if(NULL != pSession->callback)
+    {
+        if( pRoamInfo )
+        {
+            pRoamInfo->sessionId = (tANI_U8)sessionId;
+        }
+
+        /* avoid holding the global lock when making the roaming callback , original change came 
+        from a raised CR (CR304874).  Since this callback is in HDD a potential deadlock 
+        is possible on other OS ports where the callback may need to take locks to protect 
+        HDD state 
+         UPDATE : revert this change but keep the comments here. Need to revisit as there are callbacks
+         that may actually depend on the lock being held */
+        // TODO: revisit: sme_ReleaseGlobalLock( &pMac->sme );
+        status = pSession->callback(pSession->pContext, pRoamInfo, roamId, u1, u2);
+        // TODO: revisit: sme_AcquireGlobalLock( &pMac->sme );
+    }
+    //EVENT_WLAN_STATUS: eCSR_ROAM_ASSOCIATION_COMPLETION, 
+    //                   eCSR_ROAM_LOSTLINK, eCSR_ROAM_DISASSOCIATED, 
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR    
+    palZeroMemory(pMac->hHdd, &connectionStatus, sizeof(vos_event_wlan_status_payload_type));
+    if((eCSR_ROAM_ASSOCIATION_COMPLETION == u1) && (eCSR_ROAM_RESULT_ASSOCIATED == u2))
+    {
+       connectionStatus.eventId = eCSR_WLAN_STATUS_CONNECT;
+       connectionStatus.bssType = pRoamInfo->u.pConnectedProfile->BSSType;
+       if(NULL != pRoamInfo->pBssDesc)
+       {
+          connectionStatus.rssi = pRoamInfo->pBssDesc->rssi * (-1);
+          connectionStatus.channel = pRoamInfo->pBssDesc->channelId;
+       }
+
+       connectionStatus.qosCapability = pRoamInfo->u.pConnectedProfile->qosConnection;
+       connectionStatus.authType = (v_U8_t)diagAuthTypeFromCSRType(pRoamInfo->u.pConnectedProfile->AuthType);
+       connectionStatus.encryptionType = (v_U8_t)diagEncTypeFromCSRType(pRoamInfo->u.pConnectedProfile->EncryptionType);
+       palCopyMemory(pMac->hHdd, connectionStatus.ssid, pRoamInfo->u.pConnectedProfile->SSID.ssId, 6);
+       connectionStatus.reason = eCSR_REASON_UNSPECIFIED;
+       WLAN_VOS_DIAG_EVENT_REPORT(&connectionStatus, EVENT_WLAN_STATUS);
+    }
+
+    if((eCSR_ROAM_MIC_ERROR_IND == u1) || (eCSR_ROAM_RESULT_MIC_FAILURE == u2))
+    {
+       connectionStatus.eventId = eCSR_WLAN_STATUS_DISCONNECT;
+       connectionStatus.reason = eCSR_REASON_MIC_ERROR;
+       WLAN_VOS_DIAG_EVENT_REPORT(&connectionStatus, EVENT_WLAN_STATUS);
+    }
+
+    if(eCSR_ROAM_RESULT_FORCED == u2)
+    {
+       connectionStatus.eventId = eCSR_WLAN_STATUS_DISCONNECT;
+       connectionStatus.reason = eCSR_REASON_USER_REQUESTED;
+       WLAN_VOS_DIAG_EVENT_REPORT(&connectionStatus, EVENT_WLAN_STATUS);
+    }
+
+    if(eCSR_ROAM_RESULT_DISASSOC_IND == u2)
+    {
+       connectionStatus.eventId = eCSR_WLAN_STATUS_DISCONNECT;
+       connectionStatus.reason = eCSR_REASON_DISASSOC;
+       WLAN_VOS_DIAG_EVENT_REPORT(&connectionStatus, EVENT_WLAN_STATUS);
+    }
+
+    if(eCSR_ROAM_RESULT_DEAUTH_IND == u2)
+    {
+       connectionStatus.eventId = eCSR_WLAN_STATUS_DISCONNECT;
+       connectionStatus.reason = eCSR_REASON_DEAUTH;
+       WLAN_VOS_DIAG_EVENT_REPORT(&connectionStatus, EVENT_WLAN_STATUS);
+    }
+
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+    
+    return (status);
+}
+
+// Returns whether handoff is currently in progress or not
+tANI_BOOLEAN csrRoamIsHandoffInProgress(tpAniSirGlobal pMac)
+{
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+    return csrNeighborRoamIsHandoffInProgress(pMac);                    
+#else
+    return eANI_BOOLEAN_FALSE;
+#endif
+
+}
+
+eHalStatus csrRoamIssueDisassociate( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                     eCsrRoamSubState NewSubstate, tANI_BOOLEAN fMICFailure )
+{   
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrBssid bssId = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+    tANI_U16 reasonCode;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    //Restore AC weight in case we change it 
+    if ( csrIsConnStateConnectedInfra( pMac, sessionId ) )
+    {
+        smsLog(pMac, LOGE, FL(" restore AC weights (%d-%d-%d-%d)\n"), pMac->roam.ucACWeights[0], pMac->roam.ucACWeights[1],
+            pMac->roam.ucACWeights[2], pMac->roam.ucACWeights[3]);
+        WLANTL_SetACWeights(pMac->roam.gVosContext, pMac->roam.ucACWeights);
+    }
+    
+    if ( fMICFailure )
+    {
+        reasonCode = eSIR_MAC_MIC_FAILURE_REASON;
+    }
+    else if (NewSubstate == eCSR_ROAM_SUBSTATE_DISASSOC_HANDOFF)
+    {
+        reasonCode = eSIR_MAC_DISASSOC_DUE_TO_FTHANDOFF_REASON;
+    } else 
+    {
+        reasonCode = eSIR_MAC_UNSPEC_FAILURE_REASON;
+    }    
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    if ( (csrRoamIsHandoffInProgress(pMac)) && 
+         (NewSubstate != eCSR_ROAM_SUBSTATE_DISASSOC_HANDOFF))
+    {
+        tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+        palCopyMemory(pMac->hHdd, &bssId, pNeighborRoamInfo->csrNeighborRoamProfile.BSSIDs.bssid, sizeof(tSirMacAddr));
+
+    } else 
+#endif
+    if(pSession->pConnectBssDesc)
+    {
+        palCopyMemory(pMac->hHdd, &bssId, pSession->pConnectBssDesc->bssId, sizeof(tCsrBssid));
+    }
+
+    
+    smsLog( pMac, LOGE, "CSR Attempting to Disassociate Bssid= %02x-%02x-%02x-%02x-%02x-%02x subState = %d\n", 
+                  bssId[ 0 ], bssId[ 1 ], bssId[ 2 ],
+                  bssId[ 3 ], bssId[ 4 ], bssId[ 5 ], NewSubstate );    
+
+    csrRoamSubstateChange( pMac, NewSubstate, sessionId);
+
+    status = csrSendMBDisassocReqMsg( pMac, sessionId, bssId, reasonCode );    
+    
+    if(HAL_STATUS_SUCCESS(status)) 
+    {
+        csrRoamLinkDown(pMac, sessionId);
+
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+        //no need to tell QoS that we are disassociating, it will be taken care off in assoc req for HO
+        if(eCSR_ROAM_SUBSTATE_DISASSOC_HANDOFF != NewSubstate)
+        {
+            //Tush-QoS: notify QoS module that disassoc happening
+            sme_QosCsrEventInd(pMac, (v_U8_t)sessionId, SME_QOS_CSR_DISCONNECT_REQ, NULL);
+        }
+#endif
+     }
+
+    return (status);
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+
+
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamIssueDisassociateStaCmd
+    \brief csr function that HDD calls to disassociate a associated station
+    \param sessionId    - session Id for Soft AP
+    \param pPeerMacAddr - MAC of associated station to delete
+    \param reason - reason code, be one of the tSirMacReasonCodes
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus csrRoamIssueDisassociateStaCmd( tpAniSirGlobal pMac, 
+                                           tANI_U32 sessionId, 
+                                           tANI_U8 *pPeerMacAddr,
+                                           tANI_U32 reason)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand;
+
+    do
+    {
+        pCommand = csrGetCommandBuffer( pMac );
+        if ( !pCommand ) 
+        {
+            smsLog( pMac, LOGE, FL(" fail to get command buffer") );
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        pCommand->command = eSmeCommandRoam;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.roamCmd.roamReason = eCsrForcedDisassocSta;
+        vos_mem_copy(pCommand->u.roamCmd.peerMac, pPeerMacAddr, 6);
+        pCommand->u.roamCmd.reason = (tSirMacReasonCodes)reason;
+        status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_FALSE);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            csrReleaseCommandRoam( pMac, pCommand );
+        }
+    }while(0);
+
+    return status;
+}
+
+
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamIssueDeauthSta
+    \brief csr function that HDD calls to delete a associated station
+    \param sessionId    - session Id for Soft AP
+    \param pPeerMacAddr - MAC of associated station to delete
+    \param reason - reason code, be one of the tSirMacReasonCodes
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus csrRoamIssueDeauthStaCmd( tpAniSirGlobal pMac, 
+                                     tANI_U32 sessionId, 
+                                     tANI_U8 *pPeerMacAddr,
+                                     tANI_U32 reason)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand;
+
+    do
+    {
+        pCommand = csrGetCommandBuffer( pMac );
+        if ( !pCommand ) 
+        {
+            smsLog( pMac, LOGE, FL(" fail to get command buffer") );
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        pCommand->command = eSmeCommandRoam;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.roamCmd.roamReason = eCsrForcedDeauthSta;
+        vos_mem_copy(pCommand->u.roamCmd.peerMac, pPeerMacAddr, 6);
+        pCommand->u.roamCmd.reason = (tSirMacReasonCodes)reason;
+        status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_FALSE);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            csrReleaseCommandRoam( pMac, pCommand );
+        }
+    }while(0);
+
+    return status;
+}
+
+
+
+eHalStatus
+csrRoamIssueTkipCounterMeasures( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                    tANI_BOOLEAN bEnable )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tCsrBssid bssId = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if (!pSession)
+    {
+        smsLog( pMac, LOGE, "csrRoamIssueTkipCounterMeasures:CSR Session not found\n");
+        return (status);
+    }
+
+    if (pSession->pConnectBssDesc)
+    {
+        palCopyMemory(pMac->hHdd, &bssId, pSession->pConnectBssDesc->bssId, sizeof(tCsrBssid));
+    }
+    else
+    {
+        smsLog( pMac, LOGE, "csrRoamIssueTkipCounterMeasures:Connected BSS Description in CSR Session not found\n");
+        return (status);
+    }
+
+    smsLog( pMac, LOG2, "CSR issuing tkip counter measures for Bssid = %02x-%02x-%02x-%02x-%02x-%02x, Enable = %d\n", 
+                  bssId[ 0 ], bssId[ 1 ], bssId[ 2 ],
+                  bssId[ 3 ], bssId[ 4 ], bssId[ 5 ] , bEnable);
+
+    status = csrSendMBTkipCounterMeasuresReqMsg( pMac, sessionId, bEnable, bssId );
+    return (status);
+}
+
+eHalStatus
+csrRoamGetAssociatedStas( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                            VOS_MODULE_ID modId,  void *pUsrContext,
+                            void *pfnSapEventCallback, v_U8_t *pAssocStasBuf )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrBssid bssId = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if (!pSession)
+    {
+        smsLog( pMac, LOGE, "csrRoamGetAssociatedStas:CSR Session not found\n");
+        return (status);
+    }
+
+    if(pSession->pConnectBssDesc)
+    {
+        palCopyMemory( pMac->hHdd, &bssId, pSession->pConnectBssDesc->bssId, sizeof(tCsrBssid) );
+    }
+    else
+    {
+        smsLog( pMac, LOGE, "csrRoamGetAssociatedStas:Connected BSS Description in CSR Session not found\n");
+        return (status);
+    }
+
+    smsLog( pMac, LOG2, "CSR getting associated stations for Bssid = %02x-%02x-%02x-%02x-%02x-%02x\n",
+                  bssId[ 0 ], bssId[ 1 ], bssId[ 2 ],
+                  bssId[ 3 ], bssId[ 4 ], bssId[ 5 ] );
+
+    status = csrSendMBGetAssociatedStasReqMsg( pMac, sessionId, modId, bssId, pUsrContext, pfnSapEventCallback, pAssocStasBuf );
+    return (status);
+}
+
+eHalStatus
+csrRoamGetWpsSessionOverlap( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                             void *pUsrContext, void *pfnSapEventCallback, v_MACADDR_t pRemoveMac )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrBssid bssId = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    if (!pSession)
+    {
+        smsLog( pMac, LOGE, "csrRoamGetWpsSessionOverlap:CSR Session not found\n");
+        return (status);
+    }
+
+    if(pSession->pConnectBssDesc)
+    {
+        palCopyMemory( pMac->hHdd, &bssId, pSession->pConnectBssDesc->bssId, sizeof(tCsrBssid) );
+    }
+    else
+    {
+        smsLog( pMac, LOGE, "csrRoamGetWpsSessionOverlap:Connected BSS Description in CSR Session not found\n");
+        return (status);
+    }
+
+    smsLog( pMac, LOG2, "CSR getting WPS Session Overlap for Bssid = %02x-%02x-%02x-%02x-%02x-%02x\n",
+                  bssId[ 0 ], bssId[ 1 ], bssId[ 2 ],
+                  bssId[ 3 ], bssId[ 4 ], bssId[ 5 ] );
+     
+    status = csrSendMBGetWPSPBCSessions( pMac, sessionId, bssId, pUsrContext, pfnSapEventCallback, pRemoveMac);            
+            
+    return (status);
+}
+
+#endif
+
+eHalStatus csrRoamIssueDeauth( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamSubState NewSubstate )
+{   
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrBssid bssId = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    if(pSession->pConnectBssDesc)
+    {
+        palCopyMemory(pMac->hHdd, &bssId, pSession->pConnectBssDesc->bssId, sizeof(tCsrBssid));
+    }
+
+    smsLog( pMac, LOG2, "CSR Attempting to Deauth Bssid= %02x-%02x-%02x-%02x-%02x-%02x\n", 
+                  bssId[ 0 ], bssId[ 1 ], bssId[ 2 ],
+                  bssId[ 3 ], bssId[ 4 ], bssId[ 5 ] );    
+
+    csrRoamSubstateChange( pMac, NewSubstate, sessionId);
+    
+    status = csrSendMBDeauthReqMsg( pMac, sessionId, bssId, eSIR_MAC_DISASSOC_LEAVING_BSS_REASON );    
+    
+    return (status);
+}
+
+
+
+eHalStatus csrRoamSaveConnectedBssDesc( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirBssDescription *pBssDesc )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tANI_U32 size;
+    
+    // If no BSS description was found in this connection (happens with start IBSS), then 
+    // nix the BSS description that we keep around for the connected BSS) and get out...
+    if(NULL == pBssDesc)
+    {
+        csrFreeConnectBssDesc(pMac, sessionId);
+    }
+    else 
+    {
+        size = pBssDesc->length + sizeof( pBssDesc->length );
+        if(NULL != pSession->pConnectBssDesc)
+        {
+            if(((pSession->pConnectBssDesc->length) + sizeof(pSession->pConnectBssDesc->length)) < size)
+            {
+                //not enough room for the new BSS, pMac->roam.pConnectBssDesc is freed inside
+                csrFreeConnectBssDesc(pMac, sessionId);
+            }
+        }
+        if(NULL == pSession->pConnectBssDesc)
+        {
+            status = palAllocateMemory( pMac->hHdd, (void **)&pSession->pConnectBssDesc, size); 
+        }
+        if ( HAL_STATUS_SUCCESS(status) && pSession->pConnectBssDesc ) 
+        {
+            palCopyMemory( pMac->hHdd, pSession->pConnectBssDesc, pBssDesc, size );    
+        }
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrRoamPrepareBssConfig(tpAniSirGlobal pMac, tCsrRoamProfile *pProfile, 
+                                    tSirBssDescription *pBssDesc, tBssConfigParam *pBssConfig,
+                                    tDot11fBeaconIEs *pIes)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    eCsrCfgDot11Mode cfgDot11Mode;
+
+#if defined(VOSS_ENABLED)
+    VOS_ASSERT( pIes != NULL );
+#endif
+    
+    do
+    {
+        palCopyMemory(pMac->hHdd, &pBssConfig->BssCap, &pBssDesc->capabilityInfo, sizeof(tSirMacCapabilityInfo));
+        //get qos
+        pBssConfig->qosType = csrGetQoSFromBssDesc(pMac, pBssDesc, pIes);
+        //get SSID
+        if(pIes->SSID.present)
+        {
+            palCopyMemory(pMac->hHdd, &pBssConfig->SSID.ssId, pIes->SSID.ssid, pIes->SSID.num_ssid);
+            pBssConfig->SSID.length = pIes->SSID.num_ssid;
+        }
+        else
+            pBssConfig->SSID.length = 0;
+        if(csrIsNULLSSID(pBssConfig->SSID.ssId, pBssConfig->SSID.length))
+        {
+            smsLog(pMac, LOGW, "  BSS desc SSID is a wildcard\n");
+            //Return failed if profile doesn't have an SSID either.
+            if(pProfile->SSIDs.numOfSSIDs == 0)
+            {
+                smsLog(pMac, LOGW, "  Both BSS desc and profile doesn't have SSID\n");
+                status = eHAL_STATUS_FAILURE;
+                break;
+            }
+        }
+        if(CSR_IS_CHANNEL_5GHZ(pBssDesc->channelId))
+        {
+            pBssConfig->eBand = eCSR_BAND_5G;
+        }
+        else
+        {
+            pBssConfig->eBand = eCSR_BAND_24;
+        }
+        //phymode
+        if(csrIsPhyModeMatch( pMac, pProfile->phyMode, pBssDesc, pProfile, &cfgDot11Mode, pIes ))
+        {
+            pBssConfig->uCfgDot11Mode = cfgDot11Mode;
+        }
+        else 
+        {
+            smsLog(pMac, LOGW, "   Can not find match phy mode\n");
+            //force it
+            if(eCSR_BAND_24 == pBssConfig->eBand)
+            {
+                pBssConfig->uCfgDot11Mode = eCSR_CFG_DOT11_MODE_11G;
+            }
+            else
+            {
+                pBssConfig->uCfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+            }
+        }
+
+        //Qos
+        if ((pBssConfig->uCfgDot11Mode != eCSR_CFG_DOT11_MODE_11N) &&
+                (pMac->roam.configParam.WMMSupportMode == eCsrRoamWmmNoQos))
+        {
+            //Joining BSS is not 11n capable and WMM is disabled on client.
+            //Disable QoS and WMM
+            pBssConfig->qosType = eCSR_MEDIUM_ACCESS_DCF;
+        }
+       
+        //auth type
+        switch( pProfile->negotiatedAuthType ) 
+        {
+            default:
+            case eCSR_AUTH_TYPE_WPA:
+            case eCSR_AUTH_TYPE_WPA_PSK:
+            case eCSR_AUTH_TYPE_WPA_NONE:
+            case eCSR_AUTH_TYPE_OPEN_SYSTEM:
+                pBssConfig->authType = eSIR_OPEN_SYSTEM;
+                break;
+
+            case eCSR_AUTH_TYPE_SHARED_KEY:
+                pBssConfig->authType = eSIR_SHARED_KEY;
+                break;
+
+            case eCSR_AUTH_TYPE_AUTOSWITCH:
+                pBssConfig->authType = eSIR_AUTO_SWITCH;
+                break;
+        }
+        //short slot time
+        if( eCSR_CFG_DOT11_MODE_11B != cfgDot11Mode )
+        {
+            pBssConfig->uShortSlotTime = pMac->roam.configParam.shortSlotTime;
+        }
+        else
+        {
+            pBssConfig->uShortSlotTime = 0;
+        }
+        if(pBssConfig->BssCap.ibss)
+        {
+            //We don't support 11h on IBSS
+            pBssConfig->f11hSupport = eANI_BOOLEAN_FALSE; 
+        }
+        else
+        {
+            pBssConfig->f11hSupport = pMac->roam.configParam.Is11hSupportEnabled;
+        }
+        //power constraint
+        pBssConfig->uPowerLimit = csrGet11hPowerConstraint(pMac, &pIes->PowerConstraints);
+        //heartbeat
+        if ( CSR_IS_11A_BSS( pBssDesc ) )
+        {
+             pBssConfig->uHeartBeatThresh = pMac->roam.configParam.HeartbeatThresh50;        
+        }
+        else
+        {
+             pBssConfig->uHeartBeatThresh = pMac->roam.configParam.HeartbeatThresh24;
+        }
+        //Join timeout
+        // if we find a BeaconInterval in the BssDescription, then set the Join Timeout to 
+        // be 3 x the BeaconInterval.                          
+        if ( pBssDesc->beaconInterval )
+        {
+            //Make sure it is bigger than the minimal
+            pBssConfig->uJoinTimeOut = CSR_ROAM_MAX(3 * pBssDesc->beaconInterval, CSR_JOIN_FAILURE_TIMEOUT_MIN);
+        }
+        else 
+        {
+            pBssConfig->uJoinTimeOut = CSR_JOIN_FAILURE_TIMEOUT_DEFAULT;
+        }
+        //validate CB
+        pBssConfig->cbMode = csrGetCBModeFromIes(pMac, pBssDesc->channelId, pIes);
+    }while(0);
+
+    return (status);
+}
+
+
+static eHalStatus csrRoamPrepareBssConfigFromProfile(tpAniSirGlobal pMac, tCsrRoamProfile *pProfile, 
+                                                     tBssConfigParam *pBssConfig, tSirBssDescription *pBssDesc)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U8 operationChannel = 0; 
+    tANI_U8 qAPisEnabled = FALSE;
+    //SSID
+    pBssConfig->SSID.length = 0;
+    if(pProfile->SSIDs.numOfSSIDs)
+    {
+        //only use the first one
+        palCopyMemory(pMac->hHdd, &pBssConfig->SSID, &pProfile->SSIDs.SSIDList[0].SSID, sizeof(tSirMacSSid));
+    }
+    else
+    {
+        //SSID must present
+        return eHAL_STATUS_FAILURE;
+    }
+
+    //Settomg up the capabilities
+    if( csrIsBssTypeIBSS(pProfile->BSSType) )
+    {
+        pBssConfig->BssCap.ibss = 1;
+    }
+    else
+    {
+        pBssConfig->BssCap.ess = 1;
+    }
+    if( eCSR_ENCRYPT_TYPE_NONE != pProfile->EncryptionType.encryptionType[0] )
+    {
+        pBssConfig->BssCap.privacy = 1;
+    }
+
+    pBssConfig->eBand = pMac->roam.configParam.eBand;
+    //phymode
+    if(pProfile->ChannelInfo.ChannelList)
+    {
+       operationChannel = pProfile->ChannelInfo.ChannelList[0];
+    }
+
+#ifdef WLAN_SOFTAP_FEATURE
+    pBssConfig->uCfgDot11Mode = csrRoamGetPhyModeBandForBss(pMac, pProfile, operationChannel, 
+                                        &pBssConfig->eBand);
+#else
+
+    pBssConfig->uCfgDot11Mode = csrRoamGetPhyModeBandForBss(pMac, (eCsrPhyMode)pProfile->phyMode, operationChannel, 
+                                        &pBssConfig->eBand);
+#endif
+    //QOS
+    //Is this correct to always set to this //***
+
+    if ( pBssConfig->BssCap.ess == 1 ) 
+    {
+#ifdef WLAN_SOFTAP_FEATURE
+        /*For Softap case enable WMM*/
+        if(CSR_IS_INFRA_AP(pProfile) && (eCsrRoamWmmNoQos != pMac->roam.configParam.WMMSupportMode )){
+             qAPisEnabled = TRUE;
+        }
+        else
+#endif
+        if (csrRoamGetQosInfoFromBss(pMac, pBssDesc) == eHAL_STATUS_SUCCESS) {
+             qAPisEnabled = TRUE;
+        } else {
+             qAPisEnabled = FALSE;
+        }
+    } else {
+             qAPisEnabled = TRUE;
+    }
+
+    if (( eCsrRoamWmmNoQos != pMac->roam.configParam.WMMSupportMode && qAPisEnabled) ||
+          (( eCSR_CFG_DOT11_MODE_11N == pBssConfig->uCfgDot11Mode && qAPisEnabled) ||
+             ( eCSR_CFG_DOT11_MODE_TAURUS == pBssConfig->uCfgDot11Mode ) ) //For 11n, need QoS
+      )
+    {
+        pBssConfig->qosType = eCSR_MEDIUM_ACCESS_WMM_eDCF_DSCP;
+    } else {
+        pBssConfig->qosType = eCSR_MEDIUM_ACCESS_DCF;
+    }
+    
+    //auth type
+    switch( pProfile->AuthType.authType[0] ) //Take the prefered Auth type.
+    {
+        default:
+        case eCSR_AUTH_TYPE_WPA:
+        case eCSR_AUTH_TYPE_WPA_PSK:
+        case eCSR_AUTH_TYPE_WPA_NONE:
+        case eCSR_AUTH_TYPE_OPEN_SYSTEM:
+            pBssConfig->authType = eSIR_OPEN_SYSTEM;
+            break;
+
+        case eCSR_AUTH_TYPE_SHARED_KEY:
+            pBssConfig->authType = eSIR_SHARED_KEY;
+            break;
+
+        case eCSR_AUTH_TYPE_AUTOSWITCH:
+            pBssConfig->authType = eSIR_AUTO_SWITCH;
+            break;
+    }
+    //short slot time
+    if( WNI_CFG_PHY_MODE_11B != pBssConfig->uCfgDot11Mode )
+    {
+        pBssConfig->uShortSlotTime = pMac->roam.configParam.shortSlotTime;
+    }
+    else
+    {
+        pBssConfig->uShortSlotTime = 0;
+    }
+    //power constraint. We don't support 11h on IBSS
+    pBssConfig->f11hSupport = eANI_BOOLEAN_FALSE;
+    pBssConfig->uPowerLimit = 0;
+    //heartbeat
+    if ( eCSR_BAND_5G == pBssConfig->eBand )
+    {
+        pBssConfig->uHeartBeatThresh = pMac->roam.configParam.HeartbeatThresh50;        
+    }
+    else
+    {
+        pBssConfig->uHeartBeatThresh = pMac->roam.configParam.HeartbeatThresh24;
+    }
+    //Join timeout
+    pBssConfig->uJoinTimeOut = CSR_JOIN_FAILURE_TIMEOUT_DEFAULT;
+    
+    return (status);
+}
+
+static eHalStatus csrRoamGetQosInfoFromBss(tpAniSirGlobal pMac, tSirBssDescription *pBssDesc)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tDot11fBeaconIEs *pIes = NULL;
+   
+  do
+   {
+      if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIes)))
+      {
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                   "csrRoamGetQosInfoFromBss() failed\n");
+
+         break;
+      }
+      //check if the AP is QAP & it supports APSD
+      if( CSR_IS_QOS_BSS(pIes) )
+      {
+         return eHAL_STATUS_SUCCESS;
+      }
+   } while (0);
+
+   return status;
+}
+
+
+void csrSetCfgPrivacy( tpAniSirGlobal pMac, tCsrRoamProfile *pProfile, tANI_BOOLEAN fPrivacy )
+{
+
+    // !! Note:  the only difference between this function and the csrSetCfgPrivacyFromProfile() is the 
+    // setting of the privacy CFG based on the advertised privacy setting from the AP for WPA associations. 
+    // See !!Note: below in this function...
+    tANI_U32 PrivacyEnabled = 0;
+    tANI_U32 RsnEnabled = 0;
+    tANI_U32 WepDefaultKeyId = 0;
+    tANI_U32 WepKeyLength = WNI_CFG_WEP_KEY_LENGTH_5;   /* default 40 bits */
+    tANI_U32 Key0Length = 0;
+    tANI_U32 Key1Length = 0;
+    tANI_U32 Key2Length = 0;
+    tANI_U32 Key3Length = 0;
+    
+    // Reserve for the biggest key 
+    tANI_U8 Key0[ WNI_CFG_WEP_DEFAULT_KEY_1_LEN ];
+    tANI_U8 Key1[ WNI_CFG_WEP_DEFAULT_KEY_2_LEN ];
+    tANI_U8 Key2[ WNI_CFG_WEP_DEFAULT_KEY_3_LEN ];
+    tANI_U8 Key3[ WNI_CFG_WEP_DEFAULT_KEY_4_LEN ];
+    
+    switch ( pProfile->negotiatedUCEncryptionType )
+    {
+        case eCSR_ENCRYPT_TYPE_NONE:
+        
+            // for NO encryption, turn off Privacy and Rsn.
+            PrivacyEnabled = 0;           
+            RsnEnabled = 0;
+            
+            // WEP key length and Wep Default Key ID don't matter in this case....
+            
+            // clear out the WEP keys that may be hanging around.
+            Key0Length = 0;
+            Key1Length = 0;
+            Key2Length = 0;
+            Key3Length = 0;
+            
+            break;
+            
+        case eCSR_ENCRYPT_TYPE_WEP40_STATICKEY:
+            
+            // Privacy is ON.  NO RSN for Wep40 static key.
+            PrivacyEnabled = 1;           
+            RsnEnabled = 0;
+                        
+            // Set the Wep default key ID.
+            WepDefaultKeyId = pProfile->Keys.defaultIndex;
+
+            // Wep key size if 5 bytes (40 bits).
+            WepKeyLength = WNI_CFG_WEP_KEY_LENGTH_5;            
+            
+            // set encryption keys in the CFG database or clear those that are not present in this profile.
+            if ( pProfile->Keys.KeyLength[0] ) 
+            {
+                palCopyMemory( pMac->hHdd, Key0, pProfile->Keys.KeyMaterial[0], WNI_CFG_WEP_KEY_LENGTH_5 );
+                Key0Length = WNI_CFG_WEP_KEY_LENGTH_5;
+            }
+            else
+            {
+                Key0Length = 0;
+            }
+            
+            if ( pProfile->Keys.KeyLength[1] ) 
+            {
+                palCopyMemory( pMac->hHdd, Key1, pProfile->Keys.KeyMaterial[1], WNI_CFG_WEP_KEY_LENGTH_5 );
+                Key1Length = WNI_CFG_WEP_KEY_LENGTH_5;
+            }
+            else
+            {
+                Key1Length = 0;
+            }
+            
+            if ( pProfile->Keys.KeyLength[2] ) 
+            {
+                palCopyMemory( pMac->hHdd, Key2, pProfile->Keys.KeyMaterial[2], WNI_CFG_WEP_KEY_LENGTH_5 );
+                Key2Length = WNI_CFG_WEP_KEY_LENGTH_5;                
+            }
+            else
+            {
+                Key2Length = 0;
+            }
+            
+            if ( pProfile->Keys.KeyLength[3] ) 
+            {
+                palCopyMemory( pMac->hHdd, Key3, pProfile->Keys.KeyMaterial[3], WNI_CFG_WEP_KEY_LENGTH_5 );
+                Key3Length = WNI_CFG_WEP_KEY_LENGTH_5;                
+            }
+            else
+            {
+                Key3Length = 0;
+            }      
+
+            break;
+        
+        case eCSR_ENCRYPT_TYPE_WEP104_STATICKEY:
+            
+            // Privacy is ON.  NO RSN for Wep40 static key.
+            PrivacyEnabled = 1;           
+            RsnEnabled = 0;
+            
+            // Set the Wep default key ID.
+            WepDefaultKeyId = pProfile->Keys.defaultIndex;
+           
+            // Wep key size if 13 bytes (104 bits).
+            WepKeyLength = WNI_CFG_WEP_KEY_LENGTH_13;
+            
+            // set encryption keys in the CFG database or clear those that are not present in this profile.
+            if ( pProfile->Keys.KeyLength[0] ) 
+            {
+                palCopyMemory( pMac->hHdd, Key0, pProfile->Keys.KeyMaterial[ 0 ], WNI_CFG_WEP_KEY_LENGTH_13 );
+                Key0Length = WNI_CFG_WEP_KEY_LENGTH_13;
+            }
+            else
+            {
+                Key0Length = 0;
+            }
+            
+            if ( pProfile->Keys.KeyLength[1] ) 
+            {
+                palCopyMemory( pMac->hHdd, Key1, pProfile->Keys.KeyMaterial[ 1 ], WNI_CFG_WEP_KEY_LENGTH_13 );
+                Key1Length = WNI_CFG_WEP_KEY_LENGTH_13;
+            }
+            else
+            {
+                Key1Length = 0;
+            }
+            
+            if ( pProfile->Keys.KeyLength[2] ) 
+            {
+                palCopyMemory( pMac->hHdd, Key2, pProfile->Keys.KeyMaterial[ 2 ], WNI_CFG_WEP_KEY_LENGTH_13 );
+                Key2Length = WNI_CFG_WEP_KEY_LENGTH_13;
+            }
+            else
+            {
+                Key2Length = 0;
+            }
+            
+            if ( pProfile->Keys.KeyLength[3] ) 
+            {
+                palCopyMemory( pMac->hHdd, Key3, pProfile->Keys.KeyMaterial[ 3 ], WNI_CFG_WEP_KEY_LENGTH_13 );
+                Key3Length = WNI_CFG_WEP_KEY_LENGTH_13;
+            }
+            else
+            {
+                Key3Length = 0;
+            }
+           
+            break;
+        
+        case eCSR_ENCRYPT_TYPE_WEP40:
+        case eCSR_ENCRYPT_TYPE_WEP104:
+        case eCSR_ENCRYPT_TYPE_TKIP:
+        case eCSR_ENCRYPT_TYPE_AES:
+#ifdef FEATURE_WLAN_WAPI
+        case eCSR_ENCRYPT_TYPE_WPI:
+#endif /* FEATURE_WLAN_WAPI */
+            // !! Note:  this is the only difference between this function and the csrSetCfgPrivacyFromProfile()
+            // (setting of the privacy CFG based on the advertised privacy setting from the AP for WPA/WAPI associations ).        
+            PrivacyEnabled = (0 != fPrivacy);
+                         
+            // turn on RSN enabled for WPA associations   
+            RsnEnabled = 1;
+            
+            // WEP key length and Wep Default Key ID don't matter in this case....
+            
+            // clear out the static WEP keys that may be hanging around.
+            Key0Length = 0;
+            Key1Length = 0;
+            Key2Length = 0;
+            Key3Length = 0;        
+          
+            break;     
+
+        default:
+            PrivacyEnabled = 0;
+            RsnEnabled = 0;
+            break;            
+    }           
+    
+    ccmCfgSetInt(pMac, WNI_CFG_PRIVACY_ENABLED, PrivacyEnabled, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetInt(pMac, WNI_CFG_RSN_ENABLED, RsnEnabled, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetStr(pMac, WNI_CFG_WEP_DEFAULT_KEY_1, Key0, Key0Length, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetStr(pMac, WNI_CFG_WEP_DEFAULT_KEY_2, Key1, Key1Length, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetStr(pMac, WNI_CFG_WEP_DEFAULT_KEY_3, Key2, Key2Length, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetStr(pMac, WNI_CFG_WEP_DEFAULT_KEY_4, Key3, Key3Length, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetInt(pMac, WNI_CFG_WEP_KEY_LENGTH, WepKeyLength, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetInt(pMac, WNI_CFG_WEP_DEFAULT_KEYID, WepDefaultKeyId, NULL, eANI_BOOLEAN_FALSE);
+}
+
+
+static void csrSetCfgSsid( tpAniSirGlobal pMac, tSirMacSSid *pSSID )
+{
+    tANI_U32 len = 0;
+    if(pSSID->length <= WNI_CFG_SSID_LEN)
+    {
+        len = pSSID->length;
+    }
+    ccmCfgSetStr(pMac, WNI_CFG_SSID, (tANI_U8 *)pSSID->ssId, len, NULL, eANI_BOOLEAN_FALSE);
+}
+
+
+eHalStatus csrSetQosToCfg( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrMediaAccessType qosType )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 QoSEnabled;
+    tANI_U32 WmeEnabled;
+
+    // set the CFG enable/disable variables based on the qosType being configured...
+    switch( qosType )
+    {
+
+        case eCSR_MEDIUM_ACCESS_WMM_eDCF_802dot1p:
+            QoSEnabled = FALSE;
+            WmeEnabled = TRUE;
+            break;
+
+        case eCSR_MEDIUM_ACCESS_WMM_eDCF_DSCP:
+            QoSEnabled = FALSE;
+            WmeEnabled = TRUE;
+            break;
+
+        case eCSR_MEDIUM_ACCESS_WMM_eDCF_NoClassify:
+            QoSEnabled = FALSE;
+            WmeEnabled = TRUE;
+            break;
+
+        case eCSR_MEDIUM_ACCESS_11e_eDCF:
+            QoSEnabled = TRUE;
+            WmeEnabled = FALSE;
+            break;
+
+        case eCSR_MEDIUM_ACCESS_11e_HCF:
+            QoSEnabled = TRUE;
+            WmeEnabled = FALSE;
+            break;
+
+        default:
+        case eCSR_MEDIUM_ACCESS_DCF:
+            QoSEnabled = FALSE;
+            WmeEnabled = FALSE;
+            break;
+
+    }
+    //save the WMM setting for later use
+    pMac->roam.roamSession[sessionId].fWMMConnection = (tANI_BOOLEAN)WmeEnabled;
+
+    status = ccmCfgSetInt(pMac, WNI_CFG_QOS_ENABLED, QoSEnabled, NULL, eANI_BOOLEAN_FALSE);
+    status = ccmCfgSetInt(pMac, WNI_CFG_WME_ENABLED, WmeEnabled, NULL, eANI_BOOLEAN_FALSE);
+
+    return (status);
+}
+
+static eHalStatus csrGetRateSet( tpAniSirGlobal pMac,  tCsrRoamProfile *pProfile, eCsrPhyMode phyMode, tSirBssDescription *pBssDesc,
+                           tDot11fBeaconIEs *pIes, tSirMacRateSet *pOpRateSet, tSirMacRateSet *pExRateSet)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    int i;
+    eCsrCfgDot11Mode cfgDot11Mode;
+    tANI_U8 *pDstRate;
+
+    palZeroMemory(pMac->hHdd, pOpRateSet, sizeof(tSirMacRateSet));
+    palZeroMemory(pMac->hHdd, pExRateSet, sizeof(tSirMacRateSet));
+
+#if defined(VOSS_ENABLED)
+    VOS_ASSERT( pIes != NULL );
+#endif
+    
+    if( NULL != pIes )
+    {
+        csrIsPhyModeMatch( pMac, phyMode, pBssDesc, pProfile, &cfgDot11Mode, pIes );
+
+        // Originally, we thought that for 11a networks, the 11a rates are always
+        // in the Operational Rate set & for 11b and 11g networks, the 11b rates
+        // appear in the Operational Rate set.  Consequently, in either case, we
+        // would blindly put the rates we support into our Operational Rate set
+        // (including the basic rates, which we have already verified are
+        // supported earlier in the roaming decision).
+
+        // However, it turns out that this is not always the case.  Some AP's
+        // (e.g. D-Link DI-784) ram 11g rates into the Operational Rate set,
+        // too.  Now, we're a little more careful:
+        pDstRate = pOpRateSet->rate;
+        if(pIes->SuppRates.present)
+        {
+            for ( i = 0; i < pIes->SuppRates.num_rates; i++ ) 
+            {
+                if ( csrRatesIsDot11RateSupported( pMac, pIes->SuppRates.rates[ i ] ) ) 
+                {
+                    *pDstRate++ = pIes->SuppRates.rates[ i ];
+                    pOpRateSet->numRates++;;
+                }
+            }
+        }
+
+        if ( eCSR_CFG_DOT11_MODE_11G == cfgDot11Mode || 
+             eCSR_CFG_DOT11_MODE_11N == cfgDot11Mode ||
+             eCSR_CFG_DOT11_MODE_TAURUS == cfgDot11Mode ||
+             eCSR_CFG_DOT11_MODE_ABG == cfgDot11Mode )
+        {
+            // If there are Extended Rates in the beacon, we will reflect those
+            // extended rates that we support in out Extended Operational Rate
+            // set:
+            pDstRate = pExRateSet->rate;
+            if(pIes->ExtSuppRates.present)
+            {
+                for ( i = 0; i < pIes->ExtSuppRates.num_rates; i++ ) 
+                {
+                    if ( csrRatesIsDot11RateSupported( pMac, pIes->ExtSuppRates.rates[ i ] ) ) 
+                    {
+                        *pDstRate++ = pIes->ExtSuppRates.rates[ i ];
+                        pExRateSet->numRates++;
+                    }
+                }
+            }
+        }
+    }//Parsing BSSDesc
+    else
+    {
+        smsLog(pMac, LOGE, FL("failed to parse BssDesc\n"));
+    }
+    if (pOpRateSet->numRates > 0 || pExRateSet->numRates > 0) status = eHAL_STATUS_SUCCESS;
+    return status;
+}
+    
+static void csrSetCfgRateSet( tpAniSirGlobal pMac, eCsrPhyMode phyMode, tCsrRoamProfile *pProfile,
+                              tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes)
+{
+    int i;
+    tANI_U8 *pDstRate;
+    eCsrCfgDot11Mode cfgDot11Mode;
+    tANI_U8 OperationalRates[ CSR_DOT11_SUPPORTED_RATES_MAX ];    // leave enough room for the max number of rates
+    tANI_U32 OperationalRatesLength = 0;
+    tANI_U8 ExtendedOperationalRates[ CSR_DOT11_EXTENDED_SUPPORTED_RATES_MAX ];    // leave enough room for the max number of rates
+    tANI_U32 ExtendedOperationalRatesLength = 0;
+    tANI_U8 ProprietaryOperationalRates[ 4 ];    // leave enough room for the max number of proprietary rates
+    tANI_U32 ProprietaryOperationalRatesLength = 0;
+    tANI_U32 PropRatesEnable = 0;
+    tANI_U8 MCSRateIdxSet[ SIZE_OF_SUPPORTED_MCS_SET ];
+    tANI_U32 MCSRateLength = 0;
+
+#if defined(VOSS_ENABLED)
+    VOS_ASSERT( pIes != NULL );
+#endif
+
+    if( NULL != pIes )
+    {
+        csrIsPhyModeMatch( pMac, phyMode, pBssDesc, pProfile, &cfgDot11Mode, pIes );
+
+        // Originally, we thought that for 11a networks, the 11a rates are always
+        // in the Operational Rate set & for 11b and 11g networks, the 11b rates
+        // appear in the Operational Rate set.  Consequently, in either case, we
+        // would blindly put the rates we support into our Operational Rate set
+        // (including the basic rates, which we have already verified are
+        // supported earlier in the roaming decision).
+
+        // However, it turns out that this is not always the case.  Some AP's
+        // (e.g. D-Link DI-784) ram 11g rates into the Operational Rate set,
+        // too.  Now, we're a little more careful:
+        pDstRate = OperationalRates;
+        if(pIes->SuppRates.present)
+        {
+            for ( i = 0; i < pIes->SuppRates.num_rates; i++ ) 
+            {
+                if ( csrRatesIsDot11RateSupported( pMac, pIes->SuppRates.rates[ i ] ) &&
+                     ( OperationalRatesLength < CSR_DOT11_SUPPORTED_RATES_MAX ))
+                {
+                    *pDstRate++ = pIes->SuppRates.rates[ i ];
+                    OperationalRatesLength++;
+                }
+            }
+        }
+
+        if ( eCSR_CFG_DOT11_MODE_11G == cfgDot11Mode || 
+             eCSR_CFG_DOT11_MODE_11N == cfgDot11Mode ||
+             eCSR_CFG_DOT11_MODE_TAURUS == cfgDot11Mode ||
+             eCSR_CFG_DOT11_MODE_ABG == cfgDot11Mode )
+        {
+            // If there are Extended Rates in the beacon, we will reflect those
+            // extended rates that we support in out Extended Operational Rate
+            // set:
+            pDstRate = ExtendedOperationalRates;
+            if(pIes->ExtSuppRates.present)
+            {
+                for ( i = 0; i < pIes->ExtSuppRates.num_rates; i++ ) 
+                {
+                    if ( csrRatesIsDot11RateSupported( pMac, pIes->ExtSuppRates.rates[ i ] ) &&
+                     ( ExtendedOperationalRatesLength < CSR_DOT11_EXTENDED_SUPPORTED_RATES_MAX ))
+                    {
+                        *pDstRate++ = pIes->ExtSuppRates.rates[ i ];
+                        ExtendedOperationalRatesLength++;
+                    }
+                }
+            }
+        }
+
+        // Enable proprietary MAC features if peer node is Airgo node and STA
+        // user wants to use them
+        if( pIes->Airgo.present && pMac->roam.configParam.ProprietaryRatesEnabled )
+        {
+            PropRatesEnable = 1;
+        }
+        else
+        {
+            PropRatesEnable = 0;
+        }
+
+        // For ANI network companions, we need to populate the proprietary rate
+        // set with any proprietary rates we found in the beacon, only if user
+        // allows them...
+        if ( PropRatesEnable && pIes->Airgo.PropSuppRates.present &&
+             ( pIes->Airgo.PropSuppRates.num_rates > 0 )) 
+        {
+            ProprietaryOperationalRatesLength = pIes->Airgo.PropSuppRates.num_rates;
+            if ( ProprietaryOperationalRatesLength > sizeof(ProprietaryOperationalRates) )
+            {
+               ProprietaryOperationalRatesLength = sizeof (ProprietaryOperationalRates);
+            }
+            palCopyMemory( pMac->hHdd, ProprietaryOperationalRates, pIes->Airgo.PropSuppRates.rates, ProprietaryOperationalRatesLength );
+        }
+        else {
+            // No proprietary modes...
+            ProprietaryOperationalRatesLength = 0;
+        }
+
+        /* Get MCS Rate */
+        pDstRate = MCSRateIdxSet;
+        if ( pIes->HTCaps.present )
+        {
+           for ( i = 0; i < VALID_MAX_MCS_INDEX; i++ )
+           {
+              if ( (unsigned int)pIes->HTCaps.supportedMCSSet[0] & (1 << i) )
+              {
+                 MCSRateLength++;
+                 *pDstRate++ = i;
+              }
+           }
+        }
+
+        // Set the operational rate set CFG variables...
+        ccmCfgSetStr(pMac, WNI_CFG_OPERATIONAL_RATE_SET, OperationalRates, 
+                        OperationalRatesLength, NULL, eANI_BOOLEAN_FALSE);
+        ccmCfgSetStr(pMac, WNI_CFG_EXTENDED_OPERATIONAL_RATE_SET, ExtendedOperationalRates, 
+                            ExtendedOperationalRatesLength, NULL, eANI_BOOLEAN_FALSE);
+        ccmCfgSetStr(pMac, WNI_CFG_PROPRIETARY_OPERATIONAL_RATE_SET, 
+                        ProprietaryOperationalRates, 
+                        ProprietaryOperationalRatesLength, NULL, eANI_BOOLEAN_FALSE);
+        ccmCfgSetInt(pMac, WNI_CFG_PROPRIETARY_ANI_FEATURES_ENABLED, PropRatesEnable, NULL, eANI_BOOLEAN_FALSE);
+        ccmCfgSetStr(pMac, WNI_CFG_CURRENT_MCS_SET, MCSRateIdxSet, 
+                        MCSRateLength, NULL, eANI_BOOLEAN_FALSE);        
+    }//Parsing BSSDesc
+    else
+    {
+        smsLog(pMac, LOGE, FL("failed to parse BssDesc\n"));
+    }
+}
+
+
+static void csrSetCfgRateSetFromProfile( tpAniSirGlobal pMac,
+                                         tCsrRoamProfile *pProfile  )
+{
+    tSirMacRateSetIE DefaultSupportedRates11a = {  SIR_MAC_RATESET_EID, 
+                                                   { 8, 
+                                                     { SIR_MAC_RATE_6, 
+                                                   SIR_MAC_RATE_9, 
+                                                   SIR_MAC_RATE_12, 
+                                                   SIR_MAC_RATE_18,
+                                                   SIR_MAC_RATE_24,
+                                                   SIR_MAC_RATE_36,
+                                                   SIR_MAC_RATE_48,
+                                                       SIR_MAC_RATE_54  } } };
+
+    tSirMacRateSetIE DefaultSupportedRates11b = {  SIR_MAC_RATESET_EID, 
+                                                   { 4, 
+                                                     { SIR_MAC_RATE_1, 
+                                                   SIR_MAC_RATE_2, 
+                                                   SIR_MAC_RATE_5_5, 
+                                                       SIR_MAC_RATE_11  } } };
+                                                              
+                                                              
+    tSirMacPropRateSet DefaultSupportedPropRates = { 3, 
+                                                     { SIR_MAC_RATE_72,
+                                                     SIR_MAC_RATE_96,
+                                                       SIR_MAC_RATE_108 } };
+    eCsrCfgDot11Mode cfgDot11Mode;
+    eCsrBand eBand;
+    tANI_U8 OperationalRates[ CSR_DOT11_SUPPORTED_RATES_MAX ];    // leave enough room for the max number of rates
+    tANI_U32 OperationalRatesLength = 0;
+    tANI_U8 ExtendedOperationalRates[ CSR_DOT11_EXTENDED_SUPPORTED_RATES_MAX ];    // leave enough room for the max number of rates
+    tANI_U32 ExtendedOperationalRatesLength = 0;
+    tANI_U8 ProprietaryOperationalRates[ 4 ];    // leave enough room for the max number of proprietary rates
+    tANI_U32 ProprietaryOperationalRatesLength = 0;
+    tANI_U32 PropRatesEnable = 0;
+    tANI_U8 operationChannel = 0; 
+
+    if(pProfile->ChannelInfo.ChannelList)
+    {
+       operationChannel = pProfile->ChannelInfo.ChannelList[0];
+    }
+
+#ifdef WLAN_SOFTAP_FEATURE
+    cfgDot11Mode = csrRoamGetPhyModeBandForBss( pMac, pProfile, operationChannel, &eBand );
+#else
+    cfgDot11Mode = csrRoamGetPhyModeBandForBss( pMac, (eCsrPhyMode)pProfile->phyMode, operationChannel, &eBand );
+#endif
+    // For 11a networks, the 11a rates go into the Operational Rate set.  For 11b and 11g 
+    // networks, the 11b rates appear in the Operational Rate set.  In either case,
+    // we can blindly put the rates we support into our Operational Rate set 
+    // (including the basic rates, which we have already verified are supported 
+    // earlier in the roaming decision).
+    if ( eCSR_BAND_5G == eBand ) 
+    {       
+        // 11a rates into the Operational Rate Set.                 
+        OperationalRatesLength = DefaultSupportedRates11a.supportedRateSet.numRates *
+                                            sizeof(*DefaultSupportedRates11a.supportedRateSet.rate);
+        palCopyMemory( pMac->hHdd, OperationalRates,         
+                        DefaultSupportedRates11a.supportedRateSet.rate, 
+                        OperationalRatesLength );
+                         
+        // Nothing in the Extended rate set.
+        ExtendedOperationalRatesLength = 0;
+
+        // populate proprietary rates if user allows them
+        if ( pMac->roam.configParam.ProprietaryRatesEnabled ) 
+        {
+            ProprietaryOperationalRatesLength = DefaultSupportedPropRates.numPropRates * 
+                                                            sizeof(*DefaultSupportedPropRates.propRate);         
+            palCopyMemory( pMac->hHdd, ProprietaryOperationalRates,
+                            DefaultSupportedPropRates.propRate, 
+                            ProprietaryOperationalRatesLength );
+        }    
+        else 
+        {       
+            // No proprietary modes
+            ProprietaryOperationalRatesLength = 0;         
+        }    
+    }    
+    else if ( eCSR_CFG_DOT11_MODE_11B == cfgDot11Mode ) 
+    {       
+        // 11b rates into the Operational Rate Set.         
+        OperationalRatesLength = DefaultSupportedRates11b.supportedRateSet.numRates *
+                                              sizeof(*DefaultSupportedRates11b.supportedRateSet.rate);
+        palCopyMemory( pMac->hHdd, OperationalRates, 
+                        DefaultSupportedRates11b.supportedRateSet.rate, 
+                        OperationalRatesLength );
+        // Nothing in the Extended rate set.
+        ExtendedOperationalRatesLength = 0;
+        // No proprietary modes
+        ProprietaryOperationalRatesLength = 0;
+    }    
+    else 
+    {       
+        // 11G
+        
+        // 11b rates into the Operational Rate Set.         
+        OperationalRatesLength = DefaultSupportedRates11b.supportedRateSet.numRates * 
+                                            sizeof(*DefaultSupportedRates11b.supportedRateSet.rate);
+        palCopyMemory( pMac->hHdd, OperationalRates, 
+                        DefaultSupportedRates11b.supportedRateSet.rate, 
+                        OperationalRatesLength );
+        
+        // 11a rates go in the Extended rate set.
+        ExtendedOperationalRatesLength = DefaultSupportedRates11a.supportedRateSet.numRates * 
+                                                    sizeof(*DefaultSupportedRates11a.supportedRateSet.rate);
+        palCopyMemory( pMac->hHdd, ExtendedOperationalRates,         
+                        DefaultSupportedRates11a.supportedRateSet.rate, 
+                        ExtendedOperationalRatesLength );
+        
+        // populate proprietary rates if user allows them
+        if ( pMac->roam.configParam.ProprietaryRatesEnabled ) 
+        {
+            ProprietaryOperationalRatesLength = DefaultSupportedPropRates.numPropRates *
+                                                            sizeof(*DefaultSupportedPropRates.propRate);         
+            palCopyMemory( pMac->hHdd, ProprietaryOperationalRates, 
+                            DefaultSupportedPropRates.propRate, 
+                            ProprietaryOperationalRatesLength );
+        }  
+        else 
+        {       
+           // No proprietary modes
+            ProprietaryOperationalRatesLength = 0;         
+        }    
+    }  
+
+    // set this to 1 if prop. rates need to be advertised in to the IBSS beacon and user wants to use them
+    if ( ProprietaryOperationalRatesLength && pMac->roam.configParam.ProprietaryRatesEnabled ) 
+    {
+        PropRatesEnable = 1;                
+    }
+    else 
+    {
+        PropRatesEnable = 0;    
+    }
+        
+    // Set the operational rate set CFG variables...
+    ccmCfgSetStr(pMac, WNI_CFG_OPERATIONAL_RATE_SET, OperationalRates, 
+                    OperationalRatesLength, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetStr(pMac, WNI_CFG_EXTENDED_OPERATIONAL_RATE_SET, ExtendedOperationalRates, 
+                        ExtendedOperationalRatesLength, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetStr(pMac, WNI_CFG_PROPRIETARY_OPERATIONAL_RATE_SET, 
+                    ProprietaryOperationalRates, 
+                    ProprietaryOperationalRatesLength, NULL, eANI_BOOLEAN_FALSE);
+    ccmCfgSetInt(pMac, WNI_CFG_PROPRIETARY_ANI_FEATURES_ENABLED, PropRatesEnable, NULL, eANI_BOOLEAN_FALSE);
+
+}
+
+void csrRoamCcmCfgSetCallback(tHalHandle hHal, tANI_S32 result)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tListElem *pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+    tANI_U32 sessionId;
+    tSmeCmd *pCommand = NULL;
+
+    if(NULL == pEntry)
+    {
+        smsLog(pMac, LOGW, "   CFG_CNF with active list empty\n");
+        return;
+    }
+    pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+    sessionId = pCommand->sessionId;
+
+    if(CSR_IS_ROAM_JOINING(pMac, sessionId) && CSR_IS_ROAM_SUBSTATE_CONFIG(pMac, sessionId))
+    {
+        csrRoamingStateConfigCnfProcessor(pMac, (tANI_U32)result);
+    }
+}
+
+
+//This function is very dump. It is here because PE still need WNI_CFG_PHY_MODE
+tANI_U32 csrRoamGetPhyModeFromDot11Mode(eCsrCfgDot11Mode dot11Mode, eCsrBand band)
+{
+    if(eCSR_CFG_DOT11_MODE_11B == dot11Mode)
+    {
+        return (WNI_CFG_PHY_MODE_11B);
+    }
+    else
+    {
+        if(eCSR_BAND_24 == band)
+            return (WNI_CFG_PHY_MODE_11G);
+    }
+
+    return (WNI_CFG_PHY_MODE_11A);
+}
+
+        
+//pIes may be NULL
+eHalStatus csrRoamSetBssConfigCfg(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile,
+                          tSirBssDescription *pBssDesc, tBssConfigParam *pBssConfig,
+                          tDot11fBeaconIEs *pIes)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32   cfgCb = WNI_CFG_CHANNEL_BONDING_MODE_DISABLE;
+    tANI_U8    channel = 0;
+    //Make sure we have the domain info for the BSS we try to connect to.
+    //Do we need to worry about sequence for OSs that are not Windows??
+    if(pBssDesc)
+    {
+        if(csrLearnCountryInformation(pMac, pBssDesc, pIes, eANI_BOOLEAN_TRUE))
+        {
+            //Make sure the 11d info from this BSSDesc can be applied
+            pMac->scan.fAmbiguous11dInfoFound = eANI_BOOLEAN_FALSE;
+            csrApplyCountryInformation( pMac, TRUE );
+        }
+    }
+        
+    //Qos
+    csrSetQosToCfg( pMac, sessionId, pBssConfig->qosType );
+    //SSID
+    csrSetCfgSsid(pMac, &pBssConfig->SSID );
+    //fragment threshold
+    //ccmCfgSetInt(pMac, WNI_CFG_FRAGMENTATION_THRESHOLD, csrGetFragThresh(pMac), NULL, eANI_BOOLEAN_FALSE);
+    //RTS threshold
+    //ccmCfgSetInt(pMac, WNI_CFG_RTS_THRESHOLD, csrGetRTSThresh(pMac), NULL, eANI_BOOLEAN_FALSE);
+
+    //ccmCfgSetInt(pMac, WNI_CFG_DOT11_MODE, csrTranslateToWNICfgDot11Mode(pMac, pBssConfig->uCfgDot11Mode), NULL, eANI_BOOLEAN_FALSE);
+        
+    //Auth type
+    ccmCfgSetInt(pMac, WNI_CFG_AUTHENTICATION_TYPE, pBssConfig->authType, NULL, eANI_BOOLEAN_FALSE);
+    //encryption type
+    csrSetCfgPrivacy(pMac, pProfile, (tANI_BOOLEAN)pBssConfig->BssCap.privacy );
+    //short slot time
+    ccmCfgSetInt(pMac, WNI_CFG_11G_SHORT_SLOT_TIME_ENABLED, pBssConfig->uShortSlotTime, NULL, eANI_BOOLEAN_FALSE);
+
+#ifdef WLAN_SOFTAP_FEATURE
+    //11d
+    ccmCfgSetInt(pMac, WNI_CFG_11D_ENABLED,
+                        ((pBssConfig->f11hSupport) ? pBssConfig->f11hSupport : pProfile->ieee80211d),
+                        NULL, eANI_BOOLEAN_FALSE);
+#endif
+    /*//11h
+    ccmCfgSetInt(pMac, WNI_CFG_11H_ENABLED, pMac->roam.configParam.Is11hSupportEnabled, NULL, eANI_BOOLEAN_FALSE);
+    */
+    ccmCfgSetInt(pMac, WNI_CFG_LOCAL_POWER_CONSTRAINT, pBssConfig->uPowerLimit, NULL, eANI_BOOLEAN_FALSE);
+    //CB
+    if(CSR_IS_INFRA_AP(pProfile) || CSR_IS_WDS_AP(pProfile))
+    {
+        channel = pProfile->operationChannel;
+    }
+    else
+    {
+        if(pBssDesc)
+        {
+            channel = pBssDesc->channelId;
+        }
+    }
+    if(0 != channel)
+    {
+        if(CSR_IS_CHANNEL_24GHZ(channel))
+        {//for now if we are on 2.4 Ghz, CB will be always disabled
+            cfgCb = WNI_CFG_CHANNEL_BONDING_MODE_DISABLE;
+        }
+        else
+        {
+           //cfgCb = pBssConfig->cbMode;
+           cfgCb = pMac->roam.configParam.channelBondingMode5GHz;
+        }
+    }
+    ccmCfgSetInt(pMac, WNI_CFG_CHANNEL_BONDING_MODE, cfgCb, NULL, eANI_BOOLEAN_FALSE);
+    //Rate
+    //Fixed Rate
+    if(pBssDesc)
+    {
+        csrSetCfgRateSet(pMac, (eCsrPhyMode)pProfile->phyMode, pProfile, pBssDesc, pIes);
+    }
+    else
+    {
+        csrSetCfgRateSetFromProfile(pMac, pProfile);
+    }
+    //Make this the last CFG to set. The callback will trigger a join_req
+    //Join time out
+    csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_CONFIG, sessionId );
+
+    ccmCfgSetInt(pMac, WNI_CFG_JOIN_FAILURE_TIMEOUT, pBssConfig->uJoinTimeOut, (tCcmCfgSetCallback)csrRoamCcmCfgSetCallback, eANI_BOOLEAN_FALSE);
+
+    return (status);
+}
+
+
+
+eHalStatus csrRoamStopNetwork( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                               tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes)
+{
+    eHalStatus status;
+    tBssConfigParam *pBssConfig;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    status = palAllocateMemory(pMac->hHdd, (void **)&pBssConfig, sizeof(tBssConfigParam)); 
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, pBssConfig, sizeof(tBssConfigParam));
+        status = csrRoamPrepareBssConfig(pMac, pProfile, pBssDesc, pBssConfig, pIes);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            pSession->bssParams.uCfgDot11Mode = pBssConfig->uCfgDot11Mode;
+            //For IBSS, we need to prepare some more information
+            if( csrIsBssTypeIBSS(pProfile->BSSType) || CSR_IS_WDS( pProfile )
+#ifdef WLAN_SOFTAP_FEATURE
+              || CSR_IS_INFRA_AP(pProfile)
+#endif
+            )
+            {
+                csrRoamPrepareBssParams(pMac, sessionId, pProfile, pBssDesc, pIes);
+            }
+            // If we are in an IBSS, then stop the IBSS...
+            ////Not worry about WDS connection for now
+            if ( csrIsConnStateIbss( pMac, sessionId ) ) 
+            {
+                status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING );
+            }
+            else 
+            {
+                // if we are in an Infrastructure association....
+                if ( csrIsConnStateInfra( pMac, sessionId ) ) 
+                {
+                    // and the new Bss is an Ibss OR we are roaming from Infra to Infra
+                    // across SSIDs (roaming to a new SSID)...            //            
+                    //Not worry about WDS connection for now
+                    if ( pBssDesc && ( ( csrIsIbssBssDesc( pBssDesc ) ) ||
+                          !csrIsSsidEqual( pMac, pSession->pConnectBssDesc, pBssDesc, pIes ) ) )   
+                    {
+                        // then we need to disassociate from the Infrastructure network...
+                        status = csrRoamIssueDisassociate( pMac, sessionId, eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING, FALSE );  
+                    }
+                    else 
+                    {  
+                        // In an Infrastucture and going to an Infrastructure network with the same SSID.  This
+                        // calls for a Reassociation sequence.  So issue the CFG sets for this new AP.
+                        if ( pBssDesc ) 
+                        {
+                            // Set parameters for this Bss.    
+                            status = csrRoamSetBssConfigCfg(pMac, sessionId, pProfile, pBssDesc, pBssConfig, pIes);
+                        }
+                    }      
+                }
+                else 
+                {
+                    // Neiher in IBSS nor in Infra.  We can go ahead and set the CFG for tne new network...
+                    // Nothing to stop.
+                    if ( pBssDesc || CSR_IS_WDS_AP( pProfile )
+#ifdef WLAN_SOFTAP_FEATURE
+                     || CSR_IS_INFRA_AP(pProfile)
+#endif
+                    ) 
+                    {      
+                        // Set parameters for this Bss.    
+                        status = csrRoamSetBssConfigCfg(pMac, sessionId, pProfile, pBssDesc, pBssConfig, pIes);
+                    }  
+                }
+            }
+        }//Success getting BSS config info
+        palFreeMemory(pMac->hHdd, pBssConfig);
+    }//Allocate memory
+    
+    return (status);
+}
+
+
+eCsrJoinState csrRoamJoin( tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                           tCsrScanResultInfo *pScanResult, tCsrRoamProfile *pProfile )
+{
+    eCsrJoinState eRoamState = eCsrContinueRoaming;
+    eHalStatus status;
+    tSirBssDescription *pBssDesc = &pScanResult->BssDescriptor;
+    tDot11fBeaconIEs *pIesLocal = (tDot11fBeaconIEs *)( pScanResult->pvIes ); //This may be NULL
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if( CSR_IS_WDS_STA( pProfile ) )
+    {
+        status = csrRoamStartWds( pMac, sessionId, pProfile, pBssDesc );
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            eRoamState = eCsrStopRoaming;
+        }
+    }
+    else
+    {
+        if( !pIesLocal && (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIesLocal))) )
+        {
+            smsLog(pMac, LOGE, FL(" fail to parse IEs"));
+            return (eCsrStopRoaming);
+        }
+        if ( csrIsInfraBssDesc( pBssDesc ) ) 
+    {
+        // If we are connected in infrastructure mode and the Join Bss description is for the same BssID, then we are
+        // attempting to join the AP we are already connected with.  In that case, see if the Bss or Sta capabilities
+        // have changed and handle the changes (without disturbing the current association).
+                
+        if ( csrIsConnStateConnectedInfra(pMac, sessionId) && 
+             csrIsBssIdEqual( pMac, pBssDesc, pSession->pConnectBssDesc ) &&
+                 csrIsSsidEqual( pMac, pSession->pConnectBssDesc, pBssDesc, pIesLocal )
+           )               
+        {   
+            // Check to see if the Auth type has changed in the Profile.  If so, we don't want to Reassociate
+            // with Authenticating first.  To force this, stop the current association (Disassociate) and 
+            // then re 'Join' the AP, wihch will force an Authentication (with the new Auth type) followed by 
+            // a new Association.
+            if(csrIsSameProfile(pMac, &pSession->connectedProfile, pProfile))
+            {
+                smsLog(pMac, LOGW, FL("  detect same profile authType = %d encryType = %d\n"), pProfile->AuthType, pProfile->EncryptionType);
+                if(csrRoamIsSameProfileKeys(pMac, &pSession->connectedProfile, pProfile))
+                {
+                    eRoamState = eCsrReassocToSelfNoCapChange;
+                }
+                else
+                {
+                    tBssConfigParam bssConfig;
+
+                    //The key changes
+                    palZeroMemory(pMac->hHdd, &bssConfig, sizeof(bssConfig));
+                    status = csrRoamPrepareBssConfig(pMac, pProfile, pBssDesc, &bssConfig, pIesLocal);
+                    if(HAL_STATUS_SUCCESS(status))
+                    {
+                        pSession->bssParams.uCfgDot11Mode = bssConfig.uCfgDot11Mode;
+                        //Reapply the config including Keys so reassoc is happening.
+                        status = csrRoamSetBssConfigCfg(pMac, sessionId, pProfile, pBssDesc, &bssConfig, pIesLocal);
+                        if(!HAL_STATUS_SUCCESS(status))
+                        {
+                            eRoamState = eCsrStopRoaming;
+                        }
+                    }
+                    else
+                    {
+                        eRoamState = eCsrStopRoaming;
+                    }
+                }//same profile
+            }
+            else
+            {
+                if(!HAL_STATUS_SUCCESS(csrRoamIssueDisassociate( pMac, sessionId, 
+                                                        eCSR_ROAM_SUBSTATE_DISASSOC_REQ, FALSE )))
+                {
+                    smsLog(pMac, LOGW, FL("  fail to issue disassociate\n"));
+                    eRoamState = eCsrStopRoaming;
+                }                       
+            }
+        }            
+        else 
+        {
+            // note:  we used to pre-auth here with open authentication networks but that was not working so well.
+            // we had a lot of join timeouts when testing at Samsung.  removing this step helped associations 
+            // work much better.
+            //
+            //
+            // stop the existing network before attempting to join the new network...
+                if(!HAL_STATUS_SUCCESS(csrRoamStopNetwork(pMac, sessionId, pProfile, pBssDesc, pIesLocal)))
+            {
+                eRoamState = eCsrStopRoaming;
+            }
+        }
+        }//Infra
+    else 
+    {
+            if(!HAL_STATUS_SUCCESS(csrRoamStopNetwork(pMac, sessionId, pProfile, pBssDesc, pIesLocal)))
+        {
+            eRoamState = eCsrStopRoaming;
+        }
+    }
+        if( pIesLocal && !pScanResult->pvIes )
+        {
+            palFreeMemory(pMac->hHdd, pIesLocal);
+        }
+    }
+
+    return( eRoamState );
+}
+
+
+eHalStatus csrRoamShouldRoam(tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                             tSirBssDescription *pBssDesc, tANI_U32 roamId)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamInfo roamInfo;
+
+    palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+    roamInfo.pBssDesc = pBssDesc;
+    status = csrRoamCallCallback(pMac, sessionId, &roamInfo, roamId, eCSR_ROAM_SHOULD_ROAM, eCSR_ROAM_RESULT_NONE);
+    return (status);
+}
+
+//In case no matching BSS is found, use whatever default we can find
+static void csrRoamAssignDefaultParam( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    //Need to get all negotiated types in place first
+    //auth type
+    switch( pCommand->u.roamCmd.roamProfile.AuthType.authType[0] ) //Take the prefered Auth type.
+    {
+        default:
+        case eCSR_AUTH_TYPE_WPA:
+        case eCSR_AUTH_TYPE_WPA_PSK:
+        case eCSR_AUTH_TYPE_WPA_NONE:
+        case eCSR_AUTH_TYPE_OPEN_SYSTEM:
+             pCommand->u.roamCmd.roamProfile.negotiatedAuthType = eCSR_AUTH_TYPE_OPEN_SYSTEM;
+             break;
+
+        case eCSR_AUTH_TYPE_SHARED_KEY:
+             pCommand->u.roamCmd.roamProfile.negotiatedAuthType = eCSR_AUTH_TYPE_SHARED_KEY;
+             break;
+
+        case eCSR_AUTH_TYPE_AUTOSWITCH:
+             pCommand->u.roamCmd.roamProfile.negotiatedAuthType = eCSR_AUTH_TYPE_AUTOSWITCH;
+             break;
+    }
+    pCommand->u.roamCmd.roamProfile.negotiatedUCEncryptionType = 
+    pCommand->u.roamCmd.roamProfile.EncryptionType.encryptionType[0]; 
+    //In this case, the multicast encryption needs to follow the uncast ones.
+    pCommand->u.roamCmd.roamProfile.negotiatedMCEncryptionType = 
+    pCommand->u.roamCmd.roamProfile.EncryptionType.encryptionType[0];
+}
+
+static eCsrJoinState csrRoamJoinNextBss( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fUseSameBss )
+{
+    eHalStatus status;
+    tCsrScanResult *pScanResult = NULL;
+    eCsrJoinState eRoamState = eCsrStopRoaming;
+    tScanResultList *pBSSList = (tScanResultList *)pCommand->u.roamCmd.hBSSList;
+    tANI_BOOLEAN fDone = eANI_BOOLEAN_FALSE;
+    tCsrRoamInfo roamInfo, *pRoamInfo = NULL;
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+    v_U8_t acm_mask = 0;
+#endif 
+    tANI_U32 sessionId = pCommand->sessionId;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tCsrRoamProfile *pProfile = &pCommand->u.roamCmd.roamProfile;
+    tANI_U8  concurrentChannel = 0;
+    
+    do  
+    {
+        // Check for Cardbus eject condition, before trying to Roam to any BSS
+        //***if( !balIsCardPresent(pAdapter) ) break;
+        
+        if(NULL != pBSSList)
+        {
+            // When handling AP's capability change, continue to associate to
+            // same BSS and make sure pRoamBssEntry is not Null.
+            if((eANI_BOOLEAN_FALSE == fUseSameBss) || (pCommand->u.roamCmd.pRoamBssEntry == NULL))
+            {
+                if(pCommand->u.roamCmd.pRoamBssEntry == NULL)
+                {
+                    //Try the first BSS
+                    pCommand->u.roamCmd.pLastRoamBss = NULL;
+                    pCommand->u.roamCmd.pRoamBssEntry = csrLLPeekHead(&pBSSList->List, LL_ACCESS_LOCK);
+                }
+                else
+                {
+                    pCommand->u.roamCmd.pRoamBssEntry = csrLLNext(&pBSSList->List, pCommand->u.roamCmd.pRoamBssEntry, LL_ACCESS_LOCK);
+                    if(NULL == pCommand->u.roamCmd.pRoamBssEntry)
+                    {
+                        //Done with all the BSSs
+                        //In this case,   will tell HDD the completion
+                        break;
+                    }
+                    else
+                    {
+                        //We need to indicate to HDD that we are done with this one.
+                        palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+                        roamInfo.pBssDesc = pCommand->u.roamCmd.pLastRoamBss;     //this shall not be NULL
+                        roamInfo.statusCode = pSession->joinFailStatusCode.statusCode;
+                        roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+                        pRoamInfo = &roamInfo;
+                    }
+                }
+                while(pCommand->u.roamCmd.pRoamBssEntry)
+                {
+                    pScanResult = GET_BASE_ADDR(pCommand->u.roamCmd.pRoamBssEntry, tCsrScanResult, Link);
+
+                    /*If concurrency enabled take the concurrent connected channel first. */
+                    /* Valid multichannel concurrent sessions exempted */
+                    if (vos_concurrent_sessions_running() && !csrIsValidMcConcurrentSession(pMac, sessionId))
+                    {
+                        concurrentChannel = 
+                            csrGetConcurrentOperationChannel(pMac);
+                        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, "%s: "
+                                " csr Concurrent Channel = %d", __FUNCTION__, concurrentChannel);
+
+                        if ((concurrentChannel) && 
+                                (concurrentChannel == 
+                                 pScanResult->Result.BssDescriptor.channelId))
+                        {
+                            //make this 0 because we do not want the 
+                            //below check to pass as we don't want to 
+                            //connect on other channel
+                            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+                                    FL("Concurrent channel match =%d"),
+                                    concurrentChannel);
+                            concurrentChannel = 0; 
+
+                        }
+                    }
+                    if ((vos_concurrent_sessions_running()) && 
+                         csrIsAnySessionInConnectState( pMac ))
+                    {
+                        pMac->roam.configParam.concurrencyEnabled = 1;
+                    }
+
+                    if (!concurrentChannel)
+                    {
+                        
+                        if(HAL_STATUS_SUCCESS(csrRoamShouldRoam(pMac,
+                            sessionId, &pScanResult->Result.BssDescriptor,
+                            pCommand->u.roamCmd.roamId)))
+                        {
+                            //Ok to roam this
+                            break;
+                        }
+                     }
+                    pCommand->u.roamCmd.pRoamBssEntry = csrLLNext(&pBSSList->List, pCommand->u.roamCmd.pRoamBssEntry, LL_ACCESS_LOCK);
+                    if(NULL == pCommand->u.roamCmd.pRoamBssEntry)
+                    {
+                        //Done with all the BSSs
+                        fDone = eANI_BOOLEAN_TRUE;
+                        break;
+                    }
+                }
+                if(fDone)
+                {
+                    break;
+                }
+            }
+        }
+        //We have something to roam, tell HDD when it is infra.
+        //For IBSS, the indication goes back to HDD via eCSR_ROAM_IBSS_IND
+        //For WDS, the indication is eCSR_ROAM_WDS_IND
+        if( CSR_IS_INFRASTRUCTURE( pProfile ) )
+        {
+            if(pRoamInfo)
+            {
+                pSession->bRefAssocStartCnt--;
+                //Complete the last association attemp because a new one is about to be tried
+                csrRoamCallCallback(pMac, sessionId, pRoamInfo, pCommand->u.roamCmd.roamId, 
+                                        eCSR_ROAM_ASSOCIATION_COMPLETION, 
+                                        eCSR_ROAM_RESULT_NOT_ASSOCIATED);
+            }
+            palZeroMemory(pMac->hHdd, &roamInfo, sizeof(roamInfo));
+            if(pScanResult)
+            {
+                tDot11fBeaconIEs *pIesLocal = (tDot11fBeaconIEs *)pScanResult->Result.pvIes;
+
+                if( !pIesLocal && (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, &pScanResult->Result.BssDescriptor, &pIesLocal))) )
+                {
+                    smsLog(pMac, LOGE, FL(" cannot parse IEs\n"));
+                    fDone = eANI_BOOLEAN_TRUE;
+                    eRoamState = eCsrStopRoaming;
+                    break;
+                }
+                roamInfo.pBssDesc = &pScanResult->Result.BssDescriptor;
+                pCommand->u.roamCmd.pLastRoamBss = roamInfo.pBssDesc;
+                //No need to put uapsd_mask in if the BSS doesn't support uAPSD
+                if( pCommand->u.roamCmd.roamProfile.uapsd_mask &&
+                    CSR_IS_QOS_BSS(pIesLocal) &&
+                    CSR_IS_UAPSD_BSS(pIesLocal) )
+                {
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+
+                    acm_mask = sme_QosGetACMMask(pMac, &pScanResult->Result.BssDescriptor, 
+                         pIesLocal);
+                    pCommand->u.roamCmd.roamProfile.uapsd_mask &= ~(acm_mask);
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+
+                }
+                else
+                {
+                    pCommand->u.roamCmd.roamProfile.uapsd_mask = 0;
+                }
+                if( pIesLocal && !pScanResult->Result.pvIes)
+                {
+                    palFreeMemory(pMac->hHdd, pIesLocal);
+                }
+            }
+            else
+            {
+                pCommand->u.roamCmd.roamProfile.uapsd_mask = 0;
+            }
+            roamInfo.pProfile = pProfile;
+            pSession->bRefAssocStartCnt++;
+            csrRoamCallCallback( pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                                 eCSR_ROAM_ASSOCIATION_START, eCSR_ROAM_RESULT_NONE );
+        }
+
+        if ( NULL == pCommand->u.roamCmd.pRoamBssEntry ) 
+        {
+            // If this is a start IBSS profile, then we need to start the IBSS.
+            if ( CSR_IS_START_IBSS(pProfile) ) 
+            {
+                tANI_BOOLEAN fSameIbss = eANI_BOOLEAN_FALSE;
+
+                // Attempt to start this IBSS...
+                csrRoamAssignDefaultParam( pMac, pCommand );
+                status = csrRoamStartIbss( pMac, sessionId, pProfile, &fSameIbss );
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    if ( fSameIbss ) 
+                    {
+                        eRoamState = eCsrStartIbssSameIbss;
+                    }
+                    else
+                    {
+                        eRoamState = eCsrContinueRoaming;
+                    }
+                }
+                else
+                {
+                    //it somehow fail need to stop
+                    eRoamState = eCsrStopRoaming;
+                }
+                break;
+            }
+            else if ( (CSR_IS_WDS_AP(pProfile))
+#ifdef WLAN_SOFTAP_FEATURE
+             || (CSR_IS_INFRA_AP(pProfile))
+#endif
+            )
+            {
+                // Attempt to start this WDS...
+                csrRoamAssignDefaultParam( pMac, pCommand );
+                /* For AP WDS, we dont have any BSSDescription */
+                status = csrRoamStartWds( pMac, sessionId, pProfile, NULL );
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    eRoamState = eCsrContinueRoaming;
+                }
+                else 
+                {
+                    //it somehow fail need to stop
+                    eRoamState = eCsrStopRoaming;
+                }
+            }
+            else 
+            {
+                //Nothing we can do
+                smsLog(pMac, LOGW, FL("cannot continue without BSS list\n"));
+                eRoamState = eCsrStopRoaming;
+                break;
+            }
+        } 
+        else //We have BSS 
+        {
+            //Need to assign these value because they are used in csrIsSameProfile
+            pScanResult = GET_BASE_ADDR(pCommand->u.roamCmd.pRoamBssEntry, tCsrScanResult, Link);
+            pCommand->u.roamCmd.roamProfile.negotiatedUCEncryptionType = pScanResult->ucEncryptionType; //Negotiated while building scan result.
+            pCommand->u.roamCmd.roamProfile.negotiatedMCEncryptionType = pScanResult->mcEncryptionType;
+            pCommand->u.roamCmd.roamProfile.negotiatedAuthType = pScanResult->authType;
+            if ( CSR_IS_START_IBSS(&pCommand->u.roamCmd.roamProfile) )
+            {
+                if(csrIsSameProfile(pMac, &pSession->connectedProfile, pProfile))
+                {
+                    eRoamState = eCsrStartIbssSameIbss;
+                    break;
+                } 
+            }
+            if( pCommand->u.roamCmd.fReassocToSelfNoCapChange )
+            {
+                //trying to connect to the one already connected
+                pCommand->u.roamCmd.fReassocToSelfNoCapChange = eANI_BOOLEAN_FALSE;
+                eRoamState = eCsrReassocToSelfNoCapChange;
+                break;
+            }
+            // Attempt to Join this Bss...
+            eRoamState = csrRoamJoin( pMac, sessionId, &pScanResult->Result, pProfile );
+            break;
+        }
+        
+    } while( 0 );
+
+    if( (eCsrStopRoaming == eRoamState) && (CSR_IS_INFRASTRUCTURE( pProfile )) )
+    {
+        //Need to indicate association_completion if association_start has been done
+        if(pSession->bRefAssocStartCnt > 0)
+        {
+            pSession->bRefAssocStartCnt--;
+            //Complete the last association attemp because a new one is about to be tried
+            csrRoamCallCallback(pMac, sessionId, pRoamInfo, pCommand->u.roamCmd.roamId, 
+                                        eCSR_ROAM_ASSOCIATION_COMPLETION, 
+                                        eCSR_ROAM_RESULT_NOT_ASSOCIATED);
+        }
+    }
+
+    return( eRoamState );
+}
+
+
+static eHalStatus csrRoam( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    eCsrJoinState RoamState;
+    tANI_U32 sessionId = pCommand->sessionId;
+    
+    smsLog(pMac, LOG2, FL("is called\n"));
+    //***if( hddIsRadioStateOn( pAdapter ) )
+    {
+        // Attept to join a Bss...
+        RoamState = csrRoamJoinNextBss( pMac, pCommand, eANI_BOOLEAN_FALSE );
+    
+        // if nothing to join..
+        if ( eCsrStopRoaming == RoamState ) 
+        {
+            tANI_BOOLEAN fComplete = eANI_BOOLEAN_FALSE;
+
+            // and if connected in Infrastructure mode...
+            if ( csrIsConnStateInfra(pMac, sessionId) ) 
+            {
+                //... then we need to issue a disassociation
+                status = csrRoamIssueDisassociate( pMac, sessionId, eCSR_ROAM_SUBSTATE_DISASSOC_NOTHING_TO_JOIN, FALSE );
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    smsLog(pMac, LOGW, FL("  failed to issue disassociate, status = %d\n"), status);
+                    //roam command is completed by caller in the failed case
+                    fComplete = eANI_BOOLEAN_TRUE;
+                }
+            }
+            else if( csrIsConnStateIbss(pMac, sessionId) )
+            {
+                status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_STOP_BSS_REQ );
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    smsLog(pMac, LOGW, FL("  failed to issue stop bss, status = %d\n"), status);
+                    //roam command is completed by caller in the failed case
+                    fComplete = eANI_BOOLEAN_TRUE;
+                }
+            }
+#ifdef WLAN_SOFTAP_FEATURE
+            else if (csrIsConnStateConnectedInfraAp(pMac, sessionId))
+            {
+                status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_STOP_BSS_REQ );
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    smsLog(pMac, LOGW, FL("  failed to issue stop bss, status = %d\n"), status);
+                    //roam command is completed by caller in the failed case
+                    fComplete = eANI_BOOLEAN_TRUE;
+                }
+            }
+#endif
+            else
+            {        
+                fComplete = eANI_BOOLEAN_TRUE;
+            }
+            if(fComplete)
+            {
+               // ... otherwise, we can complete the Roam command here.
+               csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+            }    
+       }
+       else if ( eCsrReassocToSelfNoCapChange == RoamState )
+       {
+           csrRoamComplete( pMac, eCsrSilentlyStopRoamingSaveState, NULL );
+       }
+       else if ( eCsrStartIbssSameIbss == RoamState )
+       {
+           csrRoamComplete( pMac, eCsrSilentlyStopRoaming, NULL );        
+       }
+    }//hddIsRadioStateOn
+    
+    return status;
+}
+
+eHalStatus csrProcessFTReassocRoamCommand ( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    tANI_U32 sessionId;
+    tCsrRoamSession *pSession;
+    tCsrScanResult *pScanResult = NULL;
+    tSirBssDescription *pBssDesc = NULL;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    sessionId = pCommand->sessionId;
+    pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if(CSR_IS_ROAMING(pSession) && pSession->fCancelRoaming)
+    {
+        //the roaming is cancelled. Simply complete the command
+        smsLog(pMac, LOG1, FL("  Roam command cancelled\n"));
+        csrRoamComplete(pMac, eCsrNothingToJoin, NULL); 
+        return eHAL_STATUS_FAILURE;
+    }
+
+    if (pCommand->u.roamCmd.pRoamBssEntry)
+    {
+        pScanResult = GET_BASE_ADDR(pCommand->u.roamCmd.pRoamBssEntry, tCsrScanResult, Link);
+        pBssDesc = &pScanResult->Result.BssDescriptor;
+    }
+    else
+    {
+        //the roaming is cancelled. Simply complete the command
+        smsLog(pMac, LOG1, FL("  Roam command cancelled\n"));
+        csrRoamComplete(pMac, eCsrNothingToJoin, NULL); 
+        return eHAL_STATUS_FAILURE;
+    }
+
+    status = csrRoamIssueReassociate(pMac, sessionId, pBssDesc, 
+        (tDot11fBeaconIEs *)( pScanResult->Result.pvIes ), &pCommand->u.roamCmd.roamProfile);
+    return status;
+}
+
+
+eHalStatus csrRoamProcessCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamInfo roamInfo;
+    tANI_U32 sessionId = pCommand->sessionId;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    switch ( pCommand->u.roamCmd.roamReason )
+    {
+    case eCsrForcedDisassoc:
+        csrFreeRoamProfile(pMac, sessionId);
+        status = csrRoamProcessDisassocDeauth( pMac, pCommand, TRUE, FALSE );
+        break;
+
+     case eCsrSmeIssuedDisassocForHandoff:
+        //Not to free pMac->roam.pCurRoamProfile (via csrFreeRoamProfile) because it is needed after disconnect
+#if 0 // TODO : Confirm this change
+        status = csrRoamProcessDisassociate( pMac, pCommand, FALSE );
+#else
+        status = csrRoamProcessDisassocDeauth( pMac, pCommand, TRUE, FALSE );
+#endif
+
+        break;
+
+    case eCsrForcedDisassocMICFailure:
+        csrFreeRoamProfile(pMac, sessionId);
+        status = csrRoamProcessDisassocDeauth( pMac, pCommand, TRUE, TRUE );
+        break;
+
+    case eCsrForcedDeauth:
+        csrFreeRoamProfile(pMac, sessionId);
+        status = csrRoamProcessDisassocDeauth( pMac, pCommand, FALSE, FALSE );
+        break;
+
+    case eCsrHddIssuedReassocToSameAP:
+    case eCsrSmeIssuedReassocToSameAP:
+    {
+        tDot11fBeaconIEs *pIes = NULL;
+
+
+        if( pSession->pConnectBssDesc )
+        {
+            status = csrGetParsedBssDescriptionIEs(pMac, pSession->pConnectBssDesc, &pIes);
+            if(!HAL_STATUS_SUCCESS(status) )
+            {
+                smsLog(pMac, LOGE, FL("  fail to parse IEs\n"));
+            }
+            else
+            {
+                roamInfo.reasonCode = eCsrRoamReasonStaCapabilityChanged;
+                csrRoamCallCallback(pMac, pSession->sessionId, &roamInfo, 0, eCSR_ROAM_ROAMING_START, eCSR_ROAM_RESULT_NONE);
+                pSession->roamingReason = eCsrReassocRoaming;
+
+                roamInfo.pBssDesc = pSession->pConnectBssDesc;
+                roamInfo.pProfile = &pCommand->u.roamCmd.roamProfile;
+                pSession->bRefAssocStartCnt++;
+                csrRoamCallCallback( pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                                     eCSR_ROAM_ASSOCIATION_START, eCSR_ROAM_RESULT_NONE );
+   
+                smsLog(pMac, LOG1, FL("  calling csrRoamIssueReassociate\n"));
+                csrRoamIssueReassociate( pMac, sessionId, pSession->pConnectBssDesc, pIes,
+                                         &pCommand->u.roamCmd.roamProfile );
+                palFreeMemory(pMac->hHdd, pIes);
+                pIes = NULL;
+            }
+        }
+        break;
+    }
+
+    case eCsrCapsChange:
+        smsLog(pMac, LOGE, FL("received eCsrCapsChange \n"));
+        csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINING, sessionId );
+        status = csrRoamIssueDisassociate( pMac, sessionId, eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING, FALSE); 
+        break;
+
+    case eCsrSmeIssuedFTReassoc:
+        smsLog(pMac, LOGE, FL("received FT Reassoc Req \n"));
+        status = csrProcessFTReassocRoamCommand(pMac, pCommand);
+        break;
+    case eCsrStopBss:
+       csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINING, sessionId);
+       status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_STOP_BSS_REQ );
+       break;
+
+    case eCsrForcedDisassocSta:
+       csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINING, sessionId);
+       csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_DISASSOC_REQ, sessionId);
+       status = csrSendMBDisassocReqMsg( pMac, sessionId, pCommand->u.roamCmd.peerMac, 
+                     pCommand->u.roamCmd.reason);
+       break;
+
+    case eCsrForcedDeauthSta:
+       csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINING, sessionId);
+       csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_DEAUTH_REQ, sessionId);
+       status = csrSendMBDeauthReqMsg( pMac, sessionId, pCommand->u.roamCmd.peerMac, 
+                     pCommand->u.roamCmd.reason);
+       break;
+
+    default:
+        csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINING, sessionId );
+
+        if( pCommand->u.roamCmd.fUpdateCurRoamProfile )
+        {
+            //Remember the roaming profile 
+            csrFreeRoamProfile(pMac, sessionId);
+            if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, (void **)&pSession->pCurRoamProfile, sizeof(tCsrRoamProfile))))
+            {
+                palZeroMemory(pMac->hHdd, pSession->pCurRoamProfile, sizeof(tCsrRoamProfile));
+                csrRoamCopyProfile(pMac, pSession->pCurRoamProfile, &pCommand->u.roamCmd.roamProfile);
+            }
+        }
+ 
+        //At this point, original uapsd_mask is saved in pCurRoamProfile
+        //uapsd_mask in the pCommand may change from this point on.
+ 
+        // Attempt to roam with the new scan results (if we need to..)
+        status = csrRoam( pMac, pCommand );
+        break;
+    }
+
+    return (status);
+}
+
+
+void csrReinitRoamCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand) 
+{
+    if(pCommand->u.roamCmd.fReleaseBssList)
+    {
+        csrScanResultPurge(pMac, pCommand->u.roamCmd.hBSSList);
+        pCommand->u.roamCmd.fReleaseBssList = eANI_BOOLEAN_FALSE;
+        pCommand->u.roamCmd.hBSSList = CSR_INVALID_SCANRESULT_HANDLE;
+    }
+    if(pCommand->u.roamCmd.fReleaseProfile)
+    {
+        csrReleaseProfile(pMac, &pCommand->u.roamCmd.roamProfile);
+        pCommand->u.roamCmd.fReleaseProfile = eANI_BOOLEAN_FALSE;
+    }
+    pCommand->u.roamCmd.pRoamBssEntry = NULL;
+    //Because u.roamCmd is union and share with scanCmd and StatusChange
+    palZeroMemory(pMac->hHdd, &pCommand->u.roamCmd, sizeof(tRoamCmd));
+}
+
+
+void csrReinitWmStatusChangeCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    palZeroMemory(pMac->hHdd, &pCommand->u.wmStatusChangeCmd, sizeof(tWmStatusChangeCmd));
+}
+
+void csrRoamComplete( tpAniSirGlobal pMac, eCsrRoamCompleteResult Result, void *Context )
+{
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+    tANI_BOOLEAN fReleaseCommand = eANI_BOOLEAN_TRUE;
+
+    smsLog( pMac, LOG2, "roamQ: Roam Completion ...\n" );
+
+    pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+    if ( pEntry )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+
+        // If the head of the queue is Active and it is a ROAM command, remove
+        // and put this on the Free queue.
+        if ( eSmeCommandRoam == pCommand->command )
+        {
+            //we need to process the result first before removing it from active list because state changes 
+            //still happening insides roamQProcessRoamResults so no other roam command should be issued
+            fReleaseCommand = csrRoamProcessResults( pMac, pCommand, Result, Context );
+            if( fReleaseCommand )
+            {
+                if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+                {
+                    csrReleaseCommandRoam( pMac, pCommand );
+                }
+                else
+                {
+                    smsLog( pMac, LOGE, " **********csrRoamComplete fail to release command reason %d\n",
+                        pCommand->u.roamCmd.roamReason );
+                }
+            }
+            else
+            {
+                smsLog( pMac, LOGE, " **********csrRoamComplete fail to release command reason %d\n",
+                    pCommand->u.roamCmd.roamReason );
+            }
+        }
+        else
+        {
+            smsLog( pMac, LOGW, "CSR: Roam Completion called but ROAM command is not ACTIVE ...\n" );
+        }
+    }
+    else
+    {
+        smsLog( pMac, LOGW, "CSR: Roam Completion called but NO commands are ACTIVE ...\n" );
+    }
+
+    if( fReleaseCommand )
+    {
+        smeProcessPendingQueue( pMac );
+    }
+}
+
+
+void csrResetPMKIDCandidateList( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    palZeroMemory( pMac->hHdd, &(pSession->PmkidCandidateInfo[0]), sizeof(tPmkidCandidateInfo) * CSR_MAX_PMKID_ALLOWED );
+    pSession->NumPmkidCandidate = 0;
+}
+
+#ifdef FEATURE_WLAN_WAPI
+void csrResetBKIDCandidateList( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    palZeroMemory( pMac->hHdd, &(pSession->BkidCandidateInfo[0]), sizeof(tBkidCandidateInfo) * CSR_MAX_BKID_ALLOWED );
+    pSession->NumBkidCandidate = 0;
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+extern tANI_U8 csrWpaOui[][ CSR_WPA_OUI_SIZE ];
+
+
+
+static eHalStatus csrRoamSaveSecurityRspIE(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrAuthType authType, 
+                                         tSirBssDescription *pSirBssDesc,
+                                         tDot11fBeaconIEs *pIes)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tDot11fBeaconIEs *pIesLocal = pIes;
+
+    if((eCSR_AUTH_TYPE_WPA == authType) ||
+        (eCSR_AUTH_TYPE_WPA_PSK == authType) ||
+        (eCSR_AUTH_TYPE_RSN == authType) ||
+        (eCSR_AUTH_TYPE_RSN_PSK == authType)
+#if defined WLAN_FEATURE_VOWIFI_11R
+      ||
+       (eCSR_AUTH_TYPE_FT_RSN == authType) ||
+       (eCSR_AUTH_TYPE_FT_RSN_PSK == authType)
+#endif /* FEATURE_WLAN_WAPI */
+#ifdef FEATURE_WLAN_WAPI 
+      ||
+       (eCSR_AUTH_TYPE_WAPI_WAI_PSK == authType) ||
+       (eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE == authType)
+#endif /* FEATURE_WLAN_WAPI */
+        )
+    {
+
+        if( !pIesLocal && (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc, &pIesLocal))) )
+        {
+            smsLog(pMac, LOGE, FL(" cannot parse IEs\n"));
+        }
+        if( pIesLocal )
+        {
+            tANI_U32 nIeLen;
+            tANI_U8 *pIeBuf;
+
+            if((eCSR_AUTH_TYPE_RSN == authType) ||
+#if defined WLAN_FEATURE_VOWIFI_11R
+                (eCSR_AUTH_TYPE_FT_RSN == authType) ||
+                (eCSR_AUTH_TYPE_FT_RSN_PSK == authType) ||
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+                (eCSR_AUTH_TYPE_RSN_PSK == authType))
+            {
+                if(pIesLocal->RSN.present)
+                {
+                    //Calculate the actual length
+                    nIeLen = 8 //version + gp_cipher_suite + pwise_cipher_suite_count
+                        + pIesLocal->RSN.pwise_cipher_suite_count * 4    //pwise_cipher_suites
+                        + 2 //akm_suite_count
+                        + pIesLocal->RSN.akm_suite_count * 4 //akm_suites
+                        + 2; //reserved
+                    if( pIesLocal->RSN.pmkid_count )
+                    {
+                        nIeLen += 2 + pIesLocal->RSN.pmkid_count * 4;  //pmkid
+                    }
+                    //nIeLen doesn't count EID and length fields
+                    if(HAL_STATUS_SUCCESS((status = palAllocateMemory(pMac->hHdd, (void **)&pSession->pWpaRsnRspIE, nIeLen + 2))))
+                    {
+                        pSession->pWpaRsnRspIE[0] = DOT11F_EID_RSN;
+                        pSession->pWpaRsnRspIE[1] = (tANI_U8)nIeLen;
+                        //copy upto akm_suites
+                        pIeBuf = pSession->pWpaRsnRspIE + 2;
+                        palCopyMemory(pMac->hHdd, pIeBuf, &pIesLocal->RSN.version, 8);
+                        pIeBuf += 8;
+                        if( pIesLocal->RSN.pwise_cipher_suite_count )
+                        {
+                            //copy pwise_cipher_suites
+                            palCopyMemory(pMac->hHdd, pIeBuf, pIesLocal->RSN.pwise_cipher_suites, 
+                                            pIesLocal->RSN.pwise_cipher_suite_count * 4);
+                            pIeBuf += pIesLocal->RSN.pwise_cipher_suite_count * 4;
+                        }
+                        palCopyMemory(pMac->hHdd, pIeBuf, &pIesLocal->RSN.akm_suite_count, 2);
+                        pIeBuf += 2;
+                        if( pIesLocal->RSN.akm_suite_count )
+                        {
+                            //copy akm_suites
+                            palCopyMemory(pMac->hHdd, pIeBuf, pIesLocal->RSN.akm_suites, 
+                                            pIesLocal->RSN.akm_suite_count * 4);
+                            pIeBuf += pIesLocal->RSN.akm_suite_count * 4;
+                        }
+                        //copy the rest
+                        palCopyMemory(pMac->hHdd, pIeBuf, pIesLocal->RSN.akm_suites + 
+                                        pIesLocal->RSN.akm_suite_count * 4, 
+                                        2 + pIesLocal->RSN.pmkid_count * 4);
+                        pSession->nWpaRsnRspIeLength = nIeLen + 2; 
+                    }
+                }
+            }
+            else if((eCSR_AUTH_TYPE_WPA == authType) ||
+                (eCSR_AUTH_TYPE_WPA_PSK == authType))
+            {
+                if(pIesLocal->WPA.present)
+                {
+                    //Calculate the actual length
+                    nIeLen = 12 //OUI + version + multicast_cipher + unicast_cipher_count
+                        + pIesLocal->WPA.unicast_cipher_count * 4    //unicast_ciphers
+                        + 2 //auth_suite_count
+                        + pIesLocal->WPA.auth_suite_count * 4; //auth_suites
+                    // The WPA capabilities follows the Auth Suite (two octects)--
+                    // this field is optional, and we always "send" zero, so just
+                    // remove it.  This is consistent with our assumptions in the
+                    // frames compiler; c.f. bug 15234:
+                    //nIeLen doesn't count EID and length fields
+                    if(HAL_STATUS_SUCCESS((status = palAllocateMemory(pMac->hHdd, (void **)&pSession->pWpaRsnRspIE, nIeLen + 2))))
+                    {
+                        pSession->pWpaRsnRspIE[0] = DOT11F_EID_WPA;
+                        pSession->pWpaRsnRspIE[1] = (tANI_U8)nIeLen;
+                        pIeBuf = pSession->pWpaRsnRspIE + 2;
+                        //Copy WPA OUI
+                        palCopyMemory(pMac->hHdd, pIeBuf, &csrWpaOui[1], 4);
+                        pIeBuf += 4;
+                        palCopyMemory(pMac->hHdd, pIeBuf, &pIesLocal->WPA.version, 8 + 
+                                        pIesLocal->WPA.unicast_cipher_count * 4);
+                        pIeBuf += 8 + pIesLocal->WPA.unicast_cipher_count * 4;
+                        palCopyMemory(pMac->hHdd, pIeBuf, &pIesLocal->WPA.auth_suite_count, 2 + 
+                                        pIesLocal->WPA.auth_suite_count * 4);
+                        pIeBuf += pIesLocal->WPA.auth_suite_count * 4;
+                        pSession->nWpaRsnRspIeLength = nIeLen + 2; 
+                    }
+                }
+            }
+#ifdef FEATURE_WLAN_WAPI
+          else if((eCSR_AUTH_TYPE_WAPI_WAI_PSK == authType) ||
+                  (eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE == authType))
+          {
+                if(pIesLocal->WAPI.present)
+                {
+                   //Calculate the actual length
+                   nIeLen = 4 //version + akm_suite_count 
+                      + pIesLocal->WAPI.akm_suite_count * 4 // akm_suites
+                      + 2 //pwise_cipher_suite_count
+                      + pIesLocal->WAPI.unicast_cipher_suite_count * 4    //pwise_cipher_suites
+                      + 6; //gp_cipher_suite + preauth + reserved
+                      if( pIesLocal->WAPI.bkid_count )
+                      {
+                           nIeLen += 2 + pIesLocal->WAPI.bkid_count * 4;  //bkid
+        }
+                      
+                   //nIeLen doesn't count EID and length fields
+                   if(HAL_STATUS_SUCCESS((status = palAllocateMemory(pMac->hHdd, (void **)&pSession->pWapiRspIE, nIeLen + 2))))
+                   {
+                      pSession->pWapiRspIE[0] = DOT11F_EID_WAPI;
+                      pSession->pWapiRspIE[1] = (tANI_U8)nIeLen;
+                      pIeBuf = pSession->pWapiRspIE + 2;
+                      //copy upto akm_suite_count
+                      palCopyMemory(pMac->hHdd, pIeBuf, &pIesLocal->WAPI.version, 4);
+                      pIeBuf += 4;
+                      if( pIesLocal->WAPI.akm_suite_count )
+                      {
+                         //copy akm_suites
+                         palCopyMemory(pMac->hHdd, pIeBuf, pIesLocal->WAPI.akm_suites, 
+                                        pIesLocal->WAPI.akm_suite_count * 4);
+                         pIeBuf += pIesLocal->WAPI.akm_suite_count * 4;
+    }
+                      palCopyMemory(pMac->hHdd, pIeBuf, &pIesLocal->WAPI.unicast_cipher_suite_count, 2);
+                      pIeBuf += 2;
+
+                      if( pIesLocal->WAPI.unicast_cipher_suite_count )
+                      {
+                         //copy pwise_cipher_suites
+                         palCopyMemory(pMac->hHdd, pIeBuf, pIesLocal->WAPI.unicast_cipher_suites, 
+                                        pIesLocal->WAPI.unicast_cipher_suite_count * 4);
+                         pIeBuf += pIesLocal->WAPI.unicast_cipher_suite_count * 4;
+                      }
+                      //gp_cipher_suite + preauth + reserved + bkid_count
+                      palCopyMemory(pMac->hHdd, pIeBuf, &pIesLocal->WAPI.multicast_cipher_suite, 8);
+                      pIeBuf += 8;
+                      if( pIesLocal->WAPI.bkid_count )
+                      {
+                         //copy akm_suites
+                         palCopyMemory(pMac->hHdd, pIeBuf, pIesLocal->WAPI.bkid, pIesLocal->WAPI.bkid_count * 4);
+                         pIeBuf += pIesLocal->WAPI.bkid_count * 4;
+                      }
+                      pSession->nWapiRspIeLength = nIeLen + 2; 
+                   }
+
+                }
+          }
+#endif /* FEATURE_WLAN_WAPI */
+            if( !pIes )
+            {
+                //locally allocated
+                palFreeMemory(pMac->hHdd, pIesLocal);
+        }
+    }
+    }
+
+    return (status);
+}
+
+
+
+static void csrCheckAndUpdateACWeight( tpAniSirGlobal pMac, tDot11fBeaconIEs *pIEs )
+{
+    v_U8_t bACWeights[WLANTL_MAX_AC];
+    v_U8_t paramBk, paramBe, paramVi, paramVo;
+    v_BOOL_t fWeightChange = VOS_FALSE;
+
+    //Compare two ACs' EDCA parameters, from low to high (BK, BE, VI, VO)
+    //The "formula" is, if lower AC's AIFSN+CWMin is bigger than a fixed amount
+    //of the higher AC one, make the higher AC has the same weight as the lower AC.
+    //This doesn't address the case where the lower AC needs a real higher weight
+    if( pIEs->WMMParams.present )
+    {
+        //no change to the lowest ones
+        bACWeights[WLANTL_AC_BK] = pMac->roam.ucACWeights[WLANTL_AC_BK];
+        bACWeights[WLANTL_AC_BE] = pMac->roam.ucACWeights[WLANTL_AC_BE];
+        bACWeights[WLANTL_AC_VI] = pMac->roam.ucACWeights[WLANTL_AC_VI];
+        bACWeights[WLANTL_AC_VO] = pMac->roam.ucACWeights[WLANTL_AC_VO];
+        paramBk = pIEs->WMMParams.acbk_aifsn + pIEs->WMMParams.acbk_acwmin;
+        paramBe = pIEs->WMMParams.acbe_aifsn + pIEs->WMMParams.acbe_acwmin;
+        paramVi = pIEs->WMMParams.acvi_aifsn + pIEs->WMMParams.acvi_acwmin;
+        paramVo = pIEs->WMMParams.acvo_aifsn + pIEs->WMMParams.acvo_acwmin;
+        if( SME_DETECT_AC_WEIGHT_DIFF(paramBk, paramBe) )
+        {
+            bACWeights[WLANTL_AC_BE] = bACWeights[WLANTL_AC_BK];
+            fWeightChange = VOS_TRUE;
+        }
+        if( SME_DETECT_AC_WEIGHT_DIFF(paramBk, paramVi) )
+        {
+            bACWeights[WLANTL_AC_VI] = bACWeights[WLANTL_AC_BK];
+            fWeightChange = VOS_TRUE;
+        }
+        else if( SME_DETECT_AC_WEIGHT_DIFF(paramBe, paramVi) )
+        {
+            bACWeights[WLANTL_AC_VI] = bACWeights[WLANTL_AC_BE];
+            fWeightChange = VOS_TRUE;
+        }
+        if( SME_DETECT_AC_WEIGHT_DIFF(paramBk, paramVo) )
+        {
+            bACWeights[WLANTL_AC_VO] = bACWeights[WLANTL_AC_BK];
+            fWeightChange = VOS_TRUE;
+        }
+        else if( SME_DETECT_AC_WEIGHT_DIFF(paramBe, paramVo) )
+        {
+            bACWeights[WLANTL_AC_VO] = bACWeights[WLANTL_AC_BE];
+            fWeightChange = VOS_TRUE;
+        }
+        else if( SME_DETECT_AC_WEIGHT_DIFF(paramVi, paramVo) )
+        {
+            bACWeights[WLANTL_AC_VO] = bACWeights[WLANTL_AC_VI];
+            fWeightChange = VOS_TRUE;
+        }
+        if(fWeightChange)
+        {
+            smsLog(pMac, LOGE, FL(" change AC weights (%d-%d-%d-%d)\n"), bACWeights[0], bACWeights[1],
+                bACWeights[2], bACWeights[3]);
+            WLANTL_SetACWeights(pMac->roam.gVosContext, bACWeights);
+        }
+    }
+}
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+//Returns whether the current association is a 11r assoc or not
+tANI_BOOLEAN csrRoamIs11rAssoc(tpAniSirGlobal pMac)
+{
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+    return csrNeighborRoamIs11rAssoc(pMac);
+#else
+    return eANI_BOOLEAN_FALSE;
+#endif
+}
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+//Returns whether the current association is a CCX assoc or not
+tANI_BOOLEAN csrRoamIsCCXAssoc(tpAniSirGlobal pMac)
+{
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+    return csrNeighborRoamIsCCXAssoc(pMac);
+#else
+    return eANI_BOOLEAN_FALSE;
+#endif
+}
+#endif
+
+//Return true means the command can be release, else not
+static tANI_BOOLEAN csrRoamProcessResults( tpAniSirGlobal pMac, tSmeCmd *pCommand,
+                                       eCsrRoamCompleteResult Result, void *Context )
+{
+    tANI_BOOLEAN fReleaseCommand = eANI_BOOLEAN_TRUE;
+    tSirBssDescription *pSirBssDesc = NULL;   
+    tSirMacAddr BroadcastMac = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
+    tCsrScanResult *pScanResult = NULL;
+    tCsrRoamInfo roamInfo;
+    sme_QosAssocInfo assocInfo;
+    sme_QosCsrEventIndType ind_qos;//indication for QoS module in SME
+    tANI_U8 acm_mask = 0; //HDD needs the ACM mask in the assoc rsp callback
+    tDot11fBeaconIEs *pIes = NULL;
+    tANI_U32 sessionId = pCommand->sessionId;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tCsrRoamProfile *pProfile = &pCommand->u.roamCmd.roamProfile;
+    eRoamCmdStatus roamStatus;
+    eCsrRoamResult roamResult;
+    eHalStatus status;
+    tANI_U32 key_timeout_interval = 0;
+#ifdef WLAN_SOFTAP_FEATURE
+    tSirSmeStartBssRsp  *pSmeStartBssRsp = NULL;
+#endif
+
+
+    smsLog( pMac, LOG1, FL("Processing ROAM results...\n"));
+
+    switch( Result )
+    {
+        case eCsrJoinSuccess:
+            // reset the IDLE timer
+            // !!
+            // !! fall through to the next CASE statement here is intentional !!
+            // !!
+        case eCsrReassocSuccess:
+            if(eCsrReassocSuccess == Result)
+            {
+                ind_qos = SME_QOS_CSR_REASSOC_COMPLETE;
+            }
+            else
+            {
+                ind_qos = SME_QOS_CSR_ASSOC_COMPLETE;
+            }
+            // Success Join Response from LIM.  Tell NDIS we are connected and save the
+            // Connected state...
+            smsLog(pMac, LOGW, FL("receives association indication\n"));
+            palZeroMemory(pMac->hHdd, &roamInfo, sizeof(roamInfo));
+            //always free the memory here
+            if(pSession->pWpaRsnRspIE)
+            {
+                pSession->nWpaRsnRspIeLength = 0;
+                palFreeMemory(pMac->hHdd, pSession->pWpaRsnRspIE);
+                pSession->pWpaRsnRspIE = NULL;
+            }
+
+#ifdef FEATURE_WLAN_WAPI
+            if(pSession->pWapiRspIE)
+            {
+                pSession->nWapiRspIeLength = 0;
+                palFreeMemory(pMac->hHdd, pSession->pWapiRspIE);
+                pSession->pWapiRspIE = NULL;
+            }
+#endif /* FEATURE_WLAN_WAPI */
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+            //Reset counter so no join retry is needed.
+            pSession->maxRetryCount = 0;
+            csrRoamStopJoinRetryTimer(pMac, sessionId);
+#endif
+            /* This creates problem since we have not saved the connected profile.
+            So moving this after saving the profile
+            */
+            //csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINED );
+            if( CSR_IS_INFRASTRUCTURE( pProfile ) )
+            {
+                pSession->connectState = eCSR_ASSOC_STATE_TYPE_INFRA_ASSOCIATED;
+            }
+            else
+            {
+                pSession->connectState = eCSR_ASSOC_STATE_TYPE_WDS_CONNECTED;
+            }
+
+            //Use the last connected bssdesc for reassoc-ing to the same AP.
+            //NOTE: What to do when reassoc to a different AP???
+            if( (eCsrHddIssuedReassocToSameAP == pCommand->u.roamCmd.roamReason) ||
+                (eCsrSmeIssuedReassocToSameAP == pCommand->u.roamCmd.roamReason) )
+            {
+                pSirBssDesc = pSession->pConnectBssDesc;
+                if(pSirBssDesc)
+                {
+                    palCopyMemory(pMac->hHdd, &roamInfo.bssid, &pSirBssDesc->bssId, sizeof(tCsrBssid));
+                } 
+            }
+            else
+            {
+     
+                if(pCommand->u.roamCmd.pRoamBssEntry)
+                {
+                    pScanResult = GET_BASE_ADDR(pCommand->u.roamCmd.pRoamBssEntry, tCsrScanResult, Link);
+                    if(pScanResult != NULL)
+                    {
+                        pSirBssDesc = &pScanResult->Result.BssDescriptor;
+                        //this can be NULL
+                        pIes = (tDot11fBeaconIEs *)( pScanResult->Result.pvIes );
+                        palCopyMemory(pMac->hHdd, &roamInfo.bssid, &pSirBssDesc->bssId, sizeof(tCsrBssid));
+                    }
+                }
+            }
+            if( pSirBssDesc )
+            {
+
+                roamInfo.staId = HAL_STA_INVALID_IDX;
+
+                csrRoamSaveConnectedInfomation(pMac, sessionId, pProfile, pSirBssDesc, pIes);
+                    //Save WPA/RSN IE
+                csrRoamSaveSecurityRspIE(pMac, sessionId, pProfile->negotiatedAuthType, pSirBssDesc, pIes);
+#ifdef FEATURE_WLAN_CCX
+                roamInfo.isCCXAssoc = pSession->connectedProfile.isCCXAssoc;
+#endif
+                
+                // csrRoamStateChange also affects sub-state. Hence, csrRoamStateChange happens first and then
+                // substate change.
+                // Moving even save profile above so that below mentioned conditon is also met.
+                // JEZ100225: Moved to after saving the profile. Fix needed in main/latest
+                csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINED, sessionId );
+
+                // Make sure the Set Context is issued before link indication to NDIS.  After link indication is 
+                // made to NDIS, frames could start flowing.  If we have not set context with LIM, the frames
+                // will be dropped for the security context may not be set properly. 
+                //
+                // this was causing issues in the 2c_wlan_wep WHQL test when the SetContext was issued after the link
+                // indication.  (Link Indication happens in the profFSMSetConnectedInfra call).
+                //
+                // this reordering was done on titan_prod_usb branch and is being replicated here.
+                //
+            
+                if( CSR_IS_ENC_TYPE_STATIC( pProfile->negotiatedUCEncryptionType ) &&
+                                        !pProfile->bWPSAssociation)
+                {
+                    // Issue the set Context request to LIM to establish the Unicast STA context
+                    if( !HAL_STATUS_SUCCESS( csrRoamIssueSetContextReq( pMac, sessionId,
+                                                pProfile->negotiatedUCEncryptionType, 
+                                                pSirBssDesc, &(pSirBssDesc->bssId),
+                                                FALSE, TRUE, eSIR_TX_RX, 0, 0, NULL, 0 ) ) ) // NO keys... these key parameters don't matter.
+                    {
+                        smsLog( pMac, LOGE, FL("  Set context for unicast fail\n") );
+                        csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId );
+                    }
+                    // Issue the set Context request to LIM to establish the Broadcast STA context
+                    csrRoamIssueSetContextReq( pMac, sessionId, pProfile->negotiatedMCEncryptionType,
+                                               pSirBssDesc, &BroadcastMac,
+                                               FALSE, FALSE, eSIR_TX_RX, 0, 0, NULL, 0 ); // NO keys... these key parameters don't matter.
+                }
+                else
+                {
+                    //Need to wait for supplicant authtication
+                    roamInfo.fAuthRequired = eANI_BOOLEAN_TRUE;
+
+                    //Set the subestate to WaitForKey in case authentiation is needed
+                    csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_WAIT_FOR_KEY, sessionId );
+
+
+                    if(pProfile->bWPSAssociation)
+                    {
+                        key_timeout_interval = CSR_WAIT_FOR_WPS_KEY_TIMEOUT_PERIOD;
+                    }
+                    else
+                    {
+                        key_timeout_interval = CSR_WAIT_FOR_KEY_TIMEOUT_PERIOD;
+                    }
+                    
+                    //Save sessionId in case of timeout
+                    pMac->roam.WaitForKeyTimerInfo.sessionId = (tANI_U8)sessionId;
+                    //This time should be long enough for the rest of the process plus setting key
+                    if(!HAL_STATUS_SUCCESS( csrRoamStartWaitForKeyTimer( pMac, key_timeout_interval ) ) )
+                    {
+                        //Reset our state so nothting is blocked.
+                        smsLog( pMac, LOGE, FL("   Failed to start pre-auth timer\n") );
+                        csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId);
+                    }
+                }
+                
+                assocInfo.pBssDesc = pSirBssDesc; //could be NULL
+                assocInfo.pProfile = pProfile;
+
+                if(Context)
+                {
+                    tSirSmeJoinRsp *pJoinRsp = (tSirSmeJoinRsp *)Context;
+                    tANI_U32 len;
+
+                    csrRoamFreeConnectedInfo( pMac, &pSession->connectedInfo );
+                    len = pJoinRsp->assocReqLength + pJoinRsp->assocRspLength + pJoinRsp->beaconLength;
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                    len += pJoinRsp->parsedRicRspLen;
+#endif /* WLAN_FEATURE_VOWIFI_11R */                    
+#ifdef FEATURE_WLAN_CCX
+                    len += pJoinRsp->tspecIeLen;
+#endif
+                    if(len)
+                    {
+                        if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, 
+                                        (void **)&pSession->connectedInfo.pbFrames, len)))
+                        {
+                            if(HAL_STATUS_SUCCESS( palCopyMemory(pMac->hHdd, 
+                                            pSession->connectedInfo.pbFrames, pJoinRsp->frames, len) ))
+                            {
+                                pSession->connectedInfo.nAssocReqLength = pJoinRsp->assocReqLength;
+                                pSession->connectedInfo.nAssocRspLength = pJoinRsp->assocRspLength;
+                                pSession->connectedInfo.nBeaconLength = pJoinRsp->beaconLength;
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                                pSession->connectedInfo.nRICRspLength = pJoinRsp->parsedRicRspLen;
+#endif /* WLAN_FEATURE_VOWIFI_11R */                                
+#ifdef FEATURE_WLAN_CCX
+                                pSession->connectedInfo.nTspecIeLength = pJoinRsp->tspecIeLen;
+#endif
+                                roamInfo.nAssocReqLength = pJoinRsp->assocReqLength;
+                                roamInfo.nAssocRspLength = pJoinRsp->assocRspLength;
+                                roamInfo.nBeaconLength = pJoinRsp->beaconLength;
+                                roamInfo.pbFrames = pSession->connectedInfo.pbFrames;
+                            }
+                            else
+                            {
+                                smsLog(pMac, LOGE, "%s: Copying of memory failed for %d bytes !!!\n", 
+                                        __FUNCTION__, len);
+                                palFreeMemory( pMac->hHdd, pSession->connectedInfo.pbFrames );
+                                pSession->connectedInfo.pbFrames = NULL;
+                            }
+                        }
+                    }
+                    if(pCommand->u.roamCmd.fReassoc)
+                    {
+                        roamInfo.fReassocReq = roamInfo.fReassocRsp = eANI_BOOLEAN_TRUE;
+                    }
+                    pSession->connectedInfo.staId = ( tANI_U8 )pJoinRsp->staId;
+                    roamInfo.staId = ( tANI_U8 )pJoinRsp->staId;
+                    roamInfo.ucastSig = ( tANI_U8 )pJoinRsp->ucastSig;
+                    roamInfo.bcastSig = ( tANI_U8 )pJoinRsp->bcastSig;
+                }
+                else
+                {
+                   if(pCommand->u.roamCmd.fReassoc)
+                   {
+                       roamInfo.fReassocReq = roamInfo.fReassocRsp = eANI_BOOLEAN_TRUE;
+                       roamInfo.nAssocReqLength = pSession->connectedInfo.nAssocReqLength;
+                       roamInfo.nAssocRspLength = pSession->connectedInfo.nAssocRspLength;
+                       roamInfo.nBeaconLength = pSession->connectedInfo.nBeaconLength;
+                       roamInfo.pbFrames = pSession->connectedInfo.pbFrames;
+                   }
+                }
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                // Indicate SME-QOS with reassoc success event, only after 
+                // copying the frames 
+                sme_QosCsrEventInd(pMac, (v_U8_t)sessionId, ind_qos, &assocInfo);
+#endif
+
+
+                roamInfo.pBssDesc = pSirBssDesc;
+                roamInfo.statusCode = pSession->joinFailStatusCode.statusCode;
+                roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                acm_mask = sme_QosGetACMMask(pMac, pSirBssDesc, NULL);
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+                pSession->connectedProfile.acm_mask = acm_mask;
+
+#ifdef FEATURE_WLAN_UAPSD_FW_TRG_FRAMES
+                //start UAPSD if uapsd_mask is not 0 because HDD will configure for trigger frame
+                //It may be better to let QoS do this????
+                if( pSession->connectedProfile.modifyProfileFields.uapsd_mask )
+                {
+                    smsLog(pMac, LOGE, " uapsd_mask (0x%X) set, request UAPSD now\n",
+                        pSession->connectedProfile.modifyProfileFields.uapsd_mask);
+                    pmcStartUapsd( pMac, NULL, NULL );
+                }
+#endif
+
+                roamInfo.u.pConnectedProfile = &pSession->connectedProfile;
+                if( pSession->bRefAssocStartCnt > 0 )
+                {
+                    pSession->bRefAssocStartCnt--;
+                    csrRoamCallCallback(pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, eCSR_ROAM_ASSOCIATION_COMPLETION, eCSR_ROAM_RESULT_ASSOCIATED);
+                }
+                
+                csrRoamCompletion(pMac, sessionId, NULL, pCommand, eCSR_ROAM_RESULT_NONE, eANI_BOOLEAN_TRUE);
+
+                // reset the PMKID candidate list
+                csrResetPMKIDCandidateList( pMac, sessionId );
+                //Update TL's AC weight base on the current EDCA parameters
+                //These parameters may change in the course of the connection, that sictuation
+                //is not taken care here. This change is mainly to address a WIFI WMM test where
+                //BE has a equal or higher TX priority than VI. 
+                //We only do this for infra link
+                if( csrIsConnStateConnectedInfra(pMac, sessionId ) && pIes )
+                {
+                    csrCheckAndUpdateACWeight(pMac, pIes);
+                }
+#ifdef FEATURE_WLAN_WAPI
+                // reset the BKID candidate list
+                csrResetBKIDCandidateList( pMac, sessionId );
+#endif /* FEATURE_WLAN_WAPI */
+            }
+            else
+            {
+                smsLog(pMac, LOGW, "  Roam command doesn't have a BSS desc\n");
+            }
+
+            csrScanCancelIdleScan(pMac);
+            //Not to signal link up because keys are yet to be set.
+            //The linkup function will overwrite the sub-state that we need to keep at this point.
+            if( !CSR_IS_WAIT_FOR_KEY(pMac, sessionId) )
+            {
+                csrRoamLinkUp(pMac, pSession->connectedProfile.bssid);
+            }
+
+            //Check if BMPS is required and start the BMPS retry timer.  Timer period is large
+            //enough to let security and DHCP handshake succeed before entry into BMPS
+            if (pmcShouldBmpsTimerRun(pMac))
+            {
+                if (pmcStartTrafficTimer(pMac, BMPS_TRAFFIC_TIMER_ALLOW_SECURITY_DHCP)
+                    != eHAL_STATUS_SUCCESS)
+                {
+                    smsLog(pMac, LOGP, FL("Cannot start BMPS Retry timer"));
+                }
+                smsLog(pMac, LOG2, FL("BMPS Retry Timer already running or started"));
+            }
+
+            break;
+
+
+        case eCsrStartBssSuccess:
+            // on the StartBss Response, LIM is returning the Bss Description that we
+            // are beaconing.  Add this Bss Description to our scan results and
+            // chain the Profile to this Bss Description.  On a Start BSS, there was no
+            // detected Bss description (no partner) so we issued the Start Bss to
+            // start the Ibss without any Bss description.  Lim was kind enough to return
+            // the Bss Description that we start beaconing for the newly started Ibss.
+            smsLog(pMac, LOG2, FL("receives start BSS ok indication\n"));
+            status = eHAL_STATUS_FAILURE;
+#ifdef WLAN_SOFTAP_FEATURE
+            pSmeStartBssRsp = (tSirSmeStartBssRsp *)Context;
+#endif             
+            palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+            if( CSR_IS_IBSS( pProfile ) )
+            {
+                pSession->connectState = eCSR_ASSOC_STATE_TYPE_IBSS_DISCONNECTED;
+            }
+#ifdef WLAN_SOFTAP_FEATURE
+            else if (CSR_IS_INFRA_AP(pProfile))
+            {
+                pSession->connectState = eCSR_ASSOC_STATE_TYPE_INFRA_DISCONNECTED;
+            }
+#endif
+            else
+            {
+                pSession->connectState = eCSR_ASSOC_STATE_TYPE_WDS_DISCONNECTED;
+            }
+            if( !CSR_IS_WDS_STA( pProfile ) )
+            {
+                csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINED, sessionId );
+#ifdef WLAN_SOFTAP_FEATURE
+                pSirBssDesc = &pSmeStartBssRsp->bssDescription;
+#else
+                pSirBssDesc = (tSirBssDescription *)Context;
+#endif
+                if( !HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs( pMac, pSirBssDesc, &pIes )) )
+                {
+                    smsLog(pMac, LOG2, FL("cannot parse IBSS IEs\n"));
+                    roamInfo.pBssDesc = pSirBssDesc;
+                    //We need to associate_complete it first, becasue Associate_start already indicated.
+                    csrRoamCallCallback( pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                            eCSR_ROAM_IBSS_IND, eCSR_ROAM_RESULT_IBSS_START_FAILED );
+                    break;
+                }
+#ifdef WLAN_SOFTAP_FEATURE
+                if (!CSR_IS_INFRA_AP(pProfile))
+#endif
+                {
+                    pScanResult = csrScanAppendBssDescription( pMac, pSirBssDesc, pIes );
+                }
+                csrRoamSaveConnectedBssDesc(pMac, sessionId, pSirBssDesc);
+                csrRoamFreeConnectProfile(pMac, &pSession->connectedProfile);
+                csrRoamFreeConnectedInfo( pMac, &pSession->connectedInfo );
+                if(pSirBssDesc)
+                {
+                    csrRoamSaveConnectedInfomation(pMac, sessionId, pProfile, pSirBssDesc, pIes);
+                    palCopyMemory(pMac->hHdd, &roamInfo.bssid, &pSirBssDesc->bssId, sizeof(tCsrBssid));
+                }
+                //We are doen with the IEs so free it
+                palFreeMemory(pMac->hHdd, pIes);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                {
+                    vos_log_ibss_pkt_type *pIbssLog;
+                    tANI_U32 bi;
+    
+                    WLAN_VOS_DIAG_LOG_ALLOC(pIbssLog, vos_log_ibss_pkt_type, LOG_WLAN_IBSS_C);
+                    if(pIbssLog)
+                    { 
+                        if(CSR_INVALID_SCANRESULT_HANDLE == pCommand->u.roamCmd.hBSSList)
+                        {
+                            //We start the IBSS (didn't find any matched IBSS out there)
+                            pIbssLog->eventId = WLAN_IBSS_EVENT_START_IBSS_RSP;
+                        }
+                        else
+                        {
+                            pIbssLog->eventId = WLAN_IBSS_EVENT_JOIN_IBSS_RSP;
+                        }
+                        if(pSirBssDesc)
+                        {
+                            palCopyMemory(pMac->hHdd, pIbssLog->bssid, pSirBssDesc->bssId, 6);
+                            pIbssLog->operatingChannel = pSirBssDesc->channelId;
+                        }
+                        if(HAL_STATUS_SUCCESS(ccmCfgGetInt(pMac, WNI_CFG_BEACON_INTERVAL, &bi)))
+                        {
+                            //***U8 is not enough for beacon interval
+                            pIbssLog->beaconInterval = (v_U8_t)bi;
+                        }
+                        WLAN_VOS_DIAG_LOG_REPORT(pIbssLog);
+                    }
+                }
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                //Only set context for non-WDS_STA. We don't even need it for WDS_AP. But since the encryption
+                //is WPA2-PSK so it won't matter.
+
+#ifdef WLAN_SOFTAP_FEATURE
+                if( CSR_IS_ENC_TYPE_STATIC( pProfile->negotiatedUCEncryptionType ) && !CSR_IS_INFRA_AP( pSession->pCurRoamProfile ))
+                {
+#else 
+                if( CSR_IS_ENC_TYPE_STATIC( pProfile->negotiatedUCEncryptionType ))
+                {
+#endif
+                    // Issue the set Context request to LIM to establish the Broadcast STA context for the Ibss.
+                    csrRoamIssueSetContextReq( pMac, sessionId, 
+                                        pProfile->negotiatedMCEncryptionType, 
+                                        pSirBssDesc, &BroadcastMac,
+                                        FALSE, FALSE, eSIR_TX_RX, 0, 0, NULL, 0 ); // NO keys... these key parameters don't matter.
+                }
+            }
+            else
+            {
+                //Keep the state to eCSR_ROAMING_STATE_JOINING
+                //Need to send join_req.
+                if(pCommand->u.roamCmd.pRoamBssEntry)
+                {
+                    if((pScanResult = GET_BASE_ADDR(pCommand->u.roamCmd.pRoamBssEntry, tCsrScanResult, Link)))
+                    {
+                        pSirBssDesc = &pScanResult->Result.BssDescriptor;
+                        pIes = (tDot11fBeaconIEs *)( pScanResult->Result.pvIes );
+                        // Set the roaming substate to 'join attempt'...
+                        csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_JOIN_REQ, sessionId);
+                        status = csrSendJoinReqMsg( pMac, sessionId, pSirBssDesc, pProfile, pIes );
+                    }
+                }
+                else
+                {
+                    smsLog( pMac, LOGE, " StartBSS for WDS station with no BssDesc\n" );
+                    VOS_ASSERT( 0 );
+                }
+            }
+            //Only tell upper layer is we start the BSS because Vista doesn't like multiple connection
+            //indications. If we don't start the BSS ourself, handler of eSIR_SME_JOINED_NEW_BSS will 
+            //trigger the connection start indication in Vista
+            if( !CSR_IS_JOIN_TO_IBSS( pProfile ) )
+            {
+                roamStatus = eCSR_ROAM_IBSS_IND;
+                roamResult = eCSR_ROAM_RESULT_IBSS_STARTED;
+                if( CSR_IS_WDS( pProfile ) )
+                {
+                    roamStatus = eCSR_ROAM_WDS_IND;
+                    roamResult = eCSR_ROAM_RESULT_WDS_STARTED;
+                }
+#ifdef WLAN_SOFTAP_FEATURE
+                if( CSR_IS_INFRA_AP( pProfile ) )
+                {
+                    roamStatus = eCSR_ROAM_INFRA_IND;
+                    roamResult = eCSR_ROAM_RESULT_INFRA_STARTED;
+                }
+#endif  
+                 
+                //Only tell upper layer is we start the BSS because Vista doesn't like multiple connection
+                //indications. If we don't start the BSS ourself, handler of eSIR_SME_JOINED_NEW_BSS will 
+                //trigger the connection start indication in Vista
+                palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+                roamInfo.statusCode = pSession->joinFailStatusCode.statusCode;
+                roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+                if(CSR_INVALID_SCANRESULT_HANDLE == pCommand->u.roamCmd.hBSSList)
+                {
+                    //We start the IBSS (didn't find any matched IBSS out there)
+                    roamInfo.pBssDesc = pSirBssDesc;
+                }
+#ifdef WLAN_SOFTAP_FEATURE
+                roamInfo.staId = (tANI_U8)pSmeStartBssRsp->staId;
+#endif
+                csrRoamCallCallback( pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, roamStatus, roamResult );
+            }
+    
+            csrScanCancelIdleScan(pMac);
+            //Only use this timer for ibss. BAP has its own timer for WDS
+            if( CSR_IS_IBSS( pProfile) && CSR_INVALID_SCANRESULT_HANDLE != pCommand->u.roamCmd.hBSSList)
+            {
+              //start the join IBSS timer
+                csrRoamStartIbssJoinTimer(pMac, sessionId, CSR_IBSS_JOIN_TIMEOUT_PERIOD); //interval
+                pSession->ibss_join_pending = TRUE;
+            }
+            if( HAL_STATUS_SUCCESS( status ) )
+            {
+                //Already sent join_req for the WDS station
+                fReleaseCommand = eANI_BOOLEAN_FALSE;
+            }
+            else if( CSR_IS_WDS_STA( pProfile ) )
+            {
+                //need to send stop BSS because we fail to send join_req
+                csrRoamIssueDisassociateCmd( pMac, sessionId, eCSR_DISCONNECT_REASON_UNSPECIFIED );
+                csrRoamCallCallback( pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                                        eCSR_ROAM_WDS_IND, eCSR_ROAM_RESULT_WDS_STOPPED );
+            }
+
+            break;
+
+        case eCsrStartBssFailure:
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+            {
+                vos_log_ibss_pkt_type *pIbssLog;
+
+                WLAN_VOS_DIAG_LOG_ALLOC(pIbssLog, vos_log_ibss_pkt_type, LOG_WLAN_IBSS_C);
+                if(pIbssLog)
+                {
+                    pIbssLog->status = WLAN_IBSS_STATUS_FAILURE;
+                    WLAN_VOS_DIAG_LOG_REPORT(pIbssLog);
+                }
+            }
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+            roamStatus = eCSR_ROAM_IBSS_IND;
+            roamResult = eCSR_ROAM_RESULT_IBSS_STARTED;
+            if( CSR_IS_WDS( pProfile ) )
+            {
+                roamStatus = eCSR_ROAM_WDS_IND;
+                roamResult = eCSR_ROAM_RESULT_WDS_STARTED;
+            }
+#ifdef WLAN_SOFTAP_FEATURE
+            if( CSR_IS_INFRA_AP( pProfile ) )
+            {
+                roamStatus = eCSR_ROAM_INFRA_IND;
+                roamResult = eCSR_ROAM_RESULT_INFRA_START_FAILED;
+            }
+#endif
+            if(Context)
+            {
+                pSirBssDesc = (tSirBssDescription *)Context;
+            }
+            else
+            {
+                pSirBssDesc = NULL;
+            }
+            palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+            roamInfo.pBssDesc = pSirBssDesc;
+            //We need to associate_complete it first, becasue Associate_start already indicated.
+            csrRoamCallCallback( pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, roamStatus, roamResult );
+            csrSetDefaultDot11Mode( pMac );
+            break;
+
+        case eCsrSilentlyStopRoaming:
+            // We are here because we try to start the same IBSS
+            //No message to PE
+            // return the roaming state to Joined.
+            smsLog(pMac, LOGW, FL("receives silently roaming indication\n"));
+            csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINED, sessionId );
+            csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId );
+            palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+            roamInfo.pBssDesc = pSession->pConnectBssDesc;
+            if( roamInfo.pBssDesc )
+            {
+                palCopyMemory(pMac->hHdd, &roamInfo.bssid, &roamInfo.pBssDesc->bssId, sizeof(tCsrBssid));
+            }
+            //Since there is no change in the current state, simply pass back no result otherwise
+            //HDD may be mistakenly mark to disconnected state.
+            csrRoamCallCallback( pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                                        eCSR_ROAM_IBSS_IND, eCSR_ROAM_RESULT_NONE );
+
+            break;
+
+        case eCsrSilentlyStopRoamingSaveState:
+            //We are here because we try to connect to the same AP
+            //No message to PE
+            smsLog(pMac, LOGW, FL("receives silently stop roaming indication\n"));
+            palZeroMemory(pMac->hHdd, &roamInfo, sizeof(roamInfo));
+            
+            //to aviod resetting the substate to NONE
+            pMac->roam.curState[sessionId] = eCSR_ROAMING_STATE_JOINED;
+            //No need to change substate to wai_for_key because there is no state change
+            roamInfo.pBssDesc = pSession->pConnectBssDesc;
+            if( roamInfo.pBssDesc )
+            {
+                palCopyMemory(pMac->hHdd, &roamInfo.bssid, &roamInfo.pBssDesc->bssId, sizeof(tCsrBssid));
+            }
+
+            roamInfo.statusCode = pSession->joinFailStatusCode.statusCode;
+            roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+            roamInfo.nBeaconLength = pSession->connectedInfo.nBeaconLength;
+            roamInfo.nAssocReqLength = pSession->connectedInfo.nAssocReqLength;
+            roamInfo.nAssocRspLength = pSession->connectedInfo.nAssocRspLength;
+            roamInfo.pbFrames = pSession->connectedInfo.pbFrames;
+            roamInfo.staId = pSession->connectedInfo.staId;
+            roamInfo.u.pConnectedProfile = &pSession->connectedProfile;
+#if defined(VOSS_ENABLED)
+            VOS_ASSERT( roamInfo.staId != 0 );
+#endif
+            pSession->bRefAssocStartCnt--;
+            csrRoamCallCallback(pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                                        eCSR_ROAM_ASSOCIATION_COMPLETION, eCSR_ROAM_RESULT_ASSOCIATED);
+            csrRoamCompletion(pMac, sessionId, NULL, pCommand, eCSR_ROAM_RESULT_ASSOCIATED, eANI_BOOLEAN_TRUE);
+            break;
+
+        case eCsrReassocFailure:
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+            sme_QosCsrEventInd(pMac, (tANI_U8)sessionId, SME_QOS_CSR_REASSOC_FAILURE, NULL);
+#endif
+        case eCsrJoinWdsFailure:
+            smsLog(pMac, LOGW, FL("failed to join WDS\n"));
+            csrFreeConnectBssDesc(pMac, sessionId);
+            csrRoamFreeConnectProfile(pMac, &pSession->connectedProfile);
+            csrRoamFreeConnectedInfo( pMac, &pSession->connectedInfo );
+            palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+            roamInfo.pBssDesc = pCommand->u.roamCmd.pLastRoamBss;
+            roamInfo.statusCode = pSession->joinFailStatusCode.statusCode;
+            roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+            csrRoamCallCallback(pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                                    eCSR_ROAM_WDS_IND, 
+                                    eCSR_ROAM_RESULT_WDS_NOT_ASSOCIATED);
+            //Need to issue stop_bss
+            break;
+
+        case eCsrJoinFailure:
+        case eCsrNothingToJoin:
+        default:
+        {
+            smsLog(pMac, LOGW, FL("receives no association indication\n"));
+            if( CSR_IS_INFRASTRUCTURE( &pSession->connectedProfile ) || 
+                CSR_IS_ROAM_SUBSTATE_STOP_BSS_REQ( pMac, sessionId ) )
+            {
+                //do not free for the other profiles as we need to send down stop BSS later
+                csrFreeConnectBssDesc(pMac, sessionId);
+                csrRoamFreeConnectProfile(pMac, &pSession->connectedProfile);
+                csrRoamFreeConnectedInfo( pMac, &pSession->connectedInfo );
+                csrSetDefaultDot11Mode( pMac );
+            }
+
+            switch( pCommand->u.roamCmd.roamReason )
+            {
+                // If this transition is because of an 802.11 OID, then we transition
+                // back to INIT state so we sit waiting for more OIDs to be issued and
+                // we don't start the IDLE timer.
+                case eCsrSmeIssuedAssocToSimilarAP:
+                case eCsrHddIssued:
+                    csrRoamStateChange( pMac, eCSR_ROAMING_STATE_IDLE, sessionId );
+                    palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+                    roamInfo.pBssDesc = pCommand->u.roamCmd.pLastRoamBss;
+                    roamInfo.statusCode = pSession->joinFailStatusCode.statusCode;
+                    roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+
+                    /* Defeaturize this later if needed */
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+                    /* If Join fails while Handoff is in progress, indicate disassociated event to supplicant to reconnect */
+                    if (csrRoamIsHandoffInProgress(pMac))
+                    {
+                        csrRoamCallCallback(pMac, sessionId, NULL, pCommand->u.roamCmd.roamId, eCSR_ROAM_DISASSOCIATED, eCSR_ROAM_RESULT_FORCED);
+                        /* Should indicate neighbor roam algorithm about the connect failure here */
+                        csrNeighborRoamIndicateConnect(pMac, (tANI_U8)sessionId, VOS_STATUS_E_FAILURE);
+                    }
+                    else
+#endif
+                    {
+                        if(pSession->bRefAssocStartCnt > 0)
+                        {
+                            pSession->bRefAssocStartCnt--;
+                            csrRoamCallCallback(pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                                                eCSR_ROAM_ASSOCIATION_COMPLETION, 
+                                                eCSR_ROAM_RESULT_FAILURE);
+                        }
+                    }
+                    smsLog(pMac, LOG1, FL("  roam(reason %d) failed\n"), pCommand->u.roamCmd.roamReason);
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                    sme_QosCsrEventInd(pMac, (tANI_U8)sessionId, SME_QOS_CSR_DISCONNECT_IND, NULL);
+#endif
+                    csrRoamCompletion(pMac, sessionId, NULL, pCommand, eCSR_ROAM_RESULT_FAILURE, eANI_BOOLEAN_FALSE);
+                    csrScanStartIdleScan(pMac);
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+                    //For WDS STA. To fix the issue where the WDS AP side may be too busy by
+                    //BT activity and not able to recevie WLAN traffic. Retry the join
+                    if( CSR_IS_WDS_STA(pProfile) )
+                    {
+                        csrRoamStartJoinRetryTimer(pMac, sessionId, CSR_JOIN_RETRY_TIMEOUT_PERIOD);
+                    }
+#endif
+                    break;
+
+                case eCsrHddIssuedReassocToSameAP:
+                case eCsrSmeIssuedReassocToSameAP:
+                    csrRoamStateChange( pMac, eCSR_ROAMING_STATE_IDLE, sessionId);
+
+                    csrRoamCallCallback(pMac, sessionId, NULL, pCommand->u.roamCmd.roamId, eCSR_ROAM_DISASSOCIATED, eCSR_ROAM_RESULT_FORCED);
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT                                        
+                    sme_QosCsrEventInd(pMac, (tANI_U8)sessionId, SME_QOS_CSR_DISCONNECT_IND, NULL);
+#endif
+                    csrRoamCompletion(pMac, sessionId, NULL, pCommand, eCSR_ROAM_RESULT_FAILURE, eANI_BOOLEAN_FALSE);
+                    csrScanStartIdleScan(pMac);
+                    break;
+                case eCsrForcedDisassoc:
+                case eCsrForcedDeauth:
+                case eCsrSmeIssuedIbssJoinFailure:
+                    csrRoamStateChange( pMac, eCSR_ROAMING_STATE_IDLE, sessionId);
+
+                    if(eCsrSmeIssuedIbssJoinFailure == pCommand->u.roamCmd.roamReason)
+                    {
+                        // Notify HDD that IBSS join failed
+                        csrRoamCallCallback(pMac, sessionId, NULL, 0, eCSR_ROAM_IBSS_IND, eCSR_ROAM_RESULT_IBSS_JOIN_FAILED);
+                    }
+                    else
+                    {
+                        csrRoamCallCallback(pMac, sessionId, NULL, 
+                                            pCommand->u.roamCmd.roamId, 
+                                            eCSR_ROAM_DISASSOCIATED, eCSR_ROAM_RESULT_FORCED);
+                    }
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                    sme_QosCsrEventInd(pMac, (tANI_U8)sessionId, SME_QOS_CSR_DISCONNECT_IND, NULL);
+#endif
+                    csrRoamLinkDown(pMac, sessionId);
+                    csrScanStartIdleScan(pMac);
+                    break;
+                case eCsrForcedIbssLeave:
+                     csrRoamCallCallback(pMac, sessionId, NULL, 
+                                        pCommand->u.roamCmd.roamId, 
+                                        eCSR_ROAM_IBSS_LEAVE,
+                                        eCSR_ROAM_RESULT_IBSS_STOP);
+                    break;
+                case eCsrForcedDisassocMICFailure:
+                    csrRoamStateChange( pMac, eCSR_ROAMING_STATE_IDLE, sessionId );
+
+                    csrRoamCallCallback(pMac, sessionId, NULL, pCommand->u.roamCmd.roamId, eCSR_ROAM_DISASSOCIATED, eCSR_ROAM_RESULT_MIC_FAILURE);
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                    sme_QosCsrEventInd(pMac, (tANI_U8)sessionId, SME_QOS_CSR_DISCONNECT_REQ, NULL);
+#endif
+                    csrScanStartIdleScan(pMac);
+                    break;
+#ifdef WLAN_SOFTAP_FEATURE
+                case eCsrStopBss:
+                    csrRoamCallCallback(pMac, sessionId, NULL, 
+                                        pCommand->u.roamCmd.roamId, 
+                                        eCSR_ROAM_INFRA_IND, 
+                                        eCSR_ROAM_RESULT_INFRA_STOPPED);
+                    break;
+                case eCsrForcedDisassocSta:
+                case eCsrForcedDeauthSta:
+                   csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINED, sessionId);
+                   if( CSR_IS_SESSION_VALID(pMac, sessionId) )
+                   {                    
+                       pSession = CSR_GET_SESSION(pMac, sessionId);
+                       if (!pSession)
+                           break;
+
+                       if ( CSR_IS_INFRA_AP(&pSession->connectedProfile) )
+                       {
+                           roamInfo.u.pConnectedProfile = &pSession->connectedProfile;
+                           palCopyMemory(pMac->hHdd, roamInfo.peerMac, 
+                              pCommand->u.roamCmd.peerMac, sizeof(tSirMacAddr));
+                           roamInfo.reasonCode = eCSR_ROAM_RESULT_FORCED;
+                           roamInfo.statusCode = eSIR_SME_SUCCESS;
+                           status = csrRoamCallCallback(pMac, sessionId, 
+                                       &roamInfo, pCommand->u.roamCmd.roamId, 
+                                       eCSR_ROAM_LOSTLINK, eCSR_ROAM_RESULT_FORCED);
+                       }
+                   }
+                   break;
+#endif
+                case eCsrLostLink1:
+                    // if lost link roam1 failed, then issue lost link Scan2 ...
+                    csrScanRequestLostLink2(pMac, sessionId);
+                    break;
+                case eCsrLostLink2:
+                    // if lost link roam2 failed, then issue lost link scan3 ...
+                    csrScanRequestLostLink3(pMac, sessionId);
+                    break;
+                case eCsrLostLink3:
+                default:
+                    csrRoamStateChange( pMac, eCSR_ROAMING_STATE_IDLE, sessionId );
+
+                    //We are done with one round of lostlink roaming here
+                    csrScanHandleFailedLostlink3(pMac, sessionId);
+                    break;
+            }
+
+            break;
+        }
+    }
+
+    return ( fReleaseCommand );
+}
+
+
+eHalStatus csrRoamRegisterCallback(tpAniSirGlobal pMac, csrRoamCompleteCallback callback, void *pContext)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    return (status);
+}
+
+
+eHalStatus csrRoamCopyProfile(tpAniSirGlobal pMac, tCsrRoamProfile *pDstProfile, tCsrRoamProfile *pSrcProfile)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 size = 0;
+    
+    do
+    {
+        palZeroMemory(pMac->hHdd, pDstProfile, sizeof(tCsrRoamProfile));
+        if(pSrcProfile->BSSIDs.numOfBSSIDs)
+        {
+            size = sizeof(tCsrBssid) * pSrcProfile->BSSIDs.numOfBSSIDs;
+            status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->BSSIDs.bssid, size);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->BSSIDs.numOfBSSIDs = pSrcProfile->BSSIDs.numOfBSSIDs;
+            palCopyMemory(pMac->hHdd, pDstProfile->BSSIDs.bssid, pSrcProfile->BSSIDs.bssid, size);
+        }
+        if(pSrcProfile->SSIDs.numOfSSIDs)
+        {
+            size = sizeof(tCsrSSIDInfo) * pSrcProfile->SSIDs.numOfSSIDs;
+            status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->SSIDs.SSIDList, size);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->SSIDs.numOfSSIDs = pSrcProfile->SSIDs.numOfSSIDs;
+            palCopyMemory(pMac->hHdd, pDstProfile->SSIDs.SSIDList, pSrcProfile->SSIDs.SSIDList, size);
+        }
+        if(pSrcProfile->nWPAReqIELength)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->pWPAReqIE, pSrcProfile->nWPAReqIELength);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->nWPAReqIELength = pSrcProfile->nWPAReqIELength;
+            palCopyMemory(pMac->hHdd, pDstProfile->pWPAReqIE, pSrcProfile->pWPAReqIE, pSrcProfile->nWPAReqIELength);
+        }
+        if(pSrcProfile->nRSNReqIELength)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->pRSNReqIE, pSrcProfile->nRSNReqIELength);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->nRSNReqIELength = pSrcProfile->nRSNReqIELength;
+            palCopyMemory(pMac->hHdd, pDstProfile->pRSNReqIE, pSrcProfile->pRSNReqIE, pSrcProfile->nRSNReqIELength);
+        }
+#ifdef FEATURE_WLAN_WAPI
+        if(pSrcProfile->nWAPIReqIELength)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->pWAPIReqIE, pSrcProfile->nWAPIReqIELength);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->nWAPIReqIELength = pSrcProfile->nWAPIReqIELength;
+            palCopyMemory(pMac->hHdd, pDstProfile->pWAPIReqIE, pSrcProfile->pWAPIReqIE, pSrcProfile->nWAPIReqIELength);
+        }
+#endif /* FEATURE_WLAN_WAPI */
+
+        if(pSrcProfile->nAddIEScanLength)
+        {
+            status = palAllocateMemory(pMac->hHdd,
+                     (void **)&pDstProfile->pAddIEScan, pSrcProfile->nAddIEScanLength);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->nAddIEScanLength = pSrcProfile->nAddIEScanLength;
+            palCopyMemory(pMac->hHdd, pDstProfile->pAddIEScan, pSrcProfile->pAddIEScan,
+                pSrcProfile->nAddIEScanLength);
+        }
+
+        if(pSrcProfile->nAddIEAssocLength)
+        {
+            status = palAllocateMemory(pMac->hHdd,
+                     (void **)&pDstProfile->pAddIEAssoc, pSrcProfile->nAddIEAssocLength);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->nAddIEAssocLength = pSrcProfile->nAddIEAssocLength;
+            palCopyMemory(pMac->hHdd, pDstProfile->pAddIEAssoc, pSrcProfile->pAddIEAssoc,
+                pSrcProfile->nAddIEAssocLength);
+        }
+
+        if(pSrcProfile->ChannelInfo.ChannelList)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->ChannelInfo.ChannelList, pSrcProfile->ChannelInfo.numOfChannels);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->ChannelInfo.numOfChannels = pSrcProfile->ChannelInfo.numOfChannels;
+            palCopyMemory(pMac->hHdd, pDstProfile->ChannelInfo.ChannelList, pSrcProfile->ChannelInfo.ChannelList, pSrcProfile->ChannelInfo.numOfChannels);
+        }
+
+        pDstProfile->AuthType = pSrcProfile->AuthType;
+        pDstProfile->EncryptionType = pSrcProfile->EncryptionType;
+        pDstProfile->mcEncryptionType = pSrcProfile->mcEncryptionType;
+        pDstProfile->negotiatedUCEncryptionType = pSrcProfile->negotiatedUCEncryptionType;
+        pDstProfile->negotiatedMCEncryptionType = pSrcProfile->negotiatedMCEncryptionType;
+        pDstProfile->negotiatedAuthType = pSrcProfile->negotiatedAuthType;
+        pDstProfile->BSSType = pSrcProfile->BSSType;
+        pDstProfile->phyMode = pSrcProfile->phyMode;
+        pDstProfile->csrPersona = pSrcProfile->csrPersona;
+        
+#ifdef FEATURE_WLAN_WAPI
+        if(csrIsProfileWapi(pSrcProfile))
+        {
+             if(pDstProfile->phyMode & eCSR_DOT11_MODE_11n)
+             {
+                pDstProfile->phyMode &= ~eCSR_DOT11_MODE_11n;
+             }
+        }
+#endif /* FEATURE_WLAN_WAPI */
+        pDstProfile->CBMode = pSrcProfile->CBMode;
+        /*Save the WPS info*/
+        pDstProfile->bWPSAssociation = pSrcProfile->bWPSAssociation;
+        pDstProfile->uapsd_mask = pSrcProfile->uapsd_mask;
+
+        pDstProfile->beaconInterval = pSrcProfile->beaconInterval;
+#ifdef WLAN_SOFTAP_FEATURE
+        pDstProfile->privacy           = pSrcProfile->privacy;
+        pDstProfile->fwdWPSPBCProbeReq = pSrcProfile->fwdWPSPBCProbeReq;
+        pDstProfile->csr80211AuthType  = pSrcProfile->csr80211AuthType;
+        pDstProfile->dtimPeriod        = pSrcProfile->dtimPeriod;
+        pDstProfile->ApUapsdEnable     = pSrcProfile->ApUapsdEnable;   
+        pDstProfile->SSIDs.SSIDList[0].ssidHidden = pSrcProfile->SSIDs.SSIDList[0].ssidHidden;
+        pDstProfile->protEnabled       = pSrcProfile->protEnabled;  
+        pDstProfile->obssProtEnabled   = pSrcProfile->obssProtEnabled;  
+        pDstProfile->cfg_protection    = pSrcProfile->cfg_protection;
+        pDstProfile->wps_state         = pSrcProfile->wps_state;
+        pDstProfile->ieee80211d        = pSrcProfile->ieee80211d;
+#endif
+
+        palCopyMemory(pMac->hHdd, &pDstProfile->Keys, &pSrcProfile->Keys, sizeof(pDstProfile->Keys));
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        if (pSrcProfile->MDID.mdiePresent)
+        {
+            pDstProfile->MDID.mdiePresent = 1;
+            pDstProfile->MDID.mobilityDomain = pSrcProfile->MDID.mobilityDomain;
+        }
+#endif
+
+    }while(0);
+    
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        csrReleaseProfile(pMac, pDstProfile);
+        pDstProfile = NULL;
+    }
+    
+    return (status);
+}
+
+eHalStatus csrRoamCopyConnectedProfile(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pDstProfile )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamConnectedProfile *pSrcProfile = &pMac->roam.roamSession[sessionId].connectedProfile; 
+    do
+    {
+        palZeroMemory(pMac->hHdd, pDstProfile, sizeof(tCsrRoamProfile));
+        if(pSrcProfile->bssid)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->BSSIDs.bssid, sizeof(tCsrBssid));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->BSSIDs.numOfBSSIDs = 1;
+            palCopyMemory(pMac->hHdd, pDstProfile->BSSIDs.bssid, pSrcProfile->bssid, sizeof(tCsrBssid));
+        }
+        if(pSrcProfile->SSID.ssId)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->SSIDs.SSIDList, sizeof(tCsrSSIDInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pDstProfile->SSIDs.numOfSSIDs = 1;
+            pDstProfile->SSIDs.SSIDList[0].handoffPermitted = pSrcProfile->handoffPermitted;
+            pDstProfile->SSIDs.SSIDList[0].ssidHidden = pSrcProfile->ssidHidden;
+            palCopyMemory(pMac->hHdd, &pDstProfile->SSIDs.SSIDList[0].SSID, &pSrcProfile->SSID, sizeof(tSirMacSSid));
+        }
+
+        status = palAllocateMemory(pMac->hHdd, (void **)&pDstProfile->ChannelInfo.ChannelList, 1);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+           break;
+        }
+        pDstProfile->ChannelInfo.numOfChannels = 1;
+        pDstProfile->ChannelInfo.ChannelList[0] = pSrcProfile->operationChannel;
+
+        pDstProfile->AuthType.numEntries = 1;
+        pDstProfile->AuthType.authType[0] = pSrcProfile->AuthType;
+        pDstProfile->negotiatedAuthType = pSrcProfile->AuthType;
+        pDstProfile->EncryptionType.numEntries = 1;
+        pDstProfile->EncryptionType.encryptionType[0] = pSrcProfile->EncryptionType;
+        pDstProfile->negotiatedUCEncryptionType = pSrcProfile->EncryptionType;
+        pDstProfile->mcEncryptionType.numEntries = 1;
+        pDstProfile->mcEncryptionType.encryptionType[0] = pSrcProfile->mcEncryptionType;
+        pDstProfile->negotiatedMCEncryptionType = pSrcProfile->mcEncryptionType;
+        pDstProfile->BSSType = pSrcProfile->BSSType;
+        pDstProfile->CBMode = pSrcProfile->CBMode;
+        palCopyMemory(pMac->hHdd, &pDstProfile->Keys, &pSrcProfile->Keys, sizeof(pDstProfile->Keys));
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        if (pSrcProfile->MDID.mdiePresent)
+        {
+            pDstProfile->MDID.mdiePresent = 1;
+            pDstProfile->MDID.mobilityDomain = pSrcProfile->MDID.mobilityDomain;
+        }
+#endif
+    
+    }while(0);
+    
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        csrReleaseProfile(pMac, pDstProfile);
+        pDstProfile = NULL;
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrRoamIssueConnect(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                                tScanResultHandle hBSSList, 
+                                eCsrRoamReason reason, tANI_U32 roamId, tANI_BOOLEAN fImediate,
+                                tANI_BOOLEAN fClearScan)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand;
+    
+    pCommand = csrGetCommandBuffer(pMac);
+    if(NULL == pCommand)
+    {
+        smsLog( pMac, LOGE, FL(" fail to get command buffer\n") );
+        status = eHAL_STATUS_RESOURCES;
+    }
+    else
+    {
+        if( fClearScan )
+        {
+            csrScanCancelIdleScan(pMac);
+            csrScanAbortMacScanNotForConnect(pMac);
+        }
+        pCommand->u.roamCmd.fReleaseProfile = eANI_BOOLEAN_FALSE;
+        if(NULL == pProfile)
+        {
+            //We can roam now
+            //Since pProfile is NULL, we need to build our own profile, set everything to default
+            //We can only support open and no encryption
+            pCommand->u.roamCmd.roamProfile.AuthType.numEntries = 1; 
+            pCommand->u.roamCmd.roamProfile.AuthType.authType[0] = eCSR_AUTH_TYPE_OPEN_SYSTEM;
+            pCommand->u.roamCmd.roamProfile.EncryptionType.numEntries = 1;
+            pCommand->u.roamCmd.roamProfile.EncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_NONE;
+            pCommand->u.roamCmd.roamProfile.csrPersona = VOS_STA_MODE; 
+        }
+        else
+        {
+            //make a copy of the profile
+            status = csrRoamCopyProfile(pMac, &pCommand->u.roamCmd.roamProfile, pProfile);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                pCommand->u.roamCmd.fReleaseProfile = eANI_BOOLEAN_TRUE;
+            }
+        }
+        pCommand->command = eSmeCommandRoam;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.roamCmd.hBSSList = hBSSList;
+        pCommand->u.roamCmd.roamId = roamId;
+        pCommand->u.roamCmd.roamReason = reason;
+        //We need to free the BssList when the command is done
+        pCommand->u.roamCmd.fReleaseBssList = eANI_BOOLEAN_TRUE;
+        pCommand->u.roamCmd.fUpdateCurRoamProfile = eANI_BOOLEAN_TRUE;
+
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+                  FL("CSR PERSONA=%d"),
+                  pCommand->u.roamCmd.roamProfile.csrPersona);
+
+        status = csrQueueSmeCommand(pMac, pCommand, fImediate);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            csrReleaseCommandRoam( pMac, pCommand );
+        }
+    }
+    
+    return (status);
+}
+
+eHalStatus csrRoamIssueReassoc(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile,
+                               tCsrRoamModifyProfileFields *pMmodProfileFields,
+                               eCsrRoamReason reason, tANI_U32 roamId, tANI_BOOLEAN fImediate)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand;
+    
+    pCommand = csrGetCommandBuffer(pMac);
+    if(NULL == pCommand)
+    {
+        smsLog( pMac, LOGE, FL(" fail to get command buffer\n") );
+        status = eHAL_STATUS_RESOURCES;
+    }
+    else
+    {
+        csrScanCancelIdleScan(pMac);
+        csrScanAbortMacScanNotForConnect(pMac);
+        if(pProfile)
+        {
+
+           //This is likely trying to reassoc to different profile
+           pCommand->u.roamCmd.fReleaseProfile = eANI_BOOLEAN_FALSE;
+           //make a copy of the profile
+           status = csrRoamCopyProfile(pMac, &pCommand->u.roamCmd.roamProfile, pProfile);
+           pCommand->u.roamCmd.fUpdateCurRoamProfile = eANI_BOOLEAN_TRUE;
+
+        }
+        else
+        {
+            status = csrRoamCopyConnectedProfile(pMac, sessionId, &pCommand->u.roamCmd.roamProfile);
+            //how to update WPA/WPA2 info in roamProfile??
+            pCommand->u.roamCmd.roamProfile.uapsd_mask = pMmodProfileFields->uapsd_mask;
+
+        }
+
+        if(HAL_STATUS_SUCCESS(status))
+        {
+           pCommand->u.roamCmd.fReleaseProfile = eANI_BOOLEAN_TRUE;
+        }
+        pCommand->command = eSmeCommandRoam;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.roamCmd.roamId = roamId;
+        pCommand->u.roamCmd.roamReason = reason;
+        //We need to free the BssList when the command is done
+        //For reassoc there is no BSS list, so the boolean set to false
+        pCommand->u.roamCmd.hBSSList = CSR_INVALID_SCANRESULT_HANDLE; 
+        pCommand->u.roamCmd.fReleaseBssList = eANI_BOOLEAN_FALSE;
+        pCommand->u.roamCmd.fReassoc = eANI_BOOLEAN_TRUE;
+
+        status = csrQueueSmeCommand(pMac, pCommand, fImediate);
+        if( !HAL_STATUS_SUCCESS( status ) )
+    {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            csrRoamCompletion(pMac, sessionId, NULL, pCommand, eCSR_ROAM_RESULT_FAILURE, eANI_BOOLEAN_FALSE);
+            csrReleaseCommandRoam( pMac, pCommand );
+    }
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrRoamConnectWithBSSList(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                                     tScanResultHandle hBssListIn, tANI_U32 *pRoamId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tScanResultHandle hBSSList;
+    tANI_U32 roamId = 0;
+
+    status = csrScanCopyResultList(pMac, hBssListIn, &hBSSList);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+        if(pRoamId)
+        {
+            *pRoamId = roamId;
+        }
+        status = csrRoamIssueConnect(pMac, sessionId, pProfile, hBSSList, eCsrHddIssued, 
+                                        roamId, eANI_BOOLEAN_FALSE, eANI_BOOLEAN_FALSE);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            smsLog(pMac, LOGE, FL("failed to start a join process\n"));
+            csrScanResultPurge(pMac, hBSSList);
+        }
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrRoamConnect(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                          tScanResultHandle hBssListIn, tANI_U32 *pRoamId)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tScanResultHandle hBSSList;
+    tCsrScanResultFilter *pScanFilter;
+    tANI_U32 roamId = 0;
+    tANI_BOOLEAN fCallCallback = eANI_BOOLEAN_FALSE;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if (NULL == pProfile)
+    {
+        smsLog(pMac, LOGP, FL("No profile specified"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    smsLog(pMac, LOG1, FL("called  BSSType = %d authtype = %d  encryType = %d\n"),
+                pProfile->BSSType, pProfile->AuthType.authType[0], pProfile->EncryptionType.encryptionType[0]);
+
+    if( CSR_IS_WDS( pProfile ) && 
+        !HAL_STATUS_SUCCESS( status = csrIsBTAMPAllowed( pMac, pProfile->operationChannel ) ) )
+    {
+        return status;
+    }
+    csrRoamCancelRoaming(pMac, sessionId);
+    csrScanRemoveFreshScanCommand(pMac, sessionId);
+    csrScanCancelIdleScan(pMac);
+    //Only abort the scan if it is not used for other roam/connect purpose
+    csrScanAbortMacScan(pMac);
+
+#ifdef WLAN_SOFTAP_FEATURE
+    if (!vos_concurrent_sessions_running() && (VOS_STA_SAP_MODE == pProfile->csrPersona))//In case of AP mode we do not want idle mode scan
+    {
+        csrScanDisable(pMac);
+    }
+#endif
+
+    csrRoamRemoveDuplicateCommand(pMac, sessionId, NULL, eCsrHddIssued);
+    //Check whether ssid changes
+    if(csrIsConnStateConnected(pMac, sessionId))
+    {
+        if(pProfile->SSIDs.numOfSSIDs && !csrIsSsidInList(pMac, &pSession->connectedProfile.SSID, &pProfile->SSIDs))
+        {
+            csrRoamIssueDisassociateCmd(pMac, sessionId, eCSR_DISCONNECT_REASON_UNSPECIFIED);
+        }
+    }
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+    pSession->maxRetryCount = CSR_JOIN_MAX_RETRY_COUNT; 
+#endif
+    if(CSR_INVALID_SCANRESULT_HANDLE != hBssListIn)
+    {
+        smsLog(pMac, LOGW, FL("is called with BSSList\n"));
+        status = csrRoamConnectWithBSSList(pMac, sessionId, pProfile, hBssListIn, pRoamId);
+        if(pRoamId)
+        {
+            roamId = *pRoamId;
+        }
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            fCallCallback = eANI_BOOLEAN_TRUE;
+        }
+    }
+    else
+    {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            //Try to connect to any BSS
+            if(NULL == pProfile)
+            {
+                //No encryption
+                pScanFilter->EncryptionType.numEntries = 1;
+                pScanFilter->EncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_NONE;
+            }//we don't have a profile
+            else 
+            {
+                //Here is the profile we need to connect to
+                status = csrRoamPrepareFilterFromProfile(pMac, pProfile, pScanFilter);
+            }//We have a profile
+            roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+            if(pRoamId)
+            {
+                *pRoamId = roamId;
+            }
+            
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                /*Save the WPS info*/
+                if(NULL != pProfile)
+                {
+                    pScanFilter->bWPSAssociation = pProfile->bWPSAssociation;
+                }
+                else
+                {
+                    pScanFilter->bWPSAssociation = 0;
+                }
+
+                do
+                {
+                    if( (pProfile && CSR_IS_WDS_AP( pProfile ) )
+#ifdef WLAN_SOFTAP_FEATURE
+                     || (pProfile && CSR_IS_INFRA_AP ( pProfile ))
+#endif
+                    )
+                    {
+                        //This can be start right away
+                        status = csrRoamIssueConnect(pMac, sessionId, pProfile, NULL, eCsrHddIssued, 
+                                                    roamId, eANI_BOOLEAN_FALSE, eANI_BOOLEAN_FALSE);
+                        if(!HAL_STATUS_SUCCESS(status))
+                        {
+                            fCallCallback = eANI_BOOLEAN_TRUE;
+                        }
+
+                        break;
+                    }
+                    status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+                    smsLog(pMac, LOGE, "************ csrScanGetResult Status ********* %d\n", status);
+                    if(HAL_STATUS_SUCCESS(status))
+                    {
+
+                        status = csrRoamIssueConnect(pMac, sessionId, pProfile, hBSSList, eCsrHddIssued, 
+                                                    roamId, eANI_BOOLEAN_FALSE, eANI_BOOLEAN_FALSE);
+                        if(!HAL_STATUS_SUCCESS(status))
+                        {
+                            csrScanResultPurge(pMac, hBSSList);
+                            fCallCallback = eANI_BOOLEAN_TRUE;
+                        }
+                    }//Have scan result
+                    else if(NULL != pProfile)
+                    {
+                        //Check whether it is for start ibss
+                        if(CSR_IS_START_IBSS(pProfile))
+                        {
+                            status = csrRoamIssueConnect(pMac, sessionId, pProfile, NULL, eCsrHddIssued, 
+                                                        roamId, eANI_BOOLEAN_FALSE, eANI_BOOLEAN_FALSE);
+                            if(!HAL_STATUS_SUCCESS(status))
+                            {
+                                smsLog(pMac, LOGE, "   CSR failed to issue startIBSS command with status = 0x%08X\n", status);
+                                fCallCallback = eANI_BOOLEAN_TRUE;
+                            }
+                        }
+                        else
+                        {
+                            //scan for this SSID
+                            status = csrScanForSSID(pMac, sessionId, pProfile, roamId);
+                            if(!HAL_STATUS_SUCCESS(status))
+                            {
+                                fCallCallback = eANI_BOOLEAN_TRUE;
+                            }
+                        }
+                    }
+                    else
+                    {
+                        fCallCallback = eANI_BOOLEAN_TRUE;
+                    }
+                } while (0);
+                if(NULL != pProfile)
+                {
+                    //we need to free memory for filter if profile exists
+                    csrFreeScanFilter(pMac, pScanFilter);
+                }
+            }//Got the scan filter from profile
+            
+            palFreeMemory(pMac->hHdd, pScanFilter);
+        }//allocated memory for pScanFilter
+    }//No Bsslist coming in
+    //tell the caller if we fail to trigger a join request
+    if( fCallCallback )
+    {
+        csrRoamCallCallback(pMac, sessionId, NULL, roamId, eCSR_ROAM_FAILED, eCSR_ROAM_RESULT_FAILURE);
+    }
+   
+    return (status);
+}                         
+
+eHalStatus csrRoamReassoc(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile,
+                          tCsrRoamModifyProfileFields modProfileFields,
+                          tANI_U32 *pRoamId)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tANI_BOOLEAN fCallCallback = eANI_BOOLEAN_TRUE;
+   tANI_U32 roamId = 0;
+   tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+   if (NULL == pProfile)
+   {
+      smsLog(pMac, LOGP, FL("No profile specified"));
+      return eHAL_STATUS_FAILURE;
+   }
+
+   smsLog(pMac, LOG1, FL("called  BSSType = %d authtype = %d  encryType = %d\n"), pProfile->BSSType, pProfile->AuthType.authType[0], pProfile->EncryptionType.encryptionType[0]);
+   csrRoamCancelRoaming(pMac, sessionId);
+   csrScanRemoveFreshScanCommand(pMac, sessionId);
+   csrScanCancelIdleScan(pMac);
+   csrScanAbortMacScanNotForConnect(pMac);
+   csrRoamRemoveDuplicateCommand(pMac, sessionId, NULL, eCsrHddIssuedReassocToSameAP);
+
+   if(csrIsConnStateConnected(pMac, sessionId))
+   {
+      if(pProfile)
+      {
+         if(pProfile->SSIDs.numOfSSIDs && 
+            csrIsSsidInList(pMac, &pSession->connectedProfile.SSID, &pProfile->SSIDs))
+         {
+            fCallCallback = eANI_BOOLEAN_FALSE;
+         }
+         else
+         {
+            smsLog(pMac, LOG1, FL("Not connected to the same SSID asked in the profile\n"));
+         }
+      }
+      else if(!palEqualMemory(pMac->hHdd, &modProfileFields, 
+                              &pSession->connectedProfile.modifyProfileFields, 
+                              sizeof(tCsrRoamModifyProfileFields)))
+      {
+         fCallCallback = eANI_BOOLEAN_FALSE;
+      }
+      else
+      {
+         smsLog(pMac, LOG1, FL("Either the profile is NULL or none of the fields "
+                               "in tCsrRoamModifyProfileFields got modified\n"));
+      }
+   }
+   else
+   {
+      smsLog(pMac, LOG1, FL("Not connected! No need to reassoc\n"));
+   }
+
+   if(!fCallCallback)
+   {
+      roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+      if(pRoamId)
+      {
+         *pRoamId = roamId;
+      }
+
+
+      status = csrRoamIssueReassoc(pMac, sessionId, pProfile, &modProfileFields, 
+                                   eCsrHddIssuedReassocToSameAP, roamId, eANI_BOOLEAN_FALSE);
+
+   }
+   else
+   {
+      status = csrRoamCallCallback(pMac, sessionId, NULL, roamId, 
+                                   eCSR_ROAM_FAILED, eCSR_ROAM_RESULT_FAILURE);
+   }
+
+   return status;
+}
+
+eHalStatus csrRoamJoinLastProfile(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tScanResultHandle hBSSList = NULL;
+    tCsrScanResultFilter *pScanFilter = NULL;
+    tANI_U32 roamId;
+    tCsrRoamProfile *pProfile = NULL;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    do
+    {
+        if(pSession->pCurRoamProfile)
+        {
+            csrScanCancelIdleScan(pMac);
+            csrScanAbortMacScanNotForConnect(pMac);
+            //We have to make a copy of pCurRoamProfile because it will be free inside csrRoamIssueConnect
+            status = palAllocateMemory(pMac->hHdd, (void **)&pProfile, sizeof(tCsrRoamProfile));
+            if(!HAL_STATUS_SUCCESS(status))
+                break;
+            palZeroMemory(pMac->hHdd, pProfile, sizeof(tCsrRoamProfile));
+            status = csrRoamCopyProfile(pMac, pProfile, pSession->pCurRoamProfile);
+            if(!HAL_STATUS_SUCCESS(status))
+                break;
+            status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            status = csrRoamPrepareFilterFromProfile(pMac, pProfile, pScanFilter);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+            status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                //we want to put the last connected BSS to the very beginning, if possible
+                csrMoveBssToHeadFromBSSID(pMac, &pSession->connectedProfile.bssid, hBSSList);
+                status = csrRoamIssueConnect(pMac, sessionId, pProfile, hBSSList, eCsrHddIssued, 
+                                                roamId, eANI_BOOLEAN_FALSE, eANI_BOOLEAN_FALSE);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    csrScanResultPurge(pMac, hBSSList);
+                    break;
+                }
+            }
+            else
+            {
+                //Do a scan on this profile
+                //scan for this SSID only in case the AP suppresses SSID
+                status = csrScanForSSID(pMac, sessionId, pProfile, roamId);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    break;
+                }
+            }
+        }//We have a profile
+        else
+        {
+            smsLog(pMac, LOGW, FL("cannot find a roaming profile\n"));
+            break;
+        }
+    }while(0);
+    if(pScanFilter)
+    {
+        csrFreeScanFilter(pMac, pScanFilter);
+        palFreeMemory(pMac->hHdd, pScanFilter);
+    }
+    if(NULL != pProfile)
+    {
+        csrReleaseProfile(pMac, pProfile);
+        palFreeMemory(pMac->hHdd, pProfile);
+    }
+
+    return (status);
+}
+
+eHalStatus csrRoamReconnect(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+
+    if(csrIsConnStateConnected(pMac, sessionId))
+    {
+        status = csrRoamIssueDisassociateCmd(pMac, sessionId, eCSR_DISCONNECT_REASON_UNSPECIFIED);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            status = csrRoamJoinLastProfile(pMac, sessionId);
+        }
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrRoamConnectToLastProfile(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+
+    smsLog(pMac, LOGW, FL("is called\n"));
+    csrRoamCancelRoaming(pMac, sessionId);
+    csrRoamRemoveDuplicateCommand(pMac, sessionId, NULL, eCsrHddIssued);
+    if(csrIsConnStateDisconnected(pMac, sessionId))
+    {
+        status = csrRoamJoinLastProfile(pMac, sessionId);
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrRoamProcessDisassocDeauth( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fDisassoc, tANI_BOOLEAN fMICFailure )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_BOOLEAN fComplete = eANI_BOOLEAN_FALSE;
+    eCsrRoamSubState NewSubstate;
+    tANI_U32 sessionId = pCommand->sessionId;
+    
+    // change state to 'Roaming'...
+    csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINING, sessionId );
+
+    if ( csrIsConnStateIbss( pMac, sessionId ) )
+    {
+        // If we are in an IBSS, then stop the IBSS...
+        status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_STOP_BSS_REQ );
+        fComplete = (!HAL_STATUS_SUCCESS(status));
+    }
+    else if ( csrIsConnStateInfra( pMac, sessionId ) )
+    {
+        smsLog(pMac, LOGE, FL(" restore AC weights (%d-%d-%d-%d)\n"), pMac->roam.ucACWeights[0], pMac->roam.ucACWeights[1],
+            pMac->roam.ucACWeights[2], pMac->roam.ucACWeights[3]);
+        //Restore AC weight in case we change it 
+        WLANTL_SetACWeights(pMac->roam.gVosContext, pMac->roam.ucACWeights);
+        // in Infrasturcture, we need to disassociate from the Infrastructure network...
+        NewSubstate = eCSR_ROAM_SUBSTATE_DISASSOC_FORCED;
+        if(eCsrSmeIssuedDisassocForHandoff == pCommand->u.roamCmd.roamReason)
+        {
+            NewSubstate = eCSR_ROAM_SUBSTATE_DISASSOC_HANDOFF;
+        }
+        if( fDisassoc )
+        {
+            status = csrRoamIssueDisassociate( pMac, sessionId, NewSubstate, fMICFailure );
+        }
+        else
+        {
+            status = csrRoamIssueDeauth( pMac, sessionId, eCSR_ROAM_SUBSTATE_DEAUTH_REQ );
+        }
+        fComplete = (!HAL_STATUS_SUCCESS(status));
+    }
+    else if ( csrIsConnStateWds( pMac, sessionId ) )
+    {
+        if( CSR_IS_WDS_AP( &pMac->roam.roamSession[sessionId].connectedProfile ) )
+        {
+            status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_STOP_BSS_REQ );
+            fComplete = (!HAL_STATUS_SUCCESS(status));
+        }
+        //This has to be WDS station
+        else  if( csrIsConnStateConnectedWds( pMac, sessionId ) ) //This has to be WDS station
+        {
+ 
+            pCommand->u.roamCmd.fStopWds = eANI_BOOLEAN_TRUE;
+            if( fDisassoc )
+            {
+                status = csrRoamIssueDisassociate( pMac, sessionId, 
+                                eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING, fMICFailure );
+                fComplete = (!HAL_STATUS_SUCCESS(status));
+            }
+        }
+    } else {
+        // we got a dis-assoc request while not connected to any peer
+        // just complete the command
+           fComplete = eANI_BOOLEAN_TRUE;
+           status = eHAL_STATUS_FAILURE;
+    }
+    if(fComplete)
+    {
+        csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+    }
+
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        if ( csrIsConnStateInfra( pMac, sessionId ) )
+        {
+            //Set the state to disconnect here 
+            pMac->roam.roamSession[sessionId].connectState = eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED;
+        }
+    }
+    return (status);
+}
+
+
+/* This is been removed from latest code base */
+/*
+static eHalStatus csrRoamProcessStopBss( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status;
+    tANI_U32 sessionId = pCommand->sessionId;
+
+    csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINING );
+    status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_STOP_BSS_REQ );
+
+    return ( status );
+}
+*/
+
+
+eHalStatus csrRoamIssueDisassociateCmd( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamDisconnectReason reason )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand;
+        tANI_BOOLEAN fHighPriority = eANI_BOOLEAN_FALSE;
+
+    do
+    {
+        smsLog( pMac, LOGE, FL("  reason = %d\n"), reason );
+        pCommand = csrGetCommandBuffer( pMac );
+        if ( !pCommand ) 
+        {
+            smsLog( pMac, LOGE, FL(" fail to get command buffer\n") );
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        //Change the substate in case it is wait-for-key
+        if( CSR_IS_WAIT_FOR_KEY( pMac, sessionId ) )
+        {
+            csrRoamStopWaitForKeyTimer( pMac );
+            csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId);
+        }
+        pCommand->command = eSmeCommandRoam;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        switch ( reason )
+        {
+        case eCSR_DISCONNECT_REASON_MIC_ERROR:
+            pCommand->u.roamCmd.roamReason = eCsrForcedDisassocMICFailure;
+            break;
+
+        case eCSR_DISCONNECT_REASON_DEAUTH:
+            pCommand->u.roamCmd.roamReason = eCsrForcedDeauth;
+            break;
+
+        case eCSR_DISCONNECT_REASON_HANDOFF:
+            fHighPriority = eANI_BOOLEAN_TRUE;
+            pCommand->u.roamCmd.roamReason = eCsrSmeIssuedDisassocForHandoff;
+            break;
+
+        case eCSR_DISCONNECT_REASON_UNSPECIFIED:
+        case eCSR_DISCONNECT_REASON_DISASSOC:
+            pCommand->u.roamCmd.roamReason = eCsrForcedDisassoc;
+            break;
+
+        case eCSR_DISCONNECT_REASON_IBSS_JOIN_FAILURE:
+            pCommand->u.roamCmd.roamReason = eCsrSmeIssuedIbssJoinFailure;
+            break;
+
+        case eCSR_DISCONNECT_REASON_IBSS_LEAVE:
+            pCommand->u.roamCmd.roamReason = eCsrForcedIbssLeave;
+            break;
+
+        default:
+            break;
+        }
+        status = csrQueueSmeCommand(pMac, pCommand, fHighPriority);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            csrReleaseCommandRoam( pMac, pCommand );
+        }
+    } while( 0 );
+
+    return( status );
+}
+
+
+eHalStatus csrRoamIssueStopBssCmd( tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_BOOLEAN fHighPriority )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand;
+
+    pCommand = csrGetCommandBuffer( pMac );
+    if ( NULL != pCommand ) 
+    {
+        //Change the substate in case it is wait-for-key
+        if( CSR_IS_WAIT_FOR_KEY( pMac, sessionId) )
+        {
+            csrRoamStopWaitForKeyTimer( pMac );
+            csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId);
+        }
+        pCommand->command = eSmeCommandRoam;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.roamCmd.roamReason = eCsrStopBss;
+        status = csrQueueSmeCommand(pMac, pCommand, fHighPriority);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            csrReleaseCommandRoam( pMac, pCommand );
+        }
+    }
+    else
+    {
+        smsLog( pMac, LOGE, FL(" fail to get command buffer\n") );
+        status = eHAL_STATUS_RESOURCES;
+    }
+
+    return ( status );
+}
+
+
+eHalStatus csrRoamDisconnectInternal(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamDisconnectReason reason)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+    //Stop te retry
+    pSession->maxRetryCount = 0;
+    csrRoamStopJoinRetryTimer(pMac, sessionId);
+#endif
+    //Not to call cancel roaming here
+    //Only issue disconnect when necessary
+    if(csrIsConnStateConnected(pMac, sessionId) || csrIsBssTypeIBSS(pSession->connectedProfile.BSSType) 
+                || csrIsBssTypeWDS(pSession->connectedProfile.BSSType) 
+                || csrIsRoamCommandWaitingForSession(pMac, sessionId) )
+                
+    {
+        smsLog(pMac, LOG2, FL("called\n"));
+        status = csrRoamIssueDisassociateCmd(pMac, sessionId, reason);
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrRoamDisconnect(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamDisconnectReason reason)
+{
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    csrRoamCancelRoaming(pMac, sessionId);
+    pSession->ibss_join_pending = FALSE;
+    csrRoamStopIbssJoinTimer(pMac, sessionId);
+    csrRoamRemoveDuplicateCommand(pMac, sessionId, NULL, eCsrForcedDisassoc);
+    
+    return (csrRoamDisconnectInternal(pMac, sessionId, reason));
+}
+
+
+eHalStatus csrRoamSaveConnectedInfomation(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                                          tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tDot11fBeaconIEs *pIesTemp = pIes;
+    tANI_U8 index;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tCsrRoamConnectedProfile *pConnectProfile = &pSession->connectedProfile;
+    
+    palZeroMemory(pMac->hHdd, &pSession->connectedProfile, sizeof(tCsrRoamConnectedProfile));
+    pConnectProfile->AuthType = pProfile->negotiatedAuthType;
+        pConnectProfile->AuthInfo = pProfile->AuthType;
+    pConnectProfile->CBMode = pProfile->CBMode;  //*** this may not be valid
+    pConnectProfile->EncryptionType = pProfile->negotiatedUCEncryptionType;
+        pConnectProfile->EncryptionInfo = pProfile->EncryptionType;
+    pConnectProfile->mcEncryptionType = pProfile->negotiatedMCEncryptionType;
+        pConnectProfile->mcEncryptionInfo = pProfile->mcEncryptionType;
+    pConnectProfile->BSSType = pProfile->BSSType;
+    pConnectProfile->modifyProfileFields.uapsd_mask = pProfile->uapsd_mask;
+    pConnectProfile->operationChannel = pSirBssDesc->channelId;
+    palCopyMemory(pMac->hHdd, &pConnectProfile->Keys, &pProfile->Keys, sizeof(tCsrKeys));
+    //Save bssid
+    csrGetBssIdBssDesc(pMac, pSirBssDesc, &pConnectProfile->bssid);
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    if (pSirBssDesc->mdiePresent)
+    {
+        pConnectProfile->MDID.mdiePresent = 1;
+        pConnectProfile->MDID.mobilityDomain = (pSirBssDesc->mdie[1] << 8) | (pSirBssDesc->mdie[0]);
+    }
+#endif
+#ifdef FEATURE_WLAN_CCX
+    if ((csrIsProfileCCX(pProfile) || ((pIesTemp->CCXVersion.present) && ((pProfile->negotiatedAuthType == eCSR_AUTH_TYPE_OPEN_SYSTEM) || (pProfile->negotiatedAuthType == eCSR_AUTH_TYPE_WPA)))) && (!(csrIsProfile11r( pProfile ))) && (pMac->roam.configParam.isCcxIniFeatureEnabled))
+    {
+        pConnectProfile->isCCXAssoc = 1;
+    }
+#endif
+    //save ssid
+    if( NULL == pIesTemp )
+    {
+        status = csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc, &pIesTemp);
+    }
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        if(pIesTemp->SSID.present)
+        {
+            pConnectProfile->SSID.length = pIesTemp->SSID.num_ssid;
+            palCopyMemory(pMac->hHdd, pConnectProfile->SSID.ssId, 
+                            pIesTemp->SSID.ssid, pIesTemp->SSID.num_ssid);
+        }
+        
+        //Save the bss desc
+        status = csrRoamSaveConnectedBssDesc(pMac, sessionId, pSirBssDesc);
+
+           if( CSR_IS_QOS_BSS(pIesTemp) )
+           {
+              pConnectProfile->qap = TRUE;
+           }
+           else
+           {
+              pConnectProfile->qap = FALSE;
+           }
+
+        if ( NULL == pIes )
+        {
+            //Free memory if it allocated locally
+            palFreeMemory(pMac->hHdd, pIesTemp);
+        }
+    }
+    //Save Qos connection
+    pConnectProfile->qosConnection = pMac->roam.roamSession[sessionId].fWMMConnection;
+    
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        csrFreeConnectBssDesc(pMac, sessionId);
+    }
+    for(index = 0; index < pProfile->SSIDs.numOfSSIDs; index++)
+    {
+       if((pProfile->SSIDs.SSIDList[index].SSID.length == pConnectProfile->SSID.length) &&
+          palEqualMemory(pMac->hHdd, pProfile->SSIDs.SSIDList[index].SSID.ssId, 
+                         pConnectProfile->SSID.ssId, pConnectProfile->SSID.length))
+       {
+          pConnectProfile->handoffPermitted = pProfile->SSIDs.SSIDList[index].handoffPermitted;
+          break;
+       }
+       pConnectProfile->handoffPermitted = FALSE;
+    }
+    
+    return (status);
+}
+
+
+
+static void csrRoamJoinRspProcessor( tpAniSirGlobal pMac, tSirSmeJoinRsp *pSmeJoinRsp )
+{
+   tListElem *pEntry = NULL;
+   tSmeCmd *pCommand = NULL;
+
+   //The head of the active list is the request we sent
+   pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+   if(pEntry)
+   {
+       pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+   }
+
+   if ( eSIR_SME_SUCCESS == pSmeJoinRsp->statusCode ) 
+   {
+            if(pCommand && eCsrSmeIssuedAssocToSimilarAP == pCommand->u.roamCmd.roamReason)
+            {
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+               sme_QosCsrEventInd(pMac, pSmeJoinRsp->sessionId, SME_QOS_CSR_HANDOFF_COMPLETE, NULL);
+#endif
+            }
+            csrRoamComplete( pMac, eCsrJoinSuccess, (void *)pSmeJoinRsp );
+   }
+   else
+   {
+        tANI_U32 roamId = 0;
+        tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, pSmeJoinRsp->sessionId );
+        
+        //The head of the active list is the request we sent
+        //Try to get back the same profile and roam again
+        if(pCommand)
+        {
+            roamId = pCommand->u.roamCmd.roamId;
+        }
+
+        pSession->joinFailStatusCode.statusCode = pSmeJoinRsp->statusCode;
+        pSession->joinFailStatusCode.reasonCode = pSmeJoinRsp->protStatusCode;
+        smsLog( pMac, LOGW, "SmeJoinReq failed with statusCode= 0x%08lX [%d]\n", pSmeJoinRsp->statusCode, pSmeJoinRsp->statusCode );
+#if   defined WLAN_FEATURE_NEIGHBOR_ROAMING
+        /* If Join fails while Handoff is in progress, indicate disassociated event to supplicant to reconnect */
+        if (csrRoamIsHandoffInProgress(pMac))
+        {
+            csrRoamCallCallback(pMac, pSmeJoinRsp->sessionId, NULL, roamId, eCSR_ROAM_DISASSOCIATED, eCSR_ROAM_RESULT_FORCED);
+            /* Should indicate neighbor roam algorithm about the connect failure here */
+            csrNeighborRoamIndicateConnect(pMac, pSmeJoinRsp->sessionId, VOS_STATUS_E_FAILURE);
+        }
+#endif
+        if (pCommand)
+        {
+            if(CSR_IS_WDS_STA( &pCommand->u.roamCmd.roamProfile ))
+            {
+              pCommand->u.roamCmd.fStopWds = eANI_BOOLEAN_TRUE;
+              pSession->connectedProfile.BSSType = eCSR_BSS_TYPE_WDS_STA;
+              csrRoamReissueRoamCommand(pMac);
+            }
+            else if( CSR_IS_WDS( &pCommand->u.roamCmd.roamProfile ) )
+            {
+                csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+            }
+            else
+            {
+                csrRoam(pMac, pCommand);
+            }    
+        }    
+        else
+        {
+           csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+        }
+    } /*else: ( eSIR_SME_SUCCESS == pSmeJoinRsp->statusCode ) */
+}
+
+
+eHalStatus csrRoamIssueJoin( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirBssDescription *pSirBssDesc, 
+                             tDot11fBeaconIEs *pIes,
+                             tCsrRoamProfile *pProfile, tANI_U32 roamId )
+{
+    eHalStatus status;
+
+    smsLog( pMac, LOG1, "Attempting to Join Bssid= %02x-%02x-%02x-%02x-%02x-%02x\n", 
+                  pSirBssDesc->bssId[ 0 ],pSirBssDesc->bssId[ 1 ],pSirBssDesc->bssId[ 2 ],
+                  pSirBssDesc->bssId[ 3 ],pSirBssDesc->bssId[ 4 ],pSirBssDesc->bssId[ 5 ] );
+    
+    // Set the roaming substate to 'join attempt'...
+    csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_JOIN_REQ, sessionId);
+
+    // attempt to Join this BSS...
+    status = csrSendJoinReqMsg( pMac, sessionId, pSirBssDesc, pProfile, pIes );
+
+    return (status);
+}
+
+
+static eHalStatus csrRoamIssueReassociate( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirBssDescription *pSirBssDesc, 
+                              tDot11fBeaconIEs *pIes, tCsrRoamProfile *pProfile)
+{
+    csrRoamStateChange( pMac, eCSR_ROAMING_STATE_JOINING, sessionId);
+
+    // Set the roaming substate to 'join attempt'...
+    csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_REASSOC_REQ, sessionId );
+
+    smsLog(pMac, LOGE, FL("  calling csrSendSmeReassocReqMsg\n"));
+    
+    // attempt to Join this BSS...
+    return csrSendSmeReassocReqMsg( pMac, sessionId, pSirBssDesc, pIes, pProfile );
+}
+
+
+
+void csrRoamReissueRoamCommand(tpAniSirGlobal pMac)
+{
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+    tCsrRoamInfo roamInfo;
+    tANI_U32 sessionId;
+    tCsrRoamSession *pSession;
+            
+    pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+    if(pEntry)
+    {
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+        if ( eSmeCommandRoam == pCommand->command )
+        {
+            sessionId = pCommand->sessionId;
+            pSession = CSR_GET_SESSION( pMac, sessionId );
+            if( pCommand->u.roamCmd.fStopWds )
+            {
+                palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+                roamInfo.pBssDesc = pCommand->u.roamCmd.pLastRoamBss;
+                roamInfo.statusCode = pSession->joinFailStatusCode.statusCode;
+                roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+#ifdef WLAN_SOFTAP_FEATURE              
+                if (CSR_IS_WDS(&pSession->connectedProfile)){
+#endif
+                pSession->connectState = eCSR_ASSOC_STATE_TYPE_WDS_DISCONNECTED;
+                csrRoamCallCallback(pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId, 
+                                        eCSR_ROAM_WDS_IND, 
+                                        eCSR_ROAM_RESULT_WDS_DISASSOCIATED);
+#ifdef  WLAN_SOFTAP_FEATURE
+                                }else if (CSR_IS_INFRA_AP(&pSession->connectedProfile)){
+                                        pSession->connectState = eCSR_ASSOC_STATE_TYPE_INFRA_DISCONNECTED;
+                                        csrRoamCallCallback(pMac, sessionId, &roamInfo, pCommand->u.roamCmd.roamId,
+                                                                                eCSR_ROAM_INFRA_IND,
+                                                                                eCSR_ROAM_RESULT_INFRA_DISASSOCIATED);
+                                }  
+ 
+#endif                  
+
+
+                if( !HAL_STATUS_SUCCESS( csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_STOP_BSS_REQ ) ) )
+                {
+                    smsLog(pMac, LOGE, " Failed to reissue stop_bss command for WDS after disassociated\n");
+                    csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+                }
+            }
+            else if(eCsrStopRoaming == csrRoamJoinNextBss(pMac, pCommand, eANI_BOOLEAN_TRUE))
+            {
+                smsLog(pMac, LOGW, " Failed to reissue join command after disassociated\n");
+                csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+            }
+        }
+        else
+        {
+            smsLog(pMac, LOGW, "  Command is not roaming after disassociated\n");
+        }
+    }
+    else 
+    {
+        smsLog(pMac, LOGE, "   Disassoc rsp cannot continue because no command is available\n");
+    }
+}
+
+
+tANI_BOOLEAN csrIsRoamCommandWaitingForSession(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    tListElem *pEntry;
+    tSmeCmd *pCommand = NULL;
+
+    //alwasy lock active list before locking pending list
+    csrLLLock( &pMac->sme.smeCmdActiveList );
+    pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_NOLOCK);
+    if(pEntry)
+    {
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+        if( ( eSmeCommandRoam == pCommand->command ) && ( sessionId == pCommand->sessionId ) )
+        {
+            fRet = eANI_BOOLEAN_TRUE;
+        }
+    }
+    if(eANI_BOOLEAN_FALSE == fRet)
+    {
+        csrLLLock(&pMac->sme.smeCmdPendingList);
+        pEntry = csrLLPeekHead(&pMac->sme.smeCmdPendingList, LL_ACCESS_NOLOCK);
+        while(pEntry)
+        {
+            pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+            if( ( eSmeCommandRoam == pCommand->command ) && ( sessionId == pCommand->sessionId ) )
+            {
+                fRet = eANI_BOOLEAN_TRUE;
+                break;
+            }
+            pEntry = csrLLNext(&pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_NOLOCK);
+        }
+        csrLLUnlock(&pMac->sme.smeCmdPendingList);
+    }
+    csrLLUnlock( &pMac->sme.smeCmdActiveList );
+
+    return (fRet);
+}
+
+
+tANI_BOOLEAN csrIsRoamCommandWaiting(tpAniSirGlobal pMac)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    tANI_U32 i;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && ( fRet = csrIsRoamCommandWaitingForSession( pMac, i ) ) )
+        {
+            break;
+        }
+    }
+
+    return ( fRet );
+}
+
+
+tANI_BOOLEAN csrIsCommandWaiting(tpAniSirGlobal pMac)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+
+    //alwasy lock active list before locking pending list
+    csrLLLock( &pMac->sme.smeCmdActiveList );
+    fRet = csrLLIsListEmpty(&pMac->sme.smeCmdActiveList, LL_ACCESS_NOLOCK);
+    if(eANI_BOOLEAN_FALSE == fRet)
+    {
+        fRet = csrLLIsListEmpty(&pMac->sme.smeCmdPendingList, LL_ACCESS_LOCK);
+    }
+    csrLLUnlock( &pMac->sme.smeCmdActiveList );
+
+    return (fRet);
+}
+
+
+tANI_BOOLEAN csrIsScanForRoamCommandActive( tpAniSirGlobal pMac )
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    tListElem *pEntry;
+    tCsrCmd *pCommand;
+
+    //alwasy lock active list before locking pending list
+    csrLLLock( &pMac->sme.smeCmdActiveList );
+    pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_NOLOCK);
+    if( pEntry )
+    {
+        pCommand = GET_BASE_ADDR(pEntry, tCsrCmd, Link);
+        if( ( eCsrRoamCommandScan == pCommand->command ) && 
+            ( ( eCsrScanForSsid == pCommand->u.scanCmd.reason ) || 
+              ( eCsrScanForCapsChange == pCommand->u.scanCmd.reason ) ||
+              ( eCsrScanP2PFindPeer == pCommand->u.scanCmd.reason ) ) )
+        {
+            fRet = eANI_BOOLEAN_TRUE;
+        }
+    }
+    csrLLUnlock( &pMac->sme.smeCmdActiveList );
+
+    return (fRet);
+}
+
+eHalStatus csrRoamIssueReassociateCmd( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand = NULL;
+    tANI_BOOLEAN fHighPriority = eANI_BOOLEAN_TRUE;
+    tANI_BOOLEAN fRemoveCmd = FALSE;
+    tListElem *pEntry; 
+
+    // Delete the old assoc command. All is setup for reassoc to be serialized
+    pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+    if ( pEntry )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        if ( !pCommand ) 
+        {
+            smsLog( pMac, LOGE, FL(" fail to get command buffer\n") );
+            return eHAL_STATUS_RESOURCES;
+        }
+        if ( eSmeCommandRoam == pCommand->command )
+        {
+            if (pCommand->u.roamCmd.roamReason == eCsrSmeIssuedAssocToSimilarAP)
+            {
+                fRemoveCmd = csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK );
+            }
+            else 
+            {
+                smsLog( pMac, LOGE, FL(" Unexpected active roam command present \n") );
+            }
+            if (fRemoveCmd == FALSE)
+            {
+                // Implies we did not get the serialized assoc command we
+                // were expecting
+                pCommand = NULL;
+            }
+        }
+    }
+
+    if(NULL == pCommand)
+    {
+        smsLog( pMac, LOGE, FL(" fail to get command buffer as expected based on previous connect roam command\n") );
+        return eHAL_STATUS_RESOURCES;
+    }
+
+    do 
+    {
+        //Change the substate in case it is wait-for-key
+        if( CSR_IS_WAIT_FOR_KEY( pMac, sessionId ) )
+        {
+            csrRoamStopWaitForKeyTimer( pMac );
+            csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId );
+        }
+        pCommand->command = eSmeCommandRoam;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.roamCmd.roamReason = eCsrSmeIssuedFTReassoc;
+
+        status = csrQueueSmeCommand(pMac, pCommand, fHighPriority);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            csrReleaseCommandRoam( pMac, pCommand );
+        }
+    } while( 0 );
+
+
+    return( status );
+}
+static void csrRoamingStateConfigCnfProcessor( tpAniSirGlobal pMac, tANI_U32 result )
+{
+    tListElem *pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+    tCsrScanResult *pScanResult = NULL;
+    tSirBssDescription *pBssDesc = NULL;
+    tSmeCmd *pCommand = NULL;
+    tANI_U32 sessionId;
+    tCsrRoamSession *pSession;
+
+    if(NULL == pEntry)
+    {
+        smsLog(pMac, LOGW, "   CFG_CNF with active list empty\n");
+        return;
+    }
+    pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+    sessionId = pCommand->sessionId;
+    pSession = CSR_GET_SESSION( pMac, sessionId );
+    if(CSR_IS_ROAMING(pSession) && pSession->fCancelRoaming)
+    {
+        //the roaming is cancelled. Simply complete the command
+        smsLog(pMac, LOGW, FL("  Roam command cancelled\n"));
+        csrRoamComplete(pMac, eCsrNothingToJoin, NULL); 
+    }
+    else
+    {
+        if ( CCM_IS_RESULT_SUCCESS(result) )
+        {
+            smsLog(pMac, LOG2, "Cfg sequence complete\n");
+            // Successfully set the configuration parameters for the new Bss.  Attempt to
+            // join the roaming Bss.
+            if(pCommand->u.roamCmd.pRoamBssEntry)
+            {
+                pScanResult = GET_BASE_ADDR(pCommand->u.roamCmd.pRoamBssEntry, tCsrScanResult, Link);
+                pBssDesc = &pScanResult->Result.BssDescriptor;
+            }
+            if ( csrIsBssTypeIBSS( pCommand->u.roamCmd.roamProfile.BSSType ) ||
+                 CSR_IS_WDS( &pCommand->u.roamCmd.roamProfile ) 
+#ifdef WLAN_SOFTAP_FEATURE
+                  || CSR_IS_INFRA_AP(&pCommand->u.roamCmd.roamProfile) 
+#endif
+            )
+            {
+                if(!HAL_STATUS_SUCCESS(csrRoamIssueStartBss( pMac, sessionId,
+                                        &pSession->bssParams, &pCommand->u.roamCmd.roamProfile, 
+                                        pBssDesc, pCommand->u.roamCmd.roamId )))
+                {
+                    smsLog(pMac, LOGW, " CSR start BSS failed\n");
+                    //We need to complete the command
+                    csrRoamComplete(pMac, eCsrStartBssFailure, NULL);
+                }
+            }
+            else
+            {
+                if (!pCommand->u.roamCmd.pRoamBssEntry)
+                {
+                    smsLog(pMac, LOGW, " pRoamBssEntry is NULL\n");
+                    //We need to complete the command
+                    csrRoamComplete(pMac, eCsrJoinFailure, NULL);
+                    return;
+                } 
+                // If we are roaming TO an Infrastructure BSS...
+                VOS_ASSERT(pScanResult != NULL); 
+                if ( csrIsInfraBssDesc( pBssDesc ) )
+                {
+                    tDot11fBeaconIEs *pIesLocal = (tDot11fBeaconIEs *)pScanResult->Result.pvIes;
+
+                    if(pIesLocal || (HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIesLocal))) )
+                    {
+                    // ..and currently in an Infrastructure connection....
+                    if( csrIsConnStateConnectedInfra( pMac, sessionId ) )
+                    {
+                        // ...and the SSIDs are equal, then we Reassoc.
+                        if (  csrIsSsidEqual( pMac, pSession->pConnectBssDesc, pBssDesc, 
+                                                    pIesLocal ) )
+                        // ..and currently in an infrastructure connection
+                        {
+                            // then issue a Reassoc.
+                            pCommand->u.roamCmd.fReassoc = eANI_BOOLEAN_TRUE;
+                                csrRoamIssueReassociate( pMac, sessionId, pBssDesc, pIesLocal,
+                                                        &pCommand->u.roamCmd.roamProfile );
+                        }
+                        else
+                        {
+                                                     
+                            // otherwise, we have to issue a new Join request to LIM because we disassociated from the
+                            // previously associated AP.
+                            if(!HAL_STATUS_SUCCESS(csrRoamIssueJoin( pMac, sessionId, pBssDesc, 
+                                                                                                            pIesLocal, 
+                                                    &pCommand->u.roamCmd.roamProfile, pCommand->u.roamCmd.roamId )))
+                            {
+                                //try something else
+                                csrRoam( pMac, pCommand );
+                            }
+                        }
+                    }
+                    else
+                    {
+                        eHalStatus  status = eHAL_STATUS_SUCCESS;
+                         
+                        /* We need to come with other way to figure out that this is because of HO in BMP
+                           The below API will be only available for Android as it uses a different HO algorithm */
+                        /* Reassoc request will be used only for CCX and 11r handoff whereas other legacy roaming should 
+                         * use join request */
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                        if (csrRoamIsHandoffInProgress(pMac) && 
+                                                csrRoamIs11rAssoc(pMac))
+                        {
+                            status = csrRoamIssueReassociate(pMac, sessionId, pBssDesc, 
+                                    (tDot11fBeaconIEs *)( pScanResult->Result.pvIes ), &pCommand->u.roamCmd.roamProfile);
+                        }
+                        else
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+                        if (csrRoamIsHandoffInProgress(pMac) && 
+                                                csrRoamIsCCXAssoc(pMac))
+                        {
+                            // Now serialize the reassoc command.
+                            status = csrRoamIssueReassociateCmd(pMac, sessionId);
+                        }
+                        else
+#endif
+                        // else we are not connected and attempting to Join.  Issue the
+                        // Join request.
+                        {
+                            status = csrRoamIssueJoin( pMac, sessionId, pBssDesc, 
+                                                (tDot11fBeaconIEs *)( pScanResult->Result.pvIes ),
+                                                &pCommand->u.roamCmd.roamProfile, pCommand->u.roamCmd.roamId );
+                        }
+                        if(!HAL_STATUS_SUCCESS(status))
+                        {
+                            //try something else
+                            csrRoam( pMac, pCommand );
+                        }
+                    }
+                        if( !pScanResult->Result.pvIes )
+                        {
+                            //Locally allocated
+                            palFreeMemory(pMac->hHdd, pIesLocal);
+                        }
+                    }
+                }//if ( csrIsInfraBssDesc( pBssDesc ) )
+                else
+                {
+                    smsLog(pMac, LOGW, FL("  found BSSType mismatching the one in BSS description\n"));
+                }
+            }//else
+        }//if ( WNI_CFG_SUCCESS == result )
+        else
+        {
+            // In the event the configuration failed,  for infra let the roam processor 
+            //attempt to join something else...
+            if( pCommand->u.roamCmd.pRoamBssEntry && CSR_IS_INFRASTRUCTURE( &pCommand->u.roamCmd.roamProfile ) )
+            {
+            csrRoam(pMac, pCommand);
+            }
+            else
+            {
+                //We need to complete the command
+                if ( csrIsBssTypeIBSS( pCommand->u.roamCmd.roamProfile.BSSType ) )
+                {
+                    csrRoamComplete(pMac, eCsrStartBssFailure, NULL);
+                }
+                else
+                {
+                    csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+                }
+            }
+        }
+    }//we have active entry
+}
+
+
+static void csrRoamRoamingStateAuthRspProcessor( tpAniSirGlobal pMac, tSirSmeAuthRsp *pSmeAuthRsp )
+{
+    //No one is sending eWNI_SME_AUTH_REQ to PE.
+    smsLog(pMac, LOGW, FL("is no-op\n"));
+    if ( eSIR_SME_SUCCESS == pSmeAuthRsp->statusCode ) 
+    {
+        smsLog( pMac, LOGW, "CSR SmeAuthReq Successful\n" );
+        // Successfully authenticated with a new Bss.  Attempt to stop the current Bss and
+        // join the new one...
+        /***pBssDesc = profGetRoamingBssDesc( pAdapter, &pHddProfile );
+
+        roamStopNetwork( pAdapter, &pBssDesc->SirBssDescription );***/
+    }
+    else {
+        smsLog( pMac, LOGW, "CSR SmeAuthReq failed with statusCode= 0x%08lX [%d]\n", pSmeAuthRsp->statusCode, pSmeAuthRsp->statusCode );
+        /***profHandleLostLinkAfterReset(pAdapter);
+        // In the event the authenticate fails, let the roam processor attempt to join something else...
+        roamRoam( pAdapter );***/
+    }
+}
+
+
+static void csrRoamRoamingStateReassocRspProcessor( tpAniSirGlobal pMac, tpSirSmeJoinRsp pSmeJoinRsp )
+{
+    eCsrRoamCompleteResult result;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tCsrRoamInfo roamInfo;
+    tANI_U32 roamId = 0;
+    
+    if ( eSIR_SME_SUCCESS == pSmeJoinRsp->statusCode ) 
+    {
+        smsLog( pMac, LOGW, "CSR SmeReassocReq Successful\n" );
+        result = eCsrReassocSuccess;
+
+        /* Defeaturize this part later if needed */
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+        /* Since the neighbor roam algorithm uses reassoc req for handoff instead of join, 
+         * we need the response contents while processing the result in csrRoamProcessResults() */
+        if (csrRoamIsHandoffInProgress(pMac))
+        {
+            /* Need to dig more on indicating events to SME QoS module */
+            sme_QosCsrEventInd(pMac, pSmeJoinRsp->sessionId, SME_QOS_CSR_HANDOFF_COMPLETE, NULL);
+            csrRoamComplete( pMac, result, pSmeJoinRsp);
+        }
+        else
+#endif
+        {
+            csrRoamComplete( pMac, result, NULL );
+        }
+    }
+    /* Should we handle this similar to handling the join failure? Is it ok
+     * to call csrRoamComplete() with state as CsrJoinFailure */
+    else
+    {
+        smsLog( pMac, LOGW, "CSR SmeReassocReq failed with statusCode= 0x%08lX [%d]\n", pSmeJoinRsp->statusCode, pSmeJoinRsp->statusCode );
+        result = eCsrReassocFailure;
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        if ((eSIR_SME_FT_REASSOC_TIMEOUT_FAILURE == pSmeJoinRsp->statusCode) ||
+                        (eSIR_SME_FT_REASSOC_FAILURE == pSmeJoinRsp->statusCode))
+        {
+                // Inform HDD to turn off FT flag in HDD 
+                if (pNeighborRoamInfo)
+                {
+                        vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
+                        csrRoamCallCallback(pMac, pNeighborRoamInfo->csrSessionId,
+                                        &roamInfo, roamId, eCSR_ROAM_FT_REASSOC_FAILED, eSIR_SME_SUCCESS);
+                }
+        }
+#endif
+        // In the event that the Reassociation fails, then we need to Disassociate the current association and keep
+        // roaming.  Note that we will attempt to Join the AP instead of a Reassoc since we may have attempted a
+        // 'Reassoc to self', which AP's that don't support Reassoc will force a Disassoc.
+        //The disassoc rsp message will remove the command from active list
+        if(!HAL_STATUS_SUCCESS(csrRoamIssueDisassociate( pMac, pSmeJoinRsp->sessionId,
+                        eCSR_ROAM_SUBSTATE_DISASSOC_REASSOC_FAILURE, FALSE )))
+        {
+            csrRoamComplete( pMac, eCsrJoinFailure, NULL );
+        }
+    }
+}
+
+
+static void csrRoamRoamingStateStopBssRspProcessor(tpAniSirGlobal pMac, tSirSmeRsp *pSmeRsp)
+{
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+    {
+        vos_log_ibss_pkt_type *pIbssLog;
+
+        WLAN_VOS_DIAG_LOG_ALLOC(pIbssLog, vos_log_ibss_pkt_type, LOG_WLAN_IBSS_C);
+        if(pIbssLog)
+        {
+            pIbssLog->eventId = WLAN_IBSS_EVENT_STOP_RSP;
+            if(eSIR_SME_SUCCESS != pSmeRsp->statusCode)
+            {
+                pIbssLog->status = WLAN_IBSS_STATUS_FAILURE;
+            }
+            WLAN_VOS_DIAG_LOG_REPORT(pIbssLog);
+        }
+    }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+    pMac->roam.roamSession[pSmeRsp->sessionId].connectState = eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED;
+    if(CSR_IS_ROAM_SUBSTATE_STOP_BSS_REQ( pMac, pSmeRsp->sessionId))
+    {
+        csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+    }
+    else if(CSR_IS_ROAM_SUBSTATE_DISCONNECT_CONTINUE( pMac, pSmeRsp->sessionId))
+    {
+        csrRoamReissueRoamCommand(pMac);
+    }
+}
+
+
+void csrRoamRoamingStateDisassocRspProcessor( tpAniSirGlobal pMac, tSirSmeDisassocRsp *pSmeRsp )
+{
+    tSirResultCodes statusCode;
+#if defined WLAN_FEATURE_NEIGHBOR_ROAMING
+    tScanResultHandle hBSSList;
+    tANI_BOOLEAN fCallCallback, fRemoveCmd;
+    eHalStatus status;
+    tCsrRoamInfo roamInfo;
+    tCsrScanResultFilter *pScanFilter = NULL;
+    tANI_U32 roamId = 0;
+    tCsrRoamProfile *pCurRoamProfile = NULL;
+    tListElem *pEntry = NULL;
+    tSmeCmd *pCommand = NULL;
+#endif
+    tANI_U32 sessionId;
+    tCsrRoamSession *pSession;
+    tSirSmeDisassocRsp SmeDisassocRsp;
+
+    csrSerDesUnpackDiassocRsp((tANI_U8 *)pSmeRsp, &SmeDisassocRsp);
+    sessionId = SmeDisassocRsp.sessionId;
+    statusCode = SmeDisassocRsp.statusCode;
+
+    smsLog( pMac, LOG2, "csrRoamRoamingStateDisassocRspProcessor sessionId %d\n", sessionId);
+
+    if ( csrIsConnStateInfra( pMac, sessionId ) )
+    {
+        pMac->roam.roamSession[sessionId].connectState = eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED;
+    }
+
+    pSession = CSR_GET_SESSION( pMac, sessionId );
+    if ( CSR_IS_ROAM_SUBSTATE_DISASSOC_NO_JOIN( pMac, sessionId ) )
+    {
+        csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+    }
+    else if ( CSR_IS_ROAM_SUBSTATE_DISASSOC_FORCED( pMac, sessionId ) ||
+              CSR_IS_ROAM_SUBSTATE_DISASSOC_REQ( pMac, sessionId ) )
+    {
+        if ( eSIR_SME_SUCCESS == statusCode )
+        {
+            smsLog( pMac, LOG2, "CSR SmeDisassocReq force disassociated Successfully\n" );
+            //A callback to HDD will be issued from csrRoamComplete so no need to do anything here
+        } 
+        csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+    }
+
+    else if ( CSR_IS_ROAM_SUBSTATE_DISASSOC_HO( pMac, sessionId ) )
+    {
+       smsLog( pMac, LOGE, "CSR SmeDisassocReq due to HO\n" );
+#if   defined (WLAN_FEATURE_NEIGHBOR_ROAMING)
+        pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+        if ( pEntry )
+        {
+            pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+
+            // If the head of the queue is Active and it is a ROAM command, remove
+            // and put this on the Free queue.
+            if ( eSmeCommandRoam == pCommand->command )
+            {
+                //we need to process the result first before removing it from active list because state changes 
+                //still happening insides roamQProcessRoamResults so no other roam command should be issued
+                fRemoveCmd = csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK );
+                if(pCommand->u.roamCmd.fReleaseProfile)
+                {
+                    csrReleaseProfile(pMac, &pCommand->u.roamCmd.roamProfile);
+                    pCommand->u.roamCmd.fReleaseProfile = eANI_BOOLEAN_FALSE;
+                }
+
+                if( fRemoveCmd )
+                {
+                    csrReleaseCommandRoam( pMac, pCommand );
+                }
+                else
+                {
+                    smsLog( pMac, LOGE, "  ********csrRoamRoamingStateDisassocRspProcessor fail to remove cmd reason %d\n",
+                        pCommand->u.roamCmd.roamReason );
+                }
+            }
+            else
+            {
+                smsLog( pMac, LOGW, "CSR: Roam Completion called but ROAM command is not ACTIVE ...\n" );
+            }
+        }
+        else
+        {
+            smsLog( pMac, LOGW, "CSR: Roam Completion called but NO commands are ACTIVE ...\n" );
+        }
+
+        //notify HDD for handoff, providing the BSSID too
+        roamInfo.reasonCode = eCsrRoamReasonBetterAP;
+
+        palCopyMemory(pMac->hHdd, roamInfo.bssid, pMac->roam.neighborRoamInfo.csrNeighborRoamProfile.BSSIDs.bssid, sizeof(tSirMacAddr));
+
+        csrRoamCallCallback(pMac,sessionId, &roamInfo, 0, eCSR_ROAM_ROAMING_START, eCSR_ROAM_RESULT_NONE);
+
+        status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            status = csrRoamPrepareFilterFromProfile(pMac, &pMac->roam.neighborRoamInfo.csrNeighborRoamProfile, pScanFilter);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                smsLog(pMac, LOGE, FL(" csrRoamPrepareFilterFromProfile fail to create scan filter\n"));
+            }
+        
+            status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                //copy over the connected profile to apply the same for this connection as well
+                if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, (void **)&pCurRoamProfile, sizeof(tCsrRoamProfile))))
+                {
+                    palZeroMemory(pMac->hHdd, pCurRoamProfile, sizeof(tCsrRoamProfile));
+                    csrRoamCopyProfile(pMac, pCurRoamProfile, pSession->pCurRoamProfile);
+                }
+                //make sure to put it at the head of the cmd queue
+                status = csrRoamIssueConnect(pMac, sessionId, pCurRoamProfile, 
+                                             hBSSList, eCsrSmeIssuedAssocToSimilarAP, 
+                                             roamId, eANI_BOOLEAN_TRUE, eANI_BOOLEAN_FALSE);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    //msg
+                    fCallCallback = eANI_BOOLEAN_TRUE;
+                }
+                /* Notify sub-modules like QoS etc. that handoff happening         */
+                sme_QosCsrEventInd(pMac, sessionId, SME_QOS_CSR_HANDOFF_ASSOC_REQ, NULL);
+                palFreeMemory(pMac->hHdd, pCurRoamProfile);
+            }
+            else
+            {
+                //msg
+                smsLog( pMac, LOGE,"csrRoamRoamingStateDisassocRspProcessor: csrScanGetResult failed");
+                // should have asserted, sending up roam complete instead. Let upper layer
+                // decide what to do next
+                csrCallRoamingCompletionCallback(pMac, pSession, &roamInfo, 0, eCSR_ROAM_RESULT_FAILURE);
+            }
+        }
+        else
+        {
+            smsLog(pMac, LOGE, FL(" fail to allocate memory for scan filter\n"));
+            csrCallRoamingCompletionCallback(pMac, pSession, &roamInfo, 0, eCSR_ROAM_RESULT_FAILURE);
+        }
+        if( pScanFilter )
+        {
+            csrFreeScanFilter(pMac, pScanFilter);
+            palFreeMemory( pMac->hHdd, pScanFilter );
+        }
+
+
+#endif
+    } //else if ( CSR_IS_ROAM_SUBSTATE_DISASSOC_HO( pMac ) )
+    else if ( CSR_IS_ROAM_SUBSTATE_REASSOC_FAIL( pMac, sessionId ) )
+    {
+        // Disassoc due to Reassoc failure falls into this codepath....
+        csrRoamComplete( pMac, eCsrJoinFailure, NULL );
+    }
+    else
+    {
+        if ( eSIR_SME_SUCCESS == statusCode )
+        {
+            // Successfully disassociated from the 'old' Bss...
+            //
+            // We get Disassociate response in three conditions.
+            // - First is the case where we are disasociating from an Infra Bss to start an IBSS.
+            // - Second is the when we are disassociating from an Infra Bss to join an IBSS or a new
+            // Infrastructure network.
+            // - Third is where we are doing an Infra to Infra roam between networks with different
+            // SSIDs.  In all cases, we set the new Bss configuration here and attempt to join
+            
+            smsLog( pMac, LOG2, "CSR SmeDisassocReq disassociated Successfully\n" );
+        }
+        else
+        {
+            smsLog( pMac, LOGE, "SmeDisassocReq failed with statusCode= 0x%08lX\n", statusCode );
+        }
+        //We are not done yet. Get the data and continue roaming
+        csrRoamReissueRoamCommand(pMac);
+    }
+
+}
+
+
+static void csrRoamRoamingStateDeauthRspProcessor( tpAniSirGlobal pMac, tSirSmeDeauthRsp *pSmeRsp )
+{
+    tSirResultCodes statusCode;
+
+    //No one is sending eWNI_SME_DEAUTH_REQ to PE.
+    smsLog(pMac, LOGW, FL("is no-op\n"));
+    statusCode = csrGetDeAuthRspStatusCode( pSmeRsp );
+    if ( CSR_IS_ROAM_SUBSTATE_DEAUTH_REQ( pMac, pSmeRsp->sessionId) )
+    {
+        csrRoamComplete( pMac, eCsrNothingToJoin, NULL );
+    }
+    else
+    {
+        if ( eSIR_SME_SUCCESS == statusCode ) 
+        {
+            // Successfully deauth from the 'old' Bss...
+            //
+            smsLog( pMac, LOG2, "CSR SmeDeauthReq disassociated Successfully\n" );
+        }
+        else
+        {
+            smsLog( pMac, LOGW, "SmeDeauthReq failed with statusCode= 0x%08lX\n", statusCode );
+        }
+        //We are not done yet. Get the data and continue roaming
+        csrRoamReissueRoamCommand(pMac);
+    }
+}
+
+
+static void csrRoamRoamingStateStartBssRspProcessor( tpAniSirGlobal pMac, tSirSmeStartBssRsp *pSmeStartBssRsp )
+{
+    eCsrRoamCompleteResult result;
+    
+    if ( eSIR_SME_SUCCESS == pSmeStartBssRsp->statusCode ) 
+    {
+        smsLog( pMac, LOGW, "SmeStartBssReq Successful\n" );
+        result = eCsrStartBssSuccess;
+    }
+    else 
+    {
+        smsLog( pMac, LOGW, "SmeStartBssReq failed with statusCode= 0x%08lX\n", pSmeStartBssRsp->statusCode );
+        //Let csrRoamComplete decide what to do
+        result = eCsrStartBssFailure;
+    }
+#ifdef WLAN_SOFTAP_FEATURE
+    csrRoamComplete( pMac, result, pSmeStartBssRsp);
+#else
+    csrRoamComplete( pMac, result, &pSmeStartBssRsp->bssDescription );
+#endif
+}
+
+
+/*
+  We need to be careful on whether to cast pMsgBuf (pSmeRsp) to other type of strucutres.
+  It depends on how the message is constructed. If the message is sent by limSendSmeRsp,
+  the pMsgBuf is only a generic response and can only be used as pointer to tSirSmeRsp.
+  For the messages where sender allocates memory for specific structures, then it can be 
+  cast accordingly.
+*/
+void csrRoamingStateMsgProcessor( tpAniSirGlobal pMac, void *pMsgBuf )
+{
+    tSirSmeRsp *pSmeRsp;
+    tSmeIbssPeerInd *pIbssPeerInd;
+    tCsrRoamInfo roamInfo;
+        // TODO Session Id need to be acquired in this function
+        tANI_U32 sessionId = 0;
+
+    pSmeRsp = (tSirSmeRsp *)pMsgBuf;
+
+    smsLog( pMac, LOG2, "Message %d[0x%04X] received in substate %d\n",
+                pSmeRsp->messageType, pSmeRsp->messageType,
+                pMac->roam.curSubState[pSmeRsp->sessionId] );
+#if defined ANI_PRODUCT_TYPE_AP
+    pSmeRsp->messageType = pal_be16_to_cpu(pSmeRsp->messageType);
+    pSmeRsp->length = pal_be16_to_cpu(pSmeRsp->length);
+    pSmeRsp->statusCode = pal_be32_to_cpu(pSmeRsp->statusCode);
+#else
+    pSmeRsp->messageType = (pSmeRsp->messageType);
+    pSmeRsp->length = (pSmeRsp->length);
+    pSmeRsp->statusCode = (pSmeRsp->statusCode);
+#endif
+    switch (pSmeRsp->messageType) 
+    {
+        
+        case eWNI_SME_JOIN_RSP:      // in Roaming state, process the Join response message...
+            if (CSR_IS_ROAM_SUBSTATE_JOIN_REQ(pMac, pSmeRsp->sessionId))
+            {
+                //We sent a JOIN_REQ
+                csrRoamJoinRspProcessor( pMac, (tSirSmeJoinRsp *)pSmeRsp );
+            }
+            break;
+                
+        case eWNI_SME_AUTH_RSP:       // or the Authenticate response message...
+            if (CSR_IS_ROAM_SUBSTATE_AUTH_REQ( pMac, pSmeRsp->sessionId) ) 
+            {
+                //We sent a AUTH_REQ
+                csrRoamRoamingStateAuthRspProcessor( pMac, (tSirSmeAuthRsp *)pSmeRsp );
+            }
+            break;
+                
+        case eWNI_SME_REASSOC_RSP:     // or the Reassociation response message...
+            if (CSR_IS_ROAM_SUBSTATE_REASSOC_REQ( pMac, pSmeRsp->sessionId) ) 
+            {
+                csrRoamRoamingStateReassocRspProcessor( pMac, (tpSirSmeJoinRsp )pSmeRsp );
+            }
+            break;
+                   
+        case eWNI_SME_STOP_BSS_RSP:    // or the Stop Bss response message...
+            {
+                csrRoamRoamingStateStopBssRspProcessor(pMac, pSmeRsp);
+            }
+            break;
+                
+        case eWNI_SME_DISASSOC_RSP:    // or the Disassociate response message...
+            if ( CSR_IS_ROAM_SUBSTATE_DISASSOC_REQ( pMac, pSmeRsp->sessionId )      ||
+                 CSR_IS_ROAM_SUBSTATE_DISASSOC_NO_JOIN( pMac, pSmeRsp->sessionId )  ||
+                 CSR_IS_ROAM_SUBSTATE_REASSOC_FAIL( pMac, pSmeRsp->sessionId )      ||
+                 CSR_IS_ROAM_SUBSTATE_DISASSOC_FORCED( pMac, pSmeRsp->sessionId )   ||
+                 CSR_IS_ROAM_SUBSTATE_DISCONNECT_CONTINUE( pMac, pSmeRsp->sessionId ) ||
+//HO
+                 CSR_IS_ROAM_SUBSTATE_DISASSOC_HO( pMac, pSmeRsp->sessionId )         )
+            {
+                smsLog(pMac, LOGE, FL("eWNI_SME_DISASSOC_RSP subState = %d\n"), pMac->roam.curSubState[pSmeRsp->sessionId]);
+                csrRoamRoamingStateDisassocRspProcessor( pMac, (tSirSmeDisassocRsp *)pSmeRsp );
+            }
+            break;
+                   
+        case eWNI_SME_DEAUTH_RSP:    // or the Deauthentication response message...
+            if ( CSR_IS_ROAM_SUBSTATE_DEAUTH_REQ( pMac, pSmeRsp->sessionId ) ) 
+            {
+                csrRoamRoamingStateDeauthRspProcessor( pMac, (tSirSmeDeauthRsp *)pSmeRsp );
+            }
+            break;
+                   
+        case eWNI_SME_START_BSS_RSP:      // or the Start BSS response message...
+            if (CSR_IS_ROAM_SUBSTATE_START_BSS_REQ( pMac, pSmeRsp->sessionId ) ) 
+            {
+                csrRoamRoamingStateStartBssRspProcessor( pMac, (tSirSmeStartBssRsp *)pSmeRsp );
+            } 
+            break;
+                   
+        case WNI_CFG_SET_CNF:    // process the Config Confirm messages when we are in 'Config' substate...
+            if ( CSR_IS_ROAM_SUBSTATE_CONFIG( pMac, pSmeRsp->sessionId ) ) 
+            {
+                csrRoamingStateConfigCnfProcessor( pMac, ((tCsrCfgSetRsp *)pSmeRsp)->respStatus );
+            }
+
+            break;
+
+        //In case CSR issues STOP_BSS, we need to tell HDD about peer departed becasue PE is removing them
+        case eWNI_SME_IBSS_PEER_DEPARTED_IND:
+            pIbssPeerInd = (tSmeIbssPeerInd*)pSmeRsp;
+            smsLog(pMac, LOGE, "CSR: Peer departed notification from LIM in joining state\n");
+            palZeroMemory( pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo) );
+                        roamInfo.staId = (tANI_U8)pIbssPeerInd->staId;
+            roamInfo.ucastSig = (tANI_U8)pIbssPeerInd->ucastSig;
+            roamInfo.bcastSig = (tANI_U8)pIbssPeerInd->bcastSig;
+            palCopyMemory(pMac->hHdd, &roamInfo.peerMac, pIbssPeerInd->peerAddr, sizeof(tCsrBssid));
+            csrRoamCallCallback(pMac, sessionId, &roamInfo, 0, 
+                                eCSR_ROAM_CONNECT_STATUS_UPDATE, 
+                                eCSR_ROAM_RESULT_IBSS_PEER_DEPARTED);
+            break;
+
+        default:
+            smsLog( pMac, LOG1, "Unexpected message type = %d[0x%X] received in substate %d\n",
+                      pSmeRsp->messageType, pSmeRsp->messageType,
+                      pMac->roam.curSubState[pSmeRsp->sessionId] );
+
+            //If we are connected, check the link status change 
+                        if(!csrIsConnStateDisconnected(pMac, sessionId))
+                        {
+                                csrRoamCheckForLinkStatusChange( pMac, pSmeRsp );
+                        }
+            break;          
+    }
+}
+
+
+void csrRoamJoinedStateMsgProcessor( tpAniSirGlobal pMac, void *pMsgBuf )
+{
+    tSirSmeRsp *pSirMsg = (tSirSmeRsp *)pMsgBuf;
+
+    switch (pSirMsg->messageType) 
+    {
+       case eWNI_SME_GET_STATISTICS_RSP:
+          smsLog( pMac, LOGW, FL("Stats rsp from PE\n"));
+          csrRoamStatsRspProcessor( pMac, pSirMsg );
+          break;
+#ifdef WLAN_SOFTAP_FEATURE
+        case eWNI_SME_UPPER_LAYER_ASSOC_CNF:
+        {
+            tCsrRoamSession  *pSession;
+            tSirSmeAssocIndToUpperLayerCnf *pUpperLayerAssocCnf;
+            tCsrRoamInfo roamInfo;
+            tCsrRoamInfo *pRoamInfo = NULL;
+            tANI_U32 sessionId;
+            eHalStatus status;
+
+            smsLog( pMac, LOG1, FL("ASSOCIATION confirmation can be given to upper layer \n"));
+
+            palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+            pRoamInfo = &roamInfo;
+
+            pUpperLayerAssocCnf = (tSirSmeAssocIndToUpperLayerCnf *)pMsgBuf;
+            status = csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid *)pUpperLayerAssocCnf->bssId, &sessionId );
+            pSession = CSR_GET_SESSION(pMac, sessionId);
+
+            pRoamInfo->statusCode = eSIR_SME_SUCCESS; //send the status code as Success 
+            pRoamInfo->u.pConnectedProfile = &pSession->connectedProfile;
+
+            pRoamInfo->staId = (tANI_U8)pUpperLayerAssocCnf->aid;
+            pRoamInfo->rsnIELen = (tANI_U8)pUpperLayerAssocCnf->rsnIE.length;
+            pRoamInfo->prsnIE = pUpperLayerAssocCnf->rsnIE.rsnIEdata;
+
+            pRoamInfo->addIELen = (tANI_U8)pUpperLayerAssocCnf->addIE.length;
+            pRoamInfo->paddIE = pUpperLayerAssocCnf->addIE.addIEdata;           
+
+            palCopyMemory(pMac->hHdd, pRoamInfo->peerMac, pUpperLayerAssocCnf->peerMacAddr, sizeof(tSirMacAddr));
+            palCopyMemory(pMac->hHdd, &pRoamInfo->bssid, pUpperLayerAssocCnf->bssId, sizeof(tCsrBssid));
+
+            pRoamInfo->wmmEnabledSta = pUpperLayerAssocCnf->wmmEnabledSta;
+
+            if(CSR_IS_INFRA_AP(pRoamInfo->u.pConnectedProfile) )
+            {
+                pMac->roam.roamSession[sessionId].connectState = eCSR_ASSOC_STATE_TYPE_INFRA_CONNECTED;
+                pRoamInfo->fReassocReq = pUpperLayerAssocCnf->reassocReq;
+                status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_INFRA_IND, eCSR_ROAM_RESULT_INFRA_ASSOCIATION_CNF);
+            }
+            if(CSR_IS_WDS_AP( pRoamInfo->u.pConnectedProfile))
+            {
+                vos_sleep( 100 );
+                pMac->roam.roamSession[sessionId].connectState = eCSR_ASSOC_STATE_TYPE_WDS_CONNECTED;//Sta
+                status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_WDS_IND, eCSR_ROAM_RESULT_WDS_ASSOCIATION_IND);//Sta
+            }
+
+
+        }
+        break;
+#endif
+
+       default:
+          csrRoamCheckForLinkStatusChange( pMac, pSirMsg );
+          break;
+    }
+
+}
+
+
+eHalStatus csrRoamIssueSetContextReq( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrEncryptionType EncryptType, 
+                                     tSirBssDescription *pBssDescription,
+                                tSirMacAddr *bssId, tANI_BOOLEAN addKey,
+                                 tANI_BOOLEAN fUnicast, tAniKeyDirection aniKeyDirection, 
+                                 tANI_U8 keyId, tANI_U16 keyLength, 
+                                 tANI_U8 *pKey, tANI_U8 paeRole )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tAniEdType edType;
+    
+    if(eCSR_ENCRYPT_TYPE_UNKNOWN == EncryptType)
+    {
+        EncryptType = eCSR_ENCRYPT_TYPE_NONE; //***
+    }
+    
+    edType = csrTranslateEncryptTypeToEdType( EncryptType );
+    
+    // Allow 0 keys to be set for the non-WPA encrypt types...  For WPA encrypt types, the num keys must be non-zero
+    // or LIM will reject the set context (assumes the SET_CONTEXT does not occur until the keys are distrubuted).
+    if ( CSR_IS_ENC_TYPE_STATIC( EncryptType ) ||
+           addKey )     
+    {
+        tCsrRoamSetKey setKey;
+
+        setKey.encType = EncryptType;
+        setKey.keyDirection = aniKeyDirection;    //Tx, Rx or Tx-and-Rx
+        palCopyMemory( pMac->hHdd, &setKey.peerMac, bssId, sizeof(tCsrBssid) );   
+        setKey.paeRole = paeRole;      //0 for supplicant
+        setKey.keyId = keyId;  // Kye index
+        setKey.keyLength = keyLength;  
+        if( keyLength )
+        {
+            palCopyMemory( pMac->hHdd, setKey.Key, pKey, keyLength );
+        }
+        status = csrRoamIssueSetKeyCommand( pMac, sessionId, &setKey, 0 );
+    }
+
+    return (status);
+}
+
+
+static eHalStatus csrRoamIssueSetKeyCommand( tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                             tCsrRoamSetKey *pSetKey, tANI_U32 roamId )
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tSmeCmd *pCommand = NULL;
+#ifdef FEATURE_WLAN_CCX
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+#endif /* FEATURE_WLAN_CCX */
+ 
+    do
+    {
+        pCommand = csrGetCommandBuffer(pMac);
+        if(NULL == pCommand)
+        {
+            smsLog( pMac, LOGE, FL(" fail to get command buffer\n") );
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        pCommand->command = eSmeCommandSetKey;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        // validate the key length,  Adjust if too long...
+        // for static WEP the keys are not set thru' SetContextReq
+        if ( ( eCSR_ENCRYPT_TYPE_WEP40 == pSetKey->encType ) || 
+             ( eCSR_ENCRYPT_TYPE_WEP40_STATICKEY == pSetKey->encType ) ) 
+        {
+            //KeyLength maybe 0 for static WEP
+            if( pSetKey->keyLength )
+            {
+                if ( pSetKey->keyLength < CSR_WEP40_KEY_LEN ) 
+                {
+                    smsLog( pMac, LOGW, "Invalid WEP40 keylength [= %d] in SetContext call\n", pSetKey->keyLength );
+                    break;        
+                }
+                
+                pCommand->u.setKeyCmd.keyLength = CSR_WEP40_KEY_LEN;
+                palCopyMemory( pMac->hHdd, pCommand->u.setKeyCmd.Key, pSetKey->Key, CSR_WEP40_KEY_LEN );
+            }
+        }
+        else if ( ( eCSR_ENCRYPT_TYPE_WEP104 == pSetKey->encType ) || 
+             ( eCSR_ENCRYPT_TYPE_WEP104_STATICKEY == pSetKey->encType ) ) 
+        {
+            //KeyLength maybe 0 for static WEP
+            if( pSetKey->keyLength )
+            {
+                if ( pSetKey->keyLength < CSR_WEP104_KEY_LEN ) 
+                {
+                    smsLog( pMac, LOGW, "Invalid WEP104 keylength [= %d] in SetContext call\n", pSetKey->keyLength );
+                    break;        
+                }
+                
+                pCommand->u.setKeyCmd.keyLength = CSR_WEP104_KEY_LEN;
+                palCopyMemory( pMac->hHdd, pCommand->u.setKeyCmd.Key, pSetKey->Key, CSR_WEP104_KEY_LEN );
+            }
+        }
+        else if ( eCSR_ENCRYPT_TYPE_TKIP == pSetKey->encType ) 
+        {
+            if ( pSetKey->keyLength < CSR_TKIP_KEY_LEN )
+            {
+                smsLog( pMac, LOGW, "Invalid TKIP keylength [= %d] in SetContext call\n", pSetKey->keyLength );
+                break;
+            }
+            pCommand->u.setKeyCmd.keyLength = CSR_TKIP_KEY_LEN;
+            palCopyMemory( pMac->hHdd, pCommand->u.setKeyCmd.Key, pSetKey->Key, CSR_TKIP_KEY_LEN );
+        }
+        else if ( eCSR_ENCRYPT_TYPE_AES == pSetKey->encType ) 
+        {
+            if ( pSetKey->keyLength < CSR_AES_KEY_LEN )
+            {
+                smsLog( pMac, LOGW, "Invalid AES/CCMP keylength [= %d] in SetContext call\n", pSetKey->keyLength );
+                break;
+            }
+            pCommand->u.setKeyCmd.keyLength = CSR_AES_KEY_LEN;
+            palCopyMemory( pMac->hHdd, pCommand->u.setKeyCmd.Key, pSetKey->Key, CSR_AES_KEY_LEN );
+        }
+#ifdef FEATURE_WLAN_WAPI
+        else if ( eCSR_ENCRYPT_TYPE_WPI == pSetKey->encType ) 
+        {
+            if ( pSetKey->keyLength < CSR_WAPI_KEY_LEN )
+            {
+                smsLog( pMac, LOGW, "Invalid WAPI keylength [= %d] in SetContext call\n", pSetKey->keyLength );
+                break;
+            }
+            pCommand->u.setKeyCmd.keyLength = CSR_WAPI_KEY_LEN;
+            palCopyMemory( pMac->hHdd, pCommand->u.setKeyCmd.Key, pSetKey->Key, CSR_WAPI_KEY_LEN );
+        }
+#endif /* FEATURE_WLAN_WAPI */
+#ifdef FEATURE_WLAN_CCX
+        else if ( eCSR_ENCRYPT_TYPE_KRK == pSetKey->encType ) 
+        {
+            if ( pSetKey->keyLength < CSR_KRK_KEY_LEN )
+            {
+                smsLog( pMac, LOGW, "Invalid KRK keylength [= %d] in SetContext call\n", pSetKey->keyLength );
+                break;
+            }
+            palCopyMemory( pMac->hHdd, pSession->ccxCckmInfo.krk, pSetKey->Key, CSR_KRK_KEY_LEN );
+            pSession->ccxCckmInfo.reassoc_req_num=1;
+            pSession->ccxCckmInfo.krk_plumbed = eANI_BOOLEAN_TRUE;
+            status = eHAL_STATUS_SUCCESS;
+            break;
+        }
+#endif /* FEATURE_WLAN_CCX */
+#ifdef WLAN_FEATURE_11W
+        //Check for 11w BIP
+        else if ( eCSR_ENCRYPT_TYPE_AES_CMAC == pSetKey->encType )
+        {
+            tANI_U16 count = 0;
+            if ( pSetKey->keyLength < CSR_AES_KEY_LEN )
+            {
+                smsLog( pMac, LOGW, "Invalid AES/CCMP keylength [= %d] in SetContext call\n", pSetKey->keyLength );
+                break;
+            }
+            pCommand->u.setKeyCmd.keyLength = CSR_AES_KEY_LEN;
+            palCopyMemory( pMac->hHdd, pCommand->u.setKeyCmd.Key, pSetKey->Key, CSR_AES_KEY_LEN );
+        }
+#endif
+        status = eHAL_STATUS_SUCCESS;
+        pCommand->u.setKeyCmd.roamId = roamId;
+        pCommand->u.setKeyCmd.encType = pSetKey->encType;
+        pCommand->u.setKeyCmd.keyDirection = pSetKey->keyDirection;    //Tx, Rx or Tx-and-Rx
+        palCopyMemory( pMac->hHdd, &pCommand->u.setKeyCmd.peerMac, &pSetKey->peerMac, sizeof(tCsrBssid) );   
+        pCommand->u.setKeyCmd.paeRole = pSetKey->paeRole;      //0 for supplicant
+        pCommand->u.setKeyCmd.keyId = pSetKey->keyId;
+        palCopyMemory( pMac->hHdd, pCommand->u.setKeyCmd.keyRsc, pSetKey->keyRsc, CSR_MAX_RSC_LEN );
+        //Always put set key to the head of the Q because it is the only thing to get executed in case of WT_KEY state
+         
+        status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_TRUE);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+        }
+    } while (0);
+
+    // Free the command if there has been a failure, or it is a 
+    // "local" operation like the set CCX CCKM KRK key.
+    if( (!HAL_STATUS_SUCCESS( status ) && ( NULL != pCommand )) 
+#ifdef FEATURE_WLAN_CCX
+            || ( eCSR_ENCRYPT_TYPE_KRK == pSetKey->encType ) 
+#endif /* FEATURE_WLAN_CCX */
+            )
+    {
+        csrReleaseCommandSetKey( pMac, pCommand );
+    }
+
+    return( status );
+}
+
+
+eHalStatus csrRoamIssueRemoveKeyCommand( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                         tCsrRoamRemoveKey *pRemoveKey, tANI_U32 roamId )
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tSmeCmd *pCommand = NULL;
+    tANI_BOOLEAN fImediate = eANI_BOOLEAN_TRUE;
+
+    do
+    {
+        if( !csrIsSetKeyAllowed(pMac, sessionId) ) 
+        {
+            smsLog( pMac, LOGW, FL(" wrong state not allowed to set key\n") );
+            status = eHAL_STATUS_CSR_WRONG_STATE;
+            break;
+        }
+        pCommand = csrGetCommandBuffer(pMac);
+        if(NULL == pCommand)
+        {
+            smsLog( pMac, LOGE, FL(" fail to get command buffer\n") );
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        pCommand->command = eSmeCommandRemoveKey;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.removeKeyCmd.roamId = roamId;
+        pCommand->u.removeKeyCmd.encType = pRemoveKey->encType;
+        palCopyMemory( pMac->hHdd, &pCommand->u.removeKeyCmd.peerMac, &pRemoveKey->peerMac, sizeof(tSirMacAddr) );
+        pCommand->u.removeKeyCmd.keyId = pRemoveKey->keyId;
+        if( CSR_IS_WAIT_FOR_KEY( pMac, sessionId ) )
+        {
+            //in this case, put it to the end of the Q incase there is a set key pending.
+            fImediate = eANI_BOOLEAN_FALSE;
+        }
+
+        smsLog( pMac, LOGE, FL("keyType=%d, keyId=%d, PeerMac=%02x, %02x, %02x, %02x, %02x, %02x\n"),       
+            pRemoveKey->encType, pRemoveKey->keyId,
+            pCommand->u.removeKeyCmd.peerMac[0],
+            pCommand->u.removeKeyCmd.peerMac[1],
+            pCommand->u.removeKeyCmd.peerMac[2], 
+            pCommand->u.removeKeyCmd.peerMac[3], 
+            pCommand->u.removeKeyCmd.peerMac[4],
+            pCommand->u.removeKeyCmd.peerMac[5]);
+
+        status = csrQueueSmeCommand(pMac, pCommand, fImediate);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            break;
+        }
+    } while (0);
+
+    if( !HAL_STATUS_SUCCESS( status ) && ( NULL != pCommand ) )
+    {
+        csrReleaseCommandRemoveKey( pMac, pCommand );
+    }
+
+    return (status );
+}
+
+
+eHalStatus csrRoamProcessSetKeyCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status;
+    tANI_U8 numKeys = ( pCommand->u.setKeyCmd.keyLength ) ? 1 : 0;
+    tAniEdType edType = csrTranslateEncryptTypeToEdType( pCommand->u.setKeyCmd.encType );
+    tANI_BOOLEAN fUnicast = ( pCommand->u.setKeyCmd.peerMac[0] == 0xFF ) ? eANI_BOOLEAN_FALSE : eANI_BOOLEAN_TRUE;
+    tANI_U32 sessionId = pCommand->sessionId;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    WLAN_VOS_DIAG_EVENT_DEF(setKeyEvent, vos_event_wlan_security_payload_type);
+
+    if(eCSR_ENCRYPT_TYPE_NONE != edType)
+    {
+        palZeroMemory(pMac->hHdd, &setKeyEvent, sizeof(vos_event_wlan_security_payload_type));
+        if( *(( tANI_U8 *)&pCommand->u.setKeyCmd.peerMac) & 0x01 )
+        {
+            setKeyEvent.eventId = WLAN_SECURITY_EVENT_SET_GTK_REQ;
+            setKeyEvent.encryptionModeMulticast = (v_U8_t)diagEncTypeFromCSRType(pCommand->u.setKeyCmd.encType);
+            setKeyEvent.encryptionModeUnicast = (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.EncryptionType);
+        }
+        else
+        {
+            setKeyEvent.eventId = WLAN_SECURITY_EVENT_SET_PTK_REQ;
+            setKeyEvent.encryptionModeUnicast = (v_U8_t)diagEncTypeFromCSRType(pCommand->u.setKeyCmd.encType);
+            setKeyEvent.encryptionModeMulticast = (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.mcEncryptionType);
+        }
+        palCopyMemory( pMac->hHdd, setKeyEvent.bssid, pSession->connectedProfile.bssid, 6 );
+        if(CSR_IS_ENC_TYPE_STATIC(edType))
+        {
+            tANI_U32 defKeyId;
+
+            //It has to be static WEP here
+            if(HAL_STATUS_SUCCESS(ccmCfgGetInt(pMac, WNI_CFG_WEP_DEFAULT_KEYID, &defKeyId)))
+            {
+                setKeyEvent.keyId = (v_U8_t)defKeyId;
+            }
+        }
+        else
+        {
+            setKeyEvent.keyId = pCommand->u.setKeyCmd.keyId;
+        }
+        setKeyEvent.authMode = (v_U8_t)diagAuthTypeFromCSRType(pSession->connectedProfile.AuthType);
+        WLAN_VOS_DIAG_EVENT_REPORT(&setKeyEvent, EVENT_WLAN_SECURITY);
+    }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+    if( csrIsSetKeyAllowed(pMac, sessionId) )
+    {
+        status = csrSendMBSetContextReqMsg( pMac, sessionId, 
+                    ( tANI_U8 *)&pCommand->u.setKeyCmd.peerMac, 
+                                            numKeys, edType, fUnicast, pCommand->u.setKeyCmd.keyDirection, 
+                                            pCommand->u.setKeyCmd.keyId, pCommand->u.setKeyCmd.keyLength, 
+                    pCommand->u.setKeyCmd.Key, pCommand->u.setKeyCmd.paeRole, 
+                    pCommand->u.setKeyCmd.keyRsc);
+    }
+    else
+    {
+        smsLog( pMac, LOGW, FL(" cannot process not connected\n") );
+        //Set this status so the error handling take care of the case.
+        status = eHAL_STATUS_CSR_WRONG_STATE;
+    }
+    if( !HAL_STATUS_SUCCESS(status) )
+    {
+        smsLog( pMac, LOGE, FL("  error status %d\n"), status );
+        csrRoamCallCallback( pMac, sessionId, NULL, pCommand->u.setKeyCmd.roamId, eCSR_ROAM_SET_KEY_COMPLETE, eCSR_ROAM_RESULT_FAILURE);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+        if(eCSR_ENCRYPT_TYPE_NONE != edType)
+        {
+            if( *(( tANI_U8 *)&pCommand->u.setKeyCmd.peerMac) & 0x01 )
+            {
+                setKeyEvent.eventId = WLAN_SECURITY_EVENT_SET_GTK_RSP;
+            }
+            else
+            {
+                setKeyEvent.eventId = WLAN_SECURITY_EVENT_SET_PTK_RSP;
+            }
+            setKeyEvent.status = WLAN_SECURITY_STATUS_FAILURE;
+            WLAN_VOS_DIAG_EVENT_REPORT(&setKeyEvent, EVENT_WLAN_SECURITY);
+        }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+    }
+
+    return ( status );
+}
+
+
+eHalStatus csrRoamProcessRemoveKeyCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status;
+    tpSirSmeRemoveKeyReq pMsg = NULL;
+    tANI_U16 wMsgLen = sizeof(tSirSmeRemoveKeyReq);
+    tANI_U8 *p;
+    tANI_U32 sessionId = pCommand->sessionId;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    WLAN_VOS_DIAG_EVENT_DEF(removeKeyEvent, vos_event_wlan_security_payload_type);
+
+    palZeroMemory(pMac->hHdd, &removeKeyEvent, sizeof(vos_event_wlan_security_payload_type));
+    removeKeyEvent.eventId = WLAN_SECURITY_EVENT_REMOVE_KEY_REQ;
+    removeKeyEvent.encryptionModeMulticast = (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.mcEncryptionType);
+    removeKeyEvent.encryptionModeUnicast = (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.EncryptionType);
+    palCopyMemory( pMac->hHdd, removeKeyEvent.bssid, pSession->connectedProfile.bssid, 6 );
+    removeKeyEvent.keyId = pCommand->u.removeKeyCmd.keyId;
+    removeKeyEvent.authMode = (v_U8_t)diagAuthTypeFromCSRType(pSession->connectedProfile.AuthType);
+    WLAN_VOS_DIAG_EVENT_REPORT(&removeKeyEvent, EVENT_WLAN_SECURITY);
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+    if( csrIsSetKeyAllowed(pMac, sessionId) )
+    {
+        status = palAllocateMemory( pMac->hHdd, (void **)&pMsg, wMsgLen );
+    }
+    else
+    {
+        smsLog( pMac, LOGW, FL(" wrong state not allowed to set key\n") );
+        //Set the error status so error handling kicks in below
+        status = eHAL_STATUS_CSR_WRONG_STATE;
+    }
+    if( HAL_STATUS_SUCCESS( status ) )
+    {
+        palZeroMemory(pMac->hHdd, pMsg, wMsgLen);
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_REMOVEKEY_REQ);
+                pMsg->length = pal_cpu_to_be16(wMsgLen);
+
+        pMsg->sessionId = (tANI_U8)sessionId;
+        pMsg->transactionId = 0;
+        p = (tANI_U8 *)pMsg + sizeof(pMsg->messageType) + sizeof(pMsg->length) +
+            sizeof(pMsg->sessionId) + sizeof(pMsg->transactionId);
+        // bssId - copy from session Info
+        palCopyMemory( pMac->hHdd, p, &pMac->roam.roamSession[sessionId].connectedProfile.bssid, sizeof(tSirMacAddr) );
+        p += sizeof(tSirMacAddr);
+        // peerMacAddr
+        palCopyMemory( pMac->hHdd, p, pCommand->u.removeKeyCmd.peerMac, sizeof(tSirMacAddr) );
+        p += sizeof(tSirMacAddr);
+        // edType
+        *p = (tANI_U8)csrTranslateEncryptTypeToEdType( pCommand->u.removeKeyCmd.encType );
+        p++;
+        // weptype
+        if( ( eCSR_ENCRYPT_TYPE_WEP40_STATICKEY == pCommand->u.removeKeyCmd.encType ) || 
+            ( eCSR_ENCRYPT_TYPE_WEP104_STATICKEY == pCommand->u.removeKeyCmd.encType ) )
+        {
+            *p = (tANI_U8)eSIR_WEP_STATIC;
+        }
+        else
+        {
+            *p = (tANI_U8)eSIR_WEP_DYNAMIC;
+        }
+        p++;
+        //keyid
+        *p = pCommand->u.removeKeyCmd.keyId;
+        p++;
+        *p = (pCommand->u.removeKeyCmd.peerMac[0] == 0xFF ) ? 0 : 1;
+
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+    }
+
+    if( !HAL_STATUS_SUCCESS( status ) )
+    {
+        smsLog( pMac, LOGE, FL(" error status \n"), status );
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+        removeKeyEvent.eventId = WLAN_SECURITY_EVENT_REMOVE_KEY_RSP;
+        removeKeyEvent.status = WLAN_SECURITY_STATUS_FAILURE;;
+        WLAN_VOS_DIAG_EVENT_REPORT(&removeKeyEvent, EVENT_WLAN_SECURITY);
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+        csrRoamCallCallback( pMac, sessionId, NULL, pCommand->u.removeKeyCmd.roamId, eCSR_ROAM_REMOVE_KEY_COMPLETE, eCSR_ROAM_RESULT_FAILURE);
+    }
+
+    return ( status );
+}
+
+
+
+eHalStatus csrRoamSetKey( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamSetKey *pSetKey, tANI_U32 roamId )
+{
+    eHalStatus status;
+ 
+    if( !csrIsSetKeyAllowed(pMac, sessionId) )
+    {
+        status = eHAL_STATUS_CSR_WRONG_STATE;
+    }
+    else
+    {
+        status = csrRoamIssueSetKeyCommand( pMac, sessionId, pSetKey, roamId );
+    }
+
+    return ( status );
+}
+
+
+/*
+   Prepare a filter base on a profile for parsing the scan results.
+   Upon successful return, caller MUST call csrFreeScanFilter on 
+   pScanFilter when it is done with the filter.
+*/
+eHalStatus csrRoamPrepareFilterFromProfile(tpAniSirGlobal pMac, tCsrRoamProfile *pProfile, 
+                                           tCsrScanResultFilter *pScanFilter)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 size = 0;
+    tANI_U8  index = 0;
+    
+    do
+    {
+        if(pProfile->BSSIDs.numOfBSSIDs)
+        {
+            size = sizeof(tCsrBssid) * pProfile->BSSIDs.numOfBSSIDs;
+            status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter->BSSIDs.bssid, size);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pScanFilter->BSSIDs.numOfBSSIDs = pProfile->BSSIDs.numOfBSSIDs;
+            palCopyMemory(pMac->hHdd, pScanFilter->BSSIDs.bssid, pProfile->BSSIDs.bssid, size);
+        }
+        if(pProfile->SSIDs.numOfSSIDs)
+        {
+            if( !CSR_IS_WDS_STA( pProfile ) )
+            {
+                pScanFilter->SSIDs.numOfSSIDs = pProfile->SSIDs.numOfSSIDs;
+            }
+            else
+            {
+                //For WDS station
+                //We always use index 1 for self SSID. Index 0 for peer's SSID that we want to join
+                pScanFilter->SSIDs.numOfSSIDs = 1;
+            }
+            size = sizeof(tCsrSSIDInfo) * pProfile->SSIDs.numOfSSIDs;
+            status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter->SSIDs.SSIDList, size);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            palCopyMemory(pMac->hHdd, pScanFilter->SSIDs.SSIDList, pProfile->SSIDs.SSIDList, size);
+        }
+        if(!pProfile->ChannelInfo.ChannelList || (pProfile->ChannelInfo.ChannelList[0] == 0) )
+        {
+            pScanFilter->ChannelInfo.numOfChannels = 0;
+            pScanFilter->ChannelInfo.ChannelList = NULL;
+        }
+        else if(pProfile->ChannelInfo.numOfChannels)
+        {
+           status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter->ChannelInfo.ChannelList, sizeof(*pScanFilter->ChannelInfo.ChannelList) * pProfile->ChannelInfo.numOfChannels);
+           pScanFilter->ChannelInfo.numOfChannels = 0;
+            if(HAL_STATUS_SUCCESS(status))
+            {
+              for(index = 0; index < pProfile->ChannelInfo.numOfChannels; index++)
+              {
+                 if(csrRoamIsChannelValid(pMac, pProfile->ChannelInfo.ChannelList[index]))
+                 {
+                    pScanFilter->ChannelInfo.ChannelList[pScanFilter->ChannelInfo.numOfChannels] 
+                       = pProfile->ChannelInfo.ChannelList[index];
+                    pScanFilter->ChannelInfo.numOfChannels++;
+                 }
+                 else 
+                 {
+                         smsLog(pMac, LOG1, FL("process a channel (%d) that is invalid\n"), pProfile->ChannelInfo.ChannelList[index]);
+                 }
+
+            }
+            }
+            else
+            {
+                break;
+            }
+
+        }
+        else 
+        {
+            smsLog(pMac, LOGW, FL("Channel list empty\n"));
+            status = eHAL_STATUS_FAILURE;
+            break;
+        }
+        pScanFilter->uapsd_mask = pProfile->uapsd_mask;
+        pScanFilter->authType = pProfile->AuthType;
+        pScanFilter->EncryptionType = pProfile->EncryptionType;
+        pScanFilter->mcEncryptionType = pProfile->mcEncryptionType;
+        pScanFilter->BSSType = pProfile->BSSType;
+        pScanFilter->phyMode = pProfile->phyMode;
+#ifdef FEATURE_WLAN_WAPI
+        //check if user asked for WAPI with 11n or auto mode, in that case modify
+        //the phymode to 11g
+        if(csrIsProfileWapi(pProfile))
+        {
+             if(pScanFilter->phyMode & eCSR_DOT11_MODE_11n)
+             {
+                pScanFilter->phyMode &= ~eCSR_DOT11_MODE_11n;
+             }
+             if(pScanFilter->phyMode & eCSR_DOT11_MODE_AUTO)
+             {
+                pScanFilter->phyMode &= ~eCSR_DOT11_MODE_AUTO;
+             }
+             if(!pScanFilter->phyMode)
+             {
+                 pScanFilter->phyMode = eCSR_DOT11_MODE_11g;
+             }
+        }
+#endif /* FEATURE_WLAN_WAPI */
+
+        /*Save the WPS info*/
+        pScanFilter->bWPSAssociation = pProfile->bWPSAssociation;
+
+        if( pProfile->countryCode[0] )
+        {
+            //This causes the matching function to use countryCode as one of the criteria.
+            palCopyMemory( pMac->hHdd, pScanFilter->countryCode, pProfile->countryCode, 
+                        WNI_CFG_COUNTRY_CODE_LEN );
+        }
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        if (pProfile->MDID.mdiePresent)
+        {
+            pScanFilter->MDID.mdiePresent = 1;
+            pScanFilter->MDID.mobilityDomain = pProfile->MDID.mobilityDomain;
+        }
+#endif
+    
+    }while(0);
+    
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        csrFreeScanFilter(pMac, pScanFilter);
+    }
+    
+    return(status);
+}
+
+
+tANI_BOOLEAN csrRoamIssueWmStatusChange( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                         eCsrRoamWmStatusChangeTypes Type, tSirSmeRsp *pSmeRsp )
+{
+    tANI_BOOLEAN fCommandQueued = eANI_BOOLEAN_FALSE;
+    tSmeCmd *pCommand;
+
+    do
+    {
+        // Validate the type is ok...
+        if ( ( eCsrDisassociated != Type ) && ( eCsrDeauthenticated != Type ) ) break;
+        pCommand = csrGetCommandBuffer( pMac );
+        if ( !pCommand )
+        {
+            smsLog( pMac, LOGE, FL(" fail to get command buffer\n") );
+            break;
+        }
+        //Change the substate in case it is waiting for key
+        if( CSR_IS_WAIT_FOR_KEY( pMac, sessionId ) )
+        {
+            csrRoamStopWaitForKeyTimer( pMac );
+            csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId);
+        }
+        pCommand->command = eSmeCommandWmStatusChange;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.wmStatusChangeCmd.Type = Type;
+        if ( eCsrDisassociated ==  Type )
+        {
+            palCopyMemory( pMac->hHdd, &pCommand->u.wmStatusChangeCmd.u.DisassocIndMsg, pSmeRsp, 
+                                sizeof( pCommand->u.wmStatusChangeCmd.u.DisassocIndMsg ) );
+        }
+        else
+        {
+            palCopyMemory( pMac->hHdd, &pCommand->u.wmStatusChangeCmd.u.DeauthIndMsg, pSmeRsp, 
+                            sizeof( pCommand->u.wmStatusChangeCmd.u.DeauthIndMsg ) );
+        }
+        if( HAL_STATUS_SUCCESS( csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_TRUE) ) )
+        {
+            fCommandQueued = eANI_BOOLEAN_TRUE;
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message \n") );
+            csrReleaseCommandWmStatusChange( pMac, pCommand );
+        }
+
+
+        /* AP has issued Dissac/Deauth, Set the operating mode value to configured value */
+        csrSetDefaultDot11Mode( pMac );
+
+    } while( 0 );
+
+    return( fCommandQueued );
+}
+
+
+static void csrUpdateRssi(tpAniSirGlobal pMac, void* pMsg)
+{
+    v_S7_t  rssi = 0;
+    tAniGetRssiReq *pGetRssiReq = (tAniGetRssiReq*)pMsg;
+    if(pGetRssiReq)
+    {
+        if(NULL != pGetRssiReq->pVosContext)
+        {
+            WLANTL_GetRssi(pGetRssiReq->pVosContext, pGetRssiReq->staId, &rssi);
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL("pGetRssiReq->pVosContext is NULL\n"));                
+            return;
+        }
+            
+        if(NULL != pGetRssiReq->rssiCallback)
+        {
+            ((tCsrRssiCallback)(pGetRssiReq->rssiCallback))(rssi, pGetRssiReq->staId, pGetRssiReq->pDevContext);
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL("pGetRssiReq->rssiCallback is NULL\n"));                
+            return;
+        }
+    }
+    else
+    {
+        smsLog( pMac, LOGE, FL("pGetRssiReq is NULL\n"));    
+    }
+    return;
+}
+
+void csrRoamCheckForLinkStatusChange( tpAniSirGlobal pMac, tSirSmeRsp *pSirMsg )
+{
+    tSirSmeAssocInd *pAssocInd;
+    tSirSmeDisassocInd *pDisassocInd;
+    tSirSmeDeauthInd *pDeauthInd;
+    tSirSmeWmStatusChangeNtf *pStatusChangeMsg;
+    tSirSmeNewBssInfo *pNewBss;
+    tSmeIbssPeerInd *pIbssPeerInd;
+    tSirMacAddr Broadcastaddr = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
+    tSirSmeApNewCaps *pApNewCaps;
+    eCsrRoamResult result = eCSR_ROAM_RESULT_NONE;
+    eRoamCmdStatus roamStatus = eCSR_ROAM_FAILED;
+    tCsrRoamInfo *pRoamInfo = NULL;
+    tCsrRoamInfo roamInfo;
+    eHalStatus status;
+    tANI_U32 sessionId = CSR_SESSION_ID_INVALID;
+    tCsrRoamSession *pSession = NULL;
+    tpSirSmeSwitchChannelInd pSwitchChnInd;
+    tSmeMaxAssocInd *pSmeMaxAssocInd;
+
+#if defined ANI_PRODUCT_TYPE_AP
+    pSirMsg->messageType = pal_be16_to_cpu(pSirMsg->messageType);
+    pSirMsg->length = pal_be16_to_cpu(pSirMsg->length);
+    pSirMsg->statusCode = pal_be32_to_cpu(pSirMsg->statusCode);
+#else
+    pSirMsg->messageType = (pSirMsg->messageType);
+    pSirMsg->length = (pSirMsg->length);
+    pSirMsg->statusCode = (pSirMsg->statusCode);
+#endif
+
+    palZeroMemory(pMac->hHdd, &roamInfo, sizeof(roamInfo));
+
+    switch( pSirMsg->messageType ) 
+    {
+        case eWNI_SME_ASSOC_IND:
+            {
+                tCsrRoamSession  *pSession;
+                smsLog( pMac, LOG1, FL("ASSOCIATION Indication from SME\n"));
+                pAssocInd = (tSirSmeAssocInd *)pSirMsg;
+                status = csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid *)pAssocInd->bssId, &sessionId );
+                if( HAL_STATUS_SUCCESS( status ) )
+                {
+                    pSession = CSR_GET_SESSION(pMac, sessionId);
+
+                pRoamInfo = &roamInfo;
+
+                // Required for indicating the frames to upper layer
+                pRoamInfo->assocReqLength = pAssocInd->assocReqLength;
+                pRoamInfo->assocReqPtr = pAssocInd->assocReqPtr;
+
+                pRoamInfo->beaconPtr = pAssocInd->beaconPtr;
+                pRoamInfo->beaconLength = pAssocInd->beaconLength;                
+                pRoamInfo->statusCode = eSIR_SME_SUCCESS; //send the status code as Success 
+                pRoamInfo->u.pConnectedProfile = &pSession->connectedProfile;
+
+                    pRoamInfo->staId = (tANI_U8)pAssocInd->staId;
+                    pRoamInfo->rsnIELen = (tANI_U8)pAssocInd->rsnIE.length;
+                    pRoamInfo->prsnIE = pAssocInd->rsnIE.rsnIEdata;
+                
+                pRoamInfo->addIELen = (tANI_U8)pAssocInd->addIE.length;
+                pRoamInfo->paddIE =  pAssocInd->addIE.addIEdata;
+
+                    palCopyMemory(pMac->hHdd, pRoamInfo->peerMac, pAssocInd->peerMacAddr, sizeof(tSirMacAddr));
+                    palCopyMemory(pMac->hHdd, &pRoamInfo->bssid, pAssocInd->bssId, sizeof(tCsrBssid));
+#ifdef WLAN_SOFTAP_FEATURE
+                    pRoamInfo->wmmEnabledSta = pAssocInd->wmmEnabledSta;
+                    if(CSR_IS_WDS_AP( pRoamInfo->u.pConnectedProfile))
+#endif 
+                        status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_WDS_IND, eCSR_ROAM_RESULT_WDS_ASSOCIATION_IND);//Sta
+#ifdef WLAN_SOFTAP_FEATURE
+                    if(CSR_IS_INFRA_AP(pRoamInfo->u.pConnectedProfile))
+                    {
+                        if( CSR_IS_ENC_TYPE_STATIC( pSession->pCurRoamProfile->negotiatedUCEncryptionType ))
+                        {
+                            csrRoamIssueSetContextReq( pMac, sessionId, pSession->pCurRoamProfile->negotiatedUCEncryptionType, 
+                                    pSession->pConnectBssDesc,
+                                    &(pRoamInfo->peerMac),
+                                    FALSE, TRUE, eSIR_TX_RX, 0, 0, NULL, 0 ); // NO keys... these key parameters don't matter.
+                            pRoamInfo->fAuthRequired = FALSE;
+                        }
+                        else
+                        {
+                            pRoamInfo->fAuthRequired = TRUE;
+                        }
+                        status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_INFRA_IND, eCSR_ROAM_RESULT_INFRA_ASSOCIATION_IND);
+                        if (!HAL_STATUS_SUCCESS(status))
+                            pRoamInfo->statusCode = eSIR_SME_ASSOC_REFUSED;// Refused due to Mac filtering 
+                    }
+#endif 
+                    /* Send Association completion message to PE */
+                    status = csrSendAssocCnfMsg( pMac, pAssocInd, status );//Sta
+                    
+                    /* send a message to CSR itself just to avoid the EAPOL frames going
+                     * OTA before association response */
+
+                    if(CSR_IS_WDS_AP( pRoamInfo->u.pConnectedProfile))
+                {
+                    status = csrSendAssocIndToUpperLayerCnfMsg(pMac, pAssocInd, status, sessionId);
+                }
+#ifdef WLAN_SOFTAP_FEATURE
+                else if(CSR_IS_INFRA_AP(pRoamInfo->u.pConnectedProfile) && (pRoamInfo->statusCode != eSIR_SME_ASSOC_REFUSED))
+                {
+                    pRoamInfo->fReassocReq = pAssocInd->reassocReq;
+                    //status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_INFRA_IND, eCSR_ROAM_RESULT_INFRA_ASSOCIATION_CNF);
+                    status = csrSendAssocIndToUpperLayerCnfMsg(pMac, pAssocInd, status, sessionId);
+                }
+#endif
+                }
+            }
+            break;
+
+        case eWNI_SME_DISASSOC_IND:
+            smsLog( pMac, LOGE, FL("DISASSOCIATION Indication from MAC\n"));
+
+            // Check if AP dis-associated us because of MIC failure. If so,
+            // then we need to take action immediately and not wait till the
+            // the WmStatusChange requests is pushed and processed
+            pDisassocInd = (tSirSmeDisassocInd *)pSirMsg;
+            status = csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid *)pDisassocInd->bssId, &sessionId );
+            if( HAL_STATUS_SUCCESS( status ) )
+            {
+                // If we are in neighbor preauth done state then on receiving
+                // disassoc or deauth we dont roam instead we just disassoc
+                // from current ap and then go to disconnected state 
+                // This happens for CCX and 11r FT connections ONLY.
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                if (csrRoamIs11rAssoc(pMac) && (csrNeighborRoamStatePreauthDone(pMac)))
+                {
+                    csrNeighborRoamTranistionPreauthDoneToDisconnected(pMac);
+                }
+#endif
+#ifdef FEATURE_WLAN_CCX
+                if (csrRoamIsCCXAssoc(pMac) && (csrNeighborRoamStatePreauthDone(pMac)))
+                {
+                    csrNeighborRoamTranistionPreauthDoneToDisconnected(pMac);
+                }
+#endif
+                pSession = CSR_GET_SESSION( pMac, sessionId );
+
+                if ( csrIsConnStateInfra( pMac, sessionId ) )
+                {
+                    pSession->connectState = eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED;
+                }
+
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                sme_QosCsrEventInd(pMac, (v_U8_t)sessionId, SME_QOS_CSR_DISCONNECT_IND, NULL);
+#endif
+                csrRoamLinkDown(pMac, sessionId);
+                csrRoamIssueWmStatusChange( pMac, sessionId, eCsrDisassociated, pSirMsg );
+#ifdef WLAN_SOFTAP_FEATURE
+                if(CSR_IS_INFRA_AP(&pSession->connectedProfile))
+                {
+
+                    pRoamInfo = &roamInfo;
+
+                    pRoamInfo->statusCode = pDisassocInd->statusCode; 
+                    pRoamInfo->u.pConnectedProfile = &pSession->connectedProfile;
+
+                    pRoamInfo->staId = (tANI_U8)pDisassocInd->staId;
+
+                    palCopyMemory(pMac->hHdd, pRoamInfo->peerMac, pDisassocInd->peerMacAddr, sizeof(tSirMacAddr));
+                    palCopyMemory(pMac->hHdd, &pRoamInfo->bssid, pDisassocInd->bssId, sizeof(tCsrBssid));
+
+                    status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_INFRA_IND, eCSR_ROAM_RESULT_DISASSOC_IND);
+                }
+#endif                
+            }
+            break;
+
+        case eWNI_SME_DEAUTH_IND:
+            smsLog( pMac, LOG1, FL("DEAUTHENTICATION Indication from MAC\n"));
+            pDeauthInd = (tpSirSmeDeauthInd)pSirMsg;
+            status = csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid *)pDeauthInd->bssId, &sessionId );
+            if( HAL_STATUS_SUCCESS( status ) )
+            {
+                // If we are in neighbor preauth done state then on receiving
+                // disassoc or deauth we dont roam instead we just disassoc
+                // from current ap and then go to disconnected state 
+                // This happens for CCX and 11r FT connections ONLY.
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                if (csrRoamIs11rAssoc(pMac) && (csrNeighborRoamStatePreauthDone(pMac)))
+                {
+                    csrNeighborRoamTranistionPreauthDoneToDisconnected(pMac);
+                }
+#endif
+#ifdef FEATURE_WLAN_CCX
+                if (csrRoamIsCCXAssoc(pMac) && (csrNeighborRoamStatePreauthDone(pMac)))
+                {
+                    csrNeighborRoamTranistionPreauthDoneToDisconnected(pMac);
+                }
+#endif
+                pSession = CSR_GET_SESSION( pMac, sessionId );
+
+                if ( csrIsConnStateInfra( pMac, sessionId ) )
+                {
+                    pSession->connectState = eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED;
+                }
+
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                sme_QosCsrEventInd(pMac, (v_U8_t)sessionId, SME_QOS_CSR_DISCONNECT_IND, NULL);
+#endif
+                csrRoamLinkDown(pMac, sessionId);
+                csrRoamIssueWmStatusChange( pMac, sessionId, eCsrDeauthenticated, pSirMsg );
+#ifdef WLAN_SOFTAP_FEATURE
+                if(CSR_IS_INFRA_AP(&pSession->connectedProfile))
+                {
+
+                    pRoamInfo = &roamInfo;
+
+                    pRoamInfo->statusCode = pDeauthInd->statusCode;
+                    pRoamInfo->u.pConnectedProfile = &pSession->connectedProfile;
+
+                    pRoamInfo->staId = (tANI_U8)pDeauthInd->staId;
+
+                    palCopyMemory(pMac->hHdd, pRoamInfo->peerMac, pDeauthInd->peerMacAddr, sizeof(tSirMacAddr));
+                    palCopyMemory(pMac->hHdd, &pRoamInfo->bssid, pDeauthInd->bssId, sizeof(tCsrBssid));
+
+                    status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_INFRA_IND, eCSR_ROAM_RESULT_DEAUTH_IND);
+                }
+#endif                
+            }
+            break;
+        
+        case eWNI_SME_SWITCH_CHL_REQ:        // in case of STA, the SWITCH_CHANNEL originates from its AP
+            smsLog( pMac, LOGW, FL("eWNI_SME_SWITCH_CHL_REQ from SME\n"));
+            pSwitchChnInd = (tpSirSmeSwitchChannelInd)pSirMsg;
+            //Update with the new channel id.
+            //The channel id is hidden in the statusCode.
+            status = csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid *)pSwitchChnInd->bssId, &sessionId );
+            if( HAL_STATUS_SUCCESS( status ) )
+            {
+                pSession = CSR_GET_SESSION( pMac, sessionId );
+                pSession->connectedProfile.operationChannel = (tANI_U8)pSwitchChnInd->newChannelId;
+                if(pSession->pConnectBssDesc)
+                {
+                    pSession->pConnectBssDesc->channelId = (tANI_U8)pSwitchChnInd->newChannelId;
+                }
+            }
+            break;
+                
+        case eWNI_SME_DEAUTH_RSP:
+            smsLog( pMac, LOGW, FL("eWNI_SME_DEAUTH_RSP from SME\n"));
+#ifdef WLAN_SOFTAP_FEATURE
+            {
+                tSirSmeDeauthRsp* pDeauthRsp = (tSirSmeDeauthRsp *)pSirMsg;
+                sessionId = pDeauthRsp->sessionId;
+                if( CSR_IS_SESSION_VALID(pMac, sessionId) )
+                {                    
+                    pSession = CSR_GET_SESSION(pMac, sessionId);
+
+                    if ( CSR_IS_INFRA_AP(&pSession->connectedProfile) )
+                    {
+                        pRoamInfo = &roamInfo;
+                        pRoamInfo->u.pConnectedProfile = &pSession->connectedProfile;
+                        palCopyMemory(pMac->hHdd, pRoamInfo->peerMac, pDeauthRsp->peerMacAddr, sizeof(tSirMacAddr));
+                        pRoamInfo->reasonCode = eCSR_ROAM_RESULT_FORCED;
+                        pRoamInfo->statusCode = pDeauthRsp->statusCode;
+                        status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_LOSTLINK, eCSR_ROAM_RESULT_FORCED);
+                    }
+                }
+            }
+#endif
+            break;
+            
+        case eWNI_SME_DISASSOC_RSP:
+            smsLog( pMac, LOGW, FL("eWNI_SME_DISASSOC_RSP from SME subState = %d\n"), pMac->roam.curSubState[sessionId]);
+#ifdef WLAN_SOFTAP_FEATURE
+            {
+                tSirSmeDisassocRsp *pDisassocRsp = (tSirSmeDisassocRsp *)pSirMsg;
+                sessionId = pDisassocRsp->sessionId;
+                if( CSR_IS_SESSION_VALID(pMac, sessionId) )
+                {                    
+                    pSession = CSR_GET_SESSION(pMac, sessionId);
+
+                    if ( CSR_IS_INFRA_AP(&pSession->connectedProfile) )
+                    {
+                        pRoamInfo = &roamInfo;
+                        pRoamInfo->u.pConnectedProfile = &pSession->connectedProfile;
+                        palCopyMemory(pMac->hHdd, pRoamInfo->peerMac, pDisassocRsp->peerMacAddr, sizeof(tSirMacAddr));
+                        pRoamInfo->reasonCode = eCSR_ROAM_RESULT_FORCED;
+                        pRoamInfo->statusCode = pDisassocRsp->statusCode;
+                        status = csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_LOSTLINK, eCSR_ROAM_RESULT_FORCED);
+                    }
+                }
+            }
+#endif
+            break;
+
+        case eWNI_SME_MIC_FAILURE_IND:
+            {
+                tpSirSmeMicFailureInd pMicInd = (tpSirSmeMicFailureInd)pSirMsg;
+                tCsrRoamInfo roamInfo, *pRoamInfo = NULL;
+                eCsrRoamResult result = eCSR_ROAM_RESULT_MIC_ERROR_UNICAST;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                {
+                    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+                    WLAN_VOS_DIAG_EVENT_DEF(secEvent, vos_event_wlan_security_payload_type);
+                    palZeroMemory(pMac->hHdd, &secEvent, sizeof(vos_event_wlan_security_payload_type));
+                    secEvent.eventId = WLAN_SECURITY_EVENT_MIC_ERROR;
+                    secEvent.encryptionModeMulticast = 
+                        (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.mcEncryptionType);
+                    secEvent.encryptionModeUnicast = 
+                        (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.EncryptionType);
+                    secEvent.authMode = 
+                        (v_U8_t)diagAuthTypeFromCSRType(pSession->connectedProfile.AuthType);
+                    palCopyMemory( pMac->hHdd, secEvent.bssid, pSession->connectedProfile.bssid, 6 );
+                    WLAN_VOS_DIAG_EVENT_REPORT(&secEvent, EVENT_WLAN_SECURITY);
+                }
+#endif//FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+                status = csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid *)pMicInd->bssId, &sessionId );
+                if( HAL_STATUS_SUCCESS( status ) )
+                {
+                    palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+                    roamInfo.u.pMICFailureInfo = &pMicInd->info;
+                    pRoamInfo = &roamInfo;
+                    if(pMicInd->info.multicast)
+                    {
+                        result = eCSR_ROAM_RESULT_MIC_ERROR_GROUP;
+                    }
+                    else
+                    {
+                        result = eCSR_ROAM_RESULT_MIC_ERROR_UNICAST;
+                    }
+                    csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_MIC_ERROR_IND, result);
+                }
+            }
+            break;
+
+#ifdef WLAN_SOFTAP_FEATURE
+        case eWNI_SME_WPS_PBC_PROBE_REQ_IND:
+            {
+                tpSirSmeProbeReqInd pProbeReqInd = (tpSirSmeProbeReqInd)pSirMsg;
+                tCsrRoamInfo roamInfo;
+
+                smsLog( pMac, LOG1, FL("WPS PBC Probe request Indication from SME\n"));
+           
+                status = csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid *)pProbeReqInd->bssId, &sessionId );
+                if( HAL_STATUS_SUCCESS( status ) )
+                {
+                    palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+                    roamInfo.u.pWPSPBCProbeReq = &pProbeReqInd->WPSPBCProbeReq;
+                    csrRoamCallCallback(pMac, sessionId, &roamInfo, 0, eCSR_ROAM_WPS_PBC_PROBE_REQ_IND, 
+                        eCSR_ROAM_RESULT_WPS_PBC_PROBE_REQ_IND);
+                }
+            }
+            break;        
+#endif
+            
+
+        case eWNI_SME_WM_STATUS_CHANGE_NTF:
+            pStatusChangeMsg = (tSirSmeWmStatusChangeNtf *)pSirMsg;
+            switch( pStatusChangeMsg->statusChangeCode ) 
+            {
+                case eSIR_SME_IBSS_ACTIVE:
+                    sessionId = csrFindIbssSession( pMac );
+                    if( CSR_SESSION_ID_INVALID != sessionId )
+                    {
+                        pSession = CSR_GET_SESSION( pMac, sessionId );
+                        pSession->connectState = eCSR_ASSOC_STATE_TYPE_IBSS_CONNECTED;
+                        if(pSession->pConnectBssDesc)
+                        {
+                            palCopyMemory(pMac->hHdd, &roamInfo.bssid, pSession->pConnectBssDesc->bssId, sizeof(tCsrBssid));
+                            roamInfo.u.pConnectedProfile = &pSession->connectedProfile;
+                            pRoamInfo = &roamInfo;
+                        }
+                        else
+                        {
+                            smsLog(pMac, LOGE, "  CSR eSIR_SME_IBSS_NEW_PEER connected BSS is empty\n");
+                        }
+                        result = eCSR_ROAM_RESULT_IBSS_CONNECT;
+                        roamStatus = eCSR_ROAM_CONNECT_STATUS_UPDATE;
+                    }
+                    break;
+
+                case eSIR_SME_IBSS_INACTIVE:
+                    sessionId = csrFindIbssSession( pMac );
+                    if( CSR_SESSION_ID_INVALID != sessionId )
+                    {
+                        pSession = CSR_GET_SESSION( pMac, sessionId );
+                        pSession->connectState = eCSR_ASSOC_STATE_TYPE_IBSS_DISCONNECTED;
+                        result = eCSR_ROAM_RESULT_IBSS_INACTIVE;
+                        roamStatus = eCSR_ROAM_CONNECT_STATUS_UPDATE;
+                    }
+                    break;
+
+                case eSIR_SME_JOINED_NEW_BSS:    // IBSS coalescing.
+                    sessionId = csrFindIbssSession( pMac );
+                    if( CSR_SESSION_ID_INVALID != sessionId )
+                    {
+                        pSession = CSR_GET_SESSION( pMac, sessionId );
+                        // update the connection state information
+                        pNewBss = &pStatusChangeMsg->statusChangeInfo.newBssInfo;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                        {
+                            vos_log_ibss_pkt_type *pIbssLog;
+                            tANI_U32 bi;
+
+                            WLAN_VOS_DIAG_LOG_ALLOC(pIbssLog, vos_log_ibss_pkt_type, LOG_WLAN_IBSS_C);
+                            if(pIbssLog)
+                            {
+                                pIbssLog->eventId = WLAN_IBSS_EVENT_COALESCING;
+                                if(pNewBss)
+                                {
+                                    palCopyMemory(pMac->hHdd, pIbssLog->bssid, pNewBss->bssId, 6);
+                                    if(pNewBss->ssId.length)
+                                    {
+                                        palCopyMemory(pMac->hHdd, pIbssLog->ssid, pNewBss->ssId.ssId, pNewBss->ssId.length);
+                                    }
+                                    pIbssLog->operatingChannel = pNewBss->channelNumber;
+                                }
+                                if(HAL_STATUS_SUCCESS(ccmCfgGetInt(pMac, WNI_CFG_BEACON_INTERVAL, &bi)))
+                                {
+                                    //***U8 is not enough for beacon interval
+                                    pIbssLog->beaconInterval = (v_U8_t)bi;
+                                }
+                                WLAN_VOS_DIAG_LOG_REPORT(pIbssLog);
+                            }
+                        }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+                        csrRoamUpdateConnectedProfileFromNewBss( pMac, sessionId, pNewBss );
+                        csrRoamIssueSetContextReq( pMac, sessionId, pSession->connectedProfile.EncryptionType, 
+                                                    pSession->pConnectBssDesc,
+                                                &Broadcastaddr,
+                                                FALSE, FALSE, eSIR_TX_RX, 0, 0, NULL, 0 );
+                        result = eCSR_ROAM_RESULT_IBSS_COALESCED;
+                        roamStatus = eCSR_ROAM_IBSS_IND;
+                        palCopyMemory(pMac->hHdd, &roamInfo.bssid, &pNewBss->bssId, sizeof(tCsrBssid));
+                        pRoamInfo = &roamInfo;
+                        //This BSSID is th ereal BSSID, let's save it
+                        if(pSession->pConnectBssDesc)
+                        {
+                            palCopyMemory(pMac->hHdd, pSession->pConnectBssDesc->bssId, &pNewBss->bssId, sizeof(tCsrBssid));
+                        }
+                        // Stop the join IBSS timer in case of join, for 
+                        // genuine merge do nothing
+                        if(pSession->ibss_join_pending)
+                        {
+                           pSession->ibss_join_pending = FALSE;
+                           csrRoamStopIbssJoinTimer(pMac, sessionId);
+                           result = eCSR_ROAM_RESULT_IBSS_JOIN_SUCCESS;
+                        }
+                    }
+                    smsLog(pMac, LOGW, "CSR:  eSIR_SME_JOINED_NEW_BSS received from PE\n");
+                    break;
+
+                // detection by LIM that the capabilities of the associated AP have changed.
+                case eSIR_SME_AP_CAPS_CHANGED:
+                    pApNewCaps = &pStatusChangeMsg->statusChangeInfo.apNewCaps;
+                    smsLog(pMac, LOGW, "CSR handling eSIR_SME_AP_CAPS_CHANGED\n");
+                    status = csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid *)pApNewCaps->bssId, &sessionId );
+                    if( HAL_STATUS_SUCCESS( status ) )
+                    {
+                    csrScanForCapabilityChange( pMac, pApNewCaps );
+                    result = eCSR_ROAM_RESULT_CAP_CHANGED;
+                    roamStatus = eCSR_ROAM_GEN_INFO;
+                    }
+                    break;
+            
+                default:
+                    roamStatus = eCSR_ROAM_FAILED;
+                    result = eCSR_ROAM_RESULT_NONE;
+                    break;
+
+            }  // end switch on statusChangeCode
+            if(eCSR_ROAM_RESULT_NONE != result)
+            {
+                csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, roamStatus, result);
+            }
+            break;
+
+        case eWNI_SME_IBSS_NEW_PEER_IND:
+            pIbssPeerInd = (tSmeIbssPeerInd *)pSirMsg;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+            {
+                vos_log_ibss_pkt_type *pIbssLog;
+
+                WLAN_VOS_DIAG_LOG_ALLOC(pIbssLog, vos_log_ibss_pkt_type, LOG_WLAN_IBSS_C);
+                if(pIbssLog)
+                {
+                    pIbssLog->eventId = WLAN_IBSS_EVENT_PEER_JOIN;
+                    palCopyMemory(pMac->hHdd, pIbssLog->peerMacAddr, &pIbssPeerInd->peerAddr, 6);
+                    WLAN_VOS_DIAG_LOG_REPORT(pIbssLog);
+                }
+            }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+            sessionId = csrFindIbssSession( pMac );
+            if( CSR_SESSION_ID_INVALID != sessionId )
+            {
+                pSession = CSR_GET_SESSION( pMac, sessionId );
+            // Issue the set Context request to LIM to establish the Unicast STA context for the new peer...
+                if(pSession->pConnectBssDesc)
+                {
+                    palCopyMemory(pMac->hHdd, &roamInfo.peerMac, pIbssPeerInd->peerAddr, sizeof(tCsrBssid));
+                    palCopyMemory(pMac->hHdd, &roamInfo.bssid, pSession->pConnectBssDesc->bssId, sizeof(tCsrBssid));
+                    if(pIbssPeerInd->mesgLen > sizeof(tSmeIbssPeerInd))
+                    {
+                        status = palAllocateMemory(pMac->hHdd, (void **)&roamInfo.pbFrames, 
+                                                (pIbssPeerInd->mesgLen - sizeof(tSmeIbssPeerInd)));
+                        if(HAL_STATUS_SUCCESS(status))
+                        {
+                            roamInfo.nBeaconLength = (pIbssPeerInd->mesgLen - sizeof(tSmeIbssPeerInd));
+                            palCopyMemory(pMac->hHdd, roamInfo.pbFrames, ((tANI_U8 *)pIbssPeerInd) + sizeof(tSmeIbssPeerInd),
+                                                roamInfo.nBeaconLength);
+                        }
+                        roamInfo.staId = (tANI_U8)pIbssPeerInd->staId;
+                        roamInfo.ucastSig = (tANI_U8)pIbssPeerInd->ucastSig;
+                        roamInfo.bcastSig = (tANI_U8)pIbssPeerInd->bcastSig;
+                        status = palAllocateMemory(pMac->hHdd, (void **)&roamInfo.pBssDesc, 
+                                                pSession->pConnectBssDesc->length);
+                        if(HAL_STATUS_SUCCESS(status))
+                        {
+                            palCopyMemory(pMac->hHdd, roamInfo.pBssDesc, pSession->pConnectBssDesc, 
+                                                pSession->pConnectBssDesc->length);
+                        }
+                        if(HAL_STATUS_SUCCESS(status))
+                        {
+                            pRoamInfo = &roamInfo;
+                        }
+                        else
+                        {
+                            if(roamInfo.pbFrames)
+                            {
+                                palFreeMemory(pMac->hHdd, roamInfo.pbFrames);
+                            }
+                            if(roamInfo.pBssDesc)
+                            {
+                                palFreeMemory(pMac->hHdd, roamInfo.pBssDesc);
+                            }
+                        }
+                    }
+                    else
+                    {
+                        pRoamInfo = &roamInfo;
+                    }
+                        csrRoamIssueSetContextReq( pMac, sessionId, pSession->connectedProfile.EncryptionType, 
+                                            pSession->pConnectBssDesc,
+                                            &(pIbssPeerInd->peerAddr),
+                                            FALSE, TRUE, eSIR_TX_RX, 0, 0, NULL, 0 ); // NO keys... these key parameters don't matter.
+                }
+                else
+                {
+                    smsLog(pMac, LOGW, "  CSR eSIR_SME_IBSS_NEW_PEER connected BSS is empty\n");
+                }
+                //send up the sec type for the new peer
+                if (pRoamInfo)
+                {
+                    pRoamInfo->u.pConnectedProfile = &pSession->connectedProfile;
+                }
+                csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, 
+                            eCSR_ROAM_CONNECT_STATUS_UPDATE, eCSR_ROAM_RESULT_IBSS_NEW_PEER);
+                if(pRoamInfo)
+                {
+                    if(roamInfo.pbFrames)
+                    {
+                        palFreeMemory(pMac->hHdd, roamInfo.pbFrames);
+                    }
+                    if(roamInfo.pBssDesc)
+                    {
+                        palFreeMemory(pMac->hHdd, roamInfo.pBssDesc);
+                    }
+                }
+            }
+            break;
+
+        case eWNI_SME_IBSS_PEER_DEPARTED_IND:
+            pIbssPeerInd = (tSmeIbssPeerInd*)pSirMsg;
+            sessionId = csrFindIbssSession( pMac );
+            if( CSR_SESSION_ID_INVALID != sessionId )
+            {
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                {
+                    vos_log_ibss_pkt_type *pIbssLog;
+ 
+                    WLAN_VOS_DIAG_LOG_ALLOC(pIbssLog, vos_log_ibss_pkt_type, LOG_WLAN_IBSS_C);
+                    if(pIbssLog)
+                    {
+                        pIbssLog->eventId = WLAN_IBSS_EVENT_PEER_LEAVE;
+                        if(pIbssPeerInd)
+                        {
+                            palCopyMemory(pMac->hHdd, pIbssLog->peerMacAddr, &pIbssPeerInd->peerAddr, 6);
+                        }
+                        WLAN_VOS_DIAG_LOG_REPORT(pIbssLog);
+                    }
+                }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+                smsLog(pMac, LOGW, "CSR: Peer departed notification from LIM\n");
+                roamInfo.staId = (tANI_U8)pIbssPeerInd->staId;
+                roamInfo.ucastSig = (tANI_U8)pIbssPeerInd->ucastSig;
+                roamInfo.bcastSig = (tANI_U8)pIbssPeerInd->bcastSig;
+                palCopyMemory(pMac->hHdd, &roamInfo.peerMac, pIbssPeerInd->peerAddr, sizeof(tCsrBssid));
+                csrRoamCallCallback(pMac, sessionId, &roamInfo, 0, 
+                        eCSR_ROAM_CONNECT_STATUS_UPDATE, eCSR_ROAM_RESULT_IBSS_PEER_DEPARTED);
+            }
+            break;
+
+        case eWNI_SME_SETCONTEXT_RSP:
+            {
+                tSirSmeSetContextRsp *pRsp = (tSirSmeSetContextRsp *)pSirMsg;
+                tListElem *pEntry;
+                tSmeCmd *pCommand;
+                
+                pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+                if ( pEntry )
+                {
+                    pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+                    if ( eSmeCommandSetKey == pCommand->command )
+                    {                
+                        sessionId = pCommand->sessionId;        
+                        pSession = CSR_GET_SESSION( pMac, sessionId );
+       
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                        if(eCSR_ENCRYPT_TYPE_NONE != pSession->connectedProfile.EncryptionType)
+                        {
+                            WLAN_VOS_DIAG_EVENT_DEF(setKeyEvent, vos_event_wlan_security_payload_type);
+                            palZeroMemory(pMac->hHdd, &setKeyEvent, sizeof(vos_event_wlan_security_payload_type));
+                            if( pRsp->peerMacAddr[0] & 0x01 )
+                            {
+                                setKeyEvent.eventId = WLAN_SECURITY_EVENT_SET_GTK_RSP;
+                            }
+                            else
+                            {
+                                setKeyEvent.eventId = WLAN_SECURITY_EVENT_SET_PTK_RSP;
+                            }
+                            setKeyEvent.encryptionModeMulticast = 
+                                (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.mcEncryptionType);
+                            setKeyEvent.encryptionModeUnicast = 
+                                (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.EncryptionType);
+                            palCopyMemory( pMac->hHdd, setKeyEvent.bssid, pSession->connectedProfile.bssid, 6 );
+                            setKeyEvent.authMode = 
+                                (v_U8_t)diagAuthTypeFromCSRType(pSession->connectedProfile.AuthType);
+                            if( eSIR_SUCCESS != pRsp->statusCode )
+                            {
+                                setKeyEvent.status = WLAN_SECURITY_STATUS_FAILURE;
+                            }
+                            WLAN_VOS_DIAG_EVENT_REPORT(&setKeyEvent, EVENT_WLAN_SECURITY);
+                        }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+                        if( CSR_IS_WAIT_FOR_KEY( pMac, sessionId) )
+                        {
+                            //We are done with authentication, whethere succeed or not
+                            csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, sessionId);
+
+                            csrRoamStopWaitForKeyTimer( pMac );
+                            //We do it here because this linkup function is not called after association 
+                            //when a key needs to be set. 
+                            if( csrIsConnStateConnectedInfra(pMac, sessionId) ) 
+                            {
+                                csrRoamLinkUp(pMac, pSession->connectedProfile.bssid);
+                            }
+                        }
+                        if( eSIR_SUCCESS == pRsp->statusCode )
+                        {
+                            palCopyMemory( pMac, &roamInfo.peerMac, &pRsp->peerMacAddr, sizeof(tCsrBssid) );
+                            //Make sure we install the GTK before indicating to HDD as authenticated
+                            //This is to prevent broadcast packets go out after PTK and before GTK.
+                            if( palEqualMemory( pMac->hHdd, &Broadcastaddr, pRsp->peerMacAddr, 
+                                        sizeof(tSirMacAddr) ) )
+                            {
+                                result = eCSR_ROAM_RESULT_AUTHENTICATED;
+                            }
+                            else
+                            {
+                            result = eCSR_ROAM_RESULT_NONE;
+                            }
+                            pRoamInfo = &roamInfo;
+                        }
+                        else
+                        {
+                            result = eCSR_ROAM_RESULT_FAILURE;
+                            smsLog( pMac, LOGE, "CSR: Roam Completion setkey command failed(%d) PeerMac %02X-%02X-%02X-%02X-%02X-%02X...\n", 
+                                pRsp->statusCode, pRsp->peerMacAddr[0], pRsp->peerMacAddr[1], pRsp->peerMacAddr[2],
+                                pRsp->peerMacAddr[3], pRsp->peerMacAddr[4], pRsp->peerMacAddr[5] );
+                        }
+                        csrRoamCallCallback(pMac, sessionId, &roamInfo, pCommand->u.setKeyCmd.roamId, 
+                                            eCSR_ROAM_SET_KEY_COMPLETE, result);
+
+                        // Indicate SME_QOS that the SET_KEY is completed, so that SME_QOS
+                        // can go ahead and initiate the TSPEC if any are pending
+                        sme_QosCsrEventInd(pMac, (v_U8_t)sessionId, SME_QOS_CSR_SET_KEY_SUCCESS_IND, NULL);
+
+#ifdef FEATURE_WLAN_CCX
+                        //Send Adjacent AP repot to new AP.
+                        if (result == eCSR_ROAM_RESULT_AUTHENTICATED &&
+                            pSession->isPrevApInfoValid && 
+                            pSession->connectedProfile.isCCXAssoc)
+                        {
+#ifdef WLAN_FEATURE_VOWIFI
+                            csrCcxSendAdjacentApRepMsg(pMac, pSession);
+#endif
+                            pSession->isPrevApInfoValid = FALSE;
+                        }
+#endif
+
+                        if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+                        {
+                            csrReleaseCommandSetKey( pMac, pCommand );
+                        }
+                    }
+                    else
+                    {
+                        smsLog( pMac, LOGE, "CSR: Roam Completion called but setkey command is not ACTIVE ...\n" );
+                    }
+                }
+                else
+                {
+                    smsLog( pMac, LOGE, "CSR: SetKey Completion called but NO commands are ACTIVE ...\n" );
+                }
+
+                smeProcessPendingQueue( pMac );
+            }
+            break;
+
+        case eWNI_SME_REMOVEKEY_RSP:
+            {
+                tSirSmeRemoveKeyRsp *pRsp = (tSirSmeRemoveKeyRsp *)pSirMsg;
+                tListElem *pEntry;
+                tSmeCmd *pCommand;
+                
+                pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+                if ( pEntry )
+                {
+                    pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+                    if ( eSmeCommandRemoveKey == pCommand->command )
+                    {                
+                        sessionId = pCommand->sessionId;
+                        pSession = CSR_GET_SESSION( pMac, sessionId );
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                        {
+                            WLAN_VOS_DIAG_EVENT_DEF(removeKeyEvent, vos_event_wlan_security_payload_type);
+                            palZeroMemory(pMac->hHdd, &removeKeyEvent, sizeof(vos_event_wlan_security_payload_type));
+                            removeKeyEvent.eventId = WLAN_SECURITY_EVENT_REMOVE_KEY_RSP;
+                            removeKeyEvent.encryptionModeMulticast = 
+                                (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.mcEncryptionType);
+                            removeKeyEvent.encryptionModeUnicast = 
+                                (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.EncryptionType);
+                            palCopyMemory( pMac->hHdd, removeKeyEvent.bssid, pSession->connectedProfile.bssid, 6 );
+                            removeKeyEvent.authMode = 
+                                (v_U8_t)diagAuthTypeFromCSRType(pSession->connectedProfile.AuthType);
+                            if( eSIR_SUCCESS != pRsp->statusCode )
+                            {
+                                removeKeyEvent.status = WLAN_SECURITY_STATUS_FAILURE;
+                            }
+                            WLAN_VOS_DIAG_EVENT_REPORT(&removeKeyEvent, EVENT_WLAN_SECURITY);
+                        }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+                        if( eSIR_SUCCESS == pRsp->statusCode )
+                        {
+                            palCopyMemory( pMac, &roamInfo.peerMac, &pRsp->peerMacAddr, sizeof(tCsrBssid) );
+                            result = eCSR_ROAM_RESULT_NONE;
+                            pRoamInfo = &roamInfo;
+                        }
+                        else
+                        {
+                            result = eCSR_ROAM_RESULT_FAILURE;
+                        }
+                        csrRoamCallCallback(pMac, sessionId, &roamInfo, pCommand->u.setKeyCmd.roamId, 
+                                            eCSR_ROAM_REMOVE_KEY_COMPLETE, result);
+                        if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+                        {
+                            csrReleaseCommandRemoveKey( pMac, pCommand );
+                        }
+                    }
+                    else
+                    {
+                        smsLog( pMac, LOGW, "CSR: Roam Completion called but setkey command is not ACTIVE ...\n" );
+                    }
+                }
+                else
+                {
+                    smsLog( pMac, LOGW, "CSR: SetKey Completion called but NO commands are ACTIVE ...\n" );
+                }
+
+                smeProcessPendingQueue( pMac );
+            }
+            break;
+
+        case eWNI_SME_GET_STATISTICS_RSP:
+            smsLog( pMac, LOGW, FL("Stats rsp from PE\n"));
+            csrRoamStatsRspProcessor( pMac, pSirMsg );
+            break;
+
+        case eWNI_SME_GET_RSSI_REQ:
+            smsLog( pMac, LOGW, FL("GetRssiReq from self\n"));
+            csrUpdateRssi( pMac, pSirMsg );
+            break;
+
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        case eWNI_SME_FT_PRE_AUTH_RSP:
+            csrRoamFTPreAuthRspProcessor( pMac, (tpSirFTPreAuthRsp)pSirMsg );
+            break;
+#endif
+
+        case eWNI_SME_MAX_ASSOC_EXCEEDED:
+            pSmeMaxAssocInd = (tSmeMaxAssocInd*)pSirMsg;
+            smsLog( pMac, LOG1, FL("send indication that max assoc have been reached and the new peer cannot be accepted\n"));          
+            sessionId = pSmeMaxAssocInd->sessionId;
+            roamInfo.sessionId = sessionId;
+            palCopyMemory(pMac->hHdd, &roamInfo.peerMac, pSmeMaxAssocInd->peerMac, sizeof(tCsrBssid));
+            csrRoamCallCallback(pMac, sessionId, &roamInfo, 0, 
+                    eCSR_ROAM_INFRA_IND, eCSR_ROAM_RESULT_MAX_ASSOC_EXCEEDED);
+            break;
+            
+        case eWNI_SME_BTAMP_LOG_LINK_IND:
+            smsLog( pMac, LOG1, FL("Establish logical link req from HCI serialized through MC thread\n"));
+            btampEstablishLogLinkHdlr( pSirMsg );
+            break;
+
+        default:
+            break;
+
+    }  // end switch on message type
+
+}
+
+
+void csrCallRoamingCompletionCallback(tpAniSirGlobal pMac, tCsrRoamSession *pSession, 
+                                      tCsrRoamInfo *pRoamInfo, tANI_U32 roamId, eCsrRoamResult roamResult)
+{
+   if(pSession)
+   {
+      if(pSession->bRefAssocStartCnt)
+      {
+         pSession->bRefAssocStartCnt--;
+         VOS_ASSERT( pSession->bRefAssocStartCnt == 0);
+         //Need to call association_completion because there is an assoc_start pending.
+         csrRoamCallCallback(pMac, pSession->sessionId, NULL, roamId, 
+                                               eCSR_ROAM_ASSOCIATION_COMPLETION, 
+                                               eCSR_ROAM_RESULT_FAILURE);
+      }
+      csrRoamCallCallback(pMac, pSession->sessionId, pRoamInfo, roamId, eCSR_ROAM_ROAMING_COMPLETION, roamResult);
+   }
+   else
+   {
+      smsLog(pMac, LOGW, FL("  pSession is NULL"));
+   }
+}
+
+
+eHalStatus csrRoamStartRoaming(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamingReason roamingReason)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+
+    if(CSR_IS_LOSTLINK_ROAMING(roamingReason) && 
+        (eANI_BOOLEAN_FALSE == pMac->roam.roamSession[sessionId].fCancelRoaming))
+    {
+        status = csrScanRequestLostLink1( pMac, sessionId );
+    }
+
+    return(status);
+}
+
+
+//return a boolean to indicate whether roaming completed or continue.
+tANI_BOOLEAN csrRoamCompleteRoaming(tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                    tANI_BOOLEAN fForce, eCsrRoamResult roamResult)
+{
+    tANI_BOOLEAN fCompleted = eANI_BOOLEAN_TRUE;
+    tANI_TIMESTAMP roamTime = (tANI_TIMESTAMP)(pMac->roam.configParam.nRoamingTime * PAL_TICKS_PER_SECOND);
+    tANI_TIMESTAMP curTime = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    //Check whether time is up
+    if(pSession->fCancelRoaming || fForce || 
+       ((curTime - pSession->roamingStartTime) > roamTime) ||
+       eCsrReassocRoaming == pSession->roamingReason ||
+       eCsrDynamicRoaming == pSession->roamingReason)
+    {
+        smsLog(pMac, LOGW, FL("  indicates roaming completion\n"));
+        if(pSession->fCancelRoaming && CSR_IS_LOSTLINK_ROAMING(pSession->roamingReason))
+        {
+            //roaming is cancelled, tell HDD to indicate disconnect
+            //Because LIM overload deauth_ind for both deauth frame and missed beacon
+            //we need to use this logic to detinguish it. For missed beacon, LIM set reason
+            //to be eSIR_BEACON_MISSED
+            if(eSIR_BEACON_MISSED == pSession->roamingStatusCode)
+            {
+                roamResult = eCSR_ROAM_RESULT_LOSTLINK;
+            }
+            else if(eCsrLostlinkRoamingDisassoc == pSession->roamingReason)
+            {
+                roamResult = eCSR_ROAM_RESULT_DISASSOC_IND;
+            }
+            else if(eCsrLostlinkRoamingDeauth == pSession->roamingReason)
+            {
+                roamResult = eCSR_ROAM_RESULT_DEAUTH_IND;
+            }
+            else
+            {
+                roamResult = eCSR_ROAM_RESULT_LOSTLINK;
+            }
+        }
+        csrCallRoamingCompletionCallback(pMac, pSession, NULL, 0, roamResult);
+        pSession->roamingReason = eCsrNotRoaming;
+    }
+    else
+    {
+        pSession->roamResult = roamResult;
+        if(!HAL_STATUS_SUCCESS(csrRoamStartRoamingTimer(pMac, sessionId, PAL_TIMER_TO_SEC_UNIT)))
+        {
+            csrCallRoamingCompletionCallback(pMac, pSession, NULL, 0, roamResult);
+            pSession->roamingReason = eCsrNotRoaming;
+        }
+        else
+        {
+            fCompleted = eANI_BOOLEAN_FALSE;
+        }
+    }
+
+    return(fCompleted);
+}
+
+
+void csrRoamCancelRoaming(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if(CSR_IS_ROAMING(pSession))
+    {
+        smsLog(pMac, LOGW, "   Cancelling roaming\n");
+        pSession->fCancelRoaming = eANI_BOOLEAN_TRUE;
+        if(CSR_IS_ROAM_JOINING(pMac, sessionId) && CSR_IS_ROAM_SUBSTATE_CONFIG(pMac, sessionId))
+        {
+            //No need to do anything in here because the handler takes care of it
+        }
+        else
+        {
+            eCsrRoamResult roamResult = CSR_IS_LOSTLINK_ROAMING(pSession->roamingReason) ? 
+                                                    eCSR_ROAM_RESULT_LOSTLINK : eCSR_ROAM_RESULT_NONE;
+            //Roaming is stopped after here 
+            csrRoamCompleteRoaming(pMac, sessionId, eANI_BOOLEAN_TRUE, roamResult);
+            //Since CSR may be in lostlink roaming situation, abort all roaming related activities
+            csrScanAbortMacScan(pMac);
+            csrRoamStopRoamingTimer(pMac, sessionId);
+        }
+    }
+}
+
+
+void csrRoamRoamingTimerHandler(void *pv)
+{
+    tCsrTimerInfo *pInfo = (tCsrTimerInfo *)pv;
+    tpAniSirGlobal pMac = pInfo->pMac;
+    tANI_U32 sessionId = pInfo->sessionId;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    if(eANI_BOOLEAN_FALSE == pSession->fCancelRoaming) 
+    {
+        if(!HAL_STATUS_SUCCESS(csrRoamStartRoaming(pMac, sessionId, pSession->roamingReason)))
+        {
+            csrCallRoamingCompletionCallback(pMac, pSession, NULL, 0, pSession->roamResult);
+            pSession->roamingReason = eCsrNotRoaming;
+        }
+    }
+}
+
+
+eHalStatus csrRoamStartRoamingTimer(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 interval)
+{
+    eHalStatus status;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    smsLog(pMac, LOG1, " csrScanStartRoamingTimer \n ");
+    pSession->roamingTimerInfo.sessionId = (tANI_U8)sessionId;
+    status = palTimerStart(pMac->hHdd, pSession->hTimerRoaming, interval, eANI_BOOLEAN_FALSE);
+    
+    return (status);
+}
+
+
+eHalStatus csrRoamStopRoamingTimer(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    return (palTimerStop(pMac->hHdd, pMac->roam.roamSession[sessionId].hTimerRoaming));
+}
+
+
+void csrRoamWaitForKeyTimeOutHandler(void *pv)
+{
+    tCsrTimerInfo *pInfo = (tCsrTimerInfo *)pv;
+    tpAniSirGlobal pMac = pInfo->pMac;
+
+    if( CSR_IS_WAIT_FOR_KEY( pMac, pInfo->sessionId ) )
+    {
+        smsLog(pMac, LOGW, " SME pre-auth state timeout. \n ");
+        //Change the substate so command queue is unblocked.
+        csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_NONE, pInfo->sessionId);
+    }
+    
+}
+
+
+eHalStatus csrRoamStartWaitForKeyTimer(tpAniSirGlobal pMac, tANI_U32 interval)
+{
+    eHalStatus status;
+    
+    smsLog(pMac, LOG1, " csrScanStartWaitForKeyTimer \n ");
+    status = palTimerStart(pMac->hHdd, pMac->roam.hTimerWaitForKey, interval, eANI_BOOLEAN_FALSE);
+    
+    return (status);
+}
+
+
+eHalStatus csrRoamStopWaitForKeyTimer(tpAniSirGlobal pMac)
+{
+    return (palTimerStop(pMac->hHdd, pMac->roam.hTimerWaitForKey));
+}
+
+
+void csrRoamIbssJoinTimerHandler(void *pv)
+{
+    tCsrTimerInfo *pInfo = (tCsrTimerInfo *)pv;
+    tpAniSirGlobal pMac = pInfo->pMac;
+    eCsrRoamDisconnectReason reason = eCSR_DISCONNECT_REASON_IBSS_JOIN_FAILURE;
+    tANI_U32 sessionId = pInfo->sessionId;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    pSession->ibss_join_pending = FALSE;
+    // JEZ100225:  As of main/latest "tip", we are no longer doing this. Check on this.
+    //csrRoamCallCallback(pMac, sessionId, NULL, 0, eCSR_ROAM_IBS_IND, eCSR_ROAM_RESULT_IBSS_JOIN_FAILED);
+    // Send an IBSS stop request to PE
+    csrRoamDisconnectInternal(pMac, sessionId, reason);
+
+}
+
+eHalStatus csrRoamStartIbssJoinTimer(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 interval)
+{
+    eHalStatus status;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    smsLog(pMac, LOG1, " csrRoamStartIbssJoinTimer \n ");
+    pSession->ibssJoinTimerInfo.sessionId = (tANI_U8)sessionId;
+    status = palTimerStart(pMac->hHdd, pSession->hTimerIbssJoining, interval, eANI_BOOLEAN_FALSE);
+    
+    return (status);
+}
+
+eHalStatus csrRoamStopIbssJoinTimer(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    return (palTimerStop(pMac->hHdd, pMac->roam.roamSession[sessionId].hTimerIbssJoining));
+}
+
+void csrRoamCompletion(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamInfo *pRoamInfo, tSmeCmd *pCommand, 
+                        eCsrRoamResult roamResult, tANI_BOOLEAN fSuccess)
+{
+    eRoamCmdStatus roamStatus = csrGetRoamCompleteStatus(pMac, sessionId);
+    tANI_U32 roamId = 0;
+    
+    if(pCommand)
+    {
+        roamId = pCommand->u.roamCmd.roamId;
+#if defined(VOSS_ENABLED)
+        VOS_ASSERT( sessionId == pCommand->sessionId );
+#endif
+    }
+
+    if(eCSR_ROAM_ROAMING_COMPLETION == roamStatus)
+    {
+        //if success, force roaming completion
+        csrRoamCompleteRoaming(pMac, sessionId, fSuccess, roamResult);
+    }
+    else
+    {
+        VOS_ASSERT((CSR_GET_SESSION( pMac, sessionId ))->bRefAssocStartCnt == 0);
+        smsLog(pMac, LOGW, FL("  indicates association completion. roamResult = %d\n"), roamResult);
+        csrRoamCallCallback(pMac, sessionId, pRoamInfo, roamId, roamStatus, roamResult);
+    }
+}
+
+
+eHalStatus csrRoamLostLink( tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 type, tSirSmeRsp *pSirMsg)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeDeauthInd *pDeauthIndMsg = NULL;
+    tSirSmeDisassocInd *pDisassocIndMsg = NULL;
+    eCsrRoamResult result = eCSR_ROAM_RESULT_LOSTLINK;
+    tCsrRoamInfo *pRoamInfo = NULL;
+    tCsrRoamInfo roamInfo;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    //Only need to roam for infra station. In this case P2P client will roam as well
+    tANI_BOOLEAN fToRoam = CSR_IS_INFRASTRUCTURE(&pSession->connectedProfile);
+
+    pSession->fCancelRoaming = eANI_BOOLEAN_FALSE;
+    if ( eWNI_SME_DISASSOC_IND == type )
+    {
+        result = eCSR_ROAM_RESULT_DISASSOC_IND;
+        pDisassocIndMsg = (tSirSmeDisassocInd *)pSirMsg;
+        pSession->roamingStatusCode = pDisassocIndMsg->statusCode;
+    }
+    else if ( eWNI_SME_DEAUTH_IND == type )
+    {
+        result = eCSR_ROAM_RESULT_DEAUTH_IND;
+        pDeauthIndMsg = (tSirSmeDeauthInd *)pSirMsg;
+        pSession->roamingStatusCode = pDeauthIndMsg->statusCode;
+    }
+    else
+    {
+        smsLog(pMac, LOGW, FL("gets an unknown type (%d)\n"), type);
+        result = eCSR_ROAM_RESULT_NONE;
+    }
+    
+    // call profile lost link routine here
+#ifdef WLAN_SOFTAP_FEATURE
+    if(!CSR_IS_INFRA_AP(&pSession->connectedProfile))
+#endif
+    {
+        csrRoamCallCallback(pMac, sessionId, NULL, 0, eCSR_ROAM_LOSTLINK_DETECTED, result);
+    }
+    
+    if ( eWNI_SME_DISASSOC_IND == type )
+    {
+        status = csrSendMBDisassocCnfMsg(pMac, pDisassocIndMsg);
+    }
+    else if ( eWNI_SME_DEAUTH_IND == type )
+    {
+        status = csrSendMBDeauthCnfMsg(pMac, pDeauthIndMsg);
+    }
+
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+       //If fail to send confirmation to PE, not to trigger roaming
+       fToRoam = eANI_BOOLEAN_FALSE;
+    }
+
+    //tell HDD to disconnect
+    palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+    roamInfo.statusCode = (tSirResultCodes)pSession->roamingStatusCode;
+    roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+#ifdef WLAN_SOFTAP_FEATURE
+    if( eWNI_SME_DISASSOC_IND == type)
+    {
+        //staMacAddr
+        palCopyMemory(pMac->hHdd, roamInfo.peerMac, pDisassocIndMsg->peerMacAddr, sizeof(tSirMacAddr));
+        roamInfo.staId = (tANI_U8)pDisassocIndMsg->staId;
+    }
+    else if( eWNI_SME_DEAUTH_IND == type )
+    {
+        //staMacAddr
+        palCopyMemory(pMac->hHdd, roamInfo.peerMac, pDeauthIndMsg->peerMacAddr, sizeof(tSirMacAddr));
+        roamInfo.staId = (tANI_U8)pDeauthIndMsg->staId;
+    }
+#endif
+    smsLog(pMac, LOGW, FL("roamInfo.staId (%d)\n"), roamInfo.staId);
+    csrRoamCallCallback(pMac, sessionId, &roamInfo, 0, eCSR_ROAM_LOSTLINK, result);
+    if(fToRoam)
+    {
+        //Only remove the connected BSS in infrastructure mode
+        csrRoamRemoveConnectedBssFromScanCache(pMac, &pSession->connectedProfile);
+        //Not to do anying for lostlink with WDS
+        if( pMac->roam.configParam.nRoamingTime )
+        {
+            if(HAL_STATUS_SUCCESS(status = csrRoamStartRoaming(pMac, sessionId,
+                        ( eWNI_SME_DEAUTH_IND == type ) ? 
+                        eCsrLostlinkRoamingDeauth : eCsrLostlinkRoamingDisassoc)))
+            {
+                palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+                //For IBSS, we need to give some more info to HDD
+                if(csrIsBssTypeIBSS(pSession->connectedProfile.BSSType))
+                {
+                    roamInfo.u.pConnectedProfile = &pSession->connectedProfile;
+                    roamInfo.statusCode = (tSirResultCodes)pSession->roamingStatusCode;
+                    roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+                }
+                else
+                {
+                   roamInfo.reasonCode = eCsrRoamReasonSmeIssuedForLostLink;
+                }
+                pRoamInfo = &roamInfo;
+                pSession->roamingReason = ( eWNI_SME_DEAUTH_IND == type ) ? 
+                        eCsrLostlinkRoamingDeauth : eCsrLostlinkRoamingDisassoc;
+                pSession->roamingStartTime = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
+                csrRoamCallCallback(pMac, sessionId, pRoamInfo, 0, eCSR_ROAM_ROAMING_START, eCSR_ROAM_RESULT_LOSTLINK);
+            }
+            else
+            {
+                smsLog(pMac, LOGW, " %s Fail to start roaming, status = %d", __FUNCTION__, status);
+                fToRoam = eANI_BOOLEAN_FALSE;
+            }
+        }
+        else
+        {
+            //We are told not to roam, indicate lostlink
+            fToRoam = eANI_BOOLEAN_FALSE;
+        }
+    }
+
+    if(!fToRoam)
+    {
+       if( eWNI_SME_DISASSOC_IND == type)
+       {
+           //staMacAddr
+           palCopyMemory(pMac->hHdd, roamInfo.peerMac, pDisassocIndMsg->peerMacAddr, sizeof(tSirMacAddr));
+           roamInfo.staId = (tANI_U8)pDisassocIndMsg->staId;
+       }
+       else if( eWNI_SME_DEAUTH_IND == type )
+       {
+           //staMacAddr
+            palCopyMemory(pMac->hHdd, roamInfo.peerMac, pDeauthIndMsg->peerMacAddr, sizeof(tSirMacAddr));
+            roamInfo.staId = (tANI_U8)pDeauthIndMsg->staId;
+        }
+        csrRoamCallCallback(pMac, sessionId, &roamInfo, 0, eCSR_ROAM_LOSTLINK, result);
+       
+        /*No need to start idle scan in case of IBSS/SAP 
+         Still enable idle scan for polling in case concurrent sessions are running */
+        if(CSR_IS_INFRASTRUCTURE(&pSession->connectedProfile))
+        {
+           csrScanStartIdleScan(pMac);
+        }
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrRoamLostLinkAfterhandoffFailure( tpAniSirGlobal pMac,tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tListElem *pEntry = NULL;
+    tSmeCmd *pCommand = NULL;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    pSession->fCancelRoaming =  eANI_BOOLEAN_FALSE;
+
+    //Only remove the connected BSS in infrastructure mode
+    csrRoamRemoveConnectedBssFromScanCache(pMac, &pSession->connectedProfile);
+    if(pMac->roam.configParam.nRoamingTime)
+    {
+       if(HAL_STATUS_SUCCESS(status = csrRoamStartRoaming(pMac,sessionId, pSession->roamingReason)))
+       {
+          //before starting the lost link logic release the roam command for handoff
+          pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+          if(pEntry)
+          {
+              pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+          }
+          if(pCommand)
+          {
+             if (( eSmeCommandRoam == pCommand->command ) &&
+                 ( eCsrSmeIssuedAssocToSimilarAP == pCommand->u.roamCmd.roamReason))
+             {
+                 if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+                 {
+                    csrReleaseCommandRoam( pMac, pCommand );
+                 }
+             }
+          }
+
+          smsLog( pMac, LOGW, "Lost link roaming started ...\n");
+       }
+    }
+    else
+    {
+       //We are told not to roam, indicate lostlink
+       status = eHAL_STATUS_FAILURE;
+    }
+    
+    return (status);
+}
+
+void csrRoamWmStatusChangeComplete( tpAniSirGlobal pMac )
+{
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+
+    pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+    if ( pEntry )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        if ( eSmeCommandWmStatusChange == pCommand->command )
+        {
+            // Nothing to process in a Lost Link completion....  It just kicks off a
+            // roaming sequence.
+            if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+            {
+                csrReleaseCommandWmStatusChange( pMac, pCommand );            
+            }
+            else
+            {
+                smsLog( pMac, LOGE, " ******csrRoamWmStatusChangeComplete fail to release command\n");
+            }
+            
+        }
+        else
+        {
+            smsLog( pMac, LOGW, "CSR: WmStatusChange Completion called but LOST LINK command is not ACTIVE ...\n" );
+        }
+    }
+    else
+    {
+        smsLog( pMac, LOGW, "CSR: WmStatusChange Completion called but NO commands are ACTIVE ...\n" );
+    }
+
+    smeProcessPendingQueue( pMac );
+}
+
+
+void csrRoamProcessWmStatusChangeCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tSirSmeRsp *pSirSmeMsg;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, pCommand->sessionId );
+
+    switch ( pCommand->u.wmStatusChangeCmd.Type )
+    {
+        case eCsrDisassociated:
+            pSirSmeMsg = (tSirSmeRsp *)&pCommand->u.wmStatusChangeCmd.u.DisassocIndMsg;
+            status = csrRoamLostLink(pMac, pCommand->sessionId, eWNI_SME_DISASSOC_IND, pSirSmeMsg);
+            break;
+
+        case eCsrDeauthenticated:
+            pSirSmeMsg = (tSirSmeRsp *)&pCommand->u.wmStatusChangeCmd.u.DeauthIndMsg;
+            status = csrRoamLostLink(pMac, pCommand->sessionId, eWNI_SME_DEAUTH_IND, pSirSmeMsg);
+            break;
+
+        default:
+            smsLog(pMac, LOGW, FL("gets an unknown command %d\n"), pCommand->u.wmStatusChangeCmd.Type);
+            break;
+    }
+    //For WDS, we want to stop BSS as well when it is indicated that it is disconnected.
+    if( CSR_IS_CONN_WDS(&pSession->connectedProfile) )
+    {
+        if( !HAL_STATUS_SUCCESS(csrRoamIssueStopBssCmd( pMac, pCommand->sessionId, eANI_BOOLEAN_TRUE )) )
+        {
+            //This is not good
+            smsLog(pMac, LOGE, FL("  failed to issue stopBSS command\n"));
+        }
+    }
+
+    // Lost Link just triggers a roaming sequence.  We can complte the Lost Link
+    // command here since there is nothing else to do.
+    csrRoamWmStatusChangeComplete( pMac );
+}
+
+
+//This function returns band and mode information.
+//The only tricky part is that if phyMode is set to 11abg, this function may return eCSR_CFG_DOT11_MODE_11B
+//instead of eCSR_CFG_DOT11_MODE_11G if everything is set to auto-pick.
+#ifdef WLAN_SOFTAP_FEATURE
+static eCsrCfgDot11Mode csrRoamGetPhyModeBandForBss( tpAniSirGlobal pMac, tCsrRoamProfile *pProfile, 
+                                                     tANI_U8 operationChn, eCsrBand *pBand )
+#else
+static eCsrCfgDot11Mode csrRoamGetPhyModeBandForBss( tpAniSirGlobal pMac, eCsrPhyMode phyModeIn, 
+                                                     tANI_U8 operationChn, eCsrBand *pBand )
+#endif
+{
+
+#ifdef WLAN_SOFTAP_FEATURE
+    eCsrPhyMode phyModeIn = (eCsrPhyMode)pProfile->phyMode;
+    eCsrCfgDot11Mode cfgDot11Mode = csrGetCfgDot11ModeFromCsrPhyMode(pProfile, phyModeIn, 
+                                            pMac->roam.configParam.ProprietaryRatesEnabled);
+#else
+    eCsrCfgDot11Mode cfgDot11Mode = csrGetCfgDot11ModeFromCsrPhyMode(phyModeIn, 
+                                            pMac->roam.configParam.ProprietaryRatesEnabled);
+#endif
+    eCsrBand eBand;
+    
+    //If the global setting for dot11Mode is set to auto/abg, we overwrite the setting in the profile.
+#ifdef WLAN_SOFTAP_FEATURE
+    if( ((!CSR_IS_INFRA_AP(pProfile )&& !CSR_IS_WDS(pProfile )) && 
+         ((eCSR_CFG_DOT11_MODE_AUTO == pMac->roam.configParam.uCfgDot11Mode) ||
+         (eCSR_CFG_DOT11_MODE_ABG == pMac->roam.configParam.uCfgDot11Mode))) ||
+        (eCSR_CFG_DOT11_MODE_AUTO == cfgDot11Mode) || (eCSR_CFG_DOT11_MODE_ABG == cfgDot11Mode) )
+#else
+    if( (eCSR_CFG_DOT11_MODE_AUTO == pMac->roam.configParam.uCfgDot11Mode) ||
+        (eCSR_CFG_DOT11_MODE_ABG == pMac->roam.configParam.uCfgDot11Mode) ||
+        (eCSR_CFG_DOT11_MODE_AUTO == cfgDot11Mode) || (eCSR_CFG_DOT11_MODE_ABG == cfgDot11Mode) )
+
+#endif
+    {
+        switch( pMac->roam.configParam.uCfgDot11Mode )
+        {
+            case eCSR_CFG_DOT11_MODE_11A:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+                eBand = eCSR_BAND_5G;
+                break;
+            case eCSR_CFG_DOT11_MODE_11B:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+                eBand = eCSR_BAND_24;
+                break;
+            case eCSR_CFG_DOT11_MODE_11G:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11G;
+                eBand = eCSR_BAND_24;
+                break;            
+            case eCSR_CFG_DOT11_MODE_11N:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11N;
+                eBand = eCSR_BAND_24;
+                break;            
+            //case eCSR_CFG_DOT11_MODE_BEST:
+            //    cfgDot11Mode = eCSR_CFG_DOT11_MODE_BEST;
+            //    eBand = eCSR_BAND_24;
+            //    break;            
+            default:
+                // Global dot11 Mode setting is 11a/b/g.
+                // use the channel number to determine the Mode setting.
+                if ( eCSR_OPERATING_CHANNEL_AUTO == operationChn )
+                {
+                    eBand = pMac->roam.configParam.eBand;
+                    if(eCSR_BAND_24 == eBand)
+                    {
+                        //See reason in else if ( CSR_IS_CHANNEL_24GHZ(operationChn) ) to pick 11B
+                        cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+                    }
+                    else
+                    {
+                        //prefer 5GHz
+                        eBand = eCSR_BAND_5G;
+                        cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+                    }
+                }
+                else if ( CSR_IS_CHANNEL_24GHZ(operationChn) )
+                {
+                    // channel is a 2.4GHz channel.  Set mode to 11g.
+                    //
+                    // !!LAC - WiFi tests require IBSS networks to start in 11b mode without any change to the
+                    // default parameter settings on the adapter.  We use ACU to start an IBSS through creation
+                    // of a startIBSS profile.   this startIBSS profile has Auto MACProtocol and the 
+                    // adapter property setting for dot11Mode is also AUTO.   So in this case, let's start 
+                    // the IBSS network in 11b mode instead of 11g mode.
+                    //
+                    // so this is for Auto=profile->MacProtocol && Auto=Global.dot11Mode && profile->channel is < 14, 
+                    // then start the IBSS in b mode.
+                    // 
+                    // Note:  we used to have this start as an 11g IBSS for best performance... now to specify that
+                    // the user will have to set the do11Mode in the property page to 11g to force it.
+                    cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+                    eBand = eCSR_BAND_24;
+                }
+                else 
+                {   
+                    // else, it's a 5.0GHz channel.  Set mode to 11a.
+                    cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+                    eBand = eCSR_BAND_5G;
+                }
+                break;
+        }//switch
+    }//if( eCSR_CFG_DOT11_MODE_ABG == cfgDot11Mode )
+    else
+    {
+            //dot11 mode is set, lets pick the band
+            if ( eCSR_OPERATING_CHANNEL_AUTO == operationChn )
+            {
+                // channel is Auto also. 
+                eBand = pMac->roam.configParam.eBand;
+                if(eCSR_BAND_ALL == eBand)
+                {
+                    //prefer 5GHz
+                    eBand = eCSR_BAND_5G;
+                }
+            }
+            else if ( CSR_IS_CHANNEL_24GHZ(operationChn) )
+            {
+                eBand = eCSR_BAND_24;
+            }
+            else 
+            {   
+                eBand = eCSR_BAND_5G;
+            }
+        }
+    if(pBand)
+    {
+        *pBand = eBand;
+    }
+    
+   if (operationChn == 14){ 
+     smsLog(pMac, LOGE, FL("  Switching to Dot11B mode \n"));
+     cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+   }
+
+    return( cfgDot11Mode );
+}
+
+
+eHalStatus csrRoamIssueStopBss( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamSubState NewSubstate )
+{
+    eHalStatus status;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+    {
+        vos_log_ibss_pkt_type *pIbssLog;
+
+        WLAN_VOS_DIAG_LOG_ALLOC(pIbssLog, vos_log_ibss_pkt_type, LOG_WLAN_IBSS_C);
+        if(pIbssLog)
+        {
+            pIbssLog->eventId = WLAN_IBSS_EVENT_STOP_REQ;
+            WLAN_VOS_DIAG_LOG_REPORT(pIbssLog);
+        }
+    }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+    pSession->ibss_join_pending = FALSE;
+    csrRoamStopIbssJoinTimer(pMac, sessionId );
+    // Set the roaming substate to 'stop Bss request'...
+    csrRoamSubstateChange( pMac, NewSubstate, sessionId );
+
+    // attempt to stop the Bss (reason code is ignored...)
+    status = csrSendMBStopBssReqMsg( pMac, sessionId );
+    
+    return (status);
+}
+
+
+//pNumChan is a caller allocated space with the sizeof pChannels
+eHalStatus csrGetCfgValidChannels(tpAniSirGlobal pMac, tANI_U8 *pChannels, tANI_U32 *pNumChan)
+{
+   
+    return (ccmCfgGetStr(pMac, WNI_CFG_VALID_CHANNEL_LIST,
+                  (tANI_U8 *)pChannels,
+                  pNumChan));
+}
+
+
+tANI_BOOLEAN csrRoamIsChannelValid( tpAniSirGlobal pMac, tANI_U8 channel )
+{
+    tANI_BOOLEAN fValid = FALSE;
+    tANI_U32 idxValidChannels;
+    tANI_U32 len = sizeof(pMac->roam.validChannelList);
+    
+    if (HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, pMac->roam.validChannelList, &len)))
+    {
+        for ( idxValidChannels = 0; ( idxValidChannels < len ); idxValidChannels++ )
+        {
+            if ( channel == pMac->roam.validChannelList[ idxValidChannels ] )
+            {
+                fValid = TRUE;
+                break;
+            }
+        }
+    }    
+    pMac->roam.numValidChannels = len;   
+    return fValid;
+}
+
+
+tANI_BOOLEAN csrRoamIsValid40MhzChannel(tpAniSirGlobal pMac, tANI_U8 channel)
+{
+    tANI_BOOLEAN fValid = eANI_BOOLEAN_FALSE;
+    tANI_U8 i;
+
+    for(i = 0; i < pMac->scan.base40MHzChannels.numChannels; i++)
+    {
+        if(channel == pMac->scan.base40MHzChannels.channelList[i])
+        {
+            fValid = eANI_BOOLEAN_TRUE;
+            break;
+        }
+    }
+
+    return (fValid);
+}
+
+
+//This function check and validate whether the NIC can do CB (40MHz)
+static tAniCBSecondaryMode csrGetCBModeFromIes(tpAniSirGlobal pMac, tANI_U8 primaryChn, tDot11fBeaconIEs *pIes)
+{
+    tAniCBSecondaryMode eRet = eANI_CB_SECONDARY_NONE;
+    tANI_U8 centerChn;
+    tANI_U32 ChannelBondingMode;
+
+    if(CSR_IS_CHANNEL_24GHZ(primaryChn))
+    {
+        ChannelBondingMode = pMac->roam.configParam.channelBondingMode24GHz;
+    }
+    else
+    {
+        ChannelBondingMode = pMac->roam.configParam.channelBondingMode5GHz;
+    }
+    //Figure what the other side's CB mode
+    if(WNI_CFG_CHANNEL_BONDING_MODE_DISABLE != ChannelBondingMode)
+    {
+        if(pIes->HTCaps.present && (eHT_CHANNEL_WIDTH_40MHZ == pIes->HTCaps.supportedChannelWidthSet))
+        {
+            if(pIes->HTInfo.present)
+            {
+                if(PHY_DOUBLE_CHANNEL_LOW_PRIMARY == pIes->HTInfo.secondaryChannelOffset)
+                {
+                    eRet = eANI_CB_SECONDARY_UP;
+                    centerChn = primaryChn + CSR_CB_CENTER_CHANNEL_OFFSET;
+                }
+                else if(PHY_DOUBLE_CHANNEL_HIGH_PRIMARY == pIes->HTInfo.secondaryChannelOffset)
+                {
+                    eRet = eANI_CB_SECONDARY_DOWN;
+                    centerChn = primaryChn - CSR_CB_CENTER_CHANNEL_OFFSET;
+                }
+                else
+                {
+                    //PHY_SINGLE_CHANNEL_CENTERED
+                    centerChn = primaryChn;
+                    eRet = eANI_CB_SECONDARY_NONE;
+                }
+                if((eANI_CB_SECONDARY_NONE != eRet) && !csrRoamIsValid40MhzChannel(pMac, centerChn))
+                {
+                    smsLog(pMac, LOGW, "  Invalid center channel (%d), disable 40MHz mode\n", centerChn);
+                    eRet = eANI_CB_SECONDARY_NONE;
+                }
+            }
+        }
+    }
+
+    return eRet;
+}
+
+tANI_BOOLEAN csrIsEncryptionInList( tpAniSirGlobal pMac, tCsrEncryptionList *pCipherList, eCsrEncryptionType encryptionType )
+{
+    tANI_BOOLEAN fFound = FALSE;
+    tANI_U32 idx;
+
+    for( idx = 0; idx < pCipherList->numEntries; idx++ )
+    {
+        if( pCipherList->encryptionType[idx] == encryptionType )
+        {
+            fFound = TRUE;
+            break;
+        }
+    }
+
+    return fFound;
+}
+
+tANI_BOOLEAN csrIsAuthInList( tpAniSirGlobal pMac, tCsrAuthList *pAuthList, eCsrAuthType authType )
+{
+    tANI_BOOLEAN fFound = FALSE;
+    tANI_U32 idx;
+
+    for( idx = 0; idx < pAuthList->numEntries; idx++ )
+    {
+        if( pAuthList->authType[idx] == authType )
+        {
+            fFound = TRUE;
+            break;
+        }
+    }
+
+    return fFound;
+}
+
+tANI_BOOLEAN csrIsSameProfile(tpAniSirGlobal pMac, tCsrRoamConnectedProfile *pProfile1, tCsrRoamProfile *pProfile2)
+{
+    tANI_BOOLEAN fCheck = eANI_BOOLEAN_FALSE;
+    tCsrScanResultFilter *pScanFilter = NULL;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    
+    if(pProfile1 && pProfile2)
+    {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            status = csrRoamPrepareFilterFromProfile(pMac, pProfile2, pScanFilter);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                fCheck = eANI_BOOLEAN_FALSE;
+                do
+                {
+                    tANI_U32 i;
+                    for(i = 0; i < pScanFilter->SSIDs.numOfSSIDs; i++)
+                    {
+                        fCheck = csrIsSsidMatch( pMac, pScanFilter->SSIDs.SSIDList[i].SSID.ssId, 
+                                                pScanFilter->SSIDs.SSIDList[i].SSID.length,
+                                                pProfile1->SSID.ssId, pProfile1->SSID.length, eANI_BOOLEAN_FALSE );
+                        if ( fCheck ) break;
+                    }
+                    if(!fCheck)
+                    {
+                        break;
+                    }
+                    if( !csrIsAuthInList( pMac, &pProfile2->AuthType, pProfile1->AuthType)
+                        || pProfile2->BSSType != pProfile1->BSSType
+                        || !csrIsEncryptionInList( pMac, &pProfile2->EncryptionType, pProfile1->EncryptionType )
+                        )
+                    {
+                        fCheck = eANI_BOOLEAN_FALSE;
+                        break;
+                    }
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                    if (pProfile1->MDID.mdiePresent || pProfile2->MDID.mdiePresent)
+                    {
+                        if (pProfile1->MDID.mobilityDomain != pProfile2->MDID.mobilityDomain)
+                        {
+                            fCheck = eANI_BOOLEAN_FALSE;
+                            break;
+                        }
+                    }
+#endif
+                    //Match found
+                    fCheck = eANI_BOOLEAN_TRUE;
+                }while(0);
+                csrFreeScanFilter(pMac, pScanFilter);
+            }
+            palFreeMemory(pMac->hHdd, pScanFilter);
+        }
+    }
+    
+    return (fCheck);
+}
+
+
+tANI_BOOLEAN csrRoamIsSameProfileKeys(tpAniSirGlobal pMac, tCsrRoamConnectedProfile *pConnProfile, tCsrRoamProfile *pProfile2)
+{
+    tANI_BOOLEAN fCheck = eANI_BOOLEAN_FALSE;
+    int i;
+
+    do
+    {
+        //Only check for static WEP
+        if(!csrIsEncryptionInList(pMac, &pProfile2->EncryptionType, eCSR_ENCRYPT_TYPE_WEP40_STATICKEY) &&
+            !csrIsEncryptionInList(pMac, &pProfile2->EncryptionType, eCSR_ENCRYPT_TYPE_WEP104_STATICKEY))
+        {
+            fCheck = eANI_BOOLEAN_TRUE;
+            break;
+        }
+        if(!csrIsEncryptionInList(pMac, &pProfile2->EncryptionType, pConnProfile->EncryptionType)) break;
+        if(pConnProfile->Keys.defaultIndex != pProfile2->Keys.defaultIndex) break;
+        for(i = 0; i < CSR_MAX_NUM_KEY; i++)
+        {
+            if(pConnProfile->Keys.KeyLength[i] != pProfile2->Keys.KeyLength[i]) break;
+            if(!palEqualMemory(pMac->hHdd, &pConnProfile->Keys.KeyMaterial[i], 
+                            &pProfile2->Keys.KeyMaterial[i], pProfile2->Keys.KeyLength[i]))
+            {
+                break;
+            }
+        }
+        if( i == CSR_MAX_NUM_KEY)
+        {
+            fCheck = eANI_BOOLEAN_TRUE;
+        }
+    }while(0);
+
+    return (fCheck);
+}
+
+
+//IBSS
+
+
+tANI_U8 csrRoamGetIbssStartChannelNumber50( tpAniSirGlobal pMac )
+{
+    tANI_U8 channel = 0;     
+    tANI_U32 idx;
+    tANI_U32 idxValidChannels;
+    tANI_BOOLEAN fFound = FALSE;
+    tANI_U32 len = sizeof(pMac->roam.validChannelList);
+    
+    if(eCSR_OPERATING_CHANNEL_ANY != pMac->roam.configParam.AdHocChannel5G)
+    {
+        channel = pMac->roam.configParam.AdHocChannel5G;
+        if(!csrRoamIsChannelValid(pMac, channel))
+        {
+            channel = 0;
+        }
+    }
+    if (0 == channel && HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, (tANI_U8 *)pMac->roam.validChannelList, &len)))
+    {
+        for ( idx = 0; ( idx < CSR_NUM_IBSS_START_CHANNELS_50 ) && !fFound; idx++ ) 
+        {
+            for ( idxValidChannels = 0; ( idxValidChannels < len ) && !fFound; idxValidChannels++ )
+            {
+                if ( csrStartIbssChannels50[ idx ] == pMac->roam.validChannelList[ idxValidChannels ] )
+                {
+                    fFound = TRUE;
+                    channel = csrStartIbssChannels50[ idx ];
+                }
+            }
+        }
+
+        // this is rare, but if it does happen, we find anyone in 11a bandwidth and return the first 11a channel found!
+        if (!fFound)    
+        {
+            for ( idxValidChannels = 0; idxValidChannels < len ; idxValidChannels++ )
+            {
+                if ( CSR_IS_CHANNEL_5GHZ(pMac->roam.validChannelList[ idx ]) )   // the max channel# in 11g is 14
+                {
+                    channel = csrStartIbssChannels50[ idx ];
+                    break;
+                }
+            }
+        }
+    }//if
+    
+    return( channel );    
+}
+
+
+tANI_U8 csrRoamGetIbssStartChannelNumber24( tpAniSirGlobal pMac )
+{
+    tANI_U8 channel = 1;
+    tANI_U32 idx;
+    tANI_U32 idxValidChannels;
+    tANI_BOOLEAN fFound = FALSE;
+    tANI_U32 len = sizeof(pMac->roam.validChannelList);
+    
+    if(eCSR_OPERATING_CHANNEL_ANY != pMac->roam.configParam.AdHocChannel24)
+    {
+        channel = pMac->roam.configParam.AdHocChannel24;
+        if(!csrRoamIsChannelValid(pMac, channel))
+        {
+            channel = 0;
+        }
+    }
+    
+    if (0 == channel && HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, (tANI_U8 *)pMac->roam.validChannelList, &len)))
+    {
+        for ( idx = 0; ( idx < CSR_NUM_IBSS_START_CHANNELS_24 ) && !fFound; idx++ ) 
+        {
+            for ( idxValidChannels = 0; ( idxValidChannels < len ) && !fFound; idxValidChannels++ )
+            {
+                if ( csrStartIbssChannels24[ idx ] == pMac->roam.validChannelList[ idxValidChannels ] )
+                {
+                    fFound = TRUE;
+                    channel = csrStartIbssChannels24[ idx ];
+                }
+            }
+        }
+    }
+    
+    return( channel );    
+}
+
+
+static void csrRoamGetBssStartParms( tpAniSirGlobal pMac, tCsrRoamProfile *pProfile, 
+                                      tCsrRoamStartBssParams *pParam )
+{
+    eCsrCfgDot11Mode cfgDot11Mode;
+    eCsrBand eBand;
+    tANI_U8 channel = 0;
+    tSirNwType nwType;
+    tANI_U8 operationChannel = 0; 
+    
+    if(pProfile->ChannelInfo.numOfChannels && pProfile->ChannelInfo.ChannelList)
+    {
+       operationChannel = pProfile->ChannelInfo.ChannelList[0];
+    }
+    
+#ifdef WLAN_SOFTAP_FEATURE
+    cfgDot11Mode = csrRoamGetPhyModeBandForBss( pMac, pProfile, operationChannel, &eBand );
+#else
+    cfgDot11Mode = csrRoamGetPhyModeBandForBss( pMac, (eCsrPhyMode)pProfile->phyMode, operationChannel, &eBand );
+#endif
+    
+#ifdef WLAN_FEATURE_P2P
+    if( ( (pProfile->csrPersona == VOS_P2P_CLIENT_MODE) ||
+          (pProfile->csrPersona == VOS_P2P_GO_MODE) )
+     && ( cfgDot11Mode == eCSR_CFG_DOT11_MODE_11B)
+      )
+    {
+        /* This should never happen */
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, 
+              FL("For P2PClient/P2P-GO (persona %d) cfgDot11Mode is 11B\n"), 
+              pProfile->csrPersona);
+        VOS_ASSERT(0);
+    }
+#endif
+
+    switch( cfgDot11Mode )
+    {
+        case eCSR_CFG_DOT11_MODE_11G:
+            nwType = eSIR_11G_NW_TYPE;
+            break;
+
+        case eCSR_CFG_DOT11_MODE_11B:
+            nwType = eSIR_11B_NW_TYPE;
+            break;   
+
+        case eCSR_CFG_DOT11_MODE_11A:
+            nwType = eSIR_11A_NW_TYPE;
+            break;
+
+        default:
+        case eCSR_CFG_DOT11_MODE_11N:
+        case eCSR_CFG_DOT11_MODE_TAURUS:
+            //Because LIM only verifies it against 11a, 11b or 11g, set only 11g or 11a here
+            if(eCSR_BAND_24 == eBand)
+            {
+                nwType = eSIR_11G_NW_TYPE;
+            }
+            else
+            {
+                nwType = eSIR_11A_NW_TYPE;
+            }
+            break;
+    }   
+
+    pParam->extendedRateSet.numRates = 0;
+
+    switch ( nwType )
+    {
+        default:
+            smsLog(pMac, LOGE, FL("sees an unknown pSirNwType (%d)\n"), nwType);
+        case eSIR_11A_NW_TYPE:
+        
+            pParam->operationalRateSet.numRates = 8;
+        
+            pParam->operationalRateSet.rate[0] = SIR_MAC_RATE_6 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[1] = SIR_MAC_RATE_9;
+            pParam->operationalRateSet.rate[2] = SIR_MAC_RATE_12 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[3] = SIR_MAC_RATE_18;
+            pParam->operationalRateSet.rate[4] = SIR_MAC_RATE_24 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[5] = SIR_MAC_RATE_36;
+            pParam->operationalRateSet.rate[6] = SIR_MAC_RATE_48;
+            pParam->operationalRateSet.rate[7] = SIR_MAC_RATE_54;
+            
+            if ( eCSR_OPERATING_CHANNEL_ANY == operationChannel ) 
+            {
+                channel = csrRoamGetIbssStartChannelNumber50( pMac );
+                if( 0 == channel &&
+                    CSR_IS_PHY_MODE_DUAL_BAND(pProfile->phyMode) && 
+                    CSR_IS_PHY_MODE_DUAL_BAND(pMac->roam.configParam.phyMode) 
+                    )
+                {
+                    //We could not find a 5G channel by auto pick, let's try 2.4G channels
+                    //We only do this here because csrRoamGetPhyModeBandForBss always picks 11a for AUTO
+                    nwType = eSIR_11B_NW_TYPE;
+                    channel = csrRoamGetIbssStartChannelNumber24( pMac );
+                   pParam->operationalRateSet.numRates = 4;
+                   pParam->operationalRateSet.rate[0] = SIR_MAC_RATE_1 | CSR_DOT11_BASIC_RATE_MASK;
+                   pParam->operationalRateSet.rate[1] = SIR_MAC_RATE_2 | CSR_DOT11_BASIC_RATE_MASK;
+                   pParam->operationalRateSet.rate[2] = SIR_MAC_RATE_5_5 | CSR_DOT11_BASIC_RATE_MASK;
+                   pParam->operationalRateSet.rate[3] = SIR_MAC_RATE_11 | CSR_DOT11_BASIC_RATE_MASK;
+                }
+            }
+            else 
+            {
+                channel = operationChannel;
+            }
+            break;
+            
+        case eSIR_11B_NW_TYPE:
+            pParam->operationalRateSet.numRates = 4;
+            pParam->operationalRateSet.rate[0] = SIR_MAC_RATE_1 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[1] = SIR_MAC_RATE_2 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[2] = SIR_MAC_RATE_5_5 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[3] = SIR_MAC_RATE_11 | CSR_DOT11_BASIC_RATE_MASK;
+
+            if ( eCSR_OPERATING_CHANNEL_ANY == operationChannel ) 
+            {
+                channel = csrRoamGetIbssStartChannelNumber24( pMac );
+            }
+            else 
+            {
+                channel = operationChannel;
+            }
+            
+            break;     
+
+        case eSIR_11G_NW_TYPE:
+#ifdef WLAN_FEATURE_P2P
+            /* For P2P Client and P2P GO, disable 11b rates */ 
+            if( (pProfile->csrPersona == VOS_P2P_CLIENT_MODE) ||
+                (pProfile->csrPersona == VOS_P2P_GO_MODE)
+              )
+            {
+                pParam->operationalRateSet.numRates = 8;
+            
+                pParam->operationalRateSet.rate[0] = SIR_MAC_RATE_6 | CSR_DOT11_BASIC_RATE_MASK;
+                pParam->operationalRateSet.rate[1] = SIR_MAC_RATE_9;
+                pParam->operationalRateSet.rate[2] = SIR_MAC_RATE_12 | CSR_DOT11_BASIC_RATE_MASK;
+                pParam->operationalRateSet.rate[3] = SIR_MAC_RATE_18;
+                pParam->operationalRateSet.rate[4] = SIR_MAC_RATE_24 | CSR_DOT11_BASIC_RATE_MASK;
+                pParam->operationalRateSet.rate[5] = SIR_MAC_RATE_36;
+                pParam->operationalRateSet.rate[6] = SIR_MAC_RATE_48;
+                pParam->operationalRateSet.rate[7] = SIR_MAC_RATE_54;
+            }
+            else
+#endif            
+            {
+            pParam->operationalRateSet.numRates = 4;
+
+            pParam->operationalRateSet.rate[0] = SIR_MAC_RATE_1 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[1] = SIR_MAC_RATE_2 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[2] = SIR_MAC_RATE_5_5 | CSR_DOT11_BASIC_RATE_MASK;
+            pParam->operationalRateSet.rate[3] = SIR_MAC_RATE_11 | CSR_DOT11_BASIC_RATE_MASK;
+               
+            pParam->extendedRateSet.numRates = 8;
+
+                        pParam->extendedRateSet.rate[0] = SIR_MAC_RATE_6;
+            pParam->extendedRateSet.rate[1] = SIR_MAC_RATE_9;
+            pParam->extendedRateSet.rate[2] = SIR_MAC_RATE_12;
+            pParam->extendedRateSet.rate[3] = SIR_MAC_RATE_18;
+            pParam->extendedRateSet.rate[4] = SIR_MAC_RATE_24;
+            pParam->extendedRateSet.rate[5] = SIR_MAC_RATE_36;
+            pParam->extendedRateSet.rate[6] = SIR_MAC_RATE_48;
+            pParam->extendedRateSet.rate[7] = SIR_MAC_RATE_54;
+            }
+            
+            if ( eCSR_OPERATING_CHANNEL_ANY == operationChannel ) 
+            {
+                channel = csrRoamGetIbssStartChannelNumber24( pMac );
+            }
+            else 
+            {
+                channel = operationChannel;
+            }
+            
+            break;            
+    }
+    pParam->operationChn = channel;
+    pParam->sirNwType = nwType;
+}
+
+
+static void csrRoamGetBssStartParmsFromBssDesc( tpAniSirGlobal pMac, tSirBssDescription *pBssDesc, 
+                                                 tDot11fBeaconIEs *pIes, tCsrRoamStartBssParams *pParam )
+{
+    
+    if( pParam )
+    {
+        pParam->sirNwType = pBssDesc->nwType;
+        pParam->cbMode = eANI_CB_SECONDARY_NONE;
+        pParam->operationChn = pBssDesc->channelId;
+        palCopyMemory( pMac->hHdd, &pParam->bssid, pBssDesc->bssId, sizeof(tCsrBssid) );
+    
+        if( pIes )
+        {
+            if(pIes->SuppRates.present)
+            {
+                pParam->operationalRateSet.numRates = pIes->SuppRates.num_rates;
+                if(pIes->SuppRates.num_rates > SIR_MAC_RATESET_EID_MAX)
+                {
+                    smsLog(pMac, LOGE, FL("num_rates :%d is more than SIR_MAC_RATESET_EID_MAX, resetting to SIR_MAC_RATESET_EID_MAX\n"),
+                      pIes->SuppRates.num_rates);
+                    pIes->SuppRates.num_rates = SIR_MAC_RATESET_EID_MAX;
+                }
+                palCopyMemory(pMac->hHdd, pParam->operationalRateSet.rate, pIes->SuppRates.rates, 
+                    sizeof(*pIes->SuppRates.rates) * pIes->SuppRates.num_rates);
+            }
+            if( pIes->SSID.present )
+            {
+                pParam->ssId.length = pIes->SSID.num_ssid;
+                palCopyMemory(pMac->hHdd, pParam->ssId.ssId, pIes->SSID.ssid, pParam->ssId.length);
+            }
+            pParam->cbMode = csrGetCBModeFromIes(pMac, pParam->operationChn, pIes);
+
+        }
+        else
+        {
+            pParam->ssId.length = 0;
+           pParam->operationalRateSet.numRates = 0;
+        }
+    }
+}
+
+
+static void csrRoamDetermineMaxRateForAdHoc( tpAniSirGlobal pMac, tSirMacRateSet *pSirRateSet )
+{
+    tANI_U8 MaxRate = 0;
+    tANI_U32 i;
+    tANI_U8 *pRate;    
+   
+    pRate = pSirRateSet->rate;
+    for ( i = 0; i < pSirRateSet->numRates; i++ )
+    {
+        MaxRate = CSR_MAX( MaxRate, ( pRate[ i ] & (~CSR_DOT11_BASIC_RATE_MASK) ) );
+    }
+    
+    // Save the max rate in the connected state information...
+    
+    // modify LastRates variable as well
+    
+    return;
+}
+
+
+//this function finds a valid secondary channel for channel bonding with "channel".
+//Param: channel -- primary channel, caller must validate it
+//       cbChoice -- CB directory
+//Return: if 0, no secondary channel is found. Otherwise a valid secondary channel.
+static tANI_U8 csrRoamGetSecondaryChannel(tpAniSirGlobal pMac, tANI_U8 channel, eCsrCBChoice cbChoice)
+{
+    tANI_U8 chnUp = 0, chnDown = 0, chnRet = 0;
+
+    switch (cbChoice)
+    {
+    case eCSR_CB_OFF:
+        chnUp = 0;
+        chnDown = 0;
+        break;
+    case eCSR_CB_DOWN:
+        chnUp = 0;
+        chnDown = channel - CSR_CB_CHANNEL_GAP;
+        break;
+    case eCSR_CB_UP:
+        chnUp = channel + CSR_CB_CHANNEL_GAP;
+        chnDown = 0;
+        break;
+    case eCSR_CB_AUTO:
+    //consider every other value means auto
+    default:
+        chnUp = channel + CSR_CB_CHANNEL_GAP;
+        chnDown = channel - CSR_CB_CHANNEL_GAP;
+        break;
+    }
+
+    //if CB_UP or auto, try channel up first
+    if(chnUp && CSR_IS_SAME_BAND_CHANNELS(chnUp, channel) && csrRoamIsChannelValid(pMac, chnUp))
+    {
+        //found a valid up channel for channel bonding
+        //check whether the center channel is valid
+        if(csrRoamIsValid40MhzChannel(pMac, channel + CSR_CB_CENTER_CHANNEL_OFFSET))
+        {
+            chnRet = chnUp;
+        }
+    }
+    if(chnRet == 0 && chnDown && CSR_IS_SAME_BAND_CHANNELS(chnDown, channel) && csrRoamIsChannelValid(pMac, chnDown))
+    {
+        //found a valid down channel for channel bonding
+        if(csrRoamIsValid40MhzChannel(pMac, channel - CSR_CB_CENTER_CHANNEL_OFFSET))
+        {
+            chnRet = chnDown;
+        }
+    }
+
+    return chnRet;
+}
+
+
+eHalStatus csrRoamIssueStartBss( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamStartBssParams *pParam, 
+                                 tCsrRoamProfile *pProfile, tSirBssDescription *pBssDesc, tANI_U32 roamId )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    eCsrBand eBand;
+
+    // Set the roaming substate to 'Start BSS attempt'...
+    csrRoamSubstateChange( pMac, eCSR_ROAM_SUBSTATE_START_BSS_REQ, sessionId );
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+    //Need to figure out whether we need to log WDS???
+    if( CSR_IS_IBSS( pProfile ) )
+    {
+        vos_log_ibss_pkt_type *pIbssLog;
+
+        WLAN_VOS_DIAG_LOG_ALLOC(pIbssLog, vos_log_ibss_pkt_type, LOG_WLAN_IBSS_C);
+        if(pIbssLog)
+        {
+            if(pBssDesc)
+            {
+                pIbssLog->eventId = WLAN_IBSS_EVENT_JOIN_IBSS_REQ;
+                palCopyMemory(pMac->hHdd, pIbssLog->bssid, pBssDesc->bssId, 6);
+            }
+            else
+            {
+                pIbssLog->eventId = WLAN_IBSS_EVENT_START_IBSS_REQ;
+            }
+            palCopyMemory(pMac->hHdd, pIbssLog->ssid, pParam->ssId.ssId,
+                pParam->ssId.length);
+            if(pProfile->ChannelInfo.numOfChannels == 0)
+            {
+                pIbssLog->channelSetting = AUTO_PICK;
+            }
+            else
+            {
+                pIbssLog->channelSetting = SPECIFIED;
+            }
+            pIbssLog->operatingChannel = pParam->operationChn;
+            WLAN_VOS_DIAG_LOG_REPORT(pIbssLog);
+        }
+    }
+#endif //FEATURE_WLAN_DIAG_SUPPORT_CSR
+    //Put RSN information in for Starting BSS
+    pParam->nRSNIELength = (tANI_U16)pProfile->nRSNReqIELength;
+    pParam->pRSNIE = pProfile->pRSNReqIE;
+
+
+#ifdef WLAN_SOFTAP_FEATURE
+    pParam->privacy           = pProfile->privacy;
+    pParam->fwdWPSPBCProbeReq = pProfile->fwdWPSPBCProbeReq;   
+    pParam->authType          = pProfile->csr80211AuthType;
+    pParam->beaconInterval    = pProfile->beaconInterval;
+    pParam->dtimPeriod        = pProfile->dtimPeriod;
+    pParam->ApUapsdEnable     = pProfile->ApUapsdEnable;
+    pParam->ssidHidden        = pProfile->SSIDs.SSIDList[0].ssidHidden;
+    if (CSR_IS_INFRA_AP(pProfile)&& (pParam->operationChn != 0))
+    {
+        if (csrIsValidChannel(pMac, pParam->operationChn) != eHAL_STATUS_SUCCESS)
+        {
+            pParam->operationChn = INFRA_AP_DEFAULT_CHANNEL;                   
+        }  
+    }
+
+    pParam->protEnabled     = pProfile->protEnabled;
+    pParam->obssProtEnabled = pProfile->obssProtEnabled;
+    pParam->ht_protection   = pProfile->cfg_protection;
+    pParam->wps_state       = pProfile->wps_state;
+#endif
+    
+
+#ifdef WLAN_SOFTAP_FEATURE
+    pParam->uCfgDot11Mode = csrRoamGetPhyModeBandForBss(pMac, pProfile, pParam->operationChn /* pProfile->operationChannel*/, 
+                                        &eBand);
+#else
+    pParam->uCfgDot11Mode = csrRoamGetPhyModeBandForBss(pMac, (eCsrPhyMode)pProfile->phyMode, pProfile->operationChannel, 
+                                        &eBand);
+#endif
+    pParam->bssPersona = pProfile->csrPersona;
+    // When starting an IBSS, start on the channel from the Profile.
+    status = csrSendMBStartBssReqMsg( pMac, sessionId, pProfile->BSSType, pParam, pBssDesc );
+
+    return (status);
+}
+
+
+static void csrRoamPrepareBssParams(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                                     tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes)
+{
+    tANI_U8 Channel, SecondChn;
+    tAniCBSecondaryMode cbMode = eANI_CB_SECONDARY_NONE;
+    eCsrCBChoice cbChoice;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if( pBssDesc )
+    {
+        csrRoamGetBssStartParmsFromBssDesc( pMac, pBssDesc, pIes, &pSession->bssParams );
+        //Since csrRoamGetBssStartParmsFromBssDesc fills in the bssid for pSession->bssParams
+        //The following code has to be do after that.
+        //For WDS station, use selfMac as the self BSSID
+        if( CSR_IS_WDS_STA( pProfile ) )
+        {
+            palCopyMemory(pMac->hHdd, &pSession->bssParams.bssid, &pSession->selfMacAddr, sizeof(tCsrBssid));
+        }
+    }
+    else
+    {
+        csrRoamGetBssStartParms(pMac, pProfile, &pSession->bssParams);
+
+        //Use the first SSID
+        if(pProfile->SSIDs.numOfSSIDs)
+        {
+            palCopyMemory(pMac->hHdd, &pSession->bssParams.ssId, pProfile->SSIDs.SSIDList, sizeof(tSirMacSSid));
+        }
+        //For WDS station, use selfMac as the self BSSID
+        if( CSR_IS_WDS_STA( pProfile ) )
+        {
+            palCopyMemory(pMac->hHdd, &pSession->bssParams.bssid, &pSession->selfMacAddr, sizeof(tCsrBssid));
+        }
+        //Use the first BSSID
+        else if( pProfile->BSSIDs.numOfBSSIDs )
+        {
+            palCopyMemory(pMac->hHdd, &pSession->bssParams.bssid, pProfile->BSSIDs.bssid, sizeof(tCsrBssid));
+        }
+        else
+        {
+            palZeroMemory( pMac->hHdd, &pSession->bssParams.bssid, sizeof(tCsrBssid) );
+        }
+    }
+    Channel = pSession->bssParams.operationChn;
+
+    //Set operating channel in pProfile which will be used 
+    //in csrRoamSetBssConfigCfg() to determine channel bonding
+    //mode and will be configured in CFG later 
+    pProfile->operationChannel = Channel;
+    
+    if(Channel == 0)
+    {
+        smsLog(pMac, LOGW, "   CSR cannot find a channel to start IBSS\n");
+    }
+    else
+    {
+  
+        csrRoamDetermineMaxRateForAdHoc( pMac, &pSession->bssParams.operationalRateSet );
+
+        if( CSR_IS_START_IBSS( pProfile ) )
+        {
+           //TBH: channel bonding is not supported for Libra
+            if( pProfile->ChannelInfo.ChannelList && eCSR_OPERATING_CHANNEL_AUTO != pProfile->ChannelInfo.ChannelList[0] )
+            {
+                Channel = pProfile->ChannelInfo.ChannelList[0];
+                cbChoice = pProfile->CBMode;
+            }
+            else {
+                cbChoice = pMac->roam.configParam.cbChoice;
+            }
+            pSession->bssParams.operationChn = Channel;
+            //make sure channel is valid
+            if(!csrRoamIsChannelValid(pMac, Channel))
+            {
+                //set Channel to 0 to let lim know this is invalid
+                //We still send this request down to lim even though we know the channel is wrong because
+                //lim will response with error and hdd's eWNI_SME_START_BSS_RSP handler will roam other profile (if any)
+                Channel = 0;
+                pSession->bssParams.operationChn = 0;
+            }
+            else {
+                tANI_U32 ChannelBondingMode;
+
+                if(CSR_IS_CHANNEL_24GHZ(Channel))
+                {
+                    ChannelBondingMode = pMac->roam.configParam.channelBondingMode24GHz;
+                }
+                else
+                {
+                    ChannelBondingMode = pMac->roam.configParam.channelBondingMode5GHz;
+                }
+
+                //now we have a valid channel
+                if(WNI_CFG_CHANNEL_BONDING_MODE_DISABLE != ChannelBondingMode)
+                {
+                    //let's pick a secondard channel
+                    SecondChn = csrRoamGetSecondaryChannel(pMac, Channel, cbChoice);
+
+                    if(SecondChn > Channel)
+                    {
+                        cbMode = eANI_CB_SECONDARY_UP;
+                    }
+                    else if(SecondChn && SecondChn < Channel)
+                    {
+                        cbMode =eANI_CB_SECONDARY_DOWN;
+                    }
+                    else
+                    {
+                        cbMode = eANI_CB_SECONDARY_NONE;
+                    }
+                    pSession->bssParams.cbMode = cbMode;
+                }
+                else
+                {
+                    pSession->bssParams.cbMode = eANI_CB_SECONDARY_NONE;
+                }
+            }
+        }
+    }
+}
+
+
+
+static eHalStatus csrRoamStartIbss( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                                    tANI_BOOLEAN *pfSameIbss )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_BOOLEAN fSameIbss = FALSE;
+     
+    if ( csrIsConnStateIbss( pMac, sessionId ) ) 
+    { 
+        // Check if any profile parameter has changed ? If any profile parameter
+        // has changed then stop old BSS and start a new one with new parameters
+        if ( csrIsSameProfile( pMac, &pMac->roam.roamSession[sessionId].connectedProfile, pProfile ) ) 
+        {
+            fSameIbss = TRUE;
+        }
+        else
+        {
+            status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING );
+        }       
+    }
+    else if ( csrIsConnStateConnectedInfra( pMac, sessionId ) ) 
+    {
+        // Disassociate from the connected Infrastructure network...
+        status = csrRoamIssueDisassociate( pMac, sessionId, eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING, FALSE );
+    }
+    else 
+    {
+        tBssConfigParam *pBssConfig;
+        
+        status = palAllocateMemory(pMac->hHdd, (void **)&pBssConfig, sizeof(tBssConfigParam)); 
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pBssConfig, sizeof(tBssConfigParam));
+            // there is no Bss description before we start an IBSS so we need to adopt
+            // all Bss configuration parameters from the Profile.
+            status = csrRoamPrepareBssConfigFromProfile(pMac, pProfile, pBssConfig, NULL);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                //save dotMode
+                pMac->roam.roamSession[sessionId].bssParams.uCfgDot11Mode = pBssConfig->uCfgDot11Mode;
+                //Prepare some more parameters for this IBSS
+                csrRoamPrepareBssParams(pMac, sessionId, pProfile, NULL, NULL);
+                status = csrRoamSetBssConfigCfg(pMac, sessionId, pProfile, NULL, pBssConfig, NULL);
+            }
+            
+            palFreeMemory(pMac->hHdd, pBssConfig);
+        }//Allocate memory
+    }
+    
+    if(pfSameIbss)
+    {
+        *pfSameIbss = fSameIbss;
+    }
+    return( status );
+}
+
+
+static void csrRoamUpdateConnectedProfileFromNewBss( tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                                     tSirSmeNewBssInfo *pNewBss )
+{
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if( pNewBss )
+    {
+        // Set the operating channel.
+        pSession->connectedProfile.operationChannel = pNewBss->channelNumber;
+        // move the BSSId from the BSS description into the connected state information.
+        palCopyMemory( pMac->hHdd, &pSession->connectedProfile.bssid, 
+                      &(pNewBss->bssId), sizeof( tCsrBssid ) );    
+    }
+
+    return;
+}
+
+
+#ifdef FEATURE_WLAN_WAPI
+eHalStatus csrRoamSetBKIDCache( tpAniSirGlobal pMac, tANI_U32 sessionId, tBkidCacheInfo *pBKIDCache,
+                                 tANI_U32 numItems )
+{
+   eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+   tCsrRoamSession *pSession;
+
+   if(!CSR_IS_SESSION_VALID( pMac, sessionId ))
+   {
+       smsLog(pMac, LOGE, FL("  Invalid session ID\n"));
+       return status;
+   }
+   smsLog(pMac, LOGW, "csrRoamSetBKIDCache called, numItems = %d\n", numItems);
+   pSession = CSR_GET_SESSION( pMac, sessionId );
+   if(numItems <= CSR_MAX_BKID_ALLOWED)
+   {
+       status = eHAL_STATUS_SUCCESS;
+       //numItems may be 0 to clear the cache
+       pSession->NumBkidCache = (tANI_U16)numItems;
+       if(numItems && pBKIDCache)
+       {
+           status = palCopyMemory( pMac->hHdd, pSession->BkidCacheInfo, pBKIDCache,
+                           sizeof(tBkidCacheInfo) * numItems );
+       }
+   }
+
+   return (status);
+}
+
+eHalStatus csrRoamGetBKIDCache(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pNum,
+                                tBkidCacheInfo *pBkidCache)
+{
+   eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+   tCsrRoamSession *pSession;
+
+   if(!CSR_IS_SESSION_VALID( pMac, sessionId ))
+   {
+       smsLog(pMac, LOGE, FL("  Invalid session ID\n"));
+       return status;
+   }
+
+   pSession = CSR_GET_SESSION( pMac, sessionId );
+   if(pNum && pBkidCache)
+   {
+       if(pSession->NumBkidCache == 0)
+       {
+           *pNum = 0;
+           status = eHAL_STATUS_SUCCESS;
+       }
+       else if(*pNum >= pSession->NumBkidCache)
+       {
+           if(pSession->NumBkidCache > CSR_MAX_PMKID_ALLOWED)
+           {
+               smsLog(pMac, LOGE, FL("NumPmkidCache :%d is more than CSR_MAX_PMKID_ALLOWED, resetting to CSR_MAX_PMKID_ALLOWED\n"),
+                 pSession->NumBkidCache);
+               pSession->NumBkidCache = CSR_MAX_PMKID_ALLOWED;
+           }
+           palCopyMemory( pMac->hHdd, pBkidCache, pSession->BkidCacheInfo,
+                           sizeof(tBkidCacheInfo) * pSession->NumBkidCache );
+           *pNum = pSession->NumBkidCache;
+           status = eHAL_STATUS_SUCCESS;
+       }
+   }
+
+   return (status);
+
+}
+
+tANI_U32 csrRoamGetNumBKIDCache(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+   return (pMac->roam.roamSession[sessionId].NumBkidCache);
+
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+eHalStatus csrRoamSetPMKIDCache( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                 tPmkidCacheInfo *pPMKIDCache, tANI_U32 numItems )
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, "csrRoamSetPMKIDCache called, numItems = %d\n", numItems);
+    if(numItems <= CSR_MAX_PMKID_ALLOWED)
+    {
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+        {
+            WLAN_VOS_DIAG_EVENT_DEF(secEvent, vos_event_wlan_security_payload_type);
+            palZeroMemory(pMac->hHdd, &secEvent, sizeof(vos_event_wlan_security_payload_type));
+            secEvent.eventId = WLAN_SECURITY_EVENT_PMKID_UPDATE;
+            secEvent.encryptionModeMulticast = 
+                (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.mcEncryptionType);
+            secEvent.encryptionModeUnicast = 
+                (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.EncryptionType);
+            palCopyMemory( pMac->hHdd, secEvent.bssid, pSession->connectedProfile.bssid, 6 );
+            secEvent.authMode = 
+                (v_U8_t)diagAuthTypeFromCSRType(pSession->connectedProfile.AuthType);
+            WLAN_VOS_DIAG_EVENT_REPORT(&secEvent, EVENT_WLAN_SECURITY);
+        }
+#endif//FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+        status = eHAL_STATUS_SUCCESS;
+        //numItems may be 0 to clear the cache
+        pSession->NumPmkidCache = (tANI_U16)numItems;
+        if(numItems && pPMKIDCache)
+        {
+            status = palCopyMemory( pMac->hHdd, pSession->PmkidCacheInfo, pPMKIDCache,
+                            sizeof(tPmkidCacheInfo) * numItems );
+        }
+    }
+
+    return (status);
+}
+
+
+tANI_U32 csrRoamGetNumPMKIDCache(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    return (pMac->roam.roamSession[sessionId].NumPmkidCache);
+}
+
+
+eHalStatus csrRoamGetPMKIDCache(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pNum, tPmkidCacheInfo *pPmkidCache)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if(pNum && pPmkidCache)
+    {
+        if(pSession->NumPmkidCache == 0)
+        {
+            *pNum = 0;
+            status = eHAL_STATUS_SUCCESS;
+        }
+        else if(*pNum >= pSession->NumPmkidCache)
+        {
+            if(pSession->NumPmkidCache > CSR_MAX_PMKID_ALLOWED)
+            {
+                smsLog(pMac, LOGE, FL("NumPmkidCache :%d is more than CSR_MAX_PMKID_ALLOWED, resetting to CSR_MAX_PMKID_ALLOWED\n"),
+                  pSession->NumPmkidCache);
+                pSession->NumPmkidCache = CSR_MAX_PMKID_ALLOWED;
+            }
+            palCopyMemory( pMac->hHdd, pPmkidCache, pSession->PmkidCacheInfo,
+                            sizeof(tPmkidCacheInfo) * pSession->NumPmkidCache );
+            *pNum = pSession->NumPmkidCache;
+            status = eHAL_STATUS_SUCCESS;
+        }
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrRoamGetWpaRsnReqIE(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pLen, tANI_U8 *pBuf)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tANI_U32 len;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if(pLen)
+    {
+        len = *pLen;
+        *pLen = pSession->nWpaRsnReqIeLength;
+        if(pBuf)
+        {
+            if(len >= pSession->nWpaRsnReqIeLength)
+            {
+                status = palCopyMemory(pMac->hHdd, pBuf, pSession->pWpaRsnReqIE, pSession->nWpaRsnReqIeLength);
+            }
+        }
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrRoamGetWpaRsnRspIE(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pLen, tANI_U8 *pBuf)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tANI_U32 len;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if(pLen)
+    {
+        len = *pLen;
+        *pLen = pSession->nWpaRsnRspIeLength;
+        if(pBuf)
+        {
+            if(len >= pSession->nWpaRsnRspIeLength)
+            {
+                status = palCopyMemory(pMac->hHdd, pBuf, pSession->pWpaRsnRspIE, pSession->nWpaRsnRspIeLength);
+            }
+        }
+    }
+
+    return (status);
+}
+
+#ifdef FEATURE_WLAN_WAPI
+eHalStatus csrRoamGetWapiReqIE(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pLen, tANI_U8 *pBuf)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tANI_U32 len;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    if(pLen)
+    {
+        len = *pLen;
+        *pLen = pSession->nWapiReqIeLength;
+        if(pBuf)
+        {
+            if(len >= pSession->nWapiReqIeLength)
+            {
+                status = palCopyMemory(pMac->hHdd, pBuf, pSession->pWapiReqIE, pSession->nWapiReqIeLength);
+            }
+        }
+    }
+
+    return (status);
+}
+
+eHalStatus csrRoamGetWapiRspIE(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pLen, tANI_U8 *pBuf)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tANI_U32 len;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if(pLen)
+    {
+        len = *pLen;
+        *pLen = pSession->nWapiRspIeLength;
+        if(pBuf)
+        {
+            if(len >= pSession->nWapiRspIeLength)
+            {
+                status = palCopyMemory(pMac->hHdd, pBuf, pSession->pWapiRspIE, pSession->nWapiRspIeLength);
+            }
+        }
+    }
+
+    return (status);
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+eRoamCmdStatus csrGetRoamCompleteStatus(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eRoamCmdStatus retStatus = eCSR_ROAM_CONNECT_COMPLETION;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    if(CSR_IS_ROAMING(pSession))
+    {
+        retStatus = eCSR_ROAM_ROAMING_COMPLETION;
+        pSession->fRoaming = eANI_BOOLEAN_FALSE;
+    }
+
+    return (retStatus);
+}
+
+
+//This function remove the connected BSS from te cached scan result
+eHalStatus csrRoamRemoveConnectedBssFromScanCache(tpAniSirGlobal pMac,
+                                                  tCsrRoamConnectedProfile *pConnProfile)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tCsrScanResultFilter *pScanFilter = NULL;
+    tListElem *pEntry;
+    tCsrScanResult *pResult;
+        tDot11fBeaconIEs *pIes;
+    tANI_BOOLEAN fMatch;
+
+    if(!(csrIsMacAddressZero(pMac, &pConnProfile->bssid) ||
+            csrIsMacAddressBroadcast(pMac, &pConnProfile->bssid)))
+    {
+        do
+        {
+            //Prepare the filter. Only fill in the necessary fields. Not all fields are needed
+            status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+            if(!HAL_STATUS_SUCCESS(status)) break;
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter->BSSIDs.bssid, sizeof(tCsrBssid));
+            if(!HAL_STATUS_SUCCESS(status)) break;
+            palCopyMemory(pMac->hHdd, pScanFilter->BSSIDs.bssid, &pConnProfile->bssid, sizeof(tCsrBssid));
+            pScanFilter->BSSIDs.numOfBSSIDs = 1;
+            if(!csrIsNULLSSID(pConnProfile->SSID.ssId, pConnProfile->SSID.length))
+            {
+                status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter->SSIDs.SSIDList, sizeof(tCsrSSIDInfo));
+                if(!HAL_STATUS_SUCCESS(status)) break;
+                palCopyMemory(pMac->hHdd, &pScanFilter->SSIDs.SSIDList[0].SSID, &pConnProfile->SSID, sizeof(tSirMacSSid));
+            }
+            pScanFilter->authType.numEntries = 1;
+            pScanFilter->authType.authType[0] = pConnProfile->AuthType;
+            pScanFilter->BSSType = pConnProfile->BSSType;
+            pScanFilter->EncryptionType.numEntries = 1;
+            pScanFilter->EncryptionType.encryptionType[0] = pConnProfile->EncryptionType;
+            pScanFilter->mcEncryptionType.numEntries = 1;
+            pScanFilter->mcEncryptionType.encryptionType[0] = pConnProfile->mcEncryptionType;
+            //We ignore the channel for now, BSSID should be enough
+            pScanFilter->ChannelInfo.numOfChannels = 0;
+            //Also ignore the following fields
+            pScanFilter->uapsd_mask = 0;
+            pScanFilter->bWPSAssociation = eANI_BOOLEAN_FALSE;
+            pScanFilter->countryCode[0] = 0;
+            pScanFilter->phyMode = eCSR_DOT11_MODE_TAURUS;
+
+            csrLLLock(&pMac->scan.scanResultList);
+            pEntry = csrLLPeekHead( &pMac->scan.scanResultList, LL_ACCESS_NOLOCK );
+            while( pEntry ) 
+            {
+                pResult = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+                                pIes = (tDot11fBeaconIEs *)( pResult->Result.pvIes );
+                fMatch = csrMatchBSS(pMac, &pResult->Result.BssDescriptor, 
+                               pScanFilter, NULL, NULL, NULL, &pIes);
+                //Release the IEs allocated by csrMatchBSS is needed
+                if( !pResult->Result.pvIes )
+                {
+                    //need to free the IEs since it is allocated by csrMatchBSS
+                    palFreeMemory(pMac->hHdd, pIes);
+                }
+                if(fMatch)
+                {
+                    //We found the one
+                    if( csrLLRemoveEntry(&pMac->scan.scanResultList, pEntry, LL_ACCESS_NOLOCK) )
+                    {
+                        //Free the memory
+                        csrFreeScanResultEntry( pMac, pResult );
+                    }
+                    break;
+                }
+                pEntry = csrLLNext(&pMac->scan.scanResultList, pEntry, LL_ACCESS_NOLOCK);
+            }//while
+            csrLLUnlock(&pMac->scan.scanResultList);
+        }while(0);
+        if(pScanFilter)
+        {
+            csrFreeScanFilter(pMac, pScanFilter);
+            palFreeMemory(pMac->hHdd, pScanFilter);
+        }
+    }
+    return (status);
+}
+
+
+
+//BT-AMP
+
+eHalStatus csrIsBTAMPAllowed( tpAniSirGlobal pMac, tANI_U32 chnId )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 sessionId;
+
+    for( sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; sessionId++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+            if( csrIsConnStateIbss( pMac, sessionId ) || csrIsBTAMP( pMac, sessionId ) )
+            {
+                //co-exist with IBSS or BT-AMP is not supported
+                smsLog( pMac, LOGW, " BTAMP is not allowed due to IBSS/BT-AMP exist in session %d\n", sessionId );
+                status = eHAL_STATUS_CSR_WRONG_STATE;
+                break;
+            }
+            if( csrIsConnStateInfra( pMac, sessionId ) )
+            {
+                if( chnId && 
+                    ( (tANI_U8)chnId != pMac->roam.roamSession[sessionId].connectedProfile.operationChannel ) )
+                {
+                    smsLog( pMac, LOGW, " BTAMP is not allowed due to channel (%d) diff than infr channel (%d)\n",
+                        chnId, pMac->roam.roamSession[sessionId].connectedProfile.operationChannel );
+                    status = eHAL_STATUS_CSR_WRONG_STATE;
+                    break;
+                }
+            }
+        }
+    }
+
+    return ( status );
+}
+
+
+static eHalStatus csrRoamStartWds( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, tSirBssDescription *pBssDesc )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tBssConfigParam bssConfig;
+
+    if ( csrIsConnStateIbss( pMac, sessionId ) ) 
+    { 
+        status = csrRoamIssueStopBss( pMac, sessionId, eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING );
+    }
+    else if ( csrIsConnStateConnectedInfra( pMac, sessionId ) ) 
+    {
+        // Disassociate from the connected Infrastructure network...
+        status = csrRoamIssueDisassociate( pMac, sessionId, eCSR_ROAM_SUBSTATE_DISCONNECT_CONTINUE_ROAMING, FALSE );
+    }
+    else
+    {
+#if defined(VOSS_ENABLED)
+        //We don't expect Bt-AMP HDD not to disconnect the last connection first at this time. 
+        //Otherwise we need to add code to handle the
+        //situation just like IBSS. Though for WDS station, we need to send disassoc to PE first then 
+        //send stop_bss to PE, before we can continue.
+        VOS_ASSERT( !csrIsConnStateWds( pMac, sessionId ) );
+#endif
+        palZeroMemory(pMac->hHdd, &bssConfig, sizeof(tBssConfigParam));
+        /* Assume HDD provide bssid in profile */
+        palCopyMemory( pMac->hHdd, &pSession->bssParams.bssid, pProfile->BSSIDs.bssid[0], sizeof(tCsrBssid) );
+        // there is no Bss description before we start an WDS so we need
+        // to adopt all Bss configuration parameters from the Profile.
+        status = csrRoamPrepareBssConfigFromProfile(pMac, pProfile, &bssConfig, pBssDesc);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            //Save profile for late use
+            csrFreeRoamProfile( pMac, sessionId );
+            if (HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, 
+                                   (void **)&pSession->pCurRoamProfile,
+                                   sizeof(tCsrRoamProfile))))
+            {
+                palZeroMemory(pMac->hHdd, pSession->pCurRoamProfile, sizeof(tCsrRoamProfile));
+                csrRoamCopyProfile(pMac, pSession->pCurRoamProfile, pProfile);
+            }
+
+            //Prepare some more parameters for this WDS
+            csrRoamPrepareBssParams(pMac, sessionId, pProfile, NULL, NULL);
+            status = csrRoamSetBssConfigCfg(pMac, sessionId, pProfile, NULL, &bssConfig, NULL);
+        }
+    }
+    
+    return( status );
+}
+
+
+////////////////////Mail box
+
+
+//pBuf is caller allocated memory point to &(tSirSmeJoinReq->rsnIE.rsnIEdata[ 0 ]) + pMsg->rsnIE.length;
+//or &(tSirSmeReassocReq->rsnIE.rsnIEdata[ 0 ]) + pMsg->rsnIE.length;
+static void csrPrepareJoinReassocReqBuffer( tpAniSirGlobal pMac, 
+                                            tSirBssDescription *pBssDescription, 
+                                            tANI_U8 *pBuf, tANI_U8 uapsdMask)
+{
+    tCsrChannelSet channelGroup;
+    tSirMacCapabilityInfo *pAP_capabilityInfo;
+    tAniBool fTmp;
+    tANI_BOOLEAN found = FALSE;
+    tANI_U32 size = 0;
+        tANI_U16 i;
+
+    // plug in neighborhood occupancy info (i.e. BSSes on primary or secondary channels)
+    *pBuf++ = (tANI_U8)FALSE;  //tAniTitanCBNeighborInfo->cbBssFoundPri
+    *pBuf++ = (tANI_U8)FALSE;  //tAniTitanCBNeighborInfo->cbBssFoundSecDown
+    *pBuf++ = (tANI_U8)FALSE;  //tAniTitanCBNeighborInfo->cbBssFoundSecUp
+
+    // 802.11h
+    //We can do this because it is in HOST CPU order for now.
+    pAP_capabilityInfo = (tSirMacCapabilityInfo *)&pBssDescription->capabilityInfo;
+
+        //tell the target AP my 11H capability only if both AP and STA support 11H and the channel being used is 11a
+        if ( csrIs11hSupported( pMac ) && pAP_capabilityInfo->spectrumMgt && eSIR_11A_NW_TYPE == pBssDescription->nwType )   
+        {  
+        fTmp = (tAniBool)pal_cpu_to_be32(1);
+    }
+    else
+        fTmp = (tAniBool)0;
+   
+    // corresponds to --- pMsg->spectrumMgtIndicator = ON;
+    palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&fTmp, sizeof(tAniBool) );
+    pBuf += sizeof(tAniBool);
+    *pBuf++ = MIN_STA_PWR_CAP_DBM; // it is for pMsg->powerCap.minTxPower = 0;
+        found = csrSearchChannelListForTxPower(pMac, pBssDescription, &channelGroup);
+
+    // This is required for 11k test VoWiFi Ent: Test 2.
+    // We need the power capabilities for Assoc Req. 
+    // This macro is provided by the halPhyCfg.h. We pick our
+    // max and min capability by the halPhy provided macros
+    *pBuf++ = MAX_STA_PWR_CAP_DBM;
+
+    size = sizeof(pMac->roam.validChannelList);
+    if(HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, (tANI_U8 *)pMac->roam.validChannelList, &size)))
+    { 
+        *pBuf++ = (tANI_U8)size;        //tSirSupChnl->numChnl        
+        for ( i = 0; i < size; i++) 
+        {
+            *pBuf++ = pMac->roam.validChannelList[ i ];   //tSirSupChnl->channelList[ i ]
+             
+        }
+    }
+    else
+    {
+        smsLog(pMac, LOGE, FL("can not find any valid channel\n"));
+        *pBuf++ = 0;  //tSirSupChnl->numChnl
+    }                                                                                                                     
+
+    //Check whether it is ok to enter UAPSD
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+    if( btcIsReadyForUapsd(pMac) )
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+    {
+       *pBuf++ = uapsdMask;
+    }
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+    else
+    {
+        smsLog(pMac, LOGE, FL(" BTC doesn't allow UAPSD for uapsd_mask(0x%X)\n"), uapsdMask);
+        *pBuf++ = 0;
+    }
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+  
+
+    // move the entire BssDescription into the join request.
+    palCopyMemory( pMac->hHdd, pBuf, pBssDescription, 
+                    pBssDescription->length + sizeof( pBssDescription->length ) );
+
+    pBuf += pBssDescription->length + sizeof( pBssDescription->length );   // update to new location
+}
+
+
+/* 
+  * The communication between HDD and LIM is thru mailbox (MB).
+  * Both sides will access the data structure "tSirSmeJoinReq".
+  *  The rule is, while the components of "tSirSmeJoinReq" can be accessed in the regular way like tSirSmeJoinReq.assocType, this guideline
+  *  stops at component tSirRSNie; any acces to the components after tSirRSNie is forbidden because the space from tSirRSNie is quueezed
+  *  with the component "tSirBssDescription". And since the size of actual 'tSirBssDescription' varies, the receiving side (which is the routine
+  *  limJoinReqSerDes() of limSerDesUtils.cc) should keep in mind not to access the components DIRECTLY after tSirRSNie.
+  */
+eHalStatus csrSendJoinReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirBssDescription *pBssDescription, 
+                              tCsrRoamProfile *pProfile, tDot11fBeaconIEs *pIes )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeJoinReq *pMsg;
+    tANI_U8 *pBuf;
+    tANI_U16 msgLen, wTmp, ieLen;
+    tSirMacRateSet OpRateSet;
+    tSirMacRateSet ExRateSet;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tANI_U32 dwTmp;
+    tANI_U8 wpaRsnIE[DOT11F_IE_RSN_MAX_LEN];    //RSN MAX is bigger than WPA MAX
+
+    do {
+        pSession->joinFailStatusCode.statusCode = eSIR_SME_SUCCESS;
+        pSession->joinFailStatusCode.reasonCode = 0;
+        // There are a number of variable length fields to consider.  First, the tSirSmeJoinReq
+        // includes a single bssDescription.   bssDescription includes a single tANI_U32 for the 
+        // IE fields, but the length field in the bssDescription needs to be interpreted to 
+        // determine length of the IE fields.
+        //
+        // So, take the size of the JoinReq, subtract the size of the bssDescription and 
+        // add in the length from the bssDescription (then add the size of the 'length' field
+        // itself because that is NOT included in the length field).
+        msgLen = sizeof( tSirSmeJoinReq ) - sizeof( *pBssDescription ) + 
+            pBssDescription->length + sizeof( pBssDescription->length ) +
+            sizeof( tCsrWpaIe ) + sizeof( tCsrWpaAuthIe ) + sizeof( tANI_U16 ); // add in the size of the WPA IE that we may build.
+
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, msgLen);
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_JOIN_REQ);
+        pMsg->length = pal_cpu_to_be16(msgLen);
+        pBuf = &pMsg->sessionId;
+
+        // sessionId
+        *pBuf = (tANI_U8)sessionId;
+        pBuf++;
+
+        // transactionId
+        *pBuf = 0;
+        *( pBuf + 1 ) = 0;
+        pBuf += sizeof(tANI_U16);
+
+        // ssId
+        if( pIes->SSID.present && pIes->SSID.num_ssid )
+        {
+            // ssId len
+            *pBuf = pIes->SSID.num_ssid;
+            pBuf++;
+            palCopyMemory( pMac->hHdd, pBuf, pIes->SSID.ssid, pIes->SSID.num_ssid );
+            pBuf += pIes->SSID.num_ssid;
+        }
+        else
+        {
+            *pBuf = 0;
+            pBuf++;
+        }
+
+        // selfMacAddr
+        palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, &pSession->selfMacAddr, sizeof(tSirMacAddr) );
+        pBuf += sizeof(tSirMacAddr);
+        // bsstype
+        dwTmp = pal_cpu_to_be32( csrTranslateBsstypeToMacType( pProfile->BSSType ) );
+        if (dwTmp == eSIR_BTAMP_STA_MODE) dwTmp = eSIR_BTAMP_AP_MODE; // Override BssType for BTAMP
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tSirBssType) );
+        pBuf += sizeof(tSirBssType);
+        // dot11mode
+        *pBuf = (tANI_U8)csrTranslateToWNICfgDot11Mode( pMac, pSession->bssParams.uCfgDot11Mode );
+        pBuf++;
+
+        //Persona
+        *pBuf = (tANI_U8)pProfile->csrPersona;
+        pBuf++;
+
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+                  FL("CSR PERSONA=%d"), pProfile->csrPersona);
+        
+        // uapsdPerAcBitmask
+        *pBuf = pProfile->uapsd_mask;
+        pBuf++;
+
+
+    
+#if (WNI_POLARIS_FW_PACKAGE == ADVANCED)        
+#endif /*(WNI_POLARIS_FW_PACKAGE == ADVANCED)*/
+
+        status = csrGetRateSet(pMac, pProfile, (eCsrPhyMode)pProfile->phyMode, pBssDescription, pIes, &OpRateSet, &ExRateSet);
+        if (HAL_STATUS_SUCCESS(status) ) 
+        {
+            // OperationalRateSet
+            if (OpRateSet.numRates) {
+                *pBuf++ = OpRateSet.numRates;
+                palCopyMemory(pMac->hHdd, pBuf, OpRateSet.rate, OpRateSet.numRates);
+                pBuf += OpRateSet.numRates;
+            } else *pBuf++ = 0;
+            // ExtendedRateSet
+            if (ExRateSet.numRates) {
+                *pBuf++ = ExRateSet.numRates;
+                palCopyMemory(pMac->hHdd, pBuf, ExRateSet.rate, ExRateSet.numRates);
+                pBuf += ExRateSet.numRates;
+            } else *pBuf++ = 0;
+        }
+        else
+        {
+            *pBuf++ = 0;
+            *pBuf++ = 0;
+        }
+
+        // rsnIE
+        if ( csrIsProfileWpa( pProfile ) )
+        {
+            // Insert the Wpa IE into the join request
+            ieLen = csrRetrieveWpaIe( pMac, pProfile, pBssDescription, pIes,
+                    (tCsrWpaIe *)( wpaRsnIE ) );
+        }
+        else if( csrIsProfileRSN( pProfile ) )
+        {
+            // Insert the RSN IE into the join request
+            ieLen = csrRetrieveRsnIe( pMac, sessionId, pProfile, pBssDescription, pIes,
+                    (tCsrRSNIe *)( wpaRsnIE ) );
+        }
+#ifdef FEATURE_WLAN_WAPI
+        else if( csrIsProfileWapi( pProfile ) )
+        {
+            // Insert the WAPI IE into the join request
+            ieLen = csrRetrieveWapiIe( pMac, sessionId, pProfile, pBssDescription, pIes,
+                    (tCsrWapiIe *)( wpaRsnIE ) );
+        }
+#endif /* FEATURE_WLAN_WAPI */
+
+        else
+        {
+            ieLen = 0;
+        }
+        //remember the IE for future use
+        if( ieLen )
+        {
+            if(ieLen > DOT11F_IE_RSN_MAX_LEN)
+            {
+                smsLog(pMac, LOGE, FL(" WPA RSN IE length :%d is more than DOT11F_IE_RSN_MAX_LEN, resetting to %d\n"), ieLen, DOT11F_IE_RSN_MAX_LEN);
+                ieLen = DOT11F_IE_RSN_MAX_LEN;
+            }
+#ifdef FEATURE_WLAN_WAPI
+            if( csrIsProfileWapi( pProfile ) )
+            {
+                //Check whether we need to allocate more memory
+                if(ieLen > pSession->nWapiReqIeLength)
+                {
+                    if(pSession->pWapiReqIE && pSession->nWapiReqIeLength)
+                    {
+                        palFreeMemory(pMac->hHdd, pSession->pWapiReqIE);
+                    }
+                    status = palAllocateMemory(pMac->hHdd, (void **)&pSession->pWapiReqIE, ieLen);
+                    if(!HAL_STATUS_SUCCESS(status)) break;
+                }
+                pSession->nWapiReqIeLength = ieLen;
+                palCopyMemory(pMac->hHdd, pSession->pWapiReqIE, wpaRsnIE, ieLen);
+                wTmp = pal_cpu_to_be16( ieLen );
+                palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+                pBuf += sizeof(tANI_U16);
+                palCopyMemory( pMac->hHdd, pBuf, wpaRsnIE, ieLen );
+                pBuf += ieLen;
+            }
+            else//should be WPA/WPA2 otherwise
+#endif /* FEATURE_WLAN_WAPI */
+            {
+                //Check whether we need to allocate more memory
+                if(ieLen > pSession->nWpaRsnReqIeLength)
+                {
+                    if(pSession->pWpaRsnReqIE && pSession->nWpaRsnReqIeLength)
+                    {
+                        palFreeMemory(pMac->hHdd, pSession->pWpaRsnReqIE);
+                    }
+                    status = palAllocateMemory(pMac->hHdd, (void **)&pSession->pWpaRsnReqIE, ieLen);
+                    if(!HAL_STATUS_SUCCESS(status)) break;
+                }
+                pSession->nWpaRsnReqIeLength = ieLen;
+                palCopyMemory(pMac->hHdd, pSession->pWpaRsnReqIE, wpaRsnIE, ieLen);
+                wTmp = pal_cpu_to_be16( ieLen );
+                palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+                pBuf += sizeof(tANI_U16);
+                palCopyMemory( pMac->hHdd, pBuf, wpaRsnIE, ieLen );
+                pBuf += ieLen;
+            }
+        }
+        else
+        {
+            //free whatever old info
+            pSession->nWpaRsnReqIeLength = 0;
+            if(pSession->pWpaRsnReqIE)
+            {
+                palFreeMemory(pMac->hHdd, pSession->pWpaRsnReqIE);
+                pSession->pWpaRsnReqIE = NULL;
+            }
+#ifdef FEATURE_WLAN_WAPI
+            pSession->nWapiReqIeLength = 0;
+            if(pSession->pWapiReqIE)
+            {
+                palFreeMemory(pMac->hHdd, pSession->pWapiReqIE);
+                pSession->pWapiReqIE = NULL;
+            }
+#endif /* FEATURE_WLAN_WAPI */
+            //length is two bytes
+            *pBuf = 0;
+            *(pBuf + 1) = 0;
+            pBuf += 2;
+        }
+
+#ifdef FEATURE_WLAN_CCX
+        // Never include the cckmIE in an Join Request
+        //length is two bytes
+        *pBuf = 0;
+        *(pBuf + 1) = 0;
+        pBuf += 2;
+#endif 
+
+        // addIEScan
+        if(pProfile->nAddIEScanLength && pProfile->pAddIEScan)
+        {
+            ieLen = pProfile->nAddIEScanLength;
+
+            if(ieLen > pSession->nAddIEScanLength)
+            {
+                if(pSession->pAddIEScan && pSession->nAddIEScanLength)
+        {
+                    palFreeMemory(pMac->hHdd, pSession->pAddIEScan);
+                }
+                status = palAllocateMemory(pMac->hHdd, 
+                                 (void **)&pSession->pAddIEScan, ieLen);
+                if(!HAL_STATUS_SUCCESS(status)) break;
+            }
+            pSession->nAddIEScanLength = ieLen;
+            palCopyMemory(pMac->hHdd, pSession->pAddIEScan, 
+                                      pProfile->pAddIEScan, ieLen);
+            wTmp = pal_cpu_to_be16( ieLen );
+            palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+            pBuf += sizeof(tANI_U16);
+            palCopyMemory( pMac->hHdd, pBuf, pProfile->pAddIEScan, ieLen );
+            pBuf += ieLen;
+        }
+        else
+        {
+            pSession->nAddIEScanLength = 0;
+            if(pSession->pAddIEScan)
+            {
+                palFreeMemory(pMac->hHdd, pSession->pAddIEScan);
+                pSession->pAddIEScan = NULL;
+            }
+            *pBuf = 0;
+            *(pBuf + 1) = 0;
+            pBuf += 2;
+        }
+
+        // addIEAssoc
+        if(pProfile->nAddIEAssocLength && pProfile->pAddIEAssoc)
+        {
+            ieLen = pProfile->nAddIEAssocLength;
+
+            if(ieLen > pSession->nAddIEAssocLength)
+            {
+                if(pSession->pAddIEAssoc && pSession->nAddIEAssocLength)
+                {
+                    palFreeMemory(pMac->hHdd, pSession->pAddIEAssoc);
+                }
+                status = palAllocateMemory(pMac->hHdd, 
+                                 (void **)&pSession->pAddIEAssoc, ieLen);
+                if(!HAL_STATUS_SUCCESS(status)) break;
+            }
+            pSession->nAddIEAssocLength = ieLen;
+            palCopyMemory(pMac->hHdd, pSession->pAddIEAssoc, 
+                                      pProfile->pAddIEAssoc, ieLen);
+            wTmp = pal_cpu_to_be16( ieLen );
+            palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+            pBuf += sizeof(tANI_U16);
+            palCopyMemory( pMac->hHdd, pBuf, pProfile->pAddIEAssoc, ieLen );
+            pBuf += ieLen;
+        }
+        else
+        {
+            pSession->nAddIEAssocLength = 0;
+            if(pSession->pAddIEAssoc)
+            {
+                palFreeMemory(pMac->hHdd, pSession->pAddIEAssoc);
+                pSession->pAddIEAssoc = NULL;
+            }
+            *pBuf = 0;
+            *(pBuf + 1) = 0;
+            pBuf += 2;
+        }
+
+        dwTmp = pal_cpu_to_be32( csrTranslateEncryptTypeToEdType( pProfile->negotiatedUCEncryptionType) );
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tANI_U32) );
+        pBuf += sizeof(tANI_U32);        
+
+        dwTmp = pal_cpu_to_be32( csrTranslateEncryptTypeToEdType( pProfile->negotiatedMCEncryptionType) );
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tANI_U32) );
+        pBuf += sizeof(tANI_U32);        
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        if (csrIsProfile11r( pProfile ) )
+        {
+            // is11Rconnection;
+            dwTmp = pal_cpu_to_be32(TRUE); 
+            palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+            pBuf += sizeof(tAniBool);        
+        }
+        else
+        {
+            // is11Rconnection;
+            dwTmp = pal_cpu_to_be32(FALSE); 
+            palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+            pBuf += sizeof(tAniBool);        
+        }
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+        /* A profile can not be both CCX and 11R. But an 802.11R AP
+         * may be advertising support for CCX as well. So if we are 
+         * associating Open or explicitly CCX then we will get CCX.
+         * If we are associating explictly 11R only then we will get
+         * 11R.
+         */
+        if ((csrIsProfileCCX(pProfile) || ((pIes->CCXVersion.present) && ((pProfile->negotiatedAuthType == eCSR_AUTH_TYPE_OPEN_SYSTEM) || (pProfile->negotiatedAuthType == eCSR_AUTH_TYPE_WPA)))) && (!(csrIsProfile11r( pProfile ))) && (pMac->roam.configParam.isCcxIniFeatureEnabled))
+        {
+            // isCCXconnection;
+            dwTmp = pal_cpu_to_be32(TRUE); 
+            palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+            pBuf += sizeof(tAniBool);        
+        }
+        else 
+        {
+            //isCCXconnection;
+            dwTmp = pal_cpu_to_be32(FALSE); 
+            palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+            pBuf += sizeof(tAniBool);        
+        }
+        {
+            tCCXTspecInfo ccxTspec;
+            // CCX-Tspec IEs in the ASSOC request is presently not supported
+            // so nullify the TSPEC parameters
+            palZeroMemory(pMac->hHdd, &ccxTspec, sizeof(tCCXTspecInfo));
+            palCopyMemory( pMac->hHdd, pBuf, &ccxTspec, sizeof(tCCXTspecInfo));
+            pBuf += sizeof(tCCXTspecInfo);
+        }
+#endif
+
+#if defined WLAN_FEATURE_VOWIFI_11R || defined FEATURE_WLAN_CCX
+        // Fill in isFastTransitionEnabled
+        if (pMac->roam.configParam.isFastTransitionEnabled)
+        {
+            dwTmp = pal_cpu_to_be32(TRUE); 
+            palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+            pBuf += sizeof(tAniBool);        
+        }
+        else
+        {
+            dwTmp = pal_cpu_to_be32(FALSE); 
+            palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+            pBuf += sizeof(tAniBool);        
+        }
+#endif
+
+        //BssDesc
+        csrPrepareJoinReassocReqBuffer( pMac, pBssDescription, pBuf, 
+                (tANI_U8)pProfile->uapsd_mask);
+
+        status = palSendMBMessage(pMac->hHdd, pMsg );    
+        if(!HAL_STATUS_SUCCESS(status)) 
+        {
+            break;
+        }
+        //Tush-QoS: notify QoS module that join happening
+        else
+        {
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+            sme_QosCsrEventInd(pMac, (v_U8_t)sessionId, SME_QOS_CSR_JOIN_REQ, NULL);
+#endif
+        }
+    } while( 0 );
+    return( status );
+}
+
+
+eHalStatus csrSendSmeReassocReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirBssDescription *pBssDescription, 
+                                    tDot11fBeaconIEs *pIes, tCsrRoamProfile *pProfile )
+{
+    eHalStatus status;
+    tSirSmeReassocReq *pMsg;
+    tANI_U8 *pBuf;
+    v_U8_t acm_mask = 0, uapsd_mask;
+    tANI_U16 msgLen, ieLen, wTmp;
+    tANI_U32 dwTmp;
+    tSirMacRateSet OpRateSet;
+    tSirMacRateSet ExRateSet;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tANI_U8 wpaRsnIE[DOT11F_IE_RSN_MAX_LEN];    //RSN MAX is bigger than WPA MAX
+
+    /* To satisfy klockworks */
+    if (pBssDescription == NULL)
+    {
+        smsLog(pMac, LOGE, FL(" pBssDescription is NULL\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    do {
+        // There are a number of variable length fields to consider.  First, the tSirSmeJoinReq
+        // includes a single bssDescription.   bssDescription includes a single tANI_U32 for the 
+        // IE fields, but the length field in the bssDescription needs to be interpreted to 
+        // determine length of the IE fields.
+        //
+        // So, take the size of the JoinReq, subtract the size of the bssDescription and 
+        // add in the length from the bssDescription (then add the size of the 'length' field
+        // itself because that is NOT included in the length field).
+        msgLen = sizeof( tSirSmeReassocReq ) - sizeof( *pBssDescription ) + 
+                 pBssDescription->length + sizeof( pBssDescription->length ) +
+                 sizeof( tCsrWpaIe ) + sizeof( tCsrWpaAuthIe ) + sizeof( tANI_U16 ); // add in the size of the WPA IE that we may build.
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);         
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, msgLen);
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_REASSOC_REQ);
+                pMsg->length = pal_cpu_to_be16(msgLen);
+        pBuf = &pMsg->sessionId;
+        // sessionId
+        *pBuf++ = (tANI_U8)sessionId;
+        // transactionId
+        *pBuf = 0;
+        *(pBuf + 1) = 0;
+        pBuf += sizeof (tANI_U16);
+        // ssId
+        if( pIes->SSID.present && pIes->SSID.num_ssid )
+        {
+            // ssId len
+            *pBuf++ = pIes->SSID.num_ssid;
+            palCopyMemory( pMac->hHdd, pBuf, pIes->SSID.ssid, pIes->SSID.num_ssid );
+            pBuf += pIes->SSID.num_ssid;
+        } 
+        else
+        {
+            *pBuf++ = 0;
+        }
+        // selfMacAddr
+        palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, &pSession->selfMacAddr, sizeof(tSirMacAddr) );
+        pBuf += sizeof(tSirMacAddr);
+        // bsstype
+        dwTmp = pal_cpu_to_be32( csrTranslateBsstypeToMacType( pProfile->BSSType ) );
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tSirBssType) );
+        pBuf += sizeof(tSirBssType);
+        // dot11mode
+        *pBuf = (tANI_U8)csrTranslateToWNICfgDot11Mode( pMac, pSession->bssParams.uCfgDot11Mode );
+        pBuf++;
+
+        //Persona
+        *pBuf = (tANI_U8)pProfile->csrPersona;
+        pBuf++;
+
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, FL("CSR PERSONA=%d\n"), pProfile->csrPersona);
+        
+        // uapsdPerAcBitmask
+        *pBuf = pProfile->uapsd_mask;
+        pBuf++;
+
+
+
+        status = csrGetRateSet(pMac, pProfile, (eCsrPhyMode)pProfile->phyMode, 
+                        pBssDescription, pIes, &OpRateSet, &ExRateSet);
+        if (HAL_STATUS_SUCCESS(status) ) 
+        {
+            // OperationalRateSet
+            if (OpRateSet.numRates) 
+            {
+                *pBuf++ = OpRateSet.numRates;
+                palCopyMemory(pMac->hHdd, pBuf, OpRateSet.rate, OpRateSet.numRates);
+                pBuf += OpRateSet.numRates;
+            } 
+            else *pBuf++ = 0;
+            // ExtendedRateSet
+            if (ExRateSet.numRates) 
+            {
+                *pBuf++ = ExRateSet.numRates;
+                palCopyMemory(pMac->hHdd, pBuf, ExRateSet.rate, ExRateSet.numRates);
+                pBuf += ExRateSet.numRates;
+            } 
+            else *pBuf++ = 0;
+        }
+        else
+        {
+            *pBuf++ = 0;
+            *pBuf++ = 0;
+        }
+
+                // rsnIE
+        if ( csrIsProfileWpa( pProfile ) )
+                {
+                    // Insert the Wpa IE into the join request
+            ieLen = csrRetrieveWpaIe( pMac, pProfile, pBssDescription, pIes,
+                                                   (tCsrWpaIe *)( wpaRsnIE ) );
+                }
+                else if( csrIsProfileRSN( pProfile ) )
+                {
+                    // Insert the RSN IE into the join request
+            ieLen = csrRetrieveRsnIe( pMac, sessionId, pProfile, pBssDescription, pIes,
+                                                    (tCsrRSNIe *)( wpaRsnIE ) );
+        }
+#ifdef FEATURE_WLAN_WAPI
+        else if( csrIsProfileWapi( pProfile ) )
+        {
+            // Insert the WAPI IE into the join request
+            ieLen = csrRetrieveWapiIe( pMac, sessionId, pProfile, pBssDescription, pIes,
+                                                (tCsrWapiIe *)( wpaRsnIE) );
+        }
+#endif /* FEATURE_WLAN_WAPI */
+        else
+        {
+            ieLen = 0;
+        }
+        //remember the IE for future use
+        if( ieLen )
+        {
+            if(ieLen > DOT11F_IE_RSN_MAX_LEN)
+             {
+                 smsLog(pMac, LOGE, FL(" WPA RSN IE length :%d is more than DOT11F_IE_RSN_MAX_LEN, resetting to %d\n"), ieLen, DOT11F_IE_RSN_MAX_LEN);
+                 ieLen = DOT11F_IE_RSN_MAX_LEN;
+             }
+
+            //Check whether we need to allocate more memory
+            if(ieLen > pSession->nWpaRsnReqIeLength)
+            {
+                if(pSession->pWpaRsnReqIE && pSession->nWpaRsnReqIeLength)
+                {
+                    palFreeMemory(pMac->hHdd, pSession->pWpaRsnReqIE);
+                }
+                status = palAllocateMemory(pMac->hHdd, (void **)&pSession->pWpaRsnReqIE, ieLen);
+                if(!HAL_STATUS_SUCCESS(status)) break;
+            }
+            pSession->nWpaRsnReqIeLength = ieLen;
+            palCopyMemory(pMac->hHdd, pSession->pWpaRsnReqIE, wpaRsnIE, ieLen);
+            wTmp = pal_cpu_to_be16( ieLen );
+            palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+            pBuf += sizeof(tANI_U16);
+            palCopyMemory( pMac->hHdd, pBuf, wpaRsnIE, ieLen );
+            pBuf += ieLen;
+                }
+                else
+                {
+            //free whatever old info
+            pSession->nWpaRsnReqIeLength = 0;
+            if(pSession->pWpaRsnReqIE)
+            {
+                palFreeMemory(pMac->hHdd, pSession->pWpaRsnReqIE);
+                pSession->pWpaRsnReqIE = NULL;
+            }
+            //length is two bytes
+            *pBuf = 0;
+            *(pBuf + 1) = 0;
+            pBuf += 2;
+                }
+
+#ifdef FEATURE_WLAN_CCX
+        // cckmIE
+        if( csrIsProfileCCX( pProfile ) )
+        {
+            // Insert the CCKM IE into the join request
+            ieLen = csrConstructCcxCckmIe( pMac, 
+                                          pSession, 
+                                          pProfile, 
+                                          pBssDescription, 
+                                          pSession->pWpaRsnReqIE, 
+                                          pSession->nWpaRsnReqIeLength,
+                                          (void *)( wpaRsnIE ) );
+        }
+        else
+        {
+            ieLen = 0;
+        }
+        //If present, copy the IE into the eWNI_SME_REASSOC_REQ message buffer
+        if( ieLen )
+        {
+            //Copy the CCKM IE over from the temp buffer (wpaRsnIE)
+            wTmp = pal_cpu_to_be16( ieLen );
+            palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+            pBuf += sizeof(tANI_U16);
+            palCopyMemory( pMac->hHdd, pBuf, wpaRsnIE, ieLen );
+            pBuf += ieLen;
+        }
+        else
+        {
+            //Indicate you have no CCKM IE
+            //length is two bytes
+            *pBuf = 0;
+            *(pBuf + 1) = 0;
+            pBuf += 2;
+        }
+#endif /* FEATURE_WLAN_CCX */
+
+        // addIEScan
+        if(pProfile->nAddIEScanLength && pProfile->pAddIEScan)
+        {
+            ieLen = pProfile->nAddIEScanLength;
+
+            if(ieLen > pSession->nAddIEScanLength)
+            {
+                if(pSession->pAddIEScan && pSession->nAddIEScanLength)
+                {
+                    palFreeMemory(pMac->hHdd, pSession->pAddIEScan);
+                }
+                status = palAllocateMemory(pMac->hHdd, 
+                                 (void **)&pSession->pAddIEScan, ieLen);
+                if(!HAL_STATUS_SUCCESS(status)) break;
+            }
+            pSession->nAddIEScanLength = ieLen;
+            palCopyMemory(pMac->hHdd, pSession->pAddIEScan, 
+                                      pProfile->pAddIEScan, ieLen);
+            wTmp = pal_cpu_to_be16( ieLen );
+            palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+            pBuf += sizeof(tANI_U16);
+            palCopyMemory( pMac->hHdd, pBuf, pProfile->pAddIEScan, ieLen );
+            pBuf += ieLen;
+        }
+        else
+        {
+            pSession->nAddIEScanLength = 0;
+            if(pSession->pAddIEScan)
+            {
+                palFreeMemory(pMac->hHdd, pSession->pAddIEScan);
+                pSession->pAddIEScan = NULL;
+            }
+            *pBuf = 0;
+            *(pBuf + 1) = 0;
+            pBuf += 2;
+        }
+
+        // addIEAssoc
+        if(pProfile->nAddIEAssocLength && pProfile->pAddIEAssoc)
+        {
+            ieLen = pProfile->nAddIEAssocLength;
+
+            if(ieLen > pSession->nAddIEAssocLength)
+            {
+                if(pSession->pAddIEAssoc && pSession->nAddIEAssocLength)
+        {
+                    palFreeMemory(pMac->hHdd, pSession->pAddIEAssoc);
+        }
+                status = palAllocateMemory(pMac->hHdd, 
+                                 (void **)&pSession->pAddIEAssoc, ieLen);
+                if(!HAL_STATUS_SUCCESS(status)) break;
+        }
+            pSession->nAddIEAssocLength = ieLen;
+            palCopyMemory(pMac->hHdd, pSession->pAddIEAssoc, 
+                                      pProfile->pAddIEAssoc, ieLen);
+            wTmp = pal_cpu_to_be16( ieLen );
+            palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+            pBuf += sizeof(tANI_U16);
+            palCopyMemory( pMac->hHdd, pBuf, pProfile->pAddIEAssoc, ieLen );
+            pBuf += ieLen;
+        }
+        else
+        {
+            pSession->nAddIEAssocLength = 0;
+            if(pSession->pAddIEAssoc)
+            {
+                palFreeMemory(pMac->hHdd, pSession->pAddIEAssoc);
+                pSession->pAddIEAssoc = NULL;
+            }
+            *pBuf = 0;
+            *(pBuf + 1) = 0;
+            pBuf += 2;
+        }
+
+        //Unmask any AC in reassoc that is ACM-set
+        uapsd_mask = (v_U8_t)pProfile->uapsd_mask;
+        if( uapsd_mask && ( NULL != pBssDescription ) )
+        {
+            if( CSR_IS_QOS_BSS(pIes) && CSR_IS_UAPSD_BSS(pIes) )
+            {
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                acm_mask = sme_QosGetACMMask(pMac, pBssDescription, pIes);
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+                uapsd_mask &= ~(acm_mask);
+            }
+            else
+            {
+                uapsd_mask = 0;
+            }
+        }
+        
+        dwTmp = pal_cpu_to_be32( csrTranslateEncryptTypeToEdType( pProfile->negotiatedUCEncryptionType) );
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tANI_U32) );
+        pBuf += sizeof(tANI_U32);        
+        
+        dwTmp = pal_cpu_to_be32( csrTranslateEncryptTypeToEdType( pProfile->negotiatedMCEncryptionType) );
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tANI_U32) );
+        pBuf += sizeof(tANI_U32);        
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        // is11Rconnection;
+        dwTmp = csrIsProfile11r( pProfile )?  pal_cpu_to_be32(TRUE) : 0; 
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+        pBuf += sizeof(tAniBool);        
+
+#ifdef FEATURE_WLAN_CCX
+        //isCCXconnection;
+        //CCKM profile, ccxversion ie present, not 11r and ini file has CCX enabled
+        dwTmp = ((csrIsProfileCCX(pProfile) || ((pIes->CCXVersion.present) && ((pProfile->negotiatedAuthType == eCSR_AUTH_TYPE_OPEN_SYSTEM) || (pProfile->negotiatedAuthType == eCSR_AUTH_TYPE_WPA)))) && (!(csrIsProfile11r( pProfile ))) && (pMac->roam.configParam.isCcxIniFeatureEnabled)) ? pal_cpu_to_be32(TRUE) : 0;
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+        pBuf += sizeof(tAniBool);        
+#endif // FEATURE_WLAN_CCX
+#endif // WLAN_FEATURE_VOWIFI_11R
+
+#ifdef FEATURE_WLAN_CCX
+        if ((csrIsProfileCCX(pProfile) || ((pIes->CCXVersion.present) && ((pProfile->negotiatedAuthType == eCSR_AUTH_TYPE_OPEN_SYSTEM) || (pProfile->negotiatedAuthType == eCSR_AUTH_TYPE_WPA)))) && (!(csrIsProfile11r( pProfile ))) && (pMac->roam.configParam.isCcxIniFeatureEnabled))
+        {
+           tCCXTspecInfo ccxTspec;
+
+           // CCX Tspec information
+           palZeroMemory(pMac->hHdd, &ccxTspec, sizeof(tCCXTspecInfo));
+           ccxTspec.numTspecs = sme_QosCCxRetrieveTspecInfo(pMac, sessionId, (tTspecInfo *) &ccxTspec.tspec[0]);
+           *pBuf = ccxTspec.numTspecs;
+           pBuf += sizeof(tANI_U8);
+
+           // Copy the TSPEC information only if present
+           if (ccxTspec.numTspecs) {
+               palCopyMemory(pMac->hHdd, pBuf, (void*)&ccxTspec.tspec[0], (ccxTspec.numTspecs*sizeof(tTspecInfo)));
+           }
+           pBuf += sizeof(ccxTspec.tspec);
+        }
+        else 
+        {
+            {
+                tCCXTspecInfo ccxTspec;
+                // CCX-Tspec IEs in the ASSOC request is presently not supported
+                // so nullify the TSPEC parameters
+                palZeroMemory(pMac->hHdd, &ccxTspec, sizeof(tCCXTspecInfo));
+                palCopyMemory( pMac->hHdd, pBuf, &ccxTspec, sizeof(tCCXTspecInfo));
+                pBuf += sizeof(tCCXTspecInfo);
+            }
+        }
+#endif // FEATURE_WLAN_CCX
+
+#if defined WLAN_FEATURE_VOWIFI_11R || defined FEATURE_WLAN_CCX
+        // Fill in isFastTransitionEnabled
+        if (pMac->roam.configParam.isFastTransitionEnabled)
+        {
+            dwTmp = pal_cpu_to_be32(TRUE); 
+            palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+            pBuf += sizeof(tAniBool);        
+        }
+        else
+        {
+            dwTmp = pal_cpu_to_be32(FALSE); 
+            palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tAniBool) );
+            pBuf += sizeof(tAniBool);        
+        }
+#endif
+
+        csrPrepareJoinReassocReqBuffer( pMac, pBssDescription, pBuf, uapsd_mask);
+        
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+        //Tush-QoS: notify QoS module that reassoc happening
+        sme_QosCsrEventInd(pMac, (v_U8_t)sessionId, SME_QOS_CSR_REASSOC_REQ, NULL);
+#endif
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+    } while( 0 );
+
+    return( status );
+
+}
+
+
+//
+eHalStatus csrSendMBDisassocReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirMacAddr bssId, tANI_U16 reasonCode )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeDisassocReq *pMsg;
+    tANI_U8 *pBuf;
+    tANI_U16 wTmp;
+#ifdef WLAN_SOFTAP_FEATURE
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    if (!CSR_IS_SESSION_VALID( pMac, sessionId ))
+        return eHAL_STATUS_FAILURE;
+#endif
+
+    do {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof( tSirSmeDisassocReq ));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeDisassocReq ));
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_DISASSOC_REQ);
+        pMsg->length = pal_cpu_to_be16((tANI_U16)sizeof( tSirSmeDisassocReq ));
+
+        pBuf = &pMsg->sessionId;
+        // sessionId
+        *pBuf++ = (tANI_U8)sessionId;
+        // transactionId
+        *pBuf = 0;
+        *( pBuf + 1 ) = 0;
+        pBuf += sizeof(tANI_U16);
+     
+#ifdef WLAN_SOFTAP_FEATURE        
+        if ( (pSession->pCurRoamProfile != NULL ) && 
+             ( reasonCode == eSIR_MAC_UNSPEC_FAILURE_REASON ) && 
+             ((CSR_IS_INFRA_AP(pSession->pCurRoamProfile)) || (CSR_IS_WDS_AP(pSession->pCurRoamProfile))))
+        {
+            // Set the bssid address before sending the message to LIM
+            status = palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, pSession->selfMacAddr, sizeof( tSirMacAddr ) );
+            pBuf = pBuf + sizeof ( tSirMacAddr );
+
+            // Set the peer MAC address before sending the message to LIM
+            status = palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, bssId, sizeof( tSirMacAddr ) ); //perMacAddr is passed as bssId for softAP
+            pBuf = pBuf + sizeof ( tSirMacAddr );
+        }
+        else
+        {
+#endif
+            // Set the peer MAC address before sending the message to LIM
+            status = palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, bssId, sizeof( tSirMacAddr ) );
+            pBuf = pBuf + sizeof ( tSirMacAddr );
+
+            status = palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, bssId, sizeof( pMsg->bssId ) );
+            pBuf = pBuf + sizeof ( tSirMacAddr );
+#ifdef WLAN_SOFTAP_FEATURE
+        }
+#endif
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }
+
+        // reasonCode
+        wTmp = pal_cpu_to_be16(reasonCode);
+        status = palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }
+        pBuf += sizeof(tANI_U16);
+
+        /* The state will be DISASSOC_HANDOFF only when we are doing handoff. 
+                    Here we should not send the disassoc over the air to the AP */
+        if ( CSR_IS_ROAM_SUBSTATE_DISASSOC_HO(pMac, sessionId)
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                && csrRoamIs11rAssoc(pMac)
+#endif
+           )            
+        {
+            *pBuf = CSR_DONT_SEND_DISASSOC_OVER_THE_AIR;  /* Set DoNotSendOverTheAir flag to 1 only for handoff case */
+        }
+        pBuf += sizeof(tANI_U8);
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+
+    } while( 0 );
+
+    return( status );
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+eHalStatus csrSendMBTkipCounterMeasuresReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_BOOLEAN bEnable, tSirMacAddr bssId )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeTkipCntrMeasReq *pMsg;
+    tANI_U8 *pBuf;
+
+    do
+    {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof( tSirSmeTkipCntrMeasReq ));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeTkipCntrMeasReq ));
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_TKIP_CNTR_MEAS_REQ);
+        pMsg->length = pal_cpu_to_be16((tANI_U16)sizeof( tSirSmeTkipCntrMeasReq ));
+
+        pBuf = &pMsg->sessionId;
+        // sessionId
+        *pBuf++ = (tANI_U8)sessionId;
+        // transactionId
+        *pBuf = 0;
+        *( pBuf + 1 ) = 0;
+        pBuf += sizeof(tANI_U16);
+        // bssid
+        status = palCopyMemory( pMac->hHdd, pMsg->bssId, bssId, sizeof( tSirMacAddr ) );
+        pBuf = pBuf + sizeof ( tSirMacAddr );
+        // bEnable
+        *pBuf = (tANI_BOOLEAN)bEnable;
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }
+
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+
+    } while( 0 );
+
+    return( status );
+}
+
+eHalStatus
+csrSendMBGetAssociatedStasReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                    VOS_MODULE_ID modId, tSirMacAddr bssId,
+                                    void *pUsrContext, void *pfnSapEventCallback,
+                                    tANI_U8 *pAssocStasBuf )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeGetAssocSTAsReq *pMsg;
+    tANI_U8 *pBuf = NULL, *wTmpBuf = NULL;
+    tANI_U32 dwTmp;
+
+    do
+    {
+        status = palAllocateMemory( pMac->hHdd, (void **)&pMsg, sizeof( tSirSmeGetAssocSTAsReq ) );
+        if (!HAL_STATUS_SUCCESS(status)) break;
+        palZeroMemory( pMac->hHdd, pMsg, sizeof( tSirSmeGetAssocSTAsReq ) );
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_GET_ASSOC_STAS_REQ);
+
+        pBuf = (tANI_U8 *)&pMsg->bssId;
+        wTmpBuf = pBuf;
+
+        // bssId
+        palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, bssId, sizeof(tSirMacAddr) );
+        pBuf += sizeof(tSirMacAddr);
+
+        // modId 
+        dwTmp = pal_cpu_to_be16((tANI_U16)modId);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&dwTmp, sizeof(tANI_U16));
+        pBuf += sizeof(tANI_U16);
+
+        // pUsrContext
+        dwTmp = pal_cpu_to_be32((tANI_U32)pUsrContext);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&dwTmp, sizeof(tANI_U32));
+        pBuf += sizeof(tANI_U32);
+
+        // pfnSapEventCallback
+        dwTmp = pal_cpu_to_be32((tANI_U32)pfnSapEventCallback);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&dwTmp, sizeof(tANI_U32));
+        pBuf += sizeof(tANI_U32);
+
+        // pAssocStasBuf
+        dwTmp = pal_cpu_to_be32((tANI_U32)pAssocStasBuf);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&dwTmp, sizeof(tANI_U32));
+        pBuf += sizeof(tANI_U32);
+
+        pMsg->length = pal_cpu_to_be16((tANI_U16)(sizeof(tANI_U32 ) + (pBuf - wTmpBuf)));//msg_header + msg
+
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+    } while( 0 );
+
+    return( status );
+        }
+
+eHalStatus
+csrSendMBGetWPSPBCSessions( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                            tSirMacAddr bssId, void *pUsrContext, void *pfnSapEventCallback,v_MACADDR_t pRemoveMac)
+        {
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeGetWPSPBCSessionsReq *pMsg;
+    tANI_U8 *pBuf = NULL, *wTmpBuf = NULL;
+    tANI_U32 dwTmp;
+
+    do
+        {
+        status = palAllocateMemory( pMac->hHdd, (void **)&pMsg, sizeof(tSirSmeGetWPSPBCSessionsReq) );
+        if (!HAL_STATUS_SUCCESS(status)) break;
+        palZeroMemory( pMac->hHdd, pMsg, sizeof( tSirSmeGetWPSPBCSessionsReq ) );
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_GET_WPSPBC_SESSION_REQ);
+
+        pBuf = (tANI_U8 *)&pMsg->pUsrContext;
+        wTmpBuf = pBuf;
+
+        // pUsrContext
+        dwTmp = pal_cpu_to_be32((tANI_U32)pUsrContext);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&dwTmp, sizeof(tANI_U32));
+        pBuf += sizeof(tANI_U32);
+
+        // pSapEventCallback
+        dwTmp = pal_cpu_to_be32((tANI_U32)pfnSapEventCallback);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&dwTmp, sizeof(tANI_U32));
+        pBuf += sizeof(tANI_U32);
+
+        // bssId
+        palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, bssId, sizeof(tSirMacAddr) );
+        pBuf += sizeof(tSirMacAddr);
+
+        // MAC Address of STA in WPS session
+        palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, pRemoveMac.bytes, sizeof(v_MACADDR_t));
+        pBuf += sizeof(v_MACADDR_t);
+
+        pMsg->length = pal_cpu_to_be16((tANI_U16)(sizeof(tANI_U32 ) + (pBuf - wTmpBuf)));//msg_header + msg
+
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+
+    } while( 0 );
+
+    return( status );
+}
+#endif
+
+eHalStatus csrSendMBDeauthReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirMacAddr bssId, tANI_U16 reasonCode )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeDeauthReq *pMsg;
+    tANI_U8 *pBuf;
+    tANI_U16 wTmp;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    if (!CSR_IS_SESSION_VALID( pMac, sessionId ))
+        return eHAL_STATUS_FAILURE;
+
+    do {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof( tSirSmeDeauthReq ));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeDeauthReq ));
+                pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_DEAUTH_REQ);
+                pMsg->length = pal_cpu_to_be16((tANI_U16)sizeof( tSirSmeDeauthReq ));
+        //sessionId
+        pBuf = &pMsg->sessionId;
+        *pBuf++ = (tANI_U8)sessionId;
+        
+        //tansactionId
+        *pBuf = 0;
+        *(pBuf + 1 ) = 0;
+        pBuf += sizeof(tANI_U16);
+
+        if ((pSession->pCurRoamProfile != NULL)  && (
+#ifdef WLAN_SOFTAP_FEATURE
+             (CSR_IS_INFRA_AP(pSession->pCurRoamProfile)) || 
+#endif
+             (CSR_IS_WDS_AP(pSession->pCurRoamProfile)))){ 
+            // Set the BSSID before sending the message to LIM
+            status = palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, pSession->selfMacAddr, sizeof( pMsg->peerMacAddr ) );
+            pBuf =  pBuf + sizeof(tSirMacAddr);
+        }
+        else
+        {
+            // Set the BSSID before sending the message to LIM
+            status = palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, bssId, sizeof( pMsg->peerMacAddr ) );
+            pBuf =  pBuf + sizeof(tSirMacAddr);
+
+        }
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }     
+                // Set the peer MAC address before sending the message to LIM
+        status = palCopyMemory( pMac->hHdd, (tSirMacAddr *) pBuf, bssId, sizeof( pMsg->peerMacAddr ) );
+        pBuf =  pBuf + sizeof(tSirMacAddr);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }     
+        wTmp = pal_cpu_to_be16(reasonCode);
+        status = palCopyMemory( pMac->hHdd, pBuf, &wTmp,sizeof( tANI_U16 ) );
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+
+    } while( 0 );
+
+    return( status );
+}
+
+
+eHalStatus csrSendMBDisassocCnfMsg( tpAniSirGlobal pMac, tpSirSmeDisassocInd pDisassocInd )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeDisassocCnf *pMsg;
+
+    do {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof( tSirSmeDisassocCnf ));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeDisassocCnf ));
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_DISASSOC_CNF);
+        pMsg->statusCode = (tSirResultCodes)pal_cpu_to_be32(eSIR_SME_SUCCESS);
+        pMsg->length = pal_cpu_to_be16((tANI_U16)sizeof( tSirSmeDisassocCnf ));
+        status = palCopyMemory(pMac->hHdd, pMsg->peerMacAddr, pDisassocInd->peerMacAddr, sizeof(pMsg->peerMacAddr)); 
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }
+//To test reconn        
+        status = palCopyMemory(pMac->hHdd, pMsg->bssId, pDisassocInd->bssId, sizeof(pMsg->peerMacAddr)); 
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }
+//To test reconn ends
+
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+
+    } while( 0 );
+
+    return( status );
+}
+
+
+eHalStatus csrSendMBDeauthCnfMsg( tpAniSirGlobal pMac, tpSirSmeDeauthInd pDeauthInd )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeDeauthCnf *pMsg;
+
+    do {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof( tSirSmeDeauthCnf ));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeDeauthCnf ));
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_DEAUTH_CNF);
+        pMsg->statusCode = (tSirResultCodes)pal_cpu_to_be32(eSIR_SME_SUCCESS);
+        pMsg->length = pal_cpu_to_be16((tANI_U16)sizeof( tSirSmeDeauthCnf ));
+        status = palCopyMemory(pMac->hHdd, pMsg->bssId, pDeauthInd->bssId, sizeof(pMsg->bssId)); 
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }
+        status = palCopyMemory(pMac->hHdd, pMsg->peerMacAddr, pDeauthInd->peerMacAddr, sizeof(pMsg->peerMacAddr)); 
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            palFreeMemory(pMac->hHdd, pMsg);
+            break;
+        }
+
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+
+    } while( 0 );
+
+    return( status );
+}
+
+eHalStatus csrSendAssocCnfMsg( tpAniSirGlobal pMac, tpSirSmeAssocInd pAssocInd, eHalStatus Halstatus )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeAssocCnf *pMsg;
+    tANI_U8 *pBuf;
+    tSirResultCodes statusCode;
+    tANI_U16 wTmp;
+
+    do {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof( tSirSmeAssocCnf ));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeAssocCnf ));
+                pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_ASSOC_CNF);
+                pMsg->length = pal_cpu_to_be16((tANI_U16)sizeof( tSirSmeAssocCnf ));
+
+        pBuf = (tANI_U8 *)&pMsg->statusCode;
+        if(HAL_STATUS_SUCCESS(Halstatus))
+            statusCode = (tSirResultCodes)pal_cpu_to_be32(eSIR_SME_SUCCESS);
+        else
+            statusCode = (tSirResultCodes)pal_cpu_to_be32(eSIR_SME_ASSOC_REFUSED);
+        palCopyMemory( pMac->hHdd, pBuf, &statusCode, sizeof(tSirResultCodes) );
+        pBuf += sizeof(tSirResultCodes);
+        // bssId
+        status = palCopyMemory(pMac->hHdd, (tSirMacAddr *)pBuf, pAssocInd->bssId, sizeof(tSirMacAddr));
+        pBuf += sizeof (tSirMacAddr);
+        // peerMacAddr
+        status = palCopyMemory(pMac->hHdd, (tSirMacAddr *)pBuf, pAssocInd->peerMacAddr, sizeof(tSirMacAddr)); 
+        pBuf += sizeof (tSirMacAddr);
+        // aid
+        wTmp = pal_cpu_to_be16(pAssocInd->aid);
+        palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+        pBuf += sizeof (tANI_U16);
+        // alternateBssId
+        status = palCopyMemory(pMac->hHdd, (tSirMacAddr *)pBuf, pAssocInd->bssId, sizeof(tSirMacAddr));
+        pBuf += sizeof (tSirMacAddr);
+        // alternateChannelId
+        *pBuf = 11;
+
+        status = palSendMBMessage( pMac->hHdd, pMsg );
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            //pMsg is freed by palSendMBMessage
+            break;
+        }
+
+    } while( 0 );
+
+    return( status );
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+eHalStatus csrSendAssocIndToUpperLayerCnfMsg(   tpAniSirGlobal pMac, 
+                                                tpSirSmeAssocInd pAssocInd, 
+                                                eHalStatus Halstatus, 
+                                                tANI_U8 sessionId)
+{
+    tSirMsgQ            msgQ;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeAssocIndToUpperLayerCnf *pMsg;
+    tANI_U8 *pBuf;
+    tSirResultCodes statusCode;
+    tANI_U16 wTmp;
+
+    do {
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof( tSirSmeAssocIndToUpperLayerCnf ));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeAssocIndToUpperLayerCnf ));
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_UPPER_LAYER_ASSOC_CNF);
+        pMsg->length = pal_cpu_to_be16((tANI_U16)sizeof( tSirSmeAssocIndToUpperLayerCnf ));
+
+        pMsg->sessionId = sessionId;
+
+        pBuf = (tANI_U8 *)&pMsg->statusCode;
+        if(HAL_STATUS_SUCCESS(Halstatus))
+            statusCode = (tSirResultCodes)pal_cpu_to_be32(eSIR_SME_SUCCESS);
+        else
+            statusCode = (tSirResultCodes)pal_cpu_to_be32(eSIR_SME_ASSOC_REFUSED);
+        palCopyMemory( pMac->hHdd, pBuf, &statusCode, sizeof(tSirResultCodes) );
+        pBuf += sizeof(tSirResultCodes);
+        // bssId
+        status = palCopyMemory(pMac->hHdd, (tSirMacAddr *)pBuf, pAssocInd->bssId, sizeof(tSirMacAddr));
+        pBuf += sizeof (tSirMacAddr);
+        // peerMacAddr
+        status = palCopyMemory(pMac->hHdd, (tSirMacAddr *)pBuf, pAssocInd->peerMacAddr, sizeof(tSirMacAddr)); 
+        pBuf += sizeof (tSirMacAddr);
+        // StaId
+        wTmp = pal_cpu_to_be16(pAssocInd->staId);
+        palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+        pBuf += sizeof (tANI_U16);
+        // alternateBssId
+        status = palCopyMemory(pMac->hHdd, (tSirMacAddr *)pBuf, pAssocInd->bssId, sizeof(tSirMacAddr));
+        pBuf += sizeof (tSirMacAddr);
+        // alternateChannelId
+        *pBuf = 11;
+        pBuf += sizeof (tANI_U8);
+
+        // Instead of copying roam Info, we just copy only WmmEnabled , RsnIE information
+        //Wmm
+        *pBuf = pAssocInd->wmmEnabledSta;
+        pBuf += sizeof (tANI_U8);
+
+        //RSN IE
+        status = palCopyMemory(pMac->hHdd, (tSirRSNie *)pBuf, &pAssocInd->rsnIE, sizeof(tSirRSNie));
+        pBuf += sizeof (tSirRSNie);
+
+        //Additional IE
+        status = palCopyMemory(pMac->hHdd, (void *)pBuf, &pAssocInd->addIE, sizeof(tSirAddie));
+        pBuf += sizeof (tSirAddie);
+
+        //reassocReq
+        *pBuf = pAssocInd->reassocReq;
+        pBuf += sizeof (tANI_U8);
+
+        msgQ.type = eWNI_SME_UPPER_LAYER_ASSOC_CNF;
+        msgQ.bodyptr = pMsg;
+        msgQ.bodyval = 0;
+
+        SysProcessMmhMsg(pMac, &msgQ);
+
+    } while( 0 );
+
+    return( status );
+}
+#endif
+
+
+eHalStatus csrSendMBSetContextReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId ,
+            tSirMacAddr peerMacAddr, tANI_U8 numKeys, tAniEdType edType, 
+            tANI_BOOLEAN fUnicast, tAniKeyDirection aniKeyDirection,
+            tANI_U8 keyId, tANI_U8 keyLength, tANI_U8 *pKey, tANI_U8 paeRole, 
+            tANI_U8 *pKeyRsc )
+{
+    tSirSmeSetContextReq *pMsg;
+    tANI_U16 msgLen;
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tAniEdType tmpEdType;
+    tAniKeyDirection tmpDirection;
+    tANI_U8 *pBuf;
+    tANI_U8 *p;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    do {
+
+        if( ( 1 != numKeys ) && ( 0 != numKeys ) ) break;
+
+        // all of these fields appear in every SET_CONTEXT message.  Below we'll add in the size for each 
+        // key set. Since we only support upto one key, we always allocate memory for 1 key
+        msgLen  = sizeof( tANI_U16) + sizeof( tANI_U16 ) + sizeof( tSirMacAddr ) +
+                  sizeof( tSirMacAddr ) + 1 + sizeof(tANI_U16) +
+                  sizeof( pMsg->keyMaterial.length ) + sizeof( pMsg->keyMaterial.edType ) + sizeof( pMsg->keyMaterial.numKeys ) +
+                  ( sizeof( pMsg->keyMaterial.key ) );
+                     
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, msgLen);
+                pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_SETCONTEXT_REQ);
+                pMsg->length = pal_cpu_to_be16(msgLen);
+
+        //sessionId
+        pBuf = &pMsg->sessionId;
+        *pBuf = (tANI_U8)sessionId;
+        pBuf++;
+        // transactionId
+        *pBuf = 0;
+        *(pBuf + 1) = 0;
+        pBuf += sizeof(tANI_U16);
+        // peerMacAddr
+        palCopyMemory( pMac->hHdd, pBuf, 
+             (tANI_U8 *)peerMacAddr, sizeof(tSirMacAddr) );
+
+        pBuf += sizeof(tSirMacAddr);
+
+        // bssId
+        palCopyMemory( pMac->hHdd, pBuf, 
+            (tANI_U8 *)&pSession->connectedProfile.bssid, sizeof(tSirMacAddr) );
+
+        pBuf += sizeof(tSirMacAddr);
+
+        p = pBuf;
+
+                // Set the pMsg->keyMaterial.length field (this length is defined as all data that follows the edType field
+                // in the tSirKeyMaterial keyMaterial; field).
+                //
+                // !!NOTE:  This keyMaterial.length contains the length of a MAX size key, though the keyLength can be 
+                // shorter than this max size.  Is LIM interpreting this ok ?
+                p = pal_set_U16( p, pal_cpu_to_be16((tANI_U16)( sizeof( pMsg->keyMaterial.numKeys ) + ( numKeys * sizeof( pMsg->keyMaterial.key ) ) )) );
+
+                // set pMsg->keyMaterial.edType
+        tmpEdType = (tAniEdType)pal_cpu_to_be32(edType);
+        palCopyMemory( pMac->hHdd, p, (tANI_U8 *)&tmpEdType, sizeof(tAniEdType) );
+        p += sizeof( pMsg->keyMaterial.edType );
+
+        // set the pMsg->keyMaterial.numKeys field
+        *p = numKeys;
+        p += sizeof( pMsg->keyMaterial.numKeys );   
+
+        // set pSirKey->keyId = keyId;
+        *p = keyId;
+        p += sizeof( pMsg->keyMaterial.key[ 0 ].keyId );
+
+        // set pSirKey->unicast = (tANI_U8)fUnicast;
+        *p = (tANI_U8)fUnicast;
+        p += sizeof( pMsg->keyMaterial.key[ 0 ].unicast );
+
+                // set pSirKey->keyDirection = aniKeyDirection;
+        tmpDirection = (tAniKeyDirection)pal_cpu_to_be32(aniKeyDirection);
+        palCopyMemory( pMac->hHdd, p, (tANI_U8 *)&tmpDirection, sizeof(tAniKeyDirection) );
+        p += sizeof(tAniKeyDirection);
+        //    pSirKey->keyRsc = ;;
+        palCopyMemory( pMac->hHdd, p, pKeyRsc, CSR_MAX_RSC_LEN );
+        p += sizeof( pMsg->keyMaterial.key[ 0 ].keyRsc );
+
+                // set pSirKey->paeRole
+                *p = paeRole;   // 0 is Supplicant
+                p++;
+
+                // set pSirKey->keyLength = keyLength;
+                p = pal_set_U16( p, pal_cpu_to_be16(keyLength) );
+
+        if ( keyLength && pKey ) 
+        {   
+            palCopyMemory( pMac->hHdd, p, pKey, keyLength ); 
+            if(keyLength == 16)
+            {
+                smsLog(pMac, LOGE, "  SME Set keyIdx (%d) encType(%d) key = %02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X\n",
+                keyId, edType, pKey[0], pKey[1], pKey[2], pKey[3], pKey[4],
+                pKey[5], pKey[6], pKey[7], pKey[8],
+                pKey[9], pKey[10], pKey[11], pKey[12], pKey[13], pKey[14], pKey[15]);
+            }
+        }
+
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+
+    } while( 0 );
+
+    return( status );
+}
+
+
+
+eHalStatus csrSendMBStartBssReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamBssType bssType, 
+                                    tCsrRoamStartBssParams *pParam, tSirBssDescription *pBssDesc )
+{
+    eHalStatus status;
+    tSirSmeStartBssReq *pMsg;
+    tANI_U8 *pBuf = NULL;
+    tANI_U8  *wTmpBuf  = NULL;
+    tANI_U16 msgLen, wTmp;
+    tANI_U32 dwTmp;
+    tSirNwType nwType;
+    tAniCBSecondaryMode cbMode;
+#ifdef WLAN_SOFTAP_FEATURE
+    tANI_U32 authType;
+#endif
+
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    do {
+        pSession->joinFailStatusCode.statusCode = eSIR_SME_SUCCESS;
+        pSession->joinFailStatusCode.reasonCode = 0;
+        msgLen = sizeof(tSirSmeStartBssReq);
+        status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+
+        palZeroMemory(pMac->hHdd, pMsg, msgLen);
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_START_BSS_REQ);
+
+        pBuf = &pMsg->sessionId;
+
+        wTmpBuf = pBuf;
+
+        //sessionId
+        *pBuf = (tANI_U8)sessionId;
+        pBuf++;
+        // transactionId
+        *pBuf = 0;
+        *(pBuf + 1) = 0;
+        pBuf += sizeof(tANI_U16);
+
+        // bssid 
+        palCopyMemory( pMac->hHdd, pBuf, pParam->bssid, sizeof(tSirMacAddr) );
+        pBuf += sizeof(tSirMacAddr);
+        // selfMacAddr
+        palCopyMemory( pMac->hHdd, pBuf, pSession->selfMacAddr, sizeof(tSirMacAddr) );
+        pBuf += sizeof(tSirMacAddr);
+        // beaconInterval
+        if( pBssDesc && pBssDesc->beaconInterval )
+        {
+            wTmp = pal_cpu_to_be16( pBssDesc->beaconInterval );
+        }
+#ifdef WLAN_SOFTAP_FEATURE
+        else if(pParam->beaconInterval)
+        {
+            wTmp = pal_cpu_to_be16( pParam->beaconInterval );
+        }
+#endif
+        else
+        {
+            wTmp = pal_cpu_to_be16( WNI_CFG_BEACON_INTERVAL_STADEF );
+        }
+        palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof( tANI_U16 ) ); 
+        pBuf += sizeof(tANI_U16);
+        // dot11mode
+        *pBuf = (tANI_U8)csrTranslateToWNICfgDot11Mode( pMac, pParam->uCfgDot11Mode );
+        pBuf += 1;
+        // bssType
+        dwTmp = pal_cpu_to_be32( csrTranslateBsstypeToMacType( bssType ) );
+        palCopyMemory( pMac->hHdd, pBuf, &dwTmp, sizeof(tSirBssType) );
+        pBuf += sizeof(tSirBssType);
+        // ssId
+        if( pParam->ssId.length )
+        {
+            // ssId len
+            *pBuf = pParam->ssId.length;
+            pBuf++;
+            palCopyMemory( pMac->hHdd, pBuf, pParam->ssId.ssId, pParam->ssId.length );
+            pBuf += pParam->ssId.length;
+        }
+        else
+        {
+            *pBuf = 0;
+            pBuf++;        
+        }
+
+        // set the channel Id
+        *pBuf = pParam->operationChn;
+        pBuf++;
+        //What should we really do for the cbmode.
+        cbMode = (tAniCBSecondaryMode)pal_cpu_to_be32(pParam->cbMode);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&cbMode, sizeof(tAniCBSecondaryMode) );
+        pBuf += sizeof(tAniCBSecondaryMode);
+
+#ifdef WLAN_SOFTAP_FEATURE
+        // Set privacy
+        *pBuf = pParam->privacy;
+        pBuf++;
+ 
+        //Set Uapsd 
+        *pBuf = pParam->ApUapsdEnable;
+        pBuf++;
+
+        //Set SSID hidden
+        *pBuf = pParam->ssidHidden;
+        pBuf++;
+
+        *pBuf = (tANI_U8)pParam->fwdWPSPBCProbeReq;
+        pBuf++;
+        
+        //Ht protection Enable/Disable
+        *pBuf = (tANI_U8)pParam->protEnabled;
+        pBuf++;
+
+        //Enable Beacons to Receive for OBSS protection Enable/Disable
+        *pBuf = (tANI_U8)pParam->obssProtEnabled;
+        pBuf++;
+
+        //set cfg related to protection
+        wTmp = pal_cpu_to_be16( pParam->ht_protection );
+        palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof( tANI_U16 ) ); 
+        pBuf += sizeof(tANI_U16);
+
+        // Set Auth type
+        authType = pal_cpu_to_be32(pParam->authType);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&authType, sizeof(tANI_U32));
+        pBuf += sizeof(tANI_U32);
+
+        // Set DTIM
+        dwTmp = pal_cpu_to_be32(pParam->dtimPeriod);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&dwTmp, sizeof(tANI_U32));
+        pBuf += sizeof(tANI_U32);
+
+        // Set wps_state
+        *pBuf = pParam->wps_state;
+        pBuf++;
+
+#endif
+        //Persona
+        *pBuf = (tANI_U8)pParam->bssPersona;
+        pBuf++;
+        
+
+        
+        // set RSN IE 
+        if( pParam->nRSNIELength > sizeof(pMsg->rsnIE.rsnIEdata) )
+        {
+            status = eHAL_STATUS_INVALID_PARAMETER;
+            palFreeMemory( pMac->hHdd, pMsg );
+            break;
+        }
+        wTmp = pal_cpu_to_be16( pParam->nRSNIELength );
+        palCopyMemory( pMac->hHdd, pBuf, &wTmp, sizeof(tANI_U16) );
+        pBuf += sizeof(tANI_U16);
+        if( wTmp )
+        {
+            wTmp = pParam->nRSNIELength;
+            palCopyMemory( pMac->hHdd, pBuf, pParam->pRSNIE, wTmp );
+            pBuf += wTmp;
+        }
+        nwType = (tSirNwType)pal_cpu_to_be32(pParam->sirNwType);
+        palCopyMemory( pMac->hHdd, pBuf, (tANI_U8 *)&nwType, sizeof(tSirNwType) );
+        pBuf += sizeof(tSirNwType);
+
+        *pBuf = pParam->operationalRateSet.numRates; //tSirMacRateSet->numRates
+        pBuf++;
+
+        palCopyMemory( pMac->hHdd, pBuf, pParam->operationalRateSet.rate, pParam->operationalRateSet.numRates );
+        pBuf += pParam->operationalRateSet.numRates ;
+        *pBuf++ = pParam->extendedRateSet.numRates;
+        if(0 != pParam->extendedRateSet.numRates)
+        {
+            palCopyMemory( pMac->hHdd, pBuf, pParam->extendedRateSet.rate, pParam->extendedRateSet.numRates );
+            pBuf += pParam->extendedRateSet.numRates;
+        }
+
+        msgLen = (tANI_U16)(sizeof(tANI_U32 ) + (pBuf - wTmpBuf)); //msg_header + msg
+        pMsg->length = pal_cpu_to_be16(msgLen);
+        
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+
+    } while( 0 );
+
+  return( status );
+}
+
+
+eHalStatus csrSendMBStopBssReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tSirSmeStopBssReq *pMsg;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tANI_U8 *pBuf;
+    tANI_U16 msgLen;
+
+    do {
+        status = palAllocateMemory(pMac, (void **)&pMsg, sizeof(tSirSmeStopBssReq));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeStopBssReq ));
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_STOP_BSS_REQ);
+        pBuf = &pMsg->sessionId;
+        //sessionId
+        *pBuf = (tANI_U8)sessionId;
+        pBuf++;
+        // transactionId
+        *pBuf = 0;
+        pBuf += sizeof(tANI_U16);
+        //reason code
+        *pBuf  = 0;
+        pBuf += sizeof(tSirResultCodes);
+        // bssid 
+        // if BSSType is WDS sta, use selfmacAddr as bssid, else use bssid in connectedProfile
+        if( CSR_IS_CONN_WDS_STA(&pSession->connectedProfile) )
+        {
+            palCopyMemory( pMac->hHdd, pBuf,(tANI_U8 *)&pSession->selfMacAddr,  sizeof(tSirMacAddr) );                
+        }
+        else
+        {
+            palCopyMemory( pMac->hHdd, pBuf,(tANI_U8 *)&pSession->connectedProfile.bssid,  sizeof(tSirMacAddr) );              
+        }
+       pBuf += sizeof(tSirMacAddr);
+       msgLen = sizeof(tANI_U16) + sizeof(tANI_U16) + 1 + sizeof(tANI_U16) + sizeof(tSirResultCodes) + sizeof(tSirMacAddr);
+       pMsg->length =  pal_cpu_to_be16(msgLen);
+
+       status =  palSendMBMessage( pMac->hHdd, pMsg );
+#if 0            
+        status = palAllocateMemory(pMac, (void **)&pMsg, sizeof(tSirSmeStopBssReq));
+        if ( !HAL_STATUS_SUCCESS(status) ) break;
+        palZeroMemory(pMac->hHdd, pMsg, sizeof( tSirSmeStopBssReq ));
+                pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_STOP_BSS_REQ);
+                pMsg->reasonCode = 0;
+        // bssid
+        // if BSSType is WDS sta, use selfmacAddr as bssid, else use bssid in connectedProfile
+        if( CSR_IS_CONN_WDS_STA(&pSession->connectedProfile) )
+        {
+            pbBssid = (tANI_U8 *)&pSession->selfMacAddr;
+        }
+        else
+        {
+            pbBssid = (tANI_U8 *)&pSession->connectedProfile.bssid;
+        }
+        palCopyMemory( pMac->hHdd, &pMsg->bssId, pbBssid, sizeof(tSirMacAddr) );
+        pMsg->transactionId = 0;
+        pMsg->sessionId = (tANI_U8)sessionId;
+                pMsg->length = pal_cpu_to_be16((tANI_U16)sizeof( tSirSmeStopBssReq ));
+                status = palSendMBMessage( pMac->hHdd, pMsg );
+#endif                
+        } while( 0 );
+
+    return( status );
+}
+
+
+eHalStatus csrReassoc(tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                      tCsrRoamModifyProfileFields *pModProfileFields,
+                      tANI_U32 *pRoamId, v_BOOL_t fForce)
+{
+
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tANI_U32 roamId = 0;
+   tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+   if((csrIsConnStateConnected(pMac, sessionId)) &&
+      (fForce || (!palEqualMemory(pMac->hHdd, &pModProfileFields, 
+                       &pSession->connectedProfile.modifyProfileFields, 
+                       sizeof(tCsrRoamModifyProfileFields)))) )
+   {
+      roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+      if(pRoamId)
+      {
+         *pRoamId = roamId;
+      }
+
+
+      status = csrRoamIssueReassoc(pMac, sessionId, NULL, pModProfileFields, 
+                                   eCsrSmeIssuedReassocToSameAP, roamId, 
+                                   eANI_BOOLEAN_FALSE);
+
+   }
+
+   return status;
+}
+
+static eHalStatus csrRoamSessionOpened(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamInfo roamInfo;
+
+    palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+    status = csrRoamCallCallback(pMac, sessionId, &roamInfo, 0,
+                            eCSR_ROAM_SESSION_OPENED, eCSR_ROAM_RESULT_NONE);
+    return (status);
+}
+
+eHalStatus csrProcessAddStaSessionRsp( tpAniSirGlobal pMac, tANI_U8 *pMsg)
+{
+   eHalStatus                         status = eHAL_STATUS_SUCCESS;
+   tListElem                          *pEntry = NULL;
+   tSmeCmd                            *pCommand = NULL;
+   tSirSmeAddStaSelfRsp               *pRsp;
+
+   do
+   {
+      if(pMsg == NULL)
+      {
+         smsLog(pMac, LOGE, "in %s msg ptr is NULL\n", __FUNCTION__);
+         status = eHAL_STATUS_FAILURE;
+         break;
+      }
+
+      pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+      if(pEntry)
+      {
+         pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+         if(eSmeCommandAddStaSession == pCommand->command)
+         {
+            pRsp = (tSirSmeAddStaSelfRsp*)pMsg;
+            smsLog( pMac, LOG1, "Add Sta rsp status = %d\n", pRsp->status );
+            //Nothing to be done. May be indicate the self sta addition success by calling session callback (TODO).
+
+            csrRoamSessionOpened(pMac, pCommand->sessionId);
+
+            //Remove this command out of the active list
+            if(csrLLRemoveEntry(&pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK))
+            {
+               //Now put this command back on the avilable command list
+               csrReleaseCommand(pMac, pCommand);
+            }
+            smeProcessPendingQueue( pMac );
+         }
+         else
+         {
+            smsLog(pMac, LOGE, "in %s eWNI_SME_ADD_STA_SELF_RSP Received but NO Add sta session command are ACTIVE ...\n",
+                  __FUNCTION__);
+            status = eHAL_STATUS_FAILURE;
+            break;
+         }
+      }
+      else
+      {
+         smsLog(pMac, LOGE, "in %s eWNI_SME_ADD_STA_SELF_RSP Received but NO commands are ACTIVE ...\n",
+               __FUNCTION__);
+         status = eHAL_STATUS_FAILURE;
+         break;
+      }
+   } while(0);
+
+   return status;
+
+}
+
+eHalStatus csrSendMBAddSelfStaReqMsg( tpAniSirGlobal pMac, tSirMacAddr macAddr )
+{
+   tSirSmeAddStaSelfReq *pMsg;
+   tANI_U16 msgLen;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+
+   do {
+
+      msgLen  = sizeof( tANI_U16 ) + sizeof( tANI_U16 ) + sizeof( tSirMacAddr ) /*+
+         sizeof( tSirBssType )*/;
+
+      status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+      if ( !HAL_STATUS_SUCCESS(status) ) break;
+
+      palZeroMemory(pMac->hHdd, pMsg, msgLen);
+
+      pMsg->mesgType = pal_cpu_to_be16((tANI_U16)eWNI_SME_ADD_STA_SELF_REQ);
+      pMsg->mesgLen = pal_cpu_to_be16(msgLen);
+
+      // self station address
+      palCopyMemory( pMac->hHdd, (tANI_U8 *)pMsg->selfMacAddr, (tANI_U8 *)macAddr, sizeof(tSirMacAddr) );
+
+        smsLog( pMac, LOGE, FL("selfMac=%02x, %02x, %02x, %02x, %02x, %02x\n"),       
+            pMsg->selfMacAddr[0],
+            pMsg->selfMacAddr[1],
+            pMsg->selfMacAddr[2],
+            pMsg->selfMacAddr[3],
+            pMsg->selfMacAddr[4],
+            pMsg->selfMacAddr[5]);
+      status = palSendMBMessage(pMac->hHdd, pMsg);
+
+   } while( 0 );
+
+   return( status );
+}
+
+eHalStatus csrIssueAddStaForSessionReq(tpAniSirGlobal pMac, tANI_U32 sessionId, tSirMacAddr sessionMacAddr)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tSmeCmd *pCommand;
+
+   pCommand = csrGetCommandBuffer(pMac);
+   if(NULL == pCommand)
+   {
+      status = eHAL_STATUS_RESOURCES;
+   }
+   else
+   {
+      pCommand->command = eSmeCommandAddStaSession;
+      pCommand->sessionId = (tANI_U8)sessionId;
+      palCopyMemory( pMac->hHdd, pCommand->u.addStaSessionCmd.selfMacAddr, sessionMacAddr, sizeof( tSirMacAddr ) );
+
+      status = csrQueueSmeCommand(pMac, pCommand, TRUE);
+      if( !HAL_STATUS_SUCCESS( status ) )
+      {
+         //Should be panic??
+         smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+      }
+   }
+
+   return (status);
+}
+
+eHalStatus csrProcessAddStaSessionCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+   return csrSendMBAddSelfStaReqMsg( pMac, 
+         pCommand->u.addStaSessionCmd.selfMacAddr );
+}
+
+eHalStatus csrRoamOpenSession( tpAniSirGlobal pMac, csrRoamCompleteCallback callback, void *pContext,
+                          tANI_U8 *pSelfMacAddr, tANI_U8 *pbSessionId )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 i;
+    tCsrRoamSession *pSession;
+
+    *pbSessionId = CSR_SESSION_ID_INVALID;
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( !CSR_IS_SESSION_VALID( pMac, i ) )
+        {
+            pSession = CSR_GET_SESSION( pMac, i );
+            status = eHAL_STATUS_SUCCESS;
+            pSession->sessionActive = eANI_BOOLEAN_TRUE;
+            pSession->sessionId = (tANI_U8)i;
+                pSession->callback = callback;
+            pSession->pContext = pContext;
+            palCopyMemory( pMac->hHdd, &pSession->selfMacAddr, pSelfMacAddr, sizeof(tCsrBssid) );
+            *pbSessionId = (tANI_U8)i;
+
+            status = palTimerAlloc(pMac->hHdd, &pSession->hTimerRoaming, csrRoamRoamingTimerHandler, 
+                                    &pSession->roamingTimerInfo);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                smsLog(pMac, LOGE, FL("cannot allocate memory for Roaming timer\n"));
+                break;
+            }
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+            status = palTimerAlloc(pMac->hHdd, &pSession->hTimerJoinRetry, csrRoamJoinRetryTimerHandler, 
+                                    &pSession->joinRetryTimerInfo);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                smsLog(pMac, LOGE, FL("cannot allocate memory for joinretry timer\n"));
+                break;
+            }
+#endif
+            pSession->ibssJoinTimerInfo.pMac = pMac;
+            pSession->ibssJoinTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+
+            status = palTimerAlloc(pMac->hHdd, &pSession->hTimerIbssJoining, csrRoamIbssJoinTimerHandler, 
+                                    &pSession->ibssJoinTimerInfo);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                smsLog(pMac, LOGE, FL("cannot allocate memory for IbssJoining timer\n"));
+                break;
+            }
+            status = csrIssueAddStaForSessionReq ( pMac, i, pSelfMacAddr );
+            break;
+        }
+    }
+    if( CSR_ROAM_SESSION_MAX == i )
+    {
+        //No session is available
+        status = eHAL_STATUS_RESOURCES;
+    }
+
+    return ( status );
+}
+
+eHalStatus csrProcessDelStaSessionRsp( tpAniSirGlobal pMac, tANI_U8 *pMsg)
+{
+   eHalStatus                         status = eHAL_STATUS_SUCCESS;
+   tListElem                          *pEntry = NULL;
+   tSmeCmd                            *pCommand = NULL;
+   tSirSmeDelStaSelfRsp               *pRsp;
+
+   do
+   {
+      if(pMsg == NULL)
+      {
+         smsLog(pMac, LOGE, "in %s msg ptr is NULL\n", __FUNCTION__);
+         status = eHAL_STATUS_FAILURE;
+         break;
+      }
+
+      pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+      if(pEntry)
+      {
+         pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+         if(eSmeCommandDelStaSession == pCommand->command)
+         {
+            tANI_U8 sessionId = pCommand->sessionId;
+
+            pRsp = (tSirSmeDelStaSelfRsp*)pMsg;
+            smsLog( pMac, LOG1, "Del Sta rsp status = %d\n", pRsp->status );
+
+            //This session is done.
+            csrCleanupSession(pMac, sessionId);
+
+            if(pCommand->u.delStaSessionCmd.callback)
+            {
+                 
+                status = sme_ReleaseGlobalLock( &pMac->sme );
+                if ( HAL_STATUS_SUCCESS( status ) )
+                {
+                    pCommand->u.delStaSessionCmd.callback(
+                                      pCommand->u.delStaSessionCmd.pContext);
+                    status = sme_AcquireGlobalLock( &pMac->sme );
+                    if (! HAL_STATUS_SUCCESS( status ) )
+                    {
+                        smsLog(pMac, LOGP, "%s: Failed to Acquire Lock\n", __FUNCTION__);
+                        return status;
+                    }
+                }
+                else {
+                    smsLog(pMac, LOGE, "%s: Failed to Release Lock\n", __FUNCTION__);
+                }
+            } 
+   
+            //Remove this command out of the active list
+            if(csrLLRemoveEntry(&pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK))
+            {
+               //Now put this command back on the avilable command list
+               csrReleaseCommand(pMac, pCommand);
+            }
+            smeProcessPendingQueue( pMac );
+         }
+         else
+         {
+            smsLog(pMac, LOGE, "in %s eWNI_SME_DEL_STA_SELF_RSP Received but NO Del sta session command are ACTIVE ...\n",
+                  __FUNCTION__);
+            status = eHAL_STATUS_FAILURE;
+            break;
+         }
+      }
+      else
+      {
+         smsLog(pMac, LOGE, "in %s eWNI_SME_DEL_STA_SELF_RSP Received but NO commands are ACTIVE ...\n",
+               __FUNCTION__);
+         status = eHAL_STATUS_FAILURE;
+         break;
+      }
+   } while(0);
+
+   return status;
+
+}
+
+eHalStatus csrSendMBDelSelfStaReqMsg( tpAniSirGlobal pMac, tSirMacAddr macAddr )
+{
+   tSirSmeDelStaSelfReq *pMsg;
+   tANI_U16 msgLen;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+
+   do {
+
+      msgLen  = sizeof( tANI_U16 ) + sizeof( tANI_U16 ) + sizeof( tSirMacAddr ) /*+
+         sizeof( tSirBssType )*/;
+
+      status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+      if ( !HAL_STATUS_SUCCESS(status) ) break;
+   
+      palZeroMemory(pMac->hHdd, pMsg, msgLen);
+
+      pMsg->mesgType = pal_cpu_to_be16((tANI_U16)eWNI_SME_DEL_STA_SELF_REQ);
+      pMsg->mesgLen = pal_cpu_to_be16(msgLen);
+
+      // self station address
+      palCopyMemory( pMac->hHdd, (tANI_U8 *)pMsg->selfMacAddr, (tANI_U8 *)macAddr, sizeof(tSirMacAddr) );
+
+      status = palSendMBMessage(pMac->hHdd, pMsg);
+
+   } while( 0 );
+
+   return( status );
+}
+
+eHalStatus csrIssueDelStaForSessionReq(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                       tSirMacAddr sessionMacAddr,
+                                       csrRoamSessionCloseCallback callback,
+                                       void *pContext)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+   tSmeCmd *pCommand;
+
+   pCommand = csrGetCommandBuffer(pMac);
+   if(NULL == pCommand)
+   {
+      status = eHAL_STATUS_RESOURCES;
+   }
+   else
+   {
+      pCommand->command = eSmeCommandDelStaSession;
+      pCommand->sessionId = (tANI_U8)sessionId;
+      pCommand->u.delStaSessionCmd.callback = callback;
+      pCommand->u.delStaSessionCmd.pContext = pContext;
+      palCopyMemory( pMac->hHdd, pCommand->u.delStaSessionCmd.selfMacAddr, sessionMacAddr, sizeof( tSirMacAddr ) );
+
+      status = csrQueueSmeCommand(pMac, pCommand, TRUE);
+      if( !HAL_STATUS_SUCCESS( status ) )
+      {
+         //Should be panic??
+         smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+      }
+   }
+
+   return (status);
+}
+
+eHalStatus csrProcessDelStaSessionCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+   return csrSendMBDelSelfStaReqMsg( pMac, 
+         pCommand->u.delStaSessionCmd.selfMacAddr );
+}
+
+static void purgeCsrSessionCmdList(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    tDblLinkList *pList = &pMac->roam.roamCmdPendingList;
+    tListElem *pEntry, *pNext;
+    tSmeCmd *pCommand;
+    tDblLinkList localList;
+
+    vos_mem_zero(&localList, sizeof(tDblLinkList));
+    if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &localList)))
+    {
+        smsLog(pMac, LOGE, FL(" failed to open list"));
+        return;
+    }
+
+    csrLLLock(pList);
+    pEntry = csrLLPeekHead(pList, LL_ACCESS_NOLOCK);
+    while(pEntry != NULL)
+    {
+        pNext = csrLLNext(pList, pEntry, LL_ACCESS_NOLOCK);
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        if(pCommand->sessionId == sessionId)
+        {
+            if(csrLLRemoveEntry(pList, pEntry, LL_ACCESS_NOLOCK))
+            {
+                csrLLInsertTail(&localList, pEntry, LL_ACCESS_NOLOCK);
+            }
+        }
+        pEntry = pNext;
+    }
+    csrLLUnlock(pList);
+
+    while( (pEntry = csrLLRemoveHead(&localList, LL_ACCESS_NOLOCK)) )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        csrAbortCommand(pMac, pCommand, eANI_BOOLEAN_TRUE);
+    }
+    csrLLClose(&localList);
+}
+
+
+void csrCleanupSession(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+    {
+        tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+        csrRoamStop(pMac, sessionId);
+        csrFreeConnectBssDesc(pMac, sessionId);
+        csrRoamFreeConnectProfile( pMac, &pSession->connectedProfile );
+        csrRoamFreeConnectedInfo ( pMac, &pSession->connectedInfo);
+        palTimerFree(pMac->hHdd, pSession->hTimerRoaming);
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+        palTimerFree(pMac->hHdd, pSession->hTimerJoinRetry);
+#endif
+        palTimerFree(pMac->hHdd, pSession->hTimerIbssJoining);
+        purgeSmeSessionCmdList(pMac, sessionId);
+        purgeCsrSessionCmdList(pMac, sessionId);
+        csrInitSession(pMac, sessionId);
+    }
+}
+
+
+eHalStatus csrRoamCloseSession( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                tANI_BOOLEAN fSync, 
+                                csrRoamSessionCloseCallback callback,
+                                void *pContext )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+    {
+        tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+        if(fSync)
+        {
+            csrCleanupSession(pMac, sessionId);
+        }
+        else
+        { 
+            purgeSmeSessionCmdList(pMac, sessionId);
+            purgeCsrSessionCmdList(pMac, sessionId);
+            status = csrIssueDelStaForSessionReq( pMac, sessionId,
+                                        pSession->selfMacAddr, callback, pContext);
+        }
+    }
+    else
+    {
+        status = eHAL_STATUS_INVALID_PARAMETER;
+    }
+
+    return ( status );
+}
+
+
+static void csrInitSession( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    pSession->sessionActive = eANI_BOOLEAN_FALSE;
+    pSession->sessionId = CSR_SESSION_ID_INVALID;
+    pSession->callback = NULL;
+    pSession->pContext = NULL;
+    pSession->ibss_join_pending = FALSE;
+    pSession->connectState = eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED;
+    // TODO : Confirm pMac->roam.fReadyForPowerSave = eANI_BOOLEAN_FALSE;
+    csrFreeRoamProfile( pMac, sessionId );
+    csrRoamFreeConnectProfile(pMac, &pSession->connectedProfile);
+    csrRoamFreeConnectedInfo( pMac, &pSession->connectedInfo );
+    csrFreeConnectBssDesc(pMac, sessionId);
+    csrScanEnable(pMac);
+    palZeroMemory( pMac->hHdd, &pSession->selfMacAddr, sizeof(tCsrBssid) );
+    if(pSession->pWpaRsnReqIE)
+    {
+        palFreeMemory(pMac->hHdd, pSession->pWpaRsnReqIE);
+        pSession->pWpaRsnReqIE = NULL;
+    }
+    pSession->nWpaRsnReqIeLength = 0;
+    if(pSession->pWpaRsnRspIE)
+    {
+        palFreeMemory(pMac->hHdd, pSession->pWpaRsnRspIE);
+        pSession->pWpaRsnRspIE = NULL;
+    }
+    pSession->nWpaRsnRspIeLength = 0;
+#ifdef FEATURE_WLAN_WAPI
+    if(pSession->pWapiReqIE)
+    {
+        palFreeMemory(pMac->hHdd, pSession->pWapiReqIE);
+        pSession->pWapiReqIE = NULL;
+    }
+    pSession->nWapiReqIeLength = 0;
+    if(pSession->pWapiRspIE)
+    {
+        palFreeMemory(pMac->hHdd, pSession->pWapiRspIE);
+        pSession->pWapiRspIE = NULL;
+    }
+    pSession->nWapiRspIeLength = 0;
+#endif /* FEATURE_WLAN_WAPI */
+
+    if(pSession->pAddIEScan)
+    {
+        palFreeMemory(pMac->hHdd, pSession->pAddIEScan);
+        pSession->pAddIEScan = NULL;
+    }
+    pSession->nAddIEScanLength = 0;
+
+    if(pSession->pAddIEAssoc)
+    {
+        palFreeMemory(pMac->hHdd, pSession->pAddIEAssoc);
+        pSession->pAddIEAssoc = NULL;
+}
+    pSession->nAddIEAssocLength = 0;
+
+}
+
+
+eHalStatus csrRoamGetSessionIdFromBSSID( tpAniSirGlobal pMac, tCsrBssid *bssid, tANI_U32 *pSessionId )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tANI_U32 i;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) )
+        {
+            if( csrIsMacAddressEqual( pMac, bssid, &pMac->roam.roamSession[i].connectedProfile.bssid ) )
+            {
+                //Found it
+                status = eHAL_STATUS_SUCCESS;
+                *pSessionId = i;
+                break;
+            }
+        }
+    }
+
+    return( status );
+}
+
+
+//This function assumes that we only support one IBSS session. We cannot use BSSID to identify 
+//session because for IBSS, the bssid changes.
+static tANI_U32 csrFindIbssSession( tpAniSirGlobal pMac )
+{
+    tANI_U32 i, nRet = CSR_SESSION_ID_INVALID;
+    tCsrRoamSession *pSession;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) )
+        {
+            pSession = CSR_GET_SESSION( pMac, i );
+            if( pSession->pCurRoamProfile && ( csrIsBssTypeIBSS( pSession->connectedProfile.BSSType ) ) )
+            {
+                //Found it
+                nRet = i;
+                break;
+            }
+        }
+    }
+
+    return (nRet);
+}
+
+static void csrRoamLinkUp(tpAniSirGlobal pMac, tCsrBssid bssid)
+{
+   /* Update the current BSS info in ho control block based on connected 
+      profile info from pmac global structure                              */
+   
+
+   smsLog(pMac, LOGW, " csrRoamLinkUp: WLAN link UP with AP= %02x-%02x-%02x-%02x-%02x-%02x\n", 
+          bssid[ 0 ], bssid[ 1 ], bssid[ 2 ],
+          bssid[ 3 ], bssid[ 4 ], bssid[ 5 ] );
+
+   /* Check for user misconfig of RSSI trigger threshold                  */
+   pMac->roam.configParam.vccRssiThreshold =
+      ( 0 == pMac->roam.configParam.vccRssiThreshold ) ? 
+      CSR_VCC_RSSI_THRESHOLD : pMac->roam.configParam.vccRssiThreshold;
+   pMac->roam.vccLinkQuality = eCSR_ROAM_LINK_QUAL_POOR_IND;
+
+    /* Check for user misconfig of UL MAC Loss trigger threshold           */
+   pMac->roam.configParam.vccUlMacLossThreshold =
+      ( 0 == pMac->roam.configParam.vccUlMacLossThreshold ) ? 
+      CSR_VCC_UL_MAC_LOSS_THRESHOLD : pMac->roam.configParam.vccUlMacLossThreshold;
+
+#if   defined WLAN_FEATURE_NEIGHBOR_ROAMING
+    {
+        tANI_U32 sessionId = 0;
+
+        /* Indicate the neighbor roal algorithm about the connect indication */
+        csrRoamGetSessionIdFromBSSID(pMac, (tCsrBssid *)bssid, &sessionId);
+        csrNeighborRoamIndicateConnect(pMac, sessionId, VOS_STATUS_SUCCESS);
+    }
+#endif
+
+}
+
+
+static void csrRoamLinkDown(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+   tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+   //Only to handle the case for Handover on infra link
+   if( eCSR_BSS_TYPE_INFRASTRUCTURE != pSession->connectedProfile.BSSType )
+   {
+      return;
+   }
+
+
+   /* deregister the clients requesting stats from PE/TL & also stop the corresponding timers*/
+   csrRoamDeregStatisticsReq(pMac);
+   pMac->roam.vccLinkQuality = eCSR_ROAM_LINK_QUAL_POOR_IND;
+#if   defined WLAN_FEATURE_NEIGHBOR_ROAMING
+   /* Indicate the neighbor roal algorithm about the disconnect indication */
+   csrNeighborRoamIndicateDisconnect(pMac, sessionId);
+#endif
+   
+}
+
+
+void csrRoamTlStatsTimerHandler(void *pv)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( pv );
+   eHalStatus status;
+
+   pMac->roam.tlStatsReqInfo.timerRunning = FALSE;
+
+#if 0
+   // TODO Persession .???
+   //req TL for stats
+   if(WLANTL_GetStatistics(pMac->roam.gVosContext, &tlStats, pMac->roam.connectedInfo.staId))
+   {
+      smsLog(pMac, LOGE, FL("csrRoamTlStatsTimerHandler:couldn't get the stats from TL\n"));
+   }
+   else
+   {
+      //save in SME
+      csrRoamSaveStatsFromTl(pMac, tlStats);
+   }
+#endif
+   if(!pMac->roam.tlStatsReqInfo.timerRunning)
+   {
+      if(pMac->roam.tlStatsReqInfo.periodicity)
+      {
+         //start timer
+         status = palTimerStart(pMac->hHdd, pMac->roam.tlStatsReqInfo.hTlStatsTimer, 
+                                pMac->roam.tlStatsReqInfo.periodicity * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
+         if(!HAL_STATUS_SUCCESS(status))
+         {
+            smsLog(pMac, LOGE, FL("csrRoamTlStatsTimerHandler:cannot start TlStatsTimer timer\n"));
+            return;
+         }
+         pMac->roam.tlStatsReqInfo.timerRunning = TRUE;
+      }
+   }
+}
+
+void csrRoamPeStatsTimerHandler(void *pv)
+{
+   tCsrPeStatsReqInfo *pPeStatsReqListEntry = (tCsrPeStatsReqInfo *)pv;
+   eHalStatus status;
+   tpAniSirGlobal pMac = pPeStatsReqListEntry->pMac;
+   VOS_STATUS vosStatus;
+   tPmcPowerState powerState;
+
+   pPeStatsReqListEntry->timerRunning = FALSE;
+   if( pPeStatsReqListEntry->timerStopFailed == TRUE )
+   {
+      // If we entered here, meaning the timer could not be successfully 
+      // stopped in csrRoamRemoveEntryFromPeStatsReqList(). So do it here.
+
+      /* Destroy the timer */
+      vosStatus = vos_timer_destroy( &pPeStatsReqListEntry->hPeStatsTimer );
+      if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
+      {
+         smsLog(pMac, LOGE, FL("csrRoamPeStatsTimerHandler:failed to destroy hPeStatsTimer timer\n"));
+      }
+
+      // Free the entry
+      palFreeMemory(pMac->hHdd, pPeStatsReqListEntry);
+      pPeStatsReqListEntry = NULL;
+   }
+   else
+   {
+      if(!pPeStatsReqListEntry->rspPending)
+      {
+         status = csrSendMBStatsReqMsg(pMac, pPeStatsReqListEntry->statsMask & ~(1 << eCsrGlobalClassDStats), 
+                                       pPeStatsReqListEntry->staId);
+         if(!HAL_STATUS_SUCCESS(status))
+         {
+            smsLog(pMac, LOGE, FL("csrRoamPeStatsTimerHandler:failed to send down stats req to PE\n"));
+         }
+         else
+         {
+            pPeStatsReqListEntry->rspPending = TRUE;
+         }
+      }
+
+      //send down a req
+      if(pPeStatsReqListEntry->periodicity && 
+         (VOS_TIMER_STATE_STOPPED == vos_timer_getCurrentState(&pPeStatsReqListEntry->hPeStatsTimer)))
+      {
+         pmcQueryPowerState(pMac, &powerState, NULL, NULL);
+         if(ePMC_FULL_POWER == powerState)
+         {
+            if(pPeStatsReqListEntry->periodicity < pMac->roam.configParam.statsReqPeriodicity)
+            {
+               pPeStatsReqListEntry->periodicity = pMac->roam.configParam.statsReqPeriodicity;
+            }
+         }
+         else
+         {
+            if(pPeStatsReqListEntry->periodicity < pMac->roam.configParam.statsReqPeriodicityInPS)
+            {
+               pPeStatsReqListEntry->periodicity = pMac->roam.configParam.statsReqPeriodicityInPS;
+            }
+         }
+         //start timer
+         vosStatus = vos_timer_start( &pPeStatsReqListEntry->hPeStatsTimer, pPeStatsReqListEntry->periodicity );
+         if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) ) 
+         {
+            smsLog(pMac, LOGE, FL("csrRoamPeStatsTimerHandler:cannot start hPeStatsTimer timer\n"));
+            return;
+         }
+
+         pPeStatsReqListEntry->timerRunning = TRUE;
+
+      }
+
+   }
+}
+
+void csrRoamStatsClientTimerHandler(void *pv)
+{
+   tCsrStatsClientReqInfo *pStaEntry = (tCsrStatsClientReqInfo *)pv;
+
+   if(VOS_TIMER_STATE_STOPPED == vos_timer_getCurrentState(&pStaEntry->timer))
+   {
+#if 0
+       // TODO Stats fix for multisession
+       //start the timer
+       vosStatus = vos_timer_start( &pStaEntry->timer, pStaEntry->periodicity );
+   
+       if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) ) 
+       {
+          smsLog(pStaEntry->pMac, LOGE, FL("csrGetStatistics:cannot start StatsClient timer\n"));
+
+       }
+#endif       
+   }
+#if 0
+   //send up the stats report
+   csrRoamReportStatistics(pStaEntry->pMac, pStaEntry->statsMask, pStaEntry->callback, 
+                           pStaEntry->staId, pStaEntry->pContext);
+#endif
+}
+
+
+
+
+eHalStatus csrSendMBStatsReqMsg( tpAniSirGlobal pMac, tANI_U32 statsMask, tANI_U8 staId)
+{
+   tAniGetPEStatsReq *pMsg;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof(tAniGetPEStatsReq));
+   if ( !HAL_STATUS_SUCCESS(status) ) 
+   {
+      smsLog(pMac, LOG1, " csrSendMBStatsReqMsg: failed to allocate mem for stats req \n");
+      return status;
+   }
+   // need to initiate a stats request to PE
+   pMsg->msgType = pal_cpu_to_be16((tANI_U16)eWNI_SME_GET_STATISTICS_REQ);
+   pMsg->msgLen = (tANI_U16)sizeof(tAniGetPEStatsReq);
+   pMsg->staId = staId;
+   pMsg->statsMask = statsMask;
+
+   status = palSendMBMessage(pMac->hHdd, pMsg );    
+
+   if(!HAL_STATUS_SUCCESS(status))
+   {
+      smsLog(pMac, LOG1, " csrSendMBStatsReqMsg: failed to send down the stats req \n");
+   }
+
+   return status;
+}
+
+void csrRoamStatsRspProcessor(tpAniSirGlobal pMac, tSirSmeRsp *pSirMsg)
+{
+   tAniGetPEStatsRsp *pSmeStatsRsp;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tListElem *pEntry = NULL;
+   tCsrStatsClientReqInfo *pTempStaEntry = NULL;
+   tCsrPeStatsReqInfo *pPeStaEntry = NULL;
+   tANI_U32  tempMask = 0;
+   tANI_U8 counter = 0;
+   tANI_U8 *pStats = NULL;
+   tANI_U32   length = 0;
+   v_PVOID_t  pvosGCtx;
+   v_S7_t     rssi = 0;
+   tANI_U32   *pRssi = NULL;
+
+   pSmeStatsRsp = (tAniGetPEStatsRsp *)pSirMsg;
+   if(pSmeStatsRsp->rc)
+   {
+      smsLog( pMac, LOGW, FL("csrRoamStatsRspProcessor:stats rsp from PE shows failure\n"));
+      goto post_update;
+   }
+
+   tempMask = pSmeStatsRsp->statsMask;
+   pStats = ((tANI_U8 *)&pSmeStatsRsp->statsMask) + sizeof(pSmeStatsRsp->statsMask);
+
+   /* subtract all statistics from this length, and after processing the entire 
+    * 'stat' part of the message, if the length is not zero, then rssi is piggy packed 
+    * in this 'stats' message.
+    */
+   length = pSmeStatsRsp->msgLen - sizeof(tAniGetPEStatsRsp);
+
+   //new stats info from PE, fill up the stats strucutres in PMAC
+   while(tempMask)
+   {
+      if(tempMask & 1)
+      {
+         switch(counter)
+         {
+         case eCsrSummaryStats:
+            smsLog( pMac, LOG1, FL("csrRoamStatsRspProcessor:summary stats\n"));
+            status = palCopyMemory(pMac->hHdd, (tANI_U8 *)&pMac->roam.summaryStatsInfo, 
+                                   pStats, sizeof(tCsrSummaryStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOGW, FL("csrRoamStatsRspProcessor:failed to copy summary stats\n"));
+            }
+            pStats += sizeof(tCsrSummaryStatsInfo);
+            length -= sizeof(tCsrSummaryStatsInfo);
+            break;
+
+         case eCsrGlobalClassAStats:
+            smsLog( pMac, LOG1, FL("csrRoamStatsRspProcessor:ClassA stats\n"));
+            status = palCopyMemory(pMac->hHdd, (tANI_U8 *)&pMac->roam.classAStatsInfo, 
+                                   pStats, sizeof(tCsrGlobalClassAStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOGW, FL("csrRoamStatsRspProcessor:failed to copy ClassA stats\n"));
+            }
+            pStats += sizeof(tCsrGlobalClassAStatsInfo);
+            length -= sizeof(tCsrGlobalClassAStatsInfo);
+            break;
+
+         case eCsrGlobalClassBStats:
+            smsLog( pMac, LOG1, FL("csrRoamStatsRspProcessor:ClassB stats\n"));
+            status = palCopyMemory(pMac->hHdd, (tANI_U8 *)&pMac->roam.classBStatsInfo, 
+                                   pStats, sizeof(tCsrGlobalClassBStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOGW, FL("csrRoamStatsRspProcessor:failed to copy ClassB stats\n"));
+            }
+            pStats += sizeof(tCsrGlobalClassBStatsInfo);
+            length -= sizeof(tCsrGlobalClassBStatsInfo);
+            break;
+
+         case eCsrGlobalClassCStats:
+            smsLog( pMac, LOG1, FL("csrRoamStatsRspProcessor:ClassC stats\n"));
+            status = palCopyMemory(pMac->hHdd, (tANI_U8 *)&pMac->roam.classCStatsInfo, 
+                                   pStats, sizeof(tCsrGlobalClassCStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOGW, FL("csrRoamStatsRspProcessor:failed to copy ClassC stats\n"));
+            }
+            pStats += sizeof(tCsrGlobalClassCStatsInfo);
+            length -= sizeof(tCsrGlobalClassCStatsInfo);
+            break;
+
+         case eCsrPerStaStats:
+            smsLog( pMac, LOG1, FL("csrRoamStatsRspProcessor:PerSta stats\n"));
+            if( CSR_MAX_STA > pSmeStatsRsp->staId )
+            {
+               status = palCopyMemory(pMac->hHdd, (tANI_U8 *)&pMac->roam.perStaStatsInfo[pSmeStatsRsp->staId], 
+                                      pStats, sizeof(tCsrPerStaStatsInfo));
+            }
+            else
+            {
+               status = eHAL_STATUS_FAILURE;
+               smsLog( pMac, LOGE, FL("csrRoamStatsRspProcessor:out bound staId:%d\n"), pSmeStatsRsp->staId);
+               VOS_ASSERT( 0 );
+            }
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOGW, FL("csrRoamStatsRspProcessor:failed to copy PerSta stats\n"));
+            }
+            pStats += sizeof(tCsrPerStaStatsInfo);
+            length -= sizeof(tCsrPerStaStatsInfo);
+            break;
+
+         default:
+            smsLog( pMac, LOGW, FL("csrRoamStatsRspProcessor:unknown stats type\n"));
+            break;
+
+         }
+      }
+
+      tempMask >>=1;
+      counter++;
+   }
+   pvosGCtx = vos_get_global_context(VOS_MODULE_ID_SME, pMac);
+   if (length != 0)
+   {
+       pRssi = (tANI_U32*)pStats;
+       rssi = (v_S7_t)*pRssi;
+   }
+   else
+   {
+       /* If riva is not sending rssi, continue to use the hack */
+       rssi = RSSI_HACK_BMPS;
+   }
+   WDA_UpdateRssiBmps(pvosGCtx, pSmeStatsRsp->staId, rssi);
+
+post_update:   
+   //make sure to update the pe stats req list 
+   pEntry = csrRoamFindInPeStatsReqList(pMac, pSmeStatsRsp->statsMask);
+   if(pEntry)
+      {
+      pPeStaEntry = GET_BASE_ADDR( pEntry, tCsrPeStatsReqInfo, link );
+      pPeStaEntry->rspPending = FALSE;
+   
+   }
+   //check the one timer cases
+   pEntry = csrRoamCheckClientReqList(pMac, pSmeStatsRsp->statsMask);
+   if(pEntry)
+   {
+
+      pTempStaEntry = GET_BASE_ADDR( pEntry, tCsrStatsClientReqInfo, link );
+
+      if(pTempStaEntry->timerExpired)
+      {
+         //send up the stats report
+         csrRoamReportStatistics(pMac, pTempStaEntry->statsMask, pTempStaEntry->callback, 
+                                 pTempStaEntry->staId, pTempStaEntry->pContext);
+         //also remove from the client list
+         csrRoamRemoveStatListEntry(pMac, pEntry);
+         pTempStaEntry = NULL;
+
+      }
+   }
+
+}
+
+tListElem * csrRoamFindInPeStatsReqList(tpAniSirGlobal pMac, tANI_U32  statsMask)
+{
+   tListElem *pEntry = NULL;
+   tCsrPeStatsReqInfo *pTempStaEntry = NULL;
+
+   pEntry = csrLLPeekHead( &pMac->roam.peStatsReqList, LL_ACCESS_LOCK );
+
+   if(!pEntry)
+   {
+      //list empty
+      smsLog(pMac, LOGW, "csrRoamFindInPeStatsReqList: List empty, no request to PE\n");
+      return NULL;
+   }
+
+   while( pEntry )
+   {
+      pTempStaEntry = GET_BASE_ADDR( pEntry, tCsrPeStatsReqInfo, link );
+
+      if(pTempStaEntry->statsMask == statsMask)
+      {
+         smsLog(pMac, LOGW, "csrRoamFindInPeStatsReqList: match found\n");
+         break;
+      }
+
+      pEntry = csrLLNext( &pMac->roam.peStatsReqList, pEntry, LL_ACCESS_NOLOCK );
+   }
+
+   return pEntry;
+}
+
+
+tListElem * csrRoamChecknUpdateClientReqList(tpAniSirGlobal pMac, tCsrStatsClientReqInfo *pStaEntry,
+                                             tANI_BOOLEAN update)
+{
+   tListElem *pEntry;
+   tCsrStatsClientReqInfo *pTempStaEntry;
+
+   pEntry = csrLLPeekHead( &pMac->roam.statsClientReqList, LL_ACCESS_LOCK );
+
+   if(!pEntry)
+   {
+      //list empty
+      smsLog(pMac, LOGW, "csrRoamChecknUpdateClientReqList: List empty, no request from "
+             "upper layer client(s)\n");
+      return NULL;
+   }
+
+   while( pEntry )
+   {
+      pTempStaEntry = GET_BASE_ADDR( pEntry, tCsrStatsClientReqInfo, link );
+
+      if((pTempStaEntry->requesterId == pStaEntry->requesterId) && 
+         (pTempStaEntry->statsMask == pStaEntry->statsMask))
+      {
+         smsLog(pMac, LOGW, "csrRoamChecknUpdateClientReqList: match found\n");
+         if(update)
+         {
+         pTempStaEntry->periodicity = pStaEntry->periodicity;
+         pTempStaEntry->callback = pStaEntry->callback;
+         pTempStaEntry->pContext = pStaEntry->pContext;
+         }
+         break;
+      }
+
+      pEntry = csrLLNext( &pMac->roam.statsClientReqList, pEntry, LL_ACCESS_NOLOCK );
+   }
+
+   return pEntry;
+}
+
+tListElem * csrRoamCheckClientReqList(tpAniSirGlobal pMac, tANI_U32 statsMask)
+{
+   tListElem *pEntry;
+   tCsrStatsClientReqInfo *pTempStaEntry;
+
+   pEntry = csrLLPeekHead( &pMac->roam.statsClientReqList, LL_ACCESS_LOCK );
+
+   if(!pEntry)
+   {
+      //list empty
+      smsLog(pMac, LOGW, "csrRoamCheckClientReqList: List empty, no request from "
+             "upper layer client(s)\n");
+      return NULL;
+   }
+
+   while( pEntry )
+   {
+      pTempStaEntry = GET_BASE_ADDR( pEntry, tCsrStatsClientReqInfo, link );
+
+      if((pTempStaEntry->statsMask & ~(1 << eCsrGlobalClassDStats))  == statsMask)
+      {
+         smsLog(pMac, LOGW, "csrRoamCheckClientReqList: match found\n");
+
+         break;
+      }
+
+      pEntry = csrLLNext( &pMac->roam.statsClientReqList, pEntry, LL_ACCESS_NOLOCK );
+   }
+
+   return pEntry;
+}
+
+
+eHalStatus csrRoamRegisterLinkQualityIndCallback(tpAniSirGlobal pMac,
+                                                 csrRoamLinkQualityIndCallback   callback,  
+                                                 void                           *pContext)
+{
+   pMac->roam.linkQualityIndInfo.callback = callback;
+   pMac->roam.linkQualityIndInfo.context = pContext;
+   if( NULL == callback )
+   {
+     smsLog(pMac, LOGW, "csrRoamRegisterLinkQualityIndCallback: indication callback being deregistered");
+   }
+   else
+   {
+     smsLog(pMac, LOGW, "csrRoamRegisterLinkQualityIndCallback: indication callback being registered");
+
+     /* do we need to invoke the callback to notify client of initial value ??  */
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+
+void csrRoamVccTrigger(tpAniSirGlobal pMac)
+{
+   eCsrRoamLinkQualityInd newVccLinkQuality;
+   tANI_U32 ul_mac_loss = 0;
+   tANI_U32 ul_mac_loss_trigger_threshold;
+
+ /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
+   /*-------------------------------------------------------------------------
+     Link quality is currently binary based on OBIWAN recommended triggers
+
+     Check for a change in link quality and notify client if necessary
+   -------------------------------------------------------------------------*/
+   ul_mac_loss_trigger_threshold = 
+      pMac->roam.configParam.vccUlMacLossThreshold;
+
+   VOS_ASSERT( ul_mac_loss_trigger_threshold != 0 );
+
+   smsLog(pMac, LOGW, "csrRoamVccTrigger: UL_MAC_LOSS_THRESHOLD is %d\n", 
+          ul_mac_loss_trigger_threshold );
+
+   if(ul_mac_loss_trigger_threshold < ul_mac_loss)
+   {
+      smsLog(pMac, LOGW, "csrRoamVccTrigger: link quality is POOR \n");
+      newVccLinkQuality = eCSR_ROAM_LINK_QUAL_POOR_IND;
+   }
+   else
+   {
+      smsLog(pMac, LOGW, "csrRoamVccTrigger: link quality is GOOD\n");
+      newVccLinkQuality = eCSR_ROAM_LINK_QUAL_GOOD_IND;
+   }
+
+   smsLog(pMac, LOGW, "csrRoamVccTrigger: link qual : *** UL_MAC_LOSS %d *** ",
+          ul_mac_loss);
+
+   if(newVccLinkQuality != pMac->roam.vccLinkQuality)
+   {
+      smsLog(pMac, LOGW, "csrRoamVccTrigger: link quality changed: trigger necessary\n");
+      if(NULL != pMac->roam.linkQualityIndInfo.callback) 
+      {
+         smsLog(pMac, LOGW, "csrRoamVccTrigger: link quality indication %d\n",
+                newVccLinkQuality );
+         
+         /* we now invoke the callback once to notify client of initial value   */
+         pMac->roam.linkQualityIndInfo.callback( newVccLinkQuality, 
+                                                 pMac->roam.linkQualityIndInfo.context );
+         //event: EVENT_WLAN_VCC
+      }
+   }
+
+   pMac->roam.vccLinkQuality = newVccLinkQuality;
+
+
+}
+
+VOS_STATUS csrRoamVccTriggerRssiIndCallback(tHalHandle hHal, 
+                                            v_U8_t  rssiNotification, 
+                                            void * context)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( context );
+   eCsrRoamLinkQualityInd newVccLinkQuality;
+        // TODO : Session info unavailable
+        tANI_U32 sessionId = 0;
+   VOS_STATUS status = VOS_STATUS_SUCCESS;
+   /*-------------------------------------------------------------------------
+     Link quality is currently binary based on OBIWAN recommended triggers
+
+     Check for a change in link quality and notify client if necessary
+   -------------------------------------------------------------------------*/
+   smsLog(pMac, LOGW, "csrRoamVccTriggerRssiIndCallback: RSSI trigger threshold is %d\n", 
+          pMac->roam.configParam.vccRssiThreshold);
+   if(!csrIsConnStateConnectedInfra(pMac, sessionId))
+   {
+      smsLog(pMac, LOGW, "csrRoamVccTriggerRssiIndCallback: ignoring the indication as we are not connected\n");
+      return VOS_STATUS_SUCCESS;
+   }
+
+   if(WLANTL_HO_THRESHOLD_DOWN == rssiNotification)
+   {
+      smsLog(pMac, LOGW, "csrRoamVccTriggerRssiIndCallback: link quality is POOR\n");
+      newVccLinkQuality = eCSR_ROAM_LINK_QUAL_POOR_IND;
+   }
+   else if(WLANTL_HO_THRESHOLD_UP == rssiNotification)
+   {
+      smsLog(pMac, LOGW, "csrRoamVccTriggerRssiIndCallback: link quality is GOOD \n");
+      newVccLinkQuality = eCSR_ROAM_LINK_QUAL_GOOD_IND;
+   }
+   else
+   {
+      smsLog(pMac, LOGW, "csrRoamVccTriggerRssiIndCallback: unknown rssi notification %d\n", rssiNotification);
+      //Set to this so the code below won't do anything
+      newVccLinkQuality = pMac->roam.vccLinkQuality;    
+
+      VOS_ASSERT(0);
+   }
+
+
+   if(newVccLinkQuality != pMac->roam.vccLinkQuality)
+   {
+      smsLog(pMac, LOGW, "csrRoamVccTriggerRssiIndCallback: link quality changed: trigger necessary\n");
+      if(NULL != pMac->roam.linkQualityIndInfo.callback) 
+      {
+         smsLog(pMac, LOGW, "csrRoamVccTriggerRssiIndCallback: link quality indication %d\n",
+                newVccLinkQuality);
+
+        /* we now invoke the callback once to notify client of initial value   */
+        pMac->roam.linkQualityIndInfo.callback( newVccLinkQuality, 
+                                                pMac->roam.linkQualityIndInfo.context );
+         //event: EVENT_WLAN_VCC
+      }
+   }
+
+   pMac->roam.vccLinkQuality = newVccLinkQuality;
+
+   return status;
+}
+
+
+tCsrStatsClientReqInfo * csrRoamInsertEntryIntoList( tpAniSirGlobal pMac,
+                                                     tDblLinkList *pStaList,
+                                                     tCsrStatsClientReqInfo *pStaEntry)
+{
+   tCsrStatsClientReqInfo *pNewStaEntry = NULL;
+
+   eHalStatus  status;
+
+   //if same entity requested for same set of stats with different periodicity & 
+   // callback update it
+   if(NULL == csrRoamChecknUpdateClientReqList(pMac, pStaEntry, TRUE))
+   {
+   
+      status = palAllocateMemory(pMac->hHdd, (void **)&pNewStaEntry, sizeof(tCsrStatsClientReqInfo));
+      if (!HAL_STATUS_SUCCESS(status))
+      {
+         smsLog(pMac, LOGW, "csrRoamInsertEntryIntoList: couldn't allocate memory for the "
+                "entry\n");
+         return NULL;
+      }
+   
+
+      pNewStaEntry->callback = pStaEntry->callback;
+      pNewStaEntry->pContext = pStaEntry->pContext;
+      pNewStaEntry->periodicity = pStaEntry->periodicity;
+      pNewStaEntry->requesterId = pStaEntry->requesterId;
+      pNewStaEntry->statsMask = pStaEntry->statsMask;
+      pNewStaEntry->pPeStaEntry = pStaEntry->pPeStaEntry;
+      pNewStaEntry->pMac = pStaEntry->pMac;
+      pNewStaEntry->staId = pStaEntry->staId;
+      pNewStaEntry->timerExpired = pStaEntry->timerExpired;
+      
+      csrLLInsertTail( pStaList, &pNewStaEntry->link, LL_ACCESS_LOCK  );
+   }
+   return pNewStaEntry;
+}
+
+
+tCsrPeStatsReqInfo * csrRoamInsertEntryIntoPeStatsReqList( tpAniSirGlobal pMac,
+                                                           tDblLinkList *pStaList,
+                                                           tCsrPeStatsReqInfo *pStaEntry)
+{
+   tCsrPeStatsReqInfo *pNewStaEntry = NULL;
+
+   eHalStatus  status;
+
+   status = palAllocateMemory(pMac->hHdd, (void **)&pNewStaEntry, sizeof(tCsrPeStatsReqInfo));
+   if (!HAL_STATUS_SUCCESS(status))
+   {
+      smsLog(pMac, LOGW, "csrRoamInsertEntryIntoPeStatsReqList: couldn't allocate memory for the "
+                  "entry\n");
+      return NULL;
+   }
+   
+
+   pNewStaEntry->hPeStatsTimer = pStaEntry->hPeStatsTimer;
+   pNewStaEntry->numClient = pStaEntry->numClient;
+   pNewStaEntry->periodicity = pStaEntry->periodicity;
+   pNewStaEntry->statsMask = pStaEntry->statsMask;
+   pNewStaEntry->pMac = pStaEntry->pMac;
+   pNewStaEntry->staId = pStaEntry->staId;
+   pNewStaEntry->timerRunning = pStaEntry->timerRunning;
+   pNewStaEntry->rspPending = pStaEntry->rspPending;
+   
+   csrLLInsertTail( pStaList, &pNewStaEntry->link, LL_ACCESS_LOCK  );
+
+   return pNewStaEntry;
+}
+
+
+eHalStatus csrGetRssi(tpAniSirGlobal pMac, 
+                            tCsrRssiCallback callback, 
+                            tANI_U8 staId, tCsrBssid bssId, void *pContext, void* pVosContext)
+{  
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   vos_msg_t  msg;
+   tANI_U32 sessionId;
+
+   tAniGetRssiReq *pMsg;
+   smsLog(pMac, LOG2, FL("called"));      
+   status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof(tAniGetRssiReq));
+   if ( !HAL_STATUS_SUCCESS(status) ) 
+   {
+      smsLog(pMac, LOGE, " csrGetRssi: failed to allocate mem for req \n");
+      return status;
+   }
+
+   csrRoamGetSessionIdFromBSSID(pMac, (tCsrBssid *)bssId, &sessionId);
+
+   pMsg->msgType = pal_cpu_to_be16((tANI_U16)eWNI_SME_GET_RSSI_REQ);
+   pMsg->msgLen = (tANI_U16)sizeof(tAniGetRssiReq);
+   pMsg->sessionId = sessionId;
+   pMsg->staId = staId;
+   pMsg->rssiCallback = callback;
+   pMsg->pDevContext = pContext;
+   pMsg->pVosContext = pVosContext;
+
+   msg.type = eWNI_SME_GET_RSSI_REQ;
+   msg.bodyptr = pMsg;
+   msg.reserved = 0;
+
+   if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MQ_ID_SME, &msg))
+   {
+       smsLog(pMac, LOGE, " csrGetRssi failed to post msg to self \n");   
+       palFreeMemory(pMac->hHdd, (void *)pMsg);
+       status = eHAL_STATUS_FAILURE;
+   }
+   smsLog(pMac, LOG2, FL("returned"));      
+   return status;
+}
+
+eHalStatus csrGetStatistics(tpAniSirGlobal pMac, eCsrStatsRequesterType requesterId, 
+                            tANI_U32 statsMask, 
+                            tCsrStatsCallback callback, 
+                            tANI_U32 periodicity, tANI_BOOLEAN cache, 
+                            tANI_U8 staId, void *pContext)
+{  
+   tCsrStatsClientReqInfo staEntry;
+   tCsrStatsClientReqInfo *pStaEntry = NULL;
+   tCsrPeStatsReqInfo *pPeStaEntry = NULL; 
+   tListElem *pEntry = NULL;
+   tANI_BOOLEAN found = FALSE;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tANI_BOOLEAN insertInClientList = FALSE;
+   VOS_STATUS vosStatus;
+
+   if( csrIsAllSessionDisconnected(pMac) )
+   {
+      //smsLog(pMac, LOGW, "csrGetStatistics: wrong state curState(%d) not connected\n", pMac->roam.curState);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   if((!statsMask) && (!callback))
+   {
+      //msg
+      smsLog(pMac, LOGW, "csrGetStatistics: statsMask & callback empty in the request\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   //for the search list method for deregister
+   staEntry.requesterId = requesterId;
+   staEntry.statsMask = statsMask;
+   //requester wants to deregister or just an error
+   if((statsMask) && (!callback))
+   {
+      pEntry = csrRoamChecknUpdateClientReqList(pMac, &staEntry, FALSE);
+      if(!pEntry)
+      {
+         //msg
+         smsLog(pMac, LOGW, "csrGetStatistics: callback is empty in the request & couldn't "
+                "find any existing request in statsClientReqList\n");
+         return eHAL_STATUS_FAILURE;
+      }
+      else
+      {
+         //clean up & return
+         pStaEntry = GET_BASE_ADDR( pEntry, tCsrStatsClientReqInfo, link );
+         pStaEntry->pPeStaEntry->numClient--;
+         //check if we need to delete the entry from peStatsReqList too
+         if(!pStaEntry->pPeStaEntry->numClient)
+         {
+            csrRoamRemoveEntryFromPeStatsReqList(pMac, pStaEntry->pPeStaEntry);
+         }
+         //check if we need to stop the tl stats timer too 
+         pMac->roam.tlStatsReqInfo.numClient--;
+         if(!pMac->roam.tlStatsReqInfo.numClient)
+         {
+            if(pMac->roam.tlStatsReqInfo.timerRunning)
+            {
+               status = palTimerStop(pMac->hHdd, pMac->roam.tlStatsReqInfo.hTlStatsTimer);
+               if(!HAL_STATUS_SUCCESS(status))
+               {
+                  smsLog(pMac, LOGE, FL("csrGetStatistics:cannot stop TlStatsTimer timer\n"));
+                  return eHAL_STATUS_FAILURE;
+               }
+            }
+            pMac->roam.tlStatsReqInfo.periodicity = 0;
+            pMac->roam.tlStatsReqInfo.timerRunning = FALSE;
+         }
+         vos_timer_stop( &pStaEntry->timer );
+
+         // Destroy the vos timer...      
+         vosStatus = vos_timer_destroy( &pStaEntry->timer );
+         if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
+         {
+            smsLog(pMac, LOGE, FL("csrGetStatistics:failed to destroy Client req timer\n"));
+         }
+
+         csrRoamRemoveStatListEntry(pMac, pEntry);
+         pStaEntry = NULL;
+         return eHAL_STATUS_SUCCESS;
+      }
+   }
+   
+   if(cache && !periodicity)
+   {
+      //return the cached stats
+      csrRoamReportStatistics(pMac, statsMask, callback, staId, pContext);
+   }
+   else
+   {
+      //add the request in the client req list
+      staEntry.callback = callback;
+      staEntry.pContext = pContext;
+      staEntry.periodicity = periodicity;
+      staEntry.pPeStaEntry = NULL;
+      staEntry.staId = staId;
+      staEntry.pMac = pMac;
+      staEntry.timerExpired = FALSE;
+   
+   
+
+      //if periodic report requested with non cached result from PE/TL
+      if(periodicity)
+      {
+      
+         //if looking for stats from PE
+         if(statsMask & ~(1 << eCsrGlobalClassDStats))
+         {
+         
+            //check if same request made already & waiting for rsp
+            pPeStaEntry = csrRoamCheckPeStatsReqList(pMac, statsMask & ~(1 << eCsrGlobalClassDStats), 
+                                               periodicity, &found, staId);
+            if(!pPeStaEntry)
+            {
+               //bail out, maxed out on number of req for PE
+               return eHAL_STATUS_FAILURE;
+            }
+            else
+            {
+               staEntry.pPeStaEntry = pPeStaEntry;
+            }
+               
+         }
+         //request stats from TL rightaway if requested by client, update tlStatsReqInfo if needed
+         if(statsMask & (1 << eCsrGlobalClassDStats))
+         {
+            if(cache && pMac->roam.tlStatsReqInfo.numClient)
+            {
+               smsLog(pMac, LOGE, FL("csrGetStatistics:Looking for cached stats from TL\n"));
+            }
+            else
+            {
+            
+               //update periodicity
+               if(pMac->roam.tlStatsReqInfo.periodicity)
+               {
+                  pMac->roam.tlStatsReqInfo.periodicity = 
+                     CSR_ROAM_MIN(periodicity, pMac->roam.tlStatsReqInfo.periodicity);
+               }
+               else
+               {
+                  pMac->roam.tlStatsReqInfo.periodicity = periodicity;
+               }
+               if(pMac->roam.tlStatsReqInfo.periodicity < CSR_MIN_TL_STAT_QUERY_PERIOD)
+               {
+                  pMac->roam.tlStatsReqInfo.periodicity = CSR_MIN_TL_STAT_QUERY_PERIOD;
+               }
+               
+               if(!pMac->roam.tlStatsReqInfo.timerRunning)
+               {
+#if 0
+                                   // TODO Session Specific info connectedInfo
+                  //req TL for class D stats
+                  if(WLANTL_GetStatistics(pMac->roam.gVosContext, &tlStats, pMac->roam.connectedInfo.staId))
+                  {
+                     smsLog(pMac, LOGE, FL("csrGetStatistics:couldn't get the stats from TL\n"));
+                  }
+                  else
+                  {
+                     //save in SME
+                     csrRoamSaveStatsFromTl(pMac, tlStats);
+                  }
+#endif
+                  if(pMac->roam.tlStatsReqInfo.periodicity)
+                  {
+                     //start timer
+                     status = palTimerStart(pMac->hHdd, pMac->roam.tlStatsReqInfo.hTlStatsTimer, 
+                                            pMac->roam.tlStatsReqInfo.periodicity * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
+                     if(!HAL_STATUS_SUCCESS(status))
+                     {
+                        smsLog(pMac, LOGE, FL("csrGetStatistics:cannot start TlStatsTimer timer\n"));
+                        return eHAL_STATUS_FAILURE;
+                     }
+                     pMac->roam.tlStatsReqInfo.timerRunning = TRUE;
+                  }
+               }
+            }
+            pMac->roam.tlStatsReqInfo.numClient++;
+         }
+   
+         insertInClientList = TRUE;
+      }
+      //if one time report requested with non cached result from PE/TL
+      else if(!cache && !periodicity)
+      {
+         if(statsMask & ~(1 << eCsrGlobalClassDStats))
+         {
+            //send down a req
+            status = csrSendMBStatsReqMsg(pMac, statsMask & ~(1 << eCsrGlobalClassDStats), staId);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog(pMac, LOGE, FL("csrGetStatistics:failed to send down stats req to PE\n"));
+            }
+            //so that when the stats rsp comes back from PE we respond to upper layer
+            //right away
+            staEntry.timerExpired = TRUE;
+            insertInClientList = TRUE;
+
+         }
+         if(statsMask & (1 << eCsrGlobalClassDStats))
+         {
+#if 0
+                         // TODO : Per Session info connectedInfo
+            //req TL for class D stats
+            if(WLANTL_GetStatistics(pMac->roam.gVosContext, &tlStats, pMac->roam.connectedInfo.staId))
+            {
+               smsLog(pMac, LOGE, FL("csrGetStatistics:couldn't get the stats from TL\n"));
+            }
+            else
+            {
+               //save in SME
+               csrRoamSaveStatsFromTl(pMac, tlStats);
+            }
+#endif
+
+         }
+         //if looking for stats from TL only 
+         if(!insertInClientList)
+         {
+            //return the stats
+            csrRoamReportStatistics(pMac, statsMask, callback, staId, pContext);
+         }
+
+      }
+
+      if(insertInClientList)
+      {
+         pStaEntry = csrRoamInsertEntryIntoList(pMac, &pMac->roam.statsClientReqList, &staEntry); 
+         if(!pStaEntry)
+         {
+            //msg
+            smsLog(pMac, LOGW, "csrGetStatistics: Failed to insert req in statsClientReqList\n");
+            return eHAL_STATUS_FAILURE;
+         }
+         //Init & start timer if needed
+         if(periodicity)
+         {
+            vosStatus = vos_timer_init( &pStaEntry->timer, VOS_TIMER_TYPE_SW, 
+                                        csrRoamStatsClientTimerHandler, pStaEntry );
+            if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
+            {
+               smsLog(pMac, LOGE, FL("csrGetStatistics:cannot init StatsClient timer\n"));
+               return eHAL_STATUS_FAILURE;
+            }
+            vosStatus = vos_timer_start( &pStaEntry->timer, periodicity );
+            if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) ) 
+            {
+               smsLog(pMac, LOGE, FL("csrGetStatistics:cannot start StatsClient timer\n"));
+               return eHAL_STATUS_FAILURE;
+            }
+
+         }
+
+      }
+
+   }
+   return eHAL_STATUS_SUCCESS;
+}
+
+
+tCsrPeStatsReqInfo * csrRoamCheckPeStatsReqList(tpAniSirGlobal pMac, tANI_U32  statsMask, 
+                                                tANI_U32 periodicity, tANI_BOOLEAN *pFound, tANI_U8 staId)
+{
+   tANI_BOOLEAN found = FALSE;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tCsrPeStatsReqInfo staEntry;
+   tCsrPeStatsReqInfo *pTempStaEntry = NULL;
+   tListElem *pStaEntry = NULL;
+   VOS_STATUS vosStatus;
+   tPmcPowerState powerState;
+   *pFound = FALSE;
+      
+   pStaEntry = csrRoamFindInPeStatsReqList(pMac, statsMask);
+   if(pStaEntry)
+   {
+      pTempStaEntry = GET_BASE_ADDR( pStaEntry, tCsrPeStatsReqInfo, link );
+      if(pTempStaEntry->periodicity)
+      {
+         pTempStaEntry->periodicity = 
+            CSR_ROAM_MIN(periodicity, pTempStaEntry->periodicity);
+      }
+      else
+      {
+         pTempStaEntry->periodicity = periodicity;
+      }
+
+      pTempStaEntry->numClient++;
+         found = TRUE;
+   }
+   else
+   {
+      palZeroMemory(pMac->hHdd, &staEntry, sizeof(tCsrPeStatsReqInfo));
+      staEntry.numClient = 1;
+      staEntry.periodicity = periodicity;
+      staEntry.pMac = pMac;
+      staEntry.rspPending = FALSE;
+      staEntry.staId = staId;
+      staEntry.statsMask = statsMask;
+      staEntry.timerRunning = FALSE;
+      pTempStaEntry = csrRoamInsertEntryIntoPeStatsReqList(pMac, &pMac->roam.peStatsReqList, &staEntry); 
+      if(!pTempStaEntry)
+      {
+         //msg
+         smsLog(pMac, LOGW, "csrRoamCheckPeStatsReqList: Failed to insert req in peStatsReqList\n");
+         return NULL;
+      }
+   }
+
+   pmcQueryPowerState(pMac, &powerState, NULL, NULL);
+   if(ePMC_FULL_POWER == powerState)
+   {
+      if(pTempStaEntry->periodicity < pMac->roam.configParam.statsReqPeriodicity)
+      {
+         pTempStaEntry->periodicity = pMac->roam.configParam.statsReqPeriodicity;
+      }
+   }
+   else
+   {
+      if(pTempStaEntry->periodicity < pMac->roam.configParam.statsReqPeriodicityInPS)
+      {
+         pTempStaEntry->periodicity = pMac->roam.configParam.statsReqPeriodicityInPS;
+      }
+   }
+   if(!pTempStaEntry->timerRunning)
+   {
+      //send down a req in case of one time req, for periodic ones wait for timer to expire
+      if(!pTempStaEntry->rspPending && 
+         !pTempStaEntry->periodicity)
+      {
+         status = csrSendMBStatsReqMsg(pMac, statsMask & ~(1 << eCsrGlobalClassDStats), staId);
+         if(!HAL_STATUS_SUCCESS(status))
+         {
+            smsLog(pMac, LOGE, FL("csrRoamCheckPeStatsReqList:failed to send down stats req to PE\n"));
+         }
+         else
+         {
+            pTempStaEntry->rspPending = TRUE;
+         }
+      }
+      if(pTempStaEntry->periodicity)
+      {
+         if(!found)
+         {
+            
+            vosStatus = vos_timer_init( &pTempStaEntry->hPeStatsTimer, VOS_TIMER_TYPE_SW, 
+                                        csrRoamPeStatsTimerHandler, pTempStaEntry );
+            if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
+            {
+               smsLog(pMac, LOGE, FL("csrRoamCheckPeStatsReqList:cannot init hPeStatsTimer timer\n"));
+               return NULL;
+            }
+
+         }
+         //start timer
+         smsLog(pMac, LOG1, "csrRoamCheckPeStatsReqList:peStatsTimer period %d\n", pTempStaEntry->periodicity);
+
+         vosStatus = vos_timer_start( &pTempStaEntry->hPeStatsTimer, pTempStaEntry->periodicity );
+         if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) ) 
+         {
+            smsLog(pMac, LOGE, FL("csrRoamCheckPeStatsReqList:cannot start hPeStatsTimer timer\n"));
+            return NULL;
+         }
+         pTempStaEntry->timerRunning = TRUE;
+      }
+   }
+
+   *pFound = found;
+   return pTempStaEntry;
+}
+
+
+/*
+    pStaEntry is no longer invalid upon the return of this function.
+*/
+static void csrRoamRemoveStatListEntry(tpAniSirGlobal pMac, tListElem *pEntry)
+{
+    if(pEntry)
+    {
+        if(csrLLRemoveEntry(&pMac->roam.statsClientReqList, pEntry, LL_ACCESS_LOCK))
+        {
+            palFreeMemory(pMac->hHdd, GET_BASE_ADDR( pEntry, tCsrStatsClientReqInfo, link ));
+        }
+    }
+}
+
+
+void csrRoamRemoveEntryFromPeStatsReqList(tpAniSirGlobal pMac, tCsrPeStatsReqInfo *pPeStaEntry)
+{
+   tListElem *pEntry;
+   tCsrPeStatsReqInfo *pTempStaEntry;
+   VOS_STATUS vosStatus;
+   pEntry = csrLLPeekHead( &pMac->roam.peStatsReqList, LL_ACCESS_LOCK );
+
+   if(!pEntry)
+   {
+      //list empty
+      smsLog(pMac, LOGW, "csrRoamRemoveEntryFromPeStatsReqList: List empty, no stats req for PE\n");
+      return;
+   }
+
+   while( pEntry )
+   {
+      pTempStaEntry = GET_BASE_ADDR( pEntry, tCsrPeStatsReqInfo, link );
+
+      if( pTempStaEntry && pTempStaEntry->statsMask == pPeStaEntry->statsMask)
+      {
+         smsLog(pMac, LOGW, "csrRoamRemoveEntryFromPeStatsReqList: match found\n");
+         if(pTempStaEntry->timerRunning)
+         {
+            vosStatus = vos_timer_stop( &pTempStaEntry->hPeStatsTimer );
+            /* If we are not able to stop the timer here, just remove 
+             * the entry from the linked list. Destroy the timer object 
+             * and free the memory in the timer CB
+             */
+            if( vosStatus == VOS_STATUS_SUCCESS )
+            {
+               /* the timer is successfully stopped */
+               pTempStaEntry->timerRunning = FALSE;
+
+               /* Destroy the timer */
+               vosStatus = vos_timer_destroy( &pTempStaEntry->hPeStatsTimer );
+               if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
+               {
+                  smsLog(pMac, LOGE, FL("csrRoamRemoveEntryFromPeStatsReqList:failed to destroy hPeStatsTimer timer\n"));
+               }
+            }
+            else
+            {
+               // the timer could not be stopped. Hence destroy and free the 
+               // memory for the PE stat entry in the timer CB.
+               pTempStaEntry->timerStopFailed = TRUE;
+            }
+         }
+
+         if(csrLLRemoveEntry(&pMac->roam.peStatsReqList, pEntry, LL_ACCESS_LOCK))
+         {
+            // Only free the memory if we could stop the timer successfully
+            if(!pTempStaEntry->timerStopFailed)
+            {
+               palFreeMemory(pMac->hHdd, pTempStaEntry);
+               pTempStaEntry = NULL;
+            }
+            break;
+         }
+
+         pEntry = csrLLNext( &pMac->roam.peStatsReqList, pEntry, LL_ACCESS_NOLOCK );
+      }
+   }
+
+   return;
+}
+
+
+void csrRoamSaveStatsFromTl(tpAniSirGlobal pMac, WLANTL_TRANSFER_STA_TYPE tlStats)
+{
+
+   pMac->roam.classDStatsInfo.num_rx_bytes_crc_ok = tlStats.rxBcntCRCok;
+   pMac->roam.classDStatsInfo.rx_bc_byte_cnt = tlStats.rxBCBcnt;
+   pMac->roam.classDStatsInfo.rx_bc_frm_cnt = tlStats.rxBCFcnt;
+   pMac->roam.classDStatsInfo.rx_byte_cnt = tlStats.rxBcnt;
+   pMac->roam.classDStatsInfo.rx_mc_byte_cnt = tlStats.rxMCBcnt;
+   pMac->roam.classDStatsInfo.rx_mc_frm_cnt = tlStats.rxMCFcnt;
+   pMac->roam.classDStatsInfo.rx_rate = tlStats.rxRate;
+   //?? need per AC
+   pMac->roam.classDStatsInfo.rx_uc_byte_cnt[0] = tlStats.rxUCBcnt;
+   pMac->roam.classDStatsInfo.rx_uc_frm_cnt = tlStats.rxUCFcnt;
+   pMac->roam.classDStatsInfo.tx_bc_byte_cnt = tlStats.txBCBcnt;
+   pMac->roam.classDStatsInfo.tx_bc_frm_cnt = tlStats.txBCFcnt;
+   pMac->roam.classDStatsInfo.tx_mc_byte_cnt = tlStats.txMCBcnt;
+   pMac->roam.classDStatsInfo.tx_mc_frm_cnt = tlStats.txMCFcnt;
+   //?? need per AC
+   pMac->roam.classDStatsInfo.tx_uc_byte_cnt[0] = tlStats.txUCBcnt;
+   pMac->roam.classDStatsInfo.tx_uc_frm_cnt = tlStats.txUCFcnt;
+
+}
+
+
+void csrRoamReportStatistics(tpAniSirGlobal pMac, tANI_U32 statsMask, 
+                             tCsrStatsCallback callback, tANI_U8 staId, void *pContext)
+{
+   tANI_U8 stats[500];
+   tANI_U8 *pStats = NULL;
+   tANI_U32 tempMask = 0;
+   tANI_U8 counter = 0;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+
+   if(!callback)
+   {
+      smsLog(pMac, LOGE, FL("csrRoamReportStatistics:cannot report callback NULL\n"));
+      return;
+   }
+   if(!statsMask)
+   {
+      smsLog(pMac, LOGE, FL("csrRoamReportStatistics:cannot report statsMask is 0\n"));
+      return;
+   }
+
+   pStats = stats;
+
+   tempMask = statsMask;
+
+   while(tempMask)
+   {
+      if(tempMask & 1)
+      {
+         //new stats info from PE, fill up the stats strucutres in PMAC
+         switch(counter)
+         {
+         case eCsrSummaryStats:
+            smsLog( pMac, LOG1, FL("csrRoamReportStatistics:summary stats\n"));
+            status = palCopyMemory(pMac->hHdd, pStats, (tANI_U8 *)&pMac->roam.summaryStatsInfo, 
+                                   sizeof(tCsrSummaryStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOG1, FL("csrRoamReportStatistics:failed to copy summary stats\n"));
+            }
+            pStats += sizeof(tCsrSummaryStatsInfo);
+            break;
+
+         case eCsrGlobalClassAStats:
+            smsLog( pMac, LOG1, FL("csrRoamReportStatistics:ClassA stats\n"));
+            status = palCopyMemory(pMac->hHdd, pStats, (tANI_U8 *)&pMac->roam.classAStatsInfo, 
+                                   sizeof(tCsrGlobalClassAStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOG1, FL("csrRoamReportStatistics:failed to copy ClassA stats\n"));
+            }
+            pStats += sizeof(tCsrGlobalClassAStatsInfo);
+
+            break;
+
+         case eCsrGlobalClassBStats:
+            smsLog( pMac, LOG1, FL("csrRoamReportStatistics:ClassB stats\n"));
+            status = palCopyMemory(pMac->hHdd, pStats, (tANI_U8 *)&pMac->roam.classBStatsInfo, 
+                                   sizeof(tCsrGlobalClassBStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOG1, FL("csrRoamReportStatistics:failed to copy ClassB stats\n"));
+            }
+            pStats += sizeof(tCsrGlobalClassBStatsInfo);
+
+            break;
+
+         case eCsrGlobalClassCStats:
+            smsLog( pMac, LOG1, FL("csrRoamReportStatistics:ClassC stats\n"));
+            status = palCopyMemory(pMac->hHdd, pStats, (tANI_U8 *)&pMac->roam.classCStatsInfo, 
+                                   sizeof(tCsrGlobalClassCStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOG1, FL("csrRoamReportStatistics:failed to copy ClassC stats\n"));
+            }
+            pStats += sizeof(tCsrGlobalClassCStatsInfo);
+
+            break;
+
+         case eCsrGlobalClassDStats:
+            smsLog( pMac, LOG1, FL("csrRoamReportStatistics:ClassD stats\n"));
+            status = palCopyMemory(pMac->hHdd, pStats, (tANI_U8 *)&pMac->roam.classDStatsInfo, 
+                                   sizeof(tCsrGlobalClassDStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOG1, FL("csrRoamReportStatistics:failed to copy ClassD stats\n"));
+            }
+            pStats += sizeof(tCsrGlobalClassDStatsInfo);
+
+            break;
+
+         case eCsrPerStaStats:
+            smsLog( pMac, LOG1, FL("csrRoamReportStatistics:PerSta stats\n"));
+            status = palCopyMemory(pMac->hHdd, pStats, (tANI_U8 *)&pMac->roam.perStaStatsInfo[staId], 
+                                   sizeof(tCsrPerStaStatsInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog( pMac, LOG1, FL("csrRoamReportStatistics:failed to copy PerSta stats\n"));
+            }
+            pStats += sizeof(tCsrPerStaStatsInfo);
+
+            break;
+
+         default:
+            smsLog( pMac, LOG1, FL("csrRoamReportStatistics:unknown stats type\n"));
+            break;
+
+         }
+      }
+
+      tempMask >>=1;
+      counter++;
+   }
+
+   callback(stats, pContext );
+
+}
+
+
+
+eHalStatus csrRoamDeregStatisticsReq(tpAniSirGlobal pMac)
+{
+   tListElem *pEntry = NULL;
+   tListElem *pPrevEntry = NULL;
+   tCsrStatsClientReqInfo *pTempStaEntry = NULL;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   VOS_STATUS vosStatus;
+   pEntry = csrLLPeekHead( &pMac->roam.statsClientReqList, LL_ACCESS_LOCK );
+
+   if(!pEntry)
+   {
+      //list empty
+      smsLog(pMac, LOGW, "csrRoamDeregStatisticsReq: List empty, no request from "
+             "upper layer client(s)\n");
+      return status;
+   }
+
+   while( pEntry )
+   {
+      if(pPrevEntry)
+      {
+         pTempStaEntry = GET_BASE_ADDR( pPrevEntry, tCsrStatsClientReqInfo, link );
+         //send up the stats report
+         csrRoamReportStatistics(pMac, pTempStaEntry->statsMask, pTempStaEntry->callback, 
+                                 pTempStaEntry->staId, pTempStaEntry->pContext);
+         csrRoamRemoveStatListEntry(pMac, pPrevEntry);
+      }
+
+      pTempStaEntry = GET_BASE_ADDR( pEntry, tCsrStatsClientReqInfo, link );
+
+      if (pTempStaEntry->pPeStaEntry)  //pPeStaEntry can be NULL
+      {
+      pTempStaEntry->pPeStaEntry->numClient--;
+      //check if we need to delete the entry from peStatsReqList too
+      if(!pTempStaEntry->pPeStaEntry->numClient)
+      {
+         csrRoamRemoveEntryFromPeStatsReqList(pMac, pTempStaEntry->pPeStaEntry);
+      }
+      }
+
+      //check if we need to stop the tl stats timer too 
+      pMac->roam.tlStatsReqInfo.numClient--;
+      if(!pMac->roam.tlStatsReqInfo.numClient)
+      {
+         if(pMac->roam.tlStatsReqInfo.timerRunning)
+         {
+            status = palTimerStop(pMac->hHdd, pMac->roam.tlStatsReqInfo.hTlStatsTimer);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+               smsLog(pMac, LOGE, FL("csrRoamDeregStatisticsReq:cannot stop TlStatsTimer timer\n"));
+               //we will continue
+            }
+         }
+         pMac->roam.tlStatsReqInfo.periodicity = 0;
+         pMac->roam.tlStatsReqInfo.timerRunning = FALSE;
+      }
+
+      if (pTempStaEntry->periodicity)
+      {
+          //While creating StaEntry in csrGetStatistics,
+          //Initializing and starting timer only when periodicity is set. 
+          //So Stop and Destroy timer only when periodicity is set.
+          
+
+      vos_timer_stop( &pTempStaEntry->timer );
+
+      // Destroy the vos timer...      
+      vosStatus = vos_timer_destroy( &pTempStaEntry->timer );
+      if ( !VOS_IS_STATUS_SUCCESS( vosStatus ) )
+      {
+         smsLog(pMac, LOGE, FL("csrRoamDeregStatisticsReq:failed to destroy Client req timer\n"));
+      }
+      }
+
+      
+      pPrevEntry = pEntry;
+      pEntry = csrLLNext( &pMac->roam.statsClientReqList, pEntry, LL_ACCESS_NOLOCK );
+   }
+   //the last one
+   if(pPrevEntry)
+   {
+      pTempStaEntry = GET_BASE_ADDR( pPrevEntry, tCsrStatsClientReqInfo, link );
+      //send up the stats report
+      csrRoamReportStatistics(pMac, pTempStaEntry->statsMask, pTempStaEntry->callback, 
+                                 pTempStaEntry->staId, pTempStaEntry->pContext);
+      csrRoamRemoveStatListEntry(pMac, pPrevEntry);
+   }
+
+   return status;
+   
+}
+
+
+eHalStatus csrIsFullPowerNeeded( tpAniSirGlobal pMac, tSmeCmd *pCommand, 
+                                   tRequestFullPowerReason *pReason,
+                                   tANI_BOOLEAN *pfNeedPower )
+{
+    tANI_BOOLEAN fNeedFullPower = eANI_BOOLEAN_FALSE;
+    tRequestFullPowerReason reason = eSME_REASON_OTHER;
+    tPmcState pmcState;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+        // TODO : Session info unavailable
+        tANI_U32 sessionId = 0;
+
+    if( pfNeedPower )
+    {
+        *pfNeedPower = eANI_BOOLEAN_FALSE;
+    }
+        //We only handle CSR commands
+        if( !(eSmeCsrCommandMask & pCommand->command) )
+        {
+                return eHAL_STATUS_SUCCESS;
+        }
+
+    //Check PMC state first
+    pmcState = pmcGetPmcState( pMac );
+
+    switch( pmcState )
+    {
+    case REQUEST_IMPS:
+    case IMPS:
+        if( eSmeCommandScan == pCommand->command )
+        {
+            switch( pCommand->u.scanCmd.reason )
+            {
+            case eCsrScanGetResult:
+            case eCsrScanBGScanAbort:
+            case eCsrScanBGScanEnable:
+            case eCsrScanGetScanChnInfo:
+                //Internal process, no need for full power
+                fNeedFullPower = eANI_BOOLEAN_FALSE;
+                break;
+
+            default:
+                //Other scans are real scan, ask for power
+                fNeedFullPower = eANI_BOOLEAN_TRUE;
+                break;
+            } //switch
+        }
+        else
+        {
+            //ask for power for roam and status change
+            fNeedFullPower = eANI_BOOLEAN_TRUE;
+        }
+        break;
+
+    case REQUEST_BMPS:
+    case BMPS:
+    case REQUEST_START_UAPSD:
+    case UAPSD:
+    //We treat WOWL same as BMPS
+    case REQUEST_ENTER_WOWL:
+    case WOWL:
+        if( eSmeCommandRoam == pCommand->command )
+        {
+            tScanResultList *pBSSList = (tScanResultList *)pCommand->u.roamCmd.hBSSList;
+            tCsrScanResult *pScanResult;
+            tListElem *pEntry;
+
+            switch ( pCommand->u.roamCmd.roamReason )
+            {
+            case eCsrForcedDisassoc:
+            case eCsrForcedDisassocMICFailure:
+                reason = eSME_LINK_DISCONNECTED_BY_HDD;
+                fNeedFullPower = eANI_BOOLEAN_TRUE;
+                break;
+                case eCsrSmeIssuedDisassocForHandoff:
+            case eCsrForcedDeauth:
+            case eCsrHddIssuedReassocToSameAP:
+            case eCsrSmeIssuedReassocToSameAP:
+                fNeedFullPower = eANI_BOOLEAN_TRUE;
+                break;
+
+            case eCsrCapsChange:
+                fNeedFullPower = eANI_BOOLEAN_TRUE;
+                break;
+
+            default:
+                //Check whether the profile is already connected. If so, no need for full power
+                //Note: IBSS is ignored for now because we don't support powersave in IBSS
+                if ( csrIsConnStateConnectedInfra(pMac, sessionId) && pBSSList )
+                {
+                    //Only need to check the first one
+                    pEntry = csrLLPeekHead(&pBSSList->List, LL_ACCESS_LOCK);
+                    if( pEntry )
+                    {
+                        pScanResult = GET_BASE_ADDR(pEntry, tCsrScanResult, Link);
+#if 0
+                                                // TODO : Session Specific info pConnectBssDesc
+                        if( csrIsBssIdEqual( pMac, &pScanResult->Result.BssDescriptor, pMac->roam.pConnectBssDesc ) &&
+                            csrIsSsidEqual( pMac, pMac->roam.pConnectBssDesc, 
+                                            &pScanResult->Result.BssDescriptor, (tDot11fBeaconIEs *)( pScanResult->Result.pvIes ) ) )
+                        {
+                            // Check to see if the Auth type has changed in the Profile.  If so, we don't want to Reassociate
+                            // with Authenticating first.  To force this, stop the current association (Disassociate) and 
+                            // then re 'Join' the AP, wihch will force an Authentication (with the new Auth type) followed by 
+                            // a new Association.
+                            if(csrIsSameProfile(pMac, &pMac->roam.connectedProfile, pProfile))
+                            {
+                                if(csrRoamIsSameProfileKeys(pMac, &pMac->roam.connectedProfile, pProfile))
+                                {
+                                    //Done, eventually, the command reaches eCsrReassocToSelfNoCapChange;
+                                    //No need for full power
+                                    //Set the flag so the code later can avoid to do the above
+                                    //check again.
+                                    pCommand->u.roamCmd.fReassocToSelfNoCapChange = eANI_BOOLEAN_TRUE;
+                                    break;
+                                }
+                            }
+                        }
+#endif
+                    }
+                }
+                //If we are here, full power is needed
+                fNeedFullPower = eANI_BOOLEAN_TRUE;
+                break;
+            }
+        }
+        else if( eSmeCommandWmStatusChange == pCommand->command )
+        {
+            //need full power for all
+            fNeedFullPower = eANI_BOOLEAN_TRUE;
+            reason = eSME_LINK_DISCONNECTED_BY_OTHER;
+        }
+        break;
+
+    case REQUEST_STOP_UAPSD:
+    case REQUEST_EXIT_WOWL:
+        if( eSmeCommandRoam == pCommand->command )
+        {
+            fNeedFullPower = eANI_BOOLEAN_TRUE;
+            switch ( pCommand->u.roamCmd.roamReason )
+            {
+                case eCsrForcedDisassoc:
+                case eCsrForcedDisassocMICFailure:
+                    reason = eSME_LINK_DISCONNECTED_BY_HDD;
+                    break;
+                default:
+                    break;
+            }
+                }
+        break;
+
+    case STOPPED:
+    case REQUEST_STANDBY:
+    case STANDBY:
+    case LOW_POWER:
+        //We are not supposed to do anything
+        smsLog( pMac, LOGE, FL( "  cannot process because PMC is in stopped/standby state %d\n" ), pmcState );
+        status = eHAL_STATUS_FAILURE;
+        break;
+
+    case FULL_POWER:
+    case REQUEST_FULL_POWER:
+    default:
+        //No need to ask for full power. This has to be FULL_POWER state
+        break;
+
+    } //switch
+
+    if( pReason )
+    {
+        *pReason = reason;
+    }
+    if( pfNeedPower )
+    {
+        *pfNeedPower = fNeedFullPower;
+    }
+
+    return ( status );
+}
+
+
+static eHalStatus csrRequestFullPower( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_BOOLEAN fNeedFullPower = eANI_BOOLEAN_FALSE;
+    tRequestFullPowerReason reason = eSME_REASON_OTHER;
+
+    status = csrIsFullPowerNeeded( pMac, pCommand, &reason, &fNeedFullPower );
+
+    if( fNeedFullPower && HAL_STATUS_SUCCESS( status ) )
+    {
+        status = pmcRequestFullPower(pMac, csrFullPowerCallback, pMac, reason);
+    }
+
+    return ( status );
+}
+
+
+tSmeCmd *csrGetCommandBuffer( tpAniSirGlobal pMac )
+{
+    tSmeCmd *pCmd = smeGetCommandBuffer( pMac );
+
+    if( pCmd )
+    {
+        pMac->roam.sPendingCommands++;
+    }
+
+    return ( pCmd );
+}
+
+
+void csrReleaseCommand(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+   if (pMac->roam.sPendingCommands > 0)
+   {
+       //All command allocated through csrGetCommandBuffer need to
+       //decrement the pending count when releasing.
+       pMac->roam.sPendingCommands--;
+       smeReleaseCommand( pMac, pCommand );
+   }
+   else
+   {
+       smsLog(pMac, LOGE, FL( "no pending commands"));
+       VOS_ASSERT(0);
+   }
+}
+
+
+//Return SUCCESS is the command is queued, failed
+eHalStatus csrQueueSmeCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fHighPriority )
+{
+    eHalStatus status;
+
+    if( (eSmeCommandScan == pCommand->command) && pMac->scan.fDropScanCmd )
+    {
+        smsLog(pMac, LOGW, FL(" drop scan (scan reason %d) command"),
+           pCommand->u.scanCmd.reason);
+        return eHAL_STATUS_CSR_WRONG_STATE;
+    }
+
+    //We can call request full power first before putting the command into pending Q
+    //because we are holding SME lock at this point.
+    status = csrRequestFullPower( pMac, pCommand );
+    if( HAL_STATUS_SUCCESS( status ) )
+    {
+        tANI_BOOLEAN fNoCmdPending;
+
+        //make sure roamCmdPendingList is not empty first
+        fNoCmdPending = csrLLIsListEmpty( &pMac->roam.roamCmdPendingList, eANI_BOOLEAN_FALSE );
+        if( fNoCmdPending )
+        {
+            smePushCommand( pMac, pCommand, fHighPriority );
+        }
+        else
+        {
+             //Other commands are waiting for PMC callback, queue the new command to the pending Q
+            //no list lock is needed since SME lock is held
+            if( !fHighPriority )
+            {
+                csrLLInsertTail( &pMac->roam.roamCmdPendingList, &pCommand->Link, eANI_BOOLEAN_FALSE );
+            }
+            else {
+                csrLLInsertHead( &pMac->roam.roamCmdPendingList, &pCommand->Link, eANI_BOOLEAN_FALSE );
+            }
+       }
+    }
+    else if( eHAL_STATUS_PMC_PENDING == status )
+    {
+        //no list lock is needed since SME lock is held
+        if( !fHighPriority )
+        {
+            csrLLInsertTail( &pMac->roam.roamCmdPendingList, &pCommand->Link, eANI_BOOLEAN_FALSE );
+        }
+        else {
+            csrLLInsertHead( &pMac->roam.roamCmdPendingList, &pCommand->Link, eANI_BOOLEAN_FALSE );
+        }
+        //Let caller know the command is queue
+        status = eHAL_STATUS_SUCCESS;
+    }
+    else
+    {
+        //Not to decrease pMac->roam.sPendingCommands here. Caller will decrease it when it 
+        //release the command.
+        smsLog( pMac, LOGE, FL( "  cannot queue command %d\n" ), pCommand->command );
+    }
+
+    return ( status );
+
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+eHalStatus csrRoamUpdateAPWPSIE( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirAPWPSIEs* pAPWPSIES )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirUpdateAPWPSIEsReq *pMsg;
+    tANI_U8 *pBuf = NULL, *wTmpBuf = NULL;
+    
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    if (NULL == pSession)
+    {
+        smsLog( pMac, LOGE, FL( "  Session does not exist for session id %d" ), sessionId);
+        return eHAL_STATUS_FAILURE;
+    }
+
+
+    do
+    {
+        status = palAllocateMemory( pMac->hHdd, (void **)&pMsg, sizeof(tSirUpdateAPWPSIEsReq) );
+        if (!HAL_STATUS_SUCCESS(status)) break;
+        palZeroMemory( pMac->hHdd, pMsg, sizeof(tSirUpdateAPWPSIEsReq) );
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_UPDATE_APWPSIE_REQ);
+
+        pBuf = (tANI_U8 *)&pMsg->transactionId;
+        wTmpBuf = pBuf;
+
+        // transactionId
+        *pBuf = 0;
+        *( pBuf + 1 ) = 0;
+        pBuf += sizeof(tANI_U16);
+
+        // bssId
+        palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, &pSession->selfMacAddr, sizeof(tSirMacAddr) );
+        pBuf += sizeof(tSirMacAddr);
+
+        //sessionId
+        *pBuf++ = (tANI_U8)sessionId;
+
+        // APWPSIEs
+        palCopyMemory( pMac->hHdd, (tSirAPWPSIEs *)pBuf, pAPWPSIES, sizeof(tSirAPWPSIEs));
+        pBuf += sizeof(tSirAPWPSIEs);
+
+        pMsg->length = pal_cpu_to_be16((tANI_U16)(sizeof(tANI_U32) + (pBuf - wTmpBuf))); //msg_header + msg
+
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+
+    } while( 0 );
+
+    return ( status );
+}
+
+eHalStatus csrRoamUpdateWPARSNIEs( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirRSNie * pAPSirRSNie)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirUpdateAPWPARSNIEsReq *pMsg;
+    tANI_U8 *pBuf = NULL, *wTmpBuf = NULL;
+
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    if (NULL == pSession)
+    {
+        smsLog( pMac, LOGE, FL( "  Session does not exist for session id %d" ), sessionId);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    do
+    {
+        status = palAllocateMemory( pMac->hHdd, (void **)&pMsg, sizeof(tSirUpdateAPWPARSNIEsReq) );
+        if (!HAL_STATUS_SUCCESS(status)) break;
+        palZeroMemory( pMac->hHdd, pMsg, sizeof( tSirUpdateAPWPARSNIEsReq ) );
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_SET_APWPARSNIEs_REQ);
+
+        pBuf = (tANI_U8 *)&pMsg->transactionId;
+        wTmpBuf = pBuf;
+
+        // transactionId
+        *pBuf = 0;
+        *( pBuf + 1 ) = 0;
+        pBuf += sizeof(tANI_U16);
+ 
+        // bssId
+        palCopyMemory( pMac->hHdd, (tSirMacAddr *)pBuf, &pSession->selfMacAddr, sizeof(tSirMacAddr) );
+        pBuf += sizeof(tSirMacAddr);
+
+        // sessionId
+        *pBuf++ = (tANI_U8)sessionId;
+    
+        // APWPARSNIEs
+        palCopyMemory( pMac->hHdd, (tSirRSNie *)pBuf, pAPSirRSNie, sizeof(tSirRSNie));
+        pBuf += sizeof(tSirRSNie);
+
+        pMsg->length = pal_cpu_to_be16((tANI_U16)(sizeof(tANI_U32 ) + (pBuf - wTmpBuf))); //msg_header + msg
+
+    status = palSendMBMessage(pMac->hHdd, pMsg);
+
+    } while( 0 );
+
+    return ( status );
+}
+
+#endif //#ifdef WLAN_SOFTAP_FEATURE
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+//eHalStatus csrRoamIssueFTPreauthReq(tHalHandle hHal, tANI_U32 sessionId, tCsrBssid preAuthBssid, tANI_U8 channelId)
+eHalStatus csrRoamIssueFTPreauthReq(tHalHandle hHal, tANI_U32 sessionId, tpSirBssDescription pBssDescription)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tpSirFTPreAuthReq pftPreAuthReq;
+    tANI_U16 auth_req_len = 0;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    auth_req_len = sizeof(tSirFTPreAuthReq);
+    pftPreAuthReq = (tpSirFTPreAuthReq)vos_mem_malloc(auth_req_len);
+    if (pftPreAuthReq == NULL)
+    {
+        smsLog(pMac, LOGE, FL("Memory allocation for FT Preauth request failed"));
+        return eHAL_STATUS_RESOURCES;
+    }
+
+    // Save the SME Session ID here. We need it while processing the preauth response
+    pMac->ft.ftSmeContext.smeSessionId = sessionId;
+
+    vos_mem_zero(pftPreAuthReq, auth_req_len);
+
+    pftPreAuthReq->pbssDescription = (tpSirBssDescription)vos_mem_malloc(
+            sizeof(pBssDescription->length) + pBssDescription->length);
+
+    pftPreAuthReq->messageType = pal_cpu_to_be16(eWNI_SME_FT_PRE_AUTH_REQ);
+
+    pftPreAuthReq->preAuthchannelNum = pBssDescription->channelId;
+
+
+    palCopyMemory(pMac->hHdd, (void *)&pftPreAuthReq->currbssId, (void *)pSession->connectedProfile.bssid, sizeof(tSirMacAddr));
+
+    palCopyMemory(pMac->hHdd, (void *)&pftPreAuthReq->preAuthbssId, (void *)pBssDescription->bssId, sizeof(tSirMacAddr));  
+
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    if (csrRoamIs11rAssoc(pMac))
+    {
+        pftPreAuthReq->ft_ies_length = (tANI_U16)pMac->ft.ftSmeContext.auth_ft_ies_length;
+        palCopyMemory(pMac->hHdd, pftPreAuthReq->ft_ies, pMac->ft.ftSmeContext.auth_ft_ies, 
+                                pMac->ft.ftSmeContext.auth_ft_ies_length);
+    }
+    else
+#endif
+    {
+        pftPreAuthReq->ft_ies_length = 0; 
+    }
+
+    vos_mem_copy(pftPreAuthReq->pbssDescription, pBssDescription, pBssDescription->length);
+
+    pftPreAuthReq->length = pal_cpu_to_be16(sizeof(tSirFTPreAuthReq) + sizeof(pBssDescription->length) +
+                                                    pBssDescription->length); 
+
+    return palSendMBMessage(pMac->hHdd, pftPreAuthReq);
+}
+
+/*--------------------------------------------------------------------------
+ * This will receive and process the FT Pre Auth Rsp from the current 
+ * associated ap. 
+ * 
+ * This will invoke the hdd call back. This is so that hdd can now
+ * send the FTIEs from the Auth Rsp (Auth Seq 2) to the supplicant.
+  ------------------------------------------------------------------------*/
+void csrRoamFTPreAuthRspProcessor( tHalHandle hHal, tpSirFTPreAuthRsp pFTPreAuthRsp )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+    smsLog( pMac, LOGE, FL("Preauth response status code %d"), pFTPreAuthRsp->status); 
+#endif
+
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING    
+    csrNeighborRoamPreauthRspHandler(pMac, (VOS_STATUS)pFTPreAuthRsp->status);
+#endif
+
+    /* The below function calls/timers should be invoked only if the pre-auth is successful */
+    if (VOS_STATUS_SUCCESS != (VOS_STATUS)pFTPreAuthRsp->status)
+        return;
+
+    // Implies a success
+    pMac->ft.ftSmeContext.FTState = eFT_AUTH_COMPLETE;
+
+    // Indicate SME QoS module the completion of Preauth success. This will trigger the creation of RIC IEs
+    pMac->ft.ftSmeContext.psavedFTPreAuthRsp = pFTPreAuthRsp;
+    sme_QosCsrEventInd(pMac, pMac->ft.ftSmeContext.smeSessionId, SME_QOS_CSR_PREAUTH_SUCCESS_IND, NULL);
+
+    /* Start the pre-auth reassoc interval timer with a period of 400ms. When this expires, 
+     * actual transition from the current to handoff AP is triggered */
+    status = palTimerStart(pMac->hHdd, pMac->ft.ftSmeContext.preAuthReassocIntvlTimer,
+                                                            60 * PAL_TIMER_TO_MS_UNIT,
+                                                            eANI_BOOLEAN_FALSE);
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("Preauth reassoc interval timer start failed to start with status %d\n"), status);
+        return;
+    }
+
+    // Save the received response
+    palCopyMemory(pMac->hHdd, (void *)&pMac->ft.ftSmeContext.preAuthbssId, (void *)pFTPreAuthRsp->preAuthbssId, sizeof(tCsrBssid));
+    if (csrRoamIs11rAssoc(pMac))
+       csrRoamCallCallback(pMac, pFTPreAuthRsp->smeSessionId, NULL, 0, 
+                        eCSR_ROAM_FT_RESPONSE, eCSR_ROAM_RESULT_NONE);
+
+    // Currently we dont do anything special for CCX connection.
+    
+
+    // Done with it, init it.
+    pMac->ft.ftSmeContext.psavedFTPreAuthRsp = NULL;
+}
+#endif
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+void csrRoamJoinRetryTimerHandler(void *pv)
+{
+    tCsrTimerInfo *pInfo = (tCsrTimerInfo *)pv;
+    tpAniSirGlobal pMac = pInfo->pMac;
+    tANI_U32 sessionId = pInfo->sessionId;
+    tCsrRoamSession *pSession;
+    
+    if( CSR_IS_SESSION_VALID(pMac, sessionId) )
+    {
+        smsLog( pMac, LOGE, FL( "  retrying the last roam profile on session %d\n" ), sessionId );
+        pSession = CSR_GET_SESSION( pMac, sessionId );
+        if(pSession->pCurRoamProfile && csrIsConnStateDisconnected(pMac, sessionId))
+        {
+            if( !HAL_STATUS_SUCCESS(csrRoamJoinLastProfile(pMac, sessionId)) )
+            {
+               smsLog( pMac, LOGE, FL( "  fail to retry the last roam profile\n" ) );
+            }
+        }
+    }
+}
+
+eHalStatus csrRoamStartJoinRetryTimer(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 interval)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    
+    if(pSession->pCurRoamProfile && pSession->maxRetryCount)
+    {
+        smsLog(pMac, LOGE, FL(" call sessionId %d retry count %d left\n "), sessionId, pSession->maxRetryCount);
+        pSession->maxRetryCount--;
+        pSession->joinRetryTimerInfo.pMac = pMac;
+        pSession->joinRetryTimerInfo.sessionId = (tANI_U8)sessionId;
+        status = palTimerStart(pMac->hHdd, pSession->hTimerJoinRetry, interval, eANI_BOOLEAN_FALSE);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            smsLog(pMac, LOGE, FL(" fail to start timer status %s \n "), status);
+        }
+    }
+    else
+    {
+        smsLog(pMac, LOGE, FL(" not to start timer due to no profile or reach mac ret (%d)\n "), 
+               pSession->maxRetryCount);
+    }
+    
+    return (status);
+}
+
+eHalStatus csrRoamStopJoinRetryTimer(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    smsLog(pMac, LOGE, " csrRoamStopJoinRetryTimer \n ");
+    if( CSR_IS_SESSION_VALID(pMac, sessionId) )
+    {
+        return (palTimerStop(pMac->hHdd, pMac->roam.roamSession[sessionId].hTimerJoinRetry));
+    }
+    
+    return eHAL_STATUS_SUCCESS;
+}
+#endif
+
+
+/*
+  pBuf points to the beginning of the message
+  LIM packs disassoc rsp as below,
+      messageType - 2 bytes
+      messageLength - 2 bytes
+      sessionId - 1 byte
+      transactionId - 2 bytes (tANI_U16)
+      reasonCode - 4 bytes (sizeof(tSirResultCodes))
+      peerMacAddr - 6 bytes
+      The rest is conditionally defined of (WNI_POLARIS_FW_PRODUCT == AP) and not used
+*/
+static void csrSerDesUnpackDiassocRsp(tANI_U8 *pBuf, tSirSmeDisassocRsp *pRsp)
+{
+   if(pBuf && pRsp)
+   {
+      pBuf += 4; //skip type and length
+      pRsp->sessionId  = *pBuf++;
+      pal_get_U16( pBuf, (tANI_U16 *)&pRsp->transactionId );
+      pBuf += 2;
+      pal_get_U32( pBuf, (tANI_U32 *)&pRsp->statusCode );
+      pBuf += 4;
+      vos_mem_copy(pRsp->peerMacAddr, pBuf, 6);
+   }
+}
+
diff --git a/CORE/SME/src/csr/csrApiScan.c b/CORE/SME/src/csr/csrApiScan.c
new file mode 100644
index 0000000..3241cb4
--- /dev/null
+++ b/CORE/SME/src/csr/csrApiScan.c
@@ -0,0 +1,6477 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+
+  
+    \file csrApiScan.c
+  
+    Implementation for the Common Scan interfaces.
+  
+    Copyright (C) 2006 Airgo Networks, Incorporated 
+   ========================================================================== */
+
+#include "aniGlobal.h"
+
+#include "palApi.h"
+#include "csrInsideApi.h"
+#include "smeInside.h"
+#include "smsDebug.h"
+
+#include "csrSupport.h"
+#include "wlan_qct_tl.h"
+
+#include "vos_diag_core_log.h"
+#include "vos_diag_core_event.h"
+
+#include "vos_nvitem.h"
+#include "wlan_qct_wda.h"
+                                                                     
+#define CSR_VALIDATE_LIST  //This portion of code need to be removed once the issue is resolved.
+
+#ifdef CSR_VALIDATE_LIST
+tDblLinkList *g_pchannelPowerInfoList24 = NULL, * g_pchannelPowerInfoList5 = NULL;
+tpAniSirGlobal g_pMac = NULL;
+#endif
+
+/* Purpose of HIDDEN_TIMER 
+** When we remove hidden ssid from the profile i.e., forget the SSID via GUI that SSID shouldn't see in the profile
+** For above requirement we used timer limit, logic is explained below
+** Timer value is initialsed to current time  when it receives corresponding probe response of hidden SSID (The probe request is
+** received regularly till SSID in the profile. Once it is removed from profile probe request is not sent.) when we receive probe response
+** for broadcast probe request, during update SSID with saved SSID we will diff current time with saved SSID time if it is greater than 1 min
+** then we are not updating with old one
+*/
+                                                                     
+#define HIDDEN_TIMER (1*60*1000)                                                                     
+#define CSR_SCAN_RESULT_RSSI_WEIGHT     80 // must be less than 100, represent the persentage of new RSSI
+                                                                     
+/*---------------------------------------------------------------------------
+  PER filter constant fraction: it is a %
+---------------------------------------------------------------------------*/  
+#define CSR_SCAN_PER_FILTER_FRAC 100
+                                                                     
+/*---------------------------------------------------------------------------
+  RSSI filter constant fraction: it is a %
+---------------------------------------------------------------------------*/  
+#define CSR_SCAN_RSSI_FILTER_FRAC 100
+
+/*---------------------------------------------------------------------------
+Convert RSSI into overall score: Since RSSI is in -dBm values, and the 
+overall needs to be weighted inversely (where greater value means better
+system), we convert.
+RSSI *cannot* be more than 0xFF or less than 0 for meaningful WLAN operation
+---------------------------------------------------------------------------*/
+#define CSR_SCAN_MAX_SCORE_VAL 0xFF
+#define CSR_SCAN_MIN_SCORE_VAL 0x0
+#define CSR_SCAN_HANDOFF_DELTA 10
+#define CSR_SCAN_OVERALL_SCORE( rssi ) \
+  ( rssi < CSR_SCAN_MAX_SCORE_VAL )\
+   ? (CSR_SCAN_MAX_SCORE_VAL-rssi) : CSR_SCAN_MIN_SCORE_VAL
+                                                                     
+
+#define CSR_SCAN_IS_OVER_BSS_LIMIT(pMac)  \
+   ( (pMac)->scan.nBssLimit <= (csrLLCount(&(pMac)->scan.scanResultList)) )
+
+//*** This is temporary work around. It need to call CCM api to get to CFG later
+/// Get string parameter value
+extern tSirRetStatus wlan_cfgGetStr(tpAniSirGlobal, tANI_U16, tANI_U8*, tANI_U32*);
+                                                                     
+void csrScanGetResultTimerHandler(void *);
+void csrScanResultAgingTimerHandler(void *pv);
+void csrScanIdleScanTimerHandler(void *);
+#ifdef WLAN_AP_STA_CONCURRENCY
+static void csrStaApConcTimerHandler(void *);
+#endif
+eHalStatus csrScanChannels( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+void csrSetCfgValidChannelList( tpAniSirGlobal pMac, tANI_U8 *pChannelList, tANI_U8 NumChannels );
+void csrSaveTxPowerToCfg( tpAniSirGlobal pMac, tDblLinkList *pList, tANI_U32 cfgId );
+void csrSetCfgCountryCode( tpAniSirGlobal pMac, tANI_U8 *countryCode );
+void csrPurgeChannelPower( tpAniSirGlobal pMac, tDblLinkList *pChannelList );
+//if bgPeriod is 0, background scan is disabled. It is in millisecond units
+eHalStatus csrSetCfgBackgroundScanPeriod(tpAniSirGlobal pMac, tANI_U32 bgPeriod);
+eHalStatus csrProcessSetBGScanParam(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+void csrReleaseScanCommand(tpAniSirGlobal pMac, tSmeCmd *pCommand, eCsrScanStatus scanStatus);
+static tANI_BOOLEAN csrScanValidateScanResult( tpAniSirGlobal pMac, tANI_U8 *pChannels, 
+                                               tANI_U8 numChn, tSirBssDescription *pBssDesc, 
+                                               tDot11fBeaconIEs **ppIes );
+eHalStatus csrSetBGScanChannelList( tpAniSirGlobal pMac, tANI_U8 *pAdjustChannels, tANI_U8 NumAdjustChannels);
+void csrReleaseCmdSingle(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+tANI_BOOLEAN csrRoamIsValidChannel( tpAniSirGlobal pMac, tANI_U8 channel );
+
+//pResult is invalid calling this function.
+void csrFreeScanResultEntry( tpAniSirGlobal pMac, tCsrScanResult *pResult )
+{
+    if( NULL != pResult->Result.pvIes )
+    {
+        palFreeMemory( pMac->hHdd, pResult->Result.pvIes );
+    }
+    palFreeMemory(pMac->hHdd, pResult);
+}
+
+
+static eHalStatus csrLLScanPurgeResult(tpAniSirGlobal pMac, tDblLinkList *pList)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tListElem *pEntry;
+    tCsrScanResult *pBssDesc;
+    
+    csrLLLock(pList);
+    
+    while((pEntry = csrLLRemoveHead(pList, LL_ACCESS_NOLOCK)) != NULL)
+    {
+        pBssDesc = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+        csrFreeScanResultEntry( pMac, pBssDesc );
+    }
+    
+    csrLLUnlock(pList);   
+     
+    return (status);
+}
+
+
+int csrCheckValidateLists(void * dest, const void *src, v_SIZE_t num, int idx)
+{
+#ifdef CSR_VALIDATE_LIST
+
+    int ii = 1;
+
+    if( (NULL == g_pMac) || (!g_pMac->scan.fValidateList ) )
+    {
+        return ii;
+    }
+    if(g_pchannelPowerInfoList24)
+    {
+        //check 2.4 list
+        tListElem *pElem, *pHead;
+        int count;
+        
+        count = (int)(g_pchannelPowerInfoList24->Count);
+        pHead = &g_pchannelPowerInfoList24->ListHead;
+        pElem = pHead->next;
+        if((tANI_U32)(pHead->next) > 0x00010000) //Assuming kernel address is not that low.
+        {
+            //this loop crashes if the pointer is not right
+            while(pElem->next != pHead)
+            {
+                if((tANI_U32)(pElem->next) > 0x00010000)
+                {
+                    pElem = pElem->next;
+                    VOS_ASSERT(count > 0);
+                    count--;
+                }
+                else
+                {
+                    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, 
+                         " %d Detect 1 list(0x%X) error Head(0x%X) next(0x%X) Count %d, dest(0x%X) src(0x%X) numBytes(%d)",
+                         idx, (unsigned int)g_pchannelPowerInfoList24, (unsigned int)pHead, 
+                        (unsigned int)(pHead->next), (int)g_pchannelPowerInfoList24->Count, 
+                        (unsigned int)dest, (unsigned int)src, (int)num);
+                    VOS_ASSERT(0);
+                    ii = 0;
+                    break;
+                }
+            }
+        }
+        else
+        {
+            //Bad list
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, " %d Detect list(0x%X) error Head(0x%X) next(0x%X) Count %d, dest(0x%X) src(0x%X) numBytes(%d)", 
+                idx, (unsigned int)g_pchannelPowerInfoList24, (unsigned int)pHead, 
+                (unsigned int)(pHead->next), (int)g_pchannelPowerInfoList24->Count, 
+                (unsigned int)dest, (unsigned int)src, (int)num);
+            VOS_ASSERT(0);
+            ii = 0;
+        }
+    }
+    else
+    {
+        //list ok
+        ii = 1;
+    }
+
+
+    return ii;
+
+#else
+    return 1;
+#endif //#ifdef CSR_VALIDATE_LIST
+}
+
+
+eHalStatus csrScanOpen( tpAniSirGlobal pMac )
+{
+    eHalStatus status;
+    
+    do
+    {
+        csrLLOpen(pMac->hHdd, &pMac->scan.scanResultList);
+        csrLLOpen(pMac->hHdd, &pMac->scan.tempScanResults);
+        csrLLOpen(pMac->hHdd, &pMac->scan.channelPowerInfoList24);
+        csrLLOpen(pMac->hHdd, &pMac->scan.channelPowerInfoList5G);
+#ifdef WLAN_AP_STA_CONCURRENCY
+        csrLLOpen(pMac->hHdd, &pMac->scan.scanCmdPendingList);
+#endif
+#ifdef CSR_VALIDATE_LIST
+        g_pchannelPowerInfoList5 = &pMac->scan.channelPowerInfoList5G;
+        g_pMac = pMac;
+        g_pchannelPowerInfoList24 = &pMac->scan.channelPowerInfoList24;
+#endif
+        pMac->scan.fFullScanIssued = eANI_BOOLEAN_FALSE;
+        pMac->scan.nBssLimit = CSR_MAX_BSS_SUPPORT;
+        status = palTimerAlloc(pMac->hHdd, &pMac->scan.hTimerGetResult, csrScanGetResultTimerHandler, pMac);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            smsLog(pMac, LOGE, FL("cannot allocate memory for getResult timer\n"));
+            break;
+        }
+#ifdef WLAN_AP_STA_CONCURRENCY
+        status = palTimerAlloc(pMac->hHdd, &pMac->scan.hTimerStaApConcTimer, csrStaApConcTimerHandler, pMac);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            smsLog(pMac, LOGE, FL("cannot allocate memory for hTimerStaApConcTimer timer\n"));
+            break;
+        }
+#endif        
+        status = palTimerAlloc(pMac->hHdd, &pMac->scan.hTimerIdleScan, csrScanIdleScanTimerHandler, pMac);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            smsLog(pMac, LOGE, FL("cannot allocate memory for idleScan timer\n"));
+            break;
+        }
+        status = palTimerAlloc(pMac->hHdd, &pMac->scan.hTimerResultAging, csrScanResultAgingTimerHandler, pMac);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            smsLog(pMac, LOGE, FL("cannot allocate memory for ResultAging timer\n"));
+            break;
+        }
+    }while(0);
+    
+    return (status);
+}
+
+
+eHalStatus csrScanClose( tpAniSirGlobal pMac )
+{
+#ifdef CSR_VALIDATE_LIST
+    g_pchannelPowerInfoList24 = NULL;
+    g_pchannelPowerInfoList5 = NULL;
+    g_pMac = NULL;
+#endif
+    csrLLScanPurgeResult(pMac, &pMac->scan.tempScanResults);
+    csrLLScanPurgeResult(pMac, &pMac->scan.scanResultList);
+#ifdef WLAN_AP_STA_CONCURRENCY
+    csrLLScanPurgeResult(pMac, &pMac->scan.scanCmdPendingList);
+#endif
+    csrLLClose(&pMac->scan.scanResultList);
+    csrLLClose(&pMac->scan.tempScanResults);
+#ifdef WLAN_AP_STA_CONCURRENCY
+    csrLLClose(&pMac->scan.scanCmdPendingList);
+#endif
+    csrPurgeChannelPower(pMac, &pMac->scan.channelPowerInfoList24);
+    csrPurgeChannelPower(pMac, &pMac->scan.channelPowerInfoList5G);
+    csrLLClose(&pMac->scan.channelPowerInfoList24);
+    csrLLClose(&pMac->scan.channelPowerInfoList5G);
+    csrScanDisable(pMac);
+    palTimerFree(pMac->hHdd, pMac->scan.hTimerResultAging);
+    palTimerFree(pMac->hHdd, pMac->scan.hTimerGetResult);
+#ifdef WLAN_AP_STA_CONCURRENCY
+    palTimerFree(pMac->hHdd, pMac->scan.hTimerStaApConcTimer);
+#endif
+    palTimerFree(pMac->hHdd, pMac->scan.hTimerIdleScan);
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+eHalStatus csrScanEnable( tpAniSirGlobal pMac )
+{
+    
+    pMac->scan.fScanEnable = eANI_BOOLEAN_TRUE;
+    pMac->scan.fRestartIdleScan = eANI_BOOLEAN_TRUE;
+    
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+eHalStatus csrScanDisable( tpAniSirGlobal pMac )
+{
+    
+    csrScanStopTimers(pMac);
+    pMac->scan.fScanEnable = eANI_BOOLEAN_FALSE;
+    
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+#ifdef WLAN_AP_STA_CONCURRENCY
+//Return SUCCESS is the command is queued, else returns eHAL_STATUS_FAILURE 
+eHalStatus csrQueueScanRequest( tpAniSirGlobal pMac, tSmeCmd *pScanCmd )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    tANI_BOOLEAN fNoCmdPending;
+    tSmeCmd *pQueueScanCmd=NULL;
+    tSmeCmd *pSendScanCmd=NULL;
+
+    if (vos_get_concurrency_mode() == VOS_STA_SAP) //TODO:- Also make sure AP BSS has started
+    {
+
+        tCsrScanRequest scanReq;
+        tANI_U8 numChn = pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels;
+        tCsrChannelInfo *pChnInfo = &scanReq.ChannelInfo;
+        tANI_U8    channelToScan[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+        tANI_U8    i = 0;
+        tANI_BOOLEAN bMemAlloc = eANI_BOOLEAN_FALSE;
+
+        if (numChn == 0)
+        {
+
+            numChn = pMac->scan.baseChannels.numChannels;
+             
+             status = palAllocateMemory( pMac->hHdd, (void **)&pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList, numChn );
+             if( !HAL_STATUS_SUCCESS( status ) )
+             {
+                 smsLog( pMac, LOGE, FL(" Failed to get memory for channel list \n") );
+                 return eHAL_STATUS_FAILURE;
+             }
+             bMemAlloc = eANI_BOOLEAN_TRUE;
+             status = palCopyMemory( pMac->hHdd, pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList, 
+                         pMac->scan.baseChannels.channelList, numChn );
+             if( !HAL_STATUS_SUCCESS( status ) )
+             {
+                 palFreeMemory( pMac->hHdd, pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList );
+                 pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList = NULL;
+                 smsLog( pMac, LOGE, FL(" Failed to copy memory to channel list \n") );
+                 return eHAL_STATUS_FAILURE;
+             }
+             pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = numChn;
+         }
+
+         //Whenever we get a scan request with multiple channels we break it up into 2 requests
+         //First request  for first channel to scan and second request to scan remaining channels
+         for  (i=0; i < 2; i++)
+         {   //go through max 2 iterations. 
+             //Once for using the existing command when number of channels is 1 
+             //Second to go over the remaining channels after creating a new command
+            
+            if (1 == numChn)
+            {
+                pSendScanCmd = pScanCmd;
+                pSendScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = 1;
+                pSendScanCmd->u.scanCmd.u.scanRequest.scanType = eSIR_ACTIVE_SCAN;
+                pSendScanCmd->u.scanCmd.u.scanRequest.maxChnTime = 
+                    CSR_MIN(pSendScanCmd->u.scanCmd.u.scanRequest.maxChnTime,CSR_ACTIVE_MAX_CHANNEL_TIME_CONC);
+                pSendScanCmd->u.scanCmd.u.scanRequest.minChnTime = 
+                    CSR_MIN(pSendScanCmd->u.scanCmd.u.scanRequest.minChnTime, CSR_ACTIVE_MIN_CHANNEL_TIME_CONC);
+                if (i != 0)
+                { //Callback should be NULL for all except last channel So hdd_callback will be called only after last command
+                  //i!=0 then we came here in second iteration 
+                   pSendScanCmd->u.scanCmd.callback = NULL;
+                }
+                break; //break out of this loop in case there is only 1 channel then no need for 2nd iteration
+            
+            } else { //if number of channels > 1 then
+            
+                palZeroMemory(pMac->hHdd, &scanReq, sizeof(tCsrScanRequest));
+
+                pQueueScanCmd = csrGetCommandBuffer(pMac); //optimize this to use 2 command buffer only
+                if (!pQueueScanCmd)
+                {
+                    if (bMemAlloc)
+                    {
+                        palFreeMemory( pMac->hHdd, pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList );
+                        pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList = NULL;
+                 
+                    }
+                    smsLog( pMac, LOGE, FL(" Failed to get Queue command buffer\n") );
+                    return eHAL_STATUS_FAILURE;
+                }
+                pQueueScanCmd->command = pScanCmd->command; 
+                pQueueScanCmd->sessionId = pScanCmd->sessionId;
+                pQueueScanCmd->u.scanCmd.callback = pScanCmd->u.scanCmd.callback;
+                pQueueScanCmd->u.scanCmd.pContext = pScanCmd->u.scanCmd.pContext;
+                pQueueScanCmd->u.scanCmd.reason = pScanCmd->u.scanCmd.reason;
+                pQueueScanCmd->u.scanCmd.scanID = pMac->scan.nextScanID++; //let it wrap around
+
+                pChnInfo->numOfChannels = pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels - 1;
+
+                VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, 
+                   FL(" &channelToScan %0x pScanCmd(0x%X) pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList(0x%X)numChn(%d)"),
+                   &channelToScan[0], (unsigned int)pScanCmd, 
+                   (unsigned int)pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList, numChn);
+              
+                palCopyMemory(pMac->hHdd, &channelToScan[0], &pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[1], 
+                              pChnInfo->numOfChannels * sizeof(tANI_U8));
+
+                pChnInfo->ChannelList = &channelToScan[0];
+              
+
+                scanReq.BSSType = eCSR_BSS_TYPE_ANY;
+                //Modify callers parameters in case of concurrency
+                scanReq.scanType = eSIR_ACTIVE_SCAN;
+                scanReq.maxChnTime = CSR_ACTIVE_MAX_CHANNEL_TIME_CONC;
+                scanReq.minChnTime = CSR_ACTIVE_MIN_CHANNEL_TIME_CONC;
+
+                status = csrScanCopyRequest(pMac, &pQueueScanCmd->u.scanCmd.u.scanRequest, &scanReq);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    if (bMemAlloc)
+                    {
+                        palFreeMemory( pMac->hHdd, pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList );
+                        pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList = NULL;
+                 
+                    }
+                    smsLog( pMac, LOGE, FL(" Failed to get copy csrScanRequest = %d\n"), status );
+                    return eHAL_STATUS_FAILURE;
+                }       
+                numChn = 1; //make numChn to be 1 for second iteration to create a send command
+            }  
+
+         }
+
+         fNoCmdPending = csrLLIsListEmpty( &pMac->scan.scanCmdPendingList, LL_ACCESS_LOCK );
+
+         //Logic Below is as follows
+         // If the scanCmdPendingList is empty then we directly send that command
+         // to smeCommandQueue else we buffer it in our scanCmdPendingList Queue
+         if( fNoCmdPending )
+         {
+            
+            if (pQueueScanCmd != NULL)
+            {            
+              csrLLInsertTail( &pMac->scan.scanCmdPendingList, &pQueueScanCmd->Link, LL_ACCESS_LOCK );
+            }
+
+            if (pSendScanCmd != NULL)
+            {            
+                return csrQueueSmeCommand(pMac, pSendScanCmd, eANI_BOOLEAN_FALSE);
+            }
+         }
+         else
+         {           
+            if (pSendScanCmd != NULL)
+            {
+                csrLLInsertTail( &pMac->scan.scanCmdPendingList, &pSendScanCmd->Link, LL_ACCESS_LOCK );
+            }
+            if (pQueueScanCmd != NULL)
+            {
+                csrLLInsertTail( &pMac->scan.scanCmdPendingList, &pQueueScanCmd->Link, LL_ACCESS_LOCK );
+            }
+         }
+
+    }
+    else
+    {  //No concurrency case
+        return csrQueueSmeCommand(pMac, pScanCmd, eANI_BOOLEAN_FALSE);
+    }
+    
+
+
+    return ( status );
+
+}
+#endif
+
+eHalStatus csrScanRequest(tpAniSirGlobal pMac, tANI_U16 sessionId, 
+              tCsrScanRequest *pScanRequest, tANI_U32 *pScanRequestID, 
+              csrScanCompleteCallback callback, void *pContext)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tSmeCmd *pScanCmd = NULL;
+    
+    do
+    {
+        if(pMac->scan.fScanEnable)
+        {
+            pScanCmd = csrGetCommandBuffer(pMac);
+            if(pScanCmd)
+            {
+                palZeroMemory(pMac->hHdd, &pScanCmd->u.scanCmd, sizeof(tScanCmd));
+                pScanCmd->command = eSmeCommandScan; 
+                pScanCmd->sessionId = sessionId;
+                pScanCmd->u.scanCmd.callback = callback;
+                pScanCmd->u.scanCmd.pContext = pContext;
+                if(eCSR_SCAN_REQUEST_11D_SCAN == pScanRequest->requestType)
+                {
+                    pScanCmd->u.scanCmd.reason = eCsrScan11d1;
+                }
+                else if((eCSR_SCAN_REQUEST_FULL_SCAN == pScanRequest->requestType) ||
+                        (eCSR_SCAN_P2P_DISCOVERY == pScanRequest->requestType)
+#ifdef SOFTAP_CHANNEL_RANGE
+                        ||(eCSR_SCAN_SOFTAP_CHANNEL_RANGE == pScanRequest->requestType)
+#endif
+                 )
+                {
+                    pScanCmd->u.scanCmd.reason = eCsrScanUserRequest;
+                }
+                else if(eCSR_SCAN_HO_BG_SCAN == pScanRequest->requestType)
+                {
+                    pScanCmd->u.scanCmd.reason = eCsrScanBgScan;
+                }
+                else if(eCSR_SCAN_HO_PROBE_SCAN == pScanRequest->requestType)
+                {
+                    pScanCmd->u.scanCmd.reason = eCsrScanProbeBss;
+                }
+#if defined WLAN_FEATURE_P2P
+                else if(eCSR_SCAN_P2P_FIND_PEER == pScanRequest->requestType)
+                {
+                    pScanCmd->u.scanCmd.reason = eCsrScanP2PFindPeer;
+                }
+#endif                
+                else
+                {
+                    pScanCmd->u.scanCmd.reason = eCsrScanIdleScan;
+                }
+                if(pScanRequest->minChnTime == 0 && pScanRequest->maxChnTime == 0)
+                {
+                    //The caller doesn't set the time correctly. Set it here
+                    if(pScanRequest->scanType == eSIR_ACTIVE_SCAN)
+                    {
+                        pScanRequest->maxChnTime = pMac->roam.configParam.nActiveMaxChnTime;
+                        pScanRequest->minChnTime = pMac->roam.configParam.nActiveMinChnTime;
+                    }
+                    else
+                    {
+                        pScanRequest->maxChnTime = pMac->roam.configParam.nPassiveMaxChnTime;
+                        pScanRequest->minChnTime = pMac->roam.configParam.nPassiveMinChnTime;
+                    }
+                }
+                //Need to make the following atomic
+                pScanCmd->u.scanCmd.scanID = pMac->scan.nextScanID++; //let it wrap around
+                
+                if(pScanRequestID)
+                {
+                    *pScanRequestID = pScanCmd->u.scanCmd.scanID; 
+                }
+
+                //Tush : If it is the first scan request from HDD, CSR checks if it is for 11d. 
+                // If it is not, CSR will save the scan request in the pending cmd queue 
+                // & issue an 11d scan request to PE.
+                if(((0 == pScanCmd->u.scanCmd.scanID)
+                   && (eCSR_SCAN_REQUEST_11D_SCAN != pScanRequest->requestType))
+#ifdef SOFTAP_CHANNEL_RANGE
+                   && (eCSR_SCAN_SOFTAP_CHANNEL_RANGE != pScanRequest->requestType)
+#endif                   
+                   && (eANI_BOOLEAN_FALSE == pMac->scan.fEnableBypass11d)
+                   )
+                {
+                    tSmeCmd *p11dScanCmd;
+                    tCsrScanRequest scanReq;
+                    tCsrChannelInfo *pChnInfo = &scanReq.ChannelInfo;
+
+                    palZeroMemory(pMac->hHdd, &scanReq, sizeof(tCsrScanRequest));
+
+                    p11dScanCmd = csrGetCommandBuffer(pMac);
+                    if(p11dScanCmd)
+                    {
+                        tANI_U32 numChn = pMac->scan.baseChannels.numChannels;
+
+                        palZeroMemory(pMac->hHdd, &p11dScanCmd->u.scanCmd, sizeof(tScanCmd));
+                        status = palAllocateMemory( pMac->hHdd, (void **)&pChnInfo->ChannelList, numChn );
+                        if( !HAL_STATUS_SUCCESS( status ) )
+                        {
+                            break;
+                        }
+                        status = palCopyMemory( pMac->hHdd, pChnInfo->ChannelList, 
+                                    pMac->scan.baseChannels.channelList, numChn );
+                        if( !HAL_STATUS_SUCCESS( status ) )
+                        {
+                            palFreeMemory( pMac->hHdd, pChnInfo->ChannelList );
+                            pChnInfo->ChannelList = NULL;
+                            break;
+                        }
+                        pChnInfo->numOfChannels = (tANI_U8)numChn;
+                        p11dScanCmd->command = eSmeCommandScan;
+                        p11dScanCmd->u.scanCmd.callback = NULL;
+                        p11dScanCmd->u.scanCmd.pContext = NULL;
+                        p11dScanCmd->u.scanCmd.scanID = pMac->scan.nextScanID++;                
+                        scanReq.BSSType = eCSR_BSS_TYPE_ANY;
+
+                        if ( csrIs11dSupported(pMac) )
+                        {
+                            scanReq.scanType = eSIR_PASSIVE_SCAN;
+                            scanReq.requestType = eCSR_SCAN_REQUEST_11D_SCAN;
+                            p11dScanCmd->u.scanCmd.reason = eCsrScan11d1;
+                            scanReq.maxChnTime = pMac->roam.configParam.nPassiveMaxChnTime;
+                            scanReq.minChnTime = pMac->roam.configParam.nPassiveMinChnTime;
+                        }
+                        else
+                        {
+                            scanReq.scanType = eSIR_ACTIVE_SCAN;
+                            scanReq.requestType = eCSR_SCAN_IDLE_MODE_SCAN;
+                            p11dScanCmd->u.scanCmd.reason = eCsrScanIdleScan;
+                            scanReq.maxChnTime = pMac->roam.configParam.nActiveMaxChnTime;
+                            scanReq.minChnTime = pMac->roam.configParam.nActiveMinChnTime;
+                        }
+                        status = csrScanCopyRequest(pMac, &p11dScanCmd->u.scanCmd.u.scanRequest, &scanReq);
+                        //Free the channel list
+                        palFreeMemory( pMac->hHdd, pChnInfo->ChannelList );
+
+                        if(HAL_STATUS_SUCCESS(status))
+                        {
+                            //Start process the command
+#ifdef WLAN_AP_STA_CONCURRENCY
+                            status = csrQueueScanRequest(pMac, p11dScanCmd);
+#else
+                            status = csrQueueSmeCommand(pMac, p11dScanCmd, eANI_BOOLEAN_FALSE);
+#endif                   
+                            if( !HAL_STATUS_SUCCESS( status ) )
+                            {
+                                smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+                                break;
+                            }
+                        }
+                        else 
+                        {
+                            break;
+                        }
+                    }
+                    else
+                    {
+                        //error
+                        break;
+                    }
+                }
+                status = csrScanCopyRequest(pMac, &pScanCmd->u.scanCmd.u.scanRequest, pScanRequest);
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    //Start process the command
+#ifdef WLAN_AP_STA_CONCURRENCY
+                    status = csrQueueScanRequest(pMac,pScanCmd); 
+#else
+                    status = csrQueueSmeCommand(pMac, pScanCmd, eANI_BOOLEAN_FALSE);                   
+#endif
+                    if( !HAL_STATUS_SUCCESS( status ) )
+                    {
+                        smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+                        break;
+                    }
+                }
+                else 
+                {
+                    smsLog( pMac, LOGE, FL(" fail to copy request status = %d\n"), status );
+                    break;
+                }
+            }
+            else 
+            {
+                //log error
+                break;
+            }
+        }
+    } while(0);
+    if(!HAL_STATUS_SUCCESS(status) && pScanCmd)
+    {
+        if( eCsrScanIdleScan == pScanCmd->u.scanCmd.reason )
+        {
+            //Set the flag back for restarting idle scan
+            pMac->scan.fRestartIdleScan = eANI_BOOLEAN_TRUE;
+        }
+        csrReleaseCommandScan(pMac, pScanCmd);
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrScanRequestResult(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pScanCmd;
+    
+    if(pMac->scan.fScanEnable)
+    {
+        pScanCmd = csrGetCommandBuffer(pMac);
+        if(pScanCmd)
+        {
+            pScanCmd->command = eSmeCommandScan;
+            palZeroMemory(pMac->hHdd, &pScanCmd->u.scanCmd, sizeof(tScanCmd));
+            pScanCmd->u.scanCmd.callback = NULL;
+            pScanCmd->u.scanCmd.pContext = NULL;
+            pScanCmd->u.scanCmd.reason = eCsrScanGetResult;
+            //Need to make the following atomic
+            pScanCmd->u.scanCmd.scanID = pMac->scan.nextScanID++; //let it wrap around
+            status = csrQueueSmeCommand(pMac, pScanCmd, eANI_BOOLEAN_FALSE);
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+                csrReleaseCommandScan(pMac, pScanCmd);
+            }
+        }
+        else 
+        {
+            //log error
+            smsLog(pMac, LOGE, FL("can not obtain a common buffer\n"));
+            status = eHAL_STATUS_RESOURCES;
+        }
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrScanAllChannels(tpAniSirGlobal pMac, eCsrRequestType reqType)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 scanId;
+    tCsrScanRequest scanReq;
+
+    palZeroMemory(pMac->hHdd, &scanReq, sizeof(tCsrScanRequest));
+    scanReq.BSSType = eCSR_BSS_TYPE_ANY;
+    scanReq.scanType = eSIR_ACTIVE_SCAN;
+    scanReq.requestType = reqType;
+    scanReq.maxChnTime = pMac->roam.configParam.nActiveMaxChnTime;
+    scanReq.minChnTime = pMac->roam.configParam.nActiveMinChnTime;
+    //Scan with invalid sessionId. 
+    //This results in SME using the first available session to scan.
+    status = csrScanRequest(pMac, CSR_SESSION_ID_INVALID, &scanReq, 
+                            &scanId, NULL, NULL);
+
+    return (status);
+}
+
+
+
+
+eHalStatus csrIssueRoamAfterLostlinkScan(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamReason reason)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tScanResultHandle hBSSList = NULL;
+    tCsrScanResultFilter *pScanFilter = NULL;
+    tANI_U32 roamId = 0;
+    tCsrRoamProfile *pProfile = NULL;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    do
+    {
+        smsLog(pMac, LOG1, " csrIssueRoamAfterLostlinkScan called\n");
+        if(pSession->fCancelRoaming)
+        {
+            smsLog(pMac, LOGW, " lostlink roaming is cancelled\n");
+            csrScanStartIdleScan(pMac);
+            status = eHAL_STATUS_SUCCESS;
+            break;
+        }
+        //Here is the profile we need to connect to
+        status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+        if(!HAL_STATUS_SUCCESS(status))
+            break;
+        palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+        if(NULL == pSession->pCurRoamProfile)
+        {
+            pScanFilter->EncryptionType.numEntries = 1;
+            pScanFilter->EncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_NONE;
+        }
+        else
+        {
+            //We have to make a copy of pCurRoamProfile because it will be free inside csrRoamIssueConnect
+            status = palAllocateMemory(pMac->hHdd, (void **)&pProfile, sizeof(tCsrRoamProfile));
+            if(!HAL_STATUS_SUCCESS(status))
+                break;
+            palZeroMemory(pMac->hHdd, pProfile, sizeof(tCsrRoamProfile));
+            status = csrRoamCopyProfile(pMac, pProfile, pSession->pCurRoamProfile);
+            if(!HAL_STATUS_SUCCESS(status))
+                break;
+            status = csrRoamPrepareFilterFromProfile(pMac, pProfile, pScanFilter);
+        }//We have a profile
+        roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                if(eCsrLostLink1 == reason)
+                {
+                    //we want to put the last connected BSS to the very beginning, if possible
+                    csrMoveBssToHeadFromBSSID(pMac, &pSession->connectedProfile.bssid, hBSSList);
+                }
+                status = csrRoamIssueConnect(pMac, sessionId, pProfile, hBSSList, reason, 
+                                                roamId, eANI_BOOLEAN_TRUE, eANI_BOOLEAN_TRUE);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    csrScanResultPurge(pMac, hBSSList);
+                }
+            }//Have scan result
+        }
+    }while(0);
+    if(pScanFilter)
+    {
+        //we need to free memory for filter if profile exists
+        csrFreeScanFilter(pMac, pScanFilter);
+        palFreeMemory(pMac->hHdd, pScanFilter);
+    }
+    if(NULL != pProfile)
+    {
+        csrReleaseProfile(pMac, pProfile);
+        palFreeMemory(pMac->hHdd, (void *)pProfile);
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrScanGetScanChnInfo(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pScanCmd;
+    
+    if(pMac->scan.fScanEnable)
+    {
+        pScanCmd = csrGetCommandBuffer(pMac);
+        if(pScanCmd)
+        {
+            pScanCmd->command = eSmeCommandScan;
+            palZeroMemory(pMac->hHdd, &pScanCmd->u.scanCmd, sizeof(tScanCmd));
+            pScanCmd->u.scanCmd.callback = NULL;
+            pScanCmd->u.scanCmd.pContext = NULL;
+            pScanCmd->u.scanCmd.reason = eCsrScanGetScanChnInfo;
+            //Need to make the following atomic
+            pScanCmd->u.scanCmd.scanID = pMac->scan.nextScanID++; //let it wrap around
+            status = csrQueueSmeCommand(pMac, pScanCmd, eANI_BOOLEAN_FALSE);
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+                csrReleaseCommandScan(pMac, pScanCmd);
+            }
+        }
+        else 
+        {
+            //log error
+            smsLog(pMac, LOGE, FL("can not obtain a common buffer\n"));
+            status = eHAL_STATUS_RESOURCES;
+        }
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrScanHandleFailedLostlink1(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, "  Lostlink scan 1 failed\n");
+    if(pSession->fCancelRoaming)
+    {
+        csrScanStartIdleScan(pMac);
+    }
+    else if(pSession->pCurRoamProfile)
+    {
+        //We fail lostlink1 but there may be other BSS in the cached result fit the profile. Give it a try first
+        if(pSession->pCurRoamProfile->SSIDs.numOfSSIDs == 0 ||
+            pSession->pCurRoamProfile->SSIDs.numOfSSIDs > 1)
+        {
+            //try lostlink scan2
+            status = csrScanRequestLostLink2(pMac, sessionId);
+        }
+        else if(!pSession->pCurRoamProfile->ChannelInfo.ChannelList || 
+                pSession->pCurRoamProfile->ChannelInfo.ChannelList[0] == 0)
+        {
+            //go straight to lostlink scan3
+            status = csrScanRequestLostLink3(pMac, sessionId);
+        }
+        else
+        {
+            //we are done with lostlink
+            if(csrRoamCompleteRoaming(pMac, sessionId, eANI_BOOLEAN_FALSE, eCSR_ROAM_RESULT_FAILURE))
+            {
+                csrScanStartIdleScan(pMac);
+            }
+            status = eHAL_STATUS_SUCCESS;
+        }
+    }
+    else
+    {
+        status = csrScanRequestLostLink3(pMac, sessionId);
+    }
+
+    return (status);    
+}
+
+
+
+eHalStatus csrScanHandleFailedLostlink2(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, "  Lostlink scan 2 failed\n");
+    if(pSession->fCancelRoaming)
+    {
+        csrScanStartIdleScan(pMac);
+    }
+    else if(!pSession->pCurRoamProfile || !pSession->pCurRoamProfile->ChannelInfo.ChannelList || 
+                pSession->pCurRoamProfile->ChannelInfo.ChannelList[0] == 0)
+    {
+        //try lostlink scan3
+        status = csrScanRequestLostLink3(pMac, sessionId);
+    }
+    else
+    {
+        //we are done with lostlink
+        if(csrRoamCompleteRoaming(pMac, sessionId, eANI_BOOLEAN_FALSE, eCSR_ROAM_RESULT_FAILURE))
+        {
+            csrScanStartIdleScan(pMac);
+        }
+    }
+
+    return (status);    
+}
+
+
+
+eHalStatus csrScanHandleFailedLostlink3(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    smsLog(pMac, LOGW, "  Lostlink scan 3 failed\n");
+    if(eANI_BOOLEAN_TRUE == csrRoamCompleteRoaming(pMac, sessionId, eANI_BOOLEAN_FALSE, eCSR_ROAM_RESULT_FAILURE))
+    {
+        //we are done with lostlink
+        csrScanStartIdleScan(pMac);
+    }
+    
+    return (status);    
+}
+
+
+
+
+//Lostlink1 scan is to actively scan the last connected profile's SSID on all matched BSS channels.
+//If no roam profile (it should not), it is like lostlinkscan3
+eHalStatus csrScanRequestLostLink1( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand = NULL;
+    tANI_U8 bAddr[6] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+    tCsrScanResultFilter *pScanFilter = NULL;
+    tScanResultHandle hBSSList = NULL;
+    tCsrScanResultInfo *pScanResult = NULL;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, FL(" called\n"));
+    do
+    {
+        pCommand = csrGetCommandBuffer(pMac);
+        if(!pCommand)
+        {
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        palZeroMemory(pMac->hHdd, &pCommand->u.scanCmd, sizeof(tScanCmd));
+        pCommand->command = eSmeCommandScan;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.scanCmd.reason = eCsrScanLostLink1;
+        pCommand->u.scanCmd.callback = NULL;
+        pCommand->u.scanCmd.pContext = NULL;
+        pCommand->u.scanCmd.u.scanRequest.maxChnTime = pMac->roam.configParam.nActiveMaxChnTime;
+        pCommand->u.scanCmd.u.scanRequest.minChnTime = pMac->roam.configParam.nActiveMinChnTime;
+        pCommand->u.scanCmd.u.scanRequest.scanType = eSIR_ACTIVE_SCAN;
+        if(pSession->connectedProfile.SSID.length)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pCommand->u.scanCmd.u.scanRequest.SSIDs.SSIDList, sizeof(tCsrSSIDInfo));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            pCommand->u.scanCmd.u.scanRequest.SSIDs.numOfSSIDs = 1;
+            palCopyMemory(pMac->hHdd, &pCommand->u.scanCmd.u.scanRequest.SSIDs.SSIDList[0].SSID, 
+                                &pSession->connectedProfile.SSID, sizeof(tSirMacSSid));
+        }
+        else
+        {
+            pCommand->u.scanCmd.u.scanRequest.SSIDs.numOfSSIDs = 0;
+        }
+        if(pSession->pCurRoamProfile)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            status = csrRoamPrepareFilterFromProfile(pMac, pSession->pCurRoamProfile, pScanFilter);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            //Don't change variable status here because whether we can get result or not, the command goes to PE.
+            //The status is also used to indicate whether the command is queued. Not success meaning not queue
+            if(HAL_STATUS_SUCCESS((csrScanGetResult(pMac, pScanFilter, &hBSSList))) && hBSSList)
+            {
+                tANI_U8 i, nChn = 0;
+                status = palAllocateMemory(pMac->hHdd, (void **)&pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList,
+                            WNI_CFG_VALID_CHANNEL_LIST_LEN);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    break;
+                }
+                while(((pScanResult = csrScanResultGetNext(pMac, hBSSList)) != NULL) &&
+                    nChn < WNI_CFG_VALID_CHANNEL_LIST_LEN)
+                {
+                    for(i = 0; i < nChn; i++)
+                    {
+                        if(pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[i] == 
+                                        pScanResult->BssDescriptor.channelId)
+                        {
+                            break;
+                        }
+                    }
+                    if(i == nChn)
+                    {
+                        pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[nChn++] = pScanResult->BssDescriptor.channelId;
+                    }
+                }
+                //Include the last connected BSS' channel
+                if(csrRoamIsChannelValid(pMac, pSession->connectedProfile.operationChannel))
+                {
+                    for(i = 0; i < nChn; i++)
+                    {
+                        if(pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[i] == 
+                                        pSession->connectedProfile.operationChannel)
+                        {
+                            break;
+                        }
+                    }
+                    if(i == nChn)
+                    {
+                        pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[nChn++] = pSession->connectedProfile.operationChannel;
+                    }
+                }
+                pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = nChn;
+            }
+            else
+            {
+                if(csrRoamIsChannelValid(pMac, pSession->connectedProfile.operationChannel))
+                {
+                    status = palAllocateMemory(pMac->hHdd, (void **)&pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList,
+                                1);
+                    //just try the last connected channel
+                    if(HAL_STATUS_SUCCESS(status))
+                    {
+                        pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[0] = pSession->connectedProfile.operationChannel;
+                        pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = 1;
+                    }
+                    else 
+                    {
+                        break;
+                    }
+                }
+            }
+        }
+        palCopyMemory(pMac->hHdd, &pCommand->u.scanCmd.u.scanRequest.bssid, bAddr, sizeof(tCsrBssid));
+        status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_FALSE);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            break;
+        }
+    } while( 0 );
+
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        smsLog(pMac, LOGW, " csrScanRequestLostLink1 failed with status %d\n", status);
+        if(pCommand)
+        {
+            csrReleaseCommandScan(pMac, pCommand);
+        }
+        status = csrScanHandleFailedLostlink1( pMac, sessionId );
+    }
+    if(pScanFilter)
+    {
+        csrFreeScanFilter(pMac, pScanFilter);
+        palFreeMemory(pMac->hHdd, pScanFilter);
+    }
+    if(hBSSList)
+    {
+        csrScanResultPurge(pMac, hBSSList);
+    }
+
+    return( status );
+}
+
+
+//Lostlink2 scan is to actively scan the all SSIDs of the last roaming profile's on all matched BSS channels.
+//Since MAC doesn't support multiple SSID, we scan all SSIDs and filter them afterwards
+eHalStatus csrScanRequestLostLink2( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U8 bAddr[6] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+    tCsrScanResultFilter *pScanFilter = NULL;
+    tScanResultHandle hBSSList = NULL;
+    tCsrScanResultInfo *pScanResult = NULL;
+    tSmeCmd *pCommand = NULL;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, FL(" called\n"));
+    do
+    {
+        pCommand = csrGetCommandBuffer(pMac);
+        if(!pCommand)
+        {
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        palZeroMemory(pMac->hHdd, &pCommand->u.scanCmd, sizeof(tScanCmd));
+        pCommand->command = eSmeCommandScan;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.scanCmd.reason = eCsrScanLostLink2;
+        pCommand->u.scanCmd.callback = NULL;
+        pCommand->u.scanCmd.pContext = NULL;
+        pCommand->u.scanCmd.u.scanRequest.maxChnTime = pMac->roam.configParam.nActiveMaxChnTime;
+        pCommand->u.scanCmd.u.scanRequest.minChnTime = pMac->roam.configParam.nActiveMinChnTime;
+        pCommand->u.scanCmd.u.scanRequest.scanType = eSIR_ACTIVE_SCAN;
+        if(pSession->pCurRoamProfile)
+        {
+            status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            status = csrRoamPrepareFilterFromProfile(pMac, pSession->pCurRoamProfile, pScanFilter);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                break;
+            }
+            if(hBSSList)
+            {
+                tANI_U8 i, nChn = 0;
+                status = palAllocateMemory(pMac->hHdd, (void **)&pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList,
+                            WNI_CFG_VALID_CHANNEL_LIST_LEN);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    break;
+                }
+                while(((pScanResult = csrScanResultGetNext(pMac, hBSSList)) != NULL) &&
+                    nChn < WNI_CFG_VALID_CHANNEL_LIST_LEN)
+                {
+                    for(i = 0; i < nChn; i++)
+                    {
+                        if(pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[i] == 
+                                        pScanResult->BssDescriptor.channelId)
+                        {
+                            break;
+                        }
+                    }
+                    if(i == nChn)
+                    {
+                        pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[nChn++] = pScanResult->BssDescriptor.channelId;
+                    }
+                }
+                pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = nChn;
+            }
+        }
+        palCopyMemory(pMac->hHdd, &pCommand->u.scanCmd.u.scanRequest.bssid, bAddr, sizeof(tCsrBssid));
+        //Put to the head in pending queue
+        status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_TRUE);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            break;
+        }
+    } while( 0 );
+
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        smsLog(pMac, LOGW, " csrScanRequestLostLink2 failed with status %d\n", status);
+        if(pCommand)
+        {
+            csrReleaseCommandScan(pMac, pCommand);
+        }
+        status = csrScanHandleFailedLostlink2( pMac, sessionId );
+    }
+    if(pScanFilter)
+    {
+        csrFreeScanFilter(pMac, pScanFilter);
+        palFreeMemory(pMac->hHdd, pScanFilter);
+    }
+    if(hBSSList)
+    {
+        csrScanResultPurge(pMac, hBSSList);
+    }
+
+    return( status );
+}
+
+
+//To actively scan all valid channels
+eHalStatus csrScanRequestLostLink3( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand;
+    tANI_U8 bAddr[6] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+
+    smsLog(pMac, LOGW, FL(" called\n"));
+    do
+    {
+        pCommand = csrGetCommandBuffer(pMac);
+        if(!pCommand)
+        {
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        palZeroMemory(pMac->hHdd, &pCommand->u.scanCmd, sizeof(tScanCmd));
+        pCommand->command = eSmeCommandScan;
+        pCommand->sessionId = (tANI_U8)sessionId;
+        pCommand->u.scanCmd.reason = eCsrScanLostLink3;
+        pCommand->u.scanCmd.callback = NULL;
+        pCommand->u.scanCmd.pContext = NULL;
+        pCommand->u.scanCmd.u.scanRequest.maxChnTime = pMac->roam.configParam.nActiveMaxChnTime;
+        pCommand->u.scanCmd.u.scanRequest.minChnTime = pMac->roam.configParam.nActiveMinChnTime;
+        pCommand->u.scanCmd.u.scanRequest.scanType = eSIR_ACTIVE_SCAN;
+        palCopyMemory(pMac->hHdd, &pCommand->u.scanCmd.u.scanRequest.bssid, bAddr, sizeof(tCsrBssid));
+        //Put to the head of pending queue
+        status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_TRUE);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            break;
+        }
+    } while( 0 );
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        smsLog(pMac, LOGW, " csrScanRequestLostLink3 failed with status %d\n", status);
+        if(csrRoamCompleteRoaming(pMac, sessionId, eANI_BOOLEAN_FALSE, eCSR_ROAM_RESULT_FAILURE))
+        {
+            csrScanStartIdleScan(pMac);
+        }
+        if(pCommand)
+        {
+            csrReleaseCommandScan(pMac, pCommand);
+        }
+    }
+
+    return( status );
+}
+
+
+eHalStatus csrScanHandleSearchForSSID(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tScanResultHandle hBSSList = CSR_INVALID_SCANRESULT_HANDLE;
+    tCsrScanResultFilter *pScanFilter = NULL;
+    tCsrRoamProfile *pProfile = pCommand->u.scanCmd.pToRoamProfile;
+    tANI_U32 sessionId = pCommand->sessionId;
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+#endif
+    do
+    {
+        //If there is roam command waiting, ignore this roam because the newer roam command is the one to execute
+        if(csrIsRoamCommandWaitingForSession(pMac, sessionId))
+        {
+            smsLog(pMac, LOGW, FL(" aborts because roam command waiting\n"));
+            break;
+        }
+        if(pProfile == NULL)
+            break;
+        status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+        if(!HAL_STATUS_SUCCESS(status))
+            break;
+        palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+        status = csrRoamPrepareFilterFromProfile(pMac, pProfile, pScanFilter);
+        if(!HAL_STATUS_SUCCESS(status))
+            break;
+        status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+        if(!HAL_STATUS_SUCCESS(status))
+            break;
+        status = csrRoamIssueConnect(pMac, sessionId, pProfile, hBSSList, eCsrHddIssued, 
+                                    pCommand->u.scanCmd.roamId, eANI_BOOLEAN_TRUE, eANI_BOOLEAN_TRUE);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            break;
+        }
+    }while(0);
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        if(CSR_INVALID_SCANRESULT_HANDLE != hBSSList)
+        {
+            csrScanResultPurge(pMac, hBSSList);
+        }
+        //We haven't done anything to this profile
+        csrRoamCallCallback(pMac, sessionId, NULL, pCommand->u.scanCmd.roamId,
+                     eCSR_ROAM_ASSOCIATION_FAILURE, eCSR_ROAM_RESULT_FAILURE);
+        //In case we have nothing else to do, restart idle scan
+        if(csrIsConnStateDisconnected(pMac, sessionId) && !csrIsRoamCommandWaiting(pMac))
+        {
+            status = csrScanStartIdleScan(pMac);
+        }
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+        //In case of WDS station, let it retry.
+        if( CSR_IS_WDS_STA(pProfile) )
+        {
+            //Save the roma profile so we can retry
+            csrFreeRoamProfile( pMac, sessionId );
+            if (HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, 
+                                  (void **)&pSession->pCurRoamProfile,
+                                  sizeof(tCsrRoamProfile))))
+            {
+                palZeroMemory(pMac->hHdd, pSession->pCurRoamProfile, sizeof(tCsrRoamProfile));
+                csrRoamCopyProfile(pMac, pSession->pCurRoamProfile, pProfile);
+            }
+            csrRoamStartJoinRetryTimer(pMac, sessionId, CSR_JOIN_RETRY_TIMEOUT_PERIOD);
+        }
+#endif
+    }
+    if(pScanFilter)
+    {
+        csrFreeScanFilter(pMac, pScanFilter);
+        palFreeMemory(pMac->hHdd, pScanFilter);
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrScanHandleSearchForSSIDFailure(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 sessionId = pCommand->sessionId;
+    tCsrRoamProfile *pProfile = pCommand->u.scanCmd.pToRoamProfile;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+#if defined(WLAN_DEBUG)
+    if(pCommand->u.scanCmd.u.scanRequest.SSIDs.numOfSSIDs == 1)
+    {
+        char str[36];
+        palCopyMemory(pMac->hHdd, str, pCommand->u.scanCmd.u.scanRequest.SSIDs.SSIDList[0].SSID.ssId,
+            pCommand->u.scanCmd.u.scanRequest.SSIDs.SSIDList[0].SSID.length);
+        str[pCommand->u.scanCmd.u.scanRequest.SSIDs.SSIDList[0].SSID.length] = 0;
+        smsLog(pMac, LOGW, FL(" SSID = %s\n"), str);
+    }
+#endif
+    //Check whether it is for start ibss. No need to do anything if it is a JOIN request
+    if(pProfile && CSR_IS_START_IBSS(pProfile))
+    {
+        status = csrRoamIssueConnect(pMac, sessionId, pProfile, NULL, eCsrHddIssued, 
+                                        pCommand->u.scanCmd.roamId, eANI_BOOLEAN_TRUE, eANI_BOOLEAN_TRUE);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            smsLog(pMac, LOGE, FL("failed to issue startIBSS command with status = 0x%08X\n"), status);
+            csrRoamCallCallback(pMac, sessionId, NULL, pCommand->u.scanCmd.roamId, eCSR_ROAM_FAILED, eCSR_ROAM_RESULT_FAILURE);
+        }
+    }
+    else 
+    {
+        eCsrRoamResult roamResult = eCSR_ROAM_RESULT_FAILURE;
+
+        if(csrIsConnStateDisconnected(pMac, sessionId) &&
+          !csrIsRoamCommandWaitingForSession(pMac, sessionId))
+        {
+            status = csrScanStartIdleScan(pMac);
+        }
+        if((NULL == pProfile) || !csrIsBssTypeIBSS(pProfile->BSSType))
+        {
+            //Only indicate assoc_completion if we indicate assoc_start.
+            if(pSession->bRefAssocStartCnt > 0)
+            {
+                tCsrRoamInfo *pRoamInfo = NULL, roamInfo;
+                palZeroMemory(pMac->hHdd, &roamInfo, sizeof(tCsrRoamInfo));
+                pRoamInfo = &roamInfo;
+                if(pCommand->u.roamCmd.pRoamBssEntry)
+                {
+                    tCsrScanResult *pScanResult = 
+                                GET_BASE_ADDR(pCommand->u.roamCmd.pRoamBssEntry,
+                                tCsrScanResult, Link);
+                    roamInfo.pBssDesc = &pScanResult->Result.BssDescriptor;
+                }
+                roamInfo.statusCode = pSession->joinFailStatusCode.statusCode;
+                roamInfo.reasonCode = pSession->joinFailStatusCode.reasonCode;
+                pSession->bRefAssocStartCnt--;
+                csrRoamCallCallback(pMac, sessionId, pRoamInfo,
+                                    pCommand->u.scanCmd.roamId,
+                                    eCSR_ROAM_ASSOCIATION_COMPLETION,
+                                    eCSR_ROAM_RESULT_FAILURE);
+            }
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+            //In case of WDS station, let it retry.
+            if( CSR_IS_WDS_STA(pProfile) )
+            {
+                //Save the roma profile so we can retry
+                csrFreeRoamProfile( pMac, sessionId );
+                if (HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, 
+                                      (void **)&pSession->pCurRoamProfile,
+                                      sizeof(tCsrRoamProfile))))
+                {
+                    palZeroMemory(pMac->hHdd, pSession->pCurRoamProfile, sizeof(tCsrRoamProfile));
+                    csrRoamCopyProfile(pMac, pSession->pCurRoamProfile, pProfile);
+                }
+                csrRoamStartJoinRetryTimer(pMac, sessionId, CSR_JOIN_RETRY_TIMEOUT_PERIOD);
+            }
+#endif
+        }
+        else
+        {
+            roamResult = eCSR_ROAM_RESULT_IBSS_START_FAILED;
+        }
+        csrRoamCompletion(pMac, sessionId, NULL, pCommand, roamResult, eANI_BOOLEAN_FALSE);
+    }
+
+    return (status);
+}
+
+
+//After scan for cap changes, issue a roaming command to either reconnect to the AP or pick another one to connect
+eHalStatus csrScanHandleCapChangeScanComplete(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tScanResultHandle hBSSList = NULL;
+    tCsrScanResultFilter *pScanFilter = NULL;
+    tANI_U32 roamId = 0;
+    tCsrRoamProfile *pProfile = NULL;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    do
+    {
+        //Here is the profile we need to connect to
+        status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+        if(!HAL_STATUS_SUCCESS(status))
+            break;
+        palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+        if(NULL == pSession) break;
+        if(NULL == pSession->pCurRoamProfile)
+        {
+            pScanFilter->EncryptionType.numEntries = 1;
+            pScanFilter->EncryptionType.encryptionType[0] = eCSR_ENCRYPT_TYPE_NONE;
+        }
+        else
+        {
+            //We have to make a copy of pCurRoamProfile because it will be free inside csrRoamIssueConnect
+            status = palAllocateMemory(pMac->hHdd, (void **)&pProfile, sizeof(tCsrRoamProfile));
+            if(!HAL_STATUS_SUCCESS(status))
+                break;
+            status = csrRoamCopyProfile(pMac, pProfile, pSession->pCurRoamProfile);
+            if(!HAL_STATUS_SUCCESS(status))
+                break;
+            status = csrRoamPrepareFilterFromProfile(pMac, pProfile, pScanFilter);
+        }//We have a profile
+        roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                //we want to put the last connected BSS to the very beginning, if possible
+                csrMoveBssToHeadFromBSSID(pMac, &pSession->connectedProfile.bssid, hBSSList);
+                status = csrRoamIssueConnect(pMac, sessionId, pProfile, hBSSList, 
+                                            eCsrCapsChange, 0, eANI_BOOLEAN_TRUE, eANI_BOOLEAN_TRUE);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    csrScanResultPurge(pMac, hBSSList);
+                }
+            }//Have scan result
+            else
+            {
+                smsLog(pMac, LOGW, FL("cannot find matching BSS of %02X-%02X-%02X-%02X-%02X-%02X\n"), 
+                        pSession->connectedProfile.bssid[0],
+                        pSession->connectedProfile.bssid[1],
+                        pSession->connectedProfile.bssid[2],
+                        pSession->connectedProfile.bssid[3],
+                        pSession->connectedProfile.bssid[4],
+                        pSession->connectedProfile.bssid[5]);
+                //Disconnect
+                csrRoamDisconnectInternal(pMac, sessionId, eCSR_DISCONNECT_REASON_UNSPECIFIED);
+            }
+        }
+    }while(0);
+    if(pScanFilter)
+    {
+        csrFreeScanFilter(pMac, pScanFilter);
+        palFreeMemory(pMac->hHdd, pScanFilter);
+    }
+    if(NULL != pProfile)
+    {
+        csrReleaseProfile(pMac, pProfile);
+        palFreeMemory(pMac->hHdd, pProfile);
+    }
+
+    return (status);
+}
+
+
+
+eHalStatus csrScanResultPurge(tpAniSirGlobal pMac, tScanResultHandle hScanList)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tScanResultList *pScanList = (tScanResultList *)hScanList;
+     
+    if(pScanList)
+    {
+        status = csrLLScanPurgeResult(pMac, &pScanList->List);
+        csrLLClose(&pScanList->List);
+        palFreeMemory(pMac->hHdd, pScanList);
+    }
+    return (status);
+}
+
+
+static tANI_U32 csrGetBssPreferValue(tpAniSirGlobal pMac, int rssi)
+{
+    tANI_U32 ret = 0;
+    int i = CSR_NUM_RSSI_CAT - 1;
+
+    while(i >= 0)
+    {
+        if(rssi >= pMac->roam.configParam.RSSICat[i])
+        {
+            ret = pMac->roam.configParam.BssPreferValue[i];
+            break;
+        }
+        i--;
+    };
+
+    return (ret);
+}
+
+
+//Return a CapValue base on the capabilities of a BSS
+static tANI_U32 csrGetBssCapValue(tpAniSirGlobal pMac, tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes)
+{
+    tANI_U32 ret = CSR_BSS_CAP_VALUE_NONE;
+
+    if( pIes )
+    {
+        //We only care about 11N capability
+        if(pIes->HTCaps.present)
+        {
+            ret += CSR_BSS_CAP_VALUE_HT;
+        }
+        if(CSR_IS_QOS_BSS(pIes))
+        {
+            ret += CSR_BSS_CAP_VALUE_WMM;
+            //Give advantage to UAPSD
+            if(CSR_IS_UAPSD_BSS(pIes))
+            {
+                ret += CSR_BSS_CAP_VALUE_UAPSD;
+            }
+        }
+    }
+
+    return (ret);
+}
+
+
+//To check whther pBss1 is better than pBss2
+static tANI_BOOLEAN csrIsBetterBss(tCsrScanResult *pBss1, tCsrScanResult *pBss2)
+{
+    tANI_BOOLEAN ret;
+
+    if(CSR_IS_BETTER_PREFER_VALUE(pBss1->preferValue, pBss2->preferValue))
+    {
+        ret = eANI_BOOLEAN_TRUE;
+    }
+    else if(CSR_IS_EQUAL_PREFER_VALUE(pBss1->preferValue, pBss2->preferValue))
+    {
+        if(CSR_IS_BETTER_CAP_VALUE(pBss1->capValue, pBss2->capValue))
+        {
+            ret = eANI_BOOLEAN_TRUE;
+        }
+        else
+        {
+            ret = eANI_BOOLEAN_FALSE;
+        }
+    }
+    else
+    {
+        ret = eANI_BOOLEAN_FALSE;
+    }
+
+    return (ret);
+}
+
+
+//Put the BSS into the scan result list
+//pIes can not be NULL
+static void csrScanAddResult(tpAniSirGlobal pMac, tCsrScanResult *pResult, tDot11fBeaconIEs *pIes)
+{
+    pResult->preferValue = csrGetBssPreferValue(pMac, (int)pResult->Result.BssDescriptor.rssi);
+    pResult->capValue = csrGetBssCapValue(pMac, &pResult->Result.BssDescriptor, pIes);
+    csrLLInsertTail( &pMac->scan.scanResultList, &pResult->Link, LL_ACCESS_LOCK );
+}
+
+
+eHalStatus csrScanGetResult(tpAniSirGlobal pMac, tCsrScanResultFilter *pFilter, tScanResultHandle *phResult)
+{
+    eHalStatus status;
+    tScanResultList *pRetList;
+    tCsrScanResult *pResult, *pBssDesc;
+    tANI_U32 count = 0;
+    tListElem *pEntry;
+    tANI_U32 bssLen, allocLen;
+    eCsrEncryptionType uc = eCSR_ENCRYPT_TYPE_NONE, mc = eCSR_ENCRYPT_TYPE_NONE;
+    eCsrAuthType auth = eCSR_AUTH_TYPE_OPEN_SYSTEM;
+    tDot11fBeaconIEs *pIes, *pNewIes;
+    tANI_BOOLEAN fMatch;
+    
+    if(phResult)
+    {
+        *phResult = CSR_INVALID_SCANRESULT_HANDLE;
+    }
+    status = palAllocateMemory(pMac->hHdd, (void **)&pRetList, sizeof(tScanResultList));
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, pRetList, sizeof(tScanResultList));
+        csrLLOpen(pMac->hHdd, &pRetList->List);
+        pRetList->pCurEntry = NULL;
+        
+        csrLLLock(&pMac->scan.scanResultList);
+        pEntry = csrLLPeekHead( &pMac->scan.scanResultList, LL_ACCESS_NOLOCK );
+        while( pEntry ) 
+        {
+            pBssDesc = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+            pIes = (tDot11fBeaconIEs *)( pBssDesc->Result.pvIes );
+            //if pBssDesc->Result.pvIes is NULL, we need to free any memory allocated by csrMatchBSS
+            //for any error condition, otherwiase, it will be freed later.
+            //reset
+            fMatch = eANI_BOOLEAN_FALSE;
+            pNewIes = NULL;
+
+            if(pFilter)
+            {
+                fMatch = csrMatchBSS(pMac, &pBssDesc->Result.BssDescriptor, pFilter, &auth, &uc, &mc, &pIes);
+                if( NULL != pIes )
+                {
+                    //Only save it when matching
+                    if(fMatch)
+                    {
+                        if( !pBssDesc->Result.pvIes )
+                        {
+                            //csrMatchBSS allocates the memory. Simply pass it and it is freed later
+                            pNewIes = pIes;
+                        }
+                        else
+                        {
+                            //The pIes is allocated by someone else. make a copy
+                            //Only to save parsed IEs if caller provides a filter. Most likely the caller
+                            //is using to for association, hence save the parsed IEs
+                            status = palAllocateMemory(pMac->hHdd, (void **)&pNewIes, sizeof(tDot11fBeaconIEs));
+                            if( HAL_STATUS_SUCCESS( status ) )
+                            {
+                                palCopyMemory( pMac->hHdd, pNewIes, pIes, sizeof( tDot11fBeaconIEs ) );
+                            }
+                            else
+                            {
+                                smsLog(pMac, LOGE, FL(" fail to allocate memory for IEs\n"));
+                                //Need to free memory allocated by csrMatchBSS
+                                if( !pBssDesc->Result.pvIes )
+                                {
+                                    palFreeMemory(pMac->hHdd, pIes);
+                                }
+                                break;
+                            }
+                        }
+                    }//fMatch
+                    else if( !pBssDesc->Result.pvIes )
+                    {
+                        palFreeMemory(pMac->hHdd, pIes);
+                    }
+                }
+            }
+            if(NULL == pFilter || fMatch)
+            {
+                bssLen = pBssDesc->Result.BssDescriptor.length + sizeof(pBssDesc->Result.BssDescriptor.length);
+                allocLen = sizeof( tCsrScanResult ) + bssLen;
+                status = palAllocateMemory(pMac->hHdd, (void **)&pResult, allocLen);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    smsLog(pMac, LOGE, FL("  fail to allocate memory for scan result, len=%d\n"), allocLen);
+                    if(pNewIes)
+                    {
+                        palFreeMemory(pMac->hHdd, pNewIes);
+                    }
+                    break;
+                }
+                palZeroMemory(pMac->hHdd, pResult, allocLen);
+                pResult->capValue = pBssDesc->capValue;
+                pResult->preferValue = pBssDesc->preferValue;
+                pResult->ucEncryptionType = uc;
+                pResult->mcEncryptionType = mc;
+                pResult->authType = auth;
+                pResult->Result.ssId = pBssDesc->Result.ssId;
+                pResult->Result.timer = 0;
+                //save the pIes for later use
+                pResult->Result.pvIes = pNewIes;
+                //save bss description
+                status = palCopyMemory(pMac->hHdd, &pResult->Result.BssDescriptor, &pBssDesc->Result.BssDescriptor, bssLen);
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    smsLog(pMac, LOGE, FL("  fail to copy memory for scan result\n"));
+                    palFreeMemory(pMac->hHdd, pResult);
+                    if(pNewIes)
+                    {
+                        palFreeMemory(pMac->hHdd, pNewIes);
+                    }
+                    break;
+                }
+                //No need to lock pRetList because it is locally allocated and no outside can access it at this time
+                if(csrLLIsListEmpty(&pRetList->List, LL_ACCESS_NOLOCK))
+                {
+                    csrLLInsertTail(&pRetList->List, &pResult->Link, LL_ACCESS_NOLOCK);
+                }
+                else
+                {
+                    //To sort the list
+                    tListElem *pTmpEntry;
+                    tCsrScanResult *pTmpResult;
+                    
+                    pTmpEntry = csrLLPeekHead(&pRetList->List, LL_ACCESS_NOLOCK);
+                    while(pTmpEntry)
+                    {
+                        pTmpResult = GET_BASE_ADDR( pTmpEntry, tCsrScanResult, Link );
+                        if(csrIsBetterBss(pResult, pTmpResult))
+                        {
+                            csrLLInsertEntry(&pRetList->List, pTmpEntry, &pResult->Link, LL_ACCESS_NOLOCK);
+                            //To indicate we are done
+                            pResult = NULL;
+                            break;
+                        }
+                        pTmpEntry = csrLLNext(&pRetList->List, pTmpEntry, LL_ACCESS_NOLOCK);
+                    }
+                    if(pResult != NULL)
+                    {
+                        //This one is not better than any one
+                        csrLLInsertTail(&pRetList->List, &pResult->Link, LL_ACCESS_NOLOCK);
+                    }
+                }
+                count++;
+            }
+            pEntry = csrLLNext( &pMac->scan.scanResultList, pEntry, LL_ACCESS_NOLOCK );
+        }//while
+        csrLLUnlock(&pMac->scan.scanResultList);
+        
+        smsLog(pMac, LOG2, FL("return %d BSS\n"), csrLLCount(&pRetList->List));
+        
+        if( !HAL_STATUS_SUCCESS(status) || (phResult == NULL) )
+        {
+            //Fail or No one wants the result.
+            csrScanResultPurge(pMac, (tScanResultHandle)pRetList);
+        }
+        else
+        {
+            if(0 == count)
+            {
+                //We are here meaning the there is no match
+                csrLLClose(&pRetList->List);
+                palFreeMemory(pMac->hHdd, pRetList);
+                status = eHAL_STATUS_E_NULL_VALUE;
+            }
+            else if(phResult)
+            {
+                *phResult = pRetList;
+            }
+        }
+    }//Allocated pRetList
+    
+    return (status);
+}
+
+
+eHalStatus csrScanFlushResult(tpAniSirGlobal pMac)
+{
+    return ( csrLLScanPurgeResult(pMac, &pMac->scan.scanResultList) );
+}
+
+/**
+ * csrCheck11dChannel
+ *
+ *FUNCTION:
+ * This function is called from csrScanFilter11dResult function and
+ * compare channel number with given channel list.
+ *
+ *LOGIC:
+ * Check Scan result channel number with CFG channel list
+ *
+ *ASSUMPTIONS:
+ *
+ *
+ *NOTE:
+ *
+ * @param  channelId      channel number
+ * @param  pChannelList   Pointer to channel list
+ * @param  numChannels    Number of channel in channel list
+ *
+ * @return Status
+ */
+
+eHalStatus csrCheck11dChannel(tANI_U8 channelId, tANI_U8 *pChannelList, tANI_U32 numChannels)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tANI_U8 i = 0;
+
+    for (i = 0; i < numChannels; i++)
+    {
+        if(pChannelList[ i ] == channelId)
+        {
+            status = eHAL_STATUS_SUCCESS;
+            break;
+        }
+    }
+    return status;
+}
+
+/**
+ * csrScanFilter11dResult
+ *
+ *FUNCTION:
+ * This function is called from csrApplyCountryInformation function and
+ * filter scan result based on valid channel list number.
+ *
+ *LOGIC:
+ * Get scan result from scan list and Check Scan result channel number
+ * with 11d channel list if channel number is found in 11d channel list
+ * then do not remove scan result entry from scan list
+ *
+ *ASSUMPTIONS:
+ *
+ *
+ *NOTE:
+ *
+ * @param  pMac        Pointer to Global MAC structure
+ *
+ * @return Status
+ */
+
+eHalStatus csrScanFilter11dResult(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tListElem *pEntry,*pTempEntry;
+    tCsrScanResult *pBssDesc;
+    tANI_U32 len = sizeof(pMac->roam.validChannelList);
+
+    /* Get valid channels list from CFG */
+    if (!HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac,
+                                      pMac->roam.validChannelList, &len)))
+    {
+        smsLog( pMac, LOG1, "Failed to get Channel list from CFG");
+    }
+
+    pEntry = csrLLPeekHead( &pMac->scan.scanResultList, LL_ACCESS_LOCK );
+    while( pEntry )
+    {
+        pBssDesc = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+        pTempEntry = csrLLNext( &pMac->scan.scanResultList, pEntry, 
+                                                            LL_ACCESS_LOCK );
+        if(csrCheck11dChannel(pBssDesc->Result.BssDescriptor.channelId,
+                                              pMac->roam.validChannelList, len))
+        {
+            /* Remove Scan result which does not have 11d channel */
+            if( csrLLRemoveEntry( &pMac->scan.scanResultList, pEntry,
+                                                              LL_ACCESS_LOCK ))
+            {
+                csrFreeScanResultEntry( pMac, pBssDesc );
+            }
+        }
+        pEntry = pTempEntry;
+    }
+    return status;
+}
+
+
+eHalStatus csrScanCopyResultList(tpAniSirGlobal pMac, tScanResultHandle hIn, tScanResultHandle *phResult)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tScanResultList *pRetList, *pInList = (tScanResultList *)hIn;
+    tCsrScanResult *pResult, *pScanResult;
+    tANI_U32 count = 0;
+    tListElem *pEntry;
+    tANI_U32 bssLen, allocLen;
+    
+    if(phResult)
+    {
+        *phResult = CSR_INVALID_SCANRESULT_HANDLE;
+    }
+    status = palAllocateMemory(pMac->hHdd, (void **)&pRetList, sizeof(tScanResultList));
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, pRetList, sizeof(tScanResultList));
+        csrLLOpen(pMac->hHdd, &pRetList->List);
+        pRetList->pCurEntry = NULL;
+        csrLLLock(&pMac->scan.scanResultList);
+        csrLLLock(&pInList->List);
+        
+        pEntry = csrLLPeekHead( &pInList->List, LL_ACCESS_NOLOCK );
+        while( pEntry ) 
+        {
+            pScanResult = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+            bssLen = pScanResult->Result.BssDescriptor.length + sizeof(pScanResult->Result.BssDescriptor.length);
+            allocLen = sizeof( tCsrScanResult ) + bssLen;
+            status = palAllocateMemory(pMac->hHdd, (void **)&pResult, allocLen);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                csrScanResultPurge(pMac, (tScanResultHandle *)pRetList);
+                count = 0;
+                break;
+            }
+            palZeroMemory(pMac->hHdd, pResult, allocLen);
+            status = palCopyMemory(pMac->hHdd, &pResult->Result.BssDescriptor, &pScanResult->Result.BssDescriptor, bssLen);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                csrScanResultPurge(pMac, (tScanResultHandle *)pRetList);
+                count = 0;
+                break;
+            }
+            if( pScanResult->Result.pvIes )
+            {
+                status = palAllocateMemory(pMac->hHdd, (void **)&pResult->Result.pvIes, sizeof( tDot11fBeaconIEs ));
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    //Free the memory we allocate above first
+                    palFreeMemory( pMac->hHdd, pResult );
+                    csrScanResultPurge(pMac, (tScanResultHandle *)pRetList);
+                    count = 0;
+                    break;
+                }
+                status = palCopyMemory(pMac->hHdd, pResult->Result.pvIes, 
+                                pScanResult->Result.pvIes, sizeof( tDot11fBeaconIEs ));
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    //Free the memory we allocate above first
+                    palFreeMemory( pMac->hHdd, pResult );
+                    csrScanResultPurge(pMac, (tScanResultHandle *)pRetList);
+                    count = 0;
+                    break;
+                }
+            }
+            csrLLInsertTail(&pRetList->List, &pResult->Link, LL_ACCESS_LOCK);
+            count++;
+            pEntry = csrLLNext( &pInList->List, pEntry, LL_ACCESS_NOLOCK );
+        }//while
+        csrLLUnlock(&pInList->List);
+        csrLLUnlock(&pMac->scan.scanResultList);
+        
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            if(0 == count)
+            {
+                csrLLClose(&pRetList->List);
+                palFreeMemory(pMac->hHdd, pRetList);
+                status = eHAL_STATUS_E_NULL_VALUE;
+            }
+            else if(phResult)
+            {
+                *phResult = pRetList;
+            }
+        }
+    }//Allocated pRetList
+    
+    return (status);
+}
+
+
+ 
+eHalStatus csrScanningStateMsgProcessor( tpAniSirGlobal pMac, void *pMsgBuf )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirMbMsg *pMsg = (tSirMbMsg *)pMsgBuf;
+
+    if((eWNI_SME_SCAN_RSP == pMsg->type) || (eWNI_SME_GET_SCANNED_CHANNEL_RSP == pMsg->type))
+    {
+        status = csrScanSmeScanResponse( pMac, pMsgBuf );
+    }
+    else
+    {
+        if( csrIsAnySessionInConnectState( pMac ) )
+        {
+            //In case of we are connected, we need to check whether connect status changes
+            //because scan may also run while connected.
+            csrRoamCheckForLinkStatusChange( pMac, ( tSirSmeRsp * )pMsgBuf );
+        }
+        else
+        {
+            smsLog( pMac, LOGW, "Message [0x%04x] received in state, when expecting Scan Response\n", pMsg->type );
+        }
+    }
+
+    return (status);
+}
+
+
+
+void csrCheckNSaveWscIe(tpAniSirGlobal pMac, tSirBssDescription *pNewBssDescr, tSirBssDescription *pOldBssDescr)
+{
+    int idx, len;
+    tANI_U8 *pbIe;
+
+    //If failed to remove, assuming someone else got it.
+    if((pNewBssDescr->fProbeRsp != pOldBssDescr->fProbeRsp) &&
+       (0 == pNewBssDescr->WscIeLen))
+    {
+        idx = 0;
+        len = pOldBssDescr->length - sizeof(tSirBssDescription) + 
+                sizeof(tANI_U16) + sizeof(tANI_U32) - DOT11F_IE_WSCPROBERES_MIN_LEN - 2;
+        pbIe = (tANI_U8 *)pOldBssDescr->ieFields;
+        //Save WPS IE if it exists
+        pNewBssDescr->WscIeLen = 0;
+        while(idx < len)
+        {
+            if((DOT11F_EID_WSCPROBERES == pbIe[0]) &&
+                (0x00 == pbIe[2]) && (0x50 == pbIe[3]) && (0xf2 == pbIe[4]) && (0x04 == pbIe[5]))
+            {
+                //Founrd it
+                if((DOT11F_IE_WSCPROBERES_MAX_LEN - 2) >= pbIe[1])
+                {
+                    palCopyMemory(pMac->hHdd, pNewBssDescr->WscIeProbeRsp,
+                                   pbIe, pbIe[1] + 2);
+                    pNewBssDescr->WscIeLen = pbIe[1] + 2;
+                }
+                break;
+            }
+            idx += pbIe[1] + 2;
+            pbIe += pbIe[1] + 2;
+        }
+    }
+}
+
+
+
+//pIes may be NULL
+tANI_BOOLEAN csrRemoveDupBssDescription( tpAniSirGlobal pMac, tSirBssDescription *pSirBssDescr,
+                                         tDot11fBeaconIEs *pIes, tAniSSID *pSsid , v_TIME_t *timer ) 
+{
+    tListElem *pEntry;
+
+    tCsrScanResult *pBssDesc;
+    tANI_BOOLEAN fRC = FALSE;
+
+    // Walk through all the chained BssDescriptions.  If we find a chained BssDescription that
+    // matches the BssID of the BssDescription passed in, then these must be duplicate scan
+    // results for this Bss.  In that case, remove the 'old' Bss description from the linked list.
+    pEntry = csrLLPeekHead( &pMac->scan.scanResultList, LL_ACCESS_LOCK );
+
+    while( pEntry ) 
+    {
+        pBssDesc = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+
+        // we have a duplicate scan results only when BSSID, SSID, Channel and NetworkType
+        // matches
+        if ( csrIsDuplicateBssDescription( pMac, &pBssDesc->Result.BssDescriptor, 
+                                                        pSirBssDescr, pIes ) )
+        {
+            pSirBssDescr->rssi = (tANI_S8)( (((tANI_S32)pSirBssDescr->rssi * CSR_SCAN_RESULT_RSSI_WEIGHT ) +
+                                             ((tANI_S32)pBssDesc->Result.BssDescriptor.rssi * (100 - CSR_SCAN_RESULT_RSSI_WEIGHT) )) / 100 );
+            // Remove the 'old' entry from the list....
+            if( csrLLRemoveEntry( &pMac->scan.scanResultList, pEntry, LL_ACCESS_LOCK ) )
+            {
+                // !we need to free the memory associated with this node
+                //If failed to remove, assuming someone else got it.
+                *pSsid = pBssDesc->Result.ssId;
+                *timer = pBssDesc->Result.timer;
+                csrCheckNSaveWscIe(pMac, pSirBssDescr, &pBssDesc->Result.BssDescriptor);
+                
+                csrFreeScanResultEntry( pMac, pBssDesc );
+            }
+            else
+            {
+                smsLog( pMac, LOGW, FL( "  fail to remove entry\n" ) );
+            }
+            fRC = TRUE;
+
+            // If we found a match, we can stop looking through the list.
+            break;
+        }
+
+        pEntry = csrLLNext( &pMac->scan.scanResultList, pEntry, LL_ACCESS_LOCK );
+    }
+
+    return fRC;
+}
+
+
+eHalStatus csrAddPMKIDCandidateList( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                     tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, "csrAddPMKIDCandidateList called pMac->scan.NumPmkidCandidate = %d\n", pSession->NumPmkidCandidate);
+    if( pIes )
+    {
+        // check if this is a RSN BSS
+        if( pIes->RSN.present )
+        {
+            // Check if the BSS is capable of doing pre-authentication
+            if( pSession->NumPmkidCandidate < CSR_MAX_PMKID_ALLOWED )
+            {
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                {
+                    WLAN_VOS_DIAG_EVENT_DEF(secEvent, vos_event_wlan_security_payload_type);
+                    palZeroMemory(pMac->hHdd, &secEvent, sizeof(vos_event_wlan_security_payload_type));
+                    secEvent.eventId = WLAN_SECURITY_EVENT_PMKID_CANDIDATE_FOUND;
+                    secEvent.encryptionModeMulticast = 
+                        (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.mcEncryptionType);
+                    secEvent.encryptionModeUnicast = 
+                        (v_U8_t)diagEncTypeFromCSRType(pSession->connectedProfile.EncryptionType);
+                    palCopyMemory( pMac->hHdd, secEvent.bssid, pSession->connectedProfile.bssid, 6 );
+                    secEvent.authMode = 
+                        (v_U8_t)diagAuthTypeFromCSRType(pSession->connectedProfile.AuthType);
+                    WLAN_VOS_DIAG_EVENT_REPORT(&secEvent, EVENT_WLAN_SECURITY);
+                }
+#endif//#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+                // if yes, then add to PMKIDCandidateList
+                status = palCopyMemory(pMac->hHdd, pSession->PmkidCandidateInfo[pSession->NumPmkidCandidate].BSSID, 
+                                            pBssDesc->bssId, WNI_CFG_BSSID_LEN);
+            
+                if( HAL_STATUS_SUCCESS( status ) )
+                {
+                    if ( pIes->RSN.preauth )
+                    {
+                        pSession->PmkidCandidateInfo[pSession->NumPmkidCandidate].preAuthSupported = eANI_BOOLEAN_TRUE;
+                    }
+                    else
+                    {
+                        pSession->PmkidCandidateInfo[pSession->NumPmkidCandidate].preAuthSupported = eANI_BOOLEAN_FALSE;
+                    }
+                    pSession->NumPmkidCandidate++;
+                }
+            }
+            else
+            {
+                status = eHAL_STATUS_FAILURE;
+            }
+        }
+    }
+
+    return (status);
+}
+
+//This function checks whether new AP is found for the current connected profile
+//If it is found, it return the sessionId, else it return invalid sessionID
+tANI_U32 csrProcessBSSDescForPMKIDList(tpAniSirGlobal pMac, 
+                                           tSirBssDescription *pBssDesc,
+                                           tDot11fBeaconIEs *pIes)
+{
+    tANI_U32 i, bRet = CSR_SESSION_ID_INVALID;
+    tCsrRoamSession *pSession;
+    tDot11fBeaconIEs *pIesLocal = pIes;
+
+    if( pIesLocal || HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIesLocal)) )
+    {
+        for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+        {
+            if( CSR_IS_SESSION_VALID( pMac, i ) )
+            {
+                pSession = CSR_GET_SESSION( pMac, i );
+                if( csrIsConnStateConnectedInfra( pMac, i ) && 
+                    ( eCSR_AUTH_TYPE_RSN == pSession->connectedProfile.AuthType ) )
+                {
+                    if(csrMatchBSSToConnectProfile(pMac, &pSession->connectedProfile, pBssDesc, pIesLocal))
+                    {
+                        //this new BSS fits the current profile connected
+                        if(HAL_STATUS_SUCCESS(csrAddPMKIDCandidateList(pMac, i, pBssDesc, pIesLocal)))
+                        {
+                            bRet = i;
+                        }
+                        break;
+                    }
+                }
+            }
+        }
+        if( !pIes )
+        {
+            palFreeMemory(pMac->hHdd, pIesLocal);
+        }
+    }
+
+    return (tANI_U8)bRet;
+}
+
+#ifdef FEATURE_WLAN_WAPI
+eHalStatus csrAddBKIDCandidateList( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                    tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, "csrAddBKIDCandidateList called pMac->scan.NumBkidCandidate = %d\n", pSession->NumBkidCandidate);
+    if( pIes )
+    {
+        // check if this is a WAPI BSS
+        if( pIes->WAPI.present )
+        {
+            // Check if the BSS is capable of doing pre-authentication
+            if( pSession->NumBkidCandidate < CSR_MAX_BKID_ALLOWED )
+            {
+
+                // if yes, then add to BKIDCandidateList
+                status = palCopyMemory(pMac->hHdd, pSession->BkidCandidateInfo[pSession->NumBkidCandidate].BSSID, 
+                                            pBssDesc->bssId, WNI_CFG_BSSID_LEN);
+            
+                if( HAL_STATUS_SUCCESS( status ) )
+                {
+                    if ( pIes->WAPI.preauth )
+                    {
+                        pSession->BkidCandidateInfo[pSession->NumBkidCandidate].preAuthSupported = eANI_BOOLEAN_TRUE;
+                    }
+                    else
+                    {
+                        pSession->BkidCandidateInfo[pSession->NumBkidCandidate].preAuthSupported = eANI_BOOLEAN_FALSE;
+                    }
+                    pSession->NumBkidCandidate++;
+                }
+            }
+            else
+            {
+                status = eHAL_STATUS_FAILURE;
+            }
+        }
+    }
+
+    return (status);
+}
+
+//This function checks whether new AP is found for the current connected profile
+//if so add to BKIDCandidateList
+tANI_BOOLEAN csrProcessBSSDescForBKIDList(tpAniSirGlobal pMac, tSirBssDescription *pBssDesc,
+                                          tDot11fBeaconIEs *pIes)
+{
+    tANI_BOOLEAN fRC = FALSE;
+    tDot11fBeaconIEs *pIesLocal = pIes;
+    tANI_U32 sessionId;
+    tCsrRoamSession *pSession;
+
+    if( pIesLocal || HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIesLocal)) )
+    {
+        for( sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX; sessionId++ )
+        {
+            if( CSR_IS_SESSION_VALID( pMac, sessionId) )
+            {
+                pSession = CSR_GET_SESSION( pMac, sessionId );
+                if( csrIsConnStateConnectedInfra( pMac, sessionId ) && 
+                    eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE == pSession->connectedProfile.AuthType)
+                {
+                    if(csrMatchBSSToConnectProfile(pMac, &pSession->connectedProfile,pBssDesc, pIesLocal))
+                    {
+                        //this new BSS fits the current profile connected
+                        if(HAL_STATUS_SUCCESS(csrAddBKIDCandidateList(pMac, sessionId, pBssDesc, pIesLocal)))
+                        {
+                            fRC = TRUE;
+                        }
+                    }
+                }
+            }
+        }
+        if(!pIes)
+        {
+            palFreeMemory(pMac->hHdd, pIesLocal);
+        }
+
+    }
+    return fRC;
+}
+
+#endif
+
+
+static void csrMoveTempScanResultsToMainList( tpAniSirGlobal pMac )
+{
+    tListElem *pEntry;
+    tCsrScanResult *pBssDescription;
+    tANI_S8         cand_Bss_rssi;
+    tANI_BOOLEAN    fDupBss;
+#ifdef FEATURE_WLAN_WAPI
+    tANI_BOOLEAN fNewWapiBSSForCurConnection = eANI_BOOLEAN_FALSE;
+#endif /* FEATURE_WLAN_WAPI */
+    tDot11fBeaconIEs *pIesLocal = NULL;
+    tANI_U32 sessionId = CSR_SESSION_ID_INVALID;
+    tAniSSID tmpSsid;
+    v_TIME_t timer=0;
+
+    tmpSsid.length = 0;
+    cand_Bss_rssi = -128; // RSSI coming from PE is -ve
+
+    // remove the BSS descriptions from temporary list
+    while( ( pEntry = csrLLRemoveTail( &pMac->scan.tempScanResults, LL_ACCESS_LOCK ) ) != NULL)
+    {
+        pBssDescription = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+
+        smsLog( pMac, LOGW, "...Bssid= %02x-%02x-%02x-%02x-%02x-%02x chan= %d, rssi = -%d\n",
+                      pBssDescription->Result.BssDescriptor.bssId[ 0 ], pBssDescription->Result.BssDescriptor.bssId[ 1 ],
+                      pBssDescription->Result.BssDescriptor.bssId[ 2 ], pBssDescription->Result.BssDescriptor.bssId[ 3 ],
+                      pBssDescription->Result.BssDescriptor.bssId[ 4 ], pBssDescription->Result.BssDescriptor.bssId[ 5 ],
+                      pBssDescription->Result.BssDescriptor.channelId,
+                pBssDescription->Result.BssDescriptor.rssi * (-1) );
+
+        //At this time, pBssDescription->Result.pvIes may be NULL
+        pIesLocal = (tDot11fBeaconIEs *)( pBssDescription->Result.pvIes );
+        if( !pIesLocal && (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, &pBssDescription->Result.BssDescriptor, &pIesLocal))) )
+        {
+            smsLog(pMac, LOGE, FL("  Cannot pared IEs\n"));
+            csrFreeScanResultEntry(pMac, pBssDescription);
+            continue;
+        }
+        fDupBss = csrRemoveDupBssDescription( pMac, &pBssDescription->Result.BssDescriptor, pIesLocal, &tmpSsid , &timer );
+        //Check whether we have reach out limit
+        if( CSR_SCAN_IS_OVER_BSS_LIMIT(pMac) )
+        {
+            //Limit reach
+            smsLog(pMac, LOGW, FL("  BSS limit reached\n"));
+            //Free the resources
+            if( (pBssDescription->Result.pvIes == NULL) && pIesLocal )
+            {
+                palFreeMemory(pMac->hHdd, pIesLocal);
+            }
+            csrFreeScanResultEntry(pMac, pBssDescription);
+            //Continue because there may be duplicated BSS
+            continue;
+        }
+        // check for duplicate scan results
+        if ( !fDupBss )
+        {
+            //Found a new BSS
+            sessionId = csrProcessBSSDescForPMKIDList(pMac, 
+                             &pBssDescription->Result.BssDescriptor, pIesLocal);
+            if( CSR_SESSION_ID_INVALID != sessionId)
+            {
+                csrRoamCallCallback(pMac, sessionId, NULL, 0, 
+                           eCSR_ROAM_SCAN_FOUND_NEW_BSS, eCSR_ROAM_RESULT_NONE);
+            }
+        }
+        else
+        {
+            //Check if the new one has SSID it it, if not, use the older SSID if it exists.
+            if( (0 == pBssDescription->Result.ssId.length) && tmpSsid.length )
+            {
+                //New BSS has a hidden SSID and old one has the SSID. Keep the SSID only 
+                //if diff of saved SSID time and current time is less than 1 min to avoid
+                //side effect of saving SSID with old one is that if AP changes its SSID while remain
+                //hidden, we may never see it and also to address the requirement of 
+                //When we remove hidden ssid from the profile i.e., forget the SSID via 
+                // GUI that SSID shouldn't see in the profile
+                if( (vos_timer_get_system_time() - timer) <= HIDDEN_TIMER)
+                {
+                   pBssDescription->Result.timer = timer;
+                   pBssDescription->Result.ssId = tmpSsid;
+                }
+            }
+        }
+
+        //Tush: find a good AP for 11d info
+        if( csrIs11dSupported( pMac ) )
+        {
+            if(cand_Bss_rssi < pBssDescription->Result.BssDescriptor.rssi)
+            {
+                // check if country information element is present
+                if(pIesLocal->Country.present)
+                {
+                    cand_Bss_rssi = pBssDescription->Result.BssDescriptor.rssi;
+                    // learn country information
+                    csrLearnCountryInformation( pMac, &pBssDescription->Result.BssDescriptor, 
+                             pIesLocal, eANI_BOOLEAN_FALSE );
+                }
+
+            }
+        }
+
+        // append to main list
+        csrScanAddResult(pMac, pBssDescription, pIesLocal);
+        if( (pBssDescription->Result.pvIes == NULL) && pIesLocal )
+        {
+            palFreeMemory(pMac->hHdd, pIesLocal);
+        }
+    }
+
+    //Tush: If we can find the current 11d info in any of the scan results, or
+    // a good enough AP with the 11d info from the scan results then no need to
+    // get into ambiguous state
+    if(pMac->scan.fAmbiguous11dInfoFound) 
+    {
+      if((pMac->scan.fCurrent11dInfoMatch) || (cand_Bss_rssi != -128))
+      {
+        pMac->scan.fAmbiguous11dInfoFound = eANI_BOOLEAN_FALSE;
+      }
+    }
+
+#ifdef FEATURE_WLAN_WAPI
+    if(fNewWapiBSSForCurConnection)
+    {
+        //remember it first
+        csrRoamCallCallback(pMac, sessionId, NULL, 0, eCSR_ROAM_SCAN_FOUND_NEW_BSS, eCSR_ROAM_RESULT_NEW_WAPI_BSS);
+    }
+#endif /* FEATURE_WLAN_WAPI */
+
+    return;
+}
+
+
+static tCsrScanResult *csrScanSaveBssDescription( tpAniSirGlobal pMac, tSirBssDescription *pBSSDescription,
+                                                  tDot11fBeaconIEs *pIes)
+{
+    tCsrScanResult *pCsrBssDescription = NULL;
+    tANI_U32 cbBSSDesc;
+    tANI_U32 cbAllocated;
+    eHalStatus halStatus;
+
+    // figure out how big the BSS description is (the BSSDesc->length does NOT
+    // include the size of the length field itself).
+    cbBSSDesc = pBSSDescription->length + sizeof( pBSSDescription->length );
+
+    cbAllocated = sizeof( tCsrScanResult ) + cbBSSDesc;
+
+    halStatus = palAllocateMemory( pMac->hHdd, (void **)&pCsrBssDescription, cbAllocated );
+    if ( HAL_STATUS_SUCCESS(halStatus) )
+    {
+        palZeroMemory( pMac->hHdd, pCsrBssDescription, cbAllocated );
+        pCsrBssDescription->AgingCount = (tANI_S32)pMac->roam.configParam.agingCount;
+        palCopyMemory(pMac->hHdd, &pCsrBssDescription->Result.BssDescriptor, pBSSDescription, cbBSSDesc );
+#if defined(VOSS_ENSBALED)
+        VOS_ASSERT( pCsrBssDescription->Result.pvIes == NULL );
+#endif
+        csrScanAddResult(pMac, pCsrBssDescription, pIes);
+    }
+
+    return( pCsrBssDescription );
+}
+
+// Append a Bss Description...
+tCsrScanResult *csrScanAppendBssDescription( tpAniSirGlobal pMac, 
+                                             tSirBssDescription *pSirBssDescription, 
+                                             tDot11fBeaconIEs *pIes )
+{
+    tCsrScanResult *pCsrBssDescription = NULL;
+    tAniSSID tmpSsid;
+    v_TIME_t timer = 0;
+    int result;
+
+    tmpSsid.length = 0;
+    result = csrRemoveDupBssDescription( pMac, pSirBssDescription, pIes, &tmpSsid, &timer );
+    pCsrBssDescription = csrScanSaveBssDescription( pMac, pSirBssDescription, pIes );
+    if (result && (pCsrBssDescription != NULL))
+    {
+        //Check if the new one has SSID it it, if not, use the older SSID if it exists.
+        if( (0 == pCsrBssDescription->Result.ssId.length) && tmpSsid.length )
+        {
+            //New BSS has a hidden SSID and old one has the SSID. Keep the SSID only
+            //if diff of saved SSID time and current time is less than 1 min to avoid
+            //side effect of saving SSID with old one is that if AP changes its SSID while remain
+            //hidden, we may never see it and also to address the requirement of
+            //When we remove hidden ssid from the profile i.e., forget the SSID via
+            // GUI that SSID shouldn't see in the profile
+            if((vos_timer_get_system_time()-timer) <= HIDDEN_TIMER)
+            { 
+              pCsrBssDescription->Result.ssId = tmpSsid;
+              pCsrBssDescription->Result.timer = timer;
+            }
+        }
+    }
+
+
+    return( pCsrBssDescription );
+}
+
+
+
+void csrPurgeChannelPower( tpAniSirGlobal pMac, tDblLinkList *pChannelList )
+{
+    tCsrChannelPowerInfo *pChannelSet;
+    tListElem *pEntry;
+
+    csrLLLock(pChannelList); 
+    // Remove the channel sets from the learned list and put them in the free list
+    while( ( pEntry = csrLLRemoveHead( pChannelList, LL_ACCESS_NOLOCK ) ) != NULL)
+    {
+        pChannelSet = GET_BASE_ADDR( pEntry, tCsrChannelPowerInfo, link );
+        if( pChannelSet )
+        {
+            palFreeMemory( pMac->hHdd, pChannelSet );
+        }
+    }
+    csrLLUnlock(pChannelList);
+    return;
+}
+
+
+/*
+ * Save the channelList into the ultimate storage as the final stage of channel 
+ * Input: pCountryInfo -- the country code (e.g. "USI"), channel list, and power limit are all stored inside this data structure
+ */
+void csrSaveToChannelPower2G_5G( tpAniSirGlobal pMac, tANI_U32 tableSize, tSirMacChanInfo *channelTable )
+{
+    tANI_U32 i = tableSize / sizeof( tSirMacChanInfo );
+    tSirMacChanInfo *pChannelInfo;
+    tCsrChannelPowerInfo *pChannelSet;
+    tANI_BOOLEAN f2GHzInfoFound = FALSE;
+    tANI_BOOLEAN f2GListPurged = FALSE, f5GListPurged = FALSE;
+    eHalStatus halStatus;
+
+    pChannelInfo = channelTable;
+    // atleast 3 bytes have to be remaining  -- from "countryString"
+    while ( i-- )
+    {
+        halStatus = palAllocateMemory( pMac->hHdd, (void **)&pChannelSet, sizeof(tCsrChannelPowerInfo) );
+        if ( eHAL_STATUS_SUCCESS == halStatus )
+        {
+            palZeroMemory(pMac->hHdd, pChannelSet, sizeof(tCsrChannelPowerInfo));
+            pChannelSet->firstChannel = pChannelInfo->firstChanNum;
+            pChannelSet->numChannels = pChannelInfo->numChannels;
+
+            // Now set the inter-channel offset based on the frequency band the channel set lies in
+            if( CSR_IS_CHANNEL_24GHZ(pChannelSet->firstChannel) )
+            {
+                pChannelSet->interChannelOffset = 1;
+                f2GHzInfoFound = TRUE;
+            }
+            else
+            {
+                pChannelSet->interChannelOffset = 4;
+                f2GHzInfoFound = FALSE;
+            }
+            pChannelSet->txPower = CSR_ROAM_MIN( pChannelInfo->maxTxPower, pMac->roam.configParam.nTxPowerCap );
+
+            if( f2GHzInfoFound )
+            {
+                if( !f2GListPurged )
+                {
+                    // purge previous results if found new
+                    csrPurgeChannelPower( pMac, &pMac->scan.channelPowerInfoList24 );
+                    f2GListPurged = TRUE;
+                }
+
+                if(CSR_IS_OPERATING_BG_BAND(pMac))
+                {
+                    // add to the list of 2.4 GHz channel sets
+                    csrLLInsertTail( &pMac->scan.channelPowerInfoList24, &pChannelSet->link, LL_ACCESS_LOCK );
+                }
+                else {
+                    smsLog( pMac, LOGW, FL("Adding 11B/G channels in 11A mode -- First Channel is %d"), 
+                                pChannelSet->firstChannel);
+                    palFreeMemory(pMac->hHdd, pChannelSet);
+                }
+            }
+            else
+            {
+                // 5GHz info found
+                if( !f5GListPurged )
+                {
+                    // purge previous results if found new
+                    csrPurgeChannelPower( pMac, &pMac->scan.channelPowerInfoList5G );
+                    f5GListPurged = TRUE;
+                }
+
+                if(CSR_IS_OPERATING_A_BAND(pMac))
+                {
+                    // add to the list of 5GHz channel sets
+                    csrLLInsertTail( &pMac->scan.channelPowerInfoList5G, &pChannelSet->link, LL_ACCESS_LOCK );
+                }
+                else {
+                    smsLog( pMac, LOGW, FL("Adding 11A channels in B/G mode -- First Channel is %d"), 
+                                pChannelSet->firstChannel);
+                    palFreeMemory(pMac->hHdd, pChannelSet);
+                }
+            }
+        }
+
+        pChannelInfo++;                // move to next entry
+    }
+
+    return;
+}
+
+
+
+void csrApplyPower2Current( tpAniSirGlobal pMac )
+{
+    smsLog( pMac, LOG3, FL(" Updating Cfg with power settings\n"));
+    csrSaveTxPowerToCfg( pMac, &pMac->scan.channelPowerInfoList24, WNI_CFG_MAX_TX_POWER_2_4 );
+    csrSaveTxPowerToCfg( pMac, &pMac->scan.channelPowerInfoList5G, WNI_CFG_MAX_TX_POWER_5 );
+}
+
+
+void csrApplyChannelPowerCountryInfo( tpAniSirGlobal pMac, tCsrChannel *pChannelList, tANI_U8 *countryCode)
+{
+    int i;
+    eNVChannelEnabledType channelEnabledType;
+    tANI_U8 numChannels = 0;
+    tANI_U8 tempNumChannels = 0;
+    tCsrChannel ChannelList;
+    if( pChannelList->numChannels )
+    {
+        tempNumChannels = CSR_MIN(pChannelList->numChannels, WNI_CFG_VALID_CHANNEL_LIST_LEN);
+        /* If user doesn't want to scan the DFS channels lets trim them from 
+        the valid channel list*/
+        if(FALSE == pMac->scan.fEnableDFSChnlScan)
+        {
+            for(i = 0; i< tempNumChannels; i++)
+            {
+                 channelEnabledType = 
+                     vos_nv_getChannelEnabledState(pChannelList->channelList[i]);
+                 if( NV_CHANNEL_ENABLE ==  channelEnabledType)
+                 {
+                     ChannelList.channelList[numChannels] =
+                         pChannelList->channelList[i];
+                     numChannels++;
+                 }
+            }
+            ChannelList.numChannels = numChannels;
+        }
+        else
+        {
+            ChannelList.numChannels = tempNumChannels;
+             vos_mem_copy(ChannelList.channelList,
+                          pChannelList->channelList,
+                          ChannelList.numChannels);
+        }
+
+        csrSetCfgValidChannelList(pMac, ChannelList.channelList, ChannelList.numChannels);
+        // extend scan capability
+        csrSetCfgScanControlList(pMac, countryCode, &ChannelList);     //  build a scan list based on the channel list : channel# + active/passive scan
+#ifdef FEATURE_WLAN_SCAN_PNO
+        // Send HAL UpdateScanParams message
+        //pmcUpdateScanParams(pMac, &(pMac->roam.configParam), pChannelList, TRUE);
+#endif // FEATURE_WLAN_SCAN_PNO
+    }
+    else
+    {
+        smsLog( pMac, LOGE, FL("  11D channel list is empty\n"));
+    }
+    csrApplyPower2Current( pMac );     // Store the channel+power info in the global place: Cfg 
+    csrSetCfgCountryCode(pMac, countryCode);
+}
+
+
+void csrResetCountryInformation( tpAniSirGlobal pMac, tANI_BOOLEAN fForce )
+{
+    if( fForce || (csrIs11dSupported( pMac ) && (!pMac->scan.f11dInfoReset)))
+    {
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+    {
+        vos_log_802_11d_pkt_type *p11dLog;
+        int Index;
+
+        WLAN_VOS_DIAG_LOG_ALLOC(p11dLog, vos_log_802_11d_pkt_type, LOG_WLAN_80211D_C);
+        if(p11dLog)
+        {
+            p11dLog->eventId = WLAN_80211D_EVENT_RESET;
+            palCopyMemory(pMac->hHdd, p11dLog->countryCode, pMac->scan.countryCodeCurrent, 3);
+            p11dLog->numChannel = pMac->scan.base20MHzChannels.numChannels;
+            if(p11dLog->numChannel <= VOS_LOG_MAX_NUM_CHANNEL)
+            {
+                palCopyMemory(pMac->hHdd, p11dLog->Channels, pMac->scan.base20MHzChannels.channelList,
+                                p11dLog->numChannel);
+                for (Index=0; Index < pMac->scan.base20MHzChannels.numChannels; Index++)
+                {
+                    p11dLog->TxPwr[Index] = CSR_ROAM_MIN( pMac->scan.defaultPowerTable[Index].pwr, pMac->roam.configParam.nTxPowerCap );
+                }
+            }
+            if(!pMac->roam.configParam.Is11dSupportEnabled)
+            {
+                p11dLog->supportMultipleDomain = WLAN_80211D_DISABLED;
+            }
+            else if(pMac->roam.configParam.fEnforceDefaultDomain)
+            {
+                p11dLog->supportMultipleDomain = WLAN_80211D_NOT_SUPPORT_MULTI_DOMAIN;
+            }
+            else
+            {
+                p11dLog->supportMultipleDomain = WLAN_80211D_SUPPORT_MULTI_DOMAIN;
+            }
+            WLAN_VOS_DIAG_LOG_REPORT(p11dLog);
+        }
+    }
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+        // switch to passive scans only when 11d is enabled
+        if( csrIs11dSupported( pMac ) )
+        {
+            pMac->scan.curScanType = eSIR_PASSIVE_SCAN;
+        }
+        csrSaveChannelPowerForBand(pMac, eANI_BOOLEAN_FALSE);
+        csrSaveChannelPowerForBand(pMac, eANI_BOOLEAN_TRUE);
+        // ... and apply the channel list, power settings, and the country code.
+        csrApplyChannelPowerCountryInfo( pMac, &pMac->scan.base20MHzChannels, pMac->scan.countryCodeCurrent );
+        // clear the 11d channel list
+        palZeroMemory( pMac->hHdd, &pMac->scan.channels11d, sizeof(pMac->scan.channels11d) );
+        pMac->scan.f11dInfoReset = eANI_BOOLEAN_TRUE;
+        pMac->scan.f11dInfoApplied = eANI_BOOLEAN_FALSE;
+    }
+
+    return;
+}
+
+
+eHalStatus csrResetCountryCodeInformation(tpAniSirGlobal pMac, tANI_BOOLEAN *pfRestartNeeded)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_BOOLEAN fRestart = eANI_BOOLEAN_FALSE;
+
+    //Use the Country code and domain from EEPROM
+    palCopyMemory(pMac->hHdd, pMac->scan.countryCodeCurrent, pMac->scan.countryCodeDefault, WNI_CFG_COUNTRY_CODE_LEN);
+    csrSetRegulatoryDomain(pMac, pMac->scan.domainIdCurrent, &fRestart);
+    if(eANI_BOOLEAN_FALSE == fRestart || (pfRestartNeeded == NULL))
+    {
+        //Only reset the country info if we don't need to restart
+        csrResetCountryInformation(pMac, eANI_BOOLEAN_TRUE);
+    }
+    if(pfRestartNeeded)
+    {
+        *pfRestartNeeded = fRestart;
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrSetCountryCode(tpAniSirGlobal pMac, tANI_U8 *pCountry, tANI_BOOLEAN *pfRestartNeeded)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    v_REGDOMAIN_t domainId;
+
+    if(pCountry)
+    {
+        status = csrGetRegulatoryDomainForCountry(pMac, pCountry, &domainId);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            status = csrSetRegulatoryDomain(pMac, domainId, pfRestartNeeded);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                //We don't need to check the pMac->roam.configParam.fEnforceDefaultDomain flag here,
+                //csrSetRegulatoryDomain will fail if the country doesn't fit our domain criteria.
+                palCopyMemory(pMac->hHdd, pMac->scan.countryCodeCurrent, pCountry, WNI_CFG_COUNTRY_CODE_LEN);
+                if((pfRestartNeeded == NULL) || !(*pfRestartNeeded))
+                {
+                    //Simply set it to cfg. If we need to restart, restart will apply it to the CFG
+                    csrSetCfgCountryCode(pMac, pCountry);
+                }
+            }
+        }
+    }
+
+    return (status);
+}
+
+
+
+//caller allocated memory for pNumChn and pChnPowerInfo
+//As input, *pNumChn has the size of the array of pChnPowerInfo
+//Upon return, *pNumChn has the number of channels assigned.
+void csrGetChannelPowerInfo( tpAniSirGlobal pMac, tDblLinkList *pList,
+                             tANI_U32 *pNumChn, tChannelListWithPower *pChnPowerInfo)
+{
+    tListElem *pEntry;
+    tANI_U32 chnIdx = 0, idx;
+    tCsrChannelPowerInfo *pChannelSet;
+
+    //Get 2.4Ghz first
+    pEntry = csrLLPeekHead( pList, LL_ACCESS_LOCK );
+    while( pEntry && (chnIdx < *pNumChn) )
+    {
+        pChannelSet = GET_BASE_ADDR( pEntry, tCsrChannelPowerInfo, link );
+        if ( 1 != pChannelSet->interChannelOffset )
+        {
+            for( idx = 0; (idx < pChannelSet->numChannels) && (chnIdx < *pNumChn); idx++ )
+            {
+                pChnPowerInfo[chnIdx].chanId = (tANI_U8)(pChannelSet->firstChannel + ( idx * pChannelSet->interChannelOffset ));
+                pChnPowerInfo[chnIdx++].pwr = pChannelSet->txPower;
+            }
+        }
+        else
+        {
+            for( idx = 0; (idx < pChannelSet->numChannels) && (chnIdx < *pNumChn); idx++ )
+            {
+                pChnPowerInfo[chnIdx].chanId = (tANI_U8)(pChannelSet->firstChannel + idx);
+                pChnPowerInfo[chnIdx++].pwr = pChannelSet->txPower;
+            }
+        }
+
+        pEntry = csrLLNext( pList, pEntry, LL_ACCESS_LOCK );
+    }
+    *pNumChn = chnIdx;
+
+    return ;
+}
+
+
+
+void csrApplyCountryInformation( tpAniSirGlobal pMac, tANI_BOOLEAN fForce )
+{
+    v_REGDOMAIN_t domainId;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    do
+    {
+        if( !csrIs11dSupported( pMac ) || 0 == pMac->scan.channelOf11dInfo) break;
+        if( pMac->scan.fAmbiguous11dInfoFound )
+        {
+            // ambiguous info found
+            //Restore te default domain as well
+            if(HAL_STATUS_SUCCESS(csrGetRegulatoryDomainForCountry( pMac, pMac->scan.countryCodeCurrent, &domainId )))
+            {
+                pMac->scan.domainIdCurrent = domainId;
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL(" failed to get domain from currentCountryCode %02X%02X\n"), 
+                    pMac->scan.countryCodeCurrent[0], pMac->scan.countryCodeCurrent[1]);
+            }
+            csrResetCountryInformation( pMac, eANI_BOOLEAN_FALSE );
+            break;
+        }
+        if ( pMac->scan.f11dInfoApplied && !fForce ) break;
+        if(HAL_STATUS_SUCCESS(csrGetRegulatoryDomainForCountry( pMac, pMac->scan.countryCode11d, &domainId )))
+        {
+            //Check whether we need to enforce default domain
+            if( ( !pMac->roam.configParam.fEnforceDefaultDomain ) ||
+                (pMac->scan.domainIdCurrent == domainId) )
+            {
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                {
+                    vos_log_802_11d_pkt_type *p11dLog;
+                    tChannelListWithPower chnPwrInfo[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+                    tANI_U32 nChnInfo = WNI_CFG_VALID_CHANNEL_LIST_LEN, nTmp;
+
+                    WLAN_VOS_DIAG_LOG_ALLOC(p11dLog, vos_log_802_11d_pkt_type, LOG_WLAN_80211D_C);
+                    if(p11dLog)
+                    {
+                        p11dLog->eventId = WLAN_80211D_EVENT_COUNTRY_SET;
+                        palCopyMemory(pMac->hHdd, p11dLog->countryCode, pMac->scan.countryCode11d, 3);
+                        p11dLog->numChannel = pMac->scan.channels11d.numChannels;
+                        if(p11dLog->numChannel <= VOS_LOG_MAX_NUM_CHANNEL)
+                        {
+                            palCopyMemory(pMac->hHdd, p11dLog->Channels, pMac->scan.channels11d.channelList,
+                                            p11dLog->numChannel);
+                            csrGetChannelPowerInfo(pMac, &pMac->scan.channelPowerInfoList24,
+                                                    &nChnInfo, chnPwrInfo);
+                            nTmp = nChnInfo;
+                            nChnInfo = WNI_CFG_VALID_CHANNEL_LIST_LEN - nTmp;
+                            csrGetChannelPowerInfo(pMac, &pMac->scan.channelPowerInfoList5G,
+                                                    &nChnInfo, &chnPwrInfo[nTmp]);
+                            for(nTmp = 0; nTmp < p11dLog->numChannel; nTmp++)
+                            {
+                                for(nChnInfo = 0; nChnInfo < WNI_CFG_VALID_CHANNEL_LIST_LEN; nChnInfo++)
+                                {
+                                    if(p11dLog->Channels[nTmp] == chnPwrInfo[nChnInfo].chanId)
+                                    {
+                                        p11dLog->TxPwr[nTmp] = chnPwrInfo[nChnInfo].pwr;
+                                        break;
+                                    }
+                                }
+                            }
+                        }
+                        if(!pMac->roam.configParam.Is11dSupportEnabled)
+                        {
+                            p11dLog->supportMultipleDomain = WLAN_80211D_DISABLED;
+                        }
+                        else if(pMac->roam.configParam.fEnforceDefaultDomain)
+                        {
+                            p11dLog->supportMultipleDomain = WLAN_80211D_NOT_SUPPORT_MULTI_DOMAIN;
+                        }
+                        else
+                        {
+                            p11dLog->supportMultipleDomain = WLAN_80211D_SUPPORT_MULTI_DOMAIN;
+                        }
+                        WLAN_VOS_DIAG_LOG_REPORT(p11dLog);
+                    }
+                }
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+                if(pMac->scan.domainIdCurrent != domainId)
+                {
+                   /* Regulatory Domain Changed, Purge Only scan result 
+                    * which does not have channel number belong to 11d 
+                    * channel list
+                    * */
+                   smsLog(pMac, LOGW, FL("Domain Changed Old %d, new %d"),
+                                      pMac->scan.domainIdCurrent, domainId);
+                   csrScanFilter11dResult(pMac);
+                }
+                status = WDA_SetRegDomain(pMac, domainId);
+                if (status != eHAL_STATUS_SUCCESS)
+                {
+                    smsLog( pMac, LOGE, FL("  fail to set regId %d\n"), domainId );
+                }
+                pMac->scan.domainIdCurrent = domainId;
+                csrApplyChannelPowerCountryInfo( pMac, &pMac->scan.channels11d, pMac->scan.countryCode11d );
+                // switch to active scans using this new channel list
+                pMac->scan.curScanType = eSIR_ACTIVE_SCAN;
+                pMac->scan.f11dInfoApplied = eANI_BOOLEAN_TRUE;
+                pMac->scan.f11dInfoReset = eANI_BOOLEAN_FALSE;
+            }
+        }
+
+    } while( 0 );
+
+    return;
+}
+
+
+
+tANI_BOOLEAN csrSave11dCountryString( tpAniSirGlobal pMac, tANI_U8 *pCountryCode,
+                     tANI_BOOLEAN fForce)
+{
+    tANI_BOOLEAN fCountryStringChanged = FALSE, fUnknownCountryCode = FALSE;
+    tANI_U32 i;
+
+    // convert to UPPER here so we are assured the strings are always in upper case.
+    for( i = 0; i < 3; i++ )
+    {
+        pCountryCode[ i ] = (tANI_U8)csrToUpper( pCountryCode[ i ] );
+    }
+
+    // Some of the 'old' Cisco 350 series AP's advertise NA as the country code (for North America ??).
+    // NA is not a valid country code or domain so let's allow this by changing it to the proper
+    // country code (which is US).  We've also seen some NETGEAR AP's that have "XX " as the country code
+    // with valid 2.4 GHz US channel information.  If we cannot find the country code advertised in the
+    // 11d information element, let's default to US.
+    if ( !HAL_STATUS_SUCCESS(csrGetRegulatoryDomainForCountry( pMac, pCountryCode, NULL ) ) )
+    {
+        // Check the enforcement first
+        if( pMac->roam.configParam.fEnforceDefaultDomain || pMac->roam.configParam.fEnforceCountryCodeMatch )
+        {
+            fUnknownCountryCode = TRUE;
+        }
+        else
+        {
+            pCountryCode[ 0 ] = 'U';
+            pCountryCode[ 1 ] = 'S';
+        }
+    }
+
+    // We've seen some of the AP's improperly put a 0 for the third character of the country code.
+    // spec says valid charcters are 'O' (for outdoor), 'I' for Indoor, or ' ' (space; for either).
+    // if we see a 0 in this third character, let's change it to a ' '.
+    if ( 0 == pCountryCode[ 2 ] )
+    {
+        pCountryCode[ 2 ] = ' ';
+    }
+
+    if( !fUnknownCountryCode )
+    {
+        fCountryStringChanged = (!palEqualMemory( pMac->hHdd,
+              pMac->scan.countryCode11d, pCountryCode, 2));
+
+
+        if(( 0 == pMac->scan.countryCode11d[ 0 ] && 0 == pMac->scan.countryCode11d[ 1 ] )
+             || (fForce))
+        {
+            // this is the first .11d information
+            palCopyMemory( pMac->hHdd, pMac->scan.countryCode11d, pCountryCode, sizeof( pMac->scan.countryCode11d ) );
+        }
+    }
+
+    return( fCountryStringChanged );
+}
+
+
+void csrSaveChannelPowerForBand( tpAniSirGlobal pMac, tANI_BOOLEAN fPopulate5GBand )
+{
+    tANI_U32 Index, count=0;
+    tSirMacChanInfo *pChanInfo;
+    tSirMacChanInfo *pChanInfoStart;
+
+    if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, (void **)&pChanInfo, sizeof(tSirMacChanInfo) * WNI_CFG_VALID_CHANNEL_LIST_LEN)))
+    {
+        palZeroMemory(pMac->hHdd, pChanInfo, sizeof(tSirMacChanInfo) * WNI_CFG_VALID_CHANNEL_LIST_LEN);
+        pChanInfoStart = pChanInfo;
+        for (Index=0; Index < pMac->scan.base20MHzChannels.numChannels; Index++)
+        {
+            if ((fPopulate5GBand && (CSR_IS_CHANNEL_5GHZ(pMac->scan.defaultPowerTable[Index].chanId))) ||
+                (!fPopulate5GBand && (CSR_IS_CHANNEL_24GHZ(pMac->scan.defaultPowerTable[Index].chanId))) )
+            {
+                pChanInfo->firstChanNum = pMac->scan.defaultPowerTable[Index].chanId;
+                pChanInfo->numChannels  = 1;
+                pChanInfo->maxTxPower   = CSR_ROAM_MIN( pMac->scan.defaultPowerTable[Index].pwr, pMac->roam.configParam.nTxPowerCap );
+                pChanInfo++;
+                count++;
+            }
+        }
+        if(count)
+        {
+            csrSaveToChannelPower2G_5G( pMac, count * sizeof(tSirMacChanInfo), pChanInfoStart );
+        }
+        palFreeMemory(pMac->hHdd, pChanInfoStart);
+    }
+}
+
+
+void csrSetOppositeBandChannelInfo( tpAniSirGlobal pMac )
+{
+    tANI_BOOLEAN fPopulate5GBand = FALSE;
+
+    do 
+    {
+        // if this is not a dual band product, then we don't need to set the opposite
+        // band info.  We only work in one band so no need to look in the other band.
+        if ( !CSR_IS_OPEARTING_DUAL_BAND( pMac ) ) break;
+        // if we found channel info on the 5.0 band and...
+        if ( CSR_IS_CHANNEL_5GHZ( pMac->scan.channelOf11dInfo ) )
+        {
+            // and the 2.4 band is empty, then populate the 2.4 channel info
+            if ( !csrLLIsListEmpty( &pMac->scan.channelPowerInfoList24, LL_ACCESS_LOCK ) ) break;
+            fPopulate5GBand = FALSE;
+        }
+        else
+        {
+            // else, we found channel info in the 2.4 GHz band.  If the 5.0 band is empty
+            // set the 5.0 band info from the 2.4 country code.
+            if ( !csrLLIsListEmpty( &pMac->scan.channelPowerInfoList5G, LL_ACCESS_LOCK ) ) break;
+            fPopulate5GBand = TRUE;
+        }
+        csrSaveChannelPowerForBand( pMac, fPopulate5GBand );
+
+    } while( 0 );
+}
+
+
+tANI_BOOLEAN csrIsSupportedChannel(tpAniSirGlobal pMac, tANI_U8 channelId)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    tANI_U32 i;
+
+    //Make sure it is a channel that is in our supported list.
+    for ( i = 0; i < pMac->scan.baseChannels.numChannels; i++ )
+    {
+        if ( channelId == pMac->scan.baseChannels.channelList[i] )
+        {
+            fRet = eANI_BOOLEAN_TRUE;
+            break;
+        }
+    }
+
+    //If it is configured to limit a set of the channels
+    if( fRet && pMac->roam.configParam.fEnforce11dChannels )
+    {
+        fRet = eANI_BOOLEAN_FALSE;
+        for ( i = 0; i < pMac->scan.base20MHzChannels.numChannels; i++ )
+        {
+            if ( channelId == pMac->scan.base20MHzChannels.channelList[i] )
+            {
+                fRet = eANI_BOOLEAN_TRUE;
+                break;
+            }
+        }
+    }
+
+    return (fRet);
+}
+
+
+
+//bSize specify the buffer size of pChannelList
+tANI_U8 csrGetChannelListFromChannelSet( tpAniSirGlobal pMac, tANI_U8 *pChannelList, tANI_U8 bSize, tCsrChannelPowerInfo *pChannelSet )
+{
+    tANI_U8 i, j = 0, chnId;
+
+    bSize = CSR_MIN(bSize, pChannelSet->numChannels);
+    for( i = 0; i < bSize; i++ )
+    {
+        chnId = (tANI_U8)(pChannelSet->firstChannel + ( i * pChannelSet->interChannelOffset ));
+        if ( csrIsSupportedChannel( pMac, chnId ) )
+        {
+            pChannelList[j++] = chnId;
+        }
+    }
+
+    return (j);
+}
+
+
+
+//bSize -- specify the buffer size of pChannelList
+void csrConstructCurrentValidChannelList( tpAniSirGlobal pMac, tDblLinkList *pChannelSetList, 
+                                            tANI_U8 *pChannelList, tANI_U8 bSize, tANI_U8 *pNumChannels )
+{
+    tListElem *pEntry;
+    tCsrChannelPowerInfo *pChannelSet;
+    tANI_U8 numChannels;
+    tANI_U8 *pChannels;
+
+    if( pChannelSetList && pChannelList && pNumChannels )
+    {
+        pChannels = pChannelList;
+        *pNumChannels = 0;
+        pEntry = csrLLPeekHead( pChannelSetList, LL_ACCESS_LOCK );
+        while( pEntry )
+        {
+            pChannelSet = GET_BASE_ADDR( pEntry, tCsrChannelPowerInfo, link );
+            numChannels = csrGetChannelListFromChannelSet( pMac, pChannels, bSize, pChannelSet );
+            pChannels += numChannels;
+            *pNumChannels += numChannels;
+            pEntry = csrLLNext( pChannelSetList, pEntry, LL_ACCESS_LOCK );
+        }
+    }
+}
+
+
+/*
+  * 802.11D only: Gather 11d IE via beacon or Probe response and store them in pAdapter->channels11d
+*/
+tANI_BOOLEAN csrLearnCountryInformation( tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc,
+                                         tDot11fBeaconIEs *pIes, tANI_BOOLEAN fForce)
+{
+    tANI_U8 Num2GChannels, bMaxNumChn;
+    eHalStatus status;
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    v_REGDOMAIN_t domainId;
+    tDot11fBeaconIEs *pIesLocal = pIes;
+
+#ifdef WLAN_SOFTAP_FEATURE
+    if (VOS_STA_SAP_MODE == vos_get_conparam ())
+        return eHAL_STATUS_SUCCESS;
+#endif
+
+    do
+    {
+        // check if .11d support is enabled
+        if( !csrIs11dSupported( pMac ) ) break;
+        if( !pIesLocal && (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc, &pIesLocal))) )
+        {
+            break;
+        }
+        // check if country information element is present
+        if(!pIesLocal->Country.present)
+        {
+            //No country info
+            break;
+        }
+
+        if( csrSave11dCountryString( pMac, pIesLocal->Country.country, fForce ) )
+        {
+            // country string changed, this should not happen
+            //Need to check whether we care about this BSS' domain info
+            //If it doesn't match of the connected profile or roaming profile, let's ignore it
+            tANI_U32 i;
+            tCsrRoamSession *pSession;
+
+            for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+            {
+                if( CSR_IS_SESSION_VALID( pMac, i ) )
+                {
+                    pSession = CSR_GET_SESSION( pMac, i );
+                    if(pSession->pCurRoamProfile)
+                    {
+                        tCsrScanResultFilter filter;
+
+                        palZeroMemory(pMac->hHdd, &filter, sizeof(tCsrScanResultFilter));
+                        status = csrRoamPrepareFilterFromProfile(pMac, pSession->pCurRoamProfile, &filter);
+                        if(HAL_STATUS_SUCCESS(status))
+                        {
+                            tANI_BOOLEAN fMatch = csrMatchBSS(pMac, pSirBssDesc, &filter, NULL, NULL, NULL, NULL);
+                            //Free the resource first
+                            csrFreeScanFilter( pMac, &filter );
+                            if(fMatch)
+                            {
+                                smsLog(pMac, LOGW, "   Matching roam profile BSSID %02X-%02X-%02X-%02X-%02X-%02X causing ambiguous domain info\n",
+                                    pSirBssDesc->bssId[0], pSirBssDesc->bssId[1], pSirBssDesc->bssId[2], 
+                                    pSirBssDesc->bssId[3], pSirBssDesc->bssId[4], pSirBssDesc->bssId[5]);
+                                pMac->scan.fAmbiguous11dInfoFound = eANI_BOOLEAN_TRUE;
+                                break;
+                            }
+                        }
+                    }
+                    else if( csrIsConnStateConnected(pMac, i))
+                    {
+                        //Reach here only when the currention is base on no profile. 
+                        //User doesn't give profile and just connect to anything.
+                        if(csrMatchBSSToConnectProfile(pMac, &pSession->connectedProfile, pSirBssDesc, pIesLocal))
+                        {
+                            smsLog(pMac, LOGW, "   Matching connect profile BSSID %02X-%02X-%02X-%02X-%02X-%02X causing ambiguous domain info\n",
+                                pSirBssDesc->bssId[0], pSirBssDesc->bssId[1], pSirBssDesc->bssId[2],
+                                pSirBssDesc->bssId[3], pSirBssDesc->bssId[4], pSirBssDesc->bssId[5]);
+                            //Tush
+                            pMac->scan.fAmbiguous11dInfoFound = eANI_BOOLEAN_TRUE;
+                            if(csrIsBssidMatch(pMac, (tCsrBssid *)&pSirBssDesc->bssId, 
+                                                &pSession->connectedProfile.bssid))
+                            {
+                                //AP changed the 11d info on the fly, modify cfg
+                                pMac->scan.fAmbiguous11dInfoFound = eANI_BOOLEAN_FALSE;
+                                fRet = eANI_BOOLEAN_TRUE;
+                            }
+                            break;
+                        }
+                    }
+                } //valid session
+            } //for
+            if ( i == CSR_ROAM_SESSION_MAX ) 
+            {
+                //Check whether we can use this country's 11d information
+                if( !pMac->roam.configParam.fEnforceDefaultDomain )
+                {
+                    pMac->scan.fAmbiguous11dInfoFound = eANI_BOOLEAN_TRUE;
+                }
+                else 
+                {
+                    VOS_ASSERT( pMac->scan.domainIdCurrent == pMac->scan.domainIdDefault );
+                    if( HAL_STATUS_SUCCESS(csrGetRegulatoryDomainForCountry( 
+                                pMac, pIesLocal->Country.country, &domainId )) &&
+                                ( domainId == pMac->scan.domainIdCurrent ) )
+                    {
+                        //Two countries in the same domain
+                    }
+                }
+            }
+        }
+        else //Tush
+        {
+            pMac->scan.fCurrent11dInfoMatch = eANI_BOOLEAN_TRUE;
+        }
+
+        //In case that some channels in 5GHz have the same channel number as 2.4GHz (<= 14)
+        if(CSR_IS_CHANNEL_5GHZ(pSirBssDesc->channelId))
+        {
+            tANI_U8 iC;
+            tSirMacChanInfo* pMacChnSet = (tSirMacChanInfo *)(&pIesLocal->Country.triplets[0]);
+
+            for(iC = 0; iC < pIesLocal->Country.num_triplets; iC++)
+            {
+                if(CSR_IS_CHANNEL_24GHZ(pMacChnSet[iC].firstChanNum))
+                {
+                    pMacChnSet[iC].firstChanNum += 200; //*** Where is this 200 defined?
+                }
+            }
+        }
+        smsLog(pMac, LOGE, FL("  %d sets each one is %d\n"), pIesLocal->Country.num_triplets, sizeof(tSirMacChanInfo));
+        // save the channel/power information from the Channel IE.
+        //sizeof(tSirMacChanInfo) has to be 3
+        csrSaveToChannelPower2G_5G( pMac, pIesLocal->Country.num_triplets * sizeof(tSirMacChanInfo), 
+                                        (tSirMacChanInfo *)(&pIesLocal->Country.triplets[0]) );
+        // set the indicator of the channel where the country IE was found...
+        pMac->scan.channelOf11dInfo = pSirBssDesc->channelId;
+        // Populate both band channel lists based on what we found in the country information...
+        csrSetOppositeBandChannelInfo( pMac );
+        bMaxNumChn = WNI_CFG_VALID_CHANNEL_LIST_LEN;
+        // construct 2GHz channel list first
+        csrConstructCurrentValidChannelList( pMac, &pMac->scan.channelPowerInfoList24, pMac->scan.channels11d.channelList, 
+                                                bMaxNumChn, &Num2GChannels );
+        // construct 5GHz channel list now
+        if(bMaxNumChn > Num2GChannels)
+        {
+            csrConstructCurrentValidChannelList( pMac, &pMac->scan.channelPowerInfoList5G, pMac->scan.channels11d.channelList + Num2GChannels,
+                                                 bMaxNumChn - Num2GChannels,
+                                                 &pMac->scan.channels11d.numChannels );
+        }
+
+        pMac->scan.channels11d.numChannels += Num2GChannels;
+        fRet = eANI_BOOLEAN_TRUE;
+
+    } while( 0 );
+    
+    if( !pIes && pIesLocal )
+    {
+        //locally allocated
+        palFreeMemory(pMac->hHdd, pIesLocal);
+    }
+
+    return( fRet );
+}
+
+
+static void csrSaveScanResults( tpAniSirGlobal pMac )
+{
+    // initialize this to FALSE. profMoveInterimScanResultsToMainList() routine
+    // will set this to the channel where an .11d beacon is seen
+    pMac->scan.channelOf11dInfo = 0;
+    // if we get any ambiguous .11d information then this will be set to TRUE
+    pMac->scan.fAmbiguous11dInfoFound = eANI_BOOLEAN_FALSE;
+    //Tush
+    // if we get any ambiguous .11d information, then this will be set to TRUE
+    // only if the applied 11d info could be found in one of the scan results
+    pMac->scan.fCurrent11dInfoMatch = eANI_BOOLEAN_FALSE;
+    // move the scan results from interim list to the main scan list
+    csrMoveTempScanResultsToMainList( pMac );
+
+    // Now check if we gathered any domain/country specific information
+    // If so, we should update channel list and apply Tx power settings
+    csrApplyCountryInformation( pMac, FALSE );
+}
+
+
+void csrReinitScanCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    switch (pCommand->u.scanCmd.reason)
+    {
+    case eCsrScanSetBGScanParam:
+    case eCsrScanAbortBgScan:
+        if(pCommand->u.scanCmd.u.bgScanRequest.ChannelInfo.ChannelList)
+        {
+            palFreeMemory(pMac->hHdd, pCommand->u.scanCmd.u.bgScanRequest.ChannelInfo.ChannelList);
+            pCommand->u.scanCmd.u.bgScanRequest.ChannelInfo.ChannelList = NULL;
+        }
+        break;
+    case eCsrScanBGScanAbort:
+    case eCsrScanBGScanEnable:
+    case eCsrScanGetScanChnInfo:
+        break;
+    case eCsrScanAbortNormalScan:
+    default:
+        csrScanFreeRequest(pMac, &pCommand->u.scanCmd.u.scanRequest);
+        break;
+    }
+    if(pCommand->u.scanCmd.pToRoamProfile)
+    {
+        csrReleaseProfile(pMac, pCommand->u.scanCmd.pToRoamProfile);
+        palFreeMemory(pMac->hHdd, pCommand->u.scanCmd.pToRoamProfile);
+    }
+    palZeroMemory(pMac->hHdd, &pCommand->u.scanCmd, sizeof(tScanCmd));
+}
+
+
+tANI_BOOLEAN csrGetRemainingChannelsFor11dScan( tpAniSirGlobal pMac, tANI_U8 *pChannels, tANI_U8 *pcChannels )
+{
+    tANI_U32 index11dChannels, index;
+    tANI_U32 indexCurrentChannels;
+    tANI_BOOLEAN fChannelAlreadyScanned;
+    tANI_U32 len = sizeof(pMac->roam.validChannelList);
+
+    *pcChannels = 0;
+    if ( CSR_IS_11D_INFO_FOUND(pMac) && csrRoamIsChannelValid(pMac, pMac->scan.channelOf11dInfo) )
+    {
+        if (HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, (tANI_U8 *)pMac->roam.validChannelList, &len)))
+        {
+            //Find the channel index where we found the 11d info
+            for(index = 0; index < len; index++)
+            {
+                if(pMac->scan.channelOf11dInfo == pMac->roam.validChannelList[index])
+                    break;
+            }
+            //check whether we found the channel index
+            if(index < len)
+            {
+                // Now, look through the 11d channel list and create a list of all channels in the 11d list that are
+                // NOT in the current channel list.  This gives us a list of the new channels that have not been
+                // scanned.  We'll scan this new list so we have a complete set of scan results on all of the domain channels
+                // initially.
+                for ( index11dChannels = 0; index11dChannels < pMac->scan.channels11d.numChannels; index11dChannels++ )
+                {
+                    fChannelAlreadyScanned = eANI_BOOLEAN_FALSE;
+
+                    for( indexCurrentChannels = 0; indexCurrentChannels < index; indexCurrentChannels++ )
+                    {
+                        if ( pMac->roam.validChannelList[ indexCurrentChannels ] == pMac->scan.channels11d.channelList[ index11dChannels ] )
+                        {
+                            fChannelAlreadyScanned = eANI_BOOLEAN_TRUE;
+                            break;
+                        }
+                    }
+
+                    if ( !fChannelAlreadyScanned )
+                    {
+                        pChannels[ *pcChannels ] = pMac->scan.channels11d.channelList[ index11dChannels ];
+                        ( *pcChannels )++;
+                    }
+                }
+            }
+        }//GetCFG
+    }
+    return( *pcChannels );
+}
+
+
+eCsrScanCompleteNextCommand csrScanGetNextCommandState( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fSuccess )
+{
+    eCsrScanCompleteNextCommand NextCommand = eCsrNextScanNothing;
+    
+    switch( pCommand->u.scanCmd.reason )
+    {
+        case eCsrScan11d1:
+            NextCommand = (fSuccess) ? eCsrNext11dScan1Success : eCsrNext11dScan1Failure;
+            break;
+        case eCsrScan11d2:
+            NextCommand = (fSuccess) ? eCsrNext11dScan2Success : eCsrNext11dScan2Failure;
+            break;    
+        case eCsrScan11dDone:
+            NextCommand = eCsrNext11dScanComplete;
+            break;
+        case eCsrScanLostLink1:
+            NextCommand = (fSuccess) ? eCsrNextLostLinkScan1Success : eCsrNextLostLinkScan1Failed;
+            break;
+        case eCsrScanLostLink2:
+            NextCommand = (fSuccess) ? eCsrNextLostLinkScan2Success : eCsrNextLostLinkScan2Failed;
+            break;
+        case eCsrScanLostLink3:
+            NextCommand = (fSuccess) ? eCsrNextLostLinkScan3Success : eCsrNextLostLinkScan3Failed;
+            break;
+        case eCsrScanForSsid:
+            NextCommand = (fSuccess) ? eCsrNexteScanForSsidSuccess : eCsrNexteScanForSsidFailure;
+            break;
+        case eCsrScanForCapsChange:
+            NextCommand = eCsrNextCapChangeScanComplete;    //don't care success or not
+            break;
+        case eCsrScanIdleScan:
+            NextCommand = eCsrNextIdleScanComplete;
+            break;
+        default:
+            NextCommand = eCsrNextScanNothing;
+            break;
+    }
+    return( NextCommand );
+}
+
+
+//Return whether the pCommand is finished.
+tANI_BOOLEAN csrHandleScan11d1Failure(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_TRUE;
+    
+    //Apply back the default setting and passively scan one more time.
+    csrResetCountryInformation(pMac, eANI_BOOLEAN_FALSE);
+    pCommand->u.scanCmd.reason = eCsrScan11d2;
+    if(HAL_STATUS_SUCCESS(csrScanChannels(pMac, pCommand)))
+    {
+        fRet = eANI_BOOLEAN_FALSE;
+    }
+    
+    return (fRet);
+}
+
+
+tANI_BOOLEAN csrHandleScan11dSuccess(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_TRUE;
+    tANI_U8 *pChannels;
+    tANI_U8 cChannels;
+    
+    if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, (void **)&pChannels, WNI_CFG_VALID_CHANNEL_LIST_LEN)))
+    {
+        palZeroMemory(pMac->hHdd, pChannels, WNI_CFG_VALID_CHANNEL_LIST_LEN);
+        if ( csrGetRemainingChannelsFor11dScan( pMac, pChannels, &cChannels ) )
+        {
+            pCommand->u.scanCmd.reason = eCsrScan11dDone;
+            if(pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList)
+            {
+                palFreeMemory(pMac->hHdd, pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList); 
+            }
+            if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, (void **)&pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList, cChannels)))
+            {
+                palCopyMemory(pMac->hHdd, pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList, pChannels, cChannels);
+                pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = cChannels;
+                pCommand->u.scanCmd.u.scanRequest.requestType = eCSR_SCAN_REQUEST_FULL_SCAN;
+                pCommand->u.scanCmd.u.scanRequest.scanType = eSIR_ACTIVE_SCAN;
+                if(HAL_STATUS_SUCCESS(csrScanChannels(pMac, pCommand)))
+                {
+                    //Reuse the same command buffer
+                    fRet = eANI_BOOLEAN_FALSE;
+                }
+            }
+        }
+        palFreeMemory(pMac->hHdd, pChannels);
+    }
+    
+    return (fRet);
+}
+
+//Return whether the command should be removed
+tANI_BOOLEAN csrScanComplete( tpAniSirGlobal pMac, tSirSmeScanRsp *pScanRsp )
+{
+    eCsrScanCompleteNextCommand NextCommand = eCsrNextScanNothing;
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+    tANI_BOOLEAN fRemoveCommand = eANI_BOOLEAN_TRUE;
+    tANI_BOOLEAN fSuccess;
+
+    pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+
+    if ( pEntry )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+
+        // If the head of the queue is Active and it is a SCAN command, remove
+        // and put this on the Free queue.
+        if ( eSmeCommandScan == pCommand->command )
+        {     
+            tANI_U32 sessionId = pCommand->sessionId;
+
+            if(eSIR_SME_SUCCESS != pScanRsp->statusCode)
+            {
+                fSuccess = eANI_BOOLEAN_FALSE;
+            }
+            else
+            {
+                //pMac->scan.tempScanResults is not empty meaning the scan found something
+                //This check only valid here because csrSaveScanresults is not yet called
+                fSuccess = (!csrLLIsListEmpty(&pMac->scan.tempScanResults, LL_ACCESS_LOCK));
+            }
+            csrSaveScanResults(pMac);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+            {
+                vos_log_scan_pkt_type *pScanLog = NULL;
+                tScanResultHandle hScanResult;
+                tCsrScanResultInfo *pScanResult;
+                tDot11fBeaconIEs *pIes;
+                int n = 0, c = 0;
+
+                WLAN_VOS_DIAG_LOG_ALLOC(pScanLog, vos_log_scan_pkt_type, LOG_WLAN_SCAN_C);
+                if(pScanLog)
+                {
+                    if(eCsrScanBgScan == pCommand->u.scanCmd.reason || 
+                        eCsrScanProbeBss == pCommand->u.scanCmd.reason ||
+                        eCsrScanSetBGScanParam == pCommand->u.scanCmd.reason)
+                    {
+                        pScanLog->eventId = WLAN_SCAN_EVENT_HO_SCAN_RSP;
+                    }
+                    else
+                    {
+                        if( eSIR_PASSIVE_SCAN != pMac->scan.curScanType )
+                        {
+                            pScanLog->eventId = WLAN_SCAN_EVENT_ACTIVE_SCAN_RSP;
+                        }
+                        else
+                        {
+                            pScanLog->eventId = WLAN_SCAN_EVENT_PASSIVE_SCAN_RSP;
+                        }
+                    }
+                    if(eSIR_SME_SUCCESS == pScanRsp->statusCode)
+                    {
+                        if(HAL_STATUS_SUCCESS(csrScanGetResult(pMac, NULL, &hScanResult)))
+                        {
+                            while(((pScanResult = csrScanResultGetNext(pMac, hScanResult)) != NULL))
+                            {
+                                if( n < VOS_LOG_MAX_NUM_BSSID )
+                                {
+                                    if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, &pScanResult->BssDescriptor, &pIes)))
+                                    {
+                                        smsLog(pMac, LOGE, FL(" fail to parse IEs\n"));
+                                        break;
+                                    }
+                                    palCopyMemory(pMac->hHdd, pScanLog->bssid[n], pScanResult->BssDescriptor.bssId, 6);
+                                    if(pIes && pIes->SSID.present && VOS_LOG_MAX_SSID_SIZE >= pIes->SSID.num_ssid)
+                                    {
+                                        palCopyMemory(pMac->hHdd, pScanLog->ssid[n], 
+                                                pIes->SSID.ssid, pIes->SSID.num_ssid);
+                                    }
+                                    palFreeMemory(pMac->hHdd, pIes);
+                                    n++;
+                                }
+                                c++;
+                            }
+                            pScanLog->numSsid = (v_U8_t)n;
+                            pScanLog->totalSsid = (v_U8_t)c;
+                            csrScanResultPurge(pMac, hScanResult);
+                        }
+                    }
+                    else
+                    {
+                        pScanLog->status = WLAN_SCAN_STATUS_FAILURE;
+                    }
+                    WLAN_VOS_DIAG_LOG_REPORT(pScanLog);
+                }
+            }
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+            NextCommand = csrScanGetNextCommandState(pMac, pCommand, fSuccess);
+            //We reuse the command here instead reissue a new command
+            switch(NextCommand)
+            {
+            case eCsrNext11dScan1Success:
+            case eCsrNext11dScan2Success:
+                smsLog( pMac, LOG2, FL("11dScan1/3 produced results.  Reissue Active scan...\n"));
+                // if we found country information, no need to continue scanning further, bail out
+                fRemoveCommand = eANI_BOOLEAN_TRUE;
+                NextCommand = eCsrNext11dScanComplete;
+                break;
+            case eCsrNext11dScan1Failure:
+                //We are not done yet. 11d scan fail once. We will try to reset anything and do it over again
+                //The only meaningful thing for this retry is that we cannot find 11d information after a reset so
+                //we clear the "old" 11d info and give it once more chance
+                fRemoveCommand = csrHandleScan11d1Failure(pMac, pCommand);
+                if(fRemoveCommand)
+                {
+                    NextCommand = eCsrNext11dScanComplete;
+                } 
+                break;
+            case eCsrNextLostLinkScan1Success:
+                if(!HAL_STATUS_SUCCESS(csrIssueRoamAfterLostlinkScan(pMac, sessionId, eCsrLostLink1)))
+                {
+                    csrScanHandleFailedLostlink1(pMac, sessionId);
+                }
+                break;
+            case eCsrNextLostLinkScan2Success:
+                if(!HAL_STATUS_SUCCESS(csrIssueRoamAfterLostlinkScan(pMac, sessionId, eCsrLostLink2)))
+                {
+                    csrScanHandleFailedLostlink2(pMac, sessionId);
+                }
+                break;
+            case eCsrNextLostLinkScan3Success:
+                if(!HAL_STATUS_SUCCESS(csrIssueRoamAfterLostlinkScan(pMac, sessionId, eCsrLostLink3)))
+                {
+                    csrScanHandleFailedLostlink3(pMac, sessionId);
+                }
+                break;
+            case eCsrNextLostLinkScan1Failed:
+                csrScanHandleFailedLostlink1(pMac, sessionId);
+                break;
+            case eCsrNextLostLinkScan2Failed:
+                csrScanHandleFailedLostlink2(pMac, sessionId);
+                break;
+            case eCsrNextLostLinkScan3Failed:
+                csrScanHandleFailedLostlink3(pMac, sessionId);
+                break;    
+            case eCsrNexteScanForSsidSuccess:
+                csrScanHandleSearchForSSID(pMac, pCommand);
+                break;
+            case eCsrNexteScanForSsidFailure:
+                csrScanHandleSearchForSSIDFailure(pMac, pCommand);
+                break;
+            case eCsrNextIdleScanComplete:
+                pMac->scan.fRestartIdleScan = eANI_BOOLEAN_TRUE;
+                break;
+            case eCsrNextCapChangeScanComplete:
+                csrScanHandleCapChangeScanComplete(pMac, sessionId);
+                break;
+            default:
+
+                break;
+            }
+        }
+        else
+        {
+            smsLog( pMac, LOGW, FL("Scan Completion called but SCAN command is not ACTIVE ...\n"));
+            fRemoveCommand = eANI_BOOLEAN_FALSE;
+        }
+    }
+    else
+    {
+        smsLog( pMac, LOGW, FL("Scan Completion called but NO commands are ACTIVE ...\n"));
+        fRemoveCommand = eANI_BOOLEAN_FALSE;
+    }
+   
+    return( fRemoveCommand );
+}
+
+
+
+static void csrScanRemoveDupBssDescriptionFromInterimList( tpAniSirGlobal pMac, 
+                                                           tSirBssDescription *pSirBssDescr,
+                                                           tDot11fBeaconIEs *pIes)
+{
+    tListElem *pEntry;
+    tCsrScanResult *pCsrBssDescription;
+
+    // Walk through all the chained BssDescriptions.  If we find a chained BssDescription that
+    // matches the BssID of the BssDescription passed in, then these must be duplicate scan
+    // results for this Bss.  In that case, remove the 'old' Bss description from the linked list.
+    pEntry = csrLLPeekHead( &pMac->scan.tempScanResults, LL_ACCESS_LOCK );
+    while( pEntry ) 
+    {
+        pCsrBssDescription = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+
+        // we have a duplicate scan results only when BSSID, SSID, Channel and NetworkType
+        // matches
+
+        if ( csrIsDuplicateBssDescription( pMac, &pCsrBssDescription->Result.BssDescriptor, 
+                                             pSirBssDescr, pIes ) )
+        {
+            pSirBssDescr->rssi = (tANI_S8)( (((tANI_S32)pSirBssDescr->rssi * CSR_SCAN_RESULT_RSSI_WEIGHT ) +
+                                    ((tANI_S32)pCsrBssDescription->Result.BssDescriptor.rssi * (100 - CSR_SCAN_RESULT_RSSI_WEIGHT) )) / 100 );
+
+            // Remove the 'old' entry from the list....
+            if( csrLLRemoveEntry( &pMac->scan.tempScanResults, pEntry, LL_ACCESS_LOCK ) )
+            {
+                csrCheckNSaveWscIe(pMac, pSirBssDescr, &pCsrBssDescription->Result.BssDescriptor);
+                // we need to free the memory associated with this node
+                csrFreeScanResultEntry( pMac, pCsrBssDescription );
+            }
+            
+            // If we found a match, we can stop looking through the list.
+            break;
+        }
+
+        pEntry = csrLLNext( &pMac->scan.tempScanResults, pEntry, LL_ACCESS_LOCK );
+    }
+}
+
+
+
+//Caller allocated memory pfNewBssForConn to return whether new candidate for
+//current connection is found. Cannot be NULL
+tCsrScanResult *csrScanSaveBssDescriptionToInterimList( tpAniSirGlobal pMac, 
+                                                        tSirBssDescription *pBSSDescription,
+                                                        tDot11fBeaconIEs *pIes)
+{
+    tCsrScanResult *pCsrBssDescription = NULL;
+    tANI_U32 cbBSSDesc;
+    tANI_U32 cbAllocated;
+    eHalStatus halStatus;
+    
+    // figure out how big the BSS description is (the BSSDesc->length does NOT
+    // include the size of the length field itself).
+    cbBSSDesc = pBSSDescription->length + sizeof( pBSSDescription->length );
+
+    cbAllocated = sizeof( tCsrScanResult ) + cbBSSDesc;
+
+    halStatus = palAllocateMemory( pMac->hHdd, (void **)&pCsrBssDescription, cbAllocated );
+    if ( HAL_STATUS_SUCCESS(halStatus) )
+    {
+        palZeroMemory(pMac->hHdd, pCsrBssDescription, cbAllocated);
+        pCsrBssDescription->AgingCount = (tANI_S32)pMac->roam.configParam.agingCount;
+        palCopyMemory(pMac->hHdd, &pCsrBssDescription->Result.BssDescriptor, pBSSDescription, cbBSSDesc );
+        //Save SSID separately for later use
+        if( pIes->SSID.present && !csrIsNULLSSID(pIes->SSID.ssid, pIes->SSID.num_ssid) )
+        {
+            //SSID not hidden
+            tANI_U32 len = pIes->SSID.num_ssid;;
+            if (len > SIR_MAC_MAX_SSID_LENGTH)
+            {
+               // truncate to fit in our struct
+               len = SIR_MAC_MAX_SSID_LENGTH;
+            }
+            pCsrBssDescription->Result.ssId.length = len;
+            pCsrBssDescription->Result.timer = vos_timer_get_system_time();
+            palCopyMemory(pMac->hHdd, pCsrBssDescription->Result.ssId.ssId, 
+                pIes->SSID.ssid, len );
+        }
+        csrLLInsertTail( &pMac->scan.tempScanResults, &pCsrBssDescription->Link, LL_ACCESS_LOCK );
+    }
+
+    return( pCsrBssDescription );
+}
+
+
+    
+
+tANI_BOOLEAN csrIsDuplicateBssDescription( tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc1, 
+                                           tSirBssDescription *pSirBssDesc2, tDot11fBeaconIEs *pIes2 )
+{
+    tANI_BOOLEAN fMatch = FALSE;
+    tSirMacCapabilityInfo *pCap1, *pCap2;
+    tDot11fBeaconIEs *pIes1 = NULL;
+
+    pCap1 = (tSirMacCapabilityInfo *)&pSirBssDesc1->capabilityInfo;
+    pCap2 = (tSirMacCapabilityInfo *)&pSirBssDesc2->capabilityInfo;
+    if(pCap1->ess == pCap2->ess)
+    {
+        if (pCap1->ess && 
+                csrIsMacAddressEqual( pMac, (tCsrBssid *)pSirBssDesc1->bssId, (tCsrBssid *)pSirBssDesc2->bssId))
+        {
+            fMatch = TRUE;
+        }
+        else if (pCap1->ibss && (pSirBssDesc1->channelId == pSirBssDesc2->channelId))
+        {
+            tDot11fBeaconIEs *pIesTemp = pIes2;
+
+            do
+            {
+                if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc1, &pIes1)))
+                {
+                    break;
+                }
+                if( NULL == pIesTemp )
+                {
+                    if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc2, &pIesTemp)))
+                    {
+                        break;
+                    }
+                }
+                //Same channel cannot have same SSID for different IBSS
+                if(pIes1->SSID.present && pIesTemp->SSID.present)
+                {
+                    fMatch = csrIsSsidMatch(pMac, pIes1->SSID.ssid, pIes1->SSID.num_ssid, 
+                                            pIesTemp->SSID.ssid, pIesTemp->SSID.num_ssid, eANI_BOOLEAN_TRUE);
+                }
+            }while(0);
+            if( (NULL == pIes2) && pIesTemp )
+            {
+                //locally allocated
+                palFreeMemory(pMac->hHdd, pIesTemp);
+            }
+        }
+#if defined WLAN_FEATURE_P2P
+        /* In case of P2P devices, ess and ibss will be set to zero */
+        else if (!pCap1->ess && 
+                csrIsMacAddressEqual( pMac, (tCsrBssid *)pSirBssDesc1->bssId, (tCsrBssid *)pSirBssDesc2->bssId))
+        {
+            fMatch = TRUE;
+        }
+#endif
+    }
+
+    if(pIes1)
+    {
+        palFreeMemory(pMac->hHdd, pIes1);
+    }
+
+    return( fMatch );
+}
+
+
+tANI_BOOLEAN csrIsNetworkTypeEqual( tSirBssDescription *pSirBssDesc1, tSirBssDescription *pSirBssDesc2 )
+{
+    return( pSirBssDesc1->nwType == pSirBssDesc2->nwType );
+}
+
+
+//to check whether the BSS matches the dot11Mode
+static tANI_BOOLEAN csrScanIsBssAllowed(tpAniSirGlobal pMac, tSirBssDescription *pBssDesc, 
+                                        tDot11fBeaconIEs *pIes)
+{
+    tANI_BOOLEAN fAllowed = eANI_BOOLEAN_FALSE;
+    eCsrPhyMode phyMode;
+
+    if(HAL_STATUS_SUCCESS(csrGetPhyModeFromBss(pMac, pBssDesc, &phyMode, pIes)))
+    {
+        switch(pMac->roam.configParam.phyMode)
+        {
+        case eCSR_DOT11_MODE_11b:
+            fAllowed = (tANI_BOOLEAN)(eCSR_DOT11_MODE_11a != phyMode);
+            break;
+        case eCSR_DOT11_MODE_11g:
+            fAllowed = (tANI_BOOLEAN)(eCSR_DOT11_MODE_11a != phyMode);
+            break;
+        case eCSR_DOT11_MODE_11g_ONLY:
+            fAllowed = (tANI_BOOLEAN)(eCSR_DOT11_MODE_11g == phyMode);
+            break;
+        case eCSR_DOT11_MODE_11a:
+            fAllowed = (tANI_BOOLEAN)((eCSR_DOT11_MODE_11b != phyMode) && (eCSR_DOT11_MODE_11g != phyMode));
+            break;
+        case eCSR_DOT11_MODE_11n_ONLY:
+            fAllowed = (tANI_BOOLEAN)((eCSR_DOT11_MODE_11n == phyMode) || (eCSR_DOT11_MODE_TAURUS == phyMode));
+            break;
+        case eCSR_DOT11_MODE_11b_ONLY:
+            fAllowed = (tANI_BOOLEAN)(eCSR_DOT11_MODE_11b == phyMode);
+            break;
+        case eCSR_DOT11_MODE_11a_ONLY:
+            fAllowed = (tANI_BOOLEAN)(eCSR_DOT11_MODE_11a == phyMode);
+            break;
+        case eCSR_DOT11_MODE_11n:
+        case eCSR_DOT11_MODE_TAURUS:
+        default:
+            fAllowed = eANI_BOOLEAN_TRUE;
+            break;
+        }
+    }
+
+    return (fAllowed);
+}
+
+
+
+//Return pIes to caller for future use when returning TRUE.
+static tANI_BOOLEAN csrScanValidateScanResult( tpAniSirGlobal pMac, tANI_U8 *pChannels, 
+                                               tANI_U8 numChn, tSirBssDescription *pBssDesc, 
+                                               tDot11fBeaconIEs **ppIes )
+{
+    tANI_BOOLEAN fValidChannel = FALSE;
+    tDot11fBeaconIEs *pIes = NULL;
+    tANI_U8 index;
+
+    for( index = 0; index < numChn; index++ )
+    {
+        // This check relies on the fact that a single BSS description is returned in each
+        // ScanRsp call, which is the way LIM implemented the scan req/rsp funtions.  We changed 
+        // to this model when we ran with a large number of APs.  If this were to change, then 
+        // this check would have to mess with removing the bssDescription from somewhere in an 
+        // arbitrary index in the bssDescription array.
+        if ( pChannels[ index ] == pBssDesc->channelId ) 
+        {
+           fValidChannel = TRUE;
+           break;
+        }
+    }
+    *ppIes = NULL;
+    if(fValidChannel)
+    {
+        if( HAL_STATUS_SUCCESS( csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIes) ) )
+        {
+            fValidChannel = csrScanIsBssAllowed(pMac, pBssDesc, pIes);
+            if( fValidChannel )
+            {
+                *ppIes = pIes;
+            }
+            else
+            {
+                palFreeMemory( pMac->hHdd, pIes );
+            }
+        }
+        else
+        {
+            fValidChannel = FALSE;
+        }
+    }
+
+    return( fValidChannel );   
+}
+
+
+//Return whether last scan result is received
+static tANI_BOOLEAN csrScanProcessScanResults( tpAniSirGlobal pMac, tSmeCmd *pCommand, 
+                                                tSirSmeScanRsp *pScanRsp, tANI_BOOLEAN *pfRemoveCommand )
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE, fRemoveCommand = eANI_BOOLEAN_FALSE;
+    tDot11fBeaconIEs *pIes = NULL;
+    tANI_U32 cbParsed;
+    tSirBssDescription *pSirBssDescription;
+    tANI_U32 cbBssDesc;
+    tANI_U32 cbScanResult = GET_FIELD_OFFSET( tSirSmeScanRsp, bssDescription ) 
+                            + sizeof(tSirBssDescription);    //We need at least one CB
+
+    // don't consider the scan rsp to be valid if the status code is Scan Failure.  Scan Failure
+    // is returned when the scan could not find anything.  so if we get scan failure return that
+    // the scan response is invalid.  Also check the lenght in the scan result for valid scan
+    // BssDescriptions....
+    do
+    {
+        if ( ( cbScanResult <= pScanRsp->length ) && 
+             (( eSIR_SME_SUCCESS == pScanRsp->statusCode ) ||
+              ( eSIR_SME_MORE_SCAN_RESULTS_FOLLOW == pScanRsp->statusCode ) ) )
+        {
+            tANI_U8 *pChannelList = NULL;
+            tANI_U8 cChannels = 0;
+
+            //Different scan type can reach this point, we need to distinguish it
+            if( eCsrScanSetBGScanParam == pCommand->u.scanCmd.reason )
+            {
+                //eCsrScanSetBGScanParam uses different structure
+                tCsrBGScanRequest *pBgScanReq = &pCommand->u.scanCmd.u.bgScanRequest;
+
+                cChannels = pBgScanReq->ChannelInfo.numOfChannels;
+                pChannelList = pBgScanReq->ChannelInfo.ChannelList;
+            }
+            else
+            {
+                //the rest use generic scan request
+                cChannels = pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels;
+                pChannelList = pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList;
+            }
+
+            // if the scan result is not on one of the channels in the Valid channel list, then it
+            // must have come from an AP on an overlapping channel (in the 2.4GHz band).  In this case,
+            // let's drop the scan result.
+            //
+            // The other situation is where the scan request is for a scan on a particular channel set
+            // and the scan result is from a 
+            
+            // if the NumChannels is 0, then we are supposed to be scanning all channels.  Use the full channel
+            // list as the 'valid' channel list.  Otherwise, use the specific channel list in the scan parms
+            // as the valid channels.
+            if ( 0 == cChannels ) 
+            {
+                tANI_U32 len = sizeof(pMac->roam.validChannelList);
+                
+                if (HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, (tANI_U8 *)pMac->roam.validChannelList, &len)))
+                {
+                    pChannelList = pMac->roam.validChannelList;
+                    cChannels = (tANI_U8)len; 
+                }
+                else
+                {
+                    //Cannot continue
+                    smsLog( pMac, LOGE, "CSR: Processing internal SCAN results...csrGetCfgValidChannels failed\n" );
+                    break;
+                }
+            }
+
+            smsLog( pMac, LOG2, "CSR: Processing internal SCAN results..." );
+            cbParsed = GET_FIELD_OFFSET( tSirSmeScanRsp, bssDescription );
+            pSirBssDescription = pScanRsp->bssDescription;
+            while( cbParsed < pScanRsp->length )
+            {
+                if ( csrScanValidateScanResult( pMac, pChannelList, cChannels, pSirBssDescription, &pIes ) ) 
+                {
+                    csrScanRemoveDupBssDescriptionFromInterimList(pMac, pSirBssDescription, pIes);
+                    csrScanSaveBssDescriptionToInterimList( pMac, pSirBssDescription, pIes );
+                    if( eSIR_PASSIVE_SCAN == pMac->scan.curScanType )
+                    {
+                        if( csrIs11dSupported( pMac) )
+                        {
+                            //Check whether the BSS is acceptable base on 11d info and our configs.
+                            if( csrMatchCountryCode( pMac, NULL, pIes ) )
+                            {
+                                //Double check whether the channel is acceptable by us.
+                                if( csrIsSupportedChannel( pMac, pSirBssDescription->channelId ) )
+                                {
+                                    pMac->scan.curScanType = eSIR_ACTIVE_SCAN;
+                                }
+                            }
+                        }
+                        else
+                        {
+                            pMac->scan.curScanType = eSIR_ACTIVE_SCAN;
+                        }
+                    }
+                    //Free the resource
+                    palFreeMemory( pMac->hHdd, pIes );
+                }
+                // skip over the BSS description to the next one...
+                cbBssDesc = pSirBssDescription->length + sizeof( pSirBssDescription->length );
+
+                cbParsed += cbBssDesc;
+                pSirBssDescription = (tSirBssDescription *)((tANI_U8 *)pSirBssDescription + cbBssDesc );
+
+            } //while
+        }
+        else
+        {
+            smsLog( pMac, LOGW, " Scanrsp fail (0x%08X), length = %d\n", pScanRsp->statusCode, pScanRsp->length );
+            //HO bg scan/probe failed no need to try autonomously
+            if(eCsrScanBgScan == pCommand->u.scanCmd.reason ||
+               eCsrScanProbeBss == pCommand->u.scanCmd.reason ||
+               eCsrScanSetBGScanParam == pCommand->u.scanCmd.reason)
+            {
+                fRemoveCommand = eANI_BOOLEAN_TRUE;
+            }
+        }
+    }while(0);
+    if ( eSIR_SME_MORE_SCAN_RESULTS_FOLLOW != pScanRsp->statusCode )
+    {
+        smsLog(pMac, LOG1, " Scan received %d unique BSS scan reason is %d\n", csrLLCount(&pMac->scan.tempScanResults), pCommand->u.scanCmd.reason);
+        fRemoveCommand = csrScanComplete( pMac, pScanRsp );
+        fRet = eANI_BOOLEAN_TRUE;
+    }//if ( eSIR_SME_MORE_SCAN_RESULTS_FOLLOW != pScanRsp->statusCode )
+    if(pfRemoveCommand)
+    {
+        *pfRemoveCommand = fRemoveCommand;
+    }
+
+#ifdef WLAN_AP_STA_CONCURRENCY
+    if (!csrLLIsListEmpty( &pMac->scan.scanCmdPendingList, LL_ACCESS_LOCK ))
+    {
+         palTimerStart(pMac->hHdd, pMac->scan.hTimerStaApConcTimer, 
+                 CSR_SCAN_STAAP_CONC_INTERVAL, eANI_BOOLEAN_FALSE);
+    }
+#endif
+    return (fRet);
+}
+
+
+tANI_BOOLEAN csrScanIsWildCardScan( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    tANI_U8 bssid[WNI_CFG_BSSID_LEN] = {0, 0, 0, 0, 0, 0};
+    tANI_BOOLEAN f = palEqualMemory( pMac->hHdd, pCommand->u.scanCmd.u.scanRequest.bssid, 
+        bssid, sizeof(tCsrBssid) );
+
+    //It is not a wild card scan if the bssid is not broadcast and the number of SSID is 1.
+    return ((tANI_BOOLEAN)( (f || (0xff == pCommand->u.scanCmd.u.scanRequest.bssid[0])) &&
+        (pCommand->u.scanCmd.u.scanRequest.SSIDs.numOfSSIDs != 1) ));
+}
+
+
+eHalStatus csrScanSmeScanResponse( tpAniSirGlobal pMac, void *pMsgBuf )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+    eCsrScanStatus scanStatus;
+    tSirSmeScanRsp *pScanRsp = (tSirSmeScanRsp *)pMsgBuf;
+    tSmeGetScanChnRsp *pScanChnInfo;
+    tANI_BOOLEAN fRemoveCommand = eANI_BOOLEAN_TRUE;
+    eCsrScanReason reason = eCsrScanOther;
+
+    pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+
+    if ( pEntry )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        if ( eSmeCommandScan == pCommand->command )
+        {
+            scanStatus = (eSIR_SME_SUCCESS == pScanRsp->statusCode) ? eCSR_SCAN_SUCCESS : eCSR_SCAN_FAILURE;
+            reason = pCommand->u.scanCmd.reason;
+            switch(pCommand->u.scanCmd.reason)
+            {
+            case eCsrScanAbortBgScan:
+            case eCsrScanAbortNormalScan:
+            case eCsrScanBGScanAbort:
+            case eCsrScanBGScanEnable:
+                break;
+            case eCsrScanGetScanChnInfo:
+                pScanChnInfo = (tSmeGetScanChnRsp *)pMsgBuf;
+                csrScanAgeResults(pMac, pScanChnInfo);
+                break;
+            case eCsrScanForCapsChange:
+                csrScanProcessScanResults( pMac, pCommand, pScanRsp, &fRemoveCommand );
+                break;
+#if WLAN_FEATURE_P2P
+            case eCsrScanP2PFindPeer:
+              scanStatus = ((eSIR_SME_SUCCESS == pScanRsp->statusCode) && (pScanRsp->length > 50)) ? eCSR_SCAN_FOUND_PEER : eCSR_SCAN_FAILURE;
+              csrScanProcessScanResults( pMac, pCommand, pScanRsp, NULL );
+              break;
+#endif                
+            case eCsrScanSetBGScanParam:
+            default:
+                if(csrScanProcessScanResults( pMac, pCommand, pScanRsp, &fRemoveCommand ))
+                {
+                    //Not to get channel info if the scan is not a wildcard scan because
+                    //it may cause scan results got aged out incorrectly.
+                    if( csrScanIsWildCardScan( pMac, pCommand ) && (!pCommand->u.scanCmd.u.scanRequest.p2pSearch) )
+                    {
+                        //Get the list of channels scanned
+                        csrScanGetScanChnInfo(pMac);
+                    }
+                }
+                break;
+            }//switch
+            if(fRemoveCommand)
+            {
+
+                csrReleaseScanCommand(pMac, pCommand, scanStatus);
+
+            }
+            smeProcessPendingQueue( pMac );
+        }
+        else
+        {
+            smsLog( pMac, LOGW, "CSR: Scan Completion called but SCAN command is not ACTIVE ..." );
+            status = eHAL_STATUS_FAILURE;
+        }
+    }
+    else
+    {
+        smsLog( pMac, LOGW, "CSR: Scan Completion called but NO commands are ACTIVE ..." );
+        status = eHAL_STATUS_FAILURE;
+    }
+    
+    return (status);
+}
+
+
+
+
+tCsrScanResultInfo *csrScanResultGetFirst(tpAniSirGlobal pMac, tScanResultHandle hScanResult)
+{
+    tListElem *pEntry;
+    tCsrScanResult *pResult;
+    tCsrScanResultInfo *pRet = NULL;
+    tScanResultList *pResultList = (tScanResultList *)hScanResult;
+    
+    if(pResultList)
+    {
+        csrLLLock(&pResultList->List);
+        pEntry = csrLLPeekHead(&pResultList->List, LL_ACCESS_NOLOCK);
+        if(pEntry)
+        {
+            pResult = GET_BASE_ADDR(pEntry, tCsrScanResult, Link);
+            pRet = &pResult->Result;
+        }
+        pResultList->pCurEntry = pEntry;
+        csrLLUnlock(&pResultList->List);
+    }
+    
+    return pRet;
+}
+
+
+tCsrScanResultInfo *csrScanResultGetNext(tpAniSirGlobal pMac, tScanResultHandle hScanResult)
+{
+    tListElem *pEntry = NULL;
+    tCsrScanResult *pResult = NULL;
+    tCsrScanResultInfo *pRet = NULL;
+    tScanResultList *pResultList = (tScanResultList *)hScanResult;
+    
+    if(pResultList)
+    {
+        csrLLLock(&pResultList->List);
+        if(NULL == pResultList->pCurEntry)
+        {
+            pEntry = csrLLPeekHead(&pResultList->List, LL_ACCESS_NOLOCK);
+        }
+        else
+        {
+            pEntry = csrLLNext(&pResultList->List, pResultList->pCurEntry, LL_ACCESS_NOLOCK);
+        }
+        if(pEntry)
+        {
+            pResult = GET_BASE_ADDR(pEntry, tCsrScanResult, Link);
+            pRet = &pResult->Result;
+        }
+        pResultList->pCurEntry = pEntry;
+        csrLLUnlock(&pResultList->List);
+    }
+    
+    return pRet;
+}
+
+
+//This function moves the first BSS that matches the bssid to the head of the result
+eHalStatus csrMoveBssToHeadFromBSSID(tpAniSirGlobal pMac, tCsrBssid *bssid, tScanResultHandle hScanResult)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tScanResultList *pResultList = (tScanResultList *)hScanResult;
+    tCsrScanResult *pResult = NULL;
+    tListElem *pEntry = NULL;
+   
+    if(pResultList && bssid)
+    {
+        csrLLLock(&pResultList->List);
+        pEntry = csrLLPeekHead(&pResultList->List, LL_ACCESS_NOLOCK);
+        while(pEntry)
+        {
+            pResult = GET_BASE_ADDR(pEntry, tCsrScanResult, Link);
+            if(palEqualMemory(pMac->hHdd, bssid, pResult->Result.BssDescriptor.bssId, sizeof(tCsrBssid)))
+            {
+                status = eHAL_STATUS_SUCCESS;
+                csrLLRemoveEntry(&pResultList->List, pEntry, LL_ACCESS_NOLOCK);
+                csrLLInsertHead(&pResultList->List, pEntry, LL_ACCESS_NOLOCK);
+                break;
+            }
+            pEntry = csrLLNext(&pResultList->List, pResultList->pCurEntry, LL_ACCESS_NOLOCK);
+        }
+        csrLLUnlock(&pResultList->List);
+    }
+    
+    return (status);
+}
+
+
+//Remove the BSS if possible.
+//Return -- TRUE == the BSS is remove. False == Fail to remove it
+//This function is called when list lock is held. Be caution what functions it can call.
+tANI_BOOLEAN csrScanAgeOutBss(tpAniSirGlobal pMac, tCsrScanResult *pResult)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    tANI_U32 i;
+    tCsrRoamSession *pSession;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) )
+        {
+            pSession = CSR_GET_SESSION( pMac, i );
+            //Not to remove the BSS we are connected to.
+            if(csrIsConnStateDisconnected(pMac, i) || (NULL == pSession->pConnectBssDesc) ||
+              (!csrIsDuplicateBssDescription(pMac, &pResult->Result.BssDescriptor, 
+                                                      pSession->pConnectBssDesc, NULL))
+              )
+            {
+                smsLog(pMac, LOGW, "Aging out BSS %02X-%02X-%02X-%02X-%02X-%02X Channel %d\n",
+                                          pResult->Result.BssDescriptor.bssId[0],
+                                          pResult->Result.BssDescriptor.bssId[1],
+                                          pResult->Result.BssDescriptor.bssId[2],
+                                          pResult->Result.BssDescriptor.bssId[3],
+                                          pResult->Result.BssDescriptor.bssId[4],
+                                          pResult->Result.BssDescriptor.bssId[5],
+                                          pResult->Result.BssDescriptor.channelId);
+                //No need to hold the spin lock because caller should hold the lock for pMac->scan.scanResultList
+                if( csrLLRemoveEntry(&pMac->scan.scanResultList, &pResult->Link, LL_ACCESS_NOLOCK) )
+                {
+                    csrFreeScanResultEntry(pMac, pResult);
+                }
+                fRet = eANI_BOOLEAN_TRUE;
+                break;
+            }
+        } //valid session
+    } //for
+    if( CSR_ROAM_SESSION_MAX == i )
+    {
+        //reset the counter so this won't hapeen too soon
+        pResult->AgingCount = (tANI_S32)pMac->roam.configParam.agingCount;
+        pResult->Result.BssDescriptor.nReceivedTime = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
+    }
+
+    return (fRet);
+}
+
+
+eHalStatus csrScanAgeResults(tpAniSirGlobal pMac, tSmeGetScanChnRsp *pScanChnInfo)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tListElem *pEntry, *tmpEntry;
+    tCsrScanResult *pResult;
+    tLimScanChn *pChnInfo;
+    tANI_U8 i;
+
+    csrLLLock(&pMac->scan.scanResultList);
+    for(i = 0; i < pScanChnInfo->numChn; i++)
+    {
+        pChnInfo = &pScanChnInfo->scanChn[i];
+        pEntry = csrLLPeekHead( &pMac->scan.scanResultList, LL_ACCESS_NOLOCK );
+        while( pEntry ) 
+        {
+            tmpEntry = csrLLNext(&pMac->scan.scanResultList, pEntry, LL_ACCESS_NOLOCK);
+            pResult = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+            if(pResult->Result.BssDescriptor.channelId == pChnInfo->channelId)
+            {
+                pResult->AgingCount--;
+                if(pResult->AgingCount <= 0)
+                {
+                    smsLog(pMac, LOGW, " age out due to ref count");
+                    csrScanAgeOutBss(pMac, pResult);
+                }
+            }
+            pEntry = tmpEntry;
+        }
+    }
+    csrLLUnlock(&pMac->scan.scanResultList);
+
+    return (status);
+}
+
+
+eHalStatus csrSendMBScanReq( tpAniSirGlobal pMac, tANI_U16 sessionId, 
+                    tCsrScanRequest *pScanReq, tScanReqParam *pScanReqParam )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeScanReq *pMsg;
+    tANI_U16 msgLen;
+    tANI_U8 bssid[WNI_CFG_BSSID_LEN] = {0, 0, 0, 0, 0, 0};
+    tSirScanType scanType = pScanReq->scanType;
+    tANI_U32 minChnTime;    //in units of milliseconds
+    tANI_U32 maxChnTime;    //in units of milliseconds
+    tANI_U32 i;
+    tANI_U8 selfMacAddr[WNI_CFG_BSSID_LEN];
+    tANI_U8 *pSelfMac = NULL;
+
+    msgLen = (tANI_U16)(sizeof( tSirSmeScanReq ) - sizeof( pMsg->channelList.channelNumber ) + 
+                        ( sizeof( pMsg->channelList.channelNumber ) * pScanReq->ChannelInfo.numOfChannels )) +
+                   ( pScanReq->uIEFieldLen ) ;
+
+    status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        do
+        {
+            palZeroMemory(pMac->hHdd, pMsg, msgLen);
+            pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_SCAN_REQ);
+            pMsg->length = pal_cpu_to_be16(msgLen);
+            //ToDO: Fill in session info when we need to do scan base on session.
+            pMsg->sessionId = 0;
+            pMsg->transactionId = 0;
+            pMsg->dot11mode = (tANI_U8) csrTranslateToWNICfgDot11Mode(pMac, csrFindBestPhyMode( pMac, pMac->roam.configParam.phyMode ));
+            pMsg->bssType = pal_cpu_to_be32(csrTranslateBsstypeToMacType(pScanReq->BSSType));
+
+            if ( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+            {
+              pSelfMac = (tANI_U8 *)&pMac->roam.roamSession[sessionId].selfMacAddr;
+            }
+            else
+            {
+              // Since we don't have session for the scanning, we find a valid session. In case we fail to
+              // do so, get the WNI_CFG_STA_ID
+              for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+              {
+                if( CSR_IS_SESSION_VALID( pMac, i ) )
+                {
+                  pSelfMac = (tANI_U8 *)&pMac->roam.roamSession[i].selfMacAddr;
+                  break;
+                }
+              }
+              if( CSR_ROAM_SESSION_MAX == i )
+              {
+                tANI_U32 len = WNI_CFG_BSSID_LEN;
+                pSelfMac = selfMacAddr;
+                status = ccmCfgGetStr( pMac, WNI_CFG_STA_ID, pSelfMac, &len );
+                if( !HAL_STATUS_SUCCESS( status ) || 
+                    ( len < WNI_CFG_BSSID_LEN ) )
+                {
+                  smsLog( pMac, LOGE, FL(" Can not get self MAC address from CFG status = %d"), status );
+                  //Force failed status
+                  status = eHAL_STATUS_FAILURE;
+                  break;
+                }
+              }
+            }
+            palCopyMemory( pMac->hHdd, (tANI_U8 *)pMsg->selfMacAddr, pSelfMac, sizeof(tSirMacAddr) );
+
+            //sirCopyMacAddr
+            palCopyMemory( pMac->hHdd, (tANI_U8 *)pMsg->bssId, (tANI_U8 *)&pScanReq->bssid, sizeof(tSirMacAddr) );
+            if( palEqualMemory( pMac->hHdd, pScanReq->bssid, bssid, sizeof(tCsrBssid) ) )
+            {
+                palFillMemory( pMac->hHdd, pMsg->bssId, sizeof(tSirMacAddr), 0xff );
+            }
+            else
+            {
+                palCopyMemory(pMac->hHdd, pMsg->bssId, pScanReq->bssid, WNI_CFG_BSSID_LEN); 
+            }
+            minChnTime = pScanReq->minChnTime;
+            maxChnTime = pScanReq->maxChnTime;
+
+            //Verify the scan type first, if the scan is active scan, we need to make sure we 
+            //are allowed to do so.
+            /* if 11d is enabled & we don't see any beacon around, scan type falls
+               back to passive. But in BT AMP STA mode we need to send out a
+               directed probe*/
+            if( (eSIR_PASSIVE_SCAN != scanType) && (eCSR_SCAN_P2P_DISCOVERY != pScanReq->requestType)
+                && (eCSR_BSS_TYPE_WDS_STA != pScanReq->BSSType)
+                && (eANI_BOOLEAN_FALSE == pMac->scan.fEnableBypass11d))
+            {
+                scanType = pMac->scan.curScanType;
+                if(eSIR_PASSIVE_SCAN == pMac->scan.curScanType)
+                {
+                    if(minChnTime < pMac->roam.configParam.nPassiveMinChnTime) 
+                    {
+                        minChnTime = pMac->roam.configParam.nPassiveMinChnTime;
+                    }
+                    if(maxChnTime < pMac->roam.configParam.nPassiveMaxChnTime)
+                    {
+                        maxChnTime = pMac->roam.configParam.nPassiveMaxChnTime;
+                    }
+                }
+            }
+            pMsg->scanType = pal_cpu_to_be32(scanType);
+
+        pMsg->numSsid = (pScanReq->SSIDs.numOfSSIDs < SIR_SCAN_MAX_NUM_SSID) ? pScanReq->SSIDs.numOfSSIDs :
+                                                        SIR_SCAN_MAX_NUM_SSID;
+            if((pScanReq->SSIDs.numOfSSIDs != 0) && ( eSIR_PASSIVE_SCAN != scanType ))
+            {
+            for (i = 0; i < pMsg->numSsid; i++)
+            {
+                palCopyMemory(pMac->hHdd, &pMsg->ssId[i], &pScanReq->SSIDs.SSIDList[i].SSID, sizeof(tSirMacSSid));
+            }
+            }
+            else
+            {
+                //Otherwise we scan all SSID and let the result filter later
+            for (i = 0; i < SIR_SCAN_MAX_NUM_SSID; i++)
+            {
+                pMsg->ssId[i].length = 0;
+            }
+            }
+
+//TODO: This preprocessor macro should be removed from CSR for production driver
+//This is a temperarory fix for scanning on FPGA.
+#if defined (ANI_CHIPSET_VIRGO) || defined (LIBRA_FPGA)|| defined (VOLANS_FPGA)
+            pMsg->minChannelTime = pal_cpu_to_be32(minChnTime * 8);
+            pMsg->maxChannelTime = pal_cpu_to_be32(maxChnTime * 8);
+#elif defined (ANI_CHIPSET_TAURUS) || defined(ANI_CHIPSET_LIBRA) || defined(ANI_CHIPSET_VOLANS)
+            pMsg->minChannelTime = pal_cpu_to_be32(minChnTime);
+            pMsg->maxChannelTime = pal_cpu_to_be32(maxChnTime);
+#else
+#error unknown chipset
+#endif
+            //hidden SSID option
+            pMsg->hiddenSsid = pScanReqParam->hiddenSsid;
+            //rest time
+            //pMsg->restTime = pScanReq->restTime;
+            pMsg->returnAfterFirstMatch = pScanReqParam->bReturnAfter1stMatch;
+            // All the scan results caching will be done by Roaming
+            // We do not want LIM to do any caching of scan results,
+            // so delete the LIM cache on all scan requests
+            pMsg->returnFreshResults = pScanReqParam->freshScan;
+            //Always ask for unique result
+            pMsg->returnUniqueResults = pScanReqParam->fUniqueResult;
+            pMsg->channelList.numChannels = (tANI_U8)pScanReq->ChannelInfo.numOfChannels;
+            if(pScanReq->ChannelInfo.numOfChannels)
+            {
+                //Assuming the channelNumber is tANI_U8 (1 byte)
+                status = palCopyMemory(pMac->hHdd, pMsg->channelList.channelNumber, pScanReq->ChannelInfo.ChannelList, 
+                                        pScanReq->ChannelInfo.numOfChannels);
+            }
+
+            pMsg->uIEFieldLen = (tANI_U16) pScanReq->uIEFieldLen;
+            pMsg->uIEFieldOffset = (tANI_U16)(sizeof( tSirSmeScanReq ) - sizeof( pMsg->channelList.channelNumber ) + 
+                  ( sizeof( pMsg->channelList.channelNumber ) * pScanReq->ChannelInfo.numOfChannels )) ;
+            if(pScanReq->uIEFieldLen != 0) 
+            {
+                palCopyMemory(pMac->hHdd, (tANI_U8 *)pMsg+pMsg->uIEFieldOffset,
+                                    pScanReq->pIEField, pScanReq->uIEFieldLen );
+            }
+#ifdef WLAN_FEATURE_P2P
+            pMsg->p2pSearch = pScanReq->p2pSearch;
+#endif
+
+        }while(0);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            status = palSendMBMessage(pMac->hHdd, pMsg);
+        }
+        else {
+            palFreeMemory(pMac->hHdd, pMsg);
+        }
+    }//Success allocated memory
+
+
+    return( status );
+}
+
+eHalStatus csrSendMBScanResultReq( tpAniSirGlobal pMac, tScanReqParam *pScanReqParam )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeScanReq *pMsg;
+    tANI_U16 msgLen;
+
+    msgLen = (tANI_U16)(sizeof( tSirSmeScanReq ));
+    status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, pMsg, msgLen);
+        pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_SCAN_REQ);
+        pMsg->length = pal_cpu_to_be16(msgLen);
+        pMsg->sessionId = 0;
+        pMsg->returnFreshResults = pScanReqParam->freshScan;
+        //Always ask for unique result
+        pMsg->returnUniqueResults = pScanReqParam->fUniqueResult;
+        pMsg->returnAfterFirstMatch = pScanReqParam->bReturnAfter1stMatch;
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+    }                             
+
+    return( status );
+}
+
+
+
+eHalStatus csrScanChannels( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tScanReqParam scanReq;
+    
+    do
+    {    
+        scanReq.freshScan = CSR_SME_SCAN_FLAGS_DELETE_CACHE | TRUE;
+        scanReq.fUniqueResult = TRUE;
+        scanReq.hiddenSsid = SIR_SCAN_NO_HIDDEN_SSID;
+        if(eCsrScanForSsid == pCommand->u.scanCmd.reason)
+        {
+            scanReq.bReturnAfter1stMatch = CSR_SCAN_RETURN_AFTER_FIRST_MATCH;
+        }
+        else
+        {
+            // Basically do scan on all channels even for 11D 1st scan case.
+            scanReq.bReturnAfter1stMatch = CSR_SCAN_RETURN_AFTER_ALL_CHANNELS;
+        }
+        if((eCsrScanBgScan == pCommand->u.scanCmd.reason)||
+           (eCsrScanProbeBss == pCommand->u.scanCmd.reason))
+        {
+            scanReq.hiddenSsid = SIR_SCAN_HIDDEN_SSID_PE_DECISION;
+        }
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+        {
+            vos_log_scan_pkt_type *pScanLog = NULL;
+
+            WLAN_VOS_DIAG_LOG_ALLOC(pScanLog, vos_log_scan_pkt_type, LOG_WLAN_SCAN_C);
+            if(pScanLog)
+            {
+                if(eCsrScanBgScan == pCommand->u.scanCmd.reason || 
+                    eCsrScanProbeBss == pCommand->u.scanCmd.reason)
+                {
+                    pScanLog->eventId = WLAN_SCAN_EVENT_HO_SCAN_REQ;
+                }
+                else
+                {
+                    if( (eSIR_PASSIVE_SCAN != pCommand->u.scanCmd.u.scanRequest.scanType) && 
+                        (eSIR_PASSIVE_SCAN != pMac->scan.curScanType) )
+                    {
+                        pScanLog->eventId = WLAN_SCAN_EVENT_ACTIVE_SCAN_REQ;
+                    }
+                    else
+                    {
+                        pScanLog->eventId = WLAN_SCAN_EVENT_PASSIVE_SCAN_REQ;
+                    }
+                }
+                pScanLog->minChnTime = (v_U8_t)pCommand->u.scanCmd.u.scanRequest.minChnTime;
+                pScanLog->maxChnTime = (v_U8_t)pCommand->u.scanCmd.u.scanRequest.maxChnTime;
+                pScanLog->numChannel = (v_U8_t)pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels;
+                if(pScanLog->numChannel && (pScanLog->numChannel < VOS_LOG_MAX_NUM_CHANNEL))
+                {
+                    palCopyMemory(pMac->hHdd, pScanLog->channels,
+                                  pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList,
+                                  pScanLog->numChannel);
+                }
+                WLAN_VOS_DIAG_LOG_REPORT(pScanLog);
+            }
+        }
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+
+        status = csrSendMBScanReq(pMac, pCommand->sessionId,
+                                &pCommand->u.scanCmd.u.scanRequest, &scanReq);
+    }while(0);
+    
+    return( status );
+}
+
+
+eHalStatus csrScanRetrieveResult(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tScanReqParam scanReq;
+    
+    do
+    {    
+        //not a fresh scan
+        scanReq.freshScan = CSR_SME_SCAN_FLAGS_DELETE_CACHE;
+        scanReq.fUniqueResult = TRUE;
+        scanReq.bReturnAfter1stMatch = CSR_SCAN_RETURN_AFTER_ALL_CHANNELS;
+        status = csrSendMBScanResultReq(pMac, &scanReq);
+    }while(0);
+    
+    return (status);
+}
+
+
+
+eHalStatus csrProcessScanCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrChannelInfo newChannelInfo = {0, NULL};
+    int i, j;
+    tANI_U8 *pChannel = NULL;
+    tANI_U32 len = 0;
+
+    // Transition to Scanning state...
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+       if(CSR_IS_SESSION_VALID(pMac, i))
+       {
+      pCommand->u.scanCmd.lastRoamState[i] = csrRoamStateChange( pMac, eCSR_ROAMING_STATE_SCANNING, i);
+      smsLog( pMac, LOG3, "starting SCAN command from %d state.... reason is %d\n", pCommand->u.scanCmd.lastRoamState[i], pCommand->u.scanCmd.reason );
+       }
+    }
+
+    switch(pCommand->u.scanCmd.reason)
+    {
+    case eCsrScanGetResult:
+    case eCsrScanForCapsChange:     //For cap change, LIM already save BSS description
+        status = csrScanRetrieveResult(pMac);
+        break;
+    case eCsrScanSetBGScanParam:
+        status = csrProcessSetBGScanParam(pMac, pCommand);
+        break;
+    case eCsrScanBGScanAbort:
+        status = csrSetCfgBackgroundScanPeriod(pMac, 0);
+        break;
+    case eCsrScanBGScanEnable:
+        status = csrSetCfgBackgroundScanPeriod(pMac, pMac->roam.configParam.bgScanInterval);
+        break;
+    case eCsrScanGetScanChnInfo:
+        status = csrScanGetScanChannelInfo(pMac);
+        break;
+    case eCsrScanUserRequest:
+        if(pMac->roam.configParam.fScanTwice)
+        {
+            //We scan 2.4 channel twice
+            if(pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels &&
+               (NULL != pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList))
+            {
+                len = pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels;
+                //allocate twice the channel
+                newChannelInfo.ChannelList = (tANI_U8 *)vos_mem_malloc(newChannelInfo.numOfChannels * 2);
+                pChannel = pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList;
+            }
+            else
+            {
+                //get the valid channel list to scan all.
+                len = sizeof(pMac->roam.validChannelList);
+
+                if (HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, (tANI_U8 *)pMac->roam.validChannelList, &len)))
+                {
+                    //allocate twice the channel
+                    newChannelInfo.ChannelList = (tANI_U8 *)vos_mem_malloc(len * 2);
+                    pChannel = pMac->roam.validChannelList;
+                }
+            }
+            if(NULL == newChannelInfo.ChannelList)
+            {
+                newChannelInfo.numOfChannels = 0;
+            }
+            else
+            {
+                j = 0;
+                for(i = 0; i < len; i++)
+                {
+                    newChannelInfo.ChannelList[j++] = pChannel[i];
+                    if(CSR_MAX_24GHz_CHANNEL_NUMBER >= pChannel[i])
+                    {
+                        newChannelInfo.ChannelList[j++] = pChannel[i];
+                    }
+                }
+                if(NULL != pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList)
+                {
+                    //pChannel points to the channellist from the command, free it.
+                    vos_mem_free(pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList);
+                }
+                pCommand->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = j;
+                pCommand->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList = newChannelInfo.ChannelList;
+            }
+        } //if(pMac->roam.configParam.fScanTwice)
+
+        status = csrScanChannels(pMac, pCommand);
+
+        break;
+    default:
+        status = csrScanChannels(pMac, pCommand);
+        break;
+    }    
+    
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        csrReleaseScanCommand(pMac, pCommand, eCSR_SCAN_FAILURE);
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrScanSetBGScanparams(tpAniSirGlobal pMac, tCsrBGScanRequest *pScanReq)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand = NULL;
+    
+    if(pScanReq)
+    {
+        do
+        {
+            pCommand = csrGetCommandBuffer(pMac);
+            if(!pCommand)
+            {
+                status = eHAL_STATUS_RESOURCES;
+                break;
+            }
+            palZeroMemory(pMac->hHdd, &pCommand->u.scanCmd, sizeof(tScanCmd));
+            pCommand->command = eSmeCommandScan;
+            pCommand->u.scanCmd.reason = eCsrScanSetBGScanParam;
+            pCommand->u.scanCmd.callback = NULL;
+            pCommand->u.scanCmd.pContext = NULL;
+            palCopyMemory(pMac->hHdd, &pCommand->u.scanCmd.u.bgScanRequest, pScanReq, sizeof(tCsrBGScanRequest));
+            //we have to do the follow
+            if(pScanReq->ChannelInfo.numOfChannels == 0)
+            {
+                pCommand->u.scanCmd.u.bgScanRequest.ChannelInfo.ChannelList = NULL;
+            }
+            else
+            {
+                status = palAllocateMemory(pMac->hHdd, (void **)&pCommand->u.scanCmd.u.bgScanRequest.ChannelInfo.ChannelList,
+                                             pScanReq->ChannelInfo.numOfChannels);
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    palCopyMemory(pMac->hHdd, pCommand->u.scanCmd.u.bgScanRequest.ChannelInfo.ChannelList,
+                                    pScanReq->ChannelInfo.ChannelList, pScanReq->ChannelInfo.numOfChannels); 
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, FL("ran out of memory\n"));
+                    csrReleaseCommandScan(pMac, pCommand);
+                    break;
+                }
+            }
+
+            //scan req for SSID
+            if(pScanReq->SSID.length)
+            {
+               palCopyMemory(pMac->hHdd, 
+                             pCommand->u.scanCmd.u.bgScanRequest.SSID.ssId,
+                             pScanReq->SSID.ssId, 
+                             pScanReq->SSID.length);
+               pCommand->u.scanCmd.u.bgScanRequest.SSID.length = pScanReq->SSID.length;
+
+            }
+            pCommand->u.scanCmd.u.bgScanRequest.maxChnTime= pScanReq->maxChnTime;
+            pCommand->u.scanCmd.u.bgScanRequest.minChnTime = pScanReq->minChnTime;
+            pCommand->u.scanCmd.u.bgScanRequest.scanInterval = pScanReq->scanInterval;
+
+
+            status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_FALSE);
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+                csrReleaseCommandScan( pMac, pCommand );
+                break;
+            }
+        }while(0);
+    }
+    
+    return (status);
+}
+
+eHalStatus csrScanBGScanAbort( tpAniSirGlobal pMac )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand = NULL;
+    
+    do
+    {
+        pCommand = csrGetCommandBuffer(pMac);
+        if(!pCommand)
+        {
+            status = eHAL_STATUS_RESOURCES;
+            break;
+        }
+        palZeroMemory(pMac->hHdd, &pCommand->u.scanCmd, sizeof(tScanCmd));
+        pCommand->command = eSmeCommandScan; 
+        pCommand->u.scanCmd.reason = eCsrScanBGScanAbort;
+        pCommand->u.scanCmd.callback = NULL;
+        pCommand->u.scanCmd.pContext = NULL;
+        status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_FALSE);
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+            csrReleaseCommandScan( pMac, pCommand );
+            break;
+        }
+    }while(0);
+    
+    return (status);
+}
+
+
+//This will enable the background scan with the non-zero interval 
+eHalStatus csrScanBGScanEnable(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSmeCmd *pCommand = NULL;
+    
+    if(pMac->roam.configParam.bgScanInterval)
+    {
+        do
+        {
+            pCommand = csrGetCommandBuffer(pMac);
+            if(!pCommand)
+            {
+                status = eHAL_STATUS_RESOURCES;
+                break;
+            }
+            palZeroMemory(pMac->hHdd, &pCommand->u.scanCmd, sizeof(tScanCmd));
+            pCommand->command = eSmeCommandScan; 
+            pCommand->u.scanCmd.reason = eCsrScanBGScanEnable;
+            pCommand->u.scanCmd.callback = NULL;
+            pCommand->u.scanCmd.pContext = NULL;
+            status = csrQueueSmeCommand(pMac, pCommand, eANI_BOOLEAN_FALSE);
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+                csrReleaseCommandScan( pMac, pCommand );
+                break;
+            }
+        }while(0);
+        //BG scan results are reported automatically by PE to SME once the scan is done.
+        //No need to fetch the results explicitly.
+        //csrScanStartGetResultTimer(pMac);
+        csrScanStartResultAgingTimer(pMac);
+    }
+    else
+    {
+        //We don't have BG scan so stop the aging timer
+        csrScanStopResultAgingTimer(pMac);
+        smsLog(pMac, LOGE, FL("cannot continue because the bgscan interval is 0\n"));
+        status = eHAL_STATUS_INVALID_PARAMETER;
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrScanCopyRequest(tpAniSirGlobal pMac, tCsrScanRequest *pDstReq, tCsrScanRequest *pSrcReq)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 len = sizeof(pMac->roam.validChannelList);
+    tANI_U32 index = 0;
+    tANI_U32 new_index = 0;
+
+    do
+    {
+        status = csrScanFreeRequest(pMac, pDstReq);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            status = palCopyMemory(pMac->hHdd, pDstReq, pSrcReq, sizeof(tCsrScanRequest));
+            if(pSrcReq->uIEFieldLen == 0)
+            {
+                pDstReq->pIEField = NULL;
+            }
+            else
+            {
+                status = palAllocateMemory(pMac->hHdd, (void **)&pDstReq->pIEField, pSrcReq->uIEFieldLen);
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    palCopyMemory(pMac->hHdd, pDstReq->pIEField, pSrcReq->pIEField, pSrcReq->uIEFieldLen);
+                    pDstReq->uIEFieldLen = pSrcReq->uIEFieldLen;
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, "No memory for scanning IE fields\n");
+                    break;
+                }
+            }//Allocate memory for IE field
+            {
+                if(pSrcReq->ChannelInfo.numOfChannels == 0)
+                {
+                    pDstReq->ChannelInfo.ChannelList = NULL;
+                        pDstReq->ChannelInfo.numOfChannels = 0;
+                }
+                else
+                {
+                    status = palAllocateMemory(pMac->hHdd, (void **)&pDstReq->ChannelInfo.ChannelList, 
+                                        pSrcReq->ChannelInfo.numOfChannels * sizeof(*pDstReq->ChannelInfo.ChannelList));
+                    if(!HAL_STATUS_SUCCESS(status))
+                    {
+                        pDstReq->ChannelInfo.numOfChannels = 0;
+                        smsLog(pMac, LOGE, "No memory for scanning Channel List\n");
+                        break;
+                    }
+
+                    if((pSrcReq->scanType == eSIR_PASSIVE_SCAN) && (pSrcReq->requestType == eCSR_SCAN_REQUEST_11D_SCAN))
+                    {
+                       for ( index = 0; index < pSrcReq->ChannelInfo.numOfChannels ; index++ )
+                       {
+                          pDstReq->ChannelInfo.ChannelList[new_index] =
+                                             pSrcReq->ChannelInfo.ChannelList[index];
+                          new_index++;
+                    }
+                       pDstReq->ChannelInfo.numOfChannels = new_index;
+                    }
+                    else if(HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, pMac->roam.validChannelList, &len)))
+                    {
+                        new_index = 0;
+                        pMac->roam.numValidChannels = len;
+                        for ( index = 0; index < pSrcReq->ChannelInfo.numOfChannels ; index++ )
+                        {
+                            if(csrRoamIsValidChannel(pMac, pSrcReq->ChannelInfo.ChannelList[index]))
+                            {
+                                pDstReq->ChannelInfo.ChannelList[new_index] =
+                                    pSrcReq->ChannelInfo.ChannelList[index];
+                                new_index++;
+                            }
+                        }
+                        pDstReq->ChannelInfo.numOfChannels = new_index;
+                    }
+                    else
+                    {
+                        smsLog(pMac, LOGE, "Couldn't get the valid Channel List, keeping requester's list\n");
+                        palCopyMemory(pMac->hHdd, pDstReq->ChannelInfo.ChannelList, pSrcReq->ChannelInfo.ChannelList, 
+                                        pSrcReq->ChannelInfo.numOfChannels * sizeof(*pDstReq->ChannelInfo.ChannelList));
+                        pDstReq->ChannelInfo.numOfChannels = pSrcReq->ChannelInfo.numOfChannels;
+                    }
+                }//Allocate memory for Channel List
+            }
+            if(pSrcReq->SSIDs.numOfSSIDs == 0)
+            {
+                pDstReq->SSIDs.numOfSSIDs = 0;
+                pDstReq->SSIDs.SSIDList = NULL;
+            }
+            else
+            {
+                status = palAllocateMemory(pMac->hHdd, (void **)&pDstReq->SSIDs.SSIDList, 
+                                    pSrcReq->SSIDs.numOfSSIDs * sizeof(*pDstReq->SSIDs.SSIDList));
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    pDstReq->SSIDs.numOfSSIDs = pSrcReq->SSIDs.numOfSSIDs;
+                    palCopyMemory(pMac->hHdd, pDstReq->SSIDs.SSIDList, pSrcReq->SSIDs.SSIDList, 
+                                    pSrcReq->SSIDs.numOfSSIDs * sizeof(*pDstReq->SSIDs.SSIDList));
+                }
+                else
+                {
+                    pDstReq->SSIDs.numOfSSIDs = 0;
+                    smsLog(pMac, LOGE, "No memory for scanning SSID List\n");
+                    break;
+                }
+            }//Allocate memory for SSID List
+#ifdef WLAN_FEATURE_P2P
+            pDstReq->p2pSearch = pSrcReq->p2pSearch;
+#endif
+
+        }
+    }while(0);
+    
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        csrScanFreeRequest(pMac, pDstReq);
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrScanFreeRequest(tpAniSirGlobal pMac, tCsrScanRequest *pReq)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    
+    if(pReq->ChannelInfo.ChannelList)
+    {
+        status = palFreeMemory(pMac->hHdd, pReq->ChannelInfo.ChannelList);
+        pReq->ChannelInfo.ChannelList = NULL;
+    }
+    pReq->ChannelInfo.numOfChannels = 0;
+    if(pReq->pIEField)
+    {
+        status = palFreeMemory(pMac->hHdd, pReq->pIEField);
+        pReq->pIEField = NULL;
+    }
+    pReq->uIEFieldLen = 0;
+    if(pReq->SSIDs.SSIDList)
+    {
+        palFreeMemory(pMac->hHdd, pReq->SSIDs.SSIDList);
+        pReq->SSIDs.SSIDList = NULL;
+    }
+    pReq->SSIDs.numOfSSIDs = 0;
+    
+    return (status);
+}
+
+
+void csrScanCallCallback(tpAniSirGlobal pMac, tSmeCmd *pCommand, eCsrScanStatus scanStatus)
+{
+    if(pCommand->u.scanCmd.callback)
+    {
+//        sme_ReleaseGlobalLock( &pMac->sme );
+        pCommand->u.scanCmd.callback(pMac, pCommand->u.scanCmd.pContext, pCommand->u.scanCmd.scanID, scanStatus); 
+//        sme_AcquireGlobalLock( &pMac->sme );
+    } else {
+        smsLog( pMac, LOGW, "%s:%d - Callback NULL!!!\n", __FUNCTION__, __LINE__);
+    }
+}
+
+
+void csrScanStopTimers(tpAniSirGlobal pMac)
+{
+    csrScanStopResultAgingTimer(pMac);
+    csrScanStopIdleScanTimer(pMac);
+    csrScanStopGetResultTimer(pMac);
+}
+
+
+eHalStatus csrScanStartGetResultTimer(tpAniSirGlobal pMac)
+{
+    eHalStatus status;
+    
+    if(pMac->scan.fScanEnable)
+    {
+        status = palTimerStart(pMac->hHdd, pMac->scan.hTimerGetResult, CSR_SCAN_GET_RESULT_INTERVAL, eANI_BOOLEAN_TRUE);
+    }
+    else
+    {
+        status = eHAL_STATUS_FAILURE;
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrScanStopGetResultTimer(tpAniSirGlobal pMac)
+{
+    return (palTimerStop(pMac->hHdd, pMac->scan.hTimerGetResult));
+}
+
+
+void csrScanGetResultTimerHandler(void *pv)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pv );
+    
+    csrScanRequestResult(pMac);
+}
+
+#ifdef WLAN_AP_STA_CONCURRENCY
+static void csrStaApConcTimerHandler(void *pv)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pv );
+    tListElem *pEntry;
+    tSmeCmd *pScanCmd;
+
+    csrLLLock(&pMac->scan.scanCmdPendingList);
+
+    if ( NULL != ( pEntry = csrLLPeekHead( &pMac->scan.scanCmdPendingList, LL_ACCESS_NOLOCK) ) )
+    {    
+        tCsrScanRequest scanReq;
+        tSmeCmd *pSendScanCmd = NULL;
+        tANI_U8 numChn = 0;
+        tANI_U8 i;
+        tCsrChannelInfo *pChnInfo = &scanReq.ChannelInfo;
+        tANI_U8    channelToScan[WNI_CFG_VALID_CHANNEL_LIST_LEN];
+        eHalStatus status;
+       
+
+        pScanCmd = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        numChn = pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels;
+        if (numChn > 1)
+        {
+             palZeroMemory(pMac->hHdd, &scanReq, sizeof(tCsrScanRequest));
+
+             pSendScanCmd = csrGetCommandBuffer(pMac); //optimize this to use 2 command buffer only
+             if (!pSendScanCmd)
+             {
+                 smsLog( pMac, LOGE, FL(" Failed to get Queue command buffer\n") );
+                 csrLLUnlock(&pMac->scan.scanCmdPendingList);
+                 return;
+             }
+             pSendScanCmd->command = pScanCmd->command; 
+             pSendScanCmd->sessionId = pScanCmd->sessionId;
+             pSendScanCmd->u.scanCmd.callback = NULL;
+             pSendScanCmd->u.scanCmd.pContext = pScanCmd->u.scanCmd.pContext;
+             pSendScanCmd->u.scanCmd.reason = pScanCmd->u.scanCmd.reason;
+             pSendScanCmd->u.scanCmd.scanID = pMac->scan.nextScanID++; //let it wrap around
+
+             pChnInfo->numOfChannels = 1;
+             palCopyMemory(pMac->hHdd, &channelToScan[0], &pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[0], 
+                          1 * sizeof(tANI_U8)); //just send one channel
+             pChnInfo->ChannelList = &channelToScan[0];
+
+             for (i = 0; i < (numChn-2); i++)
+             {
+                 pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[i] = 
+                 pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[i+1]; //Move all the channels one step
+             }
+          
+             pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = numChn -1; //reduce outstanding # of channels to be scanned
+
+             scanReq.BSSType = eCSR_BSS_TYPE_ANY;
+             //Modify callers parameters in case of concurrency
+             scanReq.scanType = eSIR_ACTIVE_SCAN;
+             scanReq.maxChnTime = CSR_MIN(pScanCmd->u.scanCmd.u.scanRequest.maxChnTime,CSR_ACTIVE_MAX_CHANNEL_TIME_CONC);
+             scanReq.minChnTime =  CSR_MIN(pScanCmd->u.scanCmd.u.scanRequest.minChnTime,CSR_ACTIVE_MIN_CHANNEL_TIME_CONC);
+
+             status = csrScanCopyRequest(pMac, &pSendScanCmd->u.scanCmd.u.scanRequest, &scanReq);
+             if(!HAL_STATUS_SUCCESS(status))
+             {
+                 smsLog( pMac, LOGE, FL(" Failed to get copy csrScanRequest = %d\n"), status );
+                 csrLLUnlock(&pMac->scan.scanCmdPendingList);
+                 return;
+             }       
+        }
+        else
+        {    //numChn ==1 This is the last channel to be scanned
+             //last channel remaining to scan
+             pSendScanCmd = pScanCmd;
+             //remove this command from pending list 
+             if (csrLLRemoveHead( &pMac->scan.scanCmdPendingList, LL_ACCESS_NOLOCK) == NULL)
+             { //In case between PeekHead and here, the entry got removed by another thread.
+                 smsLog( pMac, LOGE, FL(" Failed to remove entry from scanCmdPendingList\n"));
+             }
+            
+        }               
+        csrQueueSmeCommand(pMac, pSendScanCmd, eANI_BOOLEAN_FALSE);
+
+    }
+
+    if (!csrLLIsListEmpty( &pMac->scan.scanCmdPendingList, LL_ACCESS_NOLOCK ))
+    {
+         palTimerStart(pMac->hHdd, pMac->scan.hTimerStaApConcTimer, 
+                 CSR_SCAN_STAAP_CONC_INTERVAL, eANI_BOOLEAN_FALSE);
+    }
+    csrLLUnlock(&pMac->scan.scanCmdPendingList);
+    
+}
+#endif
+
+eHalStatus csrScanStartResultAgingTimer(tpAniSirGlobal pMac)
+{
+    eHalStatus status;
+    
+    if(pMac->scan.fScanEnable)
+    {
+        status = palTimerStart(pMac->hHdd, pMac->scan.hTimerResultAging, CSR_SCAN_RESULT_AGING_INTERVAL, eANI_BOOLEAN_TRUE);
+    }
+    else
+    {
+        status = eHAL_STATUS_FAILURE;
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrScanStopResultAgingTimer(tpAniSirGlobal pMac)
+{
+    return (palTimerStop(pMac->hHdd, pMac->scan.hTimerResultAging));
+}
+
+
+//This function returns the maximum time a BSS is allowed in the scan result.
+//The time varies base on connection and power saving factors.
+//Not connected, No PS
+//Not connected, with PS
+//Connected w/o traffic, No PS
+//Connected w/o traffic, with PS
+//Connected w/ traffic, no PS -- Not supported
+//Connected w/ traffic, with PS -- Not supported
+//the return unit is in seconds. 
+tANI_U32 csrScanGetAgeOutTime(tpAniSirGlobal pMac)
+{
+    tANI_U32 nRet;
+
+    if(pMac->scan.nAgingCountDown)
+    {
+        //Calculate what should be the timeout value for this
+        nRet = pMac->scan.nLastAgeTimeOut * pMac->scan.nAgingCountDown;
+        pMac->scan.nAgingCountDown--;
+    }
+    else
+    {
+        if( csrIsAllSessionDisconnected( pMac ) )
+        {
+            if(pmcIsPowerSaveEnabled(pMac, ePMC_IDLE_MODE_POWER_SAVE))
+            {
+                nRet = pMac->roam.configParam.scanAgeTimeNCPS;
+            }
+            else
+            {
+                nRet = pMac->roam.configParam.scanAgeTimeNCNPS;
+            }
+        }
+        else
+        {
+            if(pmcIsPowerSaveEnabled(pMac, ePMC_BEACON_MODE_POWER_SAVE))
+            {
+                nRet = pMac->roam.configParam.scanAgeTimeCPS;
+            }
+            else
+            {
+                nRet = pMac->roam.configParam.scanAgeTimeCNPS;
+            }
+        }
+        //If state-change causing aging time out change, we want to delay it somewhat to avoid
+        //unnecessary removal of BSS. This is mostly due to transition from connect to disconnect.
+        if(pMac->scan.nLastAgeTimeOut > nRet)
+        {
+            if(nRet)
+            {
+                pMac->scan.nAgingCountDown = (pMac->scan.nLastAgeTimeOut / nRet);
+            }
+            pMac->scan.nLastAgeTimeOut = nRet;
+            nRet *= pMac->scan.nAgingCountDown;
+        }
+        else
+        {
+            pMac->scan.nLastAgeTimeOut = nRet;
+        }
+    }
+
+    return (nRet);
+}
+
+
+void csrScanResultAgingTimerHandler(void *pv)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pv );
+    tANI_BOOLEAN fDisconnected = csrIsAllSessionDisconnected(pMac);
+    
+    //no scan, no aging
+    if(pMac->scan.fScanEnable && 
+        (((eANI_BOOLEAN_FALSE == fDisconnected) && pMac->roam.configParam.bgScanInterval)    
+        || (fDisconnected && (pMac->scan.fCancelIdleScan == eANI_BOOLEAN_FALSE)))
+        )
+    {
+        tListElem *pEntry, *tmpEntry;
+        tCsrScanResult *pResult;
+        tANI_TIMESTAMP ageOutTime = (tANI_TIMESTAMP)(csrScanGetAgeOutTime(pMac) * PAL_TICKS_PER_SECOND); //turn it into 10ms units
+        tANI_TIMESTAMP curTime = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
+
+        csrLLLock(&pMac->scan.scanResultList);
+        pEntry = csrLLPeekHead( &pMac->scan.scanResultList, LL_ACCESS_NOLOCK );
+        while( pEntry ) 
+        {
+            tmpEntry = csrLLNext(&pMac->scan.scanResultList, pEntry, LL_ACCESS_NOLOCK);
+            pResult = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+            if((curTime - pResult->Result.BssDescriptor.nReceivedTime) > ageOutTime)
+            {
+                smsLog(pMac, LOGW, " age out due to time out");
+                csrScanAgeOutBss(pMac, pResult);
+            }
+            pEntry = tmpEntry;
+        }
+        csrLLUnlock(&pMac->scan.scanResultList);
+    }
+}
+
+
+eHalStatus csrScanStartIdleScanTimer(tpAniSirGlobal pMac, tANI_U32 interval)
+{
+    eHalStatus status;
+    
+    smsLog(pMac, LOG1, " csrScanStartIdleScanTimer \n ");
+    if((pMac->scan.fScanEnable) && (eANI_BOOLEAN_FALSE == pMac->scan.fCancelIdleScan) && interval)
+    {
+        pMac->scan.nIdleScanTimeGap += interval;
+        palTimerStop(pMac->hHdd, pMac->scan.hTimerIdleScan);
+        status = palTimerStart(pMac->hHdd, pMac->scan.hTimerIdleScan, interval, eANI_BOOLEAN_FALSE);
+        if( !HAL_STATUS_SUCCESS(status) )
+        {
+            smsLog(pMac, LOGE, "  Fail to start Idle scan timer. status = %d interval = %d\n", status, interval);
+            //This should not happen but set the flag to restart when ready
+            pMac->scan.fRestartIdleScan = eANI_BOOLEAN_TRUE;
+        }
+    }
+    else
+    {
+        if( pMac->scan.fScanEnable && (eANI_BOOLEAN_FALSE == pMac->scan.fCancelIdleScan) )
+        {
+            pMac->scan.fRestartIdleScan = eANI_BOOLEAN_TRUE;
+        }
+        status = eHAL_STATUS_FAILURE;
+    }
+    
+    return (status);
+}
+
+
+eHalStatus csrScanStopIdleScanTimer(tpAniSirGlobal pMac)
+{
+    return (palTimerStop(pMac->hHdd, pMac->scan.hTimerIdleScan));
+}
+
+
+//Stop CSR from asking for IMPS, This function doesn't disable IMPS from CSR
+void csrScanSuspendIMPS( tpAniSirGlobal pMac )
+{
+    csrScanCancelIdleScan(pMac);
+}
+
+
+//Start CSR from asking for IMPS. This function doesn't trigger CSR to request entering IMPS
+//because IMPS maybe disabled.
+void csrScanResumeIMPS( tpAniSirGlobal pMac )
+{
+    csrScanStartIdleScan( pMac );
+}
+
+
+void csrScanIMPSCallback(void *callbackContext, eHalStatus status)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( callbackContext );
+
+    if(eANI_BOOLEAN_FALSE == pMac->scan.fCancelIdleScan)
+    {
+        if(pMac->roam.configParam.IsIdleScanEnabled) 
+        {
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                if(csrIsAllSessionDisconnected(pMac) && !csrIsRoamCommandWaiting(pMac))
+                {
+                    smsLog(pMac, LOGW, FL("starts idle mode full scan\n"));
+                    csrScanAllChannels(pMac, eCSR_SCAN_IDLE_MODE_SCAN);
+                }
+                else
+                {
+                    smsLog(pMac, LOGW, FL("cannot start idle mode full scan\n"));
+                    //even though we are in timer handle, calling stop timer will make sure the timer
+                    //doesn't get to restart.
+                    csrScanStopIdleScanTimer(pMac);
+                }
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL("sees not success status (%d)\n"), status);
+            }
+        }
+        else
+        {//we might need another flag to check if CSR needs to request imps at all
+       
+            tANI_U32 nTime = 0;
+
+            pMac->scan.fRestartIdleScan = eANI_BOOLEAN_FALSE;
+            if(!HAL_STATUS_SUCCESS(csrScanTriggerIdleScan(pMac, &nTime)))
+            {
+                csrScanStartIdleScanTimer(pMac, nTime);
+            }
+        }
+    }
+}
+
+
+//Param: pTimeInterval -- Caller allocated memory in return, if failed, to specify the nxt time interval for 
+//idle scan timer interval
+//Return: Not success -- meaning it cannot start IMPS, caller needs to start a timer for idle scan
+eHalStatus csrScanTriggerIdleScan(tpAniSirGlobal pMac, tANI_U32 *pTimeInterval)
+{
+    eHalStatus status = eHAL_STATUS_CSR_WRONG_STATE;
+
+    //Do not trigger IMPS in case of concurrency
+    if (vos_concurrent_sessions_running())
+        return (status);
+
+    if(pTimeInterval)
+    {
+        *pTimeInterval = 0;
+    }
+
+    smsLog(pMac, LOGW, FL("called\n"));
+    if( smeCommandPending( pMac ) )
+    {
+        smsLog( pMac, LOGW, FL("  Cannot request IMPS because command pending\n") );
+        //Not to enter IMPS because more work to do
+        if(pTimeInterval)
+        {
+            *pTimeInterval = 0;
+        }
+        //restart when ready
+        pMac->scan.fRestartIdleScan = eANI_BOOLEAN_TRUE;
+
+        return (status);
+    }
+
+    if((pMac->scan.fScanEnable) && (eANI_BOOLEAN_FALSE == pMac->scan.fCancelIdleScan) 
+    /*&& pMac->roam.configParam.impsSleepTime*/)
+    {
+        //Stop get result timer because idle scan gets scan result out of PE
+        csrScanStopGetResultTimer(pMac);
+        if(pTimeInterval)
+        {
+            *pTimeInterval = pMac->roam.configParam.impsSleepTime;
+        }
+        //pmcRequestImps take a period in millisecond unit.
+        status = pmcRequestImps(pMac, pMac->roam.configParam.impsSleepTime / PAL_TIMER_TO_MS_UNIT, csrScanIMPSCallback, pMac);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            if(eHAL_STATUS_PMC_ALREADY_IN_IMPS != status)
+            {
+                //Do restart the timer if CSR thinks it cannot do IMPS
+                if( !csrCheckPSReady( pMac ) )
+                {
+                    if(pTimeInterval)
+                    {
+                    *pTimeInterval = 0;
+                }
+                    //Set the restart flag to true because that idle scan 
+                    //can be restarted even though the timer will not be running
+                    pMac->scan.fRestartIdleScan = eANI_BOOLEAN_TRUE;
+                }
+                else
+                {
+                    //For not now, we do a quicker retry
+                    if(pTimeInterval)
+                    {
+                    *pTimeInterval = CSR_IDLE_SCAN_WAIT_TIME;
+                }
+            }
+                smsLog(pMac, LOGW, FL("call pmcRequestImps and it returns status code (%d)\n"), status);
+            }
+            else
+            {
+                smsLog(pMac, LOGW, FL("already in IMPS\n"));
+                //Since CSR is the only module to request for IMPS. If it is already in IMPS, CSR assumes
+                //the callback will be called in the future. Should not happen though.
+                status = eHAL_STATUS_SUCCESS;
+                pMac->scan.nIdleScanTimeGap = 0;
+            }
+        }
+        else
+        {
+            //requested so let's reset the value
+            pMac->scan.nIdleScanTimeGap = 0;
+        }
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrScanStartIdleScan(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_CSR_WRONG_STATE;
+    tANI_U32 nTime = 0;
+
+    smsLog(pMac, LOGW, FL("called\n"));
+    if(pMac->roam.configParam.IsIdleScanEnabled)
+    {
+        //stop bg scan first
+        csrScanBGScanAbort(pMac);
+        //Stop get result timer because idle scan gets scan result out of PE
+        csrScanStopGetResultTimer(pMac);
+        //Enable aging timer since idle scan is going on
+        csrScanStartResultAgingTimer(pMac);
+    }
+    pMac->scan.fCancelIdleScan = eANI_BOOLEAN_FALSE;
+    status = csrScanTriggerIdleScan(pMac, &nTime);
+    if(!HAL_STATUS_SUCCESS(status))
+    {
+        csrScanStartIdleScanTimer(pMac, nTime);
+    }
+
+    return (status);
+}
+
+
+void csrScanCancelIdleScan(tpAniSirGlobal pMac)
+{
+    if(eANI_BOOLEAN_FALSE == pMac->scan.fCancelIdleScan)
+    {
+#ifdef WLAN_SOFTAP_FEATURE
+        if (vos_concurrent_sessions_running()) {
+            return;
+        }
+#endif
+        smsLog(pMac, LOG1, "  csrScanCancelIdleScan\n");
+        pMac->scan.fCancelIdleScan = eANI_BOOLEAN_TRUE;
+        //Set the restart flag in case later on it is uncancelled
+        pMac->scan.fRestartIdleScan = eANI_BOOLEAN_TRUE;
+        csrScanStopIdleScanTimer(pMac);
+        csrScanRemoveNotRoamingScanCommand(pMac);
+    }
+}
+
+
+void csrScanIdleScanTimerHandler(void *pv)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pv );
+    eHalStatus status;
+    tANI_U32 nTime = 0;
+
+    smsLog(pMac, LOGW, "  csrScanIdleScanTimerHandler called  ");
+    status = csrScanTriggerIdleScan(pMac, &nTime);
+    if(!HAL_STATUS_SUCCESS(status) && (eANI_BOOLEAN_FALSE == pMac->scan.fCancelIdleScan))
+    {
+        //Check whether it is time to actually do an idle scan
+        if(pMac->scan.nIdleScanTimeGap >= pMac->roam.configParam.impsSleepTime)
+        {
+            pMac->scan.nIdleScanTimeGap = 0;
+            csrScanIMPSCallback(pMac, eHAL_STATUS_SUCCESS);
+        }
+        else
+        {
+            csrScanStartIdleScanTimer(pMac, nTime);
+        }
+    }
+}
+
+
+
+
+tANI_BOOLEAN csrScanRemoveNotRoamingScanCommand(tpAniSirGlobal pMac)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    tListElem *pEntry, *pEntryTmp;
+    tSmeCmd *pCommand;
+    tDblLinkList localList;
+
+    vos_mem_zero(&localList, sizeof(tDblLinkList));
+    if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &localList)))
+    {
+        smsLog(pMac, LOGE, FL(" failed to open list"));
+        return fRet;
+    }
+
+    csrLLLock(&pMac->sme.smeCmdPendingList);
+    pEntry = csrLLPeekHead(&pMac->sme.smeCmdPendingList, LL_ACCESS_NOLOCK);
+    while(pEntry)
+    {
+        pEntryTmp = csrLLNext(&pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_NOLOCK);
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+        if( eSmeCommandScan == pCommand->command )
+        {
+            switch( pCommand->u.scanCmd.reason )
+            {
+            case eCsrScanIdleScan:
+                if( csrLLRemoveEntry(&pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_NOLOCK) )
+                {
+                    csrLLInsertTail(&localList, pEntry, LL_ACCESS_NOLOCK);
+                }
+                fRet = eANI_BOOLEAN_TRUE;
+                break;
+
+            default:
+                break;
+            } //switch
+        }
+        pEntry = pEntryTmp;
+    }
+
+    csrLLUnlock(&pMac->sme.smeCmdPendingList);
+
+    while( (pEntry = csrLLRemoveHead(&localList, LL_ACCESS_NOLOCK)) )
+    {
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+        csrReleaseCommandScan( pMac, pCommand );
+    }
+
+    csrLLClose(&localList);
+
+    return (fRet);
+}
+
+
+tANI_BOOLEAN csrScanRemoveFreshScanCommand(tpAniSirGlobal pMac, tANI_U8 sessionId)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    tListElem *pEntry, *pEntryTmp;
+    tSmeCmd *pCommand;
+    tDblLinkList localList;
+
+    vos_mem_zero(&localList, sizeof(tDblLinkList));
+    if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &localList)))
+    {
+        smsLog(pMac, LOGE, FL(" failed to open list"));
+        return fRet;
+    }
+
+    csrLLLock(&pMac->sme.smeCmdPendingList);
+    pEntry = csrLLPeekHead(&pMac->sme.smeCmdPendingList, LL_ACCESS_NOLOCK);
+    while(pEntry)
+    {
+        pEntryTmp = csrLLNext(&pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_NOLOCK);
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+        if( (eSmeCommandScan == pCommand->command) && (sessionId == pCommand->sessionId) )
+        {
+            switch(pCommand->u.scanCmd.reason)
+            {
+            case eCsrScanGetResult:
+            case eCsrScanSetBGScanParam:
+            case eCsrScanBGScanAbort:
+            case eCsrScanBGScanEnable:
+            case eCsrScanGetScanChnInfo:
+                break;
+            default:
+                 smsLog (pMac, LOGW, "%s: -------- abort scan command reason = %d\n",
+                    __FUNCTION__, pCommand->u.scanCmd.reason);
+                //The rest are fresh scan requests
+                if( csrLLRemoveEntry(&pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_NOLOCK) )
+                {
+                    csrLLInsertTail(&localList, pEntry, LL_ACCESS_NOLOCK);
+                }
+                fRet = eANI_BOOLEAN_TRUE;
+                break;
+            }
+        }
+        pEntry = pEntryTmp;
+    }
+
+    csrLLUnlock(&pMac->sme.smeCmdPendingList);
+
+    while( (pEntry = csrLLRemoveHead(&localList, LL_ACCESS_NOLOCK)) )
+    {
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+        if (pCommand->u.scanCmd.callback)
+        {
+            /* User scan request is pending, 
+                                 * send response with status eCSR_SCAN_ABORT*/
+            pCommand->u.scanCmd.callback(pMac, 
+                     pCommand->u.scanCmd.pContext, 
+                     pCommand->u.scanCmd.scanID, 
+                     eCSR_SCAN_ABORT);
+        }
+        csrReleaseCommandScan( pMac, pCommand );
+    }
+    csrLLClose(&localList);
+
+    return (fRet);
+}
+
+
+void csrReleaseScanCommand(tpAniSirGlobal pMac, tSmeCmd *pCommand, eCsrScanStatus scanStatus)
+{
+    eCsrScanReason reason = pCommand->u.scanCmd.reason;
+    tANI_U32 i;
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+       if(CSR_IS_SESSION_VALID(pMac, i))
+           csrRoamStateChange( pMac, pCommand->u.scanCmd.lastRoamState[i], i);
+    }
+
+        csrScanCallCallback(pMac, pCommand, scanStatus);
+
+    smsLog(pMac, LOG3, "   Remove Scan command reason = %d\n", reason);
+    if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, &pCommand->Link, LL_ACCESS_LOCK ) )
+    {
+        csrReleaseCommandScan( pMac, pCommand );
+    }
+    else
+    {
+        smsLog(pMac, LOGE, " ********csrReleaseScanCommand cannot release command reason %d\n", pCommand->u.scanCmd.reason );
+    }
+}
+
+
+eHalStatus csrScanGetPMKIDCandidateList(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                        tPmkidCandidateInfo *pPmkidList, tANI_U32 *pNumItems )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, "  pMac->scan.NumPmkidCandidate = %d\n ", pSession->NumPmkidCandidate);
+    csrResetPMKIDCandidateList(pMac, sessionId);
+    if(csrIsConnStateConnected(pMac, sessionId) && pSession->pCurRoamProfile)
+    {
+        tCsrScanResultFilter *pScanFilter;
+        tCsrScanResultInfo *pScanResult;
+        tScanResultHandle hBSSList;
+        tANI_U32 nItems = *pNumItems;
+
+        *pNumItems = 0;
+        status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            //Here is the profile we need to connect to
+            status = csrRoamPrepareFilterFromProfile(pMac, pSession->pCurRoamProfile, pScanFilter);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    while(((pScanResult = csrScanResultGetNext(pMac, hBSSList)) != NULL) && ( pSession->NumPmkidCandidate < nItems))
+                    {
+                        //NumPmkidCandidate adds up here
+                        csrProcessBSSDescForPMKIDList(pMac, &pScanResult->BssDescriptor, 
+                                                      (tDot11fBeaconIEs *)( pScanResult->pvIes ));
+                    }
+                    if(pSession->NumPmkidCandidate)
+                    {
+                        *pNumItems = pSession->NumPmkidCandidate;
+                        palCopyMemory(pMac->hHdd, pPmkidList, pSession->PmkidCandidateInfo, 
+                                      pSession->NumPmkidCandidate * sizeof(tPmkidCandidateInfo));
+                    }
+                    csrScanResultPurge(pMac, hBSSList);
+                }//Have scan result
+                csrFreeScanFilter(pMac, pScanFilter);
+            }
+            palFreeMemory(pMac->hHdd, pScanFilter);
+        }
+    }
+
+    return (status);
+}
+
+
+
+#ifdef FEATURE_WLAN_WAPI
+eHalStatus csrScanGetBKIDCandidateList(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                       tBkidCandidateInfo *pBkidList, tANI_U32 *pNumItems )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    smsLog(pMac, LOGW, "  pMac->scan.NumBkidCandidate = %d\n ", pSession->NumBkidCandidate);
+    csrResetBKIDCandidateList(pMac, sessionId);
+    if(csrIsConnStateConnected(pMac, sessionId) && pSession->pCurRoamProfile)
+    {
+        tCsrScanResultFilter *pScanFilter;
+        tCsrScanResultInfo *pScanResult;
+        tScanResultHandle hBSSList;
+        tANI_U32 nItems = *pNumItems;
+        *pNumItems = 0;
+        status = palAllocateMemory(pMac->hHdd, (void **)&pScanFilter, sizeof(tCsrScanResultFilter));
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pScanFilter, sizeof(tCsrScanResultFilter));
+            //Here is the profile we need to connect to
+            status = csrRoamPrepareFilterFromProfile(pMac, pSession->pCurRoamProfile, pScanFilter);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                status = csrScanGetResult(pMac, pScanFilter, &hBSSList);
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    while(((pScanResult = csrScanResultGetNext(pMac, hBSSList)) != NULL) && ( pSession->NumBkidCandidate < nItems))
+                    {
+                        //pMac->scan.NumBkidCandidate adds up here
+                        csrProcessBSSDescForBKIDList(pMac, &pScanResult->BssDescriptor,
+                              (tDot11fBeaconIEs *)( pScanResult->pvIes ));
+
+                    }
+                    if(pSession->NumBkidCandidate)
+                    {
+                        *pNumItems = pSession->NumBkidCandidate;
+                        palCopyMemory(pMac->hHdd, pBkidList, pSession->BkidCandidateInfo, pSession->NumBkidCandidate * sizeof(tBkidCandidateInfo));
+                    }
+                    csrScanResultPurge(pMac, hBSSList);
+                }//Have scan result
+            }
+            palFreeMemory(pMac->hHdd, pScanFilter);
+        }
+    }
+
+    return (status);
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+
+
+//This function is usually used for BSSs that suppresses SSID so the profile 
+//shall have one and only one SSID
+eHalStatus csrScanForSSID(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, tANI_U32 roamId)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tSmeCmd *pScanCmd = NULL;
+    tANI_U8 bAddr[6] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff}; 
+    tANI_U8  index = 0;
+    tANI_U32 numSsid = pProfile->SSIDs.numOfSSIDs;
+
+    smsLog(pMac, LOG2, FL("called\n"));
+    //For WDS, we use the index 0. There must be at least one in there
+    if( CSR_IS_WDS_STA( pProfile ) && numSsid )
+    {
+        numSsid = 1;
+    }
+    if(pMac->scan.fScanEnable && ( numSsid == 1 ) )
+    {
+        do
+        {
+            pScanCmd = csrGetCommandBuffer(pMac);
+            if(!pScanCmd)
+            {
+                smsLog(pMac, LOGE, FL("failed to allocate command buffer\n"));
+                break;
+            }
+            palZeroMemory(pMac->hHdd, &pScanCmd->u.scanCmd, sizeof(tScanCmd));
+            status = palAllocateMemory(pMac->hHdd, (void **)&pScanCmd->u.scanCmd.pToRoamProfile, sizeof(tCsrRoamProfile));
+            if(!HAL_STATUS_SUCCESS(status))
+                break;
+            status = csrRoamCopyProfile(pMac, pScanCmd->u.scanCmd.pToRoamProfile, pProfile);
+            if(!HAL_STATUS_SUCCESS(status))
+                break;
+            pScanCmd->u.scanCmd.roamId = roamId;
+            pScanCmd->command = eSmeCommandScan;
+            pScanCmd->sessionId = (tANI_U8)sessionId; 
+            pScanCmd->u.scanCmd.callback = NULL;
+            pScanCmd->u.scanCmd.pContext = NULL;
+            pScanCmd->u.scanCmd.reason = eCsrScanForSsid;
+            pScanCmd->u.scanCmd.scanID = pMac->scan.nextScanID++; //let it wrap around
+            palZeroMemory(pMac->hHdd, &pScanCmd->u.scanCmd.u.scanRequest, sizeof(tCsrScanRequest));
+            pScanCmd->u.scanCmd.u.scanRequest.scanType = eSIR_ACTIVE_SCAN;
+            pScanCmd->u.scanCmd.u.scanRequest.maxChnTime = pMac->roam.configParam.nActiveMaxChnTime;
+            pScanCmd->u.scanCmd.u.scanRequest.minChnTime = pMac->roam.configParam.nActiveMinChnTime;
+            pScanCmd->u.scanCmd.u.scanRequest.BSSType = pProfile->BSSType;
+            pScanCmd->u.scanCmd.u.scanRequest.uIEFieldLen = 0;
+            if(pProfile->BSSIDs.numOfBSSIDs == 1)
+            {
+                palCopyMemory(pMac->hHdd, pScanCmd->u.scanCmd.u.scanRequest.bssid, pProfile->BSSIDs.bssid, sizeof(tCsrBssid));
+            }
+            else
+            {
+                palCopyMemory(pMac->hHdd, pScanCmd->u.scanCmd.u.scanRequest.bssid, bAddr, 6);
+            }
+            if(pProfile->ChannelInfo.numOfChannels)
+            {
+               status = palAllocateMemory(pMac->hHdd, (void **)&pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList, sizeof(*pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList) * pProfile->ChannelInfo.numOfChannels);
+               pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = 0;
+               if(HAL_STATUS_SUCCESS(status))
+                {
+                  csrRoamIsChannelValid(pMac, pProfile->ChannelInfo.ChannelList[0]);
+                  for(index = 0; index < pProfile->ChannelInfo.numOfChannels; index++)
+                  {
+                     if(csrRoamIsValidChannel(pMac, pProfile->ChannelInfo.ChannelList[index]))
+                     {
+                        pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.ChannelList[pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels] 
+                           = pProfile->ChannelInfo.ChannelList[index];
+                        pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels++;
+                     }
+                     else 
+                     {
+                         smsLog(pMac, LOGW, FL("process a channel (%d) that is invalid\n"), pProfile->ChannelInfo.ChannelList[index]);
+                     }
+
+                  }
+               }
+               else
+                {
+                    break;
+                }
+
+            }
+            else
+            {
+                pScanCmd->u.scanCmd.u.scanRequest.ChannelInfo.numOfChannels = 0;
+            }
+            if(pProfile->SSIDs.numOfSSIDs)
+            {
+                status = palAllocateMemory(pMac->hHdd, (void **)&pScanCmd->u.scanCmd.u.scanRequest.SSIDs.SSIDList, 
+                                            pProfile->SSIDs.numOfSSIDs * sizeof(tCsrSSIDInfo)); 
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    break;
+                }
+                pScanCmd->u.scanCmd.u.scanRequest.SSIDs.numOfSSIDs = 1;
+                palCopyMemory(pMac->hHdd, pScanCmd->u.scanCmd.u.scanRequest.SSIDs.SSIDList, pProfile->SSIDs.SSIDList,
+                                sizeof(tCsrSSIDInfo));
+            }
+            //Start process the command
+            status = csrQueueSmeCommand(pMac, pScanCmd, eANI_BOOLEAN_FALSE);
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+                break;
+            }
+        }while(0);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            if(pScanCmd)
+            {
+                csrReleaseCommandScan(pMac, pScanCmd);
+                //TODO:free the memory that is allocated in this function
+            }
+            csrRoamCallCallback(pMac, sessionId, NULL, roamId, eCSR_ROAM_FAILED, eCSR_ROAM_RESULT_FAILURE);
+        }
+    }//valid
+    else
+    {
+        smsLog(pMac, LOGE, FL("cannot scan because scanEnable (%d) or numSSID (%d) is invalid\n"),
+                pMac->scan.fScanEnable, pProfile->SSIDs.numOfSSIDs);
+    }
+    
+    return (status);
+}
+
+
+//Issue a scan base on the new capability infomation
+//This should only happen when the associated AP changes its capability.
+//After this scan is done, CSR reroams base on the new scan results
+eHalStatus csrScanForCapabilityChange(tpAniSirGlobal pMac, tSirSmeApNewCaps *pNewCaps)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tSmeCmd *pScanCmd = NULL;
+
+    if(pNewCaps)
+    {
+        do
+        {
+            pScanCmd = csrGetCommandBuffer(pMac);
+            if(!pScanCmd)
+            {
+                smsLog(pMac, LOGE, FL("failed to allocate command buffer\n"));
+                status = eHAL_STATUS_RESOURCES;
+                break;
+            }
+            palZeroMemory(pMac->hHdd, &pScanCmd->u.scanCmd, sizeof(tScanCmd));
+            status = eHAL_STATUS_SUCCESS;
+            pScanCmd->u.scanCmd.roamId = 0;
+            pScanCmd->command = eSmeCommandScan; 
+            pScanCmd->u.scanCmd.callback = NULL;
+            pScanCmd->u.scanCmd.pContext = NULL;
+            pScanCmd->u.scanCmd.reason = eCsrScanForCapsChange;
+            pScanCmd->u.scanCmd.scanID = pMac->scan.nextScanID++; //let it wrap around
+            status = csrQueueSmeCommand(pMac, pScanCmd, eANI_BOOLEAN_FALSE);
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                smsLog( pMac, LOGE, FL(" fail to send message status = %d\n"), status );
+                break;
+            }
+        }while(0);
+        if(!HAL_STATUS_SUCCESS(status))
+        {
+            if(pScanCmd)
+            {
+                csrReleaseCommandScan(pMac, pScanCmd);
+            }
+        }    
+    }
+
+    return (status);
+}
+
+
+
+void csrInitBGScanChannelList(tpAniSirGlobal pMac)
+{
+    tANI_U32 len = CSR_MIN(sizeof(pMac->roam.validChannelList), sizeof(pMac->scan.bgScanChannelList));
+
+    palZeroMemory(pMac->hHdd, pMac->scan.bgScanChannelList, len);
+    pMac->scan.numBGScanChannel = 0;
+
+    if(HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac, pMac->roam.validChannelList, &len)))
+    {
+        pMac->roam.numValidChannels = len;
+        pMac->scan.numBGScanChannel = (tANI_U8)CSR_MIN(len, WNI_CFG_BG_SCAN_CHANNEL_LIST_LEN);
+        palCopyMemory(pMac->hHdd, pMac->scan.bgScanChannelList, pMac->roam.validChannelList, pMac->scan.numBGScanChannel);
+        csrSetBGScanChannelList(pMac, pMac->scan.bgScanChannelList, pMac->scan.numBGScanChannel);
+    }
+}
+
+
+//This function return TRUE if background scan channel list is adjusted. 
+//this function will only shrink the background scan channel list
+tANI_BOOLEAN csrAdjustBGScanChannelList(tpAniSirGlobal pMac, tANI_U8 *pChannelList, tANI_U8 NumChannels,
+                                        tANI_U8 *pAdjustChannels, tANI_U8 *pNumAdjustChannels)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+    tANI_U8 i, j, count = *pNumAdjustChannels;
+
+    i = 0;
+    while(i < count)
+    {
+        for(j = 0; j < NumChannels; j++)
+        {
+            if(pChannelList[j] == pAdjustChannels[i])
+                break;
+        }
+        if(j == NumChannels)
+        {
+            //This channel is not in the list, remove it
+            fRet = eANI_BOOLEAN_TRUE;
+            count--;
+            if(count - i)
+            {
+                palCopyMemory(pMac->hHdd, &pAdjustChannels[i], &pAdjustChannels[i+1], count - i);
+            }
+            else
+            {
+                //already remove the last one. Done.
+                break;
+            }
+        }
+        else
+        {
+            i++;
+        }
+    }//while(i<count)
+    *pNumAdjustChannels = count;
+
+    return (fRet);
+}
+
+
+//Get the list of the base channels to scan for passively 11d info
+eHalStatus csrScanGetSupportedChannels( tpAniSirGlobal pMac )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    int n = WNI_CFG_VALID_CHANNEL_LIST_LEN;
+
+    status = vos_nv_getSupportedChannels( pMac->scan.baseChannels.channelList, &n, NULL, NULL );
+    if( HAL_STATUS_SUCCESS(status) )
+    {
+        pMac->scan.baseChannels.numChannels = (tANI_U8)n;
+    }
+    else
+    {
+        smsLog( pMac, LOGE, FL(" failed\n") );
+        pMac->scan.baseChannels.numChannels = 0;
+    }
+    
+    return ( status );
+}
+
+//This function use the input pChannelList to validate the current saved channel list
+eHalStatus csrSetBGScanChannelList( tpAniSirGlobal pMac, tANI_U8 *pAdjustChannels, tANI_U8 NumAdjustChannels)
+{
+    tANI_U32 dataLen = sizeof( tANI_U8 ) * NumAdjustChannels;
+
+    return (ccmCfgSetStr(pMac, WNI_CFG_BG_SCAN_CHANNEL_LIST, pAdjustChannels, dataLen, NULL, eANI_BOOLEAN_FALSE));
+}
+
+
+void csrSetCfgValidChannelList( tpAniSirGlobal pMac, tANI_U8 *pChannelList, tANI_U8 NumChannels )
+{
+    tANI_U32 dataLen = sizeof( tANI_U8 ) * NumChannels;
+
+
+    ccmCfgSetStr(pMac, WNI_CFG_VALID_CHANNEL_LIST, pChannelList, dataLen, NULL, eANI_BOOLEAN_FALSE);
+
+    return;
+}
+
+
+
+/*
+ * The Tx power limits are saved in the cfg for future usage.
+ */
+void csrSaveTxPowerToCfg( tpAniSirGlobal pMac, tDblLinkList *pList, tANI_U32 cfgId )
+{
+    tListElem *pEntry;
+    tANI_U32 cbLen = 0, dataLen;
+    tCsrChannelPowerInfo *pChannelSet;
+    tANI_U32 idx;
+    tSirMacChanInfo *pChannelPowerSet;
+    tANI_U8 *pBuf = NULL;
+
+    //allocate maximum space for all channels
+    dataLen = WNI_CFG_VALID_CHANNEL_LIST_LEN * sizeof(tSirMacChanInfo);
+    if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, (void **)&pBuf, dataLen)))
+    {
+        palZeroMemory(pMac->hHdd, pBuf, dataLen);
+        pChannelPowerSet = (tSirMacChanInfo *)(pBuf);
+
+        pEntry = csrLLPeekHead( pList, LL_ACCESS_LOCK );
+        // write the tuples (startChan, numChan, txPower) for each channel found in the channel power list.
+        while( pEntry )
+        {
+            pChannelSet = GET_BASE_ADDR( pEntry, tCsrChannelPowerInfo, link );
+            if ( 1 != pChannelSet->interChannelOffset )
+            {
+                // we keep the 5G channel sets internally with an interchannel offset of 4.  Expand these
+                // to the right format... (inter channel offset of 1 is the only option for the triplets
+                // that 11d advertises.
+                if ((cbLen + (pChannelSet->numChannels * sizeof(tSirMacChanInfo))) >= dataLen)
+                {
+                    // expanding this entry will overflow our allocation
+                    smsLog(pMac, LOGE,
+                           "%s: Buffer overflow, start %d, num %d, offset %d",
+                           __FUNCTION__,
+                           pChannelSet->firstChannel,
+                           pChannelSet->numChannels,
+                           pChannelSet->interChannelOffset);
+                    break;
+                }
+
+                for( idx = 0; idx < pChannelSet->numChannels; idx++ )
+                {
+                    pChannelPowerSet->firstChanNum = (tSirMacChanNum)(pChannelSet->firstChannel + ( idx * pChannelSet->interChannelOffset ));
+                    smsLog(pMac, LOG3, " Setting Channel Number %d\n", pChannelPowerSet->firstChanNum);
+                    pChannelPowerSet->numChannels  = 1;
+#ifdef WLAN_SOFTAP_FEATURE
+                    pChannelPowerSet->maxTxPower = CSR_ROAM_MIN( pChannelSet->txPower, pMac->roam.configParam.nTxPowerCap );
+#else
+                    pChannelPowerSet->maxTxPower = pChannelSet->txPower;
+#endif
+                    smsLog(pMac, LOG3, " Setting Max Transmit Power %d\n", pChannelPowerSet->maxTxPower);
+                    cbLen += sizeof( tSirMacChanInfo );
+                    pChannelPowerSet++;
+                }
+            }
+            else
+            {
+                if (cbLen >= dataLen)
+                {
+                    // this entry will overflow our allocation
+                    smsLog(pMac, LOGE,
+                           "%s: Buffer overflow, start %d, num %d, offset %d",
+                           __FUNCTION__,
+                           pChannelSet->firstChannel,
+                           pChannelSet->numChannels,
+                           pChannelSet->interChannelOffset);
+                    break;
+                }
+                pChannelPowerSet->firstChanNum = pChannelSet->firstChannel;
+                smsLog(pMac, LOG3, " Setting Channel Number %d\n", pChannelPowerSet->firstChanNum);
+                pChannelPowerSet->numChannels = pChannelSet->numChannels;
+#ifdef WLAN_SOFTAP_FEATURE
+                pChannelPowerSet->maxTxPower = CSR_ROAM_MIN( pChannelSet->txPower, pMac->roam.configParam.nTxPowerCap );
+#else
+                pChannelPowerSet->maxTxPower = pChannelSet->txPower;
+#endif
+                smsLog(pMac, LOG3, " Setting Max Transmit Power %d, nTxPower %d\n", pChannelPowerSet->maxTxPower,pMac->roam.configParam.nTxPowerCap );
+
+
+                cbLen += sizeof( tSirMacChanInfo );
+                pChannelPowerSet++;
+            }
+
+            pEntry = csrLLNext( pList, pEntry, LL_ACCESS_LOCK );
+        }
+
+        if(cbLen)
+        {
+            ccmCfgSetStr(pMac, cfgId, (tANI_U8 *)pBuf, cbLen, NULL, eANI_BOOLEAN_FALSE); 
+        }
+        palFreeMemory( pMac->hHdd, pBuf );
+    }//Allocate memory
+}
+
+
+void csrSetCfgCountryCode( tpAniSirGlobal pMac, tANI_U8 *countryCode )
+{
+    tANI_U8 cc[WNI_CFG_COUNTRY_CODE_LEN];
+    ///v_REGDOMAIN_t DomainId;
+    
+    smsLog( pMac, LOG3, "Setting Country Code in Cfg from csrSetCfgCountryCode %s\n",countryCode );
+    palCopyMemory( pMac->hHdd, cc, countryCode, WNI_CFG_COUNTRY_CODE_LEN );
+
+    // don't program the bogus country codes that we created for Korea in the MAC.  if we see
+    // the bogus country codes, program the MAC with the right country code.
+    if ( ( 'K'  == countryCode[ 0 ] && '1' == countryCode[ 1 ]  ) ||
+         ( 'K'  == countryCode[ 0 ] && '2' == countryCode[ 1 ]  ) ||
+         ( 'K'  == countryCode[ 0 ] && '3' == countryCode[ 1 ]  ) ||
+         ( 'K'  == countryCode[ 0 ] && '4' == countryCode[ 1 ]  )    )
+    {
+        // replace the alternate Korea country codes, 'K1', 'K2', .. with 'KR' for Korea
+        cc[ 1 ] = 'R';
+    }
+    ccmCfgSetStr(pMac, WNI_CFG_COUNTRY_CODE, cc, WNI_CFG_COUNTRY_CODE_LEN, NULL, eANI_BOOLEAN_FALSE);
+
+    //Need to let HALPHY know about the current domain so it can apply some 
+    //domain-specific settings (TX filter...)
+    /*if(HAL_STATUS_SUCCESS(csrGetRegulatoryDomainForCountry(pMac, cc, &DomainId)))
+    {
+        halPhySetRegDomain(pMac, DomainId);
+    }*/
+}
+
+
+
+eHalStatus csrGetCountryCode(tpAniSirGlobal pMac, tANI_U8 *pBuf, tANI_U8 *pbLen)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tANI_U32 len;
+
+    if(pBuf && pbLen && (*pbLen >= WNI_CFG_COUNTRY_CODE_LEN))
+    {
+        len = *pbLen;
+        status = ccmCfgGetStr(pMac, WNI_CFG_COUNTRY_CODE, pBuf, &len);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            *pbLen = (tANI_U8)len;
+        }
+    }
+    
+    return (status);
+}
+
+
+void csrSetCfgScanControlList( tpAniSirGlobal pMac, tANI_U8 *countryCode, tCsrChannel *pChannelList  )
+{   
+    tANI_U8 i, j;
+    tANI_BOOLEAN found=FALSE;  
+    tANI_U8 *pControlList = NULL;
+    tANI_U32 len = WNI_CFG_SCAN_CONTROL_LIST_LEN;
+
+    if(HAL_STATUS_SUCCESS(palAllocateMemory(pMac->hHdd, (void **)&pControlList, WNI_CFG_SCAN_CONTROL_LIST_LEN)))
+    {
+        palZeroMemory(pMac->hHdd, (void *)pControlList, WNI_CFG_SCAN_CONTROL_LIST_LEN);
+        if(HAL_STATUS_SUCCESS(ccmCfgGetStr(pMac, WNI_CFG_SCAN_CONTROL_LIST, pControlList, &len)))
+        {
+            for (i = 0; i < pChannelList->numChannels; i++)
+            {
+                for (j = 0; j < len; j += 2) 
+                {
+                    if (pControlList[j] == pChannelList->channelList[i]) 
+                    {
+                        found = TRUE;
+                        break;
+                    }
+                }
+                   
+                if (found)    // insert a pair(channel#, flag)
+                {
+                    if (CSR_IS_CHANNEL_5GHZ(pControlList[j]))
+                    {
+                        pControlList[j+1] = csrGetScanType(pMac, pControlList[j]);     
+                    }
+                    else  
+                    {
+                        pControlList[j+1]  = eSIR_ACTIVE_SCAN;  
+                    }
+
+                    found = FALSE;  // reset the flag
+                }
+                       
+            }            
+
+            ccmCfgSetStr(pMac, WNI_CFG_SCAN_CONTROL_LIST, pControlList, len, NULL, eANI_BOOLEAN_FALSE);
+        }//Successfully getting scan control list
+        palFreeMemory(pMac->hHdd, pControlList);
+    }//AllocateMemory
+}
+
+
+//if bgPeriod is 0, background scan is disabled. It is in millisecond units
+eHalStatus csrSetCfgBackgroundScanPeriod(tpAniSirGlobal pMac, tANI_U32 bgPeriod)
+{
+    return (ccmCfgSetInt(pMac, WNI_CFG_BACKGROUND_SCAN_PERIOD, bgPeriod, (tCcmCfgSetCallback) csrScanCcmCfgSetCallback, eANI_BOOLEAN_FALSE));
+}
+    
+
+void csrScanCcmCfgSetCallback(tHalHandle hHal, tANI_S32 result)
+{
+    tListElem *pEntry = NULL;
+    tSmeCmd *pCommand = NULL;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    
+    pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+    if ( pEntry )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        if ( eSmeCommandScan == pCommand->command )
+        {
+            eCsrScanStatus scanStatus = (CCM_IS_RESULT_SUCCESS(result)) ? eCSR_SCAN_SUCCESS : eCSR_SCAN_FAILURE;
+            csrReleaseScanCommand(pMac, pCommand, scanStatus);
+        }
+        else
+        {
+            smsLog( pMac, LOGW, "CSR: Scan Completion called but SCAN command is not ACTIVE ...\n" );
+        }
+    }   
+    smeProcessPendingQueue( pMac );
+}
+
+eHalStatus csrProcessSetBGScanParam(tpAniSirGlobal pMac, tSmeCmd *pCommand)
+{
+    eHalStatus status;
+    tCsrBGScanRequest *pScanReq = &pCommand->u.scanCmd.u.bgScanRequest;
+    tANI_U32 dataLen = sizeof( tANI_U8 ) * pScanReq->ChannelInfo.numOfChannels;
+        
+    //***setcfg for background scan channel list
+    status = ccmCfgSetInt(pMac, WNI_CFG_ACTIVE_MINIMUM_CHANNEL_TIME, pScanReq->minChnTime, NULL, eANI_BOOLEAN_FALSE);
+    status = ccmCfgSetInt(pMac, WNI_CFG_ACTIVE_MAXIMUM_CHANNEL_TIME, pScanReq->maxChnTime, NULL, eANI_BOOLEAN_FALSE);
+    //Not set the background scan interval if not connected because bd scan should not be run if not connected
+    if(!csrIsAllSessionDisconnected(pMac))
+    {
+        //If disbaling BG scan here, we need to stop aging as well
+        if(pScanReq->scanInterval == 0)
+        {
+            //Stop aging because no new result is coming in
+            csrScanStopResultAgingTimer(pMac);
+        }
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+        {
+            vos_log_scan_pkt_type *pScanLog = NULL;
+
+            WLAN_VOS_DIAG_LOG_ALLOC(pScanLog, vos_log_scan_pkt_type, LOG_WLAN_SCAN_C);
+            if(pScanLog)
+            {
+                pScanLog->eventId = WLAN_SCAN_EVENT_HO_SCAN_REQ;
+                pScanLog->minChnTime = (v_U8_t)pScanReq->minChnTime;
+                pScanLog->maxChnTime = (v_U8_t)pScanReq->maxChnTime;
+                pScanLog->timeBetweenBgScan = (v_U8_t)pScanReq->scanInterval;
+                pScanLog->numChannel = pScanReq->ChannelInfo.numOfChannels;
+                if(pScanLog->numChannel && (pScanLog->numChannel < VOS_LOG_MAX_NUM_CHANNEL))
+                {
+                    palCopyMemory(pMac->hHdd, pScanLog->channels, pScanReq->ChannelInfo.ChannelList,
+                        pScanLog->numChannel);
+                }
+                WLAN_VOS_DIAG_LOG_REPORT(pScanLog);
+            }
+        }
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+        status = ccmCfgSetInt(pMac, WNI_CFG_BACKGROUND_SCAN_PERIOD, pScanReq->scanInterval, NULL, eANI_BOOLEAN_FALSE);
+    }
+    else
+    {
+        //No need to stop aging because IDLE scan is still running
+        status = ccmCfgSetInt(pMac, WNI_CFG_BACKGROUND_SCAN_PERIOD, 0, NULL, eANI_BOOLEAN_FALSE);
+    }
+    
+    if(pScanReq->SSID.length > WNI_CFG_SSID_LEN)
+    {
+        pScanReq->SSID.length = WNI_CFG_SSID_LEN;
+    }
+    
+    status = ccmCfgSetStr(pMac, WNI_CFG_BG_SCAN_CHANNEL_LIST, pScanReq->ChannelInfo.ChannelList, dataLen, NULL, eANI_BOOLEAN_FALSE);
+    status = ccmCfgSetStr(pMac, WNI_CFG_SSID, (tANI_U8 *)pScanReq->SSID.ssId, pScanReq->SSID.length, NULL, eANI_BOOLEAN_FALSE);
+
+
+
+    return (status);
+}
+
+
+eHalStatus csrScanAbortMacScan(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirMbMsg *pMsg;
+    tANI_U16 msgLen;
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+
+#ifdef WLAN_AP_STA_CONCURRENCY
+    csrLLLock(&pMac->scan.scanCmdPendingList);
+    while( NULL != ( pEntry = csrLLRemoveHead( &pMac->scan.scanCmdPendingList, LL_ACCESS_NOLOCK) ) )
+    {
+
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        csrAbortCommand( pMac, pCommand, eANI_BOOLEAN_FALSE);
+    }
+    csrLLUnlock(&pMac->scan.scanCmdPendingList);
+#endif
+
+    pMac->scan.fDropScanCmd = eANI_BOOLEAN_TRUE;
+    csrRemoveCmdFromPendingList( pMac, &pMac->roam.roamCmdPendingList, eSmeCommandScan);
+    csrRemoveCmdFromPendingList( pMac, &pMac->sme.smeCmdPendingList, eSmeCommandScan);
+    pMac->scan.fDropScanCmd = eANI_BOOLEAN_FALSE;
+
+    //We need to abort scan only if we are scanning
+    if(NULL != (pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK)))
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        if(eSmeCommandScan == pCommand->command)
+        {
+            msgLen = (tANI_U16)(sizeof( tSirMbMsg ));
+            status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+            if(HAL_STATUS_SUCCESS(status))
+            {
+                palZeroMemory(pMac->hHdd, (void *)pMsg, msgLen);
+                pMsg->type = pal_cpu_to_be16((tANI_U16)eWNI_SME_SCAN_ABORT_IND);
+                pMsg->msgLen = pal_cpu_to_be16(msgLen);
+                status = palSendMBMessage(pMac->hHdd, pMsg);
+            }
+        }
+    }
+
+    return( status );
+}
+
+void csrRemoveCmdFromPendingList(tpAniSirGlobal pMac, tDblLinkList *pList,
+                                 eSmeCommandType commandType )
+{
+    tDblLinkList localList;
+    tListElem *pEntry;
+    tSmeCmd   *pCommand;
+    tListElem  *pEntryToRemove;
+
+    vos_mem_zero(&localList, sizeof(tDblLinkList));
+    if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &localList)))
+    {
+        smsLog(pMac, LOGE, FL(" failed to open list"));
+        return;
+    }
+
+    csrLLLock(pList);
+    if( !csrLLIsListEmpty( pList, LL_ACCESS_NOLOCK ) )
+    {
+        pEntry = csrLLPeekHead( pList, LL_ACCESS_NOLOCK);
+
+        // Have to make sure we don't loop back to the head of the list, which will
+        // happen if the entry is NOT on the list...
+        while( pEntry )
+        {
+            pEntryToRemove = pEntry;
+            pEntry = csrLLNext(pList, pEntry, LL_ACCESS_NOLOCK);
+            pCommand = GET_BASE_ADDR( pEntryToRemove, tSmeCmd, Link );
+            if ( pCommand->command == commandType )
+            {
+                // Remove that entry only
+                if(csrLLRemoveEntry( pList, pEntryToRemove, LL_ACCESS_NOLOCK))
+                {
+                    csrLLInsertTail(&localList, pEntryToRemove, LL_ACCESS_NOLOCK);
+                }
+            }
+        }
+
+
+    }
+    csrLLUnlock(pList);
+
+    while( (pEntry = csrLLRemoveHead(&localList, LL_ACCESS_NOLOCK)) )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        csrAbortCommand( pMac, pCommand, eANI_BOOLEAN_FALSE);
+    }
+    csrLLClose(&localList);
+
+}
+
+
+eHalStatus csrScanAbortMacScanNotForConnect(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    if( !csrIsScanForRoamCommandActive( pMac ) )
+    {
+        //Only abort the scan if it is not used for other roam/connect purpose
+        status = csrScanAbortMacScan(pMac);
+    }
+
+    return (status);
+}
+
+
+eHalStatus csrScanGetScanChannelInfo(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirMbMsg *pMsg;
+    tANI_U16 msgLen;
+
+    msgLen = (tANI_U16)(sizeof( tSirMbMsg ));
+    status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, pMsg, msgLen);
+        pMsg->type = eWNI_SME_GET_SCANNED_CHANNEL_REQ;
+        pMsg->msgLen = msgLen;
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+    }                             
+
+    return( status );
+}
+
+tANI_BOOLEAN csrRoamIsValidChannel( tpAniSirGlobal pMac, tANI_U8 channel )
+{
+    tANI_BOOLEAN fValid = FALSE;
+    tANI_U32 idxValidChannels;
+    tANI_U32 len = pMac->roam.numValidChannels;
+    
+    for ( idxValidChannels = 0; ( idxValidChannels < len ); idxValidChannels++ )
+    {
+       if ( channel == pMac->roam.validChannelList[ idxValidChannels ] )
+       {
+          fValid = TRUE;
+          break;
+       }
+    }
+        
+    return fValid;
+}
+
+
+
+
diff --git a/CORE/SME/src/csr/csrCmdProcess.c b/CORE/SME/src/csr/csrCmdProcess.c
new file mode 100644
index 0000000..cd99696
--- /dev/null
+++ b/CORE/SME/src/csr/csrCmdProcess.c
@@ -0,0 +1,150 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+    \file csrCmdProcess.c
+  
+    Implementation for processing various commands.
+  
+   Copyright (C) 2006 Airgo Networks, Incorporated
+ 
+   ========================================================================== */
+
+
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halInternal.h" //Check if the below include of aniGobal.h is sufficient for Volans too.
+#endif
+
+#ifdef FEATURE_WLAN_INTEGRATED_SOC
+#include "aniGlobal.h"
+#endif
+
+#include "palApi.h"
+#include "csrInsideApi.h"
+#include "smeInside.h"
+#include "smsDebug.h"
+
+
+
+
+eHalStatus csrMsgProcessor( tpAniSirGlobal pMac,  void *pMsgBuf )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirSmeRsp *pSmeRsp = (tSirSmeRsp *)pMsgBuf;
+
+    smsLog( pMac, LOG2, "  Message %d[0x%04X] received in curState %d and substate %d\n",
+                pSmeRsp->messageType, pSmeRsp->messageType, 
+                pMac->roam.curState[pSmeRsp->sessionId],
+                pMac->roam.curSubState[pSmeRsp->sessionId] );
+
+    // Process the message based on the state of the roaming states...
+    
+#if defined( ANI_RTT_DEBUG )
+    if(!pAdapter->fRttModeEnabled)
+    {
+#endif//RTT    
+        switch (pMac->roam.curState[pSmeRsp->sessionId])
+        {
+        case eCSR_ROAMING_STATE_SCANNING: 
+        {
+            //Are we in scan state
+#if defined( ANI_EMUL_ASSOC )
+            emulScanningStateMsgProcessor( pAdapter, pMBBufHdr );
+#else
+            status = csrScanningStateMsgProcessor(pMac, pMsgBuf);
+#endif    
+            break;
+        }
+        
+        case eCSR_ROAMING_STATE_JOINED: 
+        {
+            //are we in joined state
+            csrRoamJoinedStateMsgProcessor( pMac, pMsgBuf );
+            break;
+        }
+        
+        case eCSR_ROAMING_STATE_JOINING:
+        {
+            //are we in roaming states
+#if defined( ANI_EMUL_ASSOC )
+            emulRoamingStateMsgProcessor( pAdapter, pMBBufHdr );
+#endif
+            csrRoamingStateMsgProcessor( pMac, pMsgBuf );
+            break;
+        }
+
+        //For all other messages, we ignore it        
+        default:
+        {
+            /*To work-around an issue where checking for set/remove key base on connection state is no longer 
+            * workable due to failure or finding the condition meets both SAP and infra/IBSS requirement.
+            */
+            if( (eWNI_SME_SETCONTEXT_RSP == pSmeRsp->messageType) ||
+                (eWNI_SME_REMOVEKEY_RSP == pSmeRsp->messageType) )
+            {
+                smsLog(pMac, LOGW, FL(" handling msg 0x%X CSR state is %d\n"), pSmeRsp->messageType, pMac->roam.curState[pSmeRsp->sessionId]);
+                csrRoamCheckForLinkStatusChange(pMac, pSmeRsp);
+            }
+            else
+            {
+                smsLog(pMac, LOGW, "  Message 0x%04X is not handled by CSR. CSR state is %d \n", pSmeRsp->messageType, pMac->roam.curState[pSmeRsp->sessionId]);
+            }
+            break;
+        }
+        
+        }//switch
+        
+#if defined( ANI_RTT_DEBUG )
+    }
+#endif//RTT
+
+    return (status);
+}
+
+
+
+tANI_BOOLEAN csrCheckPSReady(void *pv)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pv );
+
+    VOS_ASSERT( pMac->roam.sPendingCommands >= 0 );
+    return (pMac->roam.sPendingCommands == 0);
+}
+
+
+void csrFullPowerCallback(void *pv, eHalStatus status)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pv );
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+
+    (void)status;
+    
+    while( NULL != ( pEntry = csrLLRemoveHead( &pMac->roam.roamCmdPendingList, eANI_BOOLEAN_TRUE ) ) )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        smePushCommand( pMac, pCommand, eANI_BOOLEAN_FALSE );
+    }
+
+}
+
+
diff --git a/CORE/SME/src/csr/csrInsideApi.h b/CORE/SME/src/csr/csrInsideApi.h
new file mode 100644
index 0000000..526f680
--- /dev/null
+++ b/CORE/SME/src/csr/csrInsideApi.h
@@ -0,0 +1,918 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+
+  
+    \file csrInsideApi.h
+  
+    Define interface only used by CSR.
+  
+  
+   Copyright (C) 2006 Airgo Networks, Incorporated 
+   ========================================================================== */
+#ifndef CSR_INSIDE_API_H__
+#define CSR_INSIDE_API_H__
+
+
+#include "csrSupport.h"
+#include "smeInside.h"
+#include "vos_nvitem.h"
+
+#define CSR_PASSIVE_MAX_CHANNEL_TIME   110
+#define CSR_PASSIVE_MIN_CHANNEL_TIME   60
+
+#define CSR_ACTIVE_MAX_CHANNEL_TIME    40
+#define CSR_ACTIVE_MIN_CHANNEL_TIME    20
+
+#ifdef WLAN_AP_STA_CONCURRENCY
+#define CSR_ACTIVE_MAX_CHANNEL_TIME_CONC    27
+#define CSR_ACTIVE_MIN_CHANNEL_TIME_CONC    20
+#endif
+
+#define CSR_MAX_NUM_SUPPORTED_CHANNELS 55
+
+#define CSR_MAX_BSS_SUPPORT            100
+
+//This number minus 1 means the number of times a channel is scanned before a BSS is remvoed from
+//cache scan result
+#define CSR_AGING_COUNT     3   
+//The following defines are used by palTimer
+//This is used for palTimer when request to imps fails
+#define CSR_IDLE_SCAN_WAIT_TIME     (1 * PAL_TIMER_TO_SEC_UNIT)     //1 second 
+//This is used for palTimer when imps ps is disabled
+//This number shall not be smaller than 5-6 seconds in general because a full scan may take 3-4 seconds
+#define CSR_IDLE_SCAN_NO_PS_INTERVAL     (10 * PAL_TIMER_TO_SEC_UNIT)     //10 second 
+#define CSR_IDLE_SCAN_NO_PS_INTERVAL_MIN (5 * PAL_TIMER_TO_SEC_UNIT)
+#define CSR_SCAN_GET_RESULT_INTERVAL    (5 * PAL_TIMER_TO_SEC_UNIT)     //5 seconds
+#ifdef WLAN_AP_STA_CONCURRENCY
+#define CSR_SCAN_STAAP_CONC_INTERVAL    (20 * PAL_TIMER_TO_MS_UNIT)     //20 milliseconds
+#endif
+#define CSR_MIC_ERROR_TIMEOUT  (60 * PAL_TIMER_TO_SEC_UNIT)     //60 seconds
+#define CSR_TKIP_COUNTER_MEASURE_TIMEOUT  (60 * PAL_TIMER_TO_SEC_UNIT)     //60 seconds
+#define CSR_SCAN_RESULT_AGING_INTERVAL    (5 * PAL_TIMER_TO_SEC_UNIT)     //5 seconds
+//the following defines are NOT used by palTimer
+#define CSR_SCAN_AGING_TIME_NOT_CONNECT_NO_PS 50     //50 seconds
+#define CSR_SCAN_AGING_TIME_NOT_CONNECT_W_PS 300     //300 seconds
+#define CSR_SCAN_AGING_TIME_CONNECT_NO_PS 150        //150 seconds
+#define CSR_SCAN_AGING_TIME_CONNECT_W_PS 600         //600 seconds
+#define CSR_JOIN_FAILURE_TIMEOUT_DEFAULT ( 3000 )
+#define CSR_JOIN_FAILURE_TIMEOUT_MIN   (300)  //minimal value
+//These are going against the signed RSSI (tANI_S8) so it is between -+127
+#define CSR_BEST_RSSI_VALUE         (-30)   //RSSI >= this is in CAT4
+#define CSR_DEFAULT_RSSI_DB_GAP     30 //every 30 dbm for one category
+#define CSR_BSS_CAP_VALUE_NONE  0    //not much value
+#define CSR_BSS_CAP_VALUE_HT    2    
+#define CSR_BSS_CAP_VALUE_WMM   1
+#define CSR_BSS_CAP_VALUE_UAPSD 1
+#define CSR_DEFAULT_ROAMING_TIME 10   //10 seconds
+#define CSR_ROAM_MIN(X, Y)  ((X) < (Y) ? (X) : (Y))
+#define CSR_ROAM_MAX(X, Y)  ((X) > (Y) ? (X) : (Y))
+
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+#define CSR_JOIN_MAX_RETRY_COUNT             10
+#define CSR_JOIN_RETRY_TIMEOUT_PERIOD        ( 1 *  PAL_TIMER_TO_SEC_UNIT )  // 1 second
+#endif
+
+typedef enum 
+{
+    eCsrNextScanNothing,
+    eCsrNextLostLinkScan1Success,
+    eCsrNextLostLinkScan1Failed,
+    eCsrNextLostLinkScan2Success,
+    eCsrNextLostLinkScan2Failed,
+    eCsrNextLostLinkScan3Success,
+    eCsrNexteScanForSsidSuccess,
+    eCsrNextLostLinkScan3Failed,
+    eCsrNext11dScan1Failure,
+    eCsrNext11dScan1Success,
+    eCsrNext11dScan2Failure, 
+    eCsrNext11dScan2Success,
+    eCsrNext11dScanComplete,
+    eCsrNexteScanForSsidFailure,
+    eCsrNextIdleScanComplete,
+    eCsrNextCapChangeScanComplete,
+
+}eCsrScanCompleteNextCommand;
+
+typedef enum  
+{
+    eCsrJoinSuccess, 
+    eCsrJoinFailure,
+    eCsrReassocSuccess,
+    eCsrReassocFailure, 
+    eCsrNothingToJoin, 
+    eCsrStartBssSuccess,
+    eCsrStartBssFailure,
+    eCsrSilentlyStopRoaming,
+    eCsrSilentlyStopRoamingSaveState,
+    eCsrJoinWdsFailure,
+    
+}eCsrRoamCompleteResult;
+
+typedef struct tagScanReqParam
+{
+    tANI_U8 bReturnAfter1stMatch;
+    tANI_U8 fUniqueResult;
+    tANI_U8 freshScan;
+    tANI_U8 hiddenSsid;
+    tANI_U8 reserved;
+}tScanReqParam;
+
+typedef struct tagCsrScanResult
+{
+    tListElem Link;
+    tANI_S32 AgingCount;    //This BSS is removed when it reaches 0 or less
+    tANI_U32 preferValue;   //The bigger the number, the better the BSS. This value override capValue
+    tANI_U32 capValue;  //The biggger the better. This value is in use only if we have equal preferValue
+    //This member must be the last in the structure because the end of tSirBssDescription (inside) is an
+    //    array with nonknown size at this time
+    
+    eCsrEncryptionType ucEncryptionType; //Preferred Encryption type that matched with profile.
+    eCsrEncryptionType mcEncryptionType; 
+    eCsrAuthType authType; //Preferred auth type that matched with the profile.
+
+    tCsrScanResultInfo Result;
+}tCsrScanResult;
+
+typedef struct
+{
+    tDblLinkList List;
+    tListElem *pCurEntry;
+}tScanResultList;
+
+
+
+
+#define CSR_IS_ROAM_REASON( pCmd, reason ) ( (reason) == (pCmd)->roamCmd.roamReason )
+#define CSR_IS_BETTER_PREFER_VALUE(v1, v2)   ((v1) > (v2))
+#define CSR_IS_EQUAL_PREFER_VALUE(v1, v2)   ((v1) == (v2))
+#define CSR_IS_BETTER_CAP_VALUE(v1, v2)     ((v1) > (v2))
+#define CSR_IS_ENC_TYPE_STATIC( encType ) ( ( eCSR_ENCRYPT_TYPE_NONE == (encType) ) || \
+                                            ( eCSR_ENCRYPT_TYPE_WEP40_STATICKEY == (encType) ) || \
+                                            ( eCSR_ENCRYPT_TYPE_WEP104_STATICKEY == (encType) ) )
+#define CSR_IS_WAIT_FOR_KEY( pMac, sessionId ) ( CSR_IS_ROAM_JOINED( pMac, sessionId ) && CSR_IS_ROAM_SUBSTATE_WAITFORKEY( pMac, sessionId ) )
+//WIFI has a test case for not using HT rates with TKIP as encryption
+//We may need to add WEP but for now, TKIP only.
+
+#define CSR_IS_11n_ALLOWED( encType ) (( eCSR_ENCRYPT_TYPE_TKIP != (encType) ) && \
+                                      ( eCSR_ENCRYPT_TYPE_WEP40_STATICKEY != (encType) ) && \
+                                      ( eCSR_ENCRYPT_TYPE_WEP104_STATICKEY != (encType) ) && \
+                                      ( eCSR_ENCRYPT_TYPE_WEP40 != (encType) ) && \
+                                      ( eCSR_ENCRYPT_TYPE_WEP104 != (encType) ) )
+
+eCsrRoamState csrRoamStateChange( tpAniSirGlobal pMac, eCsrRoamState NewRoamState, tANI_U8 sessionId);
+eHalStatus csrScanningStateMsgProcessor( tpAniSirGlobal pMac, void *pMsgBuf );
+void csrRoamingStateMsgProcessor( tpAniSirGlobal pMac, void *pMsgBuf );
+void csrRoamJoinedStateMsgProcessor( tpAniSirGlobal pMac, void *pMsgBuf );
+tANI_BOOLEAN csrScanComplete( tpAniSirGlobal pMac, tSirSmeScanRsp *pScanRsp );
+void csrReleaseCommandRoam(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+void csrReleaseCommandScan(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+void csrReleaseCommandWmStatusChange(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+//pIes2 can be NULL
+tANI_BOOLEAN csrIsDuplicateBssDescription( tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc1, 
+                                           tSirBssDescription *pSirBssDesc2, tDot11fBeaconIEs *pIes2 );
+eHalStatus csrRoamSaveConnectedBssDesc( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirBssDescription *pBssDesc );
+tANI_BOOLEAN csrIsNetworkTypeEqual( tSirBssDescription *pSirBssDesc1, tSirBssDescription *pSirBssDesc2 );
+eHalStatus csrScanSmeScanResponse( tpAniSirGlobal pMac, void *pMsgBuf );
+/*
+   Prepare a filter base on a profile for parsing the scan results.
+   Upon successful return, caller MUST call csrFreeScanFilter on 
+   pScanFilter when it is done with the filter.
+*/
+eHalStatus csrRoamPrepareFilterFromProfile(tpAniSirGlobal pMac, tCsrRoamProfile *pProfile, tCsrScanResultFilter *pScanFilter);
+eHalStatus csrRoamCopyProfile(tpAniSirGlobal pMac, tCsrRoamProfile *pDstProfile, tCsrRoamProfile *pSrcProfile);
+eHalStatus csrRoamStart(tpAniSirGlobal pMac);
+void csrRoamStop(tpAniSirGlobal pMac, tANI_U32 sessionId);
+void csrRoamStartMICFailureTimer(tpAniSirGlobal pMac);
+void csrRoamStopMICFailureTimer(tpAniSirGlobal pMac);
+void csrRoamStartTKIPCounterMeasureTimer(tpAniSirGlobal pMac);
+void csrRoamStopTKIPCounterMeasureTimer(tpAniSirGlobal pMac);
+
+eHalStatus csrScanOpen(tpAniSirGlobal pMac);
+eHalStatus csrScanClose(tpAniSirGlobal pMac);
+eHalStatus csrScanRequestLostLink1( tpAniSirGlobal pMac, tANI_U32 sessionId );
+eHalStatus csrScanRequestLostLink2( tpAniSirGlobal pMac, tANI_U32 sessionId );
+eHalStatus csrScanRequestLostLink3( tpAniSirGlobal pMac, tANI_U32 sessionId );
+eHalStatus csrScanHandleFailedLostlink1(tpAniSirGlobal pMac, tANI_U32 sessionId);
+eHalStatus csrScanHandleFailedLostlink2(tpAniSirGlobal pMac, tANI_U32 sessionId);
+eHalStatus csrScanHandleFailedLostlink3(tpAniSirGlobal pMac, tANI_U32 sessionId);
+tCsrScanResult *csrScanAppendBssDescription( tpAniSirGlobal pMac, 
+                                             tSirBssDescription *pSirBssDescription,
+                                             tDot11fBeaconIEs *pIes);
+void csrScanCallCallback(tpAniSirGlobal pMac, tSmeCmd *pCommand, eCsrScanStatus scanStatus);
+eHalStatus csrScanCopyRequest(tpAniSirGlobal pMac, tCsrScanRequest *pDstReq, tCsrScanRequest *pSrcReq);
+eHalStatus csrScanFreeRequest(tpAniSirGlobal pMac, tCsrScanRequest *pReq);
+eHalStatus csrScanCopyResultList(tpAniSirGlobal pMac, tScanResultHandle hIn, tScanResultHandle *phResult);
+void csrInitBGScanChannelList(tpAniSirGlobal pMac);
+eHalStatus csrScanForSSID(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, tANI_U32 roamId);
+eHalStatus csrScanForCapabilityChange(tpAniSirGlobal pMac, tSirSmeApNewCaps *pNewCaps);
+eHalStatus csrScanStartGetResultTimer(tpAniSirGlobal pMac);
+eHalStatus csrScanStopGetResultTimer(tpAniSirGlobal pMac);
+eHalStatus csrScanStartResultAgingTimer(tpAniSirGlobal pMac);
+eHalStatus csrScanStopResultAgingTimer(tpAniSirGlobal pMac);
+eHalStatus csrScanBGScanEnable(tpAniSirGlobal pMac);
+eHalStatus csrScanStartIdleScanTimer(tpAniSirGlobal pMac, tANI_U32 interval);
+eHalStatus csrScanStopIdleScanTimer(tpAniSirGlobal pMac);
+eHalStatus csrScanStartIdleScan(tpAniSirGlobal pMac);
+//Param: pTimeInterval -- Caller allocated memory in return, if failed, to specify the nxt time interval for 
+//idle scan timer interval
+//Return: Not success -- meaning it cannot start IMPS, caller needs to start a timer for idle scan
+eHalStatus csrScanTriggerIdleScan(tpAniSirGlobal pMac, tANI_U32 *pTimeInterval);
+void csrScanCancelIdleScan(tpAniSirGlobal pMac);
+void csrScanStopTimers(tpAniSirGlobal pMac);
+//This function will remove scan commands that are not related to association or IBSS
+tANI_BOOLEAN csrScanRemoveNotRoamingScanCommand(tpAniSirGlobal pMac);
+//To remove fresh scan commands from the pending queue
+tANI_BOOLEAN csrScanRemoveFreshScanCommand(tpAniSirGlobal pMac, tANI_U8 sessionId);
+eHalStatus csrScanAbortMacScan(tpAniSirGlobal pMac);
+void csrRemoveCmdFromPendingList(tpAniSirGlobal pMac, tDblLinkList *pList, 
+                                              eSmeCommandType commandType );
+eHalStatus csrScanAbortMacScanNotForConnect(tpAniSirGlobal pMac);
+eHalStatus csrScanGetScanChannelInfo(tpAniSirGlobal pMac);
+//To age out scan results base. tSmeGetScanChnRsp is a pointer returned by LIM that
+//has the information regarding scanned channels.
+//The logic is that whenever CSR add a BSS to scan result, it set the age count to
+//a value. This function deduct the age count if channelId matches the BSS' channelId
+//The BSS is remove if the count reaches 0.
+eHalStatus csrScanAgeResults(tpAniSirGlobal pMac, tSmeGetScanChnRsp *pScanChnInfo);
+
+//If fForce is TRUE we will save the new String that is learn't.
+//Typically it will be true in case of Join or user initiated ioctl
+tANI_BOOLEAN csrLearnCountryInformation( tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc,
+                                         tDot11fBeaconIEs *pIes, tANI_BOOLEAN fForce );
+void csrApplyCountryInformation( tpAniSirGlobal pMac, tANI_BOOLEAN fForce );
+void csrSetCfgScanControlList( tpAniSirGlobal pMac, tANI_U8 *countryCode, tCsrChannel *pChannelList  );
+void csrReinitScanCmd(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+void csrFreeScanResultEntry( tpAniSirGlobal pMac, tCsrScanResult *pResult );
+
+eHalStatus csrRoamCallCallback(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamInfo *pRoamInfo, 
+                               tANI_U32 roamId, eRoamCmdStatus u1, eCsrRoamResult u2);
+eHalStatus csrRoamIssueConnect(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                               tScanResultHandle hBSSList, 
+                               eCsrRoamReason reason, tANI_U32 roamId, 
+                               tANI_BOOLEAN fImediate, tANI_BOOLEAN fClearScan);
+eHalStatus csrRoamIssueReassoc(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile,
+                               tCsrRoamModifyProfileFields *pModProfileFields,
+                               eCsrRoamReason reason, tANI_U32 roamId, tANI_BOOLEAN fImediate);
+void csrRoamComplete( tpAniSirGlobal pMac, eCsrRoamCompleteResult Result, void *Context );
+eHalStatus csrRoamIssueSetContextReq( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrEncryptionType EncryptType, 
+                                     tSirBssDescription *pBssDescription,
+                                tSirMacAddr *bssId, tANI_BOOLEAN addKey,
+                                 tANI_BOOLEAN fUnicast, tAniKeyDirection aniKeyDirection, 
+                                 tANI_U8 keyId, tANI_U16 keyLength, 
+                                 tANI_U8 *pKey, tANI_U8 paeRole );
+eHalStatus csrRoamProcessDisassocDeauth( tpAniSirGlobal pMac, tSmeCmd *pCommand, 
+                                         tANI_BOOLEAN fDisassoc, tANI_BOOLEAN fMICFailure );
+eHalStatus csrRoamSaveConnectedInfomation(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                                          tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes);
+void csrRoamCheckForLinkStatusChange( tpAniSirGlobal pMac, tSirSmeRsp *pSirMsg );
+void csrRoamStatsRspProcessor(tpAniSirGlobal pMac, tSirSmeRsp *pSirMsg);
+eHalStatus csrRoamIssueStartBss( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamStartBssParams *pParam, 
+                                 tCsrRoamProfile *pProfile, tSirBssDescription *pBssDesc, tANI_U32 roamId );
+eHalStatus csrRoamIssueStopBss( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamSubState NewSubstate );
+tANI_BOOLEAN csrIsSameProfile(tpAniSirGlobal pMac, tCsrRoamConnectedProfile *pProfile1, tCsrRoamProfile *pProfile2);
+tANI_BOOLEAN csrIsRoamCommandWaiting(tpAniSirGlobal pMac);
+tANI_BOOLEAN csrIsRoamCommandWaitingForSession(tpAniSirGlobal pMac, tANI_U32 sessionId);
+tANI_BOOLEAN csrIsScanForRoamCommandActive( tpAniSirGlobal pMac );
+eRoamCmdStatus csrGetRoamCompleteStatus(tpAniSirGlobal pMac, tANI_U32 sessionId);
+//pBand can be NULL if caller doesn't need to get it
+//eCsrCfgDot11Mode csrRoamGetPhyModeBandForBss( tpAniSirGlobal pMac, eCsrPhyMode phyModeIn, tANI_U8 operationChn, eCsrBand *pBand );
+eHalStatus csrRoamIssueDisassociateCmd( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamDisconnectReason reason );
+eHalStatus csrRoamDisconnectInternal(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamDisconnectReason reason);
+//pCommand may be NULL
+void csrRoamRemoveDuplicateCommand(tpAniSirGlobal pMac, tANI_U32 sessionId, tSmeCmd *pCommand, eCsrRoamReason eRoamReason);
+                                 
+eHalStatus csrSendJoinReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirBssDescription *pBssDescription, 
+                              tCsrRoamProfile *pProfile, tDot11fBeaconIEs *pIes );
+eHalStatus csrSendMBDisassocReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirMacAddr bssId, tANI_U16 reasonCode );
+eHalStatus csrSendMBDeauthReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirMacAddr bssId, tANI_U16 reasonCode );
+eHalStatus csrSendMBDisassocCnfMsg( tpAniSirGlobal pMac, tpSirSmeDisassocInd pDisassocInd );
+eHalStatus csrSendMBDeauthCnfMsg( tpAniSirGlobal pMac, tpSirSmeDeauthInd pDeauthInd );
+eHalStatus csrSendAssocCnfMsg( tpAniSirGlobal pMac, tpSirSmeAssocInd pAssocInd, eHalStatus status );
+#ifdef WLAN_SOFTAP_FEATURE
+eHalStatus csrSendAssocIndToUpperLayerCnfMsg( tpAniSirGlobal pMac, tpSirSmeAssocInd pAssocInd, eHalStatus Halstatus, tANI_U8 sessionId );
+#endif
+eHalStatus csrSendMBStartBssReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamBssType bssType, 
+                                    tCsrRoamStartBssParams *pParam, tSirBssDescription *pBssDesc );
+eHalStatus csrSendMBStopBssReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId );
+eHalStatus csrSendSmeReassocReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, tSirBssDescription *pBssDescription, 
+                                    tDot11fBeaconIEs *pIes, tCsrRoamProfile *pProfile );
+
+tANI_BOOLEAN csrIsMacAddressEqual( tpAniSirGlobal pMac, tCsrBssid *pMacAddr1, tCsrBssid *pMacAddr2 );
+//Caller should put the BSS' ssid to fiedl bssSsid when comparing SSID for a BSS.
+tANI_BOOLEAN csrIsSsidMatch( tpAniSirGlobal pMac, tANI_U8 *ssid1, tANI_U8 ssid1Len, tANI_U8 *bssSsid, 
+                            tANI_U8 bssSsidLen, tANI_BOOLEAN fSsidRequired );
+tANI_BOOLEAN csrIsPhyModeMatch( tpAniSirGlobal pMac, tANI_U32 phyMode,
+                                    tSirBssDescription *pSirBssDesc, tCsrRoamProfile *pProfile,
+                                    eCsrCfgDot11Mode *pReturnCfgDot11Mode,
+                                    tDot11fBeaconIEs *pIes);
+tANI_BOOLEAN csrRoamIsChannelValid( tpAniSirGlobal pMac, tANI_U8 channel );
+
+//pNumChan is a caller allocated space with the sizeof pChannels
+eHalStatus csrGetCfgValidChannels(tpAniSirGlobal pMac, tANI_U8 *pChannels, tANI_U32 *pNumChan);
+void csrRoamCcmCfgSetCallback(tHalHandle hHal, tANI_S32 result);
+void csrScanCcmCfgSetCallback(tHalHandle hHal, tANI_S32 result);
+
+//To free the last roaming profile
+void csrFreeRoamProfile(tpAniSirGlobal pMac, tANI_U32 sessionId);
+void csrFreeConnectBssDesc(tpAniSirGlobal pMac, tANI_U32 sessionId);
+eHalStatus csrMoveBssToHeadFromBSSID(tpAniSirGlobal pMac, tCsrBssid *bssid, tScanResultHandle hScanResult);
+tANI_BOOLEAN csrCheckPSReady(void *pv);
+void csrFullPowerCallback(void *pv, eHalStatus status);
+//to free memory allocated inside the profile structure
+void csrReleaseProfile(tpAniSirGlobal pMac, tCsrRoamProfile *pProfile);
+//To free memory allocated inside scanFilter
+void csrFreeScanFilter(tpAniSirGlobal pMac, tCsrScanResultFilter *pScanFilter);
+#ifdef WLAN_SOFTAP_FEATURE
+eCsrCfgDot11Mode csrGetCfgDot11ModeFromCsrPhyMode(tCsrRoamProfile *pProfile, eCsrPhyMode phyMode, tANI_BOOLEAN fProprietary);
+#else
+eCsrCfgDot11Mode csrGetCfgDot11ModeFromCsrPhyMode(eCsrPhyMode phyMode, tANI_BOOLEAN fProprietary);
+#endif
+tANI_U32 csrTranslateToWNICfgDot11Mode(tpAniSirGlobal pMac, eCsrCfgDot11Mode csrDot11Mode);
+void csrSaveChannelPowerForBand( tpAniSirGlobal pMac, tANI_BOOLEAN fPopulate5GBand );
+void csrApplyChannelPowerCountryInfo( tpAniSirGlobal pMac, tCsrChannel *pChannelList, tANI_U8 *countryCode);
+void csrAssignRssiForCategory(tpAniSirGlobal pMac, tANI_U8 catOffset);
+tANI_BOOLEAN csrIsMacAddressZero( tpAniSirGlobal pMac, tCsrBssid *pMacAddr );
+tANI_BOOLEAN csrIsMacAddressBroadcast( tpAniSirGlobal pMac, tCsrBssid *pMacAddr );
+eHalStatus csrRoamRemoveConnectedBssFromScanCache(tpAniSirGlobal pMac, tCsrRoamConnectedProfile *pConnProfile);
+eHalStatus csrRoamStartRoaming(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamingReason roamingReason);
+//return a boolean to indicate whether roaming completed or continue.
+tANI_BOOLEAN csrRoamCompleteRoaming(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                    tANI_BOOLEAN fForce, eCsrRoamResult roamResult);
+void csrRoamCompletion(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamInfo *pRoamInfo, tSmeCmd *pCommand, eCsrRoamResult roamResult, tANI_BOOLEAN fSuccess);
+void csrRoamCancelRoaming(tpAniSirGlobal pMac, tANI_U32 sessionId);
+void csrResetCountryInformation( tpAniSirGlobal pMac, tANI_BOOLEAN fForce );
+void csrResetPMKIDCandidateList( tpAniSirGlobal pMac, tANI_U32 sessionId );
+#ifdef FEATURE_WLAN_WAPI
+void csrResetBKIDCandidateList( tpAniSirGlobal pMac, tANI_U32 sessionId );
+#endif /* FEATURE_WLAN_WAPI */
+void csrSaveToChannelPower2G_5G( tpAniSirGlobal pMac, tANI_U32 tableSize, tSirMacChanInfo *channelTable );
+//Get the list of the base channels to scan for passively 11d info
+eHalStatus csrScanGetSupportedChannels( tpAniSirGlobal pMac );
+//To check whether a country code matches the one in the IE
+//Only check the first two characters, ignoring in/outdoor
+//pCountry -- caller allocated buffer contain the country code that is checking against
+//the one in pIes. It can be NULL.
+//caller must provide pIes, it cannot be NULL
+//This function always return TRUE if 11d support is not turned on.
+//pIes cannot be NULL
+tANI_BOOLEAN csrMatchCountryCode( tpAniSirGlobal pMac, tANI_U8 *pCountry, tDot11fBeaconIEs *pIes );
+eHalStatus csrRoamSetKey( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamSetKey *pSetKey, tANI_U32 roamId );
+eHalStatus csrRoamOpenSession( tpAniSirGlobal pMac, csrRoamCompleteCallback callback, void *pContext,
+                          tANI_U8 *pSelfMacAddr, tANI_U8 *pbSessionId );
+//fSync: TRUE means cleanupneeds to handle synchronously.
+eHalStatus csrRoamCloseSession( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                tANI_BOOLEAN fSync, 
+                                csrRoamSessionCloseCallback callback,
+                                void *pContext );
+void csrCleanupSession(tpAniSirGlobal pMac, tANI_U32 sessionId);
+eHalStatus csrRoamGetSessionIdFromBSSID( tpAniSirGlobal pMac, tCsrBssid *bssid, tANI_U32 *pSessionId );
+eCsrCfgDot11Mode csrFindBestPhyMode( tpAniSirGlobal pMac, tANI_U32 phyMode );
+
+/* ---------------------------------------------------------------------------
+    \fn csrScanEnable
+    \brief Enable the scanning feature of CSR. It must be called before any scan request can be performed.
+    \param tHalHandle - HAL context handle
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanEnable(tpAniSirGlobal);
+
+/* ---------------------------------------------------------------------------
+    \fn csrScanDisable
+    \brief Disableing the scanning feature of CSR. After this function return success, no scan is performed until 
+a successfull to csrScanEnable
+    \param tHalHandle - HAL context handle
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanDisable(tpAniSirGlobal);
+/* ---------------------------------------------------------------------------
+    \fn csrScanRequest
+    \brief Request a 11d or full scan.
+    \param pScanRequestID - pointer to an object to get back the request ID
+    \param callback - a callback function that scan calls upon finish, will not be called if csrScanRequest returns error
+    \param pContext - a pointer passed in for the callback
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanRequest(tpAniSirGlobal, tANI_U16, tCsrScanRequest *,
+                   tANI_U32 *pScanRequestID, csrScanCompleteCallback callback,
+                   void *pContext);
+
+/* ---------------------------------------------------------------------------
+    \fn csrScanAbort
+    \brief If a scan request is abort, the scan complete callback will be called first before csrScanAbort returns.
+    \param pScanRequestID - The request ID returned from csrScanRequest
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanAbort(tpAniSirGlobal, tANI_U32 scanRequestID);
+
+eHalStatus csrScanSetBGScanparams(tpAniSirGlobal, tCsrBGScanRequest *);
+eHalStatus csrScanBGScanAbort(tpAniSirGlobal);
+
+/* ---------------------------------------------------------------------------
+    \fn csrScanGetResult
+    \brief Return scan results.
+    \param pFilter - If pFilter is NULL, all cached results are returned
+    \param phResult - an object for the result.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanGetResult(tpAniSirGlobal, tCsrScanResultFilter *pFilter, tScanResultHandle *phResult);
+
+/* ---------------------------------------------------------------------------
+    \fn csrScanFlushResult
+    \brief Clear scan results.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanFlushResult(tpAniSirGlobal);
+
+/* ---------------------------------------------------------------------------
+    \fn csrScanBGScanGetParam
+    \brief Returns the current background scan settings.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanBGScanGetParam(tpAniSirGlobal, tCsrBGScanRequest *);
+
+/* ---------------------------------------------------------------------------
+    \fn csrScanResultGetFirst
+    \brief Returns the first element of scan result.
+    \param hScanResult - returned from csrScanGetResult
+    \return tCsrScanResultInfo * - NULL if no result     
+  -------------------------------------------------------------------------------*/
+tCsrScanResultInfo *csrScanResultGetFirst(tpAniSirGlobal, tScanResultHandle hScanResult);
+/* ---------------------------------------------------------------------------
+    \fn csrScanResultGetNext
+    \brief Returns the next element of scan result. It can be called without calling csrScanResultGetFirst first
+    \param hScanResult - returned from csrScanGetResult
+    \return Null if no result or reach the end     
+  -------------------------------------------------------------------------------*/
+tCsrScanResultInfo *csrScanResultGetNext(tpAniSirGlobal, tScanResultHandle hScanResult);
+
+/* ---------------------------------------------------------------------------
+    \fn csrGetCountryCode
+    \brief this function is to get the country code current being used
+    \param pBuf - Caller allocated buffer with at least 3 bytes, upon success return, this has the country code
+    \param pbLen - Caller allocated, as input, it indicates the length of pBuf. Upon success return,
+    this contains the length of the data in pBuf
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrGetCountryCode(tpAniSirGlobal pMac, tANI_U8 *pBuf, tANI_U8 *pbLen);
+
+/* ---------------------------------------------------------------------------
+    \fn csrSetCountryCode
+    \brief this function is to set the country code so channel/power setting matches the countrycode and
+    the domain it belongs to.
+    \param pCountry - Caller allocated buffer with at least 3 bytes specifying the country code
+    \param pfRestartNeeded - pointer to a caller allocated space. Upon successful return, it indicates whether 
+    a restart is needed to apply the change
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrSetCountryCode(tpAniSirGlobal pMac, tANI_U8 *pCountry, tANI_BOOLEAN *pfRestartNeeded);
+
+/* ---------------------------------------------------------------------------
+    \fn csrResetCountryCodeInformation
+    \brief this function is to reset the country code current being used back to EEPROM default
+    this includes channel list and power setting.
+    \param pfRestartNeeded - pointer to a caller allocated space. Upon successful return, it indicates whether 
+    a restart is needed to apply the change
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrResetCountryCodeInformation(tpAniSirGlobal pMac, tANI_BOOLEAN *pfRestartNeeded);
+
+/* ---------------------------------------------------------------------------
+    \fn csrGetSupportedCountryCode
+    \brief this function is to get a list of the country code current being supported
+    \param pBuf - Caller allocated buffer with at least 3 bytes, upon success return, 
+    this has the country code list. 3 bytes for each country code. This may be NULL if
+    caller wants to know the needed bytes.
+    \param pbLen - Caller allocated, as input, it indicates the length of pBuf. Upon success return,
+    this contains the length of the data in pBuf
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrGetSupportedCountryCode(tpAniSirGlobal pMac, tANI_U8 *pBuf, tANI_U32 *pbLen);
+
+/* ---------------------------------------------------------------------------
+    \fn csrSetRegulatoryDomain
+    \brief this function is to set the current regulatory domain.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    CSR.
+    \param domainId - indicate the domain (defined in the driver) needs to set to.  
+    See eRegDomainId for definition
+    \param pfRestartNeeded - pointer to a caller allocated space. Upon successful return, it indicates whether 
+    a restart is needed to apply the change
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrSetRegulatoryDomain(tpAniSirGlobal pMac, v_REGDOMAIN_t domainId, tANI_BOOLEAN *pfRestartNeeded);
+
+/* ---------------------------------------------------------------------------
+    \fn csrGetCurrentRegulatoryDomain
+    \brief this function is to get the current regulatory domain.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    CSR.
+    \return eRegDomainId     
+  -------------------------------------------------------------------------------*/
+v_REGDOMAIN_t csrGetCurrentRegulatoryDomain(tpAniSirGlobal pMac);
+
+/* ---------------------------------------------------------------------------
+    \fn csrGetRegulatoryDomainForCountry
+    \brief this function is to get the regulatory domain for a country.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    CSR.
+    \param pCountry - Caller allocated buffer with at least 3 bytes specifying the country code
+    \param pDomainId - Caller allocated buffer to get the return domain ID upon success return. Can be NULL.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrGetRegulatoryDomainForCountry(tpAniSirGlobal pMac, tANI_U8 *pCountry, v_REGDOMAIN_t *pDomainId);
+
+
+tANI_BOOLEAN csrSave11dCountryString( tpAniSirGlobal pMac, tANI_U8 *pCountryCode, tANI_BOOLEAN fForce );
+
+//some support functions
+tANI_BOOLEAN csrIs11dSupported(tpAniSirGlobal pMac);
+tANI_BOOLEAN csrIs11hSupported(tpAniSirGlobal pMac);
+tANI_BOOLEAN csrIs11eSupported(tpAniSirGlobal pMac);
+tANI_BOOLEAN csrIsWmmSupported(tpAniSirGlobal pMac);
+tANI_BOOLEAN csrIsMCCSupported(tpAniSirGlobal pMac);
+
+//Upper layer to get the list of the base channels to scan for passively 11d info from csr
+eHalStatus csrScanGetBaseChannels( tpAniSirGlobal pMac, tCsrChannelInfo * pChannelInfo );
+//Return SUCCESS is the command is queued, failed
+eHalStatus csrQueueSmeCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fHighPriority );
+tSmeCmd *csrGetCommandBuffer( tpAniSirGlobal pMac );
+void csrReleaseCommand(tpAniSirGlobal pMac, tSmeCmd *pCommand);
+#ifdef FEATURE_WLAN_WAPI
+tANI_BOOLEAN csrIsProfileWapi( tCsrRoamProfile *pProfile );
+#endif /* FEATURE_WLAN_WAPI */
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+
+//Security
+#define WLAN_SECURITY_EVENT_SET_PTK_REQ     1
+#define WLAN_SECURITY_EVENT_SET_PTK_RSP     2
+#define WLAN_SECURITY_EVENT_SET_GTK_REQ     3
+#define WLAN_SECURITY_EVENT_SET_GTK_RSP     4
+#define WLAN_SECURITY_EVENT_REMOVE_KEY_REQ  5
+#define WLAN_SECURITY_EVENT_REMOVE_KEY_RSP  6
+#define WLAN_SECURITY_EVENT_PMKID_CANDIDATE_FOUND  7
+#define WLAN_SECURITY_EVENT_PMKID_UPDATE    8
+#define WLAN_SECURITY_EVENT_MIC_ERROR       9   
+
+#define AUTH_OPEN       0
+#define AUTH_SHARED     1
+#define AUTH_WPA_EAP    2
+#define AUTH_WPA_PSK    3
+#define AUTH_WPA2_EAP   4
+#define AUTH_WPA2_PSK   5
+#ifdef FEATURE_WLAN_WAPI
+#define AUTH_WAPI_CERT  6
+#define AUTH_WAPI_PSK   7
+#endif /* FEATURE_WLAN_WAPI */
+
+#define ENC_MODE_OPEN   0
+#define ENC_MODE_WEP40  1
+#define ENC_MODE_WEP104 2
+#define ENC_MODE_TKIP   3
+#define ENC_MODE_AES    4
+#ifdef FEATURE_WLAN_WAPI
+#define ENC_MODE_SMS4   5 //WAPI
+#endif /* FEATURE_WLAN_WAPI */
+
+#define NO_MATCH    0
+#define MATCH       1
+
+#define WLAN_SECURITY_STATUS_SUCCESS        0
+#define WLAN_SECURITY_STATUS_FAILURE        1
+
+//Scan
+#define WLAN_SCAN_EVENT_ACTIVE_SCAN_REQ     1
+#define WLAN_SCAN_EVENT_ACTIVE_SCAN_RSP     2
+#define WLAN_SCAN_EVENT_PASSIVE_SCAN_REQ    3
+#define WLAN_SCAN_EVENT_PASSIVE_SCAN_RSP    4
+#define WLAN_SCAN_EVENT_HO_SCAN_REQ         5
+#define WLAN_SCAN_EVENT_HO_SCAN_RSP         6
+
+#define WLAN_SCAN_STATUS_SUCCESS        0
+#define WLAN_SCAN_STATUS_FAILURE        1
+#define WLAN_SCAN_STATUS_ABORT          2
+
+//Ibss
+#define WLAN_IBSS_EVENT_START_IBSS_REQ      0
+#define WLAN_IBSS_EVENT_START_IBSS_RSP      1
+#define WLAN_IBSS_EVENT_JOIN_IBSS_REQ       2
+#define WLAN_IBSS_EVENT_JOIN_IBSS_RSP       3
+#define WLAN_IBSS_EVENT_COALESCING          4
+#define WLAN_IBSS_EVENT_PEER_JOIN           5
+#define WLAN_IBSS_EVENT_PEER_LEAVE          6
+#define WLAN_IBSS_EVENT_STOP_REQ            7
+#define WLAN_IBSS_EVENT_STOP_RSP            8
+
+#define AUTO_PICK       0
+#define SPECIFIED       1
+
+#define WLAN_IBSS_STATUS_SUCCESS        0
+#define WLAN_IBSS_STATUS_FAILURE        1
+
+//11d
+#define WLAN_80211D_EVENT_COUNTRY_SET   0
+#define WLAN_80211D_EVENT_RESET         1
+
+#define WLAN_80211D_DISABLED         0
+#define WLAN_80211D_SUPPORT_MULTI_DOMAIN     1
+#define WLAN_80211D_NOT_SUPPORT_MULTI_DOMAIN     2
+
+int diagAuthTypeFromCSRType(eCsrAuthType authType);
+int diagEncTypeFromCSRType(eCsrEncryptionType encType);
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT_CSR
+/* ---------------------------------------------------------------------------
+    \fn csrScanResultPurge
+    \brief remove all items(tCsrScanResult) in the list and free memory for each item
+    \param hScanResult - returned from csrScanGetResult. hScanResult is considered gone by 
+    calling this function and even before this function reutrns.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanResultPurge(tpAniSirGlobal pMac, tScanResultHandle hScanResult);
+
+
+///////////////////////////////////////////Common Scan ends
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamConnect
+    \brief To inititiate an association
+    \param pProfile - can be NULL to join to any open ones
+    \param hBssListIn - a list of BSS descriptor to roam to. It is returned from csrScanGetResult
+    \param pRoamId - to get back the request ID
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamConnect(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                          tScanResultHandle hBssListIn, tANI_U32 *pRoamId);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamReassoc
+    \brief To inititiate a re-association
+    \param pProfile - can be NULL to join the currently connected AP. In that 
+    case modProfileFields should carry the modified field(s) which could trigger
+    reassoc  
+    \param modProfileFields - fields which are part of tCsrRoamConnectedProfile 
+    that might need modification dynamically once STA is up & running and this 
+    could trigger a reassoc
+    \param pRoamId - to get back the request ID
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamReassoc(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile,
+                          tCsrRoamModifyProfileFields modProfileFields,
+                          tANI_U32 *pRoamId);
+
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamReconnect
+    \brief To disconnect and reconnect with the same profile
+    \return eHalStatus. It returns fail if currently not connected     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamReconnect(tpAniSirGlobal pMac, tANI_U32 sessionId);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamSetPMKIDCache
+    \brief return the PMKID candidate list
+    \param pPMKIDCache - caller allocated buffer point to an array of tPmkidCacheInfo
+    \param numItems - a variable that has the number of tPmkidCacheInfo allocated
+    when retruning, this is either the number needed or number of items put into pPMKIDCache
+    \return eHalStatus - when fail, it usually means the buffer allocated is not big enough and pNumItems
+    has the number of tPmkidCacheInfo.
+    \Note: pNumItems is a number of tPmkidCacheInfo, not sizeof(tPmkidCacheInfo) * something
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamSetPMKIDCache( tpAniSirGlobal pMac, tANI_U32 sessionId, tPmkidCacheInfo *pPMKIDCache, tANI_U32 numItems );
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetWpaRsnReqIE
+    \brief return the WPA or RSN IE CSR passes to PE to JOIN request or START_BSS request
+    \param pLen - caller allocated memory that has the length of pBuf as input. Upon returned, *pLen has the 
+    needed or IE length in pBuf.
+    \param pBuf - Caller allocated memory that contain the IE field, if any, upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not big enough
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamGetWpaRsnReqIE(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pLen, tANI_U8 *pBuf);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetWpaRsnRspIE
+    \brief return the WPA or RSN IE from the beacon or probe rsp if connected
+    \param pLen - caller allocated memory that has the length of pBuf as input. Upon returned, *pLen has the 
+    needed or IE length in pBuf.
+    \param pBuf - Caller allocated memory that contain the IE field, if any, upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not big enough
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamGetWpaRsnRspIE(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 *pLen, tANI_U8 *pBuf);
+
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetNumPMKIDCache
+    \brief return number of PMKID cache entries
+    \return tANI_U32 - the number of PMKID cache entries
+  -------------------------------------------------------------------------------*/
+tANI_U32 csrRoamGetNumPMKIDCache(tpAniSirGlobal pMac, tANI_U32 sessionId);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetPMKIDCache
+    \brief return PMKID cache from CSR
+    \param pNum - caller allocated memory that has the space of the number of pBuf tPmkidCacheInfo as input. Upon returned, *pNum has the 
+    needed or actually number in tPmkidCacheInfo.
+    \param pPmkidCache - Caller allocated memory that contains PMKID cache, if any, upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not big enough
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamGetPMKIDCache(tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                tANI_U32 *pNum, tPmkidCacheInfo *pPmkidCache);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetConnectProfile
+    \brief To return the current connect profile. Caller must call csrRoamFreeConnectProfile
+           after it is done and before reuse for another csrRoamGetConnectProfile call.
+    \param pProfile - pointer to a caller allocated structure tCsrRoamConnectedProfile
+    \return eHalStatus. Failure if not connected     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamGetConnectProfile(tpAniSirGlobal pMac, tANI_U32 sessionId, 
+                                    tCsrRoamConnectedProfile *pProfile);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetConnectState
+    \brief To return the current connect state of Roaming
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamGetConnectState(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrConnectState *pState);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamFreeConnectProfile
+    \brief To free and reinitialize the profile return previous by csrRoamGetConnectProfile.
+    \param pProfile - pointer to a caller allocated structure tCsrRoamConnectedProfile
+    \return eHalStatus.      
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamFreeConnectProfile(tpAniSirGlobal pMac, tCsrRoamConnectedProfile *pProfile);
+
+/* ---------------------------------------------------------------------------
+    \fn csrInitChannelList
+    \brief HDD calls this function to set the WNI_CFG_VALID_CHANNEL_LIST base on the band/mode settings.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    CSR.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrInitChannelList( tHalHandle hHal );
+
+/* ---------------------------------------------------------------------------
+    \fn csrChangeConfigParams
+    \brief The CSR API exposed for HDD to provide config params to CSR during 
+    SMEs stop -> start sequence.
+    If HDD changed the domain that will cause a reset. This function will 
+    provide the new set of 11d information for the new domain. Currrently this
+    API provides info regarding 11d only at reset but we can extend this for
+    other params (PMC, QoS) which needs to be initialized again at reset.
+    \param 
+    hHal - Handle to the HAL. The HAL handle is returned by the HAL after it is 
+           opened (by calling halOpen).
+    pUpdateConfigParam - a pointer to a structure (tCsrUpdateConfigParam) that 
+                currently provides 11d related information like Country code, 
+                Regulatory domain, valid channel list, Tx power per channel, a 
+                list with active/passive scan allowed per valid channel. 
+
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus csrChangeConfigParams(tpAniSirGlobal pMac, 
+                                 tCsrUpdateConfigParam *pUpdateConfigParam);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamConnectToLastProfile
+    \brief To disconnect and reconnect with the same profile
+    \return eHalStatus. It returns fail if currently connected     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamConnectToLastProfile(tpAniSirGlobal pMac, tANI_U32 sessionId);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamDisconnect
+    \brief To disconnect from a network
+    \param reason -- To indicate the reason for disconnecting. Currently, only eCSR_DISCONNECT_REASON_MIC_ERROR is meanful.
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrRoamDisconnect(tpAniSirGlobal pMac, tANI_U32 sessionId, eCsrRoamDisconnectReason reason);
+
+/* ---------------------------------------------------------------------------
+    \fn csrScanGetPMKIDCandidateList
+    \brief return the PMKID candidate list
+    \param pPmkidList - caller allocated buffer point to an array of tPmkidCandidateInfo
+    \param pNumItems - pointer to a variable that has the number of tPmkidCandidateInfo allocated
+    when retruning, this is either the number needed or number of items put into pPmkidList
+    \return eHalStatus - when fail, it usually means the buffer allocated is not big enough and pNumItems
+    has the number of tPmkidCandidateInfo.
+    \Note: pNumItems is a number of tPmkidCandidateInfo, not sizeof(tPmkidCandidateInfo) * something
+  -------------------------------------------------------------------------------*/
+eHalStatus csrScanGetPMKIDCandidateList(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                        tPmkidCandidateInfo *pPmkidList, tANI_U32 *pNumItems );
+
+//This function is used to stop a BSS. It is similar of csrRoamIssueDisconnect but this function
+//doesn't have any logic other than blindly trying to stop BSS
+eHalStatus csrRoamIssueStopBssCmd( tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_BOOLEAN fHighPriority );
+
+void csrCallRoamingCompletionCallback(tpAniSirGlobal pMac, tCsrRoamSession *pSession, 
+                                      tCsrRoamInfo *pRoamInfo, tANI_U32 roamId, eCsrRoamResult roamResult);
+
+#ifdef WLAN_SOFTAP_FEATURE
+/* ---------------------------------------------------------------------------
+    \fn csrRoamIssueDisassociateStaCmd
+    \brief csr function that HDD calls to disassociate a associated station
+    \param sessionId    - session Id for Soft AP
+    \param pPeerMacAddr - MAC of associated station to delete
+    \param reason - reason code, be one of the tSirMacReasonCodes
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus csrRoamIssueDisassociateStaCmd( tpAniSirGlobal pMac, 
+                                           tANI_U32 sessionId, 
+                                           tANI_U8 *pPeerMacAddr,
+                                           tANI_U32 reason);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamIssueDeauthSta
+    \brief csr function that HDD calls to delete a associated station
+    \param sessionId    - session Id for Soft AP
+    \param pPeerMacAddr - MAC of associated station to delete
+    \param reason - reason code, be one of the tSirMacReasonCodes
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus csrRoamIssueDeauthStaCmd( tpAniSirGlobal pMac, 
+                                     tANI_U32 sessionId, 
+                                     tANI_U8 *pPeerMacAddr,
+                                     tANI_U32 reason);
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamIssueTkipCounterMeasures
+    \brief csr function that HDD calls to start and stop tkip countermeasures
+    \param sessionId - session Id for Soft AP
+    \param bEnable   - Flag to start/stop countermeasures
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus csrRoamIssueTkipCounterMeasures( tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_BOOLEAN bEnable);
+
+eHalStatus csrSendMBTkipCounterMeasuresReqMsg( tpAniSirGlobal pMac, tANI_U32 sessinId, tANI_BOOLEAN bEnable, tSirMacAddr bssId );
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetAssociatedStas
+    \brief csr function that HDD calls to get list of associated stations based on module ID
+    \param sessionId - session Id for Soft AP
+    \param modId - module ID - PE/HAL/TL
+    \param pUsrContext - Opaque HDD context
+    \param pfnSapEventCallback - Sap event callback in HDD
+    \param pAssocStasBuf - Caller allocated memory to be filled with associatd stations info
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus csrRoamGetAssociatedStas( tpAniSirGlobal pMac, tANI_U32 sessionId, VOS_MODULE_ID modId,
+                                     void *pUsrContext, void *pfnSapEventCallback, tANI_U8 *pAssocStasBuf );
+
+eHalStatus csrSendMBGetAssociatedStasReqMsg( tpAniSirGlobal pMac, tANI_U32 sessionId, VOS_MODULE_ID modId,  tSirMacAddr bssId,
+                                             void *pUsrContext, void *pfnSapEventCallback, tANI_U8 *pAssocStasBuf );
+
+/* ---------------------------------------------------------------------------
+    \fn csrRoamGetWpsSessionOverlap
+    \brief csr function that HDD calls to get WPS PBC session overlap information
+    \param sessionId - session Id for Soft AP
+    \param pUsrContext - Opaque HDD context
+    \param pfnSapEventCallback - Sap event callback in HDD
+    \param pRemoveMac - pointer to MAC address of session to be removed
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus csrRoamGetWpsSessionOverlap( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                             void *pUsrContext, void *pfnSapEventCallback,v_MACADDR_t pRemoveMac );
+                                        
+eHalStatus csrSendMBGetWPSPBCSessions( tpAniSirGlobal pMac, tANI_U32 sessionId,
+                            tSirMacAddr bssId, void *pUsrContext, void *pfnSapEventCallback,v_MACADDR_t pRemoveMac);
+                            
+#endif
+#ifdef FEATURE_WLAN_BTAMP_UT_RF
+eHalStatus csrRoamStartJoinRetryTimer(tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U32 interval);
+eHalStatus csrRoamStopJoinRetryTimer(tpAniSirGlobal pMac, tANI_U32 sessionId);
+#endif
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/* ---------------------------------------------------------------------------
+    \fn csrRoamFTPreAuthRspProcessor
+    \brief csr function that handles pre auth response from LIM 
+  ---------------------------------------------------------------------------*/
+void csrRoamFTPreAuthRspProcessor( tHalHandle hHal, tpSirFTPreAuthRsp pFTPreAuthRsp );
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+void csrCcxSendAdjacentApRepMsg(tpAniSirGlobal pMac, tCsrRoamSession *pSession);
+#endif
+#endif
+
diff --git a/CORE/SME/src/csr/csrLinkList.c b/CORE/SME/src/csr/csrLinkList.c
new file mode 100644
index 0000000..a2b08e8
--- /dev/null
+++ b/CORE/SME/src/csr/csrLinkList.c
@@ -0,0 +1,648 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+    \file csrLinkList.c
+  
+    Implementation for the Common link list interfaces.
+  
+  
+    Copyright (C) 2006 Airgo Networks, Incorporated 
+   ========================================================================== */
+
+#include "palApi.h"
+#include "csrLinkList.h"
+#include "vos_lock.h"
+#include "vos_memory.h"
+#include "vos_trace.h"
+
+ANI_INLINE_FUNCTION void csrListInit(tListElem *pList)
+{
+    pList->last = pList->next = pList;
+}
+
+
+ANI_INLINE_FUNCTION void csrListRemoveEntry(tListElem *pEntry)
+{
+    tListElem *pLast;
+    tListElem *pNext;
+    
+    pLast = pEntry->last;
+    pNext = pEntry->next;
+    pLast->next = pNext;
+    pNext->last = pLast;
+}
+
+
+ANI_INLINE_FUNCTION tListElem * csrListRemoveHead(tListElem *pHead)
+{
+    tListElem *pEntry;
+    tListElem *pNext;
+    
+    pEntry = pHead->next;
+    pNext = pEntry->next;
+    pHead->next = pNext;
+    pNext->last = pHead;
+    
+    return (pEntry);
+}
+
+
+
+ANI_INLINE_FUNCTION tListElem * csrListRemoveTail(tListElem *pHead)
+{
+    tListElem *pEntry;
+    tListElem *pLast;
+    
+    pEntry = pHead->last;
+    pLast = pEntry->last;
+    pHead->last = pLast;
+    pLast->next = pHead;
+    
+    return (pEntry);
+}
+
+
+ANI_INLINE_FUNCTION void csrListInsertTail(tListElem *pHead, tListElem *pEntry)
+{
+    tListElem *pLast;
+    
+    pLast = pHead->last;
+    pEntry->last = pLast;
+    pEntry->next = pHead;
+    pLast->next = pEntry;
+    pHead->last = pEntry;
+}
+
+
+ANI_INLINE_FUNCTION void csrListInsertHead(tListElem *pHead, tListElem *pEntry)
+{
+    tListElem *pNext;
+    
+    pNext = pHead->next;
+    pEntry->next = pNext;
+    pEntry->last = pHead;
+    pNext->last = pEntry;
+    pHead->next = pEntry;
+}
+
+
+//Insert pNewEntry before pEntry
+void csrListInsertEntry(tListElem *pEntry, tListElem *pNewEntry)
+{
+    tListElem *pLast;
+    if( !pEntry) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pEntry is Null", __FUNCTION__);
+        return; 
+    }
+       
+    pLast = pEntry->last;
+    pLast->next = pNewEntry;
+    pEntry->last = pNewEntry;
+    pNewEntry->next = pEntry;
+    pNewEntry->last = pLast;
+}
+
+tANI_U32 csrLLCount( tDblLinkList *pList ) 
+{
+    tANI_U32 c = 0; 
+    
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return c; 
+    }
+
+    if ( pList && ( LIST_FLAG_OPEN == pList->Flag ) ) 
+    {
+        c = pList->Count;
+    }
+
+    return( c ); 
+}
+
+
+void csrLLLock( tDblLinkList *pList ) 
+{
+    
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag )
+    {
+        vos_lock_acquire(&pList->Lock);
+    }
+}
+
+
+void csrLLUnlock( tDblLinkList *pList )
+{
+    
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        vos_lock_release(&pList->Lock);
+    }
+}
+
+
+tANI_BOOLEAN csrLLIsListEmpty( tDblLinkList *pList, tANI_BOOLEAN fInterlocked )
+{
+    tANI_BOOLEAN fEmpty = eANI_BOOLEAN_TRUE;
+
+    
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return fEmpty ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if(fInterlocked)
+        {
+            csrLLLock(pList);
+        }
+
+        fEmpty = csrIsListEmpty( &pList->ListHead );
+         
+        if(fInterlocked)
+        {
+            csrLLUnlock(pList);
+        }
+    }
+    return( fEmpty );
+}
+
+
+
+tANI_BOOLEAN csrLLFindEntry( tDblLinkList *pList, tListElem *pEntryToFind )
+{
+    tANI_BOOLEAN fFound = eANI_BOOLEAN_FALSE;
+    tListElem *pEntry;
+
+    
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return fFound ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        pEntry = csrLLPeekHead( pList, LL_ACCESS_NOLOCK);
+
+        // Have to make sure we don't loop back to the head of the list, which will
+        // happen if the entry is NOT on the list...
+    
+        while( pEntry && ( pEntry != &pList->ListHead ) ) 
+        {
+            if ( pEntry == pEntryToFind ) 
+            {
+                fFound = eANI_BOOLEAN_TRUE;
+                break;
+            }
+            pEntry = pEntry->next;
+        }
+        
+    }
+    return( fFound );
+}
+
+
+eHalStatus csrLLOpen( tHddHandle hHdd, tDblLinkList *pList )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    VOS_STATUS vosStatus;
+    
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return eHAL_STATUS_FAILURE ; 
+    }
+    
+    if ( LIST_FLAG_OPEN != pList->Flag ) 
+    {
+        pList->Count = 0;
+
+        vosStatus = vos_lock_init(&pList->Lock);
+
+        if(VOS_IS_STATUS_SUCCESS(vosStatus))
+        {
+            csrListInit( &pList->ListHead );
+            pList->Flag = LIST_FLAG_OPEN;
+            pList->hHdd = hHdd;
+        }
+        else
+        {
+           status = eHAL_STATUS_FAILURE;
+        }
+    }
+    return (status);
+}
+
+void csrLLClose( tDblLinkList *pList )
+{
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        // Make sure the list is empty...
+        csrLLPurge( pList, LL_ACCESS_LOCK );
+        vos_lock_destroy( &pList->Lock );
+        pList->Flag = LIST_FLAG_CLOSE;
+    }
+}
+
+void csrLLInsertTail( tDblLinkList *pList, tListElem *pEntry, tANI_BOOLEAN fInterlocked )
+{    
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if(fInterlocked)
+        {  
+            csrLLLock(pList);
+        }
+        csrListInsertTail( &pList->ListHead, pEntry );
+        pList->Count++;
+        if(fInterlocked)
+        {  
+            csrLLUnlock(pList);
+        }
+    }
+}
+
+
+
+void csrLLInsertHead( tDblLinkList *pList, tListElem *pEntry, tANI_BOOLEAN fInterlocked )
+{
+    
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if(fInterlocked)
+        {
+            csrLLLock(pList);
+        }
+        csrListInsertHead( &pList->ListHead, pEntry );
+        pList->Count++;
+        if(fInterlocked)
+        {
+            csrLLUnlock(pList);
+        }
+    }
+}
+
+
+void csrLLInsertEntry( tDblLinkList *pList, tListElem *pEntry, tListElem *pNewEntry, tANI_BOOLEAN fInterlocked )
+{    
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if(fInterlocked)
+        {
+            csrLLLock(pList);
+        }
+        csrListInsertEntry( pEntry, pNewEntry );
+        pList->Count++;
+        if(fInterlocked)
+        {
+            csrLLUnlock(pList);
+        }
+    }
+}
+
+
+
+tListElem *csrLLRemoveTail( tDblLinkList *pList, tANI_BOOLEAN fInterlocked )
+{
+    tListElem *pEntry = NULL;
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return pEntry ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if ( fInterlocked ) 
+        {
+            csrLLLock( pList );
+        }
+
+        if ( !csrIsListEmpty(&pList->ListHead) ) 
+        {
+
+            pEntry = csrListRemoveTail( &pList->ListHead );
+            pList->Count--;
+        }
+        if ( fInterlocked ) 
+        {
+            csrLLUnlock( pList );
+        }
+    }
+
+    return( pEntry );
+}
+
+
+tListElem *csrLLPeekTail( tDblLinkList *pList, tANI_BOOLEAN fInterlocked )
+{
+    tListElem *pEntry = NULL;
+
+    
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return pEntry ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if ( fInterlocked ) 
+        {  
+            csrLLLock( pList );
+        }
+
+        if ( !csrIsListEmpty(&pList->ListHead) ) 
+        {
+            pEntry = pList->ListHead.last; 
+        }
+        if ( fInterlocked ) 
+        {
+            csrLLUnlock( pList );
+        }
+    }
+
+    return( pEntry );
+}
+
+
+
+tListElem *csrLLRemoveHead( tDblLinkList *pList, tANI_BOOLEAN fInterlocked )
+{
+    tListElem *pEntry = NULL;
+    
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return pEntry ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if ( fInterlocked ) 
+        {  
+            csrLLLock( pList );
+        }
+
+        if ( !csrIsListEmpty(&pList->ListHead) ) 
+        {
+            pEntry = csrListRemoveHead( &pList->ListHead );
+            pList->Count--;
+        }
+
+        if ( fInterlocked ) 
+        {
+            csrLLUnlock( pList );
+        }
+    }
+
+    return( pEntry );
+}
+
+
+tListElem *csrLLPeekHead( tDblLinkList *pList, tANI_BOOLEAN fInterlocked )
+{
+    tListElem *pEntry = NULL;
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return pEntry ; 
+    }
+     
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if ( fInterlocked ) 
+        {  
+            csrLLLock( pList );
+        }
+
+        if ( !csrIsListEmpty(&pList->ListHead) ) 
+        {
+            pEntry = pList->ListHead.next; 
+        }
+        if ( fInterlocked ) 
+        {
+            csrLLUnlock( pList );
+        }
+    }
+
+    return( pEntry );
+}
+
+
+
+void csrLLPurge( tDblLinkList *pList, tANI_BOOLEAN fInterlocked )
+{
+    tListElem *pEntry;
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if ( fInterlocked ) 
+        {  
+            csrLLLock( pList );
+        }
+        while( (pEntry = csrLLRemoveHead( pList, LL_ACCESS_NOLOCK )) ) 
+        {
+            // just remove everything from the list until 
+            // nothing left on the list.
+        }
+        if ( fInterlocked ) 
+        {  
+            csrLLUnlock( pList );
+        }
+    }
+}
+
+
+tANI_BOOLEAN csrLLRemoveEntry( tDblLinkList *pList, tListElem *pEntryToRemove, tANI_BOOLEAN fInterlocked )
+{
+    tANI_BOOLEAN fFound = eANI_BOOLEAN_FALSE;
+    tListElem *pEntry;
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return fFound; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if ( fInterlocked ) 
+        {
+            csrLLLock( pList );
+        }
+
+        pEntry = csrLLPeekHead( pList, LL_ACCESS_NOLOCK );
+
+        // Have to make sure we don't loop back to the head of the list, which will
+        // happen if the entry is NOT on the list...
+        while( pEntry && ( pEntry != &pList->ListHead ) ) 
+        {
+            if ( pEntry == pEntryToRemove )
+            {
+                csrListRemoveEntry( pEntry );
+                pList->Count--;
+
+                fFound = eANI_BOOLEAN_TRUE;
+                break;
+            }
+
+            pEntry = pEntry->next; 
+        }
+        if ( fInterlocked ) 
+        {
+            csrLLUnlock( pList );
+        }
+    }
+
+    return( fFound );
+}
+
+
+
+tListElem *csrLLNext( tDblLinkList *pList, tListElem *pEntry, tANI_BOOLEAN fInterlocked )
+{
+    tListElem *pNextEntry = NULL;
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return pNextEntry ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if ( fInterlocked ) 
+        {
+            csrLLLock( pList );
+        }
+
+        if ( !csrIsListEmpty(&pList->ListHead) && csrLLFindEntry( pList, pEntry ) ) 
+        {
+            pNextEntry = pEntry->next;
+            //Make sure we don't walk past the head
+            if ( pNextEntry == &pList->ListHead ) 
+            {
+                pNextEntry = NULL;
+            }
+        }
+
+        if ( fInterlocked ) 
+        {
+            csrLLUnlock( pList );
+        }
+    }
+
+    return( pNextEntry );
+}
+
+
+tListElem *csrLLPrevious( tDblLinkList *pList, tListElem *pEntry, tANI_BOOLEAN fInterlocked )
+{
+    tListElem *pNextEntry = NULL;
+
+    if( !pList) 
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL,"%s: Error!! pList is Null", __FUNCTION__);
+        return pNextEntry ; 
+    }
+
+    if ( LIST_FLAG_OPEN == pList->Flag ) 
+    {
+        if ( fInterlocked ) 
+        {
+            csrLLLock( pList );
+        }
+
+        if ( !csrIsListEmpty(&pList->ListHead) && csrLLFindEntry( pList, pEntry ) ) 
+        {
+            pNextEntry = pEntry->last; 
+            //Make sure we don't walk past the head
+            if ( pNextEntry == &pList->ListHead ) 
+            {
+                pNextEntry = NULL;
+            }
+        }  
+
+        if ( fInterlocked ) 
+        {
+            csrLLUnlock( pList );
+        }
+    }
+
+    return( pNextEntry );
+}
+
+
+
+
diff --git a/CORE/SME/src/csr/csrLogDump.c b/CORE/SME/src/csr/csrLogDump.c
new file mode 100644
index 0000000..26fb3eb
--- /dev/null
+++ b/CORE/SME/src/csr/csrLogDump.c
@@ -0,0 +1,112 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/*============================================================================
+Copyright (c) 2007 QUALCOMM Incorporated.
+All Rights Reserved.
+Qualcomm Confidential and Proprietary
+csrLogDump.c
+Implements the dump commands specific to the csr module. 
+============================================================================*/
+#include "aniGlobal.h"
+#include "csrApi.h"
+#include "btcApi.h"
+#include "logDump.h"
+#include "smsDebug.h"
+#include "smeInside.h"
+#include "csrInsideApi.h"
+#if defined(ANI_LOGDUMP)
+static char *
+dump_csr( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p )
+{
+    static tCsrRoamProfile x;
+    static tSirMacSSid ssid;   //To be allocated for array of SSIDs
+    static tANI_U8 sessionId = 0; // Defined for fixed session ID
+    palZeroMemory(pMac->hHdd, (void*)&x, sizeof(x)); 
+    x.SSIDs.numOfSSIDs=1 ;
+    x.SSIDs.SSIDList[0].SSID = ssid ;
+    ssid.length=6 ;
+    palCopyMemory(pMac->hHdd, ssid.ssId, "AniNet", 6);
+    if(HAL_STATUS_SUCCESS(sme_AcquireGlobalLock( &pMac->sme )))
+    {
+        (void)csrRoamConnect(pMac, sessionId, &x, NULL, NULL);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    return p;
+}
+static char *dump_btcSetEvent( tpAniSirGlobal pMac, tANI_U32 arg1, 
+                               tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p )
+{
+    tSmeBtEvent btEvent;
+    if( arg1 < BT_EVENT_TYPE_MAX )
+    {
+        smsLog(pMac, LOGE, FL(" signal BT event (%d) handle (%d) 3rd param(%d)\n"), arg1, arg2, arg3);
+        vos_mem_zero(&btEvent, sizeof(tSmeBtEvent));
+        btEvent.btEventType = arg1;
+        switch( arg1 )
+        {
+        case BT_EVENT_SYNC_CONNECTION_COMPLETE:
+        case BT_EVENT_SYNC_CONNECTION_UPDATED:
+            btEvent.uEventParam.btSyncConnection.connectionHandle = (v_U16_t)arg2;
+            btEvent.uEventParam.btSyncConnection.status = (v_U8_t)arg3;
+            break;
+        case BT_EVENT_DISCONNECTION_COMPLETE:
+            btEvent.uEventParam.btDisconnect.connectionHandle = (v_U16_t)arg2;
+            break;
+        case BT_EVENT_CREATE_ACL_CONNECTION:
+        case BT_EVENT_ACL_CONNECTION_COMPLETE:
+            btEvent.uEventParam.btAclConnection.connectionHandle = (v_U16_t)arg2;
+            btEvent.uEventParam.btAclConnection.status = (v_U8_t)arg3;
+            break;
+        case BT_EVENT_MODE_CHANGED:
+            btEvent.uEventParam.btAclModeChange.connectionHandle = (v_U16_t)arg2;
+            break;
+        default:
+            break;
+        }
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+        if(HAL_STATUS_SUCCESS(sme_AcquireGlobalLock( &pMac->sme )))
+        {
+            btcSignalBTEvent(pMac, &btEvent);
+            sme_ReleaseGlobalLock( &pMac->sme );
+        }
+#endif
+    }
+    else
+    {
+        smsLog(pMac, LOGE, FL(" invalid event (%d)\n"), arg1);
+    }
+    return p;
+}
+
+static tDumpFuncEntry csrMenuDumpTable[] = {
+    {0,     "CSR (850-860)",                                    NULL},
+    {851,   "CSR: CSR testing connection to AniNet",            dump_csr},
+    {852,   "BTC: Fake BT events (event, handle)",              dump_btcSetEvent},
+};
+
+void csrDumpInit(tHalHandle hHal)
+{
+    logDumpRegisterTable( (tpAniSirGlobal)hHal, &csrMenuDumpTable[0], 
+                          sizeof(csrMenuDumpTable)/sizeof(csrMenuDumpTable[0]) );
+}
+
+#endif //#if defined(ANI_LOGDUMP)
diff --git a/CORE/SME/src/csr/csrNeighborRoam.c b/CORE/SME/src/csr/csrNeighborRoam.c
new file mode 100644
index 0000000..9ae1066
--- /dev/null
+++ b/CORE/SME/src/csr/csrNeighborRoam.c
@@ -0,0 +1,2842 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/*
+ * */
+/** ------------------------------------------------------------------------- * 
+    ------------------------------------------------------------------------- *  
+
+  
+    \file csrNeighborRoam.c
+  
+    Implementation for the simple roaming algorithm for 802.11r Fast transitions and Legacy roaming for Android platform.
+  
+    Copyright (C) 2010 Qualcomm, Incorporated
+  
+ 
+   ========================================================================== */
+
+/*===========================================================================
+
+                      EDIT HISTORY FOR FILE
+
+
+  This section contains comments describing changes made to the module.
+  Notice that changes are listed in reverse chronological order.
+
+
+
+  when           who                 what, where, why
+----------       ---                --------------------------------------------------------
+08/01/10          Murali             Created
+
+===========================================================================*/
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+#include "wlan_qct_wda.h"
+#include "palApi.h"
+#include "csrInsideApi.h"
+#include "smsDebug.h"
+#include "logDump.h"
+#include "smeQosInternal.h"
+#include "wlan_qct_tl.h"
+#include "smeInside.h"
+#include "vos_diag_core_event.h"
+#include "vos_diag_core_log.h"
+#include "csrApi.h"
+#include "wlan_qct_tl.h"
+#include "sme_Api.h"
+#include "csrNeighborRoam.h"
+#ifdef FEATURE_WLAN_CCX
+#include "csrCcx.h"
+#endif
+
+#define WLAN_FEATURE_NEIGHBOR_ROAMING_DEBUG 1
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING_DEBUG
+#define NEIGHBOR_ROAM_DEBUG smsLog
+#else
+#define NEIGHBOR_ROAM_DEBUG(x...)
+#endif
+
+VOS_STATUS csrNeighborRoamNeighborLookupUPCallback (v_PVOID_t pAdapter, v_U8_t rssiNotification,
+                                                                               v_PVOID_t pUserCtxt);
+VOS_STATUS csrNeighborRoamNeighborLookupDOWNCallback (v_PVOID_t pAdapter, v_U8_t rssiNotification,
+                                                                               v_PVOID_t pUserCtxt);
+void csrNeighborRoamRRMNeighborReportResult(void *context, VOS_STATUS vosStatus);
+eHalStatus csrRoamCopyConnectedProfile(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pDstProfile );
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+static eHalStatus csrNeighborRoamIssuePreauthReq(tpAniSirGlobal pMac);
+VOS_STATUS csrNeighborRoamIssueNeighborRptRequest(tpAniSirGlobal pMac);
+#endif
+
+/* State Transition macro */
+#define CSR_NEIGHBOR_ROAM_STATE_TRANSITION(newState)\
+{\
+    pMac->roam.neighborRoamInfo.prevNeighborRoamState = pMac->roam.neighborRoamInfo.neighborRoamState;\
+    pMac->roam.neighborRoamInfo.neighborRoamState = newState;\
+    smsLog(pMac, LOGE, FL("Neighbor Roam Transition from state %d ==> %d"), pMac->roam.neighborRoamInfo.prevNeighborRoamState, newState);\
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamFreeNeighborRoamBSSNode
+
+    \brief  This function frees all the internal pointers CSR NeighborRoam BSS Info 
+            and also frees the node itself
+
+    \param  pMac - The handle returned by macOpen.
+            neighborRoamBSSNode - Neighbor Roam BSS Node to be freed
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamFreeNeighborRoamBSSNode(tpAniSirGlobal pMac, tpCsrNeighborRoamBSSInfo neighborRoamBSSNode)
+{
+    if (neighborRoamBSSNode)
+    {
+        if (neighborRoamBSSNode->pBssDescription)
+        {
+            vos_mem_free(neighborRoamBSSNode->pBssDescription);
+            neighborRoamBSSNode->pBssDescription = NULL;
+        }
+        vos_mem_free(neighborRoamBSSNode);
+        neighborRoamBSSNode = NULL;
+    }
+
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamRemoveRoamableAPListEntry
+
+    \brief  This function removes a given entry from the given list
+
+    \param  pMac - The handle returned by macOpen.
+            pList - The list from which the entry should be removed
+            pNeighborEntry - Neighbor Roam BSS Node to be removed
+
+    \return TRUE if successfully removed, else FALSE
+
+---------------------------------------------------------------------------*/
+tANI_BOOLEAN csrNeighborRoamRemoveRoamableAPListEntry(tpAniSirGlobal pMac, 
+                                                tDblLinkList *pList, tpCsrNeighborRoamBSSInfo pNeighborEntry)
+{
+    if(pList)
+    {
+        return csrLLRemoveEntry(pList, &pNeighborEntry->List, LL_ACCESS_LOCK);
+    }
+
+    smsLog(pMac, LOGE, FL("Removing neighbor BSS node from list failed. Current count = %d\n"), csrLLCount(pList));
+
+    return eANI_BOOLEAN_FALSE;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamGetRoamableAPListNextEntry
+
+    \brief  Gets the entry next to passed entry. If NULL is passed, return the entry in the head of the list
+
+    \param  pMac - The handle returned by macOpen.
+            pList - The list from which the entry should be returned
+            pNeighborEntry - Neighbor Roam BSS Node whose next entry should be returned
+
+    \return Neighbor Roam BSS Node to be returned
+
+---------------------------------------------------------------------------*/
+tpCsrNeighborRoamBSSInfo csrNeighborRoamGetRoamableAPListNextEntry(tpAniSirGlobal pMac, 
+                                        tDblLinkList *pList, tpCsrNeighborRoamBSSInfo pNeighborEntry)
+{
+    tListElem *pEntry = NULL;
+    tpCsrNeighborRoamBSSInfo pResult = NULL;
+    
+    if(pList)
+    {
+        if(NULL == pNeighborEntry)
+        {
+            pEntry = csrLLPeekHead(pList, LL_ACCESS_LOCK);
+        }
+        else
+        {
+            pEntry = csrLLNext(pList, &pNeighborEntry->List, LL_ACCESS_LOCK);
+        }
+        if(pEntry)
+        {
+            pResult = GET_BASE_ADDR(pEntry, tCsrNeighborRoamBSSInfo, List);
+        }
+    }
+    
+    return pResult;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamFreeRoamableBSSList
+
+    \brief   Empties and frees all the nodes in the roamable AP list 
+
+    \param  pMac - The handle returned by macOpen.
+            pList - Neighbor Roam BSS List to be emptied
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamFreeRoamableBSSList(tpAniSirGlobal pMac, tDblLinkList *pList)
+{
+    tpCsrNeighborRoamBSSInfo pResult = NULL;
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Emptying the BSS list. Current count = %d\n"), csrLLCount(pList));
+
+    /* Pick up the head, remove and free the node till the list becomes empty */
+    while ((pResult = csrNeighborRoamGetRoamableAPListNextEntry(pMac, pList, NULL)) != NULL)
+    {
+        csrNeighborRoamRemoveRoamableAPListEntry(pMac, pList, pResult);
+        csrNeighborRoamFreeNeighborRoamBSSNode(pMac, pResult);
+    }
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamReassocIndCallback
+
+    \brief Reassoc callback invoked by TL on crossing the registered re-assoc threshold.
+           Directly triggere HO in case of non-11r association
+           In case of 11R association, triggers a pre-auth eventually followed by actual HO
+
+    \param  pAdapter - VOS Context
+            trafficStatus - UP/DOWN indication from TL
+            pUserCtxt - Parameter for callback registered during callback registration. Should be pMac
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+VOS_STATUS csrNeighborRoamReassocIndCallback(v_PVOID_t pAdapter, 
+                               v_U8_t trafficStatus, 
+                               v_PVOID_t pUserCtxt)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pUserCtxt );
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;   
+ 
+    smsLog(pMac, LOG1, FL("Reassoc indication callback called"));
+
+
+    //smsLog(pMac, LOGE, FL("Reassoc indication callback called at state %d"), pNeighborRoamInfo->neighborRoamState);
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event reassoc callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1));
+
+
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
+                                                        WLANTL_HO_THRESHOLD_DOWN, 
+                                                        csrNeighborRoamReassocIndCallback,
+                                                        VOS_MODULE_ID_SME);
+                        
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+        //err msg
+        smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
+    }
+    
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering UP event neighbor lookup callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborLookupThreshold * (-1));
+    /* Deregister reassoc callback. Ignore return status */
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborLookupThreshold * (-1),
+                                                        WLANTL_HO_THRESHOLD_DOWN, 
+                                                        csrNeighborRoamNeighborLookupUPCallback,
+                                                        VOS_MODULE_ID_SME);
+                        
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+        //err msg
+        smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
+    }
+
+    /* We dont need to run this timer any more. */
+    palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    if (pNeighborRoamInfo->is11rAssoc)
+    {
+        if (eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN == pNeighborRoamInfo->neighborRoamState)
+        {
+            csrNeighborRoamIssuePreauthReq(pMac);
+        }
+        else
+        {
+            smsLog(pMac, LOGE, FL("11R Reassoc indication received in unexpected state %d"), pNeighborRoamInfo->neighborRoamState);
+            VOS_ASSERT(0);
+        }
+    }
+    else
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+    if (pNeighborRoamInfo->isCCXAssoc)
+    {
+        if (eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN == pNeighborRoamInfo->neighborRoamState)
+        {
+            csrNeighborRoamIssuePreauthReq(pMac);
+        }
+        else
+        {
+            smsLog(pMac, LOGE, FL("CCX Reassoc indication received in unexpected state %d"), pNeighborRoamInfo->neighborRoamState);
+            VOS_ASSERT(0);
+        }
+    }
+    else
+#endif
+    {
+        if (eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN == pNeighborRoamInfo->neighborRoamState)
+        {
+            csrNeighborRoamRequestHandoff(pMac);
+        }
+        else
+        {
+            smsLog(pMac, LOGE, FL("Non-11R Reassoc indication received in unexpected state %d"), pNeighborRoamInfo->neighborRoamState);
+            VOS_ASSERT(0);
+        }
+    }
+    return VOS_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamResetConnectedStateControlInfo
+
+    \brief  This function will reset the neighbor roam control info data structures. 
+            This function should be invoked whenever we move to CONNECTED state from 
+            any state other than INIT state
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamResetConnectedStateControlInfo(tpAniSirGlobal pMac)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    /* Do not reset the currentNeighborLookup Threshold here. The threshold and multiplier will be set before calling this API */
+    if ((pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived == FALSE) &&
+        (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels))
+    {
+        pNeighborRoamInfo->roamChannelInfo.currentChanIndex = CSR_NEIGHBOR_ROAM_INVALID_CHANNEL_INDEX;
+        pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels = 0;
+
+        if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
+            vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
+    
+        pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+        pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_FALSE;
+    }
+    else 
+    {
+        pNeighborRoamInfo->roamChannelInfo.currentChanIndex = 0;
+        pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_TRUE;
+    }
+
+    csrNeighborRoamFreeRoamableBSSList(pMac, &pNeighborRoamInfo->roamableAPList);
+
+    palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+
+    /* Abort any ongoing BG scans */
+    if (eANI_BOOLEAN_TRUE == pNeighborRoamInfo->scanRspPending)
+        csrScanAbortMacScan(pMac);
+
+    pNeighborRoamInfo->scanRspPending = eANI_BOOLEAN_FALSE;
+    
+    /* We dont need to run this timer any more. */
+    palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    /* Do not free up the preauth done list here */
+    pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;
+    pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_FALSE;
+    pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries = 0;
+    pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport = 0;
+    pNeighborRoamInfo->FTRoamInfo.preauthRspPending = 0;
+    vos_mem_zero(pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo, sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
+    palTimerStop(pMac->hHdd, pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimer);
+#endif
+
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamResetInitStateControlInfo
+
+    \brief  This function will reset the neighbor roam control info data structures. 
+            This function should be invoked whenever we move to CONNECTED state from 
+            INIT state
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamResetInitStateControlInfo(tpAniSirGlobal pMac)
+{
+    tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    VOS_STATUS                    vosStatus = VOS_STATUS_SUCCESS;
+
+    csrNeighborRoamResetConnectedStateControlInfo(pMac);
+
+    /* In addition to the above resets, we should clear off the curAPBssId/Session ID in the timers */
+    pNeighborRoamInfo->csrSessionId            =   CSR_SESSION_ID_INVALID;
+    vos_mem_set(pNeighborRoamInfo->currAPbssid, sizeof(tCsrBssid), 0);
+    pNeighborRoamInfo->neighborScanTimerInfo.pMac = pMac;
+    pNeighborRoamInfo->neighborScanTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+    pNeighborRoamInfo->is11rAssoc = eANI_BOOLEAN_FALSE;
+    pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimerInfo.pMac = pMac;
+    pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+    csrNeighborRoamPurgePreauthFailedList(pMac);
+#endif
+#ifdef FEATURE_WLAN_CCX
+    pNeighborRoamInfo->isCCXAssoc = eANI_BOOLEAN_FALSE;
+    pNeighborRoamInfo->isVOAdmitted = eANI_BOOLEAN_FALSE;
+    pNeighborRoamInfo->MinQBssLoadRequired = 0;
+#endif
+    
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event reassoc callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1));
+    /* Deregister reassoc callback. Ignore return status */
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
+                                                        WLANTL_HO_THRESHOLD_DOWN, 
+                                                        csrNeighborRoamReassocIndCallback,
+                                                        VOS_MODULE_ID_SME);
+                        
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+        //err msg
+        smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
+    }
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event neighborLookup callback with TL. RSSI = %d"), pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
+    /* Deregister neighbor lookup callback. Ignore return status */
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
+                                                        WLANTL_HO_THRESHOLD_DOWN, 
+                                                        csrNeighborRoamNeighborLookupDOWNCallback,
+                                                        VOS_MODULE_ID_SME);
+                        
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+        //err msg
+        smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamNeighborLookupDOWNCallback with TL: Status = %d\n"), vosStatus);
+    }
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering UP event neighbor lookup callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborLookupThreshold * (-1));
+    /* Deregister reassoc callback. Ignore return status */
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborLookupThreshold * (-1),
+                                                        WLANTL_HO_THRESHOLD_UP, 
+                                                        csrNeighborRoamNeighborLookupUPCallback,
+                                                        VOS_MODULE_ID_SME);
+                        
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+        //err msg
+        smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
+    }
+    
+    /* Reset currentNeighborLookupThreshold only after deregistering DOWN event from TL */
+    pNeighborRoamInfo->currentLookupIncrementMultiplier = 0;
+    pNeighborRoamInfo->currentNeighborLookupThreshold = pNeighborRoamInfo->cfgParams.neighborLookupThreshold;
+
+    return;
+}
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamBssIdScanFilter
+
+    \brief  This API is used to prepare a filter to obtain scan results when 
+            we complete the scan in the REPORT_SCAN state after receiving a 
+            valid neighbor report from AP. This filter includes BSSIDs received from 
+            the neighbor report from the AP in addition to the other filter parameters 
+            created from connected profile
+
+    \param  pMac - The handle returned by macOpen.
+            pScanFilter - Scan filter to be filled and returned
+
+    \return eHAL_STATUS_SUCCESS on succesful filter creation, corresponding error 
+            code otherwise
+
+---------------------------------------------------------------------------*/
+static eHalStatus csrNeighborRoamBssIdScanFilter(tpAniSirGlobal pMac, tCsrScanResultFilter *pScanFilter)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tANI_U8 i = 0;
+
+    VOS_ASSERT(pScanFilter != NULL);
+    vos_mem_zero(pScanFilter, sizeof(tCsrScanResultFilter));
+
+    pScanFilter->BSSIDs.numOfBSSIDs = pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport;
+    pScanFilter->BSSIDs.bssid = vos_mem_malloc(sizeof(tSirMacAddr) * pScanFilter->BSSIDs.numOfBSSIDs);
+    if (NULL == pScanFilter->BSSIDs.bssid)
+    {
+        smsLog(pMac, LOGE, FL("Scan Filter BSSID mem alloc failed"));
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+
+    vos_mem_zero(pScanFilter->BSSIDs.bssid, sizeof(tSirMacAddr) * pScanFilter->BSSIDs.numOfBSSIDs);
+
+    /* Populate the BSSID from Neighbor BSS info received from neighbor report */
+    for (i = 0; i < pScanFilter->BSSIDs.numOfBSSIDs; i++)
+    {
+        vos_mem_copy(&pScanFilter->BSSIDs.bssid[i], 
+                pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo[i].neighborBssId, sizeof(tSirMacAddr));
+    }
+
+    /* Fill other general scan filter params */
+    return csrNeighborRoamPrepareScanProfileFilter(pMac, pScanFilter);
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamPurgePreauthFailList
+
+    \brief  This function empties the preauth fail list
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamPurgePreauthFailList(tpAniSirGlobal pMac)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Purging the preauth fail list"));
+    while (pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress)
+    {
+        vos_mem_zero(pNeighborRoamInfo->FTRoamInfo.preAuthFailList.macAddress[pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress-1],
+                                    sizeof(tSirMacAddr));
+        pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress--;
+    }
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamAddBssIdToPreauthFailList
+
+    \brief  This function adds the given BSSID to the Preauth fail list
+
+    \param  pMac - The handle returned by macOpen.
+            bssId - BSSID to be added to the preauth fail list
+
+    \return eHAL_STATUS_SUCCESS on success, eHAL_STATUS_FAILURE otherwise
+
+---------------------------------------------------------------------------*/
+eHalStatus csrNeighborRoamAddBssIdToPreauthFailList(tpAniSirGlobal pMac, tSirMacAddr bssId)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL(" Added BSSID %02x:%02x:%02x:%02x:%02x:%02x to Preauth failed list\n"), 
+                        bssId[0], bssId[1], bssId[2], bssId[3], bssId[4], bssId[5]);
+
+
+    if ((pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress + 1) >
+            MAX_NUM_PREAUTH_FAIL_LIST_ADDRESS)
+    {
+        smsLog(pMac, LOGE, FL("Preauth fail list already full.. Cannot add new one"));
+        return eHAL_STATUS_FAILURE;
+    }
+    vos_mem_copy(pNeighborRoamInfo->FTRoamInfo.preAuthFailList.macAddress[pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress],
+                        bssId, sizeof(tSirMacAddr));
+    pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress++;
+    
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamIsPreauthCandidate
+
+    \brief  This function checks whether the given MAC address is already 
+            present in the preauth fail list and returns TRUE/FALSE accordingly
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return eANI_BOOLEAN_TRUE if preauth candidate, eANI_BOOLEAN_FALSE otherwise
+
+---------------------------------------------------------------------------*/
+tANI_BOOLEAN csrNeighborRoamIsPreauthCandidate(tpAniSirGlobal pMac, tSirMacAddr bssId)
+{
+    tANI_U8 i = 0;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    if (0 == pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress)
+        return eANI_BOOLEAN_TRUE;
+    
+    for (i = 0; i < pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress; i++)
+    {
+        if (VOS_TRUE == vos_mem_compare(pNeighborRoamInfo->FTRoamInfo.preAuthFailList.macAddress[i],
+                                                                        bssId, sizeof(tSirMacAddr)))
+        {
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("BSSID %02x:%02x:%02x:%02x:%02x:%02x already present in preauth fail list"),
+                                                bssId[0], bssId[1], bssId[2], bssId[3], bssId[4], bssId[5]);
+            return eANI_BOOLEAN_FALSE;
+        }
+    }
+
+    return eANI_BOOLEAN_TRUE;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamIssuePreauthReq
+
+    \brief  This function issues preauth request to PE with the 1st AP entry in the 
+            roamable AP list
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return eHAL_STATUS_SUCCESS on success, eHAL_STATUS_FAILURE otherwise
+
+---------------------------------------------------------------------------*/
+static eHalStatus csrNeighborRoamIssuePreauthReq(tpAniSirGlobal pMac)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpCsrNeighborRoamBSSInfo    pNeighborBssNode;
+    
+    /* This must not be true here */
+    VOS_ASSERT(pNeighborRoamInfo->FTRoamInfo.preauthRspPending == eANI_BOOLEAN_FALSE);
+
+    /* Issue Preauth request to PE here */
+    /* Need to issue the preauth request with the BSSID that is there in the head of the roamable AP list */
+    /* Parameters that should be passed are BSSID, Channel number and the neighborScanPeriod(probably) */
+    /* If roamableAPList gets empty, should transition to REPORT_SCAN state */
+    pNeighborBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->roamableAPList, NULL);
+
+    if (NULL == pNeighborBssNode)
+    {
+        smsLog(pMac, LOG1, FL("Roamable AP list is empty.. "));
+        return eHAL_STATUS_FAILURE;
+    }
+    else
+    {
+        status = csrRoamIssueFTPreauthReq(pMac, pNeighborRoamInfo->csrSessionId, pNeighborBssNode->pBssDescription); 
+        if (eHAL_STATUS_SUCCESS != status)
+        {
+            smsLog(pMac, LOGE, FL("Send Preauth request to PE failed with status %d\n"), status);
+            return status;
+        }
+    }
+    
+    pNeighborRoamInfo->FTRoamInfo.preauthRspPending = eANI_BOOLEAN_TRUE;
+
+    /* Increment the preauth retry count */
+    pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries++;
+    
+    /* Transition the state to preauthenticating */
+    CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_PREAUTHENTICATING)
+    
+    /* Start the preauth rsp timer */
+    status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimer, 
+                   CSR_NEIGHBOR_ROAM_PREAUTH_RSP_WAIT_MULTIPLIER * pNeighborRoamInfo->cfgParams.neighborScanPeriod * PAL_TIMER_TO_MS_UNIT,
+                   eANI_BOOLEAN_FALSE);
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("Preauth response wait timer start failed with status %d\n"), status);
+        return status;
+    }
+
+    
+    return status;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamPreauthRspHandler
+
+    \brief  This function handle the Preauth response from PE
+            Every preauth is allowed max 3 tries if it fails. If a bssid failed 
+            for more than MAX_TRIES, we will remove it from the list and try 
+            with the next node in the roamable AP list and add the BSSID to pre-auth failed 
+            list. If no more entries present in 
+            roamable AP list, transition to REPORT_SCAN state
+
+    \param  pMac - The handle returned by macOpen.
+            vosStatus - VOS_STATUS_SUCCESS/FAILURE/TIMEOUT status from PE
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamPreauthRspHandler(tpAniSirGlobal pMac, VOS_STATUS vosStatus)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+    tpCsrNeighborRoamBSSInfo pPreauthRspNode = NULL;
+
+    // We can receive it in these 2 states.
+    VOS_ASSERT((pNeighborRoamInfo->neighborRoamState == eCSR_NEIGHBOR_ROAM_STATE_PREAUTHENTICATING) ||
+        (pNeighborRoamInfo->neighborRoamState == eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN));
+
+    if ((pNeighborRoamInfo->neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_PREAUTHENTICATING) &&
+        (pNeighborRoamInfo->neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN))
+    {
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("Preauth response received in state %\n"), 
+            pNeighborRoamInfo->neighborRoamState);
+    }
+
+    if (VOS_STATUS_E_TIMEOUT != vosStatus)
+    {
+        /* This means we got the response from PE. Hence stop the timer */
+        status = palTimerStop(pMac->hHdd, pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimer);
+        pNeighborRoamInfo->FTRoamInfo.preauthRspPending = eANI_BOOLEAN_FALSE;
+    }
+
+    if (VOS_STATUS_SUCCESS == vosStatus)
+    {
+        pPreauthRspNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->roamableAPList, NULL);
+    }
+    if ((VOS_STATUS_SUCCESS == vosStatus) && (NULL != pPreauthRspNode))
+    {
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Preauth completed successfully after %d tries\n"), pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries);
+
+        /* Preauth competer successfully. Insert the preauthenticated node to tail of preAuthDoneList */
+        csrNeighborRoamRemoveRoamableAPListEntry(pMac, &pNeighborRoamInfo->roamableAPList, pPreauthRspNode);
+        csrLLInsertTail(&pNeighborRoamInfo->FTRoamInfo.preAuthDoneList, &pPreauthRspNode->List, LL_ACCESS_LOCK);
+
+        /* Pre-auth completed successfully. Transition to PREAUTH Done state */
+        CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE)
+        pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries = 0;
+
+        /* The caller of this function would start a timer and by the time it expires, supplicant should 
+           have provided the updated FTIEs to SME. So, when it expires, handoff will be triggered then */
+    }
+    else
+    {
+        tpCsrNeighborRoamBSSInfo    pNeighborBssNode = NULL;
+        tListElem                   *pEntry;
+
+        smsLog(pMac, LOGE, FL("Preauth failed retry number %d, status = %d\n"), pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries, vosStatus);
+        
+        /* Preauth failed. Add the bssId to the preAuth failed list MAC Address. Also remove the AP from roamable AP list */
+        if (pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries >=  CSR_NEIGHBOR_ROAM_MAX_NUM_PREAUTH_RETRIES)
+        {
+            /* We are going to remove the node as it fails for more than MAX tries. Reset this count to 0 */
+            pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries = 0;
+
+            /* The one in the head of the list should be one with which we issued pre-auth and failed */
+            pEntry = csrLLRemoveHead(&pNeighborRoamInfo->roamableAPList, LL_ACCESS_LOCK);
+            if(pEntry)
+            {
+                pNeighborBssNode = GET_BASE_ADDR(pEntry, tCsrNeighborRoamBSSInfo, List);
+            /* Add the BSSID to pre-auth fail list */
+            status = csrNeighborRoamAddBssIdToPreauthFailList(pMac, pNeighborBssNode->pBssDescription->bssId);
+            /* Now we can free this node */
+            csrNeighborRoamFreeNeighborRoamBSSNode(pMac, pNeighborBssNode);
+            }
+        }
+
+        /* Issue preauth request for the same/next entry */
+        if (eHAL_STATUS_SUCCESS == csrNeighborRoamIssuePreauthReq(pMac))
+            return;
+
+        CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN)
+
+        /* Start the neighbor results refresh timer and transition to REPORT_SCAN state to perform scan again */
+        status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer, 
+                        pNeighborRoamInfo->cfgParams.neighborResultsRefreshPeriod * PAL_TIMER_TO_MS_UNIT, 
+                        eANI_BOOLEAN_FALSE);
+        if (eHAL_STATUS_SUCCESS != status)
+        {
+            smsLog(pMac, LOGE, FL("Neighbor results refresh timer start failed with status %d\n"), status);
+            return;
+        }
+    }
+}
+#endif  /* WLAN_FEATURE_NEIGHBOR_ROAMING */
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamPrepareScanProfileFilter
+
+    \brief  This function creates a scan filter based on the currently connected profile.
+            Based on this filter, scan results are obtained
+
+    \param  pMac - The handle returned by macOpen.
+            pScanFilter - Populated scan filter based on the connected profile
+
+    \return eHAL_STATUS_SUCCESS on success, eHAL_STATUS_FAILURE otherwise
+
+---------------------------------------------------------------------------*/
+eHalStatus csrNeighborRoamPrepareScanProfileFilter(tpAniSirGlobal pMac, tCsrScanResultFilter *pScanFilter)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tANI_U8 sessionId   = (tANI_U8)pNeighborRoamInfo->csrSessionId;
+    tCsrRoamConnectedProfile *pCurProfile = &pMac->roam.roamSession[sessionId].connectedProfile;
+    tANI_U8 i = 0;
+    
+    VOS_ASSERT(pScanFilter != NULL);
+
+    vos_mem_zero(pScanFilter, sizeof(tCsrScanResultFilter));
+
+    /* We dont want to set BSSID based Filter */
+    pScanFilter->BSSIDs.numOfBSSIDs = 0;
+
+    /* Populate all the information from the connected profile */
+    pScanFilter->SSIDs.numOfSSIDs = 1;  
+    pScanFilter->SSIDs.SSIDList = vos_mem_malloc(sizeof(tCsrSSIDInfo));
+    if (NULL == pScanFilter->SSIDs.SSIDList)
+    {
+        smsLog(pMac, LOGE, FL("Scan Filter SSID mem alloc failed"));
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+    pScanFilter->SSIDs.SSIDList->handoffPermitted = 1;
+    pScanFilter->SSIDs.SSIDList->ssidHidden = 0;
+    pScanFilter->SSIDs.SSIDList->SSID.length =  pCurProfile->SSID.length;
+    vos_mem_copy((void *)pScanFilter->SSIDs.SSIDList->SSID.ssId, (void *)pCurProfile->SSID.ssId, pCurProfile->SSID.length); 
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Filtering for SSID %s from scan results.. SSID Length = %d\n"), 
+                        pScanFilter->SSIDs.SSIDList->SSID.ssId, pScanFilter->SSIDs.SSIDList->SSID.length);
+    pScanFilter->authType.numEntries = 1;
+    pScanFilter->authType.authType[0] = pCurProfile->AuthType;
+
+    pScanFilter->EncryptionType.numEntries = 1; //This must be 1
+    pScanFilter->EncryptionType.encryptionType[0] = pCurProfile->EncryptionType;
+
+    pScanFilter->mcEncryptionType.numEntries = 1;
+    pScanFilter->mcEncryptionType.encryptionType[0] = pCurProfile->mcEncryptionType;
+
+    pScanFilter->BSSType = pCurProfile->BSSType;
+
+    /* We are intrested only in the scan results on channels that we scanned  */
+    pScanFilter->ChannelInfo.numOfChannels = pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels;
+    pScanFilter->ChannelInfo.ChannelList = vos_mem_malloc(pScanFilter->ChannelInfo.numOfChannels * sizeof(tANI_U8));
+    if (NULL == pScanFilter->ChannelInfo.ChannelList)
+    {
+        smsLog(pMac, LOGE, FL("Scan Filter Channel list mem alloc failed"));
+        vos_mem_free(pScanFilter->SSIDs.SSIDList);
+        pScanFilter->SSIDs.SSIDList = NULL;
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+    for (i = 0; i < pScanFilter->ChannelInfo.numOfChannels; i++)
+    {
+        pScanFilter->ChannelInfo.ChannelList[i] = pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i];
+    }
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    if (pNeighborRoamInfo->is11rAssoc)
+    {
+        /* MDIE should be added as a part of profile. This should be added as a part of filter as well  */
+        pScanFilter->MDID.mdiePresent = pCurProfile->MDID.mdiePresent;
+        pScanFilter->MDID.mobilityDomain = pCurProfile->MDID.mobilityDomain;
+    }
+#endif
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamProcessScanResults
+
+    \brief  This function extracts scan results, sorts on the basis of neighbor score(todo). 
+            Assumed that the results are already sorted by RSSI by csrScanGetResult
+
+    \param  pMac - The handle returned by macOpen.
+            pScanResultList - Scan result result obtained from csrScanGetResult()
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+
+static void csrNeighborRoamProcessScanResults(tpAniSirGlobal pMac, tScanResultHandle *pScanResultList)
+{
+    tCsrScanResultInfo *pScanResult;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tpCsrNeighborRoamBSSInfo    pBssInfo;
+
+    /* Expecting the scan result already to be in the sorted order based on the RSSI */
+    /* Based on the previous state we need to check whether the list should be sorted again taking neighbor score into consideration */
+    /* If previous state is CFG_CHAN_LIST_SCAN, there should not be any neighbor score associated with any of the BSS.
+       If the previous state is REPORT_QUERY, then there will be neighbor score for each of the APs */
+    /* For now, let us take the top of the list provided as it is by the CSR Scan result API. This means it is assumed that neighbor score 
+       and rssi score are in the same order. This will be taken care later */
+
+    while (NULL != (pScanResult = csrScanResultGetNext(pMac, *pScanResultList)))
+    {
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Scan result: BSSID : %02x:%02x:%02x:%02x:%02x:%02x"), 
+                        pScanResult->BssDescriptor.bssId[0],
+                        pScanResult->BssDescriptor.bssId[1],
+                        pScanResult->BssDescriptor.bssId[2],
+                        pScanResult->BssDescriptor.bssId[3],
+                        pScanResult->BssDescriptor.bssId[4],
+                        pScanResult->BssDescriptor.bssId[5]);
+
+        if (VOS_TRUE == vos_mem_compare(pScanResult->BssDescriptor.bssId, 
+                       pNeighborRoamInfo->currAPbssid, sizeof(tSirMacAddr)))
+        {
+            //currently associated AP. Do not have this in the roamable AP list
+            continue;
+        }
+
+        if (abs(pNeighborRoamInfo->cfgParams.neighborReassocThreshold) < abs(pScanResult->BssDescriptor.rssi))
+        {
+            VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+                  "%s: [INFOLOG]Current reassoc threshold %d new ap rssi worse=%d\n", __func__,
+                      (int)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
+                      (int)pScanResult->BssDescriptor.rssi * (-1) );
+            continue;
+        }        
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        if (pNeighborRoamInfo->is11rAssoc)
+        {
+            if (!csrNeighborRoamIsPreauthCandidate(pMac, pScanResult->BssDescriptor.bssId))
+            {
+                smsLog(pMac, LOGE, FL("BSSID present in pre-auth fail list.. Ignoring"));
+                continue;
+            }
+        }
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+
+#ifdef FEATURE_WLAN_CCX
+        if (pNeighborRoamInfo->isCCXAssoc)
+        {
+            if (!csrNeighborRoamIsPreauthCandidate(pMac, pScanResult->BssDescriptor.bssId))
+            {
+                smsLog(pMac, LOGE, FL("BSSID present in pre-auth fail list.. Ignoring"));
+                continue;
+            }
+        }
+        if ((pScanResult->BssDescriptor.QBSSLoad_present) &&
+             (pScanResult->BssDescriptor.QBSSLoad_avail))
+        {
+            if (pNeighborRoamInfo->isVOAdmitted)
+            {
+                smsLog(pMac, LOG1, FL("New AP has %x BW available\n"), (unsigned int)pScanResult->BssDescriptor.QBSSLoad_avail);
+                smsLog(pMac, LOG1, FL("We need %x BW available\n"),(unsigned int)pNeighborRoamInfo->MinQBssLoadRequired);
+                if (pScanResult->BssDescriptor.QBSSLoad_avail < pNeighborRoamInfo->MinQBssLoadRequired) 
+                {
+                    VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                        "[INFOLOG]BSSID : %02x:%02x:%02x:%02x:%02x:%02x has no bandwidth ignoring..not adding to roam list\n",
+                        pScanResult->BssDescriptor.bssId[0],
+                        pScanResult->BssDescriptor.bssId[1],
+                        pScanResult->BssDescriptor.bssId[2],
+                        pScanResult->BssDescriptor.bssId[3],
+                        pScanResult->BssDescriptor.bssId[4],
+                        pScanResult->BssDescriptor.bssId[5]);
+                    continue;
+                }
+            }
+        }
+        else
+        {
+            smsLog(pMac, LOGE, FL("No QBss %x %x\n"), (unsigned int)pScanResult->BssDescriptor.QBSSLoad_avail, (unsigned int)pScanResult->BssDescriptor.QBSSLoad_present);
+            if (pNeighborRoamInfo->isVOAdmitted)
+            {
+                VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                    "[INFOLOG]BSSID : %02x:%02x:%02x:%02x:%02x:%02x has no QBSSLoad IE, ignoring..not adding to roam list\n",
+                    pScanResult->BssDescriptor.bssId[0],
+                    pScanResult->BssDescriptor.bssId[1],
+                    pScanResult->BssDescriptor.bssId[2],
+                    pScanResult->BssDescriptor.bssId[3],
+                    pScanResult->BssDescriptor.bssId[4],
+                    pScanResult->BssDescriptor.bssId[5]);
+                continue;
+            }
+        }
+#endif /* FEATURE_WLAN_CCX */
+
+        /* If the received timestamp in BSS description is earlier than the scan request timestamp, skip 
+         * this result */
+        if (pNeighborRoamInfo->scanRequestTimeStamp >= pScanResult->BssDescriptor.nReceivedTime)
+        {
+            smsLog(pMac, LOGE, FL("Ignoring BSS as it is older than the scan request timestamp"));
+            continue;
+        }
+
+        pBssInfo = vos_mem_malloc(sizeof(tCsrNeighborRoamBSSInfo));
+        if (NULL == pBssInfo)
+        {
+            smsLog(pMac, LOGE, FL("Memory allocation for Neighbor Roam BSS Info failed.. Just ignoring"));
+            continue;
+        }
+
+        pBssInfo->pBssDescription = vos_mem_malloc(pScanResult->BssDescriptor.length + sizeof(pScanResult->BssDescriptor.length));
+        if (pBssInfo->pBssDescription != NULL)
+        {
+            vos_mem_copy(pBssInfo->pBssDescription, &pScanResult->BssDescriptor, 
+                    pScanResult->BssDescriptor.length + sizeof(pScanResult->BssDescriptor.length));
+        }
+        else
+        {
+            smsLog(pMac, LOGE, FL("Memory allocation for Neighbor Roam BSS Descriptor failed.. Just ignoring"));
+            vos_mem_free(pBssInfo);
+            continue;
+            
+        }
+        pBssInfo->apPreferenceVal = 10; //some value for now. Need to calculate the actual score based on RSSI and neighbor AP score
+
+        /* Just add to the end of the list as it is already sorted by RSSI */
+        csrLLInsertTail(&pNeighborRoamInfo->roamableAPList, &pBssInfo->List, LL_ACCESS_LOCK);
+    }
+
+    /* Now we have all the scan results in our local list. Good time to free up the the list we got as a part of csrGetScanResult */
+    csrScanResultPurge(pMac, *pScanResultList);
+
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamHandleEmptyScanResult
+
+    \brief      This function will be invoked in CFG_CHAN_LIST_SCAN state when 
+                there are no valid APs in the scan result for roaming. This means 
+                out AP is the best and no other AP is around. No point in scanning 
+                again and again. Performing the following here.
+                1. Deregister the pre-auth callback from TL
+                2. Stop the neighbor scan timer
+                3. Re-register the neighbor lookup callback with increased pre-auth threshold
+                4. Transition the state to CONNECTED state
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+static VOS_STATUS csrNeighborRoamHandleEmptyScanResult(tpAniSirGlobal pMac)
+{
+    VOS_STATUS  vosStatus = VOS_STATUS_SUCCESS;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+
+    /* Stop the neighbor scan timer now */
+    status = palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGW, FL(" palTimerStop failed with status %d\n"), status);
+    }
+
+    /* Increase the neighbor lookup threshold by a constant factor or 1 */
+    if ((pNeighborRoamInfo->currentNeighborLookupThreshold+3) < pNeighborRoamInfo->cfgParams.neighborReassocThreshold)
+    {
+        pNeighborRoamInfo->currentNeighborLookupThreshold += 3;
+    }
+
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    /* Clear off the old neighbor report details */
+    vos_mem_zero(&pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo, sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
+#endif
+
+    /* Reset all the necessary variables before transitioning to the CONNECTED state */
+    csrNeighborRoamResetConnectedStateControlInfo(pMac);
+
+    /* Transition to CONNECTED state */
+    CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CONNECTED)
+    /* Re-register Neighbor Lookup threshold callback with TL */
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering DOWN event neighbor lookup callback with TL for RSSI = %d"), pNeighborRoamInfo->currentNeighborLookupThreshold * (-1)); 
+    vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
+                                    WLANTL_HO_THRESHOLD_DOWN, 
+                                    csrNeighborRoamNeighborLookupDOWNCallback, 
+                                    VOS_MODULE_ID_SME, pMac);
+    
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+       //err msg
+       smsLog(pMac, LOGW, FL(" Couldn't re-register csrNeighborRoamNeighborLookupDOWNCallback with TL: Status = %d\n"), status);
+    }
+    return vosStatus;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamScanRequestCallback
+
+    \brief  This function is the callback function registered in csrScanRequest() to 
+            indicate the completion of scan. If scan is completed for all the channels in 
+            the channel list, this function gets the scan result and starts the refresh results
+            timer to avoid having stale results. If scan is not completed on all the channels,
+            it restarts the neighbor scan timer which on expiry issues scan on the next 
+            channel
+
+    \param  halHandle - The handle returned by macOpen.
+            pContext - not used
+            scanId - not used
+            status - not used
+
+    \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+static eHalStatus csrNeighborRoamScanRequestCallback(tHalHandle halHandle, void *pContext,
+                         tANI_U32 scanId, eCsrScanStatus status)
+{
+    tpAniSirGlobal                  pMac = (tpAniSirGlobal) halHandle;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tANI_U8                         currentChanIndex;
+    tCsrScanResultFilter    scanFilter;
+    tScanResultHandle       scanResult;
+    tANI_U32                tempVal = 0;
+
+    pMac->roam.neighborRoamInfo.scanRspPending = eANI_BOOLEAN_FALSE;
+    
+    /* This can happen when we receive a UP event from TL in any of the scan states. Silently ignore it */
+    if (eCSR_NEIGHBOR_ROAM_STATE_CONNECTED == pNeighborRoamInfo->neighborRoamState)
+    {
+        smsLog(pMac, LOGE, FL("Received in CONNECTED state. Must be because a UP event from TL after issuing scan request. Ignore it"));
+        return eHAL_STATUS_SUCCESS;
+    }
+
+    /* -1 is done because the chanIndex would have got incremented after issuing a successful scan request */
+    currentChanIndex = (pMac->roam.neighborRoamInfo.roamChannelInfo.currentChanIndex) ? (pMac->roam.neighborRoamInfo.roamChannelInfo.currentChanIndex - 1) : 0;
+
+    /* Validate inputs */
+    if (pMac->roam.neighborRoamInfo.roamChannelInfo.currentChannelListInfo.ChannelList) { 
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("csrNeighborRoamScanRequestCallback received for Channel = %d, ChanIndex = %d"), 
+                    pMac->roam.neighborRoamInfo.roamChannelInfo.currentChannelListInfo.ChannelList[currentChanIndex], currentChanIndex);
+    }
+    else
+    {
+        smsLog(pMac, LOG1, FL("Received during clean-up. Silently ignore scan completion event."));
+        return eHAL_STATUS_SUCCESS;
+    }
+
+    if (eANI_BOOLEAN_FALSE == pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress)
+    {
+        /* Scan is completed in the  CFG_CHAN_SCAN state. We can transition to REPORT_SCAN state 
+           just to get the results and perform PREAUTH */
+        /* Now we have completed scanning the channel list. We have get the result by applying appropriate filter
+           sort the results based on neighborScore and RSSI and select the best candidate out of the list */
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("Channel list scan completed. Current chan index = %d"), currentChanIndex);
+        VOS_ASSERT(pNeighborRoamInfo->roamChannelInfo.currentChanIndex == 0);
+
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+        /* If the state is REPORT_SCAN, then this must be the scan after the REPORT_QUERY state. So, we 
+           should use the BSSID filter made out of neighbor reports */
+        if (eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN == pNeighborRoamInfo->neighborRoamState)
+        {
+            status = csrNeighborRoamBssIdScanFilter(pMac, &scanFilter);
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("11R or CCX Association: Prepare scan filter status  with neighbor AP = %d"), status);
+            tempVal = 1;
+        }
+        else
+#endif
+        {
+            status = csrNeighborRoamPrepareScanProfileFilter(pMac, &scanFilter);
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("11R/CCX/Other Association: Prepare scan to find neighbor AP filter status  = %d"), status);
+        }
+        if (eHAL_STATUS_SUCCESS != status)
+        {
+            smsLog(pMac, LOGE, FL("Scan Filter preparation failed for Assoc type %d.. Bailing out.."), tempVal);
+            return eHAL_STATUS_FAILURE;
+        }
+        status = csrScanGetResult(pMac, &scanFilter, &scanResult);
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Get Scan Result status code %d"), status);
+        /* Process the scan results and update roamable AP list */
+        csrNeighborRoamProcessScanResults(pMac, &scanResult);
+
+        /* Free the scan filter */
+        csrFreeScanFilter(pMac, &scanFilter);
+
+        tempVal = csrLLCount(&pNeighborRoamInfo->roamableAPList);
+
+        switch(pNeighborRoamInfo->neighborRoamState)
+        {
+            case eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN:
+                if (tempVal)
+                {
+#ifdef WLAN_FEATURE_VOWIFI_11R
+                    /* If this is a non-11r association, then we can register the reassoc callback here as we have some 
+                                        APs in the roamable AP list */
+                    if (pNeighborRoamInfo->is11rAssoc)
+                    {
+                        /* Valid APs are found after scan. Now we can initiate pre-authentication */
+                        CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN)
+                    }
+                    else
+#endif
+#ifdef FEATURE_WLAN_CCX
+                    /* If this is a non-11r association, then we can register the reassoc callback here as we have some 
+                                        APs in the roamable AP list */
+                    if (pNeighborRoamInfo->isCCXAssoc)
+                    {
+                        /* Valid APs are found after scan. Now we can initiate pre-authentication */
+                        CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN)
+                    }
+                    else
+#endif
+                    {
+                       
+                        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Completed scanning of CFG CHAN LIST in non-11r association. Registering reassoc callback"));
+                        /* Nothing much to do now. Will continue to remain in this state in case of non-11r association */
+                        /* Stop the timer. But how long the roamable AP list will be valid in here. At some point of time, we 
+                           need to restart the CFG CHAN list scan procedure if reassoc callback is not invoked from TL 
+                           within certain duration */
+                        
+//                        palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+                    }
+                }
+                else
+                {
+                    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("No candidate found after scanning in state %d.. "), pNeighborRoamInfo->neighborRoamState);
+                    /* Handle it appropriately */
+                    csrNeighborRoamHandleEmptyScanResult(pMac);
+                }
+                break;
+#ifdef WLAN_FEATURE_VOWIFI_11R                
+            case eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN:
+                if (!tempVal)
+                {
+                    smsLog(pMac, LOGE, FL("No candidate found after scanning in state %d.. "), pNeighborRoamInfo->neighborRoamState);
+                    /* Stop the timer here as the same timer will be started again in CFG_CHAN_SCAN_STATE */
+                    csrNeighborRoamTransitToCFGChanScan(pMac);
+                }
+                break;
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+            default:
+                // Can come only in INIT state. Where in we are associated, we sent scan and user
+                // in the meantime decides to disassoc, we will be in init state and still received call
+                // back issued. Should not come here in any other state, printing just in case
+                VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                        "%s: [INFOLOG] State %d\n", __func__, (pNeighborRoamInfo->neighborRoamState));
+
+                // Lets just exit out silently.
+                return eHAL_STATUS_SUCCESS;
+        }
+
+        if (tempVal)
+        {
+            VOS_STATUS  vosStatus = VOS_STATUS_SUCCESS;
+
+           /* This timer should be started before registering the Reassoc callback with TL. This is because, it is very likely 
+            * that the callback getting called immediately and the timer would never be stopped when pre-auth is in progress */
+           if (eHAL_STATUS_SUCCESS != palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer, 
+                        pNeighborRoamInfo->cfgParams.neighborResultsRefreshPeriod * PAL_TIMER_TO_MS_UNIT, 
+                        eANI_BOOLEAN_FALSE))
+            {
+                smsLog(pMac, LOGE, FL("Neighbor results refresh timer failed to start, status = %d"), status);
+                vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
+                pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+                return VOS_STATUS_E_FAILURE;
+            }
+            
+            NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering DOWN event Reassoc callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1));
+            /* Register a reassoc Indication callback */
+            vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
+                                            WLANTL_HO_THRESHOLD_DOWN, 
+                                            csrNeighborRoamReassocIndCallback,
+                                            VOS_MODULE_ID_SME, pMac);
+            
+            if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+            {
+               //err msg
+               smsLog(pMac, LOGW, FL(" Couldn't register csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
+            }
+ 
+        }
+    }
+    else
+    {
+
+        /* Restart the timer for the next scan sequence as scanning is not over */
+        status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer, 
+                    pNeighborRoamInfo->cfgParams.neighborScanPeriod * PAL_TIMER_TO_MS_UNIT, 
+                    eANI_BOOLEAN_FALSE);
+    
+        if (eHAL_STATUS_SUCCESS != status)
+        {
+            /* Timer start failed.. Should we ASSERT here??? */
+            smsLog(pMac, LOGE, FL("Neighbor scan PAL Timer start failed, status = %d, Ignoring state transition"), status);
+            vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
+            pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+            return VOS_STATUS_E_FAILURE;
+        }
+    }
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamIssueBgScanRequest
+
+    \brief  This function issues CSR scan request after populating all the BG scan params 
+            passed
+
+    \param  pMac - The handle returned by macOpen.
+            pBgScanParams - Params that need to be populated into csr Scan request
+
+    \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+eHalStatus csrNeighborRoamIssueBgScanRequest(tpAniSirGlobal pMac, tCsrBGScanRequest *pBgScanParams)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 scanId;
+    tCsrScanRequest scanReq;
+    tANI_U8 channel;
+    
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("csrNeighborRoamIssueBgScanRequest for Channel = %d, ChanIndex = %d"), 
+                    pBgScanParams->ChannelInfo.ChannelList[0], pMac->roam.neighborRoamInfo.roamChannelInfo.currentChanIndex);
+
+
+    //send down the scan req for 1 channel on the associated SSID
+    palZeroMemory(pMac->hHdd, &scanReq, sizeof(tCsrScanRequest));
+    /* Fill in the SSID Info */
+    scanReq.SSIDs.numOfSSIDs = 1;
+    scanReq.SSIDs.SSIDList = vos_mem_malloc(sizeof(tCsrSSIDInfo) * scanReq.SSIDs.numOfSSIDs);
+    if(NULL == scanReq.SSIDs.SSIDList)
+    {
+       //err msg
+       smsLog(pMac, LOGW, FL("Couldn't allocate memory for the SSID..Freeing memory allocated for Channel List\n"));
+       return eHAL_STATUS_FAILURE;
+    }
+    vos_mem_zero(scanReq.SSIDs.SSIDList, sizeof(tCsrSSIDInfo) * scanReq.SSIDs.numOfSSIDs);
+
+    scanReq.SSIDs.SSIDList[0].handoffPermitted = eANI_BOOLEAN_TRUE;
+    scanReq.SSIDs.SSIDList[0].ssidHidden = eANI_BOOLEAN_TRUE;
+    vos_mem_copy((void *)&scanReq.SSIDs.SSIDList[0].SSID, (void *)&pBgScanParams->SSID, sizeof(pBgScanParams->SSID));
+    
+    scanReq.ChannelInfo.numOfChannels = pBgScanParams->ChannelInfo.numOfChannels;
+    
+    channel = pBgScanParams->ChannelInfo.ChannelList[0];
+    scanReq.ChannelInfo.ChannelList = &channel;    
+
+    scanReq.BSSType = eCSR_BSS_TYPE_INFRASTRUCTURE;
+    scanReq.scanType = eSIR_ACTIVE_SCAN;
+    scanReq.requestType = eCSR_SCAN_HO_BG_SCAN;
+    scanReq.maxChnTime = pBgScanParams->maxChnTime;
+    scanReq.minChnTime = pBgScanParams->minChnTime;
+    status = csrScanRequest(pMac, CSR_SESSION_ID_INVALID, &scanReq,
+                        &scanId, csrNeighborRoamScanRequestCallback, NULL);
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("CSR Scan Request failed with status %d"), status);
+        vos_mem_free(scanReq.SSIDs.SSIDList);
+        return status;
+    }
+    pMac->roam.neighborRoamInfo.scanRspPending = eANI_BOOLEAN_TRUE;
+
+    vos_mem_free(scanReq.SSIDs.SSIDList);
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Channel List Address = %08x, Actual index = %d"), 
+                    &pMac->roam.neighborRoamInfo.roamChannelInfo.currentChannelListInfo.ChannelList[0], 
+                    pMac->roam.neighborRoamInfo.roamChannelInfo.currentChanIndex);
+    return status;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamPerformBgScan
+
+    \brief  This function is invoked on every expiry of neighborScanTimer till all 
+            the channels in the channel list are scanned. It populates necessary 
+            parameters for BG scan and calls appropriate AP to invoke the CSR scan 
+            request
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+eHalStatus csrNeighborRoamPerformBgScan(tpAniSirGlobal pMac)
+{
+    eHalStatus      status = eHAL_STATUS_SUCCESS;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tCsrBGScanRequest   bgScanParams;
+    tANI_U8             broadcastBssid[] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
+    tANI_U8             channel = 0;
+
+    if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
+    {
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Channel List Address = %08x"), &pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[0]);
+    }
+    else 
+    {
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Channel List Empty"));
+        // Go back and restart. Mostly timer start failure has occured.
+        // When timer start is declared a failure, then we delete the list.
+        // Should not happen now as we stop and then only start the scan timer. 
+        // still handle the unlikely case.
+        csrNeighborRoamHandleEmptyScanResult(pMac);
+        return status;
+    }
+    /* Need to perform scan here before getting the list */
+    vos_mem_copy(bgScanParams.bssid, broadcastBssid, sizeof(tCsrBssid));
+    bgScanParams.SSID.length = pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.length;
+    vos_mem_copy(bgScanParams.SSID.ssId, pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.ssId, 
+                                    pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.length);
+
+    channel = pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[pNeighborRoamInfo->roamChannelInfo.currentChanIndex];
+    bgScanParams.ChannelInfo.numOfChannels = 1;
+    bgScanParams.ChannelInfo.ChannelList = &channel;
+   
+    bgScanParams.minChnTime = pNeighborRoamInfo->cfgParams.minChannelScanTime;
+    bgScanParams.maxChnTime = pNeighborRoamInfo->cfgParams.maxChannelScanTime;
+
+    status = csrNeighborRoamIssueBgScanRequest(pMac, &bgScanParams);
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("Issue of BG Scan request failed: Status = %d"), status);
+        return status;
+    }
+
+    pNeighborRoamInfo->roamChannelInfo.currentChanIndex++;
+    if (pNeighborRoamInfo->roamChannelInfo.currentChanIndex >= 
+            pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels)
+    {      
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Completed scanning channels in Channel List: CurrChanIndex = %d, Num Channels = %d"),
+                                            pNeighborRoamInfo->roamChannelInfo.currentChanIndex, 
+                                            pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels);
+        /* We have completed scanning all the channels */
+        pNeighborRoamInfo->roamChannelInfo.currentChanIndex = 0;
+        /* We are no longer scanning the channel list. Next timer firing should be used to get the scan results 
+           and select the best AP in the list */
+        if (eANI_BOOLEAN_TRUE == pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress)
+        {
+            pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_FALSE;
+        }
+    }
+
+    return status;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamNeighborScanTimerCallback
+
+    \brief  This function is the neighbor scan timer callback function. It invokes 
+            the BG scan request based on the current and previous states
+
+    \param  pv - CSR timer context info which includes pMac and session ID
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamNeighborScanTimerCallback(void *pv)
+{
+    tCsrTimerInfo *pInfo = (tCsrTimerInfo *)pv;
+    tpAniSirGlobal pMac = pInfo->pMac;
+    tANI_U32         sessionId = pInfo->sessionId;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    // check if bg scan is on going, no need to send down the new params if true
+    if(eANI_BOOLEAN_TRUE == pNeighborRoamInfo->scanRspPending)
+    {
+       //msg
+       smsLog(pMac, LOGW, FL("Already BgScanRsp is Pending\n"));
+       return;
+    }
+
+    VOS_ASSERT(sessionId == pNeighborRoamInfo->csrSessionId);
+
+    switch (pNeighborRoamInfo->neighborRoamState)
+    {
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        case eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN:
+            switch(pNeighborRoamInfo->prevNeighborRoamState)
+            {
+                case eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY:
+                    csrNeighborRoamPerformBgScan(pMac);
+                    break;
+                default:
+                    smsLog(pMac, LOGE, FL("Neighbor scan callback received in state %d, prev state = %d"), 
+                                    pNeighborRoamInfo->neighborRoamState, pNeighborRoamInfo->prevNeighborRoamState);
+                    break;
+            }
+            break;
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+        case eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN:     
+            csrNeighborRoamPerformBgScan(pMac);
+            break;
+        default:
+            break;
+    }
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamResultsRefreshTimerCallback
+
+    \brief  This function is the timer callback function for results refresh timer.
+            When this is invoked, it is as good as down event received from TL. So, 
+            clear off the roamable AP list and start the scan procedure based on 11R 
+            or non-11R association
+
+    \param  context - CSR timer context info which includes pMac and session ID
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamResultsRefreshTimerCallback(void *context)
+{
+    tCsrTimerInfo *pInfo = (tCsrTimerInfo *)context;
+    tpAniSirGlobal pMac = pInfo->pMac;
+    VOS_STATUS     vosStatus = VOS_STATUS_SUCCESS;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+     
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event reassoc callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1));
+
+    /* Deregister reassoc callback. Ignore return status */
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
+                                                        WLANTL_HO_THRESHOLD_DOWN, 
+                                                        csrNeighborRoamReassocIndCallback,
+                                                        VOS_MODULE_ID_SME);
+                        
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+        //err msg
+        smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
+    }
+
+    /* Reset all the variables just as no scan had happened before */
+    csrNeighborRoamResetConnectedStateControlInfo(pMac);
+
+#if defined WLAN_FEATURE_VOWIFI_11R && defined WLAN_FEATURE_VOWIFI
+    if ((pNeighborRoamInfo->is11rAssoc) && (pMac->rrm.rrmSmeContext.rrmConfig.rrmEnabled))
+    {
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("11R Association:Neighbor Lookup Down event received in CONNECTED state"));
+        vosStatus = csrNeighborRoamIssueNeighborRptRequest(pMac);
+        if (VOS_STATUS_SUCCESS != vosStatus)
+        {
+            smsLog(pMac, LOGE, FL("Neighbor report request failed. status = %d\n"), vosStatus);
+            return;
+        }
+        /* Increment the neighbor report retry count after sending the neighbor request successfully */
+        pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum++;
+        pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_TRUE;
+        CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY)
+    }
+    else
+#endif      
+    {
+        NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Non 11R or CCX Association:Neighbor Lookup Down event received in CONNECTED state"));
+        vosStatus = csrNeighborRoamTransitToCFGChanScan(pMac);
+        if (VOS_STATUS_SUCCESS != vosStatus)
+        {
+            return;
+        }
+    }
+    return;
+}
+
+#if defined WLAN_FEATURE_VOWIFI_11R && defined WLAN_FEATURE_VOWIFI
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamIssueNeighborRptRequest
+
+    \brief  This function is invoked when TL issues a down event and the current assoc 
+            is a 11R association. It invokes SME RRM API to issue the neighbor request to 
+            the currently associated AP with the current SSID
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+VOS_STATUS csrNeighborRoamIssueNeighborRptRequest(tpAniSirGlobal pMac)
+{
+    tRrmNeighborRspCallbackInfo callbackInfo;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tRrmNeighborReq neighborReq;
+
+
+    neighborReq.no_ssid = 0;
+
+    /* Fill in the SSID */
+    neighborReq.ssid.length = pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.length;
+    vos_mem_copy(neighborReq.ssid.ssId, pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.ssId, 
+                                    pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.length);
+    
+    callbackInfo.neighborRspCallback = csrNeighborRoamRRMNeighborReportResult;
+    callbackInfo.neighborRspCallbackContext = pMac;
+    callbackInfo.timeout = pNeighborRoamInfo->FTRoamInfo.neighborReportTimeout;
+
+    return sme_NeighborReportRequest(pMac,(tANI_U8) pNeighborRoamInfo->csrSessionId, &neighborReq, &callbackInfo);
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamCreateChanListFromNeighborReport
+
+    \brief  This function is invoked when neighbor report is received for the 
+            neighbor request. Based on the channels present in the neighbor report, 
+            it generates channel list which will be used in REPORT_SCAN state to
+            scan for these neighbor APs
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+VOS_STATUS csrNeighborRoamCreateChanListFromNeighborReport(tpAniSirGlobal pMac)
+{
+    tpRrmNeighborReportDesc pNeighborBssDesc;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tANI_U8         numChannels = 0, i = 0, j=0;
+    tANI_U8         channelList[MAX_BSS_IN_NEIGHBOR_RPT];
+
+    /* This should always start from 0 whenever we create a channel list out of neighbor AP list */
+    pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport = 0;
+
+    pNeighborBssDesc = smeRrmGetFirstBssEntryFromNeighborCache(pMac);
+
+    while (pNeighborBssDesc)
+    {
+        if (pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport >= MAX_BSS_IN_NEIGHBOR_RPT) break;
+        
+        /* Update the neighbor BSS Info in the 11r FT Roam Info */
+        pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo[pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport].channelNum = 
+                                    pNeighborBssDesc->pNeighborBssDescription->channel;
+        pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo[pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport].neighborScore = 
+                                    (tANI_U8)pNeighborBssDesc->roamScore;
+        vos_mem_copy(pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo[pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport].neighborBssId,
+                                     pNeighborBssDesc->pNeighborBssDescription->bssId, sizeof(tSirMacAddr));
+        pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport++;
+
+        /* Saving the channel list non-redundantly */
+        if (numChannels > 0)
+        {
+            for (i = 0; i < numChannels; i++)
+            {
+                if (pNeighborBssDesc->pNeighborBssDescription->channel == channelList[i])
+                    break;
+            }
+            
+        }
+        if (i == numChannels)
+        {
+            if (pNeighborBssDesc->pNeighborBssDescription->channel)
+            {
+                // Make sure to add only if its the same band
+                if ((pNeighborRoamInfo->currAPoperationChannel <= (RF_CHAN_14+1)) &&
+                    (pNeighborBssDesc->pNeighborBssDescription->channel <= (RF_CHAN_14+1)))
+                {
+                        VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                                "%s: [INFOLOG] Adding %d to Neighbor channel list\n", __func__,
+                                pNeighborBssDesc->pNeighborBssDescription->channel);
+                        channelList[numChannels] = pNeighborBssDesc->pNeighborBssDescription->channel;
+                        numChannels++;
+                }
+                else if ((pNeighborRoamInfo->currAPoperationChannel >= RF_CHAN_128) &&
+                    (pNeighborBssDesc->pNeighborBssDescription->channel >= RF_CHAN_128))
+                {
+                        VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                                "%s: [INFOLOG] Adding %d to Neighbor channel list\n", __func__,
+                                pNeighborBssDesc->pNeighborBssDescription->channel);
+                        channelList[numChannels] = pNeighborBssDesc->pNeighborBssDescription->channel;
+                        numChannels++;
+                }
+            }
+        }
+            
+        pNeighborBssDesc = smeRrmGetNextBssEntryFromNeighborCache(pMac, pNeighborBssDesc);
+    }
+
+    if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
+    {
+        // Before we free the existing channel list for a safety net make sure
+        // we have a union of the IAPP and the already existing list. 
+        for (i = 0; i < pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels; i++)
+        {
+            for (j = 0; j < numChannels; j++)
+            {
+                if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i] == channelList[j])
+                    break;
+            }
+            if (j == numChannels)
+            {
+                if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i])
+                {
+                    // Make sure to add only if its the same band
+                    if ((pNeighborRoamInfo->currAPoperationChannel <= (RF_CHAN_14+1)) &&
+                        (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i] <= (RF_CHAN_14+1)))
+                    {
+                            VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                                    "%s: [INFOLOG] Adding extra %d to Neighbor channel list\n", __func__,
+                            pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i]);
+                            channelList[numChannels] = 
+                            pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i];
+                            numChannels++;
+                    }
+                    if ((pNeighborRoamInfo->currAPoperationChannel >= RF_CHAN_128) &&
+                         (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i] >= RF_CHAN_128))
+                    {
+                            VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+                                    "%s: [INFOLOG] Adding extra %d to Neighbor channel list\n", __func__,
+                                pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i]);
+                            channelList[numChannels] = 
+                                pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i];
+                            numChannels++;
+                    }
+                }
+            }
+        }
+        vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
+    }
+
+    pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+    /* Store the obtained channel list to the Neighbor Control data structure */
+    if (numChannels)
+        pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = vos_mem_malloc((numChannels) * sizeof(tANI_U8));
+    if (NULL == pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
+    {
+        smsLog(pMac, LOGE, FL("Memory allocation for Channel list failed.. TL event ignored"));
+        return VOS_STATUS_E_RESOURCES;
+    }
+
+    vos_mem_copy(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList, 
+                                            channelList, (numChannels) * sizeof(tANI_U8));
+    pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels = numChannels;
+    if (numChannels)
+    {
+        smsLog(pMac, LOG1, FL("IAPP Neighbor list callback received as expected in state %d."), 
+            pNeighborRoamInfo->neighborRoamState);
+        pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived = eANI_BOOLEAN_TRUE;
+    }
+    pNeighborRoamInfo->roamChannelInfo.currentChanIndex = 0;
+    pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_TRUE;
+    
+    return VOS_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamRRMNeighborReportResult
+
+    \brief  This function is the neighbor report callback that will be invoked by 
+            SME RRM on receiving a neighbor report or of neighbor report is not 
+            received after timeout. On receiving a valid report, it generates a 
+            channel list from the neighbor report and starts the 
+            neighbor scan timer
+
+    \param  context - The handle returned by macOpen.
+            vosStatus - Status of the callback(SUCCESS/FAILURE)
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamRRMNeighborReportResult(void *context, VOS_STATUS vosStatus)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(context);
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+
+    smsLog(pMac, LOG1, FL("Neighbor report result callback with status = %d\n"), vosStatus);
+    switch (pNeighborRoamInfo->neighborRoamState)
+    {
+        case eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY:
+            /* Reset the report pending variable */
+            pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_FALSE;
+            if (VOS_STATUS_SUCCESS == vosStatus)
+            {
+                /* Need to create channel list based on the neighbor AP list and transition to REPORT_SCAN state */
+                vosStatus = csrNeighborRoamCreateChanListFromNeighborReport(pMac);
+                if (VOS_STATUS_SUCCESS == vosStatus)
+                {
+                    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Channel List created from Neighbor report, Transitioning to NEIGHBOR_SCAN state\n")); 
+                }
+
+                /* We are gonna scan now. Remember the time stamp to filter out results only after this timestamp */
+                pNeighborRoamInfo->scanRequestTimeStamp = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
+                
+                /* Now ready for neighbor scan based on the channel list created */
+                /* Start Neighbor scan timer now. Multiplication by PAL_TIMER_TO_MS_UNIT is to convert ms to us which is 
+                   what palTimerStart expects */
+                status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer, 
+                                pNeighborRoamInfo->cfgParams.neighborScanPeriod * PAL_TIMER_TO_MS_UNIT, 
+                                eANI_BOOLEAN_FALSE);
+                if (eHAL_STATUS_SUCCESS != status)
+                {
+                    /* Timer start failed.. Should we ASSERT here??? */
+                    smsLog(pMac, LOGE, FL("PAL Timer start for neighbor scan timer failed, status = %d, Ignoring state transition"), status);
+                    vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
+                    pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+                    return;
+                }
+                pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;                
+                /* Neighbor scan timer started. Transition to REPORT_SCAN state */
+                CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN)
+            }
+            else
+            {
+                /* Neighbor report timeout happened in SME RRM. We can try sending more neighbor requests until we 
+                                reach the maxNeighborRetries or receiving a successful neighbor response */
+                smsLog(pMac, LOGE, FL("Neighbor report result failed after %d retries, MAX RETRIES = %d\n"), 
+                     pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum, pNeighborRoamInfo->cfgParams.maxNeighborRetries);
+                if (pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum >= 
+                        pNeighborRoamInfo->cfgParams.maxNeighborRetries)
+                {
+                    smsLog(pMac, LOGE, FL("Bailing out to CFG Channel list scan.. \n"));
+                    vosStatus = csrNeighborRoamTransitToCFGChanScan(pMac);
+                    if (VOS_STATUS_SUCCESS != vosStatus)
+                    {
+                        smsLog(pMac, LOGE, FL("Transit to CFG Channel list scan state failed with status %d \n"), vosStatus);
+                        return;
+                    }
+                    /* We transitioned to different state now. Reset the Neighbor report retry count */
+                    pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;
+                }
+                else
+                {
+                    vosStatus = csrNeighborRoamIssueNeighborRptRequest(pMac);
+                    if (VOS_STATUS_SUCCESS != vosStatus)
+                    {
+                        smsLog(pMac, LOGE, FL("Neighbor report request failed. status = %d\n"), vosStatus);
+                        return;
+                    }
+                    pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_TRUE;
+                    /* Increment the neighbor report retry count after sending the neighbor request successfully */
+                    pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum++;
+                }
+            }
+            break;
+        default:
+            smsLog(pMac, LOGE, FL("Neighbor result callback not expected in state %d, Ignoring.."), pNeighborRoamInfo->neighborRoamState);
+            break;
+    }
+    return;
+}
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamTransitToCFGChanScan
+
+    \brief  This function is called whenever there is a transition to CFG chan scan 
+            state from any state. It frees up the current channel list and allocates 
+            a new memory for the channels received from CFG item. It then starts the 
+            neighbor scan timer to perform the scan on each channel one by one
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+VOS_STATUS csrNeighborRoamTransitToCFGChanScan(tpAniSirGlobal pMac)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    eHalStatus  status  = eHAL_STATUS_SUCCESS;
+    int i = 0;
+    int numOfChannels = 0;
+    tANI_U8   channelList[MAX_BSS_IN_NEIGHBOR_RPT];
+
+    if (
+#ifdef FEATURE_WLAN_CCX
+        ((pNeighborRoamInfo->isCCXAssoc) && 
+        (pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived == eANI_BOOLEAN_FALSE)) ||
+        (pNeighborRoamInfo->isCCXAssoc == eANI_BOOLEAN_FALSE) || 
+#endif // CCX
+        pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels == 0)
+
+    {
+        smsLog(pMac, LOGW, FL("Falling back to CFG channel list"));
+
+
+        /* Free up the channel list and allocate a new memory. This is because we dont know how much 
+            was allocated last time. If we directly copy more number of bytes than allocated earlier, this might 
+            result in memory corruption */
+        if (NULL != pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
+        {
+            vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
+            pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+        }
+        // Find the right subset of the cfg list based on the current band we are on.
+        for (i = 0; i < pNeighborRoamInfo->cfgParams.channelInfo.numOfChannels; i++)
+        {
+            if (pNeighborRoamInfo->cfgParams.channelInfo.ChannelList[i])
+            {
+                // Make sure to add only if its the same band
+                if ((pNeighborRoamInfo->currAPoperationChannel <= (RF_CHAN_14+1)) &&
+                    (pNeighborRoamInfo->cfgParams.channelInfo.ChannelList[i] <= (RF_CHAN_14+1)))
+                {
+                        VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                                "%s: [INFOLOG] Adding %d to Neighbor channel list\n", __func__,
+                                pNeighborRoamInfo->cfgParams.channelInfo.ChannelList[i]);
+                        channelList[numOfChannels] = pNeighborRoamInfo->cfgParams.channelInfo.ChannelList[i];
+                        numOfChannels++;
+                }
+                if ((pNeighborRoamInfo->currAPoperationChannel >= RF_CHAN_128) &&
+                    (pNeighborRoamInfo->cfgParams.channelInfo.ChannelList[i] >= RF_CHAN_128))
+                {
+                        VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                                "%s: [INFOLOG] Adding %d to Neighbor channel list\n", __func__,
+                                pNeighborRoamInfo->cfgParams.channelInfo.ChannelList[i]);
+                        channelList[numOfChannels] = pNeighborRoamInfo->cfgParams.channelInfo.ChannelList[i];
+                        numOfChannels++;
+                }
+            }
+        }
+
+        pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels = numOfChannels;
+        pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL; 
+        if (numOfChannels)
+            pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = vos_mem_malloc(numOfChannels);
+    
+        if (NULL == pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
+        {
+            smsLog(pMac, LOGE, FL("Memory allocation for Channel list failed.. TL event ignored"));
+            return VOS_STATUS_E_RESOURCES;
+        }
+    
+        /* Since this is a legacy case, copy the channel list from CFG here */
+        vos_mem_copy(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList, 
+                                channelList, numOfChannels * sizeof(tANI_U8));
+
+        for (i = 0; i < pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels; i++)
+        {
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGE, "Channel List from CFG = %d\n", 
+                pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i]);
+        }
+    }
+
+    /* We are gonna scan now. Remember the time stamp to filter out results only after this timestamp */
+    pNeighborRoamInfo->scanRequestTimeStamp = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
+    
+    palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+    /* Start Neighbor scan timer now. Multiplication by PAL_TIMER_TO_MS_UNIT is to convert ms to us which is 
+            what palTimerStart expects */
+    status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer, 
+                    pNeighborRoamInfo->cfgParams.neighborScanPeriod * PAL_TIMER_TO_MS_UNIT, 
+                    eANI_BOOLEAN_FALSE);
+    
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        /* Timer start failed..  */
+        smsLog(pMac, LOGE, FL("Neighbor scan PAL Timer start failed, status = %d, Ignoring state transition"), status);
+        vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
+        pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+        return VOS_STATUS_E_FAILURE;
+    }
+    
+    pNeighborRoamInfo->roamChannelInfo.currentChanIndex = 0;
+    pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_TRUE;
+    
+    /* Transition to CFG_CHAN_LIST_SCAN_STATE */
+    CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN)
+
+    return VOS_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamNeighborLookupUpEvent
+
+    \brief  This function is called as soon as TL indicates that the current AP's 
+            RSSI is better than the neighbor lookup threshold. Here, we transition to 
+            CONNECTED state and reset all the scan parameters
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+VOS_STATUS  csrNeighborRoamNeighborLookupUpEvent(tpAniSirGlobal pMac)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    VOS_STATUS  vosStatus;
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering UP event neighbor lookup callback with TL. RSSI = %d,"), pNeighborRoamInfo->cfgParams.neighborLookupThreshold * (-1));
+    /* Deregister the UP event now */
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborLookupThreshold * (-1),
+                                    WLANTL_HO_THRESHOLD_UP, 
+                                    csrNeighborRoamNeighborLookupUPCallback, 
+                                    VOS_MODULE_ID_SME);
+
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+       //err msg
+       smsLog(pMac, LOGW, FL(" Couldn't Deregister csrNeighborRoamNeighborLookupCallback UP event from TL: Status = %d\n"), vosStatus);
+    }
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event neighbor lookup callback with TL. RSSI = %d,"), pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
+    /* Deregister the UP event now */
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
+                                    WLANTL_HO_THRESHOLD_DOWN, 
+                                    csrNeighborRoamNeighborLookupDOWNCallback, 
+                                    VOS_MODULE_ID_SME);
+
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+       //err msg
+       smsLog(pMac, LOGW, FL(" Couldn't Deregister csrNeighborRoamNeighborLookupCallback UP event from TL: Status = %d\n"), vosStatus);
+    }
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event reassoc callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1));
+    /* Deregister reassoc callback. */
+    vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
+                                                        WLANTL_HO_THRESHOLD_DOWN, 
+                                                        csrNeighborRoamReassocIndCallback,
+                                                        VOS_MODULE_ID_SME);
+                        
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+        //err msg
+        smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
+    }
+
+
+    /* RSSI got better than the CFG neighbor lookup threshold. Reset the threshold to older value and set the increment multiplier to 0 */
+    pNeighborRoamInfo->currentLookupIncrementMultiplier = 0;
+
+    pNeighborRoamInfo->currentNeighborLookupThreshold = pNeighborRoamInfo->cfgParams.neighborLookupThreshold;
+    
+    /* Reset all the neighbor roam info control variables. Free all the allocated memory. It is like we are just associated now */
+    csrNeighborRoamResetConnectedStateControlInfo(pMac);
+
+    /* Recheck whether the below check is needed. */
+    if (pNeighborRoamInfo->neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_CONNECTED)
+        CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CONNECTED)
+    
+    NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering DOWN event neighbor lookup callback with TL. RSSI = %d,"), pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
+    /* Register Neighbor Lookup threshold callback with TL for DOWN event now */
+    vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
+                                    WLANTL_HO_THRESHOLD_DOWN, 
+                                    csrNeighborRoamNeighborLookupDOWNCallback, 
+                                    VOS_MODULE_ID_SME, pMac);
+    if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+    {
+       //err msg
+       smsLog(pMac, LOGW, FL(" Couldn't register csrNeighborRoamNeighborLookupCallback DOWN event with TL: Status = %d\n"), vosStatus);
+    }
+
+
+    return vosStatus;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamNeighborLookupDownEvent
+
+    \brief  This function is called as soon as TL indicates that the current AP's 
+            RSSI falls below the current eighbor lookup threshold. Here, we transition to 
+            REPORT_QUERY for 11r association and CFG_CHAN_LIST_SCAN state if the assoc is 
+            a non-11R association.
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+VOS_STATUS  csrNeighborRoamNeighborLookupDownEvent(tpAniSirGlobal pMac)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    VOS_STATUS  vosStatus = VOS_STATUS_SUCCESS;
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+
+    switch (pNeighborRoamInfo->neighborRoamState)
+    {
+        case eCSR_NEIGHBOR_ROAM_STATE_CONNECTED:
+            
+            NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event neighbor lookup callback with TL. RSSI = %d,"), 
+                                                            pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
+            /* De-register Neighbor Lookup threshold callback with TL */
+            vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
+                                            WLANTL_HO_THRESHOLD_DOWN, 
+                                            csrNeighborRoamNeighborLookupDOWNCallback, 
+                                            VOS_MODULE_ID_SME);
+            
+            if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+            {
+               //err msg
+               smsLog(pMac, LOGW, FL(" Couldn't Deregister csrNeighborRoamNeighborLookupCallback DOWN event from TL: Status = %d\n"), status);
+            }
+            
+           
+#if defined WLAN_FEATURE_VOWIFI_11R && defined WLAN_FEATURE_VOWIFI
+            if ((pNeighborRoamInfo->is11rAssoc) && (pMac->rrm.rrmSmeContext.rrmConfig.rrmEnabled))
+            {
+               
+                NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("11R Association:Neighbor Lookup Down event received in CONNECTED state"));
+                vosStatus = csrNeighborRoamIssueNeighborRptRequest(pMac);
+                if (VOS_STATUS_SUCCESS != vosStatus)
+                {
+                    smsLog(pMac, LOGE, FL("Neighbor report request failed. status = %d\n"), vosStatus);
+                    return vosStatus;
+                }
+                /* Increment the neighbor report retry count after sending the neighbor request successfully */
+                pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum++;
+                pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_TRUE;
+                CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY)
+            }
+            else
+#endif      
+            {
+                NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Non 11R or CCX Association:Neighbor Lookup Down event received in CONNECTED state"));
+
+                vosStatus = csrNeighborRoamTransitToCFGChanScan(pMac);
+                if (VOS_STATUS_SUCCESS != vosStatus)
+                {
+                    return vosStatus;
+                }
+            }
+            NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering UP event neighbor lookup callback with TL. RSSI = %d,"), pNeighborRoamInfo->cfgParams.neighborLookupThreshold * (-1));
+            /* Register Neighbor Lookup threshold callback with TL for UP event now */
+            vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborLookupThreshold * (-1),
+                                            WLANTL_HO_THRESHOLD_UP, 
+                                            csrNeighborRoamNeighborLookupUPCallback, 
+                                            VOS_MODULE_ID_SME, pMac);
+            if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+            {
+               //err msg
+               smsLog(pMac, LOGW, FL(" Couldn't register csrNeighborRoamNeighborLookupCallback UP event with TL: Status = %d\n"), status);
+            }
+            break;
+        default:
+            smsLog(pMac, LOGE, FL("DOWN event received in invalid state %d..Ignoring..."), pNeighborRoamInfo->neighborRoamState);
+            break;
+            
+    }
+    return vosStatus;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamNeighborLookupUPCallback
+
+    \brief  This function is registered with TL to indicate whenever the RSSI 
+            gets better than the neighborLookup RSSI Threshold
+
+    \param  pAdapter - VOS Context
+            trafficStatus - UP/DOWN indication from TL
+            pUserCtxt - Parameter for callback registered during callback registration. Should be pMac
+
+    \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+VOS_STATUS csrNeighborRoamNeighborLookupUPCallback (v_PVOID_t pAdapter, v_U8_t rssiNotification,
+                                                                               v_PVOID_t pUserCtxt)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pUserCtxt );
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    VOS_STATUS  vosStatus = eHAL_STATUS_SUCCESS;
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Neighbor Lookup UP indication callback called with notification %d"), rssiNotification);
+
+    if(!csrIsConnStateConnectedInfra(pMac, pNeighborRoamInfo->csrSessionId))
+    {
+       smsLog(pMac, LOGW, "Ignoring the indication as we are not connected\n");
+       return VOS_STATUS_SUCCESS;
+    }
+
+    VOS_ASSERT(WLANTL_HO_THRESHOLD_UP == rssiNotification);
+    vosStatus = csrNeighborRoamNeighborLookupUpEvent(pMac);
+    return vosStatus;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamNeighborLookupDOWNCallback
+
+    \brief  This function is registered with TL to indicate whenever the RSSI 
+            falls below the current neighborLookup RSSI Threshold
+
+    \param  pAdapter - VOS Context
+            trafficStatus - UP/DOWN indication from TL
+            pUserCtxt - Parameter for callback registered during callback registration. Should be pMac
+
+    \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+VOS_STATUS csrNeighborRoamNeighborLookupDOWNCallback (v_PVOID_t pAdapter, v_U8_t rssiNotification,
+                                                                               v_PVOID_t pUserCtxt)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( pUserCtxt );
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    VOS_STATUS  vosStatus = eHAL_STATUS_SUCCESS;
+
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Neighbor Lookup DOWN indication callback called with notification %d"), rssiNotification);
+
+    if(!csrIsConnStateConnectedInfra(pMac, pNeighborRoamInfo->csrSessionId))
+    {
+       smsLog(pMac, LOGW, "Ignoring the indication as we are not connected\n");
+       return VOS_STATUS_SUCCESS;
+    }
+
+    VOS_ASSERT(WLANTL_HO_THRESHOLD_DOWN == rssiNotification);
+    vosStatus = csrNeighborRoamNeighborLookupDownEvent(pMac);
+
+    return vosStatus;
+}
+
+#ifdef RSSI_HACK
+extern int dumpCmdRSSI;
+#endif
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamIndicateDisconnect
+
+    \brief  This function is called by CSR as soon as the station disconnects from 
+            the AP. This function does the necessary cleanup of neighbor roam data 
+            structures. Neighbor roam state transitions to INIT state whenever this 
+            function is called except if the current state is REASSOCIATING
+
+    \param  pMac - The handle returned by macOpen.
+            sessionId - CSR session id that got disconnected
+
+    \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+eHalStatus csrNeighborRoamIndicateDisconnect(tpAniSirGlobal pMac, tANI_U8 sessionId)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    smsLog(pMac, LOGE, FL("Disconnect indication received with session id %d in state %d"), sessionId, pNeighborRoamInfo->neighborRoamState);
+ 
+#ifdef FEATURE_WLAN_CCX
+    {
+      tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId);
+      if (pSession->connectedProfile.isCCXAssoc)
+      {
+          vos_mem_copy(&pSession->prevApSSID, &pSession->connectedProfile.SSID, sizeof(tSirMacSSid));
+          vos_mem_copy(pSession->prevApBssid, pSession->connectedProfile.bssid, sizeof(tSirMacAddr));
+          pSession->prevOpChannel = pSession->connectedProfile.operationChannel;
+          pSession->isPrevApInfoValid = TRUE;
+          pSession->roamTS1 = vos_timer_get_system_time();
+
+      }
+    }
+#endif
+   
+#ifdef RSSI_HACK
+    dumpCmdRSSI = -40;
+#endif
+    switch (pNeighborRoamInfo->neighborRoamState)
+    {
+        case eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING:
+            // Stop scan and neighbor refresh timers.
+            // These are indeed not required when we are in reassociating
+            // state.
+            palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+            palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
+            break;
+
+        case eCSR_NEIGHBOR_ROAM_STATE_INIT:
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Ignoring disconnect event in INIT state"));
+            csrNeighborRoamResetInitStateControlInfo(pMac);
+            break; 
+
+        default:
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Received disconnect event in state %d"), pNeighborRoamInfo->neighborRoamState);
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Transitioning to INIT state"));
+            CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
+    }
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamIndicateConnect
+
+    \brief  This function is called by CSR as soon as the station connects to an AP.
+            This initializes all the necessary data structures related to the 
+            associated AP and transitions the state to CONNECTED state
+
+    \param  pMac - The handle returned by macOpen.
+            sessionId - CSR session id that got connected
+            vosStatus - connect status SUCCESS/FAILURE
+
+    \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+eHalStatus csrNeighborRoamIndicateConnect(tpAniSirGlobal pMac, tANI_U8 sessionId, VOS_STATUS vosStatus)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+    int  init_ft_flag = FALSE;
+#endif
+
+    smsLog(pMac, LOGE, FL("Connect indication received with session id %d in state %d"), sessionId, pNeighborRoamInfo->neighborRoamState);
+
+    switch (pNeighborRoamInfo->neighborRoamState)
+    {
+        case eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING:
+            if (VOS_STATUS_SUCCESS != vosStatus)
+            {
+                /* Just transition the state to INIT state. Rest of the clean up happens when we get next connect indication */
+                CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
+                break;
+            }
+            /* Fall through if the status is SUCCESS */
+        case eCSR_NEIGHBOR_ROAM_STATE_INIT:
+            /* Reset all the data structures here */ 
+            csrNeighborRoamResetInitStateControlInfo(pMac);
+
+            CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CONNECTED)
+
+            pNeighborRoamInfo->csrSessionId = sessionId;
+            vos_mem_copy(pNeighborRoamInfo->currAPbssid, 
+                        pMac->roam.roamSession[sessionId].connectedProfile.bssid, sizeof(tCsrBssid));
+            pNeighborRoamInfo->currAPoperationChannel = pMac->roam.roamSession[sessionId].connectedProfile.operationChannel;
+            pNeighborRoamInfo->neighborScanTimerInfo.pMac = pMac;
+            pNeighborRoamInfo->neighborScanTimerInfo.sessionId = sessionId;
+            
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+            /* Now we can clear the preauthDone that was saved as we are connected afresh */
+            csrNeighborRoamFreeRoamableBSSList(pMac, &pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthDoneList);
+#endif
+            
+#ifdef WLAN_FEATURE_VOWIFI_11R
+            // Based on the auth scheme tell if we are 11r
+            if ( csrIsAuthType11r( pMac->roam.roamSession[sessionId].connectedProfile.AuthType ) )
+            {
+                if (pMac->roam.configParam.isFastTransitionEnabled)
+                    init_ft_flag = TRUE;
+                pNeighborRoamInfo->is11rAssoc = eANI_BOOLEAN_TRUE;
+            }
+            else
+                pNeighborRoamInfo->is11rAssoc = eANI_BOOLEAN_FALSE;
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("11rAssoc is = %d"), pNeighborRoamInfo->is11rAssoc);
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+            // Based on the auth scheme tell if we are 11r
+            if (pMac->roam.roamSession[sessionId].connectedProfile.isCCXAssoc)
+            {
+                if (pMac->roam.configParam.isFastTransitionEnabled)
+                    init_ft_flag = TRUE;
+                pNeighborRoamInfo->isCCXAssoc = eANI_BOOLEAN_TRUE;
+            }
+            else
+                pNeighborRoamInfo->isCCXAssoc = eANI_BOOLEAN_FALSE;
+            NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("isCCXAssoc is = %d"), pNeighborRoamInfo->isCCXAssoc);
+            VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, 
+                        "ccx=%d ft=%d\n", pNeighborRoamInfo->isCCXAssoc, init_ft_flag);
+                            
+#endif
+
+#if  defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX)
+            if ( init_ft_flag == TRUE )
+            {
+                /* Initialize all the data structures needed for the 11r FT Preauth */
+                pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimerInfo.pMac = pMac;
+                pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimerInfo.sessionId = sessionId;
+                pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;
+                csrNeighborRoamPurgePreauthFailedList(pMac);
+
+                NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering neighbor lookup DOWN event with TL, RSSI = %d"), pNeighborRoamInfo->currentNeighborLookupThreshold);
+                /* Register Neighbor Lookup threshold callback with TL for DOWN event only */
+                status = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
+                                            WLANTL_HO_THRESHOLD_DOWN, 
+                                            csrNeighborRoamNeighborLookupDOWNCallback, 
+                                            VOS_MODULE_ID_SME, pMac);
+            
+                if(!VOS_IS_STATUS_SUCCESS( status))
+                {
+                   //err msg
+                   smsLog(pMac, LOGW, FL(" Couldn't register csrNeighborRoamNeighborLookupDOWNCallback with TL: Status = %d\n"), status);
+                }
+            }
+#endif
+
+            
+            break;
+        default:
+            smsLog(pMac, LOGE, FL("Connect event received in invalid state %d..Ignoring..."), pNeighborRoamInfo->neighborRoamState);
+            break;
+    }
+    return status;
+}
+
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamPreAuthResponseWaitTimerHandler
+
+    \brief  If this function is invoked, that means the preauthentication response 
+            is timed out from the PE. Preauth rsp handler is called with status as 
+            TIMEOUT
+
+    \param  context - CSR Timer info which holds pMac and session ID
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamPreAuthResponseWaitTimerHandler(void *context)
+{
+    tCsrTimerInfo *pTimerInfo = (tCsrTimerInfo *)context;
+    tpAniSirGlobal pMac = (tpAniSirGlobal)pTimerInfo->pMac;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    pNeighborRoamInfo->FTRoamInfo.preauthRspPending = eANI_BOOLEAN_FALSE;
+
+    csrNeighborRoamPreauthRspHandler(pMac, VOS_STATUS_E_TIMEOUT);
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamPurgePreauthFailedList
+
+    \brief  This function purges all the MAC addresses in the pre-auth fail list
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamPurgePreauthFailedList(tpAniSirGlobal pMac)
+{
+    tANI_U8 i;
+
+    for (i = 0; i < pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthFailList.numMACAddress; i++)
+    {
+        vos_mem_zero(pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthFailList.macAddress[i], sizeof(tSirMacAddr));
+    }
+    pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthFailList.numMACAddress = 0;
+
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamInit11rAssocInfo
+
+    \brief  This function initializes 11r related neighbor roam data structures
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+eHalStatus csrNeighborRoamInit11rAssocInfo(tpAniSirGlobal pMac)
+{
+    eHalStatus  status;
+    tpCsr11rAssocNeighborInfo   pFTRoamInfo = &pMac->roam.neighborRoamInfo.FTRoamInfo;
+
+    pMac->roam.neighborRoamInfo.is11rAssoc = eANI_BOOLEAN_FALSE;
+    pMac->roam.neighborRoamInfo.cfgParams.maxNeighborRetries = pMac->roam.configParam.neighborRoamConfig.nMaxNeighborRetries;
+    pFTRoamInfo->neighborReportTimeout = CSR_NEIGHBOR_ROAM_REPORT_QUERY_TIMEOUT;
+    pFTRoamInfo->PEPreauthRespTimeout = CSR_NEIGHBOR_ROAM_PREAUTH_RSP_WAIT_MULTIPLIER * pMac->roam.neighborRoamInfo.cfgParams.neighborScanPeriod;
+    pFTRoamInfo->neighborRptPending = eANI_BOOLEAN_FALSE;
+    pFTRoamInfo->preauthRspPending = eANI_BOOLEAN_FALSE;
+    
+    pFTRoamInfo->preAuthRspWaitTimerInfo.pMac = pMac;
+    pFTRoamInfo->preAuthRspWaitTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+    status = palTimerAlloc(pMac->hHdd, &pFTRoamInfo->preAuthRspWaitTimer, 
+                    csrNeighborRoamPreAuthResponseWaitTimerHandler, (void *)&pFTRoamInfo->preAuthRspWaitTimerInfo);
+
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("Response wait Timer allocation failed"));
+        return eHAL_STATUS_RESOURCES;
+    }
+    
+    pMac->roam.neighborRoamInfo.FTRoamInfo.currentNeighborRptRetryNum = 0;
+    pMac->roam.neighborRoamInfo.FTRoamInfo.numBssFromNeighborReport = 0;
+    vos_mem_zero(pMac->roam.neighborRoamInfo.FTRoamInfo.neighboReportBssInfo, 
+                            sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
+
+    
+    status = csrLLOpen(pMac->hHdd, &pFTRoamInfo->preAuthDoneList);
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("LL Open of preauth done AP List failed"));
+        palTimerFree(pMac->hHdd, pFTRoamInfo->preAuthRspWaitTimer);
+        return eHAL_STATUS_RESOURCES;
+    }
+    return status;
+}
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamInit
+
+    \brief  This function initializes neighbor roam data structures
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
+
+---------------------------------------------------------------------------*/
+eHalStatus csrNeighborRoamInit(tpAniSirGlobal pMac)
+{
+    eHalStatus status;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    pNeighborRoamInfo->neighborRoamState       =   eCSR_NEIGHBOR_ROAM_STATE_CLOSED;
+    pNeighborRoamInfo->prevNeighborRoamState   =   eCSR_NEIGHBOR_ROAM_STATE_CLOSED;
+    pNeighborRoamInfo->csrSessionId            =   CSR_SESSION_ID_INVALID;
+    pNeighborRoamInfo->cfgParams.maxChannelScanTime = pMac->roam.configParam.neighborRoamConfig.nNeighborScanMaxChanTime;
+    pNeighborRoamInfo->cfgParams.minChannelScanTime = pMac->roam.configParam.neighborRoamConfig.nNeighborScanMinChanTime;
+    pNeighborRoamInfo->cfgParams.maxNeighborRetries = 0;
+    pNeighborRoamInfo->cfgParams.neighborLookupThreshold = pMac->roam.configParam.neighborRoamConfig.nNeighborLookupRssiThreshold;
+    pNeighborRoamInfo->cfgParams.neighborReassocThreshold = pMac->roam.configParam.neighborRoamConfig.nNeighborReassocRssiThreshold;
+    pNeighborRoamInfo->cfgParams.neighborScanPeriod = pMac->roam.configParam.neighborRoamConfig.nNeighborScanTimerPeriod;
+    pNeighborRoamInfo->cfgParams.neighborResultsRefreshPeriod = pMac->roam.configParam.neighborRoamConfig.nNeighborResultsRefreshPeriod;
+    
+    pNeighborRoamInfo->cfgParams.channelInfo.numOfChannels   =   
+                        pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels;
+
+    pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = 
+                vos_mem_malloc(pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels);
+
+    if (NULL == pNeighborRoamInfo->cfgParams.channelInfo.ChannelList)
+    {
+        smsLog(pMac, LOGE, FL("Memory Allocation for CFG Channel List failed"));
+        return eHAL_STATUS_RESOURCES;
+    }
+
+    /* Update the roam global structure from CFG */
+    palCopyMemory(pMac->hHdd, pNeighborRoamInfo->cfgParams.channelInfo.ChannelList, 
+                        pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.channelList,
+                        pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels);
+
+    vos_mem_set(pNeighborRoamInfo->currAPbssid, sizeof(tCsrBssid), 0);
+    pNeighborRoamInfo->currentNeighborLookupThreshold = pMac->roam.neighborRoamInfo.cfgParams.neighborLookupThreshold;
+    pNeighborRoamInfo->currentLookupIncrementMultiplier = 0;
+    pNeighborRoamInfo->scanRspPending = eANI_BOOLEAN_FALSE;
+
+    pNeighborRoamInfo->neighborScanTimerInfo.pMac = pMac;
+    pNeighborRoamInfo->neighborScanTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+    status = palTimerAlloc(pMac->hHdd, &pNeighborRoamInfo->neighborScanTimer, 
+                    csrNeighborRoamNeighborScanTimerCallback, (void *)&pNeighborRoamInfo->neighborScanTimerInfo);
+
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("Response wait Timer allocation failed"));
+        vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
+        pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
+        return eHAL_STATUS_RESOURCES;
+    }
+
+    status = palTimerAlloc(pMac->hHdd, &pNeighborRoamInfo->neighborResultsRefreshTimer, 
+                    csrNeighborRoamResultsRefreshTimerCallback, (void *)&pNeighborRoamInfo->neighborScanTimerInfo);
+
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("Response wait Timer allocation failed"));
+        smsLog(pMac, LOGE, FL("LL Open of roamable AP List failed"));
+        vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
+        pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
+        palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+        return eHAL_STATUS_RESOURCES;
+    }
+
+    status = csrLLOpen(pMac->hHdd, &pNeighborRoamInfo->roamableAPList);
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("LL Open of roamable AP List failed"));
+        vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
+        pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
+        palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+        palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
+        return eHAL_STATUS_RESOURCES;
+    }
+
+    pNeighborRoamInfo->roamChannelInfo.currentChanIndex = CSR_NEIGHBOR_ROAM_INVALID_CHANNEL_INDEX;
+    pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels = 0;
+    pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+    pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_FALSE;
+    pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived = eANI_BOOLEAN_FALSE;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    status = csrNeighborRoamInit11rAssocInfo(pMac);
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("LL Open of roamable AP List failed"));
+        vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
+        pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
+        palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+        palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);        
+        csrLLClose(&pNeighborRoamInfo->roamableAPList);
+        return eHAL_STATUS_RESOURCES;
+    }
+#endif
+    /* Initialize this with the current tick count */
+    pNeighborRoamInfo->scanRequestTimeStamp = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
+
+    CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
+    
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamClose
+
+    \brief  This function closes/frees all the neighbor roam data structures
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamClose(tpAniSirGlobal pMac)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+
+    if (eCSR_NEIGHBOR_ROAM_STATE_CLOSED == pNeighborRoamInfo->neighborRoamState)
+    {
+        smsLog(pMac, LOGE, FL("Neighbor Roam Algorithm Already Closed\n"));
+        return;
+    }
+
+    if (pNeighborRoamInfo->cfgParams.channelInfo.ChannelList)
+        vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
+   
+    pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
+    
+    pNeighborRoamInfo->neighborScanTimerInfo.pMac = NULL;
+    pNeighborRoamInfo->neighborScanTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+    palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
+    palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
+
+    /* Should free up the nodes in the list before closing the double Linked list */
+    csrNeighborRoamFreeRoamableBSSList(pMac, &pNeighborRoamInfo->roamableAPList);
+    csrLLClose(&pNeighborRoamInfo->roamableAPList);
+    
+    if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
+    {
+        vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
+    }
+
+    pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+    pNeighborRoamInfo->roamChannelInfo.currentChanIndex = CSR_NEIGHBOR_ROAM_INVALID_CHANNEL_INDEX;
+    pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels = 0;
+    pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
+    pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_FALSE;    
+    pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived = eANI_BOOLEAN_FALSE;
+
+    /* Free the profile.. */ 
+    csrReleaseProfile(pMac, &pNeighborRoamInfo->csrNeighborRoamProfile);
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    pMac->roam.neighborRoamInfo.FTRoamInfo.currentNeighborRptRetryNum = 0;
+    palTimerFree(pMac->hHdd, pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthRspWaitTimer);
+    pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthRspWaitTimerInfo.pMac = NULL;
+    pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthRspWaitTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
+    pMac->roam.neighborRoamInfo.FTRoamInfo.numBssFromNeighborReport = 0;
+    vos_mem_zero(pMac->roam.neighborRoamInfo.FTRoamInfo.neighboReportBssInfo, 
+                            sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
+    csrNeighborRoamFreeRoamableBSSList(pMac, &pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthDoneList);
+    csrLLClose(&pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthDoneList);
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+
+    CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CLOSED)
+    
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamRequestHandoff
+
+    \brief  This function triggers actual switching from one AP to the new AP.
+            It issues disassociate with reason code as Handoff and CSR as a part of 
+            handling disassoc rsp, issues reassociate to the new AP
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamRequestHandoff(tpAniSirGlobal pMac)
+{
+
+    tCsrRoamInfo roamInfo;
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tANI_U32 sessionId = pNeighborRoamInfo->csrSessionId;
+    tCsrNeighborRoamBSSInfo     handoffNode;
+    extern void csrRoamRoamingStateDisassocRspProcessor( tpAniSirGlobal pMac, tSirSmeDisassocRsp *pSmeDisassocRsp );
+    tANI_U32 roamId = 0;
+
+    if (pMac->roam.neighborRoamInfo.neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE) 
+    {
+        smsLog(pMac, LOGE, FL("Roam requested when Neighbor roam is in %d state"), 
+            pMac->roam.neighborRoamInfo.neighborRoamState);
+        return;
+    }
+
+    vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
+    csrRoamCallCallback(pMac, pNeighborRoamInfo->csrSessionId, &roamInfo, roamId, eCSR_ROAM_FT_START, 
+                eSIR_SME_SUCCESS);
+
+    vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
+    CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING)
+    
+    csrNeighborRoamGetHandoffAPInfo(pMac, &handoffNode);
+    smsLog(pMac, LOGE, FL("HANDOFF CANDIDATE BSSID %02x:%02x:%02x:%02x:%02x:%02x"),
+                                                handoffNode.pBssDescription->bssId[0], 
+                                                handoffNode.pBssDescription->bssId[1], 
+                                                handoffNode.pBssDescription->bssId[2], 
+                                                handoffNode.pBssDescription->bssId[3], 
+                                                handoffNode.pBssDescription->bssId[4], 
+                                                handoffNode.pBssDescription->bssId[5]);
+   
+    /* Free the profile.. Just to make sure we dont leak memory here */ 
+    csrReleaseProfile(pMac, &pNeighborRoamInfo->csrNeighborRoamProfile);
+    /* Create the Handoff AP profile. Copy the currently connected profile and update only the BSSID and channel number
+        This should happen before issuing disconnect */
+    csrRoamCopyConnectedProfile(pMac, pNeighborRoamInfo->csrSessionId, &pNeighborRoamInfo->csrNeighborRoamProfile);
+    vos_mem_copy(pNeighborRoamInfo->csrNeighborRoamProfile.BSSIDs.bssid, handoffNode.pBssDescription->bssId, sizeof(tSirMacAddr));
+    pNeighborRoamInfo->csrNeighborRoamProfile.ChannelInfo.ChannelList[0] = handoffNode.pBssDescription->channelId;
+    
+    NEIGHBOR_ROAM_DEBUG(pMac, LOGW, " csrRoamHandoffRequested: disassociating with current AP\n");
+
+    if(!HAL_STATUS_SUCCESS(csrRoamIssueDisassociateCmd(pMac, sessionId, eCSR_DISCONNECT_REASON_HANDOFF)))
+    {
+        smsLog(pMac, LOGW, "csrRoamHandoffRequested:  fail to issue disassociate\n");
+        return;
+    }                       
+
+    //notify HDD for handoff, providing the BSSID too
+    roamInfo.reasonCode = eCsrRoamReasonBetterAP;
+
+    vos_mem_copy(roamInfo.bssid, 
+                 handoffNode.pBssDescription->bssId, 
+                 sizeof( tCsrBssid ));
+
+    csrRoamCallCallback(pMac, sessionId, &roamInfo, 0, eCSR_ROAM_ROAMING_START, eCSR_ROAM_RESULT_NONE);
+
+
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamIsHandoffInProgress
+
+    \brief  This function returns whether handoff is in progress or not based on 
+            the current neighbor roam state
+
+    \param  pMac - The handle returned by macOpen.
+            is11rReassoc - Return whether reassoc is of type 802.11r reassoc
+
+    \return eANI_BOOLEAN_TRUE if reassoc in progress, eANI_BOOLEAN_FALSE otherwise
+
+---------------------------------------------------------------------------*/
+tANI_BOOLEAN csrNeighborRoamIsHandoffInProgress(tpAniSirGlobal pMac)
+{
+    if (eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING == pMac->roam.neighborRoamInfo.neighborRoamState)
+        return eANI_BOOLEAN_TRUE;
+
+    return eANI_BOOLEAN_FALSE;
+}
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamIs11rAssoc
+
+    \brief  This function returns whether the current association is a 11r assoc or not
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return eANI_BOOLEAN_TRUE if current assoc is 11r, eANI_BOOLEAN_FALSE otherwise
+
+---------------------------------------------------------------------------*/
+tANI_BOOLEAN csrNeighborRoamIs11rAssoc(tpAniSirGlobal pMac)
+{
+    return pMac->roam.neighborRoamInfo.is11rAssoc;
+}
+#endif /* WLAN_FEATURE_VOWIFI_11R */
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn csrNeighborRoamGetHandoffAPInfo
+
+    \brief  This function returns the best possible AP for handoff. For 11R case, it 
+            returns the 1st entry from pre-auth done list. For non-11r case, it returns 
+            the 1st entry from roamable AP list
+
+    \param  pMac - The handle returned by macOpen.
+            pHandoffNode - AP node that is the handoff candidate returned
+
+    \return VOID
+
+---------------------------------------------------------------------------*/
+void csrNeighborRoamGetHandoffAPInfo(tpAniSirGlobal pMac, tpCsrNeighborRoamBSSInfo pHandoffNode)
+{
+    tpCsrNeighborRoamControlInfo    pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
+    tpCsrNeighborRoamBSSInfo        pBssNode;
+    
+    VOS_ASSERT(NULL != pHandoffNode); 
+        
+#ifdef WLAN_FEATURE_VOWIFI_11R
+    if (pNeighborRoamInfo->is11rAssoc)
+    {
+        /* Always the BSS info in the head is the handoff candidate */
+        pBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->FTRoamInfo.preAuthDoneList, NULL);
+        NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Number of Handoff candidates = %d"), csrLLCount(&pNeighborRoamInfo->FTRoamInfo.preAuthDoneList));
+    }
+    else
+#endif
+#ifdef FEATURE_WLAN_CCX
+    if (pNeighborRoamInfo->isCCXAssoc)
+    {
+        /* Always the BSS info in the head is the handoff candidate */
+        pBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->FTRoamInfo.preAuthDoneList, NULL);
+        NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Number of Handoff candidates = %d"), csrLLCount(&pNeighborRoamInfo->FTRoamInfo.preAuthDoneList));
+    }
+    else
+#endif
+    {
+        pBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->roamableAPList, NULL);
+        NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Number of Handoff candidates = %d"), csrLLCount(&pNeighborRoamInfo->roamableAPList));
+    }
+    vos_mem_copy(pHandoffNode, pBssNode, sizeof(tCsrNeighborRoamBSSInfo));
+
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+    \brief  This function returns TRUE if preauth is completed 
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return boolean
+
+---------------------------------------------------------------------------*/
+tANI_BOOLEAN csrNeighborRoamStatePreauthDone(tpAniSirGlobal pMac)
+{
+    return (pMac->roam.neighborRoamInfo.neighborRoamState == 
+               eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE);
+}
+
+/* ---------------------------------------------------------------------------
+    \brief  In the event that we are associated with AP1 and we have
+    completed pre auth with AP2. Then we receive a deauth/disassoc from
+    AP1. 
+    At this point neighbor roam is in pre auth done state, pre auth timer
+    is running. We now handle this case by stopping timer and clearing
+    the pre-auth state. We basically clear up and just go to disconnected
+    state. 
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return boolean
+---------------------------------------------------------------------------*/
+void csrNeighborRoamTranistionPreauthDoneToDisconnected(tpAniSirGlobal pMac)
+{
+    if (pMac->roam.neighborRoamInfo.neighborRoamState != 
+               eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE) return;
+
+    // Stop timer
+    palTimerStop(pMac->hHdd, pMac->ft.ftSmeContext.preAuthReassocIntvlTimer);
+
+    // Transition to init state
+    CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
+}
+
+#endif /* WLAN_FEATURE_NEIGHBOR_ROAMING */
diff --git a/CORE/SME/src/csr/csrUtil.c b/CORE/SME/src/csr/csrUtil.c
new file mode 100644
index 0000000..5910069
--- /dev/null
+++ b/CORE/SME/src/csr/csrUtil.c
@@ -0,0 +1,5846 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/** ------------------------------------------------------------------------- *
+    ------------------------------------------------------------------------- *
+
+
+    \file csrUtil.c
+
+    Implementation supporting routines for CSR.
+
+
+    Copyright (C) 2006 Airgo Networks, Incorporated
+   ========================================================================== */
+
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halInternal.h" //Check if the below include of aniGobal.h is sufficient for Volans too.
+#endif
+
+#ifdef FEATURE_WLAN_INTEGRATED_SOC
+#include "aniGlobal.h"
+#endif
+
+#include "palApi.h"
+#include "csrSupport.h"
+#include "csrInsideApi.h"
+#include "smsDebug.h"
+#include "smeQosInternal.h"
+#ifdef FEATURE_WLAN_CCX
+#include "vos_utils.h"
+#include "csrCcx.h"
+#endif /* FEATURE_WLAN_CCX */
+
+tANI_U8 csrWpaOui[][ CSR_WPA_OUI_SIZE ] = {
+    { 0x00, 0x50, 0xf2, 0x00 },
+    { 0x00, 0x50, 0xf2, 0x01 },
+    { 0x00, 0x50, 0xf2, 0x02 },
+    { 0x00, 0x50, 0xf2, 0x03 },
+    { 0x00, 0x50, 0xf2, 0x04 },
+    { 0x00, 0x50, 0xf2, 0x05 },
+#ifdef FEATURE_WLAN_CCX
+    { 0x00, 0x40, 0x96, 0x00 }, // CCKM
+#endif /* FEATURE_WLAN_CCX */
+};
+
+tANI_U8 csrRSNOui[][ CSR_RSN_OUI_SIZE ] = {
+    { 0x00, 0x0F, 0xAC, 0x00 }, // group cipher
+    { 0x00, 0x0F, 0xAC, 0x01 }, // WEP-40 or RSN
+    { 0x00, 0x0F, 0xAC, 0x02 }, // TKIP or RSN-PSK
+    { 0x00, 0x0F, 0xAC, 0x03 }, // Reserved
+    { 0x00, 0x0F, 0xAC, 0x04 }, // AES-CCMP
+    { 0x00, 0x0F, 0xAC, 0x05 }, // WEP-104
+#ifdef WLAN_FEATURE_11W
+    { 0x00, 0x0F, 0xAC, 0x06 },  // BIP(encryption type) or (RSN-PSK-SHA256(authentication type)
+#endif
+#ifdef FEATURE_WLAN_CCX
+    { 0x00, 0x40, 0x96, 0x00 } // CCKM
+#endif /* FEATURE_WLAN_CCX */
+    
+};
+
+#ifdef FEATURE_WLAN_WAPI
+tANI_U8 csrWapiOui[][ CSR_WAPI_OUI_SIZE ] = {
+    { 0x00, 0x14, 0x72, 0x00 }, // Reserved
+    { 0x00, 0x14, 0x72, 0x01 }, // WAI certificate or SMS4
+    { 0x00, 0x14, 0x72, 0x02 } // WAI PSK
+};
+#endif /* FEATURE_WLAN_WAPI */
+tANI_U8 csrWmeInfoOui[ CSR_WME_OUI_SIZE ] = { 0x00, 0x50, 0xf2, 0x02 };
+tANI_U8 csrWmeParmOui[ CSR_WME_OUI_SIZE ] = { 0x00, 0x50, 0xf2, 0x02 };
+
+static tCsrIELenInfo gCsrIELengthTable[] = {
+/* 000 */ { SIR_MAC_SSID_EID_MIN, SIR_MAC_SSID_EID_MAX },
+/* 001 */ { SIR_MAC_RATESET_EID_MIN, SIR_MAC_RATESET_EID_MAX },
+/* 002 */ { SIR_MAC_FH_PARAM_SET_EID_MIN, SIR_MAC_FH_PARAM_SET_EID_MAX },
+/* 003 */ { SIR_MAC_DS_PARAM_SET_EID_MIN, SIR_MAC_DS_PARAM_SET_EID_MAX },
+/* 004 */ { SIR_MAC_CF_PARAM_SET_EID_MIN, SIR_MAC_CF_PARAM_SET_EID_MAX },
+/* 005 */ { SIR_MAC_TIM_EID_MIN, SIR_MAC_TIM_EID_MAX },
+/* 006 */ { SIR_MAC_IBSS_PARAM_SET_EID_MIN, SIR_MAC_IBSS_PARAM_SET_EID_MAX },
+/* 007 */ { SIR_MAC_COUNTRY_EID_MIN, SIR_MAC_COUNTRY_EID_MAX },
+/* 008 */ { SIR_MAC_FH_PARAMS_EID_MIN, SIR_MAC_FH_PARAMS_EID_MAX },
+/* 009 */ { SIR_MAC_FH_PATTERN_EID_MIN, SIR_MAC_FH_PATTERN_EID_MAX },
+/* 010 */ { SIR_MAC_REQUEST_EID_MIN, SIR_MAC_REQUEST_EID_MAX },
+/* 011 */ { SIR_MAC_QBSS_LOAD_EID_MIN, SIR_MAC_QBSS_LOAD_EID_MAX },
+/* 012 */ { SIR_MAC_EDCA_PARAM_SET_EID_MIN, SIR_MAC_EDCA_PARAM_SET_EID_MAX },
+/* 013 */ { SIR_MAC_TSPEC_EID_MIN, SIR_MAC_TSPEC_EID_MAX },
+/* 014 */ { SIR_MAC_TCLAS_EID_MIN, SIR_MAC_TCLAS_EID_MAX },
+/* 015 */ { SIR_MAC_QOS_SCHEDULE_EID_MIN, SIR_MAC_QOS_SCHEDULE_EID_MAX },
+/* 016 */ { SIR_MAC_CHALLENGE_TEXT_EID_MIN, SIR_MAC_CHALLENGE_TEXT_EID_MAX },
+/* 017 */ { 0, 255 },
+/* 018 */ { 0, 255 },
+/* 019 */ { 0, 255 },
+/* 020 */ { 0, 255 },
+/* 021 */ { 0, 255 },
+/* 022 */ { 0, 255 },
+/* 023 */ { 0, 255 },
+/* 024 */ { 0, 255 },
+/* 025 */ { 0, 255 },
+/* 026 */ { 0, 255 },
+/* 027 */ { 0, 255 },
+/* 028 */ { 0, 255 },
+/* 029 */ { 0, 255 },
+/* 030 */ { 0, 255 },
+/* 031 */ { 0, 255 },
+/* 032 */ { SIR_MAC_PWR_CONSTRAINT_EID_MIN, SIR_MAC_PWR_CONSTRAINT_EID_MAX },
+/* 033 */ { SIR_MAC_PWR_CAPABILITY_EID_MIN, SIR_MAC_PWR_CAPABILITY_EID_MAX },
+/* 034 */ { SIR_MAC_TPC_REQ_EID_MIN, SIR_MAC_TPC_REQ_EID_MAX },
+/* 035 */ { SIR_MAC_TPC_RPT_EID_MIN, SIR_MAC_TPC_RPT_EID_MAX },
+/* 036 */ { SIR_MAC_SPRTD_CHNLS_EID_MIN, SIR_MAC_SPRTD_CHNLS_EID_MAX },
+/* 037 */ { SIR_MAC_CHNL_SWITCH_ANN_EID_MIN, SIR_MAC_CHNL_SWITCH_ANN_EID_MAX },
+/* 038 */ { SIR_MAC_MEAS_REQ_EID_MIN, SIR_MAC_MEAS_REQ_EID_MAX },
+/* 039 */ { SIR_MAC_MEAS_RPT_EID_MIN, SIR_MAC_MEAS_RPT_EID_MAX },
+/* 040 */ { SIR_MAC_QUIET_EID_MIN, SIR_MAC_QUIET_EID_MAX },
+/* 041 */ { SIR_MAC_IBSS_DFS_EID_MIN, SIR_MAC_IBSS_DFS_EID_MAX },
+/* 042 */ { SIR_MAC_ERP_INFO_EID_MIN, SIR_MAC_ERP_INFO_EID_MAX },
+/* 043 */ { SIR_MAC_TS_DELAY_EID_MIN, SIR_MAC_TS_DELAY_EID_MAX },
+/* 044 */ { SIR_MAC_TCLAS_PROC_EID_MIN, SIR_MAC_TCLAS_PROC_EID_MAX },
+/* 045 */ { SIR_MAC_QOS_ACTION_EID_MIN, SIR_MAC_QOS_ACTION_EID_MAX },
+/* 046 */ { SIR_MAC_QOS_CAPABILITY_EID_MIN, SIR_MAC_QOS_CAPABILITY_EID_MAX },
+/* 047 */ { 0, 255 },
+/* 048 */ { SIR_MAC_RSN_EID_MIN, SIR_MAC_RSN_EID_MAX },
+/* 049 */ { 0, 255 },
+/* 050 */ { SIR_MAC_EXTENDED_RATE_EID_MIN, SIR_MAC_EXTENDED_RATE_EID_MAX },
+/* 051 */ { 0, 255 },
+/* 052 */ { 0, 255 },
+/* 053 */ { 0, 255 },
+/* 054 */ { 0, 255 },
+/* 055 */ { 0, 255 },
+/* 056 */ { 0, 255 },
+/* 057 */ { 0, 255 },
+/* 058 */ { 0, 255 },
+/* 059 */ { 0, 255 },
+/* 060 */ { 0, 255 },
+/* 061 */ { 0, 255 },
+/* 062 */ { 0, 255 },
+/* 063 */ { 0, 255 },
+/* 064 */ { 0, 255 },
+/* 065 */ { 0, 255 },
+/* 066 */ { 0, 255 },
+/* 067 */ { 0, 255 },
+#ifdef FEATURE_WLAN_WAPI
+/* 068 */ { DOT11F_EID_WAPI, DOT11F_IE_WAPI_MAX_LEN },
+#else
+/* 068 */ { 0, 255 },
+#endif /* FEATURE_WLAN_WAPI */
+/* 069 */ { 0, 255 },
+/* 070 */ { 0, 255 },
+/* 071 */ { 0, 255 },
+/* 072 */ { 0, 255 },
+/* 073 */ { 0, 255 },
+/* 074 */ { 0, 255 },
+/* 075 */ { 0, 255 },
+/* 076 */ { 0, 255 },
+/* 077 */ { 0, 255 },
+/* 078 */ { 0, 255 },
+/* 079 */ { 0, 255 },
+/* 080 */ { 0, 255 },
+/* 081 */ { 0, 255 },
+/* 082 */ { 0, 255 },
+/* 083 */ { 0, 255 },
+/* 084 */ { 0, 255 },
+/* 085 */ { 0, 255 },
+/* 086 */ { 0, 255 },
+/* 087 */ { 0, 255 },
+/* 088 */ { 0, 255 },
+/* 089 */ { 0, 255 },
+/* 090 */ { 0, 255 },
+/* 091 */ { 0, 255 },
+/* 092 */ { 0, 255 },
+/* 093 */ { 0, 255 },
+/* 094 */ { 0, 255 },
+/* 095 */ { 0, 255 },
+/* 096 */ { 0, 255 },
+/* 097 */ { 0, 255 },
+/* 098 */ { 0, 255 },
+/* 099 */ { 0, 255 },
+/* 100 */ { 0, 255 },
+/* 101 */ { 0, 255 },
+/* 102 */ { 0, 255 },
+/* 103 */ { 0, 255 },
+/* 104 */ { 0, 255 },
+/* 105 */ { 0, 255 },
+/* 106 */ { 0, 255 },
+/* 107 */ { 0, 255 },
+/* 108 */ { 0, 255 },
+/* 109 */ { 0, 255 },
+/* 110 */ { 0, 255 },
+/* 111 */ { 0, 255 },
+/* 112 */ { 0, 255 },
+/* 113 */ { 0, 255 },
+/* 114 */ { 0, 255 },
+/* 115 */ { 0, 255 },
+/* 116 */ { 0, 255 },
+/* 117 */ { 0, 255 },
+/* 118 */ { 0, 255 },
+/* 119 */ { 0, 255 },
+/* 120 */ { 0, 255 },
+/* 121 */ { 0, 255 },
+/* 122 */ { 0, 255 },
+/* 123 */ { 0, 255 },
+/* 124 */ { 0, 255 },
+/* 125 */ { 0, 255 },
+/* 126 */ { 0, 255 },
+/* 127 */ { 0, 255 },
+/* 128 */ { 0, 255 },
+/* 129 */ { 0, 255 },
+/* 130 */ { 0, 255 },
+/* 131 */ { 0, 255 },
+/* 132 */ { 0, 255 },
+/* 133 */ { 0, 255 },
+/* 134 */ { 0, 255 },
+/* 135 */ { 0, 255 },
+/* 136 */ { 0, 255 },
+/* 137 */ { 0, 255 },
+/* 138 */ { 0, 255 },
+/* 139 */ { 0, 255 },
+/* 140 */ { 0, 255 },
+/* 141 */ { 0, 255 },
+/* 142 */ { 0, 255 },
+/* 143 */ { 0, 255 },
+/* 144 */ { 0, 255 },
+/* 145 */ { 0, 255 },
+/* 146 */ { 0, 255 },
+/* 147 */ { 0, 255 },
+/* 148 */ { 0, 255 },
+/* 149 */ { 0, 255 },
+/* 150 */ { 0, 255 },
+/* 151 */ { 0, 255 },
+/* 152 */ { 0, 255 },
+/* 153 */ { 0, 255 },
+/* 154 */ { 0, 255 },
+/* 155 */ { 0, 255 },
+/* 156 */ { 0, 255 },
+/* 157 */ { 0, 255 },
+/* 158 */ { 0, 255 },
+/* 159 */ { 0, 255 },
+/* 160 */ { 0, 255 },
+/* 161 */ { 0, 255 },
+/* 162 */ { 0, 255 },
+/* 163 */ { 0, 255 },
+/* 164 */ { 0, 255 },
+/* 165 */ { 0, 255 },
+/* 166 */ { 0, 255 },
+/* 167 */ { 0, 255 },
+/* 168 */ { 0, 255 },
+/* 169 */ { 0, 255 },
+/* 170 */ { 0, 255 },
+/* 171 */ { 0, 255 },
+/* 172 */ { 0, 255 },
+/* 173 */ { 0, 255 },
+/* 174 */ { 0, 255 },
+/* 175 */ { 0, 255 },
+/* 176 */ { 0, 255 },
+/* 177 */ { 0, 255 },
+/* 178 */ { 0, 255 },
+/* 179 */ { 0, 255 },
+/* 180 */ { 0, 255 },
+/* 181 */ { 0, 255 },
+/* 182 */ { 0, 255 },
+/* 183 */ { 0, 255 },
+/* 184 */ { 0, 255 },
+/* 185 */ { 0, 255 },
+/* 186 */ { 0, 255 },
+/* 187 */ { 0, 255 },
+/* 188 */ { 0, 255 },
+/* 189 */ { 0, 255 },
+/* 190 */ { 0, 255 },
+/* 191 */ { 0, 255 },
+/* 192 */ { 0, 255 },
+/* 193 */ { 0, 255 },
+/* 194 */ { 0, 255 },
+/* 195 */ { 0, 255 },
+/* 196 */ { 0, 255 },
+/* 197 */ { 0, 255 },
+/* 198 */ { 0, 255 },
+/* 199 */ { 0, 255 },
+/* 200 */ { 0, 255 },
+/* 201 */ { 0, 255 },
+/* 202 */ { 0, 255 },
+/* 203 */ { 0, 255 },
+/* 204 */ { 0, 255 },
+/* 205 */ { 0, 255 },
+/* 206 */ { 0, 255 },
+/* 207 */ { 0, 255 },
+/* 208 */ { 0, 255 },
+/* 209 */ { 0, 255 },
+/* 210 */ { 0, 255 },
+/* 211 */ { 0, 255 },
+/* 212 */ { 0, 255 },
+/* 213 */ { 0, 255 },
+/* 214 */ { 0, 255 },
+/* 215 */ { 0, 255 },
+/* 216 */ { 0, 255 },
+/* 217 */ { 0, 255 },
+/* 218 */ { 0, 255 },
+/* 219 */ { 0, 255 },
+/* 220 */ { 0, 255 },
+/* 221 */ { SIR_MAC_WPA_EID_MIN, SIR_MAC_WPA_EID_MAX },
+/* 222 */ { 0, 255 },
+/* 223 */ { 0, 255 },
+/* 224 */ { 0, 255 },
+/* 225 */ { 0, 255 },
+/* 226 */ { 0, 255 },
+/* 227 */ { 0, 255 },
+/* 228 */ { 0, 255 },
+/* 229 */ { 0, 255 },
+/* 230 */ { 0, 255 },
+/* 231 */ { 0, 255 },
+/* 232 */ { 0, 255 },
+/* 233 */ { 0, 255 },
+/* 234 */ { 0, 255 },
+/* 235 */ { 0, 255 },
+/* 236 */ { 0, 255 },
+/* 237 */ { 0, 255 },
+/* 238 */ { 0, 255 },
+/* 239 */ { 0, 255 },
+/* 240 */ { 0, 255 },
+/* 241 */ { 0, 255 },
+/* 242 */ { 0, 255 },
+/* 243 */ { 0, 255 },
+/* 244 */ { 0, 255 },
+/* 245 */ { 0, 255 },
+/* 246 */ { 0, 255 },
+/* 247 */ { 0, 255 },
+/* 248 */ { 0, 255 },
+/* 249 */ { 0, 255 },
+/* 250 */ { 0, 255 },
+/* 251 */ { 0, 255 },
+/* 252 */ { 0, 255 },
+/* 253 */ { 0, 255 },
+/* 254 */ { 0, 255 },
+/* 255 */ { SIR_MAC_ANI_WORKAROUND_EID_MIN, SIR_MAC_ANI_WORKAROUND_EID_MAX }
+};
+
+#if 0
+//Don't not insert entry into the table, put it to the end. If you have to insert, make sure it is also
+//reflected in eCsrCountryIndex
+static tCsrCountryInfo gCsrCountryInfo[eCSR_NUM_COUNTRY_INDEX] =
+{
+    {REG_DOMAIN_FCC, {'U', 'S', ' '}},       //USA/******The "US" MUST be at index 0*******/
+    {REG_DOMAIN_WORLD, {'A', 'D', ' '}},     //ANDORRA
+    {REG_DOMAIN_WORLD, {'A', 'E', ' '}},       //UAE
+    {REG_DOMAIN_WORLD, {'A', 'F', ' '}},     //AFGHANISTAN
+    {REG_DOMAIN_WORLD, {'A', 'G', ' '}},     //ANTIGUA AND BARBUDA
+    {REG_DOMAIN_WORLD, {'A', 'I', ' '}},     //ANGUILLA
+    {REG_DOMAIN_HI_5GHZ, {'A', 'L', ' '}},     //ALBANIA
+    {REG_DOMAIN_WORLD, {'A', 'M', ' '}},     //ARMENIA
+    {REG_DOMAIN_WORLD, {'A', 'N', ' '}},     //NETHERLANDS ANTILLES
+    {REG_DOMAIN_WORLD, {'A', 'O', ' '}},     //ANGOLA
+    {REG_DOMAIN_WORLD, {'A', 'Q', ' '}},     //ANTARCTICA
+    {REG_DOMAIN_HI_5GHZ, {'A', 'R', ' '}},    //ARGENTINA
+    {REG_DOMAIN_FCC, {'A', 'S', ' '}},     //AMERICAN SOMOA
+    {REG_DOMAIN_ETSI, {'A', 'T', ' '}},      //AUSTRIA
+    {REG_DOMAIN_ETSI, {'A', 'U', ' '}},      //AUSTRALIA
+    {REG_DOMAIN_WORLD, {'A', 'W', ' '}},     //ARUBA
+    {REG_DOMAIN_WORLD, {'A', 'X', ' '}},     //ALAND ISLANDS
+    {REG_DOMAIN_WORLD, {'A', 'Z', ' '}},     //AZERBAIJAN
+    {REG_DOMAIN_WORLD, {'B', 'A', ' '}},     //BOSNIA AND HERZEGOVINA
+    {REG_DOMAIN_WORLD, {'B', 'B', ' '}},     //BARBADOS
+    {REG_DOMAIN_WORLD, {'B', 'D', ' '}},     //BANGLADESH
+    {REG_DOMAIN_ETSI, {'B', 'E', ' '}},      //BELGIUM
+    {REG_DOMAIN_WORLD, {'B', 'F', ' '}},     //BURKINA FASO
+    {REG_DOMAIN_HI_5GHZ, {'B', 'G', ' '}},      //BULGARIA
+    {REG_DOMAIN_WORLD, {'B', 'H', ' '}},     //BAHRAIN
+    {REG_DOMAIN_WORLD, {'B', 'I', ' '}},     //BURUNDI
+    {REG_DOMAIN_WORLD, {'B', 'J', ' '}},     //BENIN
+    {REG_DOMAIN_WORLD, {'B', 'L', ' '}},     //SAINT BARTHELEMY
+    {REG_DOMAIN_ETSI, {'B', 'M', ' '}},     //BERMUDA
+    {REG_DOMAIN_WORLD, {'B', 'N', ' '}},     //BRUNEI DARUSSALAM
+    {REG_DOMAIN_WORLD, {'B', 'O', ' '}},     //BOLIVIA
+    {REG_DOMAIN_WORLD, {'B', 'R', ' '}},       //BRAZIL
+    {REG_DOMAIN_WORLD, {'B', 'S', ' '}},     //BAHAMAS
+    {REG_DOMAIN_WORLD, {'B', 'T', ' '}},     //BHUTAN
+    {REG_DOMAIN_WORLD, {'B', 'V', ' '}},     //BOUVET ISLAND
+    {REG_DOMAIN_WORLD, {'B', 'W', ' '}},     //BOTSWANA
+    {REG_DOMAIN_WORLD, {'B', 'Y', ' '}},     //BELARUS
+    {REG_DOMAIN_WORLD, {'B', 'Z', ' '}},     //BELIZE
+    {REG_DOMAIN_FCC, {'C', 'A', ' '}},       //CANADA
+    {REG_DOMAIN_WORLD, {'C', 'C', ' '}},     //COCOS (KEELING) ISLANDS
+    {REG_DOMAIN_WORLD, {'C', 'D', ' '}},     //CONGO, THE DEMOCRATIC REPUBLIC OF THE
+    {REG_DOMAIN_WORLD, {'C', 'F', ' '}},     //CENTRAL AFRICAN REPUBLIC
+    {REG_DOMAIN_WORLD, {'C', 'G', ' '}},     //CONGO
+    {REG_DOMAIN_ETSI, {'C', 'H', ' '}},      //SWITZERLAND
+    {REG_DOMAIN_WORLD, {'C', 'I', ' '}},     //COTE D'IVOIRE
+    {REG_DOMAIN_WORLD, {'C', 'K', ' '}},     //COOK ISLANDS
+    {REG_DOMAIN_WORLD, {'C', 'L', ' '}},       //CHILE
+    {REG_DOMAIN_WORLD, {'C', 'M', ' '}},     //CAMEROON
+    {REG_DOMAIN_HI_5GHZ, {'C', 'N', ' '}},   //CHINA
+    {REG_DOMAIN_WORLD, {'C', 'O', ' '}},       //COLOMBIA
+    {REG_DOMAIN_WORLD, {'C', 'R', ' '}},       //COSTA RICA
+    {REG_DOMAIN_WORLD, {'C', 'U', ' '}},     //CUBA  
+    {REG_DOMAIN_WORLD, {'C', 'V', ' '}},     //CAPE VERDE
+    {REG_DOMAIN_WORLD, {'C', 'X', ' '}},     //CHRISTMAS ISLAND
+    {REG_DOMAIN_WORLD, {'C', 'Y', ' '}},      //CYPRUS
+    {REG_DOMAIN_HI_5GHZ, {'C', 'Z', ' '}},      //CZECH REPUBLIC
+    {REG_DOMAIN_ETSI, {'D', 'E', ' '}},      //GERMANY
+    {REG_DOMAIN_WORLD, {'D', 'J', ' '}},     //DJIBOUTI
+    {REG_DOMAIN_ETSI, {'D', 'K', ' '}},      //DENMARK
+    {REG_DOMAIN_WORLD, {'D', 'M', ' '}},     //DOMINICA
+    {REG_DOMAIN_WORLD, {'D', 'O', ' '}},       //DOMINICAN REPUBLIC
+    {REG_DOMAIN_WORLD, {'D', 'Z', ' '}},     //ALGERIA
+    {REG_DOMAIN_WORLD, {'E', 'C', ' '}},       //ECUADOR
+    {REG_DOMAIN_HI_5GHZ, {'E', 'E', ' '}},      //ESTONIA
+    {REG_DOMAIN_WORLD, {'E', 'G', ' '}},     //EGYPT
+    {REG_DOMAIN_WORLD, {'E', 'H', ' '}},     //WESTERN SAHARA
+    {REG_DOMAIN_WORLD, {'E', 'R', ' '}},     //ERITREA
+    {REG_DOMAIN_ETSI, {'E', 'S', ' '}},      //SPAIN
+    {REG_DOMAIN_WORLD, {'E', 'T', ' '}},     //ETHIOPIA
+    {REG_DOMAIN_WORLD, {'F', 'I', ' '}},      //FINLAND
+    {REG_DOMAIN_WORLD, {'F', 'J', ' '}},     //FIJI
+    {REG_DOMAIN_WORLD, {'F', 'K', ' '}},     //FALKLAND ISLANDS (MALVINAS)
+    {REG_DOMAIN_WORLD, {'F', 'M', ' '}},     //MICRONESIA, FEDERATED STATES OF
+    {REG_DOMAIN_WORLD, {'F', 'O', ' '}},     //FAROE ISLANDS
+    {REG_DOMAIN_ETSI, {'F', 'R', ' '}},      //FRANCE
+    {REG_DOMAIN_WORLD, {'G', 'A', ' '}},     //GABON
+    {REG_DOMAIN_ETSI, {'G', 'B', ' '}},      //UNITED KINGDOM
+    {REG_DOMAIN_WORLD, {'G', 'D', ' '}},     //GRENADA
+    {REG_DOMAIN_HI_5GHZ, {'G', 'E', ' '}},     //GEORGIA
+    {REG_DOMAIN_WORLD, {'G', 'F', ' '}},     //FRENCH GUIANA
+    {REG_DOMAIN_ETSI, {'G', 'G', ' '}},      //GUERNSEY
+    {REG_DOMAIN_WORLD, {'G', 'H', ' '}},     //GHANA
+    {REG_DOMAIN_WORLD, {'G', 'I', ' '}},      //GIBRALTAR
+    {REG_DOMAIN_WORLD, {'G', 'L', ' '}},     //GREENLAND
+    {REG_DOMAIN_WORLD, {'G', 'M', ' '}},     //GAMBIA
+    {REG_DOMAIN_WORLD, {'G', 'N', ' '}},     //GUINEA
+    {REG_DOMAIN_WORLD, {'G', 'P', ' '}},     //GUADELOUPE
+    {REG_DOMAIN_WORLD, {'G', 'Q', ' '}},     //EQUATORIAL GUINEA
+    {REG_DOMAIN_ETSI, {'G', 'R', ' '}},      //GREECE
+    {REG_DOMAIN_WORLD, {'G', 'S', ' '}},     //SOUTH GEORGIA AND THE SOUTH SANDWICH ISLANDS
+    {REG_DOMAIN_WORLD, {'G', 'T', ' '}},       //GUATEMALA
+    {REG_DOMAIN_WORLD, {'G', 'U', ' '}},     //GUAM
+    {REG_DOMAIN_WORLD, {'G', 'W', ' '}},     //GUINEA-BISSAU
+    {REG_DOMAIN_WORLD, {'G', 'Y', ' '}},     //GUYANA
+    {REG_DOMAIN_WORLD, {'H', 'K', ' '}},      //HONGKONG
+    {REG_DOMAIN_WORLD, {'H', 'M', ' '}},     //HEARD ISLAND AND MCDONALD ISLANDS
+    {REG_DOMAIN_WORLD, {'H', 'N', ' '}},       //HONDURAS
+    {REG_DOMAIN_HI_5GHZ, {'H', 'R', ' '}},      //CROATIA
+    {REG_DOMAIN_WORLD, {'H', 'T', ' '}},     //HAITI
+    {REG_DOMAIN_HI_5GHZ, {'H', 'U', ' '}},      //HUNGARY
+    {REG_DOMAIN_APAC, {'I', 'D', ' '}},     //INDONESIA
+    {REG_DOMAIN_ETSI, {'I', 'E', ' '}},     //IRELAND        
+    {REG_DOMAIN_WORLD, {'I', 'L', ' '}},        //ISREAL
+    {REG_DOMAIN_ETSI, {'I', 'M', ' '}},      //ISLE OF MAN
+    {REG_DOMAIN_WORLD, {'I', 'N', ' '}},      //INDIA
+    {REG_DOMAIN_ETSI, {'I', 'O', ' '}},     //BRITISH INDIAN OCEAN TERRITORY
+    {REG_DOMAIN_WORLD, {'I', 'Q', ' '}},     //IRAQ
+    {REG_DOMAIN_WORLD, {'I', 'R', ' '}},     //IRAN, ISLAMIC REPUBLIC OF
+    {REG_DOMAIN_WORLD, {'I', 'S', ' '}},      //ICELAND
+    {REG_DOMAIN_ETSI, {'I', 'T', ' '}},      //ITALY
+    {REG_DOMAIN_ETSI, {'J', 'E', ' '}},      //JERSEY
+    {REG_DOMAIN_WORLD, {'J', 'M', ' '}},     //JAMAICA
+    {REG_DOMAIN_WORLD, {'J', 'O', ' '}},     //JORDAN
+    {REG_DOMAIN_JAPAN, {'J', 'P', ' '}},     //JAPAN
+    {REG_DOMAIN_WORLD, {'K', 'E', ' '}},     //KENYA
+    {REG_DOMAIN_WORLD, {'K', 'G', ' '}},     //KYRGYZSTAN
+    {REG_DOMAIN_WORLD, {'K', 'H', ' '}},     //CAMBODIA
+    {REG_DOMAIN_WORLD, {'K', 'I', ' '}},     //KIRIBATI
+    {REG_DOMAIN_WORLD, {'K', 'M', ' '}},     //COMOROS
+    {REG_DOMAIN_WORLD, {'K', 'N', ' '}},     //SAINT KITTS AND NEVIS
+    {REG_DOMAIN_KOREA, {'K', 'P', ' '}},     //KOREA, DEMOCRATIC PEOPLE'S REPUBLIC OF
+    {REG_DOMAIN_KOREA, {'K', 'R', ' '}},     //KOREA, REPUBLIC OF 
+    {REG_DOMAIN_WORLD, {'K', 'W', ' '}},     //KUWAIT
+    {REG_DOMAIN_WORLD, {'K', 'Y', ' '}},     //CAYMAN ISLANDS
+    {REG_DOMAIN_WORLD, {'K', 'Z', ' '}},     //KAZAKHSTAN
+    {REG_DOMAIN_WORLD, {'L', 'A', ' '}},     //LAO PEOPLE'S DEMOCRATIC REPUBLIC
+    {REG_DOMAIN_WORLD, {'L', 'B', ' '}},     //LEBANON
+    {REG_DOMAIN_WORLD, {'L', 'C', ' '}},     //SAINT LUCIA
+    {REG_DOMAIN_ETSI, {'L', 'I', ' '}},      //LIECHTENSTEIN
+    {REG_DOMAIN_WORLD, {'L', 'K', ' '}},     //SRI LANKA
+    {REG_DOMAIN_WORLD, {'L', 'R', ' '}},     //LIBERIA
+    {REG_DOMAIN_WORLD, {'L', 'S', ' '}},     //LESOTHO
+    {REG_DOMAIN_HI_5GHZ, {'L', 'T', ' '}},      //LITHUANIA
+    {REG_DOMAIN_ETSI, {'L', 'U', ' '}},      //LUXEMBOURG
+    {REG_DOMAIN_HI_5GHZ, {'L', 'V', ' '}},      //LATVIA
+    {REG_DOMAIN_WORLD, {'L', 'Y', ' '}},     //LIBYAN ARAB JAMAHIRIYA
+    {REG_DOMAIN_WORLD, {'M', 'A', ' '}},     //MOROCCO
+    {REG_DOMAIN_ETSI, {'M', 'C', ' '}},      //MONACO
+    {REG_DOMAIN_WORLD, {'M', 'D', ' '}},     //MOLDOVA, REPUBLIC OF
+    {REG_DOMAIN_WORLD, {'M', 'E', ' '}},     //MONTENEGRO
+    {REG_DOMAIN_WORLD, {'M', 'G', ' '}},     //MADAGASCAR
+    {REG_DOMAIN_WORLD, {'M', 'H', ' '}},     //MARSHALL ISLANDS
+    {REG_DOMAIN_WORLD, {'M', 'K', ' '}},     //MACEDONIA, THE FORMER YUGOSLAV REPUBLIC OF
+    {REG_DOMAIN_WORLD, {'M', 'L', ' '}},     //MALI
+    {REG_DOMAIN_WORLD, {'M', 'M', ' '}},     //MYANMAR
+    {REG_DOMAIN_HI_5GHZ, {'M', 'N', ' '}},     //MONGOLIA
+    {REG_DOMAIN_WORLD, {'M', 'O', ' '}},     //MACAO
+    {REG_DOMAIN_WORLD, {'M', 'P', ' '}},     //NORTHERN MARIANA ISLANDS
+    {REG_DOMAIN_WORLD, {'M', 'Q', ' '}},     //MARTINIQUE
+    {REG_DOMAIN_WORLD, {'M', 'R', ' '}},     //MAURITANIA
+    {REG_DOMAIN_WORLD, {'M', 'S', ' '}},     //MONTSERRAT
+    {REG_DOMAIN_WORLD, {'M', 'T', ' '}},      //MALTA     
+    {REG_DOMAIN_WORLD, {'M', 'U', ' '}},     //MAURITIUS
+    {REG_DOMAIN_WORLD, {'M', 'V', ' '}},     //MALDIVES
+    {REG_DOMAIN_WORLD, {'M', 'W', ' '}},     //MALAWI
+    {REG_DOMAIN_WORLD, {'M', 'X', ' '}},       //MEXICO
+    {REG_DOMAIN_HI_5GHZ, {'M', 'Y', ' '}},       //MALAYSIA
+    {REG_DOMAIN_WORLD, {'M', 'Z', ' '}},     //MOZAMBIQUE
+    {REG_DOMAIN_WORLD, {'N', 'A', ' '}},     //NAMIBIA
+    {REG_DOMAIN_WORLD, {'N', 'C', ' '}},     //NEW CALEDONIA
+    {REG_DOMAIN_WORLD, {'N', 'E', ' '}},     //NIGER
+    {REG_DOMAIN_WORLD, {'N', 'F', ' '}},     //NORFOLD ISLAND
+    {REG_DOMAIN_WORLD, {'N', 'G', ' '}},     //NIGERIA
+    {REG_DOMAIN_WORLD, {'N', 'I', ' '}},       //NICARAGUA
+    {REG_DOMAIN_ETSI, {'N', 'L', ' '}},      //NETHERLANDS
+    {REG_DOMAIN_WORLD, {'N', 'O', ' '}},      //NORWAY
+    {REG_DOMAIN_WORLD, {'N', 'P', ' '}},     //NEPAL
+    {REG_DOMAIN_WORLD, {'N', 'R', ' '}},     //NAURU
+    {REG_DOMAIN_WORLD, {'N', 'U', ' '}},     //NIUE
+    {REG_DOMAIN_ETSI, {'N', 'Z', ' '}},      //NEW ZEALAND
+    {REG_DOMAIN_WORLD, {'O', 'M', ' '}},     //OMAN
+    {REG_DOMAIN_WORLD, {'P', 'A', ' '}},       //PANAMA
+    {REG_DOMAIN_WORLD, {'P', 'E', ' '}},       //PERU
+    {REG_DOMAIN_WORLD, {'P', 'F', ' '}},     //FRENCH POLYNESIA
+    {REG_DOMAIN_WORLD, {'P', 'G', ' '}},     //PAPUA NEW GUINEA
+    {REG_DOMAIN_WORLD, {'P', 'H', ' '}},      //PHILIPPINES
+    {REG_DOMAIN_WORLD, {'P', 'K', ' '}},     //PAKISTAN
+    {REG_DOMAIN_WORLD, {'P', 'L', ' '}},      //POLAND
+    {REG_DOMAIN_WORLD, {'P', 'M', ' '}},     //SAINT PIERRE AND MIQUELON
+    {REG_DOMAIN_WORLD, {'P', 'N', ' '}},     //PITCAIRN
+    {REG_DOMAIN_FCC, {'P', 'R', ' '}},       //PUERTO RICO
+    {REG_DOMAIN_WORLD, {'P', 'S', ' '}},        //PALESTINIAN TERRITORY, OCCUPIED
+    {REG_DOMAIN_ETSI, {'P', 'T', ' '}},      //PORTUGAL
+    {REG_DOMAIN_WORLD, {'P', 'W', ' '}},     //PALAU
+    {REG_DOMAIN_WORLD, {'P', 'Y', ' '}},     //PARAGUAY
+    {REG_DOMAIN_WORLD, {'Q', 'A', ' '}},     //QATAR
+    {REG_DOMAIN_WORLD, {'R', 'E', ' '}},     //REUNION
+    {REG_DOMAIN_HI_5GHZ, {'R', 'O', ' '}},      //ROMANIA
+    {REG_DOMAIN_HI_5GHZ, {'R', 'S', ' '}},      //SERBIA
+    {REG_DOMAIN_WORLD, {'R', 'U', ' '}},       //RUSSIA
+    {REG_DOMAIN_WORLD, {'R', 'W', ' '}},     //RWANDA
+    {REG_DOMAIN_WORLD, {'S', 'A', ' '}},      //SAUDI ARABIA
+    {REG_DOMAIN_WORLD, {'S', 'B', ' '}},     //SOLOMON ISLANDS
+    {REG_DOMAIN_ETSI, {'S', 'C', ' '}},      //SEYCHELLES
+    {REG_DOMAIN_WORLD, {'S', 'D', ' '}},     //SUDAN
+    {REG_DOMAIN_ETSI, {'S', 'E', ' '}},      //SWEDEN
+    {REG_DOMAIN_APAC, {'S', 'G', ' '}},      //SINGAPORE
+    {REG_DOMAIN_WORLD, {'S', 'H', ' '}},     //SAINT HELENA
+    {REG_DOMAIN_HI_5GHZ, {'S', 'I', ' '}},      //SLOVENNIA
+    {REG_DOMAIN_WORLD, {'S', 'J', ' '}},     //SVALBARD AND JAN MAYEN
+    {REG_DOMAIN_HI_5GHZ, {'S', 'K', ' '}},      //SLOVAKIA
+    {REG_DOMAIN_WORLD, {'S', 'L', ' '}},     //SIERRA LEONE      
+    {REG_DOMAIN_WORLD, {'S', 'M', ' '}},     //SAN MARINO
+    {REG_DOMAIN_WORLD, {'S', 'N', ' '}},     //SENEGAL
+    {REG_DOMAIN_WORLD, {'S', 'O', ' '}},     //SOMALIA
+    {REG_DOMAIN_WORLD, {'S', 'R', ' '}},     //SURINAME
+    {REG_DOMAIN_WORLD, {'S', 'T', ' '}},     //SAO TOME AND PRINCIPE
+    {REG_DOMAIN_WORLD, {'S', 'V', ' '}},       //EL SALVADOR
+    {REG_DOMAIN_WORLD, {'S', 'Y', ' '}},     //SYRIAN ARAB REPUBLIC
+    {REG_DOMAIN_WORLD, {'S', 'Z', ' '}},     //SWAZILAND
+    {REG_DOMAIN_WORLD, {'T', 'C', ' '}},     //TURKS AND CAICOS ISLANDS
+    {REG_DOMAIN_WORLD, {'T', 'D', ' '}},     //CHAD
+    {REG_DOMAIN_WORLD, {'T', 'F', ' '}},     //FRENCH SOUTHERN TERRITORIES
+    {REG_DOMAIN_WORLD, {'T', 'G', ' '}},     //TOGO
+    {REG_DOMAIN_WORLD, {'T', 'H', ' '}},       //THAILAND
+    {REG_DOMAIN_WORLD, {'T', 'J', ' '}},     //TAJIKISTAN
+    {REG_DOMAIN_WORLD, {'T', 'K', ' '}},     //TOKELAU
+    {REG_DOMAIN_WORLD, {'T', 'L', ' '}},     //TIMOR-LESTE
+    {REG_DOMAIN_WORLD, {'T', 'M', ' '}},     //TURKMENISTAN
+    {REG_DOMAIN_WORLD, {'T', 'N', ' '}},     //TUNISIA
+    {REG_DOMAIN_WORLD, {'T', 'O', ' '}},     //TONGA
+    {REG_DOMAIN_WORLD, {'T', 'R', ' '}},      //TURKEY
+    {REG_DOMAIN_WORLD, {'T', 'T', ' '}},     //TRINIDAD AND TOBAGO
+    {REG_DOMAIN_WORLD, {'T', 'V', ' '}},     //TUVALU
+    {REG_DOMAIN_HI_5GHZ, {'T', 'W', ' '}},       //TAIWAN, PROVINCE OF CHINA
+    {REG_DOMAIN_WORLD, {'T', 'Z', ' '}},     //TANZANIA, UNITED REPUBLIC OF
+    {REG_DOMAIN_HI_5GHZ, {'U', 'A', ' '}},       //UKRAINE
+    {REG_DOMAIN_WORLD, {'U', 'G', ' '}},     //UGANDA
+    {REG_DOMAIN_FCC, {'U', 'M', ' '}},       //UNITED STATES MINOR OUTLYING ISLANDS
+    {REG_DOMAIN_WORLD, {'U', 'Y', ' '}},       //URUGUAY
+    {REG_DOMAIN_HI_5GHZ, {'U', 'Z', ' '}},     //UZBEKISTAN
+    {REG_DOMAIN_ETSI, {'V', 'A', ' '}},      //HOLY SEE (VATICAN CITY STATE)
+    {REG_DOMAIN_WORLD, {'V', 'C', ' '}},     //SAINT VINCENT AND THE GRENADINES
+    {REG_DOMAIN_HI_5GHZ, {'V', 'E', ' '}},       //VENEZUELA
+    {REG_DOMAIN_ETSI, {'V', 'G', ' '}},       //VIRGIN ISLANDS, BRITISH
+    {REG_DOMAIN_FCC, {'V', 'I', ' '}},       //VIRGIN ISLANDS, US
+    {REG_DOMAIN_WORLD, {'V', 'N', ' '}},      //VIET NAM
+    {REG_DOMAIN_WORLD, {'V', 'U', ' '}},     //VANUATU
+    {REG_DOMAIN_WORLD, {'W', 'F', ' '}},     //WALLIS AND FUTUNA
+    {REG_DOMAIN_WORLD, {'W', 'S', ' '}},     //SOMOA
+    {REG_DOMAIN_WORLD, {'Y', 'E', ' '}},     //YEMEN
+    {REG_DOMAIN_WORLD, {'Y', 'T', ' '}},     //MAYOTTE
+    {REG_DOMAIN_WORLD, {'Z', 'A', ' '}},      //SOUTH AFRICA
+    {REG_DOMAIN_WORLD, {'Z', 'M', ' '}},     //ZAMBIA
+    {REG_DOMAIN_WORLD, {'Z', 'W', ' '}},     //ZIMBABWE
+
+    {REG_DOMAIN_KOREA, {'K', '1', ' '}},    //Korea alternate 1
+    {REG_DOMAIN_KOREA, {'K', '2', ' '}},    //Korea alternate 2
+    {REG_DOMAIN_KOREA, {'K', '3', ' '}},    //Korea alternate 3
+    {REG_DOMAIN_KOREA, {'K', '4', ' '}},    //Korea alternate 4
+};
+
+
+//The channels listed here doesn't mean they are valid channels for certain domain. They are here only to present
+//whether they should be passive scanned.
+tCsrDomainChnInfo gCsrDomainChnInfo[NUM_REG_DOMAINS] =
+{
+    //REG_DOMAIN_FCC
+    {
+        REG_DOMAIN_FCC,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_PASSIVE_SCAN},
+            {56, eSIR_PASSIVE_SCAN},
+            {60, eSIR_PASSIVE_SCAN},
+            {64, eSIR_PASSIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_PASSIVE_SCAN},
+            {104, eSIR_PASSIVE_SCAN},
+            {108, eSIR_PASSIVE_SCAN},
+            {112, eSIR_PASSIVE_SCAN},
+            {116, eSIR_PASSIVE_SCAN},
+            {120, eSIR_PASSIVE_SCAN},
+            {124, eSIR_PASSIVE_SCAN},
+            {128, eSIR_PASSIVE_SCAN},
+            {132, eSIR_PASSIVE_SCAN},
+            {136, eSIR_PASSIVE_SCAN},
+            {140, eSIR_PASSIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+    //REG_DOMAIN_ETSI
+    {
+        REG_DOMAIN_ETSI,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_PASSIVE_SCAN},
+            {56, eSIR_PASSIVE_SCAN},
+            {60, eSIR_PASSIVE_SCAN},
+            {64, eSIR_PASSIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_PASSIVE_SCAN},
+            {104, eSIR_PASSIVE_SCAN},
+            {108, eSIR_PASSIVE_SCAN},
+            {112, eSIR_PASSIVE_SCAN},
+            {116, eSIR_PASSIVE_SCAN},
+            {120, eSIR_PASSIVE_SCAN},
+            {124, eSIR_PASSIVE_SCAN},
+            {128, eSIR_PASSIVE_SCAN},
+            {132, eSIR_PASSIVE_SCAN},
+            {136, eSIR_PASSIVE_SCAN},
+            {140, eSIR_PASSIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+    //REG_DOMAIN_JAPAN
+    {
+        REG_DOMAIN_JAPAN,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_PASSIVE_SCAN},
+            {56, eSIR_PASSIVE_SCAN},
+            {60, eSIR_PASSIVE_SCAN},
+            {64, eSIR_PASSIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_PASSIVE_SCAN},
+            {104, eSIR_PASSIVE_SCAN},
+            {108, eSIR_PASSIVE_SCAN},
+            {112, eSIR_PASSIVE_SCAN},
+            {116, eSIR_PASSIVE_SCAN},
+            {120, eSIR_PASSIVE_SCAN},
+            {124, eSIR_PASSIVE_SCAN},
+            {128, eSIR_PASSIVE_SCAN},
+            {132, eSIR_PASSIVE_SCAN},
+            {136, eSIR_PASSIVE_SCAN},
+            {140, eSIR_PASSIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+    //REG_DOMAIN_WORLD
+    {
+        REG_DOMAIN_WORLD,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_ACTIVE_SCAN},
+            {56, eSIR_ACTIVE_SCAN},
+            {60, eSIR_ACTIVE_SCAN},
+            {64, eSIR_ACTIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_ACTIVE_SCAN},
+            {104, eSIR_ACTIVE_SCAN},
+            {108, eSIR_ACTIVE_SCAN},
+            {112, eSIR_ACTIVE_SCAN},
+            {116, eSIR_ACTIVE_SCAN},
+            {120, eSIR_ACTIVE_SCAN},
+            {124, eSIR_ACTIVE_SCAN},
+            {128, eSIR_ACTIVE_SCAN},
+            {132, eSIR_ACTIVE_SCAN},
+            {136, eSIR_ACTIVE_SCAN},
+            {140, eSIR_ACTIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+    //REG_DOMAIN_N_AMER_EXC_FCC
+    {
+        REG_DOMAIN_N_AMER_EXC_FCC,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_PASSIVE_SCAN},
+            {56, eSIR_PASSIVE_SCAN},
+            {60, eSIR_PASSIVE_SCAN},
+            {64, eSIR_PASSIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_ACTIVE_SCAN},
+            {104, eSIR_ACTIVE_SCAN},
+            {108, eSIR_ACTIVE_SCAN},
+            {112, eSIR_ACTIVE_SCAN},
+            {116, eSIR_ACTIVE_SCAN},
+            {120, eSIR_ACTIVE_SCAN},
+            {124, eSIR_ACTIVE_SCAN},
+            {128, eSIR_ACTIVE_SCAN},
+            {132, eSIR_ACTIVE_SCAN},
+            {136, eSIR_ACTIVE_SCAN},
+            {140, eSIR_ACTIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+    //REG_DOMAIN_APAC
+    {
+        REG_DOMAIN_APAC,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_PASSIVE_SCAN},
+            {56, eSIR_PASSIVE_SCAN},
+            {60, eSIR_PASSIVE_SCAN},
+            {64, eSIR_PASSIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_ACTIVE_SCAN},
+            {104, eSIR_ACTIVE_SCAN},
+            {108, eSIR_ACTIVE_SCAN},
+            {112, eSIR_ACTIVE_SCAN},
+            {116, eSIR_ACTIVE_SCAN},
+            {120, eSIR_ACTIVE_SCAN},
+            {124, eSIR_ACTIVE_SCAN},
+            {128, eSIR_ACTIVE_SCAN},
+            {132, eSIR_ACTIVE_SCAN},
+            {136, eSIR_ACTIVE_SCAN},
+            {140, eSIR_ACTIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+    //REG_DOMAIN_KOREA
+    {
+        REG_DOMAIN_KOREA,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_PASSIVE_SCAN},
+            {56, eSIR_PASSIVE_SCAN},
+            {60, eSIR_PASSIVE_SCAN},
+            {64, eSIR_PASSIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_PASSIVE_SCAN},
+            {104, eSIR_PASSIVE_SCAN},
+            {108, eSIR_PASSIVE_SCAN},
+            {112, eSIR_PASSIVE_SCAN},
+            {116, eSIR_PASSIVE_SCAN},
+            {120, eSIR_PASSIVE_SCAN},
+            {124, eSIR_PASSIVE_SCAN},
+            {128, eSIR_PASSIVE_SCAN},
+            {132, eSIR_PASSIVE_SCAN},
+            {136, eSIR_PASSIVE_SCAN},
+            {140, eSIR_PASSIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+    //REG_DOMAIN_HI_5GHZ
+    {
+        REG_DOMAIN_HI_5GHZ,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_ACTIVE_SCAN},
+            {56, eSIR_ACTIVE_SCAN},
+            {60, eSIR_ACTIVE_SCAN},
+            {64, eSIR_ACTIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_ACTIVE_SCAN},
+            {104, eSIR_ACTIVE_SCAN},
+            {108, eSIR_ACTIVE_SCAN},
+            {112, eSIR_ACTIVE_SCAN},
+            {116, eSIR_ACTIVE_SCAN},
+            {120, eSIR_ACTIVE_SCAN},
+            {124, eSIR_ACTIVE_SCAN},
+            {128, eSIR_ACTIVE_SCAN},
+            {132, eSIR_ACTIVE_SCAN},
+            {136, eSIR_ACTIVE_SCAN},
+            {140, eSIR_ACTIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+    //REG_DOMAIN_NO_5GHZ
+    {
+        REG_DOMAIN_NO_5GHZ,
+        45, //Num channels
+        //Channels
+        {
+            //5GHz
+            //5180 - 5240
+            {36, eSIR_ACTIVE_SCAN},
+            {40, eSIR_ACTIVE_SCAN},
+            {44, eSIR_ACTIVE_SCAN},
+            {48, eSIR_ACTIVE_SCAN},
+            //5250 to 5350
+            {52, eSIR_ACTIVE_SCAN},
+            {56, eSIR_ACTIVE_SCAN},
+            {60, eSIR_ACTIVE_SCAN},
+            {64, eSIR_ACTIVE_SCAN},
+            //5470 to 5725
+            {100, eSIR_ACTIVE_SCAN},
+            {104, eSIR_ACTIVE_SCAN},
+            {108, eSIR_ACTIVE_SCAN},
+            {112, eSIR_ACTIVE_SCAN},
+            {116, eSIR_ACTIVE_SCAN},
+            {120, eSIR_ACTIVE_SCAN},
+            {124, eSIR_ACTIVE_SCAN},
+            {128, eSIR_ACTIVE_SCAN},
+            {132, eSIR_ACTIVE_SCAN},
+            {136, eSIR_ACTIVE_SCAN},
+            {140, eSIR_ACTIVE_SCAN},
+            //5745 - 5825
+            {149, eSIR_ACTIVE_SCAN},
+            {153, eSIR_ACTIVE_SCAN},
+            {157, eSIR_ACTIVE_SCAN},
+            {161, eSIR_ACTIVE_SCAN},
+            {165, eSIR_ACTIVE_SCAN},
+            //4.9GHz
+            //4920 - 5080
+            {240, eSIR_ACTIVE_SCAN},
+            {244, eSIR_ACTIVE_SCAN},
+            {248, eSIR_ACTIVE_SCAN},
+            {252, eSIR_ACTIVE_SCAN},
+            {208, eSIR_ACTIVE_SCAN},
+            {212, eSIR_ACTIVE_SCAN},
+            {216, eSIR_ACTIVE_SCAN},
+            //2,4GHz
+            {1, eSIR_ACTIVE_SCAN},
+            {2, eSIR_ACTIVE_SCAN},
+            {3, eSIR_ACTIVE_SCAN},
+            {4, eSIR_ACTIVE_SCAN},
+            {5, eSIR_ACTIVE_SCAN},
+            {6, eSIR_ACTIVE_SCAN},
+            {7, eSIR_ACTIVE_SCAN},
+            {8, eSIR_ACTIVE_SCAN},
+            {9, eSIR_ACTIVE_SCAN},
+            {10, eSIR_ACTIVE_SCAN},
+            {11, eSIR_ACTIVE_SCAN},
+            {12, eSIR_ACTIVE_SCAN},
+            {13, eSIR_ACTIVE_SCAN},
+            {14, eSIR_ACTIVE_SCAN},
+        }
+    },
+};
+#endif
+
+extern const tRfChannelProps rfChannels[NUM_RF_CHANNELS];
+
+
+////////////////////////////////////////////////////////////////////////
+
+/**
+ * \var gPhyRatesSuppt
+ *
+ * \brief Rate support lookup table
+ *
+ *
+ * This is a  lookup table indexing rates &  configuration parameters to
+ * support.  Given a rate (in  unites of 0.5Mpbs) & three booleans (MIMO
+ * Enabled, Channel  Bonding Enabled, & Concatenation  Enabled), one can
+ * determine  whether  the given  rate  is  supported  by computing  two
+ * indices.  The  first maps  the rate to  table row as  indicated below
+ * (i.e. eHddSuppRate_6Mbps maps to  row zero, eHddSuppRate_9Mbps to row
+ * 1, and so on).  Index two can be computed like so:
+ *
+ * \code
+   idx2 = ( fEsf  ? 0x4 : 0x0 ) |
+          ( fCb   ? 0x2 : 0x0 ) |
+          ( fMimo ? 0x1 : 0x0 );
+ * \endcode
+ *
+ *
+ * Given that:
+ *
+ \code
+   fSupported = gPhyRatesSuppt[idx1][idx2];
+ \endcode
+ *
+ *
+ * This table is based on  the document "PHY Supported Rates.doc".  This
+ * table is  permissive in that a  rate is reflected  as being supported
+ * even  when turning  off an  enabled feature  would be  required.  For
+ * instance, "PHY Supported Rates"  lists 42Mpbs as unsupported when CB,
+ * ESF, &  MIMO are all  on.  However,  if we turn  off either of  CB or
+ * MIMO, it then becomes supported.   Therefore, we mark it as supported
+ * even in index 7 of this table.
+ *
+ *
+ */
+
+static const tANI_BOOLEAN gPhyRatesSuppt[24][8] = {
+
+    // SSF   SSF    SSF    SSF    ESF    ESF    ESF    ESF
+    // SIMO  MIMO   SIMO   MIMO   SIMO   MIMO   SIMO   MIMO
+    // No CB No CB  CB     CB     No CB  No CB  CB     CB
+    { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE  }, // 6Mbps
+    { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE  }, // 9Mbps
+    { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE  }, // 12Mbps
+    { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE  }, // 18Mbps
+    { FALSE, FALSE, TRUE,  TRUE,  FALSE, FALSE, TRUE,  TRUE  }, // 20Mbps
+    { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE  }, // 24Mbps
+    { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE  }, // 36Mbps
+    { FALSE, FALSE, TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 40Mbps
+    { FALSE, FALSE, TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 42Mbps
+    { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE  }, // 48Mbps
+    { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE  }, // 54Mbps
+    { FALSE, TRUE,  TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 72Mbps
+    { FALSE, FALSE, TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 80Mbps
+    { FALSE, FALSE, TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 84Mbps
+    { FALSE, TRUE,  TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 96Mbps
+    { FALSE, TRUE,  TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 108Mbps
+    { FALSE, FALSE, TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 120Mbps
+    { FALSE, FALSE, TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE  }, // 126Mbps
+    { FALSE, FALSE, FALSE, TRUE,  FALSE, FALSE, FALSE, TRUE  }, // 144Mbps
+    { FALSE, FALSE, FALSE, TRUE,  FALSE, FALSE, FALSE, TRUE  }, // 160Mbps
+    { FALSE, FALSE, FALSE, TRUE,  FALSE, FALSE, FALSE, TRUE  }, // 168Mbps
+    { FALSE, FALSE, FALSE, TRUE,  FALSE, FALSE, FALSE, TRUE  }, // 192Mbps
+    { FALSE, FALSE, FALSE, TRUE,  FALSE, FALSE, FALSE, TRUE  }, // 216Mbps
+    { FALSE, FALSE, FALSE, TRUE,  FALSE, FALSE, FALSE, TRUE  }, // 240Mbps
+
+};
+
+#define CASE_RETURN_STR(n) case (n): return (#n)
+
+const char *
+get_eRoamCmdStatus_str(eRoamCmdStatus val)
+{
+    switch (val)
+    {
+        CASE_RETURN_STR(eCSR_ROAM_CANCELLED);
+        CASE_RETURN_STR(eCSR_ROAM_ROAMING_START);
+        CASE_RETURN_STR(eCSR_ROAM_ROAMING_COMPLETION);
+        CASE_RETURN_STR(eCSR_ROAM_ASSOCIATION_START);
+        CASE_RETURN_STR(eCSR_ROAM_ASSOCIATION_COMPLETION);
+        CASE_RETURN_STR(eCSR_ROAM_DISASSOCIATED);
+        CASE_RETURN_STR(eCSR_ROAM_SHOULD_ROAM);
+        CASE_RETURN_STR(eCSR_ROAM_SCAN_FOUND_NEW_BSS);
+        CASE_RETURN_STR(eCSR_ROAM_LOSTLINK);
+    default:
+        return "unknown";
+    }
+}
+
+const char *
+get_eCsrRoamResult_str(eCsrRoamResult val)
+{
+    switch (val)
+    {
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_NONE);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_FAILURE);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_ASSOCIATED);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_NOT_ASSOCIATED);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_MIC_FAILURE);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_FORCED);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_DISASSOC_IND);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_DEAUTH_IND);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_CAP_CHANGED);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_IBSS_CONNECT);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_IBSS_INACTIVE);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_IBSS_NEW_PEER);
+        CASE_RETURN_STR(eCSR_ROAM_RESULT_IBSS_COALESCED);
+    default:
+        return "unknown";
+    }
+}
+
+
+
+tANI_BOOLEAN csrGetBssIdBssDesc( tHalHandle hHal, tSirBssDescription *pSirBssDesc, tCsrBssid *pBssId )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    palCopyMemory( pMac->hHdd, pBssId, &pSirBssDesc->bssId[ 0 ], sizeof(tCsrBssid) );
+    return( TRUE );
+}
+
+
+tANI_BOOLEAN csrIsBssIdEqual( tHalHandle hHal, tSirBssDescription *pSirBssDesc1, tSirBssDescription *pSirBssDesc2 )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fEqual = FALSE;
+    tCsrBssid bssId1;
+    tCsrBssid bssId2;
+
+    do {
+        if ( !pSirBssDesc1 ) break;
+        if ( !pSirBssDesc2 ) break;
+
+        if ( !csrGetBssIdBssDesc( pMac, pSirBssDesc1, &bssId1 ) ) break;
+        if ( !csrGetBssIdBssDesc( pMac, pSirBssDesc2, &bssId2 ) ) break;
+
+        //sirCompareMacAddr
+        fEqual = csrIsMacAddressEqual(pMac, &bssId1, &bssId2);
+
+    } while( 0 );
+
+    return( fEqual );
+}
+
+tANI_BOOLEAN csrIsConnStateConnectedIbss( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( eCSR_ASSOC_STATE_TYPE_IBSS_CONNECTED == pMac->roam.roamSession[sessionId].connectState );
+}
+
+tANI_BOOLEAN csrIsConnStateDisconnectedIbss( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( eCSR_ASSOC_STATE_TYPE_IBSS_DISCONNECTED == pMac->roam.roamSession[sessionId].connectState );
+}
+
+tANI_BOOLEAN csrIsConnStateConnectedInfra( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( eCSR_ASSOC_STATE_TYPE_INFRA_ASSOCIATED == pMac->roam.roamSession[sessionId].connectState );
+}
+
+tANI_BOOLEAN csrIsConnStateConnected( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    if( csrIsConnStateConnectedIbss( pMac, sessionId ) || csrIsConnStateConnectedInfra( pMac, sessionId ) || csrIsConnStateConnectedWds( pMac, sessionId) )
+        return TRUE;
+    else
+        return FALSE;
+}
+
+tANI_BOOLEAN csrIsConnStateInfra( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( csrIsConnStateConnectedInfra( pMac, sessionId ) );
+}
+
+tANI_BOOLEAN csrIsConnStateIbss( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( csrIsConnStateConnectedIbss( pMac, sessionId ) || csrIsConnStateDisconnectedIbss( pMac, sessionId ) );
+}
+
+
+tANI_BOOLEAN csrIsConnStateConnectedWds( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( eCSR_ASSOC_STATE_TYPE_WDS_CONNECTED == pMac->roam.roamSession[sessionId].connectState );
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+tANI_BOOLEAN csrIsConnStateConnectedInfraAp( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( (eCSR_ASSOC_STATE_TYPE_INFRA_CONNECTED == pMac->roam.roamSession[sessionId].connectState) ||
+        (eCSR_ASSOC_STATE_TYPE_INFRA_DISCONNECTED == pMac->roam.roamSession[sessionId].connectState ) );
+}
+#endif
+
+tANI_BOOLEAN csrIsConnStateDisconnectedWds( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( eCSR_ASSOC_STATE_TYPE_WDS_DISCONNECTED == pMac->roam.roamSession[sessionId].connectState );
+}
+
+tANI_BOOLEAN csrIsConnStateWds( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return( csrIsConnStateConnectedWds( pMac, sessionId ) ||
+        csrIsConnStateDisconnectedWds( pMac, sessionId ) );
+}
+
+tANI_BOOLEAN csrIsAnySessionInConnectState( tpAniSirGlobal pMac )
+{
+    tANI_U32 i;
+    tANI_BOOLEAN fRc = eANI_BOOLEAN_FALSE;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && 
+            ( csrIsConnStateInfra( pMac, i ) || csrIsConnStateIbss( pMac, i ) ) )
+        {
+            fRc = eANI_BOOLEAN_TRUE;
+            break;
+        }
+    }
+
+    return ( fRc );
+}
+
+tANI_S8 csrGetInfraSessionId( tpAniSirGlobal pMac )
+{
+    tANI_U8 i;
+    tANI_S8 sessionid = -1;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && csrIsConnStateInfra( pMac, i )  )
+        {
+            sessionid = i;
+            break;
+        }
+    }
+
+    return ( sessionid );
+}
+
+tANI_U8 csrGetInfraOperationChannel( tpAniSirGlobal pMac, tANI_U8 sessionId)
+{
+    tANI_U8 channel;
+
+    if( CSR_IS_SESSION_VALID( pMac, sessionId ))
+    {
+        channel = pMac->roam.roamSession[sessionId].connectedProfile.operationChannel;
+    }
+    else
+    {
+        channel = 0;
+    }
+    return channel;
+}
+
+//This routine will return operating channel on FIRST BSS that is active/operating to be used for concurrency mode.
+//If other BSS is not up or not connected it will return 0 
+
+tANI_U8 csrGetConcurrentOperationChannel( tpAniSirGlobal pMac )
+{
+  tCsrRoamSession *pSession = NULL;
+  tANI_U8 i = 0;
+
+  for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+  {
+      if( CSR_IS_SESSION_VALID( pMac, i ) )
+      {
+          pSession = CSR_GET_SESSION( pMac, i );
+
+          if (NULL != pSession->pCurRoamProfile)
+          {
+              if (
+                      (((pSession->pCurRoamProfile->csrPersona == VOS_STA_MODE) ||
+                        (pSession->pCurRoamProfile->csrPersona == VOS_P2P_CLIENT_MODE)) &&
+                       (pSession->connectState == eCSR_ASSOC_STATE_TYPE_INFRA_ASSOCIATED)) 
+                      || 
+                      (((pSession->pCurRoamProfile->csrPersona == VOS_P2P_GO_MODE) ||
+                        (pSession->pCurRoamProfile->csrPersona == VOS_STA_SAP_MODE)) &&
+                       (pSession->connectState != eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED))
+                 )
+                  return (pSession->connectedProfile.operationChannel);
+          }
+
+      }
+  }
+  return 0;
+}
+
+tANI_BOOLEAN csrIsAllSessionDisconnected( tpAniSirGlobal pMac )
+{
+    tANI_U32 i;
+    tANI_BOOLEAN fRc = eANI_BOOLEAN_TRUE;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && !csrIsConnStateDisconnected( pMac, i ) )
+        {
+            fRc = eANI_BOOLEAN_FALSE;
+            break;
+        }
+    }
+
+    return ( fRc );
+}
+
+
+tANI_BOOLEAN csrIsInfraConnected( tpAniSirGlobal pMac )
+{
+    tANI_U32 i;
+    tANI_BOOLEAN fRc = eANI_BOOLEAN_FALSE;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && csrIsConnStateConnectedInfra( pMac, i ) )
+        {
+            fRc = eANI_BOOLEAN_TRUE;
+            break;
+        }
+    }
+
+    return ( fRc );
+}
+
+tANI_BOOLEAN csrIsConcurrentInfraConnected( tpAniSirGlobal pMac )
+{
+    tANI_U32 i, noOfConnectedInfra = 0;
+
+    tANI_BOOLEAN fRc = eANI_BOOLEAN_FALSE;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && csrIsConnStateConnectedInfra( pMac, i ) )
+        {
+            ++noOfConnectedInfra;
+        }
+    }
+
+    // More than one Infra Sta Connected
+    if(noOfConnectedInfra > 1)
+    {
+        fRc = eANI_BOOLEAN_TRUE;
+    }
+
+    return ( fRc );
+}
+
+tANI_BOOLEAN csrIsIBSSStarted( tpAniSirGlobal pMac )
+{
+    tANI_U32 i;
+    tANI_BOOLEAN fRc = eANI_BOOLEAN_FALSE;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && csrIsConnStateIbss( pMac, i ) )
+        {
+            fRc = eANI_BOOLEAN_TRUE;
+            break;
+        }
+    }
+
+    return ( fRc );
+}
+
+
+tANI_BOOLEAN csrIsBTAMPStarted( tpAniSirGlobal pMac )
+{
+    tANI_U32 i;
+    tANI_BOOLEAN fRc = eANI_BOOLEAN_FALSE;
+
+    for( i = 0; i < CSR_ROAM_SESSION_MAX; i++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && csrIsConnStateConnectedWds( pMac, i ) )
+        {
+            fRc = eANI_BOOLEAN_TRUE;
+            break;
+        }
+    }
+
+    return ( fRc );
+}
+
+tANI_BOOLEAN csrIsBTAMP( tpAniSirGlobal pMac, tANI_U32 sessionId )
+{
+    return ( csrIsConnStateConnectedWds( pMac, sessionId ) );
+}
+
+
+tANI_BOOLEAN csrIsConnStateDisconnected(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    return (eCSR_ASSOC_STATE_TYPE_NOT_CONNECTED == pMac->roam.roamSession[sessionId].connectState);
+}
+
+tANI_BOOLEAN csrIsValidMcConcurrentSession(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    tCsrRoamSession *pSession = NULL;
+    tANI_U8 Index = 0, ConnId = 0;
+    tVOS_CON_MODE Mode[CSR_ROAM_SESSION_MAX];
+
+    //Check for MCC support
+    if (!pMac->roam.configParam.fenableMCCMode)
+    {
+        return eANI_BOOLEAN_FALSE;
+    }
+
+    for( Index = 0; Index < CSR_ROAM_SESSION_MAX; Index++ ) 
+        Mode[Index] = VOS_MAX_NO_OF_MODE;
+ 
+    for( Index = 0; Index < CSR_ROAM_SESSION_MAX; Index++ )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, Index ) )
+        {
+            pSession = CSR_GET_SESSION( pMac, Index );
+
+            if (NULL != pSession->pCurRoamProfile)
+            {
+                Mode[ConnId] = pSession->pCurRoamProfile->csrPersona;
+                ConnId++;
+             }
+         }
+    }
+
+    Index  = 0;
+    if (Mode[Index] == VOS_STA_MODE && ConnId > Index)
+    {
+        switch (Mode[Index+1])
+        {
+            case VOS_P2P_CLIENT_MODE :
+              return eANI_BOOLEAN_TRUE;
+            case VOS_MAX_NO_OF_MODE :
+            default :
+                 break;
+        }
+    }
+    else if (Mode[Index] == VOS_P2P_CLIENT_MODE && ConnId > Index)
+    {
+        switch (Mode[Index +1])
+        {
+            case VOS_STA_MODE :
+                return eANI_BOOLEAN_TRUE;
+            case VOS_MAX_NO_OF_MODE :
+            default :
+                break;
+         }
+    }
+
+    return eANI_BOOLEAN_FALSE;
+}
+
+static tSirMacCapabilityInfo csrGetBssCapabilities( tSirBssDescription *pSirBssDesc )
+{
+    tSirMacCapabilityInfo dot11Caps;
+
+    //tSirMacCapabilityInfo is 16-bit
+    pal_get_U16( (tANI_U8 *)&pSirBssDesc->capabilityInfo, (tANI_U16 *)&dot11Caps );
+
+    return( dot11Caps );
+}
+
+tANI_BOOLEAN csrIsInfraBssDesc( tSirBssDescription *pSirBssDesc )
+{
+    tSirMacCapabilityInfo dot11Caps = csrGetBssCapabilities( pSirBssDesc );
+
+    return( (tANI_BOOLEAN)dot11Caps.ess );
+}
+
+
+tANI_BOOLEAN csrIsIbssBssDesc( tSirBssDescription *pSirBssDesc )
+{
+    tSirMacCapabilityInfo dot11Caps = csrGetBssCapabilities( pSirBssDesc );
+
+    return( (tANI_BOOLEAN)dot11Caps.ibss );
+}
+
+tANI_BOOLEAN csrIsQoSBssDesc( tSirBssDescription *pSirBssDesc )
+{
+    tSirMacCapabilityInfo dot11Caps = csrGetBssCapabilities( pSirBssDesc );
+
+    return( (tANI_BOOLEAN)dot11Caps.qos );
+}
+
+tANI_BOOLEAN csrIsPrivacy( tSirBssDescription *pSirBssDesc )
+{
+    tSirMacCapabilityInfo dot11Caps = csrGetBssCapabilities( pSirBssDesc );
+
+    return( (tANI_BOOLEAN)dot11Caps.privacy );
+}
+
+
+tANI_BOOLEAN csrIs11dSupported(tpAniSirGlobal pMac)
+{
+    return(pMac->roam.configParam.Is11dSupportEnabled);
+}
+
+
+tANI_BOOLEAN csrIs11hSupported(tpAniSirGlobal pMac)
+{
+    return(pMac->roam.configParam.Is11hSupportEnabled);
+}
+
+
+tANI_BOOLEAN csrIs11eSupported(tpAniSirGlobal pMac)
+{
+    return(pMac->roam.configParam.Is11eSupportEnabled);
+}
+
+tANI_BOOLEAN csrIsMCCSupported ( tpAniSirGlobal pMac )
+{
+   return(pMac->roam.configParam.fenableMCCMode);
+
+}
+
+tANI_BOOLEAN csrIsWmmSupported(tpAniSirGlobal pMac)
+{
+    if(eCsrRoamWmmNoQos == pMac->roam.configParam.WMMSupportMode)
+    {
+       return eANI_BOOLEAN_FALSE;
+    }
+    else
+    {
+       return eANI_BOOLEAN_TRUE;
+    }
+}
+
+
+
+
+//pIes is the IEs for pSirBssDesc2
+tANI_BOOLEAN csrIsSsidEqual( tHalHandle hHal, tSirBssDescription *pSirBssDesc1, 
+                             tSirBssDescription *pSirBssDesc2, tDot11fBeaconIEs *pIes2 )
+{
+    tANI_BOOLEAN fEqual = FALSE;
+    tSirMacSSid Ssid1, Ssid2;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tDot11fBeaconIEs *pIes1 = NULL;
+    tDot11fBeaconIEs *pIesLocal = pIes2;
+
+    do {
+        if( ( NULL == pSirBssDesc1 ) || ( NULL == pSirBssDesc2 ) ) break;
+        if( !pIesLocal && !HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc2, &pIesLocal)) )
+        {
+            smsLog(pMac, LOGE, FL("  fail to parse IEs\n"));
+            break;
+        }
+        if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc1, &pIes1)))
+        {
+            break;
+        }
+        if( ( !pIes1->SSID.present ) || ( !pIesLocal->SSID.present ) ) break;
+        if ( pIes1->SSID.num_ssid != pIesLocal->SSID.num_ssid ) break;
+        palCopyMemory(pMac->hHdd, Ssid1.ssId, pIes1->SSID.ssid, pIes1->SSID.num_ssid);
+        palCopyMemory(pMac->hHdd, Ssid2.ssId, pIesLocal->SSID.ssid, pIesLocal->SSID.num_ssid);
+
+        fEqual = palEqualMemory(pMac->hHdd, Ssid1.ssId, Ssid2.ssId, pIesLocal->SSID.num_ssid );
+
+    } while( 0 );
+    if(pIes1)
+    {
+        palFreeMemory(pMac->hHdd, pIes1);
+    }
+    if( pIesLocal && !pIes2 )
+    {
+        palFreeMemory(pMac->hHdd, pIesLocal);
+    }
+
+    return( fEqual );
+}
+
+tANI_BOOLEAN csrIsAniWmeSupported(tDot11fIEAirgo *pIeAirgo)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_FALSE;
+
+    if(pIeAirgo && pIeAirgo->present && pIeAirgo->PropCapability.present)
+    {
+        fRet = (tANI_BOOLEAN)(PROP_CAPABILITY_GET( WME, pIeAirgo->PropCapability.capability ));
+    }
+
+    return fRet;
+}
+
+
+
+
+//pIes can be passed in as NULL if the caller doesn't have one prepared
+tANI_BOOLEAN csrIsBssDescriptionWme( tHalHandle hHal, tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    // Assume that WME is found...
+    tANI_BOOLEAN fWme = TRUE;
+    tDot11fBeaconIEs *pIesTemp = pIes;
+
+    do
+    {
+        if(pIesTemp == NULL)
+        {
+            if( !HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc, &pIesTemp)) )
+            {
+                fWme = FALSE;
+                break;
+            }
+        }
+        // if the AirgoProprietary indicator is found, then WME is supported...
+        if ( csrIsAniWmeSupported(&pIesTemp->Airgo) ) break;
+        // if the Wme Info IE is found, then WME is supported...
+        if ( CSR_IS_QOS_BSS(pIesTemp) ) break;
+        // if none of these are found, then WME is NOT supported...
+        fWme = FALSE;
+    } while( 0 );
+    if( !csrIsWmmSupported( pMac ) && fWme)
+    {
+        if( !pIesTemp->HTCaps.present )
+        {
+            fWme = FALSE;
+        }
+    }
+    if( ( pIes == NULL ) && ( NULL != pIesTemp ) )
+    {
+        //we allocate memory here so free it before returning
+        palFreeMemory(pMac->hHdd, pIesTemp);
+    }
+
+    return( fWme );
+}
+
+tANI_BOOLEAN csrIsHcfEnabled( tDot11fIEAirgo *pIeAirgo )
+{
+    tANI_BOOLEAN fHcfSupported = FALSE;
+
+    fHcfSupported = ((tANI_BOOLEAN)(PROP_CAPABILITY_GET( WME, pIeAirgo->PropCapability.capability )) ||
+        (pIeAirgo->present && pIeAirgo->HCF.present && pIeAirgo->HCF.enabled));
+
+    return( fHcfSupported );
+}
+
+
+eCsrMediaAccessType csrGetQoSFromBssDesc( tHalHandle hHal, tSirBssDescription *pSirBssDesc, 
+                                          tDot11fBeaconIEs *pIes )
+{
+    eCsrMediaAccessType qosType = eCSR_MEDIUM_ACCESS_DCF;
+
+#if defined(VOSS_ENABLED)
+    VOS_ASSERT( pIes != NULL );
+#endif
+
+    do
+   {
+        // if we find WMM in the Bss Description, then we let this
+        // override and use WMM.
+        if ( csrIsBssDescriptionWme( hHal, pSirBssDesc, pIes ) )
+        {
+            qosType = eCSR_MEDIUM_ACCESS_WMM_eDCF_DSCP;
+        }
+        else
+        {
+            // if the QoS bit is on, then the AP is advertising 11E QoS...
+            if ( csrIsQoSBssDesc( pSirBssDesc ) )
+            {
+                // which could be HCF or eDCF.
+                    if ( csrIsHcfEnabled( &pIes->Airgo ) )
+                {
+                    qosType = eCSR_MEDIUM_ACCESS_11e_HCF;
+                }
+                else
+                {
+                    qosType = eCSR_MEDIUM_ACCESS_11e_eDCF;
+                }
+            }
+            else
+            {
+                qosType = eCSR_MEDIUM_ACCESS_DCF;
+            }
+            // scale back based on the types turned on for the adapter...
+            if ( eCSR_MEDIUM_ACCESS_11e_eDCF == qosType && !csrIs11eSupported( hHal ) )
+            {
+                qosType = eCSR_MEDIUM_ACCESS_DCF;
+            }
+        }
+
+    } while(0);
+
+    return( qosType );
+}
+
+
+
+
+//Caller allocates memory for pIEStruct
+eHalStatus csrParseBssDescriptionIEs(tHalHandle hHal, tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIEStruct)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    int ieLen = (int)(pBssDesc->length + sizeof( pBssDesc->length ) - GET_FIELD_OFFSET( tSirBssDescription, ieFields ));
+
+    if(ieLen > 0 && pIEStruct)
+    {
+        if(!DOT11F_FAILED(dot11fUnpackBeaconIEs( pMac, (tANI_U8 *)pBssDesc->ieFields, ieLen, pIEStruct )))
+        {
+            status = eHAL_STATUS_SUCCESS;
+        }
+    }
+
+    return (status);
+}
+
+
+//This function will allocate memory for the parsed IEs to the caller. Caller must free the memory
+//after it is done with the data only if this function succeeds
+eHalStatus csrGetParsedBssDescriptionIEs(tHalHandle hHal, tSirBssDescription *pBssDesc, tDot11fBeaconIEs **ppIEStruct)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    if(pBssDesc && ppIEStruct)
+    {
+        status = palAllocateMemory(pMac->hHdd, (void **)ppIEStruct, sizeof(tDot11fBeaconIEs));
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, (void *)*ppIEStruct, sizeof(tDot11fBeaconIEs));
+            status = csrParseBssDescriptionIEs(hHal, pBssDesc, *ppIEStruct);
+            if(!HAL_STATUS_SUCCESS(status))
+            {
+                palFreeMemory(pMac->hHdd, *ppIEStruct);
+                *ppIEStruct = NULL;
+            }
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL(" failed to allocate memory\n") );
+            VOS_ASSERT( 0 );
+    }
+    }
+
+    return (status);
+}
+
+
+
+
+tANI_BOOLEAN csrIsNULLSSID( tANI_U8 *pBssSsid, tANI_U8 len )
+{
+    tANI_BOOLEAN fNullSsid = FALSE;
+
+    tANI_U32 SsidLength;
+    tANI_U8 *pSsidStr;
+
+    do
+    {
+        if ( 0 == len )
+        {
+            fNullSsid = TRUE;
+            break;
+        }
+
+        //Consider 0 or space for hidden SSID
+        if ( 0 == pBssSsid[0] )
+        {
+             fNullSsid = TRUE;
+             break;
+        }
+
+        SsidLength = len;
+        pSsidStr = pBssSsid;
+
+        while ( SsidLength )
+        {
+            if( *pSsidStr )
+                break;
+
+            pSsidStr++;
+            SsidLength--;
+        }
+
+        if( 0 == SsidLength )
+        {
+            fNullSsid = TRUE;
+            break;
+        }
+    }
+    while( 0 );
+
+    return fNullSsid;
+}
+
+
+tANI_U32 csrGetFragThresh( tHalHandle hHal )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return pMac->roam.configParam.FragmentationThreshold;
+}
+
+tANI_U32 csrGetRTSThresh( tHalHandle hHal )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return pMac->roam.configParam.RTSThreshold;
+}
+
+eCsrPhyMode csrTranslateToPhyModeFromBssDesc( tSirBssDescription *pSirBssDesc )
+{
+    eCsrPhyMode phyMode;
+
+    switch ( pSirBssDesc->nwType )
+    {
+        case eSIR_11A_NW_TYPE:
+            phyMode = eCSR_DOT11_MODE_11a;
+            break;
+
+        case eSIR_11B_NW_TYPE:
+            phyMode = eCSR_DOT11_MODE_11b;
+            break;
+
+        case eSIR_11G_NW_TYPE:
+            phyMode = eCSR_DOT11_MODE_11g;
+            break;
+
+        case eSIR_11N_NW_TYPE:
+        default:
+            phyMode = eCSR_DOT11_MODE_11n;
+            break;
+    }
+
+    return( phyMode );
+}
+
+
+tANI_U32 csrTranslateToWNICfgDot11Mode(tpAniSirGlobal pMac, eCsrCfgDot11Mode csrDot11Mode)
+{
+    tANI_U32 ret;
+
+    switch(csrDot11Mode)
+    {
+    case eCSR_CFG_DOT11_MODE_AUTO:
+        smsLog(pMac, LOGW, FL("  Warning: sees eCSR_CFG_DOT11_MODE_AUTO \n"));
+        //We cannot decide until now.
+        if(pMac->roam.configParam.ProprietaryRatesEnabled)
+        {
+            ret = WNI_CFG_DOT11_MODE_TAURUS;
+        }
+        else
+        {
+            ret = WNI_CFG_DOT11_MODE_11N;
+        }
+        break;
+    case eCSR_CFG_DOT11_MODE_TAURUS:
+        ret = WNI_CFG_DOT11_MODE_TAURUS;
+        break;
+    case eCSR_CFG_DOT11_MODE_11A:
+        ret = WNI_CFG_DOT11_MODE_11A;
+        break;
+    case eCSR_CFG_DOT11_MODE_11B:
+        ret = WNI_CFG_DOT11_MODE_11B;
+        break;
+    case eCSR_CFG_DOT11_MODE_11G:
+        ret = WNI_CFG_DOT11_MODE_11G;
+        break;
+    case eCSR_CFG_DOT11_MODE_11N:
+        ret = WNI_CFG_DOT11_MODE_11N;
+        break;
+    case eCSR_CFG_DOT11_MODE_POLARIS:
+        ret = WNI_CFG_DOT11_MODE_POLARIS;
+        break;
+    case eCSR_CFG_DOT11_MODE_TITAN:
+        ret = WNI_CFG_DOT11_MODE_TITAN;
+        break;
+#ifdef WLAN_SOFTAP_FEATURE
+    case eCSR_CFG_DOT11_MODE_11G_ONLY:
+       ret = WNI_CFG_DOT11_MODE_11G_ONLY;
+       break;
+    case eCSR_CFG_DOT11_MODE_11N_ONLY:
+       ret = WNI_CFG_DOT11_MODE_11N_ONLY;
+       break;
+#endif
+    default:
+        smsLog(pMac, LOGW, FL("doesn't expect %d as csrDo11Mode\n"), csrDot11Mode);
+        if(eCSR_BAND_24 == pMac->roam.configParam.eBand)
+        {
+            ret = WNI_CFG_DOT11_MODE_11G;
+        }
+        else
+        {
+            ret = WNI_CFG_DOT11_MODE_11A;
+        }
+        break;
+    }
+
+    return (ret);
+}
+
+
+//This function should only return the super set of supported modes. 11n implies 11b/g/a/n.
+eHalStatus csrGetPhyModeFromBss(tpAniSirGlobal pMac, tSirBssDescription *pBSSDescription, 
+                                eCsrPhyMode *pPhyMode, tDot11fBeaconIEs *pIes)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    eCsrPhyMode phyMode = csrTranslateToPhyModeFromBssDesc(pBSSDescription);
+
+    if( pIes )
+    {
+        if(pIes->Airgo.present)
+        {
+            if(pIes->Airgo.PropCapability.present)
+            {
+                if( PROP_CAPABILITY_GET( TAURUS, pIes->Airgo.PropCapability.capability ))
+                {
+                    phyMode = eCSR_DOT11_MODE_TAURUS;
+                }
+                }
+                }
+        if(pIes->HTCaps.present && (eCSR_DOT11_MODE_TAURUS != phyMode))
+        {
+            phyMode = eCSR_DOT11_MODE_11n;
+        }
+        *pPhyMode = phyMode;
+    }
+
+    return (status);
+
+}
+
+
+//This function returns the correct eCSR_CFG_DOT11_MODE is the two phyModes matches
+//bssPhyMode is the mode derived from the BSS description
+//f5GhzBand is derived from the channel id of BSS description
+tANI_BOOLEAN csrGetPhyModeInUse( eCsrPhyMode phyModeIn, eCsrPhyMode bssPhyMode, tANI_BOOLEAN f5GhzBand,
+                                 eCsrCfgDot11Mode *pCfgDot11ModeToUse )
+{
+    tANI_BOOLEAN fMatch = FALSE;
+    eCsrCfgDot11Mode cfgDot11Mode;
+
+    cfgDot11Mode = eCSR_CFG_DOT11_MODE_11N; // to suppress compiler warning
+
+    switch( phyModeIn )
+    {
+        case eCSR_DOT11_MODE_abg:   //11a or 11b or 11g
+            if( f5GhzBand )
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+            }
+            else if( eCSR_DOT11_MODE_11b == bssPhyMode )
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+            }
+            else
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11G;
+            }
+            break;
+
+        case eCSR_DOT11_MODE_11a:   //11a
+            if( f5GhzBand )
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+            }
+            break;
+
+        case eCSR_DOT11_MODE_11a_ONLY:   //11a
+            if( eCSR_DOT11_MODE_11a == bssPhyMode )
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+            }
+            break;
+
+        case eCSR_DOT11_MODE_11g:
+            if(!f5GhzBand)
+            {
+                if( eCSR_DOT11_MODE_11b == bssPhyMode )
+                {
+                    fMatch = TRUE;
+                    cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+                }
+                else
+                {
+                    fMatch = TRUE;
+                    cfgDot11Mode = eCSR_CFG_DOT11_MODE_11G;
+                }
+            }
+            break;
+
+        case eCSR_DOT11_MODE_11g_ONLY:
+            if( eCSR_DOT11_MODE_11g == bssPhyMode )
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11G;
+            }
+            break;
+
+        case eCSR_DOT11_MODE_11b:
+            if( !f5GhzBand )
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+            }
+            break;
+
+        case eCSR_DOT11_MODE_11b_ONLY:
+            if( eCSR_DOT11_MODE_11b == bssPhyMode )
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+            }
+            break;
+
+        case eCSR_DOT11_MODE_11n:
+            fMatch = TRUE;
+            switch(bssPhyMode)
+            {
+            case eCSR_DOT11_MODE_11g:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11G;
+                break;
+            case eCSR_DOT11_MODE_11b:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+                break;
+            case eCSR_DOT11_MODE_11a:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+                break;
+            case eCSR_DOT11_MODE_11n:
+            case eCSR_DOT11_MODE_TAURUS:
+            default:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11N;
+                break;
+            }
+            break;
+
+        case eCSR_DOT11_MODE_11n_ONLY:
+            if((eCSR_DOT11_MODE_11n == bssPhyMode) || (eCSR_DOT11_MODE_TAURUS == bssPhyMode))
+            {
+                fMatch = TRUE;
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11N;
+            }
+            break;
+
+        case eCSR_DOT11_MODE_TAURUS:
+        default:
+            fMatch = TRUE;
+            switch(bssPhyMode)
+            {
+            case eCSR_DOT11_MODE_11g:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11G;
+                break;
+            case eCSR_DOT11_MODE_11b:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+                break;
+            case eCSR_DOT11_MODE_11a:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+                break;
+            case eCSR_DOT11_MODE_11n:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_11N;
+                break;
+            case eCSR_DOT11_MODE_TAURUS:
+            default:
+                cfgDot11Mode = eCSR_CFG_DOT11_MODE_TAURUS;
+                break;
+            }
+            break;
+
+    }
+
+    if ( fMatch && pCfgDot11ModeToUse )
+    {
+        *pCfgDot11ModeToUse = cfgDot11Mode;
+    }
+
+    return( fMatch );
+}
+
+
+//This function decides whether the one of the bit of phyMode is matching the mode in the BSS and allowed by the user
+//setting, pMac->roam.configParam.uCfgDot11Mode. It returns the mode that fits the criteria.
+tANI_BOOLEAN csrIsPhyModeMatch( tpAniSirGlobal pMac, tANI_U32 phyMode,
+                                tSirBssDescription *pSirBssDesc, tCsrRoamProfile *pProfile,
+                                eCsrCfgDot11Mode *pReturnCfgDot11Mode,
+                                tDot11fBeaconIEs *pIes)
+{
+    tANI_BOOLEAN fMatch = FALSE;
+    eCsrPhyMode phyModeInBssDesc, phyMode2;
+    eCsrCfgDot11Mode cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_TAURUS;
+    tANI_U32 bitMask, loopCount;
+
+    if(HAL_STATUS_SUCCESS(csrGetPhyModeFromBss(pMac, pSirBssDesc, &phyModeInBssDesc, pIes )))
+    {
+        //In case some change change eCSR_DOT11_MODE_TAURUS to non-0
+        if ( (0 == phyMode) || (eCSR_DOT11_MODE_AUTO & phyMode) || (eCSR_DOT11_MODE_TAURUS & phyMode))
+        {
+            //Taurus means anything
+            if ( eCSR_CFG_DOT11_MODE_ABG == pMac->roam.configParam.uCfgDot11Mode )
+            {
+                phyMode = eCSR_DOT11_MODE_abg;
+            }
+            else if(eCSR_CFG_DOT11_MODE_AUTO == pMac->roam.configParam.uCfgDot11Mode)
+            {
+                if(pMac->roam.configParam.ProprietaryRatesEnabled)
+                {
+                    phyMode = eCSR_DOT11_MODE_TAURUS;
+                }
+                else
+                {
+                    phyMode = eCSR_DOT11_MODE_11n;
+                }
+            }
+            else
+            {
+                //user's pick
+                phyMode = pMac->roam.configParam.phyMode;
+            }
+        }
+        if ( (0 == phyMode) || (eCSR_DOT11_MODE_AUTO & phyMode) || (eCSR_DOT11_MODE_TAURUS & phyMode) )
+        {
+            if(0 != phyMode)
+            {
+                if(eCSR_DOT11_MODE_AUTO & phyMode)
+                {
+                    phyMode2 = eCSR_DOT11_MODE_AUTO & phyMode;
+                }
+                else
+                {
+                    phyMode2 = eCSR_DOT11_MODE_TAURUS & phyMode;
+                }
+            }
+            else
+            {
+                phyMode2 = phyMode;
+            }
+            fMatch = csrGetPhyModeInUse( phyMode2, phyModeInBssDesc, CSR_IS_CHANNEL_5GHZ(pSirBssDesc->channelId),
+                                                &cfgDot11ModeToUse );
+        }
+        else
+        {
+            bitMask = 1;
+            loopCount = 0;
+            while(loopCount < eCSR_NUM_PHY_MODE)   
+            {
+                if(0 != ( phyMode2 = (phyMode & (bitMask << loopCount++)) ))
+                {
+                    fMatch = csrGetPhyModeInUse( phyMode2, phyModeInBssDesc, CSR_IS_CHANNEL_5GHZ(pSirBssDesc->channelId),
+                                        &cfgDot11ModeToUse );
+                    if(fMatch) break;
+                }
+            }
+        }
+        if ( fMatch && pReturnCfgDot11Mode )
+        {
+            if( pProfile )
+            {
+                /* IEEE 11n spec (8.4.3): HT STA shall eliminate TKIP as a 
+                 * choice for the pairwise cipher suite if CCMP is advertised 
+                 * by the AP or if the AP included an HT capabilities element 
+                 * in its Beacons and Probe Response.
+                 */
+                if( (!CSR_IS_11n_ALLOWED( pProfile->negotiatedUCEncryptionType )) &&
+                    ((eCSR_CFG_DOT11_MODE_11N == cfgDot11ModeToUse) ||
+                     (eCSR_CFG_DOT11_MODE_TAURUS == cfgDot11ModeToUse)) )
+                {
+                    //We cannot do 11n here
+                    if( !CSR_IS_CHANNEL_5GHZ(pSirBssDesc->channelId) )
+                    {
+                        cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11G;
+                    }
+                    else
+                    {
+                        cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11A;
+                    }
+                }
+            }
+            *pReturnCfgDot11Mode = cfgDot11ModeToUse;
+        }
+    }
+
+    return( fMatch );
+}
+
+
+eCsrCfgDot11Mode csrFindBestPhyMode( tpAniSirGlobal pMac, tANI_U32 phyMode )
+{
+    eCsrCfgDot11Mode cfgDot11ModeToUse;
+    eCsrBand eBand = pMac->roam.configParam.eBand;
+
+    if ( (0 == phyMode) || (eCSR_DOT11_MODE_AUTO & phyMode) || (eCSR_DOT11_MODE_TAURUS & phyMode))
+    {
+        cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11N;
+    }
+    else
+    {
+        if( ( eCSR_DOT11_MODE_11n | eCSR_DOT11_MODE_11n_ONLY ) & phyMode )
+        {
+            cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11N;
+        }
+        else if ( eCSR_DOT11_MODE_abg & phyMode )
+        {
+            if( eCSR_BAND_24 != eBand )
+            {
+                cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11A;
+            }
+            else
+            {
+                cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11G;
+            }
+        }
+        else if( ( eCSR_DOT11_MODE_11a | eCSR_DOT11_MODE_11a_ONLY ) & phyMode )
+        {
+            cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11A;
+        }
+        else if( ( eCSR_DOT11_MODE_11g | eCSR_DOT11_MODE_11g_ONLY ) & phyMode )
+        {
+            cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11G;
+        }
+        else
+        {
+            cfgDot11ModeToUse = eCSR_CFG_DOT11_MODE_11B;
+        }
+    }
+
+    return ( cfgDot11ModeToUse );
+}
+
+
+
+
+tANI_U32 csrGet11hPowerConstraint( tHalHandle hHal, tDot11fIEPowerConstraints *pPowerConstraint )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_U32 localPowerConstraint = 0;
+
+    // check if .11h support is enabled, if not, the power constraint is 0.
+    if(pMac->roam.configParam.Is11hSupportEnabled && pPowerConstraint->present)
+    {
+        localPowerConstraint = pPowerConstraint->localPowerConstraints;
+    }
+
+    return( localPowerConstraint );
+}
+
+
+tANI_BOOLEAN csrIsProfileWpa( tCsrRoamProfile *pProfile )
+{
+    tANI_BOOLEAN fWpaProfile = FALSE;
+
+    switch ( pProfile->negotiatedAuthType )
+    {
+        case eCSR_AUTH_TYPE_WPA:
+        case eCSR_AUTH_TYPE_WPA_PSK:
+        case eCSR_AUTH_TYPE_WPA_NONE:
+#ifdef FEATURE_WLAN_CCX
+        case eCSR_AUTH_TYPE_CCKM_WPA:
+#endif
+            fWpaProfile = TRUE;
+            break;
+
+        default:
+            fWpaProfile = FALSE;
+            break;
+    }
+
+    if ( fWpaProfile )
+    {
+        switch ( pProfile->negotiatedUCEncryptionType )
+        {
+            case eCSR_ENCRYPT_TYPE_WEP40:
+            case eCSR_ENCRYPT_TYPE_WEP104:
+            case eCSR_ENCRYPT_TYPE_TKIP:
+            case eCSR_ENCRYPT_TYPE_AES:
+                fWpaProfile = TRUE;
+                break;
+
+            default:
+                fWpaProfile = FALSE;
+                break;
+        }
+    }
+    return( fWpaProfile );
+}
+
+tANI_BOOLEAN csrIsProfileRSN( tCsrRoamProfile *pProfile )
+{
+    tANI_BOOLEAN fRSNProfile = FALSE;
+
+    switch ( pProfile->negotiatedAuthType )
+    {
+        case eCSR_AUTH_TYPE_RSN:
+        case eCSR_AUTH_TYPE_RSN_PSK:
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        case eCSR_AUTH_TYPE_FT_RSN:
+        case eCSR_AUTH_TYPE_FT_RSN_PSK:
+#endif 
+#ifdef FEATURE_WLAN_CCX
+        case eCSR_AUTH_TYPE_CCKM_RSN:
+#endif 
+            fRSNProfile = TRUE;
+            break;
+
+        default:
+            fRSNProfile = FALSE;
+            break;
+    }
+
+    if ( fRSNProfile )
+    {
+        switch ( pProfile->negotiatedUCEncryptionType )
+        {
+            // !!REVIEW - For WPA2, use of RSN IE mandates
+            // use of AES as encryption. Here, we qualify
+            // even if encryption type is WEP or TKIP
+            case eCSR_ENCRYPT_TYPE_WEP40:
+            case eCSR_ENCRYPT_TYPE_WEP104:
+            case eCSR_ENCRYPT_TYPE_TKIP:
+            case eCSR_ENCRYPT_TYPE_AES:
+                fRSNProfile = TRUE;
+                break;
+
+            default:
+                fRSNProfile = FALSE;
+                break;
+        }
+    }
+    return( fRSNProfile );
+}
+
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/* Function to return TRUE if the authtype is 11r */
+tANI_BOOLEAN csrIsAuthType11r( eCsrAuthType AuthType )
+{
+    switch ( AuthType )
+    {
+        case eCSR_AUTH_TYPE_FT_RSN_PSK:
+        case eCSR_AUTH_TYPE_FT_RSN:
+            return TRUE;
+            break;
+        default:
+            break;
+    }
+    return FALSE;
+}
+
+/* Function to return TRUE if the profile is 11r */
+tANI_BOOLEAN csrIsProfile11r( tCsrRoamProfile *pProfile )
+{
+    return csrIsAuthType11r( pProfile->negotiatedAuthType );
+}
+
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+
+/* Function to return TRUE if the authtype is CCX */
+tANI_BOOLEAN csrIsAuthTypeCCX( eCsrAuthType AuthType )
+{
+    switch ( AuthType )
+    {
+        case eCSR_AUTH_TYPE_CCKM_WPA:
+        case eCSR_AUTH_TYPE_CCKM_RSN:
+            return TRUE;
+            break;
+        default:
+            break;
+    }
+    return FALSE;
+}
+
+/* Function to return TRUE if the profile is CCX */
+tANI_BOOLEAN csrIsProfileCCX( tCsrRoamProfile *pProfile )
+{
+    return (csrIsAuthTypeCCX( pProfile->negotiatedAuthType ));
+}
+
+#endif
+
+#ifdef FEATURE_WLAN_WAPI
+tANI_BOOLEAN csrIsProfileWapi( tCsrRoamProfile *pProfile )
+{
+    tANI_BOOLEAN fWapiProfile = FALSE;
+
+    switch ( pProfile->negotiatedAuthType )
+    {
+        case eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE:
+        case eCSR_AUTH_TYPE_WAPI_WAI_PSK:
+            fWapiProfile = TRUE;
+            break;
+
+        default:
+            fWapiProfile = FALSE;
+            break;
+    }
+
+    if ( fWapiProfile )
+    {
+        switch ( pProfile->negotiatedUCEncryptionType )
+        {
+            case eCSR_ENCRYPT_TYPE_WPI:
+                fWapiProfile = TRUE;
+                break;
+
+            default:
+                fWapiProfile = FALSE;
+                break;
+        }
+    }
+    return( fWapiProfile );
+}
+
+static tANI_BOOLEAN csrIsWapiOuiEqual( tpAniSirGlobal pMac, tANI_U8 *Oui1, tANI_U8 *Oui2 )
+{
+    return( palEqualMemory(pMac->hHdd, Oui1, Oui2, CSR_WAPI_OUI_SIZE ) );
+}
+
+static tANI_BOOLEAN csrIsWapiOuiMatch( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WAPI_OUI_SIZE],
+                                     tANI_U8 cAllCyphers,
+                                     tANI_U8 Cypher[],
+                                     tANI_U8 Oui[] )
+{
+    tANI_BOOLEAN fYes = FALSE;
+    tANI_U8 idx;
+
+    for ( idx = 0; idx < cAllCyphers; idx++ )
+    {
+        if ( csrIsWapiOuiEqual( pMac, AllCyphers[ idx ], Cypher ) )
+        {
+            fYes = TRUE;
+            break;
+        }
+    }
+
+    if ( fYes && Oui )
+    {
+        palCopyMemory( pMac->hHdd, Oui, AllCyphers[ idx ], CSR_WAPI_OUI_SIZE );
+    }
+
+    return( fYes );
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+static tANI_BOOLEAN csrIsWpaOuiEqual( tpAniSirGlobal pMac, tANI_U8 *Oui1, tANI_U8 *Oui2 )
+{
+    return( palEqualMemory(pMac->hHdd, Oui1, Oui2, CSR_WPA_OUI_SIZE ) );
+}
+
+static tANI_BOOLEAN csrIsOuiMatch( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WPA_OUI_SIZE],
+                                     tANI_U8 cAllCyphers,
+                                     tANI_U8 Cypher[],
+                                     tANI_U8 Oui[] )
+{
+    tANI_BOOLEAN fYes = FALSE;
+    tANI_U8 idx;
+
+    for ( idx = 0; idx < cAllCyphers; idx++ )
+    {
+        if ( csrIsWpaOuiEqual( pMac, AllCyphers[ idx ], Cypher ) )
+        {
+            fYes = TRUE;
+            break;
+        }
+    }
+
+    if ( fYes && Oui )
+    {
+        palCopyMemory( pMac->hHdd, Oui, AllCyphers[ idx ], CSR_WPA_OUI_SIZE );
+    }
+
+    return( fYes );
+}
+
+static tANI_BOOLEAN csrMatchRSNOUIIndex( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_RSN_OUI_SIZE],
+                                            tANI_U8 cAllCyphers, tANI_U8 ouiIndex,
+                                            tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrRSNOui[ouiIndex], Oui ) );
+
+}
+
+#ifdef FEATURE_WLAN_WAPI
+static tANI_BOOLEAN csrMatchWapiOUIIndex( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WAPI_OUI_SIZE],
+                                            tANI_U8 cAllCyphers, tANI_U8 ouiIndex,
+                                            tANI_U8 Oui[] )
+{
+    return( csrIsWapiOuiMatch( pMac, AllCyphers, cAllCyphers, csrWapiOui[ouiIndex], Oui ) );
+
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+static tANI_BOOLEAN csrMatchWPAOUIIndex( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_RSN_OUI_SIZE],
+                                            tANI_U8 cAllCyphers, tANI_U8 ouiIndex,
+                                            tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrWpaOui[ouiIndex], Oui ) );
+
+}
+
+#if 0
+static tANI_BOOLEAN csrIsRSNUnicastNone( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_RSN_OUI_SIZE],
+                                            tANI_U8 cAllCyphers,
+                                            tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrRSNOui00, Oui ) );
+}
+
+static tANI_BOOLEAN csrIsRSNMulticastWep( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_RSN_OUI_SIZE],
+                                           tANI_U8 cAllCyphers,
+                                           tANI_U8 Oui[] )
+{
+    tANI_BOOLEAN fYes = FALSE;
+
+    // Check Wep 104 first, if fails, then check Wep40.
+    fYes = csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrRSNOui05, Oui );
+
+    if ( !fYes )
+    {
+        // if not Wep-104, check Wep-40
+        fYes = csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrRSNOui01, Oui );
+    }
+
+    return( fYes );
+}
+
+
+static tANI_BOOLEAN csrIsRSNUnicastTkip( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_RSN_OUI_SIZE],
+                                    tANI_U8 cAllCyphers,
+                                    tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrRSNOui02, Oui ) );
+}
+
+
+static tANI_BOOLEAN csrIsRSNMulticastTkip( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_RSN_OUI_SIZE],
+                                              tANI_U8 cAllCyphers,
+                                              tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrRSNOui02, Oui ) );
+}
+
+static tANI_BOOLEAN csrIsRSNUnicastAes( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_RSN_OUI_SIZE],
+                                              tANI_U8 cAllCyphers,
+                                              tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrRSNOui04, Oui ) );
+}
+
+static tANI_BOOLEAN csrIsRSNMulticastAes( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_RSN_OUI_SIZE],
+                                              tANI_U8 cAllCyphers,
+                                              tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrRSNOui04, Oui ) );
+}
+#endif
+#ifdef FEATURE_WLAN_WAPI
+static tANI_BOOLEAN csrIsAuthWapiCert( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_WAPI_OUI_SIZE],
+                                  tANI_U8 cAllSuites,
+                                  tANI_U8 Oui[] )
+{
+    return( csrIsWapiOuiMatch( pMac, AllSuites, cAllSuites, csrWapiOui[1], Oui ) );
+}
+static tANI_BOOLEAN csrIsAuthWapiPsk( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_WAPI_OUI_SIZE],
+                                      tANI_U8 cAllSuites,
+                                      tANI_U8 Oui[] )
+{
+    return( csrIsWapiOuiMatch( pMac, AllSuites, cAllSuites, csrWapiOui[2], Oui ) );
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+
+/* 
+ * Function for 11R FT Authentication. We match the FT Authentication Cipher suite
+ * here. This matches for FT Auth with the 802.1X exchange.
+ *
+ */
+static tANI_BOOLEAN csrIsFTAuthRSN( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_RSN_OUI_SIZE],
+                                  tANI_U8 cAllSuites,
+                                  tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[03], Oui ) );
+}
+
+/* 
+ * Function for 11R FT Authentication. We match the FT Authentication Cipher suite
+ * here. This matches for FT Auth with the PSK.
+ *
+ */
+static tANI_BOOLEAN csrIsFTAuthRSNPsk( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_RSN_OUI_SIZE],
+                                      tANI_U8 cAllSuites,
+                                      tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[04], Oui ) );
+}
+
+#endif
+
+#ifdef FEATURE_WLAN_CCX
+
+/* 
+ * Function for CCX CCKM AKM Authentication. We match the CCKM AKM Authentication Key Management suite
+ * here. This matches for CCKM AKM Auth with the 802.1X exchange.
+ *
+ */
+static tANI_BOOLEAN csrIsCcxCckmAuthRSN( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_RSN_OUI_SIZE],
+                                  tANI_U8 cAllSuites,
+                                  tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[06], Oui ) );
+}
+
+static tANI_BOOLEAN csrIsCcxCckmAuthWpa( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_WPA_OUI_SIZE],
+                                tANI_U8 cAllSuites,
+                                tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrWpaOui[06], Oui ) );
+}
+
+#endif
+
+static tANI_BOOLEAN csrIsAuthRSN( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_RSN_OUI_SIZE],
+                                  tANI_U8 cAllSuites,
+                                  tANI_U8 Oui[] )
+{
+#ifdef WLAN_FEATURE_11W
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[01], Oui ) ||
+            csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[05], Oui ));
+#else
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[01], Oui ) );
+#endif
+}
+static tANI_BOOLEAN csrIsAuthRSNPsk( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_RSN_OUI_SIZE],
+                                      tANI_U8 cAllSuites,
+                                      tANI_U8 Oui[] )
+{
+#ifdef WLAN_FEATURE_11W
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[02], Oui ) ||
+            csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[06], Oui ) );
+#else
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrRSNOui[02], Oui ) );
+#endif
+}
+
+static tANI_BOOLEAN csrIsAuthWpa( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_WPA_OUI_SIZE],
+                                tANI_U8 cAllSuites,
+                                tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrWpaOui[01], Oui ) );
+}
+
+#ifdef NOT_CURRENTLY_USED
+static tANI_BOOLEAN csrIsAuth802_1x( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_WPA_OUI_SIZE],
+                                tANI_U8 cAllSuites,
+                                tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrWpaOui[00], Oui ) );
+}
+#endif // NOT_CURRENTLY_USED
+
+static tANI_BOOLEAN csrIsAuthWpaPsk( tpAniSirGlobal pMac, tANI_U8 AllSuites[][CSR_WPA_OUI_SIZE],
+                                tANI_U8 cAllSuites,
+                                tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllSuites, cAllSuites, csrWpaOui[02], Oui ) );
+}
+#if 0
+static tANI_BOOLEAN csrIsUnicastNone( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WPA_OUI_SIZE],
+                                      tANI_U8 cAllCyphers,
+                                      tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrWpaOui00, Oui ) );
+}
+
+static tANI_BOOLEAN csrIsUnicastTkip( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WPA_OUI_SIZE],
+                                      tANI_U8 cAllCyphers,
+                                      tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrWpaOui02, Oui ) );
+}
+
+static tANI_BOOLEAN csrIsUnicastAes( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WPA_OUI_SIZE],
+                                      tANI_U8 cAllCyphers,
+                                      tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrWpaOui04, Oui ) );
+}
+
+
+static tANI_BOOLEAN csrIsMulticastWep( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WPA_OUI_SIZE],
+                                          tANI_U8 cAllCyphers,
+                                          tANI_U8 Oui[] )
+{
+    tANI_BOOLEAN fYes = FALSE;
+
+    // Check Wep 104 first, if fails, then check Wep40.
+    fYes = csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrWpaOui05, Oui );
+
+    if ( !fYes )
+    {
+        // if not Wep-104, check Wep-40
+        fYes = csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrWpaOui01, Oui );
+    }
+
+    return( fYes );
+}
+
+
+static tANI_BOOLEAN csrIsMulticastTkip( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WPA_OUI_SIZE],
+                                          tANI_U8 cAllCyphers,
+                                          tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrWpaOui02, Oui ) );
+}
+
+
+static tANI_BOOLEAN csrIsMulticastAes( tpAniSirGlobal pMac, tANI_U8 AllCyphers[][CSR_WPA_OUI_SIZE],
+                                          tANI_U8 cAllCyphers,
+                                          tANI_U8 Oui[] )
+{
+    return( csrIsOuiMatch( pMac, AllCyphers, cAllCyphers, csrWpaOui04, Oui ) );
+}
+
+#endif
+
+tANI_U8 csrGetOUIIndexFromCipher( eCsrEncryptionType enType )
+{
+    tANI_U8 OUIIndex;
+
+        switch ( enType )
+        {
+            case eCSR_ENCRYPT_TYPE_WEP40:
+            case eCSR_ENCRYPT_TYPE_WEP40_STATICKEY:
+                OUIIndex = CSR_OUI_WEP40_OR_1X_INDEX;
+                break;
+            case eCSR_ENCRYPT_TYPE_WEP104:
+            case eCSR_ENCRYPT_TYPE_WEP104_STATICKEY:
+                OUIIndex = CSR_OUI_WEP104_INDEX;
+                break;
+            case eCSR_ENCRYPT_TYPE_TKIP:
+                OUIIndex = CSR_OUI_TKIP_OR_PSK_INDEX;
+                break;
+            case eCSR_ENCRYPT_TYPE_AES:
+                OUIIndex = CSR_OUI_AES_INDEX;
+                break;
+            case eCSR_ENCRYPT_TYPE_NONE:
+                OUIIndex = CSR_OUI_USE_GROUP_CIPHER_INDEX;
+                break;
+#ifdef FEATURE_WLAN_WAPI
+           case eCSR_ENCRYPT_TYPE_WPI:
+               OUIIndex = CSR_OUI_WAPI_WAI_CERT_OR_SMS4_INDEX;
+               break;
+#endif /* FEATURE_WLAN_WAPI */
+            default: //HOWTO handle this?
+                OUIIndex = CSR_OUI_RESERVED_INDEX;
+                break;
+        }//switch
+
+        return OUIIndex;
+}
+
+tANI_BOOLEAN csrGetRSNInformation( tHalHandle hHal, tCsrAuthList *pAuthType, eCsrEncryptionType enType, tCsrEncryptionList *pMCEncryption,
+                                   tDot11fIERSN *pRSNIe,
+                           tANI_U8 *UnicastCypher,
+                           tANI_U8 *MulticastCypher,
+                           tANI_U8 *AuthSuite,
+                           tCsrRSNCapabilities *Capabilities,
+                           eCsrAuthType *pNegotiatedAuthtype,
+                           eCsrEncryptionType *pNegotiatedMCCipher )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fAcceptableCyphers = FALSE;
+    tANI_U8 cUnicastCyphers = 0;
+    tANI_U8 cMulticastCyphers = 0;
+    tANI_U8 cAuthSuites = 0, i;
+    tANI_U8 Unicast[ CSR_RSN_OUI_SIZE ];
+    tANI_U8 Multicast[ CSR_RSN_OUI_SIZE ];
+    tANI_U8 AuthSuites[ CSR_RSN_MAX_AUTH_SUITES ][ CSR_RSN_OUI_SIZE ];
+    tANI_U8 Authentication[ CSR_RSN_OUI_SIZE ];
+    tANI_U8 MulticastCyphers[ CSR_RSN_MAX_MULTICAST_CYPHERS ][ CSR_RSN_OUI_SIZE ];
+    eCsrAuthType negAuthType = eCSR_AUTH_TYPE_UNKNOWN;
+
+    do{
+        if ( pRSNIe->present )
+        {
+            cMulticastCyphers++;
+            palCopyMemory(pMac->hHdd, MulticastCyphers, pRSNIe->gp_cipher_suite, CSR_RSN_OUI_SIZE);
+            cUnicastCyphers = (tANI_U8)(pRSNIe->pwise_cipher_suite_count);
+            cAuthSuites = (tANI_U8)(pRSNIe->akm_suite_count);
+            for(i = 0; i < cAuthSuites && i < CSR_RSN_MAX_AUTH_SUITES; i++)
+            {
+                palCopyMemory(pMac->hHdd, (void *)&AuthSuites[i],
+                        (void *)&pRSNIe->akm_suites[i], CSR_RSN_OUI_SIZE);
+            }
+
+            //Check - Is requested Unicast Cipher supported by the BSS.
+            fAcceptableCyphers = csrMatchRSNOUIIndex( pMac, pRSNIe->pwise_cipher_suites, cUnicastCyphers, 
+                    csrGetOUIIndexFromCipher( enType ), Unicast ); 
+
+            if( !fAcceptableCyphers ) break;
+
+
+            //Unicast is supported. Pick the first matching Group cipher, if any.
+            for( i = 0 ; i < pMCEncryption->numEntries ; i++ )
+            {
+                fAcceptableCyphers = csrMatchRSNOUIIndex( pMac, MulticastCyphers,  cMulticastCyphers, 
+                            csrGetOUIIndexFromCipher( pMCEncryption->encryptionType[i] ), Multicast );
+                if(fAcceptableCyphers)
+                {
+                    break;
+                }
+            }
+            if( !fAcceptableCyphers ) break;
+
+            if( pNegotiatedMCCipher )
+                *pNegotiatedMCCipher = pMCEncryption->encryptionType[i];
+            
+            /* Initializing with FALSE as it has TRUE value already */
+            fAcceptableCyphers = FALSE;
+            for (i = 0 ; i < pAuthType->numEntries; i++)
+            {
+                //Ciphers are supported, Match authentication algorithm and pick first matching authtype.
+ #ifdef WLAN_FEATURE_VOWIFI_11R
+                /* Changed the AKM suites according to order of preference */
+                if ( csrIsFTAuthRSN( pMac, AuthSuites, cAuthSuites, Authentication ) )
+                {
+                    if (eCSR_AUTH_TYPE_FT_RSN == pAuthType->authType[i])
+                        negAuthType = eCSR_AUTH_TYPE_FT_RSN;
+                }
+                if ( (negAuthType == eCSR_AUTH_TYPE_UNKNOWN) && csrIsFTAuthRSNPsk( pMac, AuthSuites, cAuthSuites, Authentication ) )
+                {
+                    if (eCSR_AUTH_TYPE_FT_RSN_PSK == pAuthType->authType[i])
+                        negAuthType = eCSR_AUTH_TYPE_FT_RSN_PSK;
+                }
+#endif
+#ifdef FEATURE_WLAN_CCX
+                /* CCX only supports 802.1X.  No PSK. */
+                if ( (negAuthType == eCSR_AUTH_TYPE_UNKNOWN) && csrIsCcxCckmAuthRSN( pMac, AuthSuites, cAuthSuites, Authentication ) )
+                {
+                    if (eCSR_AUTH_TYPE_CCKM_RSN == pAuthType->authType[i])
+                        negAuthType = eCSR_AUTH_TYPE_CCKM_RSN;
+                }
+#endif
+                if ( (negAuthType == eCSR_AUTH_TYPE_UNKNOWN) && csrIsAuthRSN( pMac, AuthSuites, cAuthSuites, Authentication ) )
+                {
+                    if (eCSR_AUTH_TYPE_RSN == pAuthType->authType[i])
+                        negAuthType = eCSR_AUTH_TYPE_RSN;
+                }
+                if ((negAuthType == eCSR_AUTH_TYPE_UNKNOWN) && csrIsAuthRSNPsk( pMac, AuthSuites, cAuthSuites, Authentication ) )
+                {
+                    if (eCSR_AUTH_TYPE_RSN_PSK == pAuthType->authType[i])
+                        negAuthType = eCSR_AUTH_TYPE_RSN_PSK;
+                }
+
+                // The 1st auth type in the APs RSN IE, to match stations connecting
+                // profiles auth type will cause us to exit this loop
+                // This is added as some APs advertise multiple akms in the RSN IE.
+                if (eCSR_AUTH_TYPE_UNKNOWN != negAuthType)
+                {
+                    fAcceptableCyphers = TRUE;
+                    break;
+                }
+            } // for
+        }
+
+    }while (0);
+
+    if ( fAcceptableCyphers )
+    {
+        if ( MulticastCypher )
+        {
+            palCopyMemory( pMac->hHdd, MulticastCypher, Multicast, CSR_RSN_OUI_SIZE );
+        }
+
+        if ( UnicastCypher )
+        {
+            palCopyMemory( pMac->hHdd, UnicastCypher, Unicast, CSR_RSN_OUI_SIZE );
+        }
+
+        if ( AuthSuite )
+        {
+            palCopyMemory( pMac->hHdd, AuthSuite, Authentication, CSR_RSN_OUI_SIZE );
+        }
+
+        if ( pNegotiatedAuthtype )
+        {
+            *pNegotiatedAuthtype = negAuthType;
+        }
+        if ( Capabilities )
+        {
+            Capabilities->PreAuthSupported = pRSNIe->preauth;
+            Capabilities->NoPairwise = pRSNIe->no_pwise;
+            Capabilities->PTKSAReplayCounter = pRSNIe->PTKSA_replay_counter;
+            Capabilities->GTKSAReplayCounter = pRSNIe->GTKSA_replay_counter;
+            Capabilities->Reserved = pRSNIe->reserved;
+        }
+    }
+    return( fAcceptableCyphers );
+}
+
+
+tANI_BOOLEAN csrIsRSNMatch( tHalHandle hHal, tCsrAuthList *pAuthType, eCsrEncryptionType enType, tCsrEncryptionList *pEnMcType, 
+                            tDot11fBeaconIEs *pIes, eCsrAuthType *pNegotiatedAuthType, eCsrEncryptionType *pNegotiatedMCCipher )
+{
+    tANI_BOOLEAN fRSNMatch = FALSE;
+
+        // See if the cyphers in the Bss description match with the settings in the profile.
+    fRSNMatch = csrGetRSNInformation( hHal, pAuthType, enType, pEnMcType, &pIes->RSN, NULL, NULL, NULL, NULL, 
+                                      pNegotiatedAuthType, pNegotiatedMCCipher );
+
+    return( fRSNMatch );
+}
+
+
+tANI_BOOLEAN csrLookupPMKID( tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U8 *pBSSId, tANI_U8 *pPMKId )
+{
+    tANI_BOOLEAN fRC = FALSE, fMatchFound = FALSE;
+    tANI_U32 Index;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    do
+    {
+        for( Index=0; Index < pSession->NumPmkidCache; Index++ )
+        {
+            smsLog(pMac, LOGW, "match PMKID %02X-%02X-%02X-%02X-%02X-%02X to \n",
+                pBSSId[0], pBSSId[1], pBSSId[2], pBSSId[3], pBSSId[4], pBSSId[5]);
+            if( palEqualMemory( pMac->hHdd, pBSSId, pSession->PmkidCacheInfo[Index].BSSID, sizeof(tCsrBssid) ) )
+            {
+                // match found
+                fMatchFound = TRUE;
+                break;
+            }
+        }
+
+        if( !fMatchFound ) break;
+
+        palCopyMemory( pMac->hHdd, pPMKId, pSession->PmkidCacheInfo[Index].PMKID, CSR_RSN_PMKID_SIZE );
+
+        fRC = TRUE;
+    }
+    while( 0 );
+    smsLog(pMac, LOGW, "csrLookupPMKID called return match = %d pMac->roam.NumPmkidCache = %d", 
+        fRC, pSession->NumPmkidCache);
+
+    return fRC;
+}
+
+
+tANI_U8 csrConstructRSNIe( tHalHandle hHal, tANI_U32 sessionId, tCsrRoamProfile *pProfile,
+                            tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes, tCsrRSNIe *pRSNIe )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fRSNMatch;
+    tANI_U8 cbRSNIe = 0;
+    tANI_U8 UnicastCypher[ CSR_RSN_OUI_SIZE ];
+    tANI_U8 MulticastCypher[ CSR_RSN_OUI_SIZE ];
+    tANI_U8 AuthSuite[ CSR_RSN_OUI_SIZE ];
+    tCsrRSNAuthIe *pAuthSuite;
+    tCsrRSNCapabilities RSNCapabilities;
+    tCsrRSNPMKIe        *pPMK;
+    tANI_U8 PMKId[CSR_RSN_PMKID_SIZE];
+    tDot11fBeaconIEs *pIesLocal = pIes;
+
+    do
+    {
+        if ( !csrIsProfileRSN( pProfile ) ) break;
+
+        if( !pIesLocal && (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc, &pIesLocal))) )
+        {
+            break;
+        }
+
+        // See if the cyphers in the Bss description match with the settings in the profile.
+        fRSNMatch = csrGetRSNInformation( hHal, &pProfile->AuthType, pProfile->negotiatedUCEncryptionType, 
+                                            &pProfile->mcEncryptionType, &pIesLocal->RSN,
+                                            UnicastCypher, MulticastCypher, AuthSuite, &RSNCapabilities, NULL, NULL );
+        if ( !fRSNMatch ) break;
+
+        pRSNIe->IeHeader.ElementID = SIR_MAC_RSN_EID;
+
+        pRSNIe->Version = CSR_RSN_VERSION_SUPPORTED;
+
+        palCopyMemory( pMac->hHdd, pRSNIe->MulticastOui, MulticastCypher, sizeof( MulticastCypher ) );
+
+        pRSNIe->cUnicastCyphers = 1;
+
+        palCopyMemory( pMac->hHdd, &pRSNIe->UnicastOui[ 0 ], UnicastCypher, sizeof( UnicastCypher ) );
+
+        pAuthSuite = (tCsrRSNAuthIe *)( &pRSNIe->UnicastOui[ pRSNIe->cUnicastCyphers ] );
+
+        pAuthSuite->cAuthenticationSuites = 1;
+        palCopyMemory( pMac->hHdd, &pAuthSuite->AuthOui[ 0 ], AuthSuite, sizeof( AuthSuite ) );
+
+        // RSN capabilities follows the Auth Suite (two octects)
+        // !!REVIEW - What should STA put in RSN capabilities, currently
+        // just putting back APs capabilities
+        // For one, we shouldn't EVER be sending out "pre-auth supported".  It is an AP only capability
+        RSNCapabilities.PreAuthSupported = 0;
+        *(tANI_U16 *)( &pAuthSuite->AuthOui[ 1 ] ) = *((tANI_U16 *)(&RSNCapabilities));
+
+        pPMK = (tCsrRSNPMKIe *)( ((tANI_U8 *)(&pAuthSuite->AuthOui[ 1 ])) + sizeof(tANI_U16) );
+
+        if( csrLookupPMKID( pMac, sessionId, pSirBssDesc->bssId, &(PMKId[0]) ) )
+        {
+            pPMK->cPMKIDs = 1;
+
+            palCopyMemory( pMac->hHdd, pPMK->PMKIDList[0].PMKID, PMKId, CSR_RSN_PMKID_SIZE );
+        }
+        else
+        {
+            pPMK->cPMKIDs = 0;
+        }
+
+        // Add in the fixed fields plus 1 Unicast cypher, less the IE Header length
+        // Add in the size of the Auth suite (count plus a single OUI)
+        // Add in the RSN caps field.
+        // Add PMKID count and PMKID (if any)
+        pRSNIe->IeHeader.Length = (tANI_U8) (sizeof( *pRSNIe ) - sizeof ( pRSNIe->IeHeader ) +
+                                  sizeof( *pAuthSuite ) +
+                                  sizeof( tCsrRSNCapabilities ));
+        if(pPMK->cPMKIDs)
+        {
+            pRSNIe->IeHeader.Length += (tANI_U8)(sizeof( tANI_U16 ) +
+                                        (pPMK->cPMKIDs * CSR_RSN_PMKID_SIZE));
+        }
+        // return the size of the IE header (total) constructed...
+        cbRSNIe = pRSNIe->IeHeader.Length + sizeof( pRSNIe->IeHeader );
+
+    } while( 0 );
+
+    if( !pIes && pIesLocal )
+    {
+        //locally allocated
+        palFreeMemory(pMac->hHdd, pIesLocal);
+    }
+
+    return( cbRSNIe );
+}
+
+
+#ifdef FEATURE_WLAN_WAPI
+tANI_BOOLEAN csrGetWapiInformation( tHalHandle hHal, tCsrAuthList *pAuthType, eCsrEncryptionType enType, tCsrEncryptionList *pMCEncryption,
+                                   tDot11fIEWAPI *pWapiIe,
+                                    tANI_U8 *UnicastCypher,
+                                    tANI_U8 *MulticastCypher,
+                                    tANI_U8 *AuthSuite,
+                                    eCsrAuthType *pNegotiatedAuthtype,
+                                    eCsrEncryptionType *pNegotiatedMCCipher )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fAcceptableCyphers = FALSE;
+    tANI_U8 cUnicastCyphers = 0;
+    tANI_U8 cMulticastCyphers = 0;
+    tANI_U8 cAuthSuites = 0, i;
+    tANI_U8 Unicast[ CSR_WAPI_OUI_SIZE ];
+    tANI_U8 Multicast[ CSR_WAPI_OUI_SIZE ];
+    tANI_U8 AuthSuites[ CSR_WAPI_MAX_AUTH_SUITES ][ CSR_WAPI_OUI_SIZE ];
+    tANI_U8 Authentication[ CSR_WAPI_OUI_SIZE ];
+    tANI_U8 MulticastCyphers[ CSR_WAPI_MAX_MULTICAST_CYPHERS ][ CSR_WAPI_OUI_SIZE ];
+    eCsrAuthType negAuthType = eCSR_AUTH_TYPE_UNKNOWN;
+
+    do{
+        if ( pWapiIe->present )
+        {
+            cMulticastCyphers++;
+            palCopyMemory(pMac->hHdd, MulticastCyphers, pWapiIe->multicast_cipher_suite, CSR_WAPI_OUI_SIZE);
+            cUnicastCyphers = (tANI_U8)(pWapiIe->unicast_cipher_suite_count);
+            cAuthSuites = (tANI_U8)(pWapiIe->akm_suite_count);
+            for(i = 0; i < cAuthSuites && i < CSR_WAPI_MAX_AUTH_SUITES; i++)
+            {
+                palCopyMemory(pMac->hHdd, (void *)&AuthSuites[i],
+                        (void *)&pWapiIe->akm_suites[i], CSR_WAPI_OUI_SIZE);
+            }
+
+            //Check - Is requested Unicast Cipher supported by the BSS.
+            fAcceptableCyphers = csrMatchWapiOUIIndex( pMac, pWapiIe->unicast_cipher_suites, cUnicastCyphers, 
+                    csrGetOUIIndexFromCipher( enType ), Unicast ); 
+
+            if( !fAcceptableCyphers ) break;
+
+
+            //Unicast is supported. Pick the first matching Group cipher, if any.
+            for( i = 0 ; i < pMCEncryption->numEntries ; i++ )
+            {
+                fAcceptableCyphers = csrMatchWapiOUIIndex( pMac, MulticastCyphers,  cMulticastCyphers, 
+                csrGetOUIIndexFromCipher( pMCEncryption->encryptionType[i] ), Multicast );
+                if(fAcceptableCyphers)
+                {
+                    break;
+                }
+            }
+            if( !fAcceptableCyphers ) break;
+
+            if( pNegotiatedMCCipher )
+                *pNegotiatedMCCipher = pMCEncryption->encryptionType[i];
+
+            //Ciphers are supported, Match authentication algorithm and pick first matching authtype.
+            if ( csrIsAuthWapiCert( pMac, AuthSuites, cAuthSuites, Authentication ) )
+            {
+                negAuthType = eCSR_AUTH_TYPE_WAPI_WAI_CERTIFICATE;
+            }
+            else if ( csrIsAuthWapiPsk( pMac, AuthSuites, cAuthSuites, Authentication ) )
+            {
+                negAuthType = eCSR_AUTH_TYPE_WAPI_WAI_PSK;
+            }
+            else
+            {
+                fAcceptableCyphers = FALSE;
+                negAuthType = eCSR_AUTH_TYPE_UNKNOWN;
+            }
+            if( ( 0 == pAuthType->numEntries ) || ( FALSE == fAcceptableCyphers ) )
+            {
+                //Caller doesn't care about auth type, or BSS doesn't match
+                break;
+            }
+            fAcceptableCyphers = FALSE;
+            for( i = 0 ; i < pAuthType->numEntries; i++ )
+            {
+                if( pAuthType->authType[i] == negAuthType )
+                {
+                    fAcceptableCyphers = TRUE;
+                    break;
+                }
+            }
+        }
+    }while (0);
+
+    if ( fAcceptableCyphers )
+    {
+        if ( MulticastCypher )
+        {
+            palCopyMemory( pMac->hHdd, MulticastCypher, Multicast, CSR_WAPI_OUI_SIZE );
+        }
+
+        if ( UnicastCypher )
+        {
+            palCopyMemory( pMac->hHdd, UnicastCypher, Unicast, CSR_WAPI_OUI_SIZE );
+        }
+
+        if ( AuthSuite )
+        {
+            palCopyMemory( pMac->hHdd, AuthSuite, Authentication, CSR_WAPI_OUI_SIZE );
+        }
+
+        if ( pNegotiatedAuthtype )
+        {
+            *pNegotiatedAuthtype = negAuthType;
+        }
+    }
+    return( fAcceptableCyphers );
+}
+
+tANI_BOOLEAN csrIsWapiMatch( tHalHandle hHal, tCsrAuthList *pAuthType, eCsrEncryptionType enType, tCsrEncryptionList *pEnMcType, 
+                            tDot11fBeaconIEs *pIes, eCsrAuthType *pNegotiatedAuthType, eCsrEncryptionType *pNegotiatedMCCipher )
+{
+    tANI_BOOLEAN fWapiMatch = FALSE;
+
+        // See if the cyphers in the Bss description match with the settings in the profile.
+    fWapiMatch = csrGetWapiInformation( hHal, pAuthType, enType, pEnMcType, &pIes->WAPI, NULL, NULL, NULL, 
+                                      pNegotiatedAuthType, pNegotiatedMCCipher );
+
+    return( fWapiMatch );
+}
+
+tANI_BOOLEAN csrLookupBKID( tpAniSirGlobal pMac, tANI_U32 sessionId, tANI_U8 *pBSSId, tANI_U8 *pBKId )
+{
+    tANI_BOOLEAN fRC = FALSE, fMatchFound = FALSE;
+    tANI_U32 Index;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+    do
+    {
+        for( Index=0; Index < pSession->NumBkidCache; Index++ )
+        {
+            smsLog(pMac, LOGW, "match BKID %02X-%02X-%02X-%02X-%02X-%02X to \n",
+                pBSSId[0], pBSSId[1], pBSSId[2], pBSSId[3], pBSSId[4], pBSSId[5]);
+            if( palEqualMemory( pMac->hHdd, pBSSId, pSession->BkidCacheInfo[Index].BSSID, sizeof(tCsrBssid) ) )
+            {
+                // match found
+                fMatchFound = TRUE;
+                break;
+            }
+        }
+
+        if( !fMatchFound ) break;
+
+        palCopyMemory( pMac->hHdd, pBKId, pSession->BkidCacheInfo[Index].BKID, CSR_WAPI_BKID_SIZE );
+
+        fRC = TRUE;
+    }
+    while( 0 );
+    smsLog(pMac, LOGW, "csrLookupBKID called return match = %d pMac->roam.NumBkidCache = %d", fRC, pSession->NumBkidCache);
+
+    return fRC;
+}
+
+tANI_U8 csrConstructWapiIe( tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pProfile,
+                            tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes, tCsrWapiIe *pWapiIe )
+{
+    tANI_BOOLEAN fWapiMatch = FALSE;
+    tANI_U8 cbWapiIe = 0;
+    tANI_U8 UnicastCypher[ CSR_WAPI_OUI_SIZE ];
+    tANI_U8 MulticastCypher[ CSR_WAPI_OUI_SIZE ];
+    tANI_U8 AuthSuite[ CSR_WAPI_OUI_SIZE ];
+    tANI_U8 BKId[CSR_WAPI_BKID_SIZE];
+    tANI_U8 *pWapi = NULL;
+    tANI_BOOLEAN fBKIDFound = FALSE;
+    tDot11fBeaconIEs *pIesLocal = pIes;
+
+    do
+    {
+        if ( !csrIsProfileWapi( pProfile ) ) break;
+
+        if( !pIesLocal && (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc, &pIesLocal))) )
+        {
+            break;
+        }
+
+        // See if the cyphers in the Bss description match with the settings in the profile.
+        fWapiMatch = csrGetWapiInformation( pMac, &pProfile->AuthType, pProfile->negotiatedUCEncryptionType, 
+                                            &pProfile->mcEncryptionType, &pIesLocal->WAPI,
+                                            UnicastCypher, MulticastCypher, AuthSuite, NULL, NULL );
+        if ( !fWapiMatch ) break;
+
+        palZeroMemory(pMac->hHdd, pWapiIe, sizeof(tCsrWapiIe));
+
+        pWapiIe->IeHeader.ElementID = DOT11F_EID_WAPI;
+
+        pWapiIe->Version = CSR_WAPI_VERSION_SUPPORTED;
+
+        pWapiIe->cAuthenticationSuites = 1;
+        palCopyMemory( pMac->hHdd, &pWapiIe->AuthOui[ 0 ], AuthSuite, sizeof( AuthSuite ) );
+
+        pWapi = (tANI_U8 *) (&pWapiIe->AuthOui[ 1 ]);
+
+        *pWapi = (tANI_U16)1; //cUnicastCyphers
+        pWapi+=2;
+        palCopyMemory( pMac->hHdd, pWapi, UnicastCypher, sizeof( UnicastCypher ) );
+        pWapi += sizeof( UnicastCypher );
+
+        palCopyMemory( pMac->hHdd, pWapi, MulticastCypher, sizeof( MulticastCypher ) );
+        pWapi += sizeof( MulticastCypher );
+
+
+        // WAPI capabilities follows the Auth Suite (two octects)
+        // we shouldn't EVER be sending out "pre-auth supported".  It is an AP only capability
+        // & since we already did a memset pWapiIe to 0, skip these fields
+        pWapi +=2;
+
+        fBKIDFound = csrLookupBKID( pMac, sessionId, pSirBssDesc->bssId, &(BKId[0]) );
+
+
+        if( fBKIDFound )
+        {
+            /* Do we need to change the endianness here */
+            *pWapi = (tANI_U16)1; //cBKIDs
+            pWapi+=2;
+            palCopyMemory( pMac->hHdd, pWapi, BKId, CSR_WAPI_BKID_SIZE );
+        }
+        else
+        {
+            *pWapi = 0;
+            pWapi+=1;
+            *pWapi = 0;
+            pWapi+=1;
+        }
+
+        // Add in the IE fields except the IE header
+        // Add BKID count and BKID (if any)
+        pWapiIe->IeHeader.Length = (tANI_U8) (sizeof( *pWapiIe ) - sizeof ( pWapiIe->IeHeader ));
+
+        /*2 bytes for BKID Count field*/
+        pWapiIe->IeHeader.Length += sizeof( tANI_U16 );
+
+        if(fBKIDFound)
+        {
+            pWapiIe->IeHeader.Length += CSR_WAPI_BKID_SIZE;
+        }
+        // return the size of the IE header (total) constructed...
+        cbWapiIe = pWapiIe->IeHeader.Length + sizeof( pWapiIe->IeHeader );
+
+    } while( 0 );
+
+    if( !pIes && pIesLocal )
+    {
+        //locally allocated
+        palFreeMemory(pMac->hHdd, pIesLocal);
+    }
+
+    return( cbWapiIe );
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+tANI_BOOLEAN csrGetWpaCyphers( tpAniSirGlobal pMac, tCsrAuthList *pAuthType, eCsrEncryptionType enType, tCsrEncryptionList *pMCEncryption,
+                               tDot11fIEWPA *pWpaIe,
+                           tANI_U8 *UnicastCypher,
+                           tANI_U8 *MulticastCypher,
+                           tANI_U8 *AuthSuite,
+                           eCsrAuthType *pNegotiatedAuthtype,
+                           eCsrEncryptionType *pNegotiatedMCCipher )
+{
+    tANI_BOOLEAN fAcceptableCyphers = FALSE;
+    tANI_U8 cUnicastCyphers = 0;
+    tANI_U8 cMulticastCyphers = 0;
+    tANI_U8 cAuthSuites = 0;
+    tANI_U8 Unicast[ CSR_WPA_OUI_SIZE ];
+    tANI_U8 Multicast[ CSR_WPA_OUI_SIZE ];
+    tANI_U8 Authentication[ CSR_WPA_OUI_SIZE ];
+    tANI_U8 MulticastCyphers[ 1 ][ CSR_WPA_OUI_SIZE ];
+    tANI_U8 i;
+    eCsrAuthType negAuthType = eCSR_AUTH_TYPE_UNKNOWN;
+
+    do
+    {
+        if ( pWpaIe->present )
+        {
+            cMulticastCyphers = 1;
+            palCopyMemory(pMac->hHdd, MulticastCyphers, pWpaIe->multicast_cipher, CSR_WPA_OUI_SIZE);
+            cUnicastCyphers = (tANI_U8)(pWpaIe->unicast_cipher_count);
+            cAuthSuites = (tANI_U8)(pWpaIe->auth_suite_count);
+
+            //Check - Is requested Unicast Cipher supported by the BSS.
+            fAcceptableCyphers = csrMatchWPAOUIIndex( pMac, pWpaIe->unicast_ciphers, cUnicastCyphers, 
+                    csrGetOUIIndexFromCipher( enType ), Unicast );
+
+            if( !fAcceptableCyphers ) break;
+
+
+            //Unicast is supported. Pick the first matching Group cipher, if any.
+            for( i = 0 ; i < pMCEncryption->numEntries ; i++ )
+            {
+                fAcceptableCyphers = csrMatchWPAOUIIndex( pMac, MulticastCyphers,  cMulticastCyphers, 
+                            csrGetOUIIndexFromCipher( pMCEncryption->encryptionType[i]), Multicast );
+                if(fAcceptableCyphers)
+                {
+                    break;
+                }
+            }
+            if( !fAcceptableCyphers ) break;
+            
+            if( pNegotiatedMCCipher )
+                *pNegotiatedMCCipher = pMCEncryption->encryptionType[i];
+
+                /* Initializing with FALSE as it has TRUE value already */
+            fAcceptableCyphers = FALSE;
+            for (i = 0 ; i < pAuthType->numEntries; i++)
+            {
+            //Ciphers are supported, Match authentication algorithm and pick first matching authtype.
+                if ( csrIsAuthWpa( pMac, pWpaIe->auth_suites, cAuthSuites, Authentication ) )
+                {
+                    if (eCSR_AUTH_TYPE_WPA == pAuthType->authType[i])
+                    negAuthType = eCSR_AUTH_TYPE_WPA;
+                }
+                if ( (negAuthType == eCSR_AUTH_TYPE_UNKNOWN) && csrIsAuthWpaPsk( pMac, pWpaIe->auth_suites, cAuthSuites, Authentication ) )
+                {
+                    if (eCSR_AUTH_TYPE_WPA_PSK == pAuthType->authType[i])
+                    negAuthType = eCSR_AUTH_TYPE_WPA_PSK;
+                }
+#ifdef FEATURE_WLAN_CCX
+                if ( (negAuthType == eCSR_AUTH_TYPE_UNKNOWN) && csrIsCcxCckmAuthWpa( pMac, pWpaIe->auth_suites, cAuthSuites, Authentication ) )
+                {
+                    if (eCSR_AUTH_TYPE_CCKM_WPA == pAuthType->authType[i])
+                        negAuthType = eCSR_AUTH_TYPE_CCKM_WPA;
+                }
+#endif /* FEATURE_WLAN_CCX */
+
+                // The 1st auth type in the APs WPA IE, to match stations connecting
+                // profiles auth type will cause us to exit this loop
+                // This is added as some APs advertise multiple akms in the WPA IE.
+                if (eCSR_AUTH_TYPE_UNKNOWN != negAuthType)
+                {
+                        fAcceptableCyphers = TRUE;
+                        break;
+                    }
+            } // for
+            }
+    }while(0);
+
+    if ( fAcceptableCyphers )
+    {
+        if ( MulticastCypher )
+        {
+            palCopyMemory( pMac->hHdd, (tANI_U8 **)MulticastCypher, Multicast, CSR_WPA_OUI_SIZE );
+        }
+
+        if ( UnicastCypher )
+        {
+            palCopyMemory( pMac->hHdd, (tANI_U8 **)UnicastCypher, Unicast, CSR_WPA_OUI_SIZE );
+        }
+
+        if ( AuthSuite )
+        {
+            palCopyMemory( pMac->hHdd, (tANI_U8 **)AuthSuite, Authentication, CSR_WPA_OUI_SIZE );
+        }
+
+        if( pNegotiatedAuthtype )
+        {
+            *pNegotiatedAuthtype = negAuthType;
+        }
+    }
+
+    return( fAcceptableCyphers );
+}
+
+
+
+tANI_BOOLEAN csrIsWpaEncryptionMatch( tpAniSirGlobal pMac, tCsrAuthList *pAuthType, eCsrEncryptionType enType, tCsrEncryptionList *pEnMcType,
+                                        tDot11fBeaconIEs *pIes, eCsrAuthType *pNegotiatedAuthtype, eCsrEncryptionType *pNegotiatedMCCipher )
+{
+    tANI_BOOLEAN fWpaMatch = eANI_BOOLEAN_FALSE;
+
+        // See if the cyphers in the Bss description match with the settings in the profile.
+    fWpaMatch = csrGetWpaCyphers( pMac, pAuthType, enType, pEnMcType, &pIes->WPA, NULL, NULL, NULL, pNegotiatedAuthtype, pNegotiatedMCCipher );
+
+    return( fWpaMatch );
+}
+
+
+tANI_U8 csrConstructWpaIe( tHalHandle hHal, tCsrRoamProfile *pProfile, tSirBssDescription *pSirBssDesc, 
+                           tDot11fBeaconIEs *pIes, tCsrWpaIe *pWpaIe )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fWpaMatch;
+    tANI_U8 cbWpaIe = 0;
+    tANI_U8 UnicastCypher[ CSR_WPA_OUI_SIZE ];
+    tANI_U8 MulticastCypher[ CSR_WPA_OUI_SIZE ];
+    tANI_U8 AuthSuite[ CSR_WPA_OUI_SIZE ];
+    tCsrWpaAuthIe *pAuthSuite;
+    tDot11fBeaconIEs *pIesLocal = pIes;
+
+    do
+    {
+        if ( !csrIsProfileWpa( pProfile ) ) break;
+
+        if( !pIesLocal && (!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pSirBssDesc, &pIesLocal))) )
+        {
+            break;
+        }
+        // See if the cyphers in the Bss description match with the settings in the profile.
+        fWpaMatch = csrGetWpaCyphers( hHal, &pProfile->AuthType, pProfile->negotiatedUCEncryptionType, &pProfile->mcEncryptionType,
+                                      &pIesLocal->WPA, UnicastCypher, MulticastCypher, AuthSuite, NULL, NULL );
+        if ( !fWpaMatch ) break;
+
+        pWpaIe->IeHeader.ElementID = SIR_MAC_WPA_EID;
+
+        palCopyMemory( pMac->hHdd, pWpaIe->Oui, csrWpaOui[01], sizeof( pWpaIe->Oui ) );
+
+        pWpaIe->Version = CSR_WPA_VERSION_SUPPORTED;
+
+        palCopyMemory( pMac->hHdd, pWpaIe->MulticastOui, MulticastCypher, sizeof( MulticastCypher ) );
+
+        pWpaIe->cUnicastCyphers = 1;
+
+        palCopyMemory( pMac->hHdd, &pWpaIe->UnicastOui[ 0 ], UnicastCypher, sizeof( UnicastCypher ) );
+
+        pAuthSuite = (tCsrWpaAuthIe *)( &pWpaIe->UnicastOui[ pWpaIe->cUnicastCyphers ] );
+
+        pAuthSuite->cAuthenticationSuites = 1;
+        palCopyMemory( pMac->hHdd, &pAuthSuite->AuthOui[ 0 ], AuthSuite, sizeof( AuthSuite ) );
+
+        // The WPA capabilities follows the Auth Suite (two octects)--
+        // this field is optional, and we always "send" zero, so just
+        // remove it.  This is consistent with our assumptions in the
+        // frames compiler; c.f. bug 15234:
+        // http://gold.woodsidenet.com/bugzilla/show_bug.cgi?id=15234
+
+        // Add in the fixed fields plus 1 Unicast cypher, less the IE Header length
+        // Add in the size of the Auth suite (count plus a single OUI)
+        pWpaIe->IeHeader.Length = sizeof( *pWpaIe ) - sizeof ( pWpaIe->IeHeader ) +
+                                  sizeof( *pAuthSuite );
+
+        // return the size of the IE header (total) constructed...
+        cbWpaIe = pWpaIe->IeHeader.Length + sizeof( pWpaIe->IeHeader );
+
+    } while( 0 );
+
+    if( !pIes && pIesLocal )
+    {
+        //locally allocated
+        palFreeMemory(pMac->hHdd, pIesLocal);
+    }
+
+    return( cbWpaIe );
+}
+
+
+tANI_BOOLEAN csrGetWpaRsnIe( tHalHandle hHal, tANI_U8 *pIes, tANI_U32 len,
+                             tANI_U8 *pWpaIe, tANI_U8 *pcbWpaIe, tANI_U8 *pRSNIe, tANI_U8 *pcbRSNIe)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tDot11IEHeader *pIEHeader;
+    tSirMacPropIE *pSirMacPropIE;
+    tANI_U32 cbParsed;
+    tANI_U32 cbIE;
+    int cExpectedIEs = 0;
+    int cFoundIEs = 0;
+    int cbPropIETotal;
+
+    pIEHeader = (tDot11IEHeader *)pIes;
+    if(pWpaIe) cExpectedIEs++;
+    if(pRSNIe) cExpectedIEs++;
+
+    // bss description length includes all fields other than the length itself
+    cbParsed  = 0;
+
+    // Loop as long as there is data left in the IE of the Bss Description
+    // and the number of Expected IEs is NOT found yet.
+    while( ( (cbParsed + sizeof( *pIEHeader )) <= len ) && ( cFoundIEs < cExpectedIEs  ) )
+    {
+        cbIE = sizeof( *pIEHeader ) + pIEHeader->Length;
+
+        if ( ( cbIE + cbParsed ) > len ) break;
+
+        if ( ( pIEHeader->Length >= gCsrIELengthTable[ pIEHeader->ElementID ].min ) &&
+             ( pIEHeader->Length <= gCsrIELengthTable[ pIEHeader->ElementID ].max ) )
+        {
+            switch( pIEHeader->ElementID )
+            {
+                // Parse the 221 (0xdd) Proprietary IEs here...
+                // Note that the 221 IE is overloaded, containing the WPA IE, WMM/WME IE, and the
+                // Airgo proprietary IE information.
+                case SIR_MAC_WPA_EID:
+                {
+                    tANI_U32 aniOUI;
+                    tANI_U8 *pOui = (tANI_U8 *)&aniOUI;
+
+                    pOui++;
+                    aniOUI = ANI_OUI;
+                    aniOUI = i_ntohl( aniOUI );
+
+                    pSirMacPropIE = ( tSirMacPropIE *)pIEHeader;
+                    cbPropIETotal = pSirMacPropIE->length;
+
+                    // Validate the ANI OUI is in the OUI field in the proprietary IE...
+                    if ( ( pSirMacPropIE->length >= WNI_CFG_MANUFACTURER_OUI_LEN ) &&
+                          pOui[ 0 ] == pSirMacPropIE->oui[ 0 ] &&
+                          pOui[ 1 ] == pSirMacPropIE->oui[ 1 ] &&
+                          pOui[ 2 ] == pSirMacPropIE->oui[ 2 ]  )
+                    {
+                    }
+                    else
+                    {
+                        tCsrWpaIe     *pIe        = ( tCsrWpaIe *    )pIEHeader;
+
+                        if(!pWpaIe || !pcbWpaIe) break;
+                        // Check if this is a valid WPA IE.  Then check that the
+                        // WPA OUI is in place and the version is one that we support.
+                        if ( ( pIe->IeHeader.Length >= SIR_MAC_WPA_IE_MIN_LENGTH )   &&
+                             ( palEqualMemory(pMac->hHdd, pIe->Oui, (void *)csrWpaOui[1], sizeof( pIe->Oui ) ) ) &&
+                             ( pIe->Version <= CSR_WPA_VERSION_SUPPORTED ) )
+                        {
+                            palCopyMemory(pMac->hHdd, pWpaIe, pIe, pIe->IeHeader.Length + sizeof( pIe->IeHeader ) );
+                            *pcbWpaIe = pIe->IeHeader.Length + sizeof( pIe->IeHeader );
+                            cFoundIEs++;
+
+                            break;
+                        }
+                    }
+
+                    break;
+                }
+
+                case SIR_MAC_RSN_EID:
+                {
+                    tCsrRSNIe *pIe;
+
+                    if(!pcbRSNIe || !pRSNIe) break;
+                    pIe = (tCsrRSNIe *)pIEHeader;
+
+                    // Check the length of the RSN Ie to assure it is valid.  Then check that the
+                    // version is one that we support.
+
+                    if ( pIe->IeHeader.Length < SIR_MAC_RSN_IE_MIN_LENGTH ) break;
+                    if ( pIe->Version > CSR_RSN_VERSION_SUPPORTED ) break;
+
+                    cFoundIEs++;
+
+                    // if there is enough room in the WpaIE passed in, then copy the Wpa IE into
+                    // the buffer passed in.
+                    if ( *pcbRSNIe < pIe->IeHeader.Length + sizeof( pIe->IeHeader ) ) break;
+                    palCopyMemory(pMac->hHdd, pRSNIe, pIe, pIe->IeHeader.Length + sizeof( pIe->IeHeader ) );
+                    *pcbRSNIe = pIe->IeHeader.Length + sizeof( pIe->IeHeader );
+
+                    break;
+                }
+
+                // Add support for other IE here...
+                default:
+                    break;
+            }
+        }
+
+        cbParsed += cbIE;
+
+        pIEHeader = (tDot11IEHeader *)( ((tANI_U8 *)pIEHeader) + cbIE );
+
+    }
+
+    // return a BOOL that tells if all of the IEs asked for were found...
+    return( cFoundIEs == cExpectedIEs );
+}
+
+
+//If a WPAIE exists in the profile, just use it. Or else construct one from the BSS
+//Caller allocated memory for pWpaIe and guarrantee it can contain a max length WPA IE
+tANI_U8 csrRetrieveWpaIe( tHalHandle hHal, tCsrRoamProfile *pProfile, tSirBssDescription *pSirBssDesc, 
+                          tDot11fBeaconIEs *pIes, tCsrWpaIe *pWpaIe )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_U8 cbWpaIe = 0;
+
+    do
+    {
+        if ( !csrIsProfileWpa( pProfile ) ) break;
+        if(pProfile->nWPAReqIELength && pProfile->pWPAReqIE)
+        {
+            if(SIR_MAC_WPA_IE_MAX_LENGTH >= pProfile->nWPAReqIELength)
+            {
+                cbWpaIe = (tANI_U8)pProfile->nWPAReqIELength;
+                palCopyMemory(pMac->hHdd, pWpaIe, pProfile->pWPAReqIE, cbWpaIe);
+            }
+            else
+            {
+                smsLog(pMac, LOGW, "  csrRetrieveWpaIe detect invalid WPA IE length (%d) \n", pProfile->nWPAReqIELength);
+            }
+        }
+        else
+        {
+            cbWpaIe = csrConstructWpaIe(pMac, pProfile, pSirBssDesc, pIes, pWpaIe);
+        }
+    }while(0);
+
+    return (cbWpaIe);
+}
+
+
+//If a RSNIE exists in the profile, just use it. Or else construct one from the BSS
+//Caller allocated memory for pWpaIe and guarrantee it can contain a max length WPA IE
+tANI_U8 csrRetrieveRsnIe( tHalHandle hHal, tANI_U32 sessionId, tCsrRoamProfile *pProfile, 
+                         tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes, tCsrRSNIe *pRsnIe )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_U8 cbRsnIe = 0;
+
+    do
+    {
+        if ( !csrIsProfileRSN( pProfile ) ) break;
+        if(pProfile->nRSNReqIELength && pProfile->pRSNReqIE)
+        {
+            if(SIR_MAC_WPA_IE_MAX_LENGTH >= pProfile->nRSNReqIELength)
+            {
+                cbRsnIe = (tANI_U8)pProfile->nRSNReqIELength;
+                palCopyMemory(pMac->hHdd, pRsnIe, pProfile->pRSNReqIE, cbRsnIe);
+            }
+            else
+            {
+                smsLog(pMac, LOGW, "  csrRetrieveRsnIe detect invalid RSN IE length (%d) \n", pProfile->nRSNReqIELength);
+            }
+        }
+        else
+        {
+            cbRsnIe = csrConstructRSNIe(pMac, sessionId, pProfile, pSirBssDesc, pIes, pRsnIe);
+        }
+    }while(0);
+
+    return (cbRsnIe);
+}
+
+
+#ifdef FEATURE_WLAN_WAPI
+//If a WAPI IE exists in the profile, just use it. Or else construct one from the BSS
+//Caller allocated memory for pWapiIe and guarrantee it can contain a max length WAPI IE
+tANI_U8 csrRetrieveWapiIe( tHalHandle hHal, tANI_U32 sessionId, 
+                          tCsrRoamProfile *pProfile, tSirBssDescription *pSirBssDesc, 
+                          tDot11fBeaconIEs *pIes, tCsrWapiIe *pWapiIe )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_U8 cbWapiIe = 0;
+
+    do
+    {
+        if ( !csrIsProfileWapi( pProfile ) ) break;
+        if(pProfile->nWAPIReqIELength && pProfile->pWAPIReqIE)
+        {
+            if(DOT11F_IE_WAPI_MAX_LEN >= pProfile->nWAPIReqIELength)
+            {
+                cbWapiIe = (tANI_U8)pProfile->nWAPIReqIELength;
+                palCopyMemory(pMac->hHdd, pWapiIe, pProfile->pWAPIReqIE, cbWapiIe);
+            }
+            else
+            {
+                smsLog(pMac, LOGW, "  csrRetrieveWapiIe detect invalid WAPI IE length (%d) \n", pProfile->nWAPIReqIELength);
+            }
+        }
+        else
+        {
+            cbWapiIe = csrConstructWapiIe(pMac, sessionId, pProfile, pSirBssDesc, pIes, pWapiIe);
+        }
+    }while(0);
+
+    return (cbWapiIe);
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+tANI_BOOLEAN csrSearchChannelListForTxPower(tHalHandle hHal, tSirBssDescription *pBssDescription, tCsrChannelSet *returnChannelGroup)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tListElem *pEntry;
+    tANI_U16 i;
+    tANI_U16 startingChannel;
+    tANI_BOOLEAN found = FALSE;
+    tCsrChannelSet *pChannelGroup;
+
+    pEntry = csrLLPeekHead( &pMac->roam.channelList5G, LL_ACCESS_LOCK );
+
+    while ( pEntry )
+    {
+        pChannelGroup = GET_BASE_ADDR( pEntry, tCsrChannelSet, channelListLink );
+        startingChannel = pChannelGroup->firstChannel;
+        for ( i = 0; i < pChannelGroup->numChannels; i++ )
+        {
+            if ( startingChannel + i * pChannelGroup->interChannelOffset == pBssDescription->channelId )
+            {
+                found = TRUE;
+                break;
+            }
+        }
+
+        if ( found )
+        {
+            palCopyMemory(pMac->hHdd, returnChannelGroup, pChannelGroup, sizeof(tCsrChannelSet));
+            break;
+        }
+        else
+        {
+            pEntry = csrLLNext( &pMac->roam.channelList5G, pEntry, LL_ACCESS_LOCK );
+        }
+    }
+
+    return( found );
+}
+
+tANI_BOOLEAN csrRatesIsDot11Rate11bSupportedRate( tANI_U8 dot11Rate )
+{
+    tANI_BOOLEAN fSupported = FALSE;
+    tANI_U16 nonBasicRate = (tANI_U16)( BITS_OFF( dot11Rate, CSR_DOT11_BASIC_RATE_MASK ) );
+
+    switch ( nonBasicRate )
+    {
+        case eCsrSuppRate_1Mbps:
+        case eCsrSuppRate_2Mbps:
+        case eCsrSuppRate_5_5Mbps:
+        case eCsrSuppRate_11Mbps:
+            fSupported = TRUE;
+            break;
+
+        default:
+            break;
+    }
+
+    return( fSupported );
+}
+
+tANI_BOOLEAN csrRatesIsDot11Rate11aSupportedRate( tANI_U8 dot11Rate )
+{
+    tANI_BOOLEAN fSupported = FALSE;
+    tANI_U16 nonBasicRate = (tANI_U16)( BITS_OFF( dot11Rate, CSR_DOT11_BASIC_RATE_MASK ) );
+
+    switch ( nonBasicRate )
+    {
+        case eCsrSuppRate_6Mbps:
+        case eCsrSuppRate_9Mbps:
+        case eCsrSuppRate_12Mbps:
+        case eCsrSuppRate_18Mbps:
+        case eCsrSuppRate_24Mbps:
+        case eCsrSuppRate_36Mbps:
+        case eCsrSuppRate_48Mbps:
+        case eCsrSuppRate_54Mbps:
+            fSupported = TRUE;
+            break;
+
+        default:
+            break;
+    }
+
+    return( fSupported );
+}
+
+
+
+tAniEdType csrTranslateEncryptTypeToEdType( eCsrEncryptionType EncryptType )
+{
+    tAniEdType edType;
+
+    switch ( EncryptType )
+    {
+        default:
+        case eCSR_ENCRYPT_TYPE_NONE:
+            edType = eSIR_ED_NONE;
+            break;
+
+        case eCSR_ENCRYPT_TYPE_WEP40_STATICKEY:
+        case eCSR_ENCRYPT_TYPE_WEP40:
+            edType = eSIR_ED_WEP40;
+            break;
+
+        case eCSR_ENCRYPT_TYPE_WEP104_STATICKEY:
+        case eCSR_ENCRYPT_TYPE_WEP104:
+            edType = eSIR_ED_WEP104;
+            break;
+
+        case eCSR_ENCRYPT_TYPE_TKIP:
+            edType = eSIR_ED_TKIP;
+            break;
+
+        case eCSR_ENCRYPT_TYPE_AES:
+            edType = eSIR_ED_CCMP;
+            break;
+#ifdef FEATURE_WLAN_WAPI
+        case eCSR_ENCRYPT_TYPE_WPI:
+            edType = eSIR_ED_WPI;
+#endif
+#ifdef WLAN_FEATURE_11W
+        //11w BIP
+        case eCSR_ENCRYPT_TYPE_AES_CMAC:
+            edType = eSIR_ED_AES_128_CMAC;
+            break;
+#endif
+    }
+
+    return( edType );
+}
+
+
+//pIes can be NULL
+tANI_BOOLEAN csrValidateWep( tpAniSirGlobal pMac, eCsrEncryptionType ucEncryptionType, 
+                             tCsrAuthList *pAuthList, tCsrEncryptionList *pMCEncryptionList, 
+                             eCsrAuthType *pNegotiatedAuthType, eCsrEncryptionType *pNegotiatedMCEncryption,
+                             tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes )
+{
+    tANI_U32 idx;
+    tANI_BOOLEAN fMatch = FALSE;
+    eCsrAuthType negotiatedAuth = eCSR_AUTH_TYPE_OPEN_SYSTEM;
+    eCsrEncryptionType negotiatedMCCipher = eCSR_ENCRYPT_TYPE_UNKNOWN;
+
+    //This function just checks whether HDD is giving correct values for Multicast cipher and Auth.
+    
+    do
+    {
+        //If privacy bit is not set, consider no match
+        if ( !csrIsPrivacy( pSirBssDesc ) ) break;
+
+        for( idx = 0; idx < pMCEncryptionList->numEntries; idx++ )
+        {
+            switch( pMCEncryptionList->encryptionType[idx] )
+            {
+                case eCSR_ENCRYPT_TYPE_WEP40_STATICKEY:
+                case eCSR_ENCRYPT_TYPE_WEP104_STATICKEY:
+                case eCSR_ENCRYPT_TYPE_WEP40:
+                case eCSR_ENCRYPT_TYPE_WEP104:
+                    /* Multicast list may contain WEP40/WEP104. Check whether it matches UC.
+                    */
+                    if( ucEncryptionType == pMCEncryptionList->encryptionType[idx] )
+                    {
+                        fMatch = TRUE;
+                        negotiatedMCCipher = pMCEncryptionList->encryptionType[idx];
+                    }
+                    break;
+                default:
+                    fMatch = FALSE;
+                    break;
+            }
+            if(fMatch) break; 
+        }
+
+        if(!fMatch) break;
+
+        for( idx = 0; idx < pAuthList->numEntries; idx++ )
+        {
+            switch( pAuthList->authType[idx] )
+            {
+                case eCSR_AUTH_TYPE_OPEN_SYSTEM:
+                case eCSR_AUTH_TYPE_SHARED_KEY:
+                case eCSR_AUTH_TYPE_AUTOSWITCH:
+                    fMatch = TRUE;
+                    negotiatedAuth = pAuthList->authType[idx];
+                    break;
+                default:
+                    fMatch = FALSE;
+            }
+            if (fMatch) break;
+        }
+
+        if(!fMatch) break;
+        //In case of WPA / WPA2, check whether it supports WEP as well
+        if(pIes)
+        {
+            //Prepare the encryption type for WPA/WPA2 functions
+            if( eCSR_ENCRYPT_TYPE_WEP40_STATICKEY == ucEncryptionType )
+            {
+                ucEncryptionType = eCSR_ENCRYPT_TYPE_WEP40;
+            }
+            else if( eCSR_ENCRYPT_TYPE_WEP104 == ucEncryptionType )
+            {
+                ucEncryptionType = eCSR_ENCRYPT_TYPE_WEP104;
+            }
+            //else we can use the encryption type directly
+            if( pIes->WPA.present )
+            {
+                fMatch = palEqualMemory(pMac->hHdd, pIes->WPA.multicast_cipher, 
+                            csrWpaOui[csrGetOUIIndexFromCipher( ucEncryptionType )], CSR_WPA_OUI_SIZE );
+                if( fMatch ) break;
+            }
+            if( pIes->RSN.present )
+            {
+                fMatch = palEqualMemory(pMac->hHdd, pIes->RSN.gp_cipher_suite, 
+                            csrRSNOui[csrGetOUIIndexFromCipher( ucEncryptionType )], CSR_RSN_OUI_SIZE );
+            }
+        }
+
+    }while(0);
+
+    if( fMatch )
+    {
+        if( pNegotiatedAuthType )
+            *pNegotiatedAuthType = negotiatedAuth;
+
+        if( pNegotiatedMCEncryption )
+            *pNegotiatedMCEncryption = negotiatedMCCipher;
+    }    
+
+
+    return fMatch;
+}
+
+
+//pIes shall contain IEs from pSirBssDesc. It shall be returned from function csrGetParsedBssDescriptionIEs
+tANI_BOOLEAN csrIsSecurityMatch( tHalHandle hHal, tCsrAuthList *authType, tCsrEncryptionList *pUCEncryptionType, tCsrEncryptionList *pMCEncryptionType,
+                                 tSirBssDescription *pSirBssDesc, tDot11fBeaconIEs *pIes, 
+                                 eCsrAuthType *negotiatedAuthtype, eCsrEncryptionType *negotiatedUCCipher, eCsrEncryptionType *negotiatedMCCipher )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fMatch = FALSE;
+    tANI_U8 i,idx;
+    eCsrEncryptionType mcCipher = eCSR_ENCRYPT_TYPE_UNKNOWN, ucCipher = eCSR_ENCRYPT_TYPE_UNKNOWN;
+    eCsrAuthType negAuthType = eCSR_AUTH_TYPE_UNKNOWN;
+
+    for( i = 0 ; ((i < pUCEncryptionType->numEntries) && (!fMatch)) ; i++ )
+    {
+        ucCipher = pUCEncryptionType->encryptionType[i];
+        // If the Bss description shows the Privacy bit is on, then we must have some sort of encryption configured
+        // for the profile to work.  Don't attempt to join networks with Privacy bit set when profiles say NONE for
+        // encryption type.
+        switch ( ucCipher )
+        {
+            case eCSR_ENCRYPT_TYPE_NONE:
+                {
+                    // for NO encryption, if the Bss description has the Privacy bit turned on, then encryption is
+                    // required so we have to reject this Bss.
+                    if ( csrIsPrivacy( pSirBssDesc ) )
+                    {
+                        fMatch = FALSE;
+                    }
+                    else
+                    {
+                        fMatch = TRUE;
+                    }
+
+                    if ( fMatch )
+                    {
+                        fMatch = FALSE;
+                        //Check Multicast cipher requested and Auth type requested.
+                        for( idx = 0 ; idx < pMCEncryptionType->numEntries ; idx++ )
+                        {
+                            if( eCSR_ENCRYPT_TYPE_NONE == pMCEncryptionType->encryptionType[idx] )
+                            {
+                                fMatch = TRUE; //Multicast can only be none.
+                                mcCipher = pMCEncryptionType->encryptionType[idx];
+                                break;
+                            }
+                        }
+                        if (!fMatch) break;
+
+                        fMatch = FALSE;
+                        //Check Auth list. It should contain AuthOpen.
+                        for( idx = 0 ; idx < authType->numEntries ; idx++ )
+                        {
+                            if( eCSR_AUTH_TYPE_OPEN_SYSTEM == authType->authType[idx] )
+                            {
+                               fMatch = TRUE;
+                               negAuthType = eCSR_AUTH_TYPE_OPEN_SYSTEM;
+                               break;
+                            }
+                        } 
+                        if (!fMatch) break;
+
+                    }
+                    break;
+                }
+
+            case eCSR_ENCRYPT_TYPE_WEP40_STATICKEY:
+            case eCSR_ENCRYPT_TYPE_WEP104_STATICKEY:
+                // !! might want to check for WEP keys set in the Profile.... ?
+                // !! don't need to have the privacy bit in the Bss description.  Many AP policies make legacy
+                // encryption 'optional' so we don't know if we can associate or not.  The AP will reject if
+                // encryption is not allowed without the Privacy bit turned on.
+                fMatch = csrValidateWep( pMac, ucCipher, authType, pMCEncryptionType, &negAuthType, &mcCipher, pSirBssDesc, pIes);
+
+                break;
+
+                // these are all of the WPA encryption types...
+            case eCSR_ENCRYPT_TYPE_WEP40:
+            case eCSR_ENCRYPT_TYPE_WEP104:
+                fMatch = csrValidateWep( pMac, ucCipher, authType, pMCEncryptionType, &negAuthType, &mcCipher, pSirBssDesc, pIes);
+                break;
+
+            case eCSR_ENCRYPT_TYPE_TKIP:
+            case eCSR_ENCRYPT_TYPE_AES:
+                {
+                    if(pIes)
+                    {
+                        // First check if there is a RSN match
+                        fMatch = csrIsRSNMatch( pMac, authType, ucCipher, pMCEncryptionType, pIes, &negAuthType, &mcCipher );
+                        if( !fMatch )
+                        {
+                            // If not RSN, then check if there is a WPA match
+                            fMatch = csrIsWpaEncryptionMatch( pMac, authType, ucCipher, pMCEncryptionType, pIes, 
+                                                              &negAuthType, &mcCipher );
+                        }
+                    }
+                    else
+                    {
+                        fMatch = FALSE;
+                    }
+                    break;
+                }
+#ifdef FEATURE_WLAN_WAPI
+           case eCSR_ENCRYPT_TYPE_WPI://WAPI
+               {
+                   if(pIes)
+                   {
+                       fMatch = csrIsWapiMatch( hHal, authType, ucCipher, pMCEncryptionType, pIes, &negAuthType, &mcCipher );
+                   }
+                   else
+                   {
+                       fMatch = FALSE;
+                   }
+                   break;
+               }
+#endif /* FEATURE_WLAN_WAPI */
+            case eCSR_ENCRYPT_TYPE_ANY: 
+            default: 
+            {
+                tANI_BOOLEAN fMatchAny = eANI_BOOLEAN_FALSE;
+
+                fMatch = eANI_BOOLEAN_TRUE;
+                //It is allowed to match anything. Try the more secured ones first.
+                if(pIes)
+                {
+                    //Check AES first
+                    ucCipher = eCSR_ENCRYPT_TYPE_AES;
+                    fMatchAny = csrIsRSNMatch( hHal, authType, ucCipher, pMCEncryptionType, pIes, &negAuthType, &mcCipher );
+                    if(!fMatchAny)
+                    {
+                        //Check TKIP
+                        ucCipher = eCSR_ENCRYPT_TYPE_TKIP;
+                        fMatchAny = csrIsRSNMatch( hHal, authType, ucCipher, pMCEncryptionType, pIes, &negAuthType, &mcCipher );
+                    }
+#ifdef FEATURE_WLAN_WAPI
+                    if(!fMatchAny)
+                    {
+                        //Check WAPI
+                        ucCipher = eCSR_ENCRYPT_TYPE_WPI;
+                        fMatchAny = csrIsWapiMatch( hHal, authType, ucCipher, pMCEncryptionType, pIes, &negAuthType, &mcCipher );
+                    }
+#endif /* FEATURE_WLAN_WAPI */
+                }
+                if(!fMatchAny)
+                {
+                    ucCipher = eCSR_ENCRYPT_TYPE_WEP104;
+                    if(!csrValidateWep( pMac, ucCipher, authType, pMCEncryptionType, &negAuthType, &mcCipher, pSirBssDesc, pIes))
+                    {
+                        ucCipher = eCSR_ENCRYPT_TYPE_WEP40;
+                        if(!csrValidateWep( pMac, ucCipher, authType, pMCEncryptionType, &negAuthType, &mcCipher, pSirBssDesc, pIes))
+                        {
+                            ucCipher = eCSR_ENCRYPT_TYPE_WEP104_STATICKEY;
+                            if(!csrValidateWep( pMac, ucCipher, authType, pMCEncryptionType, &negAuthType, &mcCipher, pSirBssDesc, pIes))
+                            {
+                                ucCipher = eCSR_ENCRYPT_TYPE_WEP40_STATICKEY;
+                                if(!csrValidateWep( pMac, ucCipher, authType, pMCEncryptionType, &negAuthType, &mcCipher, pSirBssDesc, pIes))
+                                {
+                                    //It must be open and no encryption
+                                    if ( csrIsPrivacy( pSirBssDesc ) )
+                                    {
+                                        //This is not right
+                                        fMatch = eANI_BOOLEAN_FALSE;
+                                    }
+                                    else
+                                    {
+                                        negAuthType = eCSR_AUTH_TYPE_OPEN_SYSTEM;
+                                        mcCipher = eCSR_ENCRYPT_TYPE_NONE;
+                                        ucCipher = eCSR_ENCRYPT_TYPE_NONE;
+                                    }
+                                }
+                            }
+                        }
+                    }
+                }
+                break;
+            }
+        }
+
+    }
+
+    if( fMatch ) 
+    {
+        if( negotiatedUCCipher )
+            *negotiatedUCCipher = ucCipher;
+   
+        if( negotiatedMCCipher )
+            *negotiatedMCCipher = mcCipher;
+   
+        if( negotiatedAuthtype )
+            *negotiatedAuthtype = negAuthType;
+    }
+
+    return( fMatch );
+}
+
+
+tANI_BOOLEAN csrIsSsidMatch( tpAniSirGlobal pMac, tANI_U8 *ssid1, tANI_U8 ssid1Len, tANI_U8 *bssSsid,
+                            tANI_U8 bssSsidLen, tANI_BOOLEAN fSsidRequired )
+{
+    tANI_BOOLEAN fMatch = FALSE;
+
+    do {
+
+        // There are a few special cases.  If the Bss description has a Broadcast SSID,
+        // then our Profile must have a single SSID without Wildcards so we can program
+        // the SSID.
+        // SSID could be suppressed in beacons. In that case SSID IE has valid length
+        // but the SSID value is all NULL characters. That condition is trated same
+        // as NULL SSID
+        if ( csrIsNULLSSID( bssSsid, bssSsidLen ) )
+        {
+            if ( eANI_BOOLEAN_FALSE == fSsidRequired )
+            {
+                fMatch = TRUE;
+            }
+            break;
+        }
+
+        // Check for the specification of the Broadcast SSID at the beginning of the list.
+        // If specified, then all SSIDs are matches (broadcast SSID means accept all SSIDs).
+        if ( ssid1Len == 0 )
+        {
+            fMatch = TRUE;
+            break;
+        }
+
+        if(ssid1Len != bssSsidLen) break;
+        if(palEqualMemory(pMac->hHdd, bssSsid, ssid1, bssSsidLen))
+        {
+            fMatch = TRUE;
+            break;
+        }
+
+    } while( 0 );
+
+    return( fMatch );
+}
+
+
+//Null ssid means match
+tANI_BOOLEAN csrIsSsidInList( tHalHandle hHal, tSirMacSSid *pSsid, tCsrSSIDs *pSsidList )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fMatch = FALSE;
+    tANI_U32 i;
+
+    if ( pSsidList && pSsid )
+    {
+        for(i = 0; i < pSsidList->numOfSSIDs; i++)
+        {
+            if(csrIsNULLSSID(pSsidList->SSIDList[i].SSID.ssId, pSsidList->SSIDList[i].SSID.length) ||
+                ((pSsidList->SSIDList[i].SSID.length == pSsid->length) &&
+                    palEqualMemory(pMac->hHdd, pSsid->ssId, pSsidList->SSIDList[i].SSID.ssId, pSsid->length)))
+            {
+                fMatch = TRUE;
+                break;
+            }
+        }
+    }
+
+    return (fMatch);
+}
+
+//like to use sirCompareMacAddr
+tANI_BOOLEAN csrIsMacAddressZero( tpAniSirGlobal pMac, tCsrBssid *pMacAddr )
+{
+    tANI_U8 bssid[WNI_CFG_BSSID_LEN] = {0, 0, 0, 0, 0, 0};
+
+    return( palEqualMemory(pMac->hHdd, bssid, pMacAddr, WNI_CFG_BSSID_LEN));
+}
+
+//like to use sirCompareMacAddr
+tANI_BOOLEAN csrIsMacAddressBroadcast( tpAniSirGlobal pMac, tCsrBssid *pMacAddr )
+{
+    tANI_U8 bssid[WNI_CFG_BSSID_LEN] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+
+    return( palEqualMemory(pMac->hHdd, bssid, pMacAddr, WNI_CFG_BSSID_LEN));
+}
+
+
+//like to use sirCompareMacAddr
+tANI_BOOLEAN csrIsMacAddressEqual( tpAniSirGlobal pMac, tCsrBssid *pMacAddr1, tCsrBssid *pMacAddr2 )
+{
+    return( palEqualMemory(pMac->hHdd, pMacAddr1, pMacAddr2, sizeof(tCsrBssid)) );
+}
+
+
+tANI_BOOLEAN csrIsBssidMatch( tHalHandle hHal, tCsrBssid *pProfBssid, tCsrBssid *BssBssid )
+{
+    tANI_BOOLEAN fMatch = FALSE;
+    tCsrBssid ProfileBssid;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    // for efficiency of the MAC_ADDRESS functions, move the
+    // Bssid's into MAC_ADDRESS structs.
+    palCopyMemory( pMac->hHdd, &ProfileBssid, pProfBssid, sizeof(tCsrBssid) );
+
+    do {
+
+        // Give the profile the benefit of the doubt... accept either all 0 or
+        // the real broadcast Bssid (all 0xff) as broadcast Bssids (meaning to
+        // match any Bssids).
+        if ( csrIsMacAddressZero( pMac, &ProfileBssid ) ||
+             csrIsMacAddressBroadcast( pMac, &ProfileBssid ) )
+        {
+             fMatch = TRUE;
+             break;
+        }
+
+        if ( csrIsMacAddressEqual( pMac, BssBssid, &ProfileBssid ) )
+        {
+            fMatch = TRUE;
+            break;
+        }
+
+    } while( 0 );
+
+    return( fMatch );
+}
+
+
+tANI_BOOLEAN csrIsBSSTypeMatch(eCsrRoamBssType bssType1, eCsrRoamBssType bssType2)
+{
+    if((eCSR_BSS_TYPE_ANY != bssType1 && eCSR_BSS_TYPE_ANY != bssType2) && (bssType1 != bssType2))
+        return eANI_BOOLEAN_FALSE;
+    else
+        return eANI_BOOLEAN_TRUE;
+}
+
+
+tANI_BOOLEAN csrIsBssTypeIBSS(eCsrRoamBssType bssType)
+{
+    return((tANI_BOOLEAN)(eCSR_BSS_TYPE_START_IBSS == bssType || eCSR_BSS_TYPE_IBSS == bssType));
+}
+
+tANI_BOOLEAN csrIsBssTypeWDS(eCsrRoamBssType bssType)
+{
+    return((tANI_BOOLEAN)(eCSR_BSS_TYPE_WDS_STA == bssType || eCSR_BSS_TYPE_WDS_AP == bssType));
+}
+
+tANI_BOOLEAN csrIsBSSTypeCapsMatch( eCsrRoamBssType bssType, tSirBssDescription *pSirBssDesc )
+{
+    tANI_BOOLEAN fMatch = TRUE;
+
+    do
+    {
+        switch( bssType )
+        {
+            case eCSR_BSS_TYPE_ANY:
+                break;
+
+            case eCSR_BSS_TYPE_INFRASTRUCTURE:
+            case eCSR_BSS_TYPE_WDS_STA:
+                if( !csrIsInfraBssDesc( pSirBssDesc ) )
+                    fMatch = FALSE;
+
+                break;
+
+            case eCSR_BSS_TYPE_IBSS:
+            case eCSR_BSS_TYPE_START_IBSS:
+                if( !csrIsIbssBssDesc( pSirBssDesc ) )
+                    fMatch = FALSE;
+
+                break;
+
+            case eCSR_BSS_TYPE_WDS_AP: //For WDS AP, no need to match anything
+            default:
+                fMatch = FALSE;
+                break;
+        }
+    }
+    while( 0 );
+
+
+    return( fMatch );
+}
+
+static tANI_BOOLEAN csrIsCapabilitiesMatch( tpAniSirGlobal pMac, eCsrRoamBssType bssType, tSirBssDescription *pSirBssDesc )
+{
+  return( csrIsBSSTypeCapsMatch( bssType, pSirBssDesc ) );
+}
+
+
+
+static tANI_BOOLEAN csrIsSpecificChannelMatch( tpAniSirGlobal pMac, tSirBssDescription *pSirBssDesc, tANI_U8 Channel )
+{
+    tANI_BOOLEAN fMatch = TRUE;
+
+    do
+    {
+        // if the channel is ANY, then always match...
+        if ( eCSR_OPERATING_CHANNEL_ANY == Channel ) break;
+        if ( Channel == pSirBssDesc->channelId ) break;
+
+        // didn't match anything.. so return NO match
+        fMatch = FALSE;
+
+    } while( 0 );
+
+    return( fMatch );
+}
+
+
+tANI_BOOLEAN csrIsChannelBandMatch( tpAniSirGlobal pMac, tANI_U8 channelId, tSirBssDescription *pSirBssDesc )
+{
+    tANI_BOOLEAN fMatch = TRUE;
+
+    do
+    {
+        // if the profile says Any channel AND the global settings says ANY channel, then we
+        // always match...
+        if ( eCSR_OPERATING_CHANNEL_ANY == channelId ) break;
+
+        if ( eCSR_OPERATING_CHANNEL_ANY != channelId )
+        {
+            fMatch = csrIsSpecificChannelMatch( pMac, pSirBssDesc, channelId );
+        }
+
+    } while( 0 );
+
+    return( fMatch );
+}
+
+
+/**
+ * \brief Enquire as to whether a given rate is supported by the
+ * adapter as currently configured
+ *
+ *
+ * \param nRate A rate in units of 500kbps
+ *
+ * \return TRUE if  the adapter is currently capable  of supporting this
+ * rate, FALSE else
+ *
+ *
+ * The rate encoding  is just as in 802.11  Information Elements, except
+ * that the high bit is \em  not interpreted as indicating a Basic Rate,
+ * and proprietary rates are allowed, too.
+ *
+ * Note  that if the  adapter's dot11Mode  is g,  we don't  restrict the
+ * rates.  According to hwReadEepromParameters, this will happen when:
+ *
+ *   ... the  card is  configured for ALL  bands through  the property
+ *   page.  If this occurs, and the card is not an ABG card ,then this
+ *   code  is  setting the  dot11Mode  to  assume  the mode  that  the
+ *   hardware can support.   For example, if the card  is an 11BG card
+ *   and we  are configured to support  ALL bands, then  we change the
+ *   dot11Mode  to 11g  because  ALL in  this  case is  only what  the
+ *   hardware can support.
+ *
+ *
+ */
+
+static tANI_BOOLEAN csrIsAggregateRateSupported( tpAniSirGlobal pMac, tANI_U16 rate )
+{
+    tANI_BOOLEAN fSupported = eANI_BOOLEAN_FALSE;
+    tANI_U16 idx, newRate;
+
+    //In case basic rate flag is set
+    newRate = BITS_OFF(rate, CSR_DOT11_BASIC_RATE_MASK);
+    if ( eCSR_CFG_DOT11_MODE_11A == pMac->roam.configParam.uCfgDot11Mode )
+    {
+        switch ( newRate )
+        {
+        case eCsrSuppRate_6Mbps:
+        case eCsrSuppRate_9Mbps:
+        case eCsrSuppRate_12Mbps:
+        case eCsrSuppRate_18Mbps:
+        case eCsrSuppRate_24Mbps:
+        case eCsrSuppRate_36Mbps:
+        case eCsrSuppRate_48Mbps:
+        case eCsrSuppRate_54Mbps:
+            fSupported = TRUE;
+            break;
+        default:
+            fSupported = FALSE;
+            break;
+        }
+
+    }
+    else if( eCSR_CFG_DOT11_MODE_11B == pMac->roam.configParam.uCfgDot11Mode )
+    {
+        switch ( newRate )
+        {
+        case eCsrSuppRate_1Mbps:
+        case eCsrSuppRate_2Mbps:
+        case eCsrSuppRate_5_5Mbps:
+        case eCsrSuppRate_11Mbps:
+            fSupported = TRUE;
+            break;
+        default:
+            fSupported = FALSE;
+            break;
+        }
+    }
+    else if ( !pMac->roam.configParam.ProprietaryRatesEnabled )
+    {
+
+        switch ( newRate )
+        {
+        case eCsrSuppRate_1Mbps:
+        case eCsrSuppRate_2Mbps:
+        case eCsrSuppRate_5_5Mbps:
+        case eCsrSuppRate_6Mbps:
+        case eCsrSuppRate_9Mbps:
+        case eCsrSuppRate_11Mbps:
+        case eCsrSuppRate_12Mbps:
+        case eCsrSuppRate_18Mbps:
+        case eCsrSuppRate_24Mbps:
+        case eCsrSuppRate_36Mbps:
+        case eCsrSuppRate_48Mbps:
+        case eCsrSuppRate_54Mbps:
+            fSupported = TRUE;
+            break;
+        default:
+            fSupported = FALSE;
+            break;
+        }
+
+    }
+    else {
+
+        if ( eCsrSuppRate_1Mbps   == newRate ||
+             eCsrSuppRate_2Mbps   == newRate ||
+             eCsrSuppRate_5_5Mbps == newRate ||
+             eCsrSuppRate_11Mbps  == newRate )
+        {
+            fSupported = TRUE;
+        }
+        else {
+            idx = 0x1;
+
+            switch ( newRate )
+            {
+            case eCsrSuppRate_6Mbps:
+                fSupported = gPhyRatesSuppt[0][idx];
+                break;
+            case eCsrSuppRate_9Mbps:
+                fSupported = gPhyRatesSuppt[1][idx];
+                break;
+            case eCsrSuppRate_12Mbps:
+                fSupported = gPhyRatesSuppt[2][idx];
+                break;
+            case eCsrSuppRate_18Mbps:
+                fSupported = gPhyRatesSuppt[3][idx];
+                break;
+            case eCsrSuppRate_20Mbps:
+                fSupported = gPhyRatesSuppt[4][idx];
+                break;
+            case eCsrSuppRate_24Mbps:
+                fSupported = gPhyRatesSuppt[5][idx];
+                break;
+            case eCsrSuppRate_36Mbps:
+                fSupported = gPhyRatesSuppt[6][idx];
+                break;
+            case eCsrSuppRate_40Mbps:
+                fSupported = gPhyRatesSuppt[7][idx];
+                break;
+            case eCsrSuppRate_42Mbps:
+                fSupported = gPhyRatesSuppt[8][idx];
+                break;
+            case eCsrSuppRate_48Mbps:
+                fSupported = gPhyRatesSuppt[9][idx];
+                break;
+            case eCsrSuppRate_54Mbps:
+                fSupported = gPhyRatesSuppt[10][idx];
+                break;
+            case eCsrSuppRate_72Mbps:
+                fSupported = gPhyRatesSuppt[11][idx];
+                break;
+            case eCsrSuppRate_80Mbps:
+                fSupported = gPhyRatesSuppt[12][idx];
+                break;
+            case eCsrSuppRate_84Mbps:
+                fSupported = gPhyRatesSuppt[13][idx];
+                break;
+            case eCsrSuppRate_96Mbps:
+                fSupported = gPhyRatesSuppt[14][idx];
+                break;
+            case eCsrSuppRate_108Mbps:
+                fSupported = gPhyRatesSuppt[15][idx];
+                break;
+            case eCsrSuppRate_120Mbps:
+                fSupported = gPhyRatesSuppt[16][idx];
+                break;
+            case eCsrSuppRate_126Mbps:
+                fSupported = gPhyRatesSuppt[17][idx];
+                break;
+            case eCsrSuppRate_144Mbps:
+                fSupported = gPhyRatesSuppt[18][idx];
+                break;
+            case eCsrSuppRate_160Mbps:
+                fSupported = gPhyRatesSuppt[19][idx];
+                break;
+            case eCsrSuppRate_168Mbps:
+                fSupported = gPhyRatesSuppt[20][idx];
+                break;
+            case eCsrSuppRate_192Mbps:
+                fSupported = gPhyRatesSuppt[21][idx];
+                break;
+            case eCsrSuppRate_216Mbps:
+                fSupported = gPhyRatesSuppt[22][idx];
+                break;
+            case eCsrSuppRate_240Mbps:
+                fSupported = gPhyRatesSuppt[23][idx];
+                break;
+            default:
+                fSupported = FALSE;
+                break;
+            }
+        }
+    }
+
+    return fSupported;
+}
+
+
+
+static tANI_BOOLEAN csrIsRateSetMatch( tpAniSirGlobal pMac,
+                                     tDot11fIESuppRates *pBssSuppRates,
+                                     tDot11fIEExtSuppRates *pBssExtSuppRates )
+{
+    tANI_BOOLEAN fMatch = TRUE;
+    tANI_U32 i;
+
+
+    // Validate that all of the Basic rates advertised in the Bss description are supported.
+    if ( pBssSuppRates )
+    {
+        for( i = 0; i < pBssSuppRates->num_rates; i++ )
+        {
+            if ( CSR_IS_BASIC_RATE( pBssSuppRates->rates[ i ] ) )
+            {
+                if ( !csrIsAggregateRateSupported( pMac, pBssSuppRates->rates[ i ] ) )
+                {
+                    fMatch = FALSE;
+                    break;
+                }
+            }
+        }
+    }
+
+    if ( fMatch && pBssExtSuppRates )
+    {
+        for( i = 0; i < pBssExtSuppRates->num_rates; i++ )
+        {
+            if ( CSR_IS_BASIC_RATE( pBssExtSuppRates->rates[ i ] ) )
+            {
+                if ( !csrIsAggregateRateSupported( pMac, pBssExtSuppRates->rates[ i ] ) )
+                {
+                    fMatch = FALSE;
+                    break;
+                }
+            }
+        }
+    }
+
+    return( fMatch );
+
+}
+
+
+//ppIes can be NULL. If caller want to get the *ppIes allocated by this function, pass in *ppIes = NULL
+tANI_BOOLEAN csrMatchBSS( tHalHandle hHal, tSirBssDescription *pBssDesc, tCsrScanResultFilter *pFilter, 
+                          eCsrAuthType *pNegAuth, eCsrEncryptionType *pNegUc, eCsrEncryptionType *pNegMc,
+                          tDot11fBeaconIEs **ppIes)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fRC = eANI_BOOLEAN_FALSE, fCheck;
+    tANI_U32 i;
+    tDot11fBeaconIEs *pIes = NULL;
+    tANI_U8 *pb;
+
+    do {
+        if( ( NULL == ppIes ) || ( *ppIes ) == NULL )
+        {
+            //If no IEs passed in, get our own.
+            if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIes)))
+            {
+                break;
+            }
+        }
+        else
+        {
+            //Save the one pass in for local use
+            pIes = *ppIes;
+        }
+        
+        //Check if caller wants P2P
+        fCheck = (!pFilter->p2pResult || pIes->P2PBeaconProbeRes.present);
+        if(!fCheck) break;
+
+        if(pIes->SSID.present)
+        {
+            for(i = 0; i < pFilter->SSIDs.numOfSSIDs; i++)
+            {
+                fCheck = csrIsSsidMatch( pMac, pFilter->SSIDs.SSIDList[i].SSID.ssId, pFilter->SSIDs.SSIDList[i].SSID.length,
+                                        pIes->SSID.ssid,
+                                        pIes->SSID.num_ssid, eANI_BOOLEAN_TRUE );
+                if ( fCheck ) break;
+            }
+            if(!fCheck) break;
+        }
+        fCheck = eANI_BOOLEAN_TRUE;
+        for(i = 0; i < pFilter->BSSIDs.numOfBSSIDs; i++)
+        {
+            fCheck = csrIsBssidMatch( pMac, (tCsrBssid *)&pFilter->BSSIDs.bssid[i], (tCsrBssid *)pBssDesc->bssId );
+            if ( fCheck ) break;
+
+            if (pFilter->p2pResult && pIes->P2PBeaconProbeRes.present)
+            {
+               fCheck = csrIsBssidMatch( pMac, (tCsrBssid *)&pFilter->BSSIDs.bssid[i], 
+                              (tCsrBssid *)pIes->P2PBeaconProbeRes.P2PDeviceInfo.P2PDeviceAddress );
+
+               if ( fCheck ) break;
+            }
+        }
+        if(!fCheck) break;
+
+        fCheck = eANI_BOOLEAN_TRUE;
+        for(i = 0; i < pFilter->ChannelInfo.numOfChannels; i++)
+        {
+            fCheck = csrIsChannelBandMatch( pMac, pFilter->ChannelInfo.ChannelList[i], pBssDesc );
+            if ( fCheck ) break;
+        }
+        if(!fCheck)
+            break;
+#if defined WLAN_FEATURE_VOWIFI
+        /* If this is for measurement filtering */
+        if( pFilter->fMeasurement )
+        {
+           fRC = eANI_BOOLEAN_TRUE;
+           break;
+        }
+#endif
+        if ( !csrIsPhyModeMatch( pMac, pFilter->phyMode, pBssDesc, NULL, NULL, pIes ) ) break;
+        if ( (!pFilter->bWPSAssociation) &&
+             !csrIsSecurityMatch( pMac, &pFilter->authType, &pFilter->EncryptionType, &pFilter->mcEncryptionType,
+                                 pBssDesc, pIes, pNegAuth, pNegUc, pNegMc ) ) break;
+        if ( !csrIsCapabilitiesMatch( pMac, pFilter->BSSType, pBssDesc ) ) break;
+        if ( !csrIsRateSetMatch( pMac, &pIes->SuppRates, &pIes->ExtSuppRates ) ) break;
+        //Tush-QoS: validate first if asked for APSD or WMM association
+        if ( (eCsrRoamWmmQbssOnly == pMac->roam.configParam.WMMSupportMode) &&
+             !CSR_IS_QOS_BSS(pIes) )
+             break;
+        //Check country. check even when pb is NULL because we may want to make sure
+        //AP has a country code in it if fEnforceCountryCodeMatch is set.
+        pb = ( pFilter->countryCode[0] ) ? ( pFilter->countryCode) : NULL;
+
+        fCheck = csrMatchCountryCode( pMac, pb, pIes );
+        if(!fCheck)
+            break;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+        if (pFilter->MDID.mdiePresent)
+        {
+            if (pBssDesc->mdiePresent)
+            {
+                if (pFilter->MDID.mobilityDomain != (pBssDesc->mdie[1] << 8 | pBssDesc->mdie[0]))
+                    break;
+            }
+            else
+                break;
+        }
+#endif
+        fRC = eANI_BOOLEAN_TRUE;
+
+    } while( 0 );
+    if( ppIes )
+    {
+        *ppIes = pIes;
+    }
+    else if( pIes )
+    {
+        palFreeMemory(pMac->hHdd, pIes);
+    }
+
+    return( fRC );
+}
+
+tANI_BOOLEAN csrMatchConnectedBSSSecurity( tpAniSirGlobal pMac, tCsrRoamConnectedProfile *pProfile, 
+                                           tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes)
+{
+    tCsrEncryptionList ucEncryptionList, mcEncryptionList;
+    tCsrAuthList authList;
+
+    ucEncryptionList.numEntries = 1;
+    ucEncryptionList.encryptionType[0] = pProfile->EncryptionType;
+
+    mcEncryptionList.numEntries = 1;
+    mcEncryptionList.encryptionType[0] = pProfile->mcEncryptionType;
+
+    authList.numEntries = 1;
+    authList.authType[0] = pProfile->AuthType;
+
+    return( csrIsSecurityMatch( pMac, &authList, &ucEncryptionList, &mcEncryptionList, pBssDesc, pIes, NULL, NULL, NULL ));
+
+}
+
+
+tANI_BOOLEAN csrMatchBSSToConnectProfile( tHalHandle hHal, tCsrRoamConnectedProfile *pProfile,
+                                          tSirBssDescription *pBssDesc, tDot11fBeaconIEs *pIes )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_BOOLEAN fRC = eANI_BOOLEAN_FALSE, fCheck;
+    tDot11fBeaconIEs *pIesLocal = pIes;
+
+    do {
+        if( !pIes )
+        {
+            if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, pBssDesc, &pIesLocal)))
+            {
+                break;
+            }
+        }
+        fCheck = eANI_BOOLEAN_TRUE;
+        if(pIesLocal->SSID.present)
+        {
+            tANI_BOOLEAN fCheckSsid = eANI_BOOLEAN_FALSE;
+            if(pProfile->SSID.length)
+            {
+                fCheckSsid = eANI_BOOLEAN_TRUE;
+            }
+            fCheck = csrIsSsidMatch( pMac, pProfile->SSID.ssId, pProfile->SSID.length,
+                                        pIesLocal->SSID.ssid, pIesLocal->SSID.num_ssid, fCheckSsid );
+            if(!fCheck) break;
+        }
+        if ( !csrMatchConnectedBSSSecurity( pMac, pProfile, pBssDesc, pIesLocal) ) break;
+        if ( !csrIsCapabilitiesMatch( pMac, pProfile->BSSType, pBssDesc ) ) break;
+        if ( !csrIsRateSetMatch( pMac, &pIesLocal->SuppRates, &pIesLocal->ExtSuppRates ) ) break;
+        fCheck = csrIsChannelBandMatch( pMac, pProfile->operationChannel, pBssDesc );
+        if(!fCheck)
+            break;
+
+        fRC = eANI_BOOLEAN_TRUE;
+
+    } while( 0 );
+
+    if( !pIes && pIesLocal )
+    {
+        //locally allocated
+        palFreeMemory(pMac->hHdd, pIesLocal);
+    }
+
+    return( fRC );
+}
+
+
+
+tANI_BOOLEAN csrRatesIsDot11RateSupported( tHalHandle hHal, tANI_U8 rate )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_U16 n = BITS_OFF( rate, CSR_DOT11_BASIC_RATE_MASK );
+
+    return csrIsAggregateRateSupported( pMac, n );
+}
+
+
+tANI_U16 csrRatesMacPropToDot11( tANI_U16 Rate )
+{
+    tANI_U16 ConvertedRate = Rate;
+
+    switch( Rate )
+    {
+        case SIR_MAC_RATE_1:
+            ConvertedRate = 2;
+            break;
+        case SIR_MAC_RATE_2:
+            ConvertedRate = 4;
+            break;
+        case SIR_MAC_RATE_5_5:
+            ConvertedRate = 11;
+            break;
+        case SIR_MAC_RATE_11:
+            ConvertedRate = 22;
+            break;
+
+        case SIR_MAC_RATE_6:
+            ConvertedRate = 12;
+            break;
+        case SIR_MAC_RATE_9:
+            ConvertedRate = 18;
+            break;
+        case SIR_MAC_RATE_12:
+            ConvertedRate = 24;
+            break;
+        case SIR_MAC_RATE_18:
+            ConvertedRate = 36;
+            break;
+        case SIR_MAC_RATE_24:
+            ConvertedRate = 48;
+            break;
+        case SIR_MAC_RATE_36:
+            ConvertedRate = 72;
+            break;
+        case SIR_MAC_RATE_42:
+            ConvertedRate = 84;
+            break;
+        case SIR_MAC_RATE_48:
+            ConvertedRate = 96;
+            break;
+        case SIR_MAC_RATE_54:
+            ConvertedRate = 108;
+            break;
+
+        case SIR_MAC_RATE_72:
+            ConvertedRate = 144;
+            break;
+        case SIR_MAC_RATE_84:
+            ConvertedRate = 168;
+            break;
+        case SIR_MAC_RATE_96:
+            ConvertedRate = 192;
+            break;
+        case SIR_MAC_RATE_108:
+            ConvertedRate = 216;
+            break;
+        case SIR_MAC_RATE_126:
+            ConvertedRate = 252;
+            break;
+        case SIR_MAC_RATE_144:
+            ConvertedRate = 288;
+            break;
+        case SIR_MAC_RATE_168:
+            ConvertedRate = 336;
+            break;
+        case SIR_MAC_RATE_192:
+            ConvertedRate = 384;
+            break;
+        case SIR_MAC_RATE_216:
+            ConvertedRate = 432;
+            break;
+        case SIR_MAC_RATE_240:
+            ConvertedRate = 480;
+            break;
+
+        case 0xff:
+            ConvertedRate = 0;
+            break;
+    }
+
+    return ConvertedRate;
+}
+
+
+tANI_U16 csrRatesFindBestRate( tSirMacRateSet *pSuppRates, tSirMacRateSet *pExtRates, tSirMacPropRateSet *pPropRates )
+{
+    tANI_U8 i;
+    tANI_U16 nBest;
+
+    nBest = pSuppRates->rate[ 0 ] & ( ~CSR_DOT11_BASIC_RATE_MASK );
+
+    if(pSuppRates->numRates > SIR_MAC_RATESET_EID_MAX)
+    {
+        pSuppRates->numRates = SIR_MAC_RATESET_EID_MAX;
+    }
+
+    for ( i = 1U; i < pSuppRates->numRates; ++i )
+    {
+        nBest = (tANI_U16)CSR_MAX( nBest, pSuppRates->rate[ i ] & ( ~CSR_DOT11_BASIC_RATE_MASK ) );
+    }
+
+    if ( NULL != pExtRates )
+    {
+        for ( i = 0U; i < pExtRates->numRates; ++i )
+        {
+            nBest = (tANI_U16)CSR_MAX( nBest, pExtRates->rate[ i ] & ( ~CSR_DOT11_BASIC_RATE_MASK ) );
+        }
+    }
+
+    if ( NULL != pPropRates )
+    {
+        for ( i = 0U; i < pPropRates->numPropRates; ++i )
+        {
+            nBest = (tANI_U16)CSR_MAX( nBest,  csrRatesMacPropToDot11( pPropRates->propRate[ i ] ) );
+        }
+    }
+
+    return nBest;
+}
+
+
+void csrReleaseProfile(tpAniSirGlobal pMac, tCsrRoamProfile *pProfile)
+{
+    if(pProfile)
+    {
+        if(pProfile->BSSIDs.bssid)
+        {
+            palFreeMemory(pMac->hHdd, pProfile->BSSIDs.bssid);
+            pProfile->BSSIDs.bssid = NULL;
+        }
+        if(pProfile->SSIDs.SSIDList)
+        {
+            palFreeMemory(pMac->hHdd, pProfile->SSIDs.SSIDList);
+            pProfile->SSIDs.SSIDList = NULL;
+        }
+        if(pProfile->pWPAReqIE)
+        {
+            palFreeMemory(pMac->hHdd, pProfile->pWPAReqIE);
+            pProfile->pWPAReqIE = NULL;
+        }
+        if(pProfile->pRSNReqIE)
+        {
+            palFreeMemory(pMac->hHdd, pProfile->pRSNReqIE);
+            pProfile->pRSNReqIE = NULL;
+        }
+#ifdef FEATURE_WLAN_WAPI
+        if(pProfile->pWAPIReqIE)
+        {
+            palFreeMemory(pMac->hHdd, pProfile->pWAPIReqIE);
+            pProfile->pWAPIReqIE = NULL;
+        }
+#endif /* FEATURE_WLAN_WAPI */
+
+        if(pProfile->pAddIEScan)
+        {
+            palFreeMemory(pMac->hHdd, pProfile->pAddIEScan);
+            pProfile->pAddIEScan = NULL;
+        }
+
+        if(pProfile->pAddIEAssoc)
+        {
+            palFreeMemory(pMac->hHdd, pProfile->pAddIEAssoc);
+            pProfile->pAddIEAssoc = NULL;
+        }
+        {
+            palFreeMemory(pMac->hHdd, pProfile->pAddIEAssoc);
+            pProfile->pAddIEAssoc = NULL;
+        }
+
+        if(pProfile->ChannelInfo.ChannelList)
+        {
+            palFreeMemory(pMac->hHdd, pProfile->ChannelInfo.ChannelList);
+            pProfile->ChannelInfo.ChannelList = NULL;
+        }
+
+    
+        palZeroMemory(pMac->hHdd, pProfile, sizeof(tCsrRoamProfile));
+    }
+}
+
+void csrFreeScanFilter(tpAniSirGlobal pMac, tCsrScanResultFilter *pScanFilter)
+{
+    if(pScanFilter->BSSIDs.bssid)
+    {
+        palFreeMemory(pMac->hHdd, pScanFilter->BSSIDs.bssid);
+        pScanFilter->BSSIDs.bssid = NULL;
+    }
+    if(pScanFilter->ChannelInfo.ChannelList)
+    {
+        palFreeMemory(pMac->hHdd, pScanFilter->ChannelInfo.ChannelList);
+        pScanFilter->ChannelInfo.ChannelList = NULL;
+    }
+    if(pScanFilter->SSIDs.SSIDList)
+    {
+        palFreeMemory(pMac->hHdd, pScanFilter->SSIDs.SSIDList);
+        pScanFilter->SSIDs.SSIDList = NULL;
+    }
+}
+
+
+void csrFreeRoamProfile(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    tCsrRoamSession *pSession = &pMac->roam.roamSession[sessionId];
+
+    if(pSession->pCurRoamProfile)
+    {
+        csrReleaseProfile(pMac, pSession->pCurRoamProfile);
+        palFreeMemory(pMac->hHdd, pSession->pCurRoamProfile);
+        pSession->pCurRoamProfile = NULL;
+    }
+}
+
+
+void csrFreeConnectBssDesc(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    tCsrRoamSession *pSession = &pMac->roam.roamSession[sessionId];
+
+    if(pSession->pConnectBssDesc)
+    {
+        palFreeMemory(pMac->hHdd, pSession->pConnectBssDesc);
+        pSession->pConnectBssDesc = NULL;
+    }
+}
+
+
+
+tSirResultCodes csrGetDisassocRspStatusCode( tSirSmeDisassocRsp *pSmeDisassocRsp )
+{
+    tANI_U8 *pBuffer = (tANI_U8 *)pSmeDisassocRsp;
+    tANI_U32 ret;
+
+    pBuffer += (sizeof(tANI_U16) + sizeof(tANI_U16) + sizeof(tSirMacAddr));
+    //tSirResultCodes is an enum, assuming is 32bit
+    //If we cannot make this assumption, use copymemory
+    pal_get_U32( pBuffer, &ret );
+
+    return( ( tSirResultCodes )ret );
+}
+
+
+tSirResultCodes csrGetDeAuthRspStatusCode( tSirSmeDeauthRsp *pSmeRsp )
+{
+    tANI_U8 *pBuffer = (tANI_U8 *)pSmeRsp;
+    tANI_U32 ret;
+
+    pBuffer += (sizeof(tANI_U16) + sizeof(tANI_U16) + sizeof(tSirMacAddr));
+    //tSirResultCodes is an enum, assuming is 32bit
+    //If we cannot make this assumption, use copymemory
+    pal_get_U32( pBuffer, &ret );
+
+    return( ( tSirResultCodes )ret );
+}
+
+#if 0
+tSirScanType csrGetScanType(tANI_U8 chnId, eRegDomainId domainId, tANI_U8 *countryCode)
+{
+    tSirScanType scanType = eSIR_PASSIVE_SCAN;
+    tANI_U8 cc = 0;
+
+    while (cc++ < gCsrDomainChnInfo[domainId].numChannels)
+    {
+        if(chnId == gCsrDomainChnInfo[domainId].chnInfo[cc].chnId)
+        {
+            scanType = gCsrDomainChnInfo[domainId].chnInfo[cc].scanType;
+            break;
+        }
+    }
+
+    return (scanType);
+}
+#endif
+
+tSirScanType csrGetScanType(tpAniSirGlobal pMac, tANI_U8 chnId)
+{
+    tSirScanType scanType = eSIR_PASSIVE_SCAN;
+    eNVChannelEnabledType channelEnabledType;
+
+    channelEnabledType = vos_nv_getChannelEnabledState(chnId);
+    if( NV_CHANNEL_ENABLE ==  channelEnabledType)
+    {
+         scanType = eSIR_ACTIVE_SCAN;
+    }
+    return (scanType);
+}
+
+
+tANI_U8 csrToUpper( tANI_U8 ch )
+{
+    tANI_U8 chOut;
+
+    if ( ch >= 'a' && ch <= 'z' )
+    {
+        chOut = ch - 'a' + 'A';
+    }
+    else
+    {
+        chOut = ch;
+    }
+    return( chOut );
+}
+
+
+tSirBssType csrTranslateBsstypeToMacType(eCsrRoamBssType csrtype)
+{
+    tSirBssType ret;
+
+    switch(csrtype)
+    {
+    case eCSR_BSS_TYPE_INFRASTRUCTURE:
+        ret = eSIR_INFRASTRUCTURE_MODE;
+        break;
+    case eCSR_BSS_TYPE_IBSS:
+    case eCSR_BSS_TYPE_START_IBSS:
+        ret = eSIR_IBSS_MODE;
+        break;
+    case eCSR_BSS_TYPE_WDS_AP:
+        ret = eSIR_BTAMP_AP_MODE;
+        break;
+    case eCSR_BSS_TYPE_WDS_STA:
+        ret = eSIR_BTAMP_STA_MODE;
+        break;
+#ifdef WLAN_SOFTAP_FEATURE
+    case eCSR_BSS_TYPE_INFRA_AP:
+        ret = eSIR_INFRA_AP_MODE;
+        break;
+#endif
+    case eCSR_BSS_TYPE_ANY:
+    default:
+        ret = eSIR_AUTO_MODE;
+        break;
+    }
+
+    return (ret);
+}
+
+
+//This function use the parameters to decide the CFG value.
+//CSR never sets WNI_CFG_DOT11_MODE_ALL to the CFG
+//So PE should not see WNI_CFG_DOT11_MODE_ALL when it gets the CFG value
+#ifdef WLAN_SOFTAP_FEATURE
+eCsrCfgDot11Mode csrGetCfgDot11ModeFromCsrPhyMode(tCsrRoamProfile *pProfile, eCsrPhyMode phyMode, tANI_BOOLEAN fProprietary)
+#else
+eCsrCfgDot11Mode csrGetCfgDot11ModeFromCsrPhyMode(eCsrPhyMode phyMode, tANI_BOOLEAN fProprietary)
+#endif
+{
+    tANI_U32 cfgDot11Mode = eCSR_CFG_DOT11_MODE_ABG;
+
+    switch(phyMode)
+    {
+    case eCSR_DOT11_MODE_11a:
+    case eCSR_DOT11_MODE_11a_ONLY:
+        cfgDot11Mode = eCSR_CFG_DOT11_MODE_11A;
+        break;
+    case eCSR_DOT11_MODE_11b:
+    case eCSR_DOT11_MODE_11b_ONLY:
+        cfgDot11Mode = eCSR_CFG_DOT11_MODE_11B;
+        break;
+    case eCSR_DOT11_MODE_11g:
+    case eCSR_DOT11_MODE_11g_ONLY:
+#ifdef WLAN_SOFTAP_FEATURE
+        if(pProfile && (CSR_IS_INFRA_AP(pProfile)) && (phyMode == eCSR_DOT11_MODE_11g_ONLY))
+            cfgDot11Mode = eCSR_CFG_DOT11_MODE_11G_ONLY;
+        else
+#endif
+        cfgDot11Mode = eCSR_CFG_DOT11_MODE_11G;
+        break;
+    case eCSR_DOT11_MODE_11n:
+        if(fProprietary)
+        {
+            cfgDot11Mode = eCSR_CFG_DOT11_MODE_TAURUS;
+        }
+        else
+        {
+            cfgDot11Mode = eCSR_CFG_DOT11_MODE_11N;
+        }
+        break;
+    case eCSR_DOT11_MODE_11n_ONLY:
+#ifdef WLAN_SOFTAP_FEATURE
+       if(pProfile && CSR_IS_INFRA_AP(pProfile))
+           cfgDot11Mode = eCSR_CFG_DOT11_MODE_11N_ONLY;
+       else
+#endif
+       cfgDot11Mode = eCSR_CFG_DOT11_MODE_11N;
+       break;
+    case eCSR_DOT11_MODE_TAURUS:
+        cfgDot11Mode = eCSR_CFG_DOT11_MODE_TAURUS;
+        break;
+    case eCSR_DOT11_MODE_abg:
+        cfgDot11Mode = eCSR_CFG_DOT11_MODE_ABG;
+        break;
+    case eCSR_DOT11_MODE_AUTO:
+        cfgDot11Mode = eCSR_CFG_DOT11_MODE_AUTO;
+        break;
+    default:
+        //No need to assign anything here
+        break;
+    }
+
+    return (cfgDot11Mode);
+}
+
+
+eHalStatus csrSetRegulatoryDomain(tpAniSirGlobal pMac, v_REGDOMAIN_t domainId, tANI_BOOLEAN *pfRestartNeeded)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_BOOLEAN fRestart;
+
+    if(pMac->scan.domainIdCurrent == domainId)
+    {
+        //no change
+        fRestart = eANI_BOOLEAN_FALSE;
+    }
+    else if( !pMac->roam.configParam.fEnforceDefaultDomain )
+    {
+        pMac->scan.domainIdCurrent = domainId;
+        fRestart = eANI_BOOLEAN_TRUE;
+    }
+    else
+    {
+        //We cannot change the domain
+        status = eHAL_STATUS_CSR_WRONG_STATE;
+        fRestart = eANI_BOOLEAN_FALSE;
+    }
+    if(pfRestartNeeded)
+    {
+        *pfRestartNeeded = fRestart;
+    }
+
+    return (status);
+}
+
+
+v_REGDOMAIN_t csrGetCurrentRegulatoryDomain(tpAniSirGlobal pMac)
+{
+    return (pMac->scan.domainIdCurrent);
+}
+
+#if 0
+eHalStatus csrGetRegulatoryDomainForCountry(tpAniSirGlobal pMac, tANI_U8 *pCountry, eRegDomainId *pDomainId)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_U32 i, count = sizeof( gCsrCountryInfo ) / sizeof( gCsrCountryInfo[0] );
+
+    if(pCountry)
+    {
+        for(i = 0; i < count; i++)
+        {
+            if(palEqualMemory(pMac->hHdd, gCsrCountryInfo[i].countryCode, pCountry, 2))
+            {
+                if( pDomainId )
+                {
+                    *pDomainId = gCsrCountryInfo[i].domainId;
+                }
+                break;
+            }
+        }
+        if(i == count)
+        {
+            smsLog(pMac, LOGW, FL("  doesn't match country %c%c\n"), pCountry[0], pCountry[1]);
+            status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+    }
+
+    return (status);
+}
+#endif
+
+eHalStatus csrGetRegulatoryDomainForCountry(tpAniSirGlobal pMac, tANI_U8 *pCountry, v_REGDOMAIN_t *pDomainId)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    VOS_STATUS vosStatus;
+    v_COUNTRYCODE_t countryCode;
+    v_REGDOMAIN_t domainId;
+
+    if(pCountry)
+    {
+        countryCode[0] = pCountry[0];
+        countryCode[1] = pCountry[1];
+        vosStatus = vos_nv_getRegDomainFromCountryCode( &domainId, countryCode );
+        if( VOS_IS_STATUS_SUCCESS(vosStatus) )
+        {
+            if( pDomainId )
+            {
+                *pDomainId = domainId;
+            }
+            status = eHAL_STATUS_SUCCESS;
+        }
+        else
+        {
+            smsLog(pMac, LOGW, FL("  doesn't match country %c%c\n"), pCountry[0], pCountry[1]);
+            status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+    }
+
+    return (status);
+}
+
+//To check whether a country code matches the one in the IE
+//Only check the first two characters, ignoring in/outdoor
+//pCountry -- caller allocated buffer contain the country code that is checking against
+//the one in pIes. It can be NULL.
+//caller must provide pIes, it cannot be NULL
+//This function always return TRUE if 11d support is not turned on.
+tANI_BOOLEAN csrMatchCountryCode( tpAniSirGlobal pMac, tANI_U8 *pCountry, tDot11fBeaconIEs *pIes )
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_TRUE;
+    v_REGDOMAIN_t domainId = NUM_REG_DOMAINS;   //This is init to invalid value
+    eHalStatus status;
+
+    do
+    {
+        if( !csrIs11dSupported( pMac) )
+        {
+            break;
+        }
+        if( !pIes )
+        {
+            smsLog(pMac, LOGE, FL("  No IEs\n"));
+            break;
+        }
+        //Make sure this country is recognizable
+        if( pIes->Country.present )
+        {
+            status = csrGetRegulatoryDomainForCountry( pMac, pIes->Country.country,(v_REGDOMAIN_t *) &domainId );
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                fRet = eANI_BOOLEAN_FALSE;
+                break;
+            }
+        }
+        //check whether it is needed to enforce to the default regulatory domain first
+        if( pMac->roam.configParam.fEnforceDefaultDomain )
+        {
+            if( domainId != pMac->scan.domainIdCurrent )
+            {
+                fRet = eANI_BOOLEAN_FALSE;
+                break;
+            }
+        }
+        if( pMac->roam.configParam.fEnforceCountryCodeMatch )
+        {
+            if( domainId >= NUM_REG_DOMAINS )
+            {
+                fRet = eANI_BOOLEAN_FALSE;
+                break;
+            }
+        }
+        if( pCountry )
+        {
+            tANI_U32 i;
+
+            if( !pIes->Country.present )
+            {
+                fRet = eANI_BOOLEAN_FALSE;
+                break;
+            }
+            // Convert the CountryCode characters to upper
+            for ( i = 0; i < WNI_CFG_COUNTRY_CODE_LEN - 1; i++ )
+            {
+                pCountry[i] = csrToUpper( pCountry[i] );
+            }
+            if( !palEqualMemory(pMac->hHdd, pIes->Country.country, pCountry, WNI_CFG_COUNTRY_CODE_LEN - 1) )
+            {
+                fRet = eANI_BOOLEAN_FALSE;
+                break;
+            }
+        }
+    } while(0);
+
+    return (fRet);
+}
+
+#if 0
+eHalStatus csrSetCountryDomainMapping(tpAniSirGlobal pMac, tCsrCountryDomainMapping *pCountryDomainMapping)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tANI_U32 i, j;
+    tANI_BOOLEAN fDomainChanged = eANI_BOOLEAN_FALSE;
+    tANI_U8 countryCode[WNI_CFG_COUNTRY_CODE_LEN];
+
+    i = WNI_CFG_COUNTRY_CODE_LEN;
+    //Get the currently used country code
+    status = ccmCfgGetStr(pMac, WNI_CFG_COUNTRY_CODE, countryCode, &i);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        if(pCountryDomainMapping && pCountryDomainMapping->numEntry)
+        {
+            for(i = 0; i < pCountryDomainMapping->numEntry; i++)
+            {
+                for(j = 0; j < eCSR_NUM_COUNTRY_INDEX; j++)
+                {
+                    if(palEqualMemory(pMac->hHdd, gCsrCountryInfo[j].countryCode, 
+                                    pCountryDomainMapping->pCountryInfo[i].countryCode, 2))
+                    {
+                        if(gCsrCountryInfo[j].domainId != pCountryDomainMapping->pCountryInfo[i].domainId)
+                        {
+                            gCsrCountryInfo[j].domainId = pCountryDomainMapping->pCountryInfo[i].domainId;
+                            //Check whether it matches the currently used country code
+                            //If matching, need to update base on the new domain setting.
+                            if(palEqualMemory(pMac->hHdd, countryCode, 
+                                        pCountryDomainMapping->pCountryInfo[i].countryCode, 2))
+                            {
+                                fDomainChanged = eANI_BOOLEAN_TRUE;
+                            }
+                        }
+                        break;
+                    }
+                }
+            }
+            status = eHAL_STATUS_SUCCESS;
+            if(fDomainChanged)
+            {
+                tCsrChannel *pChannelList;
+
+                if(pMac->scan.f11dInfoApplied)
+                {
+                    //11d info already applied. Let's reapply with the new domain setting
+                    if(pMac->scan.channels11d.numChannels)
+                    {
+                        pChannelList = &pMac->scan.channels11d;
+                    }
+                    else
+                    {
+                        pChannelList = &pMac->scan.base20MHzChannels;
+                    }
+                }
+                else
+                {
+                    //no 11d so we use the base channelist from EEPROM
+                    pChannelList = &pMac->scan.base20MHzChannels;
+                }
+                //set the new domain's scan requirement to CFG
+                csrSetCfgScanControlList(pMac, countryCode, pChannelList);
+            }
+        }
+    }
+
+    return (status);
+}
+
+eHalStatus csrSetDomainScanSetting(tpAniSirGlobal pMac, tCsrDomainFreqInfo *pDomainFreqInfo)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+    tANI_U32 i, j;
+    tANI_U16 freq;
+
+    if(pDomainFreqInfo && pDomainFreqInfo->numEntry && (pDomainFreqInfo->domainId < NUM_REG_DOMAINS))
+    {
+        tCsrDomainChnInfo *pDomainChnInfo = &gCsrDomainChnInfo[pDomainFreqInfo->domainId];
+
+        for(j = 0; j < pDomainChnInfo->numChannels; j++)
+        {
+            if(HAL_STATUS_SUCCESS(halPhyChIdToFreqConversion(pDomainChnInfo->chnInfo[j].chnId, &freq)))
+            {
+                for(i = 0; i < pDomainFreqInfo->numEntry; i++)
+                {
+                    if((pDomainFreqInfo->pCsrScanFreqInfo[i].nStartFreq <= freq) &&
+                        (freq <= pDomainFreqInfo->pCsrScanFreqInfo[i].nEndFreq))
+                    {
+                        pDomainChnInfo->chnInfo[j].scanType = pDomainFreqInfo->pCsrScanFreqInfo[i].scanType;
+                        break;
+                    }
+                }
+            }
+            else
+            {
+                smsLog(pMac, LOGW, "   Failed to get frequency of channel %d", pDomainChnInfo->chnInfo[j].chnId);
+            }
+        }
+        status = eHAL_STATUS_SUCCESS;
+    }
+
+    return (status);
+}
+#endif
+
+eHalStatus csrGetModifyProfileFields(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                     tCsrRoamModifyProfileFields *pModifyProfileFields)
+{
+
+   if(!pModifyProfileFields)
+   {
+      return eHAL_STATUS_FAILURE;
+   }
+
+   palCopyMemory( pMac->hHdd, pModifyProfileFields, 
+                  &pMac->roam.roamSession[sessionId].connectedProfile.modifyProfileFields, 
+                  sizeof(tCsrRoamModifyProfileFields) );
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+eHalStatus csrSetModifyProfileFields(tpAniSirGlobal pMac, tANI_U32 sessionId,
+                                     tCsrRoamModifyProfileFields *pModifyProfileFields)
+{
+   tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+
+   palCopyMemory( pMac->hHdd, &pSession->connectedProfile.modifyProfileFields,
+                  pModifyProfileFields,
+                  sizeof(tCsrRoamModifyProfileFields) );
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+
+#if 0
+/* ---------------------------------------------------------------------------
+    \fn csrGetSupportedCountryCode
+    \brief this function is to get a list of the country code current being supported
+    \param pBuf - Caller allocated buffer with at least 3 bytes, upon success return, 
+    this has the country code list. 3 bytes for each country code. This may be NULL if
+    caller wants to know the needed bytes.
+    \param pbLen - Caller allocated, as input, it indicates the length of pBuf. Upon success return,
+    this contains the length of the data in pBuf
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrGetSupportedCountryCode(tpAniSirGlobal pMac, tANI_U8 *pBuf, tANI_U32 *pbLen)
+{
+    tANI_U32 numOfCountry = sizeof( gCsrCountryInfo ) / sizeof( gCsrCountryInfo[0] );
+    tANI_U32 numBytes = 0;
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+
+    if( pbLen )
+    {
+        numBytes = *pbLen;
+        //Consider it ok, at least we can return the number of bytes needed;
+        *pbLen = numOfCountry * WNI_CFG_COUNTRY_CODE_LEN;
+        status = eHAL_STATUS_SUCCESS;
+        if( pBuf && ( numBytes >= *pbLen ) )
+        {
+            //The ugly part starts.
+            //We may need to alter the data structure and find a way to make this faster.
+            tANI_U32 i;
+
+            for( i = 0; i < numOfCountry; i++ )
+            {
+                palCopyMemory( pMac->hHdd, pBuf + ( i * WNI_CFG_COUNTRY_CODE_LEN ),
+                    gCsrCountryInfo[i].countryCode, WNI_CFG_COUNTRY_CODE_LEN );
+            }
+        }
+    }
+
+    return ( status );
+}
+#endif
+
+/* ---------------------------------------------------------------------------
+    \fn csrGetSupportedCountryCode
+    \brief this function is to get a list of the country code current being supported
+    \param pBuf - Caller allocated buffer with at least 3 bytes, upon success return, 
+    this has the country code list. 3 bytes for each country code. This may be NULL if
+    caller wants to know the needed bytes.
+    \param pbLen - Caller allocated, as input, it indicates the length of pBuf. Upon success return,
+    this contains the length of the data in pBuf
+    \return eHalStatus     
+  -------------------------------------------------------------------------------*/
+eHalStatus csrGetSupportedCountryCode(tpAniSirGlobal pMac, tANI_U8 *pBuf, tANI_U32 *pbLen)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    VOS_STATUS vosStatus;
+    v_SIZE_t size = (v_SIZE_t)*pbLen;
+
+    vosStatus = vos_nv_getSupportedCountryCode( pBuf, &size, 1 );
+    //eiter way, return the value back
+    *pbLen = (tANI_U32)size;
+
+    //If pBuf is NULL, caller just want to get the size, consider it success
+    if(pBuf)
+    {
+        if( VOS_IS_STATUS_SUCCESS( vosStatus ) )
+        {
+            tANI_U32 i, n = *pbLen / 3;
+
+            for( i = 0; i < n; i++ )
+            {
+                pBuf[i*3 + 2] = ' ';
+            }
+        }
+        else
+        {
+            status = eHAL_STATUS_FAILURE;
+        }
+    }
+
+    return (status);
+}
+
+
+
+//Upper layer to get the list of the base channels to scan for passively 11d info from csr
+eHalStatus csrScanGetBaseChannels( tpAniSirGlobal pMac, tCsrChannelInfo * pChannelInfo )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+
+    do
+    {
+    
+       if(!pMac->scan.baseChannels.numChannels || !pChannelInfo)
+       {
+          break;
+       }
+       status = palAllocateMemory( pMac->hHdd, (void **)&pChannelInfo->ChannelList, 
+                                   pMac->scan.baseChannels.numChannels );
+       if( !HAL_STATUS_SUCCESS( status ) )
+       {
+          smsLog( pMac, LOGE, FL("csrScanGetBaseChannels: fail to allocate memory\n") );
+          break;
+       }
+       status = palCopyMemory( pMac->hHdd, pChannelInfo->ChannelList, pMac->scan.baseChannels.channelList, 
+                               pMac->scan.baseChannels.numChannels );
+       if( !HAL_STATUS_SUCCESS( status ) )
+       {
+          break;
+       }
+       pChannelInfo->numOfChannels = pMac->scan.baseChannels.numChannels;
+
+    }while(0);
+
+    return ( status );
+}
+
+
+tANI_BOOLEAN csrIsSetKeyAllowed(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    tANI_BOOLEAN fRet = eANI_BOOLEAN_TRUE;
+#ifdef WLAN_SOFTAP_FEATURE
+    tCsrRoamSession *pSession;
+
+    pSession =CSR_GET_SESSION(pMac, sessionId);
+
+    /*This condition is not working for infra state. When infra is in not-connected state
+    * the pSession->pCurRoamProfile is NULL. And this function returns TRUE, that is incorrect.
+    * Since SAP requires to set key without any BSS started, it needs this condition to be met.
+    * In other words, this function is useless.
+    * The current work-around is to process setcontext_rsp and removekey_rsp no matter what the 
+    * state is.
+    */
+    smsLog( pMac, LOGE, FL(" is not what it intends to. Must be revisit or removed\n") );
+    if( (NULL == pSession) || 
+        ( csrIsConnStateDisconnected( pMac, sessionId ) && 
+        (pSession->pCurRoamProfile != NULL) &&
+        (!(CSR_IS_INFRA_AP(pSession->pCurRoamProfile))) )
+        )
+    {
+        fRet = eANI_BOOLEAN_FALSE;
+    }
+#else
+    fRet = !( csrIsConnStateDisconnected( pMac, sessionId ) );
+#endif
+
+    return ( fRet );
+}
+
+//no need to acquire lock for this basic function
+tANI_U16 sme_ChnToFreq(tANI_U8 chanNum)
+{
+   int i;
+
+   for (i = 0; i < NUM_RF_CHANNELS; i++) 
+   {
+      if (rfChannels[i].channelNum == chanNum) 
+      {
+         return rfChannels[i].targetFreq;
+      }
+   }
+
+   return (0);
+}
+
+/* Disconnect all active sessions by sending disassoc. This is mainly used to disconnect the remaining session when we 
+ * transition from concurrent sessions to a single session. The use case is Infra STA and wifi direct multiple sessions are up and 
+ * P2P session is removed. The Infra STA session remains and should resume BMPS if BMPS is enabled by default. However, there
+ * are some issues seen with BMPS resume during this transition and this is a workaround which will allow the Infra STA session to
+ * disconnect and auto connect back and enter BMPS this giving the same effect as resuming BMPS
+ */
+void csrDisconnectAllActiveSessions(tpAniSirGlobal pMac)
+{
+    tANI_U8 i;
+
+    /* Disconnect all the active sessions */
+    for (i=0; i<CSR_ROAM_SESSION_MAX; i++)
+    {
+        if( CSR_IS_SESSION_VALID( pMac, i ) && !csrIsConnStateDisconnected( pMac, i ) )
+        {
+            csrRoamDisconnectInternal(pMac, i, eCSR_DISCONNECT_REASON_UNSPECIFIED);
+        }
+    }
+}
diff --git a/CORE/SME/src/meas/measApi.c b/CORE/SME/src/meas/measApi.c
new file mode 100644
index 0000000..1e9b029
--- /dev/null
+++ b/CORE/SME/src/meas/measApi.c
@@ -0,0 +1,21 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
diff --git a/CORE/SME/src/p2p/p2p_Api.c b/CORE/SME/src/p2p/p2p_Api.c
new file mode 100644
index 0000000..057f013
--- /dev/null
+++ b/CORE/SME/src/p2p/p2p_Api.c
@@ -0,0 +1,2243 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/*
+ * Copyright (c) 2008 QUALCOMM Incorporated. All Rights Reserved.
+ * Qualcomm Confidential and Proprietary 
+ */
+
+#if defined WLAN_FEATURE_P2P
+
+#include "sme_Api.h"
+#include "smsDebug.h"
+#include "csrInsideApi.h"
+#include "smeInside.h"
+#include "p2p_Api.h"
+#include "limApi.h"
+#include "cfgApi.h"
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+#include "p2p_ie.h"
+#include "p2pFsm.h"
+
+extern tp2pie gP2PIe;
+
+static eHalStatus p2pSendActionFrame(tpAniSirGlobal pMac, tANI_U8 SessionID, eP2PFrameType actionFrameType);
+static eHalStatus p2pListenStateDiscoverableCallback(tHalHandle halHandle, void *pContext, eHalStatus retStatus);
+static eHalStatus p2pRemainOnChannelReadyCallback(tHalHandle halHandle, void *pContext, eHalStatus scan_status);
+static tANI_BOOLEAN p2pIsGOportEnabled(tpAniSirGlobal pMac);
+#endif
+
+eHalStatus p2pProcessNoAReq(tpAniSirGlobal pMac, tSmeCmd *pNoACmd);
+/*------------------------------------------------------------------
+ *
+ * handle SME remain on channel request.
+ *
+ *------------------------------------------------------------------*/
+
+eHalStatus p2pProcessRemainOnChannelCmd(tpAniSirGlobal pMac, tSmeCmd *p2pRemainonChn)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tSirRemainOnChnReq* pMsg;
+    tANI_U16 len;
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, p2pRemainonChn->sessionId );
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+    tANI_U8 P2PsessionId = getP2PSessionIdFromSMESessionId(pMac, p2pRemainonChn->sessionId);
+    tp2pContext *p2pContext = &pMac->p2pContext[P2PsessionId];
+    tANI_U32 ieLen = 0;
+#endif
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+    if( !pSession->sessionActive || (CSR_SESSION_ID_INVALID == P2PsessionId)) 
+    {
+       smsLog(pMac, LOGE, FL("  session %d (P2P session %d) is invalid or listen is disabled "), 
+            p2pRemainonChn->sessionId, P2PsessionId);
+       return eHAL_STATUS_FAILURE;
+    }
+#else
+    if(!pSession->sessionActive) 
+    {
+       smsLog(pMac, LOGE, FL("  session %d is invalid or listen is disabled "), 
+            p2pRemainonChn->sessionId);
+       return eHAL_STATUS_FAILURE;
+    }
+#endif
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+    P2P_GetIE(p2pContext, 
+              p2pContext->sessionId, eP2P_PROBE_RSP, 
+              &p2pContext->probeRspIe, &ieLen);
+    p2pContext->probeRspIeLength = ieLen;
+    len = sizeof(tSirRemainOnChnReq) + ieLen;
+#else
+    len = sizeof(tSirRemainOnChnReq) + pMac->p2pContext.probeRspIeLength;
+#endif
+
+    status = palAllocateMemory(pMac->hHdd, (void**)&pMsg, len );
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s call\n", __FUNCTION__);
+        palZeroMemory(pMac->hHdd, pMsg, sizeof(tSirRemainOnChnReq));
+        pMsg->messageType = eWNI_SME_REMAIN_ON_CHANNEL_REQ;
+        pMsg->length = len;
+        palCopyMemory( pMac, pMsg->selfMacAddr, pSession->selfMacAddr, sizeof(tSirMacAddr) ); 
+        pMsg->chnNum = p2pRemainonChn->u.remainChlCmd.chn;
+        pMsg->phyMode = p2pRemainonChn->u.remainChlCmd.phyMode;
+        pMsg->duration = p2pRemainonChn->u.remainChlCmd.duration;
+        pMsg->sessionId = p2pRemainonChn->sessionId;
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+        pMsg->sessionId = pSession->sessionId;
+        if( p2pContext->probeRspIeLength )
+        {
+            palCopyMemory(pMac->hHdd, (void *)pMsg->probeRspIe,
+                         (void *)p2pContext->probeRspIe, 
+                         p2pContext->probeRspIeLength);
+        }
+#else
+        if( pMac->p2pContext.probeRspIeLength )
+           palCopyMemory(pMac->hHdd, (void *)pMsg->probeRspIe, (void *)pMac->p2pContext.probeRspIe, pMac->p2pContext.probeRspIeLength);
+#endif
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+    }
+    
+    return status;
+}
+
+
+/*------------------------------------------------------------------
+ *
+ * handle LIM remain on channel rsp: Success/failure.
+ *
+ *------------------------------------------------------------------*/
+
+eHalStatus sme_remainOnChnRsp( tpAniSirGlobal pMac, tANI_U8 *pMsg)
+{
+    eHalStatus                         status = eHAL_STATUS_SUCCESS;
+    tListElem                          *pEntry = NULL;
+    tSmeCmd                            *pCommand = NULL;
+
+    pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+    if( pEntry )
+    {
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+        if( eSmeCommandRemainOnChannel == pCommand->command )
+        {
+            remainOnChanCallback callback = pCommand->u.remainChlCmd.callback;
+            /* process the msg */
+            if( callback )
+                callback(pMac, pCommand->u.remainChlCmd.callbackCtx, 0);
+             
+            if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+            {
+                //Now put this command back on the avilable command list
+                smeReleaseCommand(pMac, pCommand);
+            }
+            smeProcessPendingQueue( pMac );
+        }
+    }
+    return status;
+}
+
+
+/*------------------------------------------------------------------
+ *
+ * Handle the Mgmt frm ind from LIM and forward to HDD.
+ *
+ *------------------------------------------------------------------*/
+
+eHalStatus sme_mgmtFrmInd( tHalHandle hHal, tpSirSmeMgmtFrameInd pSmeMgmtFrm)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+    tCsrRoamInfo pRoamInfo = {0};
+#ifndef WLAN_FEATURE_P2P_INTERNAL
+    tANI_U32 SessionId = pSmeMgmtFrm->sessionId;
+#endif
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+    tANI_U8 i;
+
+    //For now, only action frames are needed.
+    if(SIR_MAC_MGMT_ACTION == pSmeMgmtFrm->frameType)
+    {
+       pRoamInfo.nFrameLength = pSmeMgmtFrm->mesgLen - sizeof(tSirSmeMgmtFrameInd);
+       pRoamInfo.pbFrames = pSmeMgmtFrm->frameBuf;
+       pRoamInfo.frameType = pSmeMgmtFrm->frameType;
+       pRoamInfo.rxChan   = pSmeMgmtFrm->rxChan;
+
+       //Somehow we don't get the right sessionId.
+       for(i = 0; i < CSR_ROAM_SESSION_MAX; i++)
+       {
+          if( CSR_IS_SESSION_VALID( pMac, i ) )
+          {
+              status = eHAL_STATUS_SUCCESS;
+              /* forward the mgmt frame to all active sessions*/
+              csrRoamCallCallback(pMac, i, &pRoamInfo, 0, eCSR_ROAM_INDICATE_MGMT_FRAME, 0);
+          }
+       }
+    }
+#else
+    pRoamInfo.nFrameLength = pSmeMgmtFrm->mesgLen - sizeof(tSirSmeMgmtFrameInd);
+    pRoamInfo.pbFrames = pSmeMgmtFrm->frameBuf;
+    pRoamInfo.frameType = pSmeMgmtFrm->frameType;
+    pRoamInfo.rxChan   = pSmeMgmtFrm->rxChan;
+
+    /* forward the mgmt frame to HDD */
+    csrRoamCallCallback(pMac, SessionId, &pRoamInfo, 0, eCSR_ROAM_INDICATE_MGMT_FRAME, 0);
+#endif
+
+    return status;
+}
+
+
+/*------------------------------------------------------------------
+ *
+ * Handle the remain on channel ready indication from PE
+ *
+ *------------------------------------------------------------------*/
+
+eHalStatus sme_remainOnChnReady( tHalHandle hHal, tANI_U8* pMsg)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus  status = eHAL_STATUS_SUCCESS;
+    tListElem *pEntry = NULL;
+    tSmeCmd *pCommand = NULL;
+    tCsrRoamInfo RoamInfo; 
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+    tSirSmeRsp *pRsp = (tSirSmeRsp *)pMsg;
+    //pRsp->sessionId is SME's session index
+    tANI_U8  P2PSessionID = getP2PSessionIdFromSMESessionId(pMac, pRsp->sessionId);
+
+    if(CSR_SESSION_ID_INVALID == P2PSessionID)
+    {
+       return eHAL_STATUS_FAILURE;
+    }
+#endif
+
+    pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+    if( pEntry )
+    {
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+        if( eSmeCommandRemainOnChannel == pCommand->command )
+        {
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+            if (pMac->p2pContext[P2PSessionID].PeerFound)
+            {
+                p2pRemainOnChannelReadyCallback(pMac, &pMac->p2pContext[P2PSessionID], eHAL_STATUS_SUCCESS);
+            }
+#else
+            /* forward the indication to HDD */
+            RoamInfo.pRemainCtx = pCommand->u.remainChlCmd.callbackCtx;
+            csrRoamCallCallback(pMac, ((tSirSmeRsp*)pMsg)->sessionId, &RoamInfo, 
+                                0, eCSR_ROAM_REMAIN_CHAN_READY, 0);
+#endif
+        }
+    }
+  
+    return status;
+}
+
+
+eHalStatus sme_sendActionCnf( tHalHandle hHal, tANI_U8* pMsg)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   eHalStatus  status = eHAL_STATUS_SUCCESS;
+   tCsrRoamInfo RoamInfo;
+   tSirSmeRsp* pSmeRsp = (tSirSmeRsp*)pMsg;
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+   tSirResultCodes rspStatus = pSmeRsp->statusCode;
+   tANI_U8 HDDsessionId = getP2PSessionIdFromSMESessionId(pMac, pSmeRsp->sessionId);
+   tANI_U8 *pBuf = NULL;
+   tp2pContext *pP2pContext;
+
+   if(CSR_SESSION_ID_INVALID == HDDsessionId)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+         " %s fail to get HDD sessionID (SMESessionID %d)", __FUNCTION__, pSmeRsp->sessionId);
+      return eHAL_STATUS_INVALID_PARAMETER;
+   }
+
+   pP2pContext = &pMac->p2pContext[HDDsessionId];
+
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s status %d Action Frame %d actionFrameTimeout %d\n", 
+         __FUNCTION__, pSmeRsp->statusCode, pP2pContext->actionFrameType
+         , pP2pContext->actionFrameTimeout);
+   vos_mem_zero(&RoamInfo, sizeof(tCsrRoamInfo));
+
+   if (pSmeRsp->statusCode != eSIR_SME_SUCCESS && !pP2pContext->actionFrameTimeout
+         && pP2pContext->pSentActionFrame)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Action frame:Ack not received. Retransmitting\n", __FUNCTION__);
+
+      if(NULL == pP2pContext->pNextActionFrm)
+      {
+         status = palTimerStart(pMac->hHdd, pP2pContext->retryActionFrameTimer, 
+                        ACTION_FRAME_RETRY_TIMEOUT * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
+         if (!HAL_STATUS_SUCCESS(status))
+         {
+            smsLog(pMac, LOGE, " %s fail to start retryActionFrameTimerHandler\n", 
+               __FUNCTION__, pP2pContext->NextActionFrameType);
+         }
+         return status;
+      }
+      //In case if there is new frame to send, finish the current frame
+      else
+      {
+         smsLog(pMac, LOGE, " %s send next action frame type %d Last frame status (%d)",
+            __FUNCTION__, rspStatus);
+         //Force it to be success
+         rspStatus = eSIR_SME_SUCCESS;
+      }
+   }
+
+   if (pP2pContext->actionFrameTimer)
+   {
+      status = palTimerStop(pMac, pP2pContext->actionFrameTimer);
+   }
+
+   if (pP2pContext->retryActionFrameTimer)
+   {
+      status = palTimerStop(pMac, pP2pContext->retryActionFrameTimer);
+   }
+
+   if(pP2pContext->pSentActionFrame)
+   {
+      csrRoamCallCallback((tpAniSirGlobal)pP2pContext->hHal, 
+                     pP2pContext->SMEsessionId, &RoamInfo, 0, 
+                     eCSR_ROAM_SEND_ACTION_CNF, 
+                     ((rspStatus == eSIR_SME_SUCCESS) ? 
+                     eCSR_ROAM_RESULT_NONE: eCSR_ROAM_RESULT_SEND_ACTION_FAIL));
+   }
+
+   if(VOS_IS_STATUS_SUCCESS(vos_spin_lock_acquire(&pP2pContext->lState)))
+   {
+      if(pP2pContext->pSentActionFrame)
+      {
+         pBuf = pP2pContext->pSentActionFrame;
+         pP2pContext->pSentActionFrame = NULL;
+      }
+      vos_spin_lock_release(&pP2pContext->lState);
+
+      if(NULL != pBuf)
+      {
+         vos_mem_free(pBuf);
+         pBuf = NULL;
+      }
+      else
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, "%s pSentActionFrame is null \n", __FUNCTION__);
+      }
+      if(pP2pContext->pNextActionFrm)
+      {
+         //need to send the next action frame
+         pP2pContext->pSentActionFrame = pP2pContext->pNextActionFrm;
+         pP2pContext->ActionFrameLen = pP2pContext->nNextFrmLen;
+         pP2pContext->actionFrameType = pP2pContext->NextActionFrameType;
+         pP2pContext->pNextActionFrm = NULL;
+         pP2pContext->ActionFrameSendTimeout = pP2pContext->nNextFrameTimeOut;
+      }
+   }
+   else
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s cannot get lock1", __FUNCTION__);
+   }
+
+   if(NULL != pP2pContext->pSentActionFrame)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, " sending next frame %d type\n", 
+                  pP2pContext->NextActionFrameType);
+      status = palTimerStart(pMac->hHdd, pP2pContext->actionFrameTimer, 
+                        pP2pContext->ActionFrameSendTimeout * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
+      if (!HAL_STATUS_SUCCESS(status))
+      {
+         smsLog(pMac, LOGE, FL(" %s fail to start timer status %d"), __FUNCTION__, status);
+         //Without the timer we cannot continue
+         csrRoamCallCallback((tpAniSirGlobal)pP2pContext->hHal, 
+                     pP2pContext->SMEsessionId, &RoamInfo, 0, 
+                     eCSR_ROAM_SEND_ACTION_CNF, 
+                     eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
+         vos_spin_lock_acquire(&pP2pContext->lState);
+         pBuf = pP2pContext->pSentActionFrame;
+         pP2pContext->pSentActionFrame = NULL;
+         vos_spin_lock_release(&pP2pContext->lState);
+         vos_mem_free(pBuf);
+         pBuf = NULL;
+         p2pFsm(pP2pContext, eP2P_TRIGGER_DISCONNECTED);
+         return status;
+      }
+      status = p2pSendActionFrame(pMac, pP2pContext->sessionId, pP2pContext->actionFrameType);
+      if(!HAL_STATUS_SUCCESS(status))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, " sending next frame %d type\n", 
+                  pP2pContext->NextActionFrameType);
+         status = palTimerStart(pMac->hHdd, pP2pContext->retryActionFrameTimer, 
+                     ACTION_FRAME_RETRY_TIMEOUT * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
+         if (!HAL_STATUS_SUCCESS(status))
+         {
+            smsLog(pMac, LOGE, " %s fail to start retryActionFrameTimerHandler\n", __FUNCTION__);
+         }
+      }
+   }
+   else
+   {
+      p2pFsm(pP2pContext, eP2P_TRIGGER_DISCONNECTED);
+   }
+    
+#else  
+    /* forward the indication to HDD */
+    //RoamInfo can be passed as NULL....todo
+    csrRoamCallCallback(pMac, pSmeRsp->sessionId, &RoamInfo, 0, 
+                        eCSR_ROAM_SEND_ACTION_CNF, 
+                       (pSmeRsp->statusCode == eSIR_SME_SUCCESS) ? 0:
+                        eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
+#endif    
+    return status;
+}
+
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+void p2pResetContext(tp2pContext *pP2pContext)
+{
+   if(NULL != pP2pContext)
+   {
+      tpAniSirGlobal pMac = PMAC_STRUCT(pP2pContext->hHal);
+      int i;
+
+      //When it is resetting a GO or client session, we
+      //need to reset the group capability back to the original one
+      if( (OPERATION_MODE_P2P_GROUP_OWNER == pP2pContext->operatingmode) ||
+         (OPERATION_MODE_P2P_CLIENT == pP2pContext->operatingmode) )
+      {
+         for( i = 0; i < MAX_NO_OF_P2P_SESSIONS; i++ )
+         {
+            if(OPERATION_MODE_P2P_DEVICE == pMac->p2pContext[i].operatingmode)
+            {
+               gP2PIe[i].p2pCapabilityAttrib.groupCapability = pMac->p2pContext[i].OriginalGroupCapability;
+            }
+         }
+      }
+
+      pP2pContext->state = eP2P_STATE_DISCONNECTED;
+      pP2pContext->currentSearchIndex = 0;
+      pP2pContext->listenIndex = 1;
+
+      pP2pContext->actionFrameType = eP2P_INVALID_FRM;
+
+      pP2pContext->dialogToken = 0;
+      pP2pContext->PeerFound = FALSE;
+      pP2pContext->GroupFormationPending = FALSE;
+      pP2pContext->directedDiscovery = FALSE;
+      pP2pContext->listenDiscoverableState = eStateDisabled;
+
+
+      if(pP2pContext->pSentActionFrame)
+      {
+         vos_mem_free(pP2pContext->pSentActionFrame);
+         pP2pContext->pSentActionFrame = NULL;
+      }
+      if(pP2pContext->pNextActionFrm)
+      {
+         vos_mem_free(pP2pContext->pSentActionFrame);
+         pP2pContext->pSentActionFrame = NULL;
+      }      
+      if( pP2pContext->probeRspIe )
+      {
+         vos_mem_free( pP2pContext->probeRspIe );
+         pP2pContext->probeRspIe = NULL;
+         pP2pContext->probeRspIeLength = 0;
+      }
+
+      if( pP2pContext->DiscoverReqIeField )
+      {
+         vos_mem_free(pP2pContext->DiscoverReqIeField );
+         pP2pContext->DiscoverReqIeField = NULL;
+         pP2pContext->DiscoverReqIeLength = 0;
+      }
+
+      if( pP2pContext->GoNegoCnfIeField )
+      {
+         vos_mem_free( pP2pContext->GoNegoCnfIeField);
+         pP2pContext->GoNegoCnfIeField = NULL;
+         pP2pContext->GoNegoCnfIeLength = 0;
+      }
+
+      if( pP2pContext->GoNegoReqIeField )
+      {
+         vos_mem_free( pP2pContext->GoNegoReqIeField );
+         pP2pContext->GoNegoReqIeField = NULL;
+         pP2pContext->GoNegoReqIeLength = 0;
+      }
+
+      if( pP2pContext->GoNegoResIeField )
+      {
+         vos_mem_free( pP2pContext->GoNegoResIeField );
+         pP2pContext->GoNegoResIeField = NULL;
+         pP2pContext->GoNegoResIeLength = 0;
+      }
+
+      if( pP2pContext->ProvDiscReqIeField )
+      {
+         vos_mem_free( pP2pContext->ProvDiscReqIeField );
+         pP2pContext->ProvDiscReqIeField = NULL;
+         pP2pContext->ProvDiscReqIeLength = 0;
+      }
+
+      if( pP2pContext->ProvDiscResIeField )
+      {
+         vos_mem_free( pP2pContext->ProvDiscResIeField );
+         pP2pContext->ProvDiscResIeLength = 0;
+         pP2pContext->ProvDiscResIeField = NULL;
+      }
+
+      if (pP2pContext->actionFrameTimer)
+      {
+         palTimerStop(pMac->hHdd, pP2pContext->actionFrameTimer);
+      }
+
+      if (pP2pContext->discoverTimer)
+      {
+         palTimerStop(pMac->hHdd, pP2pContext->discoverTimer);
+      }
+
+      if (pP2pContext->listenTimerHandler)
+      {
+         palTimerStop(pMac->hHdd, pP2pContext->listenTimerHandler);
+      }
+
+      if (pP2pContext->WPSRegistrarCheckTimerHandler)
+      {
+         palTimerStop(pMac->hHdd, pP2pContext->WPSRegistrarCheckTimerHandler);
+      }
+
+      if (pP2pContext->directedDiscoveryFilter)
+      {
+         pP2pContext->uNumDeviceFilterAllocated = 0;
+         vos_mem_free(pP2pContext->directedDiscoveryFilter);
+         pP2pContext->directedDiscoveryFilter = NULL;
+      }
+
+      vos_mem_zero(pP2pContext->peerMacAddress, P2P_MAC_ADDRESS_LEN);
+   }
+}
+#endif    
+
+
+eHalStatus sme_p2pOpen( tHalHandle hHal )
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+   int i;
+   tp2pContext *pP2pContext;
+
+   for ( i=0; i < MAX_NO_OF_P2P_SESSIONS; i++ ) 
+   {
+      pP2pContext = &pMac->p2pContext[i];
+      pP2pContext->hHal = hHal;
+
+      pP2pContext->socialChannel[0] = 1;
+      pP2pContext->socialChannel[1] = 6;
+      pP2pContext->socialChannel[2] = 11;
+
+      vos_spin_lock_init(&pP2pContext->lState);
+
+      p2pResetContext(pP2pContext);
+
+      status = palTimerAlloc(pMac->hHdd, &pP2pContext->actionFrameTimer, 
+                                    p2pActionFrameTimerHandler, pP2pContext);
+      if (!HAL_STATUS_SUCCESS(status))
+      {
+         smsLog(pMac, LOGE, " %s fail to alloc actionFrame timer for session %d\n", __FUNCTION__, i);
+         break;
+      }
+      status = palTimerAlloc(pMac->hHdd, &pP2pContext->listenTimerHandler, 
+                              p2pListenDiscoverTimerHandler, pP2pContext);
+      if (!HAL_STATUS_SUCCESS(status))
+      {
+         smsLog(pMac, LOGE, " %s fail to alloc listen timer for session %d\n", __FUNCTION__, i);
+         break;
+      } 
+      status = palTimerAlloc(pMac->hHdd, &pP2pContext->discoverTimer, p2pDiscoverTimerHandler, pP2pContext);
+      if (!HAL_STATUS_SUCCESS(status))
+      {
+         smsLog(pMac, LOGE, " %s fail to alloc discover timer for session %d\n", __FUNCTION__, i);
+         break;
+      }
+
+      status = palTimerAlloc(pMac->hHdd, &pP2pContext->retryActionFrameTimer, 
+                     p2pRetryActionFrameTimerHandler, pP2pContext);
+      if (!HAL_STATUS_SUCCESS(status))
+      {
+         smsLog(pMac, LOGE, " %s fail to alloc retryActionFrameTimerHandler timer for session %d\n", __FUNCTION__, i);
+         break;
+      }
+
+      p2pCreateDefaultIEs(hHal, i);
+   }
+#else
+   //If static structure is too big, Need to change this function to allocate memory dynamically
+   vos_mem_zero( &pMac->p2pContext, sizeof( tp2pContext ) );
+#endif
+
+   if(!HAL_STATUS_SUCCESS(status))
+   {
+      sme_p2pClose(hHal);
+    }
+
+   return status;
+}
+
+
+eHalStatus p2pStop( tHalHandle hHal )
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+   int i;
+
+   for ( i = 0; i < MAX_NO_OF_P2P_SESSIONS; i++ ) 
+   {
+      p2pCloseSession(pMac, i);
+   }
+#else  
+   if( pMac->p2pContext.probeRspIe )
+   {
+      vos_mem_free( pMac->p2pContext.probeRspIe );
+      pMac->p2pContext.probeRspIe = NULL;
+   }
+  
+   pMac->p2pContext.probeRspIeLength = 0;
+#endif
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+
+eHalStatus sme_p2pClose( tHalHandle hHal )
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+   tp2pContext *pContext;
+   int i;
+
+   p2pStop(hHal);
+
+   for ( i = 0; i < MAX_NO_OF_P2P_SESSIONS; i++ ) 
+   {
+      p2pCloseSession(pMac, i);
+      pContext = &pMac->p2pContext[i];
+      if (pContext->actionFrameTimer)
+      {
+         palTimerFree(hHal, pContext->actionFrameTimer);
+         pContext->actionFrameTimer = NULL;
+      }
+
+      if (pContext->discoverTimer)
+      {
+         palTimerFree(hHal, pContext->discoverTimer);
+         pContext->discoverTimer = NULL;
+      }
+
+      if (pContext->listenTimerHandler)
+      {
+         palTimerFree(hHal, pContext->listenTimerHandler);
+         pContext->listenTimerHandler = NULL;
+      }
+
+      if (pContext->WPSRegistrarCheckTimerHandler)
+      {
+         palTimerFree(hHal, pContext->WPSRegistrarCheckTimerHandler);
+         pContext->WPSRegistrarCheckTimerHandler = NULL;
+      }
+
+      vos_spin_lock_destroy(&pContext->lState);
+   }
+#else  
+    if( pMac->p2pContext.probeRspIe )
+    {
+        vos_mem_free( pMac->p2pContext.probeRspIe );
+        pMac->p2pContext.probeRspIe = NULL;
+    }
+  
+    pMac->p2pContext.probeRspIeLength = 0;
+#endif
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+
+tSirRFBand GetRFBand(tANI_U8 channel)
+{
+    if ((channel >= SIR_11A_CHANNEL_BEGIN) &&
+        (channel <= SIR_11A_CHANNEL_END))
+        return SIR_BAND_5_GHZ;
+
+    if ((channel >= SIR_11B_CHANNEL_BEGIN) &&
+        (channel <= SIR_11B_CHANNEL_END))
+        return SIR_BAND_2_4_GHZ;
+
+    return SIR_BAND_UNKNOWN;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn p2pRemainOnChannel
+    \brief  API to post the remain on channel command.
+    \param  hHal - The handle returned by macOpen.
+    \param  sessinId - HDD session ID.
+    \param  channel - Channel to remain on channel.
+    \param  duration - Duration for which we should remain on channel
+    \param  callback - callback function.
+    \param  pContext - argument to the callback function
+    \return eHalStatus
+
+  -------------------------------------------------------------------------------*/
+eHalStatus p2pRemainOnChannel(tHalHandle hHal, tANI_U8 sessionId,
+         tANI_U8 channel, tANI_U32 duration,
+        remainOnChanCallback callback, 
+        void *pContext
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+        , eP2PRemainOnChnReason reason
+#endif
+        )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tSmeCmd *pRemainChlCmd = NULL;
+    tANI_U32 phyMode;
+  
+    pRemainChlCmd = smeGetCommandBuffer(pMac);
+    if(pRemainChlCmd == NULL)
+        return eHAL_STATUS_FAILURE;
+  
+    if (SIR_BAND_5_GHZ == GetRFBand(channel))
+    {
+       phyMode = WNI_CFG_PHY_MODE_11A;
+    }
+    else
+    {
+       phyMode = WNI_CFG_PHY_MODE_11G;
+    }
+    
+    cfgSetInt(pMac, WNI_CFG_PHY_MODE, phyMode);
+
+    do
+    {
+        /* call set in context */
+        pRemainChlCmd->command = eSmeCommandRemainOnChannel;
+        pRemainChlCmd->sessionId = sessionId;
+        pRemainChlCmd->u.remainChlCmd.chn = channel;
+        pRemainChlCmd->u.remainChlCmd.duration = duration;
+        pRemainChlCmd->u.remainChlCmd.callback = callback;
+        pRemainChlCmd->u.remainChlCmd.callbackCtx = pContext;
+    
+        //Put it at the head of the Q if we just finish finding the peer and ready to send a frame
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+        smePushCommand(pMac, pRemainChlCmd, (eP2PRemainOnChnReasonSendFrame == reason));
+#else
+        csrQueueSmeCommand(pMac, pRemainChlCmd, eANI_BOOLEAN_FALSE);
+#endif
+    } while(0);
+  
+    smsLog(pMac, LOGW, "exiting function %s\n", __FUNCTION__);
+  
+    return(status);
+}
+
+eHalStatus p2pSendAction(tHalHandle hHal, tANI_U8 sessionId,
+         const tANI_U8 *pBuf, tANI_U32 len)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tSirMbMsgP2p *pMsg;
+    tANI_U16 msgLen;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED,
+       " %s sends action frame", __FUNCTION__);
+    msgLen = (tANI_U16)((sizeof( tSirMbMsg )) + len);
+    status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, (void *)pMsg, msgLen);
+        pMsg->type = pal_cpu_to_be16((tANI_U16)eWNI_SME_SEND_ACTION_FRAME_IND);
+        pMsg->msgLen = pal_cpu_to_be16(msgLen);
+        pMsg->sessionId = sessionId;
+        palCopyMemory( pMac->hHdd, pMsg->data, pBuf, len ); 
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+    }                             
+
+    return( status );
+}
+
+eHalStatus p2pCancelRemainOnChannel(tHalHandle hHal, tANI_U8 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tSirMbMsg *pMsg;
+    tANI_U16 msgLen;
+
+    //Need to check session ID to support concurrency
+
+    msgLen = (tANI_U16)(sizeof( tSirMbMsg ));
+    status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, (void *)pMsg, msgLen);
+        pMsg->type = pal_cpu_to_be16((tANI_U16)eWNI_SME_ABORT_REMAIN_ON_CHAN_IND);
+        pMsg->msgLen = pal_cpu_to_be16(msgLen);
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+    }                             
+
+    return( status );
+}
+
+eHalStatus p2pSetPs(tHalHandle hHal, tP2pPsConfig *pNoA)
+{
+    tpP2pPsConfig pNoAParam;
+    tSirMsgQ msg;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    status = palAllocateMemory(pMac->hHdd, (void**)&pNoAParam, sizeof(tP2pPsConfig));
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, pNoAParam, sizeof(tP2pPsConfig));
+        palCopyMemory(pMac->hHdd, pNoAParam, pNoA, sizeof(tP2pPsConfig)); 
+        msg.type = eWNI_SME_UPDATE_NOA;
+        msg.bodyval = 0;
+        msg.bodyptr = pNoAParam;
+        limPostMsgApi(pMac, &msg);
+    }   
+    return status;
+}
+
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+eHalStatus p2pGetConfigParam(tHalHandle hHal, tP2PConfigParam *pParam)
+{
+   eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   if(pParam)
+   {
+      pParam->P2PListenChannel = pMac->p2pContext[0].P2PListenChannel;
+      pParam->P2POperatingChannel = pMac->p2pContext[0].P2POperatingChannel;
+      pParam->P2POpPSCTWindow = pMac->p2pContext[0].pNoA.ctWindow;
+      pParam->P2PPSSelection = pMac->p2pContext[0].pNoA.psSelection;
+      pParam->P2POpPSCTWindow = pMac->p2pContext[0].pNoA.ctWindow;
+      pParam->P2PNoADuration = pMac->p2pContext[0].pNoA.duration;
+      pParam->P2PNoACount = pMac->p2pContext[0].pNoA.count;
+      pParam->P2PNoAInterval = pMac->p2pContext[0].pNoA.interval;
+
+      status = eHAL_STATUS_SUCCESS;
+   }
+
+   return (status);
+}
+
+eHalStatus p2pChangeDefaultConfigParam(tHalHandle hHal, tP2PConfigParam *pParam)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   int i;
+   tANI_U8 pBuf[P2P_COUNTRY_CODE_LEN];
+   tANI_U8 uBufLen = P2P_COUNTRY_CODE_LEN;
+   tP2P_OperatingChannel p2pChannel;
+
+   status = sme_GetCountryCode( pMac, pBuf, &uBufLen );
+   if ( !HAL_STATUS_SUCCESS( status ) )
+   {
+      status = eHAL_STATUS_FAILURE;
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s Cannot get the country code\n", __FUNCTION__);
+   }
+
+   vos_mem_copy(p2pChannel.countryString, pBuf, sizeof(pBuf));
+   p2pChannel.regulatoryClass = 0x51;
+
+   if(pParam)
+   {
+      for ( i=0; i < MAX_NO_OF_P2P_SESSIONS; i++ ) 
+      {
+         if (pParam->P2PListenChannel == 1 || pParam->P2PListenChannel == 6 
+               || pParam->P2PListenChannel == 11)
+         {
+            pMac->p2pContext[i].P2PListenChannel = pParam->P2PListenChannel;
+         }
+         else
+         {
+            pMac->p2pContext[i].P2PListenChannel = P2P_OPERATING_CHANNEL;
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+               "Invalid P2P Listen Channel in config. Switch to default Listen Channel %d\n",
+               __FUNCTION__, P2P_OPERATING_CHANNEL);
+         }
+         
+         if(csrRoamIsChannelValid(pMac, pParam->P2POperatingChannel))
+         {
+            pMac->p2pContext[i].P2POperatingChannel = pParam->P2POperatingChannel;
+         }
+         else
+         {
+            pMac->p2pContext[i].P2POperatingChannel = P2P_OPERATING_CHANNEL;
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+               "Invalid P2P Operating Channel in config. Switch to default Channel %d\n", 
+               __FUNCTION__, P2P_OPERATING_CHANNEL);
+         }
+         pMac->p2pContext[i].pNoA.ctWindow = pParam->P2POpPSCTWindow;
+         pMac->p2pContext[i].pNoA.psSelection = pParam->P2PPSSelection;
+         pMac->p2pContext[i].pNoA.ctWindow = pParam->P2POpPSCTWindow;
+         pMac->p2pContext[i].pNoA.duration = pParam->P2PNoADuration;
+         pMac->p2pContext[i].pNoA.count = pParam->P2PNoACount;
+         pMac->p2pContext[i].pNoA.interval = pParam->P2PNoAInterval;
+
+         p2pChannel.channel = pMac->p2pContext[i].P2POperatingChannel;
+         P2P_UpdateIE(pMac, i, eWFD_OPERATING_CHANNEL, &p2pChannel, 1);
+         p2pChannel.channel = pMac->p2pContext[i].P2PListenChannel;
+         P2P_UpdateIE(pMac, i, eWFD_LISTEN_CHANNEL, &p2pChannel, 1);
+      }
+   }
+
+    return status;
+}
+
+eHalStatus p2pPS(tHalHandle hHal, tANI_U8 sessionId)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tP2pPsConfig pNoA;
+
+   /* call set in context */
+   pNoA.psSelection = pMac->p2pContext[sessionId].pNoA.psSelection;
+   pNoA.sessionid = sessionId;
+
+   if (pMac->p2pContext[sessionId].pNoA.psSelection == P2P_CLEAR_POWERSAVE)
+   {
+      return status;
+   }
+
+   if (pMac->p2pContext[sessionId].pNoA.psSelection == P2P_OPPORTUNISTIC_PS)
+   {
+      pNoA.opp_ps = TRUE;
+      pNoA.ctWindow = pMac->p2pContext[sessionId].pNoA.ctWindow;
+      pNoA.count = 0;
+      pNoA.duration = 0;
+      pNoA.interval = 0; 
+      pNoA.single_noa_duration = 0;
+   }
+   else if (pMac->p2pContext[sessionId].pNoA.psSelection == P2P_PERIODIC_NOA)
+   {
+      pNoA.opp_ps = 0;
+      pNoA.ctWindow = 0;
+      pNoA.count = pMac->p2pContext[sessionId].pNoA.count;
+      pNoA.duration = pMac->p2pContext[sessionId].pNoA.duration;
+      pNoA.interval = pMac->p2pContext[sessionId].pNoA.interval; 
+      pNoA.single_noa_duration = 0;
+   } 
+   else if(pMac->p2pContext[sessionId].pNoA.psSelection == P2P_SINGLE_NOA)
+   {
+      pNoA.opp_ps = 0;
+      pNoA.ctWindow = 0;
+      pNoA.count = 0;
+      pNoA.duration = 0;
+      pNoA.interval = 0; 
+      pNoA.single_noa_duration = pMac->p2pContext[sessionId].pNoA.duration;
+   }
+
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+      " %s HDDSession %d set NoA parameters. Selection %d, opp_ps %d, ctWindow %d, count %d, "
+      "duration %d, interval %d single NoA duration %d",
+      __FUNCTION__, sessionId, pMac->p2pContext[sessionId].pNoA.psSelection,
+      pNoA.opp_ps, pNoA.ctWindow, pNoA.count, pNoA.duration, 
+      pNoA.interval, pNoA.single_noa_duration );
+
+   status = sme_p2pSetPs(pMac, &pNoA);
+   if(!HAL_STATUS_SUCCESS(status))
+   {
+      smsLog(pMac, LOGE, FL(" sme_p2pSetPs fail with status %d"), status);
+      return status;
+   }
+
+   return status;
+}
+
+void P2P_UpdateMacHdr(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 *pBuf)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tSirMacMgmtHdr *macHdr = (tSirMacMgmtHdr *)pBuf;
+
+   macHdr->fc.protVer = 0;
+   macHdr->fc.type = 0;
+   macHdr->fc.subType = 13;
+   macHdr->durationLo = 0;
+   macHdr->durationHi = 0;
+   vos_mem_copy(macHdr->da, pMac->p2pContext[SessionID].peerMacAddress, P2P_MAC_ADDRESS_LEN);
+   vos_mem_copy(macHdr->sa, pMac->p2pContext[SessionID].selfMacAddress, P2P_MAC_ADDRESS_LEN);
+   vos_mem_copy(macHdr->bssId, pMac->p2pContext[SessionID].peerMacAddress, P2P_MAC_ADDRESS_LEN);
+
+   return;
+}
+
+static eHalStatus p2pRemainOnChannelReadyCallback(tHalHandle halHandle,
+                     void *pContext,
+                     eHalStatus scan_status)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tp2pContext *p2pContext = (tp2pContext*) pContext;
+
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s GroupFormationPending %d  PeerFound %d\n", 
+               __FUNCTION__, p2pContext->GroupFormationPending, p2pContext->PeerFound);
+
+   if (p2pContext->PeerFound)
+   {
+      p2pContext->PeerFound = FALSE;
+
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Sending actionframe\n", __FUNCTION__);
+      if (p2pContext->pSentActionFrame)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s calling p2pSendAction\n", __FUNCTION__);
+         p2pSendAction(halHandle, p2pContext->SMEsessionId, (tANI_U8 *)p2pContext->pSentActionFrame, p2pContext->ActionFrameLen);
+      }
+   }
+
+   return status;
+}
+
+eHalStatus p2pGrpFormationRemainOnChanRspCallback(tHalHandle halHandle, void *pContext, tANI_U32 scanId, eCsrScanStatus scan_status)
+{
+   return eHAL_STATUS_SUCCESS;
+}
+
+tANI_U8 p2pGetDialogToken(tHalHandle hHal, tANI_U8 SessionID, eP2PFrameType actionFrameType)
+{
+   tANI_U8 dialogToken = 0;
+
+   dialogToken = (tANI_U8) vos_timer_get_system_ticks();
+
+   return(dialogToken);
+}
+
+void p2pRetryActionFrameTimerHandler(void *pContext)
+{
+   tp2pContext *p2pContext = (tp2pContext*) pContext;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tpAniSirGlobal pMac = PMAC_STRUCT( p2pContext->hHal );
+
+   p2pContext->PeerFound = TRUE;
+   smsLog( pMac, LOGE, "%s Calling remain on channel \n", __FUNCTION__);
+   status = p2pRemainOnChannel( pMac, p2pContext->SMEsessionId, p2pContext->P2PListenChannel/*pScanResult->BssDescriptor.channelId*/, P2P_REMAIN_ON_CHAN_TIMEOUT_LOW,
+                                    NULL, NULL, eP2PRemainOnChnReasonSendFrame);
+   if(status != eHAL_STATUS_SUCCESS)
+   {
+      smsLog( pMac, LOGE, "%s remain on channel failed\n", __FUNCTION__);
+   }
+
+   return;
+}
+
+void p2pActionFrameTimerHandler(void *pContext)
+{
+   tp2pContext *p2pContext = (tp2pContext*) pContext;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tANI_U8 *pBuf = NULL, *pNextBuf = NULL;
+   tCsrRoamInfo roamInfo;
+
+
+   if(p2pContext->pSentActionFrame)
+   {
+      vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
+      csrRoamCallCallback((tpAniSirGlobal)p2pContext->hHal, p2pContext->SMEsessionId, &roamInfo, 0, 
+                          eCSR_ROAM_SEND_ACTION_CNF, 
+                          eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
+   }
+
+   if(VOS_IS_STATUS_SUCCESS(vos_spin_lock_acquire(&p2pContext->lState)))
+   {
+      if(p2pContext->pSentActionFrame)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN,
+            " %s actionframe timeout type %d", __FUNCTION__, p2pContext->actionFrameType);
+         pBuf = p2pContext->pSentActionFrame;
+         p2pContext->pSentActionFrame = NULL;
+      }
+      if(p2pContext->pNextActionFrm)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN,
+            " %s next actionframe timeout type %d", __FUNCTION__, p2pContext->NextActionFrameType);
+         pNextBuf = p2pContext->pNextActionFrm;
+         p2pContext->pNextActionFrm = NULL;
+      }
+      vos_spin_lock_release(&p2pContext->lState);
+
+      if(pBuf)
+      {
+         vos_mem_free(pBuf);
+      }
+      if(pNextBuf)
+      {
+         //Inform the failure of the next frame.
+         p2pContext->pSentActionFrame = pNextBuf;
+         p2pContext->ActionFrameLen = p2pContext->nNextFrmLen;
+         p2pContext->actionFrameType = p2pContext->NextActionFrameType;
+         vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
+         csrRoamCallCallback((tpAniSirGlobal)p2pContext->hHal, p2pContext->SMEsessionId, &roamInfo, 0, 
+                          eCSR_ROAM_SEND_ACTION_CNF, 
+                          eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
+         p2pContext->pSentActionFrame = NULL;
+         vos_mem_free(pNextBuf);
+      }
+   }
+   status = p2pFsm(p2pContext, eP2P_TRIGGER_DISCONNECTED);
+   p2pContext->actionFrameTimeout = TRUE;
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s timedout\n", __FUNCTION__);
+
+   return;
+}
+
+
+eHalStatus p2pCreateActionFrame(tpAniSirGlobal pMac, tANI_U8 SessionID, void *p2pactionframe, 
+                                 eP2PFrameType actionFrameType, tANI_U8 **ppFrm)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tANI_U32 len = 0;
+   tANI_U32 nActionFrmlen = 0, pendingFrameLen;
+   tANI_U8 *pActionFrm = NULL;
+   tANI_U8 *pBuf = NULL, *pLocal = NULL;
+   eP2PFrameType pendingActionFrameType;
+   tp2pContext *pP2pContext = &pMac->p2pContext[SessionID];
+
+   if(NULL == ppFrm)
+   {
+      smsLog(pMac, LOGE, FL("  invalid parameters"));
+      return eHAL_STATUS_FAILURE;
+   }
+
+   csrScanAbortMacScan(pMac);
+
+   switch (actionFrameType)
+   {
+   case eP2P_GONEGO_REQ:
+      status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_GO_NEGOTIATION_REQUEST, p2pactionframe, len);
+      break;
+
+   case eP2P_GONEGO_RES:
+      status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_GO_NEGOTIATION_RESPONSE, p2pactionframe, len);
+      break;
+
+   case eP2P_GONEGO_CNF:
+      status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_GO_NEGOTIATION_CONFIRMATION, p2pactionframe, len);
+      break;
+
+   case eP2P_PROVISION_DISCOVERY_REQUEST:
+      status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_PROVISION_DISCOVERY_REQUEST, p2pactionframe, len);
+      break;
+
+   case eP2P_PROVISION_DISCOVERY_RESPONSE:
+      status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_PROVISION_DISCOVERY_RESPONSE, p2pactionframe, len);
+      break;
+
+   case eP2P_INVITATION_REQ:
+      status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_INVITATION_REQUEST, p2pactionframe, len);
+      break;
+
+   case eP2P_INVITATION_RSP:
+      status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_INVITATION_RESPONSE, p2pactionframe, len);
+      break;
+   default:
+      return status;
+   }
+
+   status = P2P_GetActionFrame(pMac, SessionID, actionFrameType, &pActionFrm, &nActionFrmlen);
+   if(!HAL_STATUS_SUCCESS(status))
+   {
+      smsLog(pMac, LOGE, FL(" P2P_GetActionFrame fail with status %d"), status);
+      return status;
+   }
+
+   P2P_UpdateMacHdr(pMac, SessionID, pActionFrm);
+
+   pBuf = (tANI_U8 *)vos_mem_malloc( nActionFrmlen);
+   if(NULL == pBuf)
+   {
+      smsLog(pMac, LOGE, FL("  fail to allocate memory"));
+      if (pActionFrm) 
+         vos_mem_free(pActionFrm);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   vos_mem_copy(pBuf, pActionFrm, nActionFrmlen);
+   vos_mem_free(pActionFrm);
+
+   if( !VOS_IS_STATUS_SUCCESS(vos_spin_lock_acquire(&pP2pContext->lState)))
+   {
+      smsLog(pMac, LOGE, FL("  fail to acquire spinlock"));
+      vos_mem_free(pBuf);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   if(NULL != pP2pContext->pSentActionFrame)
+   {
+      //If there is one pending frame already. Drop that one and save the new one
+      pLocal = pP2pContext->pNextActionFrm;
+      pendingActionFrameType = pP2pContext->NextActionFrameType;
+      pendingFrameLen = pP2pContext->nNextFrmLen;
+      pP2pContext->pNextActionFrm = pBuf;
+      pP2pContext->nNextFrmLen = nActionFrmlen;
+      pP2pContext->NextActionFrameType = actionFrameType;
+      *ppFrm = NULL;
+   }
+   else
+   {
+      pP2pContext->pSentActionFrame = pBuf;
+      pP2pContext->ActionFrameLen = nActionFrmlen;
+      pP2pContext->actionFrameType = actionFrameType;
+      *ppFrm = pBuf;
+   }
+   vos_spin_lock_release(&pP2pContext->lState);
+
+   if(NULL != pLocal)
+   {
+      smsLog(pMac, LOGE, FL(" Drop a waiting action frame 0x%x, type %d lenth %d"), 
+         pLocal, pendingActionFrameType, pendingFrameLen);
+      vos_mem_free(pLocal);
+   }
+
+   return status;
+}
+
+
+extern eHalStatus p2pGetSSID(tANI_U8 *ssId, tANI_U32 *ssIdLen, tANI_U8 SessionID);
+
+static eHalStatus p2pSendActionFrame(tpAniSirGlobal pMac, tANI_U8 HDDSessionID, eP2PFrameType actionFrameType)
+{
+   tCsrScanResultFilter filter;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tScanResultHandle hScanResult = NULL;
+   tCsrScanResultInfo   *pScanResult   = NULL;
+   tANI_U8 ssId[SIR_MAC_MAX_SSID_LENGTH];
+   tANI_U32 ssIdLen = 0;
+   tp2pContext *pP2pContext = &pMac->p2pContext[HDDSessionID];
+
+   pP2pContext->GroupFormationPending = TRUE;
+   if (actionFrameType == eP2P_GONEGO_REQ || actionFrameType == eP2P_PROVISION_DISCOVERY_REQUEST 
+      || actionFrameType == eP2P_INVITATION_REQ)
+   {
+      vos_mem_zero(&filter, sizeof(filter));
+      filter.BSSIDs.numOfBSSIDs = 1;
+      filter.BSSIDs.bssid = &pP2pContext->peerMacAddress;
+      filter.bWPSAssociation = TRUE;
+      filter.BSSType = eCSR_BSS_TYPE_ANY;
+
+      status = csrScanGetResult(pMac, &filter, &hScanResult);
+
+      if (hScanResult)
+      {
+         pScanResult = csrScanResultGetFirst(pMac, hScanResult );
+         if(pScanResult)
+         {
+
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s found match on channel %d", 
+               __FUNCTION__, pScanResult->BssDescriptor.channelId);
+            pP2pContext->formationReq.targetListenChannel = pScanResult->BssDescriptor.channelId;
+            if(pP2pContext->P2PListenChannel != pScanResult->BssDescriptor.channelId)
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+                  "%s adapt listen channel to %d", 
+                  __FUNCTION__, pScanResult->BssDescriptor.channelId);
+               p2pSetListenChannel(pMac, pP2pContext->sessionId, pScanResult->BssDescriptor.channelId);
+            }
+            vos_mem_copy(pP2pContext->formationReq.deviceAddress, pScanResult->BssDescriptor.bssId, P2P_MAC_ADDRESS_LEN);
+         }
+         csrScanResultPurge(pMac, hScanResult);
+      } 
+      else 
+      {
+         vos_mem_zero(&filter, sizeof(filter));
+         filter.bWPSAssociation = TRUE;
+         filter.BSSType = eCSR_BSS_TYPE_ANY;
+         filter.SSIDs.SSIDList =( tCsrSSIDInfo *)vos_mem_malloc(sizeof(tCsrSSIDInfo));
+         if( filter.SSIDs.SSIDList == NULL )
+         {
+            smsLog( pMac, LOGP, FL("vos_mem_malloc failed:") );
+            pP2pContext->GroupFormationPending = FALSE;
+            return eHAL_STATUS_FAILURE;
+         }
+         vos_mem_zero( filter.SSIDs.SSIDList, sizeof(tCsrSSIDInfo) );
+         p2pGetSSID(ssId, &ssIdLen, HDDSessionID);
+
+         if (ssIdLen)
+         {
+            filter.SSIDs.SSIDList->SSID.length = ssIdLen;
+            vos_mem_copy(&filter.SSIDs.SSIDList[0].SSID.ssId, &ssId, ssIdLen);
+            filter.SSIDs.numOfSSIDs = 1;
+            status = csrScanGetResult(pMac, &filter, &hScanResult);
+            if (hScanResult)
+            {
+               pScanResult = csrScanResultGetFirst(pMac, hScanResult );
+               pP2pContext->formationReq.targetListenChannel = pScanResult->BssDescriptor.channelId;
+               vos_mem_copy(pP2pContext->formationReq.deviceAddress, pScanResult->BssDescriptor.bssId, P2P_MAC_ADDRESS_LEN);
+               csrScanResultPurge(pMac, hScanResult);
+            }
+            else
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s not found match\n", __FUNCTION__);
+               pP2pContext->formationReq.targetListenChannel = 0;
+               vos_mem_copy(pP2pContext->formationReq.deviceAddress, pP2pContext->peerMacAddress, P2P_MAC_ADDRESS_LEN);
+               status = eHAL_STATUS_SUCCESS;
+            }
+            vos_mem_free(filter.SSIDs.SSIDList);
+         }
+         else
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s not found match\n", __FUNCTION__);
+            pP2pContext->formationReq.targetListenChannel = 0;
+            vos_mem_copy(pP2pContext->formationReq.deviceAddress, pP2pContext->peerMacAddress, P2P_MAC_ADDRESS_LEN);
+            status = eHAL_STATUS_SUCCESS;
+         }    
+      }
+      sme_CancelRemainOnChannel(pMac, pP2pContext->SMEsessionId );
+      p2pFsm(pP2pContext, eP2P_TRIGGER_GROUP_FORMATION);     
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, " %s send action frame %d timeout %d\n", 
+               __FUNCTION__, actionFrameType, pP2pContext->ActionFrameSendTimeout);
+   } 
+   else
+   {
+      pP2pContext->PeerFound = TRUE;
+
+      status = p2pSendAction(pMac, pP2pContext->SMEsessionId, (tANI_U8 *)pP2pContext->pSentActionFrame, 
+                              pP2pContext->ActionFrameLen);
+      if(status != eHAL_STATUS_SUCCESS)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,  
+            "%s p2pSendAction failed to send frame type %d\n", __FUNCTION__, actionFrameType);
+         pP2pContext->GroupFormationPending = FALSE;
+         return status;
+      }
+
+      if ( actionFrameType == eP2P_GONEGO_RES )
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling p2pRemainOnChannel with duration"
+            "%d on channel %d\n", __FUNCTION__, P2P_REMAIN_ON_CHAN_TIMEOUT, pP2pContext->P2PListenChannel);
+
+         if(p2pRemainOnChannel( pMac, pP2pContext->SMEsessionId, 
+                                      pP2pContext->P2PListenChannel, P2P_REMAIN_ON_CHAN_TIMEOUT_LOW,
+                                      NULL, NULL, eP2PRemainOnChnReasonSendFrame))
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,  "%s remain on channel failed\n", __FUNCTION__);
+         }
+      }
+   }
+
+   return(status);
+}
+
+
+#define WLAN_P2P_DEF_ACTION_FRM_TIMEOUT_VALUE 1000  //1s
+
+eHalStatus p2pCreateSendActionFrame(tHalHandle hHal, tANI_U8 HDDSessionID, 
+   void *p2pactionframe, eP2PFrameType actionFrameType, tANI_U32 timeout)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tANI_U8 *pBuf = NULL;
+   tp2pContext *pP2pContext = &pMac->p2pContext[HDDSessionID];
+   
+   status = p2pCreateActionFrame(pMac, HDDSessionID, p2pactionframe, actionFrameType, &pBuf);
+   if(!HAL_STATUS_SUCCESS(status))
+   {
+      smsLog(pMac, LOGE, FL("  fail to create action frame"));
+      return status;
+   }
+      
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, " %s send action frame %d timeout %d\n", 
+                  __FUNCTION__, actionFrameType, timeout);
+
+   if(NULL != pBuf)
+   {
+      if (timeout)
+      {
+         pP2pContext->ActionFrameSendTimeout = timeout;
+      }
+      else
+      {
+         pP2pContext->ActionFrameSendTimeout = WLAN_P2P_DEF_ACTION_FRM_TIMEOUT_VALUE;
+      }
+
+      status = palTimerStart(pMac->hHdd, pP2pContext->actionFrameTimer, 
+                        pP2pContext->ActionFrameSendTimeout * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
+      if (!HAL_STATUS_SUCCESS(status))
+      {
+         tCsrRoamInfo RoamInfo;
+
+         vos_mem_zero(&RoamInfo, sizeof(tCsrRoamInfo));
+         smsLog(pMac, LOGE, FL(" %s fail to start timer status %d"), __FUNCTION__, status);
+         //Without the timer we cannot continue
+         csrRoamCallCallback((tpAniSirGlobal)pP2pContext->hHal, 
+                     pP2pContext->SMEsessionId, &RoamInfo, 0, 
+                     eCSR_ROAM_SEND_ACTION_CNF, 
+                     eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
+         vos_spin_lock_acquire(&pP2pContext->lState);
+         pBuf = pP2pContext->pSentActionFrame;
+         pP2pContext->pSentActionFrame = NULL;
+         vos_spin_lock_release(&pP2pContext->lState);
+         vos_mem_free(pBuf);
+         pBuf = NULL;
+         p2pFsm(pP2pContext, eP2P_TRIGGER_DISCONNECTED);
+         return status;
+      }
+      //We can send this frame now
+      status = p2pSendActionFrame(pMac, HDDSessionID, actionFrameType);
+      if(!HAL_STATUS_SUCCESS(status))
+      {
+         smsLog(pMac, LOGE, FL("  fail to send action frame status %d"), status);
+      }
+      //Let them retry
+      pP2pContext->actionFrameTimeout = FALSE;
+   }
+   else
+   {
+      //An action frame is pedning at lower layer
+      smsLog(pMac, LOGW, FL("  An action frame is pending while trying to send frametype %d"), actionFrameType);
+      if (timeout)
+      {
+         pP2pContext->nNextFrameTimeOut = timeout;
+      }
+      else
+      {
+         pP2pContext->nNextFrameTimeOut = WLAN_P2P_DEF_ACTION_FRM_TIMEOUT_VALUE;
+      }
+   }
+
+   return status;
+}
+
+
+void p2pListenDiscoverTimerHandlerCB(void *pContext)
+{
+}
+
+void p2pListenDiscoverTimerHandler(void *pContext)
+{
+   tp2pContext *p2pContext = (tp2pContext*) pContext;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+
+   if( (eP2P_STATE_DISCONNECTED == p2pContext->state) && 
+       (eStateDisabled != p2pContext->listenDiscoverableState) )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling RemainOnChannel with duration %d on channel %d\n", 
+             __FUNCTION__, p2pContext->listenDuration, p2pContext->P2PListenChannel);
+      status = p2pRemainOnChannel( p2pContext->hHal, p2pContext->SMEsessionId, p2pContext->P2PListenChannel, p2pContext->listenDuration, 
+                                    p2pListenStateDiscoverableCallback, p2pContext, eP2PRemainOnChnReasonListen);
+   }
+   else
+   {
+      smsLog(((tpAniSirGlobal)p2pContext->hHal), LOGW, FL(" cannot call p2pRemainOnChannel state %d\n"), p2pContext->state);
+   }
+
+   return;
+}
+
+
+static eHalStatus p2pListenStateDiscoverableCallback(tHalHandle halHandle, void *pContext, eHalStatus retStatus)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tpAniSirGlobal pMac = PMAC_STRUCT(halHandle);
+   tp2pContext *p2pContext = (tp2pContext*) pContext;
+
+   if( (eP2P_STATE_DISCONNECTED == p2pContext->state) && 
+       (eStateDisabled != p2pContext->listenDiscoverableState) && 
+       (NULL == p2pContext->p2pDiscoverCBFunc) )
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s restart listen timer expire time %d\n", 
+                  __FUNCTION__, p2pContext->expire_time);
+      //We can restart the listening
+      status = palTimerStart(pMac->hHdd, p2pContext->listenTimerHandler, p2pContext->expire_time, eANI_BOOLEAN_FALSE);
+      if (eHAL_STATUS_SUCCESS != status)
+      {
+         VOS_ASSERT(status);
+      }
+   }
+   else
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s not restart listen timer  state (%d)\n", 
+                  __FUNCTION__, p2pContext->state);
+   }
+
+   return status;
+}
+
+
+eHalStatus P2P_ListenStateDiscoverable(tHalHandle hHal, tANI_U8 sessionId,
+                                       ep2pListenStateDiscoverability listenState)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   switch (listenState) 
+   {
+   case P2P_DEVICE_NOT_DISCOVERABLE:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s P2P_NOT_DISCOVERABLE\n", __FUNCTION__);
+      pMac->p2pContext[sessionId].listenDiscoverableState = eStateDisabled;
+      pMac->p2pContext[sessionId].DiscoverableCfg = listenState;
+      if (pMac->p2pContext[sessionId].state == eP2P_STATE_DISCONNECTED)
+      {
+         sme_CancelRemainOnChannel(hHal, sessionId );
+
+         if (pMac->p2pContext[sessionId].listenTimerHandler)
+         {
+            status = palTimerStop(pMac->hHdd, pMac->p2pContext[sessionId].listenTimerHandler);
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Timer Stop status %d\n", 
+                        __FUNCTION__, status);
+         }
+      }
+      else
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s P2P_NOT_DISCOVERABLE not in right state (%d)",
+            __FUNCTION__, pMac->p2pContext[sessionId].state);
+      }
+      break;
+
+   case P2P_DEVICE_AUTO_AVAILABILITY:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s P2P_AUTO_AVAILABILITY\n",__FUNCTION__);
+      pMac->p2pContext[sessionId].listenDiscoverableState = eStateEnabled;
+      pMac->p2pContext[sessionId].DiscoverableCfg = listenState;
+      pMac->p2pContext[sessionId].expire_time = P2P_LISTEN_TIMEOUT_AUTO * PAL_TIMER_TO_MS_UNIT;
+      pMac->p2pContext[sessionId].listenDuration = P2P_LISTEN_TIMEOUT;
+      if (pMac->p2pContext[sessionId].state == eP2P_STATE_DISCONNECTED)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling RemainOnChannel with diration %d on channel %d\n",
+                     __FUNCTION__, pMac->p2pContext[sessionId].listenDuration, pMac->p2pContext[sessionId].P2PListenChannel);
+         p2pRemainOnChannel( pMac, pMac->p2pContext[sessionId].SMEsessionId, pMac->p2pContext[sessionId].P2PListenChannel, 
+                              pMac->p2pContext[sessionId].listenDuration, p2pListenStateDiscoverableCallback, 
+                              &pMac->p2pContext[sessionId], eP2PRemainOnChnReasonListen);
+      }
+      else
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s P2P_AUTO_DISCOVERABLE not in right state (%d)",
+            __FUNCTION__, pMac->p2pContext[sessionId].state);
+      }
+      break;
+
+   case P2P_DEVICE_HIGH_AVAILABILITY:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s P2P_HIGH_AVAILABILITY\n",__FUNCTION__);
+      pMac->p2pContext[sessionId].listenDiscoverableState = eStateEnabled;
+      pMac->p2pContext[sessionId].DiscoverableCfg = listenState;
+      pMac->p2pContext[sessionId].expire_time = P2P_REMAIN_ON_CHAN_TIMEOUT_LOW * PAL_TIMER_TO_MS_UNIT;
+      pMac->p2pContext[sessionId].listenDuration = P2P_LISTEN_TIMEOUT_HIGH;
+      if (pMac->p2pContext[sessionId].state == eP2P_STATE_DISCONNECTED)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling RemainOnChannel with diration %d on channel %d\n",
+                     __FUNCTION__, pMac->p2pContext[sessionId].listenDuration, pMac->p2pContext[sessionId].P2PListenChannel);
+         p2pRemainOnChannel( pMac, pMac->p2pContext[sessionId].SMEsessionId, pMac->p2pContext[sessionId].P2PListenChannel, 
+                              pMac->p2pContext[sessionId].listenDuration, p2pListenStateDiscoverableCallback, 
+                              &pMac->p2pContext[sessionId], eP2PRemainOnChnReasonListen);
+      }
+      else
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s P2P_HIGH_DISCOVERABLE not in right state (%d)",
+            __FUNCTION__, pMac->p2pContext[sessionId].state);
+      }
+      break;
+
+   case 234: //Not to use this as it enabling GO to be concurrent with P2P device P2P_DEVICE_HIGH_AVAILABILITY:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s P2P_HIGH_AVAILABILITY\n",__FUNCTION__);
+      pMac->p2pContext[sessionId].listenDiscoverableState = eStateEnabled;
+      pMac->p2pContext[sessionId].DiscoverableCfg = listenState;
+
+      if ((pMac->p2pContext[sessionId].P2POperatingChannel != pMac->p2pContext[sessionId].P2PListenChannel)
+           && p2pIsGOportEnabled(pMac))
+      {
+         pMac->p2pContext[sessionId].expire_time = P2P_LISTEN_TIMEOUT_HIGH * PAL_TIMER_TO_MS_UNIT * 5;
+         pMac->p2pContext[sessionId].listenDuration = P2P_REMAIN_ON_CHAN_TIMEOUT_LOW;
+      } 
+      else
+      {
+         pMac->p2pContext[sessionId].expire_time = P2P_LISTEN_TIMEOUT_HIGH * PAL_TIMER_TO_MS_UNIT;
+         pMac->p2pContext[sessionId].listenDuration = P2P_LISTEN_TIMEOUT;
+      }
+
+      if (pMac->p2pContext[sessionId].state == eP2P_STATE_DISCONNECTED)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling RemainOnChannel with diration %d on channel %d\n",
+                     __FUNCTION__, pMac->p2pContext[sessionId].listenDuration, pMac->p2pContext[sessionId].P2PListenChannel);
+         p2pRemainOnChannel( pMac, pMac->p2pContext[sessionId].SMEsessionId, pMac->p2pContext[sessionId].P2PListenChannel, 
+                              pMac->p2pContext[sessionId].listenDuration, p2pListenStateDiscoverableCallback, 
+                              &pMac->p2pContext[sessionId], eP2PRemainOnChnReasonListen);
+      }
+      
+      break;
+
+   default:
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+         "%s Unknown listen setting",__FUNCTION__, listenState);
+      break;
+   }
+
+    return( status );
+}
+
+
+void p2pCallDiscoverCallback(tp2pContext *p2pContext, eP2PDiscoverStatus statusCode)
+{
+   if (p2pContext->p2pDiscoverCBFunc)
+   {
+      p2pDiscoverCompleteCallback pcallback = p2pContext->p2pDiscoverCBFunc;
+      p2pContext->p2pDiscoverCBFunc = NULL;
+      pcallback(p2pContext->hHal, p2pContext->pContext, statusCode);
+   }
+   p2pContext->directedDiscovery = FALSE;
+}
+
+
+void p2pDiscoverTimerHandler(void *pContext)
+{
+   tp2pContext *p2pContext = (tp2pContext*) pContext;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s enter", __FUNCTION__);
+   p2pCallDiscoverCallback(p2pContext, 
+         (p2pContext->directedDiscovery) ? eP2P_DIRECTED_DISCOVER : eP2P_DISCOVER_SUCCESS);
+
+   status = p2pFsm(p2pContext, eP2P_TRIGGER_DISCONNECTED);
+
+   return;
+}
+
+
+
+eHalStatus p2pGetResultFilter(tp2pContext *pP2pContext,
+                              tCsrScanResultFilter *pFilter)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   v_U32_t uNumDeviceFilters;
+   tp2pDiscoverDeviceFilter *directedDiscoveryFilter;
+   int i;
+   tCsrBssid *bssid = NULL;
+
+   do
+   {
+      if( (NULL != pP2pContext) && (NULL != pFilter) )
+      {
+         vos_mem_zero(pFilter, sizeof(tCsrScanResultFilter));
+         uNumDeviceFilters = pP2pContext->uNumDeviceFilters;
+         directedDiscoveryFilter = pP2pContext->directedDiscoveryFilter;
+         for(i = 0; i < uNumDeviceFilters; i++)
+         {
+            if (directedDiscoveryFilter->ucBitmask & DISCOVERY_FILTER_BITMASK_DEVICE)
+            {
+               pFilter->BSSIDs.numOfBSSIDs++;
+            }
+            
+            if ((directedDiscoveryFilter->ucBitmask != QCWLAN_P2P_DISCOVER_ANY) 
+               && (directedDiscoveryFilter->ucBitmask & DISCOVERY_FILTER_BITMASK_GO))
+            {
+               //Matching Device ID and GroupSSID
+               pFilter->BSSIDs.numOfBSSIDs++;
+               if(directedDiscoveryFilter->GroupSSID.length)
+               {
+                  pFilter->SSIDs.numOfSSIDs++;
+               }
+            }
+            directedDiscoveryFilter += sizeof(tp2pDiscoverDeviceFilter);
+         }
+
+         directedDiscoveryFilter = pP2pContext->directedDiscoveryFilter;
+         if (pFilter->BSSIDs.numOfBSSIDs)
+         {
+            bssid = ( tCsrBssid *) vos_mem_malloc( sizeof( tCsrBssid ) * pFilter->BSSIDs.numOfBSSIDs );
+            if(NULL == bssid)
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                  " %s fail to allocate bssid", __FUNCTION__);
+               status = eHAL_STATUS_RESOURCES;
+               break;
+            }
+
+            pFilter->BSSIDs.bssid = bssid;
+
+            for (i = 0; i < uNumDeviceFilters; i++)
+            {
+               vos_mem_copy(bssid, directedDiscoveryFilter->DeviceID, P2P_MAC_ADDRESS_LEN);
+               bssid += sizeof(tCsrBssid);
+               directedDiscoveryFilter += sizeof(tp2pDiscoverDeviceFilter);
+            }
+         }
+
+         directedDiscoveryFilter = pP2pContext->directedDiscoveryFilter;
+         if (pFilter->SSIDs.numOfSSIDs)
+         {
+            pFilter->SSIDs.SSIDList = (tCsrSSIDInfo *)vos_mem_malloc( sizeof( *pFilter->SSIDs.SSIDList ) *
+                                                      pFilter->SSIDs.numOfSSIDs );
+            if(NULL == pFilter->SSIDs.SSIDList)
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                  " %s fail to allocate bssid", __FUNCTION__);
+               status = eHAL_STATUS_RESOURCES;
+               break;
+            }
+
+            if ( pFilter->SSIDs.SSIDList )
+            {
+               for ( i = 0; i < uNumDeviceFilters; i++ )
+               {
+                  if (directedDiscoveryFilter->ucBitmask == DISCOVERY_FILTER_BITMASK_GO)
+                  {
+                     if(directedDiscoveryFilter->GroupSSID.length)
+                     {
+                        pFilter->SSIDs.SSIDList[i].SSID.length = directedDiscoveryFilter->GroupSSID.length;
+                        vos_mem_copy( pFilter->SSIDs.SSIDList[i].SSID.ssId,
+                                       directedDiscoveryFilter->GroupSSID.ssId,
+                                       directedDiscoveryFilter->GroupSSID.length );
+                     }
+                  }
+                  directedDiscoveryFilter += sizeof(tp2pDiscoverDeviceFilter);
+               }
+            }
+         }
+      }
+
+      pFilter->p2pResult = TRUE;
+      pFilter->bWPSAssociation = TRUE;
+      pFilter->BSSType = eCSR_BSS_TYPE_ANY;
+   } while(0);
+
+   if(!HAL_STATUS_SUCCESS(status))
+   {
+      if(pFilter->SSIDs.SSIDList)
+      {
+         vos_mem_free(pFilter->SSIDs.SSIDList);
+         pFilter->SSIDs.SSIDList = NULL;
+      }
+      if( pFilter->BSSIDs.bssid )
+      {
+         vos_mem_free(pFilter->BSSIDs.bssid);
+         pFilter->BSSIDs.bssid = NULL;
+      }
+   }
+
+   return status;
+}
+
+
+/*
+  @breif Function calls P2P_Fsm function to initiate the P2P Discover process
+
+  @param[in] hHal - Handle to MAC structure.
+        [in] sessionID - Session ID returned by sme_OpenSession
+        [in] pDiscoverRequest - pointer to the tp2pDiscoverRequest structure
+             whose parameters are filled in the HDD.
+        [in] callback - HDD callback function to be called when Discover
+             is complete
+        [in] pContext - a pointer passed in for the callback
+
+  @return eHAL_STATUS_FAILURE - If success.
+          eHAL_STATUS_SUCCESS - If failure.
+*/
+eHalStatus P2P_DiscoverRequest(tHalHandle hHal,
+                tANI_U8 SessionID,
+                tP2PDiscoverRequest *pDiscoverRequest,
+                p2pDiscoverCompleteCallback callback,
+                void *pContext)
+{
+   eHalStatus           status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal       pMac = PMAC_STRUCT(hHal);
+   tScanResultHandle    hScanResult = NULL;
+   tCsrScanResultFilter filter;
+   tANI_U32 uNumDeviceFilters;
+   tp2pDiscoverDeviceFilter *pDeviceFilters;
+   tANI_U32 i = 0;
+   tp2pContext *pP2pContext = &pMac->p2pContext[SessionID];
+   tCsrBssid *bssid = NULL;
+   tp2pDiscoverDeviceFilter discoverFilter;
+   tANI_BOOLEAN fDirect = FALSE;
+
+   if (pDiscoverRequest == NULL)
+   {
+      return status;
+   }
+
+   pP2pContext->discoverType      = pDiscoverRequest->discoverType;
+   pP2pContext->scanType          = pDiscoverRequest->scanType;
+   pP2pContext->uDiscoverTimeout  = pDiscoverRequest->uDiscoverTimeout;
+
+   if (pP2pContext->DiscoverReqIeField)
+   {
+      vos_mem_free(pP2pContext->DiscoverReqIeField);
+      pP2pContext->DiscoverReqIeLength = 0;
+      pP2pContext->DiscoverReqIeField = NULL;
+   }
+
+   if (pDiscoverRequest->uIELen)
+   {
+      pP2pContext->DiscoverReqIeField = (tANI_U8 *)vos_mem_malloc(pDiscoverRequest->uIELen);
+      vos_mem_copy((tANI_U8 *)pP2pContext->DiscoverReqIeField, pDiscoverRequest->pIEField, pDiscoverRequest->uIELen);
+      pP2pContext->DiscoverReqIeLength = pDiscoverRequest->uIELen;
+   } 
+   else
+   {
+      pP2pContext->DiscoverReqIeLength = 0;
+   }
+
+   vos_mem_zero(&filter, sizeof(filter));
+
+   do
+   {
+      if (pDiscoverRequest->uNumDeviceFilters)
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s directed\n", __FUNCTION__);
+         fDirect = TRUE;
+         uNumDeviceFilters = pDiscoverRequest->uNumDeviceFilters;
+
+         pP2pContext->uDiscoverTimeout = pP2pContext->uDiscoverTimeout;
+         pP2pContext->uNumDeviceFilters = pDiscoverRequest->uNumDeviceFilters;
+         if(pP2pContext->uNumDeviceFilterAllocated < pDiscoverRequest->uNumDeviceFilters)
+         {
+            if(pP2pContext->directedDiscoveryFilter)
+            {
+               pP2pContext->uNumDeviceFilterAllocated = 0;
+               vos_mem_free(pP2pContext->directedDiscoveryFilter);
+               pP2pContext->directedDiscoveryFilter = NULL;
+            }
+            pP2pContext->directedDiscoveryFilter = (tp2pDiscoverDeviceFilter *)
+                  vos_mem_malloc(sizeof(tp2pDiscoverDeviceFilter) * uNumDeviceFilters);
+            if(NULL == pP2pContext->directedDiscoveryFilter)
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                  "%s fail to allocate memory for discoverFilter", __FUNCTION__);
+               status = eHAL_STATUS_RESOURCES;
+               break;
+            }
+            pP2pContext->uNumDeviceFilterAllocated = uNumDeviceFilters;
+         }
+
+         pDeviceFilters = pDiscoverRequest->pDeviceFilters;
+         if(NULL != pDeviceFilters)
+         {
+            vos_mem_copy ( pP2pContext->directedDiscoveryFilter, pDeviceFilters,
+                              sizeof(tp2pDiscoverDeviceFilter) * uNumDeviceFilters);
+
+            if(!HAL_STATUS_SUCCESS(status = p2pGetResultFilter(pP2pContext, &filter)))
+            {
+               VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                  "%s fail to create filter", __FUNCTION__);
+               break;
+            }
+         }//if(NULL != pDeviceFilters)
+
+         status = csrScanGetResult(pMac, &filter, &hScanResult);
+         if (hScanResult)
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+               "%s calling p2pDiscoverCompleteCallback\n", __FUNCTION__);
+            if (callback)
+            {
+               callback(hHal, pContext, eP2P_DIRECTED_DISCOVER);
+
+            }       
+            status =  eHAL_STATUS_SUCCESS;
+            break;
+         }
+         else
+         {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+               "%s Directed find did not find BSSID in cache\n", __FUNCTION__);
+            pP2pContext->formationReq.targetListenChannel = 0;
+            if (pDiscoverRequest->uNumDeviceFilters == 1 && filter.BSSIDs.numOfBSSIDs == 1)
+            {
+               vos_mem_copy(&pP2pContext->formationReq.deviceAddress, 
+                              pDiscoverRequest->pDeviceFilters->DeviceID, P2P_MAC_ADDRESS_LEN);
+            }
+         }
+      }
+
+      pP2pContext->p2pDiscoverCBFunc = callback;
+      pP2pContext->pContext          = pContext;
+      pP2pContext->directedDiscovery = fDirect;
+      if(!pP2pContext->GroupFormationPending)
+      {
+         p2pFsm(&pMac->p2pContext[SessionID], eP2P_TRIGGER_DEVICE_MODE_DEVICE);
+      }
+      else
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, 
+               "%s while group formation", __FUNCTION__);
+      }
+
+      pP2pContext->uDiscoverTimeout = pDiscoverRequest->uDiscoverTimeout;
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s Start discover", __FUNCTION__);
+      status = palTimerStart(pMac->hHdd, pP2pContext->discoverTimer, 
+                     pP2pContext->uDiscoverTimeout * 1000, eANI_BOOLEAN_FALSE);
+      if(!HAL_STATUS_SUCCESS(status))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+            "%s failt to start discover timer", __FUNCTION__);
+            pP2pContext->p2pDiscoverCBFunc = NULL;
+            pP2pContext->pContext          = NULL;
+            if(callback)
+            {
+               callback(pMac, pContext, eP2P_DISCOVER_FAILURE);
+            }
+      }
+   }while(0);
+
+   if(filter.SSIDs.SSIDList)
+   {
+      vos_mem_free(filter.SSIDs.SSIDList);
+   }
+   if( hScanResult )
+   {
+      sme_ScanResultPurge( pMac, hScanResult );
+   }
+   if( filter.BSSIDs.bssid )
+   {
+      vos_mem_free(filter.BSSIDs.bssid);
+   }
+
+   return status;
+}
+
+eHalStatus p2pScanRequest(tp2pContext *p2pContext, p2pDiscoverCompleteCallback callback, void *pContext)
+{
+   tCsrScanRequest scanRequest;
+   v_U32_t scanId = 0;
+   tANI_U32 len = 0;
+   tCsrSSIDInfo wcSSID = { {P2P_WILDCARD_SSID_LEN, P2P_WILDCARD_SSID}, 0, 0 };
+   tANI_U8 Channel; 
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tP2P_OperatingChannel p2pOperatingChannel;
+   tpAniSirGlobal pMac = PMAC_STRUCT(p2pContext->hHal);
+   tANI_U8 *p2pIe = NULL;
+   tANI_U32 p2pIeLen;
+
+   vos_mem_zero( &scanRequest, sizeof(scanRequest));
+
+   P2P_GetOperatingChannel(p2pContext->hHal, p2pContext->sessionId, &p2pOperatingChannel);
+   Channel = p2pOperatingChannel.channel;
+   
+   if (Channel)
+   {
+      scanRequest.ChannelInfo.numOfChannels = 1;      
+      scanRequest.ChannelInfo.ChannelList = &Channel;
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s Scan on channel %d p2pContext->sessionId %d\n", 
+                  __FUNCTION__, Channel, p2pContext->sessionId);
+   }
+   else
+   {
+       getChannelInfo(p2pContext, &scanRequest.ChannelInfo, WFD_DISCOVER_TYPE_AUTO);
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s Scan on all channels\n", 
+                  __FUNCTION__);
+   }
+
+   /* set the scan type to active */
+   scanRequest.scanType = eSIR_ACTIVE_SCAN;
+
+   vos_mem_set( scanRequest.bssid, sizeof( tCsrBssid ), 0xff );
+
+   scanRequest.requestType = eCSR_SCAN_P2P_FIND_PEER;
+   /* set min and max channel time to zero */
+   scanRequest.minChnTime = 30;
+   scanRequest.maxChnTime = 100;
+
+   /* set BSSType to default type */
+   scanRequest.BSSType = eCSR_BSS_TYPE_ANY;
+
+   scanRequest.SSIDs.numOfSSIDs = 1;
+   scanRequest.SSIDs.SSIDList = &wcSSID;
+   scanRequest.p2pSearch = VOS_FALSE;
+       
+   P2P_GetIE(p2pContext, p2pContext->sessionId, eP2P_GROUP_ID, &p2pIe, &p2pIeLen);
+   vos_mem_copy(scanRequest.bssid, ((tP2PGroupId *)p2pIe)->deviceAddress, P2P_MAC_ADDRESS_LEN);
+
+   P2P_GetIE(p2pContext, p2pContext->sessionId, eP2P_PROBE_REQ,  &scanRequest.pIEField, &len);
+
+   scanRequest.uIEFieldLen = len;
+
+   status = csrScanRequest( p2pContext->hHal, p2pContext->SMEsessionId, &scanRequest, &scanId, callback, pContext );
+
+   if(scanRequest.pIEField)
+   {
+      vos_mem_free(scanRequest.pIEField);
+   }
+
+   if(p2pIe)
+   {
+      vos_mem_free(p2pIe);
+   }
+   return status;
+}
+
+tANI_U8 getP2PSessionIdFromSMESessionId(tHalHandle hHal, tANI_U8 SessionID)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tANI_U8 num_session;
+
+   for (num_session = 0; num_session < MAX_NO_OF_P2P_SESSIONS; num_session++)
+   {
+      if(SessionID == pMac->p2pContext[num_session].SMEsessionId)
+      {
+         return pMac->p2pContext[num_session].sessionId;
+      }
+   }
+   
+   return CSR_SESSION_ID_INVALID;
+}
+
+
+/* SessionID is HDD session id, not SME sessionId*/
+eHalStatus p2pCloseSession(tHalHandle hHal, tANI_U8 SessionID)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tp2pContext *pContext = &pMac->p2pContext[SessionID];
+
+   pContext->SMEsessionId = CSR_SESSION_ID_INVALID;
+   p2pResetContext(pContext);
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+
+eHalStatus p2pSetSessionId(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 SmeSessionId)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   pMac->p2pContext[SessionID].sessionId = SessionID;
+   pMac->p2pContext[SessionID].SMEsessionId = SmeSessionId;
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+static tANI_BOOLEAN p2pIsGOportEnabled(tpAniSirGlobal pMac)
+{
+
+   tANI_U8 num_session = 0;
+
+   for (num_session = 0; num_session < MAX_NO_OF_P2P_SESSIONS ; num_session++)
+   {
+      if (pMac->p2pContext[num_session].operatingmode == OPERATION_MODE_P2P_GROUP_OWNER)
+      {
+         return eANI_BOOLEAN_TRUE;
+      }
+   }
+
+   return eANI_BOOLEAN_FALSE;
+}
+
+tANI_BOOLEAN p2pIsOperatingChannEqualListenChann(tHalHandle hHal, tANI_U8 SessionID)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   if(pMac->p2pContext[SessionID].P2POperatingChannel == pMac->p2pContext[SessionID].P2PListenChannel)
+   {
+      return eANI_BOOLEAN_TRUE;
+   }
+
+   return eANI_BOOLEAN_FALSE;
+}
+
+eHalStatus p2pGetListenChannel(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 *channel)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   *channel = pMac->p2pContext[SessionID].P2PListenChannel;
+  
+   return eHAL_STATUS_SUCCESS;
+}
+
+eHalStatus p2pSetListenChannel(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 channel)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tP2P_OperatingChannel p2pListenChannel;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+
+   if(csrRoamIsChannelValid(pMac, channel))
+   {
+      pMac->p2pContext[SessionID].P2PListenChannel = channel;
+      p2pGetListenChannelAttrib(pMac, pMac->p2pContext[SessionID].sessionId, &p2pListenChannel);
+      p2pListenChannel.channel = channel;
+      p2pUpdateListenChannelAttrib(pMac, pMac->p2pContext[SessionID].sessionId, &p2pListenChannel);
+   }
+   else
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+         " %s fail with invalid channel %d", __FUNCTION__, channel);
+      status = eHAL_STATUS_INVALID_PARAMETER;
+   }
+  
+   return status;
+}
+
+
+
+eHalStatus p2pStopDiscovery(tHalHandle hHal, tANI_U8 SessionID)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+
+   status = palTimerStop(pMac->hHdd, pMac->p2pContext[SessionID].discoverTimer);
+   if (status != eHAL_STATUS_SUCCESS)
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s Timer Stop status %d\n",  __FUNCTION__, status);
+      return status;
+   }
+
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Timer Stop status %d\n",  __FUNCTION__, status);
+   p2pCallDiscoverCallback(&pMac->p2pContext[SessionID],  eP2P_DIRECTED_DISCOVER);
+
+   status = p2pFsm( &pMac->p2pContext[SessionID], eP2P_TRIGGER_DISCONNECTED );
+
+   return status;
+}
+
+//Purge P2P device/GO from the list
+eHalStatus p2pPurgeDeviceList(tpAniSirGlobal pMac, tDblLinkList *pList)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tListElem *pEntry, *pNext;
+   tCsrScanResult *pBssResult;
+   tDot11fBeaconIEs *pIes;
+    
+   csrLLLock(pList);
+   
+   pEntry = csrLLPeekHead(pList, LL_ACCESS_NOLOCK);
+   while( NULL != pEntry )
+   {
+      pNext = csrLLNext(pList, pEntry, LL_ACCESS_NOLOCK);
+      pBssResult = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
+      pIes = NULL;
+      if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, &pBssResult->Result.BssDescriptor, &pIes)))
+      {
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+            " %s fail to parse IEs. pEntry (0x%X)",
+            __FUNCTION__, pEntry);
+         pEntry = pNext;
+         continue;
+      }
+      if( pIes->P2PBeaconProbeRes.present )
+      {
+         //Found a P2P BSS
+         if(csrLLRemoveEntry(pList, pEntry, LL_ACCESS_NOLOCK) )
+         {
+            csrFreeScanResultEntry( pMac, pBssResult );
+         }
+      }
+      palFreeMemory(pMac->hHdd, pIes);
+      pEntry = pNext;
+   }
+
+   csrLLUnlock(pList);
+
+   return (status);
+}
+
+
+eHalStatus sme_p2pFlushDeviceList(tHalHandle hHal, tANI_U8 HDDSessionId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   smsLog(pMac, LOG2, FL("enter"));
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      status = p2pPurgeDeviceList(pMac, &pMac->scan.scanResultList);
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+
+eHalStatus sme_p2pResetSession(tHalHandle hHal, tANI_U8 HDDSessionId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   smsLog(pMac, LOG2, FL("enter"));
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if(MAX_NO_OF_P2P_SESSIONS > HDDSessionId)
+      {
+         p2pResetContext(&pMac->p2pContext[HDDSessionId]);
+         status = eHAL_STATUS_SUCCESS;
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+
+
+eHalStatus sme_p2pGetResultFilter(tHalHandle hHal, tANI_U8 HDDSessionId,
+                              tCsrScanResultFilter *pFilter)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if(MAX_NO_OF_P2P_SESSIONS > HDDSessionId)
+      {
+         status = p2pGetResultFilter(&pMac->p2pContext[HDDSessionId], pFilter);
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return status;
+}
+
+
+
+#endif //WLAN_FEATURE_P2P_INTERNAL
+
+eHalStatus p2pProcessNoAReq(tpAniSirGlobal pMac, tSmeCmd *pNoACmd)
+{
+    tpP2pPsConfig pNoA;
+    tSirMsgQ msg;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    status = palAllocateMemory(pMac->hHdd, (void**)&pNoA, sizeof(tP2pPsConfig));
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, pNoA, sizeof(tP2pPsConfig));
+        pNoA->opp_ps = pNoACmd->u.NoACmd.NoA.opp_ps;
+        pNoA->ctWindow = pNoACmd->u.NoACmd.NoA.ctWindow;
+        pNoA->duration = pNoACmd->u.NoACmd.NoA.duration;
+        pNoA->interval = pNoACmd->u.NoACmd.NoA.interval;
+        pNoA->count = pNoACmd->u.NoACmd.NoA.count;
+        pNoA->single_noa_duration = pNoACmd->u.NoACmd.NoA.single_noa_duration;
+        pNoA->psSelection = pNoACmd->u.NoACmd.NoA.psSelection;
+        pNoA->sessionid = pNoACmd->u.NoACmd.NoA.sessionid;
+        msg.type = eWNI_SME_UPDATE_NOA;
+        msg.bodyval = 0;
+        msg.bodyptr = pNoA;
+        limPostMsgApi(pMac, &msg);
+    }   
+    return status;
+}
+
+
+
+
+#endif //WLAN_FEATURE_P2P
diff --git a/CORE/SME/src/pmc/pmc.c b/CORE/SME/src/pmc/pmc.c
new file mode 100644
index 0000000..5afc0db
--- /dev/null
+++ b/CORE/SME/src/pmc/pmc.c
@@ -0,0 +1,2588 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/******************************************************************************
+*
+* Name:  pmc.c
+*
+* Description: 
+      Power Management Control (PMC) processing routines.
+*
+* Copyright 2008 (c) Qualcomm, Incorporated. All Rights Reserved.
+*     Qualcomm Confidential and Proprietary.
+*
+*
+******************************************************************************/
+
+#include "palTypes.h"
+#include "aniGlobal.h"
+#include "csrLinkList.h"
+#include "csrApi.h"
+#include "smeInside.h"
+#include "sme_Api.h"
+#include "smsDebug.h"
+#include "pmc.h"
+#include "wlan_ps_wow_diag.h"
+#include <vos_power.h>
+#include "csrInsideApi.h"
+
+static void pmcProcessDeferredMsg( tpAniSirGlobal pMac );
+
+/******************************************************************************
+*
+* Name:  pmcEnterLowPowerState
+*
+* Description:
+*    Have the device enter Low Power State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterLowPowerState (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcEnterLowPowerState\n"));
+
+    /* If already in Low Power State, just return. */
+    if (pMac->pmc.pmcState == LOW_POWER)
+        return eHAL_STATUS_SUCCESS;
+
+    /* Cancel any running timers. */
+    if (palTimerStop(pMac->hHdd, pMac->pmc.hImpsTimer) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot cancel IMPS timer\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    pmcStopTrafficTimer(hHal);
+
+    if (palTimerStop(pMac->hHdd, pMac->pmc.hExitPowerSaveTimer) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot cancel exit power save mode timer\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Do all the callbacks. */
+    pmcDoCallbacks(hHal, eHAL_STATUS_FAILURE);
+
+    /* Change state. */
+    pMac->pmc.pmcState = LOW_POWER;
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcExitLowPowerState
+*
+* Description:
+*    Have the device exit the Low Power State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcExitLowPowerState (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcExitLowPowerState\n"));
+
+    /* Must be in Low Power State if we are going to exit that state. */
+    if (pMac->pmc.pmcState != LOW_POWER)
+    {
+        smsLog(pMac, LOGE, FL("Cannot exit Low Power State if not in that state\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Both WLAN switches much be on to exit Low Power State. */
+    if ((pMac->pmc.hwWlanSwitchState == ePMC_SWITCH_OFF) || (pMac->pmc.swWlanSwitchState == ePMC_SWITCH_OFF))
+        return eHAL_STATUS_SUCCESS;
+
+    /* Change state. */
+    pMac->pmc.pmcState = FULL_POWER;
+    if(pmcShouldBmpsTimerRun(pMac))
+    {
+        if (pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod) != eHAL_STATUS_SUCCESS)
+            return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcEnterFullPowerState
+*
+* Description:
+*    Have the device enter the Full Power State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterFullPowerState (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcEnterFullPowerState\n"));
+
+    /* Take action based on the current state. */
+    switch (pMac->pmc.pmcState)
+    {
+
+    /* Already in Full Power State. */
+    case FULL_POWER:
+        break;
+
+    /* Notify everyone that we are going to full power.
+       Change to Full Power State. */
+    case REQUEST_FULL_POWER:
+    case REQUEST_IMPS:
+    case REQUEST_BMPS:
+    case REQUEST_STANDBY:
+
+        /* Change state. */
+        pMac->pmc.pmcState = FULL_POWER;
+        pMac->pmc.requestFullPowerPending = FALSE;
+
+        if(pmcShouldBmpsTimerRun(pMac))
+            (void)pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+
+        pmcProcessDeferredMsg( pMac );
+        /* Do all the callbacks. */
+        pmcDoCallbacks(hHal, eHAL_STATUS_SUCCESS);
+
+        /* Update registerd modules that we are entering Full Power. This is
+           only way to inform modules if PMC exited a power save mode because
+           of error conditions or if som other module requested full power */
+        pmcDoDeviceStateUpdateCallbacks(hHal, FULL_POWER);
+        break;
+
+    /* Cannot go directly to Full Power State from these states. */
+    default:
+        smsLog(pMac, LOGE, FL("Trying to enter Full Power State from state %d\n"), pMac->pmc.pmcState);
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    smsLog(pMac, LOGW, "PMC: Enter full power done: Cancel XO Core ON vote\n");
+    if (vos_chipVoteXOCore(NULL, NULL, NULL, VOS_FALSE) != VOS_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, "Could not cancel XO Core ON vote. Not returning failure. "
+                                "Power consumed will be high\n");
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcEnterRequestFullPowerState
+*
+* Description:
+*    Have the device enter the Request Full Power State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    fullPowerReason - Reason code for requesting full power
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterRequestFullPowerState (tHalHandle hHal, tRequestFullPowerReason fullPowerReason)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    vos_call_status_type callType;
+    VOS_STATUS status;
+
+    smsLog(pMac, LOG2, FL("Entering pmcEnterRequestFullPowerState\n"));
+
+    /* Take action based on the current state of the device. */
+    switch (pMac->pmc.pmcState)
+    {
+
+    /* Should not request full power if already there. */
+    case FULL_POWER:
+        smsLog(pMac, LOGE, FL("Requesting Full Power State when already there\n"));
+        return eHAL_STATUS_FAILURE;
+
+    /* Only power events can take device out of Low Power State. */
+    case LOW_POWER:
+        smsLog(pMac, LOGE, FL("Cannot request exit from Low Power State\n"));
+        return eHAL_STATUS_FAILURE;
+
+    /* Cannot go directly to Request Full Power state from these states.
+       Record that this is pending and take care of it later. */
+    case REQUEST_IMPS:
+    case REQUEST_START_UAPSD:
+    case REQUEST_STOP_UAPSD:
+    case REQUEST_STANDBY:
+    case REQUEST_BMPS:
+    case REQUEST_ENTER_WOWL:
+    case REQUEST_EXIT_WOWL:
+        smsLog(pMac, LOGW, FL("Request for full power is being buffered. "
+            "Current state is %d\n"), pMac->pmc.pmcState);
+        //Ignore the new reason if request for full power is already pending
+        if( !pMac->pmc.requestFullPowerPending )
+        {
+            pMac->pmc.requestFullPowerPending = TRUE;
+            pMac->pmc.requestFullPowerReason = fullPowerReason;
+        }
+        return eHAL_STATUS_SUCCESS;
+
+    /* Tell MAC to have device enter full power mode. */
+    case IMPS:
+        if ( pMac->pmc.rfSuppliesVotedOff )
+        {
+            status = vos_chipVoteOnRFSupply(&callType, NULL, NULL);
+            VOS_ASSERT( VOS_IS_STATUS_SUCCESS( status ) );
+
+            status = vos_chipVoteOnXOBuffer(&callType, NULL, NULL);
+            VOS_ASSERT( VOS_IS_STATUS_SUCCESS( status ) );
+
+            pMac->pmc.rfSuppliesVotedOff = FALSE;
+        }
+
+        if (pmcIssueCommand( pMac, eSmeCommandExitImps, NULL, 0, FALSE ) != eHAL_STATUS_SUCCESS)
+        {
+            return eHAL_STATUS_FAILURE;
+        }
+        return eHAL_STATUS_SUCCESS;
+
+    /* Tell MAC to have device enter full power mode. */
+    case BMPS:
+    {
+        tExitBmpsInfo exitBmpsInfo;
+        exitBmpsInfo.exitBmpsReason = fullPowerReason;
+
+        if (pmcIssueCommand(hHal, eSmeCommandExitBmps, &exitBmpsInfo, sizeof(tExitBmpsInfo), FALSE)
+               != eHAL_STATUS_SUCCESS)
+        {
+            return eHAL_STATUS_FAILURE;
+        }
+        return eHAL_STATUS_SUCCESS;
+    }
+    /* Already in Request Full Power State. */
+    case REQUEST_FULL_POWER:
+        return eHAL_STATUS_SUCCESS;
+
+    /* Tell MAC to have device enter full power mode. */
+    case STANDBY:
+        if ( pMac->pmc.rfSuppliesVotedOff )
+        {
+            status = vos_chipVoteOnXOBuffer(&callType, NULL, NULL);
+            if(VOS_STATUS_SUCCESS != status)
+            {
+                return eHAL_STATUS_FAILURE;
+            }
+            status = vos_chipVoteOnRFSupply(&callType, NULL, NULL);
+            if(VOS_STATUS_SUCCESS != status)
+            {
+                return eHAL_STATUS_FAILURE;
+            }
+
+            pMac->pmc.rfSuppliesVotedOff = FALSE;
+        }
+
+        if (pmcIssueCommand(hHal, eSmeCommandExitImps, NULL, 0, FALSE) !=
+            eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, "PMC: failure to send message "
+            "eWNI_PMC_EXIT_IMPS_REQ\n");
+            return eHAL_STATUS_FAILURE;
+        }
+        
+        return eHAL_STATUS_SUCCESS;
+
+    /* Tell MAC to have device exit UAPSD mode first */
+    case UAPSD:
+        //Need to save the reason code here in case later on we need to exit BMPS as well
+        if (pmcIssueCommand(hHal, eSmeCommandExitUapsd, &fullPowerReason, sizeof(tRequestFullPowerReason), FALSE) !=
+            eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, "PMC: failure to send message "
+            "eWNI_PMC_EXIT_UAPSD_REQ\n");
+            return eHAL_STATUS_FAILURE;
+        }
+        return eHAL_STATUS_SUCCESS;
+
+    /* Tell MAC to have device exit WOWL mode first */
+    case WOWL:
+        if (pmcIssueCommand(hHal, eSmeCommandExitWowl, &fullPowerReason, sizeof(tRequestFullPowerReason), FALSE) !=
+            eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGP, "PMC: failure to send message "
+            "eWNI_PMC_EXIT_WOWL_REQ\n");
+            return eHAL_STATUS_FAILURE;
+        }
+        return eHAL_STATUS_SUCCESS;
+
+    /* Cannot go directly to Request Full Power State from these states. */
+    default:
+        smsLog(pMac, LOGE, FL("Trying to enter Request Full Power State from state %d\n"), pMac->pmc.pmcState);
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcEnterRequestImpsState
+*
+* Description:
+*    Have the device enter the Request IMPS State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterRequestImpsState (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcEnterRequestImpsState\n"));
+
+    /* Can enter Request IMPS State only from Full Power State. */
+    if (pMac->pmc.pmcState != FULL_POWER)
+    {
+        smsLog(pMac, LOGE, FL("Trying to enter Request IMPS State from state %d\n"), pMac->pmc.pmcState);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Make sure traffic timer that triggers bmps entry is not running */
+    pmcStopTrafficTimer(hHal);
+
+    /* Tell MAC to have device enter IMPS mode. */
+    if (pmcIssueCommand(hHal, eSmeCommandEnterImps, NULL, 0, FALSE) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, "PMC: failure to send message eWNI_PMC_ENTER_IMPS_REQ\n");
+        pMac->pmc.pmcState = FULL_POWER;
+        if(pmcShouldBmpsTimerRun(pMac))
+            (void)pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+        return eHAL_STATUS_FAILURE;
+     }
+
+    smsLog(pMac, LOGW, FL("eWNI_PMC_ENTER_IMPS_REQ sent to PE\n"));
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcEnterImpsState
+*
+* Description:
+*    Have the device enter the IMPS State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterImpsState (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    vos_call_status_type callType;
+    VOS_STATUS status;
+    smsLog(pMac, LOG2, FL("Entering pmcEnterImpsState\n"));
+
+    /* Can enter IMPS State only from Request IMPS State. */
+    if (pMac->pmc.pmcState != REQUEST_IMPS)
+    {
+        smsLog(pMac, LOGE, FL("Trying to enter IMPS State from state %d\n"), pMac->pmc.pmcState);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Change state. */
+    pMac->pmc.pmcState = IMPS;
+
+    /* If we have a reqeust for full power pending then we have to go
+       directly into full power. */
+    if (pMac->pmc.requestFullPowerPending)
+    {
+
+#if defined(ANI_OS_TYPE_WINDOWS) && !defined(GEN6_ONWARDS)
+        /* In Windows we cannot do this now since we are in DPC context and the message to the
+           SoftMAC to put the device into IMPS will be sent at the end of DPC processing.  Instead
+           we set a short timer and start the IMPS exit sequence when the timer fires. */
+        if (palTimerStart(pMac->hHdd, pMac->pmc.hExitPowerSaveTimer, 1000, FALSE) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot start exit power save mode timer\n"));
+            PMC_ABORT;
+            return eHAL_STATUS_FAILURE;
+        }
+        return eHAL_STATUS_SUCCESS;
+
+#else
+        /* Start exit IMPS sequence now. */
+        return pmcEnterRequestFullPowerState(hHal, pMac->pmc.requestFullPowerReason);
+#endif
+    }
+
+    /* Set timer to come out of IMPS.only if impsPeriod is non-Zero*/
+    if(0 != pMac->pmc.impsPeriod)
+    {
+        if (palTimerStart(pMac->hHdd, pMac->pmc.hImpsTimer, pMac->pmc.impsPeriod * 1000, FALSE) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot start IMPS timer\n"));
+            PMC_ABORT;
+            pmcEnterRequestFullPowerState(hHal, eSME_REASON_OTHER);
+            return eHAL_STATUS_FAILURE;
+        }
+    }
+
+    //Vote off RF supplies. Note RF supllies are not voted off if there is a 
+    //pending request for full power already
+    status = vos_chipVoteOffRFSupply(&callType, NULL, NULL);
+    VOS_ASSERT( VOS_IS_STATUS_SUCCESS( status ) );
+
+    status = vos_chipVoteOffXOBuffer(&callType, NULL, NULL);
+    VOS_ASSERT( VOS_IS_STATUS_SUCCESS( status ) );
+
+    pMac->pmc.rfSuppliesVotedOff= TRUE;
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcEnterRequestBmpsState
+*
+* Description:
+*    Have the device enter the Request BMPS State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterRequestBmpsState (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    
+    smsLog(pMac, LOG2, FL("Entering pmcEnterRequestBmpsState\n"));
+
+    /* Can enter Request BMPS State only from Full Power State. */
+    if (pMac->pmc.pmcState != FULL_POWER)
+    {
+        smsLog(pMac, LOGE, FL("Trying to enter Request BMPS State from state %d\n"), pMac->pmc.pmcState);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Stop Traffic timer if running. Note: timer could have expired because of possible
+       race conditions. So no need to check for errors. Just make sure timer is not running */
+    pmcStopTrafficTimer(hHal);
+
+    /* Tell MAC to have device enter BMPS mode. */
+    if ( !pMac->pmc.bmpsRequestQueued )
+    {
+        pMac->pmc.bmpsRequestQueued = eANI_BOOLEAN_TRUE;
+        if(pmcIssueCommand(hHal, eSmeCommandEnterBmps, NULL, 0, FALSE) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, "PMC: failure to send message eWNI_PMC_ENTER_BMPS_REQ\n");
+            pMac->pmc.bmpsRequestQueued = eANI_BOOLEAN_FALSE;
+            pMac->pmc.pmcState = FULL_POWER;
+            if(pmcShouldBmpsTimerRun(pMac))
+            {
+                (void)pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+            }
+            return eHAL_STATUS_FAILURE;
+        }
+    }
+    else
+    {
+        smsLog(pMac, LOGE, "PMC: enter BMPS command already queued\n");
+        //restart the timer if needed
+        if(pmcShouldBmpsTimerRun(pMac))
+        {
+            (void)pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+        }
+        return eHAL_STATUS_SUCCESS;
+    }
+
+    smsLog(pMac, LOGW, FL("eWNI_PMC_ENTER_BMPS_REQ sent to PE\n"));
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcEnterBmpsState
+*
+* Description:
+*    Have the device enter the BMPS State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterBmpsState (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcEnterBmpsState\n"));
+
+    /* Can enter BMPS State only from 5 states. */
+    if (pMac->pmc.pmcState != REQUEST_BMPS &&
+        pMac->pmc.pmcState != REQUEST_START_UAPSD &&
+        pMac->pmc.pmcState != REQUEST_STOP_UAPSD &&
+        pMac->pmc.pmcState != REQUEST_ENTER_WOWL &&
+        pMac->pmc.pmcState != REQUEST_EXIT_WOWL)
+    {
+        smsLog(pMac, LOGE, FL("Trying to enter BMPS State from state %d\n"), pMac->pmc.pmcState);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Change state. */
+    pMac->pmc.pmcState = BMPS;
+
+   /* Update registerd modules that we are entering BMPS. This is
+      only way to inform modules if PMC entered BMPS power save mode
+      on its own because of traffic timer */
+    pmcDoDeviceStateUpdateCallbacks(hHal, BMPS);
+
+    /* If we have a reqeust for full power pending then we have to go directly into full power. */
+    if (pMac->pmc.requestFullPowerPending)
+    {
+
+#if defined(ANI_OS_TYPE_WINDOWS) && !defined(GEN6_ONWARDS)
+        /* In Windows, we cannot do this now since we are in DPC context and the message to the
+           SoftMAC to put the device into BMPS will be sent at the end of DPC processing.  Instead
+           we set a short timer and start the BMPS exit sequence when the timer fires. */
+        if (palTimerStart(pMac->hHdd, pMac->pmc.hExitPowerSaveTimer, 1000, FALSE) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot start exit power save mode timer\n"));
+            PMC_ABORT;
+            return eHAL_STATUS_FAILURE;
+        }
+        return eHAL_STATUS_SUCCESS;
+
+#else
+        /* Start exit BMPS sequence now. */
+        smsLog(pMac, LOGW, FL("Pending Full Power request found on entering BMPS mode. "
+                  "Start exit BMPS exit sequence\n"));
+        //Note: Reason must have been set when requestFullPowerPending flag was set.
+        pmcEnterRequestFullPowerState(hHal, pMac->pmc.requestFullPowerReason);
+        return eHAL_STATUS_SUCCESS;
+#endif
+    }
+
+    /*This should never happen ideally. WOWL and UAPSD not supported at the same time */
+    if (pMac->pmc.wowlModeRequired && pMac->pmc.uapsdSessionRequired)
+    {
+        smsLog(pMac, LOGW, FL("Both UAPSD and WOWL is required on entering BMPS mode. "
+               "UAPSD will be prioritized over WOWL\n"));
+    }
+
+    /* Do we need Uapsd?*/
+    if (pMac->pmc.uapsdSessionRequired)
+    {
+        smsLog(pMac, LOGW, FL("UAPSD session is required on entering BMPS mode. "
+                  "Start UAPSD entry sequence\n"));
+        pmcEnterRequestStartUapsdState(hHal);
+        return eHAL_STATUS_SUCCESS;
+    }
+
+    /* Do we need WOWL?*/
+    if (pMac->pmc.wowlModeRequired)
+    {
+        smsLog(pMac, LOGW, FL("WOWL is required on entering BMPS mode. "
+                  "Start WOWL entry sequence\n"));
+        pmcRequestEnterWowlState(hHal, &(pMac->pmc.wowlEnterParams));
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcPowerSaveCheck
+*
+* Description:
+*    Check if device is allowed to enter a power save mode.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    TRUE - entry is allowed
+*    FALSE - entry is not allowed at this time
+*
+******************************************************************************/
+tANI_BOOLEAN pmcPowerSaveCheck (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tListElem *pEntry;
+    tpPowerSaveCheckEntry pPowerSaveCheckEntry;
+    tANI_BOOLEAN (*checkRoutine) (void *checkContext);
+    tANI_BOOLEAN bResult=FALSE;
+
+    smsLog(pMac, LOG2, FL("Entering pmcPowerSaveCheck\n"));
+
+    /* Call the routines in the power save check routine list.  If any
+       return FALSE, then we cannot go into power save mode. */
+    pEntry = csrLLPeekHead(&pMac->pmc.powerSaveCheckList, FALSE);
+    while (pEntry != NULL)
+    {
+        pPowerSaveCheckEntry = GET_BASE_ADDR(pEntry, tPowerSaveCheckEntry, link);
+        checkRoutine = pPowerSaveCheckEntry->checkRoutine;
+
+        /* If the checkRoutine is NULL for a paricular entry, proceed with other entries
+         * in the list */
+        if (NULL != checkRoutine)
+        {
+            if (!checkRoutine(pPowerSaveCheckEntry->checkContext))
+            {
+                smsLog(pMac, LOGE, FL("pmcPowerSaveCheck fail!\n"));
+                bResult = FALSE; 
+                break;
+            }
+            else
+            {
+                bResult = TRUE;
+            }
+        }
+        pEntry = csrLLNext(&pMac->pmc.powerSaveCheckList, pEntry, FALSE);
+    }
+
+    return bResult;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcSendPowerSaveConfigMessage
+*
+* Description:
+*    Send a message to PE/MAC to configure the power saving modes.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - message successfuly sent
+*    eHAL_STATUS_FAILURE - error while sending message
+*
+******************************************************************************/
+eHalStatus pmcSendPowerSaveConfigMessage (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tSirPowerSaveCfg powerSaveConfig;
+
+    smsLog(pMac, LOG2, FL("Entering pmcSendPowerSaveConfigMessage\n"));
+    
+    palZeroMemory(pMac->hHdd, &(powerSaveConfig), sizeof(tSirPowerSaveCfg));
+
+    switch (pMac->pmc.bmpsConfig.forwardBeacons)
+    {
+    case ePMC_NO_BEACONS:
+        powerSaveConfig.beaconFwd = ePM_BEACON_FWD_NONE;
+        break;
+    case ePMC_BEACONS_WITH_TIM_SET:
+        powerSaveConfig.beaconFwd = ePM_BEACON_FWD_TIM;
+        break;
+    case ePMC_BEACONS_WITH_DTIM_SET:
+        powerSaveConfig.beaconFwd = ePM_BEACON_FWD_DTIM;
+        break;
+    case ePMC_NTH_BEACON:
+        powerSaveConfig.beaconFwd = ePM_BEACON_FWD_NTH;
+        powerSaveConfig.nthBeaconFwd = (tANI_U16)pMac->pmc.bmpsConfig.valueOfN;
+        break;
+    case ePMC_ALL_BEACONS:
+        powerSaveConfig.beaconFwd = ePM_BEACON_FWD_NTH;
+        powerSaveConfig.nthBeaconFwd = 1;
+        break;
+    }
+    powerSaveConfig.fEnablePwrSaveImmediately = pMac->pmc.bmpsConfig.setPmOnLastFrame;
+    powerSaveConfig.fPSPoll = pMac->pmc.bmpsConfig.usePsPoll;
+    powerSaveConfig.fEnableBeaconEarlyTermination = 
+        pMac->pmc.bmpsConfig.enableBeaconEarlyTermination;
+    powerSaveConfig.bcnEarlyTermWakeInterval = 
+        pMac->pmc.bmpsConfig.bcnEarlyTermWakeInterval;
+
+    /* setcfg for listenInterval. Make sure CFG is updated because PE reads this 
+       from CFG at the time of assoc or reassoc */
+    ccmCfgSetInt(pMac, WNI_CFG_LISTEN_INTERVAL, pMac->pmc.bmpsConfig.bmpsPeriod, 
+        NULL, eANI_BOOLEAN_FALSE);
+
+    if( pMac->pmc.pmcState == IMPS || pMac->pmc.pmcState == REQUEST_IMPS )
+    {
+        //Wake up the chip first
+        eHalStatus status = pmcDeferMsg( pMac, eWNI_PMC_PWR_SAVE_CFG, 
+                                    &powerSaveConfig, sizeof(tSirPowerSaveCfg) );
+
+        if( eHAL_STATUS_PMC_PENDING == status )
+        {
+            return eHAL_STATUS_SUCCESS;
+        }
+        else 
+        {
+            //either fail or already in full power
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                return ( status );
+            }
+            //else let it through because it is in full power state
+        }
+    }
+    /* Send a message so that FW System config is also updated and is in sync with
+       the CFG.*/
+    if (pmcSendMessage(hHal, eWNI_PMC_PWR_SAVE_CFG, &powerSaveConfig, sizeof(tSirPowerSaveCfg)) 
+        != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Send of eWNI_PMC_PWR_SAVE_CFG to PE failed\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+   
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcSendMessage
+*
+* Description:
+*    Send a message to PE/MAC.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    messageType - message type to send
+*    pMessageData - pointer to message data
+*    messageSize - Size of the message data
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - message successfuly sent
+*    eHAL_STATUS_FAILURE - error while sending message
+*
+******************************************************************************/
+eHalStatus pmcSendMessage (tpAniSirGlobal pMac, tANI_U16 messageType, void *pMessageData, tANI_U32 messageSize)
+{
+    tSirMbMsg *pMsg;
+
+    smsLog(pMac, LOG2, FL("Entering pmcSendMessage, message type %d\n"), messageType);
+
+    /* Allocate and fill in message. */
+    if (palAllocateMemory(pMac->hHdd, (void **)&pMsg, WNI_CFG_MB_HDR_LEN + messageSize) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot allocate memory for message\n"));
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+    pMsg->type = messageType;
+    pMsg->msgLen = (tANI_U16) (WNI_CFG_MB_HDR_LEN + messageSize);
+    if (messageSize > 0)
+    {
+        if (palCopyMemory(pMac->hHdd, pMsg->data, pMessageData, messageSize) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot copy message data\n"));
+            PMC_ABORT;
+            return eHAL_STATUS_FAILURE;
+        }
+    }
+
+    /* Send message. */
+    if (palSendMBMessage(pMac->hHdd, pMsg) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot send message\n"));
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcDoCallbacks
+*
+* Description:
+*    Call the IMPS callback routine and the routines in the request full
+*    power callback routine list.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    callbackStatus - status to pass to the callback routines
+*
+* Returns:
+*    nothing
+*
+******************************************************************************/
+void pmcDoCallbacks (tHalHandle hHal, eHalStatus callbackStatus)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tListElem *pEntry;
+    tpRequestFullPowerEntry pRequestFullPowerEntry;
+
+    smsLog(pMac, LOG2, FL("Entering pmcDoCallbacks\n"));
+
+    /* Call IMPS callback routine. */
+    if (pMac->pmc.impsCallbackRoutine != NULL)
+    {
+        pMac->pmc.impsCallbackRoutine(pMac->pmc.impsCallbackContext, callbackStatus);
+        pMac->pmc.impsCallbackRoutine = NULL;
+    }
+
+    /* Call the routines in the request full power callback routine list. */
+    while (NULL != (pEntry = csrLLRemoveHead(&pMac->pmc.requestFullPowerList, TRUE)))
+    {
+        pRequestFullPowerEntry = GET_BASE_ADDR(pEntry, tRequestFullPowerEntry, link);
+        if (pRequestFullPowerEntry->callbackRoutine)
+           pRequestFullPowerEntry->callbackRoutine(pRequestFullPowerEntry->callbackContext, callbackStatus);
+        if (palFreeMemory(pMac->hHdd, pRequestFullPowerEntry) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot free request full power routine list entry\n"));
+            PMC_ABORT;
+        }
+    }
+
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcStartTrafficTimer
+*
+* Description:
+*    Start the timer used in Full Power State to measure traffic
+*    levels and determine when to enter BMPS.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - timer successfuly started
+*    eHAL_STATUS_FAILURE - error while starting timer
+*
+******************************************************************************/
+eHalStatus pmcStartTrafficTimer (tHalHandle hHal, tANI_U32 expirationTime)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    VOS_STATUS vosStatus;
+
+    smsLog(pMac, LOG2, FL("Entering pmcStartTrafficTimer\n"));
+
+    vosStatus = vos_timer_start(&pMac->pmc.hTrafficTimer, expirationTime);
+    if ( !VOS_IS_STATUS_SUCCESS(vosStatus) )
+    {
+        if( VOS_STATUS_E_ALREADY == vosStatus )
+        {
+            //Consider this ok since the timer is already started.
+            smsLog(pMac, LOGW, FL("  traffic timer is already started\n"));
+        }
+        else
+        {
+            smsLog(pMac, LOGP, FL("Cannot start traffic timer\n"));
+            return eHAL_STATUS_FAILURE;
+        }
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcStopTrafficTimer
+*
+* Description:
+*    Cancels the timer (if running) used in Full Power State to measure traffic
+*    levels and determine when to enter BMPS.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+*
+******************************************************************************/
+void pmcStopTrafficTimer (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    smsLog(pMac, LOG2, FL("Entering pmcStopTrafficTimer\n"));
+    vos_timer_stop(&pMac->pmc.hTrafficTimer);
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcImpsTimerExpired
+*
+* Description:
+*    Called when IMPS timer expires.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    nothing
+*
+******************************************************************************/
+void pmcImpsTimerExpired (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcImpsTimerExpired\n"));
+
+    /* If timer expires and we are in a state other than IMPS State then something is wrong. */
+    if (pMac->pmc.pmcState != IMPS)
+    {
+        smsLog(pMac, LOGE, FL("Got IMPS timer expiration in state %d\n"), pMac->pmc.pmcState);
+        PMC_ABORT;
+        return;
+    }
+
+    /* Start on the path of going back to full power. */
+    pmcEnterRequestFullPowerState(hHal, eSME_REASON_OTHER);
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcTrafficTimerExpired
+*
+* Description:
+*    Called when traffic measurement timer expires.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    nothing
+*
+******************************************************************************/
+void pmcTrafficTimerExpired (tHalHandle hHal)
+{
+
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    VOS_STATUS vosStatus;
+
+    smsLog(pMac, LOGW, FL("BMPS Traffic timer expired"));
+
+    /* If timer expires and we are in a state other than Full Power State then something is wrong. */
+    if (pMac->pmc.pmcState != FULL_POWER)
+    {
+        smsLog(pMac, LOGE, FL("Got traffic timer expiration in state %d"), pMac->pmc.pmcState);
+        return;
+    }
+
+    /* Untill DHCP is not completed remain in power active */
+    if(pMac->pmc.remainInPowerActiveTillDHCP)
+    {
+        smsLog(pMac, LOGE, FL("BMPS Traffic Timer expired before DHCP completion ignore enter BMPS\n"));
+        pMac->pmc.remainInPowerActiveThreshold++;
+        if( pMac->pmc.remainInPowerActiveThreshold >= DHCP_REMAIN_POWER_ACTIVE_THRESHOLD)
+        {
+           smsLog(pMac, LOGE, FL("Remain in power active DHCP threshold reached FALLBACK to enable enter BMPS\n"));
+           /*FALLBACK: reset the flag to make BMPS entry possible*/
+           pMac->pmc.remainInPowerActiveTillDHCP = FALSE;
+           pMac->pmc.remainInPowerActiveThreshold = 0;
+        }
+        //Activate the Traffic Timer again for entering into BMPS
+        vosStatus = vos_timer_start(&pMac->pmc.hTrafficTimer, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+        if ( !VOS_IS_STATUS_SUCCESS(vosStatus) && (VOS_STATUS_E_ALREADY != vosStatus) )
+        {
+            smsLog(pMac, LOGP, FL("Cannot re-start traffic timer\n"));
+        }
+        return;
+    }
+
+    /* Clear remain in power active threshold */
+    pMac->pmc.remainInPowerActiveThreshold = 0;
+
+    /* Check if the timer should be running */
+    if (!pmcShouldBmpsTimerRun(pMac))
+    {
+        smsLog(pMac, LOGE, FL("BMPS timer should not be running"));
+        return;
+    }
+
+    if (pmcPowerSaveCheck(hHal)) 
+    {
+        smsLog(pMac, LOGW, FL("BMPS entry criteria satisfied. Requesting BMPS state"));
+        (void)pmcEnterRequestBmpsState(hHal);    
+    } 
+    else 
+    {
+        /*Some module voted against Power Save. So timer should be restarted again to retry BMPS */
+        smsLog(pMac, LOGE, FL("Power Save check failed. Retry BMPS again later"));
+        //Since hTrafficTimer is a vos_timer now, we need to restart the timer here
+        vosStatus = vos_timer_start(&pMac->pmc.hTrafficTimer, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+        if ( !VOS_IS_STATUS_SUCCESS(vosStatus) && (VOS_STATUS_E_ALREADY != vosStatus) )
+        {
+            smsLog(pMac, LOGP, FL("Cannot start traffic timer\n"));
+            return;
+        }
+    }
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcExitPowerSaveTimerExpired
+*
+* Description:
+*    Called when timer used to schedule a deferred power save mode exit expires.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    nothing
+*
+******************************************************************************/
+void pmcExitPowerSaveTimerExpired (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcExitPowerSaveTimerExpired\n"));
+
+    /* Make sure process of exiting power save mode might hasn't already been started due to another trigger. */
+    if (pMac->pmc.requestFullPowerPending)
+
+        /* Start on the path of going back to full power. */
+        pmcEnterRequestFullPowerState(hHal, pMac->pmc.requestFullPowerReason);
+}
+
+/******************************************************************************
+*
+* Name:  pmcDoBmpsCallbacks
+*
+* Description:
+*    Call the registered BMPS callback routines because device is unable to
+*    enter BMPS state
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    callbackStatus - Success or Failure.
+*
+* Returns:
+*    nothing
+*
+******************************************************************************/
+void pmcDoBmpsCallbacks (tHalHandle hHal, eHalStatus callbackStatus)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tListElem *pEntry;
+   tpRequestBmpsEntry pRequestBmpsEntry;
+
+   smsLog(pMac, LOG2, "PMC: entering pmcDoBmpsCallbacks\n");
+
+   /* Call the routines in the request BMPS callback routine list. */
+   pEntry = csrLLRemoveHead(&pMac->pmc.requestBmpsList, FALSE);
+   while (pEntry != NULL)
+   {
+      pRequestBmpsEntry = GET_BASE_ADDR(pEntry, tRequestBmpsEntry, link);
+      if (pRequestBmpsEntry->callbackRoutine)
+         pRequestBmpsEntry->callbackRoutine(pRequestBmpsEntry->callbackContext,
+         callbackStatus);
+      palFreeMemory(pMac->hHdd, pRequestBmpsEntry);
+      pEntry = csrLLRemoveHead(&pMac->pmc.requestBmpsList, FALSE);
+   }
+}
+
+
+
+
+/******************************************************************************
+*
+* Name:  pmcDoStartUapsdCallbacks
+*
+* Description:
+*    Call the registered UAPSD callback routines because device is unable to
+*    start UAPSD state
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    callbackStatus - Success or Failure. 
+*
+* Returns:
+*    nothing
+*
+******************************************************************************/
+void pmcDoStartUapsdCallbacks (tHalHandle hHal, eHalStatus callbackStatus)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tListElem *pEntry;
+   tpStartUapsdEntry pStartUapsdEntry;
+
+   smsLog(pMac, LOG2, "PMC: entering pmcDoStartUapsdCallbacks\n");
+
+   /* Call the routines in the request start UAPSD callback routine list. */
+   pEntry = csrLLRemoveHead(&pMac->pmc.requestStartUapsdList, FALSE);
+   while (pEntry != NULL)
+   {
+      pStartUapsdEntry = GET_BASE_ADDR(pEntry, tStartUapsdEntry, link);
+      pStartUapsdEntry->callbackRoutine(pStartUapsdEntry->callbackContext,
+         callbackStatus);
+      palFreeMemory(pMac->hHdd, pStartUapsdEntry);
+      pEntry = csrLLRemoveHead(&pMac->pmc.requestStartUapsdList, FALSE);
+   }
+}
+
+/******************************************************************************
+*
+* Name:  pmcEnterRequestStartUapsdState
+*
+* Description:
+*    Have the device enter the UAPSD State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterRequestStartUapsdState (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   v_BOOL_t fFullPower = VOS_FALSE;     //need to get back to full power state
+
+   smsLog(pMac, LOG2, "PMC: entering pmcEnterRequestStartUapsdState\n");
+
+   /* Can enter UAPSD State only from FULL_POWER or BMPS State. */
+   switch (pMac->pmc.pmcState)
+   {
+      case FULL_POWER:
+         /* Check that entry into a power save mode is allowed at this time. */
+         if (!pmcPowerSaveCheck(hHal))
+         {
+            smsLog(pMac, LOGW, "PMC: Power save check failed. UAPSD request "
+                      "will be accepted and buffered\n");
+            /* UAPSD mode will be attempted when we enter BMPS later */
+            pMac->pmc.uapsdSessionRequired = TRUE;
+            /* Make sure the BMPS retry timer is running */
+            if(pmcShouldBmpsTimerRun(pMac))
+               (void)pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+            break;
+         }
+         else
+         {
+            pMac->pmc.uapsdSessionRequired = TRUE;
+            //Check BTC state
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+            if( btcIsReadyForUapsd( pMac ) )
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+            {
+               /* Put device in BMPS mode first. This step should NEVER fail.
+                  That is why no need to buffer the UAPSD request*/
+               if(pmcEnterRequestBmpsState(hHal) != eHAL_STATUS_SUCCESS)
+               {
+                   smsLog(pMac, LOGE, "PMC: Device in Full Power. Enter Request Bmps failed. "
+                            "UAPSD request will be dropped \n");
+                  return eHAL_STATUS_FAILURE;
+               }
+            }
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+            else
+            {
+               (void)pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+            }
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+         }
+         break;
+
+      case BMPS:
+         //It is already in BMPS mode, check BTC state
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+         if( btcIsReadyForUapsd(pMac) )
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+         {
+            /* Tell MAC to have device enter UAPSD mode. */
+            if (pmcIssueCommand(hHal, eSmeCommandEnterUapsd, NULL, 0, FALSE) !=
+               eHAL_STATUS_SUCCESS)
+            {
+               smsLog(pMac, LOGE, "PMC: failure to send message "
+                  "eWNI_PMC_ENTER_BMPS_REQ\n");
+               return eHAL_STATUS_FAILURE;
+            }
+         }
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+         else
+         {
+            //Not ready for UAPSD at this time, save it first and wake up the chip
+            smsLog(pMac, LOGE, " PMC state = %d\n",pMac->pmc.pmcState);
+            pMac->pmc.uapsdSessionRequired = TRUE;
+            /* While BTC traffic is going on, STA can be in BMPS 
+             * and need not go to Full Power */
+            //fFullPower = VOS_TRUE; 
+         }
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+         break;
+
+      case REQUEST_START_UAPSD:
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+         if( !btcIsReadyForUapsd(pMac) )
+         {
+            //BTC rejects UAPSD, bring it back to full power
+            fFullPower = VOS_TRUE;
+         }
+#endif
+         break;
+
+      case REQUEST_BMPS:
+        /* Buffer request for UAPSD mode. */
+        pMac->pmc.uapsdSessionRequired = TRUE;
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+        if( !btcIsReadyForUapsd(pMac) )
+         {
+            //BTC rejects UAPSD, bring it back to full power
+            fFullPower = VOS_TRUE;
+         }
+#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+        break;
+
+      default:
+         smsLog(pMac, LOGE, "PMC: trying to enter UAPSD State from state %d\n",
+            pMac->pmc.pmcState);
+         return eHAL_STATUS_FAILURE;
+   }
+
+   if(fFullPower)
+   {
+      if( eHAL_STATUS_PMC_PENDING != pmcRequestFullPower( pMac, NULL, NULL, eSME_REASON_OTHER ) )
+      {
+         //This is an error
+         smsLog(pMac, LOGE, FL(" fail to request full power because BTC\n"));
+      }
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcEnterUapsdState
+*
+* Description:
+*    Have the device enter the UAPSD State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterUapsdState (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   smsLog(pMac, LOG2, "PMC: entering pmcEnterUapsdState\n");
+
+   /* Can enter UAPSD State only from Request UAPSD State. */
+   if (pMac->pmc.pmcState != REQUEST_START_UAPSD )
+   {
+      smsLog(pMac, LOGE, "PMC: trying to enter UAPSD State from state %d\n",
+      pMac->pmc.pmcState);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   /* Change state. */
+   pMac->pmc.pmcState = UAPSD;
+
+   /* Update registerd modules that we are entering UAPSD. This is
+      only way to inform modules if PMC resumed UAPSD power save mode
+      on its own after full power mode */
+   pmcDoDeviceStateUpdateCallbacks(hHal, UAPSD);
+   
+   /* If we have a reqeust for full power pending then we have to go
+   directly into full power. */
+   if (pMac->pmc.requestFullPowerPending)
+   {
+      /* Start exit UAPSD sequence now. */
+      return pmcEnterRequestFullPowerState(hHal, pMac->pmc.requestFullPowerReason);
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcEnterRequestStopUapsdState
+*
+* Description:
+*    Have the device Stop the UAPSD State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterRequestStopUapsdState (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   smsLog(pMac, LOG2, "PMC: entering pmcEnterRequestStopUapsdState\n");
+
+   /* If already in REQUEST_STOP_UAPSD, simply return */
+   if (pMac->pmc.pmcState == REQUEST_STOP_UAPSD)
+   {
+      return eHAL_STATUS_SUCCESS;
+   }
+
+   /* Can enter Request Stop UAPSD State only from UAPSD */
+   if (pMac->pmc.pmcState != UAPSD)
+   {
+      smsLog(pMac, LOGE, "PMC: trying to enter Request Stop UAPSD State from "
+         "state %d\n", pMac->pmc.pmcState);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   /* Tell MAC to have device exit UAPSD mode. */
+   if (pmcIssueCommand(hHal, eSmeCommandExitUapsd, NULL, 0, FALSE) !=
+      eHAL_STATUS_SUCCESS)
+   {
+      smsLog(pMac, LOGE, "PMC: failure to send message "
+         "eWNI_PMC_EXIT_UAPSD_REQ\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcEnterRequestStandbyState
+*
+* Description:
+*    Have the device enter the Request STANDBY State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterRequestStandbyState (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   smsLog(pMac, LOG2, "PMC: entering pmcEnterRequestStandbyState\n");
+
+   /* Can enter Standby State only from Full Power State. */
+   if (pMac->pmc.pmcState != FULL_POWER)
+   {
+      smsLog(pMac, LOGE, "PMC: trying to enter Standby State from "
+         "state %d\n", pMac->pmc.pmcState);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   // Stop traffic timer. Just making sure timer is not running
+   pmcStopTrafficTimer(hHal);
+
+   /* Tell MAC to have device enter STANDBY mode. We are using the same message
+      as IMPS mode to avoid code changes in layer below (PE/HAL)*/
+   if (pmcIssueCommand(hHal, eSmeCommandEnterStandby, NULL, 0, FALSE) !=
+      eHAL_STATUS_SUCCESS)
+   {
+      smsLog(pMac, LOGE, "PMC: failure to send message "
+         "eWNI_PMC_ENTER_IMPS_REQ\n");
+      pMac->pmc.pmcState = FULL_POWER;
+
+      if(pmcShouldBmpsTimerRun(pMac))
+          (void)pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+      return eHAL_STATUS_FAILURE;
+   }
+   
+   return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcEnterStandbyState
+*
+* Description:
+*    Have the device enter the STANDBY State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterStandbyState (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   vos_call_status_type callType;
+   VOS_STATUS status;
+
+   smsLog(pMac, LOG2, "PMC: entering pmcEnterStandbyState\n");
+
+   /* Can enter STANDBY State only from REQUEST_STANDBY State. */
+   if (pMac->pmc.pmcState != REQUEST_STANDBY)
+   {
+      smsLog(pMac, LOGE, "PMC: trying to enter STANDBY State from state %d\n",
+         pMac->pmc.pmcState);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   /* Change state. */
+   pMac->pmc.pmcState = STANDBY;
+
+   /* If we have a reqeust for full power pending then we have to go
+      directly into full power. */
+   if (pMac->pmc.requestFullPowerPending)
+   {
+      /* Start exit STANDBY sequence now. */
+      return pmcEnterRequestFullPowerState(hHal, pMac->pmc.requestFullPowerReason);
+   }
+
+   //Note that RF supplies are not voted off if there is already a pending request
+   //for full power
+   status = vos_chipVoteOffRFSupply(&callType, NULL, NULL);
+   VOS_ASSERT( VOS_IS_STATUS_SUCCESS( status ) );
+
+   status = vos_chipVoteOffXOBuffer(&callType, NULL, NULL);
+   VOS_ASSERT( VOS_IS_STATUS_SUCCESS( status ) );
+
+   pMac->pmc.rfSuppliesVotedOff= TRUE;
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcDoStandbyCallbacks
+*
+* Description:
+*    Call the registered Standby callback routines 
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    callbackStatus - Success or Failure.
+*
+* Returns:
+*    nothing
+*
+******************************************************************************/
+void pmcDoStandbyCallbacks (tHalHandle hHal, eHalStatus callbackStatus)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+ 
+   smsLog(pMac, LOG2, "PMC: entering pmcDoStandbyCallbacks\n");
+
+   /* Call Standby callback routine. */
+   if (pMac->pmc.standbyCallbackRoutine != NULL)
+      pMac->pmc.standbyCallbackRoutine(pMac->pmc.standbyCallbackContext, callbackStatus);
+   pMac->pmc.standbyCallbackRoutine = NULL;
+   pMac->pmc.standbyCallbackContext = NULL;
+}
+
+/******************************************************************************
+*
+* Name:  pmcGetPmcState
+*
+* Description:
+*    Return the PMC state
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    tPmcState (one of IMPS, REQUEST_IMPS, BMPS, REQUEST_BMPS etc)
+*
+******************************************************************************/
+tPmcState pmcGetPmcState (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    return pMac->pmc.pmcState; 
+}
+
+const char* pmcGetPmcStateStr(tPmcState state)
+{
+    switch(state)
+    {
+        case STOPPED:
+            return "STOPPED";
+        case FULL_POWER:
+            return "FULL_POWER";
+        case LOW_POWER:
+            return "LOW_POWER";
+        case IMPS:
+            return "IMPS";
+        case BMPS:
+            return "BMPS";
+        case UAPSD:
+            return "UAPSD";
+        case STANDBY:
+            return "STANDBY";
+        case REQUEST_IMPS:
+            return "REQUEST_IMPS";
+        case REQUEST_BMPS:
+            return "REQUEST_BMPS";
+        case REQUEST_START_UAPSD:
+            return "REQUEST_START_UAPSD";
+        case REQUEST_STOP_UAPSD:
+            return "REQUEST_STOP_UAPSD";
+        case REQUEST_FULL_POWER:
+            return "REQUEST_FULL_POWER";
+        case REQUEST_STANDBY:
+            return "REQUEST_STANDBY";
+        case REQUEST_ENTER_WOWL:
+            return "REQUEST_ENTER_WOWL";
+        case REQUEST_EXIT_WOWL:
+            return "REQUEST_EXIT_WOWL";
+        case WOWL:
+            return "WOWL";
+        default:
+            break;
+    }
+
+    return "UNKNOWN";
+}
+
+void pmcDoDeviceStateUpdateCallbacks (tHalHandle hHal, tPmcState state)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tListElem *pEntry;
+    tpDeviceStateUpdateIndEntry pDeviceStateUpdateIndEntry;
+    void (*callbackRoutine) (void *callbackContext, tPmcState pmcState);
+
+    smsLog(pMac, LOG2, FL("PMC - Update registered modules of new device "
+           "state: %s\n"), pmcGetPmcStateStr(state));
+
+    /* Call the routines in the update device state routine list. */
+    pEntry = csrLLPeekHead(&pMac->pmc.deviceStateUpdateIndList, FALSE);
+    while (pEntry != NULL)
+    {
+        pDeviceStateUpdateIndEntry = GET_BASE_ADDR(pEntry, tDeviceStateUpdateIndEntry, link);
+        callbackRoutine = pDeviceStateUpdateIndEntry->callbackRoutine;
+        callbackRoutine(pDeviceStateUpdateIndEntry->callbackContext, state);
+        pEntry = csrLLNext(&pMac->pmc.deviceStateUpdateIndList, pEntry, FALSE);
+    }
+}
+
+/******************************************************************************
+*
+* Name:  pmcRequestEnterWowlState
+*
+* Description:
+*    Have the device enter the WOWL State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - WOWL mode will be entered
+*    eHAL_STATUS_FAILURE - WOWL mode cannot be entered
+*
+******************************************************************************/
+eHalStatus pmcRequestEnterWowlState(tHalHandle hHal, tpSirSmeWowlEnterParams wowlEnterParams)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   smsLog(pMac, LOG2, "PMC: entering pmcRequestEnterWowlState\n");
+
+   switch (pMac->pmc.pmcState)
+   {
+      case FULL_POWER:
+         /* Put device in BMPS mode first. This step should NEVER fail. */
+         if(pmcEnterRequestBmpsState(hHal) != eHAL_STATUS_SUCCESS)
+         {
+            smsLog(pMac, LOGE, "PMC: Device in Full Power. pmcEnterRequestBmpsState failed. "
+                    "Cannot enter WOWL\n");
+            return eHAL_STATUS_FAILURE;
+         }
+         break;
+
+      case REQUEST_BMPS:
+         smsLog(pMac, LOGW, "PMC: BMPS transaction going on. WOWL request "
+                    "will be buffered\n");         
+         break;
+
+      case BMPS:
+      case WOWL:
+         /* Tell MAC to have device enter WOWL mode. Note: We accept WOWL request
+            when we are in WOWL mode. This allows HDD to change WOWL configuration
+            without having to exit WOWL mode */
+         if (pmcIssueCommand(hHal, eSmeCommandEnterWowl, wowlEnterParams, sizeof(tSirSmeWowlEnterParams), FALSE) !=
+            eHAL_STATUS_SUCCESS)
+         {
+            smsLog(pMac, LOGE, "PMC: failure to send message eWNI_PMC_ENTER_WOWL_REQ\n");
+            return eHAL_STATUS_FAILURE;
+         }
+         break;
+
+      case REQUEST_ENTER_WOWL:
+         //Multiple enter WOWL requests at the same time are not accepted
+         smsLog(pMac, LOGE, "PMC: Enter WOWL transaction already going on. New WOWL request "
+                    "will be rejected\n");
+         return eHAL_STATUS_FAILURE;
+
+      case REQUEST_EXIT_WOWL:
+         smsLog(pMac, LOGW, "PMC: Exit WOWL transaction going on. New WOWL request "
+                   "will be buffered\n");         
+         break;
+
+      default:
+         smsLog(pMac, LOGE, "PMC: Trying to enter WOWL State from state %s\n",
+            pmcGetPmcStateStr(pMac->pmc.pmcState));
+         return eHAL_STATUS_FAILURE;
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcEnterWowlState
+*
+* Description:
+*    Have the device enter the WOWL State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - changing state successful
+*    eHAL_STATUS_FAILURE - changing state not successful
+*
+******************************************************************************/
+eHalStatus pmcEnterWowlState (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   smsLog(pMac, LOG2, "PMC: entering pmcEnterWowlState\n");
+
+   /* Can enter WOWL State only from Request WOWL State. */
+   if (pMac->pmc.pmcState != REQUEST_ENTER_WOWL )
+   {
+      smsLog(pMac, LOGP, "PMC: trying to enter WOWL State from state %d\n",
+        pMac->pmc.pmcState);
+      return eHAL_STATUS_FAILURE;
+   }
+
+   /* Change state. */
+   pMac->pmc.pmcState = WOWL;
+
+   /* Clear the buffered command for WOWL */
+   pMac->pmc.wowlModeRequired = FALSE;
+
+   /* If we have a reqeust for full power pending then we have to go
+   directly into full power. */
+   if (pMac->pmc.requestFullPowerPending)
+   {
+      /* Start exit Wowl sequence now. */
+      return pmcEnterRequestFullPowerState(hHal, pMac->pmc.requestFullPowerReason);
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcRequestExitWowlState
+*
+* Description:
+*    Have the device exit WOWL State.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - Exit WOWL successful
+*    eHAL_STATUS_FAILURE - Exit WOWL unsuccessful
+*
+******************************************************************************/
+eHalStatus pmcRequestExitWowlState(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, "PMC: entering pmcRequestExitWowlState\n");
+
+    switch (pMac->pmc.pmcState)
+    {
+        case WOWL:
+            /* Tell MAC to have device exit WOWL mode. */
+            if (pmcIssueCommand(hHal, eSmeCommandExitWowl, NULL, 0, FALSE) !=
+                eHAL_STATUS_SUCCESS)
+            {
+                smsLog(pMac, LOGP, "PMC: failure to send message eWNI_PMC_EXIT_WOWL_REQ\n");
+                return eHAL_STATUS_FAILURE;
+            }
+            break;
+
+        case REQUEST_ENTER_WOWL:
+            smsLog(pMac, LOGP, "PMC: Rcvd exit WOWL even before enter WOWL was completed\n");
+            return eHAL_STATUS_FAILURE;   
+
+        default:
+            smsLog(pMac, LOGW, "PMC: Got exit WOWL in state %s. Nothing to do as already out of WOWL\n",
+            pmcGetPmcStateStr(pMac->pmc.pmcState));
+            break;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcDoEnterWowlCallbacks
+*
+* Description:
+*    Invoke Enter WOWL callbacks
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns: None
+*
+******************************************************************************/
+void pmcDoEnterWowlCallbacks (tHalHandle hHal, eHalStatus callbackStatus)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+ 
+   smsLog(pMac, LOG2, "PMC: entering pmcDoWowlCallbacks\n");
+
+   /* Call Wowl callback routine. */
+   if (pMac->pmc.enterWowlCallbackRoutine != NULL)
+      pMac->pmc.enterWowlCallbackRoutine(pMac->pmc.enterWowlCallbackContext, callbackStatus);
+
+   pMac->pmc.enterWowlCallbackRoutine = NULL;
+   pMac->pmc.enterWowlCallbackContext = NULL;
+}
+
+
+static void pmcProcessDeferredMsg( tpAniSirGlobal pMac )
+{
+    tPmcDeferredMsg *pDeferredMsg;
+    tListElem *pEntry;
+
+    while( NULL != ( pEntry = csrLLRemoveHead( &pMac->pmc.deferredMsgList, eANI_BOOLEAN_TRUE ) ) )
+    {
+        pDeferredMsg = GET_BASE_ADDR( pEntry, tPmcDeferredMsg, link );
+        switch (pDeferredMsg->messageType)
+        {
+        case eWNI_PMC_WOWL_ADD_BCAST_PTRN:
+            VOS_ASSERT( pDeferredMsg->size == sizeof(tSirWowlAddBcastPtrn) );
+            if (pmcSendMessage(pMac, eWNI_PMC_WOWL_ADD_BCAST_PTRN, 
+                    &pDeferredMsg->u.wowlAddPattern, sizeof(tSirWowlAddBcastPtrn))
+                    != eHAL_STATUS_SUCCESS)
+            {
+                smsLog(pMac, LOGE, FL("Send of eWNI_PMC_WOWL_ADD_BCAST_PTRN to PE failed\n"));
+            }
+            break;
+
+        case eWNI_PMC_WOWL_DEL_BCAST_PTRN:
+            VOS_ASSERT( pDeferredMsg->size == sizeof(tSirWowlDelBcastPtrn) );
+            if (pmcSendMessage(pMac, eWNI_PMC_WOWL_DEL_BCAST_PTRN, 
+                    &pDeferredMsg->u.wowlDelPattern, sizeof(tSirWowlDelBcastPtrn))
+                    != eHAL_STATUS_SUCCESS)
+            {
+                smsLog(pMac, LOGE, FL("Send of eWNI_PMC_WOWL_ADD_BCAST_PTRN to PE failed\n"));
+            }
+            break;
+
+        case eWNI_PMC_PWR_SAVE_CFG:
+            VOS_ASSERT( pDeferredMsg->size == sizeof(tSirPowerSaveCfg) );
+            if (pmcSendMessage(pMac, eWNI_PMC_PWR_SAVE_CFG, 
+                    &pDeferredMsg->u.powerSaveConfig, sizeof(tSirPowerSaveCfg)) 
+                != eHAL_STATUS_SUCCESS)
+            {
+                smsLog(pMac, LOGE, FL("Send of eWNI_PMC_PWR_SAVE_CFG to PE failed\n"));
+            }
+            break;
+
+        default:
+            smsLog(pMac, LOGE, FL("unknown message (%d)\n"), pDeferredMsg->messageType);
+            break;
+        }
+        //Need to free the memory here
+        palFreeMemory( pMac->hHdd, pDeferredMsg );
+    } //while
+}
+
+
+eHalStatus pmcDeferMsg( tpAniSirGlobal pMac, tANI_U16 messageType, void *pData, tANI_U32 size)
+{
+    tPmcDeferredMsg *pDeferredMsg;
+    eHalStatus status;
+
+    if( !HAL_STATUS_SUCCESS( palAllocateMemory( pMac->hHdd, (void **)&pDeferredMsg, sizeof(tPmcDeferredMsg) ) ) )
+    {
+        smsLog(pMac, LOGE, FL("Cannot allocate memory for callback context\n"));
+        return eHAL_STATUS_RESOURCES;
+    }
+    palZeroMemory( pMac->hHdd, pDeferredMsg, sizeof(tPmcDeferredMsg) );
+    pDeferredMsg->messageType = messageType;
+    pDeferredMsg->size = (tANI_U16)size;
+    if( pData )
+    {
+        if( !HAL_STATUS_SUCCESS( palCopyMemory( pMac->hHdd, &pDeferredMsg->u.data, 
+                                    pData, size ) ) )
+        {
+            smsLog(pMac, LOGE, FL("Cannot copy pattern for callback context\n"));
+            palFreeMemory( pMac->hHdd, pDeferredMsg );
+            return eHAL_STATUS_FAILURE;
+        }
+    }
+    csrLLInsertTail( &pMac->pmc.deferredMsgList, &pDeferredMsg->link, eANI_BOOLEAN_TRUE );
+    //No callback is needed. The messages are put into deferred queue and be processed first 
+    //when enter full power is complete.
+    status = pmcRequestFullPower( pMac, NULL, NULL, eSME_REASON_OTHER );
+    if( eHAL_STATUS_PMC_PENDING != status )
+    {
+        //either fail or already in full power
+        if( csrLLRemoveEntry( &pMac->pmc.deferredMsgList, &pDeferredMsg->link, eANI_BOOLEAN_TRUE ) )
+        {
+            palFreeMemory( pMac->hHdd, pDeferredMsg );
+        }
+        if( !HAL_STATUS_SUCCESS( status ) )
+        {
+            smsLog(pMac, LOGE, FL("failed to request full power status = %d\n"), status);
+        }
+    }
+
+    return (status);
+}
+
+void pmcReleaseCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    if(!pCommand->u.pmcCmd.fReleaseWhenDone)
+    {
+        //This is a normal command, put it back to the free lsit
+        pCommand->u.pmcCmd.size = 0;
+        smeReleaseCommand( pMac, pCommand );
+    }
+    else
+    {
+        //this is a specially allocated comamnd due to out of command buffer. free it.
+        palFreeMemory(pMac->hHdd, pCommand);
+    }
+}
+
+
+//this function is used to abort a command where the normal processing of the command
+//is terminated without going through the normal path. it is here to take care of callbacks for
+//the command, if applicable.
+void pmcAbortCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fStopping )
+{
+    if( eSmePmcCommandMask & pCommand->command )
+    {
+        if( !fStopping )
+        {
+            switch( pCommand->command )
+            {
+            case eSmeCommandEnterImps:
+                smsLog(pMac, LOGE, FL("aborting request to enter IMPS\n"));
+                pmcEnterFullPowerState(pMac);
+                break;
+
+            case eSmeCommandExitImps:
+                smsLog(pMac, LOGE, FL("aborting request to exit IMPS \n"));
+                pmcEnterFullPowerState(pMac);
+                break;
+
+            case eSmeCommandEnterBmps:
+                smsLog(pMac, LOGE, FL("aborting request to enter BMPS \n"));
+                pMac->pmc.bmpsRequestQueued = eANI_BOOLEAN_FALSE;
+                pmcEnterFullPowerState(pMac);
+                pmcDoBmpsCallbacks(pMac, eHAL_STATUS_FAILURE);
+                break;
+
+            case eSmeCommandExitBmps:
+                smsLog(pMac, LOGE, FL("aborting request to exit BMPS \n"));
+                pmcEnterFullPowerState(pMac);
+                break;
+
+            case eSmeCommandEnterUapsd:
+                smsLog(pMac, LOGE, FL("aborting request to enter UAPSD \n"));
+                //Since there is no retry for UAPSD, tell the requester here we are done with failure
+                pMac->pmc.uapsdSessionRequired = FALSE;
+                pmcDoStartUapsdCallbacks(pMac, eHAL_STATUS_FAILURE);
+                break;
+
+            case eSmeCommandExitUapsd:
+                smsLog(pMac, LOGE, FL("aborting request to exit UAPSD \n"));
+                break;
+
+            case eSmeCommandEnterWowl:
+                smsLog(pMac, LOGE, FL("aborting request to enter WOWL \n"));
+                pmcDoEnterWowlCallbacks(pMac, eHAL_STATUS_FAILURE);
+                break;
+
+            case eSmeCommandExitWowl:
+                smsLog(pMac, LOGE, FL("aborting request to exit WOWL \n"));
+                break;
+
+            case eSmeCommandEnterStandby:
+                smsLog(pMac, LOGE, FL("aborting request to enter Standby \n"));
+                pmcDoStandbyCallbacks(pMac, eHAL_STATUS_FAILURE);
+                break;
+
+            default:
+                smsLog(pMac, LOGE, FL("Request for PMC command (%d) is dropped\n"), pCommand->command);
+                break;
+            }
+        }// !stopping
+        pmcReleaseCommand( pMac, pCommand );
+    }
+}
+
+
+
+//These commands are not supposed to fail due to out of command buffer,
+//otherwise other commands are not executed and no command is released. It will be deadlock. 
+#define PMC_IS_COMMAND_CANNOT_FAIL(cmdType)\
+    ( (eSmeCommandEnterStandby == (cmdType )) ||\
+      (eSmeCommandExitImps == (cmdType )) ||\
+      (eSmeCommandExitBmps == (cmdType )) ||\
+      (eSmeCommandExitUapsd == (cmdType )) ||\
+      (eSmeCommandExitWowl == (cmdType )) )
+
+eHalStatus pmcPrepareCommand( tpAniSirGlobal pMac, eSmeCommandType cmdType, void *pvParam, 
+                            tANI_U32 size, tSmeCmd **ppCmd )
+{
+    eHalStatus status = eHAL_STATUS_RESOURCES;
+    tSmeCmd *pCommand = NULL;
+
+    VOS_ASSERT( ppCmd );
+    do
+    {
+        pCommand = smeGetCommandBuffer( pMac );
+        if ( pCommand )
+        {
+            //Make sure it will be put back to the list
+            pCommand->u.pmcCmd.fReleaseWhenDone = FALSE;
+        }
+        else
+        {
+            smsLog( pMac, LOGE, FL(" fail to get command buffer for command 0x%X curState = %d"), cmdType, pMac->pmc.pmcState );
+            //For certain PMC command, we cannot fail
+            if( PMC_IS_COMMAND_CANNOT_FAIL(cmdType) )
+            {
+                smsLog( pMac, LOGE, FL(" command 0x%X  cannot fail try allocating memory for it"), cmdType );
+                status = palAllocateMemory(pMac->hHdd, (void **)&pCommand, sizeof(tSmeCmd));
+                if(!HAL_STATUS_SUCCESS(status))
+                {
+                    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, "%s fail to allocate memory for command (0x%X)", 
+                        __FUNCTION__, cmdType);
+                    pCommand = NULL;
+                    break;
+                }
+                palZeroMemory(pMac->hHdd, pCommand, sizeof(tSmeCmd));
+                //Make sure it will be free when it is done
+                pCommand->u.pmcCmd.fReleaseWhenDone = TRUE;
+            }
+            else
+        {
+            break;
+        }
+        }
+        pCommand->command = cmdType;
+        pCommand->u.pmcCmd.size = size;
+        //Initialize the reason code here. It may be overwritten later when
+        //a particular reason is needed.
+        pCommand->u.pmcCmd.fullPowerReason = eSME_REASON_OTHER;
+        switch ( cmdType )
+        {
+        case eSmeCommandEnterImps:
+        case eSmeCommandExitImps:
+        case eSmeCommandEnterBmps:
+        case eSmeCommandEnterUapsd:
+        case eSmeCommandEnterStandby:
+            status = eHAL_STATUS_SUCCESS;
+            break;
+
+        case eSmeCommandExitUapsd:
+        case eSmeCommandExitWowl:
+            status = eHAL_STATUS_SUCCESS;
+            if( pvParam )
+            {
+                pCommand->u.pmcCmd.fullPowerReason = *( (tRequestFullPowerReason *)pvParam );
+            }
+            break;
+
+        case eSmeCommandExitBmps:
+            status = eHAL_STATUS_SUCCESS;
+            if( pvParam )
+            {
+                pCommand->u.pmcCmd.u.exitBmpsInfo = *( (tExitBmpsInfo *)pvParam );
+                pCommand->u.pmcCmd.fullPowerReason = pCommand->u.pmcCmd.u.exitBmpsInfo.exitBmpsReason;
+            }
+            else
+            {
+                smsLog( pMac, LOGE, (" exit BMPS must have a reason code\n") );
+            }
+            break;
+
+        case eSmeCommandEnterWowl:
+            status = eHAL_STATUS_SUCCESS;
+            if( pvParam )
+            {
+                pCommand->u.pmcCmd.u.enterWowlInfo = *( ( tSirSmeWowlEnterParams * )pvParam );
+            }
+            break;
+
+        default:
+            smsLog( pMac, LOGE, FL("  invalid command type %d\n"), cmdType );
+            status = eHAL_STATUS_INVALID_PARAMETER;
+            break;
+        }
+
+    } while( 0 );
+
+    if( HAL_STATUS_SUCCESS( status ) && pCommand )
+    {
+        *ppCmd = pCommand;
+    }
+    else if( pCommand )
+    {
+        pmcReleaseCommand( pMac, pCommand );
+    }
+
+    return (status);
+}
+
+
+eHalStatus pmcIssueCommand( tpAniSirGlobal pMac, eSmeCommandType cmdType, void *pvParam, 
+                            tANI_U32 size, tANI_BOOLEAN fPutToListHead )
+{
+    eHalStatus status = eHAL_STATUS_RESOURCES;
+    tSmeCmd *pCommand = NULL;
+
+    status = pmcPrepareCommand( pMac, cmdType, pvParam, size, &pCommand );
+    if( HAL_STATUS_SUCCESS( status ) && pCommand )
+    {
+        smePushCommand( pMac, pCommand, fPutToListHead );
+    }
+
+    return( status );
+}
+
+
+
+tANI_BOOLEAN pmcProcessCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tANI_BOOLEAN fRemoveCmd = eANI_BOOLEAN_TRUE;
+
+    do
+    {
+        switch ( pCommand->command )
+        {
+        case eSmeCommandEnterImps:
+            if( FULL_POWER == pMac->pmc.pmcState )
+            {
+                status = pmcEnterImpsCheck( pMac );
+                if( HAL_STATUS_SUCCESS( status ) )
+                {
+                    /* Change state. */
+                    pMac->pmc.pmcState = REQUEST_IMPS;
+                    status = pmcSendMessage(pMac, eWNI_PMC_ENTER_IMPS_REQ, NULL, 0);
+                    if( HAL_STATUS_SUCCESS( status ) )
+                    {
+                        /* If we already went back Full Power State (meaning that request did not
+                           get as far as the device) then we are not successfull. */
+                        if ( FULL_POWER != pMac->pmc.pmcState )
+                        {
+                            fRemoveCmd = eANI_BOOLEAN_FALSE;
+                        }
+                    }
+                }
+                if( !HAL_STATUS_SUCCESS( status ) )
+                {
+                    smsLog(pMac, LOGE, "PMC: failure to send message eWNI_PMC_ENTER_IMPS_REQ or pmcEnterImpsCheck failed\n");
+                    pmcEnterFullPowerState( pMac );
+                    if(pmcShouldBmpsTimerRun(pMac))
+                        (void)pmcStartTrafficTimer(pMac, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+                }
+            }//full_power
+            break;
+
+        case eSmeCommandExitImps:
+            pMac->pmc.requestFullPowerPending = FALSE;
+            if( ( IMPS == pMac->pmc.pmcState ) || ( STANDBY == pMac->pmc.pmcState ) )
+            {
+                //Check state before sending message. The state may change after that
+                if( STANDBY == pMac->pmc.pmcState )
+                {
+                    //Enable Idle scan in CSR
+                    csrScanResumeIMPS(pMac);
+                }
+
+                status = pmcSendMessage(pMac, eWNI_PMC_EXIT_IMPS_REQ, NULL, 0);
+                if ( HAL_STATUS_SUCCESS( status ) )
+                {
+                    pMac->pmc.pmcState = REQUEST_FULL_POWER;
+                    smsLog(pMac, LOGW, FL("eWNI_PMC_EXIT_IMPS_REQ sent to PE\n")); 
+                    fRemoveCmd = eANI_BOOLEAN_FALSE;
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, FL("eWNI_PMC_EXIT_IMPS_REQ fail to be sent to PE status %d\n"), status); 
+                    //Callbacks are called with success srarus, do we need to pass in real status??
+                    pmcEnterFullPowerState(pMac);
+                }
+            }
+            break;
+
+        case eSmeCommandEnterBmps:
+            if( FULL_POWER == pMac->pmc.pmcState )
+            {
+                //This function will not return success because the pmc state is not BMPS
+                status = pmcEnterBmpsCheck( pMac );
+                if( HAL_STATUS_SUCCESS( status ) )
+                {
+                    /* Change PMC state */
+                    pMac->pmc.pmcState = REQUEST_BMPS;
+                    smsLog(pMac, LOGW, "PMC: Enter BMPS req done: Force XO Core ON\n");
+                    status = vos_chipVoteXOCore(NULL, NULL, NULL, VOS_TRUE); 
+                    if ( !VOS_IS_STATUS_SUCCESS(status) )
+                    {
+                        smsLog(pMac, LOGE, "Could not turn XO Core ON. Can't go to BMPS\n");
+                    }
+                    else /* XO Core turn ON was successful */
+                    {
+                    /* Tell MAC to have device enter BMPS mode. */
+                    status = pmcSendMessage(pMac, eWNI_PMC_ENTER_BMPS_REQ, NULL, 0);
+                    if ( HAL_STATUS_SUCCESS( status ) )
+                    {
+                        fRemoveCmd = eANI_BOOLEAN_FALSE;
+                    }
+                    else
+                    {
+                        smsLog(pMac, LOGE, "Fail to send enter BMPS msg to PE\n");
+                            /* Cancel the vote for XO Core */
+                            smsLog(pMac, LOGW, "In module init: Cancel the vote for XO CORE ON "
+                                                             "since send enter bmps failed\n");
+                            if (vos_chipVoteXOCore(NULL, NULL, NULL, VOS_FALSE) != VOS_STATUS_SUCCESS)
+                            {
+                                smsLog(pMac, LOGE, "Could not cancel XO Core ON vote."
+                                                   "Not returning failure."
+                                                   "Power consumed will be high\n");
+                            }  
+                            
+                        }
+                    }
+                }
+                if( !HAL_STATUS_SUCCESS( status ) )
+                {
+                    smsLog(pMac, LOGE, "PMC: failure to send message eWNI_PMC_ENTER_BMPS_REQ status %d\n", status);
+                    pMac->pmc.bmpsRequestQueued = eANI_BOOLEAN_FALSE;
+                    pmcEnterFullPowerState(pMac);
+                    //Do not call UAPSD callback here since it may be retried
+                    pmcDoBmpsCallbacks(pMac, eHAL_STATUS_FAILURE);
+                    if(pmcShouldBmpsTimerRun(pMac))
+                        (void)pmcStartTrafficTimer(pMac, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+                }
+            }
+            break;
+
+        case eSmeCommandExitBmps:
+            if( BMPS == pMac->pmc.pmcState )
+            {
+                pMac->pmc.requestFullPowerPending = FALSE;
+
+                status = pmcSendMessage( pMac, eWNI_PMC_EXIT_BMPS_REQ, 
+                            &pCommand->u.pmcCmd.u.exitBmpsInfo, sizeof(tExitBmpsInfo) );
+                if ( HAL_STATUS_SUCCESS( status ) )
+                {
+                    pMac->pmc.pmcState = REQUEST_FULL_POWER;
+                    fRemoveCmd = eANI_BOOLEAN_FALSE;
+                    smsLog(pMac, LOGW, FL("eWNI_PMC_EXIT_BMPS_REQ sent to PE\n"));
+
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, FL("eWNI_PMC_EXIT_BMPS_REQ fail to be sent to PE status %d\n"), status);
+                    pmcEnterFullPowerState(pMac);
+                }
+            }
+            break;
+
+        case eSmeCommandEnterUapsd:
+            if( BMPS == pMac->pmc.pmcState )
+            {
+                pMac->pmc.uapsdSessionRequired = TRUE;
+                status = pmcSendMessage(pMac, eWNI_PMC_ENTER_UAPSD_REQ, NULL, 0);
+                if ( HAL_STATUS_SUCCESS( status ) )
+                {
+                    pMac->pmc.pmcState = REQUEST_START_UAPSD;
+                    fRemoveCmd = eANI_BOOLEAN_FALSE;
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, "PMC: failure to send message "
+                       "eWNI_PMC_ENTER_BMPS_REQ\n");
+                    //there is no retry for re-entering UAPSD so tell the requester we are done witgh failure.
+                    pMac->pmc.uapsdSessionRequired = FALSE;
+                    pmcDoStartUapsdCallbacks(pMac, eHAL_STATUS_FAILURE);
+                }
+            }
+            break;
+
+        case eSmeCommandExitUapsd:
+           if( UAPSD == pMac->pmc.pmcState )
+           {
+               pMac->pmc.requestFullPowerPending = FALSE;
+                /* If already in REQUEST_STOP_UAPSD, simply return */
+               if (pMac->pmc.pmcState == REQUEST_STOP_UAPSD)
+               {
+                   break;
+               }
+
+               /* Tell MAC to have device exit UAPSD mode. */
+               status = pmcSendMessage(pMac, eWNI_PMC_EXIT_UAPSD_REQ, NULL, 0);
+               if ( HAL_STATUS_SUCCESS( status ) )
+               {
+                   /* Change state. Note that device will be put in BMPS state at the
+                      end of REQUEST_STOP_UAPSD state even if response is a failure*/
+                   pMac->pmc.pmcState = REQUEST_STOP_UAPSD;
+                   pMac->pmc.requestFullPowerPending = TRUE;
+                   pMac->pmc.requestFullPowerReason = pCommand->u.pmcCmd.fullPowerReason;
+                   fRemoveCmd = eANI_BOOLEAN_FALSE;
+               }
+               else
+               {
+                   smsLog(pMac, LOGE, "PMC: failure to send message "
+                      "eWNI_PMC_EXIT_UAPSD_REQ\n");
+                   pmcEnterBmpsState(pMac);
+               }
+           }
+
+           break;
+
+        case eSmeCommandEnterWowl:
+            if( ( BMPS == pMac->pmc.pmcState ) || ( WOWL == pMac->pmc.pmcState ) )
+            {
+                status = pmcSendMessage(pMac, eWNI_PMC_ENTER_WOWL_REQ, 
+                        &pCommand->u.pmcCmd.u.enterWowlInfo, sizeof(tSirSmeWowlEnterParams));
+                if ( HAL_STATUS_SUCCESS( status ) )
+                {
+                    pMac->pmc.pmcState = REQUEST_ENTER_WOWL;
+                    fRemoveCmd = eANI_BOOLEAN_FALSE;
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, "PMC: failure to send message eWNI_PMC_ENTER_WOWL_REQ\n");
+                    pmcDoEnterWowlCallbacks(pMac, eHAL_STATUS_FAILURE);
+                }
+            }
+            else
+            {
+                fRemoveCmd = eANI_BOOLEAN_TRUE;
+            }
+            break;
+
+        case eSmeCommandExitWowl:
+            if( WOWL == pMac->pmc.pmcState )
+            {
+                pMac->pmc.requestFullPowerPending = FALSE;
+                pMac->pmc.pmcState = REQUEST_EXIT_WOWL;
+                status = pmcSendMessage(pMac, eWNI_PMC_EXIT_WOWL_REQ, NULL, 0);
+                if ( HAL_STATUS_SUCCESS( status ) )
+                {
+                    fRemoveCmd = eANI_BOOLEAN_FALSE;
+                    pMac->pmc.requestFullPowerPending = TRUE;
+                    pMac->pmc.requestFullPowerReason = pCommand->u.pmcCmd.fullPowerReason;
+                }
+                else
+                {
+                    smsLog(pMac, LOGP, "PMC: failure to send message eWNI_PMC_EXIT_WOWL_REQ\n");
+                    pmcEnterBmpsState(pMac);
+                }
+            }
+            break;
+
+        case eSmeCommandEnterStandby:
+            if( FULL_POWER == pMac->pmc.pmcState )
+            {
+               //Disallow standby if concurrent sessions are present. Note that CSR would have
+               //caused the STA to disconnect the Infra session (if not already disconnected) because of 
+               //standby request. But we are now failing the standby request because of concurrent session.
+               //So was the tearing of infra session wasteful if we were going to fail the standby request ? 
+               //Not really. This is beacuse if and when BT-AMP etc sessions are torn down we will transition
+               //to IMPS/standby and still save power.
+               if (csrIsIBSSStarted(pMac) || csrIsBTAMPStarted(pMac))
+               {
+                  VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, 
+                      "WLAN: IBSS or BT-AMP session present. Cannot honor standby request");
+
+                  pmcDoStandbyCallbacks(pMac, eHAL_STATUS_PMC_NOT_NOW);
+                  if(pmcShouldBmpsTimerRun(pMac))
+                      (void)pmcStartTrafficTimer(pMac, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+                  break;
+               }
+ 
+                // Stop traffic timer. Just making sure timer is not running
+                pmcStopTrafficTimer(pMac);
+
+                /* Change state. */
+                pMac->pmc.pmcState = REQUEST_STANDBY;
+
+                /* Tell MAC to have device enter STANDBY mode. We are using the same message
+                  as IMPS mode to avoid code changes in layer below (PE/HAL)*/
+                status = pmcSendMessage(pMac, eWNI_PMC_ENTER_IMPS_REQ, NULL, 0);
+                if ( HAL_STATUS_SUCCESS( status ) )
+                {
+                    //Disable Idle scan in CSR
+                    csrScanSuspendIMPS(pMac);
+                    fRemoveCmd = eANI_BOOLEAN_FALSE;
+                }
+                else
+                {
+                    smsLog(pMac, LOGE, "PMC: failure to send message "
+                        "eWNI_PMC_ENTER_IMPS_REQ\n");
+                    pmcEnterFullPowerState(pMac);
+                    pmcDoStandbyCallbacks(pMac, eHAL_STATUS_FAILURE);
+                    /* Start the timer only if Auto BMPS feature is enabled or an UAPSD session is
+                     required */
+                    if(pmcShouldBmpsTimerRun(pMac))
+                        (void)pmcStartTrafficTimer(pMac, pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+                }
+            }
+            break;
+
+        default:
+            smsLog( pMac, LOGE, FL("  invalid command type %d\n"), pCommand->command );
+            break;
+        }
+
+    } while( 0 );
+
+    return( fRemoveCmd );
+}
+
+eHalStatus pmcEnterImpsCheck( tpAniSirGlobal pMac )
+{
+
+    if( !PMC_IS_READY(pMac) )
+    {
+        smsLog(pMac, LOGE, FL("Requesting IMPS when PMC not ready\n"));
+        smsLog(pMac, LOGE, FL("pmcReady = %d pmcState = %s\n"), 
+            pMac->pmc.pmcReady, pmcGetPmcStateStr(pMac->pmc.pmcState));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Check if IMPS is enabled. */
+    if (!pMac->pmc.impsEnabled)
+    {
+        smsLog(pMac, LOG2, FL("IMPS is disabled\n"));
+        return eHAL_STATUS_PMC_DISABLED;
+    }
+
+    /* Check if IMPS enabled for current power source. */
+    if ((pMac->pmc.powerSource == AC_POWER) && !pMac->pmc.impsConfig.enterOnAc)
+    {
+        smsLog(pMac, LOG2, FL("IMPS is disabled when operating on AC power\n"));
+        return eHAL_STATUS_PMC_AC_POWER;
+    }
+
+    /* Check that entry into a power save mode is allowed at this time. */
+    if (!pmcPowerSaveCheck(pMac))
+    {
+        smsLog(pMac, LOG2, FL("IMPS cannot be entered now\n"));
+        return eHAL_STATUS_PMC_NOT_NOW;
+    }
+
+    /* Check that entry into a power save mode is allowed at this time if all
+       running sessions agree. */
+    if (!pmcAllowImps(pMac))
+    {
+        smsLog(pMac, LOG2, FL("IMPS cannot be entered now\n"));
+        return eHAL_STATUS_PMC_NOT_NOW;
+    }
+    
+    /* Check if already in IMPS. */
+    if ((pMac->pmc.pmcState == REQUEST_IMPS) || (pMac->pmc.pmcState == IMPS) ||
+        (pMac->pmc.pmcState == REQUEST_FULL_POWER))
+    {
+        smsLog(pMac, LOG2, FL("Already in IMPS\n"));
+        return eHAL_STATUS_PMC_ALREADY_IN_IMPS;
+    }
+
+    return ( eHAL_STATUS_SUCCESS );
+}
+
+/* This API detrmines if it is ok to proceed with a Enter BMPS Request or not . Note when
+   device is in BMPS/UAPSD states, this API returns failure because it is not ok to issue
+   a BMPS request */
+eHalStatus pmcEnterBmpsCheck( tpAniSirGlobal pMac )
+{
+
+   /* Check if BMPS is enabled. */
+   if (!pMac->pmc.bmpsEnabled)
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot initiate BMPS. BMPS is disabled\n");
+      return eHAL_STATUS_PMC_DISABLED;
+   }
+
+   if( !PMC_IS_READY(pMac) )
+   {
+       smsLog(pMac, LOGE, FL("Requesting BMPS when PMC not ready\n"));
+       smsLog(pMac, LOGE, FL("pmcReady = %d pmcState = %s\n"), 
+           pMac->pmc.pmcReady, pmcGetPmcStateStr(pMac->pmc.pmcState));
+       return eHAL_STATUS_FAILURE;
+   }
+
+   /* Check that we are associated with a single active session. */
+   if (!pmcValidateConnectState( pMac ))
+   {
+      smsLog(pMac, LOGE, "PMC: STA not associated with an AP with single active session. BMPS cannot be entered\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   /* BMPS can only be requested when device is in Full Power */
+   if (pMac->pmc.pmcState != FULL_POWER)
+   {
+      smsLog(pMac, LOGE, "PMC: Device not in full power. Cannot request BMPS. pmcState %d\n", pMac->pmc.pmcState);
+      return eHAL_STATUS_FAILURE;
+   }
+   /* Check that entry into a power save mode is allowed at this time. */
+   if (!pmcPowerSaveCheck(pMac))
+   {
+      smsLog(pMac, LOGE, "PMC: Power save check failed. BMPS cannot be entered now\n");
+      return eHAL_STATUS_PMC_NOT_NOW;
+   }
+
+   smsLog(pMac, LOG1, FL("concurrency enabled %u\n"), pMac->roam.configParam.concurrencyEnabled);
+   if (pMac->roam.configParam.concurrencyEnabled)
+   {
+      pMac->roam.configParam.concurrencyEnabled = 0;
+      smsLog(pMac, LOG1, FL("reset concurrency to disabled %u\n"), pMac->roam.configParam.concurrencyEnabled);
+      csrDisconnectAllActiveSessions(pMac);
+   }
+   return ( eHAL_STATUS_SUCCESS );
+}
+
+tANI_BOOLEAN pmcShouldBmpsTimerRun( tpAniSirGlobal pMac )
+{
+    /* Check if BMPS is enabled and if Auto BMPS Feature is still enabled 
+     * or there is a pending Uapsd request or HDD requested BMPS or there
+     * is a pending request for WoWL. In all these cases BMPS is required. 
+     * Otherwise just stop the timer and return.
+     */
+    if (!(pMac->pmc.bmpsEnabled && (pMac->pmc.autoBmpsEntryEnabled || 
+          pMac->pmc.uapsdSessionRequired || pMac->pmc.bmpsRequestedByHdd ||
+          pMac->pmc.wowlModeRequired )))
+    {
+        smsLog(pMac, LOG1, FL("BMPS is not enabled or not required"));
+        return eANI_BOOLEAN_FALSE;
+    }
+
+    /* Check if there is an Infra session. BMPS is possible only if there is 
+     * an Infra session */
+    if (!csrIsInfraConnected(pMac))
+    {
+        smsLog(pMac, LOG1, FL("No Infra Session or multiple sessions. BMPS should not be started"));
+        return eANI_BOOLEAN_FALSE;
+    }
+    return eANI_BOOLEAN_TRUE;
+}
+
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT 
+
+#define PMC_DIAG_EVT_TIMER_INTERVAL ( 5000 )
+
+void pmcDiagEvtTimerExpired (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+    vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+    psRequest.event_subtype = WLAN_PMC_CURRENT_STATE;
+    psRequest.pmc_current_state = pMac->pmc.pmcState;
+
+    WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+
+    smsLog(pMac, LOGW, FL("DIAG event timer expired\n"));
+
+    /* re-arm timer */
+    if (pmcStartDiagEvtTimer(hHal) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGP, FL("Cannot re-arm DIAG evt timer\n"));
+    }
+}
+
+eHalStatus pmcStartDiagEvtTimer (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcStartDiagEvtTimer\n"));
+
+    if (palTimerStart(pMac->hHdd, pMac->pmc.hDiagEvtTimer, PMC_DIAG_EVT_TIMER_INTERVAL *
+                          1000, TRUE) != eHAL_STATUS_SUCCESS)
+    {
+       smsLog(pMac, LOGP, FL("Cannot start DIAG evt timer\n"));
+       return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+void pmcStopDiagEvtTimer (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    smsLog(pMac, LOG2, FL("Entering pmcStopDiagEvtTimer\n"));
+    (void)palTimerStop(pMac->hHdd, pMac->pmc.hDiagEvtTimer);
+}
+#endif
diff --git a/CORE/SME/src/pmc/pmcApi.c b/CORE/SME/src/pmc/pmcApi.c
new file mode 100644
index 0000000..ac4a73e
--- /dev/null
+++ b/CORE/SME/src/pmc/pmcApi.c
@@ -0,0 +1,3122 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/******************************************************************************
+*
+* Name:  pmcApi.c
+*
+* Description: Routines that make up the Power Management Control (PMC) API.
+*
+* Copyright 2008 (c) Qualcomm, Incorporated.  
+* All Rights Reserved.
+* Qualcomm Confidential and Proprietary.
+*
+******************************************************************************/
+
+#include "palTypes.h"
+#include "aniGlobal.h"
+#include "palTimer.h"
+#include "csrLinkList.h"
+#include "smsDebug.h"
+#include "pmcApi.h"
+#include "pmc.h"
+#include "cfgApi.h"
+#include "smeInside.h"
+#include "csrInsideApi.h"
+#include "wlan_ps_wow_diag.h"
+#include "wlan_qct_wda.h"
+#include "limSessionUtils.h"
+#include "csrInsideApi.h"
+
+extern void pmcReleaseCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+
+void pmcCloseDeferredMsgList(tpAniSirGlobal pMac);
+void pmcCloseDeviceStateUpdateList(tpAniSirGlobal pMac);
+void pmcCloseRequestStartUapsdList(tpAniSirGlobal pMac);
+void pmcCloseRequestBmpsList(tpAniSirGlobal pMac);
+void pmcCloseRequestFullPowerList(tpAniSirGlobal pMac);
+void pmcClosePowerSaveCheckList(tpAniSirGlobal pMac);
+
+/******************************************************************************
+*
+* Name:  pmcOpen
+*
+* Description:
+*    Does a PMC open operation on the device.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - open successful
+*    eHAL_STATUS_FAILURE - open not successful
+*
+******************************************************************************/
+eHalStatus pmcOpen (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcOpen\n"));
+
+    /* Initialize basic PMC information about device. */
+    pMac->pmc.powerSource = BATTERY_POWER;
+    pMac->pmc.pmcState = STOPPED;
+    pMac->pmc.pmcReady = FALSE;
+
+    /* Initialize Power Save Modes */
+    pMac->pmc.impsEnabled = FALSE;
+    pMac->pmc.autoBmpsEntryEnabled = FALSE;
+    pMac->pmc.smpsEnabled = FALSE;
+    pMac->pmc.uapsdEnabled = TRUE;
+    pMac->pmc.bmpsEnabled = TRUE;
+    pMac->pmc.standbyEnabled = TRUE;
+    pMac->pmc.wowlEnabled = TRUE;
+    pMac->pmc.rfSuppliesVotedOff= FALSE;
+
+    palZeroMemory(pMac->hHdd, &(pMac->pmc.bmpsConfig), sizeof(tPmcBmpsConfigParams));
+    palZeroMemory(pMac->hHdd, &(pMac->pmc.impsConfig), sizeof(tPmcImpsConfigParams));
+    palZeroMemory(pMac->hHdd, &(pMac->pmc.smpsConfig), sizeof(tPmcSmpsConfigParams));
+
+    /* Allocate a timer to use with IMPS. */
+    if (palTimerAlloc(pMac->hHdd, &pMac->pmc.hImpsTimer, pmcImpsTimerExpired, hHal) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot allocate timer for IMPS\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Allocate a timer used in Full Power State to measure traffic
+       levels and determine when to enter BMPS. */
+    if (!VOS_IS_STATUS_SUCCESS(vos_timer_init(&pMac->pmc.hTrafficTimer, 
+                                VOS_TIMER_TYPE_SW, pmcTrafficTimerExpired, hHal)))
+    {
+        smsLog(pMac, LOGE, FL("Cannot allocate timer for traffic measurement\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    /* Allocate a timer used to report current PMC state through periodic DIAG event */
+    if (palTimerAlloc(pMac->hHdd, &pMac->pmc.hDiagEvtTimer, pmcDiagEvtTimerExpired, hHal) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot allocate timer for diag event reporting\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+#endif
+
+    //Initialize the default value for Bmps related config. 
+    pMac->pmc.bmpsConfig.trafficMeasurePeriod = BMPS_TRAFFIC_TIMER_DEFAULT;
+    pMac->pmc.bmpsConfig.bmpsPeriod = WNI_CFG_LISTEN_INTERVAL_STADEF;
+
+    /* Allocate a timer used to schedule a deferred power save mode exit. */
+    if (palTimerAlloc(pMac->hHdd, &pMac->pmc.hExitPowerSaveTimer,
+                      pmcExitPowerSaveTimerExpired, hHal) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot allocate exit power save mode timer\n"));
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+    
+    /* Initialize lists for power save check routines and request full power callback routines. */
+    if (csrLLOpen(pMac->hHdd, &pMac->pmc.powerSaveCheckList) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot initialize power save check routine list\n"));
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+    if (csrLLOpen(pMac->hHdd, &pMac->pmc.requestFullPowerList) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot initialize request full power callback routine list\n"));
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Initialize lists for request BMPS callback routines. */
+    if (csrLLOpen(pMac->hHdd, &pMac->pmc.requestBmpsList) !=
+      eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, "PMC: cannot initialize request BMPS callback routine list\n");
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Initialize lists for request start UAPSD callback routines. */
+    if (csrLLOpen(pMac->hHdd, &pMac->pmc.requestStartUapsdList) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, "PMC: cannot initialize request start UAPSD callback routine list\n");
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Initialize lists for device state update indication callback routines. */
+    if (csrLLOpen(pMac->hHdd, &pMac->pmc.deviceStateUpdateIndList) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, "PMC: cannot initialize device state update indication callback list\n");
+        return eHAL_STATUS_FAILURE;
+    }
+
+    if (csrLLOpen(pMac->hHdd, &pMac->pmc.deferredMsgList) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot initialize deferred msg list\n"));
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcStart
+*
+* Description:
+*    Does a PMC start operation on the device.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - start successful
+*    eHAL_STATUS_FAILURE - start not successful
+*
+******************************************************************************/
+eHalStatus pmcStart (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tSirMacHTMIMOPowerSaveState  htMimoPowerSaveState;
+
+    smsLog(pMac, LOG2, FL("Entering pmcStart\n"));
+
+    /* Initialize basic PMC information about device. */
+    pMac->pmc.pmcState = FULL_POWER;
+    pMac->pmc.requestFullPowerPending = FALSE;
+    pMac->pmc.uapsdSessionRequired = FALSE;
+    pMac->pmc.wowlModeRequired = FALSE;
+    pMac->pmc.bmpsRequestedByHdd = FALSE;
+    pMac->pmc.remainInPowerActiveTillDHCP = FALSE;
+    pMac->pmc.remainInPowerActiveThreshold = 0;
+
+    /* WLAN Switch initial states. */
+    pMac->pmc.hwWlanSwitchState = ePMC_SWITCH_ON;
+    pMac->pmc.swWlanSwitchState = ePMC_SWITCH_ON;
+
+    /* No IMPS callback routine yet. */
+    pMac->pmc.impsCallbackRoutine = NULL;
+
+    /* No STANDBY callback routine yet. */
+    pMac->pmc.standbyCallbackRoutine = NULL;
+
+    /* No WOWL callback routine yet. */
+    pMac->pmc.enterWowlCallbackRoutine = NULL;
+
+    /* Initialize BMPS traffic counts. */
+    pMac->pmc.cLastTxUnicastFrames = 0;
+    pMac->pmc.cLastRxUnicastFrames = 0;
+
+    /* Configure SMPS. */
+    if (pMac->pmc.smpsEnabled && (pMac->pmc.powerSource != AC_POWER || pMac->pmc.smpsConfig.enterOnAc))
+    {
+        if (pMac->pmc.smpsConfig.mode == ePMC_DYNAMIC_SMPS)
+            htMimoPowerSaveState = eSIR_HT_MIMO_PS_DYNAMIC;
+        if (pMac->pmc.smpsConfig.mode == ePMC_STATIC_SMPS)
+            htMimoPowerSaveState = eSIR_HT_MIMO_PS_STATIC;
+    }
+    else
+        htMimoPowerSaveState = eSIR_HT_MIMO_PS_NO_LIMIT;
+    
+    if (pmcSendMessage(hHal, eWNI_PMC_SMPS_STATE_IND, &htMimoPowerSaveState,
+                       sizeof(tSirMacHTMIMOPowerSaveState)) != eHAL_STATUS_SUCCESS)
+        return eHAL_STATUS_FAILURE;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT 
+    if (pmcStartDiagEvtTimer(hHal) != eHAL_STATUS_SUCCESS)
+    {
+       return eHAL_STATUS_FAILURE;
+    }
+#endif
+
+#if defined(ANI_LOGDUMP)
+    pmcDumpInit(hHal);
+#endif
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcStop
+*
+* Description:
+*    Does a PMC stop operation on the device.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - stop successful
+*    eHAL_STATUS_FAILURE - stop not successful
+*
+******************************************************************************/
+eHalStatus pmcStop (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tListElem *pEntry;
+    tPmcDeferredMsg *pDeferredMsg;
+
+    smsLog(pMac, LOG2, FL("Entering pmcStop\n"));
+
+    /* Cancel any running timers. */
+    if (palTimerStop(pMac->hHdd, pMac->pmc.hImpsTimer) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot cancel IMPS timer\n"));
+    }
+
+    pmcStopTrafficTimer(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    pmcStopDiagEvtTimer(hHal);
+#endif
+
+    if (palTimerStop(pMac->hHdd, pMac->pmc.hExitPowerSaveTimer) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot cancel exit power save mode timer\n"));
+    }
+
+    /* Do all the callbacks. */
+    pmcDoCallbacks(hHal, eHAL_STATUS_FAILURE);
+    pmcDoBmpsCallbacks(hHal, eHAL_STATUS_FAILURE);
+    pMac->pmc.uapsdSessionRequired = FALSE;
+    pmcDoStartUapsdCallbacks(hHal, eHAL_STATUS_FAILURE);
+    pmcDoStandbyCallbacks(hHal, eHAL_STATUS_FAILURE);
+
+    //purge the deferred msg list
+    csrLLLock( &pMac->pmc.deferredMsgList );
+    while( NULL != ( pEntry = csrLLRemoveHead( &pMac->pmc.deferredMsgList, eANI_BOOLEAN_FALSE ) ) )
+    {
+        pDeferredMsg = GET_BASE_ADDR( pEntry, tPmcDeferredMsg, link );
+        palFreeMemory( pMac->hHdd, pDeferredMsg );
+    }
+    csrLLUnlock( &pMac->pmc.deferredMsgList );
+
+    /* PMC is stopped. */
+    pMac->pmc.pmcState = STOPPED;
+    pMac->pmc.pmcReady = FALSE;
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcClose
+*
+* Description:
+*    Does a PMC close operation on the device.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - close successful
+*    eHAL_STATUS_FAILURE - close not successful
+*
+******************************************************************************/
+eHalStatus pmcClose (tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcClose\n"));
+
+    /* Free up allocated resources. */
+    if (palTimerFree(pMac->hHdd, pMac->pmc.hImpsTimer) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot deallocate IMPS timer\n"));
+    }
+    if (!VOS_IS_STATUS_SUCCESS(vos_timer_destroy(&pMac->pmc.hTrafficTimer)))
+    {
+        smsLog(pMac, LOGE, FL("Cannot deallocate traffic timer\n"));
+    }
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    if (palTimerFree(pMac->hHdd, pMac->pmc.hDiagEvtTimer) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot deallocate timer for diag event reporting\n"));
+    }
+#endif
+    if (palTimerFree(pMac->hHdd, pMac->pmc.hExitPowerSaveTimer) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot deallocate exit power save mode timer\n"));
+    }
+
+    /*
+        The following list's entries are dynamically allocated so they need their own 
+        cleanup function
+    */
+    pmcClosePowerSaveCheckList(pMac);
+    pmcCloseRequestFullPowerList(pMac);
+    pmcCloseRequestBmpsList(pMac);
+    pmcCloseRequestStartUapsdList(pMac);
+    pmcCloseDeviceStateUpdateList(pMac);
+    pmcCloseDeferredMsgList(pMac);
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcSignalPowerEvent
+*
+* Description:
+*    Signals to PMC that a power event has occurred.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    event - the event that has occurred
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - signaling successful
+*    eHAL_STATUS_FAILURE - signaling not successful
+*
+******************************************************************************/
+eHalStatus pmcSignalPowerEvent (tHalHandle hHal, tPmcPowerEvent event)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+#ifndef GEN6_ONWARDS
+    tSirMacHTMIMOPowerSaveState  htMimoPowerSaveState;
+#endif
+
+    smsLog(pMac, LOG2, FL("Entering pmcSignalPowerEvent, event %d\n"), event);
+
+    /* Take action based on the event being signaled. */
+    switch (event)
+    {
+#ifndef GEN6_ONWARDS
+    case ePMC_SYSTEM_HIBERNATE:
+        return pmcEnterLowPowerState(hHal);
+
+    case ePMC_SYSTEM_RESUME:
+        return pmcExitLowPowerState(hHal);
+
+    case ePMC_HW_WLAN_SWITCH_OFF:
+        pMac->pmc.hwWlanSwitchState = ePMC_SWITCH_OFF;
+        return pmcEnterLowPowerState(hHal);
+
+    case ePMC_HW_WLAN_SWITCH_ON:
+        pMac->pmc.hwWlanSwitchState = ePMC_SWITCH_ON;
+        return pmcExitLowPowerState(hHal);
+
+    case ePMC_SW_WLAN_SWITCH_OFF:
+        pMac->pmc.swWlanSwitchState = ePMC_SWITCH_OFF;
+        return pmcEnterLowPowerState(hHal);
+
+    case ePMC_SW_WLAN_SWITCH_ON:
+        pMac->pmc.swWlanSwitchState = ePMC_SWITCH_ON;
+        return pmcExitLowPowerState(hHal);
+
+    case ePMC_BATTERY_OPERATION:
+        pMac->pmc.powerSource = BATTERY_POWER;
+
+        /* Turn on SMPS. */
+        if (pMac->pmc.smpsEnabled)
+        {
+            if (pMac->pmc.smpsConfig.mode == ePMC_DYNAMIC_SMPS)
+                htMimoPowerSaveState = eSIR_HT_MIMO_PS_DYNAMIC;
+            if (pMac->pmc.smpsConfig.mode == ePMC_STATIC_SMPS)
+                htMimoPowerSaveState = eSIR_HT_MIMO_PS_STATIC;
+            if (pmcSendMessage(hHal, eWNI_PMC_SMPS_STATE_IND, &htMimoPowerSaveState,
+                               sizeof(tSirMacHTMIMOPowerSaveState)) != eHAL_STATUS_SUCCESS)   
+                return eHAL_STATUS_FAILURE;
+        }
+        return eHAL_STATUS_SUCCESS;
+
+    case ePMC_AC_OPERATION:
+        pMac->pmc.powerSource = AC_POWER;
+
+        /* Turn off SMPS. */
+        if (!pMac->pmc.smpsConfig.enterOnAc)
+        {
+            htMimoPowerSaveState = eSIR_HT_MIMO_PS_NO_LIMIT;
+            if (pmcSendMessage(hHal, eWNI_PMC_SMPS_STATE_IND, &htMimoPowerSaveState,
+                               sizeof(tSirMacHTMIMOPowerSaveState)) != eHAL_STATUS_SUCCESS)
+                return eHAL_STATUS_FAILURE;
+        }
+        return eHAL_STATUS_SUCCESS;
+#endif //GEN6_ONWARDS
+    default:
+        smsLog(pMac, LOGE, FL("Invalid event %d\n"), event);
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcSetConfigPowerSave
+*
+* Description:
+*    Configures one of the power saving modes.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    psMode - the power saving mode to configure
+*    pConfigParams - pointer to configuration parameters specific to the
+*                    power saving mode
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - configuration successful
+*    eHAL_STATUS_FAILURE - configuration not successful
+*
+******************************************************************************/
+eHalStatus pmcSetConfigPowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode, void *pConfigParams)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+    WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+#endif
+
+    smsLog(pMac, LOG2, FL("Entering pmcSetConfigPowerSave, power save mode %d\n"), psMode);
+
+    /* Configure the specified power saving mode. */
+    switch (psMode)
+    {
+    
+    case ePMC_IDLE_MODE_POWER_SAVE:
+        pMac->pmc.impsConfig = *(tpPmcImpsConfigParams)pConfigParams;
+        smsLog(pMac, LOG3, FL("IMPS configuration"));
+        smsLog(pMac, LOG3, "          enter on AC: %d\n",
+               pMac->pmc.impsConfig.enterOnAc);
+        break;
+
+    case ePMC_BEACON_MODE_POWER_SAVE:
+        pMac->pmc.bmpsConfig = *(tpPmcBmpsConfigParams)pConfigParams;
+        smsLog(pMac, LOG3, FL("BMPS configuration"));
+        smsLog(pMac, LOG3, "          enter on AC: %d\n",
+               pMac->pmc.bmpsConfig.enterOnAc);
+        smsLog(pMac, LOG3, "          TX threshold: %d\n",
+               pMac->pmc.bmpsConfig.txThreshold);
+        smsLog(pMac, LOG3, "          RX threshold: %d\n",
+               pMac->pmc.bmpsConfig.rxThreshold);
+        smsLog(pMac, LOG3, "          traffic measurement period (ms): %d\n",
+               pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+        smsLog(pMac, LOG3, "          BMPS period: %d\n",
+               pMac->pmc.bmpsConfig.bmpsPeriod);
+        smsLog(pMac, LOG3, "          beacons to forward code: %d\n",
+               pMac->pmc.bmpsConfig.forwardBeacons);
+        smsLog(pMac, LOG3, "          value of N: %d\n",
+               pMac->pmc.bmpsConfig.valueOfN);
+        smsLog(pMac, LOG3, "          use PS poll: %d\n",
+               pMac->pmc.bmpsConfig.usePsPoll);
+        smsLog(pMac, LOG3, "          set PM on last frame: %d\n",
+               pMac->pmc.bmpsConfig.setPmOnLastFrame);
+        smsLog(pMac, LOG3, "          value of enableBeaconEarlyTermination: %d\n",
+               pMac->pmc.bmpsConfig.enableBeaconEarlyTermination);
+        smsLog(pMac, LOG3, "          value of bcnEarlyTermWakeInterval: %d\n",
+               pMac->pmc.bmpsConfig.bcnEarlyTermWakeInterval);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+        vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+        psRequest.event_subtype = WLAN_BMPS_SET_CONFIG;
+        /* possible loss of data due to mismatch but expectation is that
+        values can reasonably be expected to fit in target widths */
+        psRequest.bmps_auto_timer_duration = (v_U16_t)pMac->pmc.bmpsConfig.trafficMeasurePeriod;
+        psRequest.bmps_period = (v_U16_t)pMac->pmc.bmpsConfig.bmpsPeriod; 
+
+        WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+
+        break;
+
+    case ePMC_SPATIAL_MULTIPLEX_POWER_SAVE:
+        pMac->pmc.smpsConfig = *(tpPmcSmpsConfigParams)pConfigParams;
+        smsLog(pMac, LOG3, FL("SMPS configuration"));
+        smsLog(pMac, LOG3, "          mode: %d\n", pMac->pmc.smpsConfig.mode);
+        smsLog(pMac, LOG3, "          enter on AC: %d\n",
+               pMac->pmc.smpsConfig.enterOnAc);
+        break;
+
+    default:
+        smsLog(pMac, LOGE, FL("Invalid power save mode %d\n"), psMode);
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    //Send the power save config down to PE/HAL/FW if BMPS mode is being configured
+    //and pmcReady has been invoked
+    if(PMC_IS_READY(pMac) && psMode == ePMC_BEACON_MODE_POWER_SAVE)
+    {
+       if (pmcSendPowerSaveConfigMessage(hHal) != eHAL_STATUS_SUCCESS)
+           return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcGetConfigPowerSave
+*
+* Description:
+*    Get the config for the specified power save mode
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    psMode - the power saving mode to configure
+*    pConfigParams - pointer to configuration parameters specific to the
+*                    power saving mode
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - configuration successful
+*    eHAL_STATUS_FAILURE - configuration not successful
+*
+******************************************************************************/
+eHalStatus pmcGetConfigPowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode, void *pConfigParams)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcGetConfigPowerSave, power save mode %d\n"), psMode);
+
+    /* Configure the specified power saving mode. */
+    switch (psMode)
+    {
+    
+    case ePMC_IDLE_MODE_POWER_SAVE:
+        *(tpPmcImpsConfigParams)pConfigParams = pMac->pmc.impsConfig;
+        break;
+
+    case ePMC_BEACON_MODE_POWER_SAVE:
+        *(tpPmcBmpsConfigParams)pConfigParams = pMac->pmc.bmpsConfig;
+        break;
+
+    case ePMC_SPATIAL_MULTIPLEX_POWER_SAVE:
+        *(tpPmcSmpsConfigParams)pConfigParams = pMac->pmc.smpsConfig;
+        break;
+
+    default:
+        smsLog(pMac, LOGE, FL("Invalid power save mode %d\n"), psMode);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+/******************************************************************************
+*
+* Name:  pmcEnablePowerSave
+*
+* Description:
+*    Enables one of the power saving modes.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    psMode - the power saving mode to enable
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - successfully enabled
+*    eHAL_STATUS_FAILURE - not successfully enabled
+*
+******************************************************************************/
+eHalStatus pmcEnablePowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tSirMacHTMIMOPowerSaveState  htMimoPowerSaveState;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+    vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+    psRequest.event_subtype = WLAN_PS_MODE_ENABLE_REQ;
+    psRequest.enable_disable_powersave_mode = psMode;
+
+    WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+    
+    smsLog(pMac, LOG2, FL("Entering pmcEnablePowerSave, power save mode %d\n"), psMode);
+
+    /* Enable the specified power saving mode. */
+    switch (psMode)
+    {
+
+    case ePMC_IDLE_MODE_POWER_SAVE:
+        pMac->pmc.impsEnabled = TRUE;
+        break;
+
+    case ePMC_BEACON_MODE_POWER_SAVE:
+        pMac->pmc.bmpsEnabled = TRUE;
+        break;
+
+    case ePMC_SPATIAL_MULTIPLEX_POWER_SAVE:
+        pMac->pmc.smpsEnabled = TRUE;
+
+        /* If PMC already started, then turn on SMPS. */
+        if (pMac->pmc.pmcState != STOPPED)
+            if (pMac->pmc.powerSource != AC_POWER ||
+                pMac->pmc.smpsConfig.enterOnAc)
+            {
+                if (pMac->pmc.smpsConfig.mode == ePMC_DYNAMIC_SMPS)
+                    htMimoPowerSaveState = eSIR_HT_MIMO_PS_DYNAMIC;
+                if (pMac->pmc.smpsConfig.mode == ePMC_STATIC_SMPS)
+                    htMimoPowerSaveState = eSIR_HT_MIMO_PS_STATIC;
+                if (pmcSendMessage(hHal, eWNI_PMC_SMPS_STATE_IND, &htMimoPowerSaveState,
+                                   sizeof(tSirMacHTMIMOPowerSaveState)) != eHAL_STATUS_SUCCESS)
+                    return eHAL_STATUS_FAILURE;
+            }
+        break;
+
+    case ePMC_UAPSD_MODE_POWER_SAVE:
+        pMac->pmc.uapsdEnabled = TRUE;
+        break;
+
+    case ePMC_STANDBY_MODE_POWER_SAVE:
+        pMac->pmc.standbyEnabled = TRUE;
+        break;
+
+    case ePMC_WOWL_MODE_POWER_SAVE:
+        pMac->pmc.wowlEnabled = TRUE;
+        break;
+
+    default:
+        smsLog(pMac, LOGE, FL("Invalid power save mode %d\n"), psMode);
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+/* ---------------------------------------------------------------------------
+    \fn pmcStartAutoBmpsTimer
+    \brief  Starts a timer that periodically polls all the registered
+            module for entry into Bmps mode. This timer is started only if BMPS is
+            enabled and whenever the device is in full power.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcStartAutoBmpsTimer (tHalHandle hHal) 
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+   WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+   vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+   psRequest.event_subtype = WLAN_START_BMPS_AUTO_TIMER_REQ;
+
+   WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+   smsLog(pMac, LOG2, FL("Entering pmcStartAutoBmpsTimer\n"));
+
+   /* Check if BMPS is enabled. */
+   if (!pMac->pmc.bmpsEnabled)
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot enable BMPS timer. BMPS is disabled\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   pMac->pmc.autoBmpsEntryEnabled = TRUE;
+
+   /* Check if there is an Infra session. If there is no Infra session, timer will be started 
+         when STA associates to AP */
+
+   if (pmcShouldBmpsTimerRun(pMac))
+   {
+      if (pmcStartTrafficTimer(hHal, pMac->pmc.bmpsConfig.trafficMeasurePeriod) != eHAL_STATUS_SUCCESS)
+         return eHAL_STATUS_FAILURE;
+   }
+
+
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcStopAutoBmpsTimer
+    \brief  Stops the Auto BMPS Timer that was started using sme_startAutoBmpsTimer
+            Stopping the timer does not cause a device state change. Only the timer
+            is stopped. If "Full Power" is desired, use the pmcRequestFullPower API
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcStopAutoBmpsTimer (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+   WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+   vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+   psRequest.event_subtype = WLAN_STOP_BMPS_AUTO_TIMER_REQ;
+
+   WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+   smsLog(pMac, LOG2, FL("Entering pmcStopAutoBmpsTimer\n"));
+
+   pMac->pmc.autoBmpsEntryEnabled = FALSE;
+   /* If uapsd session is not required or HDD has not requested BMPS, stop the auto bmps timer.*/
+   if (!pMac->pmc.uapsdSessionRequired && !pMac->pmc.bmpsRequestedByHdd)
+      pmcStopTrafficTimer(hHal);
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/******************************************************************************
+*
+* Name:  pmcDisablePowerSave
+*
+* Description:
+*    Disables one of the power saving modes.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    psMode - the power saving mode to disable
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - successfully disabled
+*    eHAL_STATUS_FAILURE - not successfully disabled
+*
+******************************************************************************/
+eHalStatus pmcDisablePowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tSirMacHTMIMOPowerSaveState  htMimoPowerSaveState;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+    vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+    psRequest.event_subtype = WLAN_PS_MODE_DISABLE_REQ;
+    psRequest.enable_disable_powersave_mode = psMode;
+
+    WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+    smsLog(pMac, LOG2, FL("Entering pmcDisablePowerSave, power save mode %d\n"), psMode);
+
+    /* Disable the specified power saving mode. */
+    switch (psMode)
+    {
+
+    case ePMC_IDLE_MODE_POWER_SAVE:
+        pMac->pmc.impsEnabled = FALSE;
+        break;
+
+    case ePMC_BEACON_MODE_POWER_SAVE:
+        pMac->pmc.bmpsEnabled = FALSE;
+        break;
+
+    case ePMC_SPATIAL_MULTIPLEX_POWER_SAVE:
+        pMac->pmc.smpsEnabled = FALSE;
+
+        /* Turn off SMPS. */
+        htMimoPowerSaveState = eSIR_HT_MIMO_PS_NO_LIMIT;
+        if (pmcSendMessage(hHal, eWNI_PMC_SMPS_STATE_IND, &htMimoPowerSaveState,
+                           sizeof(tSirMacHTMIMOPowerSaveState)) != eHAL_STATUS_SUCCESS)
+            return eHAL_STATUS_FAILURE;
+        break;
+
+    case ePMC_UAPSD_MODE_POWER_SAVE:
+        pMac->pmc.uapsdEnabled = FALSE;
+        break;
+
+    case ePMC_STANDBY_MODE_POWER_SAVE:
+        pMac->pmc.standbyEnabled = FALSE;
+        break;
+
+    case ePMC_WOWL_MODE_POWER_SAVE:
+        pMac->pmc.wowlEnabled = FALSE;
+        break;
+
+    default:
+        smsLog(pMac, LOGE, FL("Invalid power save mode %d\n"), psMode);
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcQueryPowerState
+*
+* Description:
+*    Returns the current power state of the device.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    pPowerState - pointer to location to return power state
+*    pHwWlanSwitchState - pointer to location to return Hardware WLAN
+*                         Switch state
+*    pSwWlanSwitchState - pointer to location to return Software WLAN
+*                         Switch state
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - power state successfully returned
+*    eHAL_STATUS_FAILURE - power state not successfully returned
+*
+******************************************************************************/
+eHalStatus pmcQueryPowerState (tHalHandle hHal, tPmcPowerState *pPowerState,
+                               tPmcSwitchState *pHwWlanSwitchState, tPmcSwitchState *pSwWlanSwitchState)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcQueryPowerState\n"));
+
+    /* Return current power state based on PMC state. */
+    if(pPowerState != NULL)
+    {
+        /* Return current power state based on PMC state. */
+        switch (pMac->pmc.pmcState)
+        {
+    
+        case FULL_POWER:
+            *pPowerState = ePMC_FULL_POWER;
+            break;
+
+        default:
+            *pPowerState = ePMC_LOW_POWER;
+            break;
+        }
+    }
+
+    /* Return current switch settings. */
+    if(pHwWlanSwitchState != NULL)
+       *pHwWlanSwitchState = pMac->pmc.hwWlanSwitchState;
+    if(pSwWlanSwitchState != NULL)
+       *pSwWlanSwitchState = pMac->pmc.swWlanSwitchState;
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcIsPowerSaveEnabled
+*
+* Description:
+*    Checks if the device is able to enter one of the power save modes.
+*    "Able to enter" means the power save mode is enabled for the device
+*    and the host is using the correct power source for entry into the
+*    power save mode.  This routine does not indicate whether the device
+*    is actually in the power save mode at a particular point in time.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    psMode - the power saving mode
+*
+* Returns:
+*    TRUE if device is able to enter the power save mode, FALSE otherwise
+*
+******************************************************************************/
+tANI_BOOLEAN pmcIsPowerSaveEnabled (tHalHandle hHal, tPmcPowerSavingMode psMode)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcIsPowerSaveEnabled, power save mode %d\n"), psMode);
+
+    /* Check ability to enter based on the specified power saving mode. */
+    switch (psMode)
+    {
+    
+    case ePMC_IDLE_MODE_POWER_SAVE:
+        return pMac->pmc.impsEnabled && (pMac->pmc.powerSource != AC_POWER || pMac->pmc.impsConfig.enterOnAc);
+
+    case ePMC_BEACON_MODE_POWER_SAVE:
+        return pMac->pmc.bmpsEnabled;
+
+    case ePMC_SPATIAL_MULTIPLEX_POWER_SAVE:
+        return pMac->pmc.smpsEnabled && (pMac->pmc.powerSource != AC_POWER || pMac->pmc.smpsConfig.enterOnAc);
+
+    case ePMC_UAPSD_MODE_POWER_SAVE:
+        return pMac->pmc.uapsdEnabled;
+
+    case ePMC_STANDBY_MODE_POWER_SAVE:
+        return pMac->pmc.standbyEnabled;
+
+    case ePMC_WOWL_MODE_POWER_SAVE:
+        return pMac->pmc.wowlEnabled;
+        break;
+
+    default:
+        smsLog(pMac, LOGE, FL("Invalid power save mode %d\n"), psMode);
+        PMC_ABORT;
+        return FALSE;
+    }
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcRequestFullPower
+*
+* Description:
+*    Request that the device be brought to full power state.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    callbackRoutine - routine to call when device actually achieves full
+*                      power state if "eHAL_STATUS_PMC_PENDING" is returned
+*    callbackContext - value to be passed as parameter to routine specified
+*                      above
+*    fullPowerReason -  Reason for requesting full power mode. This is used
+*                       by PE to decide whether data null should be sent to
+*                       AP when exiting BMPS mode. Caller should use the
+*                       eSME_LINK_DISCONNECTED reason if link is disconnected
+*                       and there is no need to tell the AP that we are going
+*                       out of power save.
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - device brought to full power state
+*    eHAL_STATUS_FAILURE - device cannot be brought to full power state
+*    eHAL_STATUS_PMC_PENDING - device is being brought to full power state,
+*                              callbackRoutine will be called when completed
+*
+******************************************************************************/
+eHalStatus pmcRequestFullPower (tHalHandle hHal, void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+                                void *callbackContext, tRequestFullPowerReason fullPowerReason)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tpRequestFullPowerEntry pEntry;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+    vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+    psRequest.event_subtype = WLAN_ENTER_FULL_POWER_REQ;
+    psRequest.full_power_request_reason = fullPowerReason;
+ 
+    WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+    smsLog(pMac, LOG2, FL("Entering pmcRequestFullPower"));
+
+    if( !PMC_IS_READY(pMac) )
+    {
+        smsLog(pMac, LOGE, FL("Requesting Full Power when PMC not ready\n"));
+        smsLog(pMac, LOGE, FL("pmcReady = %d pmcState = %s\n"), 
+            pMac->pmc.pmcReady, pmcGetPmcStateStr(pMac->pmc.pmcState));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* If HDD is requesting full power, clear any buffered requests for WOWL and BMPS that were
+       requested by HDD previously */
+    if(SIR_IS_FULL_POWER_NEEDED_BY_HDD(fullPowerReason))
+    {
+        pMac->pmc.bmpsRequestedByHdd = FALSE;
+        pMac->pmc.wowlModeRequired = FALSE;
+    }
+
+    /* If already in full power, just return. */
+    if (pMac->pmc.pmcState == FULL_POWER)
+        return eHAL_STATUS_SUCCESS;
+
+    /* If in IMPS State, then cancel the timer. */
+    if (pMac->pmc.pmcState == IMPS)
+        if (palTimerStop(pMac->hHdd, pMac->pmc.hImpsTimer) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot cancel IMPS timer\n"));
+            return eHAL_STATUS_FAILURE;
+        }
+
+    /* Enter Request Full Power State. */
+    if (pmcEnterRequestFullPowerState(hHal, fullPowerReason) != eHAL_STATUS_SUCCESS)
+        return eHAL_STATUS_FAILURE;
+
+    /* If able to enter Request Full Power State, then request is pending.
+       Allocate entry for request full power callback routine list. */
+    //If caller doesn't need a callback, simply waits up the chip.
+    if( callbackRoutine )
+    {
+        if (palAllocateMemory(pMac->hHdd, (void **)&pEntry, sizeof(tRequestFullPowerEntry)) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot allocate memory for request full power routine list entry\n"));
+            PMC_ABORT;
+            return eHAL_STATUS_FAILURE;
+        }
+
+        /* Store routine and context in entry. */
+        pEntry->callbackRoutine = callbackRoutine;
+        pEntry->callbackContext = callbackContext;
+
+        /* Add entry to list. */
+        csrLLInsertTail(&pMac->pmc.requestFullPowerList, &pEntry->link, TRUE);
+    }
+
+    return eHAL_STATUS_PMC_PENDING;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcRequestImps
+*
+* Description:
+*    Request that the device be placed in Idle Mode Power Save (IMPS).
+*    The Common Scan/Roam Module makes this request.  The device will be
+*    placed into IMPS for the specified amount of time, and then returned
+*    to full power.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    impsPeriod - amount of time to remain in IMPS (milliseconds)
+*    callbackRoutine - routine to call when IMPS period has finished and
+*                      the device has been brought to full power
+*    callbackContext - value to be passed as parameter to routine specified
+*                      above
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - device will enter IMPS
+*    eHAL_STATUS_PMC_DISABLED - IMPS is disabled
+*    eHAL_STATUS_PMC_NOT_NOW - another module is prohibiting entering IMPS
+*                              at this time
+*    eHAL_STATUS_PMC_AC_POWER - IMPS is disabled when host operating from
+*                               AC power
+*    eHAL_STATUS_PMC_ALREADY_IN_IMPS - device is already in IMPS
+*    eHAL_STATUS_PMC_SYS_ERROR - system error that prohibits entering IMPS
+*
+******************************************************************************/
+eHalStatus pmcRequestImps (tHalHandle hHal, tANI_U32 impsPeriod,
+                           void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+                           void *callbackContext)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    eHalStatus status;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+    vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+    psRequest.event_subtype = WLAN_IMPS_ENTER_REQ;
+    psRequest.imps_period = impsPeriod;
+
+    WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+
+    smsLog(pMac, LOG2, FL("Entering pmcRequestImps"));
+
+    status = pmcEnterImpsCheck( pMac );
+    if( HAL_STATUS_SUCCESS( status ) )
+    {
+        /* Enter Request IMPS State. */
+        status = pmcEnterRequestImpsState( hHal );
+        if (HAL_STATUS_SUCCESS( status ))
+    {
+            /* Save the period and callback routine for when we need it. */
+            pMac->pmc.impsPeriod = impsPeriod;
+            pMac->pmc.impsCallbackRoutine = callbackRoutine;
+            pMac->pmc.impsCallbackContext = callbackContext;
+
+    }
+        else
+    {
+            status = eHAL_STATUS_PMC_SYS_ERROR;
+    }
+    }
+
+    return status;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcRegisterPowerSaveCheck
+*
+* Description:
+*    Allows a routine to be registered so that the routine is called whenever
+*    the device is about to enter one of the power save modes.  This routine
+*    will say whether the device is allowed to enter the power save mode at
+*    the time of the call.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    checkRoutine - routine to call before entering a power save mode, should
+*                   return TRUE if the device is allowed to enter the power
+*                   save mode, FALSE otherwise
+*    checkContext - value to be passed as parameter to routine specified above
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - successfully registered
+*    eHAL_STATUS_FAILURE - not successfully registered
+*
+******************************************************************************/
+eHalStatus pmcRegisterPowerSaveCheck (tHalHandle hHal, tANI_BOOLEAN (*checkRoutine) (void *checkContext),
+                                      void *checkContext)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tpPowerSaveCheckEntry pEntry;
+
+    smsLog(pMac, LOG2, FL("Entering pmcRegisterPowerSaveCheck"));
+
+    /* Allocate entry for power save check routine list. */
+    if (palAllocateMemory(pMac->hHdd, (void **)&pEntry, sizeof(tPowerSaveCheckEntry)) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot allocate memory for power save check routine list entry\n"));
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Store routine and context in entry. */
+    pEntry->checkRoutine = checkRoutine;
+    pEntry->checkContext = checkContext;
+
+    /* Add entry to list. */
+    csrLLInsertTail(&pMac->pmc.powerSaveCheckList, &pEntry->link, FALSE);
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcDeregisterPowerSaveCheck
+*
+* Description:
+*    Reregisters a routine that was previously registered with
+*    pmcRegisterPowerSaveCheck.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    checkRoutine - routine to deregister
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - successfully deregistered
+*    eHAL_STATUS_FAILURE - not successfully deregistered
+*
+******************************************************************************/
+eHalStatus pmcDeregisterPowerSaveCheck (tHalHandle hHal, tANI_BOOLEAN (*checkRoutine) (void *checkContext))
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tListElem *pEntry;
+    tpPowerSaveCheckEntry pPowerSaveCheckEntry;
+
+    smsLog(pMac, LOG2, FL("Entering pmcDeregisterPowerSaveCheck"));
+
+    /* Find entry in the power save check routine list that matches
+       the specified routine and remove it. */
+    pEntry = csrLLPeekHead(&pMac->pmc.powerSaveCheckList, FALSE);
+    while (pEntry != NULL)
+    {
+        pPowerSaveCheckEntry = GET_BASE_ADDR(pEntry, tPowerSaveCheckEntry, link);
+        if (pPowerSaveCheckEntry->checkRoutine == checkRoutine)
+        {
+            if (csrLLRemoveEntry(&pMac->pmc.powerSaveCheckList, pEntry, FALSE))
+            {
+                if (palFreeMemory(pMac->hHdd, pPowerSaveCheckEntry) != eHAL_STATUS_SUCCESS)
+                {
+                    smsLog(pMac, LOGE, FL("Cannot free memory for power save check routine list entry\n"));
+                    PMC_ABORT;
+                    return eHAL_STATUS_FAILURE;
+                }
+            }
+            else
+            {
+                smsLog(pMac, LOGE, FL("Cannot remove power save check routine list entry\n"));
+                return eHAL_STATUS_FAILURE;
+            }
+            return eHAL_STATUS_SUCCESS;
+        }
+        pEntry = csrLLNext(&pMac->pmc.powerSaveCheckList, pEntry, FALSE);
+    }
+
+    /* Could not find matching entry. */
+    return eHAL_STATUS_FAILURE;
+}
+
+
+static void pmcProcessResponse( tpAniSirGlobal pMac, tSirSmeRsp *pMsg )
+{
+    tListElem *pEntry = NULL;
+    tSmeCmd *pCommand = NULL;
+    tANI_BOOLEAN fRemoveCommand = eANI_BOOLEAN_TRUE;
+
+    pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
+    if(pEntry)
+    {
+        pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
+
+        smsLog(pMac, LOG1, FL("process message = %d\n"), pMsg->messageType);
+
+    /* Process each different type of message. */
+    switch (pMsg->messageType)
+    {
+
+    /* We got a response to our IMPS request.  */
+    case eWNI_PMC_ENTER_IMPS_RSP:
+        smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_ENTER_IMPS_RSP with status = %d\n"), pMsg->statusCode);
+            if( (eSmeCommandEnterImps != pCommand->command) && (eSmeCommandEnterStandby != pCommand->command) )
+            {
+                smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_ENTER_IMPS_RSP without request\n"));
+                fRemoveCommand = eANI_BOOLEAN_FALSE;
+                break;
+            }
+        if(pMac->pmc.pmcState == REQUEST_IMPS)
+        {
+            /* Enter IMPS State if response indicates success. */
+            if (pMsg->statusCode == eSIR_SME_SUCCESS)
+            {
+                    pmcEnterImpsState(pMac);
+            }
+
+            /* If response is failure, then we stay in Full Power State and tell everyone that we aren't going into IMPS. */
+            else {
+                smsLog(pMac, LOGE, FL("Response message to request to enter IMPS indicates failure, status %x\n"),
+                       pMsg->statusCode);
+                    pmcEnterFullPowerState(pMac);
+            }
+        }
+        else if (pMac->pmc.pmcState == REQUEST_STANDBY)
+        {
+            /* Enter STANDBY State if response indicates success. */
+            if (pMsg->statusCode == eSIR_SME_SUCCESS)
+            {
+                    pmcEnterStandbyState(pMac);
+                    pmcDoStandbyCallbacks(pMac, eHAL_STATUS_SUCCESS);
+            }
+
+            /* If response is failure, then we stay in Full Power State
+               and tell everyone that we aren't going into STANDBY. */
+            else
+            {
+                smsLog(pMac, LOGE, "PMC: response message to request to enter "
+                       "standby indicates failure, status %x\n", pMsg->statusCode);
+                    pmcEnterFullPowerState(pMac);
+                    pmcDoStandbyCallbacks(pMac, eHAL_STATUS_FAILURE);
+            }
+        }
+        else
+        {
+            smsLog(pMac, LOGE, "PMC: Enter IMPS rsp rcvd when device is "
+               "in %d state\n", pMac->pmc.pmcState);
+        }
+        break;
+
+    /* We got a response to our wake from IMPS request. */
+    case eWNI_PMC_EXIT_IMPS_RSP:
+            smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_EXIT_IMPS_RSP with status = %d\n"), pMsg->statusCode);
+            if( eSmeCommandExitImps != pCommand->command )
+            {
+                smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_EXIT_IMPS_RSP without request\n"));
+                fRemoveCommand = eANI_BOOLEAN_FALSE;
+                break;
+            }
+            /* Check that we are in the correct state for this message. */
+            if (pMac->pmc.pmcState != REQUEST_FULL_POWER)
+            {
+                smsLog(pMac, LOGE, FL("Got Exit IMPS Response Message while in state %d\n"), pMac->pmc.pmcState);
+                break;
+            }
+
+            /* Enter Full Power State. */
+            if (pMsg->statusCode != eSIR_SME_SUCCESS)
+            {
+                smsLog(pMac, LOGP, FL("Response message to request to exit IMPS indicates failure, status %x\n"),
+                       pMsg->statusCode);
+            }
+            pmcEnterFullPowerState(pMac);
+        break;
+
+    /* We got a response to our BMPS request.  */
+    case eWNI_PMC_ENTER_BMPS_RSP:
+            smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_ENTER_BMPS_RSP with status = %d\n"), pMsg->statusCode);
+            if( eSmeCommandEnterBmps != pCommand->command )
+            {
+                smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_ENTER_BMPS_RSP without request\n"));
+                fRemoveCommand = eANI_BOOLEAN_FALSE;
+                break;
+            }
+            pMac->pmc.bmpsRequestQueued = eANI_BOOLEAN_FALSE;
+            /* Check that we are in the correct state for this message. */
+            if (pMac->pmc.pmcState != REQUEST_BMPS)
+            {
+                smsLog(pMac, LOGE, FL("Got Enter BMPS Response Message while in state %d\n"), pMac->pmc.pmcState);
+                break;
+            }
+
+        /* Enter BMPS State if response indicates success. */
+        if (pMsg->statusCode == eSIR_SME_SUCCESS)
+        {
+                pmcEnterBmpsState(pMac);
+            /* Note: If BMPS was requested because of start UAPSD,
+               there will no entries for BMPS callback routines and
+               pmcDoBmpsCallbacks will be a No-Op*/
+                pmcDoBmpsCallbacks(pMac, eHAL_STATUS_SUCCESS);
+         }
+        /* If response is failure, then we stay in Full Power State and tell everyone that we aren't going into BMPS. */
+        else
+        {
+                smsLog(pMac, LOGE, FL("Response message to request to enter BMPS indicates failure, status %x\n"),
+                   pMsg->statusCode);
+                pmcEnterFullPowerState(pMac);
+                //Do not call UAPSD callback here since it may be re-entered
+                pmcDoBmpsCallbacks(pMac, eHAL_STATUS_FAILURE);
+        }
+        break;
+
+    /* We got a response to our wake from BMPS request. */
+    case eWNI_PMC_EXIT_BMPS_RSP:
+            smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_EXIT_BMPS_RSP with status = %d\n"), pMsg->statusCode);
+            if( eSmeCommandExitBmps != pCommand->command )
+            {
+                smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_EXIT_BMPS_RSP without request\n"));
+                fRemoveCommand = eANI_BOOLEAN_FALSE;
+                break;
+            }
+            /* Check that we are in the correct state for this message. */
+            if (pMac->pmc.pmcState != REQUEST_FULL_POWER)
+            {
+                smsLog(pMac, LOGE, FL("Got Exit BMPS Response Message while in state %d\n"), pMac->pmc.pmcState);
+                break;
+            }
+
+            /* Enter Full Power State. */
+            if (pMsg->statusCode != eSIR_SME_SUCCESS)
+            {
+                smsLog(pMac, LOGP, FL("Response message to request to exit BMPS indicates failure, status %x\n"),
+                       pMsg->statusCode);
+            }
+            pmcEnterFullPowerState(pMac);
+        break;
+
+        /* We got a response to our Start UAPSD request.  */
+        case eWNI_PMC_ENTER_UAPSD_RSP:
+            smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_ENTER_UAPSD_RSP with status = %d\n"), pMsg->statusCode);
+            if( eSmeCommandEnterUapsd != pCommand->command )
+        {
+                smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_ENTER_UAPSD_RSP without request\n"));
+                fRemoveCommand = eANI_BOOLEAN_FALSE;
+                break;
+            }
+            /* Check that we are in the correct state for this message. */
+            if (pMac->pmc.pmcState != REQUEST_START_UAPSD)
+            {
+                smsLog(pMac, LOGE, FL("Got Enter Uapsd rsp Message while in state %d\n"), pMac->pmc.pmcState);
+                break;
+            }
+
+         /* Enter UAPSD State if response indicates success. */
+            if (pMsg->statusCode == eSIR_SME_SUCCESS) 
+            {
+                pmcEnterUapsdState(pMac);
+                pmcDoStartUapsdCallbacks(pMac, eHAL_STATUS_SUCCESS);
+         }
+         /* If response is failure, then we try to put the chip back in
+            BMPS mode*/
+            else {
+                smsLog(pMac, LOGE, "PMC: response message to request to enter "
+                   "UAPSD indicates failure, status %x\n", pMsg->statusCode);
+                //Need to reset the UAPSD flag so pmcEnterBmpsState won't try to enter UAPSD.
+                pMac->pmc.uapsdSessionRequired = FALSE;
+                pmcEnterBmpsState(pMac);
+                //UAPSD will not be retied in this case so tell requester we are done with failure
+                pmcDoStartUapsdCallbacks(pMac, eHAL_STATUS_FAILURE);
+         }
+         break;
+
+      /* We got a response to our Stop UAPSD request.  */
+      case eWNI_PMC_EXIT_UAPSD_RSP:
+         smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_EXIT_UAPSD_RSP with status = %d\n"), pMsg->statusCode);
+            if( eSmeCommandExitUapsd != pCommand->command )
+            {
+                smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_EXIT_UAPSD_RSP without request\n"));
+                fRemoveCommand = eANI_BOOLEAN_FALSE;
+                break;
+            }
+            /* Check that we are in the correct state for this message. */
+            if (pMac->pmc.pmcState != REQUEST_STOP_UAPSD)
+            {
+                smsLog(pMac, LOGE, FL("Got Exit Uapsd rsp Message while in state %d\n"), pMac->pmc.pmcState);
+                break;
+            }
+
+         /* Enter BMPS State */
+         if (pMsg->statusCode != eSIR_SME_SUCCESS) {
+            smsLog(pMac, LOGP, "PMC: response message to request to exit "
+               "UAPSD indicates failure, status %x\n", pMsg->statusCode);
+         }
+            pmcEnterBmpsState(pMac);
+         break;
+
+      /* We got a response to our enter WOWL request.  */
+      case eWNI_PMC_ENTER_WOWL_RSP:
+
+            if( eSmeCommandEnterWowl != pCommand->command )
+            {
+                smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_ENTER_WOWL_RSP without request\n"));
+                fRemoveCommand = eANI_BOOLEAN_FALSE;
+                break;
+            }
+            /* Check that we are in the correct state for this message. */
+            if (pMac->pmc.pmcState != REQUEST_ENTER_WOWL)
+            {
+                smsLog(pMac, LOGE, FL("Got eWNI_PMC_ENTER_WOWL_RSP while in state %s\n"), 
+                    pmcGetPmcStateStr(pMac->pmc.pmcState));
+                break;
+            }
+
+         /* Enter WOWL State if response indicates success. */
+         if (pMsg->statusCode == eSIR_SME_SUCCESS) {
+                pmcEnterWowlState(pMac);
+                pmcDoEnterWowlCallbacks(pMac, eHAL_STATUS_SUCCESS);
+         }
+
+         /* If response is failure, then we try to put the chip back in
+            BMPS mode*/
+         else {
+            smsLog(pMac, LOGE, "PMC: response message to request to enter "
+               "WOWL indicates failure, status %x\n", pMsg->statusCode);
+                pmcEnterBmpsState(pMac);
+                pmcDoEnterWowlCallbacks(pMac, eHAL_STATUS_FAILURE);
+         }
+         break;
+
+      /* We got a response to our exit WOWL request.  */
+      case eWNI_PMC_EXIT_WOWL_RSP:
+
+            if( eSmeCommandExitWowl != pCommand->command )
+            {
+                smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_EXIT_WOWL_RSP without request\n"));
+                fRemoveCommand = eANI_BOOLEAN_FALSE;
+                break;
+            }
+            /* Check that we are in the correct state for this message. */
+            if (pMac->pmc.pmcState != REQUEST_EXIT_WOWL)
+            {
+                smsLog(pMac, LOGE, FL("Got Exit WOWL rsp Message while in state %d\n"), pMac->pmc.pmcState);
+                break;
+            }
+
+         /* Enter BMPS State */
+         if (pMsg->statusCode != eSIR_SME_SUCCESS) {
+            smsLog(pMac, LOGP, "PMC: response message to request to exit "
+               "WOWL indicates failure, status %x\n", pMsg->statusCode);
+         }
+            pmcEnterBmpsState(pMac);
+         break;
+
+    default:
+        smsLog(pMac, LOGE, FL("Invalid message type %d received\n"), pMsg->messageType);
+        PMC_ABORT;
+        break;
+        }//switch
+
+        if( fRemoveCommand )
+        {
+            if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
+            {
+                pmcReleaseCommand( pMac, pCommand );
+                smeProcessPendingQueue( pMac );
+            }
+        }
+    }
+    else
+    {
+        smsLog(pMac, LOGE, FL("message type %d received but no request is found\n"), pMsg->messageType);
+    }
+}
+
+
+/******************************************************************************
+*
+* Name:  pmcMessageProcessor
+*
+* Description:
+*    Process a message received by PMC.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    pMsg - pointer to received message
+*
+* Returns:
+*    nothing
+*
+******************************************************************************/
+void pmcMessageProcessor (tHalHandle hHal, tSirSmeRsp *pMsg)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcMessageProcessor, message type %d\n"), pMsg->messageType);
+
+    switch( pMsg->messageType )
+    {
+    case eWNI_PMC_EXIT_BMPS_IND:
+    //When PMC needs to handle more indication from PE, they need to be added here.
+    {
+        /* Device left BMPS on its own. */
+        smsLog(pMac, LOGW, FL("Rcvd eWNI_PMC_EXIT_BMPS_IND with status = %d\n"), pMsg->statusCode);
+        /* Check that we are in the correct state for this message. */
+        switch(pMac->pmc.pmcState)
+        {
+        case BMPS:
+        case REQUEST_START_UAPSD:
+        case UAPSD:
+        case REQUEST_STOP_UAPSD:
+        case REQUEST_ENTER_WOWL:
+        case WOWL:
+        case REQUEST_EXIT_WOWL:
+        case REQUEST_FULL_POWER:
+            smsLog(pMac, LOGW, FL("Got eWNI_PMC_EXIT_BMPS_IND while in state %d\n"), pMac->pmc.pmcState);
+            break;
+        default:
+            smsLog(pMac, LOGE, FL("Got eWNI_PMC_EXIT_BMPS_IND while in state %d\n"), pMac->pmc.pmcState);
+            PMC_ABORT;
+            break;
+        }
+
+        /* Enter Full Power State. */
+        if (pMsg->statusCode != eSIR_SME_SUCCESS)
+        {
+            smsLog(pMac, LOGP, FL("Exit BMPS indication indicates failure, status %x\n"), pMsg->statusCode);
+        }
+        else
+        {
+            tpSirSmeExitBmpsInd pExitBmpsInd = (tpSirSmeExitBmpsInd)pMsg;
+            pmcEnterRequestFullPowerState(hHal, pExitBmpsInd->exitBmpsReason);
+        }
+        break;
+    }
+
+    default:
+        pmcProcessResponse( pMac, pMsg );
+        break;
+    }
+
+}
+
+
+tANI_BOOLEAN pmcValidateConnectState( tHalHandle hHal )
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+   if ( !csrIsInfraConnected( pMac ) )
+   {
+      smsLog(pMac, LOGW, "PMC: STA not associated. BMPS cannot be entered\n");
+      return eANI_BOOLEAN_FALSE;
+   }
+
+   //Cannot have other session
+   if ( csrIsIBSSStarted( pMac ) )
+   {
+      smsLog(pMac, LOGW, "PMC: IBSS started. BMPS cannot be entered\n");
+      return eANI_BOOLEAN_FALSE;
+   }
+   if ( csrIsBTAMPStarted( pMac ) )
+   {
+      smsLog(pMac, LOGW, "PMC: BT-AMP exists. BMPS cannot be entered\n");
+      return eANI_BOOLEAN_FALSE;
+   }
+   if ((vos_concurrent_sessions_running()) && 
+        csrIsConcurrentInfraConnected( pMac ))
+   {
+      smsLog(pMac, LOGW, "PMC: Multiple active sessions exists. BMPS cannot be entered\n");
+      return eANI_BOOLEAN_FALSE;
+   }
+   return eANI_BOOLEAN_TRUE;
+}
+
+tANI_BOOLEAN pmcAllowImps( tHalHandle hHal )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    //Cannot have other session like IBSS or BT AMP running
+    if ( csrIsIBSSStarted( pMac ) )
+    {
+       smsLog(pMac, LOGW, "PMC: IBSS started. IMPS cannot be entered\n");
+       return eANI_BOOLEAN_FALSE;
+    }
+    if ( csrIsBTAMPStarted( pMac ) )
+    {
+       smsLog(pMac, LOGW, "PMC: BT-AMP exists. IMPS cannot be entered\n");
+       return eANI_BOOLEAN_FALSE;
+    }
+
+    //All sessions must be disconnected to allow IMPS
+    if ( !csrIsAllSessionDisconnected( pMac ) )
+    {
+       smsLog(pMac, LOGW, "PMC: Atleast one connected session. IMPS cannot be entered\n");
+       return eANI_BOOLEAN_FALSE;
+    }
+
+    return eANI_BOOLEAN_TRUE;
+}
+
+/******************************************************************************
+*
+* Name:  pmcRequestBmps
+*
+* Description:
+*    Request that the device be put in BMPS state.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    callbackRoutine - Callback routine invoked in case of success/failure
+*    callbackContext - value to be passed as parameter to routine specified
+*                      above
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - device is in BMPS state
+*    eHAL_STATUS_FAILURE - device cannot be brought to BMPS state
+*    eHAL_STATUS_PMC_PENDING - device is being brought to BMPS state,
+*
+******************************************************************************/
+eHalStatus pmcRequestBmps (
+    tHalHandle hHal,
+    void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+    void *callbackContext)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tpRequestBmpsEntry pEntry;
+   eHalStatus status;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+   WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+   vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+   psRequest.event_subtype = WLAN_BMPS_ENTER_REQ;
+
+   WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+   smsLog(pMac, LOG2, "PMC: entering pmcRequestBmps");
+
+   /* If already in BMPS, just return. */
+   if (pMac->pmc.pmcState == BMPS || REQUEST_START_UAPSD == pMac->pmc.pmcState || UAPSD == pMac->pmc.pmcState)
+   {
+      smsLog(pMac, LOG2, "PMC: Device already in BMPS pmcState %d", pMac->pmc.pmcState);
+      pMac->pmc.bmpsRequestedByHdd = TRUE;
+      return eHAL_STATUS_SUCCESS;
+   }
+   
+   status = pmcEnterBmpsCheck( pMac );
+   if(HAL_STATUS_SUCCESS( status ))
+   {
+      status = pmcEnterRequestBmpsState(hHal);
+      /* Enter Request BMPS State. */
+      if ( HAL_STATUS_SUCCESS( status ) )
+      {
+         /* Remember that HDD requested BMPS. This flag will be used to put the
+            device back into BMPS if any module other than HDD (e.g. CSR, QoS, or BAP)
+            requests full power for any reason */
+         pMac->pmc.bmpsRequestedByHdd = TRUE;
+
+         /* If able to enter Request BMPS State, then request is pending.
+            Allocate entry for request BMPS callback routine list. */
+         if (palAllocateMemory(
+               pMac->hHdd, (void **)&pEntry,
+               sizeof(tRequestBmpsEntry)) != eHAL_STATUS_SUCCESS)
+         {
+            smsLog(pMac, LOGE, "PMC: cannot allocate memory for request "
+                  "BMPS routine list entry\n");
+            return eHAL_STATUS_FAILURE;
+         }
+
+         /* Store routine and context in entry. */
+         pEntry->callbackRoutine = callbackRoutine;
+         pEntry->callbackContext = callbackContext;
+
+         /* Add entry to list. */
+         csrLLInsertTail(&pMac->pmc.requestBmpsList, &pEntry->link, FALSE);
+
+         status = eHAL_STATUS_PMC_PENDING;
+      }
+      else
+      {
+         status = eHAL_STATUS_FAILURE;
+      }
+   }
+
+   return status;
+}
+
+/******************************************************************************
+*
+* Name:  pmcStartUapsd
+*
+* Description:
+*    Request that the device be put in UAPSD state.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    callbackRoutine - Callback routine invoked in case of success/failure
+*    callbackContext - value to be passed as parameter to routine specified
+*                      above
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - device is in UAPSD state
+*    eHAL_STATUS_FAILURE - device cannot be brought to UAPSD state
+*    eHAL_STATUS_PMC_PENDING - device is being brought to UAPSD state
+*    eHAL_STATUS_PMC_DISABLED - UAPSD is disabled or BMPS mode is disabled
+*
+******************************************************************************/
+eHalStatus pmcStartUapsd (
+    tHalHandle hHal,
+    void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+    void *callbackContext)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   tpStartUapsdEntry pEntry;
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+   WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+   vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+   psRequest.event_subtype = WLAN_UAPSD_START_REQ;
+
+   WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+   smsLog(pMac, LOG2, "PMC: entering pmcStartUapsd");
+
+   if( !PMC_IS_READY(pMac) )
+   {
+       smsLog(pMac, LOGE, FL("Requesting UAPSD when PMC not ready\n"));
+       smsLog(pMac, LOGE, FL("pmcReady = %d pmcState = %s\n"), 
+           pMac->pmc.pmcReady, pmcGetPmcStateStr(pMac->pmc.pmcState));
+       return eHAL_STATUS_FAILURE;
+   }
+
+   /* Check if BMPS is enabled. */
+   if (!pMac->pmc.bmpsEnabled)
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot enter UAPSD. BMPS is disabled\n");
+      return eHAL_STATUS_PMC_DISABLED;
+   }
+
+   /* Check if UAPSD is enabled. */
+   if (!pMac->pmc.uapsdEnabled)
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot enter UAPSD. UAPSD is disabled\n");
+      return eHAL_STATUS_PMC_DISABLED;
+   }
+
+   /* If already in UAPSD, just return. */
+   if (pMac->pmc.pmcState == UAPSD)
+      return eHAL_STATUS_SUCCESS;
+
+   /* Check that we are associated. */
+   if (!pmcValidateConnectState( pMac ))
+   {
+      smsLog(pMac, LOGE, "PMC: STA not associated with an AP. UAPSD cannot be entered\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   /* Enter REQUEST_START_UAPSD State. */
+   if (pmcEnterRequestStartUapsdState(hHal) != eHAL_STATUS_SUCCESS)
+      return eHAL_STATUS_FAILURE;
+
+   if( NULL != callbackRoutine )
+   {
+      /* If success then request is pending. Allocate entry for callback routine list. */
+      if (palAllocateMemory(pMac->hHdd, (void **)&pEntry,
+            sizeof(tStartUapsdEntry)) != eHAL_STATUS_SUCCESS)
+      {
+         smsLog(pMac, LOGE, "PMC: cannot allocate memory for request "
+            "start UAPSD routine list entry\n");
+         return eHAL_STATUS_FAILURE;
+      }
+
+      /* Store routine and context in entry. */
+      pEntry->callbackRoutine = callbackRoutine;
+      pEntry->callbackContext = callbackContext;
+
+      /* Add entry to list. */
+      csrLLInsertTail(&pMac->pmc.requestStartUapsdList, &pEntry->link, FALSE);
+   }
+
+   return eHAL_STATUS_PMC_PENDING;
+}
+
+/******************************************************************************
+*
+* Name:  pmcStopUapsd
+*
+* Description:
+*    Request that the device be put out of UAPSD state.
+*
+* Parameters:
+*    hHal - HAL handle for device
+*
+* Returns:
+*    eHAL_STATUS_SUCCESS - device is put out of UAPSD and back in BMPS state
+*    eHAL_STATUS_FAILURE - device cannot be brought out of UAPSD state
+*
+******************************************************************************/
+eHalStatus pmcStopUapsd (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+   WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+   vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+   psRequest.event_subtype = WLAN_UAPSD_STOP_REQ;
+
+   WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+   smsLog(pMac, LOG2, "PMC: entering pmcStopUapsd");
+
+   /* Clear any buffered command for entering UAPSD */
+   pMac->pmc.uapsdSessionRequired = FALSE;
+
+   /* Nothing to be done if we are already out of UAPSD. This can happen if
+      some other module (HDD, BT-AMP) requested Full Power.*/
+   if (pMac->pmc.pmcState != UAPSD && pMac->pmc.pmcState != REQUEST_STOP_UAPSD)
+   {
+      smsLog(pMac, LOGW, "PMC: Device is already out of UAPSD "
+         "state. Current state is %d\n", pMac->pmc.pmcState);
+      return eHAL_STATUS_SUCCESS;
+   }
+
+   /* Enter REQUEST_STOP_UAPSD State*/
+   if (pmcEnterRequestStopUapsdState(hHal) != eHAL_STATUS_SUCCESS)
+      return eHAL_STATUS_FAILURE;
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcRequestStandby
+    \brief  Request that the device be put in standby.
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine - Callback routine invoked in case of success/failure
+    \param  callbackContext - value to be passed as parameter to callback
+    \return eHalStatus  
+      eHAL_STATUS_SUCCESS - device is in Standby mode
+      eHAL_STATUS_FAILURE - device cannot be put in standby mode
+      eHAL_STATUS_PMC_PENDING - device is being put in standby mode
+  ---------------------------------------------------------------------------*/
+extern eHalStatus pmcRequestStandby (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+   WLAN_VOS_DIAG_EVENT_DEF(psRequest, vos_event_wlan_powersave_payload_type);
+
+   vos_mem_zero(&psRequest, sizeof(vos_event_wlan_powersave_payload_type));
+   psRequest.event_subtype = WLAN_ENTER_STANDBY_REQ;
+
+   WLAN_VOS_DIAG_EVENT_REPORT(&psRequest, EVENT_WLAN_POWERSAVE_GENERIC);
+#endif
+
+   smsLog(pMac, LOG2, "PMC: entering pmcRequestStandby");
+
+   /* Check if standby is enabled. */
+   if (!pMac->pmc.standbyEnabled)
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot enter standby. Standby is disabled\n");
+      return eHAL_STATUS_PMC_DISABLED;
+   }
+
+   if( !PMC_IS_READY(pMac) )
+   {
+       smsLog(pMac, LOGE, FL("Requesting standby when PMC not ready\n"));
+       smsLog(pMac, LOGE, FL("pmcReady = %d pmcState = %s\n"), 
+           pMac->pmc.pmcReady, pmcGetPmcStateStr(pMac->pmc.pmcState));
+       return eHAL_STATUS_FAILURE;
+   }
+
+   /* If already in STANDBY, just return. */
+   if (pMac->pmc.pmcState == STANDBY)
+      return eHAL_STATUS_SUCCESS;
+
+   
+   if (csrIsIBSSStarted(pMac) || csrIsBTAMPStarted(pMac))
+   {
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, 
+          "WLAN: IBSS or BT-AMP session present. Cannot honor standby request");
+      return eHAL_STATUS_PMC_NOT_NOW;
+   }
+
+   /* Enter Request Standby State. */
+   if (pmcEnterRequestStandbyState(hHal) != eHAL_STATUS_SUCCESS)
+      return eHAL_STATUS_FAILURE;
+
+   /* Save the callback routine for when we need it. */
+   pMac->pmc.standbyCallbackRoutine = callbackRoutine;
+   pMac->pmc.standbyCallbackContext = callbackContext;
+
+   return eHAL_STATUS_PMC_PENDING;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcRegisterDeviceStateUpdateInd
+    \brief  Register a callback routine that is called whenever
+            the device enters a new device state (Full Power, BMPS, UAPSD)
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine -  Callback routine to be registered
+    \param  callbackContext -  Cookie to be passed back during callback
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully registered
+            eHAL_STATUS_FAILURE - not successfully registered  
+  ---------------------------------------------------------------------------*/
+extern eHalStatus pmcRegisterDeviceStateUpdateInd (tHalHandle hHal, 
+   void (*callbackRoutine) (void *callbackContext, tPmcState pmcState),
+   void *callbackContext)
+{
+
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tpDeviceStateUpdateIndEntry pEntry;
+
+    smsLog(pMac, LOG2, FL("Entering pmcRegisterDeviceStateUpdateInd"));
+
+    /* Allocate entry for device power state update indication. */
+    if (palAllocateMemory(pMac->hHdd, (void **)&pEntry, sizeof(tDeviceStateUpdateIndEntry)) != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Cannot allocate memory for device power state update indication\n"));
+        PMC_ABORT;
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Store routine in entry. */
+    pEntry->callbackRoutine = callbackRoutine;
+    pEntry->callbackContext = callbackContext;
+
+    /* Add entry to list. */
+    csrLLInsertTail(&pMac->pmc.deviceStateUpdateIndList, &pEntry->link, FALSE);
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcDeregisterDeviceStateUpdateInd
+    \brief  Deregister a routine that was registered for device state changes
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine -  Callback routine to be deregistered
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully deregistered
+            eHAL_STATUS_FAILURE - not successfully deregistered  
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcDeregisterDeviceStateUpdateInd (tHalHandle hHal, 
+   void (*callbackRoutine) (void *callbackContext, tPmcState pmcState))
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tListElem *pEntry;
+    tpDeviceStateUpdateIndEntry pDeviceStateUpdateIndEntry;
+
+    smsLog(pMac, LOG2, FL("Entering pmcDeregisterDeviceStateUpdateInd"));
+
+    /* Find entry in the power save update routine list that matches
+       the specified routine and remove it. */
+    pEntry = csrLLPeekHead(&pMac->pmc.deviceStateUpdateIndList, FALSE);
+    while (pEntry != NULL)
+    {
+        pDeviceStateUpdateIndEntry = GET_BASE_ADDR(pEntry, tDeviceStateUpdateIndEntry, link);
+        if (pDeviceStateUpdateIndEntry->callbackRoutine == callbackRoutine)
+        {
+            if (!csrLLRemoveEntry(&pMac->pmc.deviceStateUpdateIndList, pEntry, FALSE))
+            {
+                smsLog(pMac, LOGE, FL("Cannot remove device state update ind entry from list\n"));
+                return eHAL_STATUS_FAILURE;
+            }
+            if (palFreeMemory(pMac->hHdd, pDeviceStateUpdateIndEntry) != eHAL_STATUS_SUCCESS)
+            {
+                smsLog(pMac, LOGE, FL("Cannot free memory for device state update ind routine list entry\n"));
+                PMC_ABORT;
+                return eHAL_STATUS_FAILURE;
+            }
+            return eHAL_STATUS_SUCCESS;
+        }
+        pEntry = csrLLNext(&pMac->pmc.deviceStateUpdateIndList, pEntry, FALSE);
+    }
+
+    /* Could not find matching entry. */
+    return eHAL_STATUS_FAILURE;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcReady
+    \brief  fn to inform PMC that eWNI_SME_SYS_READY_IND has been sent to PE.
+            This acts as a trigger to send a message to PE to update the power
+            save related conig to FW. Note that if HDD configures any power save
+            related stuff before this API is invoked, PMC will buffer all the 
+            configutaion.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcReady(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    smsLog(pMac, LOG2, FL("Entering pmcReady"));
+
+    if(pMac->pmc.pmcState == STOPPED)
+    {
+        smsLog(pMac, LOGP, FL("pmcReady is invoked even before pmcStart"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    pMac->pmc.pmcReady = TRUE;
+    if (pmcSendPowerSaveConfigMessage(hHal) != eHAL_STATUS_SUCCESS)
+    {
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcWowlAddBcastPattern
+    \brief  Add a pattern for Pattern Byte Matching in Wowl mode. Firmware will
+            do a pattern match on these patterns when Wowl is enabled during BMPS
+            mode. Note that Firmware performs the pattern matching only on 
+            broadcast frames and while Libra is in BMPS mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  pattern -  Pointer to the pattern to be added
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot add pattern
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcWowlAddBcastPattern (
+    tHalHandle hHal, 
+    tpSirWowlAddBcastPtrn pattern)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+    vos_log_powersave_wow_add_ptrn_pkt_type *log_ptr = NULL;
+    WLAN_VOS_DIAG_LOG_ALLOC(log_ptr, vos_log_powersave_wow_add_ptrn_pkt_type, LOG_WLAN_POWERSAVE_WOW_ADD_PTRN_C);
+#endif //#ifdef FEATURE_WLAN_DIAG_SUPPORT
+
+    smsLog(pMac, LOG2, "PMC: entering pmcWowlAddBcastPattern");
+
+    if(pattern == NULL)
+    {
+        smsLog(pMac, LOGE, FL("Null broadcast pattern being passed\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+    if( log_ptr )
+    {
+       log_ptr->pattern_id = pattern->ucPatternId;
+       log_ptr->pattern_byte_offset = pattern->ucPatternByteOffset;
+       log_ptr->pattern_size = pattern->ucPatternSize;
+       log_ptr->pattern_mask_size = pattern->ucPatternMaskSize;
+
+       vos_mem_copy(log_ptr->pattern, pattern->ucPattern, SIR_WOWL_BCAST_PATTERN_MAX_SIZE);
+       /* 1 bit in the pattern mask denotes 1 byte of pattern hence pattern mask size is 1/8 */
+       vos_mem_copy(log_ptr->pattern_mask, pattern->ucPatternMask, SIR_WOWL_BCAST_PATTERN_MAX_SIZE >> 3);
+    }
+
+    WLAN_VOS_DIAG_LOG_REPORT(log_ptr);
+#endif
+
+
+    if(pattern->ucPatternId >= SIR_WOWL_BCAST_MAX_NUM_PATTERNS )
+    {
+        smsLog(pMac, LOGE, FL("Pattern Id must range from 0 to %d\n"), SIR_WOWL_BCAST_MAX_NUM_PATTERNS-1);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    if( pMac->pmc.pmcState == STANDBY || pMac->pmc.pmcState == REQUEST_STANDBY )
+    {
+        smsLog(pMac, LOGE, FL("Cannot add WoWL Pattern as chip is in %s state\n"),
+           pmcGetPmcStateStr(pMac->pmc.pmcState));
+        return eHAL_STATUS_FAILURE;
+    }
+    if( pMac->pmc.pmcState == IMPS || pMac->pmc.pmcState == REQUEST_IMPS )
+    {
+        //Wake up the chip first
+        eHalStatus status = pmcDeferMsg( pMac, eWNI_PMC_WOWL_ADD_BCAST_PTRN, 
+                                    pattern, sizeof(tSirWowlAddBcastPtrn) );
+
+        if( eHAL_STATUS_PMC_PENDING == status )
+        {
+            return eHAL_STATUS_SUCCESS;
+        }
+        else 
+        {
+            //either fail or already in full power
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                return ( status );
+            }
+            //else let it through because it is in full power state
+        }
+    }
+
+    if (pmcSendMessage(hHal, eWNI_PMC_WOWL_ADD_BCAST_PTRN, pattern, sizeof(tSirWowlAddBcastPtrn))
+        != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Send of eWNI_PMC_WOWL_ADD_BCAST_PTRN to PE failed\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcWowlDelBcastPattern
+    \brief  Delete a pattern that was added for Pattern Byte Matching.
+    \param  hHal - The handle returned by macOpen.
+    \param  pattern -  Pattern to be deleted
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot delete pattern
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcWowlDelBcastPattern (
+    tHalHandle hHal, 
+    tpSirWowlDelBcastPtrn pattern)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+    WLAN_VOS_DIAG_EVENT_DEF(wowRequest, vos_event_wlan_powersave_wow_payload_type);
+
+    vos_mem_zero(&wowRequest, sizeof(vos_event_wlan_powersave_wow_payload_type));
+    wowRequest.event_subtype = WLAN_WOW_DEL_PTRN_REQ;
+    wowRequest.wow_del_ptrn_id = pattern->ucPatternId; 
+
+    WLAN_VOS_DIAG_EVENT_REPORT(&wowRequest, EVENT_WLAN_POWERSAVE_WOW);
+#endif
+
+    smsLog(pMac, LOG2, "PMC: entering pmcWowlDelBcastPattern");
+
+    if(pattern->ucPatternId >= SIR_WOWL_BCAST_MAX_NUM_PATTERNS )
+    {
+        smsLog(pMac, LOGE, FL("Pattern Id must range from 0 to %d\n"), 
+            SIR_WOWL_BCAST_MAX_NUM_PATTERNS-1);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    if(pMac->pmc.pmcState == STANDBY || pMac->pmc.pmcState == REQUEST_STANDBY)
+    {
+        smsLog(pMac, LOGE, FL("Cannot delete WoWL Pattern as chip is in %s state\n"),
+           pmcGetPmcStateStr(pMac->pmc.pmcState));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    if( pMac->pmc.pmcState == IMPS || pMac->pmc.pmcState == REQUEST_IMPS )
+    {
+        //Wake up the chip first
+        eHalStatus status = pmcDeferMsg( pMac, eWNI_PMC_WOWL_DEL_BCAST_PTRN, 
+                                    pattern, sizeof(tSirWowlDelBcastPtrn) );
+
+        if( eHAL_STATUS_PMC_PENDING == status )
+        {
+            return eHAL_STATUS_SUCCESS;
+        }
+        else 
+        {
+            //either fail or already in full power
+            if( !HAL_STATUS_SUCCESS( status ) )
+            {
+                return ( status );
+            }
+            //else let it through because it is in full power state
+        }
+    }
+
+    if (pmcSendMessage(hHal, eWNI_PMC_WOWL_DEL_BCAST_PTRN, pattern, sizeof(tSirWowlDelBcastPtrn))
+        != eHAL_STATUS_SUCCESS)
+    {
+        smsLog(pMac, LOGE, FL("Send of eWNI_PMC_WOWL_DEL_BCAST_PTRN to PE failed\n"));
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcEnterWowl
+    \brief  Request that the device be brought to full power state.
+            Note 1: If "fullPowerReason" specificied in this API is set to
+            eSME_FULL_PWR_NEEDED_BY_HDD, PMC will clear any "buffered wowl" requests
+            and also clear any "buffered BMPS requests by HDD". Assumption is that since
+            HDD is requesting full power, we need to undo any previous HDD requests for 
+            BMPS (using sme_RequestBmps) or WoWL (using sme_EnterWoWL). If the reason is
+            specified anything other than above, the buffered requests for BMPS and WoWL
+            will not be cleared.
+            Note 2: Requesting full power (no matter what the fullPowerReason is) doesn't
+            disable the "auto bmps timer" (if it is enabled) or clear any "buffered uapsd
+            request".
+            Note 3: When the device finally enters Full Power PMC will start a timer 
+            if any of the following holds true:
+            - Auto BMPS mode is enabled
+            - Uapsd request is pending
+            - HDD's request for BMPS is pending
+            - HDD's request for WoWL is pending
+            On timer expiry PMC will attempt to put the device in BMPS mode if following 
+            (in addition to those listed above) holds true:
+            - Polling of all modules through the Power Save Check routine passes
+            - STA is associated to an access point
+    \param  hHal - The handle returned by macOpen.
+    \param  - enterWowlCallbackRoutine Callback routine invoked in case of success/failure
+    \param  - enterWowlCallbackContext -  Cookie to be passed back during callback
+    \param  - wakeReasonIndCB Callback routine invoked for Wake Reason Indication
+    \param  - wakeReasonIndCBContext -  Cookie to be passed back during callback
+    \param  - fullPowerReason - Reason why this API is being invoked. SME needs to
+              distinguish between BAP and HDD requests
+    \return eHalStatus - status 
+     eHAL_STATUS_SUCCESS - device brought to full power state
+     eHAL_STATUS_FAILURE - device cannot be brought to full power state
+     eHAL_STATUS_PMC_PENDING - device is being brought to full power state,
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcEnterWowl ( 
+    tHalHandle hHal, 
+    void (*enterWowlCallbackRoutine) (void *callbackContext, eHalStatus status),
+    void *enterWowlCallbackContext,
+#ifdef WLAN_WAKEUP_EVENTS
+    void (*wakeReasonIndCB) (void *callbackContext, tpSirWakeReasonInd pWakeReasonInd),
+    void *wakeReasonIndCBContext,
+#endif // WLAN_WAKEUP_EVENTS
+    tpSirSmeWowlEnterParams wowlEnterParams)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+   WLAN_VOS_DIAG_EVENT_DEF(wowRequest, vos_event_wlan_powersave_wow_payload_type);
+
+   vos_mem_zero(&wowRequest, sizeof(vos_event_wlan_powersave_wow_payload_type));
+   wowRequest.event_subtype = WLAN_WOW_ENTER_REQ;
+   wowRequest.wow_type = 0;
+
+   if(wowlEnterParams->ucMagicPktEnable)
+   {
+       wowRequest.wow_type |= 1;
+       vos_mem_copy(wowRequest.wow_magic_pattern, (tANI_U8 *)wowlEnterParams->magicPtrn, 6);
+   }
+
+   if(wowlEnterParams->ucPatternFilteringEnable)
+   {
+       wowRequest.wow_type |= 2;
+   }
+
+   WLAN_VOS_DIAG_EVENT_REPORT(&wowRequest, EVENT_WLAN_POWERSAVE_WOW);
+#endif
+
+   smsLog(pMac, LOG2, "PMC: entering pmcEnterWowl\n");
+
+   if( !PMC_IS_READY(pMac) )
+   {
+       smsLog(pMac, LOGE, FL("Requesting WoWL when PMC not ready\n"));
+       smsLog(pMac, LOGE, FL("pmcReady = %d pmcState = %s\n"), 
+           pMac->pmc.pmcReady, pmcGetPmcStateStr(pMac->pmc.pmcState));
+       return eHAL_STATUS_FAILURE;
+   }
+
+   /* Check if BMPS is enabled. */
+   if (!pMac->pmc.bmpsEnabled)
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot enter WoWL. BMPS is disabled\n");
+      return eHAL_STATUS_PMC_DISABLED;
+   }
+
+   /* Check if WoWL is enabled. */
+   if (!pMac->pmc.wowlEnabled)
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot enter WoWL. WoWL is disabled\n");
+      return eHAL_STATUS_PMC_DISABLED;
+   }
+
+   /* Check that we are associated with single Session. */
+   if (!pmcValidateConnectState( pMac ))
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot enable WOWL. STA not associated "
+             "with an Access Point in Infra Mode with single active session\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   /* Is there a pending UAPSD request? HDD should have triggered QoS
+      module to do the necessary cleanup before triggring WOWL*/
+   if(pMac->pmc.uapsdSessionRequired)
+   {
+      smsLog(pMac, LOGE, "PMC: Cannot request WOWL. Pending UAPSD request\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   /* Check that entry into a power save mode is allowed at this time. */
+   if (pMac->pmc.pmcState == FULL_POWER && !pmcPowerSaveCheck(hHal))
+   {
+      smsLog(pMac, LOGE, "PMC: Power save check failed. WOWL request "
+             "will not be accepted\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   // To avoid race condition, set callback routines before sending message.
+   /* cache the WOWL information */
+   pMac->pmc.wowlEnterParams = *wowlEnterParams;
+   pMac->pmc.enterWowlCallbackRoutine = enterWowlCallbackRoutine;
+   pMac->pmc.enterWowlCallbackContext = enterWowlCallbackContext;
+#ifdef WLAN_WAKEUP_EVENTS
+   /* Cache the Wake Reason Indication callback information */
+   pMac->pmc.wakeReasonIndCB = wakeReasonIndCB;
+   pMac->pmc.wakeReasonIndCBContext = wakeReasonIndCBContext;
+#endif // WLAN_WAKEUP_EVENTS
+
+   /* Enter Request WOWL State. */
+   if (pmcRequestEnterWowlState(hHal, wowlEnterParams) != eHAL_STATUS_SUCCESS)
+      return eHAL_STATUS_FAILURE;
+
+   pMac->pmc.wowlModeRequired = TRUE;
+
+   return eHAL_STATUS_PMC_PENDING;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcExitWowl
+    \brief  This is the SME API exposed to HDD to request exit from WoWLAN mode. 
+            SME will initiate exit from WoWLAN mode and device will be put in BMPS 
+            mode.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Device cannot exit WoWLAN mode.
+            eHAL_STATUS_SUCCESS  Request accepted to exit WoWLAN mode. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcExitWowl (tHalHandle hHal)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT    
+   WLAN_VOS_DIAG_EVENT_DEF(wowRequest, vos_event_wlan_powersave_wow_payload_type);
+
+   vos_mem_zero(&wowRequest, sizeof(vos_event_wlan_powersave_wow_payload_type));
+   wowRequest.event_subtype = WLAN_WOW_EXIT_REQ;
+
+   WLAN_VOS_DIAG_EVENT_REPORT(&wowRequest, EVENT_WLAN_POWERSAVE_WOW);
+#endif
+
+   smsLog(pMac, LOG2, "PMC: entering pmcExitWowl");
+
+   /* Clear any buffered command for entering WOWL */
+   pMac->pmc.wowlModeRequired = FALSE;
+
+   /* Enter REQUEST_EXIT_WOWL State*/
+   if (pmcRequestExitWowlState(hHal) != eHAL_STATUS_SUCCESS)
+      return eHAL_STATUS_FAILURE;
+
+   /* Clear the callback routines */
+   pMac->pmc.enterWowlCallbackRoutine = NULL;
+   pMac->pmc.enterWowlCallbackContext = NULL;
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+
+
+/* ---------------------------------------------------------------------------
+    \fn pmcSetHostOffload
+    \brief  Set the host offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest - Pointer to the offload request.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the offload.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcSetHostOffload (tHalHandle hHal, tpSirHostOffloadReq pRequest)
+{
+    tpSirHostOffloadReq pRequestBuf;
+    vos_msg_t msg;
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s: IP address = %d.%d.%d.%d", __FUNCTION__,
+        pRequest->params.hostIpv4Addr[0], pRequest->params.hostIpv4Addr[1],
+        pRequest->params.hostIpv4Addr[2], pRequest->params.hostIpv4Addr[3]);
+
+    pRequestBuf = vos_mem_malloc(sizeof(tSirHostOffloadReq));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate memory for host offload request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+    vos_mem_copy(pRequestBuf, pRequest, sizeof(tSirHostOffloadReq));
+
+    msg.type = WDA_SET_HOST_OFFLOAD;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post WDA_SET_HOST_OFFLOAD message to WDA", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcSetKeepAlive
+    \brief  Set the Keep Alive feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest - Pointer to the Keep Alive.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the keepalive.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcSetKeepAlive (tHalHandle hHal, tpSirKeepAliveReq pRequest)
+{
+    tpSirKeepAliveReq pRequestBuf;
+    vos_msg_t msg;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_LOW, "%s: "
+                  "WDA_SET_KEEP_ALIVE message", __FUNCTION__);
+
+    pRequestBuf = vos_mem_malloc(sizeof(tSirKeepAliveReq));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+                  "Not able to allocate memory for keep alive request",
+                  __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+    vos_mem_copy(pRequestBuf, pRequest, sizeof(tSirKeepAliveReq));
+    
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_LOW, "buff TP %d "
+              "input TP %d ", pRequestBuf->timePeriod, pRequest->timePeriod);
+
+    msg.type = WDA_SET_KEEP_ALIVE;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+                  "Not able to post WDA_SET_KEEP_ALIVE message to WDA",
+                  __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+#ifdef WLAN_NS_OFFLOAD
+
+/* ---------------------------------------------------------------------------
+    \fn pmcSetNSOffload
+    \brief  Set the host offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest - Pointer to the offload request.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the offload.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcSetNSOffload (tHalHandle hHal, tpSirHostOffloadReq pRequest)
+{
+    tpSirHostOffloadReq pRequestBuf;
+    vos_msg_t msg;
+    int i;
+
+    pRequestBuf = vos_mem_malloc(sizeof(tSirHostOffloadReq));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate memory for NS offload request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+    vos_mem_copy(pRequestBuf, pRequest, sizeof(tSirHostOffloadReq));
+
+    msg.type = WDA_SET_NS_OFFLOAD;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post SIR_HAL_SET_HOST_OFFLOAD message to HAL", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+#endif //WLAN_NS_OFFLOAD
+
+
+void pmcClosePowerSaveCheckList(tpAniSirGlobal pMac)
+{
+    tListElem *pEntry;
+    tpPowerSaveCheckEntry pPowerSaveCheckEntry;
+
+    csrLLLock(&pMac->pmc.powerSaveCheckList);
+    while ( (pEntry = csrLLRemoveHead(&pMac->pmc.powerSaveCheckList, FALSE)) )
+    {
+        pPowerSaveCheckEntry = GET_BASE_ADDR(pEntry, tPowerSaveCheckEntry, link);
+        if (palFreeMemory(pMac->hHdd, pPowerSaveCheckEntry) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot free memory \n"));
+            PMC_ABORT;
+            break;
+        }
+    }
+    csrLLUnlock(&pMac->pmc.powerSaveCheckList);
+    csrLLClose(&pMac->pmc.powerSaveCheckList);
+}
+
+
+void pmcCloseRequestFullPowerList(tpAniSirGlobal pMac)
+{
+    tListElem *pEntry;
+    tpRequestFullPowerEntry pRequestFullPowerEntry;
+
+    csrLLLock(&pMac->pmc.requestFullPowerList);
+    while ( (pEntry = csrLLRemoveHead(&pMac->pmc.requestFullPowerList, FALSE)) )
+    {
+        pRequestFullPowerEntry = GET_BASE_ADDR(pEntry, tRequestFullPowerEntry, link);
+        if (palFreeMemory(pMac->hHdd, pRequestFullPowerEntry) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot free memory \n"));
+            PMC_ABORT;
+            break;
+        }
+    }
+    csrLLUnlock(&pMac->pmc.requestFullPowerList);
+    csrLLClose(&pMac->pmc.requestFullPowerList);
+}
+
+
+void pmcCloseRequestBmpsList(tpAniSirGlobal pMac)
+{
+    tListElem *pEntry;
+    tpRequestBmpsEntry pRequestBmpsEntry;
+
+    csrLLLock(&pMac->pmc.requestBmpsList);
+    while ( (pEntry = csrLLRemoveHead(&pMac->pmc.requestBmpsList, FALSE)) )
+    {
+        pRequestBmpsEntry = GET_BASE_ADDR(pEntry, tRequestBmpsEntry, link);
+        if (palFreeMemory(pMac->hHdd, pRequestBmpsEntry) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot free memory \n"));
+            PMC_ABORT;
+            break;
+        }
+    }
+    csrLLUnlock(&pMac->pmc.requestBmpsList);
+    csrLLClose(&pMac->pmc.requestBmpsList);
+}
+
+
+void pmcCloseRequestStartUapsdList(tpAniSirGlobal pMac)
+{
+    tListElem *pEntry;
+    tpStartUapsdEntry pStartUapsdEntry;
+
+    csrLLLock(&pMac->pmc.requestStartUapsdList);
+    while ( (pEntry = csrLLRemoveHead(&pMac->pmc.requestStartUapsdList, FALSE)) )
+    {
+        pStartUapsdEntry = GET_BASE_ADDR(pEntry, tStartUapsdEntry, link);
+        if (palFreeMemory(pMac->hHdd, pStartUapsdEntry) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot free memory \n"));
+            PMC_ABORT;
+            break;
+        }
+    }
+    csrLLUnlock(&pMac->pmc.requestStartUapsdList);
+    csrLLClose(&pMac->pmc.requestStartUapsdList);
+}
+
+
+void pmcCloseDeviceStateUpdateList(tpAniSirGlobal pMac)
+{
+    tListElem *pEntry;
+    tpDeviceStateUpdateIndEntry pDeviceStateUpdateIndEntry;
+
+    csrLLLock(&pMac->pmc.deviceStateUpdateIndList);
+    while ( (pEntry = csrLLRemoveHead(&pMac->pmc.deviceStateUpdateIndList, FALSE)) )
+    {
+        pDeviceStateUpdateIndEntry = GET_BASE_ADDR(pEntry, tDeviceStateUpdateIndEntry, link);
+        if (palFreeMemory(pMac->hHdd, pDeviceStateUpdateIndEntry) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot free memory \n"));
+            PMC_ABORT;
+            break;
+        }
+    }
+    csrLLUnlock(&pMac->pmc.deviceStateUpdateIndList);
+    csrLLClose(&pMac->pmc.deviceStateUpdateIndList);
+}
+
+
+void pmcCloseDeferredMsgList(tpAniSirGlobal pMac)
+{
+    tListElem *pEntry;
+    tPmcDeferredMsg *pDeferredMsg;
+
+    csrLLLock(&pMac->pmc.deferredMsgList);
+    while ( (pEntry = csrLLRemoveHead(&pMac->pmc.deferredMsgList, FALSE)) )
+    {
+        pDeferredMsg = GET_BASE_ADDR(pEntry, tPmcDeferredMsg, link);
+        if (palFreeMemory(pMac->hHdd, pDeferredMsg) != eHAL_STATUS_SUCCESS)
+        {
+            smsLog(pMac, LOGE, FL("Cannot free memory \n"));
+            PMC_ABORT;
+            break;
+        }
+    }
+    csrLLUnlock(&pMac->pmc.deferredMsgList);
+    csrLLClose(&pMac->pmc.deferredMsgList);
+}
+
+
+#ifdef FEATURE_WLAN_SCAN_PNO
+
+static tSirRetStatus 
+pmcPopulateMacHeader( tpAniSirGlobal pMac,
+                      tANI_U8* pBD,
+                      tANI_U8 type,
+                      tANI_U8 subType,
+                      tSirMacAddr peerAddr ,
+                      tSirMacAddr selfMacAddr)
+{
+    tSirRetStatus   statusCode = eSIR_SUCCESS;
+    tpSirMacMgmtHdr pMacHdr;
+    
+    /// Prepare MAC management header
+    pMacHdr = (tpSirMacMgmtHdr) (pBD);
+
+    // Prepare FC
+    pMacHdr->fc.protVer = SIR_MAC_PROTOCOL_VERSION;
+    pMacHdr->fc.type    = type;
+    pMacHdr->fc.subType = subType;
+
+    // Prepare Address 1
+    palCopyMemory( pMac->hHdd,
+                   (tANI_U8 *) pMacHdr->da,
+                   (tANI_U8 *) peerAddr,
+                   sizeof( tSirMacAddr ));
+
+    sirCopyMacAddr(pMacHdr->sa,selfMacAddr);
+
+    // Prepare Address 3
+    palCopyMemory( pMac->hHdd,
+                   (tANI_U8 *) pMacHdr->bssId,
+                   (tANI_U8 *) peerAddr,
+                   sizeof( tSirMacAddr ));
+    return statusCode;
+} /*** pmcPopulateMacHeader() ***/
+
+
+static tSirRetStatus
+pmcPrepareProbeReqTemplate(tpAniSirGlobal pMac,
+                           tANI_U8        nChannelNum,
+                           tANI_U32       dot11mode,
+                           tSirMacAddr    selfMacAddr,
+                           tANI_U8        *pFrame,
+                           tANI_U16       *pusLen)
+{
+    tDot11fProbeRequest pr;
+    tANI_U32            nStatus, nBytes, nPayload;
+    tSirRetStatus       nSirStatus;
+    /*Bcast tx*/
+    tSirMacAddr         bssId = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
+    /*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
+
+    // The scheme here is to fill out a 'tDot11fProbeRequest' structure
+    // and then hand it off to 'dot11fPackProbeRequest' (for
+    // serialization).  We start by zero-initializing the structure:
+    palZeroMemory( pMac->hHdd, ( tANI_U8* )&pr, sizeof( pr ) );
+
+    PopulateDot11fSuppRates( pMac, nChannelNum, &pr.SuppRates,NULL);
+
+    if ( WNI_CFG_DOT11_MODE_11B != dot11mode )
+    {
+        PopulateDot11fExtSuppRates1( pMac, nChannelNum, &pr.ExtSuppRates );
+    }
+
+    
+    if (IS_DOT11_MODE_HT(dot11mode))
+    {
+       PopulateDot11fHTCaps( pMac, &pr.HTCaps );
+    }
+    
+    // That's it-- now we pack it.  First, how much space are we going to
+    // need?
+    nStatus = dot11fGetPackedProbeRequestSize( pMac, &pr, &nPayload );
+    if ( DOT11F_FAILED( nStatus ) )
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                  "Failed to calculate the packed size f"
+                  "or a Probe Request (0x%08x).\n", nStatus );
+
+        // We'll fall back on the worst case scenario:
+        nPayload = sizeof( tDot11fProbeRequest );
+    }
+    else if ( DOT11F_WARNED( nStatus ) )
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                  "There were warnings while calculating"
+                  "the packed size for a Probe Request ("
+                  "0x%08x).\n", nStatus );
+    }
+
+    nBytes = nPayload + sizeof( tSirMacMgmtHdr );
+  
+    /* Prepare outgoing frame*/
+    palZeroMemory( pMac->hHdd, pFrame, nBytes );
+
+    // Next, we fill out the buffer descriptor:
+    nSirStatus = pmcPopulateMacHeader( pMac, pFrame, SIR_MAC_MGMT_FRAME,
+                                SIR_MAC_MGMT_PROBE_REQ, bssId ,selfMacAddr);
+
+    if ( eSIR_SUCCESS != nSirStatus )
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+        "Failed to populate the buffer descriptor for a Probe Request (%d).\n",
+                nSirStatus );
+        return nSirStatus;      // allocated!
+    }
+
+    // That done, pack the Probe Request:
+    nStatus = dot11fPackProbeRequest( pMac, &pr, pFrame +
+                                      sizeof( tSirMacMgmtHdr ),
+                                      nPayload, &nPayload );
+    if ( DOT11F_FAILED( nStatus ) )
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                  "Failed to pack a Probe Request (0x%08x).\n", nStatus );
+        return eSIR_FAILURE;    // allocated!
+    }
+    else if ( DOT11F_WARNED( nStatus ) )
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+            "There were warnings while packing a Probe Request (0x%08x).\n" );
+    }
+
+    *pusLen = nPayload + sizeof(tSirMacMgmtHdr); 
+    return eSIR_SUCCESS;
+} // End pmcPrepareProbeReqTemplate.
+
+
+eHalStatus pmcSetPreferredNetworkList
+(
+    tHalHandle hHal, 
+    tpSirPNOScanReq pRequest, 
+    tANI_U8 sessionId, 
+    preferredNetworkFoundIndCallback callbackRoutine, 
+    void *callbackContext
+)
+{
+    tpSirPNOScanReq pRequestBuf;
+    vos_msg_t msg;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+    tANI_U8 ucDot11Mode; 
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s: SSID = %s, %s", __FUNCTION__,
+        pRequest->aNetworks[0].ssId.ssId, pRequest->aNetworks[1].ssId.ssId);
+
+    pRequestBuf = vos_mem_malloc(sizeof(tSirPNOScanReq));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate memory for PNO request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+
+    vos_mem_copy(pRequestBuf, pRequest, sizeof(tSirPNOScanReq));
+
+    /*Must translate the mode first*/
+    ucDot11Mode = (tANI_U8) csrTranslateToWNICfgDot11Mode(pMac, 
+                                       csrFindBestPhyMode( pMac, pMac->roam.configParam.phyMode ));
+
+    /*Prepare a probe request for 2.4GHz band and one for 5GHz band*/
+    pmcPrepareProbeReqTemplate(pMac,SIR_PNO_24G_DEFAULT_CH, ucDot11Mode, pSession->selfMacAddr, 
+                               pRequestBuf->p24GProbeTemplate, &pRequestBuf->us24GProbeTemplateLen); 
+
+    pmcPrepareProbeReqTemplate(pMac,SIR_PNO_5G_DEFAULT_CH, ucDot11Mode, pSession->selfMacAddr, 
+                               pRequestBuf->p5GProbeTemplate, &pRequestBuf->us5GProbeTemplateLen); 
+
+
+    msg.type     = WDA_SET_PNO_REQ;
+    msg.reserved = 0;
+    msg.bodyptr  = pRequestBuf;
+    if (!VOS_IS_STATUS_SUCCESS(vos_mq_post_message(VOS_MODULE_ID_WDA, &msg)))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post WDA_SET_PNO_REQ message to WDA", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    /* Cache the Preferred Network Found Indication callback information */
+    pMac->pmc.prefNetwFoundCB = callbackRoutine;
+    pMac->pmc.preferredNetworkFoundIndCallbackContext = callbackContext;
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "-%s", __FUNCTION__);
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+eHalStatus pmcSetRssiFilter(tHalHandle hHal,   v_U8_t        rssiThreshold)
+{
+    tpSirSetRSSIFilterReq pRequestBuf;
+    vos_msg_t msg;
+
+
+    pRequestBuf = vos_mem_malloc(sizeof(tpSirSetRSSIFilterReq));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate memory for PNO request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+
+
+    pRequestBuf->rssiThreshold = rssiThreshold; 
+
+    msg.type = WDA_SET_RSSI_FILTER_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+    if (!VOS_IS_STATUS_SUCCESS(vos_mq_post_message(VOS_MODULE_ID_WDA, &msg)))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post WDA_SET_PNO_REQ message to WDA", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+
+eHalStatus pmcUpdateScanParams(tHalHandle hHal, tCsrConfig *pRequest, tCsrChannel *pChannelList, tANI_U8 b11dResolved)
+{
+    tpSirUpdateScanParams pRequestBuf;
+    vos_msg_t msg;
+    int i;
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s started", __FUNCTION__);
+
+    pRequestBuf = vos_mem_malloc(sizeof(tSirUpdateScanParams));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate memory for UpdateScanParams request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+
+    // 
+    // Fill pRequestBuf structure from pRequest
+    //
+    pRequestBuf->b11dEnabled    = pRequest->Is11eSupportEnabled;
+    pRequestBuf->b11dResolved   = b11dResolved;
+    pRequestBuf->ucChannelCount = 
+        ( pChannelList->numChannels < SIR_PNO_MAX_NETW_CHANNELS )?
+        pChannelList->numChannels:SIR_PNO_MAX_NETW_CHANNELS;
+
+    for (i=0; i < pChannelList->numChannels; i++)
+    {    
+        pRequestBuf->aChannels[i] = pChannelList->channelList[i];
+    }
+    pRequestBuf->usPassiveMinChTime = pRequest->nPassiveMinChnTime;
+    pRequestBuf->usPassiveMaxChTime = pRequest->nPassiveMaxChnTime;
+    pRequestBuf->usActiveMinChTime  = pRequest->nActiveMinChnTime;
+    pRequestBuf->usActiveMaxChTime  = pRequest->nActiveMaxChnTime; 
+    pRequestBuf->ucCBState          = PHY_SINGLE_CHANNEL_CENTERED;
+
+    msg.type = WDA_UPDATE_SCAN_PARAMS_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+    if (!VOS_IS_STATUS_SUCCESS(vos_mq_post_message(VOS_MODULE_ID_WDA, &msg)))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post WDA_UPDATE_SCAN_PARAMS message to WDA", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+#endif // FEATURE_WLAN_SCAN_PNO
+
+eHalStatus pmcSetPowerParams(tHalHandle hHal,   tSirSetPowerParamsReq*  pwParams)
+{
+    tSirSetPowerParamsReq* pRequestBuf;
+    vos_msg_t msg;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tpPESession     psessionEntry;
+
+    if((psessionEntry = peGetValidPowerSaveSession(pMac))== NULL)
+    {
+        return eHAL_STATUS_NOT_INITIALIZED;
+    }
+
+    pRequestBuf = vos_mem_malloc(sizeof(tSirSetPowerParamsReq));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate memory for Power Paramrequest", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+
+
+    vos_mem_copy(pRequestBuf, pwParams, sizeof(*pRequestBuf)); 
+
+
+    msg.type = WDA_SET_POWER_PARAMS_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post WDA_SET_POWER_PARAMS_REQ message to WDA", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+#ifdef WLAN_FEATURE_PACKET_FILTERING
+eHalStatus pmcGetFilterMatchCount
+(
+    tHalHandle hHal, 
+    FilterMatchCountCallback callbackRoutine, 
+    void *callbackContext
+)
+{
+    tpSirRcvFltPktMatchRsp  pRequestBuf;
+    vos_msg_t               msg;
+    tpAniSirGlobal          pMac = PMAC_STRUCT(hHal);
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+        "%s: filterId = %d", __FUNCTION__);
+
+    pRequestBuf = vos_mem_malloc(sizeof(tSirRcvFltPktMatchRsp));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+                  "%s: Not able to allocate "
+                  "memory for Get PC Filter Match Count request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+
+    msg.type = WDA_PACKET_COALESCING_FILTER_MATCH_COUNT_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+
+    /* Cache the Packet Coalescing Filter Match Count callback information */
+    if (NULL != pMac->pmc.FilterMatchCountCB)
+    {
+        // Do we need to check if the callback is in use? 
+        // Because we are not sending the same message again when it is pending,
+        // the only case when the callback is not NULL is that the previous message 
+        //was timed out or failed.
+        // So, it will be safe to set the callback in this case.
+    }
+
+    pMac->pmc.FilterMatchCountCB = callbackRoutine;
+    pMac->pmc.FilterMatchCountCBContext = callbackContext;
+
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+            "%s: Not able to post WDA_PACKET_COALESCING_FILTER_MATCH_COUNT_REQ "
+            "message to WDA", __FUNCTION__);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+#endif // WLAN_FEATURE_PACKET_FILTERING
+
+#ifdef WLAN_FEATURE_GTK_OFFLOAD
+/* ---------------------------------------------------------------------------
+    \fn pmcSetGTKOffload
+    \brief  Set GTK offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pGtkOffload - Pointer to the GTK offload request.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the offload.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcSetGTKOffload (tHalHandle hHal, tpSirGtkOffloadParams pGtkOffload)
+{
+    tpSirGtkOffloadParams pRequestBuf;
+    vos_msg_t msg;
+    int i;
+
+    VOS_TRACE( VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO, "%s: KeyReplayCounter: %d", 
+                __FUNCTION__, pGtkOffload->ullKeyReplayCounter);
+
+    pRequestBuf = (tpSirGtkOffloadParams)vos_mem_malloc(sizeof(tSirGtkOffloadParams));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate "
+                  "memory for GTK offload request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+
+    vos_mem_copy(pRequestBuf, pGtkOffload, sizeof(tSirGtkOffloadParams));
+        
+    msg.type = WDA_GTK_OFFLOAD_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+    if (!VOS_IS_STATUS_SUCCESS(vos_mq_post_message(VOS_MODULE_ID_WDA, &msg)))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post "
+                  "SIR_HAL_SET_GTK_OFFLOAD message to HAL", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn pmcGetGTKOffload
+    \brief  Get GTK offload information.
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine - Pointer to the GTK Offload Get Info response callback routine.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot set the offload.
+            eHAL_STATUS_SUCCESS  Request accepted. 
+  ---------------------------------------------------------------------------*/
+eHalStatus pmcGetGTKOffload(tHalHandle hHal, GTKOffloadGetInfoCallback callbackRoutine, void *callbackContext)
+{
+    tpSirGtkOffloadGetInfoRspParams  pRequestBuf;
+    vos_msg_t               msg;
+    tpAniSirGlobal          pMac = PMAC_STRUCT(hHal);
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s: filterId = %d", 
+                __FUNCTION__);
+
+    pRequestBuf = vos_mem_malloc(sizeof(tSirGtkOffloadGetInfoRspParams));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate "
+                  "memory for Get GTK Offload request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+
+    msg.type = WDA_GTK_OFFLOAD_GETINFO_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+
+    /* Cache the Get GTK Offload callback information */
+    if (NULL != pMac->pmc.GtkOffloadGetInfoCB)
+    {
+        // Do we need to check if the callback is in use? 
+        // Because we are not sending the same message again when it is pending,
+        // the only case when the callback is not NULL is that the previous message was timed out or failed.
+        // So, it will be safe to set the callback in this case.
+    }
+
+    pMac->pmc.GtkOffloadGetInfoCB = callbackRoutine;
+    pMac->pmc.GtkOffloadGetInfoCBContext = callbackContext;
+
+    if (!VOS_IS_STATUS_SUCCESS(vos_mq_post_message(VOS_MODULE_ID_WDA, &msg)))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post WDA_GTK_OFFLOAD_GETINFO_REQ message to WDA", 
+                    __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+#endif // WLAN_FEATURE_GTK_OFFLOAD
diff --git a/CORE/SME/src/pmc/pmcLogDump.c b/CORE/SME/src/pmc/pmcLogDump.c
new file mode 100644
index 0000000..463ea21
--- /dev/null
+++ b/CORE/SME/src/pmc/pmcLogDump.c
@@ -0,0 +1,387 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/******************************************************************************
+*
+* Name:  pmcLogDump.c
+*
+* Description: Implements the dump commands specific to PMC module
+*
+* Copyright 2008 (c) Qualcomm, Incorporated.
+* All Rights Reserved.
+* Qualcomm Confidential and Proprietary.
+*
+******************************************************************************/
+
+#include "palTypes.h"
+#include "aniGlobal.h"
+#include "pmcApi.h"
+#include "pmc.h"
+#include "logDump.h"
+#include "smsDebug.h"
+#include "sme_Api.h"
+#include "cfgApi.h"
+
+#if defined(ANI_LOGDUMP)
+
+void dump_pmc_callbackRoutine (void *callbackContext, eHalStatus status)
+{
+    tpAniSirGlobal pMac = (tpAniSirGlobal)callbackContext;
+    smsLog(pMac, LOGW, "*********Received callback from PMC with status = %d\n*********",status);
+}
+
+#ifdef WLAN_WAKEUP_EVENTS
+void dump_pmc_callbackRoutine2 (void *callbackContext, tpSirWakeReasonInd pWakeReasonInd)
+{
+    tpAniSirGlobal pMac = (tpAniSirGlobal)callbackContext;
+    smsLog(pMac, LOGW, "*********Received callback from PMC with reason = %d\n*********",pWakeReasonInd->ulReason);
+}
+#endif // WLAN_WAKEUP_EVENTS
+
+void dump_pmc_deviceUpdateRoutine (void *callbackContext, tPmcState pmcState)
+{
+    tpAniSirGlobal pMac = (tpAniSirGlobal)callbackContext;
+    smsLog(pMac, LOGW, "*********Received msg from PMC: Device is in %s state\n*********", pmcGetPmcStateStr(pmcState));
+}
+
+static char *
+dump_pmc_state( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    char *ptr = p;
+
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+
+    p += log_sprintf( pMac,p, "********  PMC State & Configuration ******** \n");
+    p += log_sprintf( pMac,p, " PMC: IMPS Enabled? %d\n", pMac->pmc.impsEnabled);
+    p += log_sprintf( pMac,p, " PMC: Auto BMPS Timer Enabled? %d\n", pMac->pmc.autoBmpsEntryEnabled);
+    p += log_sprintf( pMac,p, " PMC: BMPS Enabled? %d\n", pMac->pmc.bmpsEnabled);
+    p += log_sprintf( pMac,p, " PMC: UAPSD Enabled? %d\n", pMac->pmc.uapsdEnabled);
+    p += log_sprintf( pMac,p, " PMC: WoWL Enabled? %d\n", pMac->pmc.wowlEnabled);
+    p += log_sprintf( pMac,p, " PMC: Standby Enabled? %d\n", pMac->pmc.standbyEnabled);
+    p += log_sprintf( pMac,p, " PMC: Auto BMPS timer period (ms): %d\n", pMac->pmc.bmpsConfig.trafficMeasurePeriod);
+    p += log_sprintf( pMac,p, " PMC: BMPS Listen Interval (Beacon intervals): %d\n", pMac->pmc.bmpsConfig.bmpsPeriod);
+    p += log_sprintf( pMac,p, " PMC: Device State = %s\n", pmcGetPmcStateStr(pMac->pmc.pmcState));
+    p += log_sprintf( pMac,p, " PMC: RequestFullPowerPending = %d\n", pMac->pmc.requestFullPowerPending);
+    p += log_sprintf( pMac,p, " PMC: UapsdSessionRequired = %d\n", pMac->pmc.uapsdSessionRequired);
+    p += log_sprintf( pMac,p, " PMC: wowlModeRequired = %d\n\n", pMac->pmc.wowlModeRequired);
+
+    smsLog(pMac, LOGW, "\n%s", ptr);
+
+    return p;
+}
+
+static char *
+dump_pmc_enable_imps( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)pmcEnablePowerSave(pMac, ePMC_IDLE_MODE_POWER_SAVE);
+    return p;
+}
+
+static char *
+dump_pmc_disable_imps( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)pmcDisablePowerSave(pMac, ePMC_IDLE_MODE_POWER_SAVE);
+    return p;
+}
+
+static char *
+dump_pmc_request_imps( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg2; (void) arg3; (void) arg4;
+    pMac->pmc.impsEnabled = TRUE;
+    (void)pmcRequestImps(pMac, arg1, dump_pmc_callbackRoutine, pMac);
+    return p;
+}
+
+static char *
+dump_pmc_start_auto_bmps_timer( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    pMac->pmc.bmpsEnabled = TRUE;
+    (void)pmcStartAutoBmpsTimer(pMac);
+    return p;
+}
+
+static char *
+dump_pmc_stop_auto_bmps_timer( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)pmcStopAutoBmpsTimer(pMac);
+    return p;
+}
+
+static char *
+dump_pmc_enable_bmps( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)pmcEnablePowerSave(pMac, ePMC_BEACON_MODE_POWER_SAVE);
+    return p;
+}
+
+static char *
+dump_pmc_disable_bmps( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)pmcDisablePowerSave(pMac, ePMC_BEACON_MODE_POWER_SAVE);
+    return p;
+}
+
+static char *
+dump_pmc_request_bmps( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    pMac->pmc.bmpsEnabled = TRUE;
+    (void)sme_RequestBmps(pMac, dump_pmc_callbackRoutine, pMac);
+    return p;
+}
+
+static char *
+dump_pmc_enable_uapsd( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)pmcEnablePowerSave(pMac, ePMC_UAPSD_MODE_POWER_SAVE);
+    return p;
+}
+
+static char *
+dump_pmc_disable_uapsd( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)pmcDisablePowerSave(pMac, ePMC_UAPSD_MODE_POWER_SAVE);
+    return p;
+}
+
+static char *
+dump_pmc_start_uapsd( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    pMac->pmc.bmpsEnabled = TRUE;
+    pMac->pmc.uapsdEnabled = TRUE;
+    (void)pmcStartUapsd(pMac, dump_pmc_callbackRoutine, pMac);
+    return p;
+}
+
+static char *
+dump_pmc_stop_uapsd( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)pmcStopUapsd(pMac);
+    return p;
+}
+
+static char *
+dump_pmc_request_standby( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    pMac->pmc.standbyEnabled = TRUE;
+    (void)pmcRequestStandby(pMac, dump_pmc_callbackRoutine, pMac);
+    return p;
+}
+
+static char *
+dump_pmc_request_full_power( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)sme_RequestFullPower(pMac, dump_pmc_callbackRoutine, pMac, eSME_FULL_PWR_NEEDED_BY_HDD);
+    return p;
+}
+
+static char *
+dump_pmc_enter_wowl( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    tSirSmeWowlEnterParams wowlEnterParams;
+    tSirRetStatus status;
+    tANI_U32 length;
+    (void) arg3; (void) arg4;
+    
+    palZeroMemory(pMac->hHdd, &wowlEnterParams, sizeof(tSirSmeWowlEnterParams));
+
+    if (arg1 == 0 && arg2 == 0)
+    {
+        smsLog(pMac, LOGE, "Requesting WoWL but neither magic pkt and ptrn byte matching is being enabled\n");
+        return p;
+    }
+    if(arg1 == 1)
+    {
+        wowlEnterParams.ucMagicPktEnable = 1;
+        /* magic packet */
+        length = SIR_MAC_ADDR_LENGTH;
+        status = wlan_cfgGetStr(pMac, WNI_CFG_STA_ID, (tANI_U8 *)wowlEnterParams.magicPtrn, &length); 
+        if (eSIR_SUCCESS != status)
+        {
+            smsLog(pMac, LOGE, "Reading of WNI_CFG_STA_ID from CFG failed. Using hardcoded STA MAC Addr\n");
+            wowlEnterParams.magicPtrn[0] = 0x00;
+            wowlEnterParams.magicPtrn[1] = 0x0a;
+            wowlEnterParams.magicPtrn[2] = 0xf5;
+            wowlEnterParams.magicPtrn[3] = 0x04;
+            wowlEnterParams.magicPtrn[4] = 0x05;
+            wowlEnterParams.magicPtrn[5] = 0x06;
+        }
+    }
+    if(arg2 == 1)
+    {
+      wowlEnterParams.ucPatternFilteringEnable = 1;
+    }
+
+    pMac->pmc.bmpsEnabled = TRUE;
+    pMac->pmc.wowlEnabled = TRUE;
+#ifdef WLAN_WAKEUP_EVENTS
+    (void)sme_EnterWowl(pMac, dump_pmc_callbackRoutine, pMac, dump_pmc_callbackRoutine2, pMac, &wowlEnterParams);
+#else // WLAN_WAKEUP_EVENTS
+    (void)sme_EnterWowl(pMac, dump_pmc_callbackRoutine, pMac, &wowlEnterParams);
+#endif // WLAN_WAKEUP_EVENTS
+    return p;
+}
+
+static char *
+dump_pmc_exit_wowl( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+    (void)sme_ExitWowl(pMac);
+    return p;
+}
+
+static char *
+dump_pmc_remove_ptrn( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    tSirWowlDelBcastPtrn delPattern;
+    (void) arg2; (void) arg3; (void) arg4;
+
+    palZeroMemory(pMac->hHdd, &delPattern, sizeof(tSirWowlDelBcastPtrn));
+
+    if(arg1 <= 7)
+    {
+        delPattern.ucPatternId = (tANI_U8)arg1;
+    }
+    else
+    {
+        smsLog(pMac, LOGE, "dump_pmc_remove_ptrn: Invalid pattern Id %d\n",arg1);
+        return p;
+    }
+
+    (void)pmcWowlDelBcastPattern(pMac, &delPattern);
+    return p;
+}
+
+static char *
+dump_pmc_test_uapsd( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    tSirSmeRsp smeRsp;
+    smeRsp.statusCode = eSIR_SME_SUCCESS;
+
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+
+    pMac->pmc.uapsdEnabled = TRUE;
+    pMac->pmc.pmcState = BMPS;
+
+    pmcRegisterDeviceStateUpdateInd(pMac, dump_pmc_deviceUpdateRoutine, pMac);
+
+    pmcStartUapsd(pMac, dump_pmc_callbackRoutine, pMac);
+    smeRsp.messageType = eWNI_PMC_ENTER_UAPSD_RSP;
+    pmcMessageProcessor(pMac, &smeRsp);
+    pmcStopUapsd(pMac);
+    smeRsp.messageType = eWNI_PMC_EXIT_UAPSD_RSP;
+    pmcMessageProcessor(pMac, &smeRsp);
+    pmcDeregisterDeviceStateUpdateInd(pMac, dump_pmc_deviceUpdateRoutine);
+    return p;
+}
+
+static char *
+dump_pmc_test_Wowl( tpAniSirGlobal pMac, tANI_U32 arg1, tANI_U32 arg2, tANI_U32 arg3, tANI_U32 arg4, char *p)
+{
+    tSirSmeRsp smeRsp;
+    tSirWowlAddBcastPtrn addPattern;
+    tSirWowlDelBcastPtrn delPattern;
+    tSirSmeWowlEnterParams wowlEnterParams;
+
+    smeRsp.statusCode = eSIR_SME_SUCCESS;
+    palZeroMemory(pMac->hHdd, &addPattern, sizeof(tSirWowlAddBcastPtrn));
+    palZeroMemory(pMac->hHdd, &delPattern, sizeof(tSirWowlDelBcastPtrn));
+    palZeroMemory(pMac->hHdd, &wowlEnterParams, sizeof(tSirSmeWowlEnterParams));
+
+    (void) arg1; (void) arg2; (void) arg3; (void) arg4;
+
+    //Add pattern
+    sme_WowlAddBcastPattern(pMac, &addPattern);
+
+    //Delete pattern
+    sme_WowlDelBcastPattern(pMac, &delPattern);
+
+    //Force the device into BMPS
+    pMac->pmc.pmcState = BMPS;
+
+    //Enter Wowl
+#ifdef WLAN_WAKEUP_EVENTS
+    sme_EnterWowl(pMac, dump_pmc_callbackRoutine, pMac, dump_pmc_callbackRoutine2, pMac, &wowlEnterParams);
+#else // WLAN_WAKEUP_EVENTS
+    sme_EnterWowl(pMac, dump_pmc_callbackRoutine, pMac, &wowlEnterParams);
+#endif // WLAN_WAKEUP_EVENTS
+    smeRsp.messageType = eWNI_PMC_ENTER_WOWL_RSP;
+    pmcMessageProcessor(pMac, &smeRsp);
+
+    //Exit Wowl
+    sme_ExitWowl(pMac);
+    smeRsp.messageType = eWNI_PMC_EXIT_WOWL_RSP;
+    pmcMessageProcessor(pMac, &smeRsp);
+    return p;
+}
+
+static tDumpFuncEntry pmcMenuDumpTable[] = {
+    {0,     "PMC (900-925)",           NULL},
+    // General
+    {900,   "PMC: Dump State + config", dump_pmc_state},
+    // IMPS Related
+    {901,   "PMC: Enable IMPS",         dump_pmc_enable_imps},
+    {902,   "PMC: Disable IMPS",        dump_pmc_disable_imps},
+    {903,   "PMC: Request IMPS: Syntax: dump 903 <imps_period_ms>", dump_pmc_request_imps},
+    // BMPS Related
+    {904,   "PMC: Start Auto BMPS Timer",  dump_pmc_start_auto_bmps_timer},
+    {905,   "PMC: Stop Auto BMPS Timer", dump_pmc_stop_auto_bmps_timer},
+    {906,   "PMC: Request BMPS",        dump_pmc_request_bmps},
+    // UAPSD Related
+    {907,   "PMC: Enable UAPSD",        dump_pmc_enable_uapsd},
+    {908,   "PMC: Disable UAPSD",       dump_pmc_disable_uapsd},
+    {909,   "PMC: Start UAPSD",         dump_pmc_start_uapsd},
+    {910,   "PMC: Stop UAPSD",          dump_pmc_stop_uapsd},
+    // Standby Related
+    {911,   "PMC: Request Standby",     dump_pmc_request_standby},
+    // Full Power Related
+    {912,   "PMC: Request Full Power",  dump_pmc_request_full_power},
+    //Unit Test Related
+    {913,   "PMC: Test UAPSD",          dump_pmc_test_uapsd},
+    {914,   "PMC: Test WOWL",           dump_pmc_test_Wowl},
+    // WoWL Related
+    {915,   "PMC: Enter WoWL: Syntax: dump 915 <enable_magic_pkt> <enable_ptrn_match>",  dump_pmc_enter_wowl},
+    {916,   "PMC: Exit WoWL",  dump_pmc_exit_wowl},
+    {917,   "PMC: Remove a pattern: Syntax: dump 917 <pattern_id(0-7)>",  dump_pmc_remove_ptrn},
+    {918,   "PMC: Enable BMPS",         dump_pmc_enable_bmps},
+    {919,   "PMC: Disable BMPS",        dump_pmc_disable_bmps}
+};
+
+void pmcDumpInit(tHalHandle hHal)
+{
+    logDumpRegisterTable( (tpAniSirGlobal)hHal, &pmcMenuDumpTable[0],
+                          sizeof(pmcMenuDumpTable)/sizeof(pmcMenuDumpTable[0]) );
+}
+
+#endif //#if defined(ANI_LOGDUMP)
diff --git a/CORE/SME/src/rrm/sme_rrm.c b/CORE/SME/src/rrm/sme_rrm.c
new file mode 100644
index 0000000..3ce9c0f
--- /dev/null
+++ b/CORE/SME/src/rrm/sme_rrm.c
@@ -0,0 +1,1296 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/*
+ * */
+/**=========================================================================
+  
+  \file  sme_Rrm.c
+  
+  \brief implementation for SME RRM APIs
+  
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+   
+   Qualcomm Confidential and Proprietary.
+  
+  ========================================================================*/
+
+/* $Header$ */
+
+#if defined WLAN_FEATURE_VOWIFI
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halInternal.h"
+#endif
+#include "aniGlobal.h"
+#include "smeInside.h"
+#include "sme_Api.h"
+#include "smsDebug.h"
+#include "cfgApi.h"
+
+#ifdef FEATURE_WLAN_DIAG_SUPPORT
+#include "vos_diag_core_event.h"
+#include "vos_diag_core_log.h"
+#endif /* FEATURE_WLAN_DIAG_SUPPORT */
+
+#include "csrInsideApi.h"
+
+#include "rrmGlobal.h"
+
+#ifdef FEATURE_WLAN_CCX
+#include "csrCcx.h"
+#endif
+
+/* Roam score for a neighbor AP will be calculated based on the below definitions.
+    The calculated roam score will be used to select the roamable candidate from neighbor AP list */
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_REACHABILITY             0   /* When we support 11r over the DS, this should have a non-zero value */
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_SECURITY                 10
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_KEY_SCOPE                20
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_SPECTRUM_MGMT 0   /* Not used */
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_QOS           5
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_APSD          3
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_RRM           8
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_DELAYED_BA    0   /* We dont support delayed BA */
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_IMMEDIATE_BA  3
+#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_MOBILITY_DOMAIN          30
+
+#ifdef FEATURE_WLAN_CCX
+#define RRM_ROAM_SCORE_NEIGHBOR_IAPP_LIST                       30
+#endif
+/**---------------------------------------------------------------------------
+  
+  \brief rrmLLPurgeNeighborCache() - 
+    This function purges all the entries in the neighbor cache and frees up all the internal nodes   
+
+  \param  - pMac  - Pointer to the Hal Handle.
+          - pList - Pointer the List that should be purged.
+  \return - void
+  
+  --------------------------------------------------------------------------*/
+static void rrmLLPurgeNeighborCache(tpAniSirGlobal pMac, tDblLinkList *pList)
+{
+    tListElem *pEntry;
+    tRrmNeighborReportDesc *pNeighborReportDesc;
+    
+    csrLLLock(pList);
+    
+    while((pEntry = csrLLRemoveHead(pList, LL_ACCESS_NOLOCK)) != NULL)
+    {
+        pNeighborReportDesc = GET_BASE_ADDR( pEntry, tRrmNeighborReportDesc, List );
+        vos_mem_free(pNeighborReportDesc->pNeighborBssDescription);
+        vos_mem_free(pNeighborReportDesc);
+    }
+    
+    csrLLUnlock(pList);   
+     
+    return;
+}
+
+/**---------------------------------------------------------------------------
+  
+  \brief rrmIndicateNeighborReportResult() - 
+        This function calls the callback register by the caller while requesting for 
+        neighbor report. This function gets invoked if a neighbor report is received from an AP
+        or neighbor response wait timer expires.
+
+  \param  - pMac - Pointer to the Hal Handle.
+          - vosStatus - VOS_STATUS_SUCCESS/VOS_STATUS_FAILURE based on whether a valid report is 
+            received or neighbor timer expired
+  \return - void
+  
+  --------------------------------------------------------------------------*/
+void rrmIndicateNeighborReportResult(tpAniSirGlobal pMac, VOS_STATUS vosStatus)
+{
+    NeighborReportRspCallback callback;
+    void                      *callbackContext;
+
+    /* Reset the neighbor response pending status */
+    pMac->rrm.rrmSmeContext.neighborReqControlInfo.isNeighborRspPending = eANI_BOOLEAN_FALSE;
+
+    /* Stop the timer if it is already running. The timer should be running only in the SUCCESS case. */
+    if (VOS_TIMER_STATE_RUNNING == vos_timer_getCurrentState(&pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspWaitTimer))
+    {
+        VOS_ASSERT(VOS_STATUS_SUCCESS == vosStatus);
+        vos_timer_stop(&pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspWaitTimer);
+    }
+    callback = pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallback;
+    callbackContext = pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallbackContext;
+    
+    /* Reset the callback and the callback context before calling the callback. It is very likely that there may be a registration in 
+            callback itself. */
+    pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallback = NULL;
+    pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallbackContext = NULL;
+    
+    /* Call the callback with the status received from caller */
+    if (callback)
+        callback(callbackContext, vosStatus);
+#ifdef FEATURE_WLAN_CCX
+    // We came here with IAPP AP List
+    // Make sure we inform CSR of the neighbor list
+    // for CCX Associations. First clear the cache.
+    else
+    if (csrNeighborRoamIsCCXAssoc(pMac))
+    {
+        ProcessIAPPNeighborAPList(pMac);
+    }
+#endif
+
+    return;
+
+}
+
+/**---------------------------------------------------------------------------
+  
+  \brief sme_RrmBeaconReportXmitInd() - 
+
+   Create and send the beacon report Xmit ind message to PE.
+
+  \param  - pMac - Pointer to the Hal Handle.
+              - pResult - scan result.
+              - measurementDone - flag to indicate that the measurement is done.        
+  \return - 0 for success, non zero for failure
+  
+  --------------------------------------------------------------------------*/
+static eHalStatus sme_RrmSendBeaconReportXmitInd( tpAniSirGlobal pMac, tCsrScanResultInfo **pResultArr, tANI_U8 measurementDone )
+{
+   tpSirBssDescription pBssDesc = NULL;
+   tpSirBeaconReportXmitInd pBeaconRep;
+   tANI_U16 length, ie_len;
+   tANI_U8 bssCounter=0, msgCounter=0;
+   tCsrScanResultInfo *pCurResult=NULL;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+
+
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "Beacon report xmit Ind to PE\n");
+#endif
+
+   if( NULL == pResultArr && !measurementDone )
+   {
+      smsLog( pMac, LOGE, "Beacon report xmit Ind to PE Failed\n");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   if (pResultArr)
+       pCurResult=pResultArr[bssCounter];
+
+   do 
+   {
+       length = sizeof(tSirBeaconReportXmitInd);
+       pBeaconRep = vos_mem_malloc ( length );
+       if ( NULL == pBeaconRep )
+       {
+          smsLog( pMac, LOGP, "Unable to allocate memory for beacon report");
+          return eHAL_STATUS_FAILED_ALLOC;
+       }
+       vos_mem_zero( pBeaconRep, length );
+#if defined WLAN_VOWIFI_DEBUG
+       smsLog( pMac, LOGE, FL("Allocated memory for pBeaconRep\n"));
+#endif
+       pBeaconRep->messageType = eWNI_SME_BEACON_REPORT_RESP_XMIT_IND;
+       pBeaconRep->length = length;
+       pBeaconRep->uDialogToken = pSmeRrmContext->token;
+       pBeaconRep->duration = pSmeRrmContext->duration;
+       pBeaconRep->regClass = pSmeRrmContext->regClass;
+       vos_mem_copy( pBeaconRep->bssId, pSmeRrmContext->sessionBssId, sizeof(tSirMacAddr) );
+
+       msgCounter=0;
+       while (pCurResult) 
+       {
+           pBssDesc = &pCurResult->BssDescriptor;
+           ie_len = GET_IE_LEN_IN_BSS( pBssDesc->length );
+           pBeaconRep->pBssDescription[msgCounter] = vos_mem_malloc ( ie_len+sizeof(tSirBssDescription) );
+           vos_mem_copy( pBeaconRep->pBssDescription[msgCounter], pBssDesc, sizeof(tSirBssDescription) );
+           vos_mem_copy( &pBeaconRep->pBssDescription[msgCounter]->ieFields[0], pBssDesc->ieFields, ie_len  );
+
+           pBeaconRep->numBssDesc++;
+
+           if (++msgCounter >= SIR_BCN_REPORT_MAX_BSS_DESC)
+               break;
+
+           if (csrRoamIs11rAssoc(pMac)) {
+               break;
+           }
+
+           pCurResult = pResultArr[msgCounter];
+       }
+
+       bssCounter+=msgCounter; 
+       if (!pResultArr || !pCurResult || (bssCounter>=SIR_BCN_REPORT_MAX_BSS_DESC))
+            pCurResult = NULL;
+       else
+            pCurResult = pResultArr[bssCounter];
+
+       pBeaconRep->fMeasureDone = (pCurResult)?false:measurementDone;
+
+       status = palSendMBMessage(pMac->hHdd, pBeaconRep);
+
+       smsLog( pMac, LOGW, "SME Sent BcnRepXmit to PE numBss %d\n", pBeaconRep->numBssDesc);
+
+   } while (pCurResult);
+
+   return status;
+}
+
+/**---------------------------------------------------------------------------
+  
+  \brief sme_RrmSendScanRequest() - 
+
+   This function is called to get the scan result from CSR and send the beacon report
+   xmit ind message to PE.
+
+  \param  - pMac - Pointer to the Hal Handle.
+              - num_chan - number of channels.
+              - channel list - list of channels to fetch the result from.
+              - measurementDone - flag to indicate that the measurement is done.        
+  \return - 0 for success, non zero for failure
+  
+  --------------------------------------------------------------------------*/
+static eHalStatus sme_RrmSendScanResult( tpAniSirGlobal pMac, tANI_U8 num_chan, tANI_U8* chanList, tANI_U8 measurementDone )
+{
+   tCsrScanResultFilter filter;
+   tScanResultHandle pResult;
+   tCsrScanResultInfo *pScanResult, *pNextResult;
+   tCsrScanResultInfo *pScanResultsArr[SIR_BCN_REPORT_MAX_BSS_DESC];
+   eHalStatus status;
+   tANI_U8 counter=0;
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+   tANI_U32 sessionId;
+
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "Send scan result to PE \n");
+#endif
+
+   vos_mem_zero( &filter, sizeof(filter) );
+   vos_mem_zero( pScanResultsArr, sizeof(pNextResult)*SIR_BCN_REPORT_MAX_BSS_DESC );
+
+   filter.BSSIDs.numOfBSSIDs = 1;
+   filter.BSSIDs.bssid = &pSmeRrmContext->bssId;
+
+   if( pSmeRrmContext->ssId.length )
+   {
+      filter.SSIDs.SSIDList =( tCsrSSIDInfo *)vos_mem_malloc(sizeof(tCsrSSIDInfo));
+      if( filter.SSIDs.SSIDList == NULL )
+      {
+         smsLog( pMac, LOGP, FL("vos_mem_malloc failed:") );
+         return eHAL_STATUS_FAILURE;
+      }
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, FL("Allocated memory for SSIDList\n"));
+#endif
+      vos_mem_zero( filter.SSIDs.SSIDList, sizeof(tCsrSSIDInfo) );
+
+      filter.SSIDs.SSIDList->SSID.length = pSmeRrmContext->ssId.length;
+      vos_mem_copy(filter.SSIDs.SSIDList->SSID.ssId, pSmeRrmContext->ssId.ssId, pSmeRrmContext->ssId.length);
+      filter.SSIDs.numOfSSIDs = 1;
+   }
+   else
+   {
+      filter.SSIDs.numOfSSIDs = 0;
+   }
+
+   filter.ChannelInfo.numOfChannels = num_chan;
+   filter.ChannelInfo.ChannelList = chanList; 
+
+   filter.fMeasurement = TRUE; 
+
+   csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid*)pSmeRrmContext->sessionBssId, &sessionId );
+   status = sme_ScanGetResult(pMac, (tANI_U8)sessionId, &filter, &pResult);
+
+   if( filter.SSIDs.SSIDList )
+   {
+      //Free the memory allocated for SSIDList.
+      vos_mem_free( filter.SSIDs.SSIDList );
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, FL("Free memory for SSIDList\n") );
+#endif
+   }
+
+   if (NULL == pResult)
+   {
+      // no scan results
+      //
+      // Spec. doesnt say anything about such condition. 
+      // Since section 7.4.6.2 (IEEE802.11k-2008) says-rrm report frame should contain
+      // one or more report IEs. It probably means dont send any respose if no matching
+      // BSS found. Moreover, there is no flag or field in measurement report IE(7.3.2.22)
+      // OR beacon report IE(7.3.2.22.6) that can be set to indicate no BSS found on a given channel.
+      //
+      // If we finished measurement on all the channels, we still need to
+      // send a xmit indication with moreToFollow set to MEASURMENT_DONE
+      // so that PE can clean any context allocated.
+      if( measurementDone )
+         status = sme_RrmSendBeaconReportXmitInd( pMac, NULL, measurementDone );
+      return status;
+   }
+
+   pScanResult = sme_ScanResultGetFirst(pMac, pResult);
+
+   if( NULL == pScanResult && measurementDone )
+      status = sme_RrmSendBeaconReportXmitInd( pMac, NULL, measurementDone );
+
+   counter=0;
+   while (pScanResult)
+   {
+      pNextResult = sme_ScanResultGetNext(pMac, pResult);
+      pScanResultsArr[counter++] = pScanResult;
+      pScanResult = pNextResult; //sme_ScanResultGetNext(hHal, pResult);
+      if (counter >= SIR_BCN_REPORT_MAX_BSS_DESC)
+         break;
+      }
+
+   if (counter)
+       status = sme_RrmSendBeaconReportXmitInd( pMac, pScanResultsArr, measurementDone);
+
+   sme_ScanResultPurge(pMac, pResult); 
+
+   return status;
+}
+/**---------------------------------------------------------------------------
+  
+  \brief sme_RrmScanRequestCallback() - 
+
+   The sme module calls this callback function once it finish the scan request
+   and this function send the beacon report xmit to PE and starts a timer of
+   random interval to issue next request.
+
+  \param  - halHandle - Pointer to the Hal Handle.
+              - pContext - Pointer to the data context.
+              - scanId - Scan ID.
+              - status - CSR Status.        
+  \return - 0 for success, non zero for failure
+  
+  --------------------------------------------------------------------------*/
+
+static eHalStatus sme_RrmScanRequestCallback(tHalHandle halHandle, void *pContext,
+                         tANI_U32 scanId, eCsrScanStatus status)
+{
+
+   tANI_U16 interval;
+   tpAniSirGlobal pMac = (tpAniSirGlobal) halHandle;
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+   tANI_U32 time_tick; 
+
+
+
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "Scan Request callback \n");
+#endif
+   //if any more channels are pending, start a timer of a random value within randomization interval.
+   //
+   //
+   if( (pSmeRrmContext->currentIndex + 1) < pSmeRrmContext->channelList.numOfChannels )
+   {
+      sme_RrmSendScanResult( pMac, 1, &pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex], false );
+
+      pSmeRrmContext->currentIndex++; //Advance the current index.
+      //start the timer to issue next request. 
+      //From timer tick get a random number within 10ms and max randmization interval.
+      time_tick = vos_timer_get_system_ticks();
+      interval = time_tick % (pSmeRrmContext->randnIntvl - 10 + 1) + 10;
+
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, "Set timer for interval %d \n", interval);
+#endif
+      vos_timer_start( &pSmeRrmContext->IterMeasTimer, interval );
+
+   }
+   else
+   {
+      //Done with the measurement. Clean up all context and send a message to PE with measurement done flag set.
+      sme_RrmSendScanResult( pMac, 1, &pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex], true );
+      vos_mem_free( pSmeRrmContext->channelList.ChannelList );
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, FL("Free memory for ChannelList\n") );
+#endif
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_RrmIssueScanReq() - This is called to send a scan request as part 
+         of beacon report request .
+  
+  \param 
+  
+  \return eHAL_STATUS_SUCCESS - Validation is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_RrmIssueScanReq( tpAniSirGlobal pMac )
+{
+   //Issue scan request.
+   tCsrScanRequest scanRequest;
+   v_U32_t scanId = 0;
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+   tANI_U32 sessionId;
+
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "Issue scan request \n" );
+#endif
+
+   vos_mem_zero( &scanRequest, sizeof(scanRequest));
+
+   /* set scanType, active or passive */
+
+   scanRequest.scanType = pSmeRrmContext->measMode;
+
+   vos_mem_copy(scanRequest.bssid,
+         pSmeRrmContext->bssId, sizeof(scanRequest.bssid) );
+
+   if( pSmeRrmContext->ssId.length )
+   {
+      scanRequest.SSIDs.numOfSSIDs = 1;
+      scanRequest.SSIDs.SSIDList =( tCsrSSIDInfo *)vos_mem_malloc(sizeof(tCsrSSIDInfo));
+      if( scanRequest.SSIDs.SSIDList == NULL )
+      {
+         smsLog( pMac, LOGP, FL("vos_mem_malloc failed:") );
+         return eHAL_STATUS_FAILURE;
+      }
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, FL("Allocated memory for pSSIDList\n"));
+#endif
+      vos_mem_zero( scanRequest.SSIDs.SSIDList, sizeof(tCsrSSIDInfo) );
+      scanRequest.SSIDs.SSIDList->SSID.length = pSmeRrmContext->ssId.length;
+      vos_mem_copy(scanRequest.SSIDs.SSIDList->SSID.ssId, pSmeRrmContext->ssId.ssId, pSmeRrmContext->ssId.length);
+   }
+
+   /* set min and max channel time */
+   scanRequest.minChnTime = 0; //pSmeRrmContext->duration; Dont use min timeout.
+   scanRequest.maxChnTime = pSmeRrmContext->duration;
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "For Duration %d \n", pSmeRrmContext->duration );
+#endif
+
+   /* set BSSType to default type */
+   scanRequest.BSSType = eCSR_BSS_TYPE_ANY;
+
+   /*Scan all the channels */
+   scanRequest.ChannelInfo.numOfChannels = 1;
+
+   scanRequest.ChannelInfo.ChannelList = &pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex];
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "On channel %d \n", pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex] );
+#endif
+
+   /* set requestType to full scan */
+   scanRequest.requestType = eCSR_SCAN_REQUEST_FULL_SCAN;
+
+   csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid*)pSmeRrmContext->sessionBssId, &sessionId );
+   status = sme_ScanRequest( pMac, (tANI_U8)sessionId, &scanRequest, &scanId, &sme_RrmScanRequestCallback, NULL ); 
+
+   if ( pSmeRrmContext->ssId.length )
+   {
+      vos_mem_free(scanRequest.SSIDs.SSIDList);
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, FL("Free memory for SSIDList\n"));
+#endif
+   }
+
+   return status;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_RrmProcessBeaconReportReqInd() - This is called to process the Beacon 
+         report request from peer AP forwarded through PE .
+  
+  \param pMsgBuf - a pointer to a buffer that maps to various structures base 
+                   on the message type.
+                   The beginning of the buffer can always map to tSirSmeRsp.
+  
+  \return eHAL_STATUS_SUCCESS - Validation is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+void sme_RrmProcessBeaconReportReqInd(tpAniSirGlobal pMac, void *pMsgBuf)
+{
+   tpSirBeaconReportReqInd pBeaconReq = (tpSirBeaconReportReqInd) pMsgBuf;
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+   tANI_U32 len,i;  
+
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "Received Beacon report request ind Channel = %d\n", pBeaconReq->channelInfo.channelNum );
+#endif
+   //section 11.10.8.1 (IEEE Std 802.11k-2008) 
+   //channel 0 and 255 has special meaning.
+   if( (pBeaconReq->channelInfo.channelNum == 0)  || 
+       ((pBeaconReq->channelInfo.channelNum == 255) && (pBeaconReq->channelList.numChannels == 0) ) ) 
+   {
+      //Add all the channel in the regulatory domain.
+      wlan_cfgGetStrLen( pMac, WNI_CFG_VALID_CHANNEL_LIST, &len );
+      pSmeRrmContext->channelList.ChannelList = vos_mem_malloc( len );
+      if( pSmeRrmContext->channelList.ChannelList == NULL )
+      {
+         smsLog( pMac, LOGP, FL("vos_mem_malloc failed:") );
+         return;
+      }
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, FL("Allocated memory for ChannelList\n") );
+#endif
+      csrGetCfgValidChannels( pMac, pSmeRrmContext->channelList.ChannelList, &len );
+      pSmeRrmContext->channelList.numOfChannels = (tANI_U8)len;
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, "channel == 0 perfoming on all channels \n");
+#endif
+   }
+   else
+   { 
+      len = 0;
+      pSmeRrmContext->channelList.numOfChannels = 0;
+
+      //If valid channel is present. We firt Measure on the given channel. and
+      //if there are additional channels present in APchannelreport, measure on these also.
+      if ( pBeaconReq->channelInfo.channelNum != 255 )
+         len = 1;
+#if defined WLAN_VOWIFI_DEBUG
+      else
+         smsLog( pMac, LOGE, "channel == 255  \n");
+#endif
+
+      len += pBeaconReq->channelList.numChannels;
+
+      pSmeRrmContext->channelList.ChannelList = vos_mem_malloc( len );
+      if( pSmeRrmContext->channelList.ChannelList == NULL )
+      {
+         smsLog( pMac, LOGP, FL("vos_mem_malloc failed") );
+         return;
+      }
+#if defined WLAN_VOWIFI_DEBUG
+      smsLog( pMac, LOGE, FL("Allocated memory for ChannelList\n") );
+#endif
+
+      if ( pBeaconReq->channelInfo.channelNum != 255 )
+      {
+#if defined WLAN_VOWIFI_DEBUG
+         smsLog( pMac, LOGE, "channel == %d  \n", pBeaconReq->channelInfo.channelNum );
+#endif
+         if(csrRoamIsChannelValid( pMac, pBeaconReq->channelInfo.channelNum ))
+            pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->channelList.numOfChannels++] = pBeaconReq->channelInfo.channelNum;
+#if defined WLAN_VOWIFI_DEBUG
+         else
+            smsLog( pMac, LOGE, "is Invalid channel, Ignoring this channel\n" ); 
+#endif
+      }
+
+      for ( i = 0 ; i < pBeaconReq->channelList.numChannels; i++ )
+      {
+         if(csrRoamIsChannelValid( pMac, pBeaconReq->channelList.channelNumber[i] ))
+         {
+            pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->channelList.numOfChannels] = pBeaconReq->channelList.channelNumber[i];
+            pSmeRrmContext->channelList.numOfChannels++;
+         }
+      }
+   }
+
+   //Copy session bssid
+   vos_mem_copy( pSmeRrmContext->sessionBssId, pBeaconReq->bssId, sizeof(tSirMacAddr) );
+
+   //copy measurement bssid
+   vos_mem_copy( pSmeRrmContext->bssId, pBeaconReq->macaddrBssid, sizeof(tSirMacAddr) );
+
+   //Copy ssid
+   vos_mem_copy( &pSmeRrmContext->ssId, &pBeaconReq->ssId, sizeof(tAniSSID) ); 
+
+   pSmeRrmContext->token = pBeaconReq->uDialogToken;
+   pSmeRrmContext->regClass = pBeaconReq->channelInfo.regulatoryClass;
+
+   switch( pBeaconReq->fMeasurementtype )
+   {
+      case 0: //Passive
+      case 1: //Active
+         pSmeRrmContext->measMode = pBeaconReq->fMeasurementtype? eSIR_ACTIVE_SCAN : eSIR_PASSIVE_SCAN ;
+         pSmeRrmContext->duration = pBeaconReq->measurementDuration;
+         pSmeRrmContext->randnIntvl = VOS_MAX( pBeaconReq->randomizationInterval, pSmeRrmContext->rrmConfig.maxRandnInterval );
+         pSmeRrmContext->currentIndex = 0;
+#if defined WLAN_VOWIFI_DEBUG
+         smsLog( pMac, LOGE, "Send beacon report after scan \n" );
+#endif
+         sme_RrmIssueScanReq( pMac ); 
+         break;
+      case 2: //Table
+         //Get the current scan results for the given channel and send it.
+#if defined WLAN_VOWIFI_DEBUG
+         smsLog( pMac, LOGE, "Send beacon report from table \n" );
+#endif
+         sme_RrmSendScanResult( pMac, pSmeRrmContext->channelList.numOfChannels, pSmeRrmContext->channelList.ChannelList, true );
+         vos_mem_free( pSmeRrmContext->channelList.ChannelList );
+#if defined WLAN_VOWIFI_DEBUG
+         smsLog( pMac, LOGE, FL("Free memory for ChannelList\n") );
+#endif
+         break;
+      default:
+#if defined WLAN_VOWIFI_DEBUG
+         smsLog( pMac, LOGE, "Unknown beacon report request mode\n");
+#endif
+         /* Indicate measurement completion to PE */
+         /* If this is not done, pCurrentReq pointer will not be freed and 
+            PE will not handle subsequent Beacon requests */
+         sme_RrmSendBeaconReportXmitInd(pMac, NULL, true);
+         break;
+
+   }
+
+   return;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_RrmNeighborReportRequest() - This is API can be used to trigger a 
+         Neighbor report from the peer.
+  
+  \param sessionId - session identifier on which the request should be made.       
+  \param pNeighborReq - a pointer to a neighbor report request.
+  
+  \return eHAL_STATUS_SUCCESS - Validation is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+VOS_STATUS sme_RrmNeighborReportRequest(tpAniSirGlobal pMac, tANI_U8 sessionId, 
+                                    tpRrmNeighborReq pNeighborReq, tpRrmNeighborRspCallbackInfo callbackInfo)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tpSirNeighborReportReqInd pMsg;
+   tCsrRoamSession *pSession;
+
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, FL("Request to send Neighbor report request received \n"));
+#endif
+   if( !CSR_IS_SESSION_VALID( pMac, sessionId ) )
+   {  
+      smsLog( pMac, LOGE, FL("Invalid session %d\n"), sessionId );
+      return VOS_STATUS_E_INVAL;
+   }
+   pSession = CSR_GET_SESSION( pMac, sessionId );
+
+   /* If already a report is pending, return failure */
+   if (eANI_BOOLEAN_TRUE == pMac->rrm.rrmSmeContext.neighborReqControlInfo.isNeighborRspPending)
+   {
+       smsLog( pMac, LOGE, FL("Neighbor request already pending.. Not allowed"));
+       return VOS_STATUS_E_AGAIN;
+   }
+   
+   pMsg = vos_mem_malloc ( sizeof(tSirNeighborReportReqInd) );
+   if ( NULL == pMsg )
+   {
+      smsLog( pMac, LOGE, "Unable to allocate memory for Neighbor request");
+      return VOS_STATUS_E_NOMEM;
+   }
+
+   
+   vos_mem_zero( pMsg, sizeof(tSirNeighborReportReqInd) );
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, FL(" Allocated memory for Neighbor request\n") );
+#endif
+
+   rrmLLPurgeNeighborCache(pMac, &pMac->rrm.rrmSmeContext.neighborReportCache);
+
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, FL("Purged the neighbor cache before sending Neighbor request: Status = %d\n"), status );
+#endif
+
+   pMsg->messageType = eWNI_SME_NEIGHBOR_REPORT_REQ_IND;
+   pMsg->length = sizeof( tSirNeighborReportReqInd );
+   vos_mem_copy( &pMsg->bssId, &pSession->connectedProfile.bssid, sizeof(tSirMacAddr) );
+   pMsg->noSSID = pNeighborReq->no_ssid;
+   vos_mem_copy( &pMsg->ucSSID, &pNeighborReq->ssid, sizeof(tSirMacSSid));
+
+   status = palSendMBMessage(pMac->hHdd, pMsg);
+   if( status != eHAL_STATUS_SUCCESS )
+      return VOS_STATUS_E_FAILURE;
+
+   /* Neighbor report request message sent successfully to PE. Now register the callbacks */
+   pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallback = 
+                                                            callbackInfo->neighborRspCallback;
+   pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallbackContext = 
+                                                            callbackInfo->neighborRspCallbackContext;
+   pMac->rrm.rrmSmeContext.neighborReqControlInfo.isNeighborRspPending = eANI_BOOLEAN_TRUE;
+
+   /* Start neighbor response wait timer now */
+   vos_timer_start(&pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspWaitTimer, callbackInfo->timeout);
+   
+   return VOS_STATUS_SUCCESS;
+}
+
+/*--------------------------------------------------------------------------
+  \brief rrmCalculateNeighborAPRoamScore() - This API is called while handling 
+                individual neighbor reports from the APs neighbor AP report to 
+                calculate the cumulative roam score before storing it in neighbor 
+                cache.
+  
+  \param pNeighborReportDesc - Neighbor BSS Descriptor node for which roam score 
+                                should be calculated
+  
+  \return void.
+--------------------------------------------------------------------------*/
+static void rrmCalculateNeighborAPRoamScore(tpAniSirGlobal pMac, tpRrmNeighborReportDesc pNeighborReportDesc)
+{
+    tpSirNeighborBssDescripton  pNeighborBssDesc;
+    tANI_U32    roamScore = 0;
+    
+    VOS_ASSERT(pNeighborReportDesc != NULL);
+    VOS_ASSERT(pNeighborReportDesc->pNeighborBssDescription != NULL);
+
+    pNeighborBssDesc = pNeighborReportDesc->pNeighborBssDescription;
+
+    if (pNeighborBssDesc->bssidInfo.rrmInfo.fMobilityDomain)
+    {
+        roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_MOBILITY_DOMAIN;
+        if (pNeighborBssDesc->bssidInfo.rrmInfo.fSameSecurityMode)
+        {
+            roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_SECURITY;
+            if (pNeighborBssDesc->bssidInfo.rrmInfo.fSameAuthenticator)
+            {
+                roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_KEY_SCOPE;
+                if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapRadioMeasurement)
+                {
+                    roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_RRM;
+                    if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapSpectrumMeasurement)
+                        roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_SPECTRUM_MGMT;
+                    if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapQos)
+                        roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_QOS;
+                    if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapApsd)
+                        roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_APSD;
+                    if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapDelayedBlockAck)
+                        roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_DELAYED_BA;
+                    if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapImmediateBlockAck)
+                        roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_IMMEDIATE_BA;
+                    if (pNeighborBssDesc->bssidInfo.rrmInfo.fApPreauthReachable)
+                        roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_REACHABILITY;
+                }
+            }
+        }
+    }
+#ifdef FEATURE_WLAN_CCX
+    // It has come in the report so its the best score
+    if (csrNeighborRoamIs11rAssoc(pMac) == FALSE)
+    {
+        // IAPP Route so lets make use of this info
+        // save all AP, as the list does not come all the time
+        // Save and reuse till the next AP List comes to us.
+        // Even save our own MAC address. Will be useful next time around.
+        roamScore += RRM_ROAM_SCORE_NEIGHBOR_IAPP_LIST;
+    }
+#endif
+    pNeighborReportDesc->roamScore = roamScore;
+
+    return;
+}
+
+/*--------------------------------------------------------------------------
+  \brief rrmStoreNeighborRptByRoamScore() - This API is called to store a given 
+                        Neighbor BSS descriptor to the neighbor cache. This function 
+                        stores the neighbor BSS descriptors in such a way that descriptors 
+                        are sorted by roamScore in descending order
+
+  \param pNeighborReportDesc - Neighbor BSS Descriptor node to be stored in cache
+  
+  \return void.
+--------------------------------------------------------------------------*/
+void rrmStoreNeighborRptByRoamScore(tpAniSirGlobal pMac, tpRrmNeighborReportDesc pNeighborReportDesc)
+{
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+   tListElem       *pEntry;
+   tRrmNeighborReportDesc  *pTempNeighborReportDesc;
+
+   VOS_ASSERT(pNeighborReportDesc != NULL);
+   VOS_ASSERT(pNeighborReportDesc->pNeighborBssDescription != NULL);
+
+   if (csrLLIsListEmpty(&pSmeRrmContext->neighborReportCache, LL_ACCESS_LOCK))
+   {
+       smsLog(pMac, LOGE, FL("Neighbor report cache is empty.. Adding a entry now\n"));
+        /* Neighbor list cache is empty. Insert this entry in the tail */
+       csrLLInsertTail(&pSmeRrmContext->neighborReportCache, &pNeighborReportDesc->List, LL_ACCESS_LOCK);
+       return;
+   }
+   else
+   {
+       /* Should store the neighbor BSS description in the order sorted by roamScore in descending
+              order. APs with highest roamScore should be the 1st entry in the list */
+        pEntry = csrLLPeekHead(&pSmeRrmContext->neighborReportCache, LL_ACCESS_LOCK);
+        while (pEntry != NULL)
+        {
+            pTempNeighborReportDesc = GET_BASE_ADDR( pEntry, tRrmNeighborReportDesc, List );
+            if (pTempNeighborReportDesc->roamScore < pNeighborReportDesc->roamScore)
+                break;
+            pEntry = csrLLNext(&pSmeRrmContext->neighborReportCache, pEntry, LL_ACCESS_LOCK);
+        } 
+
+        if (pEntry)
+            /* This BSS roamscore is better than something in the list. Insert this before that one */
+            csrLLInsertEntry(&pSmeRrmContext->neighborReportCache, pEntry, &pNeighborReportDesc->List, LL_ACCESS_LOCK);
+        else
+            /* All the entries in the list has a better roam Score than this one. Insert this at the last */
+            csrLLInsertTail(&pSmeRrmContext->neighborReportCache, &pNeighborReportDesc->List, LL_ACCESS_LOCK);
+   }
+   return;
+}
+
+/*--------------------------------------------------------------------------
+  \brief sme_RrmProcessNeighborReport() - This is called to process the Neighbor 
+         report received from PE.
+  
+  \param pMsgBuf - a pointer to a buffer that maps to various structures base 
+                   on the message type.
+                   The beginning of the buffer can always map to tSirSmeRsp.
+  
+  \return eHAL_STATUS_SUCCESS - Validation is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_RrmProcessNeighborReport(tpAniSirGlobal pMac, void *pMsgBuf)
+{
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tpSirNeighborReportInd pNeighborRpt = (tpSirNeighborReportInd) pMsgBuf;
+   tpRrmNeighborReportDesc  pNeighborReportDesc;
+   tANI_U8 i = 0;
+   VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
+
+#ifdef FEATURE_WLAN_CCX
+   // Clear the cache for CCX.
+   if (csrNeighborRoamIsCCXAssoc(pMac))
+   {
+       rrmLLPurgeNeighborCache(pMac, 
+           &pMac->rrm.rrmSmeContext.neighborReportCache);
+   }
+#endif
+
+   for (i = 0; i < pNeighborRpt->numNeighborReports; i++)
+   {
+       pNeighborReportDesc = vos_mem_malloc(sizeof(tRrmNeighborReportDesc));
+       if (NULL == pNeighborReportDesc)
+       {
+           smsLog( pMac, LOGE, "Failed to allocate memory for RRM Neighbor report desc\n");
+           status = eHAL_STATUS_FAILED_ALLOC;
+           goto end;
+            
+       }
+
+       vos_mem_zero(pNeighborReportDesc, sizeof(tRrmNeighborReportDesc));
+       pNeighborReportDesc->pNeighborBssDescription = vos_mem_malloc(sizeof(tSirNeighborBssDescription));
+       if (NULL == pNeighborReportDesc->pNeighborBssDescription)
+       {
+           smsLog( pMac, LOGE, "Failed to allocate memory for RRM Neighbor report BSS Description\n");
+           status = eHAL_STATUS_FAILED_ALLOC;
+           goto end;
+       }
+       vos_mem_zero(pNeighborReportDesc->pNeighborBssDescription, sizeof(tSirNeighborBssDescription));
+       vos_mem_copy(pNeighborReportDesc->pNeighborBssDescription, &pNeighborRpt->sNeighborBssDescription[i], 
+                                                sizeof(tSirNeighborBssDescription));
+
+#if defined WLAN_VOWIFI_DEBUG
+       smsLog( pMac, LOGE, "Received neighbor report with Neighbor BSSID: %02x:%02x:%02x:%02x:%02x:%02x \n",
+                    pNeighborRpt->sNeighborBssDescription[i].bssId[0], 
+                    pNeighborRpt->sNeighborBssDescription[i].bssId[1], 
+                    pNeighborRpt->sNeighborBssDescription[i].bssId[2], 
+                    pNeighborRpt->sNeighborBssDescription[i].bssId[3], 
+                    pNeighborRpt->sNeighborBssDescription[i].bssId[4], 
+                    pNeighborRpt->sNeighborBssDescription[i].bssId[5]);
+#endif
+
+       /* Calculate the roam score based on the BSS Capability in the BSSID Information and store it in Neighbor report Desc */
+       rrmCalculateNeighborAPRoamScore(pMac, pNeighborReportDesc);
+
+       /* Store the Neighbor report Desc in the cache based on the roam score */
+       if ( pNeighborReportDesc->roamScore > 0)
+       {
+          rrmStoreNeighborRptByRoamScore(pMac, pNeighborReportDesc);
+       }
+       else
+       {
+           smsLog(pMac, LOGE, FL("Roam score of BSSID  %02x:%02x:%02x:%02x:%02x:%02x is 0, Ignoring.."), 
+                        pNeighborRpt->sNeighborBssDescription[i].bssId[0],
+                        pNeighborRpt->sNeighborBssDescription[i].bssId[1],
+                        pNeighborRpt->sNeighborBssDescription[i].bssId[2],
+                        pNeighborRpt->sNeighborBssDescription[i].bssId[3],
+                        pNeighborRpt->sNeighborBssDescription[i].bssId[4],
+                        pNeighborRpt->sNeighborBssDescription[i].bssId[5]);
+
+           vos_mem_free(pNeighborReportDesc->pNeighborBssDescription);
+           vos_mem_free(pNeighborReportDesc);
+       }
+   }
+end:  
+   
+   if (!csrLLCount(&pMac->rrm.rrmSmeContext.neighborReportCache))
+      vosStatus = VOS_STATUS_E_FAILURE;
+ 
+   /* Received a report from AP. Indicate SUCCESS to the caller if there are some valid reports */
+   rrmIndicateNeighborReportResult(pMac, vosStatus);
+
+   return status;
+}
+/*--------------------------------------------------------------------------
+  \brief sme_RrmMsgProcessor() - sme_ProcessMsg() calls this function for the 
+  messages that are handled by SME RRM module.
+  
+  \param pMac - Pointer to the global MAC parameter structure.
+  \param msg_type - the type of msg passed by PE as defined in wniApi.h
+  \param pMsgBuf - a pointer to a buffer that maps to various structures base 
+                   on the message type.
+                   The beginning of the buffer can always map to tSirSmeRsp.
+  
+  \return eHAL_STATUS_SUCCESS - Validation is successful.
+  
+  \sa
+  
+  --------------------------------------------------------------------------*/
+eHalStatus sme_RrmMsgProcessor( tpAniSirGlobal pMac,  v_U16_t msg_type, 
+                                void *pMsgBuf)
+{
+   VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, 
+         FL(" Msg = %d for RRM measurement\n") , msg_type );
+
+   //switch on the msg type & make the state transition accordingly
+   switch(msg_type)
+   {
+      case eWNI_SME_NEIGHBOR_REPORT_IND:
+         sme_RrmProcessNeighborReport( pMac, pMsgBuf );
+         break;
+
+      case eWNI_SME_BEACON_REPORT_REQ_IND:
+         sme_RrmProcessBeaconReportReqInd( pMac, pMsgBuf );
+         break;
+
+      default:
+         //err msg
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, 
+               FL("sme_RrmMsgProcessor:unknown msg type = %d\n"), msg_type);
+
+         break;
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn rrmIterMeasTimerHandle
+
+    \brief  Timer handler to handlet the timeout condition when a specific BT
+
+            stop event does not come back, in which case to restore back the
+
+            heartbeat timer.
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOID
+
+  ---------------------------------------------------------------------------*/
+
+void rrmIterMeasTimerHandle( v_PVOID_t userData )
+{
+   tpAniSirGlobal pMac = (tpAniSirGlobal) userData;
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "Randomization timer expired...send on next channel \n");
+#endif
+    //Issue a scan req for next channel.
+    sme_RrmIssueScanReq( pMac ); 
+}
+
+/* ---------------------------------------------------------------------------
+    
+    \fn rrmNeighborRspTimeoutHandler
+    
+    \brief  Timer handler to handle the timeout condition when a neighbor request is sent 
+                    and no neighbor response is received from the AP
+    
+    \param  pMac - The handle returned by macOpen.
+    
+    \return VOID
+    
+---------------------------------------------------------------------------*/
+    
+void rrmNeighborRspTimeoutHandler
+( v_PVOID_t userData )
+{
+   tpAniSirGlobal pMac = (tpAniSirGlobal) userData;
+#if defined WLAN_VOWIFI_DEBUG
+   smsLog( pMac, LOGE, "Neighbor Response timed out \n");
+#endif
+    rrmIndicateNeighborReportResult(pMac, VOS_STATUS_E_FAILURE);
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn rrmOpen
+
+    \brief  
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS
+
+            VOS_STATUS_E_FAILURE  success
+
+            VOS_STATUS_SUCCESS  failure
+
+  ---------------------------------------------------------------------------*/
+
+VOS_STATUS rrmOpen (tpAniSirGlobal pMac)
+
+{
+
+   VOS_STATUS vosStatus;
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+   eHalStatus   halStatus = eHAL_STATUS_SUCCESS;
+
+   pSmeRrmContext->rrmConfig.maxRandnInterval = 50; //ms
+
+   vosStatus = vos_timer_init( &pSmeRrmContext->IterMeasTimer,
+
+                      VOS_TIMER_TYPE_SW,
+
+                      rrmIterMeasTimerHandle,
+
+                      (void*) pMac);
+
+   if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
+
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "rrmOpen: Fail to init timer");
+
+       return VOS_STATUS_E_FAILURE;
+   }
+
+   vosStatus = vos_timer_init( &pSmeRrmContext->neighborReqControlInfo.neighborRspWaitTimer,
+
+                      VOS_TIMER_TYPE_SW,
+
+                      rrmNeighborRspTimeoutHandler,
+
+                      (void*) pMac);
+
+   if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
+
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "rrmOpen: Fail to init timer");
+
+       return VOS_STATUS_E_FAILURE;
+   }
+
+   pSmeRrmContext->neighborReqControlInfo.isNeighborRspPending = eANI_BOOLEAN_FALSE;
+
+   halStatus = csrLLOpen(pMac->hHdd, &pSmeRrmContext->neighborReportCache);
+   if (eHAL_STATUS_SUCCESS != halStatus)
+   {
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "rrmOpen: Fail to open neighbor cache result");
+       return VOS_STATUS_E_FAILURE;
+   }
+
+   return VOS_STATUS_SUCCESS;
+}
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn rrmClose
+
+    \brief  
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS
+
+            VOS_STATUS_E_FAILURE  success
+
+            VOS_STATUS_SUCCESS  failure
+
+  ---------------------------------------------------------------------------*/
+
+VOS_STATUS rrmClose (tpAniSirGlobal pMac)
+
+{
+
+   VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+
+   if( VOS_TIMER_STATE_RUNNING == vos_timer_getCurrentState( &pSmeRrmContext->IterMeasTimer ) )
+   {
+      vosStatus = vos_timer_stop( &pSmeRrmContext->IterMeasTimer );
+      if(!VOS_IS_STATUS_SUCCESS(vosStatus))
+      { 
+         VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, FL("Timer stop fail") );
+      }
+   } 
+
+   vosStatus = vos_timer_destroy( &pSmeRrmContext->IterMeasTimer ); 
+   if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
+
+       VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, FL("Fail to destroy timer") );
+
+   }
+
+   rrmLLPurgeNeighborCache(pMac, &pSmeRrmContext->neighborReportCache);
+      
+   csrLLClose(&pSmeRrmContext->neighborReportCache);
+
+   return vosStatus;
+
+}
+
+
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn rrmReady
+
+    \brief  fn
+
+    \param  pMac - The handle returned by macOpen.
+
+    \return VOS_STATUS
+
+  ---------------------------------------------------------------------------*/
+
+VOS_STATUS rrmReady (tpAniSirGlobal pMac)
+
+{
+
+    return VOS_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn rrmChangeDefaultConfigParam
+    \brief  fn
+
+    \param  pMac - The handle returned by macOpen.
+    \param  pRrmConfig - pointer to new rrm configs.
+
+    \return VOS_STATUS
+
+  ---------------------------------------------------------------------------*/
+VOS_STATUS rrmChangeDefaultConfigParam(tpAniSirGlobal pMac, tpRrmConfigParam pRrmConfig)
+{
+   vos_mem_copy( &pMac->rrm.rrmSmeContext.rrmConfig, pRrmConfig, sizeof( tRrmConfigParam ) ); 
+
+   return VOS_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+    
+    \fn smeRrmGetFirstBssEntryFromNeighborCache()
+    
+    \brief  This function returns the first entry from the neighbor cache to the caller
+
+    \param  pMac - The handle returned by macOpen.
+    
+    \return VOID
+    
+---------------------------------------------------------------------------*/
+tRrmNeighborReportDesc* smeRrmGetFirstBssEntryFromNeighborCache( tpAniSirGlobal pMac)
+{
+   tListElem *pEntry;
+   tRrmNeighborReportDesc *pTempBssEntry = NULL;
+   tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
+
+
+   pEntry = csrLLPeekHead( &pSmeRrmContext->neighborReportCache, LL_ACCESS_LOCK );
+
+   if(!pEntry || !csrLLCount(&pSmeRrmContext->neighborReportCache))
+   {
+      //list empty
+      smsLog(pMac, LOGW, FL("List empty\n"));
+      return NULL;
+   }
+
+   pTempBssEntry = GET_BASE_ADDR( pEntry, tRrmNeighborReportDesc, List );
+
+   return pTempBssEntry;
+}
+
+/* ---------------------------------------------------------------------------
+    
+    \fn smeRrmGetNextBssEntryFromNeighborCache()
+    
+    \brief  This function returns the entry next to the given entry from the 
+                neighbor cache to the caller
+
+    \param  pMac - The handle returned by macOpen.
+    
+    \return VOID
+    
+---------------------------------------------------------------------------*/
+tRrmNeighborReportDesc* smeRrmGetNextBssEntryFromNeighborCache( tpAniSirGlobal pMac, 
+                                                        tpRrmNeighborReportDesc pBssEntry)
+{
+   tListElem *pEntry;
+   tRrmNeighborReportDesc *pTempBssEntry = NULL;
+
+   pEntry = csrLLNext(&pMac->rrm.rrmSmeContext.neighborReportCache, &pBssEntry->List, LL_ACCESS_LOCK);
+
+   if(!pEntry)
+   {
+      //list empty
+      smsLog(pMac, LOGW, FL("List empty\n"));
+      return NULL;
+   }
+
+   pTempBssEntry = GET_BASE_ADDR( pEntry, tRrmNeighborReportDesc, List );
+
+   return pTempBssEntry;
+}
+
+#ifdef FEATURE_WLAN_CCX
+void csrCcxSendAdjacentApRepMsg(tpAniSirGlobal pMac, tCsrRoamSession *pSession)
+{
+   tpSirAdjacentApRepInd pAdjRep;
+   tANI_U16 length;
+   tANI_U32 roamTS2;
+   
+   smsLog( pMac, LOG1, "Adjacent AP Report Msg to PE\n");
+
+   length = sizeof(tSirAdjacentApRepInd );
+   pAdjRep = vos_mem_malloc ( length );
+
+   if ( NULL == pAdjRep )
+   {
+       smsLog( pMac, LOGP, "Unable to allocate memory for Adjacent AP report");
+       return;
+   }
+
+   vos_mem_zero( pAdjRep, length );
+   pAdjRep->messageType = eWNI_SME_CCX_ADJACENT_AP_REPORT;
+   pAdjRep->length = length;
+   pAdjRep->channelNum = pSession->prevOpChannel;
+   vos_mem_copy( pAdjRep->bssid, &pSession->connectedProfile.bssid, sizeof(tSirMacAddr) );
+   vos_mem_copy( pAdjRep->prevApMacAddr, &pSession->prevApBssid, sizeof(tSirMacAddr) );
+   vos_mem_copy( &pAdjRep->prevApSSID, &pSession->prevApSSID, sizeof(tSirMacSSid) );
+   roamTS2 = vos_timer_get_system_time();
+   pAdjRep->tsmRoamdelay = roamTS2 - pSession->roamTS1;
+   pAdjRep->roamReason =SIR_CCX_ASSOC_REASON_UNSPECIFIED;
+   pAdjRep->clientDissSecs =(pAdjRep->tsmRoamdelay/1000);
+
+   palSendMBMessage(pMac->hHdd, pAdjRep);
+
+   return;
+}
+#endif   /* FEATURE_WLAN_CCX */
+#endif
diff --git a/CORE/SME/src/sme_common/sme_Api.c b/CORE/SME/src/sme_common/sme_Api.c
new file mode 100644
index 0000000..642e8f0
--- /dev/null
+++ b/CORE/SME/src/sme_common/sme_Api.c
@@ -0,0 +1,6353 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+/**=========================================================================
+
+  \file  smeApi.c
+
+  \brief Definitions for SME APIs
+
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+
+   Qualcomm Confidential and Proprietary.
+
+  ========================================================================*/
+
+/*===========================================================================
+
+                      EDIT HISTORY FOR FILE
+
+
+  This section contains comments describing changes made to the module.
+  Notice that changes are listed in reverse chronological order.
+
+
+
+  when           who                 what, where, why
+----------       ---                --------------------------------------------------------
+06/03/10     js                     Added support to hostapd driven
+ *                                  deauth/disassoc/mic failure
+
+===========================================================================*/
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+#include "halInternal.h"
+#endif
+
+#include "smsDebug.h"
+#include "sme_Api.h"
+#include "csrInsideApi.h"
+#include "smeInside.h"
+#include "csrInternal.h"
+#include "wlan_qct_wda.h"
+#include "halMsgApi.h"
+
+#ifdef WLAN_SOFTAP_FEATURE
+#include "sapApi.h"
+#endif
+
+
+
+#if !defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+extern tSirRetStatus uMacPostCtrlMsg(void* pSirGlobal, tSirMbMsg* pMb);
+
+#include <wlan_qct_pal_api.h>
+#endif
+
+// TxMB Functions
+extern eHalStatus pmcPrepareCommand( tpAniSirGlobal pMac, eSmeCommandType cmdType, void *pvParam,
+                            tANI_U32 size, tSmeCmd **ppCmd );
+extern void pmcReleaseCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+extern void qosReleaseCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand );
+#if defined WLAN_FEATURE_P2P
+extern eHalStatus p2pProcessRemainOnChannelCmd(tpAniSirGlobal pMac, tSmeCmd *p2pRemainonChn);
+extern eHalStatus sme_remainOnChnRsp( tpAniSirGlobal pMac, tANI_U8 *pMsg);
+extern eHalStatus sme_mgmtFrmInd( tHalHandle hHal, tpSirSmeMgmtFrameInd pSmeMgmtFrm);
+extern eHalStatus sme_remainOnChnReady( tHalHandle hHal, tANI_U8* pMsg);
+extern eHalStatus sme_sendActionCnf( tHalHandle hHal, tANI_U8* pMsg);
+extern eHalStatus p2pProcessNoAReq(tpAniSirGlobal pMac, tSmeCmd *pNoACmd);
+#endif
+
+static eHalStatus initSmeCmdList(tpAniSirGlobal pMac);
+static void smeAbortCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fStopping );
+
+eCsrPhyMode sme_GetPhyMode(tHalHandle hHal);
+
+eHalStatus sme_HandleChangeCountryCode(tpAniSirGlobal pMac,  void *pMsgBuf);
+
+eHalStatus sme_HandlePreChannelSwitchInd(tHalHandle hHal);
+
+eHalStatus sme_HandlePostChannelSwitchInd(tHalHandle hHal);
+
+//Internal SME APIs
+eHalStatus sme_AcquireGlobalLock( tSmeStruct *psSme)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+
+    if(psSme)
+    {
+        if( VOS_IS_STATUS_SUCCESS( vos_lock_acquire( &psSme->lkSmeGlobalLock) ) )
+        {
+            status = eHAL_STATUS_SUCCESS;
+        }
+    }
+
+    return (status);
+}
+
+
+eHalStatus sme_ReleaseGlobalLock( tSmeStruct *psSme)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+
+    if(psSme)
+    {
+        if( VOS_IS_STATUS_SUCCESS( vos_lock_release( &psSme->lkSmeGlobalLock) ) )
+        {
+            status = eHAL_STATUS_SUCCESS;
+        }
+    }
+
+    return (status);
+}
+
+
+
+static eHalStatus initSmeCmdList(tpAniSirGlobal pMac)
+{
+    eHalStatus status;
+    tSmeCmd *pCmd;
+
+    pMac->sme.totalSmeCmd = SME_TOTAL_COMMAND;
+    if(HAL_STATUS_SUCCESS(status = csrLLOpen(pMac->hHdd, &pMac->sme.smeCmdActiveList)))
+    {
+        if(HAL_STATUS_SUCCESS(status = csrLLOpen(pMac->hHdd, &pMac->sme.smeCmdPendingList)))
+        {
+            if(HAL_STATUS_SUCCESS(status = csrLLOpen(pMac->hHdd, &pMac->sme.smeCmdFreeList)))
+            {
+                status = palAllocateMemory(pMac->hHdd, (void **)&pCmd, sizeof(tSmeCmd) * pMac->sme.totalSmeCmd);
+                if(HAL_STATUS_SUCCESS(status))
+                {
+                    tANI_U32 c;
+
+                    palZeroMemory(pMac->hHdd, pCmd, sizeof(tSmeCmd) * pMac->sme.totalSmeCmd);
+                    pMac->sme.pSmeCmdBufAddr = pCmd;
+                    for(c = 0; c < pMac->sme.totalSmeCmd; c++)
+                    {
+                        csrLLInsertTail(&pMac->sme.smeCmdFreeList, &pCmd[c].Link, LL_ACCESS_LOCK);
+                    }
+                }
+            }
+        }
+    }
+
+    return (status);
+}
+
+
+void smeReleaseCommand(tpAniSirGlobal pMac, tSmeCmd *pCmd)
+{
+    pCmd->command = eSmeNoCommand;
+    csrLLInsertTail(&pMac->sme.smeCmdFreeList, &pCmd->Link, LL_ACCESS_LOCK);
+}
+
+
+
+static void smeReleaseCmdList(tpAniSirGlobal pMac, tDblLinkList *pList)
+{
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+
+    while((pEntry = csrLLRemoveHead(pList, LL_ACCESS_LOCK)) != NULL)
+    {
+        //TODO: base on command type to call release functions
+        //reinitialize different command types so they can be reused
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        smeAbortCommand(pMac, pCommand, eANI_BOOLEAN_TRUE);
+    }
+}
+
+static void purgeSmeCmdList(tpAniSirGlobal pMac)
+{
+    //release any out standing commands back to free command list
+    smeReleaseCmdList(pMac, &pMac->sme.smeCmdPendingList);
+    smeReleaseCmdList(pMac, &pMac->sme.smeCmdActiveList);
+}
+
+void purgeSmeSessionCmdList(tpAniSirGlobal pMac, tANI_U32 sessionId)
+{
+    //release any out standing commands back to free command list
+    tListElem *pEntry, *pNext;
+    tSmeCmd *pCommand;
+    tDblLinkList *pList = &pMac->sme.smeCmdPendingList;
+    tDblLinkList localList;
+
+    vos_mem_zero(&localList, sizeof(tDblLinkList));
+    if(!HAL_STATUS_SUCCESS(csrLLOpen(pMac->hHdd, &localList)))
+    {
+        smsLog(pMac, LOGE, FL(" failed to open list"));
+        return;
+    }
+
+    csrLLLock(pList);
+    pEntry = csrLLPeekHead(pList, LL_ACCESS_NOLOCK);
+    while(pEntry != NULL)
+    {
+        pNext = csrLLNext(pList, pEntry, LL_ACCESS_NOLOCK);
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        if(pCommand->sessionId == sessionId)
+        {
+            if(csrLLRemoveEntry(pList, pEntry, LL_ACCESS_NOLOCK))
+            {
+                csrLLInsertTail(&localList, pEntry, LL_ACCESS_NOLOCK);
+            }
+        }
+        pEntry = pNext;
+    }
+    csrLLUnlock(pList);
+
+    while( (pEntry = csrLLRemoveHead(&localList, LL_ACCESS_NOLOCK)) )
+    {
+        pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        smeAbortCommand(pMac, pCommand, eANI_BOOLEAN_TRUE);
+    }
+    csrLLClose(&localList);
+
+}
+
+
+static eHalStatus freeSmeCmdList(tpAniSirGlobal pMac)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+
+    purgeSmeCmdList(pMac);
+    csrLLClose(&pMac->sme.smeCmdPendingList);
+    csrLLClose(&pMac->sme.smeCmdActiveList);
+    csrLLClose(&pMac->sme.smeCmdFreeList);
+
+    if(NULL != pMac->sme.pSmeCmdBufAddr)
+    {
+        status = palFreeMemory(pMac->hHdd, pMac->sme.pSmeCmdBufAddr);
+        pMac->sme.pSmeCmdBufAddr = NULL;
+    }
+
+    return (status);
+}
+
+
+void dumpCsrCommandInfo(tpAniSirGlobal pMac, tSmeCmd *pCmd)
+{
+#ifdef WLAN_DEBUG
+    switch( pCmd->command )
+    {
+    case eSmeCommandScan:
+        smsLog( pMac, LOGE, " scan command reason is %d", pCmd->u.scanCmd.reason );
+        break;
+
+    case eSmeCommandRoam:
+        smsLog( pMac, LOGE, " roam command reason is %d", pCmd->u.roamCmd.roamReason );
+        break;
+
+    case eSmeCommandWmStatusChange:
+        smsLog( pMac, LOGE, " WMStatusChange command type is %d", pCmd->u.wmStatusChangeCmd.Type );
+        break;
+
+    case eSmeCommandSetKey:
+        smsLog( pMac, LOGE, " setKey command auth(%d) enc(%d)", 
+                        pCmd->u.setKeyCmd.authType, pCmd->u.setKeyCmd.encType );
+        break;
+
+    case eSmeCommandRemoveKey:
+        smsLog( pMac, LOGE, " removeKey command auth(%d) enc(%d)", 
+                        pCmd->u.removeKeyCmd.authType, pCmd->u.removeKeyCmd.encType );
+        break;
+
+    default:
+        break;
+    }
+#endif  //#ifdef WLAN_DEBUG
+}
+
+tSmeCmd *smeGetCommandBuffer( tpAniSirGlobal pMac )
+{
+    tSmeCmd *pRetCmd = NULL, *pTempCmd = NULL;
+    tListElem *pEntry;
+
+    pEntry = csrLLRemoveHead( &pMac->sme.smeCmdFreeList, LL_ACCESS_LOCK );
+
+    // If we can get another MS Msg buffer, then we are ok.  Just link
+    // the entry onto the linked list.  (We are using the linked list
+    // to keep track of tfhe message buffers).
+    if ( pEntry )
+    {
+        pRetCmd = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+    }
+    else {
+        int idx = 1;
+
+        //Cannot change pRetCmd here since it needs to return later.
+        pEntry = csrLLPeekHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK );
+        if( pEntry )
+        {
+           pTempCmd = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+        }
+        smsLog( pMac, LOGE, "Out of command buffer.... command (0x%X) stuck\n", 
+           (pTempCmd) ? pTempCmd->command : eSmeNoCommand );
+        if(pTempCmd)
+        {
+            if( eSmeCsrCommandMask & pTempCmd->command )
+            {
+                //CSR command is stuck. See what the reason code is for that command
+                dumpCsrCommandInfo(pMac, pTempCmd);
+            }
+        } //if(pTempCmd)
+
+        //dump what is in the pending queue
+        csrLLLock(&pMac->sme.smeCmdPendingList);
+        pEntry = csrLLPeekHead( &pMac->sme.smeCmdPendingList, LL_ACCESS_NOLOCK );
+        while(pEntry)
+        {
+            pTempCmd = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+            smsLog( pMac, LOGE, "Out of command buffer.... SME pending command #%d (0x%X)\n",
+                    idx++, pTempCmd->command );
+            if( eSmeCsrCommandMask & pTempCmd->command )
+            {
+                //CSR command is stuck. See what the reason code is for that command
+                dumpCsrCommandInfo(pMac, pTempCmd);
+            }
+            pEntry = csrLLNext( &pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_NOLOCK );
+        }
+        csrLLUnlock(&pMac->sme.smeCmdPendingList);
+
+        //There may be some more command in CSR's own pending queue
+        csrLLLock(&pMac->roam.roamCmdPendingList);
+        pEntry = csrLLPeekHead( &pMac->roam.roamCmdPendingList, LL_ACCESS_NOLOCK );
+        while(pEntry)
+        {
+            pTempCmd = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+            smsLog( pMac, LOGE, "Out of command buffer.... CSR pending command #%d (0x%X)\n",
+                    idx++, pTempCmd->command );
+            dumpCsrCommandInfo(pMac, pTempCmd);
+            pEntry = csrLLNext( &pMac->roam.roamCmdPendingList, pEntry, LL_ACCESS_NOLOCK );
+        }
+        csrLLUnlock(&pMac->roam.roamCmdPendingList);
+    }
+
+    return( pRetCmd );
+}
+
+
+void smePushCommand( tpAniSirGlobal pMac, tSmeCmd *pCmd, tANI_BOOLEAN fHighPriority )
+{
+    if ( fHighPriority )
+    {
+        csrLLInsertHead( &pMac->sme.smeCmdPendingList, &pCmd->Link, LL_ACCESS_LOCK );
+    }
+    else
+    {
+        csrLLInsertTail( &pMac->sme.smeCmdPendingList, &pCmd->Link, LL_ACCESS_LOCK );
+    }
+
+    // process the command queue...
+    smeProcessPendingQueue( pMac );
+
+    return;
+}
+
+
+static eSmeCommandType smeIsFullPowerNeeded( tpAniSirGlobal pMac, tSmeCmd *pCommand )
+{
+    eSmeCommandType pmcCommand = eSmeNoCommand;
+    tANI_BOOLEAN fFullPowerNeeded = eANI_BOOLEAN_FALSE;
+    tPmcState pmcState;
+    eHalStatus status;
+
+    do
+    {
+        pmcState = pmcGetPmcState(pMac);
+
+        status = csrIsFullPowerNeeded( pMac, pCommand, NULL, &fFullPowerNeeded );
+        if( !HAL_STATUS_SUCCESS(status) )
+        {
+            //PMC state is not right for the command, drop it
+            return ( eSmeDropCommand );
+        }
+        if( fFullPowerNeeded  ) break;
+        fFullPowerNeeded = ( ( eSmeCommandAddTs == pCommand->command ) ||
+                    ( eSmeCommandDelTs ==  pCommand->command ) );
+        if( fFullPowerNeeded ) break;
+#ifdef WLAN_FEATURE_P2P
+        fFullPowerNeeded = (pmcState == IMPS && 
+                            eSmeCommandRemainOnChannel == pCommand->command);
+        if(fFullPowerNeeded) break;
+#endif
+    } while(0);
+
+    if( fFullPowerNeeded )
+    {
+        switch( pmcState )
+        {
+        case IMPS:
+        case STANDBY:
+            pmcCommand = eSmeCommandExitImps;
+            break;
+
+        case BMPS:
+            pmcCommand = eSmeCommandExitBmps;
+            break;
+
+        case UAPSD:
+            pmcCommand = eSmeCommandExitUapsd;
+            break;
+
+        case WOWL:
+            pmcCommand = eSmeCommandExitWowl;
+            break;
+
+        default:
+            break;
+        }
+    }
+
+    return ( pmcCommand );
+}
+
+
+//For commands that need to do extra cleanup.
+static void smeAbortCommand( tpAniSirGlobal pMac, tSmeCmd *pCommand, tANI_BOOLEAN fStopping )
+{
+    if( eSmePmcCommandMask & pCommand->command )
+    {
+        pmcAbortCommand( pMac, pCommand, fStopping );
+    }
+    else if ( eSmeCsrCommandMask & pCommand->command )
+    {
+        csrAbortCommand( pMac, pCommand, fStopping );
+    }
+    else
+    {
+        switch( pCommand->command )
+        {
+#ifdef WLAN_FEATURE_P2P
+            case eSmeCommandRemainOnChannel:
+                if (NULL != pCommand->u.remainChlCmd.callback)
+                {
+                    remainOnChanCallback callback = 
+                                            pCommand->u.remainChlCmd.callback;
+                    /* process the msg */
+                    if( callback )
+                    {
+                        callback(pMac, pCommand->u.remainChlCmd.callbackCtx, 
+                                            eCSR_SCAN_ABORT );
+                    }
+                }
+                smeReleaseCommand( pMac, pCommand );
+                break;
+#endif
+            default:
+                smeReleaseCommand( pMac, pCommand );
+                break;
+        }
+    }
+}
+
+
+
+tANI_BOOLEAN smeProcessCommand( tpAniSirGlobal pMac )
+{
+    tANI_BOOLEAN fContinue = eANI_BOOLEAN_FALSE;
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tListElem *pEntry;
+    tSmeCmd *pCommand;
+    eSmeCommandType pmcCommand = eSmeNoCommand;
+
+    // if the ActiveList is empty, then nothing is active so we can process a
+    // pending command...
+    //alwasy lock active list before locking pending list
+    csrLLLock( &pMac->sme.smeCmdActiveList );
+    if ( csrLLIsListEmpty( &pMac->sme.smeCmdActiveList, LL_ACCESS_NOLOCK ) )
+    {
+        if(!csrLLIsListEmpty(&pMac->sme.smeCmdPendingList, LL_ACCESS_LOCK))
+        {
+            //Peek the command
+            pEntry = csrLLPeekHead( &pMac->sme.smeCmdPendingList, LL_ACCESS_LOCK );
+            if( pEntry )
+            {
+                pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+                //We cannot execute any command in wait-for-key state until setKey is through.
+                if( CSR_IS_WAIT_FOR_KEY( pMac, pCommand->sessionId ) )
+                {
+                    if( !CSR_IS_SET_KEY_COMMAND( pCommand ) )
+                    {
+                        csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                        smsLog(pMac, LOGE, "  Cannot process command(%d) while waiting for key\n", pCommand->command);
+                        return ( eANI_BOOLEAN_FALSE );
+                    }
+                }
+                pmcCommand = smeIsFullPowerNeeded( pMac, pCommand );
+                if( eSmeDropCommand == pmcCommand )
+                {
+                    //This command is not ok for current PMC state
+                    if( csrLLRemoveEntry( &pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_LOCK ) )
+                    {
+                        smeAbortCommand( pMac, pCommand, eANI_BOOLEAN_FALSE );
+                    }
+                    csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                    //tell caller to continue
+                    return (eANI_BOOLEAN_TRUE);
+                }
+                else if( eSmeNoCommand != pmcCommand )
+                {
+                    tExitBmpsInfo exitBmpsInfo;
+                    void *pv = NULL;
+                    tANI_U32 size = 0;
+                    tSmeCmd *pPmcCmd = NULL;
+
+                    if( eSmeCommandExitBmps == pmcCommand )
+                    {
+                        exitBmpsInfo.exitBmpsReason = eSME_REASON_OTHER;
+                        pv = (void *)&exitBmpsInfo;
+                        size = sizeof(tExitBmpsInfo);
+                    }
+                    //pmcCommand has to be one of the exit power save command
+                    status = pmcPrepareCommand( pMac, pmcCommand, pv, size, &pPmcCmd );
+                    if( HAL_STATUS_SUCCESS( status ) && pPmcCmd )
+                    {
+                        //Force this command to wake up the chip
+                        csrLLInsertHead( &pMac->sme.smeCmdActiveList, &pPmcCmd->Link, LL_ACCESS_NOLOCK );
+                        csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                        fContinue = pmcProcessCommand( pMac, pPmcCmd );
+                        if( fContinue )
+                        {
+                            //The command failed, remove it
+                            if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, &pPmcCmd->Link, LL_ACCESS_NOLOCK ) )
+                            {
+                                pmcReleaseCommand( pMac, pPmcCmd );
+                            }
+                        }
+                    }
+                    else
+                    {
+                        csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                        smsLog( pMac, LOGE, FL(  "Cannot issue command(0x%X) to wake up the chip. Status = %d\n"), pmcCommand, status );
+                        //Let it retry
+                        fContinue = eANI_BOOLEAN_TRUE;
+                    }
+                    return fContinue;
+                }
+                if ( csrLLRemoveEntry( &pMac->sme.smeCmdPendingList, pEntry, LL_ACCESS_LOCK ) )
+                {
+                    // we can reuse the pCommand
+
+                    // Insert the command onto the ActiveList...
+                    csrLLInsertHead( &pMac->sme.smeCmdActiveList, &pCommand->Link, LL_ACCESS_NOLOCK );
+
+                    // .... and process the command.
+
+                    switch ( pCommand->command )
+                    {
+
+                        case eSmeCommandScan:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            status = csrProcessScanCommand( pMac, pCommand );
+                            break;
+
+                        case eSmeCommandRoam:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            status  = csrRoamProcessCommand( pMac, pCommand );
+                            break;
+
+                        case eSmeCommandWmStatusChange:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            csrRoamProcessWmStatusChangeCommand(pMac, pCommand);
+                            break;
+
+                        case eSmeCommandSetKey:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            status = csrRoamProcessSetKeyCommand( pMac, pCommand );
+                            if(!HAL_STATUS_SUCCESS(status))
+                            {
+                                if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, 
+                                            &pCommand->Link, LL_ACCESS_LOCK ) )
+                                {
+                                    csrReleaseCommandSetKey( pMac, pCommand );
+                                }
+                            }
+                            break;
+
+                        case eSmeCommandRemoveKey:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            status = csrRoamProcessRemoveKeyCommand( pMac, pCommand );
+                            if(!HAL_STATUS_SUCCESS(status))
+                            {
+                                if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, 
+                                            &pCommand->Link, LL_ACCESS_LOCK ) )
+                                {
+                                    csrReleaseCommandRemoveKey( pMac, pCommand );
+                                }
+                            }
+                            break;
+
+                        case eSmeCommandAddStaSession:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            csrProcessAddStaSessionCommand( pMac, pCommand );
+                            break;
+                        case eSmeCommandDelStaSession:    
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            csrProcessDelStaSessionCommand( pMac, pCommand );
+                            break;
+
+#if defined WLAN_FEATURE_P2P
+                        case eSmeCommandRemainOnChannel:
+                            csrLLUnlock(&pMac->sme.smeCmdActiveList);
+                            p2pProcessRemainOnChannelCmd(pMac, pCommand);
+                            break;
+                        case eSmeCommandNoAUpdate:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            p2pProcessNoAReq(pMac,pCommand);
+#endif
+                        case eSmeCommandEnterImps:
+                        case eSmeCommandExitImps:
+                        case eSmeCommandEnterBmps:
+                        case eSmeCommandExitBmps:
+                        case eSmeCommandEnterUapsd:
+                        case eSmeCommandExitUapsd:
+                        case eSmeCommandEnterWowl:
+                        case eSmeCommandExitWowl:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            fContinue = pmcProcessCommand( pMac, pCommand );
+                            if( fContinue )
+                            {
+                                //The command failed, remove it
+                                if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList,
+                                            &pCommand->Link, LL_ACCESS_LOCK ) )
+                                {
+                                    pmcReleaseCommand( pMac, pCommand );
+                                }
+                            }
+                            break;
+
+                        //Treat standby differently here because caller may not be able to handle
+                        //the failure so we do our best here
+                        case eSmeCommandEnterStandby:
+                            if( csrIsConnStateDisconnected( pMac, pCommand->sessionId ) )
+                            {
+                                //It can continue
+                                csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                                fContinue = pmcProcessCommand( pMac, pCommand );
+                                if( fContinue )
+                                {
+                                    //The command failed, remove it
+                                    if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList,
+                                                &pCommand->Link, LL_ACCESS_LOCK ) )
+                                    {
+                                        pmcReleaseCommand( pMac, pCommand );
+                                    }
+                                }
+                            }
+                            else
+                            {
+                                //Need to issue a disconnect first before processing this command
+                                tSmeCmd *pNewCmd;
+
+                                //We need to re-run the command
+                                fContinue = eANI_BOOLEAN_TRUE;
+                                //Pull off the standby command first
+                                if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList,
+                                                &pCommand->Link, LL_ACCESS_NOLOCK ) )
+                                {
+                                    csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                                    //Need to call CSR function here because the disconnect command
+                                    //is handled by CSR
+                                    pNewCmd = csrGetCommandBuffer( pMac );
+                                    if( NULL != pNewCmd )
+                                    {
+                                        //Put the standby command to the head of the pending list first
+                                        csrLLInsertHead( &pMac->sme.smeCmdPendingList, &pCommand->Link,
+                                                        LL_ACCESS_LOCK );
+                                        pNewCmd->command = eSmeCommandRoam;
+                                        pNewCmd->u.roamCmd.roamReason = eCsrForcedDisassoc;
+                                        //Put the disassoc command before the standby command
+                                        csrLLInsertHead( &pMac->sme.smeCmdPendingList, &pNewCmd->Link,
+                                                        LL_ACCESS_LOCK );
+                                    }
+                                    else
+                                    {
+                                        //Continue the command here
+                                        fContinue = pmcProcessCommand( pMac, pCommand );
+                                        if( fContinue )
+                                        {
+                                            //The command failed, remove it
+                                            if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList,
+                                                        &pCommand->Link, LL_ACCESS_LOCK ) )
+                                            {
+                                                pmcReleaseCommand( pMac, pCommand );
+                                            }
+                                        }
+                                    }
+                                }
+                                else
+                                {
+                                    csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                                    smsLog( pMac, LOGE, FL(" failed to remove standby command\n") );
+                                    VOS_ASSERT(0);
+                                }
+                            }
+                            break;
+
+                        case eSmeCommandAddTs:
+                        case eSmeCommandDelTs:
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                            fContinue = qosProcessCommand( pMac, pCommand );
+                            if( fContinue )
+                            {
+                                //The command failed, remove it
+                                if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList,
+                                            &pCommand->Link, LL_ACCESS_NOLOCK ) )
+                                {
+//#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                                    qosReleaseCommand( pMac, pCommand );
+//#endif /* WLAN_MDM_CODE_REDUCTION_OPT*/
+                                }
+                            }
+#endif
+                            break;
+
+                        default:
+                            //something is wrong
+                            //remove it from the active list
+                            smsLog(pMac, LOGE, " csrProcessCommand processes an unknown command %d\n", pCommand->command);
+                            pEntry = csrLLRemoveHead( &pMac->sme.smeCmdActiveList, LL_ACCESS_NOLOCK );
+                            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                            pCommand = GET_BASE_ADDR( pEntry, tSmeCmd, Link );
+                            smeReleaseCommand( pMac, pCommand );
+                            status = eHAL_STATUS_FAILURE;
+                            break;
+                    }
+                    if(!HAL_STATUS_SUCCESS(status))
+                    {
+                        fContinue = eANI_BOOLEAN_TRUE;
+                    }
+                }//if(pEntry)
+                else
+                {
+                    //This is odd. Some one else pull off the command.
+                    csrLLUnlock( &pMac->sme.smeCmdActiveList );
+                }
+            }
+            else
+            {
+                csrLLUnlock( &pMac->sme.smeCmdActiveList );
+            }
+        }
+        else
+        {
+            //No command waiting
+            csrLLUnlock( &pMac->sme.smeCmdActiveList );
+            //This is only used to restart an idle mode scan, it means at least one other idle scan has finished.
+            if(pMac->scan.fRestartIdleScan && eANI_BOOLEAN_FALSE == pMac->scan.fCancelIdleScan)
+            {
+                tANI_U32 nTime = 0;
+
+                pMac->scan.fRestartIdleScan = eANI_BOOLEAN_FALSE;
+                if(!HAL_STATUS_SUCCESS(csrScanTriggerIdleScan(pMac, &nTime)))
+                {
+                    csrScanStartIdleScanTimer(pMac, nTime);
+                }
+            }
+        }
+    }
+    else {
+        csrLLUnlock( &pMac->sme.smeCmdActiveList );
+    }
+
+    return ( fContinue );
+}
+
+void smeProcessPendingQueue( tpAniSirGlobal pMac )
+{
+    while( smeProcessCommand( pMac ) );
+}
+
+
+tANI_BOOLEAN smeCommandPending(tpAniSirGlobal pMac)
+{
+    return ( !csrLLIsListEmpty( &pMac->sme.smeCmdActiveList, LL_ACCESS_NOLOCK ) ||
+        !csrLLIsListEmpty(&pMac->sme.smeCmdPendingList, LL_ACCESS_NOLOCK) );
+}
+
+
+
+//Global APIs
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_Open() - Initialze all SME modules and put them at idle state
+
+  The function initializes each module inside SME, PMC, CCM, CSR, etc. . Upon
+  successfully return, all modules are at idle state ready to start.
+
+  smeOpen must be called before any other SME APIs can be involved.
+  smeOpen must be called after macOpen.
+  This is a synchronuous call
+  \param hHal - The handle returned by macOpen.
+
+  \return eHAL_STATUS_SUCCESS - SME is successfully initialized.
+
+          Other status means SME is failed to be initialized
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_Open(tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   do {
+      pMac->sme.state = SME_STATE_STOP;
+      if( !VOS_IS_STATUS_SUCCESS( vos_lock_init( &pMac->sme.lkSmeGlobalLock ) ) )
+      {
+          smsLog( pMac, LOGE, "sme_Open failed init lock\n" );
+          status = eHAL_STATUS_FAILURE;
+          break;
+      }
+
+      status = ccmOpen(hHal);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE,
+                 "ccmOpen failed during initialization with status=%d", status );
+         break;
+      }
+
+      status = csrOpen(pMac);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE,
+                 "csrOpen failed during initialization with status=%d", status );
+         break;
+      }
+
+      status = pmcOpen(hHal);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE,
+                 "pmcOpen failed during initialization with status=%d", status );
+         break;
+      }
+
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+      status = sme_QosOpen(pMac);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE,
+                 "Qos open failed during initialization with status=%d", status );
+         break;
+      }
+
+      status = btcOpen(pMac);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE,
+                 "btcOpen open failed during initialization with status=%d", status );
+         break;
+      }
+#endif
+
+      if(!HAL_STATUS_SUCCESS((status = initSmeCmdList(pMac))))
+          break;
+
+#ifdef WLAN_SOFTAP_FEATURE
+      {
+         v_PVOID_t pvosGCtx = vos_get_global_context(VOS_MODULE_ID_SAP, NULL);
+         if ( NULL == pvosGCtx ){
+            smsLog( pMac, LOGE, "WLANSAP_Open open failed during initialization");
+            status = eHAL_STATUS_FAILURE;
+            break;
+         }
+
+         status = WLANSAP_Open( pvosGCtx );
+         if ( ! HAL_STATUS_SUCCESS( status ) ) {
+             smsLog( pMac, LOGE,
+                     "WLANSAP_Open open failed during initialization with status=%d", status );
+             break;
+         }
+      }
+#endif
+#if defined WLAN_FEATURE_VOWIFI
+      status = rrmOpen(pMac);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE,
+                 "rrmOpen open failed during initialization with status=%d", status );
+         break;
+      }
+#endif
+
+#if defined WLAN_FEATURE_VOWIFI_11R
+      sme_FTOpen(pMac);
+#endif
+#if defined WLAN_FEATURE_P2P
+      sme_p2pOpen(pMac);
+#endif
+
+   }while (0);
+
+   return status;
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+/*--------------------------------------------------------------------------
+
+  \brief sme_set11dinfo() - Set the 11d information about valid channels
+   and there power using information from nvRAM
+   This function is called only for AP.
+
+  This is a synchronuous call
+
+  \param hHal - The handle returned by macOpen.
+  \Param pSmeConfigParams - a pointer to a caller allocated object of
+  typedef struct _smeConfigParams.
+
+  \return eHAL_STATUS_SUCCESS - SME update the config parameters successfully.
+
+          Other status means SME is failed to update the config parameters.
+  \sa
+--------------------------------------------------------------------------*/
+
+eHalStatus sme_set11dinfo(tHalHandle hHal,  tpSmeConfigParams pSmeConfigParams)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if (NULL == pSmeConfigParams ) {
+      smsLog( pMac, LOGE,
+              "Empty config param structure for SME, nothing to update");
+      return status;
+   }
+
+   status = csrSetChannels(hHal, &pSmeConfigParams->csrConfig );
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "csrChangeDefaultConfigParam failed with status=%d\n",
+              status );
+   }
+    return status;
+}
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_getSoftApDomain() - Get the current regulatory domain of softAp.
+
+  This is a synchronuous call
+
+  \param hHal - The handle returned by HostapdAdapter.
+  \Param v_REGDOMAIN_t - The current Regulatory Domain requested for SoftAp.
+
+  \return eHAL_STATUS_SUCCESS - SME successfully completed the request.
+
+          Other status means, failed to get the current regulatory domain.
+  \sa
+--------------------------------------------------------------------------*/
+
+eHalStatus sme_getSoftApDomain(tHalHandle hHal,  v_REGDOMAIN_t *domainIdSoftAp)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if (NULL == domainIdSoftAp ) {
+      smsLog( pMac, LOGE, "Uninitialized domain Id");
+      return status;
+   }    
+
+   *domainIdSoftAp = pMac->scan.domainIdCurrent;
+   status = eHAL_STATUS_SUCCESS;
+    
+   return status;
+}
+
+
+eHalStatus sme_setRegInfo(tHalHandle hHal,  tANI_U8 *apCntryCode)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if (NULL == apCntryCode ) {
+      smsLog( pMac, LOGE, "Empty Country Code, nothing to update");
+      return status;
+   }
+
+   status = csrSetRegInfo(hHal, apCntryCode );
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "csrSetRegInfo failed with status=%d\n",
+              status );
+   }
+    return status;
+}
+
+#endif
+#ifdef FEATURE_WLAN_SCAN_PNO
+/*--------------------------------------------------------------------------
+
+  \brief sme_UpdateChannelConfig() - Update channel configuration in RIVA.
+ 
+  It is used at driver start up to inform RIVA of the default channel 
+  configuration. 
+
+  This is a synchronuous call
+
+  \param hHal - The handle returned by macOpen.
+  
+  \return eHAL_STATUS_SUCCESS - SME update the channel config successfully.
+
+          Other status means SME is failed to update the channel config.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_UpdateChannelConfig(tHalHandle hHal)
+{
+  tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+  pmcUpdateScanParams( pMac, &(pMac->roam.configParam), 
+                      &pMac->scan.base20MHzChannels, FALSE);
+  return eHAL_STATUS_SUCCESS;
+}
+#endif // FEATURE_WLAN_SCAN_PNLO
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_UpdateConfig() - Change configurations for all SME moduels
+
+  The function updates some configuration for modules in SME, CCM, CSR, etc
+  during SMEs close open sequence.
+
+  Modules inside SME apply the new configuration at the next transaction.
+
+  This is a synchronuous call
+
+  \param hHal - The handle returned by macOpen.
+  \Param pSmeConfigParams - a pointer to a caller allocated object of
+  typedef struct _smeConfigParams.
+
+  \return eHAL_STATUS_SUCCESS - SME update the config parameters successfully.
+
+          Other status means SME is failed to update the config parameters.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_UpdateConfig(tHalHandle hHal, tpSmeConfigParams pSmeConfigParams)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if (NULL == pSmeConfigParams ) {
+      smsLog( pMac, LOGE,
+              "Empty config param structure for SME, nothing to update");
+      return status;
+   }
+
+   status = csrChangeDefaultConfigParam(pMac, &pSmeConfigParams->csrConfig);
+
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "csrChangeDefaultConfigParam failed with status=%d\n",
+              status );
+   }
+#if defined WLAN_FEATURE_P2P_INTERNAL
+   status = p2pChangeDefaultConfigParam(pMac, &pSmeConfigParams->p2pConfig);
+
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "p2pChangeDefaultConfigParam failed with status=%d\n",
+              status );
+   }
+#endif
+#if defined WLAN_FEATURE_VOWIFI
+   status = rrmChangeDefaultConfigParam(hHal, &pSmeConfigParams->rrmConfig);
+
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "rrmChangeDefaultConfigParam failed with status=%d\n",
+              status );
+   }
+#endif
+   //For SOC, CFG is set before start
+   //We don't want to apply global CFG in connect state because that may cause some side affect
+   if(
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+      //For the new init sequence, CFGs need to apply before vos_start is call
+      //No need to wait for ready state.
+      SME_IS_READY(pMac) && 
+#endif
+      csrIsAllSessionDisconnected( pMac) )
+   {
+       csrSetGlobalCfgs(pMac);
+   }
+
+   return status;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ChangeConfigParams
+    \brief The SME API exposed for HDD to provide config params to SME during
+    SMEs stop -> start sequence.
+
+    If HDD changed the domain that will cause a reset. This function will
+    provide the new set of 11d information for the new domain. Currrently this
+    API provides info regarding 11d only at reset but we can extend this for
+    other params (PMC, QoS) which needs to be initialized again at reset.
+
+    This is a synchronuous call
+
+    \param hHal - The handle returned by macOpen.
+
+    \Param
+    pUpdateConfigParam - a pointer to a structure (tCsrUpdateConfigParam) that
+                currently provides 11d related information like Country code,
+                Regulatory domain, valid channel list, Tx power per channel, a
+                list with active/passive scan allowed per valid channel.
+
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ChangeConfigParams(tHalHandle hHal,
+                                 tCsrUpdateConfigParam *pUpdateConfigParam)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if (NULL == pUpdateConfigParam ) {
+      smsLog( pMac, LOGE,
+              "Empty config param structure for SME, nothing to reset\n");
+      return status;
+   }
+
+   status = csrChangeConfigParams(pMac, pUpdateConfigParam);
+
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "csrUpdateConfigParam failed with status=%d\n",
+              status );
+   }
+
+   return status;
+
+}
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_HDDReadyInd() - SME sends eWNI_SME_SYS_READY_IND to PE to inform
+  that the NIC is ready tio run.
+
+  The function is called by HDD at the end of initialization stage so PE/HAL can
+  enable the NIC to running state.
+
+  This is a synchronuous call
+  \param hHal - The handle returned by macOpen.
+
+  \return eHAL_STATUS_SUCCESS - eWNI_SME_SYS_READY_IND is sent to PE
+                                successfully.
+
+          Other status means SME failed to send the message to PE.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_HDDReadyInd(tHalHandle hHal)
+{
+   tSirSmeReadyReq Msg;
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tPmcPowerState powerState;
+   tPmcSwitchState hwWlanSwitchState;
+   tPmcSwitchState swWlanSwitchState;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   do
+   {
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC
+      csrSetGlobalCfgs( pMac );
+#endif
+
+      Msg.messageType = eWNI_SME_SYS_READY_IND;
+      Msg.length      = sizeof( tSirSmeReadyReq );
+
+      if (eSIR_FAILURE != uMacPostCtrlMsg( hHal, (tSirMbMsg*)&Msg ))
+      {
+         status = eHAL_STATUS_SUCCESS;
+      }
+      else
+      {
+         smsLog( pMac, LOGE,
+                 "uMacPostCtrlMsg failed to send eWNI_SME_SYS_READY_IND");
+         break;
+      }
+
+      status = pmcQueryPowerState( hHal, &powerState,
+                                &hwWlanSwitchState, &swWlanSwitchState );
+      if ( ! HAL_STATUS_SUCCESS( status ) )
+      {
+         smsLog( pMac, LOGE, "pmcQueryPowerState failed with status=%d\n",
+                 status );
+         break;
+      }
+
+      if ( (ePMC_SWITCH_OFF != hwWlanSwitchState) &&
+           (ePMC_SWITCH_OFF != swWlanSwitchState) )
+      {
+         status = csrReady(pMac);
+         if ( ! HAL_STATUS_SUCCESS( status ) )
+         {
+            smsLog( pMac, LOGE, "csrReady failed with status=%d\n", status );
+            break;
+         }
+         status = pmcReady(hHal);
+         if ( ! HAL_STATUS_SUCCESS( status ) )
+         {
+             smsLog( pMac, LOGE, "pmcReady failed with status=%d\n", status );
+             break;
+         }
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+         if(VOS_STATUS_SUCCESS != btcReady(hHal))
+         {
+             status = eHAL_STATUS_FAILURE;
+             smsLog( pMac, LOGE, "btcReady failed\n");
+             break;
+         }
+#endif
+
+#if defined WLAN_FEATURE_VOWIFI
+         if(VOS_STATUS_SUCCESS != rrmReady(hHal))
+         {
+             status = eHAL_STATUS_FAILURE;
+             smsLog( pMac, LOGE, "rrmReady failed\n");
+             break;
+         }
+#endif
+      }
+      pMac->sme.state = SME_STATE_READY;
+   } while( 0 );
+
+   return status;
+}
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_Start() - Put all SME modules at ready state.
+
+  The function starts each module in SME, PMC, CCM, CSR, etc. . Upon
+  successfully return, all modules are ready to run.
+  This is a synchronuous call
+  \param hHal - The handle returned by macOpen.
+
+  \return eHAL_STATUS_SUCCESS - SME is ready.
+
+          Other status means SME is failed to start
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_Start(tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   do
+   {
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC 
+      ccmStart(hHal);
+#endif
+      status = csrStart(pMac);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE, "csrStart failed during smeStart with status=%d\n",
+                 status );
+         break;
+      }
+
+      status = pmcStart(hHal);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE, "pmcStart failed during smeStart with status=%d\n",
+                 status );
+         break;
+      }
+
+#ifdef WLAN_SOFTAP_FEATURE
+      status = WLANSAP_Start(vos_get_global_context(VOS_MODULE_ID_SAP, NULL));
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE, "WLANSAP_Start failed during smeStart with status=%d\n",
+                 status );
+         break;
+      }
+#endif
+      pMac->sme.state = SME_STATE_START;
+   }while (0);
+
+   return status;
+}
+
+
+#ifdef WLAN_FEATURE_PACKET_FILTERING
+/******************************************************************************
+*
+* Name: sme_PCFilterMatchCountResponseHandler
+*
+* Description:
+*    Invoke Packet Coalescing Filter Match Count callback routine
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    pMsg - Pointer to tRcvFltPktMatchRsp structure
+*
+* Returns: eHalStatus
+*
+******************************************************************************/
+eHalStatus sme_PCFilterMatchCountResponseHandler(tHalHandle hHal, void* pMsg)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpSirRcvFltPktMatchRsp pRcvFltPktMatchRsp = (tpSirRcvFltPktMatchRsp)pMsg;
+
+    if (NULL == pMsg)
+    {
+        smsLog(pMac, LOGE, "in %s msg ptr is NULL\n", __FUNCTION__);
+        status = eHAL_STATUS_FAILURE;
+    }
+    else
+    {
+        smsLog(pMac, LOG2, "SME: entering "
+            "sme_FilterMatchCountResponseHandler\n");
+
+        /* Call Packet Coalescing Filter Match Count callback routine. */
+        if (pMac->pmc.FilterMatchCountCB != NULL)
+           pMac->pmc.FilterMatchCountCB(pMac->pmc.FilterMatchCountCBContext,
+                                          pRcvFltPktMatchRsp);
+
+        smsLog(pMac, LOG1, "%s: status=0x%x", __FUNCTION__,
+               pRcvFltPktMatchRsp->status);
+
+        pMac->pmc.FilterMatchCountCB = NULL;
+        pMac->pmc.FilterMatchCountCBContext = NULL;
+    }
+
+    return(status);
+}
+#endif // WLAN_FEATURE_PACKET_FILTERING
+
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_ProcessMsg() - The main message processor for SME.
+
+  The function is called by a message dispatcher when to process a message
+  targeted for SME.
+
+  This is a synchronuous call
+  \param hHal - The handle returned by macOpen.
+  \param pMsg - A pointer to a caller allocated object of tSirMsgQ.
+
+  \return eHAL_STATUS_SUCCESS - SME successfully process the message.
+
+          Other status means SME failed to process the message to HAL.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_ProcessMsg(tHalHandle hHal, vos_msg_t* pMsg)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if (pMsg == NULL) {
+      smsLog( pMac, LOGE, "Empty message for SME, nothing to process\n");
+      return status;
+   }
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if( SME_IS_START(pMac) )
+      {
+          switch (pMsg->type) { // TODO: Will be modified to do a range check for msgs instead of having cases for each msgs
+          case eWNI_PMC_ENTER_BMPS_RSP:
+          case eWNI_PMC_EXIT_BMPS_RSP:
+          case eWNI_PMC_EXIT_BMPS_IND:
+          case eWNI_PMC_ENTER_IMPS_RSP:
+          case eWNI_PMC_EXIT_IMPS_RSP:
+          case eWNI_PMC_SMPS_STATE_IND:
+          case eWNI_PMC_ENTER_UAPSD_RSP:
+          case eWNI_PMC_EXIT_UAPSD_RSP:
+          case eWNI_PMC_ENTER_WOWL_RSP:
+          case eWNI_PMC_EXIT_WOWL_RSP:
+             //PMC
+             if (pMsg->bodyptr)
+             {
+                pmcMessageProcessor(hHal, pMsg->bodyptr);
+                status = eHAL_STATUS_SUCCESS;
+                vos_mem_free( pMsg->bodyptr );
+             } else {
+                smsLog( pMac, LOGE, "Empty rsp message for PMC, nothing to process\n");
+             }
+             break;
+
+          case WNI_CFG_SET_CNF:
+          case WNI_CFG_DNLD_CNF:
+          case WNI_CFG_GET_RSP:
+          case WNI_CFG_ADD_GRP_ADDR_CNF:
+          case WNI_CFG_DEL_GRP_ADDR_CNF:
+             //CCM
+             if (pMsg->bodyptr)
+             {
+                ccmCfgCnfMsgHandler(hHal, pMsg->bodyptr);
+                status = eHAL_STATUS_SUCCESS;
+                vos_mem_free( pMsg->bodyptr );
+             } else {
+                smsLog( pMac, LOGE, "Empty rsp message for CCM, nothing to process\n");
+             }
+             break;
+
+          case eWNI_SME_ADDTS_RSP:
+          case eWNI_SME_DELTS_RSP:
+          case eWNI_SME_DELTS_IND:
+#ifdef WLAN_FEATURE_VOWIFI_11R
+          case eWNI_SME_FT_AGGR_QOS_RSP:
+#endif             
+             //QoS
+             if (pMsg->bodyptr)
+             {
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+                status = sme_QosMsgProcessor(pMac, pMsg->type, pMsg->bodyptr);
+                vos_mem_free( pMsg->bodyptr );
+#endif
+             } else {
+                smsLog( pMac, LOGE, "Empty rsp message for QoS, nothing to process\n");
+             }
+             break;
+#if defined WLAN_FEATURE_VOWIFI
+          case eWNI_SME_NEIGHBOR_REPORT_IND:
+          case eWNI_SME_BEACON_REPORT_REQ_IND:
+#if defined WLAN_VOWIFI_DEBUG
+             smsLog( pMac, LOGE, "Received RRM message. Message Id = %d\n", pMsg->type );
+#endif
+             if ( pMsg->bodyptr )
+             {
+                status = sme_RrmMsgProcessor( pMac, pMsg->type, pMsg->bodyptr );
+                vos_mem_free( pMsg->bodyptr );
+             }
+             else
+             {
+                smsLog( pMac, LOGE, "Empty message for RRM, nothing to process\n");
+             }
+             break;
+#endif
+
+
+          case eWNI_SME_ADD_STA_SELF_RSP:
+                if(pMsg->bodyptr)
+                {
+                   status = csrProcessAddStaSessionRsp(pMac, pMsg->bodyptr);
+                   vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                   smsLog( pMac, LOGE, "Empty rsp message for meas (eWNI_SME_ADD_STA_SELF_RSP), nothing to process\n");
+                }
+                break;
+          case eWNI_SME_DEL_STA_SELF_RSP:
+                if(pMsg->bodyptr)
+                {
+                   status = csrProcessDelStaSessionRsp(pMac, pMsg->bodyptr);
+                   vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                   smsLog( pMac, LOGE, "Empty rsp message for meas (eWNI_SME_DEL_STA_SELF_RSP), nothing to process\n");
+                }
+                break;
+#ifdef WLAN_FEATURE_P2P
+          //Handle the eWNI_SME_INNAV_MEAS_RSP:
+          case eWNI_SME_REMAIN_ON_CHN_RSP:
+                if(pMsg->bodyptr)
+                {
+                    status = sme_remainOnChnRsp(pMac, pMsg->bodyptr);
+                    vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                    smsLog( pMac, LOGE, "Empty rsp message for meas (eWNI_SME_REMAIN_ON_CHN_RSP), nothing to process\n");
+                }
+                break;
+          case eWNI_SME_REMAIN_ON_CHN_RDY_IND:
+                if(pMsg->bodyptr)
+                {
+                    status = sme_remainOnChnReady(pMac, pMsg->bodyptr);
+                    vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                    smsLog( pMac, LOGE, "Empty rsp message for meas (eWNI_SME_REMAIN_ON_CHN_RDY_IND), nothing to process\n");
+                }
+                break;
+           case eWNI_SME_MGMT_FRM_IND:
+                if(pMsg->bodyptr)
+                {
+                    sme_mgmtFrmInd(pMac, pMsg->bodyptr);
+                    vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                { 
+                    smsLog( pMac, LOGE, "Empty rsp message for meas (eWNI_SME_MGMT_FRM_IND), nothing to process\n");
+                }
+                break;
+           case eWNI_SME_ACTION_FRAME_SEND_CNF:
+                if(pMsg->bodyptr)
+                {
+                    status = sme_sendActionCnf(pMac, pMsg->bodyptr);
+                    vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                    smsLog( pMac, LOGE, "Empty rsp message for meas (eWNI_SME_ACTION_FRAME_SEND_CNF), nothing to process\n");
+                }
+                break;
+#endif
+          case eWNI_SME_COEX_IND:
+                if(pMsg->bodyptr)
+                {
+                   status = btcHandleCoexInd((void *)pMac, pMsg->bodyptr);
+                   vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                   smsLog(pMac, LOGE, "Empty rsp message for meas (eWNI_SME_COEX_IND), nothing to process\n");
+                }
+                break;    
+
+#ifdef FEATURE_WLAN_SCAN_PNO
+          case eWNI_SME_PREF_NETWORK_FOUND_IND:
+                if(pMsg->bodyptr)
+                {
+                   status = sme_PreferredNetworkFoundInd((void *)pMac, pMsg->bodyptr);
+                   vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                   smsLog(pMac, LOGE, "Empty rsp message for meas (eWNI_SME_PREF_NETWORK_FOUND_IND), nothing to process\n");
+                }
+                break;
+#endif // FEATURE_WLAN_SCAN_PNO
+          
+          case eWNI_SME_TX_PER_HIT_IND:
+                if (pMac->sme.pTxPerHitCallback)
+                {
+                   pMac->sme.pTxPerHitCallback(pMac->sme.pTxPerHitCbContext);
+                }
+                break;
+
+          case eWNI_SME_CHANGE_COUNTRY_CODE:
+                if(pMsg->bodyptr)
+                {
+                   status = sme_HandleChangeCountryCode((void *)pMac, pMsg->bodyptr);
+                   vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                   smsLog(pMac, LOGE, "Empty rsp message for meas (eWNI_SME_COEX_IND), nothing to process\n");
+                }
+                break;
+
+#ifdef WLAN_FEATURE_PACKET_FILTERING
+          case eWNI_PMC_PACKET_COALESCING_FILTER_MATCH_COUNT_RSP:
+                if(pMsg->bodyptr)
+                {
+                   status = sme_PCFilterMatchCountResponseHandler((void *)pMac, pMsg->bodyptr);
+                   vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                   smsLog(pMac, LOGE, "Empty rsp message for meas "
+                          "(PACKET_COALESCING_FILTER_MATCH_COUNT_RSP), nothing to process\n");
+                }
+                break;
+#endif // WLAN_FEATURE_PACKET_FILTERING
+          case eWNI_SME_PRE_SWITCH_CHL_IND:
+             {
+                status = sme_HandlePreChannelSwitchInd(pMac);
+                break;
+             }
+                
+          case eWNI_SME_POST_SWITCH_CHL_IND:
+             {
+                status = sme_HandlePostChannelSwitchInd(pMac);
+                break;
+             }
+
+#ifdef WLAN_WAKEUP_EVENTS
+          case eWNI_SME_WAKE_REASON_IND:
+                if(pMsg->bodyptr)
+                {
+                   status = sme_WakeReasonIndCallback((void *)pMac, pMsg->bodyptr);
+                   vos_mem_free(pMsg->bodyptr);
+                }
+                else
+                {
+                   smsLog(pMac, LOGE, "Empty rsp message for meas (eWNI_SME_WAKE_REASON_IND), nothing to process\n");
+                }
+                break;
+#endif // WLAN_WAKEUP_EVENTS
+
+          default:
+
+             if ( ( pMsg->type >= eWNI_SME_MSG_TYPES_BEGIN )
+                  &&  ( pMsg->type <= eWNI_SME_MSG_TYPES_END ) )
+             {
+                //CSR
+                if (pMsg->bodyptr)
+                {
+                   status = csrMsgProcessor(hHal, pMsg->bodyptr);
+                   vos_mem_free( pMsg->bodyptr );
+                }
+                else
+                {
+                   smsLog( pMac, LOGE, "Empty rsp message for CSR, nothing to process\n");
+                }
+             }
+             else
+             {
+                smsLog( pMac, LOGW, "Unknown message type %d, nothing to process\n",
+                        pMsg->type);
+                if (pMsg->bodyptr)
+                {
+                   vos_mem_free( pMsg->bodyptr );
+                }
+             }
+          }//switch
+      } //SME_IS_START
+      else
+      {
+         smsLog( pMac, LOGW, "message type %d in stop state ignored\n", pMsg->type);
+         if (pMsg->bodyptr)
+         {
+            vos_mem_free( pMsg->bodyptr );
+         }
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+   else
+   {
+      smsLog( pMac, LOGW, "Locking failed, bailing out\n");
+      if (pMsg->bodyptr)
+      {
+          vos_mem_free( pMsg->bodyptr );
+      }
+   }
+
+   return status;
+}
+
+
+//No need to hold the global lock here because this function can only be called
+//after sme_Stop.
+v_VOID_t sme_FreeMsg( tHalHandle hHal, vos_msg_t* pMsg )
+{
+   if( pMsg )
+   {
+      if (pMsg->bodyptr)
+      {
+         vos_mem_free( pMsg->bodyptr );
+      }
+   }
+
+}
+
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_Stop() - Stop all SME modules and put them at idle state
+
+  The function stops each module in SME, PMC, CCM, CSR, etc. . Upon
+  return, all modules are at idle state ready to start.
+
+  This is a synchronuous call
+  \param hHal - The handle returned by macOpen
+
+  \return eHAL_STATUS_SUCCESS - SME is stopped.
+
+          Other status means SME is failed to stop but caller should still
+          consider SME is stopped.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_Stop(tHalHandle hHal, tANI_BOOLEAN pmcFlag)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   eHalStatus fail_status = eHAL_STATUS_SUCCESS;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+#ifdef WLAN_SOFTAP_FEATURE
+   status = WLANSAP_Stop(vos_get_global_context(VOS_MODULE_ID_SAP, NULL));
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "WLANSAP_Stop failed during smeStop with status=%d\n",
+                          status );
+      fail_status = status;
+   }
+#endif
+
+   p2pStop(hHal);
+
+   if(pmcFlag)
+   {
+      status = pmcStop(hHal);
+      if ( ! HAL_STATUS_SUCCESS( status ) ) {
+         smsLog( pMac, LOGE, "pmcStop failed during smeStop with status=%d\n",
+                 status );
+         fail_status = status;
+      }
+   }
+
+   status = csrStop(pMac);
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "csrStop failed during smeStop with status=%d\n",
+              status );
+      fail_status = status;
+   }
+
+   ccmStop(hHal);
+
+   purgeSmeCmdList(pMac);
+
+   if (!HAL_STATUS_SUCCESS( fail_status )) {
+      status = fail_status;
+   }
+
+   pMac->sme.state = SME_STATE_STOP;
+
+   return status;
+}
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_Close() - Release all SME modules and their resources.
+
+  The function release each module in SME, PMC, CCM, CSR, etc. . Upon
+  return, all modules are at closed state.
+
+  No SME APIs can be involved after smeClose except smeOpen.
+  smeClose must be called before macClose.
+  This is a synchronuous call
+  \param hHal - The handle returned by macOpen
+
+  \return eHAL_STATUS_SUCCESS - SME is successfully close.
+
+          Other status means SME is failed to be closed but caller still cannot
+          call any other SME functions except smeOpen.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_Close(tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   eHalStatus fail_status = eHAL_STATUS_SUCCESS;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = csrClose(pMac);
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "csrClose failed during sme close with status=%d\n",
+              status );
+      fail_status = status;
+   }
+
+#ifdef WLAN_SOFTAP_FEATURE
+   status = WLANSAP_Close(vos_get_global_context(VOS_MODULE_ID_SAP, NULL));
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "WLANSAP_close failed during sme close with status=%d\n",
+              status );
+      fail_status = status;
+   }
+#endif
+
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+   status = btcClose(hHal);
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "BTC close failed during sme close with status=%d\n",
+              status );
+      fail_status = status;
+   }
+
+   status = sme_QosClose(pMac);
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "Qos close failed during sme close with status=%d\n",
+              status );
+      fail_status = status;
+   }
+#endif
+
+   status = ccmClose(hHal);
+         if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "ccmClose failed during sme close with status=%d\n",
+                 status );
+             fail_status = status;
+         }
+
+   status = pmcClose(hHal);
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "pmcClose failed during sme close with status=%d\n",
+              status );
+      fail_status = status;
+   }
+#if defined WLAN_FEATURE_VOWIFI
+   status = rrmClose(hHal);
+   if ( ! HAL_STATUS_SUCCESS( status ) ) {
+      smsLog( pMac, LOGE, "RRM close failed during sme close with status=%d\n",
+              status );
+      fail_status = status;
+   }
+#endif
+
+#if defined WLAN_FEATURE_VOWIFI_11R
+   sme_FTClose(hHal);
+#endif
+#if defined WLAN_FEATURE_P2P
+   sme_p2pClose(hHal);
+#endif
+
+   freeSmeCmdList(pMac);
+
+   if( !VOS_IS_STATUS_SUCCESS( vos_lock_destroy( &pMac->sme.lkSmeGlobalLock ) ) )
+   {
+       fail_status = eHAL_STATUS_FAILURE;
+   }
+
+   if (!HAL_STATUS_SUCCESS( fail_status )) {
+      status = fail_status;
+   }
+
+   pMac->sme.state = SME_STATE_STOP;
+
+   return status;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanRequest
+    \brief a wrapper function to Request a 11d or full scan from CSR.
+    This is an asynchronuous call
+    \param pScanRequestID - pointer to an object to get back the request ID
+    \param callback - a callback function that scan calls upon finish, will not
+                      be called if csrScanRequest returns error
+    \param pContext - a pointer passed in for the callback
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanRequest(tHalHandle hHal, tANI_U8 sessionId, tCsrScanRequest *pscanReq, 
+                           tANI_U32 *pScanRequestID, 
+                           csrScanCompleteCallback callback, void *pContext)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    smsLog(pMac, LOG2, FL("enter"));
+    do
+    {
+        if(pMac->scan.fScanEnable)
+        {
+            status = sme_AcquireGlobalLock( &pMac->sme );
+            if ( HAL_STATUS_SUCCESS( status ) )
+            {
+                {
+                    status = csrScanRequest( hHal, sessionId, pscanReq,
+                                     pScanRequestID, callback, pContext );
+                }
+                  
+                sme_ReleaseGlobalLock( &pMac->sme );
+            } //sme_AcquireGlobalLock success
+        } //if(pMac->scan.fScanEnable)
+    } while( 0 );
+
+    return (status);
+
+
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanGetResult
+    \brief a wrapper function to request scan results from CSR.
+    This is a synchronuous call
+    \param pFilter - If pFilter is NULL, all cached results are returned
+    \param phResult - an object for the result.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanGetResult(tHalHandle hHal, tANI_U8 sessionId, tCsrScanResultFilter *pFilter,
+                            tScanResultHandle *phResult)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   smsLog(pMac, LOG2, FL("enter"));
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = csrScanGetResult( hHal, pFilter, phResult );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+   smsLog(pMac, LOG2, FL("exit status %d"), status);
+
+   return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanFlushResult
+    \brief a wrapper function to request CSR to clear scan results.
+    This is a synchronuous call
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanFlushResult(tHalHandle hHal, tANI_U8 sessionId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = csrScanFlushResult( hHal );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanResultGetFirst
+    \brief a wrapper function to request CSR to returns the first element of
+           scan result.
+    This is a synchronuous call
+    \param hScanResult - returned from csrScanGetResult
+    \return tCsrScanResultInfo * - NULL if no result
+  ---------------------------------------------------------------------------*/
+tCsrScanResultInfo *sme_ScanResultGetFirst(tHalHandle hHal,
+                                          tScanResultHandle hScanResult)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   tCsrScanResultInfo *pRet = NULL;
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       pRet = csrScanResultGetFirst( pMac, hScanResult );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (pRet);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanResultGetNext
+    \brief a wrapper function to request CSR to returns the next element of
+           scan result. It can be called without calling csrScanResultGetFirst
+           first
+    This is a synchronuous call
+    \param hScanResult - returned from csrScanGetResult
+    \return Null if no result or reach the end
+  ---------------------------------------------------------------------------*/
+tCsrScanResultInfo *sme_ScanResultGetNext(tHalHandle hHal,
+                                          tScanResultHandle hScanResult)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tCsrScanResultInfo *pRet = NULL;
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+        pRet = csrScanResultGetNext( pMac, hScanResult );
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (pRet);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanSetBGScanparams
+    \brief a wrapper function to request CSR to set BG scan params in PE
+    This is a synchronuous call
+    \param pScanReq - BG scan request structure
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanSetBGScanparams(tHalHandle hHal, tANI_U8 sessionId, tCsrBGScanRequest *pScanReq)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    if( NULL != pScanReq )
+    {
+        status = sme_AcquireGlobalLock( &pMac->sme );
+        if ( HAL_STATUS_SUCCESS( status ) )
+        {
+            status = csrScanSetBGScanparams( hHal, pScanReq );
+            sme_ReleaseGlobalLock( &pMac->sme );
+        }
+    }
+
+    return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanResultPurge
+    \brief a wrapper function to request CSR to remove all items(tCsrScanResult)
+           in the list and free memory for each item
+    This is a synchronuous call
+    \param hScanResult - returned from csrScanGetResult. hScanResult is
+                         considered gone by
+    calling this function and even before this function reutrns.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanResultPurge(tHalHandle hHal, tScanResultHandle hScanResult)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = csrScanResultPurge( hHal, hScanResult );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanGetPMKIDCandidateList
+    \brief a wrapper function to return the PMKID candidate list
+    This is a synchronuous call
+    \param pPmkidList - caller allocated buffer point to an array of
+                        tPmkidCandidateInfo
+    \param pNumItems - pointer to a variable that has the number of
+                       tPmkidCandidateInfo allocated when retruning, this is
+                       either the number needed or number of items put into
+                       pPmkidList
+    \return eHalStatus - when fail, it usually means the buffer allocated is not
+                         big enough and pNumItems
+    has the number of tPmkidCandidateInfo.
+    \Note: pNumItems is a number of tPmkidCandidateInfo,
+           not sizeof(tPmkidCandidateInfo) * something
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanGetPMKIDCandidateList(tHalHandle hHal, tANI_U8 sessionId,
+                                        tPmkidCandidateInfo *pPmkidList, 
+                                        tANI_U32 *pNumItems )
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = csrScanGetPMKIDCandidateList( pMac, sessionId, pPmkidList, pNumItems );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/*----------------------------------------------------------------------------
+  \fn sme_RoamRegisterLinkQualityIndCallback
+
+  \brief
+  a wrapper function to allow HDD to register a callback handler with CSR for
+  link quality indications.
+
+  Only one callback may be registered at any time.
+  In order to deregister the callback, a NULL cback may be provided.
+
+  Registration happens in the task context of the caller.
+
+  \param callback - Call back being registered
+  \param pContext - user data
+
+  DEPENDENCIES: After CSR open
+
+  \return eHalStatus
+-----------------------------------------------------------------------------*/
+eHalStatus sme_RoamRegisterLinkQualityIndCallback(tHalHandle hHal, tANI_U8 sessionId,
+                                                  csrRoamLinkQualityIndCallback   callback,
+                                                  void                           *pContext)
+{
+   return(csrRoamRegisterLinkQualityIndCallback((tpAniSirGlobal)hHal, callback, pContext));
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamRegisterCallback
+    \brief a wrapper function to allow HDD to register a callback with CSR.
+           Unlike scan, roam has one callback for all the roam requests
+    \param callback - a callback function that roam calls upon when state changes
+    \param pContext - a pointer passed in for the callback
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamRegisterCallback(tHalHandle hHal,
+                                    csrRoamCompleteCallback callback,
+                                    void *pContext)
+{
+   return(csrRoamRegisterCallback((tpAniSirGlobal)hHal, callback, pContext));
+}
+
+eCsrPhyMode sme_GetPhyMode(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    return pMac->roam.configParam.phyMode;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamConnect
+    \brief a wrapper function to request CSR to inititiate an association
+    This is an asynchronuous call.
+    \param sessionId - the sessionId returned by sme_OpenSession.
+    \param pProfile - description of the network to which to connect
+    \param hBssListIn - a list of BSS descriptor to roam to. It is returned
+                        from csrScanGetResult
+    \param pRoamId - to get back the request ID
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamConnect(tHalHandle hHal, tANI_U8 sessionId, tCsrRoamProfile *pProfile,
+                           tANI_U32 *pRoamId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    smsLog(pMac, LOG2, FL("enter"));
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+            status = csrRoamConnect( pMac, sessionId, pProfile, NULL, pRoamId );
+        }
+        else
+        {
+            status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamReassoc
+    \brief a wrapper function to request CSR to inititiate a re-association
+    \param pProfile - can be NULL to join the currently connected AP. In that
+    case modProfileFields should carry the modified field(s) which could trigger
+    reassoc
+    \param modProfileFields - fields which are part of tCsrRoamConnectedProfile
+    that might need modification dynamically once STA is up & running and this
+    could trigger a reassoc
+    \param pRoamId - to get back the request ID
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamReassoc(tHalHandle hHal, tANI_U8 sessionId, tCsrRoamProfile *pProfile,
+                          tCsrRoamModifyProfileFields modProfileFields,
+                          tANI_U32 *pRoamId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    smsLog(pMac, LOG2, FL("enter"));
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+            status = csrRoamReassoc( pMac, sessionId, pProfile, modProfileFields, pRoamId );
+        }
+        else
+        {
+            status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamConnectToLastProfile
+    \brief a wrapper function to request CSR to disconnect and reconnect with
+           the same profile
+    This is an asynchronuous call.
+    \return eHalStatus. It returns fail if currently connected
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamConnectToLastProfile(tHalHandle hHal, tANI_U8 sessionId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+      {
+         status = csrRoamConnectToLastProfile( pMac, sessionId );
+      }
+      else
+      {
+          status = eHAL_STATUS_INVALID_PARAMETER;
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamDisconnect
+    \brief a wrapper function to request CSR to disconnect from a network
+    This is an asynchronuous call.
+    \param reason -- To indicate the reason for disconnecting. Currently, only
+                     eCSR_DISCONNECT_REASON_MIC_ERROR is meanful.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamDisconnect(tHalHandle hHal, tANI_U8 sessionId, eCsrRoamDisconnectReason reason)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   smsLog(pMac, LOG2, FL("enter"));
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+      {
+         status = csrRoamDisconnect( pMac, sessionId, reason );
+      }
+      else
+      {
+          status = eHAL_STATUS_INVALID_PARAMETER;
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamStopBss
+    \brief To stop BSS for Soft AP. This is an asynchronous API.
+    \param hHal - Global structure
+    \param sessionId - sessionId of SoftAP
+    \return eHalStatus  SUCCESS  Roam callback will be called to indicate actual results
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamStopBss(tHalHandle hHal, tANI_U8 sessionId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   smsLog(pMac, LOG2, FL("enter"));
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+      {
+         status = csrRoamIssueStopBssCmd( pMac, sessionId, eANI_BOOLEAN_TRUE );
+      }
+      else
+      {
+          status = eHAL_STATUS_INVALID_PARAMETER;
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamDisconnectSta
+    \brief To disassociate a station. This is an asynchronous API.
+    \param hHal - Global structure
+    \param sessionId - sessionId of SoftAP
+    \param pPeerMacAddr - Caller allocated memory filled with peer MAC address (6 bytes)
+    \return eHalStatus  SUCCESS  Roam callback will be called to indicate actual results
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamDisconnectSta(tHalHandle hHal, tANI_U8 sessionId,
+                                tANI_U8 *pPeerMacAddr)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if ( NULL == pMac )
+   {
+     VOS_ASSERT(0);
+     return status;
+   }
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+      {
+         status = csrRoamIssueDisassociateStaCmd( pMac, sessionId, pPeerMacAddr, 
+                                                  eSIR_MAC_UNSPEC_FAILURE_REASON);
+      }
+      else
+      {
+         status = eHAL_STATUS_INVALID_PARAMETER;
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamDeauthSta
+    \brief To disassociate a station. This is an asynchronous API.
+    \param hHal - Global structure
+    \param sessionId - sessionId of SoftAP
+    \param pPeerMacAddr - Caller allocated memory filled with peer MAC address (6 bytes)
+    \return eHalStatus  SUCCESS  Roam callback will be called to indicate actual results
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamDeauthSta(tHalHandle hHal, tANI_U8 sessionId,
+                                tANI_U8 *pPeerMacAddr)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if ( NULL == pMac )
+   {
+     VOS_ASSERT(0);
+     return status;
+   }
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+      {
+         status = csrRoamIssueDeauthStaCmd( pMac, sessionId, pPeerMacAddr, 
+                     eSIR_MAC_UNSPEC_FAILURE_REASON);
+      }
+      else
+      {
+         status = eHAL_STATUS_INVALID_PARAMETER;
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamTKIPCounterMeasures
+    \brief To start or stop TKIP counter measures. This is an asynchronous API.
+    \param sessionId - sessionId of SoftAP
+    \param pPeerMacAddr - Caller allocated memory filled with peer MAC address (6 bytes)
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamTKIPCounterMeasures(tHalHandle hHal, tANI_U8 sessionId,
+                                        tANI_BOOLEAN bEnable)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if ( NULL == pMac )
+   {
+     VOS_ASSERT(0);
+     return status;
+   }
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+            status = csrRoamIssueTkipCounterMeasures( pMac, sessionId, bEnable);
+        }
+        else
+        {
+            status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetAssociatedStas
+    \brief To probe the list of associated stations from various modules of CORE stack.
+    \This is an asynchronous API.
+    \param sessionId    - sessionId of SoftAP
+    \param modId        - Module from whom list of associtated stations is to be probed.
+                          If an invalid module is passed then by default VOS_MODULE_ID_PE will be probed
+    \param pUsrContext  - Opaque HDD context
+    \param pfnSapEventCallback  - Sap event callback in HDD
+    \param pAssocBuf    - Caller allocated memory to be filled with associatd stations info
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetAssociatedStas(tHalHandle hHal, tANI_U8 sessionId,
+                                        VOS_MODULE_ID modId, void *pUsrContext,
+                                        void *pfnSapEventCallback, tANI_U8 *pAssocStasBuf)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if ( NULL == pMac )
+   {
+     VOS_ASSERT(0);
+     return status;
+   }
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+            status = csrRoamGetAssociatedStas( pMac, sessionId, modId, pUsrContext, pfnSapEventCallback, pAssocStasBuf );
+        }
+        else
+        {
+            status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetWpsSessionOverlap
+    \brief To get the WPS PBC session overlap information.
+    \This is an asynchronous API.
+    \param sessionId    - sessionId of SoftAP
+    \param pUsrContext  - Opaque HDD context
+    \param pfnSapEventCallback  - Sap event callback in HDD
+    \pRemoveMac - pointer to Mac address which needs to be removed from session
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetWpsSessionOverlap(tHalHandle hHal, tANI_U8 sessionId,
+                                        void *pUsrContext, void 
+                                        *pfnSapEventCallback, v_MACADDR_t pRemoveMac)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if ( NULL == pMac )
+   {
+     VOS_ASSERT(0);
+     return status;
+   }
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+            status = csrRoamGetWpsSessionOverlap( pMac, sessionId, pUsrContext, pfnSapEventCallback, pRemoveMac);
+        }
+        else
+        {
+            status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+#endif
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetConnectState
+    \brief a wrapper function to request CSR to return the current connect state
+           of Roaming
+    This is a synchronuous call.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetConnectState(tHalHandle hHal, tANI_U8 sessionId, eCsrConnectState *pState)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+       if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+       {
+          status = csrRoamGetConnectState( pMac, sessionId, pState );
+       }
+       else
+       {
+           status = eHAL_STATUS_INVALID_PARAMETER;
+       }
+       sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetConnectProfile
+    \brief a wrapper function to request CSR to return the current connect
+           profile. Caller must call csrRoamFreeConnectProfile after it is done
+           and before reuse for another csrRoamGetConnectProfile call.
+    This is a synchronuous call.
+    \param pProfile - pointer to a caller allocated structure
+                      tCsrRoamConnectedProfile
+    \return eHalStatus. Failure if not connected
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetConnectProfile(tHalHandle hHal, tANI_U8 sessionId,
+                                     tCsrRoamConnectedProfile *pProfile)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+      {
+         status = csrRoamGetConnectProfile( pMac, sessionId, pProfile );
+      }
+      else
+      {
+          status = eHAL_STATUS_INVALID_PARAMETER;
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamFreeConnectProfile
+    \brief a wrapper function to request CSR to free and reinitialize the
+           profile returned previously by csrRoamGetConnectProfile.
+    This is a synchronuous call.
+    \param pProfile - pointer to a caller allocated structure
+                      tCsrRoamConnectedProfile
+    \return eHalStatus.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamFreeConnectProfile(tHalHandle hHal,
+                                      tCsrRoamConnectedProfile *pProfile)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = csrRoamFreeConnectProfile( pMac, pProfile );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamSetPMKIDCache
+    \brief a wrapper function to request CSR to return the PMKID candidate list
+    This is a synchronuous call.
+    \param pPMKIDCache - caller allocated buffer point to an array of
+                         tPmkidCacheInfo
+    \param numItems - a variable that has the number of tPmkidCacheInfo
+                      allocated when retruning, this is either the number needed
+                      or number of items put into pPMKIDCache
+    \return eHalStatus - when fail, it usually means the buffer allocated is not
+                         big enough and pNumItems has the number of
+                         tPmkidCacheInfo.
+    \Note: pNumItems is a number of tPmkidCacheInfo,
+           not sizeof(tPmkidCacheInfo) * something
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamSetPMKIDCache( tHalHandle hHal, tANI_U8 sessionId, tPmkidCacheInfo *pPMKIDCache,
+                                  tANI_U32 numItems )
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+      {
+         status = csrRoamSetPMKIDCache( pMac, sessionId, pPMKIDCache, numItems );
+      }
+      else
+      {
+          status = eHAL_STATUS_INVALID_PARAMETER;
+      }
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetSecurityReqIE
+    \brief a wrapper function to request CSR to return the WPA or RSN or WAPI IE CSR
+           passes to PE to JOIN request or START_BSS request
+    This is a synchronuous call.
+    \param pLen - caller allocated memory that has the length of pBuf as input.
+                  Upon returned, *pLen has the needed or IE length in pBuf.
+    \param pBuf - Caller allocated memory that contain the IE field, if any,
+                  upon return
+    \param secType - Specifies whether looking for WPA/WPA2/WAPI IE
+    \return eHalStatus - when fail, it usually means the buffer allocated is not
+                         big enough
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetSecurityReqIE(tHalHandle hHal, tANI_U8 sessionId, tANI_U32 *pLen,
+                                  tANI_U8 *pBuf, eCsrSecurityType secType)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+           status = csrRoamGetWpaRsnReqIE( hHal, sessionId, pLen, pBuf );
+        }
+        else
+        {
+           status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetSecurityRspIE
+    \brief a wrapper function to request CSR to return the WPA or RSN or WAPI IE from
+           the beacon or probe rsp if connected
+    This is a synchronuous call.
+    \param pLen - caller allocated memory that has the length of pBuf as input.
+                  Upon returned, *pLen has the needed or IE length in pBuf.
+    \param pBuf - Caller allocated memory that contain the IE field, if any,
+                  upon return
+    \param secType - Specifies whether looking for WPA/WPA2/WAPI IE
+    \return eHalStatus - when fail, it usually means the buffer allocated is not
+                         big enough
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetSecurityRspIE(tHalHandle hHal, tANI_U8 sessionId, tANI_U32 *pLen,
+                                  tANI_U8 *pBuf, eCsrSecurityType secType)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+           status = csrRoamGetWpaRsnRspIE( pMac, sessionId, pLen, pBuf );
+        }
+        else
+        {
+           status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetNumPMKIDCache
+    \brief a wrapper function to request CSR to return number of PMKID cache
+           entries
+    This is a synchronuous call.
+    \return tANI_U32 - the number of PMKID cache entries
+  ---------------------------------------------------------------------------*/
+tANI_U32 sme_RoamGetNumPMKIDCache(tHalHandle hHal, tANI_U8 sessionId)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tANI_U32 numPmkidCache = 0;
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+        if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+        {
+           numPmkidCache = csrRoamGetNumPMKIDCache( pMac, sessionId );
+           status = eHAL_STATUS_SUCCESS;
+        }
+        else
+        {
+           status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (numPmkidCache);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetPMKIDCache
+    \brief a wrapper function to request CSR to return PMKID cache from CSR
+    This is a synchronuous call.
+    \param pNum - caller allocated memory that has the space of the number of
+                  pBuf tPmkidCacheInfo as input. Upon returned, *pNum has the
+                  needed or actually number in tPmkidCacheInfo.
+    \param pPmkidCache - Caller allocated memory that contains PMKID cache, if
+                         any, upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not
+                         big enough
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetPMKIDCache(tHalHandle hHal, tANI_U8 sessionId, tANI_U32 *pNum,
+                                 tPmkidCacheInfo *pPmkidCache)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+       {
+          status = csrRoamGetPMKIDCache( pMac, sessionId, pNum, pPmkidCache );
+       }
+       else
+       {
+          status = eHAL_STATUS_INVALID_PARAMETER;
+       }
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetConfigParam
+    \brief a wrapper function that HDD calls to get the global settings
+           currently maintained by CSR.
+    This is a synchronuous call.
+    \param pParam - caller allocated memory
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetConfigParam(tHalHandle hHal, tSmeConfigParams *pParam)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      status = csrGetConfigParam(pMac, &pParam->csrConfig);
+      if (status != eHAL_STATUS_SUCCESS)
+      {
+         smsLog( pMac, LOGE, "%s csrGetConfigParam failed\n", __FUNCTION__);
+         sme_ReleaseGlobalLock( &pMac->sme );
+         return status;
+      }
+#if defined WLAN_FEATURE_P2P_INTERNAL
+      status = p2pGetConfigParam(pMac, &pParam->p2pConfig);
+      if (status != eHAL_STATUS_SUCCESS)
+      {
+         smsLog( pMac, LOGE, "%s p2pGetConfigParam failed\n", __FUNCTION__);
+         sme_ReleaseGlobalLock( &pMac->sme );
+         return status;
+      }
+#endif
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_CfgSetInt
+    \brief a wrapper function that HDD calls to set parameters in CFG.
+    This is a synchronuous call.
+    \param cfgId - Configuration Parameter ID (type) for STA.
+    \param ccmValue - The information related to Configuration Parameter ID
+                      which needs to be saved in CFG
+    \param callback - To be registered by CSR with CCM. Once the CFG done with
+                      saving the information in the database, it notifies CCM &
+                      then the callback will be invoked to notify.
+    \param toBeSaved - To save the request for future reference
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_CfgSetInt(tHalHandle hHal, tANI_U32 cfgId, tANI_U32 ccmValue,
+                         tCcmCfgSetCallback callback, eAniBoolean toBeSaved)
+{
+   return(ccmCfgSetInt(hHal, cfgId, ccmValue, callback, toBeSaved));
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_CfgSetStr
+    \brief a wrapper function that HDD calls to set parameters in CFG.
+    This is a synchronuous call.
+    \param cfgId - Configuration Parameter ID (type) for STA.
+    \param pStr - Pointer to the byte array which carries the information needs
+                  to be saved in CFG
+    \param length - Length of the data to be saved
+    \param callback - To be registered by CSR with CCM. Once the CFG done with
+                      saving the information in the database, it notifies CCM &
+                      then the callback will be invoked to notify.
+    \param toBeSaved - To save the request for future reference
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_CfgSetStr(tHalHandle hHal, tANI_U32 cfgId, tANI_U8 *pStr,
+                         tANI_U32 length, tCcmCfgSetCallback callback,
+                         eAniBoolean toBeSaved)
+{
+   return(ccmCfgSetStr(hHal, cfgId, pStr, length, callback, toBeSaved));
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetModifyProfileFields
+    \brief HDD or SME - QOS calls this function to get the current values of
+    connected profile fields, changing which can cause reassoc.
+    This function must be called after CFG is downloaded and STA is in connected
+    state. Also, make sure to call this function to get the current profile
+    fields before calling the reassoc. So that pModifyProfileFields will have
+    all the latest values plus the one(s) has been updated as part of reassoc
+    request.
+    \param pModifyProfileFields - pointer to the connected profile fields
+    changing which can cause reassoc
+
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetModifyProfileFields(tHalHandle hHal, tANI_U8 sessionId,
+                                     tCsrRoamModifyProfileFields * pModifyProfileFields)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       if( CSR_IS_SESSION_VALID( pMac, sessionId ) )
+       {
+          status = csrGetModifyProfileFields(pMac, sessionId, pModifyProfileFields);
+       }
+       else
+       {
+          status = eHAL_STATUS_INVALID_PARAMETER;
+       }
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/*--------------------------------------------------------------------------
+    \fn sme_SetConfigPowerSave
+    \brief  Wrapper fn to change power save configuration in SME (PMC) module.
+            For BMPS related configuration, this function also updates the CFG
+            and sends a message to FW to pick up the new values. Note: Calling
+            this function only updates the configuration and does not enable
+            the specified power save mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  psMode - Power Saving mode being modified
+    \param  pConfigParams - a pointer to a caller allocated object of type
+            tPmcSmpsConfigParams or tPmcBmpsConfigParams or tPmcImpsConfigParams
+    \return eHalStatus
+  --------------------------------------------------------------------------*/
+eHalStatus sme_SetConfigPowerSave(tHalHandle hHal, tPmcPowerSavingMode psMode,
+                                  void *pConfigParams)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if (NULL == pConfigParams ) {
+      smsLog( pMac, LOGE, "Empty config param structure for PMC, "
+              "nothing to update");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcSetConfigPowerSave(hHal, psMode, pConfigParams);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/*--------------------------------------------------------------------------
+    \fn sme_GetConfigPowerSave
+    \brief  Wrapper fn to retrieve power save configuration in SME (PMC) module
+    \param  hHal - The handle returned by macOpen.
+    \param  psMode - Power Saving mode
+    \param  pConfigParams - a pointer to a caller allocated object of type
+            tPmcSmpsConfigParams or tPmcBmpsConfigParams or tPmcImpsConfigParams
+    \return eHalStatus
+  --------------------------------------------------------------------------*/
+eHalStatus sme_GetConfigPowerSave(tHalHandle hHal, tPmcPowerSavingMode psMode,
+                                  void *pConfigParams)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if (NULL == pConfigParams ) {
+      smsLog( pMac, LOGE, "Empty config param structure for PMC, "
+              "nothing to update");
+      return eHAL_STATUS_FAILURE;
+   }
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcGetConfigPowerSave(hHal, psMode, pConfigParams);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SignalPowerEvent
+    \brief  Signals to PMC that a power event has occurred. Used for putting
+            the chip into deep sleep mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  event - the event that has occurred
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SignalPowerEvent (tHalHandle hHal, tPmcPowerEvent event)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcSignalPowerEvent(hHal, event);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_EnablePowerSave
+    \brief  Enables one of the power saving modes.
+    \param  hHal - The handle returned by macOpen.
+    \param  psMode - The power saving mode to enable. If BMPS mode is enabled
+                     while the chip is operating in Full Power, PMC will start
+                     a timer that will try to put the chip in BMPS mode after
+                     expiry.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_EnablePowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status =  pmcEnablePowerSave(hHal, psMode);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_DisablePowerSave
+    \brief   Disables one of the power saving modes.
+    \param  hHal - The handle returned by macOpen.
+    \param  psMode - The power saving mode to disable. Disabling does not imply
+                     that device will be brought out of the current PS mode. This
+                     is purely a configuration API.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_DisablePowerSave (tHalHandle hHal, tPmcPowerSavingMode psMode)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcDisablePowerSave(hHal, psMode);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+ }
+
+/* ---------------------------------------------------------------------------
+    \fn sme_StartAutoBmpsTimer
+    \brief  Starts a timer that periodically polls all the registered
+            module for entry into Bmps mode. This timer is started only if BMPS is
+            enabled and whenever the device is in full power.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_StartAutoBmpsTimer ( tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcStartAutoBmpsTimer(hHal);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+/* ---------------------------------------------------------------------------
+    \fn sme_StopAutoBmpsTimer
+    \brief  Stops the Auto BMPS Timer that was started using sme_startAutoBmpsTimer
+            Stopping the timer does not cause a device state change. Only the timer
+            is stopped. If "Full Power" is desired, use the sme_RequestFullPower API
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_StopAutoBmpsTimer ( tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcStopAutoBmpsTimer(hHal);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+/* ---------------------------------------------------------------------------
+    \fn sme_QueryPowerState
+    \brief  Returns the current power state of the device.
+    \param  hHal - The handle returned by macOpen.
+    \param pPowerState - pointer to location to return power state (LOW or HIGH)
+    \param pSwWlanSwitchState - ptr to location to return SW WLAN Switch state
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_QueryPowerState (
+   tHalHandle hHal,
+   tPmcPowerState *pPowerState,
+   tPmcSwitchState *pSwWlanSwitchState)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcQueryPowerState (hHal, pPowerState, NULL, pSwWlanSwitchState);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_IsPowerSaveEnabled
+    \brief  Checks if the device is able to enter a particular power save mode
+            This does not imply that the device is in a particular PS mode
+    \param  hHal - The handle returned by macOpen.
+    \param psMode - the power saving mode
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+tANI_BOOLEAN sme_IsPowerSaveEnabled (tHalHandle hHal, tPmcPowerSavingMode psMode)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   tANI_BOOLEAN result = false;
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       result = pmcIsPowerSaveEnabled(hHal, psMode);
+       sme_ReleaseGlobalLock( &pMac->sme );
+       return result;
+   }
+
+   return false;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RequestFullPower
+    \brief  Request that the device be brought to full power state. When the
+            device enters Full Power PMC will start a BMPS timer if BMPS PS mode
+            is enabled. On timer expiry PMC will attempt to put the device in
+            BMPS mode if following holds true:
+            - BMPS mode is enabled
+            - Polling of all modules through the Power Save Check routine passes
+            - STA is associated to an access point
+    \param  hHal - The handle returned by macOpen.
+    \param  - callbackRoutine Callback routine invoked in case of success/failure
+    \return eHalStatus - status
+     eHAL_STATUS_SUCCESS - device brought to full power state
+     eHAL_STATUS_FAILURE - device cannot be brought to full power state
+     eHAL_STATUS_PMC_PENDING - device is being brought to full power state,
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RequestFullPower (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext,
+   tRequestFullPowerReason fullPowerReason)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcRequestFullPower(hHal, callbackRoutine, callbackContext, fullPowerReason);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RequestBmps
+    \brief  Request that the device be put in BMPS state. Request will be
+            accepted only if BMPS mode is enabled and power save check routine
+            passes.
+    \param  hHal - The handle returned by macOpen.
+    \param  - callbackRoutine Callback routine invoked in case of success/failure
+    \return eHalStatus
+      eHAL_STATUS_SUCCESS - device is in BMPS state
+      eHAL_STATUS_FAILURE - device cannot be brought to BMPS state
+      eHAL_STATUS_PMC_PENDING - device is being brought to BMPS state
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RequestBmps (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcRequestBmps(hHal, callbackRoutine, callbackContext);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn  sme_SetDHCPTillPowerActiveFlag
+    \brief  Sets/Clears DHCP related flag in PMC to disable/enable auto BMPS 
+            entry by PMC 
+    \param  hHal - The handle returned by macOpen.
+  ---------------------------------------------------------------------------*/
+void  sme_SetDHCPTillPowerActiveFlag(tHalHandle hHal, tANI_U8 flag)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   // Set/Clear the DHCP flag which will disable/enable auto BMPS entery by PMC
+   pMac->pmc.remainInPowerActiveTillDHCP = flag;
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_StartUapsd
+    \brief  Request that the device be put in UAPSD state. If the device is in
+            Full Power it will be put in BMPS mode first and then into UAPSD
+            mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  - callbackRoutine Callback routine invoked in case of success/failure
+      eHAL_STATUS_SUCCESS - device is in UAPSD state
+      eHAL_STATUS_FAILURE - device cannot be brought to UAPSD state
+      eHAL_STATUS_PMC_PENDING - device is being brought to UAPSD state
+      eHAL_STATUS_PMC_DISABLED - UAPSD is disabled or BMPS mode is disabled
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_StartUapsd (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcStartUapsd(hHal, callbackRoutine, callbackContext);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+ }
+
+/* ---------------------------------------------------------------------------
+    \fn sme_StopUapsd
+    \brief  Request that the device be put out of UAPSD state. Device will be
+            put in in BMPS state after stop UAPSD completes.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus
+      eHAL_STATUS_SUCCESS - device is put out of UAPSD and back in BMPS state
+      eHAL_STATUS_FAILURE - device cannot be brought out of UAPSD state
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_StopUapsd (tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcStopUapsd(hHal);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RequestStandby
+    \brief  Request that the device be put in standby. It is HDD's responsibility
+            to bring the chip to full power and do a disassoc before calling
+            this API.
+    \param  hHal - The handle returned by macOpen.
+    \param  - callbackRoutine Callback routine invoked in case of success/failure
+    \return eHalStatus
+      eHAL_STATUS_SUCCESS - device is in Standby mode
+      eHAL_STATUS_FAILURE - device cannot be put in standby mode
+      eHAL_STATUS_PMC_PENDING - device is being put in standby mode
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RequestStandby (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, eHalStatus status),
+   void *callbackContext)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   smsLog( pMac, LOG1, FL("") );
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcRequestStandby(hHal, callbackRoutine, callbackContext);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RegisterPowerSaveCheck
+    \brief  Register a power save check routine that is called whenever
+            the device is about to enter one of the power save modes.
+    \param  hHal - The handle returned by macOpen.
+    \param  checkRoutine -  Power save check routine to be registered
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully registered
+            eHAL_STATUS_FAILURE - not successfully registered
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RegisterPowerSaveCheck (
+   tHalHandle hHal,
+   tANI_BOOLEAN (*checkRoutine) (void *checkContext), void *checkContext)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcRegisterPowerSaveCheck (hHal, checkRoutine, checkContext);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_DeregisterPowerSaveCheck
+    \brief  Deregister a power save check routine
+    \param  hHal - The handle returned by macOpen.
+    \param  checkRoutine -  Power save check routine to be deregistered
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully deregistered
+            eHAL_STATUS_FAILURE - not successfully deregistered
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_DeregisterPowerSaveCheck (
+   tHalHandle hHal,
+   tANI_BOOLEAN (*checkRoutine) (void *checkContext))
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcDeregisterPowerSaveCheck (hHal, checkRoutine);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RegisterDeviceStateUpdateInd
+    \brief  Register a callback routine that is called whenever
+            the device enters a new device state (Full Power, BMPS, UAPSD)
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine -  Callback routine to be registered
+    \param  callbackContext -  Cookie to be passed back during callback
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully registered
+            eHAL_STATUS_FAILURE - not successfully registered
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RegisterDeviceStateUpdateInd (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, tPmcState pmcState),
+   void *callbackContext)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcRegisterDeviceStateUpdateInd (hHal, callbackRoutine, callbackContext);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_DeregisterDeviceStateUpdateInd
+    \brief  Deregister a routine that was registered for device state changes
+    \param  hHal - The handle returned by macOpen.
+    \param  callbackRoutine -  Callback routine to be deregistered
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS - successfully deregistered
+            eHAL_STATUS_FAILURE - not successfully deregistered
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_DeregisterDeviceStateUpdateInd (
+   tHalHandle hHal,
+   void (*callbackRoutine) (void *callbackContext, tPmcState pmcState))
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcDeregisterDeviceStateUpdateInd (hHal, callbackRoutine);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_WowlAddBcastPattern
+    \brief  Add a pattern for Pattern Byte Matching in Wowl mode. Firmware will
+            do a pattern match on these patterns when Wowl is enabled during BMPS
+            mode. Note that Firmware performs the pattern matching only on
+            broadcast frames and while Libra is in BMPS mode.
+    \param  hHal - The handle returned by macOpen.
+    \param  pattern -  Pattern to be added
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot add pattern
+            eHAL_STATUS_SUCCESS  Request accepted.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_WowlAddBcastPattern (
+   tHalHandle hHal,
+   tpSirWowlAddBcastPtrn pattern)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+       status = pmcWowlAddBcastPattern (hHal, pattern);
+       sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_WowlDelBcastPattern
+    \brief  Delete a pattern that was added for Pattern Byte Matching.
+    \param  hHal - The handle returned by macOpen.
+    \param  pattern -  Pattern to be deleted
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Cannot delete pattern
+            eHAL_STATUS_SUCCESS  Request accepted.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_WowlDelBcastPattern (
+   tHalHandle hHal,
+   tpSirWowlDelBcastPtrn pattern)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+       status = pmcWowlDelBcastPattern (hHal, pattern);
+       sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_EnterWowl
+    \brief  This is the SME API exposed to HDD to request enabling of WOWL mode.
+            WoWLAN works on top of BMPS mode. If the device is not in BMPS mode,
+            SME will will cache the information that WOWL has been enabled and
+            attempt to put the device in BMPS. On entry into BMPS, SME will
+            enable the WOWL mode.
+            Note 1: If we exit BMPS mode (someone requests full power), we
+            will NOT resume WOWL when we go back to BMPS again. Request for full
+            power (while in WOWL mode) means disable WOWL and go to full power.
+            Note 2: Both UAPSD and WOWL work on top of BMPS. On entry into BMPS, SME
+            will give priority to UAPSD and enable only UAPSD if both UAPSD and WOWL
+            are required. Currently there is no requirement or use case to support
+            UAPSD and WOWL at the same time.
+
+    \param  hHal - The handle returned by macOpen.
+    \param  enterWowlCallbackRoutine -  Callback routine provided by HDD.
+                               Used for success/failure notification by SME
+    \param  enterWowlCallbackContext - A cookie passed by HDD, that is passed back to HDD
+                              at the time of callback.
+    \param  wakeReasonIndCB -  Callback routine provided by HDD.
+                               Used for Wake Reason Indication by SME
+    \param  wakeReasonIndCBContext - A cookie passed by HDD, that is passed back to HDD
+                              at the time of callback.
+    \return eHalStatus
+            eHAL_STATUS_SUCCESS  Device is already in WoWLAN mode
+            eHAL_STATUS_FAILURE  Device cannot enter WoWLAN mode.
+            eHAL_STATUS_PMC_PENDING  Request accepted. SME will enable WOWL after
+                                      BMPS mode is entered.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_EnterWowl (
+    tHalHandle hHal,
+    void (*enterWowlCallbackRoutine) (void *callbackContext, eHalStatus status),
+    void *enterWowlCallbackContext,
+#ifdef WLAN_WAKEUP_EVENTS
+    void (*wakeIndicationCB) (void *callbackContext, tpSirWakeReasonInd pWakeReasonInd),
+    void *wakeIndicationCBContext,
+#endif // WLAN_WAKEUP_EVENTS
+    tpSirSmeWowlEnterParams wowlEnterParams)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+       status = pmcEnterWowl (hHal, enterWowlCallbackRoutine, enterWowlCallbackContext, 
+#ifdef WLAN_WAKEUP_EVENTS
+                              wakeIndicationCB, wakeIndicationCBContext, 
+#endif // WLAN_WAKEUP_EVENTS
+                              wowlEnterParams);
+       sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+/* ---------------------------------------------------------------------------
+    \fn sme_ExitWowl
+    \brief  This is the SME API exposed to HDD to request exit from WoWLAN mode.
+            SME will initiate exit from WoWLAN mode and device will be put in BMPS
+            mode.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus
+            eHAL_STATUS_FAILURE  Device cannot exit WoWLAN mode.
+            eHAL_STATUS_SUCCESS  Request accepted to exit WoWLAN mode.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ExitWowl (tHalHandle hHal)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+       status = pmcExitWowl (hHal);
+       sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RoamSetKey
+
+    \brief To set encryption key. This function should be called only when connected
+    This is an asynchronous API.
+
+    \param pSetKeyInfo - pointer to a caller allocated object of tCsrSetContextInfo
+
+    \param pRoamId  Upon success return, this is the id caller can use to identify the request in roamcallback
+
+    \return eHalStatus  SUCCESS  Roam callback will be called indicate actually results
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamSetKey(tHalHandle hHal, tANI_U8 sessionId, tCsrRoamSetKey *pSetKey, tANI_U32 *pRoamId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   tANI_U32 roamId;
+#ifdef WLAN_SOFTAP_FEATURE
+   tANI_U32 i;
+   tCsrRoamSession *pSession = NULL;
+#endif
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+      if(pRoamId)
+      {
+         *pRoamId = roamId;
+      }
+
+#ifdef WLAN_SOFTAP_FEATURE
+      smsLog(pMac, LOG2, FL("keyLength\n"), pSetKey->keyLength);
+
+      for(i=0; i<pSetKey->keyLength; i++)
+          smsLog(pMac, LOG2, FL("%02x"), pSetKey->Key[i]); 
+
+      smsLog(pMac, LOG2, "\n sessionId=%d roamId=%d\n", sessionId, roamId);       
+
+      pSession = CSR_GET_SESSION(pMac, sessionId);
+
+      if(CSR_IS_INFRA_AP(&pSession->connectedProfile))
+      {
+         if(pSetKey->keyDirection == eSIR_TX_DEFAULT)
+         {
+            if ( ( eCSR_ENCRYPT_TYPE_WEP40 == pSetKey->encType ) ||
+                 ( eCSR_ENCRYPT_TYPE_WEP40_STATICKEY == pSetKey->encType ))
+            {
+               pSession->pCurRoamProfile->negotiatedUCEncryptionType = eCSR_ENCRYPT_TYPE_WEP40_STATICKEY;
+            }
+            if ( ( eCSR_ENCRYPT_TYPE_WEP104 == pSetKey->encType ) ||
+                 ( eCSR_ENCRYPT_TYPE_WEP104_STATICKEY == pSetKey->encType ))
+            {
+               pSession->pCurRoamProfile->negotiatedUCEncryptionType = eCSR_ENCRYPT_TYPE_WEP104_STATICKEY;
+            }
+         }
+      }
+#endif
+
+      status = csrRoamSetKey ( pMac, sessionId, pSetKey, roamId );
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RoamRemoveKey
+
+    \brief To set encryption key. This is an asynchronous API.
+
+    \param pRemoveKey - pointer to a caller allocated object of tCsrRoamRemoveKey
+
+    \param pRoamId  Upon success return, this is the id caller can use to identify the request in roamcallback
+
+    \return eHalStatus  SUCCESS  Roam callback will be called indicate actually results
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamRemoveKey(tHalHandle hHal, tANI_U8 sessionId,
+                             tCsrRoamRemoveKey *pRemoveKey, tANI_U32 *pRoamId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   tANI_U32 roamId;
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      roamId = GET_NEXT_ROAM_ID(&pMac->roam);
+      if(pRoamId)
+      {
+         *pRoamId = roamId;
+      }
+      status = csrRoamIssueRemoveKeyCommand( pMac, sessionId, pRemoveKey, roamId );
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetRssi
+    \brief a wrapper function that client calls to register a callback to get RSSI
+
+    \param callback - SME sends back the requested stats using the callback
+    \param staId - The station ID for which the stats is requested for
+    \param pContext - user context to be passed back along with the callback
+    \param pVosContext - vos context
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetRssi(tHalHandle hHal,
+                             tCsrRssiCallback callback,
+                             tANI_U8 staId, tCsrBssid bssId, 
+                             void *pContext, void* pVosContext)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      status = csrGetRssi( pMac, callback,
+                                 staId, bssId, pContext, pVosContext);
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetStatistics
+    \brief a wrapper function that client calls to register a callback to get
+    different PHY level statistics from CSR.
+
+    \param requesterId - different client requesting for statistics, HDD, UMA/GAN etc
+    \param statsMask - The different category/categories of stats requester is looking for
+    \param callback - SME sends back the requested stats using the callback
+    \param periodicity - If requester needs periodic update in millisec, 0 means
+                         it's an one time request
+    \param cache - If requester is happy with cached stats
+    \param staId - The station ID for which the stats is requested for
+    \param pContext - user context to be passed back along with the callback
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetStatistics(tHalHandle hHal, eCsrStatsRequesterType requesterId,
+                             tANI_U32 statsMask,
+                             tCsrStatsCallback callback,
+                             tANI_U32 periodicity, tANI_BOOLEAN cache,
+                             tANI_U8 staId, void *pContext)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      status = csrGetStatistics( pMac, requesterId , statsMask, callback,
+                                 periodicity, cache, staId, pContext);
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetCountryCode
+
+    \brief To return the current country code. If no country code is applied, default country code is
+    used to fill the buffer.
+    If 11d supported is turned off, an error is return and the last applied/default country code is used.
+    This is a synchronous API.
+
+    \param pBuf - pointer to a caller allocated buffer for returned country code.
+
+    \param pbLen  For input, this parameter indicates how big is the buffer.
+                   Upon return, this parameter has the number of bytes for country. If pBuf
+                   doesn't have enough space, this function returns
+                   fail status and this parameter contains the number that is needed.
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetCountryCode(tHalHandle hHal, tANI_U8 *pBuf, tANI_U8 *pbLen)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrGetCountryCode( pMac, pBuf, pbLen ) );
+}
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_SetCountryCode
+
+    \brief To change the current/default country code.
+    If 11d supported is turned off, an error is return.
+    This is a synchronous API.
+
+    \param pCountry - pointer to a caller allocated buffer for the country code.
+
+    \param pfRestartNeeded  A pointer to caller allocated memory, upon successful return, it indicates
+    whether a reset is required.
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_SetCountryCode(tHalHandle hHal, tANI_U8 *pCountry, tANI_BOOLEAN *pfRestartNeeded)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrSetCountryCode( pMac, pCountry, pfRestartNeeded ) );
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ResetCountryCodeInformation
+    \brief this function is to reset the country code current being used back to EEPROM default
+    this includes channel list and power setting. This is a synchronous API.
+    \param pfRestartNeeded - pointer to a caller allocated space. Upon successful return, it indicates whether
+    a restart is needed to apply the change
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_ResetCountryCodeInformation(tHalHandle hHal, tANI_BOOLEAN *pfRestartNeeded)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrResetCountryCodeInformation( pMac, pfRestartNeeded ) );
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetSupportedCountryCode
+    \brief this function is to get a list of the country code current being supported
+    \param pBuf - Caller allocated buffer with at least 3 bytes, upon success return,
+    this has the country code list. 3 bytes for each country code. This may be NULL if
+    caller wants to know the needed byte count.
+    \param pbLen - Caller allocated, as input, it indicates the length of pBuf. Upon success return,
+    this contains the length of the data in pBuf. If pbuf is NULL, as input, *pbLen should be 0.
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetSupportedCountryCode(tHalHandle hHal, tANI_U8 *pBuf, tANI_U32 *pbLen)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrGetSupportedCountryCode( pMac, pBuf, pbLen ) );
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetCurrentRegulatoryDomain
+    \brief this function is to get the current regulatory domain. This is a synchronous API.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    SME. The function fails if 11d support is turned off.
+    \param pDomain - Caller allocated buffer to return the current domain.
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetCurrentRegulatoryDomain(tHalHandle hHal, v_REGDOMAIN_t *pDomain)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+
+    if( pDomain )
+    {
+        if( csrIs11dSupported( pMac ) )
+        {
+            *pDomain = csrGetCurrentRegulatoryDomain( pMac );
+            status = eHAL_STATUS_SUCCESS;
+        }
+        else
+        {
+            status = eHAL_STATUS_FAILURE;
+        }
+    }
+
+    return ( status );
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetRegulatoryDomain
+    \brief this function is to set the current regulatory domain.
+    This function must be called after CFG is downloaded and all the band/mode setting already passed into
+    SME. This is a synchronous API.
+    \param domainId - indicate the domain (defined in the driver) needs to set to.
+    See v_REGDOMAIN_t for definition
+    \param pfRestartNeeded - pointer to a caller allocated space. Upon successful return, it indicates whether
+    a restart is needed to apply the change
+    \return eHalStatus
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_SetRegulatoryDomain(tHalHandle hHal, v_REGDOMAIN_t domainId, tANI_BOOLEAN *pfRestartNeeded)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrSetRegulatoryDomain( pMac, domainId, pfRestartNeeded ) );
+}
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetRegulatoryDomainForCountry
+
+    \brief To return a regulatory domain base on a country code. This is a synchronous API.
+
+    \param pCountry - pointer to a caller allocated buffer for input country code.
+
+    \param pDomainId  Upon successful return, it is the domain that country belongs to.
+    If it is NULL, returning success means that the country code is known.
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetRegulatoryDomainForCountry(tHalHandle hHal, tANI_U8 *pCountry, v_REGDOMAIN_t *pDomainId)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrGetRegulatoryDomainForCountry( pMac, pCountry, pDomainId ) );
+}
+
+
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetSupportedRegulatoryDomains
+
+    \brief To return a list of supported regulatory domains. This is a synchronous API.
+
+    \param pDomains - pointer to a caller allocated buffer for returned regulatory domains.
+
+    \param pNumDomains  For input, this parameter indicates howm many domains pDomains can hold.
+                         Upon return, this parameter has the number for supported domains. If pDomains
+                         doesn't have enough space for all the supported domains, this function returns
+                         fail status and this parameter contains the number that is needed.
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_GetSupportedRegulatoryDomains(tHalHandle hHal, v_REGDOMAIN_t *pDomains, tANI_U32 *pNumDomains)
+{
+    eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
+
+    //We support all domains for now
+    if( pNumDomains )
+    {
+        if( NUM_REG_DOMAINS <= *pNumDomains )
+        {
+            status = eHAL_STATUS_SUCCESS;
+        }
+        *pNumDomains = NUM_REG_DOMAINS;
+    }
+    if( HAL_STATUS_SUCCESS( status ) )
+    {
+        if( pDomains )
+        {
+            pDomains[0] = REGDOMAIN_FCC;
+            pDomains[1] = REGDOMAIN_ETSI;
+            pDomains[2] = REGDOMAIN_JAPAN;
+            pDomains[3] = REGDOMAIN_WORLD;
+            pDomains[4] = REGDOMAIN_N_AMER_EXC_FCC;
+            pDomains[5] = REGDOMAIN_APAC;
+            pDomains[6] = REGDOMAIN_KOREA;
+            pDomains[7] = REGDOMAIN_HI_5GHZ;
+            pDomains[8] = REGDOMAIN_NO_5GHZ;
+        }
+        else
+        {
+            status = eHAL_STATUS_INVALID_PARAMETER;
+        }
+    }
+
+    return ( status );
+}
+
+
+//some support functions
+tANI_BOOLEAN sme_Is11dSupported(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrIs11dSupported( pMac ) );
+}
+
+
+tANI_BOOLEAN sme_Is11hSupported(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrIs11hSupported( pMac ) );
+}
+
+
+tANI_BOOLEAN sme_IsWmmSupported(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    return ( csrIsWmmSupported( pMac ) );
+}
+
+//Upper layer to get the list of the base channels to scan for passively 11d info from csr
+eHalStatus sme_ScanGetBaseChannels( tHalHandle hHal, tCsrChannelInfo * pChannelInfo )
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   return(csrScanGetBaseChannels(pMac,pChannelInfo) );
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_ChangeCountryCode
+
+    \brief Change Country code from upperlayer during WLAN driver operation.
+           This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+
+    \param pCountry New Country Code String
+
+    \return eHalStatus  SUCCESS.
+
+                         FAILURE or RESOURCES  The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_ChangeCountryCode( tHalHandle hHal,
+                                          tSmeChangeCountryCallback callback,
+                                          tANI_U8 *pCountry,
+                                          void *pContext,
+                                          void* pVosContext )
+{
+   eHalStatus                status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal            pMac = PMAC_STRUCT( hHal );
+   vos_msg_t                 msg;
+   tAniChangeCountryCodeReq *pMsg;
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      smsLog(pMac, LOG1, FL(" called\n"));      
+      status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, sizeof(tAniChangeCountryCodeReq));
+      if ( !HAL_STATUS_SUCCESS(status) ) 
+      {
+         smsLog(pMac, LOGE, " csrChangeCountryCode: failed to allocate mem for req \n");
+         return status;
+      }
+
+      pMsg->msgType = pal_cpu_to_be16((tANI_U16)eWNI_SME_CHANGE_COUNTRY_CODE);
+      pMsg->msgLen = (tANI_U16)sizeof(tAniChangeCountryCodeReq);
+      palCopyMemory(pMac->hHdd, pMsg->countryCode, pCountry, 3);
+      pMsg->changeCCCallback = callback;
+      pMsg->pDevContext = pContext;
+      pMsg->pVosContext = pVosContext;
+
+      msg.type = eWNI_SME_CHANGE_COUNTRY_CODE;
+      msg.bodyptr = pMsg;
+      msg.reserved = 0;
+
+      if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MQ_ID_SME, &msg))
+      {
+          smsLog(pMac, LOGE, " sme_ChangeCountryCode failed to post msg to self \n");   
+          palFreeMemory(pMac->hHdd, (void *)pMsg);
+          status = eHAL_STATUS_FAILURE;
+      }
+      smsLog(pMac, LOG1, FL(" returned\n"));      
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_BtcSignalBtEvent
+    \brief  API to signal Bluetooth (BT) event to the WLAN driver. Based on the
+            BT event type and the current operating mode of Libra (full power,
+            BMPS, UAPSD etc), appropriate Bluetooth Coexistence (BTC) strategy
+            would be employed.
+    \param  hHal - The handle returned by macOpen.
+    \param  pBtEvent -  Pointer to a caller allocated object of type tSmeBtEvent
+                        Caller owns the memory and is responsible for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  BT Event not passed to HAL. This can happen
+                                   if BTC execution mode is set to BTC_WLAN_ONLY
+                                   or BTC_PTA_ONLY.
+            VOS_STATUS_SUCCESS    BT Event passed to HAL
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_BtcSignalBtEvent (tHalHandle hHal, tpSmeBtEvent pBtEvent)
+{
+    VOS_STATUS status = VOS_STATUS_E_FAILURE;
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        status = btcSignalBTEvent (hHal, pBtEvent);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+#endif
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_BtcSetConfig
+    \brief  API to change the current Bluetooth Coexistence (BTC) configuration
+            This function should be invoked only after CFG download has completed.
+            Calling it after sme_HDDReadyInd is recommended.
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type tSmeBtcConfig.
+                            Caller owns the memory and is responsible for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE  Config not passed to HAL.
+            VOS_STATUS_SUCCESS  Config passed to HAL
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_BtcSetConfig (tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig)
+{
+    VOS_STATUS status = VOS_STATUS_E_FAILURE;
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        status = btcSetConfig (hHal, pSmeBtcConfig);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+#endif
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_BtcGetConfig
+    \brief  API to retrieve the current Bluetooth Coexistence (BTC) configuration
+    \param  hHal - The handle returned by macOpen.
+    \param  pSmeBtcConfig - Pointer to a caller allocated object of type
+                            tSmeBtcConfig. Caller owns the memory and is responsible
+                            for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_BtcGetConfig (tHalHandle hHal, tpSmeBtcConfig pSmeBtcConfig)
+{
+    VOS_STATUS status = VOS_STATUS_E_FAILURE;
+#ifndef WLAN_MDM_CODE_REDUCTION_OPT
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        status = btcGetConfig (hHal, pSmeBtcConfig);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+#endif
+    return (status);
+}
+/* ---------------------------------------------------------------------------
+    \fn sme_SetCfgPrivacy
+    \brief  API to set configure privacy parameters
+    \param  hHal - The handle returned by macOpen.
+    \param  pProfile - Pointer CSR Roam profile.
+    \param  fPrivacy - This parameter indicates status of privacy 
+
+    \return void
+  ---------------------------------------------------------------------------*/
+void sme_SetCfgPrivacy( tHalHandle hHal,
+                        tCsrRoamProfile *pProfile,
+                        tANI_BOOLEAN fPrivacy
+                        )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        csrSetCfgPrivacy(pMac, pProfile, fPrivacy);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+}
+
+#if defined WLAN_FEATURE_VOWIFI
+/* ---------------------------------------------------------------------------
+    \fn sme_NeighborReportRequest
+    \brief  API to request neighbor report.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRrmNeighborReq - Pointer to a caller allocated object of type
+                            tRrmNeighborReq. Caller owns the memory and is responsible
+                            for freeing it.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_NeighborReportRequest (tHalHandle hHal, tANI_U8 sessionId,
+                                    tpRrmNeighborReq pRrmNeighborReq, tpRrmNeighborRspCallbackInfo callbackInfo)
+{
+    VOS_STATUS status = VOS_STATUS_E_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        status = sme_RrmNeighborReportRequest (hHal, sessionId, pRrmNeighborReq, callbackInfo);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+#endif
+
+//The following are debug APIs to support direct read/write register/memory
+//They are placed in SME because HW cannot be access when in LOW_POWER state
+//AND not connected. The knowledge and synchronization is done in SME
+
+//sme_DbgReadRegister
+//Caller needs to validate the input values
+VOS_STATUS sme_DbgReadRegister(tHalHandle hHal, v_U32_t regAddr, v_U32_t *pRegValue)
+{
+   VOS_STATUS   status = VOS_STATUS_E_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+   tHddHandle     hHdd = pMac->hHdd;
+#endif
+   tPmcPowerState PowerState;
+   tANI_U32  sessionId = 0;
+
+   /* 1) To make Quarky work in FTM mode **************************************/
+
+   if(eDRIVER_TYPE_MFG == pMac->gDriverType)
+   {
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+      if (HAL_STATUS_SUCCESS(palReadRegister(hHdd, regAddr, pRegValue)))
+#elif defined(FEATURE_WLAN_INTEGRATED_SOC)
+      if (eWLAN_PAL_STATUS_SUCCESS == wpalDbgReadRegister(regAddr, pRegValue))
+#endif
+      {
+         return VOS_STATUS_SUCCESS;
+      }
+      return VOS_STATUS_E_FAILURE;
+   }
+
+   /* 2) NON FTM mode driver *************************************************/
+
+   /* Acquire SME global lock */
+   if (eHAL_STATUS_SUCCESS != sme_AcquireGlobalLock(&pMac->sme))
+   {
+      return VOS_STATUS_E_FAILURE;
+   }
+
+   if(HAL_STATUS_SUCCESS(pmcQueryPowerState(pMac, &PowerState, NULL, NULL)))
+   {
+      /* Are we not in IMPS mode? Or are we in connected? Then we're safe*/
+      if(!csrIsConnStateDisconnected(pMac, sessionId) || (ePMC_LOW_POWER != PowerState))
+      {
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+         if (HAL_STATUS_SUCCESS(palReadRegister(hHdd, regAddr, pRegValue )))
+#elif defined(FEATURE_WLAN_INTEGRATED_SOC)
+         if (eWLAN_PAL_STATUS_SUCCESS == wpalDbgReadRegister(regAddr, pRegValue))
+#endif
+         {
+            status = VOS_STATUS_SUCCESS;
+         }
+         else
+         {  
+            status = VOS_STATUS_E_FAILURE;
+         }
+      }
+      else
+      {
+         status = VOS_STATUS_E_FAILURE;
+      }
+   }
+
+   /* This is a hack for Qualky/pttWniSocket
+      Current implementation doesn't allow pttWniSocket to inform Qualky an error */
+   if ( VOS_STATUS_SUCCESS != status )
+   {
+      *pRegValue = 0xDEADBEEF;
+       status = VOS_STATUS_SUCCESS;
+   }
+        
+   /* Release SME global lock */
+   sme_ReleaseGlobalLock(&pMac->sme);
+    
+   return (status);
+}
+
+
+//sme_DbgWriteRegister
+//Caller needs to validate the input values
+VOS_STATUS sme_DbgWriteRegister(tHalHandle hHal, v_U32_t regAddr, v_U32_t regValue)
+{
+   VOS_STATUS    status = VOS_STATUS_E_FAILURE;
+   tpAniSirGlobal  pMac = PMAC_STRUCT(hHal);
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+   tHddHandle      hHdd = pMac->hHdd;
+#endif
+   tPmcPowerState PowerState;
+   tANI_U32   sessionId = 0;
+
+   /* 1) To make Quarky work in FTM mode **************************************/
+
+   if(eDRIVER_TYPE_MFG == pMac->gDriverType)
+   {
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+      if (HAL_STATUS_SUCCESS(palWriteRegister(hHdd, regAddr, regValue)))
+#elif defined(FEATURE_WLAN_INTEGRATED_SOC)
+      if (eWLAN_PAL_STATUS_SUCCESS == wpalDbgWriteRegister(regAddr, regValue))
+#endif
+      {
+         return VOS_STATUS_SUCCESS;
+      }
+      return VOS_STATUS_E_FAILURE;
+   }
+
+   /* 2) NON FTM mode driver *************************************************/
+
+   /* Acquire SME global lock */
+   if (eHAL_STATUS_SUCCESS != sme_AcquireGlobalLock(&pMac->sme))
+   {
+      return VOS_STATUS_E_FAILURE;
+   }
+
+   if(HAL_STATUS_SUCCESS(pmcQueryPowerState(pMac, &PowerState, NULL, NULL)))
+   {
+      /* Are we not in IMPS mode? Or are we in connected? Then we're safe*/
+      if(!csrIsConnStateDisconnected(pMac, sessionId) || (ePMC_LOW_POWER != PowerState))
+      {
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+         if (HAL_STATUS_SUCCESS(palWriteRegister(hHdd, regAddr, regValue)))
+#elif defined(FEATURE_WLAN_INTEGRATED_SOC)
+         if (eWLAN_PAL_STATUS_SUCCESS == wpalDbgWriteRegister(regAddr, regValue))
+#endif
+         {
+            status = VOS_STATUS_SUCCESS;
+         }
+         else
+         {
+            status = VOS_STATUS_E_FAILURE;
+         }
+      }
+      else
+      {
+         status = VOS_STATUS_E_FAILURE;
+      }
+   }
+        
+   /* Release SME global lock */
+   sme_ReleaseGlobalLock(&pMac->sme);
+    
+   return (status);
+}
+
+
+
+//sme_DbgReadMemory
+//Caller needs to validate the input values
+//pBuf caller allocated buffer has the length of nLen
+VOS_STATUS sme_DbgReadMemory(tHalHandle hHal, v_U32_t memAddr, v_U8_t *pBuf, v_U32_t nLen)
+{
+   VOS_STATUS  status  = VOS_STATUS_E_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+   v_PVOID_t  pvosGCTx = vos_get_global_context(VOS_MODULE_ID_PE, (v_VOID_t *)hHal);
+   tHddHandle     hHdd = pMac->hHdd;
+#endif
+   tPmcPowerState PowerState;
+   tANI_U32 sessionId  = 0;
+
+   /* 1) To make Quarky work in FTM mode **************************************/
+
+   if(eDRIVER_TYPE_MFG == pMac->gDriverType)
+   {
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+      if (HAL_STATUS_SUCCESS(palReadDeviceMemory(hHdd, memAddr, (void *)pBuf, nLen)))
+#elif defined(FEATURE_WLAN_INTEGRATED_SOC)
+      if (eWLAN_PAL_STATUS_SUCCESS == wpalDbgReadMemory(memAddr, (void *)pBuf, nLen))
+#endif
+      {
+         return VOS_STATUS_SUCCESS;
+      }
+      return VOS_STATUS_E_FAILURE;
+   }
+
+   /* 2) NON FTM mode driver *************************************************/
+
+   /* Acquire SME global lock */
+   if (eHAL_STATUS_SUCCESS != sme_AcquireGlobalLock(&pMac->sme))
+   {
+      return VOS_STATUS_E_FAILURE;
+   }
+
+   if(HAL_STATUS_SUCCESS(pmcQueryPowerState(pMac, &PowerState, NULL, NULL)))
+   {
+      /* Are we not in IMPS mode? Or are we in connected? Then we're safe*/
+      if(!csrIsConnStateDisconnected(pMac, sessionId) || (ePMC_LOW_POWER != PowerState))
+      {
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+         if (HAL_STATUS_SUCCESS(palReadDeviceMemory(pvosGCTx, memAddr, (void *)pBuf, nLen)))
+#elif defined(FEATURE_WLAN_INTEGRATED_SOC)
+         if (eWLAN_PAL_STATUS_SUCCESS == wpalDbgReadMemory(memAddr, (void *)pBuf, nLen)) 
+#endif
+         {
+            status = VOS_STATUS_SUCCESS;
+         }
+         else
+         {
+            status = VOS_STATUS_E_FAILURE;
+         }
+      }
+      else
+      {
+         status = VOS_STATUS_E_FAILURE;
+      }
+   }
+
+   /* This is a hack for Qualky/pttWniSocket
+      Current implementation doesn't allow pttWniSocket to inform Qualky an error */
+   if (VOS_STATUS_SUCCESS != status)
+   {
+      vos_mem_set(pBuf, nLen, 0xCD);
+      status = VOS_STATUS_SUCCESS;
+      smsLog(pMac, LOGE, FL(" filled with 0xCD because it cannot access the hardware\n"));
+   }
+
+   /* Release SME lock */
+   sme_ReleaseGlobalLock(&pMac->sme);
+    
+   return (status);
+}
+
+
+//sme_DbgWriteMemory
+//Caller needs to validate the input values
+VOS_STATUS sme_DbgWriteMemory(tHalHandle hHal, v_U32_t memAddr, v_U8_t *pBuf, v_U32_t nLen)
+{
+   VOS_STATUS    status = VOS_STATUS_E_FAILURE;
+   tpAniSirGlobal  pMac = PMAC_STRUCT(hHal);
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+   tHddHandle      hHdd = pMac->hHdd;
+#endif
+   tPmcPowerState PowerState;
+   tANI_U32   sessionId = 0;
+
+   /* 1) To make Quarky work in FTM mode **************************************/
+
+   if(eDRIVER_TYPE_MFG == pMac->gDriverType)
+   {
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+      if (HAL_STATUS_SUCCESS(palWriteDeviceMemory(hHdd, memAddr, (void *)pBuf, nLen)))
+#elif defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+      if (eWLAN_PAL_STATUS_SUCCESS == wpalDbgWriteMemory( memAddr, (void *)pBuf, nLen))
+#endif
+      {
+         return VOS_STATUS_SUCCESS;
+      }
+      return VOS_STATUS_E_FAILURE;
+   }
+
+   /* 2) NON FTM mode driver *************************************************/
+
+   /* Acquire SME global lock */
+   if (eHAL_STATUS_SUCCESS != sme_AcquireGlobalLock(&pMac->sme))
+   {
+      return VOS_STATUS_E_FAILURE;
+   }
+
+   if(HAL_STATUS_SUCCESS(pmcQueryPowerState(pMac, &PowerState, NULL, NULL)))
+   {
+      /* Are we not in IMPS mode? Or are we in connected? Then we're safe*/
+      if(!csrIsConnStateDisconnected(pMac, sessionId) || (ePMC_LOW_POWER != PowerState))
+      {
+#if defined(FEATURE_WLAN_NON_INTEGRATED_SOC)
+         if (HAL_STATUS_SUCCESS(palWriteDeviceMemory(hHdd, memAddr, (void *)pBuf, nLen)))
+#elif defined(FEATURE_WLAN_INTEGRATED_SOC)
+         if (eWLAN_PAL_STATUS_SUCCESS == wpalDbgWriteMemory(memAddr, (void *)pBuf, nLen))
+#endif
+         {
+            status = VOS_STATUS_SUCCESS;
+         }
+         else
+         {
+            status = VOS_STATUS_E_FAILURE;
+         }
+      }
+      else
+      {
+         status = VOS_STATUS_E_FAILURE;
+      }
+   }
+
+   /* Release Global lock */
+   sme_ReleaseGlobalLock(&pMac->sme);
+    
+   return (status);
+}
+
+
+void smsLog(tpAniSirGlobal pMac, tANI_U32 loglevel, const char *pString,...) 
+{
+#ifdef WLAN_DEBUG
+    // Verify against current log level
+    if ( loglevel > pMac->utils.gLogDbgLevel[LOG_INDEX_FOR_MODULE( SIR_SMS_MODULE_ID )] )
+        return;
+    else
+    {
+        va_list marker;
+
+        va_start( marker, pString );     /* Initialize variable arguments. */
+
+        logDebug(pMac, SIR_SMS_MODULE_ID, loglevel, pString, marker);
+
+        va_end( marker );              /* Reset variable arguments.      */
+    }
+#endif
+}
+#ifdef FEATURE_WLAN_NON_INTEGRATED_SOC  
+/* ---------------------------------------------------------------------------
+    \fn sme_GetFwVersion
+    \brief  This API returns the firmware version.
+    \param  hHal - The handle returned by macOpen.
+    \param  version - Points to the FwVersionInfo structure.
+    \return VOS_STATUS
+            VOS_STATUS_E_INVAL - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_GetFwVersion (tHalHandle hHal,FwVersionInfo *pVersion)
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        if( pVersion != NULL ) {
+            vos_mem_copy((v_VOID_t*)pVersion,(v_VOID_t*)&pMac->hal.FwParam.fwVersion, sizeof(FwVersionInfo));
+        }
+        else {
+            status = VOS_STATUS_E_INVAL;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+#endif
+
+#ifdef FEATURE_WLAN_INTEGRATED_SOC
+/* ---------------------------------------------------------------------------
+    \fn sme_GetWcnssWlanCompiledVersion
+    \brief  This API returns the version of the WCNSS WLAN API with
+            which the HOST driver was built
+    \param  hHal - The handle returned by macOpen.
+    \param  pVersion - Points to the Version structure to be filled
+    \return VOS_STATUS
+            VOS_STATUS_E_INVAL - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_GetWcnssWlanCompiledVersion(tHalHandle hHal,
+                                           tSirVersionType *pVersion)
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    v_CONTEXT_t vosContext = vos_get_global_context(VOS_MODULE_ID_SME, NULL);
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        if( pVersion != NULL )
+        {
+            status = WDA_GetWcnssWlanCompiledVersion(vosContext, pVersion);
+        }
+        else
+        {
+            status = VOS_STATUS_E_INVAL;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetWcnssWlanReportedVersion
+    \brief  This API returns the version of the WCNSS WLAN API with
+            which the WCNSS driver reports it was built
+    \param  hHal - The handle returned by macOpen.
+    \param  pVersion - Points to the Version structure to be filled
+    \return VOS_STATUS
+            VOS_STATUS_E_INVAL - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_GetWcnssWlanReportedVersion(tHalHandle hHal,
+                                           tSirVersionType *pVersion)
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    v_CONTEXT_t vosContext = vos_get_global_context(VOS_MODULE_ID_SME, NULL);
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        if( pVersion != NULL )
+        {
+            status = WDA_GetWcnssWlanReportedVersion(vosContext, pVersion);
+        }
+        else
+        {
+            status = VOS_STATUS_E_INVAL;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetWcnssSoftwareVersion
+    \brief  This API returns the version string of the WCNSS driver
+    \param  hHal - The handle returned by macOpen.
+    \param  pVersion - Points to the Version string buffer to be filled
+    \param  versionBufferSize - THe size of the Version string buffer
+    \return VOS_STATUS
+            VOS_STATUS_E_INVAL - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_GetWcnssSoftwareVersion(tHalHandle hHal,
+                                       tANI_U8 *pVersion,
+                                       tANI_U32 versionBufferSize)
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    v_CONTEXT_t vosContext = vos_get_global_context(VOS_MODULE_ID_SME, NULL);
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        if( pVersion != NULL )
+        {
+            status = WDA_GetWcnssSoftwareVersion(vosContext, pVersion,
+                                                 versionBufferSize);
+        }
+        else
+        {
+            status = VOS_STATUS_E_INVAL;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetWcnssHardwareVersion
+    \brief  This API returns the version string of the WCNSS hardware
+    \param  hHal - The handle returned by macOpen.
+    \param  pVersion - Points to the Version string buffer to be filled
+    \param  versionBufferSize - THe size of the Version string buffer
+    \return VOS_STATUS
+            VOS_STATUS_E_INVAL - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+VOS_STATUS sme_GetWcnssHardwareVersion(tHalHandle hHal,
+                                       tANI_U8 *pVersion,
+                                       tANI_U32 versionBufferSize)
+{
+    VOS_STATUS status = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    v_CONTEXT_t vosContext = vos_get_global_context(VOS_MODULE_ID_SME, NULL);
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        if( pVersion != NULL )
+        {
+            status = WDA_GetWcnssHardwareVersion(vosContext, pVersion,
+                                                 versionBufferSize);
+        }
+        else
+        {
+            status = VOS_STATUS_E_INVAL;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+#endif
+
+#ifdef FEATURE_WLAN_WAPI
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamSetBKIDCache
+    \brief The SME API exposed to HDD to allow HDD to provde SME the BKID
+    candidate list.
+    \param hHal - Handle to the HAL. The HAL handle is returned by the HAL after
+    it is opened (by calling halOpen).
+    \param pBKIDCache - caller allocated buffer point to an array of tBkidCacheInfo
+    \param numItems - a variable that has the number of tBkidCacheInfo allocated
+    when retruning, this is the number of items put into pBKIDCache
+    \return eHalStatus - when fail, it usually means the buffer allocated is not
+    big enough and pNumItems has the number of tBkidCacheInfo.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamSetBKIDCache( tHalHandle hHal, tANI_U32 sessionId, tBkidCacheInfo *pBKIDCache,
+                                 tANI_U32 numItems )
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = csrRoamSetBKIDCache( pMac, sessionId, pBKIDCache, numItems );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetBKIDCache
+    \brief The SME API exposed to HDD to allow HDD to request SME to return its
+    BKID cache.
+    \param hHal - Handle to the HAL. The HAL handle is returned by the HAL after
+    it is opened (by calling halOpen).
+    \param pNum - caller allocated memory that has the space of the number of
+    tBkidCacheInfo as input. Upon returned, *pNum has the needed number of entries
+    in SME cache.
+    \param pBkidCache - Caller allocated memory that contains BKID cache, if any,
+    upon return
+    \return eHalStatus - when fail, it usually means the buffer allocated is not
+    big enough.
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_RoamGetBKIDCache(tHalHandle hHal, tANI_U32 *pNum,
+                                tBkidCacheInfo *pBkidCache)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       smsLog(pMac, LOGE, FL(" !!!!!!!!!!!!!!!!!!SessionId is hardcoded\n"));
+       status = csrRoamGetBKIDCache( pMac, 0, pNum, pBkidCache );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RoamGetNumBKIDCache
+    \brief The SME API exposed to HDD to allow HDD to request SME to return the
+    number of BKID cache entries.
+    \param hHal - Handle to the HAL. The HAL handle is returned by the HAL after
+    it is opened (by calling halOpen).
+    \return tANI_U32 - the number of BKID cache entries.
+  ---------------------------------------------------------------------------*/
+tANI_U32 sme_RoamGetNumBKIDCache(tHalHandle hHal, tANI_U32 sessionId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   tANI_U32 numBkidCache = 0;
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       numBkidCache = csrRoamGetNumBKIDCache( pMac, sessionId );
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (numBkidCache);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ScanGetBKIDCandidateList
+    \brief a wrapper function to return the BKID candidate list
+    \param pBkidList - caller allocated buffer point to an array of
+                        tBkidCandidateInfo
+    \param pNumItems - pointer to a variable that has the number of
+                       tBkidCandidateInfo allocated when retruning, this is
+                       either the number needed or number of items put into
+                       pPmkidList
+    \return eHalStatus - when fail, it usually means the buffer allocated is not
+                         big enough and pNumItems
+    has the number of tBkidCandidateInfo.
+    \Note: pNumItems is a number of tBkidCandidateInfo,
+           not sizeof(tBkidCandidateInfo) * something
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_ScanGetBKIDCandidateList(tHalHandle hHal, tANI_U32 sessionId,
+                                        tBkidCandidateInfo *pBkidList,
+                                        tANI_U32 *pNumItems )
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+        status = csrScanGetBKIDCandidateList( pMac, sessionId, pBkidList, pNumItems );
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+#endif /* FEATURE_WLAN_WAPI */
+
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_OpenSession() - Open a session for scan/roam operation.
+
+  This is a synchronous API.
+
+
+  \param hHal - The handle returned by macOpen.
+  \param callback - A pointer to the function caller specifies for roam/connect status indication
+  \param pContext - The context passed with callback
+  \param pSelfMacAddr - Caller allocated memory filled with self MAC address (6 bytes)
+  \param pbSessionId - pointer to a caller allocated buffer for returned session ID
+
+  \return eHAL_STATUS_SUCCESS - session is opened. sessionId returned.
+
+          Other status means SME is failed to open the session.
+          eHAL_STATUS_RESOURCES - no more session available.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_OpenSession(tHalHandle hHal, csrRoamCompleteCallback callback, void *pContext,
+                           tANI_U8 *pSelfMacAddr, tANI_U8 *pbSessionId)
+{
+   eHalStatus status;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   if( NULL == pbSessionId )
+   {
+      status = eHAL_STATUS_INVALID_PARAMETER;
+   }
+   else
+   {
+      status = sme_AcquireGlobalLock( &pMac->sme );
+      if ( HAL_STATUS_SUCCESS( status ) )
+      {
+         status = csrRoamOpenSession( pMac, callback, pContext, pSelfMacAddr, pbSessionId );
+
+         sme_ReleaseGlobalLock( &pMac->sme );
+      }
+   }
+
+   return ( status );
+}
+
+
+/*--------------------------------------------------------------------------
+
+  \brief sme_CloseSession() - Open a session for scan/roam operation.
+
+  This is a synchronous API.
+
+
+  \param hHal - The handle returned by macOpen.
+
+  \param sessionId - A previous opened session's ID.
+
+  \return eHAL_STATUS_SUCCESS - session is closed.
+
+          Other status means SME is failed to open the session.
+          eHAL_STATUS_INVALID_PARAMETER - session is not opened.
+  \sa
+
+  --------------------------------------------------------------------------*/
+eHalStatus sme_CloseSession(tHalHandle hHal, tANI_U8 sessionId,
+                          csrRoamSessionCloseCallback callback, void *pContext)
+{
+   eHalStatus status;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      status = csrRoamCloseSession( pMac, sessionId, FALSE, 
+                                    callback, pContext );
+
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return ( status );
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RoamUpdateAPWPSIE
+
+    \brief To update AP's WPS IE. This function should be called after SME AP session is created
+    This is an asynchronous API.
+
+    \param pAPWPSIES - pointer to a caller allocated object of tSirAPWPSIEs
+
+    \return eHalStatus – SUCCESS –
+
+                         FAILURE or RESOURCES – The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamUpdateAPWPSIE(tHalHandle hHal, tANI_U8 sessionId, tSirAPWPSIEs *pAPWPSIES)
+{
+
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+
+      status = csrRoamUpdateAPWPSIE( pMac, sessionId, pAPWPSIES );
+
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RoamUpdateAPWPARSNIEs
+
+    \brief To update AP's WPA/RSN IEs. This function should be called after SME AP session is created
+    This is an asynchronous API.
+
+    \param pAPSirRSNie - pointer to a caller allocated object of tSirRSNie with WPS/RSN IEs
+
+    \return eHalStatus – SUCCESS –
+
+                         FAILURE or RESOURCES – The API finished and failed.
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RoamUpdateAPWPARSNIEs(tHalHandle hHal, tANI_U8 sessionId, tSirRSNie * pAPSirRSNie)
+{
+
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+
+      status = csrRoamUpdateWPARSNIEs( pMac, sessionId, pAPSirRSNie);
+
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+#endif
+
+
+/*-------------------------------------------------------------------------------*
+
+  \fn sme_sendBTAmpEvent
+
+  \brief to receive the coex priorty request from BT-AMP PAL
+  and send the BT_AMP link state to HAL
+
+  \param btAmpEvent - btAmpEvent
+
+  \return eHalStatus: SUCESS : BTAmp event successfully sent to HAL
+
+                      FAILURE: API failed
+
+-------------------------------------------------------------------------------*/
+
+eHalStatus sme_sendBTAmpEvent(tHalHandle hHal, tSmeBtAmpEvent btAmpEvent)
+{
+  vos_msg_t msg;
+  tpSmeBtAmpEvent ptrSmeBtAmpEvent = NULL;
+  eHalStatus status = eHAL_STATUS_FAILURE;
+
+  ptrSmeBtAmpEvent = vos_mem_malloc(sizeof(tpSmeBtAmpEvent));
+  if (NULL == ptrSmeBtAmpEvent)
+     {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+           "Not able to allocate memory for BTAmp event", __FUNCTION__);
+        return status;
+   }
+
+  vos_mem_copy(ptrSmeBtAmpEvent, (void*)&btAmpEvent, sizeof(tSmeBtAmpEvent));
+  msg.type = WDA_SIGNAL_BTAMP_EVENT;
+  msg.reserved = 0;
+  msg.bodyptr = ptrSmeBtAmpEvent;
+
+  //status = halFW_SendBTAmpEventMesg(pMac, event);
+
+  if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+  {
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+           "Not able to post SIR_HAL_SIGNAL_BTAMP_EVENT message to HAL", __FUNCTION__);
+    vos_mem_free(ptrSmeBtAmpEvent);
+    return status;
+  }
+
+  return eHAL_STATUS_SUCCESS;
+
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetHostOffload
+    \brief  API to set the host offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the offload request.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetHostOffload (tHalHandle hHal, tpSirHostOffloadReq pRequest)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+#ifdef WLAN_NS_OFFLOAD
+        if(SIR_IPV6_NS_OFFLOAD == pRequest->offloadType)
+        {
+            status = pmcSetNSOffload( hHal, pRequest );
+        }
+        else
+#endif //WLAN_NS_OFFLOAD
+        {
+            status = pmcSetHostOffload (hHal, pRequest);
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+#ifdef WLAN_FEATURE_GTK_OFFLOAD
+/* ---------------------------------------------------------------------------
+    \fn sme_SetGTKOffload
+    \brief  API to set GTK offload information.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the GTK offload request.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetGTKOffload (tHalHandle hHal, tpSirGtkOffloadParams pRequest)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        status = pmcSetGTKOffload( hHal, pRequest );
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetGTKOffload
+    \brief  API to get GTK offload information.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the GTK offload response.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_GetGTKOffload (tHalHandle hHal, GTKOffloadGetInfoCallback callbackRoutine, void *callbackContext )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        pmcGetGTKOffload(hHal, callbackRoutine, callbackContext);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+#endif // WLAN_FEATURE_GTK_OFFLOAD
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetKeepAlive
+    \brief  API to set the Keep Alive feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the Keep Alive request.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetKeepAlive (tHalHandle hHal, tpSirKeepAliveReq pRequest)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: "
+           "setting Keep alive in SME TP %d", __FUNCTION__,pRequest->timePeriod);
+
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        status = pmcSetKeepAlive (hHal, pRequest);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+#ifdef FEATURE_WLAN_SCAN_PNO
+/* ---------------------------------------------------------------------------
+    \fn sme_SetPreferredNetworkList
+    \brief  API to set the Preferred Network List Offload feature.
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  Pointer to the offload request.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetPreferredNetworkList (tHalHandle hHal, tpSirPNOScanReq pRequest, tANI_U8 sessionId, void (*callbackRoutine) (void *callbackContext, tSirPrefNetworkFoundInd *pPrefNetworkFoundInd), void *callbackContext )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        pmcSetPreferredNetworkList(hHal, pRequest, sessionId, callbackRoutine, callbackContext);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+eHalStatus sme_SetRSSIFilter(tHalHandle hHal, v_U8_t rssiThreshold)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        pmcSetRssiFilter(hHal, rssiThreshold);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+#endif // FEATURE_WLAN_SCAN_PNO
+
+eHalStatus sme_SetPowerParams(tHalHandle hHal, tSirSetPowerParamsReq* pwParams)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        pmcSetPowerParams(hHal, pwParams);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_AbortMacScan
+    \brief  API to cancel MAC scan.
+    \param  hHal - The handle returned by macOpen.
+    \return VOS_STATUS
+            VOS_STATUS_E_FAILURE - failure
+            VOS_STATUS_SUCCESS  success
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_AbortMacScan(tHalHandle hHal)
+{
+    eHalStatus status;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+       status = csrScanAbortMacScan(pMac);
+    
+       sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    
+    return ( status );
+}
+
+/* ----------------------------------------------------------------------------
+        \fn sme_GetOperationChannel
+        \brief API to get current channel on which STA is parked
+        this function gives channel information only of infra station or IBSS station
+        \param hHal and poiter to memory location
+        \returns eHAL_STATUS_SUCCESS
+                eHAL_STATUS_FAILURE
+-------------------------------------------------------------------------------*/
+eHalStatus sme_GetOperationChannel(tHalHandle hHal, tANI_U32 *pChannel)
+{
+    tANI_U32 sessionId;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    tCsrRoamSession *pSession;
+
+    for (sessionId = 0; sessionId < CSR_ROAM_SESSION_MAX ; sessionId++)
+    {
+       if (CSR_IS_SESSION_VALID( pMac, sessionId ))
+       {
+          pSession = CSR_GET_SESSION( pMac, sessionId );
+
+          if(( pSession->connectedProfile.BSSType == eCSR_BSS_TYPE_INFRASTRUCTURE ) || 
+             ( pSession->connectedProfile.BSSType == eCSR_BSS_TYPE_IBSS ) ||
+             ( pSession->connectedProfile.BSSType == eCSR_BSS_TYPE_START_IBSS ))
+          {
+              *pChannel =pSession->connectedProfile.operationChannel;
+              return eHAL_STATUS_SUCCESS;
+          }
+       }
+    }
+    return eHAL_STATUS_FAILURE;
+}// sme_GetOperationChannel ends here
+
+#ifdef WLAN_FEATURE_P2P
+/* ---------------------------------------------------------------------------
+
+    \fn sme_RegisterMgtFrame
+
+    \brief To register managment frame of specified type and subtype. 
+    \param frameType - type of the frame that needs to be passed to HDD.
+    \param matchData - data which needs to be matched before passing frame 
+                       to HDD. 
+    \param matchDataLen - Length of matched data.
+    \return eHalStatus 
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_RegisterMgmtFrame(tHalHandle hHal, tANI_U8 sessionId, 
+                     tANI_U16 frameType, tANI_U8* matchData, tANI_U16 matchLen)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        tSirRegisterMgmtFrame *pMsg;
+        tANI_U16 len;
+        tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+        
+        if( !pSession->sessionActive )
+        {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                        "%s Invalid Sessionid", __FUNCTION__);
+            sme_ReleaseGlobalLock( &pMac->sme );
+            return eHAL_STATUS_FAILURE;
+        }
+        
+        len = sizeof(tSirRegisterMgmtFrame) + matchLen;
+        
+        status = palAllocateMemory(pMac->hHdd, (void**)&pMsg, len );
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pMsg, len);
+            pMsg->messageType     = eWNI_SME_REGISTER_MGMT_FRAME_REQ;
+            pMsg->length          = len;
+            pMsg->sessionId       = sessionId;
+            pMsg->registerFrame   = VOS_TRUE;
+            pMsg->frameType       = frameType;
+            pMsg->matchLen        = matchLen;
+            palCopyMemory( pMac, pMsg->matchData, matchData, matchLen); 
+            status = palSendMBMessage(pMac->hHdd, pMsg);
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    return status;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_DeregisterMgtFrame
+
+    \brief To De-register managment frame of specified type and subtype. 
+    \param frameType - type of the frame that needs to be passed to HDD.
+    \param matchData - data which needs to be matched before passing frame 
+                       to HDD. 
+    \param matchDataLen - Length of matched data.
+    \return eHalStatus 
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_DeregisterMgmtFrame(tHalHandle hHal, tANI_U8 sessionId, 
+                     tANI_U16 frameType, tANI_U8* matchData, tANI_U16 matchLen)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        tSirRegisterMgmtFrame *pMsg;
+        tANI_U16 len;
+        tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+        
+        if( !pSession->sessionActive ) 
+        {
+            VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                        "%s Invalid Sessionid", __FUNCTION__);
+            sme_ReleaseGlobalLock( &pMac->sme );
+            return eHAL_STATUS_FAILURE;
+        }
+
+        len = sizeof(tSirRegisterMgmtFrame) + matchLen;
+        
+        status = palAllocateMemory(pMac->hHdd, (void**)&pMsg, len );
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pMsg, len);
+            pMsg->messageType     = eWNI_SME_REGISTER_MGMT_FRAME_REQ;
+            pMsg->length          = len; 
+            pMsg->registerFrame   = VOS_FALSE;
+            pMsg->frameType       = frameType;
+            pMsg->matchLen        = matchLen;
+            palCopyMemory( pMac, pMsg->matchData, matchData, matchLen); 
+            status = palSendMBMessage(pMac->hHdd, pMsg);
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    return status;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_RemainOnChannel
+    \brief  API to request remain on channel for 'x' duration. used in p2p in listen state
+    \param  hHal - The handle returned by macOpen.
+    \param  pRequest -  channel
+    \param  duration - duration in ms
+    \param callback - HDD registered callback to process reaminOnChannelRsp
+    \param context - HDD Callback param
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+
+eHalStatus sme_RemainOnChannel(tHalHandle hHal, tANI_U8 sessionId,
+                               tANI_U8 channel, tANI_U32 duration,
+                               remainOnChanCallback callback, 
+                               void *pContext)
+{
+  eHalStatus status = eHAL_STATUS_SUCCESS;
+  tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+  if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+  {
+    status = p2pRemainOnChannel (hHal, sessionId, channel, duration, callback, pContext
+#ifdef WLAN_FEATURE_P2P_INTERNAL
+                                , eP2PRemainOnChnReasonUnknown
+#endif
+                                );
+    sme_ReleaseGlobalLock( &pMac->sme );
+  }
+  return(status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_ReportProbeReq
+    \brief  API to enable/disable forwarding of probeReq to apps in p2p.
+    \param  hHal - The handle returned by macOpen.
+    \param  falg: to set the Probe request forarding to wpa_supplicant in listen state in p2p
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+
+#ifndef WLAN_FEATURE_CONCURRENT_P2P
+eHalStatus sme_ReportProbeReq(tHalHandle hHal, tANI_U8 flag)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    do
+    {
+        //acquire the lock for the sme object
+        status = sme_AcquireGlobalLock(&pMac->sme);
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            /* call set in context */
+            pMac->p2pContext.probeReqForwarding = flag;
+            //release the lock for the sme object
+            sme_ReleaseGlobalLock( &pMac->sme );
+        }
+    } while(0);
+
+    smsLog(pMac, LOGW, "exiting function %s\n", __FUNCTION__);
+
+    return(status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_updateP2pIe
+    \brief  API to set the P2p Ie in p2p context
+    \param  hHal - The handle returned by macOpen.
+    \param  p2pIe -  Ptr to p2pIe from HDD.
+    \param p2pIeLength: length of p2pIe
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+
+eHalStatus sme_updateP2pIe(tHalHandle hHal, void *p2pIe, tANI_U32 p2pIeLength)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    //acquire the lock for the sme object
+    status = sme_AcquireGlobalLock(&pMac->sme);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        if(NULL != pMac->p2pContext.probeRspIe){
+            vos_mem_free(pMac->p2pContext.probeRspIe);
+            pMac->p2pContext.probeRspIeLength = 0;
+        }
+
+        pMac->p2pContext.probeRspIe = vos_mem_malloc(p2pIeLength);
+        if (NULL == pMac->p2pContext.probeRspIe)
+        {
+            smsLog(pMac, LOGE, "%s: Unable to allocate P2P IE", __FUNCTION__);
+            pMac->p2pContext.probeRspIeLength = 0;
+            status = eHAL_STATUS_FAILURE;
+        }
+        else
+        {
+            pMac->p2pContext.probeRspIeLength = p2pIeLength;
+
+            sirDumpBuf( pMac, SIR_LIM_MODULE_ID, LOG2,
+                        pMac->p2pContext.probeRspIe,
+                        pMac->p2pContext.probeRspIeLength ); 
+            vos_mem_copy((tANI_U8 *)pMac->p2pContext.probeRspIe, p2pIe,
+                         p2pIeLength);
+        }
+
+        //release the lock for the sme object
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+   
+    smsLog(pMac, LOG2, "exiting function %s\n", __FUNCTION__);
+
+    return(status);
+}
+#endif
+
+/* ---------------------------------------------------------------------------
+    \fn sme_sendAction
+    \brief  API to send action frame from supplicant.
+    \param  hHal - The handle returned by macOpen.
+    \return eHalStatus
+  ---------------------------------------------------------------------------*/
+
+eHalStatus sme_sendAction(tHalHandle hHal, tANI_U8 sessionId,
+                          const tANI_U8 *pBuf, tANI_U32 len)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+    //acquire the lock for the sme object
+    status = sme_AcquireGlobalLock(&pMac->sme);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        p2pSendAction(hHal, sessionId, pBuf, len);
+        //release the lock for the sme object
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    smsLog(pMac, LOGW, "exiting function %s\n", __FUNCTION__);
+
+    return(status);
+}
+
+eHalStatus sme_CancelRemainOnChannel(tHalHandle hHal, tANI_U8 sessionId )
+{
+  eHalStatus status = eHAL_STATUS_SUCCESS;
+  tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+  if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+  {
+    status = p2pCancelRemainOnChannel (hHal, sessionId);
+    sme_ReleaseGlobalLock( &pMac->sme );
+  }
+  return(status);
+}
+
+//Power Save Related
+eHalStatus sme_p2pSetPs(tHalHandle hHal, tP2pPsConfig * data)
+{
+  eHalStatus status = eHAL_STATUS_SUCCESS;
+  tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+
+  if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+  {
+    status = p2pSetPs (hHal, data);
+    sme_ReleaseGlobalLock( &pMac->sme );
+  }
+  return(status);
+}
+
+#endif
+
+/* ---------------------------------------------------------------------------
+
+  \fn    sme_ConfigureRxpFilter
+
+  \brief 
+    SME will pass this request to lower mac to set/reset the filter on RXP for
+    multicast & broadcast traffic.
+
+  \param 
+
+    hHal - The handle returned by macOpen. 
+ 
+    filterMask- Currently the API takes a 1 or 0 (set or reset) as filter.
+    Basically to enable/disable the filter (to filter "all" mcbc traffic) based
+    on this param. In future we can use this as a mask to set various types of
+    filters as suggested below:
+    FILTER_ALL_MULTICAST:
+    FILTER_ALL_BROADCAST:
+    FILTER_ALL_MULTICAST_BROADCAST:
+
+   
+  \return eHalStatus    
+  
+  
+--------------------------------------------------------------------------- */
+eHalStatus sme_ConfigureRxpFilter( tHalHandle hHal, 
+                            tpSirWlanSetRxpFilters  wlanRxpFilterParam)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    vos_msg_t       vosMessage;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        /* serialize the req through MC thread */
+        vosMessage.bodyptr = wlanRxpFilterParam;
+        vosMessage.type         = WDA_CFG_RXP_FILTER_REQ;
+        vosStatus = vos_mq_post_message( VOS_MQ_ID_WDA, &vosMessage );
+        if ( !VOS_IS_STATUS_SUCCESS(vosStatus) )
+        {
+           status = eHAL_STATUS_FAILURE;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    return(status);
+}
+
+#ifdef FEATURE_WLAN_INTEGRATED_SOC
+/* ---------------------------------------------------------------------------
+
+  \fn    sme_ConfigureSuspendInd
+
+  \brief 
+    SME will pass this request to lower mac to Indicate that the wlan needs to 
+    be suspended
+
+  \param 
+
+    hHal - The handle returned by macOpen. 
+ 
+    wlanSuspendParam- Depicts the wlan suspend params
+
+   
+  \return eHalStatus    
+  
+  
+--------------------------------------------------------------------------- */
+eHalStatus sme_ConfigureSuspendInd( tHalHandle hHal, 
+                          tpSirWlanSuspendParam  wlanSuspendParam)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    vos_msg_t       vosMessage;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        /* serialize the req through MC thread */
+        vosMessage.bodyptr = wlanSuspendParam;
+        vosMessage.type    = WDA_WLAN_SUSPEND_IND;
+        vosStatus = vos_mq_post_message( VOS_MQ_ID_WDA, &vosMessage );
+        if ( !VOS_IS_STATUS_SUCCESS(vosStatus) )
+        {
+           status = eHAL_STATUS_FAILURE;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    return(status);
+}
+
+/* ---------------------------------------------------------------------------
+
+  \fn    sme_ConfigureResumeReq
+
+  \brief 
+    SME will pass this request to lower mac to Indicate that the wlan needs to 
+    be Resumed
+
+  \param 
+
+    hHal - The handle returned by macOpen. 
+ 
+    wlanResumeParam- Depicts the wlan resume params
+
+   
+  \return eHalStatus    
+  
+  
+--------------------------------------------------------------------------- */
+eHalStatus sme_ConfigureResumeReq( tHalHandle hHal, 
+                             tpSirWlanResumeParam  wlanResumeParam)
+{
+    eHalStatus status = eHAL_STATUS_SUCCESS;
+    VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    vos_msg_t       vosMessage;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        /* serialize the req through MC thread */
+        vosMessage.bodyptr = wlanResumeParam;
+        vosMessage.type    = WDA_WLAN_RESUME_REQ;
+        vosStatus = vos_mq_post_message( VOS_MQ_ID_WDA, &vosMessage );
+        if ( !VOS_IS_STATUS_SUCCESS(vosStatus) )
+        {
+           status = eHAL_STATUS_FAILURE;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    return(status);
+}
+
+#endif
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetInfraSessionId
+
+    \brief To get the session ID for infra session, if connected
+    This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+
+    \return sessionid, -1 if infra session is not connected
+
+  -------------------------------------------------------------------------------*/
+tANI_S8 sme_GetInfraSessionId(tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tANI_S8 sessionid = -1;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+                   
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+
+      sessionid = csrGetInfraSessionId( pMac);
+
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (sessionid);
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_GetInfraOperationChannel
+
+    \brief To get the operating channel for infra session, if connected
+    This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+    \param sessionId - the sessionId returned by sme_OpenSession.
+
+    \return operating channel, 0 if infra session is not connected
+
+  -------------------------------------------------------------------------------*/
+tANI_U8 sme_GetInfraOperationChannel( tHalHandle hHal, tANI_U8 sessionId)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   tANI_U8 channel = 0;
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+
+      channel = csrGetInfraOperationChannel( pMac, sessionId);
+
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (channel);
+}
+
+//This routine will return poerating channel on which other BSS is operating to be used for concurrency mode.
+//If other BSS is not up or not connected it will return 0 
+tANI_U8 sme_GetConcurrentOperationChannel( tHalHandle hHal )
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );   
+   tANI_U8 channel = 0;
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+
+      channel = csrGetConcurrentOperationChannel( pMac );
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH, "%s: "
+           " Other Concurrent Channel = %d", __FUNCTION__,channel);
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (channel);
+}
+
+#ifdef FEATURE_WLAN_SCAN_PNO
+/******************************************************************************
+*
+* Name: sme_PreferredNetworkFoundInd
+*
+* Description:
+*    Invoke Preferred Network Found Indication 
+*
+* Parameters:
+*    hHal - HAL handle for device
+*    pMsg - found network description
+*
+* Returns: eHalStatus
+*
+******************************************************************************/
+eHalStatus sme_PreferredNetworkFoundInd (tHalHandle hHal, void* pMsg)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tSirPrefNetworkFoundInd *pPrefNetworkFoundInd = (tSirPrefNetworkFoundInd *)pMsg;
+
+   if (NULL == pMsg)
+   {
+      smsLog(pMac, LOGE, "in %s msg ptr is NULL\n", __FUNCTION__);
+      status = eHAL_STATUS_FAILURE;
+   }
+   else
+   {
+      if (pPrefNetworkFoundInd->ssId.length > 0)
+      {
+          smsLog(pMac, LOG1, "Preferred Network Found Indication in %s(), SSID=%s", 
+                 __FUNCTION__, pPrefNetworkFoundInd->ssId.ssId);
+
+
+         /* Call Preferred Netowrk Found Indication callback routine. */
+         if (pMac->pmc.prefNetwFoundCB != NULL)
+         {    
+               pMac->pmc.prefNetwFoundCB(pMac->pmc.preferredNetworkFoundIndCallbackContext, pPrefNetworkFoundInd);
+         }
+
+      }
+      else
+      {
+         smsLog(pMac, LOGE, "%s: callback failed - SSID is NULL\n", __FUNCTION__);
+         status = eHAL_STATUS_FAILURE;
+      }
+   }
+
+
+   return(status);
+}
+
+#endif // FEATURE_WLAN_SCAN_PNO
+
+
+eHalStatus sme_GetCfgValidChannels(tHalHandle hHal, tANI_U8 *aValidChannels, tANI_U32 *len)
+{
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+           
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if ( HAL_STATUS_SUCCESS( status ) )
+    {
+        status = csrGetCfgValidChannels(pMac, aValidChannels, len);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    
+    return (status);
+}
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_SetTxPerTracking
+
+    \brief Set Tx PER tracking configuration parameters
+
+    \param hHal - The handle returned by macOpen.
+    \param pTxPerTrackingConf - Tx PER configuration parameters
+
+    \return eHalStatus
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_SetTxPerTracking(tHalHandle hHal, 
+                                void (*pCallbackfn) (void *pCallbackContext), 
+                                void *pCallbackContext,
+                                tpSirTxPerTrackingParam pTxPerTrackingParam)
+{
+    vos_msg_t msg;
+    tpSirTxPerTrackingParam pTxPerTrackingParamReq = NULL;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    if ( eHAL_STATUS_SUCCESS == sme_AcquireGlobalLock( &pMac->sme ) )
+    {
+        pMac->sme.pTxPerHitCallback = pCallbackfn;
+        pMac->sme.pTxPerHitCbContext = pCallbackContext;
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    
+    // free this memory in failure case or WDA request callback function
+    pTxPerTrackingParamReq = vos_mem_malloc(sizeof(tSirTxPerTrackingParam));
+    if (NULL == pTxPerTrackingParamReq)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate memory for tSirTxPerTrackingParam", __FUNCTION__);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    vos_mem_copy(pTxPerTrackingParamReq, (void*)pTxPerTrackingParam, sizeof(tSirTxPerTrackingParam));
+    msg.type = WDA_SET_TX_PER_TRACKING_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pTxPerTrackingParamReq;
+
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post WDA_SET_TX_PER_TRACKING_REQ message to WDA", __FUNCTION__);
+        vos_mem_free(pTxPerTrackingParamReq);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_HandleChangeCountryCode
+
+    \brief Change Country code, Reg Domain and channel list
+
+    \details Country Code Priority
+    0 = 11D > Configured Country > NV
+    1 = Configured Country > 11D > NV
+    If Supplicant country code is priority than 11d is disabled.
+    If 11D is enabled, we update the country code after every scan.
+    Hence when Supplicant country code is priority, we don't need 11D info.
+    Country code from Supplicant is set as current courtry code.
+    User can send reset command XX (instead of country code) to reset the
+    country code to default values which is read from NV.
+    In case of reset, 11D is enabled and default NV code is Set as current country code
+    If 11D is priority,
+    Than Supplicant country code code is set to default code. But 11D code is set as current country code
+
+    \param pMac - The handle returned by macOpen.
+    \param pMsgBuf - MSG Buffer
+
+    \return eHalStatus
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_HandleChangeCountryCode(tpAniSirGlobal pMac,  void *pMsgBuf)
+{
+   eHalStatus  status = eHAL_STATUS_SUCCESS;
+   tAniChangeCountryCodeReq *pMsg;
+   v_REGDOMAIN_t domainIdIoctl; 
+   VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
+   static uNvTables nvTables;
+   pMsg = (tAniChangeCountryCodeReq *)pMsgBuf;
+
+
+   /* if the reset Supplicant country code command is triggered, enable 11D, reset the NV country code and return */
+   if( VOS_TRUE == vos_mem_compare(pMsg->countryCode, SME_INVALID_COUNTRY_CODE, 2) )
+   {
+       pMac->roam.configParam.Is11dSupportEnabled = pMac->roam.configParam.Is11dSupportEnabledOriginal;
+
+       vosStatus = vos_nv_readDefaultCountryTable( &nvTables );
+
+       /* read the country code from NV and use it */
+       if ( VOS_IS_STATUS_SUCCESS(vosStatus) )
+       {
+           palCopyMemory( pMac->hHdd, pMsg->countryCode , nvTables.defaultCountryTable.countryCode, WNI_CFG_COUNTRY_CODE_LEN );
+       }
+       else
+       {
+           status = eHAL_STATUS_FAILURE;
+           return status;
+       }
+   }
+   else
+   {
+       /* if Supplicant country code has priority, disable 11d */
+       if(pMac->roam.configParam.fSupplicantCountryCodeHasPriority)
+       {
+           pMac->roam.configParam.Is11dSupportEnabled = eANI_BOOLEAN_FALSE;
+       }
+   }
+
+   /* WEXT set country code means
+    * 11D should be supported?
+    * 11D Channel should be enforced?
+    * 11D Country code should be matched?
+    * 11D Reg Domian should be matched?
+    * Country string changed */
+   if(pMac->roam.configParam.Is11dSupportEnabled &&
+      pMac->roam.configParam.fEnforce11dChannels &&
+      pMac->roam.configParam.fEnforceCountryCodeMatch &&
+      pMac->roam.configParam.fEnforceDefaultDomain &&
+      !csrSave11dCountryString(pMac, pMsg->countryCode, eANI_BOOLEAN_TRUE))
+   {
+      /* All 11D related options are already enabled
+       * Country string is not changed
+       * Do not need do anything for country code change request */
+      return eHAL_STATUS_SUCCESS;
+   }
+
+   /* Set Current Country code and Current Regulatory domain */
+   status = csrSetCountryCode(pMac, pMsg->countryCode, NULL);
+   if(eHAL_STATUS_SUCCESS != status)
+   {
+       /* Supplicant country code failed. So give 11D priority */
+       pMac->roam.configParam.Is11dSupportEnabled = pMac->roam.configParam.Is11dSupportEnabledOriginal;
+       smsLog(pMac, LOGE, "Set Country Code Fail %d", status);
+       return status;  
+   }
+
+   /* purge current scan results
+    if i don't do this than I still get old ap's (of different country code) as available (even if they are powered off). 
+    Looks like a bug in current scan sequence. 
+   */
+   csrScanFlushResult(pMac);
+
+   /* overwrite the defualt country code */
+   palCopyMemory(pMac->hHdd, pMac->scan.countryCodeDefault, pMac->scan.countryCodeCurrent, WNI_CFG_COUNTRY_CODE_LEN);
+
+   /* Get Domain ID from country code */
+   status = csrGetRegulatoryDomainForCountry( pMac, pMac->scan.countryCodeCurrent,(v_REGDOMAIN_t *) &domainIdIoctl );
+   if ( status != eHAL_STATUS_SUCCESS )
+   {
+       smsLog( pMac, LOGE, FL("  fail to get regId %d\n"), domainIdIoctl );
+       return status;
+   }
+
+   status = WDA_SetRegDomain(pMac, domainIdIoctl);
+
+   if ( status != eHAL_STATUS_SUCCESS )
+   {
+       smsLog( pMac, LOGE, FL("  fail to set regId %d\n"), domainIdIoctl );
+       return status;
+   }
+
+   /* set to default domain ID */
+   pMac->scan.domainIdDefault = pMac->scan.domainIdCurrent;
+
+   /* get the channels based on new cc */
+   status = csrInitGetChannels( pMac );
+
+   if ( status != eHAL_STATUS_SUCCESS )
+   {
+       smsLog( pMac, LOGE, FL("  fail to get Channels \n"));
+       return status;
+   }
+
+   /* reset info based on new cc, and we are done */
+   csrResetCountryInformation(pMac, eANI_BOOLEAN_TRUE);
+   if( pMsg->changeCCCallback )
+   {
+      ((tSmeChangeCountryCallback)(pMsg->changeCCCallback))((void *)pMsg->pDevContext);
+   }
+
+   return eHAL_STATUS_SUCCESS;
+}
+
+#ifdef WLAN_FEATURE_PACKET_FILTERING
+eHalStatus sme_8023MulticastList (tHalHandle hHal, tpSirRcvFltMcAddrList pMulticastAddrs)
+{
+    tpSirRcvFltMcAddrList   pRequestBuf;
+    vos_msg_t               msg;
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s: "
+               "ulMulticastAddrCnt=%d, multicastAddr[0]=%d", __FUNCTION__,
+               pMulticastAddrs->ulMulticastAddrCnt,
+               pMulticastAddrs->multicastAddr[0]);
+  
+    pRequestBuf = vos_mem_malloc(sizeof(tSirRcvFltMcAddrList));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to "
+            "allocate memory for 8023 Multicast List request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+    vos_mem_copy(pRequestBuf, pMulticastAddrs, sizeof(tSirRcvFltMcAddrList));
+
+    msg.type = WDA_8023_MULTICAST_LIST_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to "
+            "post WDA_8023_MULTICAST_LIST message to WDA", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+eHalStatus sme_ReceiveFilterSetFilter(tHalHandle hHal, tpSirRcvPktFilterCfgType pRcvPktFilterCfg)
+{
+    tpSirRcvPktFilterCfgType    pRequestBuf;
+    v_SINT_t                allocSize;
+    vos_msg_t               msg;
+    /*tpAniSirGlobal          pMac = PMAC_STRUCT(hHal);*/
+    v_U8_t   idx=0;
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s: filterType=%d, "
+               "filterId = %d", __FUNCTION__,
+               pRcvPktFilterCfg->filterType, pRcvPktFilterCfg->filterId);
+  
+    allocSize = sizeof(tSirRcvPktFilterCfgType) + 
+                      ((pRcvPktFilterCfg->numFieldParams - 1) * 
+                      sizeof(tSirRcvPktFilterFieldParams));
+    pRequestBuf = vos_mem_malloc(allocSize);
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to "
+            "allocate memory for Receive Filter Set Filter request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+    vos_mem_copy(pRequestBuf, pRcvPktFilterCfg, allocSize);
+
+    msg.type = WDA_RECEIVE_FILTER_SET_FILTER_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "Pkt Flt Req : "
+           "FT %d FID %d ", 
+           pRequestBuf->filterType, pRequestBuf->filterId);    
+
+    VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "Pkt Flt Req : "
+           "params %d CT %d", 
+           pRequestBuf->numFieldParams, pRequestBuf->coalesceTime);    
+
+    for (idx=0; idx<pRequestBuf->numFieldParams; idx++)
+    {
+
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+           "Proto %d Comp Flag %d \n",
+           pRequestBuf->paramsData[idx].protocolLayer,
+           pRequestBuf->paramsData[idx].cmpFlag);
+
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+           "Data Offset %d Data Len %d\n",
+           pRequestBuf->paramsData[idx].dataOffset,
+           pRequestBuf->paramsData[idx].dataLength);
+
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
+          "CData: %d:%d:%d:%d:%d:%d\n",
+           pRequestBuf->paramsData[idx].compareData[0],
+           pRequestBuf->paramsData[idx].compareData[1], 
+           pRequestBuf->paramsData[idx].compareData[2],
+           pRequestBuf->paramsData[idx].compareData[3],
+           pRequestBuf->paramsData[idx].compareData[4],
+           pRequestBuf->paramsData[idx].compareData[5]);
+
+      VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, 
+           "MData: %d:%d:%d:%d:%d:%d\n",
+           pRequestBuf->paramsData[idx].dataMask[0],
+           pRequestBuf->paramsData[idx].dataMask[1], 
+           pRequestBuf->paramsData[idx].dataMask[2],
+           pRequestBuf->paramsData[idx].dataMask[3],
+           pRequestBuf->paramsData[idx].dataMask[4],
+           pRequestBuf->paramsData[idx].dataMask[5]);
+
+    }
+
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post "
+            "WDA_RECEIVE_FILTER_SET_FILTER message to WDA", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+eHalStatus sme_GetFilterMatchCount(tHalHandle hHal, 
+                                   FilterMatchCountCallback callbackRoutine,
+                                   void *callbackContext )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status;
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "+%s", __FUNCTION__);
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme)))
+    {
+        pmcGetFilterMatchCount(hHal, callbackRoutine, callbackContext);
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "-%s", __FUNCTION__);
+
+    return (status);
+}
+
+eHalStatus sme_ReceiveFilterClearFilter(tHalHandle hHal, tpSirRcvFltPktClearParam pRcvFltPktClearParam)
+{
+    tpSirRcvFltPktClearParam pRequestBuf;
+    vos_msg_t               msg;
+
+    VOS_TRACE( VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s: filterId = %d", __FUNCTION__,
+               pRcvFltPktClearParam->filterId);
+  
+    pRequestBuf = vos_mem_malloc(sizeof(tSirRcvFltPktClearParam));
+    if (NULL == pRequestBuf)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+            "%s: Not able to allocate memory for Receive Filter "
+            "Clear Filter request", __FUNCTION__);
+        return eHAL_STATUS_FAILED_ALLOC;
+    }
+    vos_mem_copy(pRequestBuf, pRcvFltPktClearParam, sizeof(tSirRcvFltPktClearParam));
+
+    msg.type = WDA_RECEIVE_FILTER_CLEAR_FILTER_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pRequestBuf;
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post "
+            "WDA_RECEIVE_FILTER_CLEAR_FILTER message to WDA", __FUNCTION__);
+        vos_mem_free(pRequestBuf);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+#endif // WLAN_FEATURE_PACKET_FILTERING
+
+/* ---------------------------------------------------------------------------
+    \fn sme_PreChannelSwitchIndFullPowerCB
+    \brief  call back function for the PMC full power request because of pre 
+             channel switch.
+    \param callbackContext
+    \param status
+  ---------------------------------------------------------------------------*/
+void sme_PreChannelSwitchIndFullPowerCB(void *callbackContext, 
+                eHalStatus status)
+{
+    tpAniSirGlobal pMac = (tpAniSirGlobal)callbackContext;
+    tSirMbMsg *pMsg;
+    tANI_U16 msgLen;
+
+    msgLen = (tANI_U16)(sizeof( tSirMbMsg ));
+    status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+    if(HAL_STATUS_SUCCESS(status))
+    {
+        palZeroMemory(pMac->hHdd, (void *)pMsg, msgLen);
+        pMsg->type = pal_cpu_to_be16((tANI_U16)eWNI_SME_PRE_CHANNEL_SWITCH_FULL_POWER);
+        pMsg->msgLen = pal_cpu_to_be16(msgLen);
+        status = palSendMBMessage(pMac->hHdd, pMsg);
+    }                             
+
+    return;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_HandlePreChannelSwitchInd
+    \brief  Processes the indcation from PE for pre-channel switch.
+    \param hHal
+    \- The handle returned by macOpen. return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_HandlePreChannelSwitchInd(tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcRequestFullPower(hHal, sme_PreChannelSwitchIndFullPowerCB, 
+                            pMac, eSME_FULL_PWR_NEEDED_BY_CHANNEL_SWITCH); 
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_HandlePostChannelSwitchInd
+    \brief  Processes the indcation from PE for post-channel switch.
+    \param hHal
+    \- The handle returned by macOpen. return eHalStatus
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_HandlePostChannelSwitchInd(tHalHandle hHal)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+       status = pmcRequestBmps(hHal, NULL, NULL);
+       sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (status);
+}
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_IsChannelValid
+
+    \brief To check if the channel is valid for currently established domain
+    This is a synchronous API.
+
+    \param hHal - The handle returned by macOpen.
+    \param channel - channel to verify
+
+    \return TRUE/FALSE, TRUE if channel is valid
+
+  -------------------------------------------------------------------------------*/
+tANI_BOOLEAN sme_IsChannelValid(tHalHandle hHal, tANI_U8 channel)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tANI_BOOLEAN valid = FALSE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+                   
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+
+      valid = csrRoamIsChannelValid( pMac, channel);
+
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+
+   return (valid);
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_SetFreqBand
+    \brief  Used to set frequency band.
+    \param  hHal
+    \eBand  band value to be configured
+    \- return eHalStatus
+    -------------------------------------------------------------------------*/
+eHalStatus sme_SetFreqBand(tHalHandle hHal, eCsrBand eBand)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      status = csrSetBand(hHal, eBand);
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+   return status;
+}
+
+/* ---------------------------------------------------------------------------
+    \fn sme_GetFreqBand
+    \brief  Used to get the current band settings.
+    \param  hHal
+    \pBand  pointer to hold band value
+    \- return eHalStatus
+    -------------------------------------------------------------------------*/
+eHalStatus sme_GetFreqBand(tHalHandle hHal, eCsrBand *pBand)
+{
+   eHalStatus status = eHAL_STATUS_FAILURE;
+   tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+   status = sme_AcquireGlobalLock( &pMac->sme );
+   if ( HAL_STATUS_SUCCESS( status ) )
+   {
+      *pBand = csrGetCurrentBand( hHal );
+      sme_ReleaseGlobalLock( &pMac->sme );
+   }
+   return status;
+}
+
+#ifdef WLAN_WAKEUP_EVENTS
+/******************************************************************************
+  \fn sme_WakeReasonIndCallback
+
+  \brief
+  a callback function called when SME received eWNI_SME_WAKE_REASON_IND event from WDA
+
+  \param hHal - HAL handle for device
+  \param pMsg - Message body passed from WDA; includes Wake Reason Indication parameter
+
+  \return eHalStatus  
+******************************************************************************/
+eHalStatus sme_WakeReasonIndCallback (tHalHandle hHal, void* pMsg)
+{
+   tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+   eHalStatus status = eHAL_STATUS_SUCCESS;
+   tSirWakeReasonInd *pWakeReasonInd = (tSirWakeReasonInd *)pMsg;
+
+   if (NULL == pMsg)
+   {
+      smsLog(pMac, LOGE, "in %s msg ptr is NULL\n", __FUNCTION__);
+      status = eHAL_STATUS_FAILURE;
+   }
+   else
+   {
+      smsLog(pMac, LOG2, "SME: entering sme_WakeReasonIndCallback\n");
+
+      /* Call Wake Reason Indication callback routine. */
+      if (pMac->pmc.wakeReasonIndCB != NULL)
+          pMac->pmc.wakeReasonIndCB(pMac->pmc.wakeReasonIndCBContext, pWakeReasonInd);
+        
+      pMac->pmc.wakeReasonIndCB = NULL;
+      pMac->pmc.wakeReasonIndCBContext = NULL;
+
+      smsLog(pMac, LOG1, "Wake Reason Indication in %s(), reason=%d", __FUNCTION__, pWakeReasonInd->ulReason);
+   }
+
+   return(status);
+}
+#endif // WLAN_WAKEUP_EVENTS
+
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_SetMaxTxPower
+
+    \brief Set the Maximum Transmit Power dynamically. Note: this setting will
+    not persist over reboots.
+
+    \param  hHal
+    \param pBssid  BSSID to set the power cap for
+    \param pBssid  pSelfMacAddress self MAC Address
+    \param pBssid  power to set in dB
+    \- return eHalStatus
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_SetMaxTxPower(tHalHandle hHal, tSirMacAddr pBssid, 
+                             tSirMacAddr pSelfMacAddress, v_S7_t dB)
+{
+    vos_msg_t msg;
+    tpMaxTxPowerParams pMaxTxParams = NULL;
+
+    pMaxTxParams = vos_mem_malloc(sizeof(tMaxTxPowerParams));
+    if (NULL == pMaxTxParams)
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to allocate memory for pMaxTxParams", __FUNCTION__);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    vos_mem_copy(pMaxTxParams->bssId, pBssid, SIR_MAC_ADDR_LENGTH);
+    vos_mem_copy(pMaxTxParams->selfStaMacAddr , pSelfMacAddress, 
+                 SIR_MAC_ADDR_LENGTH);
+    pMaxTxParams->power = dB;
+
+    msg.type = WDA_SET_MAX_TX_POWER_REQ;
+    msg.reserved = 0;
+    msg.bodyptr = pMaxTxParams;
+
+    if(VOS_STATUS_SUCCESS != vos_mq_post_message(VOS_MODULE_ID_WDA, &msg))
+    {
+        VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s: Not able to post WDA_SET_MAX_TX_POWER_REQ message to WDA", __FUNCTION__);
+        vos_mem_free(pMaxTxParams);
+        return eHAL_STATUS_FAILURE;
+    }
+
+    return eHAL_STATUS_SUCCESS;
+}
+
+#ifdef WLAN_SOFTAP_FEATURE
+/* ---------------------------------------------------------------------------
+
+    \fn sme_HideSSID
+
+    \brief hide/show SSID dynamically. Note: this setting will
+    not persist over reboots.
+
+    \param hHal
+    \param sessionId
+    \param ssidHidden 0 - Broadcast SSID, 1 - Disable broadcast SSID
+    \- return eHalStatus
+
+  -------------------------------------------------------------------------------*/
+eHalStatus sme_HideSSID(tHalHandle hHal, v_U8_t sessionId, v_U8_t ssidHidden)
+{
+    eHalStatus status   = eHAL_STATUS_SUCCESS;
+    tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
+    tANI_U16 len;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        tpSirUpdateParams pMsg;
+        tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId );
+        
+        if( !pSession->sessionActive ) 
+            VOS_ASSERT(0);
+
+        /* Create the message and send to lim */
+        len = sizeof(tSirUpdateParams); 
+        status = palAllocateMemory( pMac->hHdd, (void **)&pMsg, len );
+        if(HAL_STATUS_SUCCESS(status))
+        {
+            palZeroMemory(pMac->hHdd, pMsg, sizeof(tSirUpdateParams) );
+            pMsg->messageType     = eWNI_SME_HIDE_SSID_REQ;
+            pMsg->length          = len;
+            /* Data starts from here */
+            pMsg->sessionId       = sessionId;
+            pMsg->ssidHidden      = ssidHidden; 
+            status = palSendMBMessage(pMac->hHdd, pMsg);
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+   return status;
+}
+#endif
+
+/* ---------------------------------------------------------------------------
+
+    \fn sme_SetTmLevel
+    \brief  Set Thermal Mitigation Level to RIVA
+    \param  hHal - The handle returned by macOpen.
+    \param  newTMLevel - new Thermal Mitigation Level
+    \param  tmMode - Thermal Mitigation handle mode, default 0
+    \return eHalStatus     
+  ---------------------------------------------------------------------------*/
+eHalStatus sme_SetTmLevel(tHalHandle hHal, v_U16_t newTMLevel, v_U16_t tmMode)
+{
+    eHalStatus          status    = eHAL_STATUS_SUCCESS;
+    VOS_STATUS          vosStatus = VOS_STATUS_SUCCESS;
+    tpAniSirGlobal      pMac      = PMAC_STRUCT(hHal);
+    vos_msg_t           vosMessage;
+    tAniSetTmLevelReq  *setTmLevelReq = NULL;
+
+    if ( eHAL_STATUS_SUCCESS == ( status = sme_AcquireGlobalLock( &pMac->sme ) ) )
+    {
+        setTmLevelReq = (tAniSetTmLevelReq *)vos_mem_malloc(sizeof(tAniSetTmLevelReq));
+        if(NULL == setTmLevelReq)
+        {
+           VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                     "%s: Not able to allocate memory for sme_SetTmLevel", __FUNCTION__);
+           return eHAL_STATUS_FAILURE;
+        }
+
+        setTmLevelReq->tmMode     = tmMode;
+        setTmLevelReq->newTmLevel = newTMLevel;
+
+        /* serialize the req through MC thread */
+        vosMessage.bodyptr = setTmLevelReq;
+        vosMessage.type    = WDA_SET_TM_LEVEL_REQ;
+        vosStatus = vos_mq_post_message( VOS_MQ_ID_WDA, &vosMessage );
+        if ( !VOS_IS_STATUS_SUCCESS(vosStatus) )
+        {
+           VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
+                     "%s: Post Set TM Level MSG fail", __FUNCTION__);
+           vos_mem_free(setTmLevelReq);
+           status = eHAL_STATUS_FAILURE;
+        }
+        sme_ReleaseGlobalLock( &pMac->sme );
+    }
+    return(status);
+}
+
+/*---------------------------------------------------------------------------
+
+  \brief sme_featureCapsExchange() - SME interface to exchange capabilities between
+  Host and FW.
+
+  \param  hHal - HAL handle for device
+
+  \return NONE
+
+---------------------------------------------------------------------------*/
+void sme_featureCapsExchange( tHalHandle hHal)
+{
+    v_CONTEXT_t vosContext = vos_get_global_context(VOS_MODULE_ID_SME, NULL);
+    WDA_featureCapsExchange(vosContext);
+}
diff --git a/CORE/SME/src/sme_common/sme_FTApi.c b/CORE/SME/src/sme_common/sme_FTApi.c
new file mode 100644
index 0000000..ce76b7e
--- /dev/null
+++ b/CORE/SME/src/sme_common/sme_FTApi.c
@@ -0,0 +1,486 @@
+/*
+ * Copyright (c) 2012, Code Aurora Forum. 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.
+ */
+
+#ifdef WLAN_FEATURE_VOWIFI_11R
+/**=========================================================================
+
+  \brief Definitions for SME FT APIs
+
+   Copyright 2008 (c) Qualcomm, Incorporated.  All Rights Reserved.
+
+   Qualcomm Confidential and Proprietary.
+
+  ========================================================================*/
+
+/*--------------------------------------------------------------------------
+  Include Files
+  ------------------------------------------------------------------------*/
+#include <smsDebug.h>
+#include <csrInsideApi.h>
+#include <csrNeighborRoam.h>
+
+/*--------------------------------------------------------------------------
+  Initialize the FT context. 
+  ------------------------------------------------------------------------*/
+void sme_FTOpen(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus     status = eHAL_STATUS_SUCCESS;
+
+    pMac->ft.ftSmeContext.auth_ft_ies = NULL;                        
+    pMac->ft.ftSmeContext.auth_ft_ies_length = 0;                        
+
+    pMac->ft.ftSmeContext.reassoc_ft_ies = NULL;                        
+    pMac->ft.ftSmeContext.reassoc_ft_ies_length = 0;       
+
+    status = palTimerAlloc(pMac->hHdd, &pMac->ft.ftSmeContext.preAuthReassocIntvlTimer, 
+                            sme_PreauthReassocIntvlTimerCallback, (void *)pMac);
+
+    if (eHAL_STATUS_SUCCESS != status)
+    {
+        smsLog(pMac, LOGE, FL("Preauth Reassoc interval Timer allocation failed"));
+        return;
+    }                 
+
+    pMac->ft.ftSmeContext.psavedFTPreAuthRsp = NULL;                        
+
+    pMac->ft.ftSmeContext.FTState = eFT_START_READY;
+}
+
+/*--------------------------------------------------------------------------
+  Cleanup the SME FT Global context. 
+  ------------------------------------------------------------------------*/
+void sme_FTClose(tHalHandle hHal)
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+
+    if (pMac->ft.ftSmeContext.auth_ft_ies != NULL)
+    {
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+        smsLog( pMac, LOGE, FL(" Freeing %p and setting to NULL\n"), 
+            pMac->ft.ftSmeContext.auth_ft_ies);
+#endif
+        vos_mem_free(pMac->ft.ftSmeContext.auth_ft_ies);
+        pMac->ft.ftSmeContext.auth_ft_ies = NULL;
+    }
+    pMac->ft.ftSmeContext.auth_ft_ies_length = 0;                        
+
+    if (pMac->ft.ftSmeContext.reassoc_ft_ies != NULL)
+    {
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+        smsLog( pMac, LOGE, FL(" Freeing %p and setting to NULL\n"), 
+            pMac->ft.ftSmeContext.reassoc_ft_ies);
+#endif
+        vos_mem_free(pMac->ft.ftSmeContext.reassoc_ft_ies);
+        pMac->ft.ftSmeContext.reassoc_ft_ies = NULL;                        
+    }
+    pMac->ft.ftSmeContext.reassoc_ft_ies_length = 0;                        
+
+    pMac->ft.ftSmeContext.FTState = eFT_START_READY;
+    vos_mem_zero(pMac->ft.ftSmeContext.preAuthbssId, ANI_MAC_ADDR_SIZE);
+
+    if (pMac->ft.ftSmeContext.psavedFTPreAuthRsp != NULL)
+    {
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+        smsLog( pMac, LOGE, FL("%s: Freeing %p and setting to NULL\n"), 
+            pMac->ft.ftSmeContext.psavedFTPreAuthRsp);
+#endif
+        vos_mem_free(pMac->ft.ftSmeContext.psavedFTPreAuthRsp);
+        pMac->ft.ftSmeContext.psavedFTPreAuthRsp = NULL;                        
+    }
+
+    palTimerFree(pMac->hHdd, pMac->ft.ftSmeContext.preAuthReassocIntvlTimer);
+}
+
+
+/*--------------------------------------------------------------------------
+  Each time the supplicant sends down the FT IEs to the driver.
+  This function is called in SME. This fucntion packages and sends
+  the FT IEs to PE.
+  ------------------------------------------------------------------------*/
+void sme_SetFTIEs( tHalHandle hHal, tANI_U8 sessionId, tANI_U8 *ft_ies, 
+        tANI_U16 ft_ies_length )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status = eHAL_STATUS_FAILURE;
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if (!( HAL_STATUS_SUCCESS( status ))) return;
+
+    if (ft_ies == NULL) 
+    {
+        smsLog( pMac, LOGE, FL(" ft ies is NULL\n"));
+        sme_ReleaseGlobalLock( &pMac->sme );
+        return; 
+    }
+
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+    smsLog( pMac, LOGE, "FT IEs Req is received in state %d\n", 
+        pMac->ft.ftSmeContext.FTState);
+#endif
+
+    // Global Station FT State
+    switch(pMac->ft.ftSmeContext.FTState)
+    {
+        case eFT_START_READY:
+        case eFT_AUTH_REQ_READY:
+            if ((pMac->ft.ftSmeContext.auth_ft_ies) && 
+                    (pMac->ft.ftSmeContext.auth_ft_ies_length))
+            {
+                // Free the one we received last from the supplicant
+                vos_mem_free(pMac->ft.ftSmeContext.auth_ft_ies);
+                pMac->ft.ftSmeContext.auth_ft_ies_length = 0; 
+            }
+
+            // Save the FT IEs
+            pMac->ft.ftSmeContext.auth_ft_ies = vos_mem_malloc(ft_ies_length);
+            if(pMac->ft.ftSmeContext.auth_ft_ies == NULL)
+            {
+               smsLog( pMac, LOGE, FL("Memory allocation failed for "
+                                      "auth_ft_ies\n"));
+               sme_ReleaseGlobalLock( &pMac->sme );
+               return;
+            }
+            pMac->ft.ftSmeContext.auth_ft_ies_length = ft_ies_length;
+            vos_mem_copy((tANI_U8 *)pMac->ft.ftSmeContext.auth_ft_ies, ft_ies,
+                ft_ies_length);
+                
+            pMac->ft.ftSmeContext.FTState = eFT_AUTH_REQ_READY;
+
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+            smsLog( pMac, LOGE, "ft_ies_length=%d\n", ft_ies_length);
+            /*
+            smsLog( pMac, LOGE, "%d: New Auth ft_ies_length=%02x%02x%02x\n", 
+                current->pid, pMac->ft.ftSmeContext.auth_ft_ies[0],
+                pMac->ft.ftSmeContext.auth_ft_ies[1],
+                pMac->ft.ftSmeContext.auth_ft_ies[2]);
+                */
+#endif
+            break;
+
+        case eFT_AUTH_COMPLETE:
+            // We will need to re-start preauth. If we received FT IEs in
+            // eFT_PRE_AUTH_DONE state, it implies there was a rekey in 
+            // our pre-auth state. Hence this implies we need Pre-auth again.
+
+            // OK now inform SME we have no pre-auth list.
+            // Delete the pre-auth node locally. Set your self back to restart pre-auth
+            // TBD
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+            smsLog( pMac, LOGE, 
+                "Pre-auth done and now receiving---> AUTH REQ <---- in state %d\n", 
+                pMac->ft.ftSmeContext.FTState);
+            smsLog( pMac, LOGE, "Unhandled reception of FT IES in state %d\n", 
+                pMac->ft.ftSmeContext.FTState);
+#endif
+            break;
+
+        case eFT_REASSOC_REQ_WAIT:
+            // We are done with pre-auth, hence now waiting for
+            // reassoc req. This is the new FT Roaming in place
+
+            // At this juncture we are ready to start sending Re-Assoc Req.
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+            smsLog( pMac, LOGE, "New Reassoc Req=%p in state %d\n", 
+                ft_ies, pMac->ft.ftSmeContext.FTState);
+#endif
+            if ((pMac->ft.ftSmeContext.reassoc_ft_ies) && 
+                (pMac->ft.ftSmeContext.reassoc_ft_ies_length))
+            {
+                // Free the one we received last from the supplicant
+                vos_mem_free(pMac->ft.ftSmeContext.reassoc_ft_ies);
+                pMac->ft.ftSmeContext.reassoc_ft_ies_length = 0; 
+            }
+
+            // Save the FT IEs
+            pMac->ft.ftSmeContext.reassoc_ft_ies = vos_mem_malloc(ft_ies_length);
+            if(pMac->ft.ftSmeContext.reassoc_ft_ies == NULL)
+            {
+               smsLog( pMac, LOGE, FL("Memory allocation failed for "
+                                      "reassoc_ft_ies\n"));
+               sme_ReleaseGlobalLock( &pMac->sme );
+               return;
+            }
+            pMac->ft.ftSmeContext.reassoc_ft_ies_length = ft_ies_length;
+            vos_mem_copy((tANI_U8 *)pMac->ft.ftSmeContext.reassoc_ft_ies, ft_ies,
+                ft_ies_length);
+                
+            pMac->ft.ftSmeContext.FTState = eFT_SET_KEY_WAIT;
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+            smsLog( pMac, LOGE, "ft_ies_length=%d state=%d\n", ft_ies_length,
+                pMac->ft.ftSmeContext.FTState);
+            /*
+            smsLog( pMac, LOGE, "%d: New Auth ft_ies_length=%02x%02x%02x\n", 
+                current->pid, pMac->ft.ftSmeContext.reassoc_ft_ies[0],
+                pMac->ft.ftSmeContext.reassoc_ft_ies[1],
+                pMac->ft.ftSmeContext.reassoc_ft_ies[2]);
+                */
+#endif
+            
+            break;
+
+        default:
+            smsLog( pMac, LOGE, FL(" Unhandled state=%d\n"),
+                pMac->ft.ftSmeContext.FTState);
+            break;
+    }
+    sme_ReleaseGlobalLock( &pMac->sme );
+}
+            
+eHalStatus sme_FTSendUpdateKeyInd(tHalHandle hHal, tCsrRoamSetKey * pFTKeyInfo)
+{
+    tSirFTUpdateKeyInfo *pMsg;
+    tANI_U16 msgLen;
+    eHalStatus status = eHAL_STATUS_FAILURE;
+    tAniEdType tmpEdType;
+    tAniKeyDirection tmpDirection;
+    //tANI_U8 *pBuf;
+    tANI_U8 *p = NULL;
+    tAniEdType edType;
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    int i = 0;
+
+    smsLog(pMac, LOGE, FL("keyLength %d\n"), pFTKeyInfo->keyLength);
+
+      for(i=0; i<pFTKeyInfo->keyLength; i++)
+          smsLog(pMac, LOGE, FL("%02x"), pFTKeyInfo->Key[i]); 
+
+    msgLen  = sizeof( tANI_U16) + sizeof( tANI_U16 ) + 
+       sizeof( pMsg->keyMaterial.length ) + sizeof( pMsg->keyMaterial.edType ) + 
+       sizeof( pMsg->keyMaterial.numKeys ) + sizeof( pMsg->keyMaterial.key );
+                     
+    status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
+    if ( !HAL_STATUS_SUCCESS(status) )
+    {
+       return eHAL_STATUS_FAILURE;
+    }
+
+    palZeroMemory(pMac->hHdd, pMsg, msgLen);
+    pMsg->messageType = pal_cpu_to_be16((tANI_U16)eWNI_SME_FT_UPDATE_KEY);
+    pMsg->length = pal_cpu_to_be16(msgLen);
+
+    p = (tANI_U8 *)&pMsg->keyMaterial;
+
+    // Set the pMsg->keyMaterial.length field (this length is defined as all data that follows the edType field
+    // in the tSirKeyMaterial keyMaterial; field).
+    //
+    // !!NOTE:  This keyMaterial.length contains the length of a MAX size key, though the keyLength can be 
+    // shorter than this max size.  Is LIM interpreting this ok ?
+    p = pal_set_U16( p, pal_cpu_to_be16((tANI_U16)( sizeof( pMsg->keyMaterial.numKeys ) + 
+                                                    ( pMsg->keyMaterial.numKeys * sizeof( pMsg->keyMaterial.key ) ) )) );
+
+    // set pMsg->keyMaterial.edType
+    edType = csrTranslateEncryptTypeToEdType( pFTKeyInfo->encType );
+    tmpEdType = pal_cpu_to_be32(edType);
+    palCopyMemory( pMac->hHdd, p, (tANI_U8 *)&tmpEdType, sizeof(tAniEdType) );
+    p += sizeof( pMsg->keyMaterial.edType );
+
+    // set the pMsg->keyMaterial.numKeys field
+    *p = pMsg->keyMaterial.numKeys;
+    p += sizeof( pMsg->keyMaterial.numKeys );   
+
+    // set pSirKey->keyId = keyId;
+    *p = pMsg->keyMaterial.key[ 0 ].keyId;
+    p += sizeof( pMsg->keyMaterial.key[ 0 ].keyId );
+
+    // set pSirKey->unicast = (tANI_U8)fUnicast;
+    *p = (tANI_U8)eANI_BOOLEAN_TRUE;
+    p += sizeof( pMsg->keyMaterial.key[ 0 ].unicast );
+
+    // set pSirKey->keyDirection = aniKeyDirection;
+    tmpDirection = pal_cpu_to_be32(pFTKeyInfo->keyDirection);
+    palCopyMemory( pMac->hHdd, p, (tANI_U8 *)&tmpDirection, sizeof(tAniKeyDirection) );
+    p += sizeof(tAniKeyDirection);
+    //    pSirKey->keyRsc = ;;
+    palCopyMemory( pMac->hHdd, p, pFTKeyInfo->keyRsc, CSR_MAX_RSC_LEN );
+    p += sizeof( pMsg->keyMaterial.key[ 0 ].keyRsc );
+
+    // set pSirKey->paeRole
+    *p = pFTKeyInfo->paeRole;   // 0 is Supplicant
+    p++;
+
+    // set pSirKey->keyLength = keyLength;
+    p = pal_set_U16( p, pal_cpu_to_be16(pFTKeyInfo->keyLength) );
+
+    if ( pFTKeyInfo->keyLength && pFTKeyInfo->Key ) 
+    {   
+        palCopyMemory( pMac->hHdd, p, pFTKeyInfo->Key, pFTKeyInfo->keyLength ); 
+        if(pFTKeyInfo->keyLength == 16)
+        {
+            smsLog(pMac, LOGE, "  SME Set keyIdx (%d) encType(%d) key = %02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X\n",
+            pFTKeyInfo->keyId, edType, pFTKeyInfo->Key[0], pFTKeyInfo->Key[1], pFTKeyInfo->Key[2], pFTKeyInfo->Key[3], pFTKeyInfo->Key[4],
+            pFTKeyInfo->Key[5], pFTKeyInfo->Key[6], pFTKeyInfo->Key[7], pFTKeyInfo->Key[8],
+            pFTKeyInfo->Key[9], pFTKeyInfo->Key[10], pFTKeyInfo->Key[11], pFTKeyInfo->Key[12], pFTKeyInfo->Key[13], pFTKeyInfo->Key[14], pFTKeyInfo->Key[15]);
+        }
+    }
+
+    status = palSendMBMessage(pMac->hHdd, pMsg);
+
+    return( status );
+}
+
+eHalStatus sme_FTUpdateKey( tHalHandle hHal, tCsrRoamSetKey * pFTKeyInfo )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status = eHAL_STATUS_FAILURE;
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if (!( HAL_STATUS_SUCCESS( status )))
+    {
+       return eHAL_STATUS_FAILURE;
+    }
+
+    if (pFTKeyInfo == NULL) 
+    {
+        smsLog( pMac, LOGE, "%s: pFTKeyInfo is NULL\n", __FUNCTION__);
+        sme_ReleaseGlobalLock( &pMac->sme );
+        return eHAL_STATUS_FAILURE; 
+    }
+
+#if defined WLAN_FEATURE_VOWIFI_11R_DEBUG
+    smsLog( pMac, LOGE, "sme_FTUpdateKey is received in state %d\n", 
+        pMac->ft.ftSmeContext.FTState);
+#endif
+
+    // Global Station FT State
+    switch(pMac->ft.ftSmeContext.FTState)
+    {
+    case eFT_SET_KEY_WAIT:
+       status = sme_FTSendUpdateKeyInd( hHal, pFTKeyInfo );
+       pMac->ft.ftSmeContext.FTState = eFT_START_READY;
+       break;
+          
+    default:
+       smsLog( pMac, LOGE, "%s: Unhandled state=%d\n", __FUNCTION__,
+               pMac->ft.ftSmeContext.FTState);
+       status = eHAL_STATUS_FAILURE;
+       break;
+    }
+    sme_ReleaseGlobalLock( &pMac->sme );
+
+    return status;
+}
+/*--------------------------------------------------------------------------
+ *
+ * HDD Interface to SME. SME now sends the Auth 2 and RIC IEs up to the supplicant.
+ * The supplicant will then proceed to send down the
+ * Reassoc Req.
+ *
+ *------------------------------------------------------------------------*/
+void sme_GetFTPreAuthResponse( tHalHandle hHal, tANI_U8 *ft_ies, 
+                               tANI_U32 ft_ies_ip_len, tANI_U16 *ft_ies_length )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status = eHAL_STATUS_FAILURE;
+
+    *ft_ies_length = 0;
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if (!( HAL_STATUS_SUCCESS( status ))) 
+       return;
+
+    /* All or nothing - proceed only if both BSSID and FT IE fit */
+    if((ANI_MAC_ADDR_SIZE + 
+       pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ft_ies_length) > ft_ies_ip_len) 
+    {
+       sme_ReleaseGlobalLock( &pMac->sme );
+       return;
+    }
+
+    // hdd needs to pack the bssid also along with the 
+    // auth response to supplicant
+    vos_mem_copy(ft_ies, pMac->ft.ftSmeContext.preAuthbssId, ANI_MAC_ADDR_SIZE);
+    
+    // Copy the auth resp FTIEs
+    vos_mem_copy(&(ft_ies[ANI_MAC_ADDR_SIZE]), 
+                 pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ft_ies, 
+                 pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ft_ies_length);
+
+    *ft_ies_length = ANI_MAC_ADDR_SIZE + 
+       pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ft_ies_length;
+
+    pMac->ft.ftSmeContext.FTState = eFT_REASSOC_REQ_WAIT;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R_DEBUG
+    smsLog( pMac, LOGE, FL(" Filled auth resp = %d\n"), *ft_ies_length);
+#endif
+    sme_ReleaseGlobalLock( &pMac->sme );
+    return;
+}
+
+/*--------------------------------------------------------------------------
+ *
+ * SME now sends the RIC IEs up to the supplicant.
+ * The supplicant will then proceed to send down the
+ * Reassoc Req.
+ *
+ *------------------------------------------------------------------------*/
+void sme_GetRICIEs( tHalHandle hHal, tANI_U8 *ric_ies, tANI_U32 ric_ies_ip_len,
+                    tANI_U32 *ric_ies_length )
+{
+    tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
+    eHalStatus status = eHAL_STATUS_FAILURE;
+
+    *ric_ies_length = 0;
+
+    status = sme_AcquireGlobalLock( &pMac->sme );
+    if (!( HAL_STATUS_SUCCESS( status ))) 
+       return;
+
+    /* All or nothing */
+    if (pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ric_ies_length > 
+        ric_ies_ip_len)
+    {
+       sme_ReleaseGlobalLock( &pMac->sme );
+       return;
+    }
+
+    vos_mem_copy(ric_ies, pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ric_ies, 
+                 pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ric_ies_length);
+
+    *ric_ies_length = pMac->ft.ftSmeContext.psavedFTPreAuthRsp->ric_ies_length;
+
+#ifdef WLAN_FEATURE_VOWIFI_11R_DEBUG
+    smsLog( pMac, LOGE, FL(" Filled ric ies = %d\n"), *ric_ies_length);
+#endif
+
+    sme_ReleaseGlobalLock( &pMac->sme );
+    return;
+}
+
+/*--------------------------------------------------------------------------
+ *
+ * Timer callback for the timer that is started between the preauth completion and 
+ * reassoc request to the PE. In this interval, it is expected that the pre-auth response 
+ * and RIC IEs are passed up to the WPA supplicant and received back the necessary FTIEs 
+ * required to be sent in the reassoc request
+ *
+ *------------------------------------------------------------------------*/
+void sme_PreauthReassocIntvlTimerCallback(void *context)
+{
+#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
+    tpAniSirGlobal pMac = (tpAniSirGlobal )context;
+    csrNeighborRoamRequestHandoff(pMac);
+#endif
+    return;
+}
+/* End of File */
+#endif /* WLAN_FEATURE_VOWIFI_11R */