/* Copyright 2007-2013 The MathWorks, Inc. */ /* * File: xil_data_stream.c * * SIL/PIL data stream over the rtIOStream * NOTE: the xil_ide_data_stream.c implementation does not use this module * */ /* include XIL data stream interface to implement */ #include "xil_data_stream.h" /* include XIL initialization interface to implement */ #include "xil_interface_lib.h" /* xil comms to send and receive data */ #include "xilcomms_wrapper.h" #include "rx_tx_buffer_sizes.h" #include "codeinstr_data_stream.h" #define USED_WRITE_BUFFER_SIZE (COMMAND_COMPLETE_SIZE + xilWriteDataAvail) #define TX_BUFFER_SIZE (XIL_TX_BUFFER_MEMUNIT_SIZE - COMMAND_COMPLETE_SIZE - BUFFER_HEADER_SIZE) static IOUnit_T* xilWriteBuffer = NULL; static IOUnit_T* xilWriteDataPtr; static uint16_T xilWriteDataAvail; static MemUnit_T* commandComplete; static void* pBuffer; /* not static because code instrumentation service needs it */ void* pXILCommsRTIOStream; /* reset the write buffer */ static void resetXILWriteBuffer(void) { xilWriteDataAvail = 0; xilWriteDataPtr = &xilWriteBuffer[WRITE_DATA_BUFFER_IDX]; /* ready for next command */ *commandComplete = 0; } /* send pending writes */ static XIL_DATA_STREAM_ERROR_CODE sendWriteBuffer(void) { XIL_DATA_STREAM_ERROR_CODE errorCode = XIL_DATA_STREAM_SUCCESS; if (!xilCommsEnqueue(pXILCommsRTIOStream, pBuffer, XIL_APPLICATION_ID, USED_WRITE_BUFFER_SIZE)) { /* throw flush error */ errorCode = XIL_DATA_FLUSH_ERROR; return errorCode; } /* reset */ resetXILWriteBuffer(); return errorCode; } XIL_INTERFACE_LIB_ERROR_CODE xilInit(const int argc, void *argv[]) { /* create xil comms */ XIL_INTERFACE_LIB_ERROR_CODE errorCode = XIL_INTERFACE_LIB_SUCCESS; if (!xilCommsCreate(&pXILCommsRTIOStream, argc, argv)) { errorCode = XIL_INTERFACE_LIB_ERROR; return errorCode; } /* Ask the CS to allocate a buffer that the XIL app service will use for * transmission */ if (!xilCommsAllocXILBuffer(pXILCommsRTIOStream, &pBuffer, XIL_TX_BUFFER_MEMUNIT_SIZE)) { errorCode = XIL_INTERFACE_LIB_ERROR; return errorCode; } xilWriteBuffer = xilCommsGetXILBufferDataPtr(pBuffer); /* set commandComplete pointer */ commandComplete = (MemUnit_T *) &xilWriteBuffer[COMMAND_COMPLETE_IDX]; /* reset */ resetXILWriteBuffer(); /* create code instrumentation service if required */ #ifdef CODE_INSTRUMENTATION_ENABLED if (codeInstrInit()!= XIL_INTERFACE_LIB_SUCCESS) { errorCode = XIL_INTERFACE_LIB_ERROR; return errorCode; } #endif return errorCode; } /* This function must be called prior to terminating the application in order to * ensure an orderly shutdown of communications - data will already have been sent */ XIL_INTERFACE_LIB_ERROR_CODE xilTerminateComms(void) { XIL_INTERFACE_LIB_ERROR_CODE errorCode = XIL_INTERFACE_LIB_SUCCESS; if(!xilCommsDestroy(pXILCommsRTIOStream)) { errorCode = XIL_INTERFACE_LIB_ERROR; return errorCode; } #ifdef CODE_INSTRUMENTATION_ENABLED codeInstrTerminate(); #endif return errorCode; } XIL_DATA_STREAM_ERROR_CODE xilWriteData(const MemUnit_T * src, uint32_T size) { XIL_DATA_STREAM_ERROR_CODE errorCode = XIL_DATA_STREAM_SUCCESS; const IOUnit_T * srcPtr = (const IOUnit_T *) src; size_t transferAmount; uint16_T bufferAvail; /* block until all data is processed */ while (size > 0) { /* send if we have a full message worth of data */ if (xilWriteDataAvail == TX_BUFFER_SIZE) { errorCode = sendWriteBuffer(); if (errorCode != XIL_DATA_STREAM_SUCCESS) { return errorCode; } } bufferAvail = TX_BUFFER_SIZE - xilWriteDataAvail; transferAmount = (uint16_T) MIN(bufferAvail, size); /* copy data into write buffer */ memcpy((void *) xilWriteDataPtr, srcPtr, transferAmount); size -= (uint32_T) transferAmount; xilWriteDataAvail += (uint16_T) transferAmount; srcPtr += transferAmount; xilWriteDataPtr += transferAmount; } return errorCode; } XIL_DATA_STREAM_ERROR_CODE xilDataFlush(void) { XIL_DATA_STREAM_ERROR_CODE errorCode = XIL_DATA_STREAM_SUCCESS; /* final part of command */ *commandComplete = 1; /* send the write buffer */ errorCode = sendWriteBuffer(); return errorCode; }