summaryrefslogtreecommitdiffstats
path: root/Linux_x86
diff options
context:
space:
mode:
authorNick Pelly <npelly@google.com>2010-09-23 12:47:58 -0700
committerNick Pelly <npelly@google.com>2010-09-23 13:53:18 -0700
commit5d9927ba30ba449badb9f6df0fbeb4d6aedc6e2a (patch)
tree190f9251c6db03d3550ec7f30b51a2561c01d9cf /Linux_x86
parent4ff7c86a2c706b150078274455406f1b04966e1a (diff)
downloadexternal_libnfc-nxp-5d9927ba30ba449badb9f6df0fbeb4d6aedc6e2a.zip
external_libnfc-nxp-5d9927ba30ba449badb9f6df0fbeb4d6aedc6e2a.tar.gz
external_libnfc-nxp-5d9927ba30ba449badb9f6df0fbeb4d6aedc6e2a.tar.bz2
Initial libnfc checkin
Source: Trusted_NFC_Device_Host_AA03.01e02_google.zip code drop (23-Sep-2010) Change-Id: Ie47f18423f949a8d3e0815d13f55c814312add24 Signed-off-by: Nick Pelly <npelly@google.com>
Diffstat (limited to 'Linux_x86')
-rw-r--r--Linux_x86/phDal4Nfc.c1116
-rw-r--r--Linux_x86/phDal4Nfc_debug.h42
-rw-r--r--Linux_x86/phDal4Nfc_i2c.c226
-rw-r--r--Linux_x86/phDal4Nfc_i2c.h39
-rw-r--r--Linux_x86/phDal4Nfc_link.h56
-rw-r--r--Linux_x86/phDal4Nfc_messageQueueLib.c218
-rw-r--r--Linux_x86/phDal4Nfc_uart.c326
-rw-r--r--Linux_x86/phDal4Nfc_uart.h43
-rw-r--r--Linux_x86/phOsalNfc.c165
-rw-r--r--Linux_x86/phOsalNfc_Common.h78
-rw-r--r--Linux_x86/phOsalNfc_Timer.c273
-rw-r--r--Linux_x86/phOsalNfc_Utils.c57
12 files changed, 2639 insertions, 0 deletions
diff --git a/Linux_x86/phDal4Nfc.c b/Linux_x86/phDal4Nfc.c
new file mode 100644
index 0000000..7683c39
--- /dev/null
+++ b/Linux_x86/phDal4Nfc.c
@@ -0,0 +1,1116 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phDalNfc.c
+ * \brief DAL Implementation for linux
+ *
+ * Project: Trusted NFC Linux Lignt
+ *
+ * $Date: 07 aug 2009
+ * $Author: Jonathan roux
+ * $Revision: 1.0 $
+ *
+ */
+
+#define _DAL_4_NFC_C
+
+#include <unistd.h>
+#include <pthread.h>
+#ifdef ANDROID
+#include <linux/ipc.h>
+#else
+#include <sys/msg.h>
+#endif
+
+#include <phDal4Nfc.h>
+#include <phOsalNfc.h>
+#include <phNfcStatus.h>
+#include <phDal4Nfc_DeferredCall.h>
+#include <phDal4Nfc_debug.h>
+#include <phDal4Nfc_uart.h>
+#include <phDal4Nfc_i2c.h>
+#include <phDal4Nfc_link.h>
+#include <phDal4Nfc_messageQueueLib.h>
+
+/*-----------------------------------------------------------------------------------
+ MISC DEFINITIONS
+------------------------------------------------------------------------------------*/
+#define DEFAULT_LINK_TYPE ENUM_DAL_LINK_TYPE_COM1
+
+/*-----------------------------------------------------------------------------------
+ TYPES
+------------------------------------------------------------------------------------*/
+/*structure holds members related for both read and write operations*/
+typedef struct Dal_RdWr_st
+{
+ /* Read members */
+ pthread_t nReadThread; /* Read thread Hanlde */
+ pthread_mutex_t nReadEventMutex; /* Mutex to signal a read has been requested */
+ uint8_t * pReadBuffer; /* Read local buffer */
+ int nNbOfBytesToRead; /* Number of bytes to read */
+ int nNbOfBytesRead; /* Number of read bytes */
+ char nReadBusy; /* Read state machine */
+ char nReadThreadAlive; /* Read state machine */
+ char nWaitingOnRead; /* Read state machine */
+
+ /* Read wait members */
+ pthread_mutex_t nReadCancelEventMutex; /* Mutex to signal a read cancel has been requested */
+ uint8_t * pReadWaitBuffer; /* Read wait local Buffer */
+ int nNbOfBytesToReadWait; /* Number of bytes to read */
+ int nNbOfBytesReadWait; /* Number of read bytes */
+ char nReadWaitBusy; /* Read state machine */
+ char nWaitingOnReadWait; /* Read state machine */
+ char nCancelReadWait; /* Read state machine */
+
+ /* Write members */
+ pthread_t nWriteThread; /* Write thread Hanlde */
+ pthread_mutex_t nWriteEventMutex; /* Mutex to signal a write has been requested */
+ uint8_t * pWriteBuffer; /* Write local buffer */
+ int nNbOfBytesToWrite; /* Number of bytes to write */
+ int nNbOfBytesWritten; /* Number of bytes written */
+ char nWaitingOnWrite; /* Write state machine */
+ char nWriteThreadAlive; /* Write state machine */
+ char nWriteBusy; /* Write state machine */
+} phDal4Nfc_RdWr_t;
+
+typedef void (*pphDal4Nfc_DeferFuncPointer_t) (void * );
+typedef void * (*pphDal4Nfc_thread_handler_t) (void * pParam);
+
+
+/*-----------------------------------------------------------------------------------
+ VARIABLES
+------------------------------------------------------------------------------------*/
+static phDal4Nfc_RdWr_t gReadWriteContext;
+static phDal4Nfc_SContext_t gDalContext;
+static pphDal4Nfc_SContext_t pgDalContext;
+static phHal_sHwReference_t * pgDalHwContext;
+static pthread_mutex_t nCriticalSectionMutex;
+static pthread_mutex_t nThreadsEventMutex;
+#ifdef USE_MQ_MESSAGE_QUEUE
+static phDal4Nfc_DeferredCall_Msg_t nDeferedMessage;
+static mqd_t nDeferedCallMessageQueueId;
+
+#else
+int nDeferedCallMessageQueueId = 0;
+#endif
+static phDal4Nfc_link_cbk_interface_t gLinkFunc;
+/*-----------------------------------------------------------------------------------
+ PROTOTYPES
+------------------------------------------------------------------------------------*/
+static void phDal4Nfc_DeferredCb (void *params);
+static NFCSTATUS phDal4Nfc_StartThreads (void);
+static void phDal4Nfc_FillMsg (phDal4Nfc_Message_t *pDalMsg, phOsalNfc_Message_t *pOsalMsg);
+
+/*-----------------------------------------------------------------------------------
+ DAL API IMPLEMENTATION
+------------------------------------------------------------------------------------*/
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_Register
+
+PURPOSE: DAL register function.
+
+-----------------------------------------------------------------------------*/
+NFCSTATUS phDal4Nfc_Register( phNfcIF_sReference_t *psRefer,
+ phNfcIF_sCallBack_t if_cb, void *psIFConf )
+{
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+
+ if ((NULL != psRefer) &&
+ (NULL != psRefer->plower_if) &&
+ (NULL != if_cb.receive_complete) &&
+ (NULL != if_cb.send_complete)
+ )
+ {
+ /* Register the LLC functions to the upper layer */
+ psRefer->plower_if->init = phDal4Nfc_Init;
+ psRefer->plower_if->release = phDal4Nfc_Shutdown;
+ psRefer->plower_if->send = phDal4Nfc_Write;
+ psRefer->plower_if->receive = phDal4Nfc_Read;
+ psRefer->plower_if->receive_wait = phDal4Nfc_ReadWait;
+ psRefer->plower_if->transact_abort = phDal4Nfc_ReadWaitCancel;
+ psRefer->plower_if->unregister = phDal4Nfc_Unregister;
+
+
+ if (NULL != pgDalContext)
+ {
+ /* Copy the DAL context to the upper layer */
+ psRefer->plower_if->pcontext = pgDalContext;
+ /* Register the callback function from the upper layer */
+ pgDalContext->cb_if.receive_complete = if_cb.receive_complete;
+ pgDalContext->cb_if.send_complete = if_cb.send_complete;
+ pgDalContext->cb_if.notify = if_cb.notify;
+ /* Get the upper layer context */
+ pgDalContext->cb_if.pif_ctxt = if_cb.pif_ctxt;
+ /* Update the error state */
+ result = NFCSTATUS_SUCCESS;
+ }
+ else
+ {
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_NOT_INITIALISED);
+ }
+ }
+ else /*Input parameters invalid*/
+ {
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_PARAMETER);
+ }
+ return result;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_Unregister
+
+PURPOSE: DAL unregister function.
+
+-----------------------------------------------------------------------------*/
+NFCSTATUS phDal4Nfc_Unregister(void *pContext, void *pHwRef )
+{
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+
+ if ((NULL == pContext) && (NULL == pHwRef))
+ {
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_PARAMETER);
+ }
+ else
+ {
+ if (NULL != pgDalContext)
+ {
+ /* Register the callback function from the upper layer */
+ pgDalContext->cb_if.receive_complete = NULL;
+ pgDalContext->cb_if.send_complete = NULL ;
+ pgDalContext->cb_if.notify = NULL ;
+ /* Get the upper layer context */
+ pgDalContext->cb_if.pif_ctxt = NULL ;
+// pgDalContext = NULL;
+
+ }
+ else
+ {
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_NOT_INITIALISED);
+ }
+ }
+ return result;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_Init
+
+PURPOSE: DAL Init function.
+
+-----------------------------------------------------------------------------*/
+NFCSTATUS phDal4Nfc_Init(void *pContext, void *pHwRef )
+{
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+
+ if ((NULL != pContext) && (NULL != pHwRef))
+ {
+ pContext = pgDalContext;
+ pgDalHwContext = (phHal_sHwReference_t *)pHwRef;
+
+ if ( gDalContext.hw_valid == TRUE )
+ {
+ /* The link has been opened from the application interface */
+ gLinkFunc.open_from_handle(pgDalHwContext);
+
+ if (!gLinkFunc.is_opened())
+ {
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_DEVICE);
+ }
+ else
+ {
+ /* Clear link buffers */
+ gLinkFunc.flush();
+ }
+ }
+ else
+ {
+ static phDal4Nfc_sConfig_t hw_config;
+ hw_config.nLinkType = DEFAULT_LINK_TYPE;
+ result = phDal4Nfc_Config(&hw_config, pHwRef );
+ }
+ }
+ else /*Input parametrs invalid*/
+ {
+ result = NFCSTATUS_INVALID_PARAMETER;
+ }
+
+ return result;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_Shutdown
+
+PURPOSE: DAL Shutdown function.
+
+-----------------------------------------------------------------------------*/
+
+NFCSTATUS phDal4Nfc_Shutdown( void *pContext, void *pHwRef)
+{
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+ void * pThreadReturn;
+
+// if (pContext == NULL)
+// return NFCSTATUS_INVALID_PARAMETER;
+
+ if (gDalContext.hw_valid == TRUE)
+ {
+ /* Flush the link */
+ gLinkFunc.flush();
+
+ /* Kill the read and write threads */
+// gReadWriteContext.nReadThreadAlive = 0;
+// gReadWriteContext.nWriteThreadAlive = 0;
+// pthread_mutex_unlock(&gReadWriteContext.nReadEventMutex);
+// pthread_mutex_unlock(&gReadWriteContext.nWriteEventMutex);
+// if (pthread_join(gReadWriteContext.nReadThread, &pThreadReturn) != 0)
+// {
+// result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_FAILED);
+// }
+// if (pthread_join(gReadWriteContext.nWriteThread, &pThreadReturn) != 0)
+// {
+// result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_FAILED);
+// }
+
+ /* Close the message queue */
+#ifdef USE_MQ_MESSAGE_QUEUE
+ mq_close(nDeferedCallMessageQueueId);
+#endif
+
+ /* Destroy the mutexes */
+// pthread_mutex_destroy(&gReadWriteContext.nReadEventMutex);
+// pthread_mutex_destroy(&gReadWriteContext.nReadCancelEventMutex);
+// pthread_mutex_destroy(&gReadWriteContext.nWriteEventMutex);
+// pthread_mutex_destroy(&nCriticalSectionMutex);
+// pthread_mutex_destroy(&nThreadsEventMutex);
+
+ /* Close the link */
+// gLinkFunc.close();
+
+ /* Reset the Writer Thread values to NULL */
+// memset((void *)&gReadWriteContext,0,sizeof(gReadWriteContext));
+ /* Reset the DAL context values to NULL */
+// memset((void *)&gDalContext,0,sizeof(gDalContext));
+ }
+
+// gDalContext.hw_valid = FALSE;
+
+ return result;
+}
+
+NFCSTATUS phDal4Nfc_ConfigRelease( void *pHwRef)
+{
+
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+ void * pThreadReturn;
+
+ if (gDalContext.hw_valid == TRUE)
+ {
+ /* Flush the link */
+ gLinkFunc.flush();
+
+ /* Kill the read and write threads */
+ gReadWriteContext.nReadThreadAlive = 0;
+ gReadWriteContext.nWriteThreadAlive = 0;
+ pthread_mutex_unlock(&gReadWriteContext.nReadEventMutex);
+ pthread_mutex_unlock(&gReadWriteContext.nWriteEventMutex);
+ if (pthread_join(gReadWriteContext.nReadThread, &pThreadReturn) != 0)
+ {
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_FAILED);
+ DAL_PRINT("phDal4Nfc_ConfigRelease KO");
+ }
+ if (pthread_join(gReadWriteContext.nWriteThread, &pThreadReturn) != 0)
+ {
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_FAILED);
+ DAL_PRINT("phDal4Nfc_ConfigRelease KO");
+ }
+
+ /* Close the message queue */
+#ifdef USE_MQ_MESSAGE_QUEUE
+ mq_close(nDeferedCallMessageQueueId);
+#endif
+
+ /* Destroy the mutexes */
+ pthread_mutex_destroy(&gReadWriteContext.nReadEventMutex);
+ pthread_mutex_destroy(&gReadWriteContext.nReadCancelEventMutex);
+ pthread_mutex_destroy(&gReadWriteContext.nWriteEventMutex);
+ pthread_mutex_destroy(&nCriticalSectionMutex);
+ pthread_mutex_destroy(&nThreadsEventMutex);
+
+ /* Close the link */
+ gLinkFunc.close();
+
+ /* Reset the Writer Thread values to NULL */
+ memset((void *)&gReadWriteContext,0,sizeof(gReadWriteContext));
+ /* Reset the DAL context values to NULL */
+ memset((void *)&gDalContext,0,sizeof(gDalContext));
+ }
+
+ gDalContext.hw_valid = FALSE;
+
+ DAL_DEBUG("phDal4Nfc_ConfigRelease(): %04x\n", result);
+
+ return result;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_Write
+
+PURPOSE: DAL Write function.
+
+-----------------------------------------------------------------------------*/
+NFCSTATUS phDal4Nfc_Write( void *pContext, void *pHwRef,uint8_t *pBuffer, uint16_t length)
+{
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+ if ((NULL != pContext) && (NULL != pHwRef)&&
+ (NULL != pBuffer) && (0 != length))
+ {
+ if( gDalContext.hw_valid== TRUE)
+ {
+ if((!gReadWriteContext.nWriteBusy)&&
+ (!gReadWriteContext.nWaitingOnWrite))
+ {
+ DAL_DEBUG("phDal4Nfc_Write(): %d\n", length);
+ /* Make a copy of the passed arguments */
+ gReadWriteContext.pWriteBuffer = pBuffer;
+ gReadWriteContext.nNbOfBytesToWrite = length;
+ /* Change the write state so that thread can take over the write */
+ gReadWriteContext.nWriteBusy = TRUE;
+ /* Just set variable here. This is the trigger for the Write thread */
+ gReadWriteContext.nWaitingOnWrite = TRUE;
+ /* Update the error state */
+ result = NFCSTATUS_PENDING;
+ pthread_mutex_unlock(&gReadWriteContext.nWriteEventMutex);
+ }
+ else
+ {
+ /* Driver is BUSY with previous Write */
+ DAL_PRINT("phDal4Nfc_Write() : Busy \n");
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_BUSY) ;
+ }
+ }
+ else
+ {
+ /* TBD :Additional error code : NOT_INITIALISED */
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_DEVICE);
+ }
+
+ }/*end if-Input parametrs valid-check*/
+ else
+ {
+ result = NFCSTATUS_INVALID_PARAMETER;
+ }
+ return result;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_Read
+
+PURPOSE: DAL Read function.
+
+-----------------------------------------------------------------------------*/
+
+NFCSTATUS phDal4Nfc_Read( void *pContext, void *pHwRef,uint8_t *pBuffer, uint16_t length)
+{
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+
+ if ((NULL != pContext) && (NULL != pHwRef)&&
+ (NULL != pBuffer) && (0 != length))
+ {
+ if ( gDalContext.hw_valid== TRUE)
+ {
+ if((!gReadWriteContext.nReadBusy)&&
+ (!gReadWriteContext.nWaitingOnRead))
+ {
+ DAL_DEBUG("*****DAl Read called length : %d\n", length);
+ /* Make a copy of the passed arguments */
+ gReadWriteContext.pReadBuffer = pBuffer;
+ gReadWriteContext.nNbOfBytesToRead = length;
+ /* Change the Read state so that thread can take over the read */
+ gReadWriteContext.nReadBusy = TRUE;
+ /* Just set variable here. This is the trigger for the Reader thread */
+ gReadWriteContext.nWaitingOnRead = TRUE;
+ // retval = ResetEvent(gReadWriteContext.nReadCancelEventMutex); /* TO DO */
+ /* Update the erro state */
+ result = NFCSTATUS_PENDING;
+ pthread_mutex_unlock(&gReadWriteContext.nReadEventMutex);
+ }
+ else
+ {
+ /* Driver is BUSY with prev Read */
+ DAL_PRINT("DAL BUSY\n");
+ /* Make a copy of the passed arguments */
+ gReadWriteContext.pReadBuffer = pBuffer;
+ gReadWriteContext.nNbOfBytesToRead = length;
+ result = NFCSTATUS_PENDING;
+ pthread_mutex_unlock(&gReadWriteContext.nReadEventMutex);
+ }
+ }
+ else
+ {
+ /* TBD :Additional error code : NOT_INITIALISED */
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_DEVICE);
+ }
+ }/*end if-Input parametrs valid-check*/
+ else
+ {
+ result = NFCSTATUS_INVALID_PARAMETER;
+ }
+ DAL_DEBUG("*****DAl Read called result : %x\n", result);
+ return result;
+}
+
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_ReadWait
+
+PURPOSE: DAL Read wait function.
+
+-----------------------------------------------------------------------------*/
+
+NFCSTATUS phDal4Nfc_ReadWait(void *pContext, void *pHwRef,uint8_t *pBuffer, uint16_t length)
+{
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+ if ((NULL != pContext) && (NULL != pHwRef)&&
+ (NULL != pBuffer) && (0 != length))
+ {
+ if ( gDalContext.hw_valid== TRUE)
+ {
+ if((!gReadWriteContext.nReadBusy)&&
+ (!gReadWriteContext.nReadWaitBusy)&&
+ (!gReadWriteContext.nWaitingOnRead))
+ {
+ /* Save the copy of passed arguments */
+ gReadWriteContext.pReadWaitBuffer = pBuffer;
+ gReadWriteContext.nNbOfBytesToReadWait = length;
+ /* Change the Read state so that thread can take over the read */
+ gReadWriteContext.nReadWaitBusy = TRUE;
+ /* Just set variable here. This is the trigger for the Reader thread */
+ gReadWriteContext.nWaitingOnReadWait = TRUE;
+ /* Update the error state */
+ result = NFCSTATUS_SUCCESS;
+ }
+ else
+ {
+ /* Driver is BUSY with prev Read */
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_BUSY);
+ }
+ }
+ else
+ {
+ /* TBD :Additional error code : NOT_INITIALISED */
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_DEVICE);
+ }
+ }/*end if -Input parametrs valid-check*/
+ else
+ {
+ result = NFCSTATUS_INVALID_PARAMETER;
+ }
+ return result;
+}
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_ReadWaitCancel
+
+PURPOSE: Cancel the Read wait function.
+
+-----------------------------------------------------------------------------*/
+
+NFCSTATUS phDal4Nfc_ReadWaitCancel( void *pContext, void *pHwRef)
+{
+#if 0
+ char retval;
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+ DAL_PRINT("DAl Read cancel called \n");
+ if ((NULL != pContext) && (NULL != pHwRef))
+ {
+ if ( gDalContext.hw_valid== TRUE)
+ {
+ /* Clear The Comm Port Event */
+ if (!SetCommMask(h_serial_port, 0x0000))
+ {
+ /* Windows Error */
+ result = NFCSTATUS_BOARD_COMMUNICATION_ERROR;
+ }
+ /* Cancel the Wait read */
+ retval = SetEvent(gReadWriteContext.nReadCancelEventMutex);
+ }
+ else
+ {
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_DEVICE);
+ }
+ }
+ else
+ {
+ result = NFCSTATUS_INVALID_PARAMETER;
+ }
+ return result;
+#endif
+ return 0;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_Config
+
+PURPOSE: Configure the serial port.
+
+-----------------------------------------------------------------------------*/
+NFCSTATUS phDal4Nfc_Config(pphDal4Nfc_sConfig_t config,void **phwref)
+{
+ NFCSTATUS retstatus = NFCSTATUS_SUCCESS;
+
+ DAL_PRINT("phDal4Nfc_Config");
+
+ if ((config == NULL) || (phwref == NULL) || (config->nClientId == -1))
+ return NFCSTATUS_INVALID_PARAMETER;
+
+ /* Register the link callbacks */
+ memset(&gLinkFunc, 0, sizeof(phDal4Nfc_link_cbk_interface_t));
+ switch(config->nLinkType)
+ {
+ case ENUM_DAL_LINK_TYPE_COM1:
+ case ENUM_DAL_LINK_TYPE_COM2:
+ case ENUM_DAL_LINK_TYPE_COM3:
+ case ENUM_DAL_LINK_TYPE_COM4:
+ case ENUM_DAL_LINK_TYPE_COM5:
+ case ENUM_DAL_LINK_TYPE_USB:
+ {
+ /* Uart link interface */
+ gLinkFunc.init = phDal4Nfc_uart_initialize;
+ gLinkFunc.open_from_handle = phDal4Nfc_uart_set_open_from_handle;
+ gLinkFunc.is_opened = phDal4Nfc_uart_is_opened;
+ gLinkFunc.flush = phDal4Nfc_uart_flush;
+ gLinkFunc.close = phDal4Nfc_uart_close;
+ gLinkFunc.open_and_configure = phDal4Nfc_uart_open_and_configure;
+ gLinkFunc.read = phDal4Nfc_uart_read;
+ gLinkFunc.write = phDal4Nfc_uart_write;
+ }
+ break;
+
+ case ENUM_DAL_LINK_TYPE_I2C:
+ {
+ /* Uart link interface */
+ gLinkFunc.init = phDal4Nfc_i2c_initialize;
+ gLinkFunc.open_from_handle = phDal4Nfc_i2c_set_open_from_handle;
+ gLinkFunc.is_opened = phDal4Nfc_i2c_is_opened;
+ gLinkFunc.flush = phDal4Nfc_i2c_flush;
+ gLinkFunc.close = phDal4Nfc_i2c_close;
+ gLinkFunc.open_and_configure = phDal4Nfc_i2c_open_and_configure;
+ gLinkFunc.read = phDal4Nfc_i2c_read;
+ gLinkFunc.write = phDal4Nfc_i2c_write;
+ break;
+ }
+
+ default:
+ {
+ /* Shound not happen : Bad parameter */
+ return PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_PARAMETER);
+ }
+ }
+
+ gLinkFunc.init(); /* So that link interface can initialize its internal state */
+ retstatus = gLinkFunc.open_and_configure(config, phwref);
+ if (retstatus != NFCSTATUS_SUCCESS)
+ return retstatus;
+
+ /* Iniatilize the DAL context */
+ (void)memset(&gDalContext,0,sizeof(phDal4Nfc_SContext_t));
+ pgDalContext = &gDalContext;
+
+ /* Reset the Writer Thread values to NULL */
+ memset((void *)&gReadWriteContext,0,sizeof(gReadWriteContext));
+ gReadWriteContext.nReadThreadAlive = TRUE;
+ gReadWriteContext.nWriteThreadAlive = TRUE;
+
+ /* Reset the Reader Thread values to NULL */
+ memset((void *)&gReadWriteContext,0,sizeof(gReadWriteContext));
+ gReadWriteContext.nReadThreadAlive = TRUE;
+ gReadWriteContext.nWriteThreadAlive = TRUE;
+
+ pthread_mutex_init (&gReadWriteContext.nReadEventMutex, NULL);
+ pthread_mutex_init (&gReadWriteContext.nReadCancelEventMutex, NULL);
+ pthread_mutex_init (&gReadWriteContext.nWriteEventMutex, NULL);
+
+ /* Prepare the message queue for the defered calls */
+#ifdef USE_MQ_MESSAGE_QUEUE
+ nDeferedCallMessageQueueId = mq_open(MQ_NAME_IDENTIFIER, O_CREAT|O_RDWR, 0666, &MQ_QUEUE_ATTRIBUTES);
+#else
+ nDeferedCallMessageQueueId = config->nClientId;
+#endif
+ /* Start Read and Write Threads */
+ if(NFCSTATUS_SUCCESS != phDal4Nfc_StartThreads())
+ {
+ return PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_FAILED);
+ }
+
+ gDalContext.hw_valid = TRUE;
+
+ return NFCSTATUS_SUCCESS;
+}
+
+
+
+
+/*-----------------------------------------------------------------------------------
+ DAL INTERNAL IMPLEMENTATION
+------------------------------------------------------------------------------------*/
+
+
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL Reader thread handler
+ * This function manages the reads from the link interface. The reads are done from
+ * this thread to create the asynchronous mecanism. When calling the synchronous
+ * function phDal4Nfc_Read, the nWaitingOnRead mutex is unlocked and the read
+ * can be done. Then a client callback is called to send the result.
+ *
+ * \param[in] pArg A custom argument that can be passed to the thread (not used)
+ *
+ * \retval TRUE Thread exiting.
+ */
+int phDal4Nfc_ReaderThread(void * pArg)
+{
+ char retvalue;
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+ uint8_t retry_cnt=0;
+ void * memsetRet;
+
+ static int MsgType= PHDAL4NFC_READ_MESSAGE;
+ int * pmsgType=&MsgType;
+
+ phDal4Nfc_Message_t sMsg;
+ phOsalNfc_Message_t OsalMsg ;
+ int i;
+
+ /* Create the overlapped event. Must be closed before exiting
+ to avoid a handle leak. This event is used READ API and the Reader thread*/
+ pthread_mutex_unlock(&nThreadsEventMutex); /* To indicate thread is ready */
+
+ DAL_PRINT("RX Thread \n");
+ while(gReadWriteContext.nReadThreadAlive) /* Thread Loop */
+ {
+ retvalue = 1;
+ gReadWriteContext.nWaitingOnRead = ((gReadWriteContext.nWaitingOnRead == 1)?1:0);
+ gReadWriteContext.nCancelReadWait = 0;
+ gReadWriteContext.nWaitingOnReadWait = 0;
+
+ pthread_mutex_lock(&gReadWriteContext.nReadEventMutex); /* Remains locked till we get a read request */
+
+ /* Check for the read request from user */
+ if (gReadWriteContext.nWaitingOnRead)
+ {
+ /* Issue read operation.*/
+ gReadWriteContext.nNbOfBytesRead=0;
+ DAL_DEBUG("\n*New *** *****Request Length = %d",gReadWriteContext.nNbOfBytesToRead);
+ memsetRet=memset(gReadWriteContext.pReadBuffer,0,gReadWriteContext.nNbOfBytesToRead);
+
+ /* Wait for Write Completion */
+ usleep(2500);
+ gReadWriteContext.nNbOfBytesRead = gLinkFunc.read(gReadWriteContext.pReadBuffer, gReadWriteContext.nNbOfBytesToRead);
+ if (gReadWriteContext.nNbOfBytesRead == -1)
+ {
+ DAL_DEBUG("Read failed\n", 0);
+ /* TBD : Error, report it.*/
+ result = PHNFCSTVAL(CID_NFC_DAL,
+ NFCSTATUS_BOARD_COMMUNICATION_ERROR);
+ } /* End of File Read if */
+ else if (gReadWriteContext.nNbOfBytesRead == 0)
+ {
+ /* In case of timeout, keep polling */
+ pthread_mutex_unlock(&gReadWriteContext.nReadEventMutex);
+ continue;
+ }
+ else
+ {
+ DAL_DEBUG("Read ok. nbToRead=%d\n", gReadWriteContext.nNbOfBytesToRead);
+ DAL_DEBUG("NbReallyRead=%d\n", gReadWriteContext.nNbOfBytesRead);
+ DAL_PRINT("ReadBuff[]={ ");
+ for (i = 0; i < gReadWriteContext.nNbOfBytesRead; i++)
+ {
+ DAL_DEBUG("0x%x ", gReadWriteContext.pReadBuffer[i]);
+ }
+ DAL_PRINT("}\n");
+
+ /* read completed immediately */
+ sMsg.eMsgType= PHDAL4NFC_READ_MESSAGE;
+ /* Update the state */
+ phDal4Nfc_FillMsg(&sMsg,&OsalMsg);
+ phDal4Nfc_DeferredCall((pphDal4Nfc_DeferFuncPointer_t)phDal4Nfc_DeferredCb,(void *)pmsgType);
+ memsetRet=memset(&sMsg,0,sizeof(phDal4Nfc_Message_t));
+ memsetRet=memset(&OsalMsg,0,sizeof(phOsalNfc_Message_t));
+ }
+ }
+ else if (gReadWriteContext.nWaitingOnReadWait) /* Wait Read Loop */
+ {
+
+ gReadWriteContext.nNbOfBytesReadWait = gLinkFunc.read(gReadWriteContext.pReadWaitBuffer, gReadWriteContext.nNbOfBytesToReadWait);
+ if (gReadWriteContext.nNbOfBytesReadWait == -1)
+ {
+ /* Error; report it.*/
+ result = PHNFCSTVAL(CID_NFC_DAL,
+ NFCSTATUS_BOARD_COMMUNICATION_ERROR);
+ }
+ else
+ {
+ sMsg.eMsgType= PHDAL4NFC_READWAIT_MESSAGE;
+ phDal4Nfc_FillMsg(&sMsg,&OsalMsg);
+ retry_cnt=0;
+ /* Update the state */
+ gReadWriteContext.nReadBusy = FALSE;
+ /* Reset flag so that another opertion can be issued.*/
+ gReadWriteContext.nWaitingOnRead = FALSE;
+ gReadWriteContext.nNbOfBytesRead=0;
+ gReadWriteContext.nNbOfBytesToRead=0;
+ phDal4Nfc_DeferredCall((pphDal4Nfc_DeferFuncPointer_t)
+ phDal4Nfc_DeferredCb,(void *)pmsgType);
+
+ /* Update the state */
+ gReadWriteContext.nReadWaitBusy = FALSE;
+ /* Reset flag so that another opertion can be issued.*/
+ gReadWriteContext.nWaitingOnReadWait = FALSE;
+ }/*end-else*/
+
+ }
+ else if (gReadWriteContext.nCancelReadWait)
+ {
+ DAL_PRINT("Read Wait is Canceled\n");
+ }
+ else if ( result != NFCSTATUS_SUCCESS )
+ {
+ /* Report it to user */
+ sMsg.transactInfo.status = result;
+ /*map to OSAL msg format*/
+ OsalMsg.eMsgType = PH_DAL4NFC_MESSAGE_BASE;
+ OsalMsg.pMsgData = (void*)&sMsg;
+ /* Update the state */
+ gReadWriteContext.nNbOfBytesRead=0;
+ gReadWriteContext.nNbOfBytesToRead=0;
+ phDal4Nfc_DeferredCall((pphDal4Nfc_DeferFuncPointer_t)
+ phDal4Nfc_DeferredCb,(void *)pmsgType);
+
+ } /*end-else if ( result != NFCSTATUS_SUCCESS )*/
+ else
+ {
+ continue;
+ }
+
+ } /* End of thread Loop*/
+ return TRUE;
+}
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL Writer thread handler
+ * This function manages the writes to the link interface. The writes are done from
+ * this thread to create the asynchronous mecanism. When calling the synchronous
+ * function phDal4Nfc_Write, the nWaitingOnWrite mutex is unlocked and the write
+ * can be done. Then a client callback is called to signal the operation as complete.
+ *
+ * \param[in] pArg A custom argument that can be passed to the thread (not used)
+ *
+ * \retval TRUE Thread exiting.
+ */
+int phDal4Nfc_WriterThread(void * pArg)
+{
+ char retvalue = 1;
+ NFCSTATUS result = NFCSTATUS_SUCCESS;
+ phDal4Nfc_Message_t sMsg;
+ phOsalNfc_Message_t OsalMsg ;
+ static int MsgType=PHDAL4NFC_WRITE_MESSAGE;
+ int * pmsgType=&MsgType;
+ int i;
+
+ /* Create the overlapped event. Must be closed before exiting
+ to avoid a handle leak. This event is used READ API and the Reader thread*/
+ pthread_mutex_unlock(&nThreadsEventMutex); /* To indicate thread is ready */
+
+ /* Set the thread started Event, to make sure that both threads are ready
+ in the initialization state*/
+ while(gReadWriteContext.nWriteThreadAlive) /* Thread Loop */
+ {
+
+ retvalue = 1;
+ DAL_PRINT("TX Started\n");
+ pthread_mutex_lock(&gReadWriteContext.nWriteEventMutex); /* Remains locked till we get a write request */
+ /* Check for the write request from user */
+ if(gReadWriteContext.nWaitingOnWrite)
+ {
+ /* Issue a write after a 8ms pause */
+ usleep(8000);
+ gReadWriteContext.nNbOfBytesWritten = gLinkFunc.write(gReadWriteContext.pWriteBuffer, gReadWriteContext.nNbOfBytesToWrite);
+ if (gReadWriteContext.nNbOfBytesWritten != gReadWriteContext.nNbOfBytesToWrite)
+ {
+ /* Report write failure or timeout */
+ DAL_DEBUG("Write error in write thread\n", 0);
+ result = PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_BOARD_COMMUNICATION_ERROR);
+ }/*end writeFile*/
+ else /* Results ready */
+ {
+ /* Write operation completed successfully.*/
+ sMsg.eMsgType = PHDAL4NFC_WRITE_MESSAGE;
+ //sMsg.pContext = pgDalContext;
+ sMsg.pContext= pgDalContext->cb_if.pif_ctxt;
+ phDal4Nfc_FillMsg(&sMsg,&OsalMsg);
+ /* Post a message to the HAL Thread */
+ /* Update the state */
+ gReadWriteContext.nWriteBusy = FALSE;
+ /* Reset flag so that another opertion can be issued.*/
+ gReadWriteContext.nWaitingOnWrite = FALSE;
+
+ gReadWriteContext.nNbOfBytesWritten=gReadWriteContext.nNbOfBytesToWrite;
+
+ DAL_DEBUG("NON Overlapped Write :DAl Writer thread called length : %d\n",
+ gReadWriteContext.nNbOfBytesWritten);
+
+ DAL_PRINT("WriteBuff[]={ ");
+ for (i = 0; i < gReadWriteContext.nNbOfBytesWritten; i++)
+ {
+ DAL_DEBUG("0x%x ", gReadWriteContext.pWriteBuffer[i]);
+ }
+ DAL_PRINT("}\n");
+
+ phDal4Nfc_DeferredCall(phDal4Nfc_DeferredCb,pmsgType);
+
+ }/*end else Results ready */
+ }
+ else if ( result != NFCSTATUS_SUCCESS )
+ {
+
+ /* Report it to user */
+ sMsg.transactInfo.status = result;
+ /*map to OSAL msg format*/
+ OsalMsg.eMsgType = PH_DAL4NFC_MESSAGE_BASE;
+ OsalMsg.pMsgData = (void*)&sMsg;
+ /* Update the state */
+ gReadWriteContext.nWriteBusy = FALSE;
+ /* Reset flag so that another opertion can be issued.*/
+ gReadWriteContext.nWaitingOnWrite = FALSE;
+ gReadWriteContext.nNbOfBytesWritten = 0;
+
+ DAL_DEBUG("DAl Writer thread error called length : %d\n",
+ gReadWriteContext.nNbOfBytesWritten);
+
+ }/*end elseif*/
+ else
+ {
+ continue;
+ }
+ }/* End of thread Loop*/
+ return TRUE;
+}
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL Start threads function
+ * This function is called from phDal4Nfc_Config and is responsible of creating the
+ * reader and writer threads. Also it will init necessary mutexes.
+ *
+ * \retval NFCSTATUS_SUCCESS If success.
+ * \retval NFCSTATUS_FAILED Can not create thread or retreive its attributes
+ */
+NFCSTATUS phDal4Nfc_StartThreads(void)
+{
+ pthread_attr_t nReadThreadAttributes;
+ pthread_attr_t nWriteThreadAttributes;
+ int ret;
+
+ /* Mutex init */
+ pthread_mutex_init (&nCriticalSectionMutex, NULL);
+ pthread_mutex_init (&nThreadsEventMutex, NULL);
+
+ /* Lock the request mutexes */
+ pthread_mutex_lock(&gReadWriteContext.nWriteEventMutex);
+ pthread_mutex_lock(&gReadWriteContext.nReadEventMutex);
+
+ pthread_mutex_lock(&nThreadsEventMutex); /* First thread ready lock */
+ ret = pthread_create(&gReadWriteContext.nReadThread, NULL, (pphDal4Nfc_thread_handler_t)phDal4Nfc_ReaderThread, (void*) "dal_read_thread");
+ if(ret != 0)
+ return(PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_FAILED));
+ pthread_mutex_lock(&nThreadsEventMutex); /* Blocking lock */
+ // Here we have been unblocked by the thread handler. (so the thread is ready)
+ ret = pthread_create(&gReadWriteContext.nWriteThread, NULL, (pphDal4Nfc_thread_handler_t)phDal4Nfc_WriterThread, (void*) "dal_write_thread");
+ if(ret != 0)
+ return(PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_FAILED));
+ pthread_mutex_lock(&nThreadsEventMutex); /* Blocking lock */
+ // Here we have been unblocked by the thread handler. (so the thread is ready)
+ pthread_mutex_unlock(&nThreadsEventMutex);
+ return NFCSTATUS_SUCCESS;
+}
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL fill message function
+ * Internal messages management. This function fills message structure
+ * depending on message types.
+ *
+ * \param[in, out] pDalMsg DAL message to fill
+ * \param[in, out] pOsalMsg OSAL message to fill
+ *
+ */
+void phDal4Nfc_FillMsg(phDal4Nfc_Message_t *pDalMsg,phOsalNfc_Message_t *pOsalMsg)
+{
+ if(NULL != pgDalHwContext)
+ {
+ if(pDalMsg->eMsgType == PHDAL4NFC_WRITE_MESSAGE)
+ {
+ pDalMsg->transactInfo.length = (uint8_t)gReadWriteContext.nNbOfBytesWritten;
+ pDalMsg->transactInfo.buffer = NULL;
+ pDalMsg->transactInfo.status = NFCSTATUS_SUCCESS;
+ pDalMsg->pHwRef = pgDalHwContext;
+ pDalMsg->writeCbPtr = pgDalContext->cb_if.send_complete;
+ pOsalMsg->eMsgType = PH_DAL4NFC_MESSAGE_BASE;
+ pOsalMsg->pMsgData = pDalMsg;
+ return;
+ }
+ else if(pDalMsg->eMsgType == PHDAL4NFC_READ_MESSAGE)
+ {
+ pDalMsg->transactInfo.length = (uint8_t)gReadWriteContext.nNbOfBytesRead;
+ pDalMsg->transactInfo.buffer = gReadWriteContext.pReadBuffer;
+ pDalMsg->pContext= pgDalContext->cb_if.pif_ctxt;
+ }
+ else
+ {
+ pDalMsg->transactInfo.length = (uint8_t)gReadWriteContext.nNbOfBytesReadWait;
+ pDalMsg->transactInfo.buffer = gReadWriteContext.pReadWaitBuffer;
+ pDalMsg->pContext= pgDalContext;
+ }
+ pDalMsg->transactInfo.status = NFCSTATUS_SUCCESS;
+ pDalMsg->pHwRef = pgDalHwContext;
+ pDalMsg->readCbPtr = pgDalContext->cb_if.receive_complete;
+ /*map to OSAL msg format*/
+ pOsalMsg->eMsgType = PH_DAL4NFC_MESSAGE_BASE;
+ pOsalMsg->pMsgData = pDalMsg;
+ }
+
+}
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL deferred callback function
+ * Generic handler function called by a client thread when reading a message from the queue.
+ * Will function will directly call the client function (same context). See phDal4Nfc_DeferredCall
+ *
+ * \param[in] params Parameter that will be passed to the client function.
+ *
+ */
+void phDal4Nfc_DeferredCb (void *params)
+{
+ int* pParam=NULL;
+ phNfc_sTransactionInfo_t TransactionInfo;
+
+ pParam=(int*)params;
+
+ switch(*pParam)
+ {
+ case PHDAL4NFC_READ_MESSAGE:
+ DAL_PRINT(" Dal deferred read called \n");
+ TransactionInfo.buffer=gReadWriteContext.pReadBuffer;
+ TransactionInfo.length=(uint16_t)gReadWriteContext.nNbOfBytesRead;
+ TransactionInfo.status=NFCSTATUS_SUCCESS;
+ gReadWriteContext.nReadBusy = FALSE;
+ /* Reset flag so that another opertion can be issued.*/
+ gReadWriteContext.nWaitingOnRead = FALSE;
+ if ((NULL != pgDalContext) && (NULL != pgDalContext->cb_if.receive_complete))
+ {
+ pgDalContext->cb_if.receive_complete(pgDalContext->cb_if.pif_ctxt,
+ pgDalHwContext,&TransactionInfo);
+ }
+
+ break;
+ case PHDAL4NFC_READWAIT_MESSAGE:
+ /*dalMsg->readCbPtr(dalMsg->pContext, dalMsg->pHwRef, &dalMsg->transactInfo);*/
+ break;
+ case PHDAL4NFC_WRITE_MESSAGE:
+ DAL_PRINT(" Dal deferred write called \n");
+ /* DAL_DEBUG("dalMsg->transactInfo.length : %d\n", dalMsg->transactInfo.length); */
+
+ TransactionInfo.buffer=NULL;
+ TransactionInfo.length=(uint16_t)gReadWriteContext.nNbOfBytesWritten;
+ TransactionInfo.status=NFCSTATUS_SUCCESS;
+ if ((NULL != pgDalContext) && (NULL != pgDalContext->cb_if.send_complete))
+ {
+ pgDalContext->cb_if.send_complete(pgDalContext->cb_if.pif_ctxt,
+ pgDalHwContext,&TransactionInfo);
+ }
+ break;
+ default:
+ break;
+ }
+}
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL deferred call function
+ * This function will enable to call the callback client asyncronously and in the client context.
+ * It will post a message in a queue that will be processed by a client thread.
+ *
+ * \param[in] func The function to call when message is read from the queue
+ * \param[in] param Parameter that will be passed to the 'func' function.
+ *
+ */
+void phDal4Nfc_DeferredCall(pphDal4Nfc_DeferFuncPointer_t func, void *param)
+{
+ int retvalue = 0;
+ phDal4Nfc_Message_Wrapper_t nDeferedMessageWrapper;
+ phDal4Nfc_DeferredCall_Msg_t *pDeferedMessage;
+ static phDal4Nfc_DeferredCall_Msg_t nDeferedMessageRead;
+ static phDal4Nfc_DeferredCall_Msg_t nDeferedMessageWrite;
+
+ pthread_mutex_lock(&nCriticalSectionMutex);
+
+#ifdef USE_MQ_MESSAGE_QUEUE
+ nDeferedMessage.eMsgType = PH_DAL4NFC_MESSAGE_BASE;
+ nDeferedMessage.def_call = func;
+ nDeferedMessage.params = param;
+ retvalue = (int)mq_send(nDeferedCallMessageQueueId, (char *)&nDeferedMessage, sizeof(phDal4Nfc_DeferredCall_Msg_t), 0);
+#else
+ if(PHDAL4NFC_READ_MESSAGE==(* (int*)param))
+ {
+ pDeferedMessage = &nDeferedMessageRead;
+ }
+ else
+ {
+ pDeferedMessage = &nDeferedMessageWrite;
+ }
+ nDeferedMessageWrapper.mtype = 1;
+ nDeferedMessageWrapper.msg.eMsgType = PH_DAL4NFC_MESSAGE_BASE;
+ pDeferedMessage->pCallback = func;
+ pDeferedMessage->pParameter = param;
+ nDeferedMessageWrapper.msg.pMsgData = pDeferedMessage;
+ nDeferedMessageWrapper.msg.Size = sizeof(phDal4Nfc_DeferredCall_Msg_t);
+ retvalue = phDal4Nfc_msgsnd(nDeferedCallMessageQueueId, (struct msgbuf *)&nDeferedMessageWrapper, sizeof(phLibNfc_Message_t), 0);
+#endif
+
+ pthread_mutex_unlock(&nCriticalSectionMutex);
+}
+
+#undef _DAL_4_NFC_C
+
diff --git a/Linux_x86/phDal4Nfc_debug.h b/Linux_x86/phDal4Nfc_debug.h
new file mode 100644
index 0000000..bd6ae91
--- /dev/null
+++ b/Linux_x86/phDal4Nfc_debug.h
@@ -0,0 +1,42 @@
+
+
+
+/*-----------------------------------------------------------------------------------
+ DEBUG CORNER
+------------------------------------------------------------------------------------*/
+/* Activate for debug */
+//#define DAL_TRACE
+
+#ifdef DAL_TRACE
+#include <stdio.h>
+
+#define MAX_TRACE_BUFFER 150
+
+#define DAL_PRINT( str ) phOsalNfc_DbgString(str)
+#define DAL_DEBUG(str, arg) \
+{ \
+ char trace[MAX_TRACE_BUFFER]; \
+ snprintf(trace,MAX_TRACE_BUFFER,str,arg); \
+ phOsalNfc_DbgString(trace); \
+}
+
+#define DAL_PRINT_BUFFER(msg,buf,len) \
+{ \
+ uint16_t i = 0; \
+ char trace[MAX_TRACE_BUFFER]; \
+ snprintf(trace,MAX_TRACE_BUFFER,"\n\t %s:",msg); \
+ phOsalNfc_DbgString(trace); \
+ phOsalNfc_DbgTrace(buf,len); \
+ phOsalNfc_DbgString("\r"); \
+}
+
+#define DAL_ASSERT_STR(x, str) { if (!(x)) { phOsalNfc_DbgString(str); while(1); } }
+
+#else
+#define DAL_PRINT( str )
+#define DAL_DEBUG(str, arg)
+#define DAL_PRINT_BUFFER(msg,buf,len)
+#define DAL_ASSERT_STR(x, str)
+
+#endif
+
diff --git a/Linux_x86/phDal4Nfc_i2c.c b/Linux_x86/phDal4Nfc_i2c.c
new file mode 100644
index 0000000..8a54bee
--- /dev/null
+++ b/Linux_x86/phDal4Nfc_i2c.c
@@ -0,0 +1,226 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phDalNfc_i2c.c
+ * \brief DAL I2C port implementation for linux
+ *
+ * Project: Trusted NFC Linux
+ *
+ */
+
+#include <unistd.h>
+#include <fcntl.h>
+#include <termios.h>
+#include <sys/ioctl.h>
+#include <sys/select.h>
+
+#include <phDal4Nfc_debug.h>
+#include <phDal4Nfc_i2c.h>
+#include <phOsalNfc.h>
+#include <phNfcStatus.h>
+#if defined(ANDROID)
+#include <string.h>
+#endif
+
+typedef struct
+{
+ int nHandle;
+ char nOpened;
+
+} phDal4Nfc_I2cPortContext_t;
+
+
+/*-----------------------------------------------------------------------------------
+ VARIABLES
+------------------------------------------------------------------------------------*/
+static phDal4Nfc_I2cPortContext_t gI2cPortContext;
+
+
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_i2c_set_open_from_handle
+
+PURPOSE: Initialize internal variables
+
+-----------------------------------------------------------------------------*/
+
+void phDal4Nfc_i2c_initialize(void)
+{
+ memset(&gI2cPortContext, 0, sizeof(phDal4Nfc_I2cPortContext_t));
+}
+
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_i2c_set_open_from_handle
+
+PURPOSE: The application could have opened the link itself. So we just need
+ to get the handle and consider that the open operation has already
+ been done.
+
+-----------------------------------------------------------------------------*/
+
+void phDal4Nfc_i2c_set_open_from_handle(phHal_sHwReference_t * pDalHwContext)
+{
+ gI2cPortContext.nHandle = (int) pDalHwContext->p_board_driver;
+ DAL_ASSERT_STR(gComPortContext.nHandle >= 0, "Bad passed com port handle");
+ gI2cPortContext.nOpened = 1;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_i2c_is_opened
+
+PURPOSE: Returns if the link is opened or not. (0 = not opened; 1 = opened)
+
+-----------------------------------------------------------------------------*/
+
+int phDal4Nfc_i2c_is_opened(void)
+{
+ return gI2cPortContext.nOpened;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_i2c_flush
+
+PURPOSE: Flushes the link ; clears the link buffers
+
+-----------------------------------------------------------------------------*/
+
+void phDal4Nfc_i2c_flush(void)
+{
+ /* Nothing to do (driver has no internal buffers) */
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_i2c_close
+
+PURPOSE: Closes the link
+
+-----------------------------------------------------------------------------*/
+
+void phDal4Nfc_i2c_close(void)
+{
+ DAL_PRINT("Closing port\n");
+ if (gI2cPortContext.nOpened == 1)
+ {
+ close(gI2cPortContext.nHandle);
+ gI2cPortContext.nHandle = 0;
+ gI2cPortContext.nOpened = 0;
+ }
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_i2c_open_and_configure
+
+PURPOSE: Closes the link
+
+-----------------------------------------------------------------------------*/
+
+NFCSTATUS phDal4Nfc_i2c_open_and_configure(pphDal4Nfc_sConfig_t pConfig, void ** pLinkHandle)
+{
+ char * pComPort;
+
+ DAL_ASSERT_STR(gI2cPortContext.nOpened==0, "Trying to open but already done!");
+
+ switch(pConfig->nLinkType)
+ {
+ case ENUM_DAL_LINK_TYPE_I2C:
+ pComPort = "/dev/pn544";
+ break;
+ default:
+ DAL_DEBUG("Open failed: unknown type %d\n", pConfig->nLinkType);
+ return NFCSTATUS_INVALID_PARAMETER;
+ }
+
+ DAL_DEBUG("Opening port=%s\n", pComPort);
+
+ /* open port */
+ gI2cPortContext.nHandle = open(pComPort, O_RDWR | O_NOCTTY);
+ if (gI2cPortContext.nHandle < 0)
+ {
+ DAL_DEBUG("Open failed: open() returned %d\n", gI2cPortContext.nHandle);
+ *pLinkHandle = NULL;
+ return PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_DEVICE);
+ }
+
+ gI2cPortContext.nOpened = 1;
+ *pLinkHandle = (void*)gI2cPortContext.nHandle;
+
+ DAL_PRINT("Open succeed\n");
+
+ return NFCSTATUS_SUCCESS;
+}
+
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_i2c_read
+
+PURPOSE: Reads nNbBytesToRead bytes and writes them in pBuffer.
+ Returns the number of bytes really read or -1 in case of error.
+
+-----------------------------------------------------------------------------*/
+
+int phDal4Nfc_i2c_read(uint8_t * pBuffer, int nNbBytesToRead)
+{
+ int ret;
+ DAL_ASSERT_STR(gComPortContext.nOpened == 1, "read called but not opened!");
+
+ DAL_DEBUG("Reading %d bytes\n", nNbBytesToRead);
+ ret = read(gI2cPortContext.nHandle, pBuffer, nNbBytesToRead);
+ if (ret < 0)
+ {
+ DAL_DEBUG("Read failed: read() returned %d\n", ret);
+ }
+ else
+ {
+ DAL_DEBUG("Read succeed (%d bytes)\n", ret);
+ }
+ return ret;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_i2c_write
+
+PURPOSE: Writes nNbBytesToWrite bytes from pBuffer to the link
+ Returns the number of bytes that have been wrote to the interface or -1 in case of error.
+
+-----------------------------------------------------------------------------*/
+
+int phDal4Nfc_i2c_write(uint8_t * pBuffer, int nNbBytesToWrite)
+{
+ int ret;
+ DAL_ASSERT_STR(gComPortContext.nOpened == 1, "write called but not opened!");
+
+ DAL_DEBUG("Writing %d bytes\n", nNbBytesToWrite);
+ ret = write(gI2cPortContext.nHandle, pBuffer, nNbBytesToWrite);
+ if (ret < 0)
+ {
+ DAL_DEBUG("Write failed: write() returned %d \n", ret);
+ }
+ else
+ {
+ DAL_DEBUG("Write succeed (%d bytes)\n", ret);
+ }
+ return ret;
+}
diff --git a/Linux_x86/phDal4Nfc_i2c.h b/Linux_x86/phDal4Nfc_i2c.h
new file mode 100644
index 0000000..fe391aa
--- /dev/null
+++ b/Linux_x86/phDal4Nfc_i2c.h
@@ -0,0 +1,39 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phDalNfc_i2c.h
+ * \brief DAL I2C port implementation for linux
+ *
+ * Project: Trusted NFC Linux
+ *
+ */
+
+/**< Basic type definitions */
+#include <phNfcTypes.h>
+/**< Generic Interface Layer Function Definitions */
+#include <phNfcInterface.h>
+#include <phDal4Nfc.h>
+
+void phDal4Nfc_i2c_initialize(void);
+void phDal4Nfc_i2c_set_open_from_handle(phHal_sHwReference_t * pDalHwContext);
+int phDal4Nfc_i2c_is_opened(void);
+void phDal4Nfc_i2c_flush(void);
+void phDal4Nfc_i2c_close(void);
+NFCSTATUS phDal4Nfc_i2c_open_and_configure(pphDal4Nfc_sConfig_t pConfig, void ** pLinkHandle);
+int phDal4Nfc_i2c_read(uint8_t * pBuffer, int nNbBytesToRead);
+int phDal4Nfc_i2c_write(uint8_t * pBuffer, int nNbBytesToWrite);
+
diff --git a/Linux_x86/phDal4Nfc_link.h b/Linux_x86/phDal4Nfc_link.h
new file mode 100644
index 0000000..e26ab11
--- /dev/null
+++ b/Linux_x86/phDal4Nfc_link.h
@@ -0,0 +1,56 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phDalNfc_link.h
+ * \brief DAL generic link interface for linux
+ *
+ * Project: Trusted NFC Linux Lignt
+ *
+ * $Date: 10 aug 2009
+ * $Author: Jonathan roux
+ * $Revision: 1.0 $
+ *
+ */
+
+/**< Basic type definitions */
+#include <phNfcTypes.h>
+/**< Generic Interface Layer Function Definitions */
+#include <phNfcInterface.h>
+#include <phDal4Nfc.h>
+
+typedef void (*phDal4Nfc_link_initialize_CB_t) (void);
+typedef void (*phDal4Nfc_link_set_open_from_handle_CB_t) (phHal_sHwReference_t * pDalHwContext);
+typedef int (*phDal4Nfc_link_is_opened_CB_t) (void);
+typedef void (*phDal4Nfc_link_flush_CB_t) (void);
+typedef void (*phDal4Nfc_link_close_CB_t) (void);
+typedef NFCSTATUS (*phDal4Nfc_link_open_and_configure_CB_t) (pphDal4Nfc_sConfig_t pConfig, void ** pLinkHandle);
+typedef int (*phDal4Nfc_link_read_CB_t) (uint8_t * pBuffer, int nNbBytesToRead);
+typedef int (*phDal4Nfc_link_write_CB_t) (uint8_t * pBuffer, int nNbBytesToWrite);
+
+typedef struct
+{
+ phDal4Nfc_link_initialize_CB_t init;
+ phDal4Nfc_link_set_open_from_handle_CB_t open_from_handle;
+ phDal4Nfc_link_is_opened_CB_t is_opened;
+ phDal4Nfc_link_flush_CB_t flush;
+ phDal4Nfc_link_close_CB_t close;
+ phDal4Nfc_link_open_and_configure_CB_t open_and_configure;
+ phDal4Nfc_link_read_CB_t read;
+ phDal4Nfc_link_write_CB_t write;
+} phDal4Nfc_link_cbk_interface_t;
+
+
diff --git a/Linux_x86/phDal4Nfc_messageQueueLib.c b/Linux_x86/phDal4Nfc_messageQueueLib.c
new file mode 100644
index 0000000..30d389b
--- /dev/null
+++ b/Linux_x86/phDal4Nfc_messageQueueLib.c
@@ -0,0 +1,218 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phDalNfc_messageQueueLib.c
+ * \brief DAL independant message queue implementation for android (can be used under linux too)
+ *
+ * Project: Trusted NFC Linux Lignt
+ *
+ * $Date: 13 aug 2009
+ * $Author: Jonathan roux
+ * $Revision: 1.0 $
+ *
+ */
+
+#include <pthread.h>
+#ifdef ANDROID
+#include <linux/ipc.h>
+#else
+#include <sys/msg.h>
+#endif
+
+#include <semaphore.h>
+
+#include <phDal4Nfc.h>
+#include <phOsalNfc.h>
+#include <phDal4Nfc_DeferredCall.h>
+#include <phDal4Nfc_messageQueueLib.h>
+
+typedef struct phDal4Nfc_message_queue_item
+{
+ phLibNfc_Message_t nMsg;
+ struct phDal4Nfc_message_queue_item * pPrev;
+ struct phDal4Nfc_message_queue_item * pNext;
+} phDal4Nfc_message_queue_item_t;
+
+
+typedef struct phDal4Nfc_message_queue
+{
+ phDal4Nfc_message_queue_item_t * pItems;
+ pthread_mutex_t nCriticalSectionMutex;
+ sem_t nProcessSemaphore;
+
+} phDal4Nfc_message_queue_t;
+
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL message get function
+ * This function allocates the message queue. The parameters are ignored, this is
+ * just to keep the same api as Linux queue.
+ *
+ * \retval -1 Can not allocate memory or can not init mutex.
+* \retval handle The handle on the message queue.
+ */
+int phDal4Nfc_msgget ( key_t key, int msgflg )
+{
+ phDal4Nfc_message_queue_t * pQueue;
+ pQueue = (phDal4Nfc_message_queue_t *) phOsalNfc_GetMemory(sizeof(phDal4Nfc_message_queue_t));
+ if (pQueue == NULL)
+ return -1;
+ memset(pQueue, 0, sizeof(phDal4Nfc_message_queue_t));
+ if (pthread_mutex_init (&pQueue->nCriticalSectionMutex, NULL) == -1)
+ return -1;
+ if (sem_init (&pQueue->nProcessSemaphore, 0, 0) == -1)
+ return -1;
+ return ((int)pQueue);
+}
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL message control function
+ * This function destroys the message queue. The cmd and buf parameters are ignored,
+ * this is just to keep the same api as Linux queue.
+ *
+ * \param[in] msqid The handle of the message queue.
+ *
+ * \retval 0 If success.
+ * \retval -1 Bad passed parameter
+ */
+int phDal4Nfc_msgctl ( int msqid, int cmd, void *buf )
+{
+ phDal4Nfc_message_queue_t * pQueue;
+ phDal4Nfc_message_queue_item_t * p;
+
+ if (msqid == 0)
+ return -1;
+
+ pQueue = (phDal4Nfc_message_queue_t *)msqid;
+ pthread_mutex_lock(&pQueue->nCriticalSectionMutex);
+ if (pQueue->pItems != NULL)
+ {
+ p = pQueue->pItems;
+ while(p->pNext != NULL) { p = p->pNext; }
+ while(p->pPrev != NULL)
+ {
+ p = p->pPrev;
+ phOsalNfc_FreeMemory(p->pNext);
+ p->pNext = NULL;
+ }
+ phOsalNfc_FreeMemory(p);
+ }
+ pQueue->pItems = NULL;
+ pthread_mutex_unlock(&pQueue->nCriticalSectionMutex);
+ pthread_mutex_destroy(&pQueue->nCriticalSectionMutex);
+ phOsalNfc_FreeMemory(pQueue);
+ return 0;
+}
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL message send function
+ * Use this function to send a message to the queue. The message will be added at the end of
+ * the queue with respect to FIFO policy. The msgflg parameter is ignored.
+ *
+ * \param[in] msqid The handle of the message queue.
+ * \param[in] msgp The message to send.
+ * \param[in] msgsz The message size.
+ *
+ * \retval 0 If success.
+ * \retval -1 Bad passed parameter, or can not allocate memory
+ */
+int phDal4Nfc_msgsnd (int msqid, void * msgp, size_t msgsz, int msgflg)
+{
+ phDal4Nfc_message_queue_t * pQueue;
+ phDal4Nfc_message_queue_item_t * p;
+ phDal4Nfc_message_queue_item_t * pNew;
+
+ if ((msqid == 0) || (msgp == NULL) || (msgsz == 0))
+ return -1;
+
+ if (msgsz != sizeof(phLibNfc_Message_t))
+ return -1;
+
+ pQueue = (phDal4Nfc_message_queue_t *)msqid;
+ pNew = (phDal4Nfc_message_queue_item_t *)phOsalNfc_GetMemory(sizeof(phDal4Nfc_message_queue_item_t));
+ if (pNew == NULL)
+ return -1;
+ memset(pNew, 0, sizeof(phDal4Nfc_message_queue_item_t));
+ memcpy(&pNew->nMsg, &((phDal4Nfc_Message_Wrapper_t*)msgp)->msg, sizeof(phLibNfc_Message_t));
+ pthread_mutex_lock(&pQueue->nCriticalSectionMutex);
+ if (pQueue->pItems != NULL)
+ {
+ p = pQueue->pItems;
+ while(p->pNext != NULL) { p = p->pNext; }
+ p->pNext = pNew;
+ pNew->pPrev = p;
+ }
+ else
+ {
+ pQueue->pItems = pNew;
+ }
+ pthread_mutex_unlock(&pQueue->nCriticalSectionMutex);
+
+ sem_post(&pQueue->nProcessSemaphore);
+ return 0;
+}
+
+/**
+ * \ingroup grp_nfc_dal
+ *
+ * \brief DAL message receive function
+ * The call to this function will get the older message from the queue. If the queue is empty the function waits
+ * (blocks on a mutex) until a message is posted to the queue with phDal4Nfc_msgsnd.
+ * The msgtyp and msgflg parameters are ignored.
+ *
+ * \param[in] msqid The handle of the message queue.
+ * \param[out] msgp The received message.
+ * \param[in] msgsz The message size.
+ *
+ * \retval 0 If success.
+ * \retval -1 Bad passed parameter.
+ */
+int phDal4Nfc_msgrcv (int msqid, void * msgp, size_t msgsz, long msgtyp, int msgflg)
+{
+ phDal4Nfc_message_queue_t * pQueue;
+ phDal4Nfc_message_queue_item_t * p;
+
+ if ((msqid == 0) || (msgp == NULL))
+ return -1;
+
+ if (msgsz != sizeof(phLibNfc_Message_t))
+ return -1;
+
+ pQueue = (phDal4Nfc_message_queue_t *)msqid;
+ sem_wait(&pQueue->nProcessSemaphore);
+ pthread_mutex_lock(&pQueue->nCriticalSectionMutex);
+ if (pQueue->pItems != NULL)
+ {
+ memcpy(&((phDal4Nfc_Message_Wrapper_t*)msgp)->msg, &(pQueue->pItems)->nMsg, sizeof(phLibNfc_Message_t));
+ p = pQueue->pItems->pNext;
+ phOsalNfc_FreeMemory(pQueue->pItems);
+ pQueue->pItems = p;
+ }
+ pthread_mutex_unlock(&pQueue->nCriticalSectionMutex);
+ return 0;
+}
+
+
+
+
+
diff --git a/Linux_x86/phDal4Nfc_uart.c b/Linux_x86/phDal4Nfc_uart.c
new file mode 100644
index 0000000..9d230f1
--- /dev/null
+++ b/Linux_x86/phDal4Nfc_uart.c
@@ -0,0 +1,326 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phDalNfc_uart.c
+ * \brief DAL com port implementation for linux
+ *
+ * Project: Trusted NFC Linux Lignt
+ *
+ * $Date: 07 aug 2009
+ * $Author: Jonathan roux
+ * $Revision: 1.0 $
+ *
+ */
+
+#include <unistd.h>
+#include <fcntl.h>
+#include <termios.h>
+#include <sys/ioctl.h>
+#include <sys/select.h>
+
+#include <phDal4Nfc_debug.h>
+#include <phDal4Nfc_uart.h>
+#include <phOsalNfc.h>
+#include <phNfcStatus.h>
+#if defined(ANDROID)
+#include <string.h>
+#endif
+
+typedef struct
+{
+ int nHandle;
+ char nOpened;
+ struct termios nIoConfigBackup;
+ struct termios nIoConfig;
+
+} phDal4Nfc_ComPortContext_t;
+
+/*-----------------------------------------------------------------------------------
+ COM PORT CONFIGURATION
+------------------------------------------------------------------------------------*/
+#define DAL_BAUD_RATE B115200
+
+
+
+/*-----------------------------------------------------------------------------------
+ VARIABLES
+------------------------------------------------------------------------------------*/
+static phDal4Nfc_ComPortContext_t gComPortContext;
+
+
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_uart_set_open_from_handle
+
+PURPOSE: Initialize internal variables
+
+-----------------------------------------------------------------------------*/
+
+void phDal4Nfc_uart_initialize(void)
+{
+ memset(&gComPortContext, 0, sizeof(phDal4Nfc_ComPortContext_t));
+}
+
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_uart_set_open_from_handle
+
+PURPOSE: The application could have opened the link itself. So we just need
+ to get the handle and consider that the open operation has already
+ been done.
+
+-----------------------------------------------------------------------------*/
+
+void phDal4Nfc_uart_set_open_from_handle(phHal_sHwReference_t * pDalHwContext)
+{
+ gComPortContext.nHandle = (int) pDalHwContext->p_board_driver;
+ DAL_ASSERT_STR(gComPortContext.nHandle >= 0, "Bad passed com port handle");
+ gComPortContext.nOpened = 1;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_uart_is_opened
+
+PURPOSE: Returns if the link is opened or not. (0 = not opened; 1 = opened)
+
+-----------------------------------------------------------------------------*/
+
+int phDal4Nfc_uart_is_opened(void)
+{
+ return gComPortContext.nOpened;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_uart_flush
+
+PURPOSE: Flushes the link ; clears the link buffers
+
+-----------------------------------------------------------------------------*/
+
+void phDal4Nfc_uart_flush(void)
+{
+ int ret;
+ /* flushes the com port */
+ ret = tcflush(gComPortContext.nHandle, TCIFLUSH);
+ DAL_ASSERT_STR(ret!=-1, "tcflush failed");
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_uart_close
+
+PURPOSE: Closes the link
+
+-----------------------------------------------------------------------------*/
+
+void phDal4Nfc_uart_close(void)
+{
+ if (gComPortContext.nOpened == 1)
+ {
+ close(gComPortContext.nHandle);
+ gComPortContext.nHandle = 0;
+ gComPortContext.nOpened = 0;
+ }
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_uart_close
+
+PURPOSE: Closes the link
+
+-----------------------------------------------------------------------------*/
+
+NFCSTATUS phDal4Nfc_uart_open_and_configure(pphDal4Nfc_sConfig_t pConfig, void ** pLinkHandle)
+{
+ char * pComPort;
+ int nComStatus;
+ NFCSTATUS nfcret = NFCSTATUS_SUCCESS;
+ int ret;
+
+ DAL_ASSERT_STR(gComPortContext.nOpened==0, "Trying to open but already done!");
+
+ switch(pConfig->nLinkType)
+ {
+ case ENUM_DAL_LINK_TYPE_COM1:
+ pComPort = "/dev/ttyS0";
+ break;
+ case ENUM_DAL_LINK_TYPE_COM2:
+ pComPort = "/dev/ttyS1";
+ break;
+ case ENUM_DAL_LINK_TYPE_COM3:
+ pComPort = "/dev/ttyS2";
+ break;
+ case ENUM_DAL_LINK_TYPE_COM4:
+ pComPort = "/dev/ttyS3";
+ break;
+ case ENUM_DAL_LINK_TYPE_COM5:
+ pComPort = "/dev/ttyS4";
+ break;
+ case ENUM_DAL_LINK_TYPE_COM6:
+ pComPort = "/dev/ttyS5";
+ break;
+ case ENUM_DAL_LINK_TYPE_COM7:
+ pComPort = "/dev/ttyS6";
+ break;
+ case ENUM_DAL_LINK_TYPE_COM8:
+ pComPort = "/dev/ttyS7";
+ break;
+ case ENUM_DAL_LINK_TYPE_USB:
+ pComPort = "/dev/ttyUSB0";
+ break;
+ default:
+ return NFCSTATUS_INVALID_PARAMETER;
+ }
+
+ /* open communication port handle */
+ gComPortContext.nHandle = open(pComPort, O_RDWR | O_NOCTTY);
+ if (gComPortContext.nHandle < 0)
+ {
+ *pLinkHandle = NULL;
+ return PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_DEVICE);
+ }
+
+ gComPortContext.nOpened = 1;
+ *pLinkHandle = (void*)gComPortContext.nHandle;
+
+ /*
+ * Now configure the com port
+ */
+ ret = tcgetattr(gComPortContext.nHandle, &gComPortContext.nIoConfigBackup); /* save the old io config */
+ if (ret == -1)
+ {
+ /* tcgetattr failed -- it is likely that the provided port is invalid */
+ *pLinkHandle = NULL;
+ return PHNFCSTVAL(CID_NFC_DAL, NFCSTATUS_INVALID_DEVICE);
+ }
+ ret = fcntl(gComPortContext.nHandle, F_SETFL, 0); /* Makes the read blocking (default). */
+ DAL_ASSERT_STR(ret != -1, "fcntl failed");
+ /* Configures the io */
+ memset((void *)&gComPortContext.nIoConfig, (int)0, (size_t)sizeof(struct termios));
+ /*
+ BAUDRATE: Set bps rate. You could also use cfsetispeed and cfsetospeed.
+ CRTSCTS : output hardware flow control (only used if the cable has
+ all necessary lines. See sect. 7 of Serial-HOWTO)
+ CS8 : 8n1 (8bit,no parity,1 stopbit)
+ CLOCAL : local connection, no modem contol
+ CREAD : enable receiving characters
+ */
+ gComPortContext.nIoConfig.c_cflag = DAL_BAUD_RATE | CS8 | CLOCAL | CREAD; /* Control mode flags */
+ gComPortContext.nIoConfig.c_iflag = IGNPAR; /* Input mode flags : IGNPAR Ignore parity errors */
+ gComPortContext.nIoConfig.c_oflag = 0; /* Output mode flags */
+ gComPortContext.nIoConfig.c_lflag = 0; /* Local mode flags. Read mode : non canonical, no echo */
+ gComPortContext.nIoConfig.c_cc[VTIME] = 0; /* Control characters. No inter-character timer */
+ gComPortContext.nIoConfig.c_cc[VMIN] = 1; /* Control characters. Read is blocking until X characters are read */
+
+ /*
+ TCSANOW Make changes now without waiting for data to complete
+ TCSADRAIN Wait until everything has been transmitted
+ TCSAFLUSH Flush input and output buffers and make the change
+ */
+ ret = tcsetattr(gComPortContext.nHandle, TCSANOW, &gComPortContext.nIoConfig);
+ DAL_ASSERT_STR(ret != -1, "tcsetattr failed");
+
+ /*
+ On linux the DTR signal is set by default. That causes a problem for pn544 chip
+ because this signal is connected to "reset". So we clear it. (on windows it is cleared by default).
+ */
+ ret = ioctl(gComPortContext.nHandle, TIOCMGET, &nComStatus);
+ DAL_ASSERT_STR(ret != -1, "ioctl TIOCMGET failed");
+ nComStatus &= ~TIOCM_DTR;
+ ret = ioctl(gComPortContext.nHandle, TIOCMSET, &nComStatus);
+ DAL_ASSERT_STR(ret != -1, "ioctl TIOCMSET failed");
+ DAL_DEBUG("Com port status=%d\n", nComStatus);
+ usleep(10000); /* Mandatory sleep so that the DTR line is ready before continuing */
+
+ return nfcret;
+}
+
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_uart_read
+
+PURPOSE: Reads nNbBytesToRead bytes and writes them in pBuffer.
+ Returns the number of bytes really read or -1 in case of error.
+
+-----------------------------------------------------------------------------*/
+
+int phDal4Nfc_uart_read(uint8_t * pBuffer, int nNbBytesToRead)
+{
+ fd_set rfds;
+ struct timeval tv;
+ int ret;
+
+ DAL_ASSERT_STR(gComPortContext.nOpened == 1, "read called but not opened!");
+
+ FD_ZERO(&rfds);
+ FD_SET(gComPortContext.nHandle, &rfds);
+
+ /* select will block for 10 sec */
+ tv.tv_sec = 2;
+ tv.tv_usec = 0;
+
+ ret = select(gComPortContext.nHandle + 1, &rfds, NULL, NULL, &tv);
+
+ if (ret == -1)
+ return -1;
+
+ if (ret)
+ return read(gComPortContext.nHandle, pBuffer, nNbBytesToRead);
+
+ return 0;
+}
+
+/*-----------------------------------------------------------------------------
+
+FUNCTION: phDal4Nfc_link_write
+
+PURPOSE: Writes nNbBytesToWrite bytes from pBuffer to the link
+ Returns the number of bytes that have been wrote to the interface or -1 in case of error.
+
+-----------------------------------------------------------------------------*/
+
+int phDal4Nfc_uart_write(uint8_t * pBuffer, int nNbBytesToWrite)
+{
+ fd_set wfds;
+ struct timeval tv;
+ int ret;
+
+ DAL_ASSERT_STR(gComPortContext.nOpened == 1, "write called but not opened!");
+
+ FD_ZERO(&wfds);
+ FD_SET(gComPortContext.nHandle, &wfds);
+
+ /* select will block for 10 sec */
+ tv.tv_sec = 2;
+ tv.tv_usec = 0;
+
+ ret = select(gComPortContext.nHandle + 1, NULL, &wfds, NULL, &tv);
+
+ if (ret == -1)
+ return -1;
+
+ if (ret)
+ return write(gComPortContext.nHandle, pBuffer, nNbBytesToWrite);
+
+ return 0;
+}
diff --git a/Linux_x86/phDal4Nfc_uart.h b/Linux_x86/phDal4Nfc_uart.h
new file mode 100644
index 0000000..329f626
--- /dev/null
+++ b/Linux_x86/phDal4Nfc_uart.h
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phDalNfc_uart.h
+ * \brief DAL com port implementation for linux
+ *
+ * Project: Trusted NFC Linux Lignt
+ *
+ * $Date: 07 aug 2009
+ * $Author: Jonathan roux
+ * $Revision: 1.0 $
+ *
+ */
+
+/**< Basic type definitions */
+#include <phNfcTypes.h>
+/**< Generic Interface Layer Function Definitions */
+#include <phNfcInterface.h>
+#include <phDal4Nfc.h>
+
+void phDal4Nfc_uart_initialize(void);
+void phDal4Nfc_uart_set_open_from_handle(phHal_sHwReference_t * pDalHwContext);
+int phDal4Nfc_uart_is_opened(void);
+void phDal4Nfc_uart_flush(void);
+void phDal4Nfc_uart_close(void);
+NFCSTATUS phDal4Nfc_uart_open_and_configure(pphDal4Nfc_sConfig_t pConfig, void ** pLinkHandle);
+int phDal4Nfc_uart_read(uint8_t * pBuffer, int nNbBytesToRead);
+int phDal4Nfc_uart_write(uint8_t * pBuffer, int nNbBytesToWrite);
+
diff --git a/Linux_x86/phOsalNfc.c b/Linux_x86/phOsalNfc.c
new file mode 100644
index 0000000..ce01d26
--- /dev/null
+++ b/Linux_x86/phOsalNfc.c
@@ -0,0 +1,165 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phOsalNfc.c
+ * \brief OSAL Implementation for linux
+ *
+ * Project: Trusted NFC Linux Light
+ *
+ * $Date: 03 aug 2009
+ * $Author: Jérémie Corbier
+ * $Revision: 1.0
+ *
+ */
+
+#include <stddef.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <signal.h>
+#include <unistd.h>
+
+#include <phOsalNfc.h>
+
+#ifdef ANDROID
+#define LOG_TAG "NFC-HCI"
+
+#include <utils/Log.h>
+
+phOsalNfc_Exception_t phOsalNfc_Exception;
+#endif
+
+#ifdef DEBUG
+#define MAX_PRINT_BUFSIZE (0x450U)
+char phOsalNfc_DbgTraceBuffer[MAX_PRINT_BUFSIZE];
+#endif
+
+/*!
+ * \brief Allocates memory.
+ * This function attempts to allocate \a size bytes on the heap and
+ * returns a pointer to the allocated block.
+ *
+ * \param size size of the memory block to be allocated on the heap.
+ *
+ * \return pointer to allocated memory block or NULL in case of error.
+ */
+void *phOsalNfc_GetMemory(uint32_t size)
+{
+ void *pMem = (void *)malloc(size);
+ return pMem;
+}
+
+/*!
+ * \brief Frees allocated memory block.
+ * This function deallocates memory region pointed to by \a pMem.
+ *
+ * \param pMem pointer to memory block to be freed.
+ */
+void phOsalNfc_FreeMemory(void *pMem)
+{
+ if(NULL != pMem)
+ free(pMem);
+}
+
+void phOsalNfc_DbgString(const char *pString)
+{
+#ifdef DEBUG
+ if(pString != NULL)
+#ifndef ANDROID
+ printf(pString);
+#else
+ LOGD(pString);
+#endif
+#endif
+}
+
+void phOsalNfc_DbgTrace(uint8_t data[], uint32_t size)
+{
+#ifdef DEBUG
+ uint32_t i;
+#ifdef ANDROID
+ char buf[10];
+#endif
+
+ if(size == 0)
+ return;
+
+#ifndef ANDROID
+ for(i = 0; i < size; i++)
+ {
+ if((i % 10) == 0)
+ printf("\n\t\t\t");
+ printf("%02X ", data[i]);
+ }
+ printf("\n\tBlock size is: %d\n", size);
+#else
+ phOsalNfc_DbgTraceBuffer[0] = '\0';
+ for(i = 0; i < size; i++)
+ {
+ if((i % 10) == 0)
+ {
+ LOGD(phOsalNfc_DbgTraceBuffer);
+ phOsalNfc_DbgTraceBuffer[0] = '\0';
+ }
+
+ snprintf(buf, 10, "%02X ", data[i]);
+ strncat(phOsalNfc_DbgTraceBuffer, buf, 10);
+ }
+ LOGD(phOsalNfc_DbgTraceBuffer);
+ LOGD("Block size is: %d", size);
+#endif
+#endif
+}
+
+/*!
+ * \brief Raises exception.
+ * This function raises an exception of type \a eExceptionType with
+ * reason \a reason to stack clients.
+ *
+ * \param eExceptionType exception type.
+ * \param reason reason for this exception.
+ *
+ * \note Clients willing to catch exceptions are to handle the SIGABRT signal.
+ * On Linux, exception type and reason are passed to the signal handler as
+ * a pointer to a phOsalNfc_Exception_t structure.
+ * As sigqueue is not available in Android, exception information are
+ * stored in the phOsalNfc_Exception global.
+ */
+void phOsalNfc_RaiseException(phOsalNfc_ExceptionType_t eExceptionType, uint16_t reason)
+{
+ pid_t pid;
+#ifndef ANDROID
+ static phOsalNfc_Exception_t phOsalNfc_Exception;
+ union sigval sv;
+#endif
+
+ phOsalNfc_Exception.eExceptionType = eExceptionType;
+ phOsalNfc_Exception.reason = reason;
+
+ pid = getpid();
+
+ /*
+ * JCO: Bionic does not provide, among other things, sigqueue...
+ */
+#ifdef ANDROID
+ kill(pid, SIGABRT);
+#else
+ sv.sival_ptr = &phOsalNfc_Exception;
+
+ sigqueue(pid, SIGABRT, sv);
+#endif
+}
+
diff --git a/Linux_x86/phOsalNfc_Common.h b/Linux_x86/phOsalNfc_Common.h
new file mode 100644
index 0000000..8ca7674
--- /dev/null
+++ b/Linux_x86/phOsalNfc_Common.h
@@ -0,0 +1,78 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/*!
+ * \file phOsalNfc_Common.h
+ *
+ * Project: NFC FRI / OSAL
+ *
+ * $Workfile:: phOsalNfc_Common.h $
+ * $Modtime:: $
+ * $Author: frq09147 $
+ * $Revision: 1.1 $
+ *
+ */
+
+#ifndef PHOSALNFC_COMMON_H
+#define PHOSALNFC_COMMON_H
+#include <time.h>
+#include <unistd.h>
+#include <errno.h>
+#include <pthread.h>
+#include <semaphore.h>
+#include <signal.h>
+#include <sys/time.h>
+#include <sys/sem.h>
+
+#define MAX_MESSAGE_SIZE 256
+
+typedef enum phOsalNfc_eHandleType
+{
+ phOsalNfc_eHandleTypeInvalid = 0,
+ phOsalNfc_eHandleTypeThread = 1,
+ phOsalNfc_eHandleTypeSemaphore = 2,
+
+}phOsalNfc_eHandleType_t;
+
+typedef struct phOsalNfc_sMsg
+{
+ phOsalNfc_Message_t Msg;
+ uint32_t sourceID; /* pthread_t = unsigned long int */
+ struct phOsalNfc_sMsg *nextMsg;
+} phOsalNfc_sMsg_t;
+
+typedef struct phOsalNfc_sOsalHandle
+{
+ phOsalNfc_eHandleType_t HandleType;
+ pthread_t *pThread;
+ pphOsalNfc_ThreadFunction_t pThreadFunction;
+ void *pParams;
+
+ sem_t *pSemaphore;
+ sem_t handleSem;
+ int32_t semValue;
+ uint32_t semMax;
+
+ struct sembuf semBuf;
+ int32_t semId;
+
+ phOsalNfc_sMsg_t *pMsg;
+ sem_t msgSem;
+ struct phOsalNfc_sOsalHandle *nextThread;
+} phOsalNfc_sOsalHandle_t;
+
+
+#endif /* PHOSALNFC_COMMON_H */
diff --git a/Linux_x86/phOsalNfc_Timer.c b/Linux_x86/phOsalNfc_Timer.c
new file mode 100644
index 0000000..e448f20
--- /dev/null
+++ b/Linux_x86/phOsalNfc_Timer.c
@@ -0,0 +1,273 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phOsalNfc_Timer.c
+ * \brief OSAL Timer Implementation for linux
+ *
+ * Project: Trusted NFC Linux Light
+ *
+ * $Date: 03 aug 2009
+ * $Author: Jérémie Corbier
+ * $Revision: 1.0
+ *
+ */
+
+#include <stdlib.h>
+#include <signal.h>
+#include <time.h>
+
+#include <phOsalNfc.h>
+#include <phOsalNfc_Timer.h>
+#include <stdio.h>
+
+#include <phDal4Nfc_messageQueueLib.h>
+
+#define NSECS 1000000
+#define MAX_NO_TIMERS 16
+
+/*!
+ * \struct phOsalNfc_Timer
+ * Internal OSAL timer structure
+ */
+struct phOsalNfc_Timer
+{
+ timer_t handle; /*!< System timer handle. */
+ ppCallBck_t callback; /*!< Callback to be called when timer expires. */
+ void* pContext; /*!< Callback context. */
+#ifdef NXP_MESSAGING
+ void *ptr;
+#endif
+ int nIsStopped;
+};
+
+static struct phOsalNfc_Timer timers[MAX_NO_TIMERS] =
+{
+ {0, NULL, NULL
+#ifdef NXP_MESSAGING
+ , NULL
+#endif
+ , 0
+ },
+};
+
+#ifdef NXP_MESSAGING
+extern int nDeferedCallMessageQueueId;
+
+void phOsalNfc_Timer_DeferredCall(void *params)
+{
+ phOsalNfc_Timer_Msg_t *timer_msg;
+
+ if(params == NULL)
+ return;
+
+ timer_msg = (phOsalNfc_Timer_Msg_t *)params;
+
+ if((timer_msg != NULL) && (timer_msg->pCallBck != NULL))
+ timer_msg->pCallBck(timer_msg->TimerId, timer_msg->pContext);
+
+ if ((timer_msg->TimerId >= MAX_NO_TIMERS) || (timer_msg->TimerId < 0))
+ {
+ printf("Bad TimerId=%d, should be <= to %d\n", timer_msg->TimerId, MAX_NO_TIMERS);
+ }
+ else
+ {
+ if(timers[timer_msg->TimerId].ptr != NULL)
+ {
+ phOsalNfc_FreeMemory(timers[timer_msg->TimerId].ptr);
+ timers[timer_msg->TimerId].ptr = NULL;
+ }
+ }
+ phOsalNfc_FreeMemory(timer_msg);
+}
+#endif
+
+/*!
+ * \brief System timer callback.
+ * This callback is called by Linux whenever one the timers expires. It
+ * calls the corresponding registered callback.
+ *
+ * \param sv structure storing the expired timer ID.
+ */
+static void phOsalNfc_Timer_Expired(union sigval sv)
+{
+ uint32_t timerid = (uint32_t)(sv.sival_int);
+
+ if((timerid < MAX_NO_TIMERS)&&(timers[timerid].nIsStopped == 1))
+ {
+ //printf("phOsalNfc_Timer_Expired : Expired but already stopped TimerId=%d\n", timerid);
+ return;
+ }
+
+ if(timerid < MAX_NO_TIMERS)
+ {
+#ifndef CYCLIC_TIMER
+ phOsalNfc_Timer_Stop(timerid);
+#else
+
+#endif
+#ifdef NXP_MESSAGING
+ phOsalNfc_Timer_Msg_t *timer_msg;
+ phOsalNfc_DeferedCalldInfo_t *osal_defer_msg;
+ phDal4Nfc_Message_Wrapper_t wrapper;
+
+ timer_msg = phOsalNfc_GetMemory(sizeof(phOsalNfc_Timer_Msg_t));
+ if(timer_msg == NULL)
+ phOsalNfc_RaiseException(phOsalNfc_e_NoMemory, 0);
+
+ osal_defer_msg = phOsalNfc_GetMemory(sizeof(phOsalNfc_DeferedCalldInfo_t));
+ if(osal_defer_msg == NULL)
+ {
+ phOsalNfc_FreeMemory(timer_msg);
+ phOsalNfc_RaiseException(phOsalNfc_e_NoMemory, 0);
+ }
+
+ timer_msg->TimerId = timerid;
+ timer_msg->pCallBck = timers[timerid].callback;
+ timer_msg->pContext = timers[timerid].pContext;
+
+ osal_defer_msg->pCallback = phOsalNfc_Timer_DeferredCall;
+ osal_defer_msg->pParameter = timer_msg;
+
+ wrapper.mtype = 1;
+ wrapper.msg.eMsgType = PH_OSALNFC_TIMER_MSG;
+ wrapper.msg.pMsgData = osal_defer_msg;
+ wrapper.msg.Size = sizeof(phOsalNfc_DeferedCalldInfo_t);
+
+ timers[timerid].ptr = osal_defer_msg;
+
+ phDal4Nfc_msgsnd(nDeferedCallMessageQueueId, (void *)&wrapper,
+ sizeof(phOsalNfc_Message_t), 0);
+#else
+ (timers[timerid].callback)(timerid, timers[timerid].pContext);
+#endif
+ }
+}
+
+static void phOsalNfc_Timer_Dummy_Cb(uint32_t timerid, void *pContext) {}
+
+/*!
+ * \brief Creates a new timer.
+ * This function checks whether there is an available timer slot. If
+ * this is the case, then it reserves it for future usage and returns its
+ * ID.
+ *
+ * \return a valid timer ID or PH_OSALNFC_INVALID_TIMER_ID if an error occured.
+ */
+uint32_t phOsalNfc_Timer_Create(void)
+{
+ uint32_t timerid;
+ struct sigevent se;
+
+ se.sigev_notify = SIGEV_THREAD;
+ se.sigev_notify_function = phOsalNfc_Timer_Expired;
+ se.sigev_notify_attributes = NULL;
+
+ /* Look for available timer slot */
+ for(timerid = 0; timerid < MAX_NO_TIMERS; timerid++)
+ if(timers[timerid].callback == NULL)
+ break;
+ if(timerid == MAX_NO_TIMERS)
+ return PH_OSALNFC_INVALID_TIMER_ID;
+
+ se.sigev_value.sival_int = (int)timerid;
+
+ /* Create POSIX timer */
+ if(timer_create(CLOCK_REALTIME, &se, &(timers[timerid].handle)) == -1)
+ return PH_OSALNFC_INVALID_TIMER_ID;
+ timers[timerid].callback = phOsalNfc_Timer_Dummy_Cb;
+#ifdef NXP_MESSAGING
+ timers[timerid].ptr = NULL;
+#endif
+
+ return timerid;
+}
+
+/*!
+ * \brief Starts a timer.
+ * This function starts the timer \a TimerId with an expiration time of
+ * \a RegTimeCnt milliseconds. Each time it expires, \a
+ * Application_callback is called.
+ *
+ * \param TimerId a valid timer ID.
+ * \param RegTimeCnt expiration time in milliseconds.
+ * \param Application_callback callback to be called when timer expires.
+ */
+void phOsalNfc_Timer_Start(uint32_t TimerId,
+ uint32_t RegTimeCnt,
+ ppCallBck_t Application_callback,
+ void *pContext)
+{
+ struct itimerspec its;
+
+ if(TimerId >= MAX_NO_TIMERS)
+ return;
+ if(Application_callback == NULL)
+ return;
+ if(timers[TimerId].callback == NULL)
+ return;
+
+ its.it_interval.tv_sec = 0;
+ its.it_interval.tv_nsec = 0;
+ its.it_value.tv_sec = (RegTimeCnt * NSECS) / 1000000000;
+ its.it_value.tv_nsec = ((long)RegTimeCnt * NSECS) % 1000000000;
+
+ timers[TimerId].callback = Application_callback;
+ timers[TimerId].pContext = pContext;
+ timers[TimerId].nIsStopped = 0;
+
+ timer_settime(timers[TimerId].handle, 0, &its, NULL);
+}
+
+/*!
+ * \brief Stops a timer.
+ * This function stops an already started timer.
+ *
+ * \param TimerId a valid timer ID.
+ */
+void phOsalNfc_Timer_Stop(uint32_t TimerId)
+{
+ struct itimerspec its = {{0, 0}, {0, 0}};
+
+ if(TimerId >= MAX_NO_TIMERS)
+ return;
+ if(timers[TimerId].callback == NULL)
+ return;
+ if(timers[TimerId].nIsStopped == 1)
+ return;
+
+ timers[TimerId].nIsStopped = 1;
+ timer_settime(timers[TimerId].handle, 0, &its, NULL);
+}
+
+/*!
+ * \brief Deletes a timer.
+ * This function deletes a timer.
+ *
+ * \param TimerId a valid timer ID.
+ */
+void phOsalNfc_Timer_Delete(uint32_t TimerId)
+{
+ if(TimerId >= MAX_NO_TIMERS)
+ return;
+ if(timers[TimerId].callback == NULL)
+ return;
+
+ timer_delete(timers[TimerId].handle);
+
+ timers[TimerId].callback = NULL;
+ timers[TimerId].pContext = NULL;
+}
diff --git a/Linux_x86/phOsalNfc_Utils.c b/Linux_x86/phOsalNfc_Utils.c
new file mode 100644
index 0000000..26a28c0
--- /dev/null
+++ b/Linux_x86/phOsalNfc_Utils.c
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2010 NXP Semiconductors
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * \file phOsalNfc_Utils.c
+ * \brief OSAL Implementation.
+ *
+ * Project: NFC-FRI 1.1
+ *
+ * $Date: Wed Jun 24 10:35:10 2009 $
+ * $Author: ravindrau $
+ * $Revision: 1.1 $
+ * $Aliases: NFC_FRI1.1_WK926_R28_1,NFC_FRI1.1_WK928_R29_1,NFC_FRI1.1_WK930_R30_1,NFC_FRI1.1_WK934_PREP_1,NFC_FRI1.1_WK934_R31_1,NFC_FRI1.1_WK941_PREP1,NFC_FRI1.1_WK941_PREP2,NFC_FRI1.1_WK941_1,NFC_FRI1.1_WK943_R32_1,NFC_FRI1.1_WK949_PREP1,NFC_FRI1.1_WK943_R32_10,NFC_FRI1.1_WK943_R32_13,NFC_FRI1.1_WK943_R32_14,NFC_FRI1.1_WK1007_R33_1,NFC_FRI1.1_WK1007_R33_4,NFC_FRI1.1_WK1017_PREP1,NFC_FRI1.1_WK1017_R34_1,NFC_FRI1.1_WK1017_R34_2,NFC_FRI1.1_WK1023_R35_1 $
+ *
+ */
+
+#include <phNfcStatus.h>
+#include <phNfcCompId.h>
+#include <phNfcConfig.h>
+#include <phOsalNfc.h>
+
+
+/*The function does a comparison of two strings and returns a non zero value
+if two strings are unequal*/
+int phOsalNfc_MemCompare ( void *src, void *dest, unsigned int n )
+{
+ int8_t *b1 =(int8_t *)src;
+ int8_t *b2 =(int8_t *)dest;
+ int8_t diff = 0;
+#ifdef VERIFY_MEMORY
+ if((NULL != src) && (NULL != dest))
+#endif
+ {
+ for(;((n>0)&&(diff==0));n--,b1++,b2++)
+ {
+ diff = *b1 - *b2;
+ }
+ }
+ return (int)diff;
+}
+
+
+
+