blob: 50fd9ee34491852f67e7dd48cb14b9cea94acafe [file] [log] [blame]
Jeff Johnson295189b2012-06-20 16:38:30 -07001/*
Kiet Lam0fb93dd2014-02-19 00:32:59 -08002 * Copyright (c) 2012-2014 The Linux Foundation. All rights reserved.
3 *
4 * Previously licensed under the ISC license by Qualcomm Atheros, Inc.
5 *
6 *
7 * Permission to use, copy, modify, and/or distribute this software for
8 * any purpose with or without fee is hereby granted, provided that the
9 * above copyright notice and this permission notice appear in all
10 * copies.
11 *
12 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
13 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
14 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
15 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
16 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
17 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
18 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
19 * PERFORMANCE OF THIS SOFTWARE.
Gopichand Nakkala92f07d82013-01-08 21:16:34 -080020 */
Kiet Lam0fb93dd2014-02-19 00:32:59 -080021
22/*
23 * This file was originally distributed by Qualcomm Atheros, Inc.
24 * under proprietary terms before Copyright ownership was assigned
25 * to the Linux Foundation.
26 */
27
Jeff Johnson295189b2012-06-20 16:38:30 -070028/**=========================================================================
29
30 \file sme_Rrm.c
31
32 \brief implementation for SME RRM APIs
33
Kiet Lamaa8e15a2014-02-11 23:30:06 -080034 Copyright 2008 (c) Qualcomm, Incorporated. All Rights Reserved.
35
36 Qualcomm Confidential and Proprietary.
37
Jeff Johnson295189b2012-06-20 16:38:30 -070038 ========================================================================*/
39
40/* $Header$ */
41
42#if defined WLAN_FEATURE_VOWIFI
43/*--------------------------------------------------------------------------
44 Include Files
45 ------------------------------------------------------------------------*/
Jeff Johnson295189b2012-06-20 16:38:30 -070046#include "aniGlobal.h"
47#include "smeInside.h"
48#include "sme_Api.h"
49#include "smsDebug.h"
50#include "cfgApi.h"
51
52#ifdef FEATURE_WLAN_DIAG_SUPPORT
53#include "vos_diag_core_event.h"
54#include "vos_diag_core_log.h"
55#endif /* FEATURE_WLAN_DIAG_SUPPORT */
56
57#include "csrInsideApi.h"
58
59#include "rrmGlobal.h"
60
Srinivas Girigowda5cecb202013-10-08 09:13:25 -070061#if defined(FEATURE_WLAN_CCX) && !defined(FEATURE_WLAN_CCX_UPLOAD)
Jeff Johnson295189b2012-06-20 16:38:30 -070062#include "csrCcx.h"
63#endif
64
65/* Roam score for a neighbor AP will be calculated based on the below definitions.
66 The calculated roam score will be used to select the roamable candidate from neighbor AP list */
67#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_REACHABILITY 0 /* When we support 11r over the DS, this should have a non-zero value */
68#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_SECURITY 10
69#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_KEY_SCOPE 20
70#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_SPECTRUM_MGMT 0 /* Not used */
71#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_QOS 5
72#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_APSD 3
73#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_RRM 8
74#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_DELAYED_BA 0 /* We dont support delayed BA */
75#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_IMMEDIATE_BA 3
76#define RRM_ROAM_SCORE_NEIGHBOR_REPORT_MOBILITY_DOMAIN 30
77
78#ifdef FEATURE_WLAN_CCX
79#define RRM_ROAM_SCORE_NEIGHBOR_IAPP_LIST 30
80#endif
81/**---------------------------------------------------------------------------
82
83 \brief rrmLLPurgeNeighborCache() -
84 This function purges all the entries in the neighbor cache and frees up all the internal nodes
85
86 \param - pMac - Pointer to the Hal Handle.
87 - pList - Pointer the List that should be purged.
88 \return - void
89
90 --------------------------------------------------------------------------*/
91static void rrmLLPurgeNeighborCache(tpAniSirGlobal pMac, tDblLinkList *pList)
92{
93 tListElem *pEntry;
94 tRrmNeighborReportDesc *pNeighborReportDesc;
95
96 csrLLLock(pList);
97
98 while((pEntry = csrLLRemoveHead(pList, LL_ACCESS_NOLOCK)) != NULL)
99 {
100 pNeighborReportDesc = GET_BASE_ADDR( pEntry, tRrmNeighborReportDesc, List );
101 vos_mem_free(pNeighborReportDesc->pNeighborBssDescription);
102 vos_mem_free(pNeighborReportDesc);
103 }
104
105 csrLLUnlock(pList);
106
107 return;
108}
109
110/**---------------------------------------------------------------------------
111
112 \brief rrmIndicateNeighborReportResult() -
113 This function calls the callback register by the caller while requesting for
114 neighbor report. This function gets invoked if a neighbor report is received from an AP
115 or neighbor response wait timer expires.
116
117 \param - pMac - Pointer to the Hal Handle.
118 - vosStatus - VOS_STATUS_SUCCESS/VOS_STATUS_FAILURE based on whether a valid report is
119 received or neighbor timer expired
120 \return - void
121
122 --------------------------------------------------------------------------*/
123void rrmIndicateNeighborReportResult(tpAniSirGlobal pMac, VOS_STATUS vosStatus)
124{
125 NeighborReportRspCallback callback;
126 void *callbackContext;
127
128 /* Reset the neighbor response pending status */
129 pMac->rrm.rrmSmeContext.neighborReqControlInfo.isNeighborRspPending = eANI_BOOLEAN_FALSE;
130
131 /* Stop the timer if it is already running. The timer should be running only in the SUCCESS case. */
132 if (VOS_TIMER_STATE_RUNNING == vos_timer_getCurrentState(&pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspWaitTimer))
133 {
Gopichand Nakkalaecdb2a82013-05-30 12:57:51 +0530134 smsLog( pMac, LOG1, FL("No entry in neighbor report cache"));
Jeff Johnson295189b2012-06-20 16:38:30 -0700135 vos_timer_stop(&pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspWaitTimer);
136 }
137 callback = pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallback;
138 callbackContext = pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallbackContext;
139
140 /* Reset the callback and the callback context before calling the callback. It is very likely that there may be a registration in
141 callback itself. */
142 pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallback = NULL;
143 pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallbackContext = NULL;
144
145 /* Call the callback with the status received from caller */
146 if (callback)
147 callback(callbackContext, vosStatus);
Srinivas Girigowda5cecb202013-10-08 09:13:25 -0700148#if defined(FEATURE_WLAN_CCX) && !defined(FEATURE_WLAN_CCX_UPLOAD)
Jeff Johnson295189b2012-06-20 16:38:30 -0700149 // We came here with IAPP AP List
150 // Make sure we inform CSR of the neighbor list
151 // for CCX Associations. First clear the cache.
152 else
153 if (csrNeighborRoamIsCCXAssoc(pMac))
154 {
155 ProcessIAPPNeighborAPList(pMac);
156 }
157#endif
158
159 return;
160
161}
162
163/**---------------------------------------------------------------------------
164
165 \brief sme_RrmBeaconReportXmitInd() -
166
167 Create and send the beacon report Xmit ind message to PE.
168
169 \param - pMac - Pointer to the Hal Handle.
170 - pResult - scan result.
171 - measurementDone - flag to indicate that the measurement is done.
172 \return - 0 for success, non zero for failure
173
174 --------------------------------------------------------------------------*/
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530175static eHalStatus sme_RrmSendBeaconReportXmitInd( tpAniSirGlobal pMac,
176 tCsrScanResultInfo **pResultArr,
177 tANI_U8 measurementDone,
178 tANI_U8 bss_count )
Jeff Johnson295189b2012-06-20 16:38:30 -0700179{
180 tpSirBssDescription pBssDesc = NULL;
181 tpSirBeaconReportXmitInd pBeaconRep;
182 tANI_U16 length, ie_len;
183 tANI_U8 bssCounter=0, msgCounter=0;
184 tCsrScanResultInfo *pCurResult=NULL;
185 eHalStatus status = eHAL_STATUS_FAILURE;
186 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
187
188
189#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800190 smsLog( pMac, LOGE, "Beacon report xmit Ind to PE");
Jeff Johnson295189b2012-06-20 16:38:30 -0700191#endif
192
193 if( NULL == pResultArr && !measurementDone )
194 {
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800195 smsLog( pMac, LOGE, "Beacon report xmit Ind to PE Failed");
Jeff Johnson295189b2012-06-20 16:38:30 -0700196 return eHAL_STATUS_FAILURE;
197 }
198
199 if (pResultArr)
200 pCurResult=pResultArr[bssCounter];
201
202 do
203 {
204 length = sizeof(tSirBeaconReportXmitInd);
205 pBeaconRep = vos_mem_malloc ( length );
206 if ( NULL == pBeaconRep )
207 {
208 smsLog( pMac, LOGP, "Unable to allocate memory for beacon report");
209 return eHAL_STATUS_FAILED_ALLOC;
210 }
211 vos_mem_zero( pBeaconRep, length );
212#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800213 smsLog( pMac, LOGE, FL("Allocated memory for pBeaconRep"));
Jeff Johnson295189b2012-06-20 16:38:30 -0700214#endif
215 pBeaconRep->messageType = eWNI_SME_BEACON_REPORT_RESP_XMIT_IND;
216 pBeaconRep->length = length;
217 pBeaconRep->uDialogToken = pSmeRrmContext->token;
Kanchanapally, Vidyullatha80cd3d02014-02-10 13:06:41 +0530218 pBeaconRep->duration = pSmeRrmContext->duration[0];
Jeff Johnson295189b2012-06-20 16:38:30 -0700219 pBeaconRep->regClass = pSmeRrmContext->regClass;
220 vos_mem_copy( pBeaconRep->bssId, pSmeRrmContext->sessionBssId, sizeof(tSirMacAddr) );
221
222 msgCounter=0;
223 while (pCurResult)
224 {
225 pBssDesc = &pCurResult->BssDescriptor;
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530226 if(pBssDesc != NULL)
227 {
228 ie_len = GET_IE_LEN_IN_BSS( pBssDesc->length );
229 pBeaconRep->pBssDescription[msgCounter] = vos_mem_malloc (
230 ie_len+sizeof(tSirBssDescription));
231 if (NULL == pBeaconRep->pBssDescription[msgCounter])
232 break;
233 vos_mem_copy( pBeaconRep->pBssDescription[msgCounter],
234 pBssDesc,
235 sizeof(tSirBssDescription) );
236 vos_mem_copy( &pBeaconRep->pBssDescription[msgCounter]->ieFields[0],
237 pBssDesc->ieFields, ie_len );
238 smsLog( pMac, LOG1,
Arif Hussain24bafea2013-11-15 15:10:03 -0800239 "...RRM Result Bssid = "MAC_ADDRESS_STR" chan= %d, rssi = -%d",
240 MAC_ADDR_ARRAY(pBeaconRep->pBssDescription[msgCounter]->bssId),
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530241 pBeaconRep->pBssDescription[msgCounter]->channelId,
242 pBeaconRep->pBssDescription[msgCounter]->rssi * (-1));
Jeff Johnson295189b2012-06-20 16:38:30 -0700243
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530244 pBeaconRep->numBssDesc++;
Jeff Johnson295189b2012-06-20 16:38:30 -0700245
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800246 if (++msgCounter >= SIR_BCN_REPORT_MAX_BSS_DESC)
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530247 break;
Jeff Johnson295189b2012-06-20 16:38:30 -0700248
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530249 pCurResult = pResultArr[bssCounter + msgCounter];
250 }
251 else
252 {
253 pCurResult = NULL;
Jeff Johnson295189b2012-06-20 16:38:30 -0700254 break;
255 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700256 }
257
258 bssCounter+=msgCounter;
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530259 if (!pResultArr || (pCurResult == NULL) || (bssCounter >= bss_count))
260 {
261 pCurResult = NULL;
262 smsLog(pMac, LOG1,
263 "Reached to the max/last BSS in pCurResult list");
264 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700265 else
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530266 {
267 pCurResult = pResultArr[bssCounter];
268 smsLog(pMac, LOG1,
269 "Move to the next BSS set in pCurResult list");
270 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700271
272 pBeaconRep->fMeasureDone = (pCurResult)?false:measurementDone;
273
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530274 smsLog(pMac, LOG1,
275 "SME Sending BcnRepXmit to PE numBss %d msgCounter %d bssCounter %d",
276 pBeaconRep->numBssDesc, msgCounter, bssCounter);
Jeff Johnson295189b2012-06-20 16:38:30 -0700277
Jeff Johnson0282cf02013-04-03 17:30:03 -0700278 status = palSendMBMessage(pMac->hHdd, pBeaconRep);
Jeff Johnson295189b2012-06-20 16:38:30 -0700279
280 } while (pCurResult);
281
282 return status;
283}
284
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800285#if defined(FEATURE_WLAN_CCX_UPLOAD)
286/**---------------------------------------------------------------------------
287
288 \brief sme_CcxSendBeaconReqScanResults()
289
290 This function sends up the scan results received as a part of
291 beacon request scanning.
292 This function is called after receiving the scan results per channel
293 Due to the limitation on the size of the IWEVCUSTOM buffer, we send 3 BSSIDs of
294 beacon report information in one custom event;
295
296 \param - pMac - Pointer to the Hal Handle.
297 - sessionId - Session id
298 - channel - scan results belongs to this channel
299 - pResultArr - scan result.
300 - measurementDone - flag to indicate that the measurement is done.
301 - bss_count - number of bss found
302 \return - 0 for success, non zero for failure
303
304 --------------------------------------------------------------------------*/
305static eHalStatus sme_CcxSendBeaconReqScanResults(tpAniSirGlobal pMac,
306 tANI_U32 sessionId,
307 tANI_U8 channel,
308 tCsrScanResultInfo **pResultArr,
309 tANI_U8 measurementDone,
310 tANI_U8 bss_count)
311{
312 eHalStatus status = eHAL_STATUS_FAILURE;
Varun Reddy Yeturucf02bc22013-12-06 18:18:50 -0800313 tSirRetStatus fillIeStatus;
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800314 tpSirBssDescription pBssDesc = NULL;
315 tANI_U32 ie_len = 0;
316 tANI_U32 outIeLen = 0;
317 tANI_U8 bssCounter = 0;
318 tCsrScanResultInfo *pCurResult = NULL;
319 tANI_U8 msgCounter = 0;
320 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
321 tCsrRoamInfo roamInfo;
322 tSirCcxBcnReportRsp bcnReport;
323 tpSirCcxBcnReportRsp pBcnReport = &bcnReport;
324 tpCsrCcxBeaconReqParams pCurMeasReqIe = NULL;
325 tANI_U8 i = 0;
326
327 if (NULL == pSmeRrmContext)
328 {
329 smsLog( pMac, LOGE, "pSmeRrmContext is NULL");
330 return eHAL_STATUS_FAILURE;
331 }
332
333 if (NULL == pResultArr && !measurementDone)
334 {
335 smsLog( pMac, LOGE, "Beacon report xmit Ind to HDD Failed");
336 return eHAL_STATUS_FAILURE;
337 }
338
339 if (pResultArr)
340 pCurResult=pResultArr[bssCounter];
341
342 vos_mem_zero(&bcnReport, sizeof(tSirCcxBcnReportRsp));
343 do
344 {
345 pCurMeasReqIe = NULL;
346 for (i = 0; i < pSmeRrmContext->ccxBcnReqInfo.numBcnReqIe; i++)
347 {
348 if(pSmeRrmContext->ccxBcnReqInfo.bcnReq[i].channel == channel)
349 {
350 pCurMeasReqIe = &pSmeRrmContext->ccxBcnReqInfo.bcnReq[i];
351 break;
352 }
353 }
354 pBcnReport->measurementToken = pCurMeasReqIe->measurementToken;
355 smsLog( pMac, LOG1, "Channel(%d) MeasToken(%d)", channel, pBcnReport->measurementToken);
356
357 msgCounter=0;
358 while (pCurResult)
359 {
360 pBssDesc = &pCurResult->BssDescriptor;
361 if (NULL != pBssDesc)
362 {
363 ie_len = GET_IE_LEN_IN_BSS( pBssDesc->length );
364 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.ChanNum = pBssDesc->channelId;
365 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.Spare = 0;
366 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.MeasDuration = pCurMeasReqIe->measurementDuration;
367 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.PhyType = pBssDesc->nwType;
368 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.RecvSigPower = pBssDesc->rssi;
369 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.ParentTsf = pBssDesc->parentTSF;
370 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.TargetTsf[0] = pBssDesc->timeStamp[0];
371 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.TargetTsf[1] = pBssDesc->timeStamp[1];
372 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.BcnInterval = pBssDesc->beaconInterval;
373 pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.CapabilityInfo = pBssDesc->capabilityInfo;
374 vos_mem_copy(pBcnReport->bcnRepBssInfo[msgCounter].bcnReportFields.Bssid,
375 pBssDesc->bssId, sizeof(tSirMacAddr));
376
Varun Reddy Yeturucf02bc22013-12-06 18:18:50 -0800377 fillIeStatus = sirFillBeaconMandatoryIEforCcxBcnReport(pMac,
378 (tANI_U8 *)pBssDesc->ieFields,
379 ie_len,
380 &(pBcnReport->bcnRepBssInfo[msgCounter].pBuf),
381 &outIeLen);
382 if (eSIR_FAILURE == fillIeStatus)
383 {
384 continue;
385 }
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800386 pBcnReport->bcnRepBssInfo[msgCounter].ieLen = outIeLen;
387
Arif Hussaina7c8e412013-11-20 11:06:42 -0800388 smsLog( pMac, LOG1,"Bssid("MAC_ADDRESS_STR") Channel=%d Rssi=%d",
389 MAC_ADDR_ARRAY(pBssDesc->bssId),
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800390 pBssDesc->channelId, (-1) * pBssDesc->rssi);
391
392 pBcnReport->numBss++;
393
394 if (++msgCounter >= SIR_BCN_REPORT_MAX_BSS_DESC)
395 break;
396
397 pCurResult = pResultArr[msgCounter];
398 }
399 else
400 {
401 pCurResult = NULL;
402 break;
403 }
404 }
405
406 bssCounter += msgCounter;
407 if (!pResultArr || !pCurResult || (bssCounter >= SIR_BCN_REPORT_MAX_BSS_DESC))
408 {
409 pCurResult = NULL;
410 smsLog(pMac, LOGE,
411 "Reached to the max/last BSS in pCurResult list");
412 }
413 else
414 {
415 pCurResult = pResultArr[bssCounter];
416 smsLog(pMac, LOGE,
417 "Move to the next BSS set in pCurResult list");
418 }
419
420 pBcnReport->flag = (measurementDone << 1)|((pCurResult)?true:false);
421
422 smsLog(pMac, LOG1, "SME Sending BcnRep to HDD numBss(%d)"
Srinivas Girigowda6d1f9062014-02-03 18:15:54 -0800423 " msgCounter(%d) bssCounter(%d) flag(%d)",
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800424 pBcnReport->numBss, msgCounter, bssCounter, pBcnReport->flag);
425
426 roamInfo.pCcxBcnReportRsp = pBcnReport;
427 csrRoamCallCallback(pMac, sessionId, &roamInfo,
428 0, eCSR_ROAM_CCX_BCN_REPORT_IND, 0);
429
430 /* Free the memory allocated to IE */
431 for (i = 0; i < msgCounter; i++)
432 {
433 if (pBcnReport->bcnRepBssInfo[i].pBuf)
434 vos_mem_free(pBcnReport->bcnRepBssInfo[i].pBuf);
435 }
436 } while (pCurResult);
437 return status;
438}
439
440#endif /* FEATURE_WLAN_CCX_UPLOAD */
441
Jeff Johnson295189b2012-06-20 16:38:30 -0700442/**---------------------------------------------------------------------------
443
444 \brief sme_RrmSendScanRequest() -
445
446 This function is called to get the scan result from CSR and send the beacon report
447 xmit ind message to PE.
448
449 \param - pMac - Pointer to the Hal Handle.
450 - num_chan - number of channels.
451 - channel list - list of channels to fetch the result from.
452 - measurementDone - flag to indicate that the measurement is done.
453 \return - 0 for success, non zero for failure
454
455 --------------------------------------------------------------------------*/
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530456static eHalStatus sme_RrmSendScanResult( tpAniSirGlobal pMac,
457 tANI_U8 num_chan,
458 tANI_U8* chanList,
459 tANI_U8 measurementDone )
Jeff Johnson295189b2012-06-20 16:38:30 -0700460{
461 tCsrScanResultFilter filter;
462 tScanResultHandle pResult;
463 tCsrScanResultInfo *pScanResult, *pNextResult;
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800464 tCsrScanResultInfo *pScanResultsArr[SIR_BCN_REPORT_MAX_BSS_DESC];
Jeff Johnson295189b2012-06-20 16:38:30 -0700465 eHalStatus status;
466 tANI_U8 counter=0;
467 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
468 tANI_U32 sessionId;
469
470#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800471 smsLog( pMac, LOGE, "Send scan result to PE ");
Jeff Johnson295189b2012-06-20 16:38:30 -0700472#endif
473
474 vos_mem_zero( &filter, sizeof(filter) );
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800475 vos_mem_zero( pScanResultsArr, sizeof(pNextResult)*SIR_BCN_REPORT_MAX_BSS_DESC );
Jeff Johnson295189b2012-06-20 16:38:30 -0700476
477 filter.BSSIDs.numOfBSSIDs = 1;
478 filter.BSSIDs.bssid = &pSmeRrmContext->bssId;
479
480 if( pSmeRrmContext->ssId.length )
481 {
482 filter.SSIDs.SSIDList =( tCsrSSIDInfo *)vos_mem_malloc(sizeof(tCsrSSIDInfo));
483 if( filter.SSIDs.SSIDList == NULL )
484 {
485 smsLog( pMac, LOGP, FL("vos_mem_malloc failed:") );
486 return eHAL_STATUS_FAILURE;
487 }
488#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800489 smsLog( pMac, LOGE, FL("Allocated memory for SSIDList"));
Jeff Johnson295189b2012-06-20 16:38:30 -0700490#endif
491 vos_mem_zero( filter.SSIDs.SSIDList, sizeof(tCsrSSIDInfo) );
492
493 filter.SSIDs.SSIDList->SSID.length = pSmeRrmContext->ssId.length;
494 vos_mem_copy(filter.SSIDs.SSIDList->SSID.ssId, pSmeRrmContext->ssId.ssId, pSmeRrmContext->ssId.length);
495 filter.SSIDs.numOfSSIDs = 1;
496 }
497 else
498 {
499 filter.SSIDs.numOfSSIDs = 0;
500 }
501
502 filter.ChannelInfo.numOfChannels = num_chan;
503 filter.ChannelInfo.ChannelList = chanList;
504
505 filter.fMeasurement = TRUE;
506
507 csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid*)pSmeRrmContext->sessionBssId, &sessionId );
508 status = sme_ScanGetResult(pMac, (tANI_U8)sessionId, &filter, &pResult);
509
510 if( filter.SSIDs.SSIDList )
511 {
512 //Free the memory allocated for SSIDList.
513 vos_mem_free( filter.SSIDs.SSIDList );
514#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800515 smsLog( pMac, LOGE, FL("Free memory for SSIDList") );
Jeff Johnson295189b2012-06-20 16:38:30 -0700516#endif
517 }
518
519 if (NULL == pResult)
520 {
521 // no scan results
522 //
523 // Spec. doesnt say anything about such condition.
524 // Since section 7.4.6.2 (IEEE802.11k-2008) says-rrm report frame should contain
525 // one or more report IEs. It probably means dont send any respose if no matching
526 // BSS found. Moreover, there is no flag or field in measurement report IE(7.3.2.22)
527 // OR beacon report IE(7.3.2.22.6) that can be set to indicate no BSS found on a given channel.
528 //
529 // If we finished measurement on all the channels, we still need to
530 // send a xmit indication with moreToFollow set to MEASURMENT_DONE
531 // so that PE can clean any context allocated.
532 if( measurementDone )
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800533 {
534#if defined(FEATURE_WLAN_CCX_UPLOAD)
Srinivas Girigowda6d1f9062014-02-03 18:15:54 -0800535 if (eRRM_MSG_SOURCE_CCX_UPLOAD == pSmeRrmContext->msgSource)
536 {
537 status = sme_CcxSendBeaconReqScanResults(pMac,
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800538 sessionId,
539 chanList[0],
540 NULL,
541 measurementDone,
542 0);
Srinivas Girigowda6d1f9062014-02-03 18:15:54 -0800543 }
544 else
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800545#endif /*FEATURE_WLAN_CCX_UPLOAD*/
Srinivas Girigowda6d1f9062014-02-03 18:15:54 -0800546 status = sme_RrmSendBeaconReportXmitInd( pMac, NULL, measurementDone, 0);
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800547 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700548 return status;
549 }
550
551 pScanResult = sme_ScanResultGetFirst(pMac, pResult);
552
553 if( NULL == pScanResult && measurementDone )
Srinivas Girigowda6d1f9062014-02-03 18:15:54 -0800554 {
555#if defined(FEATURE_WLAN_CCX_UPLOAD)
556 if (eRRM_MSG_SOURCE_CCX_UPLOAD == pSmeRrmContext->msgSource)
557 {
558 status = sme_CcxSendBeaconReqScanResults(pMac,
559 sessionId,
560 chanList[0],
561 NULL,
562 measurementDone,
563 0);
564 }
565 else
566#endif /*FEATURE_WLAN_CCX_UPLOAD*/
567 status = sme_RrmSendBeaconReportXmitInd( pMac, NULL, measurementDone, 0 );
568 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700569
570 counter=0;
571 while (pScanResult)
572 {
573 pNextResult = sme_ScanResultGetNext(pMac, pResult);
574 pScanResultsArr[counter++] = pScanResult;
575 pScanResult = pNextResult; //sme_ScanResultGetNext(hHal, pResult);
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800576 if (counter >= SIR_BCN_REPORT_MAX_BSS_DESC)
Jeff Johnson295189b2012-06-20 16:38:30 -0700577 break;
578 }
579
580 if (counter)
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530581 {
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800582 smsLog(pMac, LOG1, " Number of BSS Desc with RRM Scan %d ", counter);
583#if defined(FEATURE_WLAN_CCX_UPLOAD)
Srinivas Girigowda6d1f9062014-02-03 18:15:54 -0800584 if (eRRM_MSG_SOURCE_CCX_UPLOAD == pSmeRrmContext->msgSource)
585 {
586 status = sme_CcxSendBeaconReqScanResults(pMac,
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800587 sessionId,
588 chanList[0],
589 pScanResultsArr,
590 measurementDone,
591 counter);
Srinivas Girigowda6d1f9062014-02-03 18:15:54 -0800592 }
593 else
594#endif /*FEATURE_WLAN_CCX_UPLOAD*/
595 status = sme_RrmSendBeaconReportXmitInd( pMac,
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530596 pScanResultsArr,
597 measurementDone,
598 counter);
Madan Mohan Koyyalamudic6a1d882013-09-28 22:24:21 +0530599 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700600 sme_ScanResultPurge(pMac, pResult);
601
602 return status;
603}
604/**---------------------------------------------------------------------------
605
606 \brief sme_RrmScanRequestCallback() -
607
608 The sme module calls this callback function once it finish the scan request
609 and this function send the beacon report xmit to PE and starts a timer of
610 random interval to issue next request.
611
612 \param - halHandle - Pointer to the Hal Handle.
613 - pContext - Pointer to the data context.
614 - scanId - Scan ID.
615 - status - CSR Status.
616 \return - 0 for success, non zero for failure
617
618 --------------------------------------------------------------------------*/
619
620static eHalStatus sme_RrmScanRequestCallback(tHalHandle halHandle, void *pContext,
621 tANI_U32 scanId, eCsrScanStatus status)
622{
623
624 tANI_U16 interval;
625 tpAniSirGlobal pMac = (tpAniSirGlobal) halHandle;
626 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
627 tANI_U32 time_tick;
628
629
630
631#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800632 smsLog( pMac, LOGE, "Scan Request callback ");
Jeff Johnson295189b2012-06-20 16:38:30 -0700633#endif
634 //if any more channels are pending, start a timer of a random value within randomization interval.
635 //
636 //
637 if( (pSmeRrmContext->currentIndex + 1) < pSmeRrmContext->channelList.numOfChannels )
638 {
639 sme_RrmSendScanResult( pMac, 1, &pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex], false );
640
641 pSmeRrmContext->currentIndex++; //Advance the current index.
642 //start the timer to issue next request.
643 //From timer tick get a random number within 10ms and max randmization interval.
644 time_tick = vos_timer_get_system_ticks();
645 interval = time_tick % (pSmeRrmContext->randnIntvl - 10 + 1) + 10;
646
647#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800648 smsLog( pMac, LOGE, "Set timer for interval %d ", interval);
Jeff Johnson295189b2012-06-20 16:38:30 -0700649#endif
650 vos_timer_start( &pSmeRrmContext->IterMeasTimer, interval );
651
652 }
653 else
654 {
655 //Done with the measurement. Clean up all context and send a message to PE with measurement done flag set.
656 sme_RrmSendScanResult( pMac, 1, &pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex], true );
657 vos_mem_free( pSmeRrmContext->channelList.ChannelList );
658#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800659 smsLog( pMac, LOGE, FL("Free memory for ChannelList") );
Jeff Johnson295189b2012-06-20 16:38:30 -0700660#endif
661 }
662
663 return eHAL_STATUS_SUCCESS;
664}
665
666/*--------------------------------------------------------------------------
667 \brief sme_RrmIssueScanReq() - This is called to send a scan request as part
668 of beacon report request .
669
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800670 \param pMac - pMac global pointer
Jeff Johnson295189b2012-06-20 16:38:30 -0700671
672 \return eHAL_STATUS_SUCCESS - Validation is successful.
673
674 \sa
675
676 --------------------------------------------------------------------------*/
677eHalStatus sme_RrmIssueScanReq( tpAniSirGlobal pMac )
678{
679 //Issue scan request.
680 tCsrScanRequest scanRequest;
681 v_U32_t scanId = 0;
682 eHalStatus status = eHAL_STATUS_SUCCESS;
683 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
684 tANI_U32 sessionId;
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800685 tSirScanType scanType;
Jeff Johnson295189b2012-06-20 16:38:30 -0700686
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800687 if ((pSmeRrmContext->currentIndex) >= pSmeRrmContext->channelList.numOfChannels)
688 return status;
689
690 scanType = pSmeRrmContext->measMode[pSmeRrmContext->currentIndex];
691 if ((eSIR_ACTIVE_SCAN == scanType) || (eSIR_PASSIVE_SCAN == scanType))
692 {
Jeff Johnson295189b2012-06-20 16:38:30 -0700693#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800694 smsLog( pMac, LOGE, "Issue scan request " );
Jeff Johnson295189b2012-06-20 16:38:30 -0700695#endif
696
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800697 vos_mem_zero( &scanRequest, sizeof(scanRequest));
Jeff Johnson295189b2012-06-20 16:38:30 -0700698
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800699 /* set scanType, active or passive */
700 scanRequest.bcnRptReqScan = TRUE;
701 scanRequest.scanType = scanType;
Jeff Johnson295189b2012-06-20 16:38:30 -0700702
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800703 vos_mem_copy(scanRequest.bssid,
704 pSmeRrmContext->bssId, sizeof(scanRequest.bssid) );
Jeff Johnson295189b2012-06-20 16:38:30 -0700705
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800706 if (pSmeRrmContext->ssId.length)
707 {
708 scanRequest.SSIDs.numOfSSIDs = 1;
709 scanRequest.SSIDs.SSIDList =( tCsrSSIDInfo *)vos_mem_malloc(sizeof(tCsrSSIDInfo));
710 if (NULL == scanRequest.SSIDs.SSIDList)
711 {
712 smsLog( pMac, LOGP, FL("vos_mem_malloc failed:") );
713 return eHAL_STATUS_FAILURE;
714 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700715#if defined WLAN_VOWIFI_DEBUG
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800716 smsLog( pMac, LOGE, FL("Allocated memory for pSSIDList"));
Jeff Johnson295189b2012-06-20 16:38:30 -0700717#endif
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800718 vos_mem_zero( scanRequest.SSIDs.SSIDList, sizeof(tCsrSSIDInfo) );
719 scanRequest.SSIDs.SSIDList->SSID.length = pSmeRrmContext->ssId.length;
720 vos_mem_copy(scanRequest.SSIDs.SSIDList->SSID.ssId, pSmeRrmContext->ssId.ssId, pSmeRrmContext->ssId.length);
721 }
722
723 /* set min and max channel time */
724 scanRequest.minChnTime = 0; //pSmeRrmContext->duration; Dont use min timeout.
725 scanRequest.maxChnTime = pSmeRrmContext->duration[pSmeRrmContext->currentIndex];
726 smsLog( pMac, LOG1, "Scan Type(%d) Max Dwell Time(%d)", scanRequest.scanType,
727 scanRequest.maxChnTime );
728
729#if defined WLAN_VOWIFI_DEBUG
730 smsLog( pMac, LOGE, "For Duration %d ", scanRequest.maxChnTime );
731#endif
732
733 /* set BSSType to default type */
734 scanRequest.BSSType = eCSR_BSS_TYPE_ANY;
735
736 /*Scan all the channels */
737 scanRequest.ChannelInfo.numOfChannels = 1;
738
739 scanRequest.ChannelInfo.ChannelList = &pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex];
740#if defined WLAN_VOWIFI_DEBUG
741 smsLog( pMac, LOGE, "On channel %d ", pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex] );
742#endif
743
744 /* set requestType to full scan */
745 scanRequest.requestType = eCSR_SCAN_REQUEST_FULL_SCAN;
746
747 csrRoamGetSessionIdFromBSSID( pMac, (tCsrBssid*)pSmeRrmContext->sessionBssId, &sessionId );
748 status = sme_ScanRequest( pMac, (tANI_U8)sessionId, &scanRequest, &scanId, &sme_RrmScanRequestCallback, NULL );
749
750 if ( pSmeRrmContext->ssId.length )
751 {
752 vos_mem_free(scanRequest.SSIDs.SSIDList);
753#if defined WLAN_VOWIFI_DEBUG
754 smsLog( pMac, LOGE, FL("Free memory for SSIDList"));
755#endif
756 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700757 }
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800758 else if (2 == scanType) /* beacon table */
Jeff Johnson295189b2012-06-20 16:38:30 -0700759 {
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800760 if ((pSmeRrmContext->currentIndex + 1) < pSmeRrmContext->channelList.numOfChannels)
761 {
762 sme_RrmSendScanResult( pMac, 1, &pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex], false );
763 pSmeRrmContext->currentIndex++; //Advance the current index.
764 sme_RrmIssueScanReq(pMac);
765 }
766 else
767 {
768 //Done with the measurement. Clean up all context and send a message to PE with measurement done flag set.
769 sme_RrmSendScanResult( pMac, 1, &pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->currentIndex], true );
770 vos_mem_free( pSmeRrmContext->channelList.ChannelList );
771 }
772 }
773 else
774 {
775 smsLog( pMac, LOGE, "Unknown beacon report request mode(%d)", scanType);
776 /* Indicate measurement completion to PE */
777 /* If this is not done, pCurrentReq pointer will not be freed and
778 PE will not handle subsequent Beacon requests */
779 sme_RrmSendBeaconReportXmitInd(pMac, NULL, true, 0);
Jeff Johnson295189b2012-06-20 16:38:30 -0700780 }
781
782 return status;
783}
784
785/*--------------------------------------------------------------------------
786 \brief sme_RrmProcessBeaconReportReqInd() - This is called to process the Beacon
787 report request from peer AP forwarded through PE .
788
789 \param pMsgBuf - a pointer to a buffer that maps to various structures base
790 on the message type.
791 The beginning of the buffer can always map to tSirSmeRsp.
792
793 \return eHAL_STATUS_SUCCESS - Validation is successful.
794
795 \sa
796
797 --------------------------------------------------------------------------*/
798void sme_RrmProcessBeaconReportReqInd(tpAniSirGlobal pMac, void *pMsgBuf)
799{
800 tpSirBeaconReportReqInd pBeaconReq = (tpSirBeaconReportReqInd) pMsgBuf;
801 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800802 tANI_U32 len = 0, i = 0;
Jeff Johnson295189b2012-06-20 16:38:30 -0700803
804#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800805 smsLog( pMac, LOGE, "Received Beacon report request ind Channel = %d", pBeaconReq->channelInfo.channelNum );
Jeff Johnson295189b2012-06-20 16:38:30 -0700806#endif
807 //section 11.10.8.1 (IEEE Std 802.11k-2008)
808 //channel 0 and 255 has special meaning.
809 if( (pBeaconReq->channelInfo.channelNum == 0) ||
810 ((pBeaconReq->channelInfo.channelNum == 255) && (pBeaconReq->channelList.numChannels == 0) ) )
811 {
812 //Add all the channel in the regulatory domain.
813 wlan_cfgGetStrLen( pMac, WNI_CFG_VALID_CHANNEL_LIST, &len );
814 pSmeRrmContext->channelList.ChannelList = vos_mem_malloc( len );
815 if( pSmeRrmContext->channelList.ChannelList == NULL )
816 {
817 smsLog( pMac, LOGP, FL("vos_mem_malloc failed:") );
818 return;
819 }
820#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800821 smsLog( pMac, LOGE, FL("Allocated memory for ChannelList") );
Jeff Johnson295189b2012-06-20 16:38:30 -0700822#endif
823 csrGetCfgValidChannels( pMac, pSmeRrmContext->channelList.ChannelList, &len );
824 pSmeRrmContext->channelList.numOfChannels = (tANI_U8)len;
825#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800826 smsLog( pMac, LOGE, "channel == 0 performing on all channels");
Jeff Johnson295189b2012-06-20 16:38:30 -0700827#endif
828 }
829 else
830 {
831 len = 0;
832 pSmeRrmContext->channelList.numOfChannels = 0;
833
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800834 //If valid channel is present. We first Measure on the given channel. and
Jeff Johnson295189b2012-06-20 16:38:30 -0700835 //if there are additional channels present in APchannelreport, measure on these also.
836 if ( pBeaconReq->channelInfo.channelNum != 255 )
837 len = 1;
838#if defined WLAN_VOWIFI_DEBUG
839 else
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800840 smsLog( pMac, LOGE, "channel == 255");
Jeff Johnson295189b2012-06-20 16:38:30 -0700841#endif
842
843 len += pBeaconReq->channelList.numChannels;
844
845 pSmeRrmContext->channelList.ChannelList = vos_mem_malloc( len );
846 if( pSmeRrmContext->channelList.ChannelList == NULL )
847 {
848 smsLog( pMac, LOGP, FL("vos_mem_malloc failed") );
849 return;
850 }
851#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800852 smsLog( pMac, LOGE, FL("Allocated memory for ChannelList") );
Jeff Johnson295189b2012-06-20 16:38:30 -0700853#endif
854
855 if ( pBeaconReq->channelInfo.channelNum != 255 )
856 {
857#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800858 smsLog( pMac, LOGE, "channel == %d ", pBeaconReq->channelInfo.channelNum );
Jeff Johnson295189b2012-06-20 16:38:30 -0700859#endif
860 if(csrRoamIsChannelValid( pMac, pBeaconReq->channelInfo.channelNum ))
861 pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->channelList.numOfChannels++] = pBeaconReq->channelInfo.channelNum;
862#if defined WLAN_VOWIFI_DEBUG
863 else
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800864 smsLog( pMac, LOGE, "is Invalid channel, Ignoring this channel" );
Jeff Johnson295189b2012-06-20 16:38:30 -0700865#endif
866 }
867
868 for ( i = 0 ; i < pBeaconReq->channelList.numChannels; i++ )
869 {
870 if(csrRoamIsChannelValid( pMac, pBeaconReq->channelList.channelNumber[i] ))
871 {
872 pSmeRrmContext->channelList.ChannelList[pSmeRrmContext->channelList.numOfChannels] = pBeaconReq->channelList.channelNumber[i];
873 pSmeRrmContext->channelList.numOfChannels++;
874 }
875 }
876 }
877
878 //Copy session bssid
879 vos_mem_copy( pSmeRrmContext->sessionBssId, pBeaconReq->bssId, sizeof(tSirMacAddr) );
880
881 //copy measurement bssid
882 vos_mem_copy( pSmeRrmContext->bssId, pBeaconReq->macaddrBssid, sizeof(tSirMacAddr) );
883
884 //Copy ssid
885 vos_mem_copy( &pSmeRrmContext->ssId, &pBeaconReq->ssId, sizeof(tAniSSID) );
886
887 pSmeRrmContext->token = pBeaconReq->uDialogToken;
888 pSmeRrmContext->regClass = pBeaconReq->channelInfo.regulatoryClass;
Jeff Johnson295189b2012-06-20 16:38:30 -0700889 pSmeRrmContext->randnIntvl = VOS_MAX( pBeaconReq->randomizationInterval, pSmeRrmContext->rrmConfig.maxRandnInterval );
890 pSmeRrmContext->currentIndex = 0;
Srinivas Girigowda6d1f9062014-02-03 18:15:54 -0800891 pSmeRrmContext->msgSource = pBeaconReq->msgSource;
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800892 vos_mem_copy((tANI_U8*)&pSmeRrmContext->measMode, (tANI_U8*)&pBeaconReq->fMeasurementtype, SIR_CCX_MAX_MEAS_IE_REQS);
893 vos_mem_copy((tANI_U8*)&pSmeRrmContext->duration, (tANI_U8*)&pBeaconReq->measurementDuration, SIR_CCX_MAX_MEAS_IE_REQS);
Jeff Johnson295189b2012-06-20 16:38:30 -0700894
Srinivas Girigowda91ccbe82013-11-10 16:37:38 -0800895 sme_RrmIssueScanReq( pMac );
Jeff Johnson295189b2012-06-20 16:38:30 -0700896
897 return;
898}
899
900/*--------------------------------------------------------------------------
901 \brief sme_RrmNeighborReportRequest() - This is API can be used to trigger a
902 Neighbor report from the peer.
903
904 \param sessionId - session identifier on which the request should be made.
905 \param pNeighborReq - a pointer to a neighbor report request.
906
907 \return eHAL_STATUS_SUCCESS - Validation is successful.
908
909 \sa
910
911 --------------------------------------------------------------------------*/
912VOS_STATUS sme_RrmNeighborReportRequest(tpAniSirGlobal pMac, tANI_U8 sessionId,
913 tpRrmNeighborReq pNeighborReq, tpRrmNeighborRspCallbackInfo callbackInfo)
914{
915 eHalStatus status = eHAL_STATUS_SUCCESS;
916 tpSirNeighborReportReqInd pMsg;
917 tCsrRoamSession *pSession;
918
919#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800920 smsLog( pMac, LOGE, FL("Request to send Neighbor report request received "));
Jeff Johnson295189b2012-06-20 16:38:30 -0700921#endif
922 if( !CSR_IS_SESSION_VALID( pMac, sessionId ) )
923 {
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800924 smsLog( pMac, LOGE, FL("Invalid session %d"), sessionId );
Jeff Johnson295189b2012-06-20 16:38:30 -0700925 return VOS_STATUS_E_INVAL;
926 }
927 pSession = CSR_GET_SESSION( pMac, sessionId );
928
929 /* If already a report is pending, return failure */
930 if (eANI_BOOLEAN_TRUE == pMac->rrm.rrmSmeContext.neighborReqControlInfo.isNeighborRspPending)
931 {
932 smsLog( pMac, LOGE, FL("Neighbor request already pending.. Not allowed"));
933 return VOS_STATUS_E_AGAIN;
934 }
935
936 pMsg = vos_mem_malloc ( sizeof(tSirNeighborReportReqInd) );
937 if ( NULL == pMsg )
938 {
939 smsLog( pMac, LOGE, "Unable to allocate memory for Neighbor request");
940 return VOS_STATUS_E_NOMEM;
941 }
942
943
944 vos_mem_zero( pMsg, sizeof(tSirNeighborReportReqInd) );
945#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800946 smsLog( pMac, LOGE, FL(" Allocated memory for Neighbor request") );
Jeff Johnson295189b2012-06-20 16:38:30 -0700947#endif
948
949 rrmLLPurgeNeighborCache(pMac, &pMac->rrm.rrmSmeContext.neighborReportCache);
950
951#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -0800952 smsLog( pMac, LOGE, FL("Purged the neighbor cache before sending Neighbor request: Status = %d"), status );
Jeff Johnson295189b2012-06-20 16:38:30 -0700953#endif
954
955 pMsg->messageType = eWNI_SME_NEIGHBOR_REPORT_REQ_IND;
956 pMsg->length = sizeof( tSirNeighborReportReqInd );
957 vos_mem_copy( &pMsg->bssId, &pSession->connectedProfile.bssid, sizeof(tSirMacAddr) );
958 pMsg->noSSID = pNeighborReq->no_ssid;
959 vos_mem_copy( &pMsg->ucSSID, &pNeighborReq->ssid, sizeof(tSirMacSSid));
960
961 status = palSendMBMessage(pMac->hHdd, pMsg);
962 if( status != eHAL_STATUS_SUCCESS )
963 return VOS_STATUS_E_FAILURE;
964
965 /* Neighbor report request message sent successfully to PE. Now register the callbacks */
966 pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallback =
967 callbackInfo->neighborRspCallback;
968 pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo.neighborRspCallbackContext =
969 callbackInfo->neighborRspCallbackContext;
970 pMac->rrm.rrmSmeContext.neighborReqControlInfo.isNeighborRspPending = eANI_BOOLEAN_TRUE;
971
972 /* Start neighbor response wait timer now */
973 vos_timer_start(&pMac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspWaitTimer, callbackInfo->timeout);
974
975 return VOS_STATUS_SUCCESS;
976}
977
978/*--------------------------------------------------------------------------
979 \brief rrmCalculateNeighborAPRoamScore() - This API is called while handling
980 individual neighbor reports from the APs neighbor AP report to
981 calculate the cumulative roam score before storing it in neighbor
982 cache.
983
984 \param pNeighborReportDesc - Neighbor BSS Descriptor node for which roam score
985 should be calculated
986
987 \return void.
988--------------------------------------------------------------------------*/
989static void rrmCalculateNeighborAPRoamScore(tpAniSirGlobal pMac, tpRrmNeighborReportDesc pNeighborReportDesc)
990{
991 tpSirNeighborBssDescripton pNeighborBssDesc;
992 tANI_U32 roamScore = 0;
993
Gopichand Nakkalacc8cf8e2013-04-25 06:03:10 -0700994 if (NULL == pNeighborReportDesc)
995 {
996 VOS_ASSERT(0);
997 return;
998 }
999 if (NULL == pNeighborReportDesc->pNeighborBssDescription)
1000 {
1001 VOS_ASSERT(0);
1002 return;
1003 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001004
1005 pNeighborBssDesc = pNeighborReportDesc->pNeighborBssDescription;
1006
1007 if (pNeighborBssDesc->bssidInfo.rrmInfo.fMobilityDomain)
1008 {
1009 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_MOBILITY_DOMAIN;
1010 if (pNeighborBssDesc->bssidInfo.rrmInfo.fSameSecurityMode)
1011 {
1012 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_SECURITY;
1013 if (pNeighborBssDesc->bssidInfo.rrmInfo.fSameAuthenticator)
1014 {
1015 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_KEY_SCOPE;
1016 if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapRadioMeasurement)
1017 {
1018 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_RRM;
1019 if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapSpectrumMeasurement)
1020 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_SPECTRUM_MGMT;
1021 if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapQos)
1022 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_QOS;
1023 if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapApsd)
1024 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_APSD;
1025 if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapDelayedBlockAck)
1026 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_DELAYED_BA;
1027 if (pNeighborBssDesc->bssidInfo.rrmInfo.fCapImmediateBlockAck)
1028 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_CAPABILITY_IMMEDIATE_BA;
1029 if (pNeighborBssDesc->bssidInfo.rrmInfo.fApPreauthReachable)
1030 roamScore += RRM_ROAM_SCORE_NEIGHBOR_REPORT_REACHABILITY;
1031 }
1032 }
1033 }
1034 }
1035#ifdef FEATURE_WLAN_CCX
1036 // It has come in the report so its the best score
1037 if (csrNeighborRoamIs11rAssoc(pMac) == FALSE)
1038 {
1039 // IAPP Route so lets make use of this info
1040 // save all AP, as the list does not come all the time
1041 // Save and reuse till the next AP List comes to us.
1042 // Even save our own MAC address. Will be useful next time around.
1043 roamScore += RRM_ROAM_SCORE_NEIGHBOR_IAPP_LIST;
1044 }
1045#endif
1046 pNeighborReportDesc->roamScore = roamScore;
1047
1048 return;
1049}
1050
1051/*--------------------------------------------------------------------------
1052 \brief rrmStoreNeighborRptByRoamScore() - This API is called to store a given
1053 Neighbor BSS descriptor to the neighbor cache. This function
1054 stores the neighbor BSS descriptors in such a way that descriptors
1055 are sorted by roamScore in descending order
1056
1057 \param pNeighborReportDesc - Neighbor BSS Descriptor node to be stored in cache
1058
1059 \return void.
1060--------------------------------------------------------------------------*/
1061void rrmStoreNeighborRptByRoamScore(tpAniSirGlobal pMac, tpRrmNeighborReportDesc pNeighborReportDesc)
1062{
1063 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
1064 tListElem *pEntry;
1065 tRrmNeighborReportDesc *pTempNeighborReportDesc;
1066
Gopichand Nakkalacc8cf8e2013-04-25 06:03:10 -07001067 if (NULL == pNeighborReportDesc)
1068 {
1069 VOS_ASSERT(0);
1070 return;
1071 }
1072 if (NULL == pNeighborReportDesc->pNeighborBssDescription)
1073 {
1074 VOS_ASSERT(0);
1075 return;
1076 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001077
1078 if (csrLLIsListEmpty(&pSmeRrmContext->neighborReportCache, LL_ACCESS_LOCK))
1079 {
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001080 smsLog(pMac, LOGE, FL("Neighbor report cache is empty.. Adding a entry now"));
Jeff Johnson295189b2012-06-20 16:38:30 -07001081 /* Neighbor list cache is empty. Insert this entry in the tail */
1082 csrLLInsertTail(&pSmeRrmContext->neighborReportCache, &pNeighborReportDesc->List, LL_ACCESS_LOCK);
1083 return;
1084 }
1085 else
1086 {
1087 /* Should store the neighbor BSS description in the order sorted by roamScore in descending
1088 order. APs with highest roamScore should be the 1st entry in the list */
1089 pEntry = csrLLPeekHead(&pSmeRrmContext->neighborReportCache, LL_ACCESS_LOCK);
1090 while (pEntry != NULL)
1091 {
1092 pTempNeighborReportDesc = GET_BASE_ADDR( pEntry, tRrmNeighborReportDesc, List );
1093 if (pTempNeighborReportDesc->roamScore < pNeighborReportDesc->roamScore)
1094 break;
1095 pEntry = csrLLNext(&pSmeRrmContext->neighborReportCache, pEntry, LL_ACCESS_LOCK);
1096 }
1097
1098 if (pEntry)
1099 /* This BSS roamscore is better than something in the list. Insert this before that one */
1100 csrLLInsertEntry(&pSmeRrmContext->neighborReportCache, pEntry, &pNeighborReportDesc->List, LL_ACCESS_LOCK);
1101 else
1102 /* All the entries in the list has a better roam Score than this one. Insert this at the last */
1103 csrLLInsertTail(&pSmeRrmContext->neighborReportCache, &pNeighborReportDesc->List, LL_ACCESS_LOCK);
1104 }
1105 return;
1106}
1107
1108/*--------------------------------------------------------------------------
1109 \brief sme_RrmProcessNeighborReport() - This is called to process the Neighbor
1110 report received from PE.
1111
1112 \param pMsgBuf - a pointer to a buffer that maps to various structures base
1113 on the message type.
1114 The beginning of the buffer can always map to tSirSmeRsp.
1115
1116 \return eHAL_STATUS_SUCCESS - Validation is successful.
1117
1118 \sa
1119
1120 --------------------------------------------------------------------------*/
1121eHalStatus sme_RrmProcessNeighborReport(tpAniSirGlobal pMac, void *pMsgBuf)
1122{
1123 eHalStatus status = eHAL_STATUS_SUCCESS;
1124 tpSirNeighborReportInd pNeighborRpt = (tpSirNeighborReportInd) pMsgBuf;
1125 tpRrmNeighborReportDesc pNeighborReportDesc;
1126 tANI_U8 i = 0;
1127 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
1128
1129#ifdef FEATURE_WLAN_CCX
1130 // Clear the cache for CCX.
1131 if (csrNeighborRoamIsCCXAssoc(pMac))
1132 {
1133 rrmLLPurgeNeighborCache(pMac,
1134 &pMac->rrm.rrmSmeContext.neighborReportCache);
1135 }
1136#endif
1137
1138 for (i = 0; i < pNeighborRpt->numNeighborReports; i++)
1139 {
1140 pNeighborReportDesc = vos_mem_malloc(sizeof(tRrmNeighborReportDesc));
1141 if (NULL == pNeighborReportDesc)
1142 {
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001143 smsLog( pMac, LOGE, "Failed to allocate memory for RRM Neighbor report desc");
Jeff Johnson295189b2012-06-20 16:38:30 -07001144 status = eHAL_STATUS_FAILED_ALLOC;
1145 goto end;
1146
1147 }
1148
1149 vos_mem_zero(pNeighborReportDesc, sizeof(tRrmNeighborReportDesc));
1150 pNeighborReportDesc->pNeighborBssDescription = vos_mem_malloc(sizeof(tSirNeighborBssDescription));
1151 if (NULL == pNeighborReportDesc->pNeighborBssDescription)
1152 {
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001153 smsLog( pMac, LOGE, "Failed to allocate memory for RRM Neighbor report BSS Description");
Jeff Johnsonfb82ea52013-04-03 15:35:49 -07001154 vos_mem_free(pNeighborReportDesc);
Jeff Johnson295189b2012-06-20 16:38:30 -07001155 status = eHAL_STATUS_FAILED_ALLOC;
1156 goto end;
1157 }
1158 vos_mem_zero(pNeighborReportDesc->pNeighborBssDescription, sizeof(tSirNeighborBssDescription));
1159 vos_mem_copy(pNeighborReportDesc->pNeighborBssDescription, &pNeighborRpt->sNeighborBssDescription[i],
1160 sizeof(tSirNeighborBssDescription));
1161
1162#if defined WLAN_VOWIFI_DEBUG
Arif Hussain24bafea2013-11-15 15:10:03 -08001163 smsLog( pMac, LOGE, "Received neighbor report with Neighbor BSSID: "MAC_ADDRESS_STR,
1164 MAC_ADDR_ARRAY(pNeighborRpt->sNeighborBssDescription[i].bssId));
Jeff Johnson295189b2012-06-20 16:38:30 -07001165#endif
1166
1167 /* Calculate the roam score based on the BSS Capability in the BSSID Information and store it in Neighbor report Desc */
1168 rrmCalculateNeighborAPRoamScore(pMac, pNeighborReportDesc);
1169
1170 /* Store the Neighbor report Desc in the cache based on the roam score */
1171 if ( pNeighborReportDesc->roamScore > 0)
1172 {
1173 rrmStoreNeighborRptByRoamScore(pMac, pNeighborReportDesc);
1174 }
1175 else
1176 {
Arif Hussain24bafea2013-11-15 15:10:03 -08001177 smsLog(pMac, LOGE, FL("Roam score of BSSID "MAC_ADDRESS_STR" is 0, Ignoring.."),
1178 MAC_ADDR_ARRAY(pNeighborRpt->sNeighborBssDescription[i].bssId));
Jeff Johnson295189b2012-06-20 16:38:30 -07001179
1180 vos_mem_free(pNeighborReportDesc->pNeighborBssDescription);
1181 vos_mem_free(pNeighborReportDesc);
1182 }
1183 }
1184end:
1185
1186 if (!csrLLCount(&pMac->rrm.rrmSmeContext.neighborReportCache))
1187 vosStatus = VOS_STATUS_E_FAILURE;
1188
1189 /* Received a report from AP. Indicate SUCCESS to the caller if there are some valid reports */
1190 rrmIndicateNeighborReportResult(pMac, vosStatus);
1191
1192 return status;
1193}
1194/*--------------------------------------------------------------------------
1195 \brief sme_RrmMsgProcessor() - sme_ProcessMsg() calls this function for the
1196 messages that are handled by SME RRM module.
1197
1198 \param pMac - Pointer to the global MAC parameter structure.
1199 \param msg_type - the type of msg passed by PE as defined in wniApi.h
1200 \param pMsgBuf - a pointer to a buffer that maps to various structures base
1201 on the message type.
1202 The beginning of the buffer can always map to tSirSmeRsp.
1203
1204 \return eHAL_STATUS_SUCCESS - Validation is successful.
1205
1206 \sa
1207
1208 --------------------------------------------------------------------------*/
1209eHalStatus sme_RrmMsgProcessor( tpAniSirGlobal pMac, v_U16_t msg_type,
1210 void *pMsgBuf)
1211{
1212 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001213 FL(" Msg = %d for RRM measurement") , msg_type );
Jeff Johnson295189b2012-06-20 16:38:30 -07001214
1215 //switch on the msg type & make the state transition accordingly
1216 switch(msg_type)
1217 {
1218 case eWNI_SME_NEIGHBOR_REPORT_IND:
1219 sme_RrmProcessNeighborReport( pMac, pMsgBuf );
1220 break;
1221
1222 case eWNI_SME_BEACON_REPORT_REQ_IND:
1223 sme_RrmProcessBeaconReportReqInd( pMac, pMsgBuf );
1224 break;
1225
1226 default:
1227 //err msg
1228 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001229 FL("sme_RrmMsgProcessor:unknown msg type = %d"), msg_type);
Jeff Johnson295189b2012-06-20 16:38:30 -07001230
1231 break;
1232 }
1233
1234 return eHAL_STATUS_SUCCESS;
1235}
1236
1237/* ---------------------------------------------------------------------------
1238
1239 \fn rrmIterMeasTimerHandle
1240
1241 \brief Timer handler to handlet the timeout condition when a specific BT
1242
1243 stop event does not come back, in which case to restore back the
1244
1245 heartbeat timer.
1246
1247 \param pMac - The handle returned by macOpen.
1248
1249 \return VOID
1250
1251 ---------------------------------------------------------------------------*/
1252
1253void rrmIterMeasTimerHandle( v_PVOID_t userData )
1254{
1255 tpAniSirGlobal pMac = (tpAniSirGlobal) userData;
1256#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001257 smsLog( pMac, LOGE, "Randomization timer expired...send on next channel ");
Jeff Johnson295189b2012-06-20 16:38:30 -07001258#endif
1259 //Issue a scan req for next channel.
1260 sme_RrmIssueScanReq( pMac );
1261}
1262
1263/* ---------------------------------------------------------------------------
1264
1265 \fn rrmNeighborRspTimeoutHandler
1266
1267 \brief Timer handler to handle the timeout condition when a neighbor request is sent
1268 and no neighbor response is received from the AP
1269
1270 \param pMac - The handle returned by macOpen.
1271
1272 \return VOID
1273
1274---------------------------------------------------------------------------*/
1275
1276void rrmNeighborRspTimeoutHandler
1277( v_PVOID_t userData )
1278{
1279 tpAniSirGlobal pMac = (tpAniSirGlobal) userData;
1280#if defined WLAN_VOWIFI_DEBUG
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001281 smsLog( pMac, LOGE, "Neighbor Response timed out ");
Jeff Johnson295189b2012-06-20 16:38:30 -07001282#endif
1283 rrmIndicateNeighborReportResult(pMac, VOS_STATUS_E_FAILURE);
1284 return;
1285}
1286
1287/* ---------------------------------------------------------------------------
1288
1289 \fn rrmOpen
1290
1291 \brief
1292
1293 \param pMac - The handle returned by macOpen.
1294
1295 \return VOS_STATUS
1296
1297 VOS_STATUS_E_FAILURE success
1298
1299 VOS_STATUS_SUCCESS failure
1300
1301 ---------------------------------------------------------------------------*/
1302
1303VOS_STATUS rrmOpen (tpAniSirGlobal pMac)
1304
1305{
1306
1307 VOS_STATUS vosStatus;
1308 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
1309 eHalStatus halStatus = eHAL_STATUS_SUCCESS;
1310
1311 pSmeRrmContext->rrmConfig.maxRandnInterval = 50; //ms
1312
1313 vosStatus = vos_timer_init( &pSmeRrmContext->IterMeasTimer,
1314
1315 VOS_TIMER_TYPE_SW,
1316
1317 rrmIterMeasTimerHandle,
1318
1319 (void*) pMac);
1320
1321 if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
1322
1323 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "rrmOpen: Fail to init timer");
1324
1325 return VOS_STATUS_E_FAILURE;
1326 }
1327
1328 vosStatus = vos_timer_init( &pSmeRrmContext->neighborReqControlInfo.neighborRspWaitTimer,
1329
1330 VOS_TIMER_TYPE_SW,
1331
1332 rrmNeighborRspTimeoutHandler,
1333
1334 (void*) pMac);
1335
1336 if (!VOS_IS_STATUS_SUCCESS(vosStatus)) {
1337
1338 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "rrmOpen: Fail to init timer");
1339
1340 return VOS_STATUS_E_FAILURE;
1341 }
1342
1343 pSmeRrmContext->neighborReqControlInfo.isNeighborRspPending = eANI_BOOLEAN_FALSE;
1344
1345 halStatus = csrLLOpen(pMac->hHdd, &pSmeRrmContext->neighborReportCache);
1346 if (eHAL_STATUS_SUCCESS != halStatus)
1347 {
1348 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "rrmOpen: Fail to open neighbor cache result");
1349 return VOS_STATUS_E_FAILURE;
1350 }
1351
1352 return VOS_STATUS_SUCCESS;
1353}
1354
1355
1356/* ---------------------------------------------------------------------------
1357
1358 \fn rrmClose
1359
1360 \brief
1361
1362 \param pMac - The handle returned by macOpen.
1363
1364 \return VOS_STATUS
1365
1366 VOS_STATUS_E_FAILURE success
1367
1368 VOS_STATUS_SUCCESS failure
1369
1370 ---------------------------------------------------------------------------*/
1371
1372VOS_STATUS rrmClose (tpAniSirGlobal pMac)
1373
1374{
1375
1376 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
1377 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
1378
1379 if( VOS_TIMER_STATE_RUNNING == vos_timer_getCurrentState( &pSmeRrmContext->IterMeasTimer ) )
1380 {
1381 vosStatus = vos_timer_stop( &pSmeRrmContext->IterMeasTimer );
1382 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001383 {
Jeff Johnson295189b2012-06-20 16:38:30 -07001384 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, FL("Timer stop fail") );
1385 }
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001386 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001387
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001388 vosStatus = vos_timer_destroy( &pSmeRrmContext->IterMeasTimer );
1389 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
1390 {
Jeff Johnson295189b2012-06-20 16:38:30 -07001391
1392 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, FL("Fail to destroy timer") );
1393
1394 }
1395
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001396 if( VOS_TIMER_STATE_RUNNING ==
1397 vos_timer_getCurrentState( &pSmeRrmContext->neighborReqControlInfo.neighborRspWaitTimer ) )
1398 {
1399 vosStatus = vos_timer_stop( &pSmeRrmContext->neighborReqControlInfo.neighborRspWaitTimer );
1400 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
1401 {
1402 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, FL("Timer stop fail") );
1403 }
1404 }
1405
1406 vosStatus = vos_timer_destroy( &pSmeRrmContext->neighborReqControlInfo.neighborRspWaitTimer );
1407 if (!VOS_IS_STATUS_SUCCESS(vosStatus))
1408 {
1409 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_FATAL, FL("Fail to destroy timer") );
1410
1411 }
1412
Jeff Johnson295189b2012-06-20 16:38:30 -07001413 rrmLLPurgeNeighborCache(pMac, &pSmeRrmContext->neighborReportCache);
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001414
Jeff Johnson295189b2012-06-20 16:38:30 -07001415 csrLLClose(&pSmeRrmContext->neighborReportCache);
1416
1417 return vosStatus;
1418
1419}
1420
1421
1422
1423
1424/* ---------------------------------------------------------------------------
1425
1426 \fn rrmReady
1427
1428 \brief fn
1429
1430 \param pMac - The handle returned by macOpen.
1431
1432 \return VOS_STATUS
1433
1434 ---------------------------------------------------------------------------*/
1435
1436VOS_STATUS rrmReady (tpAniSirGlobal pMac)
1437
1438{
1439
1440 return VOS_STATUS_SUCCESS;
1441}
1442
1443/* ---------------------------------------------------------------------------
1444
1445 \fn rrmChangeDefaultConfigParam
1446 \brief fn
1447
1448 \param pMac - The handle returned by macOpen.
1449 \param pRrmConfig - pointer to new rrm configs.
1450
1451 \return VOS_STATUS
1452
1453 ---------------------------------------------------------------------------*/
1454VOS_STATUS rrmChangeDefaultConfigParam(tpAniSirGlobal pMac, tpRrmConfigParam pRrmConfig)
1455{
1456 vos_mem_copy( &pMac->rrm.rrmSmeContext.rrmConfig, pRrmConfig, sizeof( tRrmConfigParam ) );
1457
1458 return VOS_STATUS_SUCCESS;
1459}
1460
1461/* ---------------------------------------------------------------------------
1462
1463 \fn smeRrmGetFirstBssEntryFromNeighborCache()
1464
1465 \brief This function returns the first entry from the neighbor cache to the caller
1466
1467 \param pMac - The handle returned by macOpen.
1468
1469 \return VOID
1470
1471---------------------------------------------------------------------------*/
1472tRrmNeighborReportDesc* smeRrmGetFirstBssEntryFromNeighborCache( tpAniSirGlobal pMac)
1473{
1474 tListElem *pEntry;
1475 tRrmNeighborReportDesc *pTempBssEntry = NULL;
1476 tpRrmSMEContext pSmeRrmContext = &pMac->rrm.rrmSmeContext;
1477
1478
1479 pEntry = csrLLPeekHead( &pSmeRrmContext->neighborReportCache, LL_ACCESS_LOCK );
1480
1481 if(!pEntry || !csrLLCount(&pSmeRrmContext->neighborReportCache))
1482 {
1483 //list empty
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001484 smsLog(pMac, LOGW, FL("List empty"));
Jeff Johnson295189b2012-06-20 16:38:30 -07001485 return NULL;
1486 }
1487
1488 pTempBssEntry = GET_BASE_ADDR( pEntry, tRrmNeighborReportDesc, List );
1489
1490 return pTempBssEntry;
1491}
1492
1493/* ---------------------------------------------------------------------------
1494
1495 \fn smeRrmGetNextBssEntryFromNeighborCache()
1496
1497 \brief This function returns the entry next to the given entry from the
1498 neighbor cache to the caller
1499
1500 \param pMac - The handle returned by macOpen.
1501
1502 \return VOID
1503
1504---------------------------------------------------------------------------*/
1505tRrmNeighborReportDesc* smeRrmGetNextBssEntryFromNeighborCache( tpAniSirGlobal pMac,
1506 tpRrmNeighborReportDesc pBssEntry)
1507{
1508 tListElem *pEntry;
1509 tRrmNeighborReportDesc *pTempBssEntry = NULL;
1510
1511 pEntry = csrLLNext(&pMac->rrm.rrmSmeContext.neighborReportCache, &pBssEntry->List, LL_ACCESS_LOCK);
1512
1513 if(!pEntry)
1514 {
1515 //list empty
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001516 smsLog(pMac, LOGW, FL("List empty"));
Jeff Johnson295189b2012-06-20 16:38:30 -07001517 return NULL;
1518 }
1519
1520 pTempBssEntry = GET_BASE_ADDR( pEntry, tRrmNeighborReportDesc, List );
1521
1522 return pTempBssEntry;
1523}
1524
Srinivas Girigowda5cecb202013-10-08 09:13:25 -07001525#if defined(FEATURE_WLAN_CCX) && !defined(FEATURE_WLAN_CCX_UPLOAD)
Jeff Johnson295189b2012-06-20 16:38:30 -07001526void csrCcxSendAdjacentApRepMsg(tpAniSirGlobal pMac, tCsrRoamSession *pSession)
1527{
1528 tpSirAdjacentApRepInd pAdjRep;
1529 tANI_U16 length;
1530 tANI_U32 roamTS2;
1531
Kiran Kumar Lokere691dde12013-03-06 17:00:31 -08001532 smsLog( pMac, LOG1, "Adjacent AP Report Msg to PE");
Jeff Johnson295189b2012-06-20 16:38:30 -07001533
1534 length = sizeof(tSirAdjacentApRepInd );
1535 pAdjRep = vos_mem_malloc ( length );
1536
1537 if ( NULL == pAdjRep )
1538 {
1539 smsLog( pMac, LOGP, "Unable to allocate memory for Adjacent AP report");
1540 return;
1541 }
1542
1543 vos_mem_zero( pAdjRep, length );
1544 pAdjRep->messageType = eWNI_SME_CCX_ADJACENT_AP_REPORT;
1545 pAdjRep->length = length;
1546 pAdjRep->channelNum = pSession->prevOpChannel;
1547 vos_mem_copy( pAdjRep->bssid, &pSession->connectedProfile.bssid, sizeof(tSirMacAddr) );
1548 vos_mem_copy( pAdjRep->prevApMacAddr, &pSession->prevApBssid, sizeof(tSirMacAddr) );
1549 vos_mem_copy( &pAdjRep->prevApSSID, &pSession->prevApSSID, sizeof(tSirMacSSid) );
1550 roamTS2 = vos_timer_get_system_time();
1551 pAdjRep->tsmRoamdelay = roamTS2 - pSession->roamTS1;
1552 pAdjRep->roamReason =SIR_CCX_ASSOC_REASON_UNSPECIFIED;
1553 pAdjRep->clientDissSecs =(pAdjRep->tsmRoamdelay/1000);
1554
1555 palSendMBMessage(pMac->hHdd, pAdjRep);
1556
1557 return;
1558}
1559#endif /* FEATURE_WLAN_CCX */
1560#endif