• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 
18 /**
19  * \file  phFriNfc_LlcpMacNfcip.c
20  * \brief NFC LLCP MAC Mappings For Different RF Technologies.
21  *
22  * Project: NFC-FRI
23  *
24  */
25 
26 
27 /*include files*/
28 #include <phFriNfc_LlcpMac.h>
29 #include <phLibNfcStatus.h>
30 #include <phLibNfc.h>
31 #include <phLibNfc_Internal.h>
32 #include <stdio.h>
33 #include <string.h>
34 
35 static NFCSTATUS phFriNfc_LlcpMac_Nfcip_Send(phFriNfc_LlcpMac_t               *LlcpMac,
36                                              phNfc_sData_t                    *psData,
37                                              phFriNfc_LlcpMac_Send_CB_t       LlcpMacSend_Cb,
38                                              void                             *pContext);
39 
40 
phFriNfc_LlcpMac_Nfcip_TriggerRecvCb(phFriNfc_LlcpMac_t * LlcpMac,NFCSTATUS status)41 static void phFriNfc_LlcpMac_Nfcip_TriggerRecvCb(phFriNfc_LlcpMac_t  *LlcpMac,
42                                                  NFCSTATUS           status)
43 {
44    phFriNfc_LlcpMac_Reveive_CB_t pfReceiveCB;
45    void                          *pReceiveContext;
46 
47    if (LlcpMac->MacReceive_Cb != NULL)
48    {
49       /* Save callback params */
50       pfReceiveCB = LlcpMac->MacReceive_Cb;
51       pReceiveContext = LlcpMac->MacReceive_Context;
52 
53       /* Reset the pointer to the Receive Callback and Context*/
54       LlcpMac->MacReceive_Cb = NULL;
55       LlcpMac->MacReceive_Context = NULL;
56 
57       /* Call the receive callback */
58       pfReceiveCB(pReceiveContext, status, LlcpMac->psReceiveBuffer);
59    }
60 }
61 
phFriNfc_LlcpMac_Nfcip_TriggerSendCb(phFriNfc_LlcpMac_t * LlcpMac,NFCSTATUS status)62 static void phFriNfc_LlcpMac_Nfcip_TriggerSendCb(phFriNfc_LlcpMac_t  *LlcpMac,
63                                                  NFCSTATUS           status)
64 {
65    phFriNfc_LlcpMac_Send_CB_t pfSendCB;
66    void                       *pSendContext;
67 
68    if (LlcpMac->MacSend_Cb != NULL)
69    {
70       /* Save context in local variables */
71       pfSendCB     = LlcpMac->MacSend_Cb;
72       pSendContext = LlcpMac->MacSend_Context;
73 
74       /* Reset the pointer to the Send Callback */
75       LlcpMac->MacSend_Cb = NULL;
76       LlcpMac->MacSend_Context = NULL;
77 
78       /* Call Send callback */
79       pfSendCB(pSendContext, status);
80    }
81 }
82 
phFriNfc_LlcpMac_Nfcip_Chk(phFriNfc_LlcpMac_t * LlcpMac,phFriNfc_LlcpMac_Chk_CB_t ChkLlcpMac_Cb,void * pContext)83 static NFCSTATUS phFriNfc_LlcpMac_Nfcip_Chk(phFriNfc_LlcpMac_t                   *LlcpMac,
84                                             phFriNfc_LlcpMac_Chk_CB_t            ChkLlcpMac_Cb,
85                                             void                                 *pContext)
86 {
87    NFCSTATUS status = NFCSTATUS_SUCCESS;
88    uint8_t Llcp_Magic_Number[] = {0x46,0x66,0x6D};
89 
90    if(NULL == LlcpMac || NULL == ChkLlcpMac_Cb || NULL == pContext)
91    {
92       status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_INVALID_PARAMETER);
93    }
94    else
95    {
96       status = (NFCSTATUS)memcmp(Llcp_Magic_Number,LlcpMac->psRemoteDevInfo->RemoteDevInfo.NfcIP_Info.ATRInfo,3);
97       if(!status)
98       {
99          LlcpMac->sConfigParam.buffer = &LlcpMac->psRemoteDevInfo->RemoteDevInfo.NfcIP_Info.ATRInfo[3] ;
100          LlcpMac->sConfigParam.length = (LlcpMac->psRemoteDevInfo->RemoteDevInfo.NfcIP_Info.ATRInfo_Length - 3);
101          status = NFCSTATUS_SUCCESS;
102       }
103       else
104       {
105          status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_FAILED);
106       }
107    }
108 
109    ChkLlcpMac_Cb(pContext,status);
110    return status;
111 }
112 
phFriNfc_LlcpMac_Nfcip_Activate(phFriNfc_LlcpMac_t * LlcpMac)113 static NFCSTATUS phFriNfc_LlcpMac_Nfcip_Activate (phFriNfc_LlcpMac_t   *LlcpMac)
114 {
115    NFCSTATUS status  = NFCSTATUS_SUCCESS;
116 
117    if(LlcpMac == NULL)
118    {
119       status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_INVALID_PARAMETER);
120    }
121    else
122    {
123       LlcpMac->LinkState = phFriNfc_LlcpMac_eLinkActivated;
124       LlcpMac->LinkStatus_Cb(LlcpMac->LinkStatus_Context,
125                              LlcpMac->LinkState,
126                              &LlcpMac->sConfigParam,
127                              LlcpMac->PeerRemoteDevType);
128    }
129 
130    return status;
131 }
132 
phFriNfc_LlcpMac_Nfcip_Deactivate(phFriNfc_LlcpMac_t * LlcpMac)133 static NFCSTATUS phFriNfc_LlcpMac_Nfcip_Deactivate (phFriNfc_LlcpMac_t   *LlcpMac)
134 {
135    NFCSTATUS status  = NFCSTATUS_SUCCESS;
136 
137    if(NULL == LlcpMac)
138    {
139       status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_INVALID_PARAMETER);
140    }
141    else
142    {
143       /* Set the flag of LinkStatus to deactivate */
144       LlcpMac->LinkState = phFriNfc_LlcpMac_eLinkDeactivated;
145    }
146 
147    if (LlcpMac->SendPending)
148    {
149       /* Reset Flag */
150       LlcpMac->SendPending = FALSE;
151 
152       phFriNfc_LlcpMac_Nfcip_TriggerSendCb(LlcpMac, NFCSTATUS_FAILED);
153    }
154 
155    if (LlcpMac->RecvPending)
156    {
157       /* Reset Flag */
158       LlcpMac->RecvPending = FALSE;
159 
160       phFriNfc_LlcpMac_Nfcip_TriggerRecvCb(LlcpMac, NFCSTATUS_FAILED);
161    }
162 
163    LlcpMac->LinkStatus_Cb(LlcpMac->LinkStatus_Context,
164                           LlcpMac->LinkState,
165                           NULL,
166                           LlcpMac->PeerRemoteDevType);
167 
168    return status;
169 }
170 
phFriNfc_LlcpMac_Nfcip_Send_Cb(void * pContext,NFCSTATUS Status)171 static void phFriNfc_LlcpMac_Nfcip_Send_Cb(void       *pContext,
172                                            NFCSTATUS   Status)
173 {
174    phFriNfc_LlcpMac_t            *LlcpMac = (phFriNfc_LlcpMac_t *)pContext;
175 
176 #ifdef LLCP_CHANGES
177    if(gpphLibContext->LibNfcState.next_state
178                                == eLibNfcHalStateShutdown)
179    {
180       phLibNfc_Pending_Shutdown();
181       Status = NFCSTATUS_SHUTDOWN;
182    }
183 #endif /* #ifdef LLCP_CHANGES */
184 
185    /* Reset Send and Receive Flag */
186    LlcpMac->SendPending = FALSE;
187    LlcpMac->RecvPending = FALSE;
188 
189    phFriNfc_LlcpMac_Nfcip_TriggerSendCb(LlcpMac, Status);
190 
191 }
192 
phFriNfc_LlcpMac_Nfcip_Receive_Cb(void * pContext,NFCSTATUS Status)193 static void phFriNfc_LlcpMac_Nfcip_Receive_Cb(void       *pContext,
194                                               NFCSTATUS   Status)
195 {
196    phFriNfc_LlcpMac_t               *LlcpMac = (phFriNfc_LlcpMac_t *)pContext;
197 #ifdef LLCP_CHANGES
198 
199    phFriNfc_LlcpMac_Send_CB_t       pfSendCB;
200    void                             *pSendContext;
201 
202 
203    if(gpphLibContext->LibNfcState.next_state
204                                == eLibNfcHalStateShutdown)
205    {
206       phLibNfc_Pending_Shutdown();
207       Status = NFCSTATUS_SHUTDOWN;
208    }
209 
210    if (NFCSTATUS_SHUTDOWN == Status)
211    {
212       /* Save context in local variables */
213       pfSendCB = LlcpMac->MacSend_Cb;
214       pSendContext = LlcpMac->MacSend_Context;
215 
216       /* Reset the pointer to the Send Callback */
217       LlcpMac->MacSend_Cb = NULL;
218       LlcpMac->MacSend_Context = NULL;
219 
220       /* Reset Send and Receive Flag */
221       LlcpMac->SendPending = FALSE;
222       LlcpMac->RecvPending = FALSE;
223    }
224 
225 #endif /* #ifdef LLCP_CHANGES */
226 
227    phFriNfc_LlcpMac_Nfcip_TriggerRecvCb(LlcpMac, Status);
228 
229 #ifdef LLCP_CHANGES
230 
231    if (NFCSTATUS_SHUTDOWN == Status)
232    {
233        if ((LlcpMac->SendPending) && (NULL != pfSendCB))
234        {
235            pfSendCB(pSendContext, Status);
236       }
237    }
238    else
239 
240 #endif /* #ifdef LLCP_CHANGES */
241    {
242    /* Test if a send is pending */
243    if(LlcpMac->SendPending)
244    {
245       Status = phFriNfc_LlcpMac_Nfcip_Send(LlcpMac,LlcpMac->psSendBuffer,LlcpMac->MacSend_Cb,LlcpMac->MacSend_Context);
246    }
247 }
248 }
249 
phFriNfc_LlcpMac_Nfcip_Transceive_Cb(void * pContext,NFCSTATUS Status)250 static void phFriNfc_LlcpMac_Nfcip_Transceive_Cb(void       *pContext,
251                                                  NFCSTATUS   Status)
252 {
253    phFriNfc_LlcpMac_t               *LlcpMac = (phFriNfc_LlcpMac_t *)pContext;
254 
255 #ifdef LLCP_CHANGES
256    if(gpphLibContext->LibNfcState.next_state
257                                == eLibNfcHalStateShutdown)
258    {
259       phLibNfc_Pending_Shutdown();
260       Status = NFCSTATUS_SHUTDOWN;
261    }
262 #endif /* #ifdef LLCP_CHANGES */
263 
264    /* Reset Send and Receive Flag */
265    LlcpMac->SendPending = FALSE;
266    LlcpMac->RecvPending = FALSE;
267 
268    /* Call the callbacks */
269    phFriNfc_LlcpMac_Nfcip_TriggerSendCb(LlcpMac, Status);
270    phFriNfc_LlcpMac_Nfcip_TriggerRecvCb(LlcpMac, Status);
271 }
272 
phFriNfc_LlcpMac_Nfcip_Send(phFriNfc_LlcpMac_t * LlcpMac,phNfc_sData_t * psData,phFriNfc_LlcpMac_Send_CB_t LlcpMacSend_Cb,void * pContext)273 static NFCSTATUS phFriNfc_LlcpMac_Nfcip_Send(phFriNfc_LlcpMac_t               *LlcpMac,
274                                              phNfc_sData_t                    *psData,
275                                              phFriNfc_LlcpMac_Send_CB_t       LlcpMacSend_Cb,
276                                              void                             *pContext)
277 {
278    NFCSTATUS status = NFCSTATUS_SUCCESS;
279 
280    if(NULL == LlcpMac || NULL == psData || NULL == LlcpMacSend_Cb || NULL == pContext)
281    {
282       status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_INVALID_PARAMETER);
283    }
284    else if(LlcpMac->MacSend_Cb != NULL && LlcpMac->PeerRemoteDevType == phFriNfc_LlcpMac_ePeerTypeInitiator)
285    {
286       /*Previous callback is pending */
287       status = NFCSTATUS_REJECTED;
288    }
289    else
290    {
291       /* Save the LlcpMacSend_Cb */
292       LlcpMac->MacSend_Cb = LlcpMacSend_Cb;
293       LlcpMac->MacSend_Context = pContext;
294 
295       switch(LlcpMac->PeerRemoteDevType)
296       {
297       case phFriNfc_LlcpMac_ePeerTypeInitiator:
298          {
299             if(LlcpMac->RecvPending)
300             {
301                /*set the completion routines for the LLCP Transceive function*/
302                 LlcpMac->MacCompletionInfo.CompletionRoutine = phFriNfc_LlcpMac_Nfcip_Transceive_Cb;
303                 LlcpMac->MacCompletionInfo.Context = LlcpMac;
304 
305                 /* set the command type*/
306                 LlcpMac->Cmd.NfcIP1Cmd = phHal_eNfcIP1_Raw;
307 
308                 /* set the Additional Info*/
309                 LlcpMac->psDepAdditionalInfo.DepFlags.MetaChaining = 0;
310                 LlcpMac->psDepAdditionalInfo.DepFlags.NADPresent = 0;
311                 LlcpMac->SendPending = TRUE;
312 
313                 status = phFriNfc_OvrHal_Transceive(LlcpMac->LowerDevice,
314                                                     &LlcpMac->MacCompletionInfo,
315                                                     LlcpMac->psRemoteDevInfo,
316                                                     LlcpMac->Cmd,
317                                                     &LlcpMac->psDepAdditionalInfo,
318                                                     psData->buffer,
319                                                     (uint16_t)psData->length,
320                                                     LlcpMac->psReceiveBuffer->buffer,
321                                                     (uint16_t*)&LlcpMac->psReceiveBuffer->length);
322             }
323             else
324             {
325                LlcpMac->SendPending = TRUE;
326                LlcpMac->psSendBuffer = psData;
327                return status = NFCSTATUS_PENDING;
328             }
329          }break;
330       case phFriNfc_LlcpMac_ePeerTypeTarget:
331          {
332             if(!LlcpMac->RecvPending)
333             {
334                LlcpMac->SendPending = TRUE;
335                LlcpMac->psSendBuffer = psData;
336                return status = NFCSTATUS_PENDING;
337             }
338             else
339             {
340                /*set the completion routines for the LLCP Send function*/
341                LlcpMac->MacCompletionInfo.CompletionRoutine = phFriNfc_LlcpMac_Nfcip_Send_Cb;
342                LlcpMac->MacCompletionInfo.Context = LlcpMac;
343                status = phFriNfc_OvrHal_Send(LlcpMac->LowerDevice,
344                                              &LlcpMac->MacCompletionInfo,
345                                              LlcpMac->psRemoteDevInfo,
346                                              psData->buffer,
347                                              (uint16_t)psData->length);
348             }
349          }break;
350       default:
351          {
352             status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_INVALID_DEVICE);
353          }break;
354       }
355    }
356    return status;
357 }
358 
phFriNfc_LlcpMac_Nfcip_Receive(phFriNfc_LlcpMac_t * LlcpMac,phNfc_sData_t * psData,phFriNfc_LlcpMac_Reveive_CB_t LlcpMacReceive_Cb,void * pContext)359 static NFCSTATUS phFriNfc_LlcpMac_Nfcip_Receive(phFriNfc_LlcpMac_t               *LlcpMac,
360                                                 phNfc_sData_t                    *psData,
361                                                 phFriNfc_LlcpMac_Reveive_CB_t    LlcpMacReceive_Cb,
362                                                 void                             *pContext)
363 {
364    NFCSTATUS status = NFCSTATUS_SUCCESS;
365    if(NULL == LlcpMac || NULL==psData || NULL == LlcpMacReceive_Cb || NULL == pContext)
366    {
367       status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_INVALID_PARAMETER);
368    }
369    else if(LlcpMac->MacReceive_Cb != NULL)
370    {
371       /*Previous callback is pending */
372       status = NFCSTATUS_REJECTED;
373    }
374    else
375    {
376       /* Save the LlcpMacReceive_Cb */
377       LlcpMac->MacReceive_Cb = LlcpMacReceive_Cb;
378       LlcpMac->MacReceive_Context = pContext;
379 
380       /* Save the pointer to the receive buffer */
381       LlcpMac->psReceiveBuffer= psData;
382 
383       switch(LlcpMac->PeerRemoteDevType)
384       {
385       case phFriNfc_LlcpMac_ePeerTypeInitiator:
386          {
387             if(LlcpMac->SendPending)
388             {
389                /*set the completion routines for the LLCP Transceive function*/
390                LlcpMac->MacCompletionInfo.CompletionRoutine = phFriNfc_LlcpMac_Nfcip_Transceive_Cb;
391                LlcpMac->MacCompletionInfo.Context = LlcpMac;
392                /* set the command type*/
393                LlcpMac->Cmd.NfcIP1Cmd = phHal_eNfcIP1_Raw;
394                /* set the Additional Info*/
395                LlcpMac->psDepAdditionalInfo.DepFlags.MetaChaining = 0;
396                LlcpMac->psDepAdditionalInfo.DepFlags.NADPresent = 0;
397                LlcpMac->RecvPending = TRUE;
398 
399                status = phFriNfc_OvrHal_Transceive(LlcpMac->LowerDevice,
400                                                    &LlcpMac->MacCompletionInfo,
401                                                    LlcpMac->psRemoteDevInfo,
402                                                    LlcpMac->Cmd,
403                                                    &LlcpMac->psDepAdditionalInfo,
404                                                    LlcpMac->psSendBuffer->buffer,
405                                                    (uint16_t)LlcpMac->psSendBuffer->length,
406                                                    psData->buffer,
407                                                    (uint16_t*)&psData->length);
408             }
409             else
410             {
411                LlcpMac->RecvPending = TRUE;
412                return status = NFCSTATUS_PENDING;
413             }
414          }break;
415       case phFriNfc_LlcpMac_ePeerTypeTarget:
416          {
417              /*set the completion routines for the LLCP Receive function*/
418             LlcpMac->MacCompletionInfo.CompletionRoutine = phFriNfc_LlcpMac_Nfcip_Receive_Cb;
419             /* save the context of LlcpMacNfcip */
420             LlcpMac->MacCompletionInfo.Context = LlcpMac;
421             LlcpMac->RecvPending = TRUE;
422 
423             status = phFriNfc_OvrHal_Receive(LlcpMac->LowerDevice,
424                                              &LlcpMac->MacCompletionInfo,
425                                              LlcpMac->psRemoteDevInfo,
426                                              LlcpMac->psReceiveBuffer->buffer,
427                                              (uint16_t*)&LlcpMac->psReceiveBuffer->length);
428          }break;
429       default:
430          {
431             status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_INVALID_DEVICE);
432          }break;
433       }
434    }
435    return status;
436 }
437 
438 
phFriNfc_LlcpMac_Nfcip_Register(phFriNfc_LlcpMac_t * LlcpMac)439 NFCSTATUS phFriNfc_LlcpMac_Nfcip_Register (phFriNfc_LlcpMac_t *LlcpMac)
440 {
441    NFCSTATUS status = NFCSTATUS_SUCCESS;
442 
443    if(NULL != LlcpMac)
444    {
445       LlcpMac->LlcpMacInterface.chk = phFriNfc_LlcpMac_Nfcip_Chk;
446       LlcpMac->LlcpMacInterface.activate   = phFriNfc_LlcpMac_Nfcip_Activate;
447       LlcpMac->LlcpMacInterface.deactivate = phFriNfc_LlcpMac_Nfcip_Deactivate;
448       LlcpMac->LlcpMacInterface.send = phFriNfc_LlcpMac_Nfcip_Send;
449       LlcpMac->LlcpMacInterface.receive = phFriNfc_LlcpMac_Nfcip_Receive;
450 
451       return NFCSTATUS_SUCCESS;
452    }
453    else
454    {
455       return status = PHNFCSTVAL(CID_FRI_NFC_LLCP_MAC, NFCSTATUS_FAILED);
456    }
457 }
458