这是对此处讨论的后续行动:
https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1500812/am6422-ipc-delay
您好、
关于 rpmsg 的使用、库函数中有许多中断禁用/启用操作。 这些操作目前正在影响我的实时内核中的其他中断。 这些中断禁用/启用操作是否必要? 为什么这样实施?
RPMessage_LocalMsg *RPMessage_allocEndPtMsg(uint32_t remoteCoreId) { RPMessage_Core *coreObj = &gIpcRpmsgCtrl.coreObj[remoteCoreId]; RPMessage_LocalMsg *pMsg; uint32_t oldIntState; oldIntState = HwiP_disable(); pMsg = (RPMessage_LocalMsg*)RPMessage_queueGet(&coreObj->freeQ); if(pMsg == NULL) { coreObj->freeQAllocPending = 1; } else { coreObj->freeQAllocPending = 0; } HwiP_restore(oldIntState); return pMsg; } uint32_t RPMessage_freeEndPtMsg(uint16_t remoteCoreId, RPMessage_LocalMsg *pMsg) { RPMessage_Core *coreObj = &gIpcRpmsgCtrl.coreObj[remoteCoreId]; uint32_t oldIntState, isAllocPending; oldIntState = HwiP_disable(); isAllocPending = coreObj->freeQAllocPending; RPMessage_queuePut(&coreObj->freeQ, &pMsg->elem); HwiP_restore(oldIntState); return isAllocPending; } void RPMessage_putEndPtMsg(RPMessage_Struct *obj, RPMessage_LocalMsg *pMsg) { uint32_t oldIntState; oldIntState = HwiP_disable(); RPMessage_queuePut(&obj->endPtQ, &pMsg->elem); HwiP_restore(oldIntState); SemaphoreP_post(&obj->newEndPtMsgSem); } int32_t RPMessage_getEndPtMsg(RPMessage_Struct *obj, RPMessage_LocalMsg **pMsg, uint32_t timeout) { uint32_t oldIntState, done; int32_t status = SystemP_TIMEOUT; done = 0; do { oldIntState = HwiP_disable(); *pMsg = (RPMessage_LocalMsg*)RPMessage_queueGet(&obj->endPtQ); HwiP_restore(oldIntState); if(*pMsg==NULL) { status = SemaphoreP_pend(&obj->newEndPtMsgSem, timeout); if(status == SystemP_TIMEOUT) { done = 1; } if(status == SystemP_SUCCESS && obj->doRecvUnblock) { status = SystemP_TIMEOUT; done = 1; } } else { status = SystemP_SUCCESS; done = 1; } } while( ! done ); return status; } int32_t RPMessage_vringGetEmptyTxBuf(uint16_t remoteCoreId, uint16_t *vringBufId, uint32_t timeout) { RPMessage_Core *coreObj = &gIpcRpmsgCtrl.coreObj[remoteCoreId]; RPMessage_Vring *vringObj = &coreObj->vringTxObj; uint32_t oldIntState; uint16_t head; int32_t status = SystemP_FAILURE; uint32_t done = 0; oldIntState = HwiP_disable(); do { /* There's nothing available */ if (vringObj->lastAvailIdx == vringObj->avail->idx) { /* We need to know about added buffers */ vringObj->used->flags &= (uint16_t)~VRING_USED_F_NO_NOTIFY; HwiP_restore(oldIntState); status = SemaphoreP_pend(&coreObj->newEmptyVringBufSem, timeout); if(status==SystemP_TIMEOUT) { done = 1; } oldIntState = HwiP_disable(); } else { head = vringObj->avail->ring[vringObj->lastAvailIdx % vringObj->vringNumBuf]; vringObj->lastAvailIdx++; *vringBufId = head; done = 1; status = SystemP_SUCCESS; } } while( ! done ); HwiP_restore(oldIntState); return status; } void RPMessage_vringPutFullTxBuf(uint16_t remoteCoreId, uint16_t vringBufId, uint16_t dataLen) { RPMessage_Core *coreObj = &gIpcRpmsgCtrl.coreObj[remoteCoreId]; RPMessage_Vring *vringObj = &coreObj->vringTxObj; struct vring_used_elem *used; uint32_t oldIntState; uint32_t txMsgValue = RPMESSAGE_MSG_VRING_NEW_FULL; if(RPMessage_isLinuxCore(remoteCoreId)) { /* for linux we need to send the TX VRING ID in the mailbox message */ txMsgValue = RPMESSAGE_LINUX_TX_VRING_ID; } oldIntState = HwiP_disable(); used = &vringObj->used->ring[vringObj->used->idx % vringObj->vringNumBuf]; used->id = vringBufId; used->len = dataLen; vringObj->used->idx++; #if defined(__aarch64__) || defined(__arm__) __asm__ __volatile__ ( "dsb sy" "\n\t": : : "memory"); __asm__ __volatile__ ( "isb sy" "\n\t": : : "memory"); #endif #if defined(_TMS320C6X) _mfence(); _mfence(); #endif HwiP_restore(oldIntState); IpcNotify_sendMsg(remoteCoreId, IPC_NOTIFY_CLIENT_ID_RPMSG, txMsgValue, 1 /* wait for message to be posted */ ); } void RPMessage_vringCheckEmptyTxBuf(uint16_t remoteCoreId) { RPMessage_Core *coreObj = &gIpcRpmsgCtrl.coreObj[remoteCoreId]; RPMessage_Vring *vringObj = &coreObj->vringTxObj; uint32_t isNewEmptyBuf = 1; uint32_t oldIntState; oldIntState = HwiP_disable(); if (vringObj->lastAvailIdx == vringObj->avail->idx) { isNewEmptyBuf = 0; } HwiP_restore(oldIntState); if(isNewEmptyBuf) { SemaphoreP_post(&coreObj->newEmptyVringBufSem); } }