tEplKernel EdrvCyclicSetMaxTxBufferListSize(unsigned int uiMaxListSize_p) { tEplKernel Ret = kEplSuccessful; if (EdrvCyclicInstance_l.m_uiMaxTxBufferCount != uiMaxListSize_p) { EdrvCyclicInstance_l.m_uiMaxTxBufferCount = uiMaxListSize_p; if (EdrvCyclicInstance_l.m_paTxBufferList != NULL) { EPL_FREE(EdrvCyclicInstance_l.m_paTxBufferList); EdrvCyclicInstance_l.m_paTxBufferList = NULL; } EdrvCyclicInstance_l.m_paTxBufferList = EPL_MALLOC(sizeof (*EdrvCyclicInstance_l.m_paTxBufferList) * uiMaxListSize_p * 2); if (EdrvCyclicInstance_l.m_paTxBufferList == NULL) { Ret = kEplEdrvNoFreeBufEntry; } EdrvCyclicInstance_l.m_uiCurTxBufferList = 0; EPL_MEMSET(EdrvCyclicInstance_l.m_paTxBufferList, 0, sizeof (*EdrvCyclicInstance_l.m_paTxBufferList) * uiMaxListSize_p * 2); } return Ret; }
tEplKernel EplTimeruSetTimerMs(tEplTimerHdl *pTimerHdl_p, unsigned long ulTime_p, tEplTimerArg Argument_p) { tEplKernel Ret = kEplSuccessful; tEplTimeruData *pData; // check pointer to handle if (pTimerHdl_p == NULL) { Ret = kEplTimerInvalidHandle; goto Exit; } pData = (tEplTimeruData *) EPL_MALLOC(sizeof(tEplTimeruData)); if (pData == NULL) { Ret = kEplNoResource; goto Exit; } init_timer(&pData->m_Timer); pData->m_Timer.function = EplTimeruCbMs; pData->m_Timer.data = (unsigned long)pData; pData->m_Timer.expires = jiffies + ulTime_p * HZ / 1000; EPL_MEMCPY(&pData->TimerArgument, &Argument_p, sizeof(tEplTimerArg)); add_timer(&pData->m_Timer); *pTimerHdl_p = (tEplTimerHdl) pData; Exit: return Ret; }
static tEplKernel EplApiProcessImageCreateCompletion( tEplApiProcessImageCopyJobInt* pCopyJob_p) { tEplKernel Ret = kEplSuccessful; #if (TARGET_SYSTEM == _LINUX_) && defined(__KERNEL__) pCopyJob_p->m_Event.m_pCompletion = EPL_MALLOC(sizeof (*pCopyJob_p->m_Event.m_pCompletion)); if (pCopyJob_p->m_Event.m_pCompletion == NULL) { Ret = kEplApiPIOutOfMemory; goto Exit; } init_completion(&pCopyJob_p->m_Event.m_pCompletion->m_Completion); kref_init(&pCopyJob_p->m_Event.m_pCompletion->m_Kref); // increment ref counter once again for copy job queue reader kref_get(&pCopyJob_p->m_Event.m_pCompletion->m_Kref); EPL_MEMSET (pCopyJob_p->m_Event.m_pCompletion->m_apPageIn, 0, sizeof (pCopyJob_p->m_Event.m_pCompletion->m_apPageIn)); EPL_MEMSET (pCopyJob_p->m_Event.m_pCompletion->m_apPageOut, 0, sizeof (pCopyJob_p->m_Event.m_pCompletion->m_apPageOut)); // fetch page pointers for userspace memory Ret = EplApiProcessImageGetUserPages(&EplApiProcessImageInstance_g.m_In, &pCopyJob_p->m_CopyJob.m_In, FALSE, pCopyJob_p->m_Event.m_pCompletion->m_apPageIn); if (Ret != kEplSuccessful) { goto Exit; } Ret = EplApiProcessImageGetUserPages(&EplApiProcessImageInstance_g.m_Out, &pCopyJob_p->m_CopyJob.m_Out, TRUE, pCopyJob_p->m_Event.m_pCompletion->m_apPageOut); if (Ret != kEplSuccessful) { goto Exit; } #elif (TARGET_SYSTEM == _LINUX_) && !defined(__KERNEL__) sem_init(&pCopyJob_p->m_Event.m_semCompletion, 0, 0); #elif (TARGET_SYSTEM == _WIN32_) pCopyJob_p->m_Event.m_hEvent = CreateEvent(NULL, FALSE, FALSE, NULL); #elif (TARGET_SYSTEM == _VXWORKS_) if ((pCopyJob_p->m_Event.m_semCompletion = semBCreate(SEM_Q_FIFO, SEM_EMPTY)) == NULL) { Ret = kEplNoResource; } #else #error "OS currently not supported by EplApiProcessImage!" #endif #if (TARGET_SYSTEM == _LINUX_) && defined(__KERNEL__) Exit: #endif return Ret; }
static tEplKernel EplIdentuCbIdentResponse(tEplFrameInfo *pFrameInfo_p) { tEplKernel Ret = kEplSuccessful; unsigned int uiNodeId; unsigned int uiIndex; tEplIdentuCbResponse pfnCbResponse; uiNodeId = AmiGetByteFromLe(&pFrameInfo_p->m_pFrame->m_le_bSrcNodeId); uiIndex = uiNodeId - 1; if (uiIndex < tabentries(EplIdentuInstance_g.m_apfnCbResponse)) { // memorize pointer to callback function pfnCbResponse = EplIdentuInstance_g.m_apfnCbResponse[uiIndex]; // reset callback function pointer so that caller may issue next request immediately EplIdentuInstance_g.m_apfnCbResponse[uiIndex] = NULL; if (pFrameInfo_p->m_uiFrameSize < EPL_C_DLL_MINSIZE_IDENTRES) { // IdentResponse not received or it has invalid size if (pfnCbResponse == NULL) { // response was not requested goto Exit; } Ret = pfnCbResponse(uiNodeId, NULL); } else { // IdentResponse received if (EplIdentuInstance_g.m_apIdentResponse[uiIndex] == NULL) { // memory for IdentResponse must be allocated EplIdentuInstance_g.m_apIdentResponse[uiIndex] = EPL_MALLOC(sizeof(tEplIdentResponse)); if (EplIdentuInstance_g.m_apIdentResponse[uiIndex] == NULL) { // malloc failed if (pfnCbResponse == NULL) { // response was not requested goto Exit; } Ret = pfnCbResponse(uiNodeId, &pFrameInfo_p-> m_pFrame->m_Data. m_Asnd.m_Payload. m_IdentResponse); goto Exit; } } // copy IdentResponse to instance structure EPL_MEMCPY(EplIdentuInstance_g. m_apIdentResponse[uiIndex], &pFrameInfo_p->m_pFrame->m_Data.m_Asnd. m_Payload.m_IdentResponse, sizeof(tEplIdentResponse)); if (pfnCbResponse == NULL) { // response was not requested goto Exit; } Ret = pfnCbResponse(uiNodeId, EplIdentuInstance_g. m_apIdentResponse[uiIndex]); } } Exit: return Ret; }
tEplKernel PUBLIC EplCfmuCbObdAccess(tEplObdCbParam MEM* pParam_p) { tEplKernel Ret = kEplSuccessful; tEplObdVStringDomain* pMemVStringDomain; tEplCfmuNodeInfo* pNodeInfo = NULL; BYTE* pbBuffer; pParam_p->m_dwAbortCode = 0; if ((pParam_p->m_uiIndex != 0x1F22) || (pParam_p->m_ObdEvent != kEplObdEvWrStringDomain)) { goto Exit; } // abort any running SDO transfer pNodeInfo = EPL_CFMU_GET_NODEINFO(pParam_p->m_uiSubIndex); if ((pNodeInfo != NULL) && (pNodeInfo->m_SdoComConHdl != ~0)) { Ret = EplSdoComSdoAbort(pNodeInfo->m_SdoComConHdl, EPL_SDOAC_DATA_NOT_TRANSF_DUE_DEVICE_STATE); } pMemVStringDomain = pParam_p->m_pArg; if ((pMemVStringDomain->m_ObjSize != pMemVStringDomain->m_DownloadSize) || (pMemVStringDomain->m_pData == NULL)) { pNodeInfo = EplCfmuAllocNodeInfo(pParam_p->m_uiSubIndex); if (pNodeInfo == NULL) { pParam_p->m_dwAbortCode = EPL_SDOAC_OUT_OF_MEMORY; Ret = kEplNoResource; goto Exit; } pbBuffer = pNodeInfo->m_pbObdBufferConciseDcf; if (pbBuffer != NULL) { EPL_FREE(pbBuffer); pNodeInfo->m_pbObdBufferConciseDcf = NULL; } pbBuffer = EPL_MALLOC(pMemVStringDomain->m_DownloadSize); if (pbBuffer == NULL) { pParam_p->m_dwAbortCode = EPL_SDOAC_OUT_OF_MEMORY; Ret = kEplNoResource; goto Exit; } pNodeInfo->m_pbObdBufferConciseDcf = pbBuffer; pMemVStringDomain->m_pData = pbBuffer; pMemVStringDomain->m_ObjSize = pMemVStringDomain->m_DownloadSize; } Exit: return Ret; }
static tEplCfmuNodeInfo* EplCfmuAllocNodeInfo(unsigned int uiNodeId_p) { tEplCfmuNodeInfo* pNodeInfo = NULL; if ((uiNodeId_p == 0) || (uiNodeId_p > EPL_NMT_MAX_NODE_ID)) { goto Exit; } pNodeInfo = EPL_CFMU_GET_NODEINFO(uiNodeId_p); if (pNodeInfo != NULL) { goto Exit; } pNodeInfo = EPL_MALLOC(sizeof (*pNodeInfo)); EPL_MEMSET(pNodeInfo, 0, sizeof (*pNodeInfo)); pNodeInfo->m_EventCnProgress.m_uiNodeId = uiNodeId_p; pNodeInfo->m_SdoComConHdl = ~0U; EPL_CFMU_GET_NODEINFO(uiNodeId_p) = pNodeInfo; Exit: return pNodeInfo; }
tEplKernel PUBLIC EplApiProcessImageAlloc( unsigned int uiSizeProcessImageIn_p, unsigned int uiSizeProcessImageOut_p, unsigned int uiQueueEntriesLo_p, unsigned int uiQueueEntriesHi_p) { tEplKernel Ret = kEplSuccessful; tShbError ShbError; unsigned int fShbNewCreated; TRACE("%s: Alloc(%u, %u, %u, %u)\n", __func__, uiSizeProcessImageIn_p, uiSizeProcessImageOut_p, uiQueueEntriesLo_p, uiQueueEntriesHi_p); if ((EplApiProcessImageInstance_g.m_In.m_pImage != NULL) || (EplApiProcessImageInstance_g.m_Out.m_pImage != NULL)) { Ret = kEplApiPIAlreadyAllocated; goto Exit; } EplApiProcessImageInstance_g.m_In.m_pImage = EPL_MALLOC(uiSizeProcessImageIn_p); if (EplApiProcessImageInstance_g.m_In.m_pImage == NULL) { Ret = kEplApiPIOutOfMemory; goto Exit; } EPL_MEMSET(EplApiProcessImageInstance_g.m_In.m_pImage, 0, sizeof(uiSizeProcessImageIn_p)); EplApiProcessImageInstance_g.m_In.m_uiSize = uiSizeProcessImageIn_p; EplApiProcessImageInstance_g.m_Out.m_pImage = EPL_MALLOC(uiSizeProcessImageOut_p); if (EplApiProcessImageInstance_g.m_Out.m_pImage == NULL) { Ret = kEplApiPIOutOfMemory; goto Exit; } EPL_MEMSET(EplApiProcessImageInstance_g.m_Out.m_pImage, 0, sizeof(uiSizeProcessImageOut_p)); EplApiProcessImageInstance_g.m_Out.m_uiSize = uiSizeProcessImageOut_p; TRACE("%s: Alloc(%p, %u, %p, %u)\n", __func__, EplApiProcessImageInstance_g.m_In.m_pImage, EplApiProcessImageInstance_g.m_In.m_uiSize, EplApiProcessImageInstance_g.m_Out.m_pImage, EplApiProcessImageInstance_g.m_Out.m_uiSize); ShbError = ShbCirAllocBuffer (uiQueueEntriesLo_p * sizeof (tEplApiProcessImageCopyJobInt), EPL_API_PI_BUFFER_ID_LO, &EplApiProcessImageInstance_g.m_ShbInstanceJobQueueLo, &fShbNewCreated); // returns kShbOk, kShbOpenMismatch, kShbOutOfMem or kShbInvalidArg if (ShbError != kShbOk) { Ret = kEplNoResource; goto Exit; } ShbError = ShbCirAllocBuffer (uiQueueEntriesHi_p * sizeof (tEplApiProcessImageCopyJobInt), EPL_API_PI_BUFFER_ID_HI, &EplApiProcessImageInstance_g.m_ShbInstanceJobQueueHi, &fShbNewCreated); // returns kShbOk, kShbOpenMismatch, kShbOutOfMem or kShbInvalidArg if (ShbError != kShbOk) { Ret = kEplNoResource; goto Exit; } EplApiProcessImageInstance_g.m_pfnOrgCbSync = EplDllkRegSyncHandler(EplApiProcessImageCbSync); Exit: return Ret; }
tEplKernel EplPdokAlloc(tEplPdoAllocationParam* pAllocationParam_p) { tEplKernel Ret = kEplSuccessful; unsigned int uiIndex; #if EPL_NMT_MAX_NODE_ID > 0 tEplDllNodeOpParam NodeOpParam; NodeOpParam.m_OpNodeType = kEplDllNodeOpTypeFilterPdo; NodeOpParam.m_uiNodeId = EPL_C_ADR_BROADCAST; Ret = EplDllkDeleteNode(&NodeOpParam); if (Ret != kEplSuccessful) { goto Exit; } #endif // EPL_NMT_MAX_NODE_ID > 0 if (EplPdokInstance_g.m_Allocation.m_uiRxPdoChannelCount != pAllocationParam_p->m_uiRxPdoChannelCount) { // allocation should be changed EplPdokInstance_g.m_Allocation.m_uiRxPdoChannelCount = pAllocationParam_p->m_uiRxPdoChannelCount; if (EplPdokInstance_g.m_pRxPdoChannel != NULL) { EPL_FREE(EplPdokInstance_g.m_pRxPdoChannel); EplPdokInstance_g.m_pRxPdoChannel = NULL; } if (EplPdokInstance_g.m_paRxObject != NULL) { EPL_FREE(EplPdokInstance_g.m_paRxObject); EplPdokInstance_g.m_paRxObject = NULL; } if (pAllocationParam_p->m_uiRxPdoChannelCount > 0) { EplPdokInstance_g.m_pRxPdoChannel = EPL_MALLOC(sizeof (*EplPdokInstance_g.m_pRxPdoChannel) * pAllocationParam_p->m_uiRxPdoChannelCount); if (EplPdokInstance_g.m_pRxPdoChannel == NULL) { Ret = kEplPdoInitError; goto Exit; } EplPdokInstance_g.m_paRxObject = EPL_MALLOC(sizeof (*EplPdokInstance_g.m_paRxObject) * pAllocationParam_p->m_uiRxPdoChannelCount); if (EplPdokInstance_g.m_paRxObject == NULL) { Ret = kEplPdoInitError; goto Exit; } } } // disable all RPDOs for (uiIndex = 0; uiIndex < pAllocationParam_p->m_uiRxPdoChannelCount; uiIndex++) { EplPdokInstance_g.m_pRxPdoChannel[uiIndex].m_uiNodeId = EPL_PDO_INVALID_NODE_ID; } if (EplPdokInstance_g.m_Allocation.m_uiTxPdoChannelCount != pAllocationParam_p->m_uiTxPdoChannelCount) { // allocation should be changed EplPdokInstance_g.m_Allocation.m_uiTxPdoChannelCount = pAllocationParam_p->m_uiTxPdoChannelCount; if (EplPdokInstance_g.m_pTxPdoChannel != NULL) { EPL_FREE(EplPdokInstance_g.m_pTxPdoChannel); EplPdokInstance_g.m_pTxPdoChannel = NULL; } if (EplPdokInstance_g.m_paTxObject != NULL) { EPL_FREE(EplPdokInstance_g.m_paTxObject); EplPdokInstance_g.m_paTxObject = NULL; } if (pAllocationParam_p->m_uiTxPdoChannelCount > 0) { EplPdokInstance_g.m_pTxPdoChannel = EPL_MALLOC(sizeof (*EplPdokInstance_g.m_pTxPdoChannel) * pAllocationParam_p->m_uiTxPdoChannelCount); if (EplPdokInstance_g.m_pTxPdoChannel == NULL) { Ret = kEplPdoInitError; goto Exit; } EplPdokInstance_g.m_paTxObject = EPL_MALLOC(sizeof (*EplPdokInstance_g.m_paTxObject) * pAllocationParam_p->m_uiTxPdoChannelCount); if (EplPdokInstance_g.m_paTxObject == NULL) { Ret = kEplPdoInitError; goto Exit; } } } // disable all TPDOs for (uiIndex = 0; uiIndex < pAllocationParam_p->m_uiTxPdoChannelCount; uiIndex++) { EplPdokInstance_g.m_pTxPdoChannel[uiIndex].m_uiNodeId = EPL_PDO_INVALID_NODE_ID; } Exit: return Ret; }
tEplKernel PUBLIC EplTimeruAddInstance(void) { int nIdx; tEplKernel Ret; Ret = kEplSuccessful; // reset instance structure EPL_MEMSET(&EplTimeruInstance_g, 0, sizeof (EplTimeruInstance_g)); EplTimeruInstance_g.m_pEntries = EPL_MALLOC(sizeof (tTimerEntry) * EPL_TIMERU_MAX_ENTRIES); if (EplTimeruInstance_g.m_pEntries == NULL) { // allocating of timer entries failed Ret = kEplNoResource; goto Exit; } EplTimeruInstance_g.m_pTimerListFirst = NULL; // fill free timer list for (nIdx = 0; nIdx < EPL_TIMERU_MAX_ENTRIES-1; nIdx++) { EplTimeruInstance_g.m_pEntries[nIdx].m_pNext = &EplTimeruInstance_g.m_pEntries[nIdx+1]; } EplTimeruInstance_g.m_pEntries[EPL_TIMERU_MAX_ENTRIES-1].m_pNext = NULL; EplTimeruInstance_g.m_pFreeListFirst = EplTimeruInstance_g.m_pEntries; EplTimeruInstance_g.m_uiFreeEntries = EPL_TIMERU_MAX_ENTRIES; EplTimeruInstance_g.m_uiMinFreeEntries = EPL_TIMERU_MAX_ENTRIES; // set start time to a value which is in any case less or equal than EplTimeruGetTickCountMs() // -> the only solution = 0 EplTimeruInstance_g.m_dwStartTimeMs = 0; #if (TARGET_SYSTEM == _WIN32_) InitializeCriticalSection(&EplTimeruInstance_g.m_aCriticalSections[TIMERU_TIMER_LIST]); InitializeCriticalSection(&EplTimeruInstance_g.m_aCriticalSections[TIMERU_FREE_LIST]); EplTimeruInstance_g.m_ahEvents[TIMERU_EVENT_WAKEUP] = CreateEvent(NULL, FALSE, FALSE, NULL); EplTimeruInstance_g.m_ahEvents[TIMERU_EVENT_SHUTDOWN] = CreateEvent(NULL, FALSE, FALSE, NULL); if (EplTimeruInstance_g.m_ahEvents[TIMERU_EVENT_WAKEUP] == NULL || EplTimeruInstance_g.m_ahEvents[TIMERU_EVENT_SHUTDOWN] == NULL) { Ret = kEplTimerThreadError; goto Exit; } EplTimeruInstance_g.m_hProcessThread = CreateThread(NULL, 0, EplTimeruProcessThread, NULL, 0, NULL); if (EplTimeruInstance_g.m_hProcessThread == NULL) { Ret = kEplTimerThreadError; goto Exit; } #endif Exit: return Ret; }
static tEplKernel EplObdCdcLoadNextBuffer(tEplObdCdcInfo* pCdcInfo_p, size_t iBufferSize) { tEplKernel Ret = kEplSuccessful; int iReadSize; BYTE* pbBuffer; switch (pCdcInfo_p->m_Type) { case kEplObdCdcTypeFile: { if (pCdcInfo_p->m_iBufferSize < iBufferSize) { if (pCdcInfo_p->m_pbCurBuffer != NULL) { EPL_FREE(pCdcInfo_p->m_pbCurBuffer); pCdcInfo_p->m_pbCurBuffer = NULL; pCdcInfo_p->m_iBufferSize = 0; } pCdcInfo_p->m_pbCurBuffer = EPL_MALLOC(iBufferSize); if (pCdcInfo_p->m_pbCurBuffer == NULL) { Ret = EplEventuPostError(kEplEventSourceObdu, kEplObdOutOfMemory, 0, NULL); if (Ret != kEplSuccessful) { goto Exit; } Ret = kEplReject; goto Exit; } pCdcInfo_p->m_iBufferSize = iBufferSize; } pbBuffer = pCdcInfo_p->m_pbCurBuffer; do { iReadSize = read(pCdcInfo_p->m_Handle.m_hCdcFile, pbBuffer, iBufferSize); if (iReadSize <= 0) { Ret = EplEventuPostError(kEplEventSourceObdu, kEplObdInvalidDcf, 0, NULL); if (Ret != kEplSuccessful) { goto Exit; } Ret = kEplReject; goto Exit; } pbBuffer += iReadSize; iBufferSize -= iReadSize; pCdcInfo_p->m_iCdcSize -= iReadSize; } while (iBufferSize > 0); break; } case kEplObdCdcTypeBuffer: { if (pCdcInfo_p->m_iBufferSize < iBufferSize) { Ret = EplEventuPostError(kEplEventSourceObdu, kEplObdInvalidDcf, 0, NULL); if (Ret != kEplSuccessful) { goto Exit; } Ret = kEplReject; goto Exit; } pCdcInfo_p->m_pbCurBuffer = pCdcInfo_p->m_Handle.m_pbNextBuffer; pCdcInfo_p->m_Handle.m_pbNextBuffer += iBufferSize; pCdcInfo_p->m_iBufferSize -= iBufferSize; break; } } Exit: return Ret; }