1 /*
2 * Copyright (C) 2010 NXP Semiconductors
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16 /*!
17 * \file phHal4Nfc_Reader.c
18 * \brief Hal4Nfc Reader source.
19 *
20 * Project: NFC-FRI 1.1
21 *
22 * $Date: Mon May 31 11:43:43 2010 $
23 * $Author: ing07385 $
24 * $Revision: 1.120 $
25 * $Aliases: NFC_FRI1.1_WK1023_R35_1 $
26 *
27 */
28
29 /* ---------------------------Include files ------------------------------------*/
30 #include <phHal4Nfc.h>
31 #include <phHal4Nfc_Internal.h>
32 #include <phOsalNfc.h>
33 #include <phHciNfc.h>
34 #include <phOsalNfc_Timer.h>
35 #include <phNfcConfig.h>
36
37
38 /* ------------------------------- Macros ------------------------------------*/
39 #define PH_HAL4NFC_CMD_LENGTH PHHAL_MAX_DATASIZE+12/**< Cmd length used
40 for Transceive*/
41 #define PH_HAL4NFC_MAX_TRCV_LEN 4096 /**<Only a max of 1KB
42 can be sent at
43 a time*/
44 #define PH_HAL4NFC_FLAG_0 0
45
46 #define PH_HAL4NFC_FLAG_1 1
47
48 #define PH_HAL4NFC_SEL_SECTOR1_BYTE0 0xC2
49 #define PH_HAL4NFC_SEL_SECTOR1_BYTE1 0xFF
50
51 #define PH_HAL4NFC_SEL_SECTOR2_BYTE0 0x02
52 #define PH_HAL4NFC_SEL_SECTOR2_BYTE_RESERVED 0x00
53
54
55 /* --------------------Structures and enumerations --------------------------*/
56
57 static void phHal4Nfc_Iso_3A_Transceive(
58 phHal_sTransceiveInfo_t *psTransceiveInfo,
59 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt
60 );
61
62 static void phHal4Nfc_MifareTransceive(
63 phHal_sTransceiveInfo_t *psTransceiveInfo,
64 phHal_sRemoteDevInformation_t *psRemoteDevInfo,
65 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt
66 );
67
68 /*Allows to connect to a single, specific, already known Remote Device.*/
phHal4Nfc_Connect(phHal_sHwReference_t * psHwReference,phHal_sRemoteDevInformation_t * psRemoteDevInfo,pphHal4Nfc_ConnectCallback_t pNotifyConnectCb,void * pContext)69 NFCSTATUS phHal4Nfc_Connect(
70 phHal_sHwReference_t *psHwReference,
71 phHal_sRemoteDevInformation_t *psRemoteDevInfo,
72 pphHal4Nfc_ConnectCallback_t pNotifyConnectCb,
73 void *pContext
74 )
75 {
76 NFCSTATUS RetStatus = NFCSTATUS_SUCCESS;
77 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt = NULL;
78 uint8_t RemoteDevCount = 0;
79 int32_t MemCmpRet = 0;
80 /*NULL chks*/
81 if(NULL == psHwReference
82 || NULL == pNotifyConnectCb
83 || NULL == psRemoteDevInfo)
84 {
85 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1);
86 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_INVALID_PARAMETER);
87 }
88 /*Check initialised state*/
89 else if((NULL == psHwReference->hal_context)
90 || (((phHal4Nfc_Hal4Ctxt_t *)
91 psHwReference->hal_context)->Hal4CurrentState
92 < eHal4StateOpenAndReady)
93 || (((phHal4Nfc_Hal4Ctxt_t *)
94 psHwReference->hal_context)->Hal4NextState
95 == eHal4StateClosed))
96 {
97 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_NOT_INITIALISED);
98 }
99 else if ((psRemoteDevInfo ==
100 ((phHal4Nfc_Hal4Ctxt_t *)psHwReference->hal_context)->
101 sTgtConnectInfo.psConnectedDevice)
102 &&((phHal_eNfcIP1_Target == psRemoteDevInfo->RemDevType)
103 ||(phHal_eJewel_PICC == psRemoteDevInfo->RemDevType)))
104 {
105 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_FEATURE_NOT_SUPPORTED);
106 }
107 else
108 {
109 /*Get Hal ctxt from hardware reference*/
110 Hal4Ctxt = (phHal4Nfc_Hal4Ctxt_t *)psHwReference->hal_context;
111 /*Register upper layer context*/
112 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt = pContext;
113 /*Register upper layer callback*/
114 Hal4Ctxt->sTgtConnectInfo.pUpperConnectCb = pNotifyConnectCb;
115 /*Allow Connect only if no other remote device is connected*/
116 if((eHal4StateTargetDiscovered == Hal4Ctxt->Hal4CurrentState)
117 && (NULL == Hal4Ctxt->sTgtConnectInfo.psConnectedDevice))
118 {
119 RemoteDevCount = Hal4Ctxt->psADDCtxtInfo->nbr_of_devices;
120 while(0 != RemoteDevCount)
121 {
122 RemoteDevCount--;
123 /*Check if handle provided by upper layer matches with any
124 remote device in the list*/
125 if(psRemoteDevInfo
126 == (Hal4Ctxt->rem_dev_list[RemoteDevCount]))
127 {
128
129 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice
130 = Hal4Ctxt->rem_dev_list[RemoteDevCount];
131 break;
132 }
133 }/*End of while*/
134
135 if(NULL == Hal4Ctxt->sTgtConnectInfo.psConnectedDevice)
136 {
137 /*No matching device handle in list*/
138 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,
139 NFCSTATUS_INVALID_REMOTE_DEVICE);
140 }
141 else
142 {
143 MemCmpRet = phOsalNfc_MemCompare(
144 (void *)&(psRemoteDevInfo->RemoteDevInfo),
145 (void *)&(Hal4Ctxt->rem_dev_list[Hal4Ctxt
146 ->psADDCtxtInfo->nbr_of_devices - 1]->RemoteDevInfo),
147 sizeof(phHal_uRemoteDevInfo_t));
148
149 /*If device is already selected issue connect from here*/
150 if(0 == MemCmpRet)
151 {
152 RetStatus = phHciNfc_Connect(Hal4Ctxt->psHciHandle,
153 (void *)psHwReference,
154 Hal4Ctxt->rem_dev_list[RemoteDevCount]);
155 if(NFCSTATUS_PENDING == RetStatus)
156 {
157 Hal4Ctxt->Hal4NextState = eHal4StateTargetConnected;
158 }
159
160 }
161 else/*Select the matching device to connect to*/
162 {
163 RetStatus = phHciNfc_Reactivate (
164 Hal4Ctxt->psHciHandle,
165 (void *)psHwReference,
166 Hal4Ctxt->rem_dev_list[RemoteDevCount]
167 );
168 Hal4Ctxt->Hal4NextState = eHal4StateTargetActivate;
169 }
170 if(NFCSTATUS_PENDING != RetStatus)
171 {
172 /*Rollback state*/
173 Hal4Ctxt->Hal4CurrentState = eHal4StateOpenAndReady;
174 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice = NULL;
175 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt = NULL;
176 Hal4Ctxt->sTgtConnectInfo.pUpperConnectCb = NULL;
177 }
178 }
179 }
180 /*Issue Reconnect*/
181 else if(psRemoteDevInfo ==
182 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice)
183 {
184 RetStatus = phHciNfc_Reactivate (
185 Hal4Ctxt->psHciHandle,
186 (void *)psHwReference,
187 psRemoteDevInfo
188 );
189 Hal4Ctxt->Hal4NextState = eHal4StateTargetActivate;
190 }
191 #ifdef RECONNECT_SUPPORT
192 else if (psRemoteDevInfo !=
193 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice)
194 {
195 phHal_sRemoteDevInformation_t *ps_store_connected_device =
196 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice;
197
198 RemoteDevCount = Hal4Ctxt->psADDCtxtInfo->nbr_of_devices;
199
200 while (0 != RemoteDevCount)
201 {
202 RemoteDevCount--;
203 /*Check if handle provided by upper layer matches with any
204 remote device in the list*/
205 if(psRemoteDevInfo == (Hal4Ctxt->rem_dev_list[RemoteDevCount]))
206 {
207 break;
208 }
209 }/*End of while*/
210
211 if (ps_store_connected_device ==
212 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice)
213 {
214 RetStatus = phHciNfc_Reactivate (Hal4Ctxt->psHciHandle,
215 (void *)psHwReference,
216 psRemoteDevInfo);
217
218 if (NFCSTATUS_PENDING == RetStatus)
219 {
220 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice =
221 Hal4Ctxt->rem_dev_list[RemoteDevCount];
222 Hal4Ctxt->Hal4NextState = eHal4StateTargetActivate;
223 }
224 }
225 }
226 #endif /* #ifdef RECONNECT_SUPPORT */
227 else if(NULL == Hal4Ctxt->sTgtConnectInfo.psConnectedDevice)
228 {
229 /*Wrong state to issue connect*/
230 RetStatus = PHNFCSTVAL(CID_NFC_HAL,
231 NFCSTATUS_INVALID_REMOTE_DEVICE);
232 }
233 else/*No Target or already connected to device*/
234 {
235 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_FAILED);
236 }
237
238 }
239 return RetStatus;
240 }
241
242 /*For Ordering Transceive Info for ISO_3A type tags*/
phHal4Nfc_Iso_3A_Transceive(phHal_sTransceiveInfo_t * psTransceiveInfo,phHal4Nfc_Hal4Ctxt_t * Hal4Ctxt)243 static void phHal4Nfc_Iso_3A_Transceive(
244 phHal_sTransceiveInfo_t *psTransceiveInfo,
245 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt
246 )
247 {
248 uint16_t i;
249 uint16_t counter= 0;
250 /* Mifare UL, Keep MIFARE RAW command as it is */
251 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.cmd_type
252 = (uint8_t)psTransceiveInfo->cmd.MfCmd;
253 /* Set flags for Select Sector */
254 if (psTransceiveInfo->sSendData.buffer[0] != phHal_eMifareWrite4)
255 {
256 if (Hal4Ctxt->SelectSectorFlag == PH_HAL4NFC_FLAG_0)
257 {
258 /* First Select Sector command */
259 if ((psTransceiveInfo->sSendData.buffer[1] == PH_HAL4NFC_SEL_SECTOR1_BYTE0) &&
260 (psTransceiveInfo->sSendData.buffer[2] == PH_HAL4NFC_SEL_SECTOR1_BYTE1))
261 {
262 Hal4Ctxt->SelectSectorFlag++;
263 PHDBG_INFO("Inside 3ATrancv,first cmd, SelectSectorFlag is 1");
264 for (i = 1; i < psTransceiveInfo->sSendData.length; i++)
265 {
266 psTransceiveInfo->sSendData.buffer[i - 1] =
267 psTransceiveInfo->sSendData.buffer[i];
268 }
269
270 psTransceiveInfo->sSendData.length--;
271 }
272 else
273 {
274 PHDBG_INFO("Inside 3ATrancv,first cmd,setting SelectSectorFlag 0");
275 Hal4Ctxt->SelectSectorFlag = 0;
276 }
277 }
278 else if (Hal4Ctxt->SelectSectorFlag == PH_HAL4NFC_FLAG_1)
279 {
280 if ((psTransceiveInfo->sSendData.buffer[1] < PH_HAL4NFC_SEL_SECTOR2_BYTE0) &&
281 (psTransceiveInfo->sSendData.buffer[2] == PH_HAL4NFC_SEL_SECTOR2_BYTE_RESERVED) &&
282 (psTransceiveInfo->sSendData.buffer[3] == PH_HAL4NFC_SEL_SECTOR2_BYTE_RESERVED) &&
283 (psTransceiveInfo->sSendData.buffer[4] == PH_HAL4NFC_SEL_SECTOR2_BYTE_RESERVED))
284 {
285 Hal4Ctxt->SelectSectorFlag++;
286 PHDBG_INFO("Inside 3ATrancv,2nd cmd, SelectSectorFlag set to 2");
287 for (i = 1; i < psTransceiveInfo->sSendData.length; i++)
288 {
289 psTransceiveInfo->sSendData.buffer[i - 1] =
290 psTransceiveInfo->sSendData.buffer[i];
291 }
292
293 psTransceiveInfo->sSendData.length--;
294 }
295 else
296 {
297 PHDBG_INFO("Inside 3ATrancv,2nd cmd, SelectSectorFlag set to 0");
298 Hal4Ctxt->SelectSectorFlag = 0;
299 }
300 }
301 else
302 {
303 Hal4Ctxt->SelectSectorFlag = 0;
304 }
305 }
306 else
307 {
308 PHDBG_INFO("Inside 3ATrancv,Mifarewrite4");
309 /* Convert MIFARE RAW to MIFARE CMD */
310 if (psTransceiveInfo->cmd.MfCmd == phHal_eMifareRaw)
311 {
312 psTransceiveInfo->cmd.MfCmd =
313 (phHal_eMifareCmdList_t)psTransceiveInfo->sSendData.buffer[0];
314
315 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.cmd_type =
316 (uint8_t)psTransceiveInfo->cmd.MfCmd;
317
318 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.addr =
319 psTransceiveInfo->addr =
320 psTransceiveInfo->sSendData.buffer[1];
321
322 for (counter = 2; counter < psTransceiveInfo->sSendData.length;
323 counter++)
324 {
325 psTransceiveInfo->sSendData.buffer[counter - 2] =
326 psTransceiveInfo->sSendData.buffer[counter];
327 }
328 PHDBG_INFO("Hal4:Inside 3A_Trcv() ,minus length by 4");
329 psTransceiveInfo->sSendData.length =
330 psTransceiveInfo->sSendData.length - 4;
331 }
332 else
333 {
334 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.cmd_type
335 = (uint8_t)psTransceiveInfo->cmd.MfCmd;
336 }
337 }
338 return;
339 }
340
341 /*For Ordering Transceive Info for Mifare tags*/
phHal4Nfc_MifareTransceive(phHal_sTransceiveInfo_t * psTransceiveInfo,phHal_sRemoteDevInformation_t * psRemoteDevInfo,phHal4Nfc_Hal4Ctxt_t * Hal4Ctxt)342 static void phHal4Nfc_MifareTransceive(
343 phHal_sTransceiveInfo_t *psTransceiveInfo,
344 phHal_sRemoteDevInformation_t *psRemoteDevInfo,
345 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt
346 )
347 {
348 uint16_t counter;
349 if (
350 #ifndef DISABLE_MIFARE_UL_WRITE_WORKAROUND
351 phHal_eMifareWrite4 != psTransceiveInfo->sSendData.buffer[0]
352 #else
353 1
354 #endif/*#ifndef DISABLE_MIFARE_UL_WRITE_WORKAROUND*/
355 )
356
357 {
358 /* Mifare UL, Keep MIFARE RAW command as it is */
359 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.cmd_type
360 = (uint8_t)psTransceiveInfo->cmd.MfCmd;
361
362 }
363 else
364 {
365 /* Convert MIFARE RAW to MIFARE CMD */
366 if (psTransceiveInfo->cmd.MfCmd == phHal_eMifareRaw)
367 {
368 psTransceiveInfo->cmd.MfCmd =
369 (phHal_eMifareCmdList_t)psTransceiveInfo->sSendData.buffer[0];
370
371 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.cmd_type =
372 (uint8_t)psTransceiveInfo->cmd.MfCmd;
373
374 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.addr =
375 psTransceiveInfo->addr =
376 psTransceiveInfo->sSendData.buffer[1];
377
378 for (counter = 2; counter < psTransceiveInfo->sSendData.length;
379 counter++)
380 {
381 psTransceiveInfo->sSendData.buffer[counter - 2] =
382 psTransceiveInfo->sSendData.buffer[counter];
383 }
384 PHDBG_INFO("Hal4:Inside MifareTrcv() ,minus length by 4");
385 psTransceiveInfo->sSendData.length =
386 psTransceiveInfo->sSendData.length - 4;
387
388 }
389 else
390 {
391 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.cmd_type
392 = (uint8_t)psTransceiveInfo->cmd.MfCmd;
393 }
394 }
395 return;
396 }
397
398 /* The phHal4Nfc_Transceive function allows the Initiator to send and receive
399 * data to and from the Remote Device selected by the caller.*/
phHal4Nfc_Transceive(phHal_sHwReference_t * psHwReference,phHal_sTransceiveInfo_t * psTransceiveInfo,phHal_sRemoteDevInformation_t * psRemoteDevInfo,pphHal4Nfc_TransceiveCallback_t pTrcvCallback,void * pContext)400 NFCSTATUS phHal4Nfc_Transceive(
401 phHal_sHwReference_t *psHwReference,
402 phHal_sTransceiveInfo_t *psTransceiveInfo,
403 phHal_sRemoteDevInformation_t *psRemoteDevInfo,
404 pphHal4Nfc_TransceiveCallback_t pTrcvCallback,
405 void *pContext
406 )
407 {
408 NFCSTATUS RetStatus = NFCSTATUS_PENDING;
409 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt = (phHal4Nfc_Hal4Ctxt_t *)pContext;
410
411 /*NULL checks*/
412 if((NULL == psHwReference)
413 ||( NULL == pTrcvCallback )
414 || (NULL == psRemoteDevInfo)
415 || (NULL == psTransceiveInfo)
416 || (NULL == psTransceiveInfo->sRecvData.buffer)
417 || (NULL == psTransceiveInfo->sSendData.buffer)
418 )
419 {
420 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1);
421 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_INVALID_PARAMETER);
422 }
423 #ifdef HAL_TRCV_LIMIT
424 else if(PH_HAL4NFC_MAX_TRCV_LEN < psTransceiveInfo->sSendData.length)
425 {
426 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_NOT_ALLOWED);
427 }
428 #endif/*#ifdef HAL_TRCV_LIMIT*/
429 /*Check initialised state*/
430 else if((NULL == psHwReference->hal_context)
431 || (((phHal4Nfc_Hal4Ctxt_t *)
432 psHwReference->hal_context)->Hal4CurrentState
433 < eHal4StateOpenAndReady)
434 || (((phHal4Nfc_Hal4Ctxt_t *)
435 psHwReference->hal_context)->Hal4NextState
436 == eHal4StateClosed))
437 {
438 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_NOT_INITIALISED);
439 }
440 else
441 {
442 Hal4Ctxt = (phHal4Nfc_Hal4Ctxt_t *)psHwReference->hal_context;
443 gpphHal4Nfc_Hwref = (phHal_sHwReference_t *)psHwReference;
444 if((eHal4StateTargetConnected != Hal4Ctxt->Hal4CurrentState)
445 ||(eHal4StateInvalid != Hal4Ctxt->Hal4NextState))
446 {
447 /*Hal4 state Busy*/
448 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_BUSY);
449 PHDBG_INFO("HAL4:Trcv Failed.Returning Busy");
450 }
451 else if(psRemoteDevInfo != Hal4Ctxt->sTgtConnectInfo.psConnectedDevice)
452 {
453 /*No such Target connected*/
454 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_INVALID_REMOTE_DEVICE);
455 }
456 else
457 {
458 /*allocate Trcv context*/
459 if(NULL == Hal4Ctxt->psTrcvCtxtInfo)
460 {
461 Hal4Ctxt->psTrcvCtxtInfo= (pphHal4Nfc_TrcvCtxtInfo_t)
462 phOsalNfc_GetMemory((uint32_t)(sizeof(phHal4Nfc_TrcvCtxtInfo_t)));
463 if(NULL != Hal4Ctxt->psTrcvCtxtInfo)
464 {
465 (void)memset(Hal4Ctxt->psTrcvCtxtInfo,0,
466 sizeof(phHal4Nfc_TrcvCtxtInfo_t));
467 Hal4Ctxt->psTrcvCtxtInfo->RecvDataBufferStatus
468 = NFCSTATUS_PENDING;
469 Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId
470 = PH_OSALNFC_INVALID_TIMER_ID;
471 }
472 }
473 if(NULL == Hal4Ctxt->psTrcvCtxtInfo)
474 {
475 phOsalNfc_RaiseException(phOsalNfc_e_NoMemory,0);
476 RetStatus= PHNFCSTVAL(CID_NFC_HAL ,
477 NFCSTATUS_INSUFFICIENT_RESOURCES);
478 }
479 else
480 {
481 /*Process transceive based on Remote device type*/
482 switch(Hal4Ctxt->sTgtConnectInfo.psConnectedDevice->RemDevType)
483 {
484 case phHal_eISO14443_3A_PICC:
485 phHal4Nfc_Iso_3A_Transceive(
486 psTransceiveInfo,
487 Hal4Ctxt
488 );
489 break;
490 case phHal_eMifare_PICC:
491 PHDBG_INFO("Mifare Cmd received");
492 phHal4Nfc_MifareTransceive(
493 psTransceiveInfo,
494 psRemoteDevInfo,
495 Hal4Ctxt
496 );
497
498 #if 0
499 Hal4Ctxt->psTrcvCtxtInfo->
500 XchangeInfo.params.tag_info.cmd_type
501 = (uint8_t)psTransceiveInfo->cmd.MfCmd;
502 #endif
503 break;
504 case phHal_eISO14443_A_PICC:
505 case phHal_eISO14443_B_PICC:
506 PHDBG_INFO("ISO14443 Cmd received");
507 Hal4Ctxt->psTrcvCtxtInfo->
508 XchangeInfo.params.tag_info.cmd_type
509 = (uint8_t)psTransceiveInfo->cmd.Iso144434Cmd;
510 break;
511 case phHal_eISO15693_PICC:
512 PHDBG_INFO("ISO15693 Cmd received");
513 Hal4Ctxt->psTrcvCtxtInfo->
514 XchangeInfo.params.tag_info.cmd_type
515 = (uint8_t)psTransceiveInfo->cmd.Iso15693Cmd;
516 break;
517 case phHal_eNfcIP1_Target:
518 {
519 PHDBG_INFO("NfcIP1 Transceive");
520 Hal4Ctxt->psTrcvCtxtInfo->psUpperSendData
521 = &(psTransceiveInfo->sSendData);
522 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData =
523 &(psTransceiveInfo->sRecvData);
524 }
525 break;
526 case phHal_eFelica_PICC:
527 PHDBG_INFO("Felica Cmd received");
528 Hal4Ctxt->psTrcvCtxtInfo->
529 XchangeInfo.params.tag_info.cmd_type
530 = (uint8_t)psTransceiveInfo->cmd.FelCmd;
531 break;
532 case phHal_eJewel_PICC:
533 PHDBG_INFO("Jewel Cmd received");
534 Hal4Ctxt->psTrcvCtxtInfo->
535 XchangeInfo.params.tag_info.cmd_type
536 = (uint8_t)psTransceiveInfo->cmd.JewelCmd;
537 break;
538 case phHal_eISO14443_BPrime_PICC:
539 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,
540 NFCSTATUS_FEATURE_NOT_SUPPORTED);
541 break;
542 default:
543 PHDBG_WARNING("Invalid Device type received");
544 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_FAILED);
545 break;
546
547 }
548 }
549 }
550 /*If status is anything other than NFCSTATUS_PENDING ,an error has
551 already occured, so dont process any further and return*/
552 if(RetStatus == NFCSTATUS_PENDING)
553 {
554 if(phHal_eNfcIP1_Target ==
555 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice->RemDevType)
556 {
557 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt = pContext;
558 /*Register upper layer callback*/
559 Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb = pTrcvCallback;
560 if(PH_HAL4NFC_MAX_SEND_LEN
561 >= psTransceiveInfo->sSendData.length)
562 {
563 Hal4Ctxt->psTrcvCtxtInfo->
564 XchangeInfo.params.nfc_info.more_info = FALSE;
565 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.tx_length
566 = (uint8_t)psTransceiveInfo->sSendData.length;
567 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.tx_buffer
568 = psTransceiveInfo->sSendData.buffer;
569 /*Number of bytes remaining for next send*/
570 Hal4Ctxt->psTrcvCtxtInfo->psUpperSendData->length = 0;
571 }
572 else
573 {
574 Hal4Ctxt->psTrcvCtxtInfo->
575 XchangeInfo.params.nfc_info.more_info = TRUE;
576 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.tx_buffer
577 = Hal4Ctxt->psTrcvCtxtInfo->psUpperSendData->buffer;
578 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.tx_length
579 = PH_HAL4NFC_MAX_SEND_LEN;
580 #if 0
581 Hal4Ctxt->psTrcvCtxtInfo->psUpperSendData->buffer
582 += PH_HAL4NFC_MAX_SEND_LEN;
583 #else
584 Hal4Ctxt->psTrcvCtxtInfo->NumberOfBytesSent
585 += PH_HAL4NFC_MAX_SEND_LEN;
586 #endif
587 /*Number of bytes remaining for next send*/
588 Hal4Ctxt->psTrcvCtxtInfo->psUpperSendData->length
589 -= PH_HAL4NFC_MAX_SEND_LEN;
590 }
591 Hal4Ctxt->Hal4NextState = eHal4StateTransaction;
592 #ifdef TRANSACTION_TIMER
593 /**Create a timer to keep track of transceive timeout*/
594 if(Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId
595 == PH_OSALNFC_INVALID_TIMER_ID)
596 {
597 PHDBG_INFO("HAL4: Transaction Timer Create for transceive");
598 Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId
599 = phOsalNfc_Timer_Create();
600 }
601 if(Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId
602 == PH_OSALNFC_INVALID_TIMER_ID)
603 {
604 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,
605 NFCSTATUS_INSUFFICIENT_RESOURCES);
606 }
607 else
608 #endif/*TRANSACTION_TIMER*/
609 {
610 PHDBG_INFO("Hal4:Calling phHciNfc_Send_Data from Hal4_Transceive()");
611 RetStatus = phHciNfc_Send_Data (
612 Hal4Ctxt->psHciHandle,
613 psHwReference,
614 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice,
615 &(Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo)
616 );
617 if(NFCSTATUS_PENDING == RetStatus)
618 {
619 Hal4Ctxt->psTrcvCtxtInfo->P2P_Send_In_Progress = TRUE;
620 }
621 }
622 }
623 else if(psTransceiveInfo->sSendData.length > PH_HAL4NFC_CMD_LENGTH)
624 {
625 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_INVALID_PARAMETER);
626 }
627 else if((psTransceiveInfo->sSendData.length == 0)
628 && (Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length != 0))
629 {
630 PHDBG_INFO("Hal4:Read remaining bytes");
631 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData
632 = &(psTransceiveInfo->sRecvData);
633 /*Number of read bytes left is greater than bytes requested
634 by upper layer*/
635 if(Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length
636 < Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length)
637 {
638 (void)memcpy(Hal4Ctxt->psTrcvCtxtInfo
639 ->psUpperRecvData->buffer,
640 (Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.buffer
641 + Hal4Ctxt->psTrcvCtxtInfo->LowerRecvBufferOffset)
642 ,Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length);
643 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length -=
644 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length;
645 Hal4Ctxt->psTrcvCtxtInfo->LowerRecvBufferOffset
646 += Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length;
647 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,
648 NFCSTATUS_MORE_INFORMATION);
649 }
650 else/*Number of read bytes left is smaller.Copy all bytes
651 and free Hal's buffer*/
652 {
653 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length
654 = Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length;
655 (void)memcpy(Hal4Ctxt->psTrcvCtxtInfo
656 ->psUpperRecvData
657 ->buffer,
658 (Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.buffer
659 + Hal4Ctxt->psTrcvCtxtInfo->LowerRecvBufferOffset)
660 ,Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length);
661 phOsalNfc_FreeMemory(Hal4Ctxt->psTrcvCtxtInfo
662 ->sLowerRecvData.buffer);
663 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.buffer = NULL;
664 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length = 0;
665 Hal4Ctxt->psTrcvCtxtInfo->LowerRecvBufferOffset = 0;
666 RetStatus = NFCSTATUS_SUCCESS;
667 }
668 }
669 else/*No more bytes remaining in Hal.Read from device*/
670 {
671 /*Register upper layer context*/
672 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt = pContext;
673 /*Register upper layer callback*/
674 Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb = pTrcvCallback;
675 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params.tag_info.addr
676 = psTransceiveInfo->addr;
677 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.tx_length
678 = (uint16_t)psTransceiveInfo->sSendData.length;
679 Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.tx_buffer
680 = psTransceiveInfo->sSendData.buffer;
681 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData
682 = &(psTransceiveInfo->sRecvData);
683 #ifdef TRANSACTION_TIMER
684 /**Create a timer to keep track of transceive timeout*/
685 if(Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId
686 == PH_OSALNFC_INVALID_TIMER_ID)
687 {
688 PHDBG_INFO("HAL4: Transaction Timer Create for transceive");
689 Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId
690 = phOsalNfc_Timer_Create();
691 }
692 if(Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId
693 == PH_OSALNFC_INVALID_TIMER_ID)
694 {
695 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,
696 NFCSTATUS_INSUFFICIENT_RESOURCES);
697 }
698 else
699 #endif /*TRANSACTION_TIMER*/
700 {
701 PHDBG_INFO("Calling phHciNfc_Exchange_Data");
702 RetStatus = phHciNfc_Exchange_Data(
703 Hal4Ctxt->psHciHandle,
704 psHwReference,
705 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice,
706 &(Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo)
707 );
708
709 if(NFCSTATUS_PENDING == RetStatus)
710 {
711 Hal4Ctxt->Hal4NextState = eHal4StateTransaction;
712 #ifdef TRANSACTION_TIMER
713 /**Start timer to keep track of transceive timeout*/
714 phOsalNfc_Timer_Start(
715 Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId,
716 PH_HAL4NFC_TRANSCEIVE_TIMEOUT,
717 phHal4Nfc_TrcvTimeoutHandler
718 );
719 #endif/*#ifdef TRANSACTION_TIMER*/
720 }
721 else
722 {
723 Hal4Ctxt->Hal4NextState = eHal4StateInvalid;
724 }
725 }
726 }
727 }
728 }
729 return RetStatus;
730 }
731
732 #ifdef TRANSACTION_TIMER
733 /**Handle transceive timeout*/
phHal4Nfc_TrcvTimeoutHandler(uint32_t TrcvTimerId)734 void phHal4Nfc_TrcvTimeoutHandler(uint32_t TrcvTimerId)
735 {
736 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt = gpphHal4Nfc_Hwref->hal_context;
737 pphHal4Nfc_ReceiveCallback_t pUpperRecvCb = NULL;
738 pphHal4Nfc_TransceiveCallback_t pUpperTrcvCb = NULL;
739 phOsalNfc_Timer_Stop(TrcvTimerId);
740 phOsalNfc_Timer_Delete(TrcvTimerId);
741 Hal4Ctxt->psTrcvCtxtInfo->TransactionTimerId = PH_OSALNFC_INVALID_TIMER_ID;
742 Hal4Ctxt->Hal4NextState = eHal4StateInvalid;
743 /*For a P2P target*/
744 if(Hal4Ctxt->psTrcvCtxtInfo->pP2PRecvCb != NULL)
745 {
746 pUpperRecvCb = Hal4Ctxt->psTrcvCtxtInfo->pP2PRecvCb;
747 Hal4Ctxt->psTrcvCtxtInfo->pP2PRecvCb = NULL;
748 (*pUpperRecvCb)(
749 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt,
750 NULL,
751 NFCSTATUS_RF_TIMEOUT
752 );
753 }
754 else
755 {
756 /*For a P2P Initiator and tags*/
757 if(Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb != NULL)
758 {
759 pUpperTrcvCb = Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb;
760 Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb = NULL;
761 (*pUpperTrcvCb)(
762 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt,
763 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice,
764 NULL,
765 NFCSTATUS_RF_TIMEOUT
766 );
767 }
768 }
769 }
770 #endif /*TRANSACTION_TIMER*/
771
772
773 /**The function allows to disconnect from a specific Remote Device.*/
phHal4Nfc_Disconnect(phHal_sHwReference_t * psHwReference,phHal_sRemoteDevInformation_t * psRemoteDevInfo,phHal_eReleaseType_t ReleaseType,pphHal4Nfc_DiscntCallback_t pDscntCallback,void * pContext)774 NFCSTATUS phHal4Nfc_Disconnect(
775 phHal_sHwReference_t *psHwReference,
776 phHal_sRemoteDevInformation_t *psRemoteDevInfo,
777 phHal_eReleaseType_t ReleaseType,
778 pphHal4Nfc_DiscntCallback_t pDscntCallback,
779 void *pContext
780 )
781 {
782 NFCSTATUS RetStatus = NFCSTATUS_PENDING;
783 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt = NULL;
784 PHDBG_INFO("Hal4:Inside Hal4 disconnect");
785 /*NULL checks*/
786 if(NULL == psHwReference || NULL == pDscntCallback
787 || NULL == psRemoteDevInfo)
788 {
789 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1);
790 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_INVALID_PARAMETER);
791 }
792 /*Check Initialised state*/
793 else if((NULL == psHwReference->hal_context)
794 || (((phHal4Nfc_Hal4Ctxt_t *)
795 psHwReference->hal_context)->Hal4CurrentState
796 < eHal4StateOpenAndReady)
797 || (((phHal4Nfc_Hal4Ctxt_t *)
798 psHwReference->hal_context)->Hal4NextState
799 == eHal4StateClosed))
800 {
801 RetStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_NOT_INITIALISED);
802 }
803 else if(((phHal4Nfc_Hal4Ctxt_t *)
804 psHwReference->hal_context)->Hal4CurrentState
805 != eHal4StateTargetConnected)
806 {
807 PHDBG_INFO("Hal4:Current sate is not connect.Release returning failed");
808 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_FAILED);
809 }
810 else
811 {
812 Hal4Ctxt = (phHal4Nfc_Hal4Ctxt_t *)psHwReference->hal_context;
813 if((Hal4Ctxt->sTgtConnectInfo.psConnectedDevice == NULL)
814 || (psRemoteDevInfo != Hal4Ctxt->sTgtConnectInfo.psConnectedDevice))
815 {
816 PHDBG_INFO("Hal4:disconnect returning INVALID_REMOTE_DEVICE");
817 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_INVALID_REMOTE_DEVICE);
818 }
819 else
820 {
821 /*Register upper layer context*/
822 Hal4Ctxt->sUpperLayerInfo.psUpperLayerDisconnectCtxt = pContext;
823 /*Register upper layer callback*/
824 Hal4Ctxt->sTgtConnectInfo.pUpperDisconnectCb = pDscntCallback;
825 /*Register Release Type*/
826 Hal4Ctxt->sTgtConnectInfo.ReleaseType = ReleaseType;
827 if((eHal4StateTransaction == Hal4Ctxt->Hal4NextState)
828 &&((phHal_eNfcIP1_Target != psRemoteDevInfo->RemDevType)
829 ||((NFC_DISCOVERY_CONTINUE != ReleaseType)
830 &&(NFC_DISCOVERY_RESTART != ReleaseType))))
831 {
832 Hal4Ctxt->sTgtConnectInfo.ReleaseType
833 = NFC_INVALID_RELEASE_TYPE;
834 PHDBG_INFO("Hal4:disconnect returning NFCSTATUS_NOT_ALLOWED");
835 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_NOT_ALLOWED);
836 }
837 else if((eHal4StateTransaction == Hal4Ctxt->Hal4NextState)
838 &&(NULL != Hal4Ctxt->psTrcvCtxtInfo)
839 &&(TRUE == Hal4Ctxt->psTrcvCtxtInfo->P2P_Send_In_Progress))
840 {
841 /*store the hardware reference for executing disconnect later*/
842 gpphHal4Nfc_Hwref = psHwReference;
843 PHDBG_INFO("Hal4:disconnect deferred");
844 }
845 else/*execute disconnect*/
846 {
847 RetStatus = phHal4Nfc_Disconnect_Execute(psHwReference);
848 }
849 }
850 }
851 return RetStatus;
852 }
853
854 /**Execute Hal4 Disconnect*/
phHal4Nfc_Disconnect_Execute(phHal_sHwReference_t * psHwReference)855 NFCSTATUS phHal4Nfc_Disconnect_Execute(
856 phHal_sHwReference_t *psHwReference
857 )
858 {
859 NFCSTATUS RetStatus = NFCSTATUS_PENDING;
860 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt =
861 (phHal4Nfc_Hal4Ctxt_t *)psHwReference->hal_context;
862 phHal_eSmartMX_Mode_t SmxMode = eSmartMx_Default;
863 PHDBG_INFO("Hal4:Inside Hal4 disconnect execute");
864 switch(Hal4Ctxt->sTgtConnectInfo.ReleaseType)
865 {
866 /*Switch mode to Default*/
867 case NFC_SMARTMX_RELEASE:
868 SmxMode = eSmartMx_Default;
869 RetStatus = phHciNfc_Switch_SmxMode (
870 Hal4Ctxt->psHciHandle,
871 psHwReference,
872 SmxMode,
873 &(Hal4Ctxt->psADDCtxtInfo->sADDCfg)
874 );
875 break;
876 /*Disconnect and continue polling wheel*/
877 case NFC_DISCOVERY_CONTINUE:
878 {
879 RetStatus = phHciNfc_Disconnect (
880 Hal4Ctxt->psHciHandle,
881 psHwReference,
882 FALSE
883 );
884 if(NFCSTATUS_PENDING != RetStatus)
885 {
886 PHDBG_INFO("Hal4:Hci disconnect failed.Restarting discovery");
887 RetStatus = phHciNfc_Restart_Discovery (
888 (void *)Hal4Ctxt->psHciHandle,
889 (void *)gpphHal4Nfc_Hwref,
890 FALSE
891 );
892 if(NFCSTATUS_PENDING != RetStatus)
893 {
894 PHDBG_INFO("Hal4:Hci Restart discovery also failed");
895 }
896 }
897 break;
898 }
899 /*Disconnect and restart polling wheel*/
900 case NFC_DISCOVERY_RESTART:
901 RetStatus = phHciNfc_Disconnect (
902 Hal4Ctxt->psHciHandle,
903 psHwReference,
904 TRUE
905 );
906 break;
907 default:
908 RetStatus = PHNFCSTVAL(CID_NFC_HAL,
909 NFCSTATUS_FEATURE_NOT_SUPPORTED);
910 break;
911 }
912 Hal4Ctxt->sTgtConnectInfo.ReleaseType = NFC_INVALID_RELEASE_TYPE;
913 /*Update or rollback next state*/
914 Hal4Ctxt->Hal4NextState = (NFCSTATUS_PENDING == RetStatus?
915 eHal4StateOpenAndReady:Hal4Ctxt->Hal4NextState);
916 return RetStatus;
917 }
918
919 /*The function allows to check for presence in vicinity of connected remote
920 device.*/
phHal4Nfc_PresenceCheck(phHal_sHwReference_t * psHwReference,pphHal4Nfc_GenCallback_t pPresenceChkCb,void * context)921 NFCSTATUS phHal4Nfc_PresenceCheck(
922 phHal_sHwReference_t *psHwReference,
923 pphHal4Nfc_GenCallback_t pPresenceChkCb,
924 void *context
925 )
926 {
927 NFCSTATUS RetStatus = NFCSTATUS_FAILED;
928 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt = NULL;
929 /*NULL checks*/
930 if((NULL == pPresenceChkCb) || (NULL == psHwReference))
931 {
932 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_INVALID_PARAMETER);
933 }
934 /*Check Initialised state*/
935 else if((NULL == psHwReference->hal_context)
936 || (((phHal4Nfc_Hal4Ctxt_t *)
937 psHwReference->hal_context)->Hal4CurrentState
938 < eHal4StateOpenAndReady)
939 || (((phHal4Nfc_Hal4Ctxt_t *)
940 psHwReference->hal_context)->Hal4NextState
941 == eHal4StateClosed))
942 {
943 PHDBG_INFO("HAL4:Context not Open");
944 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_NOT_INITIALISED);
945 }
946 /*check connected state and session alive*/
947 else if((((phHal4Nfc_Hal4Ctxt_t *)
948 psHwReference->hal_context)->Hal4CurrentState
949 < eHal4StateTargetConnected)||
950 (NULL == ((phHal4Nfc_Hal4Ctxt_t *)
951 psHwReference->hal_context)->sTgtConnectInfo.psConnectedDevice)||
952 (FALSE == ((phHal4Nfc_Hal4Ctxt_t *)
953 psHwReference->hal_context)->sTgtConnectInfo.
954 psConnectedDevice->SessionOpened))
955 {
956 PHDBG_INFO("HAL4:No target connected");
957 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_RELEASED);
958 }
959 else
960 {
961 Hal4Ctxt = (phHal4Nfc_Hal4Ctxt_t *)psHwReference->hal_context;
962 /*allow only one Presence chk command at any point in time*/
963 if (eHal4StatePresenceCheck != Hal4Ctxt->Hal4NextState)
964 {
965 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt = context;
966 Hal4Ctxt->sTgtConnectInfo.pPresenceChkCb = pPresenceChkCb;
967 RetStatus = phHciNfc_Presence_Check(Hal4Ctxt->psHciHandle,
968 psHwReference
969 );
970 Hal4Ctxt->Hal4NextState = (NFCSTATUS_PENDING == RetStatus?
971 eHal4StatePresenceCheck:Hal4Ctxt->Hal4NextState);
972 }
973 else/*Ongoing presence chk*/
974 {
975 RetStatus = PHNFCSTVAL(CID_NFC_HAL,NFCSTATUS_BUSY);
976 }
977 }
978 return RetStatus;
979 }
980
phHal4Nfc_PresenceChkComplete(phHal4Nfc_Hal4Ctxt_t * Hal4Ctxt,void * pInfo)981 void phHal4Nfc_PresenceChkComplete(
982 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt,
983 void *pInfo
984 )
985 {
986 NFCSTATUS RetStatus = ((phNfc_sCompletionInfo_t *)pInfo)->status;
987 Hal4Ctxt->Hal4NextState = eHal4StateInvalid;
988 /*Notify to upper layer*/
989 if(NULL != Hal4Ctxt->sTgtConnectInfo.pPresenceChkCb)
990 {
991 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice->SessionOpened
992 =(uint8_t)(NFCSTATUS_SUCCESS == RetStatus?TRUE:FALSE);
993 (*Hal4Ctxt->sTgtConnectInfo.pPresenceChkCb)(
994 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt,
995 RetStatus
996 );
997 }
998 return;
999 }
1000
1001 /*Callback for reactivate target and to select appropriate target incase
1002 of multiple targets*/
phHal4Nfc_ReactivationComplete(phHal4Nfc_Hal4Ctxt_t * Hal4Ctxt,void * pInfo)1003 void phHal4Nfc_ReactivationComplete(
1004 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt,
1005 void *pInfo
1006 )
1007 {
1008 NFCSTATUS Status = ((phNfc_sCompletionInfo_t *)pInfo)->status;
1009 /*A NFCSTATUS_SUCCESS status returned here means that the correct device
1010 to connect to has now been selected.So issue connect from here to complete
1011 activation*/
1012 if(NFCSTATUS_SUCCESS == Status)
1013 {
1014 Hal4Ctxt->Hal4NextState = eHal4StateTargetConnected;
1015 Status = phHciNfc_Connect(
1016 Hal4Ctxt->psHciHandle,
1017 gpphHal4Nfc_Hwref,
1018 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice
1019 );
1020 Status = (NFCSTATUS_PENDING == Status)?
1021 NFCSTATUS_PENDING:NFCSTATUS_FAILED;
1022 }
1023 else/*Device unavailable, return error in connect Callback*/
1024 {
1025 Hal4Ctxt->Hal4NextState = eHal4StateInvalid;
1026 if(NULL != Hal4Ctxt->sTgtConnectInfo.pUpperConnectCb)
1027 {
1028 (*Hal4Ctxt->sTgtConnectInfo.pUpperConnectCb)(
1029 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt,
1030 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice,
1031 Status
1032 );
1033 }
1034 }
1035 return;
1036 }
1037
1038
phHal4Nfc_ConnectComplete(phHal4Nfc_Hal4Ctxt_t * Hal4Ctxt,void * pInfo)1039 void phHal4Nfc_ConnectComplete(
1040 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt,
1041 void *pInfo
1042 )
1043 {
1044 NFCSTATUS ConnectStatus = ((phNfc_sCompletionInfo_t *)pInfo)->status;
1045 pphHal4Nfc_ConnectCallback_t pUpperConnectCb
1046 = Hal4Ctxt->sTgtConnectInfo.pUpperConnectCb;
1047 /*Flag to decide whether or not upper layer callback has to be called*/
1048 uint8_t CallConnectCb = TRUE;
1049 /*Remote device Connect successful*/
1050 if((NFCSTATUS_SUCCESS == ConnectStatus)
1051 ||(eHal4StateTargetConnected == Hal4Ctxt->Hal4CurrentState))
1052 {
1053 PHDBG_INFO("Hal4:Connect status Success");
1054 Hal4Ctxt->Hal4CurrentState = eHal4StateTargetConnected;
1055 Hal4Ctxt->Hal4NextState = eHal4StateInvalid;
1056 /* Open the Session */
1057 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice->SessionOpened =
1058 (uint8_t)(NFCSTATUS_SUCCESS == ConnectStatus?TRUE:FALSE);
1059 Hal4Ctxt->sTgtConnectInfo.pUpperConnectCb = NULL;
1060
1061 }
1062 else/*Remote device Connect failed*/
1063 {
1064 Hal4Ctxt->Hal4CurrentState = eHal4StateOpenAndReady;
1065 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice->SessionOpened = FALSE;
1066 /*For a NfcIp1 target and case where it is not a internal reconnect
1067 from Hal4 ,notify callback to upper layer*/
1068 if((phHal_eNfcIP1_Target
1069 == Hal4Ctxt->rem_dev_list[0]->RemDevType)
1070 || (NULL != Hal4Ctxt->sTgtConnectInfo.pUpperConnectCb))
1071 {
1072 Hal4Ctxt->sTgtConnectInfo.pUpperConnectCb = NULL;
1073 }
1074 else/*do not notify callback*/
1075 {
1076 CallConnectCb = FALSE;
1077 }
1078 /*Free the remote device list*/
1079 do
1080 {
1081 Hal4Ctxt->psADDCtxtInfo->nbr_of_devices--;
1082 if(NULL != Hal4Ctxt->rem_dev_list[
1083 Hal4Ctxt->psADDCtxtInfo->nbr_of_devices])
1084 {
1085 phOsalNfc_FreeMemory((void *)
1086 (Hal4Ctxt->rem_dev_list[
1087 Hal4Ctxt->psADDCtxtInfo->nbr_of_devices]));
1088 Hal4Ctxt->rem_dev_list[
1089 Hal4Ctxt->psADDCtxtInfo->nbr_of_devices] = NULL;
1090 }
1091 }while(0 < Hal4Ctxt->psADDCtxtInfo->nbr_of_devices);
1092
1093 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice = NULL;
1094 }
1095 if(TRUE == CallConnectCb)
1096 {
1097 PHDBG_INFO("Hal4:Calling Connect callback");
1098 /*Notify to the upper layer*/
1099 (*pUpperConnectCb)(
1100 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt,
1101 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice,
1102 ConnectStatus
1103 );
1104 }
1105 else
1106 {
1107 PHDBG_INFO("Hal4:Connect failed ,Restarting discovery");
1108 /*Restart the Discovery wheel*/
1109 ConnectStatus = phHciNfc_Restart_Discovery (
1110 (void *)Hal4Ctxt->psHciHandle,
1111 (void *)gpphHal4Nfc_Hwref,
1112 FALSE
1113 );
1114 Hal4Ctxt->Hal4NextState = (NFCSTATUS_PENDING == ConnectStatus?
1115 eHal4StateConfiguring:eHal4StateInvalid);
1116 }
1117 return;
1118 }
1119
1120
1121
1122
phHal4Nfc_DisconnectComplete(phHal4Nfc_Hal4Ctxt_t * Hal4Ctxt,void * pInfo)1123 void phHal4Nfc_DisconnectComplete(
1124 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt,
1125 void *pInfo
1126 )
1127 {
1128 NFCSTATUS ConnectStatus = ((phNfc_sCompletionInfo_t *)pInfo)->status;
1129 phHal_sRemoteDevInformation_t *psConnectedDevice = NULL;
1130 pphHal4Nfc_DiscntCallback_t pUpperDisconnectCb = NULL;
1131 pphHal4Nfc_TransceiveCallback_t pUpperTrcvCb = NULL;
1132 PHDBG_INFO("Hal4:Inside Hal4 disconnect callback");
1133 if(NULL == Hal4Ctxt)
1134 {
1135 phOsalNfc_RaiseException(phOsalNfc_e_InternalErr,1);
1136 }
1137 else if(NFCSTATUS_SUCCESS != ConnectStatus)/*Restart the Discovery wheel*/
1138 {
1139 ConnectStatus = phHciNfc_Restart_Discovery (
1140 (void *)Hal4Ctxt->psHciHandle,
1141 (void *)gpphHal4Nfc_Hwref,
1142 FALSE
1143 );
1144 Hal4Ctxt->Hal4NextState = (NFCSTATUS_PENDING == ConnectStatus?
1145 eHal4StateConfiguring:eHal4StateInvalid);
1146 }
1147 else/*Remote device Disconnect successful*/
1148 {
1149 psConnectedDevice = Hal4Ctxt->sTgtConnectInfo.psConnectedDevice;
1150 pUpperDisconnectCb = Hal4Ctxt->sTgtConnectInfo.pUpperDisconnectCb;
1151 /*Deallocate psTrcvCtxtInfo*/
1152 if(NULL != Hal4Ctxt->psTrcvCtxtInfo)
1153 {
1154 if(NULL == Hal4Ctxt->sTgtConnectInfo.psConnectedDevice)
1155 {
1156 if(NULL != Hal4Ctxt->psTrcvCtxtInfo->psUpperSendData)
1157 {
1158 phOsalNfc_FreeMemory(
1159 Hal4Ctxt->psTrcvCtxtInfo->psUpperSendData);
1160 }
1161 }
1162 else
1163 {
1164 if(phHal_eNfcIP1_Target
1165 == Hal4Ctxt->sTgtConnectInfo.psConnectedDevice->RemDevType)
1166 {
1167 pUpperTrcvCb = Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb;
1168 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length = 0;
1169 pUpperTrcvCb = Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb;
1170 Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb = NULL;
1171 }
1172 }
1173 if(NULL != Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.buffer)
1174 {
1175 phOsalNfc_FreeMemory(
1176 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.buffer);
1177 }
1178
1179 phOsalNfc_FreeMemory(Hal4Ctxt->psTrcvCtxtInfo);
1180 Hal4Ctxt->psTrcvCtxtInfo = NULL;
1181 }
1182 /*Free the remote device list*/
1183 do
1184 {
1185 if(NULL != Hal4Ctxt->rem_dev_list[Hal4Ctxt->
1186 psADDCtxtInfo->nbr_of_devices-1])
1187 {
1188 phOsalNfc_FreeMemory((void *)
1189 (Hal4Ctxt->rem_dev_list[Hal4Ctxt->
1190 psADDCtxtInfo->nbr_of_devices-1]));
1191 Hal4Ctxt->rem_dev_list[Hal4Ctxt->
1192 psADDCtxtInfo->nbr_of_devices-1] = NULL;
1193 }
1194 }while(--(Hal4Ctxt->psADDCtxtInfo->nbr_of_devices));
1195
1196 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice = NULL;
1197 /*Disconnect successful.Go to Ready state*/
1198 Hal4Ctxt->Hal4CurrentState = Hal4Ctxt->Hal4NextState;
1199 Hal4Ctxt->sTgtConnectInfo.pUpperDisconnectCb = NULL;
1200 Hal4Ctxt->Hal4NextState = (
1201 eHal4StateOpenAndReady == Hal4Ctxt->Hal4NextState?
1202 eHal4StateInvalid:Hal4Ctxt->Hal4NextState);
1203 /*Issue any pending Trcv callback*/
1204 if(NULL != pUpperTrcvCb)
1205 {
1206 (*pUpperTrcvCb)(
1207 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt,
1208 psConnectedDevice,
1209 NULL,
1210 NFCSTATUS_FAILED
1211 );
1212 }
1213 /*Notify upper layer*/
1214 if(NULL != pUpperDisconnectCb)
1215 {
1216 PHDBG_INFO("Hal4:Calling Upper layer disconnect callback");
1217 (*pUpperDisconnectCb)(
1218 Hal4Ctxt->sUpperLayerInfo.psUpperLayerDisconnectCtxt,
1219 psConnectedDevice,
1220 ConnectStatus
1221 );
1222 }
1223 }
1224 return;
1225 }
1226
1227
1228 /*Transceive complete handler function*/
phHal4Nfc_TransceiveComplete(phHal4Nfc_Hal4Ctxt_t * Hal4Ctxt,void * pInfo)1229 void phHal4Nfc_TransceiveComplete(
1230 phHal4Nfc_Hal4Ctxt_t *Hal4Ctxt,
1231 void *pInfo
1232 )
1233 {
1234 /*Copy status code*/
1235 NFCSTATUS TrcvStatus = ((phNfc_sCompletionInfo_t *)pInfo)->status;
1236 /*Update next state*/
1237 Hal4Ctxt->Hal4NextState = (eHal4StateTransaction
1238 == Hal4Ctxt->Hal4NextState?eHal4StateInvalid:Hal4Ctxt->Hal4NextState);
1239 /*Reset SelectSectorFlag for Mifare*/
1240 if (Hal4Ctxt->SelectSectorFlag == 2)
1241 {
1242 TrcvStatus = NFCSTATUS_SUCCESS;
1243 PHDBG_INFO("Inside Hal4TrcvComplete SelectSectorFlag is 2");
1244 Hal4Ctxt->SelectSectorFlag = 0;
1245 }
1246
1247 if(NULL == Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData)
1248 {
1249 /*if recv buffer is Null*/
1250 phOsalNfc_RaiseException(phOsalNfc_e_PrecondFailed,1);
1251 TrcvStatus = NFCSTATUS_FAILED;
1252 }
1253 else if(TrcvStatus == NFCSTATUS_SUCCESS)
1254 {
1255 /*Check if recvdata buffer given by upper layer is big enough to
1256 receive all response bytes.If it is not big enough ,copy number
1257 of bytes requested by upper layer to the buffer.Remaining
1258 bytes are retained in Hal4 and upper layer has to issue another
1259 transceive call to read the same.*/
1260 if(((phNfc_sTransactionInfo_t *)pInfo)
1261 ->length > Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length )
1262 {
1263 TrcvStatus = PHNFCSTVAL(CID_NFC_HAL ,NFCSTATUS_MORE_INFORMATION);
1264 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length
1265 = ((phNfc_sTransactionInfo_t *)pInfo)->length
1266 - Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length;
1267
1268 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.buffer
1269 = (uint8_t *)phOsalNfc_GetMemory(
1270 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length
1271 );
1272 if(NULL != Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.buffer)
1273 {
1274 (void)memcpy(
1275 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.buffer,
1276 (((phNfc_sTransactionInfo_t *)pInfo)->buffer
1277 + Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData
1278 ->length)
1279 ,Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length
1280 );
1281 }
1282 else
1283 {
1284 TrcvStatus = PHNFCSTVAL(CID_NFC_HAL,
1285 NFCSTATUS_INSUFFICIENT_RESOURCES);
1286 phOsalNfc_RaiseException(phOsalNfc_e_NoMemory,0);
1287 }
1288
1289 }
1290 else/*Buffer provided by upper layer is big enough to hold all read
1291 bytes*/
1292 {
1293 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length
1294 = ((phNfc_sTransactionInfo_t *)pInfo)->length;
1295 Hal4Ctxt->psTrcvCtxtInfo->sLowerRecvData.length = 0;
1296 }
1297 (void)memcpy(Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->buffer,
1298 ((phNfc_sTransactionInfo_t *)pInfo)->buffer,
1299 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length
1300 );
1301
1302 }
1303 else/*Error scenario.Set received bytes length to zero*/
1304 {
1305 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData->length = 0;
1306 }
1307 (void)memset((void *)&(Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params),
1308 0,
1309 sizeof(Hal4Ctxt->psTrcvCtxtInfo->XchangeInfo.params)
1310 );
1311 Hal4Ctxt->psTrcvCtxtInfo->LowerRecvBufferOffset = 0;
1312 /*Issue transceive callback*/
1313 (*Hal4Ctxt->psTrcvCtxtInfo->pUpperTranceiveCb)(
1314 Hal4Ctxt->sUpperLayerInfo.psUpperLayerCtxt,
1315 Hal4Ctxt->sTgtConnectInfo.psConnectedDevice,
1316 Hal4Ctxt->psTrcvCtxtInfo->psUpperRecvData,
1317 TrcvStatus
1318 );
1319 return;
1320 }
1321