blob: 1449f86c621ed79980e229f647fdb57c22e228a6 [file] [log] [blame]
Jeff Johnson295189b2012-06-20 16:38:30 -07001/*
Jeff Johnson32d95a32012-09-10 13:15:23 -07002 * Copyright (c) 2012, The Linux Foundation. All rights reserved.
Jeff Johnson295189b2012-06-20 16:38:30 -07003 *
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.
20 */
21
22/*
23 * */
24/** ------------------------------------------------------------------------- *
25 ------------------------------------------------------------------------- *
26
27
28 \file csrNeighborRoam.c
29
30 Implementation for the simple roaming algorithm for 802.11r Fast transitions and Legacy roaming for Android platform.
31
32 Copyright (C) 2010 Qualcomm, Incorporated
33
34
35 ========================================================================== */
36
37/*===========================================================================
38
39 EDIT HISTORY FOR FILE
40
41
42 This section contains comments describing changes made to the module.
43 Notice that changes are listed in reverse chronological order.
44
45
46
47 when who what, where, why
48---------- --- --------------------------------------------------------
4908/01/10 Murali Created
50
51===========================================================================*/
52#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING
53#include "wlan_qct_wda.h"
54#include "palApi.h"
55#include "csrInsideApi.h"
56#include "smsDebug.h"
57#include "logDump.h"
58#include "smeQosInternal.h"
59#include "wlan_qct_tl.h"
60#include "smeInside.h"
61#include "vos_diag_core_event.h"
62#include "vos_diag_core_log.h"
63#include "csrApi.h"
64#include "wlan_qct_tl.h"
65#include "sme_Api.h"
66#include "csrNeighborRoam.h"
67#ifdef FEATURE_WLAN_CCX
68#include "csrCcx.h"
69#endif
70
71#define WLAN_FEATURE_NEIGHBOR_ROAMING_DEBUG 1
72#ifdef WLAN_FEATURE_NEIGHBOR_ROAMING_DEBUG
73#define NEIGHBOR_ROAM_DEBUG smsLog
74#else
75#define NEIGHBOR_ROAM_DEBUG(x...)
76#endif
77
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -070078static void csrNeighborRoamResetChannelInfo(tpCsrNeighborRoamChannelInfo rChInfo);
79static void csrNeighborRoamResetCfgListChanScanControlInfo(tpAniSirGlobal pMac);
80static void csrNeighborRoamResetPreauthControlInfo(tpAniSirGlobal pMac);
81static void csrNeighborRoamDeregAllRssiIndication(tpAniSirGlobal pMac);
82
Jeff Johnson295189b2012-06-20 16:38:30 -070083VOS_STATUS csrNeighborRoamNeighborLookupUPCallback (v_PVOID_t pAdapter, v_U8_t rssiNotification,
Srinivasdaaec712012-12-12 15:59:44 -080084 v_PVOID_t pUserCtxt,
85 v_S7_t avgRssi);
Jeff Johnson295189b2012-06-20 16:38:30 -070086VOS_STATUS csrNeighborRoamNeighborLookupDOWNCallback (v_PVOID_t pAdapter, v_U8_t rssiNotification,
Srinivasdaaec712012-12-12 15:59:44 -080087 v_PVOID_t pUserCtxt,
88 v_S7_t avgRssi);
Jeff Johnson295189b2012-06-20 16:38:30 -070089void csrNeighborRoamRRMNeighborReportResult(void *context, VOS_STATUS vosStatus);
90eHalStatus csrRoamCopyConnectedProfile(tpAniSirGlobal pMac, tANI_U32 sessionId, tCsrRoamProfile *pDstProfile );
91
92#ifdef WLAN_FEATURE_VOWIFI_11R
93static eHalStatus csrNeighborRoamIssuePreauthReq(tpAniSirGlobal pMac);
94VOS_STATUS csrNeighborRoamIssueNeighborRptRequest(tpAniSirGlobal pMac);
95#endif
96
97/* State Transition macro */
98#define CSR_NEIGHBOR_ROAM_STATE_TRANSITION(newState)\
99{\
100 pMac->roam.neighborRoamInfo.prevNeighborRoamState = pMac->roam.neighborRoamInfo.neighborRoamState;\
101 pMac->roam.neighborRoamInfo.neighborRoamState = newState;\
Madan Mohan Koyyalamudi8bdd3112012-09-24 13:55:14 -0700102 smsLog(pMac, LOG1, FL("Neighbor Roam Transition from state %d ==> %d"), pMac->roam.neighborRoamInfo.prevNeighborRoamState, newState);\
Jeff Johnson295189b2012-06-20 16:38:30 -0700103}
104
105/* ---------------------------------------------------------------------------
106
107 \fn csrNeighborRoamFreeNeighborRoamBSSNode
108
109 \brief This function frees all the internal pointers CSR NeighborRoam BSS Info
110 and also frees the node itself
111
112 \param pMac - The handle returned by macOpen.
113 neighborRoamBSSNode - Neighbor Roam BSS Node to be freed
114
115 \return VOID
116
117---------------------------------------------------------------------------*/
118void csrNeighborRoamFreeNeighborRoamBSSNode(tpAniSirGlobal pMac, tpCsrNeighborRoamBSSInfo neighborRoamBSSNode)
119{
120 if (neighborRoamBSSNode)
121 {
122 if (neighborRoamBSSNode->pBssDescription)
123 {
124 vos_mem_free(neighborRoamBSSNode->pBssDescription);
125 neighborRoamBSSNode->pBssDescription = NULL;
126 }
127 vos_mem_free(neighborRoamBSSNode);
128 neighborRoamBSSNode = NULL;
129 }
130
131 return;
132}
133
134/* ---------------------------------------------------------------------------
135
136 \fn csrNeighborRoamRemoveRoamableAPListEntry
137
138 \brief This function removes a given entry from the given list
139
140 \param pMac - The handle returned by macOpen.
141 pList - The list from which the entry should be removed
142 pNeighborEntry - Neighbor Roam BSS Node to be removed
143
144 \return TRUE if successfully removed, else FALSE
145
146---------------------------------------------------------------------------*/
147tANI_BOOLEAN csrNeighborRoamRemoveRoamableAPListEntry(tpAniSirGlobal pMac,
148 tDblLinkList *pList, tpCsrNeighborRoamBSSInfo pNeighborEntry)
149{
150 if(pList)
151 {
152 return csrLLRemoveEntry(pList, &pNeighborEntry->List, LL_ACCESS_LOCK);
153 }
154
155 smsLog(pMac, LOGE, FL("Removing neighbor BSS node from list failed. Current count = %d\n"), csrLLCount(pList));
156
157 return eANI_BOOLEAN_FALSE;
158}
159
160/* ---------------------------------------------------------------------------
161
162 \fn csrNeighborRoamGetRoamableAPListNextEntry
163
164 \brief Gets the entry next to passed entry. If NULL is passed, return the entry in the head of the list
165
166 \param pMac - The handle returned by macOpen.
167 pList - The list from which the entry should be returned
168 pNeighborEntry - Neighbor Roam BSS Node whose next entry should be returned
169
170 \return Neighbor Roam BSS Node to be returned
171
172---------------------------------------------------------------------------*/
173tpCsrNeighborRoamBSSInfo csrNeighborRoamGetRoamableAPListNextEntry(tpAniSirGlobal pMac,
174 tDblLinkList *pList, tpCsrNeighborRoamBSSInfo pNeighborEntry)
175{
176 tListElem *pEntry = NULL;
177 tpCsrNeighborRoamBSSInfo pResult = NULL;
178
179 if(pList)
180 {
181 if(NULL == pNeighborEntry)
182 {
183 pEntry = csrLLPeekHead(pList, LL_ACCESS_LOCK);
184 }
185 else
186 {
187 pEntry = csrLLNext(pList, &pNeighborEntry->List, LL_ACCESS_LOCK);
188 }
189 if(pEntry)
190 {
191 pResult = GET_BASE_ADDR(pEntry, tCsrNeighborRoamBSSInfo, List);
192 }
193 }
194
195 return pResult;
196}
197
198/* ---------------------------------------------------------------------------
199
200 \fn csrNeighborRoamFreeRoamableBSSList
201
202 \brief Empties and frees all the nodes in the roamable AP list
203
204 \param pMac - The handle returned by macOpen.
205 pList - Neighbor Roam BSS List to be emptied
206
207 \return VOID
208
209---------------------------------------------------------------------------*/
210void csrNeighborRoamFreeRoamableBSSList(tpAniSirGlobal pMac, tDblLinkList *pList)
211{
212 tpCsrNeighborRoamBSSInfo pResult = NULL;
213
Mohit Khanna23863762012-09-11 17:40:09 -0700214 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Emptying the BSS list. Current count = %d\n"), csrLLCount(pList));
Jeff Johnson295189b2012-06-20 16:38:30 -0700215
216 /* Pick up the head, remove and free the node till the list becomes empty */
217 while ((pResult = csrNeighborRoamGetRoamableAPListNextEntry(pMac, pList, NULL)) != NULL)
218 {
219 csrNeighborRoamRemoveRoamableAPListEntry(pMac, pList, pResult);
220 csrNeighborRoamFreeNeighborRoamBSSNode(pMac, pResult);
221 }
222 return;
223}
224
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -0800225static void csrNeighborRoamTriggerHandoff(tpAniSirGlobal pMac,
226 tpCsrNeighborRoamControlInfo pNeighborRoamInfo)
227{
228#ifdef WLAN_FEATURE_VOWIFI_11R
229 if (pNeighborRoamInfo->is11rAssoc)
230 {
231 if (eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN == pNeighborRoamInfo->neighborRoamState)
232 {
233 csrNeighborRoamIssuePreauthReq(pMac);
234 }
235 else
236 {
237 smsLog(pMac, LOGE, FL("11R Reassoc indication received in unexpected state %d"), pNeighborRoamInfo->neighborRoamState);
238 VOS_ASSERT(0);
239 }
240 }
241 else
242#endif
243
244#ifdef FEATURE_WLAN_CCX
245 if (pNeighborRoamInfo->isCCXAssoc)
246 {
247 if (eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN == pNeighborRoamInfo->neighborRoamState)
248 {
249 csrNeighborRoamIssuePreauthReq(pMac);
250 }
251 else
252 {
253 smsLog(pMac, LOGE, FL("CCX Reassoc indication received in unexpected state %d"), pNeighborRoamInfo->neighborRoamState);
254 VOS_ASSERT(0);
255 }
256 }
257 else
258#endif
259#ifdef FEATURE_WLAN_LFR
260 if (csrRoamIsFastRoamEnabled(pMac, CSR_SESSION_ID_INVALID))
261 {
262 if (eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN == pNeighborRoamInfo->neighborRoamState)
263 {
264 csrNeighborRoamIssuePreauthReq(pMac);
265 }
266 else
267 {
268 smsLog(pMac, LOGE, FL("LFR Reassoc indication received in unexpected state %d"), pNeighborRoamInfo->neighborRoamState);
269 VOS_ASSERT(0);
270 }
271 }
272 else
273#endif
274 {
275 if (eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN == pNeighborRoamInfo->neighborRoamState)
276 {
277 csrNeighborRoamRequestHandoff(pMac);
278 }
279 else
280 {
281 smsLog(pMac, LOGE, FL("Non-11R Reassoc indication received in unexpected state %d"), pNeighborRoamInfo->neighborRoamState);
282 VOS_ASSERT(0);
283 }
284 }
285}
286
Jeff Johnson295189b2012-06-20 16:38:30 -0700287/* ---------------------------------------------------------------------------
288
289 \fn csrNeighborRoamReassocIndCallback
290
291 \brief Reassoc callback invoked by TL on crossing the registered re-assoc threshold.
292 Directly triggere HO in case of non-11r association
293 In case of 11R association, triggers a pre-auth eventually followed by actual HO
294
295 \param pAdapter - VOS Context
296 trafficStatus - UP/DOWN indication from TL
297 pUserCtxt - Parameter for callback registered during callback registration. Should be pMac
298
299 \return VOID
300
301---------------------------------------------------------------------------*/
302VOS_STATUS csrNeighborRoamReassocIndCallback(v_PVOID_t pAdapter,
303 v_U8_t trafficStatus,
Srinivasdaaec712012-12-12 15:59:44 -0800304 v_PVOID_t pUserCtxt,
305 v_S7_t avgRssi)
Jeff Johnson295189b2012-06-20 16:38:30 -0700306{
307 tpAniSirGlobal pMac = PMAC_STRUCT( pUserCtxt );
308 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
309 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
310
Srinivasdaaec712012-12-12 15:59:44 -0800311 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event reassoc callback with TL. Threshold RSSI = %d Reported RSSI = %d"),
312 pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
313 avgRssi);
Jeff Johnson295189b2012-06-20 16:38:30 -0700314
315 vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
316 WLANTL_HO_THRESHOLD_DOWN,
317 csrNeighborRoamReassocIndCallback,
318 VOS_MODULE_ID_SME);
319
320 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
321 {
322 //err msg
323 smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
324 }
325
Srinivasdaaec712012-12-12 15:59:44 -0800326 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Rcvd reassoc notification-deregister UP indication. Threshold RSSI = %d Reported RSSI = %d"),
327 NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1), avgRssi);
Madan Mohan Koyyalamudi4450acc2012-11-15 17:24:31 -0800328 vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext,
329 (v_S7_t)NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1),
330 WLANTL_HO_THRESHOLD_UP,
331 csrNeighborRoamNeighborLookupUPCallback,
332 VOS_MODULE_ID_SME);
Jeff Johnson295189b2012-06-20 16:38:30 -0700333
334 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
335 {
336 //err msg
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +0530337 smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamNeighborLookupUPCallback with TL: Status = %d\n"), vosStatus);
Jeff Johnson295189b2012-06-20 16:38:30 -0700338 }
339
340 /* We dont need to run this timer any more. */
341 palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
342
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -0800343 csrNeighborRoamTriggerHandoff(pMac, pNeighborRoamInfo);
Jeff Johnson295189b2012-06-20 16:38:30 -0700344
Jeff Johnson295189b2012-06-20 16:38:30 -0700345 return VOS_STATUS_SUCCESS;
346}
347
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700348/*CleanUP Routines*/
349static void csrNeighborRoamResetChannelInfo(tpCsrNeighborRoamChannelInfo rChInfo)
350{
351 if ((rChInfo->IAPPNeighborListReceived == FALSE) &&
352 (rChInfo->currentChannelListInfo.numOfChannels))
353 {
354 rChInfo->currentChanIndex = CSR_NEIGHBOR_ROAM_INVALID_CHANNEL_INDEX;
355 rChInfo->currentChannelListInfo.numOfChannels = 0;
356
357 if (rChInfo->currentChannelListInfo.ChannelList)
358 vos_mem_free(rChInfo->currentChannelListInfo.ChannelList);
359
360 rChInfo->currentChannelListInfo.ChannelList = NULL;
361 rChInfo->chanListScanInProgress = eANI_BOOLEAN_FALSE;
362 }
363 else
364 {
365 rChInfo->currentChanIndex = 0;
366 rChInfo->chanListScanInProgress = eANI_BOOLEAN_TRUE;
367 }
368}
369
370static void csrNeighborRoamResetCfgListChanScanControlInfo(tpAniSirGlobal pMac)
371{
372 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
373
374 /* Stop neighbor scan timer */
375 palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
376
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -0700377 /* Stop neighbor scan results refresh timer */
378 palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
379
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700380 /* Abort any ongoing scan */
381 if (eANI_BOOLEAN_TRUE == pNeighborRoamInfo->scanRspPending)
382 {
383 csrScanAbortMacScan(pMac);
384 }
385 pNeighborRoamInfo->scanRspPending = eANI_BOOLEAN_FALSE;
386
387 /* Reset roam channel list information */
388 csrNeighborRoamResetChannelInfo(&pNeighborRoamInfo->roamChannelInfo);
389}
390
391static void csrNeighborRoamResetPreauthControlInfo(tpAniSirGlobal pMac)
392{
393 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
394
395#if defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX) || defined(FEATURE_WLAN_LFR)
396 pNeighborRoamInfo->is11rAssoc = eANI_BOOLEAN_FALSE;
397 pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimerInfo.pMac = pMac;
398 pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimerInfo.sessionId =
399 CSR_SESSION_ID_INVALID;
400 /* Purge pre-auth fail list */
401 csrNeighborRoamPurgePreauthFailedList(pMac);
402#endif
403
404 pNeighborRoamInfo->FTRoamInfo.preauthRspPending = eANI_BOOLEAN_FALSE;
405 pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries = 0;
406#ifdef WLAN_FEATURE_VOWIFI_11R
407 /* Do not free up the preauth done list here */
408 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;
409 pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_FALSE;
410 pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport = 0;
411 vos_mem_zero(pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo, sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
412 palTimerStop(pMac->hHdd, pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimer);
413#endif
414}
415
416static void csrNeighborRoamDeregAllRssiIndication(tpAniSirGlobal pMac)
417{
418 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
419 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
420
421 NEIGHBOR_ROAM_DEBUG(pMac, LOG2,
422 FL("Deregister neighbor lookup UP callback with TL. RSSI = %d"),
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -0800423 NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1));
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700424
425 /* Deregister reassoc callback. Ignore return status */
426 vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext,
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -0800427 (v_S7_t)NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1),
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700428 WLANTL_HO_THRESHOLD_UP,
429 csrNeighborRoamNeighborLookupUPCallback,
430 VOS_MODULE_ID_SME);
431
432 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
433 {
434 smsLog(pMac, LOGW,
435 FL("Couldn't deregister csrNeighborRoamNeighborLookupUPCallback "
436 "with TL: Status = %d\n"), vosStatus);
437 }
438
439 NEIGHBOR_ROAM_DEBUG(pMac, LOG2,
440 FL("Deregistering reassoc DOWN callback with TL. RSSI = %d"),
441 pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1));
442
443 /* Deregister reassoc callback. Ignore return status */
444 vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext,
445 (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
446 WLANTL_HO_THRESHOLD_DOWN,
447 csrNeighborRoamReassocIndCallback,
448 VOS_MODULE_ID_SME);
449
450 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
451 {
452 smsLog(pMac, LOGW,
453 FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with "
454 "TL: Status = %d\n"), vosStatus);
455 }
456
457 NEIGHBOR_ROAM_DEBUG(pMac, LOG2,
458 FL("Deregistering neighborLookup DOWN callback with TL. RSSI = %d"),
459 pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
460
461 /* Deregister neighbor lookup callback. Ignore return status */
462 vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext,
463 (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
464 WLANTL_HO_THRESHOLD_DOWN,
465 csrNeighborRoamNeighborLookupDOWNCallback,
466 VOS_MODULE_ID_SME);
467
468 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
469 {
470 smsLog(pMac, LOGW,
471 FL(" Couldn't deregister csrNeighborRoamNeighborLookupDOWNCallback "
472 "with TL: Status = %d\n"), vosStatus);
473 }
474
475 /* Reset thresholds only after deregistering DOWN event from TL */
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700476 pNeighborRoamInfo->currentNeighborLookupThreshold =
477 pNeighborRoamInfo->cfgParams.neighborLookupThreshold;
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -0800478#ifdef FEATURE_WLAN_LFR
479 pNeighborRoamInfo->uEmptyScanCount = 0;
480#endif
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700481}
482
Jeff Johnson295189b2012-06-20 16:38:30 -0700483/* ---------------------------------------------------------------------------
484
485 \fn csrNeighborRoamResetConnectedStateControlInfo
486
487 \brief This function will reset the neighbor roam control info data structures.
488 This function should be invoked whenever we move to CONNECTED state from
489 any state other than INIT state
490
491 \param pMac - The handle returned by macOpen.
492
493 \return VOID
494
495---------------------------------------------------------------------------*/
496void csrNeighborRoamResetConnectedStateControlInfo(tpAniSirGlobal pMac)
497{
498 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
499
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700500 csrNeighborRoamResetChannelInfo(&pNeighborRoamInfo->roamChannelInfo);
Jeff Johnson295189b2012-06-20 16:38:30 -0700501 csrNeighborRoamFreeRoamableBSSList(pMac, &pNeighborRoamInfo->roamableAPList);
Jeff Johnson295189b2012-06-20 16:38:30 -0700502
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700503 /* We dont need to run this timer any more. */
504 palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
Jeff Johnson295189b2012-06-20 16:38:30 -0700505
506#ifdef WLAN_FEATURE_VOWIFI_11R
507 /* Do not free up the preauth done list here */
508 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;
509 pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_FALSE;
510 pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries = 0;
511 pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport = 0;
512 pNeighborRoamInfo->FTRoamInfo.preauthRspPending = 0;
513 vos_mem_zero(pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo, sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
514 palTimerStop(pMac->hHdd, pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimer);
515#endif
516
517}
518
Madan Mohan Koyyalamudi4f292df2012-09-18 17:27:40 -0700519void csrNeighborRoamResetReportScanStateControlInfo(tpAniSirGlobal pMac)
Jeff Johnson295189b2012-06-20 16:38:30 -0700520{
521 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
Jeff Johnson295189b2012-06-20 16:38:30 -0700522 pNeighborRoamInfo->csrSessionId = CSR_SESSION_ID_INVALID;
523 vos_mem_set(pNeighborRoamInfo->currAPbssid, sizeof(tCsrBssid), 0);
524 pNeighborRoamInfo->neighborScanTimerInfo.pMac = pMac;
525 pNeighborRoamInfo->neighborScanTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
Jeff Johnson295189b2012-06-20 16:38:30 -0700526#ifdef FEATURE_WLAN_CCX
527 pNeighborRoamInfo->isCCXAssoc = eANI_BOOLEAN_FALSE;
528 pNeighborRoamInfo->isVOAdmitted = eANI_BOOLEAN_FALSE;
529 pNeighborRoamInfo->MinQBssLoadRequired = 0;
530#endif
Madan Mohan Koyyalamudi595208a2012-10-05 12:48:38 -0700531
532 /* Stop scan refresh timer */
533 palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700534 /* Purge roamable AP list */
535 csrNeighborRoamFreeRoamableBSSList(pMac, &pNeighborRoamInfo->roamableAPList);
Jeff Johnson295189b2012-06-20 16:38:30 -0700536 return;
537}
538
Madan Mohan Koyyalamudi4f292df2012-09-18 17:27:40 -0700539/* ---------------------------------------------------------------------------
540
541 \fn csrNeighborRoamResetInitStateControlInfo
542
543 \brief This function will reset the neighbor roam control info data structures.
544 This function should be invoked whenever we move to CONNECTED state from
545 INIT state
546
547 \param pMac - The handle returned by macOpen.
548
549 \return VOID
550
551---------------------------------------------------------------------------*/
552void csrNeighborRoamResetInitStateControlInfo(tpAniSirGlobal pMac)
553{
554 csrNeighborRoamResetConnectedStateControlInfo(pMac);
555
556 /* In addition to the above resets, we should clear off the curAPBssId/Session ID in the timers */
557 csrNeighborRoamResetReportScanStateControlInfo(pMac);
558}
559
560
561
Jeff Johnson295189b2012-06-20 16:38:30 -0700562#ifdef WLAN_FEATURE_VOWIFI_11R
563/* ---------------------------------------------------------------------------
564
565 \fn csrNeighborRoamBssIdScanFilter
566
567 \brief This API is used to prepare a filter to obtain scan results when
568 we complete the scan in the REPORT_SCAN state after receiving a
569 valid neighbor report from AP. This filter includes BSSIDs received from
570 the neighbor report from the AP in addition to the other filter parameters
571 created from connected profile
572
573 \param pMac - The handle returned by macOpen.
574 pScanFilter - Scan filter to be filled and returned
575
576 \return eHAL_STATUS_SUCCESS on succesful filter creation, corresponding error
577 code otherwise
578
579---------------------------------------------------------------------------*/
580static eHalStatus csrNeighborRoamBssIdScanFilter(tpAniSirGlobal pMac, tCsrScanResultFilter *pScanFilter)
581{
582 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
583 tANI_U8 i = 0;
584
585 VOS_ASSERT(pScanFilter != NULL);
586 vos_mem_zero(pScanFilter, sizeof(tCsrScanResultFilter));
587
588 pScanFilter->BSSIDs.numOfBSSIDs = pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport;
589 pScanFilter->BSSIDs.bssid = vos_mem_malloc(sizeof(tSirMacAddr) * pScanFilter->BSSIDs.numOfBSSIDs);
590 if (NULL == pScanFilter->BSSIDs.bssid)
591 {
592 smsLog(pMac, LOGE, FL("Scan Filter BSSID mem alloc failed"));
593 return eHAL_STATUS_FAILED_ALLOC;
594 }
595
596 vos_mem_zero(pScanFilter->BSSIDs.bssid, sizeof(tSirMacAddr) * pScanFilter->BSSIDs.numOfBSSIDs);
597
598 /* Populate the BSSID from Neighbor BSS info received from neighbor report */
599 for (i = 0; i < pScanFilter->BSSIDs.numOfBSSIDs; i++)
600 {
601 vos_mem_copy(&pScanFilter->BSSIDs.bssid[i],
602 pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo[i].neighborBssId, sizeof(tSirMacAddr));
603 }
604
605 /* Fill other general scan filter params */
606 return csrNeighborRoamPrepareScanProfileFilter(pMac, pScanFilter);
607}
608
609/* ---------------------------------------------------------------------------
610
611 \fn csrNeighborRoamPurgePreauthFailList
612
613 \brief This function empties the preauth fail list
614
615 \param pMac - The handle returned by macOpen.
616
617 \return VOID
618
619---------------------------------------------------------------------------*/
620void csrNeighborRoamPurgePreauthFailList(tpAniSirGlobal pMac)
621{
622 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
623
624 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Purging the preauth fail list"));
625 while (pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress)
626 {
627 vos_mem_zero(pNeighborRoamInfo->FTRoamInfo.preAuthFailList.macAddress[pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress-1],
628 sizeof(tSirMacAddr));
629 pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress--;
630 }
631 return;
632}
633
634/* ---------------------------------------------------------------------------
635
636 \fn csrNeighborRoamAddBssIdToPreauthFailList
637
638 \brief This function adds the given BSSID to the Preauth fail list
639
640 \param pMac - The handle returned by macOpen.
641 bssId - BSSID to be added to the preauth fail list
642
643 \return eHAL_STATUS_SUCCESS on success, eHAL_STATUS_FAILURE otherwise
644
645---------------------------------------------------------------------------*/
646eHalStatus csrNeighborRoamAddBssIdToPreauthFailList(tpAniSirGlobal pMac, tSirMacAddr bssId)
647{
648 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
649
650 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL(" Added BSSID %02x:%02x:%02x:%02x:%02x:%02x to Preauth failed list\n"),
651 bssId[0], bssId[1], bssId[2], bssId[3], bssId[4], bssId[5]);
652
653
654 if ((pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress + 1) >
655 MAX_NUM_PREAUTH_FAIL_LIST_ADDRESS)
656 {
657 smsLog(pMac, LOGE, FL("Preauth fail list already full.. Cannot add new one"));
658 return eHAL_STATUS_FAILURE;
659 }
660 vos_mem_copy(pNeighborRoamInfo->FTRoamInfo.preAuthFailList.macAddress[pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress],
661 bssId, sizeof(tSirMacAddr));
662 pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress++;
663
664 return eHAL_STATUS_SUCCESS;
665}
666
667/* ---------------------------------------------------------------------------
668
669 \fn csrNeighborRoamIsPreauthCandidate
670
671 \brief This function checks whether the given MAC address is already
672 present in the preauth fail list and returns TRUE/FALSE accordingly
673
674 \param pMac - The handle returned by macOpen.
675
676 \return eANI_BOOLEAN_TRUE if preauth candidate, eANI_BOOLEAN_FALSE otherwise
677
678---------------------------------------------------------------------------*/
679tANI_BOOLEAN csrNeighborRoamIsPreauthCandidate(tpAniSirGlobal pMac, tSirMacAddr bssId)
680{
681 tANI_U8 i = 0;
682 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
683
684 if (0 == pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress)
685 return eANI_BOOLEAN_TRUE;
686
687 for (i = 0; i < pNeighborRoamInfo->FTRoamInfo.preAuthFailList.numMACAddress; i++)
688 {
689 if (VOS_TRUE == vos_mem_compare(pNeighborRoamInfo->FTRoamInfo.preAuthFailList.macAddress[i],
690 bssId, sizeof(tSirMacAddr)))
691 {
692 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("BSSID %02x:%02x:%02x:%02x:%02x:%02x already present in preauth fail list"),
693 bssId[0], bssId[1], bssId[2], bssId[3], bssId[4], bssId[5]);
694 return eANI_BOOLEAN_FALSE;
695 }
696 }
697
698 return eANI_BOOLEAN_TRUE;
699}
700
701/* ---------------------------------------------------------------------------
702
703 \fn csrNeighborRoamIssuePreauthReq
704
705 \brief This function issues preauth request to PE with the 1st AP entry in the
706 roamable AP list
707
708 \param pMac - The handle returned by macOpen.
709
710 \return eHAL_STATUS_SUCCESS on success, eHAL_STATUS_FAILURE otherwise
711
712---------------------------------------------------------------------------*/
713static eHalStatus csrNeighborRoamIssuePreauthReq(tpAniSirGlobal pMac)
714{
715 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
716 eHalStatus status = eHAL_STATUS_SUCCESS;
717 tpCsrNeighborRoamBSSInfo pNeighborBssNode;
718
719 /* This must not be true here */
720 VOS_ASSERT(pNeighborRoamInfo->FTRoamInfo.preauthRspPending == eANI_BOOLEAN_FALSE);
721
722 /* Issue Preauth request to PE here */
723 /* Need to issue the preauth request with the BSSID that is there in the head of the roamable AP list */
724 /* Parameters that should be passed are BSSID, Channel number and the neighborScanPeriod(probably) */
725 /* If roamableAPList gets empty, should transition to REPORT_SCAN state */
726 pNeighborBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->roamableAPList, NULL);
727
728 if (NULL == pNeighborBssNode)
729 {
730 smsLog(pMac, LOG1, FL("Roamable AP list is empty.. "));
731 return eHAL_STATUS_FAILURE;
732 }
733 else
734 {
Madan Mohan Koyyalamudi286b60e2012-10-11 12:59:07 -0700735 status = csrRoamEnqueuePreauth(pMac, pNeighborRoamInfo->csrSessionId, pNeighborBssNode->pBssDescription,
736 eCsrPerformPreauth, eANI_BOOLEAN_TRUE);
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +0530737
738 smsLog(pMac, LOGE, FL("Before Pre-Auth: BSSID %02x:%02x:%02x:%02x:%02x:%02x %d"),
739 pNeighborBssNode->pBssDescription->bssId[0],
740 pNeighborBssNode->pBssDescription->bssId[1],
741 pNeighborBssNode->pBssDescription->bssId[2],
742 pNeighborBssNode->pBssDescription->bssId[3],
743 pNeighborBssNode->pBssDescription->bssId[4],
744 pNeighborBssNode->pBssDescription->bssId[5]);
745 smsLog(pMac, LOGE, FL("Before Pre-Auth: Channel %d\n"), (int)pNeighborBssNode->pBssDescription->channelId);
746
Jeff Johnson295189b2012-06-20 16:38:30 -0700747 if (eHAL_STATUS_SUCCESS != status)
748 {
749 smsLog(pMac, LOGE, FL("Send Preauth request to PE failed with status %d\n"), status);
750 return status;
751 }
752 }
753
754 pNeighborRoamInfo->FTRoamInfo.preauthRspPending = eANI_BOOLEAN_TRUE;
755
756 /* Increment the preauth retry count */
757 pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries++;
758
759 /* Transition the state to preauthenticating */
760 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_PREAUTHENTICATING)
Madan Mohan Koyyalamudi286b60e2012-10-11 12:59:07 -0700761#if 0
Jeff Johnson295189b2012-06-20 16:38:30 -0700762 /* Start the preauth rsp timer */
763 status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimer,
764 CSR_NEIGHBOR_ROAM_PREAUTH_RSP_WAIT_MULTIPLIER * pNeighborRoamInfo->cfgParams.neighborScanPeriod * PAL_TIMER_TO_MS_UNIT,
765 eANI_BOOLEAN_FALSE);
766 if (eHAL_STATUS_SUCCESS != status)
767 {
768 smsLog(pMac, LOGE, FL("Preauth response wait timer start failed with status %d\n"), status);
769 return status;
770 }
Madan Mohan Koyyalamudi286b60e2012-10-11 12:59:07 -0700771#endif
Jeff Johnson295189b2012-06-20 16:38:30 -0700772
773 return status;
774}
775
776/* ---------------------------------------------------------------------------
777
778 \fn csrNeighborRoamPreauthRspHandler
779
780 \brief This function handle the Preauth response from PE
781 Every preauth is allowed max 3 tries if it fails. If a bssid failed
782 for more than MAX_TRIES, we will remove it from the list and try
783 with the next node in the roamable AP list and add the BSSID to pre-auth failed
784 list. If no more entries present in
785 roamable AP list, transition to REPORT_SCAN state
786
787 \param pMac - The handle returned by macOpen.
788 vosStatus - VOS_STATUS_SUCCESS/FAILURE/TIMEOUT status from PE
789
Madan Mohan Koyyalamudi7a579cc2012-10-21 11:25:39 -0700790 \return eHAL_STATUS_SUCCESS on success (i.e. pre-auth processed),
791 eHAL_STATUS_FAILURE otherwise
Jeff Johnson295189b2012-06-20 16:38:30 -0700792
793---------------------------------------------------------------------------*/
Madan Mohan Koyyalamudi7a579cc2012-10-21 11:25:39 -0700794eHalStatus csrNeighborRoamPreauthRspHandler(tpAniSirGlobal pMac, VOS_STATUS vosStatus)
Jeff Johnson295189b2012-06-20 16:38:30 -0700795{
796 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
797 eHalStatus status = eHAL_STATUS_SUCCESS;
Madan Mohan Koyyalamudi7a579cc2012-10-21 11:25:39 -0700798 eHalStatus preauthProcessed = eHAL_STATUS_SUCCESS;
Jeff Johnson295189b2012-06-20 16:38:30 -0700799 tpCsrNeighborRoamBSSInfo pPreauthRspNode = NULL;
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700800
801 if (eANI_BOOLEAN_FALSE == pNeighborRoamInfo->FTRoamInfo.preauthRspPending)
802 {
803
804 /* This can happen when we disconnect immediately
805 * after sending a pre-auth request. During processing
806 * of the disconnect command, we would have reset
807 * preauthRspPending and transitioned to INIT state.
808 */
809 NEIGHBOR_ROAM_DEBUG(pMac, LOGW,
810 FL("Unexpected pre-auth response in state %d\n"),
811 pNeighborRoamInfo->neighborRoamState);
Madan Mohan Koyyalamudi7a579cc2012-10-21 11:25:39 -0700812 preauthProcessed = eHAL_STATUS_FAILURE;
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700813 goto DEQ_PREAUTH;
814 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700815
816 // We can receive it in these 2 states.
Jeff Johnson295189b2012-06-20 16:38:30 -0700817 if ((pNeighborRoamInfo->neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_PREAUTHENTICATING) &&
818 (pNeighborRoamInfo->neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN))
819 {
Madan Mohan Koyyalamudi8186a9e2012-10-11 14:23:43 -0700820 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("Preauth response received in state %d\n"),
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700821 pNeighborRoamInfo->neighborRoamState);
Madan Mohan Koyyalamudi7a579cc2012-10-21 11:25:39 -0700822 preauthProcessed = eHAL_STATUS_FAILURE;
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700823 goto DEQ_PREAUTH;
Jeff Johnson295189b2012-06-20 16:38:30 -0700824 }
825
826 if (VOS_STATUS_E_TIMEOUT != vosStatus)
827 {
Madan Mohan Koyyalamudi286b60e2012-10-11 12:59:07 -0700828#if 0
Jeff Johnson295189b2012-06-20 16:38:30 -0700829 /* This means we got the response from PE. Hence stop the timer */
830 status = palTimerStop(pMac->hHdd, pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimer);
Madan Mohan Koyyalamudi286b60e2012-10-11 12:59:07 -0700831#endif
Jeff Johnson295189b2012-06-20 16:38:30 -0700832 pNeighborRoamInfo->FTRoamInfo.preauthRspPending = eANI_BOOLEAN_FALSE;
833 }
834
835 if (VOS_STATUS_SUCCESS == vosStatus)
836 {
837 pPreauthRspNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->roamableAPList, NULL);
838 }
839 if ((VOS_STATUS_SUCCESS == vosStatus) && (NULL != pPreauthRspNode))
840 {
841 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Preauth completed successfully after %d tries\n"), pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries);
842
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +0530843 smsLog(pMac, LOGE, FL("After Pre-Auth: BSSID %02x:%02x:%02x:%02x:%02x:%02x\n"),
844 pPreauthRspNode->pBssDescription->bssId[0],
845 pPreauthRspNode->pBssDescription->bssId[1],
846 pPreauthRspNode->pBssDescription->bssId[2],
847 pPreauthRspNode->pBssDescription->bssId[3],
848 pPreauthRspNode->pBssDescription->bssId[4],
849 pPreauthRspNode->pBssDescription->bssId[5]);
850 smsLog(pMac, LOGE, FL("After Pre-Auth: Channel %d\n"), (int)pPreauthRspNode->pBssDescription->channelId);
851
Jeff Johnson295189b2012-06-20 16:38:30 -0700852 /* Preauth competer successfully. Insert the preauthenticated node to tail of preAuthDoneList */
853 csrNeighborRoamRemoveRoamableAPListEntry(pMac, &pNeighborRoamInfo->roamableAPList, pPreauthRspNode);
854 csrLLInsertTail(&pNeighborRoamInfo->FTRoamInfo.preAuthDoneList, &pPreauthRspNode->List, LL_ACCESS_LOCK);
855
856 /* Pre-auth completed successfully. Transition to PREAUTH Done state */
857 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE)
858 pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries = 0;
859
860 /* The caller of this function would start a timer and by the time it expires, supplicant should
861 have provided the updated FTIEs to SME. So, when it expires, handoff will be triggered then */
862 }
863 else
864 {
865 tpCsrNeighborRoamBSSInfo pNeighborBssNode = NULL;
866 tListElem *pEntry;
867
868 smsLog(pMac, LOGE, FL("Preauth failed retry number %d, status = %d\n"), pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries, vosStatus);
869
870 /* Preauth failed. Add the bssId to the preAuth failed list MAC Address. Also remove the AP from roamable AP list */
871 if (pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries >= CSR_NEIGHBOR_ROAM_MAX_NUM_PREAUTH_RETRIES)
872 {
873 /* We are going to remove the node as it fails for more than MAX tries. Reset this count to 0 */
874 pNeighborRoamInfo->FTRoamInfo.numPreAuthRetries = 0;
875
876 /* The one in the head of the list should be one with which we issued pre-auth and failed */
877 pEntry = csrLLRemoveHead(&pNeighborRoamInfo->roamableAPList, LL_ACCESS_LOCK);
878 if(pEntry)
879 {
880 pNeighborBssNode = GET_BASE_ADDR(pEntry, tCsrNeighborRoamBSSInfo, List);
881 /* Add the BSSID to pre-auth fail list */
882 status = csrNeighborRoamAddBssIdToPreauthFailList(pMac, pNeighborBssNode->pBssDescription->bssId);
883 /* Now we can free this node */
884 csrNeighborRoamFreeNeighborRoamBSSNode(pMac, pNeighborBssNode);
885 }
886 }
887
888 /* Issue preauth request for the same/next entry */
889 if (eHAL_STATUS_SUCCESS == csrNeighborRoamIssuePreauthReq(pMac))
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700890 goto DEQ_PREAUTH;
Jeff Johnson295189b2012-06-20 16:38:30 -0700891
Madan Mohan Koyyalamudi4450acc2012-11-15 17:24:31 -0800892 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN);
893
894 /* Register Neighbor Lookup threshold callback with TL for UP event now */
895 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("No more pre-auth candidates-"
896 "register UP indication with TL. RSSI = %d,"), NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1));
897
898 vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext,
899 (v_S7_t)NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1),
900 WLANTL_HO_THRESHOLD_UP,
901 csrNeighborRoamNeighborLookupUPCallback,
902 VOS_MODULE_ID_SME, pMac);
903 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
904 {
905 //err msg
906 smsLog(pMac, LOGE, FL(" Couldn't register csrNeighborRoamNeighborLookupCallback UP event with TL: Status = %d\n"), status);
907 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700908
909 /* Start the neighbor results refresh timer and transition to REPORT_SCAN state to perform scan again */
910 status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer,
911 pNeighborRoamInfo->cfgParams.neighborResultsRefreshPeriod * PAL_TIMER_TO_MS_UNIT,
912 eANI_BOOLEAN_FALSE);
913 if (eHAL_STATUS_SUCCESS != status)
914 {
915 smsLog(pMac, LOGE, FL("Neighbor results refresh timer start failed with status %d\n"), status);
Jeff Johnson295189b2012-06-20 16:38:30 -0700916 }
917 }
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -0700918
919DEQ_PREAUTH:
920 csrRoamDequeuePreauth(pMac);
Madan Mohan Koyyalamudi7a579cc2012-10-21 11:25:39 -0700921 return preauthProcessed;
Jeff Johnson295189b2012-06-20 16:38:30 -0700922}
923#endif /* WLAN_FEATURE_NEIGHBOR_ROAMING */
924
925/* ---------------------------------------------------------------------------
926
927 \fn csrNeighborRoamPrepareScanProfileFilter
928
929 \brief This function creates a scan filter based on the currently connected profile.
930 Based on this filter, scan results are obtained
931
932 \param pMac - The handle returned by macOpen.
933 pScanFilter - Populated scan filter based on the connected profile
934
935 \return eHAL_STATUS_SUCCESS on success, eHAL_STATUS_FAILURE otherwise
936
937---------------------------------------------------------------------------*/
938eHalStatus csrNeighborRoamPrepareScanProfileFilter(tpAniSirGlobal pMac, tCsrScanResultFilter *pScanFilter)
939{
940 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
941 tANI_U8 sessionId = (tANI_U8)pNeighborRoamInfo->csrSessionId;
942 tCsrRoamConnectedProfile *pCurProfile = &pMac->roam.roamSession[sessionId].connectedProfile;
943 tANI_U8 i = 0;
944
945 VOS_ASSERT(pScanFilter != NULL);
946
947 vos_mem_zero(pScanFilter, sizeof(tCsrScanResultFilter));
948
949 /* We dont want to set BSSID based Filter */
950 pScanFilter->BSSIDs.numOfBSSIDs = 0;
951
952 /* Populate all the information from the connected profile */
953 pScanFilter->SSIDs.numOfSSIDs = 1;
954 pScanFilter->SSIDs.SSIDList = vos_mem_malloc(sizeof(tCsrSSIDInfo));
955 if (NULL == pScanFilter->SSIDs.SSIDList)
956 {
957 smsLog(pMac, LOGE, FL("Scan Filter SSID mem alloc failed"));
958 return eHAL_STATUS_FAILED_ALLOC;
959 }
960 pScanFilter->SSIDs.SSIDList->handoffPermitted = 1;
961 pScanFilter->SSIDs.SSIDList->ssidHidden = 0;
962 pScanFilter->SSIDs.SSIDList->SSID.length = pCurProfile->SSID.length;
963 vos_mem_copy((void *)pScanFilter->SSIDs.SSIDList->SSID.ssId, (void *)pCurProfile->SSID.ssId, pCurProfile->SSID.length);
964
965 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Filtering for SSID %s from scan results.. SSID Length = %d\n"),
966 pScanFilter->SSIDs.SSIDList->SSID.ssId, pScanFilter->SSIDs.SSIDList->SSID.length);
967 pScanFilter->authType.numEntries = 1;
968 pScanFilter->authType.authType[0] = pCurProfile->AuthType;
969
970 pScanFilter->EncryptionType.numEntries = 1; //This must be 1
971 pScanFilter->EncryptionType.encryptionType[0] = pCurProfile->EncryptionType;
972
973 pScanFilter->mcEncryptionType.numEntries = 1;
974 pScanFilter->mcEncryptionType.encryptionType[0] = pCurProfile->mcEncryptionType;
975
976 pScanFilter->BSSType = pCurProfile->BSSType;
977
978 /* We are intrested only in the scan results on channels that we scanned */
979 pScanFilter->ChannelInfo.numOfChannels = pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels;
980 pScanFilter->ChannelInfo.ChannelList = vos_mem_malloc(pScanFilter->ChannelInfo.numOfChannels * sizeof(tANI_U8));
981 if (NULL == pScanFilter->ChannelInfo.ChannelList)
982 {
983 smsLog(pMac, LOGE, FL("Scan Filter Channel list mem alloc failed"));
984 vos_mem_free(pScanFilter->SSIDs.SSIDList);
985 pScanFilter->SSIDs.SSIDList = NULL;
986 return eHAL_STATUS_FAILED_ALLOC;
987 }
988 for (i = 0; i < pScanFilter->ChannelInfo.numOfChannels; i++)
989 {
990 pScanFilter->ChannelInfo.ChannelList[i] = pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[i];
991 }
992
993#ifdef WLAN_FEATURE_VOWIFI_11R
994 if (pNeighborRoamInfo->is11rAssoc)
995 {
996 /* MDIE should be added as a part of profile. This should be added as a part of filter as well */
997 pScanFilter->MDID.mdiePresent = pCurProfile->MDID.mdiePresent;
998 pScanFilter->MDID.mobilityDomain = pCurProfile->MDID.mobilityDomain;
999 }
1000#endif
1001
1002 return eHAL_STATUS_SUCCESS;
1003}
1004
Jeff Johnson43971f52012-07-17 12:26:56 -07001005tANI_U32 csrGetCurrentAPRssi(tpAniSirGlobal pMac, tScanResultHandle *pScanResultList)
1006{
1007 tCsrScanResultInfo *pScanResult;
1008 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
1009 tANI_U32 CurrAPRssi = -125; /* We are setting this as default value to make sure we return this value,
1010 when we do not see this AP in the scan result for some reason.However,it is
1011 less likely that we are associated to an AP and do not see it in the scan list*/
1012
1013 while (NULL != (pScanResult = csrScanResultGetNext(pMac, *pScanResultList)))
1014 {
1015
1016 if (VOS_TRUE == vos_mem_compare(pScanResult->BssDescriptor.bssId,
1017 pNeighborRoamInfo->currAPbssid, sizeof(tSirMacAddr)))
1018 {
1019 /* We got a match with the currently associated AP.
1020 * Capture the RSSI value and complete the while loop.
1021 * The while loop is completed in order to make the current entry go back to NULL,
1022 * and in the next while loop, it properly starts searching from the head of the list.
1023 * TODO: Can also try setting the current entry directly to NULL as soon as we find the new AP*/
1024
1025 CurrAPRssi = (int)pScanResult->BssDescriptor.rssi * (-1) ;
1026
1027 } else {
1028 continue;
1029 }
1030 }
1031
1032 return CurrAPRssi;
1033
1034}
1035
Jeff Johnson295189b2012-06-20 16:38:30 -07001036/* ---------------------------------------------------------------------------
1037
1038 \fn csrNeighborRoamProcessScanResults
1039
1040 \brief This function extracts scan results, sorts on the basis of neighbor score(todo).
1041 Assumed that the results are already sorted by RSSI by csrScanGetResult
1042
1043 \param pMac - The handle returned by macOpen.
1044 pScanResultList - Scan result result obtained from csrScanGetResult()
1045
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -08001046 \return tANI_BOOLEAN - return TRUE if we have a candidate we can immediately
1047 roam to. Otherwise, return FALSE.
Jeff Johnson295189b2012-06-20 16:38:30 -07001048
1049---------------------------------------------------------------------------*/
1050
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -08001051static tANI_BOOLEAN csrNeighborRoamProcessScanResults(tpAniSirGlobal pMac,
1052 tScanResultHandle *pScanResultList)
Jeff Johnson295189b2012-06-20 16:38:30 -07001053{
1054 tCsrScanResultInfo *pScanResult;
1055 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
1056 tpCsrNeighborRoamBSSInfo pBssInfo;
Jeff Johnson43971f52012-07-17 12:26:56 -07001057 tANI_U32 CurrAPRssi;
1058 tANI_U8 RoamRssiDiff = pMac->roam.configParam.RoamRssiDiff;
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -08001059#if defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX) || defined(FEATURE_WLAN_LFR)
1060 tANI_U8 immediateRoamRssiDiff = pMac->roam.configParam.nImmediateRoamRssiDiff;
1061#endif
1062 tANI_BOOLEAN roamNow = eANI_BOOLEAN_FALSE;
Jeff Johnson43971f52012-07-17 12:26:56 -07001063
1064 /***************************************************************
1065 * Find out the Current AP RSSI and keep it handy to check if
1066 * it is better than the RSSI of the AP which we are
1067 * going to roam.If so, we are going to continue with the
1068 * current AP.
1069 ***************************************************************/
1070 CurrAPRssi = csrGetCurrentAPRssi(pMac, pScanResultList);
Jeff Johnson295189b2012-06-20 16:38:30 -07001071
1072 /* Expecting the scan result already to be in the sorted order based on the RSSI */
1073 /* Based on the previous state we need to check whether the list should be sorted again taking neighbor score into consideration */
1074 /* If previous state is CFG_CHAN_LIST_SCAN, there should not be any neighbor score associated with any of the BSS.
1075 If the previous state is REPORT_QUERY, then there will be neighbor score for each of the APs */
1076 /* 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
1077 and rssi score are in the same order. This will be taken care later */
1078
1079 while (NULL != (pScanResult = csrScanResultGetNext(pMac, *pScanResultList)))
1080 {
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001081 NEIGHBOR_ROAM_DEBUG(pMac, LOGE,
1082 FL("Scan result: BSSID %02x:%02x:%02x:%02x:%02x:%02x (Rssi %d)"),
1083 pScanResult->BssDescriptor.bssId[0],
1084 pScanResult->BssDescriptor.bssId[1],
1085 pScanResult->BssDescriptor.bssId[2],
1086 pScanResult->BssDescriptor.bssId[3],
1087 pScanResult->BssDescriptor.bssId[4],
1088 pScanResult->BssDescriptor.bssId[5],
1089 abs(pScanResult->BssDescriptor.rssi));
Jeff Johnson295189b2012-06-20 16:38:30 -07001090
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001091 if (VOS_TRUE == vos_mem_compare(pScanResult->BssDescriptor.bssId,
Jeff Johnson295189b2012-06-20 16:38:30 -07001092 pNeighborRoamInfo->currAPbssid, sizeof(tSirMacAddr)))
1093 {
Jeff Johnson43971f52012-07-17 12:26:56 -07001094 /* currently associated AP. Do not have this in the roamable AP list */
Madan Mohan Koyyalamudi4450acc2012-11-15 17:24:31 -08001095 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1096 "SKIP-currently associated AP\n");
Jeff Johnson295189b2012-06-20 16:38:30 -07001097 continue;
1098 }
1099
Jeff Johnson43971f52012-07-17 12:26:56 -07001100 /* This condition is to ensure to roam to an AP with better RSSI. if the value of RoamRssiDiff is Zero, this feature
1101 * is disabled and we continue to roam without any check*/
1102 if(RoamRssiDiff > 0)
1103 {
Madan Mohan Koyyalamudif553b742012-12-03 16:37:39 -08001104 /*
1105 * If RSSI is lower than the lookup threshold, then continue.
1106 */
1107 if (abs(pScanResult->BssDescriptor.rssi) >
1108 pNeighborRoamInfo->currentNeighborLookupThreshold)
1109 {
1110 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1111 "%s: [INFOLOG] new ap rssi (%d) lower than lookup threshold (%d)\n",
1112 __func__, (int)pScanResult->BssDescriptor.rssi * (-1),
1113 (int)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
1114 continue;
1115 }
1116
Jeff Johnson43971f52012-07-17 12:26:56 -07001117 if (abs(CurrAPRssi) < abs(pScanResult->BssDescriptor.rssi))
1118 {
1119 /*Do not roam to an AP with worse RSSI than the current*/
1120 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1121 "%s: [INFOLOG]Current AP rssi=%d new ap rssi worse=%d\n", __func__,
1122 CurrAPRssi,
1123 (int)pScanResult->BssDescriptor.rssi * (-1) );
1124 continue;
1125 } else {
1126 /*Do not roam to an AP which is having better RSSI than the current AP, but still less than the
1127 * margin that is provided by user from the ini file (RoamRssiDiff)*/
1128 if (abs(abs(CurrAPRssi) - abs(pScanResult->BssDescriptor.rssi)) < RoamRssiDiff)
1129 {
Madan Mohan Koyyalamudi4450acc2012-11-15 17:24:31 -08001130 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1131 "%s: [INFOLOG]Current AP rssi=%d new ap rssi=%d not good enough, roamRssiDiff=%d\n", __func__,
1132 CurrAPRssi,
1133 (int)pScanResult->BssDescriptor.rssi * (-1),
1134 RoamRssiDiff);
Jeff Johnson43971f52012-07-17 12:26:56 -07001135 continue;
1136 }
1137 else {
1138 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1139 "%s: [INFOLOG]Current AP rssi=%d new ap rssi better=%d\n", __func__,
1140 CurrAPRssi,
1141 (int)pScanResult->BssDescriptor.rssi * (-1) );
1142 }
1143 }
1144 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001145
1146#ifdef WLAN_FEATURE_VOWIFI_11R
1147 if (pNeighborRoamInfo->is11rAssoc)
1148 {
1149 if (!csrNeighborRoamIsPreauthCandidate(pMac, pScanResult->BssDescriptor.bssId))
1150 {
1151 smsLog(pMac, LOGE, FL("BSSID present in pre-auth fail list.. Ignoring"));
1152 continue;
1153 }
1154 }
1155#endif /* WLAN_FEATURE_VOWIFI_11R */
1156
1157#ifdef FEATURE_WLAN_CCX
1158 if (pNeighborRoamInfo->isCCXAssoc)
1159 {
1160 if (!csrNeighborRoamIsPreauthCandidate(pMac, pScanResult->BssDescriptor.bssId))
1161 {
1162 smsLog(pMac, LOGE, FL("BSSID present in pre-auth fail list.. Ignoring"));
1163 continue;
1164 }
1165 }
1166 if ((pScanResult->BssDescriptor.QBSSLoad_present) &&
1167 (pScanResult->BssDescriptor.QBSSLoad_avail))
1168 {
1169 if (pNeighborRoamInfo->isVOAdmitted)
1170 {
1171 smsLog(pMac, LOG1, FL("New AP has %x BW available\n"), (unsigned int)pScanResult->BssDescriptor.QBSSLoad_avail);
1172 smsLog(pMac, LOG1, FL("We need %x BW available\n"),(unsigned int)pNeighborRoamInfo->MinQBssLoadRequired);
1173 if (pScanResult->BssDescriptor.QBSSLoad_avail < pNeighborRoamInfo->MinQBssLoadRequired)
1174 {
1175 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1176 "[INFOLOG]BSSID : %02x:%02x:%02x:%02x:%02x:%02x has no bandwidth ignoring..not adding to roam list\n",
1177 pScanResult->BssDescriptor.bssId[0],
1178 pScanResult->BssDescriptor.bssId[1],
1179 pScanResult->BssDescriptor.bssId[2],
1180 pScanResult->BssDescriptor.bssId[3],
1181 pScanResult->BssDescriptor.bssId[4],
1182 pScanResult->BssDescriptor.bssId[5]);
1183 continue;
1184 }
1185 }
1186 }
1187 else
1188 {
1189 smsLog(pMac, LOGE, FL("No QBss %x %x\n"), (unsigned int)pScanResult->BssDescriptor.QBSSLoad_avail, (unsigned int)pScanResult->BssDescriptor.QBSSLoad_present);
1190 if (pNeighborRoamInfo->isVOAdmitted)
1191 {
1192 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1193 "[INFOLOG]BSSID : %02x:%02x:%02x:%02x:%02x:%02x has no QBSSLoad IE, ignoring..not adding to roam list\n",
1194 pScanResult->BssDescriptor.bssId[0],
1195 pScanResult->BssDescriptor.bssId[1],
1196 pScanResult->BssDescriptor.bssId[2],
1197 pScanResult->BssDescriptor.bssId[3],
1198 pScanResult->BssDescriptor.bssId[4],
1199 pScanResult->BssDescriptor.bssId[5]);
1200 continue;
1201 }
1202 }
1203#endif /* FEATURE_WLAN_CCX */
1204
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001205#ifdef FEATURE_WLAN_LFR
1206 // If we are supporting legacy roaming, and
1207 // if the candidate is on the "pre-auth failed" list, ignore it.
Madan Mohan Koyyalamudi03aae5f2012-11-28 01:51:22 +05301208 if (csrRoamIsFastRoamEnabled(pMac, CSR_SESSION_ID_INVALID))
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001209 {
1210 if (!csrNeighborRoamIsPreauthCandidate(pMac, pScanResult->BssDescriptor.bssId))
1211 {
1212 smsLog(pMac, LOGE, FL("BSSID present in pre-auth fail list.. Ignoring"));
1213 continue;
1214 }
1215 }
1216#endif /* FEATURE_WLAN_LFR */
1217
Jeff Johnson295189b2012-06-20 16:38:30 -07001218 /* If the received timestamp in BSS description is earlier than the scan request timestamp, skip
1219 * this result */
1220 if (pNeighborRoamInfo->scanRequestTimeStamp >= pScanResult->BssDescriptor.nReceivedTime)
1221 {
1222 smsLog(pMac, LOGE, FL("Ignoring BSS as it is older than the scan request timestamp"));
1223 continue;
1224 }
1225
1226 pBssInfo = vos_mem_malloc(sizeof(tCsrNeighborRoamBSSInfo));
1227 if (NULL == pBssInfo)
1228 {
1229 smsLog(pMac, LOGE, FL("Memory allocation for Neighbor Roam BSS Info failed.. Just ignoring"));
1230 continue;
1231 }
1232
1233 pBssInfo->pBssDescription = vos_mem_malloc(pScanResult->BssDescriptor.length + sizeof(pScanResult->BssDescriptor.length));
1234 if (pBssInfo->pBssDescription != NULL)
1235 {
1236 vos_mem_copy(pBssInfo->pBssDescription, &pScanResult->BssDescriptor,
1237 pScanResult->BssDescriptor.length + sizeof(pScanResult->BssDescriptor.length));
1238 }
1239 else
1240 {
1241 smsLog(pMac, LOGE, FL("Memory allocation for Neighbor Roam BSS Descriptor failed.. Just ignoring"));
1242 vos_mem_free(pBssInfo);
1243 continue;
1244
1245 }
1246 pBssInfo->apPreferenceVal = 10; //some value for now. Need to calculate the actual score based on RSSI and neighbor AP score
1247
1248 /* Just add to the end of the list as it is already sorted by RSSI */
1249 csrLLInsertTail(&pNeighborRoamInfo->roamableAPList, &pBssInfo->List, LL_ACCESS_LOCK);
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -08001250
1251#if defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX) || defined(FEATURE_WLAN_LFR)
1252 if (immediateRoamRssiDiff &&
1253 (abs(abs(CurrAPRssi) - abs(pScanResult->BssDescriptor.rssi)) >= immediateRoamRssiDiff))
1254 {
1255 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1256 "%s: [INFOLOG] potential candidate to roam immediately (diff=%d, expected=%d)",
1257 __func__, abs(abs(CurrAPRssi) - abs(pScanResult->BssDescriptor.rssi)),
1258 immediateRoamRssiDiff);
1259 roamNow = eANI_BOOLEAN_TRUE;
1260 }
1261#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07001262 }
1263
1264 /* 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 */
1265 csrScanResultPurge(pMac, *pScanResultList);
1266
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -08001267 return roamNow;
Jeff Johnson295189b2012-06-20 16:38:30 -07001268}
1269
1270/* ---------------------------------------------------------------------------
1271
1272 \fn csrNeighborRoamHandleEmptyScanResult
1273
1274 \brief This function will be invoked in CFG_CHAN_LIST_SCAN state when
1275 there are no valid APs in the scan result for roaming. This means
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001276 our AP is the best and no other AP is around. No point in scanning
Jeff Johnson295189b2012-06-20 16:38:30 -07001277 again and again. Performing the following here.
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001278 1. Stop the neighbor scan timer.
1279 2a. If this is the first time we encountered empty scan, then
1280 re-register with TL with modified lookup threshold.
1281 2b. Else if this is the second time we encountered empty scan,
1282 then start neighbor scan results refresh timer (20s).
1283 2c. Else, nothing more to do.
1284 NOTE: In LFR, channels selected for scanning is dervied from
1285 the occuped channel list. Scan cycle following one which
1286 yielded empty results is split into two halves: (i) scan on
1287 channels in the occupied list, and (ii) scan on channels not
1288 in the occupied list. This helps converging faster (while
1289 looking for candidates in the occupied list first), and also,
1290 adds channels to the occupied channel list upon finding candidates
1291 matching SSID profile of interest.
1292
1293 uEmptyScanCount Comments
1294 eFirstEmptyScan Previous scan was done on channels in the
1295 occupied list and yielded potential candidates.
1296 This scan cycle was likely triggered through
1297 receipt of lookup DOWN notification event.
1298 eSecondEmptyScan Previous scan was done on channels in the
1299 occupied list and yielded no candidates. This scan
1300 cycle was triggered through RSSI notification
1301 with modified lookup threshold.
1302 eThirdEmptyScan Previous scan was done on channels NOT in
1303 the occupied list and yielded no candidates. This
1304 scan cycle was triggered immediately after scanning
1305 channels in the occupied list and no candidates
1306 were found.
1307 eFourthEmptyScan Previous scan was done on channels in the
1308 occupied list and yielded no candidates. This scan
1309 cycle was triggered upon expiry of
1310 neighborScanResultsRefreshPeriod (=20s).
1311 eFifthEmptyScan Previous scan was done on channels NOT in
1312 the occupied list and yielded no candidates. This
1313 scan cycle was triggered immediately after scanning
1314 channels in the occupied list and no candidates
1315 were found.
1316
1317 [1], [2,3] and [4,5] together form one discrete set of scan cycle.
Jeff Johnson295189b2012-06-20 16:38:30 -07001318
1319 \param pMac - The handle returned by macOpen.
1320
1321 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
1322
1323---------------------------------------------------------------------------*/
1324static VOS_STATUS csrNeighborRoamHandleEmptyScanResult(tpAniSirGlobal pMac)
1325{
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001326 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
Jeff Johnson295189b2012-06-20 16:38:30 -07001327 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
1328 eHalStatus status = eHAL_STATUS_SUCCESS;
1329
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001330 /* Stop neighbor scan timer */
Jeff Johnson295189b2012-06-20 16:38:30 -07001331 status = palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001332 if (eHAL_STATUS_SUCCESS != status)
Jeff Johnson295189b2012-06-20 16:38:30 -07001333 {
1334 smsLog(pMac, LOGW, FL(" palTimerStop failed with status %d\n"), status);
1335 }
1336
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001337 /*
1338 * Increase the neighbor lookup threshold by 3 dB
1339 * after every scan cycle. NOTE: uEmptyScanCount
1340 * would be either 1, 3 or 5 at the end of every
1341 * scan cycle.
1342 */
1343#ifdef FEATURE_WLAN_LFR
1344 if ((++pNeighborRoamInfo->uEmptyScanCount) > eFifthEmptyScan)
1345 {
1346 pNeighborRoamInfo->uEmptyScanCount = eFifthEmptyScan;
1347 }
1348#endif
1349 if (((pNeighborRoamInfo->currentNeighborLookupThreshold+3) <
1350 pNeighborRoamInfo->cfgParams.neighborReassocThreshold)
1351#ifdef FEATURE_WLAN_LFR
1352 && ((pNeighborRoamInfo->uEmptyScanCount % 2) == 1)
1353#endif
1354 )
1355 {
1356 pNeighborRoamInfo->currentNeighborLookupThreshold += 3;
1357 }
1358
Jeff Johnson295189b2012-06-20 16:38:30 -07001359#ifdef WLAN_FEATURE_VOWIFI_11R
1360 /* Clear off the old neighbor report details */
1361 vos_mem_zero(&pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo, sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
1362#endif
1363
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001364#ifdef FEATURE_WLAN_LFR
1365 if (pNeighborRoamInfo->uEmptyScanCount == eFirstEmptyScan)
1366 {
1367#endif
1368 /* Empty scan results for the first time */
1369 /* Transition to CONNECTED state */
1370 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CONNECTED);
1371
1372 /* Reset all the necessary variables before transitioning to the CONNECTED state */
1373 csrNeighborRoamResetConnectedStateControlInfo(pMac);
1374
1375 /* Re-register neighbor lookup DOWN threshold callback with TL */
1376 NEIGHBOR_ROAM_DEBUG(pMac, LOGE,
1377 FL("Registering DOWN event neighbor lookup callback with TL for RSSI = %d"),
1378 pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
1379
1380 vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext,
1381 (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
1382 WLANTL_HO_THRESHOLD_DOWN,
1383 csrNeighborRoamNeighborLookupDOWNCallback,
1384 VOS_MODULE_ID_SME, pMac);
1385
1386 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
1387 {
1388 smsLog(pMac, LOGW,
1389 FL("Couldn't re-register csrNeighborRoamNeighborLookupDOWNCallback"
1390 " with TL: Status = %d\n"), status);
1391 }
1392#ifdef FEATURE_WLAN_LFR
1393 }
1394 else if ((pNeighborRoamInfo->uEmptyScanCount == eSecondEmptyScan) ||
1395 (pNeighborRoamInfo->uEmptyScanCount == eFourthEmptyScan))
1396 {
1397 /* Empty scan results for the second or fourth time */
1398 /* Transition to CONNECTED state */
1399 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CONNECTED);
1400
1401 /* Reset all the necessary variables before transitioning to the CONNECTED state */
1402 csrNeighborRoamResetConnectedStateControlInfo(pMac);
1403
1404 /* Immediately scan on channels in non-occupied list */
1405 csrNeighborRoamTransitToCFGChanScan(pMac);
1406 }
1407 else if (pNeighborRoamInfo->uEmptyScanCount == eThirdEmptyScan)
1408 {
1409 /* Empty scan results for the third time */
1410 /* Remain in eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN */
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001411 /* Start neighbor scan results refresh timer */
1412 if (eHAL_STATUS_SUCCESS !=
1413 palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer,
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001414 pNeighborRoamInfo->cfgParams.neighborResultsRefreshPeriod * PAL_TIMER_TO_MS_UNIT,
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001415 eANI_BOOLEAN_FALSE))
Jeff Johnson295189b2012-06-20 16:38:30 -07001416 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001417 smsLog(pMac, LOGE, FL("Neighbor results refresh timer failed to start (%d)"),
1418 status);
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001419 vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
1420 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001421 vosStatus = VOS_STATUS_E_FAILURE;
1422 }
1423 else
1424 {
1425 smsLog(pMac, LOG2, FL("Neighbor results refresh timer started (%ld ms)"),
1426 (pNeighborRoamInfo->cfgParams.neighborResultsRefreshPeriod * PAL_TIMER_TO_MS_UNIT));
1427 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001428 }
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001429 else
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001430 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001431 /* Do nothing */
1432 /* Transition to CONNECTED state */
1433 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CONNECTED);
1434
1435 /* Reset all the necessary variables before transitioning to the CONNECTED state */
1436 csrNeighborRoamResetConnectedStateControlInfo(pMac);
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001437 }
1438
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001439 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, "Neighbor roam empty scan count=%d",
1440 pNeighborRoamInfo->uEmptyScanCount);
1441#endif
1442 return vosStatus;
Jeff Johnson295189b2012-06-20 16:38:30 -07001443}
1444
1445/* ---------------------------------------------------------------------------
1446
1447 \fn csrNeighborRoamScanRequestCallback
1448
1449 \brief This function is the callback function registered in csrScanRequest() to
1450 indicate the completion of scan. If scan is completed for all the channels in
1451 the channel list, this function gets the scan result and starts the refresh results
1452 timer to avoid having stale results. If scan is not completed on all the channels,
1453 it restarts the neighbor scan timer which on expiry issues scan on the next
1454 channel
1455
1456 \param halHandle - The handle returned by macOpen.
1457 pContext - not used
1458 scanId - not used
1459 status - not used
1460
1461 \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
1462
1463---------------------------------------------------------------------------*/
1464static eHalStatus csrNeighborRoamScanRequestCallback(tHalHandle halHandle, void *pContext,
1465 tANI_U32 scanId, eCsrScanStatus status)
1466{
1467 tpAniSirGlobal pMac = (tpAniSirGlobal) halHandle;
1468 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
1469 tANI_U8 currentChanIndex;
1470 tCsrScanResultFilter scanFilter;
1471 tScanResultHandle scanResult;
1472 tANI_U32 tempVal = 0;
Jeff Johnson43971f52012-07-17 12:26:56 -07001473 eHalStatus hstatus;
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -08001474 tANI_BOOLEAN roamNow = eANI_BOOLEAN_FALSE;
Jeff Johnson295189b2012-06-20 16:38:30 -07001475
1476 pMac->roam.neighborRoamInfo.scanRspPending = eANI_BOOLEAN_FALSE;
1477
1478 /* This can happen when we receive a UP event from TL in any of the scan states. Silently ignore it */
1479 if (eCSR_NEIGHBOR_ROAM_STATE_CONNECTED == pNeighborRoamInfo->neighborRoamState)
1480 {
1481 smsLog(pMac, LOGE, FL("Received in CONNECTED state. Must be because a UP event from TL after issuing scan request. Ignore it"));
1482 return eHAL_STATUS_SUCCESS;
1483 }
1484
1485 /* -1 is done because the chanIndex would have got incremented after issuing a successful scan request */
1486 currentChanIndex = (pMac->roam.neighborRoamInfo.roamChannelInfo.currentChanIndex) ? (pMac->roam.neighborRoamInfo.roamChannelInfo.currentChanIndex - 1) : 0;
1487
1488 /* Validate inputs */
1489 if (pMac->roam.neighborRoamInfo.roamChannelInfo.currentChannelListInfo.ChannelList) {
1490 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("csrNeighborRoamScanRequestCallback received for Channel = %d, ChanIndex = %d"),
1491 pMac->roam.neighborRoamInfo.roamChannelInfo.currentChannelListInfo.ChannelList[currentChanIndex], currentChanIndex);
1492 }
1493 else
1494 {
1495 smsLog(pMac, LOG1, FL("Received during clean-up. Silently ignore scan completion event."));
1496 return eHAL_STATUS_SUCCESS;
1497 }
1498
1499 if (eANI_BOOLEAN_FALSE == pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress)
1500 {
1501 /* Scan is completed in the CFG_CHAN_SCAN state. We can transition to REPORT_SCAN state
1502 just to get the results and perform PREAUTH */
1503 /* Now we have completed scanning the channel list. We have get the result by applying appropriate filter
1504 sort the results based on neighborScore and RSSI and select the best candidate out of the list */
1505 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("Channel list scan completed. Current chan index = %d"), currentChanIndex);
1506 VOS_ASSERT(pNeighborRoamInfo->roamChannelInfo.currentChanIndex == 0);
1507
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001508#if defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX) || defined(FEATURE_WLAN_LFR)
Jeff Johnson295189b2012-06-20 16:38:30 -07001509 /* If the state is REPORT_SCAN, then this must be the scan after the REPORT_QUERY state. So, we
1510 should use the BSSID filter made out of neighbor reports */
1511 if (eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN == pNeighborRoamInfo->neighborRoamState)
1512 {
Jeff Johnson43971f52012-07-17 12:26:56 -07001513 hstatus = csrNeighborRoamBssIdScanFilter(pMac, &scanFilter);
1514 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("11R or CCX Association: Prepare scan filter status with neighbor AP = %d"), hstatus);
Jeff Johnson295189b2012-06-20 16:38:30 -07001515 tempVal = 1;
1516 }
1517 else
1518#endif
1519 {
Jeff Johnson43971f52012-07-17 12:26:56 -07001520 hstatus = csrNeighborRoamPrepareScanProfileFilter(pMac, &scanFilter);
1521 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("11R/CCX/Other Association: Prepare scan to find neighbor AP filter status = %d"), hstatus);
Jeff Johnson295189b2012-06-20 16:38:30 -07001522 }
Jeff Johnson43971f52012-07-17 12:26:56 -07001523 if (eHAL_STATUS_SUCCESS != hstatus)
Jeff Johnson295189b2012-06-20 16:38:30 -07001524 {
1525 smsLog(pMac, LOGE, FL("Scan Filter preparation failed for Assoc type %d.. Bailing out.."), tempVal);
1526 return eHAL_STATUS_FAILURE;
1527 }
Jeff Johnson43971f52012-07-17 12:26:56 -07001528 hstatus = csrScanGetResult(pMac, &scanFilter, &scanResult);
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05301529 if (hstatus != eHAL_STATUS_SUCCESS)
1530 {
1531 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Get Scan Result status code %d"), hstatus);
1532 }
Jeff Johnson295189b2012-06-20 16:38:30 -07001533 /* Process the scan results and update roamable AP list */
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -08001534 roamNow = csrNeighborRoamProcessScanResults(pMac, &scanResult);
Jeff Johnson295189b2012-06-20 16:38:30 -07001535
1536 /* Free the scan filter */
1537 csrFreeScanFilter(pMac, &scanFilter);
1538
1539 tempVal = csrLLCount(&pNeighborRoamInfo->roamableAPList);
1540
1541 switch(pNeighborRoamInfo->neighborRoamState)
1542 {
1543 case eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN:
1544 if (tempVal)
1545 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001546#ifdef FEATURE_WLAN_LFR
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001547 /*
1548 * Since there are non-zero candidates found
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001549 * after the scan, reset empty scan count.
Madan Mohan Koyyalamudi04039a12012-10-21 12:24:56 -07001550 */
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08001551 pNeighborRoamInfo->uEmptyScanCount = 0;
1552#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07001553#ifdef WLAN_FEATURE_VOWIFI_11R
1554 /* If this is a non-11r association, then we can register the reassoc callback here as we have some
1555 APs in the roamable AP list */
1556 if (pNeighborRoamInfo->is11rAssoc)
1557 {
1558 /* Valid APs are found after scan. Now we can initiate pre-authentication */
1559 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN)
1560 }
1561 else
1562#endif
1563#ifdef FEATURE_WLAN_CCX
1564 /* If this is a non-11r association, then we can register the reassoc callback here as we have some
1565 APs in the roamable AP list */
1566 if (pNeighborRoamInfo->isCCXAssoc)
1567 {
1568 /* Valid APs are found after scan. Now we can initiate pre-authentication */
1569 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN)
1570 }
1571 else
1572#endif
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001573#ifdef FEATURE_WLAN_LFR
1574 /* If LFR is enabled, then we can register the reassoc callback here as we have some
1575 APs in the roamable AP list */
Madan Mohan Koyyalamudi03aae5f2012-11-28 01:51:22 +05301576 if (csrRoamIsFastRoamEnabled(pMac, CSR_SESSION_ID_INVALID))
Jeff Johnson04dd8a82012-06-29 20:41:40 -07001577 {
1578 /* Valid APs are found after scan. Now we can initiate pre-authentication */
1579 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN)
1580 }
1581 else
1582#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07001583 {
1584
1585 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Completed scanning of CFG CHAN LIST in non-11r association. Registering reassoc callback"));
1586 /* Nothing much to do now. Will continue to remain in this state in case of non-11r association */
1587 /* Stop the timer. But how long the roamable AP list will be valid in here. At some point of time, we
1588 need to restart the CFG CHAN list scan procedure if reassoc callback is not invoked from TL
1589 within certain duration */
1590
1591// palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
1592 }
1593 }
1594 else
1595 {
Madan Mohan Koyyalamudib40e5582012-10-11 16:48:42 -07001596 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("No candidate found after scanning in state %d.. "), pNeighborRoamInfo->neighborRoamState);
1597 /* Handle it appropriately */
1598 csrNeighborRoamHandleEmptyScanResult(pMac);
Jeff Johnson295189b2012-06-20 16:38:30 -07001599 }
1600 break;
1601#ifdef WLAN_FEATURE_VOWIFI_11R
1602 case eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN:
1603 if (!tempVal)
1604 {
1605 smsLog(pMac, LOGE, FL("No candidate found after scanning in state %d.. "), pNeighborRoamInfo->neighborRoamState);
1606 /* Stop the timer here as the same timer will be started again in CFG_CHAN_SCAN_STATE */
1607 csrNeighborRoamTransitToCFGChanScan(pMac);
1608 }
1609 break;
1610#endif /* WLAN_FEATURE_VOWIFI_11R */
1611 default:
1612 // Can come only in INIT state. Where in we are associated, we sent scan and user
1613 // in the meantime decides to disassoc, we will be in init state and still received call
1614 // back issued. Should not come here in any other state, printing just in case
1615 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
1616 "%s: [INFOLOG] State %d\n", __func__, (pNeighborRoamInfo->neighborRoamState));
1617
1618 // Lets just exit out silently.
1619 return eHAL_STATUS_SUCCESS;
1620 }
1621
1622 if (tempVal)
1623 {
1624 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
1625
Madan Mohan Koyyalamudi62b55b02012-12-03 16:45:39 -08001626 if (roamNow)
1627 {
1628 NEIGHBOR_ROAM_DEBUG(pMac, LOG2,
1629 FL("Immediate roam-deregister UP indication. RSSI = %d"),
1630 NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1));
1631
1632 vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext,
1633 (v_S7_t)NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1),
1634 WLANTL_HO_THRESHOLD_UP,
1635 csrNeighborRoamNeighborLookupUPCallback,
1636 VOS_MODULE_ID_SME);
1637
1638 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
1639 {
1640 smsLog(pMac, LOGW,
1641 FL("Couldn't deregister lookup UP callback with TL: Status = %d\n"), vosStatus);
1642 }
1643
1644 csrNeighborRoamTriggerHandoff(pMac, pNeighborRoamInfo);
1645 return eHAL_STATUS_SUCCESS;
1646 }
1647
Jeff Johnson295189b2012-06-20 16:38:30 -07001648 /* This timer should be started before registering the Reassoc callback with TL. This is because, it is very likely
1649 * that the callback getting called immediately and the timer would never be stopped when pre-auth is in progress */
1650 if (eHAL_STATUS_SUCCESS != palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer,
1651 pNeighborRoamInfo->cfgParams.neighborResultsRefreshPeriod * PAL_TIMER_TO_MS_UNIT,
1652 eANI_BOOLEAN_FALSE))
1653 {
1654 smsLog(pMac, LOGE, FL("Neighbor results refresh timer failed to start, status = %d"), status);
1655 vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
1656 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
Jeff Johnson43971f52012-07-17 12:26:56 -07001657 return eHAL_STATUS_FAILURE;
Jeff Johnson295189b2012-06-20 16:38:30 -07001658 }
Jeff Johnson43971f52012-07-17 12:26:56 -07001659
Jeff Johnson295189b2012-06-20 16:38:30 -07001660 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering DOWN event Reassoc callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1));
1661 /* Register a reassoc Indication callback */
1662 vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
1663 WLANTL_HO_THRESHOLD_DOWN,
1664 csrNeighborRoamReassocIndCallback,
1665 VOS_MODULE_ID_SME, pMac);
1666
1667 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
1668 {
1669 //err msg
1670 smsLog(pMac, LOGW, FL(" Couldn't register csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
1671 }
1672
1673 }
1674 }
1675 else
1676 {
1677
1678 /* Restart the timer for the next scan sequence as scanning is not over */
Jeff Johnson43971f52012-07-17 12:26:56 -07001679 hstatus = palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer,
Jeff Johnson295189b2012-06-20 16:38:30 -07001680 pNeighborRoamInfo->cfgParams.neighborScanPeriod * PAL_TIMER_TO_MS_UNIT,
1681 eANI_BOOLEAN_FALSE);
1682
Jeff Johnson43971f52012-07-17 12:26:56 -07001683 if (eHAL_STATUS_SUCCESS != hstatus)
Jeff Johnson295189b2012-06-20 16:38:30 -07001684 {
1685 /* Timer start failed.. Should we ASSERT here??? */
1686 smsLog(pMac, LOGE, FL("Neighbor scan PAL Timer start failed, status = %d, Ignoring state transition"), status);
1687 vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
1688 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
Jeff Johnson43971f52012-07-17 12:26:56 -07001689 return eHAL_STATUS_FAILURE;
Jeff Johnson295189b2012-06-20 16:38:30 -07001690 }
1691 }
1692 return eHAL_STATUS_SUCCESS;
1693}
1694
1695/* ---------------------------------------------------------------------------
1696
1697 \fn csrNeighborRoamIssueBgScanRequest
1698
1699 \brief This function issues CSR scan request after populating all the BG scan params
1700 passed
1701
1702 \param pMac - The handle returned by macOpen.
1703 pBgScanParams - Params that need to be populated into csr Scan request
1704
1705 \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
1706
1707---------------------------------------------------------------------------*/
1708eHalStatus csrNeighborRoamIssueBgScanRequest(tpAniSirGlobal pMac, tCsrBGScanRequest *pBgScanParams)
1709{
1710 eHalStatus status = eHAL_STATUS_SUCCESS;
1711 tANI_U32 scanId;
1712 tCsrScanRequest scanReq;
1713 tANI_U8 channel;
1714
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05301715 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("csrNeighborRoamIssueBgScanRequest for Channel = %d, ChanIndex = %d"),
Jeff Johnson295189b2012-06-20 16:38:30 -07001716 pBgScanParams->ChannelInfo.ChannelList[0], pMac->roam.neighborRoamInfo.roamChannelInfo.currentChanIndex);
1717
1718
1719 //send down the scan req for 1 channel on the associated SSID
1720 palZeroMemory(pMac->hHdd, &scanReq, sizeof(tCsrScanRequest));
1721 /* Fill in the SSID Info */
1722 scanReq.SSIDs.numOfSSIDs = 1;
1723 scanReq.SSIDs.SSIDList = vos_mem_malloc(sizeof(tCsrSSIDInfo) * scanReq.SSIDs.numOfSSIDs);
1724 if(NULL == scanReq.SSIDs.SSIDList)
1725 {
1726 //err msg
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05301727 smsLog(pMac, LOGE, FL("Couldn't allocate memory for the SSID..Freeing memory allocated for Channel List\n"));
Jeff Johnson295189b2012-06-20 16:38:30 -07001728 return eHAL_STATUS_FAILURE;
1729 }
1730 vos_mem_zero(scanReq.SSIDs.SSIDList, sizeof(tCsrSSIDInfo) * scanReq.SSIDs.numOfSSIDs);
1731
1732 scanReq.SSIDs.SSIDList[0].handoffPermitted = eANI_BOOLEAN_TRUE;
1733 scanReq.SSIDs.SSIDList[0].ssidHidden = eANI_BOOLEAN_TRUE;
1734 vos_mem_copy((void *)&scanReq.SSIDs.SSIDList[0].SSID, (void *)&pBgScanParams->SSID, sizeof(pBgScanParams->SSID));
1735
1736 scanReq.ChannelInfo.numOfChannels = pBgScanParams->ChannelInfo.numOfChannels;
1737
1738 channel = pBgScanParams->ChannelInfo.ChannelList[0];
1739 scanReq.ChannelInfo.ChannelList = &channel;
1740
1741 scanReq.BSSType = eCSR_BSS_TYPE_INFRASTRUCTURE;
1742 scanReq.scanType = eSIR_ACTIVE_SCAN;
1743 scanReq.requestType = eCSR_SCAN_HO_BG_SCAN;
1744 scanReq.maxChnTime = pBgScanParams->maxChnTime;
1745 scanReq.minChnTime = pBgScanParams->minChnTime;
1746 status = csrScanRequest(pMac, CSR_SESSION_ID_INVALID, &scanReq,
1747 &scanId, csrNeighborRoamScanRequestCallback, NULL);
1748 if (eHAL_STATUS_SUCCESS != status)
1749 {
1750 smsLog(pMac, LOGE, FL("CSR Scan Request failed with status %d"), status);
1751 vos_mem_free(scanReq.SSIDs.SSIDList);
1752 return status;
1753 }
1754 pMac->roam.neighborRoamInfo.scanRspPending = eANI_BOOLEAN_TRUE;
1755
1756 vos_mem_free(scanReq.SSIDs.SSIDList);
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05301757 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Channel List Address = %08x, Actual index = %d"),
Jeff Johnson295189b2012-06-20 16:38:30 -07001758 &pMac->roam.neighborRoamInfo.roamChannelInfo.currentChannelListInfo.ChannelList[0],
1759 pMac->roam.neighborRoamInfo.roamChannelInfo.currentChanIndex);
1760 return status;
1761}
1762
1763/* ---------------------------------------------------------------------------
1764
1765 \fn csrNeighborRoamPerformBgScan
1766
1767 \brief This function is invoked on every expiry of neighborScanTimer till all
1768 the channels in the channel list are scanned. It populates necessary
1769 parameters for BG scan and calls appropriate AP to invoke the CSR scan
1770 request
1771
1772 \param pMac - The handle returned by macOpen.
1773
1774 \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
1775
1776---------------------------------------------------------------------------*/
1777eHalStatus csrNeighborRoamPerformBgScan(tpAniSirGlobal pMac)
1778{
1779 eHalStatus status = eHAL_STATUS_SUCCESS;
1780 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
1781 tCsrBGScanRequest bgScanParams;
1782 tANI_U8 broadcastBssid[] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
1783 tANI_U8 channel = 0;
1784
1785 if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
1786 {
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05301787 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Channel List Address = %08x"), &pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[0]);
Jeff Johnson295189b2012-06-20 16:38:30 -07001788 }
1789 else
1790 {
1791 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Channel List Empty"));
Jeff Johnson902c9832012-12-10 14:28:09 -08001792 // Go back and restart. Mostly timer start failure has occurred.
Jeff Johnson295189b2012-06-20 16:38:30 -07001793 // When timer start is declared a failure, then we delete the list.
1794 // Should not happen now as we stop and then only start the scan timer.
1795 // still handle the unlikely case.
1796 csrNeighborRoamHandleEmptyScanResult(pMac);
1797 return status;
1798 }
1799 /* Need to perform scan here before getting the list */
1800 vos_mem_copy(bgScanParams.bssid, broadcastBssid, sizeof(tCsrBssid));
1801 bgScanParams.SSID.length = pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.length;
1802 vos_mem_copy(bgScanParams.SSID.ssId, pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.ssId,
1803 pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.length);
1804
1805 channel = pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList[pNeighborRoamInfo->roamChannelInfo.currentChanIndex];
1806 bgScanParams.ChannelInfo.numOfChannels = 1;
1807 bgScanParams.ChannelInfo.ChannelList = &channel;
1808
1809 bgScanParams.minChnTime = pNeighborRoamInfo->cfgParams.minChannelScanTime;
1810 bgScanParams.maxChnTime = pNeighborRoamInfo->cfgParams.maxChannelScanTime;
1811
1812 status = csrNeighborRoamIssueBgScanRequest(pMac, &bgScanParams);
1813 if (eHAL_STATUS_SUCCESS != status)
1814 {
1815 smsLog(pMac, LOGE, FL("Issue of BG Scan request failed: Status = %d"), status);
1816 return status;
1817 }
1818
1819 pNeighborRoamInfo->roamChannelInfo.currentChanIndex++;
1820 if (pNeighborRoamInfo->roamChannelInfo.currentChanIndex >=
1821 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels)
1822 {
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05301823 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Completed scanning channels in Channel List: CurrChanIndex = %d, Num Channels = %d"),
Jeff Johnson295189b2012-06-20 16:38:30 -07001824 pNeighborRoamInfo->roamChannelInfo.currentChanIndex,
1825 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels);
1826 /* We have completed scanning all the channels */
1827 pNeighborRoamInfo->roamChannelInfo.currentChanIndex = 0;
1828 /* We are no longer scanning the channel list. Next timer firing should be used to get the scan results
1829 and select the best AP in the list */
1830 if (eANI_BOOLEAN_TRUE == pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress)
1831 {
1832 pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_FALSE;
1833 }
1834 }
1835
1836 return status;
1837}
1838
1839/* ---------------------------------------------------------------------------
1840
1841 \fn csrNeighborRoamNeighborScanTimerCallback
1842
1843 \brief This function is the neighbor scan timer callback function. It invokes
1844 the BG scan request based on the current and previous states
1845
1846 \param pv - CSR timer context info which includes pMac and session ID
1847
1848 \return VOID
1849
1850---------------------------------------------------------------------------*/
1851void csrNeighborRoamNeighborScanTimerCallback(void *pv)
1852{
1853 tCsrTimerInfo *pInfo = (tCsrTimerInfo *)pv;
1854 tpAniSirGlobal pMac = pInfo->pMac;
1855 tANI_U32 sessionId = pInfo->sessionId;
1856 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
1857
1858 // check if bg scan is on going, no need to send down the new params if true
1859 if(eANI_BOOLEAN_TRUE == pNeighborRoamInfo->scanRspPending)
1860 {
1861 //msg
1862 smsLog(pMac, LOGW, FL("Already BgScanRsp is Pending\n"));
1863 return;
1864 }
1865
1866 VOS_ASSERT(sessionId == pNeighborRoamInfo->csrSessionId);
1867
1868 switch (pNeighborRoamInfo->neighborRoamState)
1869 {
1870#ifdef WLAN_FEATURE_VOWIFI_11R
1871 case eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN:
1872 switch(pNeighborRoamInfo->prevNeighborRoamState)
1873 {
1874 case eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY:
1875 csrNeighborRoamPerformBgScan(pMac);
1876 break;
1877 default:
1878 smsLog(pMac, LOGE, FL("Neighbor scan callback received in state %d, prev state = %d"),
1879 pNeighborRoamInfo->neighborRoamState, pNeighborRoamInfo->prevNeighborRoamState);
1880 break;
1881 }
1882 break;
1883#endif /* WLAN_FEATURE_VOWIFI_11R */
1884 case eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN:
1885 csrNeighborRoamPerformBgScan(pMac);
1886 break;
1887 default:
1888 break;
1889 }
1890 return;
1891}
1892
1893/* ---------------------------------------------------------------------------
1894
1895 \fn csrNeighborRoamResultsRefreshTimerCallback
1896
1897 \brief This function is the timer callback function for results refresh timer.
1898 When this is invoked, it is as good as down event received from TL. So,
1899 clear off the roamable AP list and start the scan procedure based on 11R
1900 or non-11R association
1901
1902 \param context - CSR timer context info which includes pMac and session ID
1903
1904 \return VOID
1905
1906---------------------------------------------------------------------------*/
1907void csrNeighborRoamResultsRefreshTimerCallback(void *context)
1908{
1909 tCsrTimerInfo *pInfo = (tCsrTimerInfo *)context;
1910 tpAniSirGlobal pMac = pInfo->pMac;
1911 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
1912 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
1913
1914 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event reassoc callback with TL. RSSI = %d"), pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1));
1915
1916 /* Deregister reassoc callback. Ignore return status */
1917 vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->cfgParams.neighborReassocThreshold * (-1),
1918 WLANTL_HO_THRESHOLD_DOWN,
1919 csrNeighborRoamReassocIndCallback,
1920 VOS_MODULE_ID_SME);
1921
1922 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
1923 {
1924 //err msg
1925 smsLog(pMac, LOGW, FL(" Couldn't deregister csrNeighborRoamReassocIndCallback with TL: Status = %d\n"), vosStatus);
1926 }
1927
1928 /* Reset all the variables just as no scan had happened before */
1929 csrNeighborRoamResetConnectedStateControlInfo(pMac);
1930
1931#if defined WLAN_FEATURE_VOWIFI_11R && defined WLAN_FEATURE_VOWIFI
1932 if ((pNeighborRoamInfo->is11rAssoc) && (pMac->rrm.rrmSmeContext.rrmConfig.rrmEnabled))
1933 {
1934 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("11R Association:Neighbor Lookup Down event received in CONNECTED state"));
1935 vosStatus = csrNeighborRoamIssueNeighborRptRequest(pMac);
1936 if (VOS_STATUS_SUCCESS != vosStatus)
1937 {
1938 smsLog(pMac, LOGE, FL("Neighbor report request failed. status = %d\n"), vosStatus);
1939 return;
1940 }
1941 /* Increment the neighbor report retry count after sending the neighbor request successfully */
1942 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum++;
1943 pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_TRUE;
1944 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY)
1945 }
1946 else
1947#endif
1948 {
1949 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Non 11R or CCX Association:Neighbor Lookup Down event received in CONNECTED state"));
1950 vosStatus = csrNeighborRoamTransitToCFGChanScan(pMac);
1951 if (VOS_STATUS_SUCCESS != vosStatus)
1952 {
1953 return;
1954 }
1955 }
1956 return;
1957}
1958
1959#if defined WLAN_FEATURE_VOWIFI_11R && defined WLAN_FEATURE_VOWIFI
1960/* ---------------------------------------------------------------------------
1961
1962 \fn csrNeighborRoamIssueNeighborRptRequest
1963
1964 \brief This function is invoked when TL issues a down event and the current assoc
1965 is a 11R association. It invokes SME RRM API to issue the neighbor request to
1966 the currently associated AP with the current SSID
1967
1968 \param pMac - The handle returned by macOpen.
1969
1970 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
1971
1972---------------------------------------------------------------------------*/
1973VOS_STATUS csrNeighborRoamIssueNeighborRptRequest(tpAniSirGlobal pMac)
1974{
1975 tRrmNeighborRspCallbackInfo callbackInfo;
1976 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
1977 tRrmNeighborReq neighborReq;
1978
1979
1980 neighborReq.no_ssid = 0;
1981
1982 /* Fill in the SSID */
1983 neighborReq.ssid.length = pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.length;
1984 vos_mem_copy(neighborReq.ssid.ssId, pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.ssId,
1985 pMac->roam.roamSession[pNeighborRoamInfo->csrSessionId].connectedProfile.SSID.length);
1986
1987 callbackInfo.neighborRspCallback = csrNeighborRoamRRMNeighborReportResult;
1988 callbackInfo.neighborRspCallbackContext = pMac;
1989 callbackInfo.timeout = pNeighborRoamInfo->FTRoamInfo.neighborReportTimeout;
1990
1991 return sme_NeighborReportRequest(pMac,(tANI_U8) pNeighborRoamInfo->csrSessionId, &neighborReq, &callbackInfo);
1992}
1993
1994/* ---------------------------------------------------------------------------
1995
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07001996 \fn csrNeighborRoamMergeChannelLists
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07001997
1998 \brief This function is used to merge two channel list.
1999 NB: If called with outputNumOfChannels == 0, this routines
2000 simply copies the input channel list to the output channel list.
2001
2002 \param pMac - The handle returned by macOpen.
2003 \param pInputChannelList - The addtional channels to merge in to the "merged" channels list.
2004 \param inputNumOfChannels - The number of additional channels.
2005 \param pOutputChannelList - The place to put the "merged" channel list.
2006 \param outputNumOfChannels - The original number of channels in the "merged" channels list.
2007 \param pMergedOutputNumOfChannels - The final number of channels in the "merged" channel list.
2008
2009 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
2010
2011---------------------------------------------------------------------------*/
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002012VOS_STATUS csrNeighborRoamMergeChannelLists(
2013 tpAniSirGlobal pMac,
2014 tANI_U8 *pInputChannelList,
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002015 int inputNumOfChannels,
2016 tANI_U8 *pOutputChannelList,
2017 int outputNumOfChannels,
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002018 int *pMergedOutputNumOfChannels
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002019 )
2020{
2021 int i = 0;
2022 int j = 0;
2023 int numChannels = outputNumOfChannels;
2024
2025 // Check for NULL pointer
2026 if (!pInputChannelList) return eHAL_STATUS_E_NULL_VALUE;
2027
2028 // Check for NULL pointer
2029 if (!pOutputChannelList) return eHAL_STATUS_E_NULL_VALUE;
2030
2031 // Add the "new" channels in the input list to the end of the output list.
2032 for (i = 0; i < inputNumOfChannels; i++)
2033 {
2034 for (j = 0; j < outputNumOfChannels; j++)
2035 {
2036 if (pInputChannelList[i] == pOutputChannelList[j])
2037 break;
2038 }
2039 if (j == outputNumOfChannels)
2040 {
2041 if (pInputChannelList[i])
2042 {
Madan Mohan Koyyalamudif5c368b2012-12-06 13:10:13 -08002043 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002044 "%s: [INFOLOG] Adding extra %d to Neighbor channel list\n", __func__,
2045 pInputChannelList[i]);
2046 pOutputChannelList[numChannels] = pInputChannelList[i];
2047 numChannels++;
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002048 }
2049 }
2050 }
2051
2052 // Return final number of channels
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002053 *pMergedOutputNumOfChannels = numChannels;
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002054
2055 return eHAL_STATUS_SUCCESS;
2056}
2057
2058/* ---------------------------------------------------------------------------
2059
Jeff Johnson295189b2012-06-20 16:38:30 -07002060 \fn csrNeighborRoamCreateChanListFromNeighborReport
2061
2062 \brief This function is invoked when neighbor report is received for the
2063 neighbor request. Based on the channels present in the neighbor report,
2064 it generates channel list which will be used in REPORT_SCAN state to
2065 scan for these neighbor APs
2066
2067 \param pMac - The handle returned by macOpen.
2068
2069 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
2070
2071---------------------------------------------------------------------------*/
2072VOS_STATUS csrNeighborRoamCreateChanListFromNeighborReport(tpAniSirGlobal pMac)
2073{
2074 tpRrmNeighborReportDesc pNeighborBssDesc;
2075 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002076 tANI_U8 numChannels = 0, i = 0;
Jeff Johnson295189b2012-06-20 16:38:30 -07002077 tANI_U8 channelList[MAX_BSS_IN_NEIGHBOR_RPT];
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002078#if 0
2079 eHalStatus status = eHAL_STATUS_SUCCESS;
2080#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07002081
2082 /* This should always start from 0 whenever we create a channel list out of neighbor AP list */
2083 pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport = 0;
2084
2085 pNeighborBssDesc = smeRrmGetFirstBssEntryFromNeighborCache(pMac);
2086
2087 while (pNeighborBssDesc)
2088 {
2089 if (pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport >= MAX_BSS_IN_NEIGHBOR_RPT) break;
2090
2091 /* Update the neighbor BSS Info in the 11r FT Roam Info */
2092 pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo[pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport].channelNum =
2093 pNeighborBssDesc->pNeighborBssDescription->channel;
2094 pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo[pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport].neighborScore =
2095 (tANI_U8)pNeighborBssDesc->roamScore;
2096 vos_mem_copy(pNeighborRoamInfo->FTRoamInfo.neighboReportBssInfo[pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport].neighborBssId,
2097 pNeighborBssDesc->pNeighborBssDescription->bssId, sizeof(tSirMacAddr));
2098 pNeighborRoamInfo->FTRoamInfo.numBssFromNeighborReport++;
2099
2100 /* Saving the channel list non-redundantly */
2101 if (numChannels > 0)
2102 {
2103 for (i = 0; i < numChannels; i++)
2104 {
2105 if (pNeighborBssDesc->pNeighborBssDescription->channel == channelList[i])
2106 break;
2107 }
2108
2109 }
2110 if (i == numChannels)
2111 {
2112 if (pNeighborBssDesc->pNeighborBssDescription->channel)
2113 {
Jeff Johnson295189b2012-06-20 16:38:30 -07002114 VOS_TRACE (VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO,
2115 "%s: [INFOLOG] Adding %d to Neighbor channel list\n", __func__,
2116 pNeighborBssDesc->pNeighborBssDescription->channel);
2117 channelList[numChannels] = pNeighborBssDesc->pNeighborBssDescription->channel;
2118 numChannels++;
Jeff Johnson295189b2012-06-20 16:38:30 -07002119 }
2120 }
2121
2122 pNeighborBssDesc = smeRrmGetNextBssEntryFromNeighborCache(pMac, pNeighborBssDesc);
2123 }
2124
2125 if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
2126 {
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002127#if 0
Jeff Johnson295189b2012-06-20 16:38:30 -07002128 // Before we free the existing channel list for a safety net make sure
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002129 // we have a union of the IAPP and the already existing list.
2130 status = csrNeighborRoamMergeChannelLists(
2131 pMac,
2132 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList,
2133 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels,
2134 channelList,
2135 numChannels,
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002136 &numChannels );
2137#endif
2138
Jeff Johnson295189b2012-06-20 16:38:30 -07002139 vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
2140 }
2141
2142 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
2143 /* Store the obtained channel list to the Neighbor Control data structure */
2144 if (numChannels)
2145 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = vos_mem_malloc((numChannels) * sizeof(tANI_U8));
2146 if (NULL == pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
2147 {
2148 smsLog(pMac, LOGE, FL("Memory allocation for Channel list failed.. TL event ignored"));
2149 return VOS_STATUS_E_RESOURCES;
2150 }
2151
2152 vos_mem_copy(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList,
2153 channelList, (numChannels) * sizeof(tANI_U8));
2154 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels = numChannels;
2155 if (numChannels)
2156 {
2157 smsLog(pMac, LOG1, FL("IAPP Neighbor list callback received as expected in state %d."),
2158 pNeighborRoamInfo->neighborRoamState);
2159 pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived = eANI_BOOLEAN_TRUE;
2160 }
2161 pNeighborRoamInfo->roamChannelInfo.currentChanIndex = 0;
2162 pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_TRUE;
2163
2164 return VOS_STATUS_SUCCESS;
2165}
2166
2167/* ---------------------------------------------------------------------------
2168
2169 \fn csrNeighborRoamRRMNeighborReportResult
2170
2171 \brief This function is the neighbor report callback that will be invoked by
2172 SME RRM on receiving a neighbor report or of neighbor report is not
2173 received after timeout. On receiving a valid report, it generates a
2174 channel list from the neighbor report and starts the
2175 neighbor scan timer
2176
2177 \param context - The handle returned by macOpen.
2178 vosStatus - Status of the callback(SUCCESS/FAILURE)
2179
2180 \return VOID
2181
2182---------------------------------------------------------------------------*/
2183void csrNeighborRoamRRMNeighborReportResult(void *context, VOS_STATUS vosStatus)
2184{
2185 tpAniSirGlobal pMac = PMAC_STRUCT(context);
2186 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2187 eHalStatus status = eHAL_STATUS_SUCCESS;
2188
2189 smsLog(pMac, LOG1, FL("Neighbor report result callback with status = %d\n"), vosStatus);
2190 switch (pNeighborRoamInfo->neighborRoamState)
2191 {
2192 case eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY:
2193 /* Reset the report pending variable */
2194 pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_FALSE;
2195 if (VOS_STATUS_SUCCESS == vosStatus)
2196 {
2197 /* Need to create channel list based on the neighbor AP list and transition to REPORT_SCAN state */
2198 vosStatus = csrNeighborRoamCreateChanListFromNeighborReport(pMac);
2199 if (VOS_STATUS_SUCCESS == vosStatus)
2200 {
2201 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("Channel List created from Neighbor report, Transitioning to NEIGHBOR_SCAN state\n"));
2202 }
2203
2204 /* We are gonna scan now. Remember the time stamp to filter out results only after this timestamp */
2205 pNeighborRoamInfo->scanRequestTimeStamp = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
2206
2207 /* Now ready for neighbor scan based on the channel list created */
2208 /* Start Neighbor scan timer now. Multiplication by PAL_TIMER_TO_MS_UNIT is to convert ms to us which is
2209 what palTimerStart expects */
2210 status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer,
2211 pNeighborRoamInfo->cfgParams.neighborScanPeriod * PAL_TIMER_TO_MS_UNIT,
2212 eANI_BOOLEAN_FALSE);
2213 if (eHAL_STATUS_SUCCESS != status)
2214 {
2215 /* Timer start failed.. Should we ASSERT here??? */
2216 smsLog(pMac, LOGE, FL("PAL Timer start for neighbor scan timer failed, status = %d, Ignoring state transition"), status);
2217 vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
2218 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
2219 return;
2220 }
2221 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;
2222 /* Neighbor scan timer started. Transition to REPORT_SCAN state */
2223 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN)
2224 }
2225 else
2226 {
2227 /* Neighbor report timeout happened in SME RRM. We can try sending more neighbor requests until we
2228 reach the maxNeighborRetries or receiving a successful neighbor response */
2229 smsLog(pMac, LOGE, FL("Neighbor report result failed after %d retries, MAX RETRIES = %d\n"),
2230 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum, pNeighborRoamInfo->cfgParams.maxNeighborRetries);
2231 if (pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum >=
2232 pNeighborRoamInfo->cfgParams.maxNeighborRetries)
2233 {
2234 smsLog(pMac, LOGE, FL("Bailing out to CFG Channel list scan.. \n"));
2235 vosStatus = csrNeighborRoamTransitToCFGChanScan(pMac);
2236 if (VOS_STATUS_SUCCESS != vosStatus)
2237 {
2238 smsLog(pMac, LOGE, FL("Transit to CFG Channel list scan state failed with status %d \n"), vosStatus);
2239 return;
2240 }
2241 /* We transitioned to different state now. Reset the Neighbor report retry count */
2242 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;
2243 }
2244 else
2245 {
2246 vosStatus = csrNeighborRoamIssueNeighborRptRequest(pMac);
2247 if (VOS_STATUS_SUCCESS != vosStatus)
2248 {
2249 smsLog(pMac, LOGE, FL("Neighbor report request failed. status = %d\n"), vosStatus);
2250 return;
2251 }
2252 pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_TRUE;
2253 /* Increment the neighbor report retry count after sending the neighbor request successfully */
2254 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum++;
2255 }
2256 }
2257 break;
2258 default:
2259 smsLog(pMac, LOGE, FL("Neighbor result callback not expected in state %d, Ignoring.."), pNeighborRoamInfo->neighborRoamState);
2260 break;
2261 }
2262 return;
2263}
2264#endif /* WLAN_FEATURE_VOWIFI_11R */
2265
2266
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002267#ifdef FEATURE_WLAN_LFR
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002268tANI_BOOLEAN csrNeighborRoamIsSsidAndSecurityMatch(
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002269 tpAniSirGlobal pMac,
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002270 tCsrRoamConnectedProfile *pCurProfile,
2271 tSirBssDescription *pBssDesc,
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002272 tDot11fBeaconIEs *pIes)
2273{
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002274 tCsrAuthList authType;
2275 tCsrEncryptionList uCEncryptionType;
2276 tCsrEncryptionList mCEncryptionType;
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002277 tANI_BOOLEAN fMatch = FALSE;
2278
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002279 authType.numEntries = 1;
2280 authType.authType[0] = pCurProfile->AuthType;
2281 uCEncryptionType.numEntries = 1;
2282 uCEncryptionType.encryptionType[0] = pCurProfile->EncryptionType;
2283 mCEncryptionType.numEntries = 1;
2284 mCEncryptionType.encryptionType[0] = pCurProfile->mcEncryptionType;
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002285
2286 if( pIes )
2287 {
2288 if(pIes->SSID.present)
2289 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002290 fMatch = csrIsSsidMatch( pMac,
2291 (void *)pCurProfile->SSID.ssId, pCurProfile->SSID.length,
2292 pIes->SSID.ssid, pIes->SSID.num_ssid,
2293 eANI_BOOLEAN_TRUE );
2294 if(TRUE == fMatch)
2295 {
2296 fMatch = csrIsSecurityMatch( pMac, &authType, &uCEncryptionType,
2297 &mCEncryptionType, pBssDesc, pIes, NULL, NULL, NULL );
2298 return (fMatch);
2299 }
2300 else
2301 {
2302 return (fMatch);
2303 }
2304
2305 }
2306 else
2307 {
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002308 return FALSE; // Treat a missing SSID as a non-match.
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002309 }
2310 }
2311 else
2312 {
2313 return FALSE; // Again, treat missing pIes as a non-match.
2314 }
2315}
2316
2317tANI_BOOLEAN csrNeighborRoamIsNewConnectedProfile(
2318 tpAniSirGlobal pMac)
2319{
2320 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2321 tANI_U8 sessionId = (tANI_U8)pNeighborRoamInfo->csrSessionId;
2322 tCsrRoamConnectedProfile *pCurrProfile = NULL;
2323 tCsrRoamConnectedProfile *pPrevProfile = NULL;
2324 tDot11fBeaconIEs *pIes = NULL;
2325 tSirBssDescription *pBssDesc = NULL;
2326 tANI_BOOLEAN fNew = TRUE;
2327
2328 if(!(pMac->roam.roamSession && CSR_IS_SESSION_VALID(pMac, sessionId)))
2329 {
2330 return (fNew);
2331 }
2332
2333 pCurrProfile = &pMac->roam.roamSession[sessionId].connectedProfile;
2334 if( !pCurrProfile )
2335 {
2336 return (fNew);
2337}
2338
2339 pPrevProfile = &pNeighborRoamInfo->prevConnProfile;
2340 if( !pPrevProfile )
2341 {
2342 return (fNew);
2343 }
2344
2345 pBssDesc = pPrevProfile->pBssDesc;
2346 if (pBssDesc)
2347 {
2348 if (HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac,
2349 pBssDesc, &pIes)) &&
2350 csrNeighborRoamIsSsidAndSecurityMatch(pMac, pCurrProfile, pBssDesc, pIes))
2351 {
2352 fNew = FALSE;
2353 }
2354 if (pIes) {
2355 palFreeMemory(pMac->hHdd, pIes);
2356 }
2357 }
2358
2359 if (fNew)
2360 {
2361 smsLog(pMac, LOG1, FL("Prev roam profile did not match current"));
2362 csrRoamFreeConnectProfile(pMac, pPrevProfile);
2363 csrRoamGetConnectProfile(pMac, sessionId, pPrevProfile);
2364 }
2365 else
2366 {
2367 smsLog(pMac, LOG1, FL("Prev roam profile matches current"));
2368 }
2369
2370 return (fNew);
2371}
2372
2373tANI_BOOLEAN csrNeighborRoamConnectedProfileMatch(
2374 tpAniSirGlobal pMac,
2375 tCsrScanResult *pResult,
2376 tDot11fBeaconIEs *pIes)
2377{
2378 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2379 tANI_U8 sessionId = (tANI_U8)pNeighborRoamInfo->csrSessionId;
2380 tCsrRoamConnectedProfile *pCurProfile = NULL;
2381 tSirBssDescription *pBssDesc = &pResult->Result.BssDescriptor;
2382
2383 if( !(pMac->roam.roamSession
2384 && CSR_IS_SESSION_VALID(pMac, sessionId)))
2385 {
2386 return FALSE;
2387 }
2388
2389 pCurProfile = &pMac->roam.roamSession[sessionId].connectedProfile;
2390
2391 if( !pCurProfile)
2392 {
2393 return FALSE;
2394 }
2395
2396 return csrNeighborRoamIsSsidAndSecurityMatch(pMac, pCurProfile, pBssDesc, pIes);
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002397}
2398
2399/* ---------------------------------------------------------------------------
2400
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002401 \fn csrNeighborRoamPrepareNonOccupiedChannelList
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002402
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002403 \brief This function is used to prepare a channel list that is derived from
2404 the list of valid channels and does not include those in the occupied
2405 list.
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002406
2407 \param pMac - The handle returned by macOpen.
2408 \param pInputChannelList - The default channels list.
2409 \param numOfChannels - The number of channels in the default channels list.
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002410 \param pOutputChannelList - The place to put the non-occupied channel list.
2411 \param pOutputNumOfChannels - The number of channels in the non-occupied channel list.
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002412
2413 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
2414
2415---------------------------------------------------------------------------*/
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002416VOS_STATUS csrNeighborRoamPrepareNonOccupiedChannelList(
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002417 tpAniSirGlobal pMac,
2418 tANI_U8 *pInputChannelList,
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002419 int numOfChannels,
2420 tANI_U8 *pOutputChannelList,
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002421 int *pOutputNumOfChannels
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002422 )
2423{
2424 int i = 0;
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002425 int outputNumOfChannels = 0; // Clear the output number of channels
2426 tANI_U8 numOccupiedChannels = pMac->scan.occupiedChannels.numChannels;
2427 tANI_U8 *pOccupiedChannelList = pMac->scan.occupiedChannels.channelList;
2428
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002429 for (i = 0; i < numOfChannels; i++)
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002430 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002431 if (!csrIsChannelPresentInList(pOccupiedChannelList, numOccupiedChannels,
2432 pInputChannelList[i]))
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002433 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002434 pOutputChannelList[outputNumOfChannels++] = pInputChannelList[i];
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002435 }
2436 }
2437
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002438 smsLog(pMac, LOG2, FL("Number of channels in the valid channel list=%d; "
2439 "Number of channels in the non-occupied list list=%d"),
2440 numOfChannels, outputNumOfChannels);
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002441
2442 // Return the number of channels
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002443 *pOutputNumOfChannels = outputNumOfChannels;
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002444
2445 return eHAL_STATUS_SUCCESS;
2446}
2447#endif /* FEATURE_WLAN_LFR */
2448
Jeff Johnson295189b2012-06-20 16:38:30 -07002449/* ---------------------------------------------------------------------------
2450
2451 \fn csrNeighborRoamTransitToCFGChanScan
2452
2453 \brief This function is called whenever there is a transition to CFG chan scan
2454 state from any state. It frees up the current channel list and allocates
2455 a new memory for the channels received from CFG item. It then starts the
2456 neighbor scan timer to perform the scan on each channel one by one
2457
2458 \param pMac - The handle returned by macOpen.
2459
2460 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
2461
2462---------------------------------------------------------------------------*/
2463VOS_STATUS csrNeighborRoamTransitToCFGChanScan(tpAniSirGlobal pMac)
2464{
2465 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2466 eHalStatus status = eHAL_STATUS_SUCCESS;
2467 int i = 0;
2468 int numOfChannels = 0;
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002469 tANI_U8 channelList[WNI_CFG_VALID_CHANNEL_LIST_LEN];
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002470 tpCsrChannelInfo currChannelListInfo;
2471
2472 currChannelListInfo = &pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo;
Jeff Johnson295189b2012-06-20 16:38:30 -07002473
Jeff Johnson04dd8a82012-06-29 20:41:40 -07002474 if (
Jeff Johnson295189b2012-06-20 16:38:30 -07002475#ifdef FEATURE_WLAN_CCX
2476 ((pNeighborRoamInfo->isCCXAssoc) &&
Jeff Johnson04dd8a82012-06-29 20:41:40 -07002477 (pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived == eANI_BOOLEAN_FALSE)) ||
Jeff Johnson295189b2012-06-20 16:38:30 -07002478 (pNeighborRoamInfo->isCCXAssoc == eANI_BOOLEAN_FALSE) ||
2479#endif // CCX
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002480 currChannelListInfo->numOfChannels == 0)
Jeff Johnson295189b2012-06-20 16:38:30 -07002481 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002482 smsLog(pMac, LOGW, FL("Building channel list to scan"));
Jeff Johnson295189b2012-06-20 16:38:30 -07002483
2484
2485 /* Free up the channel list and allocate a new memory. This is because we dont know how much
2486 was allocated last time. If we directly copy more number of bytes than allocated earlier, this might
2487 result in memory corruption */
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002488 if (NULL != currChannelListInfo->ChannelList)
Jeff Johnson295189b2012-06-20 16:38:30 -07002489 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002490 vos_mem_free(currChannelListInfo->ChannelList);
2491 currChannelListInfo->ChannelList = NULL;
Jeff Johnson295189b2012-06-20 16:38:30 -07002492 }
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002493
2494 // Now obtain the contents for "channelList" (the "default valid channel list") from EITHER
2495 // the gNeighborScanChannelList in "cfg.ini", OR the actual "valid channel list" information formed by CSR.
2496 if (0 != pNeighborRoamInfo->cfgParams.channelInfo.numOfChannels)
Jeff Johnson295189b2012-06-20 16:38:30 -07002497 {
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002498 // Copy the "default valid channel list" (channelList) from the gNeighborScanChannelList in "cfg.ini".
2499 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, "Using the channel list from cfg.ini");
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002500 status = csrNeighborRoamMergeChannelLists(
2501 pMac,
2502 pNeighborRoamInfo->cfgParams.channelInfo.ChannelList,
2503 pNeighborRoamInfo->cfgParams.channelInfo.numOfChannels,
2504 channelList,
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002505 0, //NB: If 0, simply copy the input channel list to the output list.
2506 &numOfChannels );
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002507
2508 currChannelListInfo->ChannelList =
2509 vos_mem_malloc(numOfChannels*sizeof(tANI_U8));
2510 if (NULL == currChannelListInfo->ChannelList)
2511 {
2512 smsLog(pMac, LOGE, FL("Memory allocation for Channel list failed"));
2513 return VOS_STATUS_E_RESOURCES;
2514 }
2515
2516 vos_mem_copy(currChannelListInfo->ChannelList,
2517 channelList, numOfChannels * sizeof(tANI_U8));
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002518 }
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002519 else
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002520 {
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002521 /* Get current list of valid channels. */
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002522 numOfChannels = pMac->scan.occupiedChannels.numChannels;
2523 if (numOfChannels
2524#ifdef FEATURE_WLAN_LFR
2525 && ((pNeighborRoamInfo->uEmptyScanCount == 0) ||
2526 ((pNeighborRoamInfo->uEmptyScanCount % 2) == 1))
2527#endif
2528 )
Jeff Johnson295189b2012-06-20 16:38:30 -07002529 {
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002530 /*
2531 * Always scan channels in the occupied channel list
2532 * before scanning on the non-occupied list.
2533 */
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05302534 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, "Switching to occupied channel list");
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002535 VOS_ASSERT(currChannelListInfo->ChannelList == NULL);
2536 currChannelListInfo->ChannelList = vos_mem_malloc(numOfChannels);
2537
2538 if (NULL == currChannelListInfo->ChannelList)
2539 {
2540 smsLog(pMac, LOGE, FL("Memory allocation for Channel list failed"));
2541 return VOS_STATUS_E_RESOURCES;
2542 }
2543 vos_mem_copy(currChannelListInfo->ChannelList,
2544 pMac->scan.occupiedChannels.channelList,
2545 numOfChannels * sizeof(tANI_U8));
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002546 }
2547 else
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002548 {
2549 /* Scan all channels from non-occupied list */
2550 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, "Get valid channel list");
2551 numOfChannels = sizeof(pMac->roam.validChannelList);
2552
2553 if(HAL_STATUS_SUCCESS(csrGetCfgValidChannels(pMac,
2554 (tANI_U8 *)pMac->roam.validChannelList,
2555 (tANI_U32 *) &numOfChannels)))
2556 {
2557#ifdef FEATURE_WLAN_LFR
2558 /*
2559 * Prepare non-occupied channel list (channelList)
2560 * from the actual "valid channel list" information
2561 * formed by CSR.
2562 */
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05302563 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, "Switching to non-occupied channel list");
2564 status = csrNeighborRoamPrepareNonOccupiedChannelList(pMac,
2565 (tANI_U8 *)pMac->roam.validChannelList,
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002566 numOfChannels,
2567 channelList,
2568 &numOfChannels);
2569#else
2570 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, "Merging channel list");
2571 status = csrNeighborRoamMergeChannelLists(
2572 pMac,
2573 (tANI_U8 *)pMac->roam.validChannelList,
2574 numOfChannels, // The number of channels in the validChannelList
2575 channelList,
2576 0, //NB: If 0, simply copy the input channel list to the output list.
2577 &numOfChannels ); // The final number of channels in the output list. Will be numOfChannels
2578#endif
2579 }
2580 else
2581 {
2582 smsLog(pMac, LOGE, FL("Could not get valid channel list"));
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002583 return VOS_STATUS_E_FAILURE;
Jeff Johnson295189b2012-06-20 16:38:30 -07002584 }
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002585 currChannelListInfo->ChannelList =
2586 vos_mem_malloc(numOfChannels*sizeof(tANI_U8));
2587
2588 if (NULL == currChannelListInfo->ChannelList)
2589 {
2590 smsLog(pMac, LOGE, FL("Memory allocation for Channel list failed"));
2591 return VOS_STATUS_E_RESOURCES;
2592 }
2593#ifdef FEATURE_WLAN_LFR
2594 vos_mem_copy(currChannelListInfo->ChannelList,
2595 channelList, numOfChannels * sizeof(tANI_U8));
2596#else
2597 vos_mem_copy(currChannelListInfo->ChannelList,
2598 (tANI_U8 *)pMac->roam.validChannelList,
2599 numOfChannels * sizeof(tANI_U8));
2600#endif
2601 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002602 }
2603
Madan Mohan Koyyalamudi470d2cf2012-09-28 14:43:44 -07002604 /* Adjust for the actual number that are used */
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002605 currChannelListInfo->numOfChannels = numOfChannels;
2606 for (i = 0; i < currChannelListInfo->numOfChannels; i++)
Jeff Johnson295189b2012-06-20 16:38:30 -07002607 {
Madan Mohan Koyyalamudi22f27082012-11-27 19:11:12 +05302608 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, "Channel List from CFG (or) (non-)occupied list"
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002609 "= %d\n", currChannelListInfo->ChannelList[i]);
Jeff Johnson295189b2012-06-20 16:38:30 -07002610 }
2611 }
2612
2613 /* We are gonna scan now. Remember the time stamp to filter out results only after this timestamp */
2614 pNeighborRoamInfo->scanRequestTimeStamp = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
2615
2616 palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
2617 /* Start Neighbor scan timer now. Multiplication by PAL_TIMER_TO_MS_UNIT is to convert ms to us which is
2618 what palTimerStart expects */
2619 status = palTimerStart(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer,
2620 pNeighborRoamInfo->cfgParams.neighborScanPeriod * PAL_TIMER_TO_MS_UNIT,
2621 eANI_BOOLEAN_FALSE);
2622
2623 if (eHAL_STATUS_SUCCESS != status)
2624 {
2625 /* Timer start failed.. */
2626 smsLog(pMac, LOGE, FL("Neighbor scan PAL Timer start failed, status = %d, Ignoring state transition"), status);
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002627 vos_mem_free(currChannelListInfo->ChannelList);
2628 currChannelListInfo->ChannelList = NULL;
Jeff Johnson295189b2012-06-20 16:38:30 -07002629 return VOS_STATUS_E_FAILURE;
2630 }
2631
2632 pNeighborRoamInfo->roamChannelInfo.currentChanIndex = 0;
2633 pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_TRUE;
Madan Mohan Koyyalamudi5850f312012-11-27 19:00:25 +05302634 /* We are about to start a fresh scan cycle,
2635 * purge non-P2P results from the past */
2636 csrScanFlushSelectiveResult(pMac, VOS_FALSE);
Jeff Johnson295189b2012-06-20 16:38:30 -07002637
2638 /* Transition to CFG_CHAN_LIST_SCAN_STATE */
2639 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN)
2640
2641 return VOS_STATUS_SUCCESS;
2642}
2643
2644/* ---------------------------------------------------------------------------
2645
2646 \fn csrNeighborRoamNeighborLookupUpEvent
2647
2648 \brief This function is called as soon as TL indicates that the current AP's
2649 RSSI is better than the neighbor lookup threshold. Here, we transition to
2650 CONNECTED state and reset all the scan parameters
2651
2652 \param pMac - The handle returned by macOpen.
2653
2654 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
2655
2656---------------------------------------------------------------------------*/
2657VOS_STATUS csrNeighborRoamNeighborLookupUpEvent(tpAniSirGlobal pMac)
2658{
2659 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2660 VOS_STATUS vosStatus;
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -07002661 csrNeighborRoamDeregAllRssiIndication(pMac);
Jeff Johnson295189b2012-06-20 16:38:30 -07002662
Jeff Johnson295189b2012-06-20 16:38:30 -07002663 /* Recheck whether the below check is needed. */
2664 if (pNeighborRoamInfo->neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_CONNECTED)
2665 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CONNECTED)
Jeff Johnsone7245742012-09-05 17:12:55 -07002666
2667 /* Reset all the neighbor roam info control variables. Free all the allocated memory. It is like we are just associated now */
2668 csrNeighborRoamResetConnectedStateControlInfo(pMac);
2669
Jeff Johnson295189b2012-06-20 16:38:30 -07002670
2671 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering DOWN event neighbor lookup callback with TL. RSSI = %d,"), pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
2672 /* Register Neighbor Lookup threshold callback with TL for DOWN event now */
2673 vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
2674 WLANTL_HO_THRESHOLD_DOWN,
2675 csrNeighborRoamNeighborLookupDOWNCallback,
2676 VOS_MODULE_ID_SME, pMac);
2677 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
2678 {
2679 //err msg
2680 smsLog(pMac, LOGW, FL(" Couldn't register csrNeighborRoamNeighborLookupCallback DOWN event with TL: Status = %d\n"), vosStatus);
2681 }
2682
2683
2684 return vosStatus;
2685}
2686
2687/* ---------------------------------------------------------------------------
2688
2689 \fn csrNeighborRoamNeighborLookupDownEvent
2690
2691 \brief This function is called as soon as TL indicates that the current AP's
2692 RSSI falls below the current eighbor lookup threshold. Here, we transition to
2693 REPORT_QUERY for 11r association and CFG_CHAN_LIST_SCAN state if the assoc is
2694 a non-11R association.
2695
2696 \param pMac - The handle returned by macOpen.
2697
2698 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
2699
2700---------------------------------------------------------------------------*/
2701VOS_STATUS csrNeighborRoamNeighborLookupDownEvent(tpAniSirGlobal pMac)
2702{
2703 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2704 VOS_STATUS vosStatus = VOS_STATUS_SUCCESS;
2705 eHalStatus status = eHAL_STATUS_SUCCESS;
2706
2707 switch (pNeighborRoamInfo->neighborRoamState)
2708 {
2709 case eCSR_NEIGHBOR_ROAM_STATE_CONNECTED:
2710
2711 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Deregistering DOWN event neighbor lookup callback with TL. RSSI = %d,"),
2712 pNeighborRoamInfo->currentNeighborLookupThreshold * (-1));
2713 /* De-register Neighbor Lookup threshold callback with TL */
2714 vosStatus = WLANTL_DeregRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
2715 WLANTL_HO_THRESHOLD_DOWN,
2716 csrNeighborRoamNeighborLookupDOWNCallback,
2717 VOS_MODULE_ID_SME);
2718
2719 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
2720 {
2721 //err msg
Madan Mohan Koyyalamudi596e4fb2012-10-05 11:39:52 -07002722 smsLog(pMac, LOGW, FL(" Couldn't Deregister csrNeighborRoamNeighborLookupCallback DOWN event from TL: Status = %d\n"), vosStatus);
Jeff Johnson295189b2012-06-20 16:38:30 -07002723 }
2724
2725
2726#if defined WLAN_FEATURE_VOWIFI_11R && defined WLAN_FEATURE_VOWIFI
2727 if ((pNeighborRoamInfo->is11rAssoc) && (pMac->rrm.rrmSmeContext.rrmConfig.rrmEnabled))
2728 {
2729
2730 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("11R Association:Neighbor Lookup Down event received in CONNECTED state"));
2731 vosStatus = csrNeighborRoamIssueNeighborRptRequest(pMac);
2732 if (VOS_STATUS_SUCCESS != vosStatus)
2733 {
2734 smsLog(pMac, LOGE, FL("Neighbor report request failed. status = %d\n"), vosStatus);
2735 return vosStatus;
2736 }
2737 /* Increment the neighbor report retry count after sending the neighbor request successfully */
2738 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum++;
2739 pNeighborRoamInfo->FTRoamInfo.neighborRptPending = eANI_BOOLEAN_TRUE;
2740 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REPORT_QUERY)
2741 }
2742 else
2743#endif
2744 {
2745 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Non 11R or CCX Association:Neighbor Lookup Down event received in CONNECTED state"));
2746
2747 vosStatus = csrNeighborRoamTransitToCFGChanScan(pMac);
2748 if (VOS_STATUS_SUCCESS != vosStatus)
2749 {
Madan Mohan Koyyalamudi4450acc2012-11-15 17:24:31 -08002750 NEIGHBOR_ROAM_DEBUG(pMac, LOGE, FL("csrNeighborRoamTransitToCFGChanScan failed"
2751 " with status=%d"), vosStatus);
Jeff Johnson295189b2012-06-20 16:38:30 -07002752 return vosStatus;
2753 }
2754 }
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002755 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering UP event neighbor lookup callback with TL. RSSI = %d,"), NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1));
Jeff Johnson295189b2012-06-20 16:38:30 -07002756 /* Register Neighbor Lookup threshold callback with TL for UP event now */
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002757 vosStatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext,
2758 (v_S7_t)NEIGHBOR_ROAM_LOOKUP_UP_THRESHOLD * (-1),
Jeff Johnson295189b2012-06-20 16:38:30 -07002759 WLANTL_HO_THRESHOLD_UP,
2760 csrNeighborRoamNeighborLookupUPCallback,
2761 VOS_MODULE_ID_SME, pMac);
2762 if(!VOS_IS_STATUS_SUCCESS(vosStatus))
2763 {
2764 //err msg
Madan Mohan Koyyalamudi4450acc2012-11-15 17:24:31 -08002765 smsLog(pMac, LOGE, FL(" Couldn't register csrNeighborRoamNeighborLookupCallback UP event with TL: Status = %d\n"), status);
Jeff Johnson295189b2012-06-20 16:38:30 -07002766 }
2767 break;
2768 default:
2769 smsLog(pMac, LOGE, FL("DOWN event received in invalid state %d..Ignoring..."), pNeighborRoamInfo->neighborRoamState);
2770 break;
2771
2772 }
2773 return vosStatus;
2774}
2775
2776/* ---------------------------------------------------------------------------
2777
2778 \fn csrNeighborRoamNeighborLookupUPCallback
2779
2780 \brief This function is registered with TL to indicate whenever the RSSI
2781 gets better than the neighborLookup RSSI Threshold
2782
2783 \param pAdapter - VOS Context
2784 trafficStatus - UP/DOWN indication from TL
2785 pUserCtxt - Parameter for callback registered during callback registration. Should be pMac
2786
2787 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
2788
2789---------------------------------------------------------------------------*/
2790VOS_STATUS csrNeighborRoamNeighborLookupUPCallback (v_PVOID_t pAdapter, v_U8_t rssiNotification,
Srinivasdaaec712012-12-12 15:59:44 -08002791 v_PVOID_t pUserCtxt,
2792 v_S7_t avgRssi)
Jeff Johnson295189b2012-06-20 16:38:30 -07002793{
2794 tpAniSirGlobal pMac = PMAC_STRUCT( pUserCtxt );
2795 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2796 VOS_STATUS vosStatus = eHAL_STATUS_SUCCESS;
2797
Srinivasdaaec712012-12-12 15:59:44 -08002798 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("Neighbor Lookup UP indication callback called with notification %d Reported RSSI = %d"),
2799 rssiNotification,
2800 avgRssi);
Jeff Johnson295189b2012-06-20 16:38:30 -07002801
2802 if(!csrIsConnStateConnectedInfra(pMac, pNeighborRoamInfo->csrSessionId))
2803 {
2804 smsLog(pMac, LOGW, "Ignoring the indication as we are not connected\n");
2805 return VOS_STATUS_SUCCESS;
2806 }
2807
2808 VOS_ASSERT(WLANTL_HO_THRESHOLD_UP == rssiNotification);
2809 vosStatus = csrNeighborRoamNeighborLookupUpEvent(pMac);
2810 return vosStatus;
2811}
2812
2813/* ---------------------------------------------------------------------------
2814
2815 \fn csrNeighborRoamNeighborLookupDOWNCallback
2816
2817 \brief This function is registered with TL to indicate whenever the RSSI
2818 falls below the current neighborLookup RSSI Threshold
2819
2820 \param pAdapter - VOS Context
2821 trafficStatus - UP/DOWN indication from TL
2822 pUserCtxt - Parameter for callback registered during callback registration. Should be pMac
2823
2824 \return VOS_STATUS_SUCCESS on success, corresponding error code otherwise
2825
2826---------------------------------------------------------------------------*/
2827VOS_STATUS csrNeighborRoamNeighborLookupDOWNCallback (v_PVOID_t pAdapter, v_U8_t rssiNotification,
Srinivasdaaec712012-12-12 15:59:44 -08002828 v_PVOID_t pUserCtxt,
2829 v_S7_t avgRssi)
Jeff Johnson295189b2012-06-20 16:38:30 -07002830{
2831 tpAniSirGlobal pMac = PMAC_STRUCT( pUserCtxt );
2832 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2833 VOS_STATUS vosStatus = eHAL_STATUS_SUCCESS;
2834
Srinivasdaaec712012-12-12 15:59:44 -08002835 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("Neighbor Lookup DOWN indication callback called with notification %d Reported RSSI = %d"),
2836 rssiNotification,
2837 avgRssi);
Jeff Johnson295189b2012-06-20 16:38:30 -07002838
2839 if(!csrIsConnStateConnectedInfra(pMac, pNeighborRoamInfo->csrSessionId))
2840 {
2841 smsLog(pMac, LOGW, "Ignoring the indication as we are not connected\n");
2842 return VOS_STATUS_SUCCESS;
2843 }
2844
2845 VOS_ASSERT(WLANTL_HO_THRESHOLD_DOWN == rssiNotification);
2846 vosStatus = csrNeighborRoamNeighborLookupDownEvent(pMac);
2847
2848 return vosStatus;
2849}
2850
2851#ifdef RSSI_HACK
2852extern int dumpCmdRSSI;
2853#endif
2854
2855/* ---------------------------------------------------------------------------
2856
2857 \fn csrNeighborRoamIndicateDisconnect
2858
2859 \brief This function is called by CSR as soon as the station disconnects from
2860 the AP. This function does the necessary cleanup of neighbor roam data
2861 structures. Neighbor roam state transitions to INIT state whenever this
2862 function is called except if the current state is REASSOCIATING
2863
2864 \param pMac - The handle returned by macOpen.
2865 sessionId - CSR session id that got disconnected
2866
2867 \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
2868
2869---------------------------------------------------------------------------*/
2870eHalStatus csrNeighborRoamIndicateDisconnect(tpAniSirGlobal pMac, tANI_U8 sessionId)
2871{
2872 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2873
Madan Mohan Koyyalamudi5ad3dff2012-10-21 11:32:02 -07002874 smsLog(pMac, LOGE, FL("Disconnect indication on session %d in state %d (sub-state %d)"),
2875 sessionId, pNeighborRoamInfo->neighborRoamState,
2876 pMac->roam.curSubState[sessionId]);
Jeff Johnson295189b2012-06-20 16:38:30 -07002877
2878#ifdef FEATURE_WLAN_CCX
2879 {
2880 tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, sessionId);
2881 if (pSession->connectedProfile.isCCXAssoc)
2882 {
2883 vos_mem_copy(&pSession->prevApSSID, &pSession->connectedProfile.SSID, sizeof(tSirMacSSid));
2884 vos_mem_copy(pSession->prevApBssid, pSession->connectedProfile.bssid, sizeof(tSirMacAddr));
2885 pSession->prevOpChannel = pSession->connectedProfile.operationChannel;
2886 pSession->isPrevApInfoValid = TRUE;
2887 pSession->roamTS1 = vos_timer_get_system_time();
2888
2889 }
2890 }
2891#endif
2892
2893#ifdef RSSI_HACK
2894 dumpCmdRSSI = -40;
2895#endif
2896 switch (pNeighborRoamInfo->neighborRoamState)
2897 {
2898 case eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING:
2899 // Stop scan and neighbor refresh timers.
2900 // These are indeed not required when we are in reassociating
2901 // state.
2902 palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
2903 palTimerStop(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
Madan Mohan Koyyalamudi5ad3dff2012-10-21 11:32:02 -07002904 if (!CSR_IS_ROAM_SUBSTATE_DISASSOC_HO( pMac, sessionId )) {
2905 /*
2906 * Disconnect indication during Disassoc Handoff sub-state
2907 * is received when we are trying to disconnect with the old
2908 * AP during roam. BUT, if receive a disconnect indication
2909 * outside of Disassoc Handoff sub-state, then it means that
2910 * this is a genuine disconnect and we need to clean up.
2911 * Otherwise, we will be stuck in reassoc state which will
2912 * in-turn block scans (see csrIsScanAllowed).
2913 */
2914 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT);
2915 }
Jeff Johnson295189b2012-06-20 16:38:30 -07002916 break;
2917
2918 case eCSR_NEIGHBOR_ROAM_STATE_INIT:
Jeff Johnson295189b2012-06-20 16:38:30 -07002919 csrNeighborRoamResetInitStateControlInfo(pMac);
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -07002920 csrNeighborRoamDeregAllRssiIndication(pMac);
Jeff Johnson295189b2012-06-20 16:38:30 -07002921 break;
2922
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -07002923 case eCSR_NEIGHBOR_ROAM_STATE_CFG_CHAN_LIST_SCAN:
2924 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT);
2925 csrNeighborRoamResetCfgListChanScanControlInfo(pMac);
2926 csrNeighborRoamDeregAllRssiIndication(pMac);
2927 break;
2928
2929 case eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE:
2930 /* Stop pre-auth to reassoc interval timer */
2931 palTimerStop(pMac->hHdd, pMac->ft.ftSmeContext.preAuthReassocIntvlTimer);
Madan Mohan Koyyalamudi4f292df2012-09-18 17:27:40 -07002932 case eCSR_NEIGHBOR_ROAM_STATE_REPORT_SCAN:
2933 case eCSR_NEIGHBOR_ROAM_STATE_PREAUTHENTICATING:
2934 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -07002935 csrNeighborRoamResetPreauthControlInfo(pMac);
Madan Mohan Koyyalamudi4f292df2012-09-18 17:27:40 -07002936 csrNeighborRoamResetReportScanStateControlInfo(pMac);
Madan Mohan Koyyalamudiedee8aa2012-10-15 15:36:40 -07002937 csrNeighborRoamDeregAllRssiIndication(pMac);
Madan Mohan Koyyalamudi4f292df2012-09-18 17:27:40 -07002938 break;
2939
Jeff Johnson295189b2012-06-20 16:38:30 -07002940 default:
Madan Mohan Koyyalamudi5695b502012-09-24 14:21:12 -07002941 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("Received disconnect event in state %d"), pNeighborRoamInfo->neighborRoamState);
2942 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, FL("Transitioning to INIT state"));
Jeff Johnson295189b2012-06-20 16:38:30 -07002943 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
Madan Mohan Koyyalamudi4f292df2012-09-18 17:27:40 -07002944 break;
Jeff Johnson295189b2012-06-20 16:38:30 -07002945 }
2946 return eHAL_STATUS_SUCCESS;
2947}
2948
2949/* ---------------------------------------------------------------------------
2950
2951 \fn csrNeighborRoamIndicateConnect
2952
2953 \brief This function is called by CSR as soon as the station connects to an AP.
2954 This initializes all the necessary data structures related to the
2955 associated AP and transitions the state to CONNECTED state
2956
2957 \param pMac - The handle returned by macOpen.
2958 sessionId - CSR session id that got connected
2959 vosStatus - connect status SUCCESS/FAILURE
2960
2961 \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
2962
2963---------------------------------------------------------------------------*/
2964eHalStatus csrNeighborRoamIndicateConnect(tpAniSirGlobal pMac, tANI_U8 sessionId, VOS_STATUS vosStatus)
2965{
2966 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
2967 eHalStatus status = eHAL_STATUS_SUCCESS;
Jeff Johnson43971f52012-07-17 12:26:56 -07002968 VOS_STATUS vstatus;
2969
Jeff Johnson04dd8a82012-06-29 20:41:40 -07002970#if defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX) || defined(FEATURE_WLAN_LFR)
Jeff Johnson295189b2012-06-20 16:38:30 -07002971 int init_ft_flag = FALSE;
2972#endif
2973
Madan Mohan Koyyalamudi8bdd3112012-09-24 13:55:14 -07002974 smsLog(pMac, LOG2, FL("Connect indication received with session id %d in state %d"), sessionId, pNeighborRoamInfo->neighborRoamState);
Jeff Johnson295189b2012-06-20 16:38:30 -07002975
2976 switch (pNeighborRoamInfo->neighborRoamState)
2977 {
2978 case eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING:
2979 if (VOS_STATUS_SUCCESS != vosStatus)
2980 {
2981 /* Just transition the state to INIT state. Rest of the clean up happens when we get next connect indication */
2982 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
2983 break;
2984 }
2985 /* Fall through if the status is SUCCESS */
2986 case eCSR_NEIGHBOR_ROAM_STATE_INIT:
2987 /* Reset all the data structures here */
2988 csrNeighborRoamResetInitStateControlInfo(pMac);
2989
Jeff Johnson295189b2012-06-20 16:38:30 -07002990 pNeighborRoamInfo->csrSessionId = sessionId;
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08002991
2992#ifdef FEATURE_WLAN_LFR
2993 /*
2994 * Initialize the occupied list ONLY if we are
2995 * transitioning from INIT state to CONNECTED state.
2996 */
2997 if (eCSR_NEIGHBOR_ROAM_STATE_INIT == pNeighborRoamInfo->neighborRoamState)
2998 csrInitOccupiedChannelsList(pMac);
2999#endif
3000 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CONNECTED);
3001
Jeff Johnson295189b2012-06-20 16:38:30 -07003002 vos_mem_copy(pNeighborRoamInfo->currAPbssid,
3003 pMac->roam.roamSession[sessionId].connectedProfile.bssid, sizeof(tCsrBssid));
3004 pNeighborRoamInfo->currAPoperationChannel = pMac->roam.roamSession[sessionId].connectedProfile.operationChannel;
3005 pNeighborRoamInfo->neighborScanTimerInfo.pMac = pMac;
3006 pNeighborRoamInfo->neighborScanTimerInfo.sessionId = sessionId;
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08003007 pNeighborRoamInfo->currentNeighborLookupThreshold =
3008 pNeighborRoamInfo->cfgParams.neighborLookupThreshold;
3009#ifdef FEATURE_WLAN_LFR
3010 pNeighborRoamInfo->uEmptyScanCount = 0;
3011#endif
3012
Jeff Johnson295189b2012-06-20 16:38:30 -07003013
Jeff Johnson04dd8a82012-06-29 20:41:40 -07003014#if defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX) || defined(FEATURE_WLAN_LFR)
Jeff Johnson295189b2012-06-20 16:38:30 -07003015 /* Now we can clear the preauthDone that was saved as we are connected afresh */
3016 csrNeighborRoamFreeRoamableBSSList(pMac, &pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthDoneList);
3017#endif
3018
3019#ifdef WLAN_FEATURE_VOWIFI_11R
3020 // Based on the auth scheme tell if we are 11r
Madan Mohan Koyyalamudi5e32b962012-11-28 16:07:55 -08003021 if ( csrIsAuthType11r( pMac->roam.roamSession[sessionId].connectedProfile.AuthType,
3022 pMac->roam.roamSession[sessionId].connectedProfile.MDID.mdiePresent))
Jeff Johnson295189b2012-06-20 16:38:30 -07003023 {
3024 if (pMac->roam.configParam.isFastTransitionEnabled)
3025 init_ft_flag = TRUE;
3026 pNeighborRoamInfo->is11rAssoc = eANI_BOOLEAN_TRUE;
3027 }
3028 else
3029 pNeighborRoamInfo->is11rAssoc = eANI_BOOLEAN_FALSE;
Madan Mohan Koyyalamudi8bdd3112012-09-24 13:55:14 -07003030 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("11rAssoc is = %d"), pNeighborRoamInfo->is11rAssoc);
Jeff Johnson295189b2012-06-20 16:38:30 -07003031#endif
3032
3033#ifdef FEATURE_WLAN_CCX
3034 // Based on the auth scheme tell if we are 11r
3035 if (pMac->roam.roamSession[sessionId].connectedProfile.isCCXAssoc)
3036 {
3037 if (pMac->roam.configParam.isFastTransitionEnabled)
3038 init_ft_flag = TRUE;
3039 pNeighborRoamInfo->isCCXAssoc = eANI_BOOLEAN_TRUE;
3040 }
3041 else
3042 pNeighborRoamInfo->isCCXAssoc = eANI_BOOLEAN_FALSE;
Madan Mohan Koyyalamudi8bdd3112012-09-24 13:55:14 -07003043 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("isCCXAssoc is = %d ft = %d"),
3044 pNeighborRoamInfo->isCCXAssoc, init_ft_flag);
Jeff Johnson295189b2012-06-20 16:38:30 -07003045
3046#endif
3047
Jeff Johnson04dd8a82012-06-29 20:41:40 -07003048#ifdef FEATURE_WLAN_LFR
3049 // If "Legacy Fast Roaming" is enabled
Madan Mohan Koyyalamudi03aae5f2012-11-28 01:51:22 +05303050 if (csrRoamIsFastRoamEnabled(pMac, sessionId))
Jeff Johnson04dd8a82012-06-29 20:41:40 -07003051 {
3052 init_ft_flag = TRUE;
3053 }
3054#endif
3055
3056#if defined (WLAN_FEATURE_VOWIFI_11R) || defined (FEATURE_WLAN_CCX) || defined(FEATURE_WLAN_LFR)
Jeff Johnson295189b2012-06-20 16:38:30 -07003057 if ( init_ft_flag == TRUE )
3058 {
3059 /* Initialize all the data structures needed for the 11r FT Preauth */
3060 pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimerInfo.pMac = pMac;
3061 pNeighborRoamInfo->FTRoamInfo.preAuthRspWaitTimerInfo.sessionId = sessionId;
3062 pNeighborRoamInfo->FTRoamInfo.currentNeighborRptRetryNum = 0;
3063 csrNeighborRoamPurgePreauthFailedList(pMac);
3064
3065 NEIGHBOR_ROAM_DEBUG(pMac, LOG2, FL("Registering neighbor lookup DOWN event with TL, RSSI = %d"), pNeighborRoamInfo->currentNeighborLookupThreshold);
3066 /* Register Neighbor Lookup threshold callback with TL for DOWN event only */
Jeff Johnson43971f52012-07-17 12:26:56 -07003067 vstatus = WLANTL_RegRSSIIndicationCB(pMac->roam.gVosContext, (v_S7_t)pNeighborRoamInfo->currentNeighborLookupThreshold * (-1),
Jeff Johnson295189b2012-06-20 16:38:30 -07003068 WLANTL_HO_THRESHOLD_DOWN,
3069 csrNeighborRoamNeighborLookupDOWNCallback,
3070 VOS_MODULE_ID_SME, pMac);
3071
Jeff Johnson43971f52012-07-17 12:26:56 -07003072 if(!VOS_IS_STATUS_SUCCESS(vstatus))
Jeff Johnson295189b2012-06-20 16:38:30 -07003073 {
3074 //err msg
Jeff Johnson43971f52012-07-17 12:26:56 -07003075 smsLog(pMac, LOGW, FL(" Couldn't register csrNeighborRoamNeighborLookupDOWNCallback with TL: Status = %d\n"), vstatus);
3076 status = eHAL_STATUS_FAILURE;
Jeff Johnson295189b2012-06-20 16:38:30 -07003077 }
3078 }
3079#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07003080 break;
3081 default:
3082 smsLog(pMac, LOGE, FL("Connect event received in invalid state %d..Ignoring..."), pNeighborRoamInfo->neighborRoamState);
3083 break;
3084 }
3085 return status;
3086}
3087
3088
3089#ifdef WLAN_FEATURE_VOWIFI_11R
3090/* ---------------------------------------------------------------------------
3091
3092 \fn csrNeighborRoamPreAuthResponseWaitTimerHandler
3093
3094 \brief If this function is invoked, that means the preauthentication response
3095 is timed out from the PE. Preauth rsp handler is called with status as
3096 TIMEOUT
3097
3098 \param context - CSR Timer info which holds pMac and session ID
3099
3100 \return VOID
3101
3102---------------------------------------------------------------------------*/
3103void csrNeighborRoamPreAuthResponseWaitTimerHandler(void *context)
3104{
3105 tCsrTimerInfo *pTimerInfo = (tCsrTimerInfo *)context;
3106 tpAniSirGlobal pMac = (tpAniSirGlobal)pTimerInfo->pMac;
3107 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
3108
3109 pNeighborRoamInfo->FTRoamInfo.preauthRspPending = eANI_BOOLEAN_FALSE;
3110
3111 csrNeighborRoamPreauthRspHandler(pMac, VOS_STATUS_E_TIMEOUT);
3112}
3113
3114/* ---------------------------------------------------------------------------
3115
3116 \fn csrNeighborRoamPurgePreauthFailedList
3117
3118 \brief This function purges all the MAC addresses in the pre-auth fail list
3119
3120 \param pMac - The handle returned by macOpen.
3121
3122 \return VOID
3123
3124---------------------------------------------------------------------------*/
3125void csrNeighborRoamPurgePreauthFailedList(tpAniSirGlobal pMac)
3126{
3127 tANI_U8 i;
3128
3129 for (i = 0; i < pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthFailList.numMACAddress; i++)
3130 {
3131 vos_mem_zero(pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthFailList.macAddress[i], sizeof(tSirMacAddr));
3132 }
3133 pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthFailList.numMACAddress = 0;
3134
3135 return;
3136}
3137
3138/* ---------------------------------------------------------------------------
3139
3140 \fn csrNeighborRoamInit11rAssocInfo
3141
3142 \brief This function initializes 11r related neighbor roam data structures
3143
3144 \param pMac - The handle returned by macOpen.
3145
3146 \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
3147
3148---------------------------------------------------------------------------*/
3149eHalStatus csrNeighborRoamInit11rAssocInfo(tpAniSirGlobal pMac)
3150{
3151 eHalStatus status;
3152 tpCsr11rAssocNeighborInfo pFTRoamInfo = &pMac->roam.neighborRoamInfo.FTRoamInfo;
3153
3154 pMac->roam.neighborRoamInfo.is11rAssoc = eANI_BOOLEAN_FALSE;
3155 pMac->roam.neighborRoamInfo.cfgParams.maxNeighborRetries = pMac->roam.configParam.neighborRoamConfig.nMaxNeighborRetries;
3156 pFTRoamInfo->neighborReportTimeout = CSR_NEIGHBOR_ROAM_REPORT_QUERY_TIMEOUT;
3157 pFTRoamInfo->PEPreauthRespTimeout = CSR_NEIGHBOR_ROAM_PREAUTH_RSP_WAIT_MULTIPLIER * pMac->roam.neighborRoamInfo.cfgParams.neighborScanPeriod;
3158 pFTRoamInfo->neighborRptPending = eANI_BOOLEAN_FALSE;
3159 pFTRoamInfo->preauthRspPending = eANI_BOOLEAN_FALSE;
3160
3161 pFTRoamInfo->preAuthRspWaitTimerInfo.pMac = pMac;
3162 pFTRoamInfo->preAuthRspWaitTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
3163 status = palTimerAlloc(pMac->hHdd, &pFTRoamInfo->preAuthRspWaitTimer,
3164 csrNeighborRoamPreAuthResponseWaitTimerHandler, (void *)&pFTRoamInfo->preAuthRspWaitTimerInfo);
3165
3166 if (eHAL_STATUS_SUCCESS != status)
3167 {
3168 smsLog(pMac, LOGE, FL("Response wait Timer allocation failed"));
3169 return eHAL_STATUS_RESOURCES;
3170 }
3171
3172 pMac->roam.neighborRoamInfo.FTRoamInfo.currentNeighborRptRetryNum = 0;
3173 pMac->roam.neighborRoamInfo.FTRoamInfo.numBssFromNeighborReport = 0;
3174 vos_mem_zero(pMac->roam.neighborRoamInfo.FTRoamInfo.neighboReportBssInfo,
3175 sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
3176
3177
3178 status = csrLLOpen(pMac->hHdd, &pFTRoamInfo->preAuthDoneList);
3179 if (eHAL_STATUS_SUCCESS != status)
3180 {
3181 smsLog(pMac, LOGE, FL("LL Open of preauth done AP List failed"));
3182 palTimerFree(pMac->hHdd, pFTRoamInfo->preAuthRspWaitTimer);
3183 return eHAL_STATUS_RESOURCES;
3184 }
3185 return status;
3186}
3187#endif /* WLAN_FEATURE_VOWIFI_11R */
3188
3189/* ---------------------------------------------------------------------------
3190
3191 \fn csrNeighborRoamInit
3192
3193 \brief This function initializes neighbor roam data structures
3194
3195 \param pMac - The handle returned by macOpen.
3196
3197 \return eHAL_STATUS_SUCCESS on success, corresponding error code otherwise
3198
3199---------------------------------------------------------------------------*/
3200eHalStatus csrNeighborRoamInit(tpAniSirGlobal pMac)
3201{
3202 eHalStatus status;
3203 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
3204
3205 pNeighborRoamInfo->neighborRoamState = eCSR_NEIGHBOR_ROAM_STATE_CLOSED;
3206 pNeighborRoamInfo->prevNeighborRoamState = eCSR_NEIGHBOR_ROAM_STATE_CLOSED;
3207 pNeighborRoamInfo->csrSessionId = CSR_SESSION_ID_INVALID;
3208 pNeighborRoamInfo->cfgParams.maxChannelScanTime = pMac->roam.configParam.neighborRoamConfig.nNeighborScanMaxChanTime;
3209 pNeighborRoamInfo->cfgParams.minChannelScanTime = pMac->roam.configParam.neighborRoamConfig.nNeighborScanMinChanTime;
3210 pNeighborRoamInfo->cfgParams.maxNeighborRetries = 0;
3211 pNeighborRoamInfo->cfgParams.neighborLookupThreshold = pMac->roam.configParam.neighborRoamConfig.nNeighborLookupRssiThreshold;
3212 pNeighborRoamInfo->cfgParams.neighborReassocThreshold = pMac->roam.configParam.neighborRoamConfig.nNeighborReassocRssiThreshold;
3213 pNeighborRoamInfo->cfgParams.neighborScanPeriod = pMac->roam.configParam.neighborRoamConfig.nNeighborScanTimerPeriod;
3214 pNeighborRoamInfo->cfgParams.neighborResultsRefreshPeriod = pMac->roam.configParam.neighborRoamConfig.nNeighborResultsRefreshPeriod;
3215
3216 pNeighborRoamInfo->cfgParams.channelInfo.numOfChannels =
3217 pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels;
3218
3219 pNeighborRoamInfo->cfgParams.channelInfo.ChannelList =
3220 vos_mem_malloc(pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels);
3221
3222 if (NULL == pNeighborRoamInfo->cfgParams.channelInfo.ChannelList)
3223 {
3224 smsLog(pMac, LOGE, FL("Memory Allocation for CFG Channel List failed"));
3225 return eHAL_STATUS_RESOURCES;
3226 }
3227
3228 /* Update the roam global structure from CFG */
3229 palCopyMemory(pMac->hHdd, pNeighborRoamInfo->cfgParams.channelInfo.ChannelList,
3230 pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.channelList,
3231 pMac->roam.configParam.neighborRoamConfig.neighborScanChanList.numChannels);
3232
3233 vos_mem_set(pNeighborRoamInfo->currAPbssid, sizeof(tCsrBssid), 0);
3234 pNeighborRoamInfo->currentNeighborLookupThreshold = pMac->roam.neighborRoamInfo.cfgParams.neighborLookupThreshold;
Madan Mohan Koyyalamudidd3c9662012-11-09 17:39:30 -08003235#ifdef FEATURE_WLAN_LFR
3236 pNeighborRoamInfo->uEmptyScanCount = 0;
3237 palZeroMemory(pMac->hHdd, &pNeighborRoamInfo->prevConnProfile,
3238 sizeof(tCsrRoamConnectedProfile));
3239#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07003240 pNeighborRoamInfo->scanRspPending = eANI_BOOLEAN_FALSE;
3241
3242 pNeighborRoamInfo->neighborScanTimerInfo.pMac = pMac;
3243 pNeighborRoamInfo->neighborScanTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
3244 status = palTimerAlloc(pMac->hHdd, &pNeighborRoamInfo->neighborScanTimer,
3245 csrNeighborRoamNeighborScanTimerCallback, (void *)&pNeighborRoamInfo->neighborScanTimerInfo);
3246
3247 if (eHAL_STATUS_SUCCESS != status)
3248 {
3249 smsLog(pMac, LOGE, FL("Response wait Timer allocation failed"));
3250 vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
3251 pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
3252 return eHAL_STATUS_RESOURCES;
3253 }
3254
3255 status = palTimerAlloc(pMac->hHdd, &pNeighborRoamInfo->neighborResultsRefreshTimer,
3256 csrNeighborRoamResultsRefreshTimerCallback, (void *)&pNeighborRoamInfo->neighborScanTimerInfo);
3257
3258 if (eHAL_STATUS_SUCCESS != status)
3259 {
3260 smsLog(pMac, LOGE, FL("Response wait Timer allocation failed"));
3261 smsLog(pMac, LOGE, FL("LL Open of roamable AP List failed"));
3262 vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
3263 pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
3264 palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
3265 return eHAL_STATUS_RESOURCES;
3266 }
3267
3268 status = csrLLOpen(pMac->hHdd, &pNeighborRoamInfo->roamableAPList);
3269 if (eHAL_STATUS_SUCCESS != status)
3270 {
3271 smsLog(pMac, LOGE, FL("LL Open of roamable AP List failed"));
3272 vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
3273 pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
3274 palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
3275 palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
3276 return eHAL_STATUS_RESOURCES;
3277 }
3278
3279 pNeighborRoamInfo->roamChannelInfo.currentChanIndex = CSR_NEIGHBOR_ROAM_INVALID_CHANNEL_INDEX;
3280 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels = 0;
3281 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
3282 pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_FALSE;
3283 pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived = eANI_BOOLEAN_FALSE;
3284
3285#ifdef WLAN_FEATURE_VOWIFI_11R
3286 status = csrNeighborRoamInit11rAssocInfo(pMac);
3287 if (eHAL_STATUS_SUCCESS != status)
3288 {
3289 smsLog(pMac, LOGE, FL("LL Open of roamable AP List failed"));
3290 vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
3291 pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
3292 palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
3293 palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
3294 csrLLClose(&pNeighborRoamInfo->roamableAPList);
3295 return eHAL_STATUS_RESOURCES;
3296 }
3297#endif
3298 /* Initialize this with the current tick count */
3299 pNeighborRoamInfo->scanRequestTimeStamp = (tANI_TIMESTAMP)palGetTickCount(pMac->hHdd);
3300
3301 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
3302
3303 return eHAL_STATUS_SUCCESS;
3304}
3305
3306/* ---------------------------------------------------------------------------
3307
3308 \fn csrNeighborRoamClose
3309
3310 \brief This function closes/frees all the neighbor roam data structures
3311
3312 \param pMac - The handle returned by macOpen.
3313
3314 \return VOID
3315
3316---------------------------------------------------------------------------*/
3317void csrNeighborRoamClose(tpAniSirGlobal pMac)
3318{
3319 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
3320
3321 if (eCSR_NEIGHBOR_ROAM_STATE_CLOSED == pNeighborRoamInfo->neighborRoamState)
3322 {
Madan Mohan Koyyalamudi8b7f1e62012-10-05 14:56:51 -07003323 smsLog(pMac, LOGW, FL("Neighbor Roam Algorithm Already Closed"));
Jeff Johnson295189b2012-06-20 16:38:30 -07003324 return;
3325 }
3326
3327 if (pNeighborRoamInfo->cfgParams.channelInfo.ChannelList)
3328 vos_mem_free(pNeighborRoamInfo->cfgParams.channelInfo.ChannelList);
3329
3330 pNeighborRoamInfo->cfgParams.channelInfo.ChannelList = NULL;
3331
3332 pNeighborRoamInfo->neighborScanTimerInfo.pMac = NULL;
3333 pNeighborRoamInfo->neighborScanTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
3334 palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborScanTimer);
3335 palTimerFree(pMac->hHdd, pNeighborRoamInfo->neighborResultsRefreshTimer);
3336
3337 /* Should free up the nodes in the list before closing the double Linked list */
3338 csrNeighborRoamFreeRoamableBSSList(pMac, &pNeighborRoamInfo->roamableAPList);
3339 csrLLClose(&pNeighborRoamInfo->roamableAPList);
3340
3341 if (pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList)
3342 {
3343 vos_mem_free(pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList);
3344 }
3345
3346 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
3347 pNeighborRoamInfo->roamChannelInfo.currentChanIndex = CSR_NEIGHBOR_ROAM_INVALID_CHANNEL_INDEX;
3348 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.numOfChannels = 0;
3349 pNeighborRoamInfo->roamChannelInfo.currentChannelListInfo.ChannelList = NULL;
3350 pNeighborRoamInfo->roamChannelInfo.chanListScanInProgress = eANI_BOOLEAN_FALSE;
3351 pNeighborRoamInfo->roamChannelInfo.IAPPNeighborListReceived = eANI_BOOLEAN_FALSE;
3352
3353 /* Free the profile.. */
3354 csrReleaseProfile(pMac, &pNeighborRoamInfo->csrNeighborRoamProfile);
3355
3356#ifdef WLAN_FEATURE_VOWIFI_11R
3357 pMac->roam.neighborRoamInfo.FTRoamInfo.currentNeighborRptRetryNum = 0;
3358 palTimerFree(pMac->hHdd, pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthRspWaitTimer);
3359 pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthRspWaitTimerInfo.pMac = NULL;
3360 pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthRspWaitTimerInfo.sessionId = CSR_SESSION_ID_INVALID;
3361 pMac->roam.neighborRoamInfo.FTRoamInfo.numBssFromNeighborReport = 0;
3362 vos_mem_zero(pMac->roam.neighborRoamInfo.FTRoamInfo.neighboReportBssInfo,
3363 sizeof(tCsrNeighborReportBssInfo) * MAX_BSS_IN_NEIGHBOR_RPT);
3364 csrNeighborRoamFreeRoamableBSSList(pMac, &pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthDoneList);
3365 csrLLClose(&pMac->roam.neighborRoamInfo.FTRoamInfo.preAuthDoneList);
3366#endif /* WLAN_FEATURE_VOWIFI_11R */
3367
3368 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_CLOSED)
3369
3370 return;
3371}
3372
3373/* ---------------------------------------------------------------------------
3374
3375 \fn csrNeighborRoamRequestHandoff
3376
3377 \brief This function triggers actual switching from one AP to the new AP.
3378 It issues disassociate with reason code as Handoff and CSR as a part of
3379 handling disassoc rsp, issues reassociate to the new AP
3380
3381 \param pMac - The handle returned by macOpen.
3382
3383 \return VOID
3384
3385---------------------------------------------------------------------------*/
3386void csrNeighborRoamRequestHandoff(tpAniSirGlobal pMac)
3387{
3388
3389 tCsrRoamInfo roamInfo;
3390 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
3391 tANI_U32 sessionId = pNeighborRoamInfo->csrSessionId;
3392 tCsrNeighborRoamBSSInfo handoffNode;
3393 extern void csrRoamRoamingStateDisassocRspProcessor( tpAniSirGlobal pMac, tSirSmeDisassocRsp *pSmeDisassocRsp );
3394 tANI_U32 roamId = 0;
3395
3396 if (pMac->roam.neighborRoamInfo.neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE)
3397 {
3398 smsLog(pMac, LOGE, FL("Roam requested when Neighbor roam is in %d state"),
3399 pMac->roam.neighborRoamInfo.neighborRoamState);
3400 return;
3401 }
3402
3403 vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
3404 csrRoamCallCallback(pMac, pNeighborRoamInfo->csrSessionId, &roamInfo, roamId, eCSR_ROAM_FT_START,
3405 eSIR_SME_SUCCESS);
3406
3407 vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
3408 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING)
3409
3410 csrNeighborRoamGetHandoffAPInfo(pMac, &handoffNode);
3411 smsLog(pMac, LOGE, FL("HANDOFF CANDIDATE BSSID %02x:%02x:%02x:%02x:%02x:%02x"),
3412 handoffNode.pBssDescription->bssId[0],
3413 handoffNode.pBssDescription->bssId[1],
3414 handoffNode.pBssDescription->bssId[2],
3415 handoffNode.pBssDescription->bssId[3],
3416 handoffNode.pBssDescription->bssId[4],
3417 handoffNode.pBssDescription->bssId[5]);
3418
3419 /* Free the profile.. Just to make sure we dont leak memory here */
3420 csrReleaseProfile(pMac, &pNeighborRoamInfo->csrNeighborRoamProfile);
3421 /* Create the Handoff AP profile. Copy the currently connected profile and update only the BSSID and channel number
3422 This should happen before issuing disconnect */
3423 csrRoamCopyConnectedProfile(pMac, pNeighborRoamInfo->csrSessionId, &pNeighborRoamInfo->csrNeighborRoamProfile);
3424 vos_mem_copy(pNeighborRoamInfo->csrNeighborRoamProfile.BSSIDs.bssid, handoffNode.pBssDescription->bssId, sizeof(tSirMacAddr));
3425 pNeighborRoamInfo->csrNeighborRoamProfile.ChannelInfo.ChannelList[0] = handoffNode.pBssDescription->channelId;
3426
3427 NEIGHBOR_ROAM_DEBUG(pMac, LOGW, " csrRoamHandoffRequested: disassociating with current AP\n");
3428
3429 if(!HAL_STATUS_SUCCESS(csrRoamIssueDisassociateCmd(pMac, sessionId, eCSR_DISCONNECT_REASON_HANDOFF)))
3430 {
3431 smsLog(pMac, LOGW, "csrRoamHandoffRequested: fail to issue disassociate\n");
3432 return;
3433 }
3434
3435 //notify HDD for handoff, providing the BSSID too
3436 roamInfo.reasonCode = eCsrRoamReasonBetterAP;
3437
3438 vos_mem_copy(roamInfo.bssid,
3439 handoffNode.pBssDescription->bssId,
3440 sizeof( tCsrBssid ));
3441
3442 csrRoamCallCallback(pMac, sessionId, &roamInfo, 0, eCSR_ROAM_ROAMING_START, eCSR_ROAM_RESULT_NONE);
3443
3444
3445 return;
3446}
3447
3448/* ---------------------------------------------------------------------------
3449
3450 \fn csrNeighborRoamIsHandoffInProgress
3451
3452 \brief This function returns whether handoff is in progress or not based on
3453 the current neighbor roam state
3454
3455 \param pMac - The handle returned by macOpen.
3456 is11rReassoc - Return whether reassoc is of type 802.11r reassoc
3457
3458 \return eANI_BOOLEAN_TRUE if reassoc in progress, eANI_BOOLEAN_FALSE otherwise
3459
3460---------------------------------------------------------------------------*/
3461tANI_BOOLEAN csrNeighborRoamIsHandoffInProgress(tpAniSirGlobal pMac)
3462{
3463 if (eCSR_NEIGHBOR_ROAM_STATE_REASSOCIATING == pMac->roam.neighborRoamInfo.neighborRoamState)
3464 return eANI_BOOLEAN_TRUE;
3465
3466 return eANI_BOOLEAN_FALSE;
3467}
3468
Madan Mohan Koyyalamudi5e32b962012-11-28 16:07:55 -08003469#if defined(WLAN_FEATURE_VOWIFI_11R) || defined(WLAN_FEATURE_NEIGHBOR_ROAMING)
Jeff Johnson295189b2012-06-20 16:38:30 -07003470/* ---------------------------------------------------------------------------
3471
3472 \fn csrNeighborRoamIs11rAssoc
3473
3474 \brief This function returns whether the current association is a 11r assoc or not
3475
3476 \param pMac - The handle returned by macOpen.
3477
3478 \return eANI_BOOLEAN_TRUE if current assoc is 11r, eANI_BOOLEAN_FALSE otherwise
3479
3480---------------------------------------------------------------------------*/
3481tANI_BOOLEAN csrNeighborRoamIs11rAssoc(tpAniSirGlobal pMac)
3482{
3483 return pMac->roam.neighborRoamInfo.is11rAssoc;
3484}
3485#endif /* WLAN_FEATURE_VOWIFI_11R */
3486
3487
3488/* ---------------------------------------------------------------------------
3489
3490 \fn csrNeighborRoamGetHandoffAPInfo
3491
3492 \brief This function returns the best possible AP for handoff. For 11R case, it
3493 returns the 1st entry from pre-auth done list. For non-11r case, it returns
3494 the 1st entry from roamable AP list
3495
3496 \param pMac - The handle returned by macOpen.
3497 pHandoffNode - AP node that is the handoff candidate returned
3498
3499 \return VOID
3500
3501---------------------------------------------------------------------------*/
3502void csrNeighborRoamGetHandoffAPInfo(tpAniSirGlobal pMac, tpCsrNeighborRoamBSSInfo pHandoffNode)
3503{
3504 tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
3505 tpCsrNeighborRoamBSSInfo pBssNode;
3506
3507 VOS_ASSERT(NULL != pHandoffNode);
3508
3509#ifdef WLAN_FEATURE_VOWIFI_11R
3510 if (pNeighborRoamInfo->is11rAssoc)
3511 {
3512 /* Always the BSS info in the head is the handoff candidate */
3513 pBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->FTRoamInfo.preAuthDoneList, NULL);
3514 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Number of Handoff candidates = %d"), csrLLCount(&pNeighborRoamInfo->FTRoamInfo.preAuthDoneList));
3515 }
3516 else
3517#endif
3518#ifdef FEATURE_WLAN_CCX
3519 if (pNeighborRoamInfo->isCCXAssoc)
3520 {
3521 /* Always the BSS info in the head is the handoff candidate */
3522 pBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->FTRoamInfo.preAuthDoneList, NULL);
3523 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Number of Handoff candidates = %d"), csrLLCount(&pNeighborRoamInfo->FTRoamInfo.preAuthDoneList));
3524 }
3525 else
3526#endif
Jeff Johnson04dd8a82012-06-29 20:41:40 -07003527#ifdef FEATURE_WLAN_LFR
Madan Mohan Koyyalamudi03aae5f2012-11-28 01:51:22 +05303528 if (csrRoamIsFastRoamEnabled(pMac, CSR_SESSION_ID_INVALID))
Jeff Johnson04dd8a82012-06-29 20:41:40 -07003529 {
3530 /* Always the BSS info in the head is the handoff candidate */
3531 pBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->FTRoamInfo.preAuthDoneList, NULL);
3532 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Number of Handoff candidates = %d"), csrLLCount(&pNeighborRoamInfo->FTRoamInfo.preAuthDoneList));
3533 }
3534 else
3535#endif
Jeff Johnson295189b2012-06-20 16:38:30 -07003536 {
3537 pBssNode = csrNeighborRoamGetRoamableAPListNextEntry(pMac, &pNeighborRoamInfo->roamableAPList, NULL);
3538 NEIGHBOR_ROAM_DEBUG(pMac, LOG1, FL("Number of Handoff candidates = %d"), csrLLCount(&pNeighborRoamInfo->roamableAPList));
3539 }
3540 vos_mem_copy(pHandoffNode, pBssNode, sizeof(tCsrNeighborRoamBSSInfo));
3541
3542 return;
3543}
3544
3545/* ---------------------------------------------------------------------------
3546 \brief This function returns TRUE if preauth is completed
3547
3548 \param pMac - The handle returned by macOpen.
3549
3550 \return boolean
3551
3552---------------------------------------------------------------------------*/
3553tANI_BOOLEAN csrNeighborRoamStatePreauthDone(tpAniSirGlobal pMac)
3554{
3555 return (pMac->roam.neighborRoamInfo.neighborRoamState ==
3556 eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE);
3557}
3558
3559/* ---------------------------------------------------------------------------
3560 \brief In the event that we are associated with AP1 and we have
3561 completed pre auth with AP2. Then we receive a deauth/disassoc from
3562 AP1.
3563 At this point neighbor roam is in pre auth done state, pre auth timer
3564 is running. We now handle this case by stopping timer and clearing
3565 the pre-auth state. We basically clear up and just go to disconnected
3566 state.
3567
3568 \param pMac - The handle returned by macOpen.
3569
3570 \return boolean
3571---------------------------------------------------------------------------*/
3572void csrNeighborRoamTranistionPreauthDoneToDisconnected(tpAniSirGlobal pMac)
3573{
3574 if (pMac->roam.neighborRoamInfo.neighborRoamState !=
3575 eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE) return;
3576
3577 // Stop timer
3578 palTimerStop(pMac->hHdd, pMac->ft.ftSmeContext.preAuthReassocIntvlTimer);
3579
3580 // Transition to init state
3581 CSR_NEIGHBOR_ROAM_STATE_TRANSITION(eCSR_NEIGHBOR_ROAM_STATE_INIT)
3582}
3583
3584#endif /* WLAN_FEATURE_NEIGHBOR_ROAMING */