Home | History | Annotate | Download | only in src
      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 #include <phNfcTypes.h>
     18 #include <phLibNfc.h>
     19 #include <phLibNfc_Internal.h>
     20 #include <phFriNfc_Llcp.h>
     21 #include <phFriNfc_LlcpTransport.h>
     22 
     23 /* ---------------------------- Internal macros -------------------------------- */
     24 
     25 #ifndef STATIC_DISABLE
     26 #define STATIC static
     27 #else
     28 #define STATIC
     29 #endif
     30 
     31 /* ----------------------- Internal functions headers -------------------------- */
     32 
     33 STATIC
     34 NFCSTATUS static_CheckState();
     35 
     36 STATIC
     37 NFCSTATUS static_CheckDevice(phLibNfc_Handle hRemoteDevice);
     38 
     39 STATIC
     40 void phLibNfc_Llcp_CheckLlcp_Cb(void *pContext,NFCSTATUS status);
     41 
     42 STATIC
     43 void phLibNfc_Llcp_Link_Cb(void *pContext,phLibNfc_Llcp_eLinkStatus_t status);
     44 
     45 /* --------------------------- Internal functions ------------------------------ */
     46 
     47 STATIC NFCSTATUS static_CheckState()
     48 {
     49    /* Check if the global context is set */
     50    if(gpphLibContext == NULL)
     51    {
     52       return NFCSTATUS_NOT_INITIALISED;
     53    }
     54 
     55    /* Check if initialized */
     56    if(gpphLibContext->LibNfcState.cur_state == eLibNfcHalStateShutdown)
     57    {
     58       return NFCSTATUS_NOT_INITIALISED;
     59    }
     60 
     61    /* Check if shutting down */
     62    if(gpphLibContext->LibNfcState.next_state == eLibNfcHalStateShutdown)
     63    {
     64       return NFCSTATUS_SHUTDOWN;
     65    }
     66 
     67    return NFCSTATUS_SUCCESS;
     68 }
     69 
     70 STATIC NFCSTATUS static_CheckDevice(phLibNfc_Handle hRemoteDevice)
     71 {
     72    phLibNfc_sRemoteDevInformation_t*   psRemoteDevInfo = (phLibNfc_sRemoteDevInformation_t*)hRemoteDevice;
     73 
     74    if (hRemoteDevice == NULL)
     75    {
     76       return NFCSTATUS_INVALID_PARAMETER;
     77    }
     78 
     79    /* If local device is the Initiator (remote is Target),
     80     * check if connection is correct
     81     */
     82    if (psRemoteDevInfo->RemDevType == phHal_eNfcIP1_Target)
     83    {
     84       /* Check if any device connected */
     85       if(gpphLibContext->Connected_handle == 0)
     86       {
     87          return NFCSTATUS_TARGET_NOT_CONNECTED;
     88       }
     89 
     90       /* Check if handle corresponds to connected one */
     91       if(hRemoteDevice != gpphLibContext->Connected_handle)
     92       {
     93          return NFCSTATUS_INVALID_HANDLE;
     94       }
     95    }
     96 
     97    /* Check if previous callback is pending or if remote peer is not LLCP compliant */
     98    if ((gpphLibContext->status.GenCb_pending_status == TRUE) ||
     99             (gpphLibContext->llcp_cntx.bIsLlcp == FALSE))
    100    {
    101       return NFCSTATUS_REJECTED;
    102    }
    103 
    104    return NFCSTATUS_SUCCESS;
    105 }
    106 
    107 /* ---------------------------- Public functions ------------------------------- */
    108 
    109 NFCSTATUS phLibNfc_Mgt_SetLlcp_ConfigParams( phLibNfc_Llcp_sLinkParameters_t* pConfigInfo,
    110                                             pphLibNfc_RspCb_t                pConfigRspCb,
    111                                             void*                            pContext
    112                                             )
    113 {
    114    NFCSTATUS      result;
    115    phNfc_sData_t  sGeneralBytesBuffer;
    116    phLibNfc_sNfcIPCfg_t sNfcIPCfg;
    117    const uint8_t  pMagicBuffer[] = { 0x46, 0x66, 0x6D };
    118 
    119    /* State checking */
    120    result = static_CheckState();
    121    if (result != NFCSTATUS_SUCCESS)
    122    {
    123       return result;
    124    }
    125 
    126    /* Parameters checking */
    127    if ((pConfigInfo == NULL) || (pConfigRspCb == NULL))
    128    {
    129       return NFCSTATUS_INVALID_PARAMETER;
    130    }
    131 
    132    /* Save the config for later use */
    133    memcpy( &gpphLibContext->llcp_cntx.sLocalParams,
    134            pConfigInfo,
    135            sizeof(phLibNfc_Llcp_sLinkParameters_t) );
    136 
    137    /* Copy magic number in NFCIP General Bytes */
    138    memcpy(sNfcIPCfg.generalBytes, pMagicBuffer, sizeof(pMagicBuffer));
    139    sNfcIPCfg.generalBytesLength = sizeof(pMagicBuffer);
    140 
    141    /* Encode link parameters in TLV to configure P2P General Bytes */
    142    sGeneralBytesBuffer.buffer = sNfcIPCfg.generalBytes + sizeof(pMagicBuffer);
    143    sGeneralBytesBuffer.length = sizeof(sNfcIPCfg.generalBytes) - sizeof(pMagicBuffer);
    144    result = phFriNfc_Llcp_EncodeLinkParams( &sGeneralBytesBuffer,
    145                                             pConfigInfo,
    146                                             PHFRINFC_LLCP_VERSION);
    147    if (result != NFCSTATUS_SUCCESS)
    148    {
    149       return PHNFCSTATUS(result);
    150    }
    151    sNfcIPCfg.generalBytesLength += (uint8_t)sGeneralBytesBuffer.length;
    152 
    153    /* Set the P2P general bytes */
    154    result = phLibNfc_Mgt_SetP2P_ConfigParams(&sNfcIPCfg, pConfigRspCb, pContext);
    155    if (result != NFCSTATUS_PENDING)
    156    {
    157       return PHNFCSTATUS(result);
    158    }
    159 
    160    /* Resets the LLCP LLC component */
    161    result = phFriNfc_Llcp_Reset( &gpphLibContext->llcp_cntx.sLlcpContext,
    162                                  gpphLibContext->psOverHalCtxt,
    163                                  pConfigInfo,
    164                                  gpphLibContext->llcp_cntx.pRxBuffer,
    165                                  sizeof(gpphLibContext->llcp_cntx.pRxBuffer),
    166                                  gpphLibContext->llcp_cntx.pTxBuffer,
    167                                  sizeof(gpphLibContext->llcp_cntx.pTxBuffer),
    168                                  phLibNfc_Llcp_Link_Cb,
    169                                  gpphLibContext);
    170    if (result != NFCSTATUS_SUCCESS)
    171    {
    172       return PHNFCSTATUS(result);
    173    }
    174 
    175    /* Resets the LLCP Transport component */
    176    result = phFriNfc_LlcpTransport_Reset( &gpphLibContext->llcp_cntx.sLlcpTransportContext,
    177                                           &gpphLibContext->llcp_cntx.sLlcpContext );
    178    if (result != NFCSTATUS_SUCCESS)
    179    {
    180       return PHNFCSTATUS(result);
    181    }
    182 
    183    return NFCSTATUS_PENDING;
    184 }
    185 
    186 NFCSTATUS phLibNfc_Llcp_CheckLlcp( phLibNfc_Handle              hRemoteDevice,
    187                                    pphLibNfc_ChkLlcpRspCb_t     pCheckLlcp_RspCb,
    188                                    pphLibNfc_LlcpLinkStatusCb_t pLink_Cb,
    189                                    void*                        pContext
    190                                    )
    191 {
    192    NFCSTATUS                           result;
    193    phLibNfc_sRemoteDevInformation_t*   psRemoteDevInfo = (phLibNfc_sRemoteDevInformation_t*)hRemoteDevice;
    194 
    195    /* State checking */
    196    result = static_CheckState();
    197    if (result != NFCSTATUS_SUCCESS)
    198    {
    199       return result;
    200    }
    201 
    202    /* Parameters checking */
    203    if ((hRemoteDevice == 0)       ||
    204        (pCheckLlcp_RspCb == NULL) ||
    205        (pLink_Cb == NULL))
    206    {
    207       return NFCSTATUS_INVALID_PARAMETER;
    208    }
    209 
    210    /* If local device is the Initiator (remote is Target),
    211     * check if connection is correct
    212     */
    213    if (psRemoteDevInfo->RemDevType == phHal_eNfcIP1_Target)
    214    {
    215       /* Check if any device connected */
    216       if(gpphLibContext->Connected_handle == 0)
    217       {
    218          return NFCSTATUS_TARGET_NOT_CONNECTED;
    219       }
    220 
    221       /* Check if handle corresponds to connected one */
    222       if(hRemoteDevice != gpphLibContext->Connected_handle)
    223       {
    224          return NFCSTATUS_INVALID_HANDLE;
    225       }
    226    }
    227 
    228    /* Prepare callback */
    229    gpphLibContext->CBInfo.pClientLlcpLinkCb = pLink_Cb;
    230    gpphLibContext->CBInfo.pClientLlcpLinkCntx = pContext;
    231 
    232    // DEBUG: Reset at least the state
    233    gpphLibContext->llcp_cntx.sLlcpContext.state = 0;
    234 
    235    /* Prepare callback */
    236    gpphLibContext->CBInfo.pClientLlcpCheckRespCb = pCheckLlcp_RspCb;
    237    gpphLibContext->CBInfo.pClientLlcpCheckRespCntx = pContext;
    238 
    239    /* Update state */
    240    result = phLibNfc_UpdateNextState(gpphLibContext, eLibNfcHalStateTransaction);
    241    if (result != NFCSTATUS_SUCCESS)
    242    {
    243       return result;
    244    }
    245 
    246    /* Call the component function */
    247    result = phFriNfc_Llcp_ChkLlcp( &gpphLibContext->llcp_cntx.sLlcpContext,
    248                                    psRemoteDevInfo,
    249                                    phLibNfc_Llcp_CheckLlcp_Cb,
    250                                    gpphLibContext
    251                                    );
    252    result = PHNFCSTATUS(result);
    253    if (result == NFCSTATUS_PENDING)
    254    {
    255       gpphLibContext->status.GenCb_pending_status = TRUE;
    256    }
    257    else if (result == NFCSTATUS_SUCCESS)
    258    {
    259       /* Nothing to do */
    260    }
    261    else if (result != NFCSTATUS_FAILED)
    262    {
    263       result = NFCSTATUS_TARGET_LOST;
    264    }
    265 
    266    return result;
    267 }
    268 
    269 /* LLCP link callback */
    270 STATIC
    271 void phLibNfc_Llcp_Link_Cb(void *pContext, phLibNfc_Llcp_eLinkStatus_t status)
    272 {
    273    phLibNfc_LibContext_t         *pLibNfc_Ctxt = (phLibNfc_LibContext_t *)pContext;
    274    pphLibNfc_LlcpLinkStatusCb_t  pClientCb = NULL;
    275    void                          *pClientContext = NULL;
    276 
    277    if(pLibNfc_Ctxt != gpphLibContext)
    278    {
    279       /*wrong context returned from below layer*/
    280       phOsalNfc_RaiseException(phOsalNfc_e_InternalErr,1);
    281    }
    282    else
    283    {
    284       /* Close all sockets */
    285       phFriNfc_LlcpTransport_CloseAll(&gpphLibContext->llcp_cntx.sLlcpTransportContext);
    286 
    287       /* Copy callback details */
    288       pClientCb = gpphLibContext->CBInfo.pClientLlcpLinkCb;
    289       pClientContext = gpphLibContext->CBInfo.pClientLlcpLinkCntx;
    290 
    291       /* Trigger the callback */
    292       if(pClientCb != NULL)
    293       {
    294          pClientCb(pClientContext, status);
    295       }
    296    }
    297 }
    298 
    299 /* Response callback for phLibNfc_Ndef_CheckNdef */
    300 STATIC
    301 void phLibNfc_Llcp_CheckLlcp_Cb(void *pContext, NFCSTATUS status)
    302 {
    303    phLibNfc_LibContext_t      *pLibNfc_Ctxt = (phLibNfc_LibContext_t *)pContext;
    304    NFCSTATUS                  RetStatus = NFCSTATUS_SUCCESS;
    305    pphLibNfc_ChkLlcpRspCb_t   pClientCb = NULL;
    306    void                       *pClientContext = NULL;
    307 
    308    if(pLibNfc_Ctxt != gpphLibContext)
    309    {
    310       /*wrong context returned from below layer*/
    311       phOsalNfc_RaiseException(phOsalNfc_e_InternalErr,1);
    312    }
    313    else
    314    {
    315       if(gpphLibContext->LibNfcState.next_state == eLibNfcHalStateShutdown)
    316       {
    317          /*shutdown called before completion of check Ndef, allow shutdown to happen */
    318          phLibNfc_Pending_Shutdown();
    319          RetStatus = NFCSTATUS_SHUTDOWN;
    320       }
    321       else if(gpphLibContext->LibNfcState.next_state == eLibNfcHalStateRelease)
    322       {
    323          RetStatus = NFCSTATUS_ABORTED;
    324       }
    325       else
    326       {
    327          if(status == NFCSTATUS_SUCCESS)
    328          {
    329             /* Remote peer is LLCP compliant */
    330             gpphLibContext->llcp_cntx.bIsLlcp = TRUE;
    331          }
    332          else if(PHNFCSTATUS(status)== NFCSTATUS_FAILED)
    333          {
    334             RetStatus = NFCSTATUS_FAILED;
    335             gpphLibContext->llcp_cntx.bIsLlcp = FALSE;
    336          }
    337          else
    338          {
    339             RetStatus = NFCSTATUS_TARGET_LOST;
    340          }
    341       }
    342 
    343       /* Update the current state */
    344       gpphLibContext->status.GenCb_pending_status = FALSE;
    345       phLibNfc_UpdateCurState(RetStatus,gpphLibContext);
    346 
    347       /* Copy callback details */
    348       pClientCb = gpphLibContext->CBInfo.pClientLlcpCheckRespCb;
    349       pClientContext = gpphLibContext->CBInfo.pClientLlcpCheckRespCntx;
    350 
    351       /* Reset saved callback */
    352       gpphLibContext->CBInfo.pClientCkNdefCb = NULL;
    353       gpphLibContext->CBInfo.pClientCkNdefCntx = NULL;
    354 
    355       /* Trigger the callback */
    356       if(pClientCb != NULL)
    357       {
    358          pClientCb(pClientContext,RetStatus);
    359       }
    360    }
    361 }
    362 
    363 NFCSTATUS phLibNfc_Llcp_Activate( phLibNfc_Handle hRemoteDevice )
    364 {
    365    NFCSTATUS result;
    366 
    367    /* State checking */
    368    result = static_CheckState();
    369    if (result != NFCSTATUS_SUCCESS)
    370    {
    371       return result;
    372    }
    373 
    374    /* Parameters checking */
    375    if (hRemoteDevice == 0)
    376    {
    377       return NFCSTATUS_INVALID_PARAMETER;
    378    }
    379 
    380    /* Check device */
    381    result = static_CheckDevice(hRemoteDevice);
    382    if (result != NFCSTATUS_SUCCESS)
    383    {
    384       return result;
    385    }
    386 
    387    /* Start activation */
    388    result = phFriNfc_Llcp_Activate(&gpphLibContext->llcp_cntx.sLlcpContext);
    389 
    390    return PHNFCSTATUS(result);
    391 }
    392 
    393 NFCSTATUS phLibNfc_Llcp_Deactivate( phLibNfc_Handle  hRemoteDevice )
    394 {
    395    NFCSTATUS result;
    396 
    397    /* State checking */
    398    result = static_CheckState();
    399    if (result != NFCSTATUS_SUCCESS)
    400    {
    401       return result;
    402    }
    403 
    404    /* Parameters checking */
    405    if (hRemoteDevice == 0)
    406    {
    407       return NFCSTATUS_INVALID_PARAMETER;
    408    }
    409 
    410    /* Check device */
    411    result = static_CheckDevice(hRemoteDevice);
    412    if (result != NFCSTATUS_SUCCESS)
    413    {
    414       return result;
    415    }
    416 
    417    /* Start deactivation */
    418    result = phFriNfc_Llcp_Deactivate(&gpphLibContext->llcp_cntx.sLlcpContext);
    419 
    420    return PHNFCSTATUS(result);
    421 }
    422 
    423 NFCSTATUS phLibNfc_Llcp_GetLocalInfo( phLibNfc_Handle                  hRemoteDevice,
    424                                       phLibNfc_Llcp_sLinkParameters_t* pConfigInfo
    425                                       )
    426 {
    427    NFCSTATUS result;
    428 
    429    /* State checking */
    430    result = static_CheckState();
    431    if (result != NFCSTATUS_SUCCESS)
    432    {
    433       return result;
    434    }
    435 
    436    /* Parameters checking */
    437    if (pConfigInfo == NULL)
    438    {
    439       return NFCSTATUS_INVALID_PARAMETER;
    440    }
    441 
    442    /* Get local infos */
    443    result = phFriNfc_Llcp_GetLocalInfo(&gpphLibContext->llcp_cntx.sLlcpContext, pConfigInfo);
    444 
    445    return PHNFCSTATUS(result);
    446 }
    447 
    448 NFCSTATUS phLibNfc_Llcp_GetRemoteInfo( phLibNfc_Handle                    hRemoteDevice,
    449                                        phLibNfc_Llcp_sLinkParameters_t*   pConfigInfo
    450                                        )
    451 {
    452    NFCSTATUS result;
    453 
    454    /* State checking */
    455    result = static_CheckState();
    456    if (result != NFCSTATUS_SUCCESS)
    457    {
    458       return result;
    459    }
    460 
    461    /* Parameters checking */
    462    if ((hRemoteDevice == 0) ||
    463        (pConfigInfo == NULL))
    464    {
    465       return NFCSTATUS_INVALID_PARAMETER;
    466    }
    467 
    468    /* Check device */
    469    result = static_CheckDevice(hRemoteDevice);
    470    if (result != NFCSTATUS_SUCCESS)
    471    {
    472       return result;
    473    }
    474 
    475    /* Get local infos */
    476    result = phFriNfc_Llcp_GetRemoteInfo(&gpphLibContext->llcp_cntx.sLlcpContext, pConfigInfo);
    477 
    478    return PHNFCSTATUS(result);
    479 }
    480 
    481 NFCSTATUS phLibNfc_Llcp_DiscoverServices( phLibNfc_Handle     hRemoteDevice,
    482                                           phNfc_sData_t       *psServiceNameList,
    483                                           uint8_t             *pnSapList,
    484                                           uint8_t             nListSize,
    485                                           pphLibNfc_RspCb_t   pDiscover_Cb,
    486                                           void                *pContext
    487                                           )
    488 {
    489    NFCSTATUS                           result;
    490    PHNFC_UNUSED_VARIABLE(hRemoteDevice);
    491 
    492    /* State checking */
    493    result = static_CheckState();
    494    if (result != NFCSTATUS_SUCCESS)
    495    {
    496       return result;
    497    }
    498 
    499    /* Parameters checking */
    500    if ((hRemoteDevice == 0)       ||
    501        (psServiceNameList == NULL) ||
    502        (pnSapList == NULL) ||
    503        (nListSize == 0) ||
    504        (pDiscover_Cb == NULL))
    505    {
    506       return NFCSTATUS_INVALID_PARAMETER;
    507    }
    508 
    509    /* Check device */
    510    result = static_CheckDevice(hRemoteDevice);
    511    if (result != NFCSTATUS_SUCCESS)
    512    {
    513       return result;
    514    }
    515 
    516    /* Prepare callback */
    517    gpphLibContext->CBInfo.pClientLlcpDiscoveryCb = pDiscover_Cb;
    518    gpphLibContext->CBInfo.pClientLlcpDiscoveryCntx = pContext;
    519 
    520    /* Update state */
    521    result = phLibNfc_UpdateNextState(gpphLibContext, eLibNfcHalStateTransaction);
    522    if (result != NFCSTATUS_SUCCESS)
    523    {
    524       return result;
    525    }
    526 
    527    /* Call the component function */
    528    result = phFriNfc_LlcpTransport_DiscoverServices( &gpphLibContext->llcp_cntx.sLlcpTransportContext,
    529                                                      psServiceNameList,
    530                                                      pnSapList,
    531                                                      nListSize,
    532                                                      pDiscover_Cb,
    533                                                      pContext
    534                                                      );
    535    result = PHNFCSTATUS(result);
    536    if ((result == NFCSTATUS_PENDING) || (result == NFCSTATUS_SUCCESS))
    537    {
    538       /* Nothing to do */
    539    }
    540    else if (result != NFCSTATUS_FAILED)
    541    {
    542       result = NFCSTATUS_TARGET_LOST;
    543    }
    544 
    545    return result;
    546 }
    547 
    548 NFCSTATUS phLibNfc_Llcp_Socket( phLibNfc_Llcp_eSocketType_t      eType,
    549                                 phLibNfc_Llcp_sSocketOptions_t*  psOptions,
    550                                 phNfc_sData_t*                   psWorkingBuffer,
    551                                 phLibNfc_Handle*                 phSocket,
    552                                 pphLibNfc_LlcpSocketErrCb_t      pErr_Cb,
    553                                 void*                            pContext
    554                                 )
    555 {
    556    NFCSTATUS                        result;
    557    phFriNfc_LlcpTransport_Socket_t  *psSocket;
    558 
    559    /* State checking */
    560    result = static_CheckState();
    561    if (result != NFCSTATUS_SUCCESS)
    562    {
    563       return result;
    564    }
    565 
    566    /* Parameters checking */
    567    /* NOTE: Transport Layer test psOption and psWorkingBuffer value */
    568    if ((phSocket == NULL)        ||
    569        (pErr_Cb == NULL))
    570    {
    571       return NFCSTATUS_INVALID_PARAMETER;
    572    }
    573 
    574    /* Get local infos */
    575    result = phFriNfc_LlcpTransport_Socket(&gpphLibContext->llcp_cntx.sLlcpTransportContext,
    576                                           eType,
    577                                           psOptions,
    578                                           psWorkingBuffer,
    579                                           &psSocket,
    580                                           pErr_Cb,
    581                                           pContext);
    582 
    583    /* Send back the socket handle */
    584    *phSocket = (phLibNfc_Handle)psSocket;
    585 
    586    return PHNFCSTATUS(result);
    587 }
    588 
    589 NFCSTATUS phLibNfc_Llcp_Close( phLibNfc_Handle hSocket )
    590 {
    591    NFCSTATUS                        result;
    592    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    593 
    594    /* State checking */
    595    result = static_CheckState();
    596    if (result != NFCSTATUS_SUCCESS)
    597    {
    598       return result;
    599    }
    600 
    601    /* Parameters checking */
    602    if (hSocket == 0)
    603    {
    604       return NFCSTATUS_INVALID_PARAMETER;
    605    }
    606 
    607    /* Get local infos */
    608    /* TODO: if connected abort and close else close only */
    609    result = phFriNfc_LlcpTransport_Close(psSocket);
    610 
    611    return PHNFCSTATUS(result);
    612 }
    613 
    614 NFCSTATUS phLibNfc_Llcp_SocketGetLocalOptions( phLibNfc_Handle                  hSocket,
    615                                                phLibNfc_Llcp_sSocketOptions_t*  psLocalOptions
    616                                                )
    617 {
    618    NFCSTATUS                        result;
    619    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    620 
    621    /* State checking */
    622    result = static_CheckState();
    623    if (result != NFCSTATUS_SUCCESS)
    624    {
    625       return result;
    626    }
    627 
    628    /* Parameters checking */
    629    if ((hSocket == 0) ||
    630        (psLocalOptions == NULL))
    631    {
    632       return NFCSTATUS_INVALID_PARAMETER;
    633    }
    634 
    635    /* Get local options */
    636    result = phFriNfc_LlcpTransport_SocketGetLocalOptions(psSocket, psLocalOptions);
    637 
    638    return PHNFCSTATUS(result);
    639 }
    640 
    641 NFCSTATUS phLibNfc_Llcp_SocketGetRemoteOptions( phLibNfc_Handle                  hRemoteDevice,
    642                                                 phLibNfc_Handle                  hSocket,
    643                                                 phLibNfc_Llcp_sSocketOptions_t*  psRemoteOptions
    644                                                 )
    645 {
    646    NFCSTATUS                        result;
    647    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    648 
    649    LLCP_PRINT("phLibNfc_Llcp_SocketGetRemoteOptions");
    650 
    651    /* State checking */
    652    result = static_CheckState();
    653    if (result != NFCSTATUS_SUCCESS)
    654    {
    655       return result;
    656    }
    657 
    658    /* Parameters checking */
    659    if ((hRemoteDevice == 0) ||
    660        (hSocket == 0)       ||
    661        (psRemoteOptions == NULL))
    662    {
    663       return NFCSTATUS_INVALID_PARAMETER;
    664    }
    665 
    666    /* Check device */
    667    result = static_CheckDevice(hRemoteDevice);
    668    if (result != NFCSTATUS_SUCCESS)
    669    {
    670       return result;
    671    }
    672 
    673    /* Get remote infos */
    674    result = phFriNfc_LlcpTransport_SocketGetRemoteOptions(psSocket, psRemoteOptions);
    675 
    676    return PHNFCSTATUS(result);
    677 }
    678 
    679 NFCSTATUS phLibNfc_Llcp_Bind( phLibNfc_Handle hSocket,
    680                               uint8_t         nSap,
    681                               phNfc_sData_t * psServiceName
    682                               )
    683 {
    684    NFCSTATUS                        result;
    685    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    686 
    687    LLCP_PRINT("phLibNfc_Llcp_Bind");
    688 
    689    /* State checking */
    690    result = static_CheckState();
    691    if (result != NFCSTATUS_SUCCESS)
    692    {
    693       return result;
    694    }
    695 
    696    /* Parameters checking */
    697    if (hSocket == 0)
    698    {
    699       return NFCSTATUS_INVALID_PARAMETER;
    700    }
    701 
    702    /* Bind the socket to the designated port */
    703    result = phFriNfc_LlcpTransport_Bind(psSocket, nSap, psServiceName);
    704 
    705    return PHNFCSTATUS(result);
    706 }
    707 
    708 NFCSTATUS phLibNfc_Llcp_Listen( phLibNfc_Handle                  hSocket,
    709                                 pphLibNfc_LlcpSocketListenCb_t   pListen_Cb,
    710                                 void*                            pContext
    711                                 )
    712 {
    713    NFCSTATUS                        result;
    714    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    715 
    716    LLCP_PRINT("phLibNfc_Llcp_Listen");
    717 
    718    /* State checking */
    719    result = static_CheckState();
    720    if (result != NFCSTATUS_SUCCESS)
    721    {
    722       return result;
    723    }
    724 
    725    /* Parameters checking */
    726    /* NOTE : psServiceName may be NULL, do not test it ! */
    727    if ((hSocket == 0) ||
    728        (pListen_Cb == NULL))
    729    {
    730       return NFCSTATUS_INVALID_PARAMETER;
    731    }
    732 
    733    /* Start listening for incoming connections */
    734    result = phFriNfc_LlcpTransport_Listen( psSocket,
    735                                            (pphFriNfc_LlcpTransportSocketListenCb_t)pListen_Cb,
    736                                            pContext );
    737 
    738    return PHNFCSTATUS(result);
    739 }
    740 
    741 NFCSTATUS phLibNfc_Llcp_Accept( phLibNfc_Handle                  hSocket,
    742                                 phLibNfc_Llcp_sSocketOptions_t*  psOptions,
    743                                 phNfc_sData_t*                   psWorkingBuffer,
    744                                 pphLibNfc_LlcpSocketErrCb_t      pErr_Cb,
    745                                 pphLibNfc_LlcpSocketAcceptCb_t   pAccept_RspCb,
    746                                 void*                            pContext
    747                                 )
    748 {
    749    NFCSTATUS                        result;
    750    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    751 
    752    LLCP_PRINT("phLibNfc_Llcp_Accept");
    753 
    754    /* State checking */
    755    result = static_CheckState();
    756    if (result != NFCSTATUS_SUCCESS)
    757    {
    758       return result;
    759    }
    760 
    761    /* Parameters checking */
    762    if ((hSocket == 0)            ||
    763        (psOptions == NULL)       ||
    764        (psWorkingBuffer == NULL) ||
    765        (pErr_Cb == NULL)         ||
    766        (pAccept_RspCb == NULL))
    767    {
    768       return NFCSTATUS_INVALID_PARAMETER;
    769    }
    770 
    771    /* Accept incoming connection */
    772    result = phFriNfc_LlcpTransport_Accept( psSocket,
    773                                            psOptions,
    774                                            psWorkingBuffer,
    775                                            pErr_Cb,
    776                                            pAccept_RspCb,
    777                                            pContext );
    778 
    779    return PHNFCSTATUS(result);
    780 }
    781 
    782 NFCSTATUS phLibNfc_Llcp_Reject( phLibNfc_Handle                  hRemoteDevice,
    783                                 phLibNfc_Handle                  hSocket,
    784                                 pphLibNfc_LlcpSocketRejectCb_t   pReject_RspCb,
    785                                 void*                            pContext
    786                                 )
    787 {
    788    NFCSTATUS                        result;
    789    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    790 
    791    LLCP_PRINT("phLibNfc_Llcp_Reject");
    792 
    793    /* State checking */
    794    result = static_CheckState();
    795    if (result != NFCSTATUS_SUCCESS)
    796    {
    797       return result;
    798    }
    799 
    800    /* Parameters checking */
    801    if ((hRemoteDevice == 0)      ||
    802        (hSocket == 0)            ||
    803        (pReject_RspCb == NULL))
    804    {
    805       return NFCSTATUS_INVALID_PARAMETER;
    806    }
    807 
    808    /* Check device */
    809    result = static_CheckDevice(hRemoteDevice);
    810    if (result != NFCSTATUS_SUCCESS)
    811    {
    812       return result;
    813    }
    814 
    815    /* Reject incoming connection */
    816    result = phFriNfc_LlcpTransport_Reject( psSocket,
    817                                            pReject_RspCb,
    818                                            pContext );
    819 
    820    return PHNFCSTATUS(result);
    821 }
    822 
    823 NFCSTATUS phLibNfc_Llcp_Connect( phLibNfc_Handle                 hRemoteDevice,
    824                                  phLibNfc_Handle                 hSocket,
    825                                  uint8_t                         nSap,
    826                                  pphLibNfc_LlcpSocketConnectCb_t pConnect_RspCb,
    827                                  void*                           pContext
    828                                  )
    829 {
    830    NFCSTATUS                        result;
    831    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    832 
    833    LLCP_PRINT("phLibNfc_Llcp_Connect");
    834 
    835    /* State checking */
    836    result = static_CheckState();
    837    if (result != NFCSTATUS_SUCCESS)
    838    {
    839       return result;
    840    }
    841 
    842    /* Parameters checking */
    843    if ((hRemoteDevice == 0)      ||
    844 	   (hSocket == 0)            ||
    845        (pConnect_RspCb == NULL))
    846    {
    847       LLCP_PRINT("phLibNfc_Llcp_Connect NFCSTATUS_INVALID_PARAMETER");
    848       return NFCSTATUS_INVALID_PARAMETER;
    849    }
    850 
    851    /* Check device */
    852    result = static_CheckDevice(hRemoteDevice);
    853    if (result != NFCSTATUS_SUCCESS)
    854    {
    855       return result;
    856    }
    857 
    858    /* Try to connect on a remote service, given its SAP */
    859    result = phFriNfc_LlcpTransport_Connect( psSocket,
    860                                             nSap,
    861                                             pConnect_RspCb,
    862                                             pContext );
    863 
    864    return PHNFCSTATUS(result);
    865 }
    866 
    867 NFCSTATUS phLibNfc_Llcp_ConnectByUri( phLibNfc_Handle                 hRemoteDevice,
    868                                       phLibNfc_Handle                 hSocket,
    869                                       phNfc_sData_t*                  psUri,
    870                                       pphLibNfc_LlcpSocketConnectCb_t pConnect_RspCb,
    871                                       void*                           pContext
    872                                       )
    873 {
    874    NFCSTATUS                        result;
    875    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    876 
    877    LLCP_PRINT("phLibNfc_Llcp_ConnectByUri");
    878 
    879    /* State checking */
    880    result = static_CheckState();
    881    if (result != NFCSTATUS_SUCCESS)
    882    {
    883       return result;
    884    }
    885 
    886    /* Parameters checking */
    887    if ((hRemoteDevice == 0)      ||
    888        (hSocket == 0)            ||
    889        (psUri   == NULL)         ||
    890        (pConnect_RspCb == NULL))
    891    {
    892       LLCP_PRINT("phLibNfc_Llcp_ConnectByUri NFCSTATUS_INVALID_PARAMETER");
    893       return NFCSTATUS_INVALID_PARAMETER;
    894    }
    895 
    896    /* Check device */
    897    result = static_CheckDevice(hRemoteDevice);
    898    if (result != NFCSTATUS_SUCCESS)
    899    {
    900       return result;
    901    }
    902 
    903    /* Try to connect on a remote service, using SDP */
    904    result = phFriNfc_LlcpTransport_ConnectByUri( psSocket,
    905                                                  psUri,
    906                                                  pConnect_RspCb,
    907                                                  pContext );
    908 
    909    return PHNFCSTATUS(result);
    910 }
    911 
    912 NFCSTATUS phLibNfc_Llcp_Disconnect( phLibNfc_Handle                    hRemoteDevice,
    913                                     phLibNfc_Handle                    hSocket,
    914                                     pphLibNfc_LlcpSocketDisconnectCb_t pDisconnect_RspCb,
    915                                     void*                              pContext
    916                                     )
    917 {
    918    NFCSTATUS                        result;
    919    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    920 
    921    LLCP_PRINT("phLibNfc_Llcp_Disconnect");
    922 
    923    /* State checking */
    924    result = static_CheckState();
    925    if (result != NFCSTATUS_SUCCESS)
    926    {
    927       return result;
    928    }
    929 
    930    /* Parameters checking */
    931    if ((hRemoteDevice == 0) ||
    932        (hSocket == 0)       ||
    933        (pDisconnect_RspCb == NULL))
    934    {
    935       return NFCSTATUS_INVALID_PARAMETER;
    936    }
    937 
    938    /* Check device */
    939    result = static_CheckDevice(hRemoteDevice);
    940    if (result != NFCSTATUS_SUCCESS)
    941    {
    942       return result;
    943    }
    944 
    945    /* Disconnect a logical link */
    946    result = phFriNfc_LlcpTransport_Disconnect( psSocket,
    947                                                pDisconnect_RspCb,
    948                                                pContext );
    949 
    950    return PHNFCSTATUS(result);
    951 }
    952 
    953 NFCSTATUS phLibNfc_Llcp_Recv( phLibNfc_Handle              hRemoteDevice,
    954                               phLibNfc_Handle              hSocket,
    955                               phNfc_sData_t*               psBuffer,
    956                               pphLibNfc_LlcpSocketRecvCb_t pRecv_RspCb,
    957                               void*                        pContext
    958                               )
    959 {
    960    NFCSTATUS                        result;
    961    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
    962 
    963    LLCP_PRINT("phLibNfc_Llcp_Recv");
    964 
    965    /* State checking */
    966    result = static_CheckState();
    967    if (result != NFCSTATUS_SUCCESS)
    968    {
    969       return result;
    970    }
    971 
    972    /* Parameters checking */
    973    if ((hRemoteDevice == 0)   ||
    974        (hSocket == 0)         ||
    975        (psBuffer == NULL)     ||
    976        (pRecv_RspCb == NULL))
    977    {
    978       return NFCSTATUS_INVALID_PARAMETER;
    979    }
    980 
    981    /* Check device */
    982    result = static_CheckDevice(hRemoteDevice);
    983    if (result != NFCSTATUS_SUCCESS)
    984    {
    985       return result;
    986    }
    987 
    988    /* Receive data from the logical link */
    989    result = phFriNfc_LlcpTransport_Recv( psSocket,
    990                                          psBuffer,
    991                                          pRecv_RspCb,
    992                                          pContext );
    993 
    994    return PHNFCSTATUS(result);
    995 }
    996 
    997 NFCSTATUS phLibNfc_Llcp_RecvFrom( phLibNfc_Handle                   hRemoteDevice,
    998                                   phLibNfc_Handle                   hSocket,
    999                                   phNfc_sData_t*                    psBuffer,
   1000                                   pphLibNfc_LlcpSocketRecvFromCb_t  pRecv_Cb,
   1001                                   void*                             pContext
   1002                                   )
   1003 {
   1004    NFCSTATUS                        result;
   1005    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
   1006 
   1007    LLCP_PRINT("phLibNfc_Llcp_RecvFrom");
   1008 
   1009    /* State checking */
   1010    result = static_CheckState();
   1011    if (result != NFCSTATUS_SUCCESS)
   1012    {
   1013       return result;
   1014    }
   1015 
   1016    /* Parameters checking */
   1017    if ((hRemoteDevice == 0)   ||
   1018        (hSocket == 0)         ||
   1019        (psBuffer == NULL)     ||
   1020        (pRecv_Cb == NULL))
   1021    {
   1022       return NFCSTATUS_INVALID_PARAMETER;
   1023    }
   1024 
   1025    /* Check device */
   1026    result = static_CheckDevice(hRemoteDevice);
   1027    if (result != NFCSTATUS_SUCCESS)
   1028    {
   1029       return result;
   1030    }
   1031 
   1032    /* Receive data from the logical link */
   1033    result = phFriNfc_LlcpTransport_RecvFrom( psSocket,
   1034                                              psBuffer,
   1035                                              pRecv_Cb,
   1036                                              pContext );
   1037 
   1038    return PHNFCSTATUS(result);
   1039 }
   1040 
   1041 NFCSTATUS phLibNfc_Llcp_Send( phLibNfc_Handle              hRemoteDevice,
   1042                               phLibNfc_Handle              hSocket,
   1043                               phNfc_sData_t*               psBuffer,
   1044                               pphLibNfc_LlcpSocketSendCb_t pSend_RspCb,
   1045                               void*                        pContext
   1046                               )
   1047 {
   1048    NFCSTATUS                        result;
   1049    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
   1050 
   1051    LLCP_PRINT("phLibNfc_Llcp_Send");
   1052 
   1053    /* State checking */
   1054    result = static_CheckState();
   1055    if (result != NFCSTATUS_SUCCESS)
   1056    {
   1057       return result;
   1058    }
   1059 
   1060    /* Parameters checking */
   1061    if ((hRemoteDevice == 0)   ||
   1062        (hSocket == 0)         ||
   1063        (psBuffer == NULL)     ||
   1064        (pSend_RspCb == NULL))
   1065    {
   1066       return NFCSTATUS_INVALID_PARAMETER;
   1067    }
   1068 
   1069    /* Check device */
   1070    result = static_CheckDevice(hRemoteDevice);
   1071    if (result != NFCSTATUS_SUCCESS)
   1072    {
   1073       return result;
   1074    }
   1075 
   1076    /* Send data to the logical link */
   1077    result = phFriNfc_LlcpTransport_Send( psSocket,
   1078                                          psBuffer,
   1079                                          pSend_RspCb,
   1080                                          pContext );
   1081 
   1082    return PHNFCSTATUS(result);
   1083 }
   1084 
   1085 NFCSTATUS phLibNfc_Llcp_SendTo( phLibNfc_Handle               hRemoteDevice,
   1086                                 phLibNfc_Handle               hSocket,
   1087                                 uint8_t                       nSap,
   1088                                 phNfc_sData_t*                psBuffer,
   1089                                 pphLibNfc_LlcpSocketSendCb_t  pSend_RspCb,
   1090                                 void*                         pContext
   1091                                 )
   1092 {
   1093    NFCSTATUS                        result;
   1094    phFriNfc_LlcpTransport_Socket_t  *psSocket = (phFriNfc_LlcpTransport_Socket_t*)hSocket;
   1095 
   1096    LLCP_PRINT("phLibNfc_Llcp_SendTo");
   1097 
   1098    /* State checking */
   1099    result = static_CheckState();
   1100    if (result != NFCSTATUS_SUCCESS)
   1101    {
   1102       return result;
   1103    }
   1104 
   1105    /* Parameters checking */
   1106    if ((hRemoteDevice == 0)   ||
   1107        (hSocket == 0)         ||
   1108        (psBuffer == NULL)     ||
   1109        (pSend_RspCb == NULL))
   1110    {
   1111       return NFCSTATUS_INVALID_PARAMETER;
   1112    }
   1113 
   1114    /* Check device */
   1115    result = static_CheckDevice(hRemoteDevice);
   1116    if (result != NFCSTATUS_SUCCESS)
   1117    {
   1118       return result;
   1119    }
   1120 
   1121    /* Send data to the logical link */
   1122    result = phFriNfc_LlcpTransport_SendTo( psSocket,
   1123                                            nSap,
   1124                                            psBuffer,
   1125                                            pSend_RspCb,
   1126                                            pContext );
   1127 
   1128    return PHNFCSTATUS(result);
   1129 }
   1130