blob: 8b45b1defa37b314b6b24ea343ff51a0af462f81 [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 * Copyright (c) 2008 QUALCOMM Incorporated. All Rights Reserved.
24 * Qualcomm Confidential and Proprietary
25 */
26
27#if defined WLAN_FEATURE_P2P
28
29#include "sme_Api.h"
30#include "smsDebug.h"
31#include "csrInsideApi.h"
32#include "smeInside.h"
33#include "p2p_Api.h"
34#include "limApi.h"
35#include "cfgApi.h"
36
37#ifdef WLAN_FEATURE_P2P_INTERNAL
38#include "p2p_ie.h"
39#include "p2pFsm.h"
40
41extern tp2pie gP2PIe;
42
43static eHalStatus p2pSendActionFrame(tpAniSirGlobal pMac, tANI_U8 SessionID, eP2PFrameType actionFrameType);
44static eHalStatus p2pListenStateDiscoverableCallback(tHalHandle halHandle, void *pContext, eHalStatus retStatus);
45static eHalStatus p2pRemainOnChannelReadyCallback(tHalHandle halHandle, void *pContext, eHalStatus scan_status);
46static tANI_BOOLEAN p2pIsGOportEnabled(tpAniSirGlobal pMac);
47#endif
48
49eHalStatus p2pProcessNoAReq(tpAniSirGlobal pMac, tSmeCmd *pNoACmd);
50/*------------------------------------------------------------------
51 *
52 * handle SME remain on channel request.
53 *
54 *------------------------------------------------------------------*/
55
56eHalStatus p2pProcessRemainOnChannelCmd(tpAniSirGlobal pMac, tSmeCmd *p2pRemainonChn)
57{
58 eHalStatus status = eHAL_STATUS_SUCCESS;
59 tSirRemainOnChnReq* pMsg;
60 tANI_U16 len;
61 tCsrRoamSession *pSession = CSR_GET_SESSION( pMac, p2pRemainonChn->sessionId );
Jeff Johnson32d95a32012-09-10 13:15:23 -070062
63 if(!pSession)
64 {
65 smsLog(pMac, LOGE, FL(" session %d not found "), p2pRemainonChn->sessionId);
66 return eHAL_STATUS_FAILURE;
67 }
68
Jeff Johnson295189b2012-06-20 16:38:30 -070069#ifdef WLAN_FEATURE_P2P_INTERNAL
70 tANI_U8 P2PsessionId = getP2PSessionIdFromSMESessionId(pMac, p2pRemainonChn->sessionId);
71 tp2pContext *p2pContext = &pMac->p2pContext[P2PsessionId];
72 tANI_U32 ieLen = 0;
73#endif
74
75#ifdef WLAN_FEATURE_P2P_INTERNAL
76 if( !pSession->sessionActive || (CSR_SESSION_ID_INVALID == P2PsessionId))
77 {
78 smsLog(pMac, LOGE, FL(" session %d (P2P session %d) is invalid or listen is disabled "),
79 p2pRemainonChn->sessionId, P2PsessionId);
80 return eHAL_STATUS_FAILURE;
81 }
82#else
83 if(!pSession->sessionActive)
84 {
85 smsLog(pMac, LOGE, FL(" session %d is invalid or listen is disabled "),
86 p2pRemainonChn->sessionId);
87 return eHAL_STATUS_FAILURE;
88 }
89#endif
90#ifdef WLAN_FEATURE_P2P_INTERNAL
91 P2P_GetIE(p2pContext,
92 p2pContext->sessionId, eP2P_PROBE_RSP,
93 &p2pContext->probeRspIe, &ieLen);
94 p2pContext->probeRspIeLength = ieLen;
95 len = sizeof(tSirRemainOnChnReq) + ieLen;
96#else
97 len = sizeof(tSirRemainOnChnReq) + pMac->p2pContext.probeRspIeLength;
98#endif
99
100 status = palAllocateMemory(pMac->hHdd, (void**)&pMsg, len );
101 if(HAL_STATUS_SUCCESS(status))
102 {
103 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s call\n", __FUNCTION__);
104 palZeroMemory(pMac->hHdd, pMsg, sizeof(tSirRemainOnChnReq));
105 pMsg->messageType = eWNI_SME_REMAIN_ON_CHANNEL_REQ;
106 pMsg->length = len;
107 palCopyMemory( pMac, pMsg->selfMacAddr, pSession->selfMacAddr, sizeof(tSirMacAddr) );
108 pMsg->chnNum = p2pRemainonChn->u.remainChlCmd.chn;
109 pMsg->phyMode = p2pRemainonChn->u.remainChlCmd.phyMode;
110 pMsg->duration = p2pRemainonChn->u.remainChlCmd.duration;
111 pMsg->sessionId = p2pRemainonChn->sessionId;
112#ifdef WLAN_FEATURE_P2P_INTERNAL
113 pMsg->sessionId = pSession->sessionId;
114 if( p2pContext->probeRspIeLength )
115 {
116 palCopyMemory(pMac->hHdd, (void *)pMsg->probeRspIe,
117 (void *)p2pContext->probeRspIe,
118 p2pContext->probeRspIeLength);
119 }
120#else
121 if( pMac->p2pContext.probeRspIeLength )
122 palCopyMemory(pMac->hHdd, (void *)pMsg->probeRspIe, (void *)pMac->p2pContext.probeRspIe, pMac->p2pContext.probeRspIeLength);
123#endif
124 status = palSendMBMessage(pMac->hHdd, pMsg);
125 }
126
127 return status;
128}
129
130
131/*------------------------------------------------------------------
132 *
133 * handle LIM remain on channel rsp: Success/failure.
134 *
135 *------------------------------------------------------------------*/
136
137eHalStatus sme_remainOnChnRsp( tpAniSirGlobal pMac, tANI_U8 *pMsg)
138{
139 eHalStatus status = eHAL_STATUS_SUCCESS;
140 tListElem *pEntry = NULL;
141 tSmeCmd *pCommand = NULL;
142
143 pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
144 if( pEntry )
145 {
146 pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
147 if( eSmeCommandRemainOnChannel == pCommand->command )
148 {
149 remainOnChanCallback callback = pCommand->u.remainChlCmd.callback;
150 /* process the msg */
151 if( callback )
152 callback(pMac, pCommand->u.remainChlCmd.callbackCtx, 0);
153
154 if( csrLLRemoveEntry( &pMac->sme.smeCmdActiveList, pEntry, LL_ACCESS_LOCK ) )
155 {
156 //Now put this command back on the avilable command list
157 smeReleaseCommand(pMac, pCommand);
158 }
159 smeProcessPendingQueue( pMac );
160 }
161 }
162 return status;
163}
164
165
166/*------------------------------------------------------------------
167 *
168 * Handle the Mgmt frm ind from LIM and forward to HDD.
169 *
170 *------------------------------------------------------------------*/
171
172eHalStatus sme_mgmtFrmInd( tHalHandle hHal, tpSirSmeMgmtFrameInd pSmeMgmtFrm)
173{
174 tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
175 eHalStatus status = eHAL_STATUS_SUCCESS;
176 tCsrRoamInfo pRoamInfo = {0};
177#ifndef WLAN_FEATURE_P2P_INTERNAL
178 tANI_U32 SessionId = pSmeMgmtFrm->sessionId;
179#endif
180
181#ifdef WLAN_FEATURE_P2P_INTERNAL
182 tANI_U8 i;
183
184 //For now, only action frames are needed.
185 if(SIR_MAC_MGMT_ACTION == pSmeMgmtFrm->frameType)
186 {
187 pRoamInfo.nFrameLength = pSmeMgmtFrm->mesgLen - sizeof(tSirSmeMgmtFrameInd);
188 pRoamInfo.pbFrames = pSmeMgmtFrm->frameBuf;
189 pRoamInfo.frameType = pSmeMgmtFrm->frameType;
190 pRoamInfo.rxChan = pSmeMgmtFrm->rxChan;
191
192 //Somehow we don't get the right sessionId.
193 for(i = 0; i < CSR_ROAM_SESSION_MAX; i++)
194 {
195 if( CSR_IS_SESSION_VALID( pMac, i ) )
196 {
197 status = eHAL_STATUS_SUCCESS;
198 /* forward the mgmt frame to all active sessions*/
199 csrRoamCallCallback(pMac, i, &pRoamInfo, 0, eCSR_ROAM_INDICATE_MGMT_FRAME, 0);
200 }
201 }
202 }
203#else
204 pRoamInfo.nFrameLength = pSmeMgmtFrm->mesgLen - sizeof(tSirSmeMgmtFrameInd);
205 pRoamInfo.pbFrames = pSmeMgmtFrm->frameBuf;
206 pRoamInfo.frameType = pSmeMgmtFrm->frameType;
207 pRoamInfo.rxChan = pSmeMgmtFrm->rxChan;
208
209 /* forward the mgmt frame to HDD */
210 csrRoamCallCallback(pMac, SessionId, &pRoamInfo, 0, eCSR_ROAM_INDICATE_MGMT_FRAME, 0);
211#endif
212
213 return status;
214}
215
216
217/*------------------------------------------------------------------
218 *
219 * Handle the remain on channel ready indication from PE
220 *
221 *------------------------------------------------------------------*/
222
223eHalStatus sme_remainOnChnReady( tHalHandle hHal, tANI_U8* pMsg)
224{
225 tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
226 eHalStatus status = eHAL_STATUS_SUCCESS;
227 tListElem *pEntry = NULL;
228 tSmeCmd *pCommand = NULL;
229 tCsrRoamInfo RoamInfo;
230#ifdef WLAN_FEATURE_P2P_INTERNAL
231 tSirSmeRsp *pRsp = (tSirSmeRsp *)pMsg;
232 //pRsp->sessionId is SME's session index
233 tANI_U8 P2PSessionID = getP2PSessionIdFromSMESessionId(pMac, pRsp->sessionId);
234
235 if(CSR_SESSION_ID_INVALID == P2PSessionID)
236 {
237 return eHAL_STATUS_FAILURE;
238 }
239#endif
240
241 pEntry = csrLLPeekHead(&pMac->sme.smeCmdActiveList, LL_ACCESS_LOCK);
242 if( pEntry )
243 {
244 pCommand = GET_BASE_ADDR(pEntry, tSmeCmd, Link);
245 if( eSmeCommandRemainOnChannel == pCommand->command )
246 {
247
248#ifdef WLAN_FEATURE_P2P_INTERNAL
249 if (pMac->p2pContext[P2PSessionID].PeerFound)
250 {
251 p2pRemainOnChannelReadyCallback(pMac, &pMac->p2pContext[P2PSessionID], eHAL_STATUS_SUCCESS);
252 }
253#else
254 /* forward the indication to HDD */
255 RoamInfo.pRemainCtx = pCommand->u.remainChlCmd.callbackCtx;
256 csrRoamCallCallback(pMac, ((tSirSmeRsp*)pMsg)->sessionId, &RoamInfo,
257 0, eCSR_ROAM_REMAIN_CHAN_READY, 0);
258#endif
259 }
260 }
261
262 return status;
263}
264
265
266eHalStatus sme_sendActionCnf( tHalHandle hHal, tANI_U8* pMsg)
267{
268 tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
269 eHalStatus status = eHAL_STATUS_SUCCESS;
270 tCsrRoamInfo RoamInfo;
271 tSirSmeRsp* pSmeRsp = (tSirSmeRsp*)pMsg;
272
273#ifdef WLAN_FEATURE_P2P_INTERNAL
274 tSirResultCodes rspStatus = pSmeRsp->statusCode;
275 tANI_U8 HDDsessionId = getP2PSessionIdFromSMESessionId(pMac, pSmeRsp->sessionId);
276 tANI_U8 *pBuf = NULL;
277 tp2pContext *pP2pContext;
278
279 if(CSR_SESSION_ID_INVALID == HDDsessionId)
280 {
281 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
282 " %s fail to get HDD sessionID (SMESessionID %d)", __FUNCTION__, pSmeRsp->sessionId);
283 return eHAL_STATUS_INVALID_PARAMETER;
284 }
285
286 pP2pContext = &pMac->p2pContext[HDDsessionId];
287
288 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s status %d Action Frame %d actionFrameTimeout %d\n",
289 __FUNCTION__, pSmeRsp->statusCode, pP2pContext->actionFrameType
290 , pP2pContext->actionFrameTimeout);
291 vos_mem_zero(&RoamInfo, sizeof(tCsrRoamInfo));
292
293 if (pSmeRsp->statusCode != eSIR_SME_SUCCESS && !pP2pContext->actionFrameTimeout
294 && pP2pContext->pSentActionFrame)
295 {
296 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Action frame:Ack not received. Retransmitting\n", __FUNCTION__);
297
298 if(NULL == pP2pContext->pNextActionFrm)
299 {
300 status = palTimerStart(pMac->hHdd, pP2pContext->retryActionFrameTimer,
301 ACTION_FRAME_RETRY_TIMEOUT * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
302 if (!HAL_STATUS_SUCCESS(status))
303 {
304 smsLog(pMac, LOGE, " %s fail to start retryActionFrameTimerHandler\n",
305 __FUNCTION__, pP2pContext->NextActionFrameType);
306 }
307 return status;
308 }
309 //In case if there is new frame to send, finish the current frame
310 else
311 {
312 smsLog(pMac, LOGE, " %s send next action frame type %d Last frame status (%d)",
313 __FUNCTION__, rspStatus);
314 //Force it to be success
315 rspStatus = eSIR_SME_SUCCESS;
316 }
317 }
318
319 if (pP2pContext->actionFrameTimer)
320 {
321 status = palTimerStop(pMac, pP2pContext->actionFrameTimer);
322 }
323
324 if (pP2pContext->retryActionFrameTimer)
325 {
326 status = palTimerStop(pMac, pP2pContext->retryActionFrameTimer);
327 }
328
329 if(pP2pContext->pSentActionFrame)
330 {
331 csrRoamCallCallback((tpAniSirGlobal)pP2pContext->hHal,
332 pP2pContext->SMEsessionId, &RoamInfo, 0,
333 eCSR_ROAM_SEND_ACTION_CNF,
334 ((rspStatus == eSIR_SME_SUCCESS) ?
335 eCSR_ROAM_RESULT_NONE: eCSR_ROAM_RESULT_SEND_ACTION_FAIL));
336 }
337
338 if(VOS_IS_STATUS_SUCCESS(vos_spin_lock_acquire(&pP2pContext->lState)))
339 {
340 if(pP2pContext->pSentActionFrame)
341 {
342 pBuf = pP2pContext->pSentActionFrame;
343 pP2pContext->pSentActionFrame = NULL;
344 }
345 vos_spin_lock_release(&pP2pContext->lState);
346
347 if(NULL != pBuf)
348 {
349 vos_mem_free(pBuf);
350 pBuf = NULL;
351 }
352 else
353 {
354 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN, "%s pSentActionFrame is null \n", __FUNCTION__);
355 }
356 if(pP2pContext->pNextActionFrm)
357 {
358 //need to send the next action frame
359 pP2pContext->pSentActionFrame = pP2pContext->pNextActionFrm;
360 pP2pContext->ActionFrameLen = pP2pContext->nNextFrmLen;
361 pP2pContext->actionFrameType = pP2pContext->NextActionFrameType;
362 pP2pContext->pNextActionFrm = NULL;
363 pP2pContext->ActionFrameSendTimeout = pP2pContext->nNextFrameTimeOut;
364 }
365 }
366 else
367 {
368 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s cannot get lock1", __FUNCTION__);
369 }
370
371 if(NULL != pP2pContext->pSentActionFrame)
372 {
373 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, " sending next frame %d type\n",
374 pP2pContext->NextActionFrameType);
375 status = palTimerStart(pMac->hHdd, pP2pContext->actionFrameTimer,
376 pP2pContext->ActionFrameSendTimeout * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
377 if (!HAL_STATUS_SUCCESS(status))
378 {
379 smsLog(pMac, LOGE, FL(" %s fail to start timer status %d"), __FUNCTION__, status);
380 //Without the timer we cannot continue
381 csrRoamCallCallback((tpAniSirGlobal)pP2pContext->hHal,
382 pP2pContext->SMEsessionId, &RoamInfo, 0,
383 eCSR_ROAM_SEND_ACTION_CNF,
384 eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
385 vos_spin_lock_acquire(&pP2pContext->lState);
386 pBuf = pP2pContext->pSentActionFrame;
387 pP2pContext->pSentActionFrame = NULL;
388 vos_spin_lock_release(&pP2pContext->lState);
389 vos_mem_free(pBuf);
390 pBuf = NULL;
391 p2pFsm(pP2pContext, eP2P_TRIGGER_DISCONNECTED);
392 return status;
393 }
394 status = p2pSendActionFrame(pMac, pP2pContext->sessionId, pP2pContext->actionFrameType);
395 if(!HAL_STATUS_SUCCESS(status))
396 {
397 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, " sending next frame %d type\n",
398 pP2pContext->NextActionFrameType);
399 status = palTimerStart(pMac->hHdd, pP2pContext->retryActionFrameTimer,
400 ACTION_FRAME_RETRY_TIMEOUT * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
401 if (!HAL_STATUS_SUCCESS(status))
402 {
403 smsLog(pMac, LOGE, " %s fail to start retryActionFrameTimerHandler\n", __FUNCTION__);
404 }
405 }
406 }
407 else
408 {
409 p2pFsm(pP2pContext, eP2P_TRIGGER_DISCONNECTED);
410 }
411
412#else
413 /* forward the indication to HDD */
414 //RoamInfo can be passed as NULL....todo
415 csrRoamCallCallback(pMac, pSmeRsp->sessionId, &RoamInfo, 0,
416 eCSR_ROAM_SEND_ACTION_CNF,
417 (pSmeRsp->statusCode == eSIR_SME_SUCCESS) ? 0:
418 eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
419#endif
420 return status;
421}
422
423
424#ifdef WLAN_FEATURE_P2P_INTERNAL
425void p2pResetContext(tp2pContext *pP2pContext)
426{
427 if(NULL != pP2pContext)
428 {
429 tpAniSirGlobal pMac = PMAC_STRUCT(pP2pContext->hHal);
430 int i;
431
432 //When it is resetting a GO or client session, we
433 //need to reset the group capability back to the original one
434 if( (OPERATION_MODE_P2P_GROUP_OWNER == pP2pContext->operatingmode) ||
435 (OPERATION_MODE_P2P_CLIENT == pP2pContext->operatingmode) )
436 {
437 for( i = 0; i < MAX_NO_OF_P2P_SESSIONS; i++ )
438 {
439 if(OPERATION_MODE_P2P_DEVICE == pMac->p2pContext[i].operatingmode)
440 {
441 gP2PIe[i].p2pCapabilityAttrib.groupCapability = pMac->p2pContext[i].OriginalGroupCapability;
442 }
443 }
444 }
445
446 pP2pContext->state = eP2P_STATE_DISCONNECTED;
447 pP2pContext->currentSearchIndex = 0;
448 pP2pContext->listenIndex = 1;
449
450 pP2pContext->actionFrameType = eP2P_INVALID_FRM;
451
452 pP2pContext->dialogToken = 0;
453 pP2pContext->PeerFound = FALSE;
454 pP2pContext->GroupFormationPending = FALSE;
455 pP2pContext->directedDiscovery = FALSE;
456 pP2pContext->listenDiscoverableState = eStateDisabled;
457
458
459 if(pP2pContext->pSentActionFrame)
460 {
461 vos_mem_free(pP2pContext->pSentActionFrame);
462 pP2pContext->pSentActionFrame = NULL;
463 }
464 if(pP2pContext->pNextActionFrm)
465 {
466 vos_mem_free(pP2pContext->pSentActionFrame);
467 pP2pContext->pSentActionFrame = NULL;
468 }
469 if( pP2pContext->probeRspIe )
470 {
471 vos_mem_free( pP2pContext->probeRspIe );
472 pP2pContext->probeRspIe = NULL;
473 pP2pContext->probeRspIeLength = 0;
474 }
475
476 if( pP2pContext->DiscoverReqIeField )
477 {
478 vos_mem_free(pP2pContext->DiscoverReqIeField );
479 pP2pContext->DiscoverReqIeField = NULL;
480 pP2pContext->DiscoverReqIeLength = 0;
481 }
482
483 if( pP2pContext->GoNegoCnfIeField )
484 {
485 vos_mem_free( pP2pContext->GoNegoCnfIeField);
486 pP2pContext->GoNegoCnfIeField = NULL;
487 pP2pContext->GoNegoCnfIeLength = 0;
488 }
489
490 if( pP2pContext->GoNegoReqIeField )
491 {
492 vos_mem_free( pP2pContext->GoNegoReqIeField );
493 pP2pContext->GoNegoReqIeField = NULL;
494 pP2pContext->GoNegoReqIeLength = 0;
495 }
496
497 if( pP2pContext->GoNegoResIeField )
498 {
499 vos_mem_free( pP2pContext->GoNegoResIeField );
500 pP2pContext->GoNegoResIeField = NULL;
501 pP2pContext->GoNegoResIeLength = 0;
502 }
503
504 if( pP2pContext->ProvDiscReqIeField )
505 {
506 vos_mem_free( pP2pContext->ProvDiscReqIeField );
507 pP2pContext->ProvDiscReqIeField = NULL;
508 pP2pContext->ProvDiscReqIeLength = 0;
509 }
510
511 if( pP2pContext->ProvDiscResIeField )
512 {
513 vos_mem_free( pP2pContext->ProvDiscResIeField );
514 pP2pContext->ProvDiscResIeLength = 0;
515 pP2pContext->ProvDiscResIeField = NULL;
516 }
517
518 if (pP2pContext->actionFrameTimer)
519 {
520 palTimerStop(pMac->hHdd, pP2pContext->actionFrameTimer);
521 }
522
523 if (pP2pContext->discoverTimer)
524 {
525 palTimerStop(pMac->hHdd, pP2pContext->discoverTimer);
526 }
527
528 if (pP2pContext->listenTimerHandler)
529 {
530 palTimerStop(pMac->hHdd, pP2pContext->listenTimerHandler);
531 }
532
533 if (pP2pContext->WPSRegistrarCheckTimerHandler)
534 {
535 palTimerStop(pMac->hHdd, pP2pContext->WPSRegistrarCheckTimerHandler);
536 }
537
538 if (pP2pContext->directedDiscoveryFilter)
539 {
540 pP2pContext->uNumDeviceFilterAllocated = 0;
541 vos_mem_free(pP2pContext->directedDiscoveryFilter);
542 pP2pContext->directedDiscoveryFilter = NULL;
543 }
544
545 vos_mem_zero(pP2pContext->peerMacAddress, P2P_MAC_ADDRESS_LEN);
546 }
547}
548#endif
549
550
551eHalStatus sme_p2pOpen( tHalHandle hHal )
552{
553 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
554 eHalStatus status = eHAL_STATUS_SUCCESS;
555
556#ifdef WLAN_FEATURE_P2P_INTERNAL
557 int i;
558 tp2pContext *pP2pContext;
559
560 for ( i=0; i < MAX_NO_OF_P2P_SESSIONS; i++ )
561 {
562 pP2pContext = &pMac->p2pContext[i];
563 pP2pContext->hHal = hHal;
564
565 pP2pContext->socialChannel[0] = 1;
566 pP2pContext->socialChannel[1] = 6;
567 pP2pContext->socialChannel[2] = 11;
568
569 vos_spin_lock_init(&pP2pContext->lState);
570
571 p2pResetContext(pP2pContext);
572
573 status = palTimerAlloc(pMac->hHdd, &pP2pContext->actionFrameTimer,
574 p2pActionFrameTimerHandler, pP2pContext);
575 if (!HAL_STATUS_SUCCESS(status))
576 {
577 smsLog(pMac, LOGE, " %s fail to alloc actionFrame timer for session %d\n", __FUNCTION__, i);
578 break;
579 }
580 status = palTimerAlloc(pMac->hHdd, &pP2pContext->listenTimerHandler,
581 p2pListenDiscoverTimerHandler, pP2pContext);
582 if (!HAL_STATUS_SUCCESS(status))
583 {
584 smsLog(pMac, LOGE, " %s fail to alloc listen timer for session %d\n", __FUNCTION__, i);
585 break;
586 }
587 status = palTimerAlloc(pMac->hHdd, &pP2pContext->discoverTimer, p2pDiscoverTimerHandler, pP2pContext);
588 if (!HAL_STATUS_SUCCESS(status))
589 {
590 smsLog(pMac, LOGE, " %s fail to alloc discover timer for session %d\n", __FUNCTION__, i);
591 break;
592 }
593
594 status = palTimerAlloc(pMac->hHdd, &pP2pContext->retryActionFrameTimer,
595 p2pRetryActionFrameTimerHandler, pP2pContext);
596 if (!HAL_STATUS_SUCCESS(status))
597 {
598 smsLog(pMac, LOGE, " %s fail to alloc retryActionFrameTimerHandler timer for session %d\n", __FUNCTION__, i);
599 break;
600 }
601
602 p2pCreateDefaultIEs(hHal, i);
603 }
604#else
605 //If static structure is too big, Need to change this function to allocate memory dynamically
606 vos_mem_zero( &pMac->p2pContext, sizeof( tp2pContext ) );
607#endif
608
609 if(!HAL_STATUS_SUCCESS(status))
610 {
611 sme_p2pClose(hHal);
612 }
613
614 return status;
615}
616
617
618eHalStatus p2pStop( tHalHandle hHal )
619{
620 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
621
622#ifdef WLAN_FEATURE_P2P_INTERNAL
623 int i;
624
625 for ( i = 0; i < MAX_NO_OF_P2P_SESSIONS; i++ )
626 {
627 p2pCloseSession(pMac, i);
628 }
629#else
630 if( pMac->p2pContext.probeRspIe )
631 {
632 vos_mem_free( pMac->p2pContext.probeRspIe );
633 pMac->p2pContext.probeRspIe = NULL;
634 }
635
636 pMac->p2pContext.probeRspIeLength = 0;
637#endif
638
639 return eHAL_STATUS_SUCCESS;
640}
641
642
643eHalStatus sme_p2pClose( tHalHandle hHal )
644{
645 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
646
647#ifdef WLAN_FEATURE_P2P_INTERNAL
648 tp2pContext *pContext;
649 int i;
650
651 p2pStop(hHal);
652
653 for ( i = 0; i < MAX_NO_OF_P2P_SESSIONS; i++ )
654 {
655 p2pCloseSession(pMac, i);
656 pContext = &pMac->p2pContext[i];
657 if (pContext->actionFrameTimer)
658 {
659 palTimerFree(hHal, pContext->actionFrameTimer);
660 pContext->actionFrameTimer = NULL;
661 }
662
663 if (pContext->discoverTimer)
664 {
665 palTimerFree(hHal, pContext->discoverTimer);
666 pContext->discoverTimer = NULL;
667 }
668
669 if (pContext->listenTimerHandler)
670 {
671 palTimerFree(hHal, pContext->listenTimerHandler);
672 pContext->listenTimerHandler = NULL;
673 }
674
675 if (pContext->WPSRegistrarCheckTimerHandler)
676 {
677 palTimerFree(hHal, pContext->WPSRegistrarCheckTimerHandler);
678 pContext->WPSRegistrarCheckTimerHandler = NULL;
679 }
680
681 vos_spin_lock_destroy(&pContext->lState);
682 }
683#else
684 if( pMac->p2pContext.probeRspIe )
685 {
686 vos_mem_free( pMac->p2pContext.probeRspIe );
687 pMac->p2pContext.probeRspIe = NULL;
688 }
689
690 pMac->p2pContext.probeRspIeLength = 0;
691#endif
692
693 return eHAL_STATUS_SUCCESS;
694}
695
696
697tSirRFBand GetRFBand(tANI_U8 channel)
698{
699 if ((channel >= SIR_11A_CHANNEL_BEGIN) &&
700 (channel <= SIR_11A_CHANNEL_END))
701 return SIR_BAND_5_GHZ;
702
703 if ((channel >= SIR_11B_CHANNEL_BEGIN) &&
704 (channel <= SIR_11B_CHANNEL_END))
705 return SIR_BAND_2_4_GHZ;
706
707 return SIR_BAND_UNKNOWN;
708}
709
710/* ---------------------------------------------------------------------------
711
712 \fn p2pRemainOnChannel
713 \brief API to post the remain on channel command.
714 \param hHal - The handle returned by macOpen.
715 \param sessinId - HDD session ID.
716 \param channel - Channel to remain on channel.
717 \param duration - Duration for which we should remain on channel
718 \param callback - callback function.
719 \param pContext - argument to the callback function
720 \return eHalStatus
721
722 -------------------------------------------------------------------------------*/
723eHalStatus p2pRemainOnChannel(tHalHandle hHal, tANI_U8 sessionId,
724 tANI_U8 channel, tANI_U32 duration,
725 remainOnChanCallback callback,
726 void *pContext
727#ifdef WLAN_FEATURE_P2P_INTERNAL
728 , eP2PRemainOnChnReason reason
729#endif
730 )
731{
732 eHalStatus status = eHAL_STATUS_SUCCESS;
733 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
734 tSmeCmd *pRemainChlCmd = NULL;
735 tANI_U32 phyMode;
736
737 pRemainChlCmd = smeGetCommandBuffer(pMac);
738 if(pRemainChlCmd == NULL)
739 return eHAL_STATUS_FAILURE;
740
741 if (SIR_BAND_5_GHZ == GetRFBand(channel))
742 {
743 phyMode = WNI_CFG_PHY_MODE_11A;
744 }
745 else
746 {
747 phyMode = WNI_CFG_PHY_MODE_11G;
748 }
749
750 cfgSetInt(pMac, WNI_CFG_PHY_MODE, phyMode);
751
752 do
753 {
754 /* call set in context */
755 pRemainChlCmd->command = eSmeCommandRemainOnChannel;
756 pRemainChlCmd->sessionId = sessionId;
757 pRemainChlCmd->u.remainChlCmd.chn = channel;
758 pRemainChlCmd->u.remainChlCmd.duration = duration;
759 pRemainChlCmd->u.remainChlCmd.callback = callback;
760 pRemainChlCmd->u.remainChlCmd.callbackCtx = pContext;
761
762 //Put it at the head of the Q if we just finish finding the peer and ready to send a frame
763#ifdef WLAN_FEATURE_P2P_INTERNAL
764 smePushCommand(pMac, pRemainChlCmd, (eP2PRemainOnChnReasonSendFrame == reason));
765#else
766 csrQueueSmeCommand(pMac, pRemainChlCmd, eANI_BOOLEAN_FALSE);
767#endif
768 } while(0);
769
770 smsLog(pMac, LOGW, "exiting function %s\n", __FUNCTION__);
771
772 return(status);
773}
774
775eHalStatus p2pSendAction(tHalHandle hHal, tANI_U8 sessionId,
Jeff Johnsone7245742012-09-05 17:12:55 -0700776 const tANI_U8 *pBuf, tANI_U32 len, tANI_U16 wait, tANI_BOOLEAN noack)
Jeff Johnson295189b2012-06-20 16:38:30 -0700777{
778 eHalStatus status = eHAL_STATUS_SUCCESS;
779 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
780 tSirMbMsgP2p *pMsg;
781 tANI_U16 msgLen;
782
783 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED,
784 " %s sends action frame", __FUNCTION__);
785 msgLen = (tANI_U16)((sizeof( tSirMbMsg )) + len);
786 status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
787 if(HAL_STATUS_SUCCESS(status))
788 {
789 palZeroMemory(pMac->hHdd, (void *)pMsg, msgLen);
790 pMsg->type = pal_cpu_to_be16((tANI_U16)eWNI_SME_SEND_ACTION_FRAME_IND);
791 pMsg->msgLen = pal_cpu_to_be16(msgLen);
792 pMsg->sessionId = sessionId;
Jeff Johnsone7245742012-09-05 17:12:55 -0700793 pMsg->noack = noack;
794 pMsg->wait = (tANI_U16)wait;
795 palCopyMemory( pMac->hHdd, pMsg->data, pBuf, len );
Jeff Johnson295189b2012-06-20 16:38:30 -0700796 status = palSendMBMessage(pMac->hHdd, pMsg);
Jeff Johnsone7245742012-09-05 17:12:55 -0700797 }
Jeff Johnson295189b2012-06-20 16:38:30 -0700798
799 return( status );
800}
801
802eHalStatus p2pCancelRemainOnChannel(tHalHandle hHal, tANI_U8 sessionId)
803{
804 eHalStatus status = eHAL_STATUS_SUCCESS;
805 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
806 tSirMbMsg *pMsg;
807 tANI_U16 msgLen;
808
809 //Need to check session ID to support concurrency
810
811 msgLen = (tANI_U16)(sizeof( tSirMbMsg ));
812 status = palAllocateMemory(pMac->hHdd, (void **)&pMsg, msgLen);
813 if(HAL_STATUS_SUCCESS(status))
814 {
815 palZeroMemory(pMac->hHdd, (void *)pMsg, msgLen);
816 pMsg->type = pal_cpu_to_be16((tANI_U16)eWNI_SME_ABORT_REMAIN_ON_CHAN_IND);
817 pMsg->msgLen = pal_cpu_to_be16(msgLen);
818 status = palSendMBMessage(pMac->hHdd, pMsg);
819 }
820
821 return( status );
822}
823
824eHalStatus p2pSetPs(tHalHandle hHal, tP2pPsConfig *pNoA)
825{
826 tpP2pPsConfig pNoAParam;
827 tSirMsgQ msg;
828 eHalStatus status = eHAL_STATUS_SUCCESS;
829 tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
830
831 status = palAllocateMemory(pMac->hHdd, (void**)&pNoAParam, sizeof(tP2pPsConfig));
832 if(HAL_STATUS_SUCCESS(status))
833 {
834 palZeroMemory(pMac->hHdd, pNoAParam, sizeof(tP2pPsConfig));
835 palCopyMemory(pMac->hHdd, pNoAParam, pNoA, sizeof(tP2pPsConfig));
836 msg.type = eWNI_SME_UPDATE_NOA;
837 msg.bodyval = 0;
838 msg.bodyptr = pNoAParam;
839 limPostMsgApi(pMac, &msg);
840 }
841 return status;
842}
843
844#ifdef WLAN_FEATURE_P2P_INTERNAL
845eHalStatus p2pGetConfigParam(tHalHandle hHal, tP2PConfigParam *pParam)
846{
847 eHalStatus status = eHAL_STATUS_INVALID_PARAMETER;
848 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
849
850 if(pParam)
851 {
852 pParam->P2PListenChannel = pMac->p2pContext[0].P2PListenChannel;
853 pParam->P2POperatingChannel = pMac->p2pContext[0].P2POperatingChannel;
854 pParam->P2POpPSCTWindow = pMac->p2pContext[0].pNoA.ctWindow;
855 pParam->P2PPSSelection = pMac->p2pContext[0].pNoA.psSelection;
856 pParam->P2POpPSCTWindow = pMac->p2pContext[0].pNoA.ctWindow;
857 pParam->P2PNoADuration = pMac->p2pContext[0].pNoA.duration;
858 pParam->P2PNoACount = pMac->p2pContext[0].pNoA.count;
859 pParam->P2PNoAInterval = pMac->p2pContext[0].pNoA.interval;
860
861 status = eHAL_STATUS_SUCCESS;
862 }
863
864 return (status);
865}
866
867eHalStatus p2pChangeDefaultConfigParam(tHalHandle hHal, tP2PConfigParam *pParam)
868{
869 eHalStatus status = eHAL_STATUS_SUCCESS;
870 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
871
872 int i;
873 tANI_U8 pBuf[P2P_COUNTRY_CODE_LEN];
874 tANI_U8 uBufLen = P2P_COUNTRY_CODE_LEN;
875 tP2P_OperatingChannel p2pChannel;
876
877 status = sme_GetCountryCode( pMac, pBuf, &uBufLen );
878 if ( !HAL_STATUS_SUCCESS( status ) )
879 {
880 status = eHAL_STATUS_FAILURE;
881 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s Cannot get the country code\n", __FUNCTION__);
882 }
883
884 vos_mem_copy(p2pChannel.countryString, pBuf, sizeof(pBuf));
885 p2pChannel.regulatoryClass = 0x51;
886
887 if(pParam)
888 {
889 for ( i=0; i < MAX_NO_OF_P2P_SESSIONS; i++ )
890 {
891 if (pParam->P2PListenChannel == 1 || pParam->P2PListenChannel == 6
892 || pParam->P2PListenChannel == 11)
893 {
894 pMac->p2pContext[i].P2PListenChannel = pParam->P2PListenChannel;
895 }
896 else
897 {
898 pMac->p2pContext[i].P2PListenChannel = P2P_OPERATING_CHANNEL;
899 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
900 "Invalid P2P Listen Channel in config. Switch to default Listen Channel %d\n",
901 __FUNCTION__, P2P_OPERATING_CHANNEL);
902 }
903
904 if(csrRoamIsChannelValid(pMac, pParam->P2POperatingChannel))
905 {
906 pMac->p2pContext[i].P2POperatingChannel = pParam->P2POperatingChannel;
907 }
908 else
909 {
910 pMac->p2pContext[i].P2POperatingChannel = P2P_OPERATING_CHANNEL;
911 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_HIGH,
912 "Invalid P2P Operating Channel in config. Switch to default Channel %d\n",
913 __FUNCTION__, P2P_OPERATING_CHANNEL);
914 }
915 pMac->p2pContext[i].pNoA.ctWindow = pParam->P2POpPSCTWindow;
916 pMac->p2pContext[i].pNoA.psSelection = pParam->P2PPSSelection;
917 pMac->p2pContext[i].pNoA.ctWindow = pParam->P2POpPSCTWindow;
918 pMac->p2pContext[i].pNoA.duration = pParam->P2PNoADuration;
919 pMac->p2pContext[i].pNoA.count = pParam->P2PNoACount;
920 pMac->p2pContext[i].pNoA.interval = pParam->P2PNoAInterval;
921
922 p2pChannel.channel = pMac->p2pContext[i].P2POperatingChannel;
923 P2P_UpdateIE(pMac, i, eWFD_OPERATING_CHANNEL, &p2pChannel, 1);
924 p2pChannel.channel = pMac->p2pContext[i].P2PListenChannel;
925 P2P_UpdateIE(pMac, i, eWFD_LISTEN_CHANNEL, &p2pChannel, 1);
926 }
927 }
928
929 return status;
930}
931
932eHalStatus p2pPS(tHalHandle hHal, tANI_U8 sessionId)
933{
934 eHalStatus status = eHAL_STATUS_SUCCESS;
935 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
936 tP2pPsConfig pNoA;
937
938 /* call set in context */
939 pNoA.psSelection = pMac->p2pContext[sessionId].pNoA.psSelection;
940 pNoA.sessionid = sessionId;
941
942 if (pMac->p2pContext[sessionId].pNoA.psSelection == P2P_CLEAR_POWERSAVE)
943 {
944 return status;
945 }
946
947 if (pMac->p2pContext[sessionId].pNoA.psSelection == P2P_OPPORTUNISTIC_PS)
948 {
949 pNoA.opp_ps = TRUE;
950 pNoA.ctWindow = pMac->p2pContext[sessionId].pNoA.ctWindow;
951 pNoA.count = 0;
952 pNoA.duration = 0;
953 pNoA.interval = 0;
954 pNoA.single_noa_duration = 0;
955 }
956 else if (pMac->p2pContext[sessionId].pNoA.psSelection == P2P_PERIODIC_NOA)
957 {
958 pNoA.opp_ps = 0;
959 pNoA.ctWindow = 0;
960 pNoA.count = pMac->p2pContext[sessionId].pNoA.count;
961 pNoA.duration = pMac->p2pContext[sessionId].pNoA.duration;
962 pNoA.interval = pMac->p2pContext[sessionId].pNoA.interval;
963 pNoA.single_noa_duration = 0;
964 }
965 else if(pMac->p2pContext[sessionId].pNoA.psSelection == P2P_SINGLE_NOA)
966 {
967 pNoA.opp_ps = 0;
968 pNoA.ctWindow = 0;
969 pNoA.count = 0;
970 pNoA.duration = 0;
971 pNoA.interval = 0;
972 pNoA.single_noa_duration = pMac->p2pContext[sessionId].pNoA.duration;
973 }
974
975 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED,
976 " %s HDDSession %d set NoA parameters. Selection %d, opp_ps %d, ctWindow %d, count %d, "
977 "duration %d, interval %d single NoA duration %d",
978 __FUNCTION__, sessionId, pMac->p2pContext[sessionId].pNoA.psSelection,
979 pNoA.opp_ps, pNoA.ctWindow, pNoA.count, pNoA.duration,
980 pNoA.interval, pNoA.single_noa_duration );
981
982 status = sme_p2pSetPs(pMac, &pNoA);
983 if(!HAL_STATUS_SUCCESS(status))
984 {
985 smsLog(pMac, LOGE, FL(" sme_p2pSetPs fail with status %d"), status);
986 return status;
987 }
988
989 return status;
990}
991
992void P2P_UpdateMacHdr(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 *pBuf)
993{
994 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
995 tSirMacMgmtHdr *macHdr = (tSirMacMgmtHdr *)pBuf;
996
997 macHdr->fc.protVer = 0;
998 macHdr->fc.type = 0;
999 macHdr->fc.subType = 13;
1000 macHdr->durationLo = 0;
1001 macHdr->durationHi = 0;
1002 vos_mem_copy(macHdr->da, pMac->p2pContext[SessionID].peerMacAddress, P2P_MAC_ADDRESS_LEN);
1003 vos_mem_copy(macHdr->sa, pMac->p2pContext[SessionID].selfMacAddress, P2P_MAC_ADDRESS_LEN);
1004 vos_mem_copy(macHdr->bssId, pMac->p2pContext[SessionID].peerMacAddress, P2P_MAC_ADDRESS_LEN);
1005
1006 return;
1007}
1008
1009static eHalStatus p2pRemainOnChannelReadyCallback(tHalHandle halHandle,
1010 void *pContext,
1011 eHalStatus scan_status)
1012{
1013 eHalStatus status = eHAL_STATUS_SUCCESS;
1014 tp2pContext *p2pContext = (tp2pContext*) pContext;
1015
1016 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s GroupFormationPending %d PeerFound %d\n",
1017 __FUNCTION__, p2pContext->GroupFormationPending, p2pContext->PeerFound);
1018
1019 if (p2pContext->PeerFound)
1020 {
1021 p2pContext->PeerFound = FALSE;
1022
1023 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Sending actionframe\n", __FUNCTION__);
1024 if (p2pContext->pSentActionFrame)
1025 {
1026 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s calling p2pSendAction\n", __FUNCTION__);
1027 p2pSendAction(halHandle, p2pContext->SMEsessionId, (tANI_U8 *)p2pContext->pSentActionFrame, p2pContext->ActionFrameLen);
1028 }
1029 }
1030
1031 return status;
1032}
1033
1034eHalStatus p2pGrpFormationRemainOnChanRspCallback(tHalHandle halHandle, void *pContext, tANI_U32 scanId, eCsrScanStatus scan_status)
1035{
1036 return eHAL_STATUS_SUCCESS;
1037}
1038
1039tANI_U8 p2pGetDialogToken(tHalHandle hHal, tANI_U8 SessionID, eP2PFrameType actionFrameType)
1040{
1041 tANI_U8 dialogToken = 0;
1042
1043 dialogToken = (tANI_U8) vos_timer_get_system_ticks();
1044
1045 return(dialogToken);
1046}
1047
1048void p2pRetryActionFrameTimerHandler(void *pContext)
1049{
1050 tp2pContext *p2pContext = (tp2pContext*) pContext;
1051 eHalStatus status = eHAL_STATUS_SUCCESS;
1052 tpAniSirGlobal pMac = PMAC_STRUCT( p2pContext->hHal );
1053
1054 p2pContext->PeerFound = TRUE;
1055 smsLog( pMac, LOGE, "%s Calling remain on channel \n", __FUNCTION__);
1056 status = p2pRemainOnChannel( pMac, p2pContext->SMEsessionId, p2pContext->P2PListenChannel/*pScanResult->BssDescriptor.channelId*/, P2P_REMAIN_ON_CHAN_TIMEOUT_LOW,
1057 NULL, NULL, eP2PRemainOnChnReasonSendFrame);
1058 if(status != eHAL_STATUS_SUCCESS)
1059 {
1060 smsLog( pMac, LOGE, "%s remain on channel failed\n", __FUNCTION__);
1061 }
1062
1063 return;
1064}
1065
1066void p2pActionFrameTimerHandler(void *pContext)
1067{
1068 tp2pContext *p2pContext = (tp2pContext*) pContext;
1069 eHalStatus status = eHAL_STATUS_SUCCESS;
1070 tANI_U8 *pBuf = NULL, *pNextBuf = NULL;
1071 tCsrRoamInfo roamInfo;
1072
1073
1074 if(p2pContext->pSentActionFrame)
1075 {
1076 vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
1077 csrRoamCallCallback((tpAniSirGlobal)p2pContext->hHal, p2pContext->SMEsessionId, &roamInfo, 0,
1078 eCSR_ROAM_SEND_ACTION_CNF,
1079 eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
1080 }
1081
1082 if(VOS_IS_STATUS_SUCCESS(vos_spin_lock_acquire(&p2pContext->lState)))
1083 {
1084 if(p2pContext->pSentActionFrame)
1085 {
1086 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN,
1087 " %s actionframe timeout type %d", __FUNCTION__, p2pContext->actionFrameType);
1088 pBuf = p2pContext->pSentActionFrame;
1089 p2pContext->pSentActionFrame = NULL;
1090 }
1091 if(p2pContext->pNextActionFrm)
1092 {
1093 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_WARN,
1094 " %s next actionframe timeout type %d", __FUNCTION__, p2pContext->NextActionFrameType);
1095 pNextBuf = p2pContext->pNextActionFrm;
1096 p2pContext->pNextActionFrm = NULL;
1097 }
1098 vos_spin_lock_release(&p2pContext->lState);
1099
1100 if(pBuf)
1101 {
1102 vos_mem_free(pBuf);
1103 }
1104 if(pNextBuf)
1105 {
1106 //Inform the failure of the next frame.
1107 p2pContext->pSentActionFrame = pNextBuf;
1108 p2pContext->ActionFrameLen = p2pContext->nNextFrmLen;
1109 p2pContext->actionFrameType = p2pContext->NextActionFrameType;
1110 vos_mem_zero(&roamInfo, sizeof(tCsrRoamInfo));
1111 csrRoamCallCallback((tpAniSirGlobal)p2pContext->hHal, p2pContext->SMEsessionId, &roamInfo, 0,
1112 eCSR_ROAM_SEND_ACTION_CNF,
1113 eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
1114 p2pContext->pSentActionFrame = NULL;
1115 vos_mem_free(pNextBuf);
1116 }
1117 }
1118 status = p2pFsm(p2pContext, eP2P_TRIGGER_DISCONNECTED);
1119 p2pContext->actionFrameTimeout = TRUE;
1120 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s timedout\n", __FUNCTION__);
1121
1122 return;
1123}
1124
1125
1126eHalStatus p2pCreateActionFrame(tpAniSirGlobal pMac, tANI_U8 SessionID, void *p2pactionframe,
1127 eP2PFrameType actionFrameType, tANI_U8 **ppFrm)
1128{
1129 eHalStatus status = eHAL_STATUS_SUCCESS;
1130 tANI_U32 len = 0;
1131 tANI_U32 nActionFrmlen = 0, pendingFrameLen;
1132 tANI_U8 *pActionFrm = NULL;
1133 tANI_U8 *pBuf = NULL, *pLocal = NULL;
1134 eP2PFrameType pendingActionFrameType;
1135 tp2pContext *pP2pContext = &pMac->p2pContext[SessionID];
1136
1137 if(NULL == ppFrm)
1138 {
1139 smsLog(pMac, LOGE, FL(" invalid parameters"));
1140 return eHAL_STATUS_FAILURE;
1141 }
1142
1143 csrScanAbortMacScan(pMac);
1144
1145 switch (actionFrameType)
1146 {
1147 case eP2P_GONEGO_REQ:
1148 status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_GO_NEGOTIATION_REQUEST, p2pactionframe, len);
1149 break;
1150
1151 case eP2P_GONEGO_RES:
1152 status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_GO_NEGOTIATION_RESPONSE, p2pactionframe, len);
1153 break;
1154
1155 case eP2P_GONEGO_CNF:
1156 status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_GO_NEGOTIATION_CONFIRMATION, p2pactionframe, len);
1157 break;
1158
1159 case eP2P_PROVISION_DISCOVERY_REQUEST:
1160 status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_PROVISION_DISCOVERY_REQUEST, p2pactionframe, len);
1161 break;
1162
1163 case eP2P_PROVISION_DISCOVERY_RESPONSE:
1164 status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_PROVISION_DISCOVERY_RESPONSE, p2pactionframe, len);
1165 break;
1166
1167 case eP2P_INVITATION_REQ:
1168 status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_INVITATION_REQUEST, p2pactionframe, len);
1169 break;
1170
1171 case eP2P_INVITATION_RSP:
1172 status = P2P_UpdateIE(pMac, SessionID, eWFD_SEND_INVITATION_RESPONSE, p2pactionframe, len);
1173 break;
1174 default:
1175 return status;
1176 }
1177
1178 status = P2P_GetActionFrame(pMac, SessionID, actionFrameType, &pActionFrm, &nActionFrmlen);
1179 if(!HAL_STATUS_SUCCESS(status))
1180 {
1181 smsLog(pMac, LOGE, FL(" P2P_GetActionFrame fail with status %d"), status);
1182 return status;
1183 }
1184
1185 P2P_UpdateMacHdr(pMac, SessionID, pActionFrm);
1186
1187 pBuf = (tANI_U8 *)vos_mem_malloc( nActionFrmlen);
1188 if(NULL == pBuf)
1189 {
1190 smsLog(pMac, LOGE, FL(" fail to allocate memory"));
1191 if (pActionFrm)
1192 vos_mem_free(pActionFrm);
1193 return eHAL_STATUS_FAILURE;
1194 }
1195
1196 vos_mem_copy(pBuf, pActionFrm, nActionFrmlen);
1197 vos_mem_free(pActionFrm);
1198
1199 if( !VOS_IS_STATUS_SUCCESS(vos_spin_lock_acquire(&pP2pContext->lState)))
1200 {
1201 smsLog(pMac, LOGE, FL(" fail to acquire spinlock"));
1202 vos_mem_free(pBuf);
1203 return eHAL_STATUS_FAILURE;
1204 }
1205
1206 if(NULL != pP2pContext->pSentActionFrame)
1207 {
1208 //If there is one pending frame already. Drop that one and save the new one
1209 pLocal = pP2pContext->pNextActionFrm;
1210 pendingActionFrameType = pP2pContext->NextActionFrameType;
1211 pendingFrameLen = pP2pContext->nNextFrmLen;
1212 pP2pContext->pNextActionFrm = pBuf;
1213 pP2pContext->nNextFrmLen = nActionFrmlen;
1214 pP2pContext->NextActionFrameType = actionFrameType;
1215 *ppFrm = NULL;
1216 }
1217 else
1218 {
1219 pP2pContext->pSentActionFrame = pBuf;
1220 pP2pContext->ActionFrameLen = nActionFrmlen;
1221 pP2pContext->actionFrameType = actionFrameType;
1222 *ppFrm = pBuf;
1223 }
1224 vos_spin_lock_release(&pP2pContext->lState);
1225
1226 if(NULL != pLocal)
1227 {
1228 smsLog(pMac, LOGE, FL(" Drop a waiting action frame 0x%x, type %d lenth %d"),
1229 pLocal, pendingActionFrameType, pendingFrameLen);
1230 vos_mem_free(pLocal);
1231 }
1232
1233 return status;
1234}
1235
1236
1237extern eHalStatus p2pGetSSID(tANI_U8 *ssId, tANI_U32 *ssIdLen, tANI_U8 SessionID);
1238
1239static eHalStatus p2pSendActionFrame(tpAniSirGlobal pMac, tANI_U8 HDDSessionID, eP2PFrameType actionFrameType)
1240{
1241 tCsrScanResultFilter filter;
1242 eHalStatus status = eHAL_STATUS_SUCCESS;
1243 tScanResultHandle hScanResult = NULL;
1244 tCsrScanResultInfo *pScanResult = NULL;
1245 tANI_U8 ssId[SIR_MAC_MAX_SSID_LENGTH];
1246 tANI_U32 ssIdLen = 0;
1247 tp2pContext *pP2pContext = &pMac->p2pContext[HDDSessionID];
1248
1249 pP2pContext->GroupFormationPending = TRUE;
1250 if (actionFrameType == eP2P_GONEGO_REQ || actionFrameType == eP2P_PROVISION_DISCOVERY_REQUEST
1251 || actionFrameType == eP2P_INVITATION_REQ)
1252 {
1253 vos_mem_zero(&filter, sizeof(filter));
1254 filter.BSSIDs.numOfBSSIDs = 1;
1255 filter.BSSIDs.bssid = &pP2pContext->peerMacAddress;
1256 filter.bWPSAssociation = TRUE;
1257 filter.BSSType = eCSR_BSS_TYPE_ANY;
1258
1259 status = csrScanGetResult(pMac, &filter, &hScanResult);
1260
1261 if (hScanResult)
1262 {
1263 pScanResult = csrScanResultGetFirst(pMac, hScanResult );
1264 if(pScanResult)
1265 {
1266
1267 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s found match on channel %d",
1268 __FUNCTION__, pScanResult->BssDescriptor.channelId);
1269 pP2pContext->formationReq.targetListenChannel = pScanResult->BssDescriptor.channelId;
1270 if(pP2pContext->P2PListenChannel != pScanResult->BssDescriptor.channelId)
1271 {
1272 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED,
1273 "%s adapt listen channel to %d",
1274 __FUNCTION__, pScanResult->BssDescriptor.channelId);
1275 p2pSetListenChannel(pMac, pP2pContext->sessionId, pScanResult->BssDescriptor.channelId);
1276 }
1277 vos_mem_copy(pP2pContext->formationReq.deviceAddress, pScanResult->BssDescriptor.bssId, P2P_MAC_ADDRESS_LEN);
1278 }
1279 csrScanResultPurge(pMac, hScanResult);
1280 }
1281 else
1282 {
1283 vos_mem_zero(&filter, sizeof(filter));
1284 filter.bWPSAssociation = TRUE;
1285 filter.BSSType = eCSR_BSS_TYPE_ANY;
1286 filter.SSIDs.SSIDList =( tCsrSSIDInfo *)vos_mem_malloc(sizeof(tCsrSSIDInfo));
1287 if( filter.SSIDs.SSIDList == NULL )
1288 {
1289 smsLog( pMac, LOGP, FL("vos_mem_malloc failed:") );
1290 pP2pContext->GroupFormationPending = FALSE;
1291 return eHAL_STATUS_FAILURE;
1292 }
1293 vos_mem_zero( filter.SSIDs.SSIDList, sizeof(tCsrSSIDInfo) );
1294 p2pGetSSID(ssId, &ssIdLen, HDDSessionID);
1295
1296 if (ssIdLen)
1297 {
1298 filter.SSIDs.SSIDList->SSID.length = ssIdLen;
1299 vos_mem_copy(&filter.SSIDs.SSIDList[0].SSID.ssId, &ssId, ssIdLen);
1300 filter.SSIDs.numOfSSIDs = 1;
1301 status = csrScanGetResult(pMac, &filter, &hScanResult);
1302 if (hScanResult)
1303 {
1304 pScanResult = csrScanResultGetFirst(pMac, hScanResult );
1305 pP2pContext->formationReq.targetListenChannel = pScanResult->BssDescriptor.channelId;
1306 vos_mem_copy(pP2pContext->formationReq.deviceAddress, pScanResult->BssDescriptor.bssId, P2P_MAC_ADDRESS_LEN);
1307 csrScanResultPurge(pMac, hScanResult);
1308 }
1309 else
1310 {
1311 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s not found match\n", __FUNCTION__);
1312 pP2pContext->formationReq.targetListenChannel = 0;
1313 vos_mem_copy(pP2pContext->formationReq.deviceAddress, pP2pContext->peerMacAddress, P2P_MAC_ADDRESS_LEN);
1314 status = eHAL_STATUS_SUCCESS;
1315 }
1316 vos_mem_free(filter.SSIDs.SSIDList);
1317 }
1318 else
1319 {
1320 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s not found match\n", __FUNCTION__);
1321 pP2pContext->formationReq.targetListenChannel = 0;
1322 vos_mem_copy(pP2pContext->formationReq.deviceAddress, pP2pContext->peerMacAddress, P2P_MAC_ADDRESS_LEN);
1323 status = eHAL_STATUS_SUCCESS;
1324 }
1325 }
1326 sme_CancelRemainOnChannel(pMac, pP2pContext->SMEsessionId );
1327 p2pFsm(pP2pContext, eP2P_TRIGGER_GROUP_FORMATION);
1328 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, " %s send action frame %d timeout %d\n",
1329 __FUNCTION__, actionFrameType, pP2pContext->ActionFrameSendTimeout);
1330 }
1331 else
1332 {
1333 pP2pContext->PeerFound = TRUE;
1334
1335 status = p2pSendAction(pMac, pP2pContext->SMEsessionId, (tANI_U8 *)pP2pContext->pSentActionFrame,
1336 pP2pContext->ActionFrameLen);
1337 if(status != eHAL_STATUS_SUCCESS)
1338 {
1339 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1340 "%s p2pSendAction failed to send frame type %d\n", __FUNCTION__, actionFrameType);
1341 pP2pContext->GroupFormationPending = FALSE;
1342 return status;
1343 }
1344
1345 if ( actionFrameType == eP2P_GONEGO_RES )
1346 {
1347 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling p2pRemainOnChannel with duration"
1348 "%d on channel %d\n", __FUNCTION__, P2P_REMAIN_ON_CHAN_TIMEOUT, pP2pContext->P2PListenChannel);
1349
1350 if(p2pRemainOnChannel( pMac, pP2pContext->SMEsessionId,
1351 pP2pContext->P2PListenChannel, P2P_REMAIN_ON_CHAN_TIMEOUT_LOW,
1352 NULL, NULL, eP2PRemainOnChnReasonSendFrame))
1353 {
1354 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s remain on channel failed\n", __FUNCTION__);
1355 }
1356 }
1357 }
1358
1359 return(status);
1360}
1361
1362
1363#define WLAN_P2P_DEF_ACTION_FRM_TIMEOUT_VALUE 1000 //1s
1364
1365eHalStatus p2pCreateSendActionFrame(tHalHandle hHal, tANI_U8 HDDSessionID,
1366 void *p2pactionframe, eP2PFrameType actionFrameType, tANI_U32 timeout)
1367{
1368 eHalStatus status = eHAL_STATUS_SUCCESS;
1369 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
1370 tANI_U8 *pBuf = NULL;
1371 tp2pContext *pP2pContext = &pMac->p2pContext[HDDSessionID];
1372
1373 status = p2pCreateActionFrame(pMac, HDDSessionID, p2pactionframe, actionFrameType, &pBuf);
1374 if(!HAL_STATUS_SUCCESS(status))
1375 {
1376 smsLog(pMac, LOGE, FL(" fail to create action frame"));
1377 return status;
1378 }
1379
1380 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, " %s send action frame %d timeout %d\n",
1381 __FUNCTION__, actionFrameType, timeout);
1382
1383 if(NULL != pBuf)
1384 {
1385 if (timeout)
1386 {
1387 pP2pContext->ActionFrameSendTimeout = timeout;
1388 }
1389 else
1390 {
1391 pP2pContext->ActionFrameSendTimeout = WLAN_P2P_DEF_ACTION_FRM_TIMEOUT_VALUE;
1392 }
1393
1394 status = palTimerStart(pMac->hHdd, pP2pContext->actionFrameTimer,
1395 pP2pContext->ActionFrameSendTimeout * PAL_TIMER_TO_MS_UNIT, eANI_BOOLEAN_FALSE);
1396 if (!HAL_STATUS_SUCCESS(status))
1397 {
1398 tCsrRoamInfo RoamInfo;
1399
1400 vos_mem_zero(&RoamInfo, sizeof(tCsrRoamInfo));
1401 smsLog(pMac, LOGE, FL(" %s fail to start timer status %d"), __FUNCTION__, status);
1402 //Without the timer we cannot continue
1403 csrRoamCallCallback((tpAniSirGlobal)pP2pContext->hHal,
1404 pP2pContext->SMEsessionId, &RoamInfo, 0,
1405 eCSR_ROAM_SEND_ACTION_CNF,
1406 eCSR_ROAM_RESULT_SEND_ACTION_FAIL);
1407 vos_spin_lock_acquire(&pP2pContext->lState);
1408 pBuf = pP2pContext->pSentActionFrame;
1409 pP2pContext->pSentActionFrame = NULL;
1410 vos_spin_lock_release(&pP2pContext->lState);
1411 vos_mem_free(pBuf);
1412 pBuf = NULL;
1413 p2pFsm(pP2pContext, eP2P_TRIGGER_DISCONNECTED);
1414 return status;
1415 }
1416 //We can send this frame now
1417 status = p2pSendActionFrame(pMac, HDDSessionID, actionFrameType);
1418 if(!HAL_STATUS_SUCCESS(status))
1419 {
1420 smsLog(pMac, LOGE, FL(" fail to send action frame status %d"), status);
1421 }
1422 //Let them retry
1423 pP2pContext->actionFrameTimeout = FALSE;
1424 }
1425 else
1426 {
1427 //An action frame is pedning at lower layer
1428 smsLog(pMac, LOGW, FL(" An action frame is pending while trying to send frametype %d"), actionFrameType);
1429 if (timeout)
1430 {
1431 pP2pContext->nNextFrameTimeOut = timeout;
1432 }
1433 else
1434 {
1435 pP2pContext->nNextFrameTimeOut = WLAN_P2P_DEF_ACTION_FRM_TIMEOUT_VALUE;
1436 }
1437 }
1438
1439 return status;
1440}
1441
1442
1443void p2pListenDiscoverTimerHandlerCB(void *pContext)
1444{
1445}
1446
1447void p2pListenDiscoverTimerHandler(void *pContext)
1448{
1449 tp2pContext *p2pContext = (tp2pContext*) pContext;
1450 eHalStatus status = eHAL_STATUS_SUCCESS;
1451
1452 if( (eP2P_STATE_DISCONNECTED == p2pContext->state) &&
1453 (eStateDisabled != p2pContext->listenDiscoverableState) )
1454 {
1455 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling RemainOnChannel with duration %d on channel %d\n",
1456 __FUNCTION__, p2pContext->listenDuration, p2pContext->P2PListenChannel);
1457 status = p2pRemainOnChannel( p2pContext->hHal, p2pContext->SMEsessionId, p2pContext->P2PListenChannel, p2pContext->listenDuration,
1458 p2pListenStateDiscoverableCallback, p2pContext, eP2PRemainOnChnReasonListen);
1459 }
1460 else
1461 {
1462 smsLog(((tpAniSirGlobal)p2pContext->hHal), LOGW, FL(" cannot call p2pRemainOnChannel state %d\n"), p2pContext->state);
1463 }
1464
1465 return;
1466}
1467
1468
1469static eHalStatus p2pListenStateDiscoverableCallback(tHalHandle halHandle, void *pContext, eHalStatus retStatus)
1470{
1471 eHalStatus status = eHAL_STATUS_SUCCESS;
1472 tpAniSirGlobal pMac = PMAC_STRUCT(halHandle);
1473 tp2pContext *p2pContext = (tp2pContext*) pContext;
1474
1475 if( (eP2P_STATE_DISCONNECTED == p2pContext->state) &&
1476 (eStateDisabled != p2pContext->listenDiscoverableState) &&
1477 (NULL == p2pContext->p2pDiscoverCBFunc) )
1478 {
1479 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s restart listen timer expire time %d\n",
1480 __FUNCTION__, p2pContext->expire_time);
1481 //We can restart the listening
1482 status = palTimerStart(pMac->hHdd, p2pContext->listenTimerHandler, p2pContext->expire_time, eANI_BOOLEAN_FALSE);
1483 if (eHAL_STATUS_SUCCESS != status)
1484 {
1485 VOS_ASSERT(status);
1486 }
1487 }
1488 else
1489 {
1490 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s not restart listen timer state (%d)\n",
1491 __FUNCTION__, p2pContext->state);
1492 }
1493
1494 return status;
1495}
1496
1497
1498eHalStatus P2P_ListenStateDiscoverable(tHalHandle hHal, tANI_U8 sessionId,
1499 ep2pListenStateDiscoverability listenState)
1500{
1501 eHalStatus status = eHAL_STATUS_SUCCESS;
1502 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
1503
1504 switch (listenState)
1505 {
1506 case P2P_DEVICE_NOT_DISCOVERABLE:
1507 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s P2P_NOT_DISCOVERABLE\n", __FUNCTION__);
1508 pMac->p2pContext[sessionId].listenDiscoverableState = eStateDisabled;
1509 pMac->p2pContext[sessionId].DiscoverableCfg = listenState;
1510 if (pMac->p2pContext[sessionId].state == eP2P_STATE_DISCONNECTED)
1511 {
1512 sme_CancelRemainOnChannel(hHal, sessionId );
1513
1514 if (pMac->p2pContext[sessionId].listenTimerHandler)
1515 {
1516 status = palTimerStop(pMac->hHdd, pMac->p2pContext[sessionId].listenTimerHandler);
1517 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Timer Stop status %d\n",
1518 __FUNCTION__, status);
1519 }
1520 }
1521 else
1522 {
1523 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s P2P_NOT_DISCOVERABLE not in right state (%d)",
1524 __FUNCTION__, pMac->p2pContext[sessionId].state);
1525 }
1526 break;
1527
1528 case P2P_DEVICE_AUTO_AVAILABILITY:
1529 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s P2P_AUTO_AVAILABILITY\n",__FUNCTION__);
1530 pMac->p2pContext[sessionId].listenDiscoverableState = eStateEnabled;
1531 pMac->p2pContext[sessionId].DiscoverableCfg = listenState;
1532 pMac->p2pContext[sessionId].expire_time = P2P_LISTEN_TIMEOUT_AUTO * PAL_TIMER_TO_MS_UNIT;
1533 pMac->p2pContext[sessionId].listenDuration = P2P_LISTEN_TIMEOUT;
1534 if (pMac->p2pContext[sessionId].state == eP2P_STATE_DISCONNECTED)
1535 {
1536 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling RemainOnChannel with diration %d on channel %d\n",
1537 __FUNCTION__, pMac->p2pContext[sessionId].listenDuration, pMac->p2pContext[sessionId].P2PListenChannel);
1538 p2pRemainOnChannel( pMac, pMac->p2pContext[sessionId].SMEsessionId, pMac->p2pContext[sessionId].P2PListenChannel,
1539 pMac->p2pContext[sessionId].listenDuration, p2pListenStateDiscoverableCallback,
1540 &pMac->p2pContext[sessionId], eP2PRemainOnChnReasonListen);
1541 }
1542 else
1543 {
1544 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s P2P_AUTO_DISCOVERABLE not in right state (%d)",
1545 __FUNCTION__, pMac->p2pContext[sessionId].state);
1546 }
1547 break;
1548
1549 case P2P_DEVICE_HIGH_AVAILABILITY:
1550 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s P2P_HIGH_AVAILABILITY\n",__FUNCTION__);
1551 pMac->p2pContext[sessionId].listenDiscoverableState = eStateEnabled;
1552 pMac->p2pContext[sessionId].DiscoverableCfg = listenState;
1553 pMac->p2pContext[sessionId].expire_time = P2P_REMAIN_ON_CHAN_TIMEOUT_LOW * PAL_TIMER_TO_MS_UNIT;
1554 pMac->p2pContext[sessionId].listenDuration = P2P_LISTEN_TIMEOUT_HIGH;
1555 if (pMac->p2pContext[sessionId].state == eP2P_STATE_DISCONNECTED)
1556 {
1557 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling RemainOnChannel with diration %d on channel %d\n",
1558 __FUNCTION__, pMac->p2pContext[sessionId].listenDuration, pMac->p2pContext[sessionId].P2PListenChannel);
1559 p2pRemainOnChannel( pMac, pMac->p2pContext[sessionId].SMEsessionId, pMac->p2pContext[sessionId].P2PListenChannel,
1560 pMac->p2pContext[sessionId].listenDuration, p2pListenStateDiscoverableCallback,
1561 &pMac->p2pContext[sessionId], eP2PRemainOnChnReasonListen);
1562 }
1563 else
1564 {
1565 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s P2P_HIGH_DISCOVERABLE not in right state (%d)",
1566 __FUNCTION__, pMac->p2pContext[sessionId].state);
1567 }
1568 break;
1569
1570 case 234: //Not to use this as it enabling GO to be concurrent with P2P device P2P_DEVICE_HIGH_AVAILABILITY:
1571 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s P2P_HIGH_AVAILABILITY\n",__FUNCTION__);
1572 pMac->p2pContext[sessionId].listenDiscoverableState = eStateEnabled;
1573 pMac->p2pContext[sessionId].DiscoverableCfg = listenState;
1574
1575 if ((pMac->p2pContext[sessionId].P2POperatingChannel != pMac->p2pContext[sessionId].P2PListenChannel)
1576 && p2pIsGOportEnabled(pMac))
1577 {
1578 pMac->p2pContext[sessionId].expire_time = P2P_LISTEN_TIMEOUT_HIGH * PAL_TIMER_TO_MS_UNIT * 5;
1579 pMac->p2pContext[sessionId].listenDuration = P2P_REMAIN_ON_CHAN_TIMEOUT_LOW;
1580 }
1581 else
1582 {
1583 pMac->p2pContext[sessionId].expire_time = P2P_LISTEN_TIMEOUT_HIGH * PAL_TIMER_TO_MS_UNIT;
1584 pMac->p2pContext[sessionId].listenDuration = P2P_LISTEN_TIMEOUT;
1585 }
1586
1587 if (pMac->p2pContext[sessionId].state == eP2P_STATE_DISCONNECTED)
1588 {
1589 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Calling RemainOnChannel with diration %d on channel %d\n",
1590 __FUNCTION__, pMac->p2pContext[sessionId].listenDuration, pMac->p2pContext[sessionId].P2PListenChannel);
1591 p2pRemainOnChannel( pMac, pMac->p2pContext[sessionId].SMEsessionId, pMac->p2pContext[sessionId].P2PListenChannel,
1592 pMac->p2pContext[sessionId].listenDuration, p2pListenStateDiscoverableCallback,
1593 &pMac->p2pContext[sessionId], eP2PRemainOnChnReasonListen);
1594 }
1595
1596 break;
1597
1598 default:
1599 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1600 "%s Unknown listen setting",__FUNCTION__, listenState);
1601 break;
1602 }
1603
1604 return( status );
1605}
1606
1607
1608void p2pCallDiscoverCallback(tp2pContext *p2pContext, eP2PDiscoverStatus statusCode)
1609{
1610 if (p2pContext->p2pDiscoverCBFunc)
1611 {
1612 p2pDiscoverCompleteCallback pcallback = p2pContext->p2pDiscoverCBFunc;
1613 p2pContext->p2pDiscoverCBFunc = NULL;
1614 pcallback(p2pContext->hHal, p2pContext->pContext, statusCode);
1615 }
1616 p2pContext->directedDiscovery = FALSE;
1617}
1618
1619
1620void p2pDiscoverTimerHandler(void *pContext)
1621{
1622 tp2pContext *p2pContext = (tp2pContext*) pContext;
1623 eHalStatus status = eHAL_STATUS_SUCCESS;
1624
1625 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s enter", __FUNCTION__);
1626 p2pCallDiscoverCallback(p2pContext,
1627 (p2pContext->directedDiscovery) ? eP2P_DIRECTED_DISCOVER : eP2P_DISCOVER_SUCCESS);
1628
1629 status = p2pFsm(p2pContext, eP2P_TRIGGER_DISCONNECTED);
1630
1631 return;
1632}
1633
1634
1635
1636eHalStatus p2pGetResultFilter(tp2pContext *pP2pContext,
1637 tCsrScanResultFilter *pFilter)
1638{
1639 eHalStatus status = eHAL_STATUS_SUCCESS;
1640 v_U32_t uNumDeviceFilters;
1641 tp2pDiscoverDeviceFilter *directedDiscoveryFilter;
1642 int i;
1643 tCsrBssid *bssid = NULL;
1644
1645 do
1646 {
1647 if( (NULL != pP2pContext) && (NULL != pFilter) )
1648 {
1649 vos_mem_zero(pFilter, sizeof(tCsrScanResultFilter));
1650 uNumDeviceFilters = pP2pContext->uNumDeviceFilters;
1651 directedDiscoveryFilter = pP2pContext->directedDiscoveryFilter;
1652 for(i = 0; i < uNumDeviceFilters; i++)
1653 {
1654 if (directedDiscoveryFilter->ucBitmask & DISCOVERY_FILTER_BITMASK_DEVICE)
1655 {
1656 pFilter->BSSIDs.numOfBSSIDs++;
1657 }
1658
1659 if ((directedDiscoveryFilter->ucBitmask != QCWLAN_P2P_DISCOVER_ANY)
1660 && (directedDiscoveryFilter->ucBitmask & DISCOVERY_FILTER_BITMASK_GO))
1661 {
1662 //Matching Device ID and GroupSSID
1663 pFilter->BSSIDs.numOfBSSIDs++;
1664 if(directedDiscoveryFilter->GroupSSID.length)
1665 {
1666 pFilter->SSIDs.numOfSSIDs++;
1667 }
1668 }
1669 directedDiscoveryFilter += sizeof(tp2pDiscoverDeviceFilter);
1670 }
1671
1672 directedDiscoveryFilter = pP2pContext->directedDiscoveryFilter;
1673 if (pFilter->BSSIDs.numOfBSSIDs)
1674 {
1675 bssid = ( tCsrBssid *) vos_mem_malloc( sizeof( tCsrBssid ) * pFilter->BSSIDs.numOfBSSIDs );
1676 if(NULL == bssid)
1677 {
1678 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1679 " %s fail to allocate bssid", __FUNCTION__);
1680 status = eHAL_STATUS_RESOURCES;
1681 break;
1682 }
1683
1684 pFilter->BSSIDs.bssid = bssid;
1685
1686 for (i = 0; i < uNumDeviceFilters; i++)
1687 {
1688 vos_mem_copy(bssid, directedDiscoveryFilter->DeviceID, P2P_MAC_ADDRESS_LEN);
1689 bssid += sizeof(tCsrBssid);
1690 directedDiscoveryFilter += sizeof(tp2pDiscoverDeviceFilter);
1691 }
1692 }
1693
1694 directedDiscoveryFilter = pP2pContext->directedDiscoveryFilter;
1695 if (pFilter->SSIDs.numOfSSIDs)
1696 {
1697 pFilter->SSIDs.SSIDList = (tCsrSSIDInfo *)vos_mem_malloc( sizeof( *pFilter->SSIDs.SSIDList ) *
1698 pFilter->SSIDs.numOfSSIDs );
1699 if(NULL == pFilter->SSIDs.SSIDList)
1700 {
1701 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1702 " %s fail to allocate bssid", __FUNCTION__);
1703 status = eHAL_STATUS_RESOURCES;
1704 break;
1705 }
1706
1707 if ( pFilter->SSIDs.SSIDList )
1708 {
1709 for ( i = 0; i < uNumDeviceFilters; i++ )
1710 {
1711 if (directedDiscoveryFilter->ucBitmask == DISCOVERY_FILTER_BITMASK_GO)
1712 {
1713 if(directedDiscoveryFilter->GroupSSID.length)
1714 {
1715 pFilter->SSIDs.SSIDList[i].SSID.length = directedDiscoveryFilter->GroupSSID.length;
1716 vos_mem_copy( pFilter->SSIDs.SSIDList[i].SSID.ssId,
1717 directedDiscoveryFilter->GroupSSID.ssId,
1718 directedDiscoveryFilter->GroupSSID.length );
1719 }
1720 }
1721 directedDiscoveryFilter += sizeof(tp2pDiscoverDeviceFilter);
1722 }
1723 }
1724 }
1725 }
1726
1727 pFilter->p2pResult = TRUE;
1728 pFilter->bWPSAssociation = TRUE;
1729 pFilter->BSSType = eCSR_BSS_TYPE_ANY;
1730 } while(0);
1731
1732 if(!HAL_STATUS_SUCCESS(status))
1733 {
1734 if(pFilter->SSIDs.SSIDList)
1735 {
1736 vos_mem_free(pFilter->SSIDs.SSIDList);
1737 pFilter->SSIDs.SSIDList = NULL;
1738 }
1739 if( pFilter->BSSIDs.bssid )
1740 {
1741 vos_mem_free(pFilter->BSSIDs.bssid);
1742 pFilter->BSSIDs.bssid = NULL;
1743 }
1744 }
1745
1746 return status;
1747}
1748
1749
1750/*
1751 @breif Function calls P2P_Fsm function to initiate the P2P Discover process
1752
1753 @param[in] hHal - Handle to MAC structure.
1754 [in] sessionID - Session ID returned by sme_OpenSession
1755 [in] pDiscoverRequest - pointer to the tp2pDiscoverRequest structure
1756 whose parameters are filled in the HDD.
1757 [in] callback - HDD callback function to be called when Discover
1758 is complete
1759 [in] pContext - a pointer passed in for the callback
1760
1761 @return eHAL_STATUS_FAILURE - If success.
1762 eHAL_STATUS_SUCCESS - If failure.
1763*/
1764eHalStatus P2P_DiscoverRequest(tHalHandle hHal,
1765 tANI_U8 SessionID,
1766 tP2PDiscoverRequest *pDiscoverRequest,
1767 p2pDiscoverCompleteCallback callback,
1768 void *pContext)
1769{
1770 eHalStatus status = eHAL_STATUS_FAILURE;
1771 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
1772 tScanResultHandle hScanResult = NULL;
1773 tCsrScanResultFilter filter;
1774 tANI_U32 uNumDeviceFilters;
1775 tp2pDiscoverDeviceFilter *pDeviceFilters;
1776 tANI_U32 i = 0;
1777 tp2pContext *pP2pContext = &pMac->p2pContext[SessionID];
1778 tCsrBssid *bssid = NULL;
1779 tp2pDiscoverDeviceFilter discoverFilter;
1780 tANI_BOOLEAN fDirect = FALSE;
1781
1782 if (pDiscoverRequest == NULL)
1783 {
1784 return status;
1785 }
1786
1787 pP2pContext->discoverType = pDiscoverRequest->discoverType;
1788 pP2pContext->scanType = pDiscoverRequest->scanType;
1789 pP2pContext->uDiscoverTimeout = pDiscoverRequest->uDiscoverTimeout;
1790
1791 if (pP2pContext->DiscoverReqIeField)
1792 {
1793 vos_mem_free(pP2pContext->DiscoverReqIeField);
1794 pP2pContext->DiscoverReqIeLength = 0;
1795 pP2pContext->DiscoverReqIeField = NULL;
1796 }
1797
1798 if (pDiscoverRequest->uIELen)
1799 {
1800 pP2pContext->DiscoverReqIeField = (tANI_U8 *)vos_mem_malloc(pDiscoverRequest->uIELen);
1801 vos_mem_copy((tANI_U8 *)pP2pContext->DiscoverReqIeField, pDiscoverRequest->pIEField, pDiscoverRequest->uIELen);
1802 pP2pContext->DiscoverReqIeLength = pDiscoverRequest->uIELen;
1803 }
1804 else
1805 {
1806 pP2pContext->DiscoverReqIeLength = 0;
1807 }
1808
1809 vos_mem_zero(&filter, sizeof(filter));
1810
1811 do
1812 {
1813 if (pDiscoverRequest->uNumDeviceFilters)
1814 {
1815 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s directed\n", __FUNCTION__);
1816 fDirect = TRUE;
1817 uNumDeviceFilters = pDiscoverRequest->uNumDeviceFilters;
1818
1819 pP2pContext->uDiscoverTimeout = pP2pContext->uDiscoverTimeout;
1820 pP2pContext->uNumDeviceFilters = pDiscoverRequest->uNumDeviceFilters;
1821 if(pP2pContext->uNumDeviceFilterAllocated < pDiscoverRequest->uNumDeviceFilters)
1822 {
1823 if(pP2pContext->directedDiscoveryFilter)
1824 {
1825 pP2pContext->uNumDeviceFilterAllocated = 0;
1826 vos_mem_free(pP2pContext->directedDiscoveryFilter);
1827 pP2pContext->directedDiscoveryFilter = NULL;
1828 }
1829 pP2pContext->directedDiscoveryFilter = (tp2pDiscoverDeviceFilter *)
1830 vos_mem_malloc(sizeof(tp2pDiscoverDeviceFilter) * uNumDeviceFilters);
1831 if(NULL == pP2pContext->directedDiscoveryFilter)
1832 {
1833 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1834 "%s fail to allocate memory for discoverFilter", __FUNCTION__);
1835 status = eHAL_STATUS_RESOURCES;
1836 break;
1837 }
1838 pP2pContext->uNumDeviceFilterAllocated = uNumDeviceFilters;
1839 }
1840
1841 pDeviceFilters = pDiscoverRequest->pDeviceFilters;
1842 if(NULL != pDeviceFilters)
1843 {
1844 vos_mem_copy ( pP2pContext->directedDiscoveryFilter, pDeviceFilters,
1845 sizeof(tp2pDiscoverDeviceFilter) * uNumDeviceFilters);
1846
1847 if(!HAL_STATUS_SUCCESS(status = p2pGetResultFilter(pP2pContext, &filter)))
1848 {
1849 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1850 "%s fail to create filter", __FUNCTION__);
1851 break;
1852 }
1853 }//if(NULL != pDeviceFilters)
1854
1855 status = csrScanGetResult(pMac, &filter, &hScanResult);
1856 if (hScanResult)
1857 {
1858 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1859 "%s calling p2pDiscoverCompleteCallback\n", __FUNCTION__);
1860 if (callback)
1861 {
1862 callback(hHal, pContext, eP2P_DIRECTED_DISCOVER);
1863
1864 }
1865 status = eHAL_STATUS_SUCCESS;
1866 break;
1867 }
1868 else
1869 {
1870 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1871 "%s Directed find did not find BSSID in cache\n", __FUNCTION__);
1872 pP2pContext->formationReq.targetListenChannel = 0;
1873 if (pDiscoverRequest->uNumDeviceFilters == 1 && filter.BSSIDs.numOfBSSIDs == 1)
1874 {
1875 vos_mem_copy(&pP2pContext->formationReq.deviceAddress,
1876 pDiscoverRequest->pDeviceFilters->DeviceID, P2P_MAC_ADDRESS_LEN);
1877 }
1878 }
1879 }
1880
1881 pP2pContext->p2pDiscoverCBFunc = callback;
1882 pP2pContext->pContext = pContext;
1883 pP2pContext->directedDiscovery = fDirect;
1884 if(!pP2pContext->GroupFormationPending)
1885 {
1886 p2pFsm(&pMac->p2pContext[SessionID], eP2P_TRIGGER_DEVICE_MODE_DEVICE);
1887 }
1888 else
1889 {
1890 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED,
1891 "%s while group formation", __FUNCTION__);
1892 }
1893
1894 pP2pContext->uDiscoverTimeout = pDiscoverRequest->uDiscoverTimeout;
1895 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO_MED, "%s Start discover", __FUNCTION__);
1896 status = palTimerStart(pMac->hHdd, pP2pContext->discoverTimer,
1897 pP2pContext->uDiscoverTimeout * 1000, eANI_BOOLEAN_FALSE);
1898 if(!HAL_STATUS_SUCCESS(status))
1899 {
1900 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
1901 "%s failt to start discover timer", __FUNCTION__);
1902 pP2pContext->p2pDiscoverCBFunc = NULL;
1903 pP2pContext->pContext = NULL;
1904 if(callback)
1905 {
1906 callback(pMac, pContext, eP2P_DISCOVER_FAILURE);
1907 }
1908 }
1909 }while(0);
1910
1911 if(filter.SSIDs.SSIDList)
1912 {
1913 vos_mem_free(filter.SSIDs.SSIDList);
1914 }
1915 if( hScanResult )
1916 {
1917 sme_ScanResultPurge( pMac, hScanResult );
1918 }
1919 if( filter.BSSIDs.bssid )
1920 {
1921 vos_mem_free(filter.BSSIDs.bssid);
1922 }
1923
1924 return status;
1925}
1926
1927eHalStatus p2pScanRequest(tp2pContext *p2pContext, p2pDiscoverCompleteCallback callback, void *pContext)
1928{
1929 tCsrScanRequest scanRequest;
1930 v_U32_t scanId = 0;
1931 tANI_U32 len = 0;
1932 tCsrSSIDInfo wcSSID = { {P2P_WILDCARD_SSID_LEN, P2P_WILDCARD_SSID}, 0, 0 };
1933 tANI_U8 Channel;
1934 eHalStatus status = eHAL_STATUS_SUCCESS;
1935 tP2P_OperatingChannel p2pOperatingChannel;
1936 tpAniSirGlobal pMac = PMAC_STRUCT(p2pContext->hHal);
1937 tANI_U8 *p2pIe = NULL;
1938 tANI_U32 p2pIeLen;
1939
1940 vos_mem_zero( &scanRequest, sizeof(scanRequest));
1941
1942 P2P_GetOperatingChannel(p2pContext->hHal, p2pContext->sessionId, &p2pOperatingChannel);
1943 Channel = p2pOperatingChannel.channel;
1944
1945 if (Channel)
1946 {
1947 scanRequest.ChannelInfo.numOfChannels = 1;
1948 scanRequest.ChannelInfo.ChannelList = &Channel;
1949 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s Scan on channel %d p2pContext->sessionId %d\n",
1950 __FUNCTION__, Channel, p2pContext->sessionId);
1951 }
1952 else
1953 {
1954 getChannelInfo(p2pContext, &scanRequest.ChannelInfo, WFD_DISCOVER_TYPE_AUTO);
1955 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s Scan on all channels\n",
1956 __FUNCTION__);
1957 }
1958
1959 /* set the scan type to active */
1960 scanRequest.scanType = eSIR_ACTIVE_SCAN;
1961
1962 vos_mem_set( scanRequest.bssid, sizeof( tCsrBssid ), 0xff );
1963
1964 scanRequest.requestType = eCSR_SCAN_P2P_FIND_PEER;
1965 /* set min and max channel time to zero */
1966 scanRequest.minChnTime = 30;
1967 scanRequest.maxChnTime = 100;
1968
1969 /* set BSSType to default type */
1970 scanRequest.BSSType = eCSR_BSS_TYPE_ANY;
1971
1972 scanRequest.SSIDs.numOfSSIDs = 1;
1973 scanRequest.SSIDs.SSIDList = &wcSSID;
1974 scanRequest.p2pSearch = VOS_FALSE;
1975
1976 P2P_GetIE(p2pContext, p2pContext->sessionId, eP2P_GROUP_ID, &p2pIe, &p2pIeLen);
1977 vos_mem_copy(scanRequest.bssid, ((tP2PGroupId *)p2pIe)->deviceAddress, P2P_MAC_ADDRESS_LEN);
1978
1979 P2P_GetIE(p2pContext, p2pContext->sessionId, eP2P_PROBE_REQ, &scanRequest.pIEField, &len);
1980
1981 scanRequest.uIEFieldLen = len;
1982
1983 status = csrScanRequest( p2pContext->hHal, p2pContext->SMEsessionId, &scanRequest, &scanId, callback, pContext );
1984
1985 if(scanRequest.pIEField)
1986 {
1987 vos_mem_free(scanRequest.pIEField);
1988 }
1989
1990 if(p2pIe)
1991 {
1992 vos_mem_free(p2pIe);
1993 }
1994 return status;
1995}
1996
1997tANI_U8 getP2PSessionIdFromSMESessionId(tHalHandle hHal, tANI_U8 SessionID)
1998{
1999 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
2000 tANI_U8 num_session;
2001
2002 for (num_session = 0; num_session < MAX_NO_OF_P2P_SESSIONS; num_session++)
2003 {
2004 if(SessionID == pMac->p2pContext[num_session].SMEsessionId)
2005 {
2006 return pMac->p2pContext[num_session].sessionId;
2007 }
2008 }
2009
2010 return CSR_SESSION_ID_INVALID;
2011}
2012
2013
2014/* SessionID is HDD session id, not SME sessionId*/
2015eHalStatus p2pCloseSession(tHalHandle hHal, tANI_U8 SessionID)
2016{
2017 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
2018 tp2pContext *pContext = &pMac->p2pContext[SessionID];
2019
2020 pContext->SMEsessionId = CSR_SESSION_ID_INVALID;
2021 p2pResetContext(pContext);
2022
2023 return eHAL_STATUS_SUCCESS;
2024}
2025
2026
2027eHalStatus p2pSetSessionId(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 SmeSessionId)
2028{
2029 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
2030
2031 pMac->p2pContext[SessionID].sessionId = SessionID;
2032 pMac->p2pContext[SessionID].SMEsessionId = SmeSessionId;
2033
2034 return eHAL_STATUS_SUCCESS;
2035}
2036
2037static tANI_BOOLEAN p2pIsGOportEnabled(tpAniSirGlobal pMac)
2038{
2039
2040 tANI_U8 num_session = 0;
2041
2042 for (num_session = 0; num_session < MAX_NO_OF_P2P_SESSIONS ; num_session++)
2043 {
2044 if (pMac->p2pContext[num_session].operatingmode == OPERATION_MODE_P2P_GROUP_OWNER)
2045 {
2046 return eANI_BOOLEAN_TRUE;
2047 }
2048 }
2049
2050 return eANI_BOOLEAN_FALSE;
2051}
2052
2053tANI_BOOLEAN p2pIsOperatingChannEqualListenChann(tHalHandle hHal, tANI_U8 SessionID)
2054{
2055 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
2056
2057 if(pMac->p2pContext[SessionID].P2POperatingChannel == pMac->p2pContext[SessionID].P2PListenChannel)
2058 {
2059 return eANI_BOOLEAN_TRUE;
2060 }
2061
2062 return eANI_BOOLEAN_FALSE;
2063}
2064
2065eHalStatus p2pGetListenChannel(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 *channel)
2066{
2067 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
2068
2069 *channel = pMac->p2pContext[SessionID].P2PListenChannel;
2070
2071 return eHAL_STATUS_SUCCESS;
2072}
2073
2074eHalStatus p2pSetListenChannel(tHalHandle hHal, tANI_U8 SessionID, tANI_U8 channel)
2075{
2076 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
2077 tP2P_OperatingChannel p2pListenChannel;
2078 eHalStatus status = eHAL_STATUS_SUCCESS;
2079
2080 if(csrRoamIsChannelValid(pMac, channel))
2081 {
2082 pMac->p2pContext[SessionID].P2PListenChannel = channel;
2083 p2pGetListenChannelAttrib(pMac, pMac->p2pContext[SessionID].sessionId, &p2pListenChannel);
2084 p2pListenChannel.channel = channel;
2085 p2pUpdateListenChannelAttrib(pMac, pMac->p2pContext[SessionID].sessionId, &p2pListenChannel);
2086 }
2087 else
2088 {
2089 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
2090 " %s fail with invalid channel %d", __FUNCTION__, channel);
2091 status = eHAL_STATUS_INVALID_PARAMETER;
2092 }
2093
2094 return status;
2095}
2096
2097
2098
2099eHalStatus p2pStopDiscovery(tHalHandle hHal, tANI_U8 SessionID)
2100{
2101 tpAniSirGlobal pMac = PMAC_STRUCT(hHal);
2102 eHalStatus status = eHAL_STATUS_SUCCESS;
2103
2104 status = palTimerStop(pMac->hHdd, pMac->p2pContext[SessionID].discoverTimer);
2105 if (status != eHAL_STATUS_SUCCESS)
2106 {
2107 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR, "%s Timer Stop status %d\n", __FUNCTION__, status);
2108 return status;
2109 }
2110
2111 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_INFO, "%s Timer Stop status %d\n", __FUNCTION__, status);
2112 p2pCallDiscoverCallback(&pMac->p2pContext[SessionID], eP2P_DIRECTED_DISCOVER);
2113
2114 status = p2pFsm( &pMac->p2pContext[SessionID], eP2P_TRIGGER_DISCONNECTED );
2115
2116 return status;
2117}
2118
2119//Purge P2P device/GO from the list
2120eHalStatus p2pPurgeDeviceList(tpAniSirGlobal pMac, tDblLinkList *pList)
2121{
2122 eHalStatus status = eHAL_STATUS_SUCCESS;
2123 tListElem *pEntry, *pNext;
2124 tCsrScanResult *pBssResult;
2125 tDot11fBeaconIEs *pIes;
2126
2127 csrLLLock(pList);
2128
2129 pEntry = csrLLPeekHead(pList, LL_ACCESS_NOLOCK);
2130 while( NULL != pEntry )
2131 {
2132 pNext = csrLLNext(pList, pEntry, LL_ACCESS_NOLOCK);
2133 pBssResult = GET_BASE_ADDR( pEntry, tCsrScanResult, Link );
2134 pIes = NULL;
2135 if(!HAL_STATUS_SUCCESS(csrGetParsedBssDescriptionIEs(pMac, &pBssResult->Result.BssDescriptor, &pIes)))
2136 {
2137 VOS_TRACE(VOS_MODULE_ID_SME, VOS_TRACE_LEVEL_ERROR,
2138 " %s fail to parse IEs. pEntry (0x%X)",
2139 __FUNCTION__, pEntry);
2140 pEntry = pNext;
2141 continue;
2142 }
2143 if( pIes->P2PBeaconProbeRes.present )
2144 {
2145 //Found a P2P BSS
2146 if(csrLLRemoveEntry(pList, pEntry, LL_ACCESS_NOLOCK) )
2147 {
2148 csrFreeScanResultEntry( pMac, pBssResult );
2149 }
2150 }
2151 palFreeMemory(pMac->hHdd, pIes);
2152 pEntry = pNext;
2153 }
2154
2155 csrLLUnlock(pList);
2156
2157 return (status);
2158}
2159
2160
2161eHalStatus sme_p2pFlushDeviceList(tHalHandle hHal, tANI_U8 HDDSessionId)
2162{
2163 eHalStatus status = eHAL_STATUS_FAILURE;
2164 tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
2165
2166 smsLog(pMac, LOG2, FL("enter"));
2167 status = sme_AcquireGlobalLock( &pMac->sme );
2168 if ( HAL_STATUS_SUCCESS( status ) )
2169 {
2170 status = p2pPurgeDeviceList(pMac, &pMac->scan.scanResultList);
2171 sme_ReleaseGlobalLock( &pMac->sme );
2172 }
2173
2174 return (status);
2175}
2176
2177
2178eHalStatus sme_p2pResetSession(tHalHandle hHal, tANI_U8 HDDSessionId)
2179{
2180 eHalStatus status = eHAL_STATUS_FAILURE;
2181 tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
2182
2183 smsLog(pMac, LOG2, FL("enter"));
2184 status = sme_AcquireGlobalLock( &pMac->sme );
2185 if ( HAL_STATUS_SUCCESS( status ) )
2186 {
2187 if(MAX_NO_OF_P2P_SESSIONS > HDDSessionId)
2188 {
2189 p2pResetContext(&pMac->p2pContext[HDDSessionId]);
2190 status = eHAL_STATUS_SUCCESS;
2191 }
2192 sme_ReleaseGlobalLock( &pMac->sme );
2193 }
2194
2195 return (status);
2196}
2197
2198
2199
2200eHalStatus sme_p2pGetResultFilter(tHalHandle hHal, tANI_U8 HDDSessionId,
2201 tCsrScanResultFilter *pFilter)
2202{
2203 eHalStatus status = eHAL_STATUS_FAILURE;
2204 tpAniSirGlobal pMac = PMAC_STRUCT( hHal );
2205
2206 status = sme_AcquireGlobalLock( &pMac->sme );
2207 if ( HAL_STATUS_SUCCESS( status ) )
2208 {
2209 if(MAX_NO_OF_P2P_SESSIONS > HDDSessionId)
2210 {
2211 status = p2pGetResultFilter(&pMac->p2pContext[HDDSessionId], pFilter);
2212 }
2213 sme_ReleaseGlobalLock( &pMac->sme );
2214 }
2215
2216 return status;
2217}
2218
2219
2220
2221#endif //WLAN_FEATURE_P2P_INTERNAL
2222
2223eHalStatus p2pProcessNoAReq(tpAniSirGlobal pMac, tSmeCmd *pNoACmd)
2224{
2225 tpP2pPsConfig pNoA;
2226 tSirMsgQ msg;
2227 eHalStatus status = eHAL_STATUS_SUCCESS;
2228
2229 status = palAllocateMemory(pMac->hHdd, (void**)&pNoA, sizeof(tP2pPsConfig));
2230 if(HAL_STATUS_SUCCESS(status))
2231 {
2232 palZeroMemory(pMac->hHdd, pNoA, sizeof(tP2pPsConfig));
2233 pNoA->opp_ps = pNoACmd->u.NoACmd.NoA.opp_ps;
2234 pNoA->ctWindow = pNoACmd->u.NoACmd.NoA.ctWindow;
2235 pNoA->duration = pNoACmd->u.NoACmd.NoA.duration;
2236 pNoA->interval = pNoACmd->u.NoACmd.NoA.interval;
2237 pNoA->count = pNoACmd->u.NoACmd.NoA.count;
2238 pNoA->single_noa_duration = pNoACmd->u.NoACmd.NoA.single_noa_duration;
2239 pNoA->psSelection = pNoACmd->u.NoACmd.NoA.psSelection;
2240 pNoA->sessionid = pNoACmd->u.NoACmd.NoA.sessionid;
2241 msg.type = eWNI_SME_UPDATE_NOA;
2242 msg.bodyval = 0;
2243 msg.bodyptr = pNoA;
2244 limPostMsgApi(pMac, &msg);
2245 }
2246 return status;
2247}
2248
2249
2250
2251
2252#endif //WLAN_FEATURE_P2P