#include <sys/cdefs.h>
#include <dev/pms/config.h>
#include <dev/pms/RefTisa/sallsdk/spc/saglobal.h>
#ifdef SA_ENABLE_TRACE_FUNCTIONS
#ifdef siTraceFileID
#undef siTraceFileID
#endif
#define siTraceFileID 'A'
#endif
#ifdef LOOPBACK_MPI
extern int loopback;
#endif
void mpiRequirementsGet(mpiConfig_t* config, mpiMemReq_t* memoryRequirement)
{
bit32 qIdx, numq;
mpiMemReq_t* memoryMap;
SA_DBG2(("Entering function:mpiRequirementsGet\n"));
SA_ASSERT((NULL != config), "config argument cannot be null");
memoryMap = memoryRequirement;
memoryMap->count = 0;
memoryMap->region[memoryMap->count].numElements = 1;
memoryMap->region[memoryMap->count].elementSize = sizeof(bit8) * config->mainConfig.eventLogSize;
memoryMap->region[memoryMap->count].totalLength = sizeof(bit8) * config->mainConfig.eventLogSize;
memoryMap->region[memoryMap->count].alignment = 32;
memoryMap->region[memoryMap->count].type = AGSA_DMA_MEM;
SA_DBG2(("mpiRequirementsGet:eventLogSize region[%d] 0x%X\n",memoryMap->count,memoryMap->region[memoryMap->count].totalLength ));
memoryMap->count++;
SA_DBG2(("mpiRequirementsGet:eventLogSize region[%d] 0x%X\n",memoryMap->count,memoryMap->region[memoryMap->count].totalLength ));
memoryMap->region[memoryMap->count].numElements = 1;
memoryMap->region[memoryMap->count].elementSize = sizeof(bit8) * config->mainConfig.IOPeventLogSize;
memoryMap->region[memoryMap->count].totalLength = sizeof(bit8) * config->mainConfig.IOPeventLogSize;
memoryMap->region[memoryMap->count].alignment = 32;
memoryMap->region[memoryMap->count].type = AGSA_DMA_MEM;
SA_DBG2(("mpiRequirementsGet:IOPeventLogSize region[%d] 0x%X\n",memoryMap->count,memoryMap->region[memoryMap->count].totalLength ));
memoryMap->count++;
memoryMap->region[memoryMap->count].numElements = 1;
memoryMap->region[memoryMap->count].elementSize = sizeof(bit32) * config->numInboundQueues;
memoryMap->region[memoryMap->count].totalLength = sizeof(bit32) * config->numInboundQueues;
memoryMap->region[memoryMap->count].alignment = 4;
memoryMap->region[memoryMap->count].type = AGSA_DMA_MEM;
SA_DBG2(("mpiRequirementsGet:numInboundQueues region[%d] 0x%X\n",memoryMap->count,memoryMap->region[memoryMap->count].totalLength ));
memoryMap->count++;
memoryMap->region[memoryMap->count].numElements = 1;
memoryMap->region[memoryMap->count].elementSize = sizeof(bit32) * config->numOutboundQueues;
memoryMap->region[memoryMap->count].totalLength = sizeof(bit32) * config->numOutboundQueues;
memoryMap->region[memoryMap->count].alignment = 4;
memoryMap->region[memoryMap->count].type = AGSA_DMA_MEM;
SA_DBG2(("mpiRequirementsGet:numOutboundQueues region[%d] 0x%X\n",memoryMap->count,memoryMap->region[memoryMap->count].totalLength ));
memoryMap->count++;
numq = 0;
for(qIdx = 0; qIdx < config->numInboundQueues; qIdx++)
{
if(0 != config->inboundQueues[qIdx].numElements)
{
bit32 memSize = config->inboundQueues[qIdx].numElements * config->inboundQueues[qIdx].elementSize;
bit32 remainder = memSize & 127;
if (remainder > 0)
{
memSize += (128 - remainder);
}
if (numq == 0)
{
memoryMap->region[memoryMap->count].numElements = 1;
memoryMap->region[memoryMap->count].elementSize = memSize;
memoryMap->region[memoryMap->count].totalLength = memSize;
memoryMap->region[memoryMap->count].alignment = 128;
memoryMap->region[memoryMap->count].type = AGSA_CACHED_DMA_MEM;
}
else
{
memoryMap->region[memoryMap->count].elementSize += memSize;
memoryMap->region[memoryMap->count].totalLength += memSize;
}
numq++;
if ((0 == ((qIdx + 1) % MAX_QUEUE_EACH_MEM)) ||
(qIdx == (bit32)(config->numInboundQueues - 1)))
{
SA_DBG2(("mpiRequirementsGet: (inboundQueues) memoryMap->region[%d].elementSize = %d\n",
memoryMap->count, memoryMap->region[memoryMap->count].elementSize));
SA_DBG2(("mpiRequirementsGet: (inboundQueues) memoryMap->region[%d].numElements = %d\n",
memoryMap->count, memoryMap->region[memoryMap->count].numElements));
memoryMap->count++;
numq = 0;
}
}
}
numq = 0;
for(qIdx = 0; qIdx < config->numOutboundQueues; qIdx++)
{
if(0 != config->outboundQueues[qIdx].numElements)
{
bit32 memSize = config->outboundQueues[qIdx].numElements * config->outboundQueues[qIdx].elementSize;
bit32 remainder = memSize & 127;
if (remainder > 0)
{
memSize += (128 - remainder);
}
if (numq == 0)
{
memoryMap->region[memoryMap->count].numElements = 1;
memoryMap->region[memoryMap->count].elementSize = memSize;
memoryMap->region[memoryMap->count].totalLength = memSize;
memoryMap->region[memoryMap->count].alignment = 128;
memoryMap->region[memoryMap->count].type = AGSA_CACHED_DMA_MEM;
}
else
{
memoryMap->region[memoryMap->count].elementSize += memSize;
memoryMap->region[memoryMap->count].totalLength += memSize;
}
numq++;
if ((0 == ((qIdx + 1) % MAX_QUEUE_EACH_MEM)) ||
(qIdx == (bit32)(config->numOutboundQueues - 1)))
{
SA_DBG2(("mpiRequirementsGet: (outboundQueues) memoryMap->region[%d].elementSize = %d\n",
memoryMap->count, memoryMap->region[memoryMap->count].elementSize));
SA_DBG2(("mpiRequirementsGet: (outboundQueues) memoryMap->region[%d].numElements = %d\n",
memoryMap->count, memoryMap->region[memoryMap->count].numElements));
memoryMap->count++;
numq = 0;
}
}
}
}
GLOBAL FORCEINLINE
bit32
mpiMsgFreeGet(
mpiICQueue_t *circularQ,
bit16 messageSize,
void** messagePtr
)
{
bit32 offset;
agsaRoot_t *agRoot=circularQ->agRoot;
mpiMsgHeader_t *msgHeader;
bit8 bcCount = 1;
SA_DBG4(("Entering function:mpiMsgFreeGet\n"));
SA_ASSERT(NULL != circularQ, "circularQ cannot be null");
SA_ASSERT(NULL != messagePtr, "messagePtr argument cannot be null");
SA_ASSERT(0 != circularQ->numElements, "The number of elements in this queue is 0");
if(messageSize > circularQ->elementSize)
{
SA_DBG1(("mpiMsgFreeGet: Message Size (%d) is larger than Q element size (%d)\n",messageSize,circularQ->elementSize));
return AGSA_RC_FAILURE;
}
OSSA_READ_LE_32(circularQ->agRoot, &circularQ->consumerIdx, circularQ->ciPointer, 0);
if (((circularQ->producerIdx + bcCount) % circularQ->numElements) == circularQ->consumerIdx)
{
*messagePtr = NULL;
smTrace(hpDBG_VERY_LOUD,"Za", (((circularQ->producerIdx & 0xFFF) << 16) | (circularQ->consumerIdx & 0xFFF) ));
ossaHwRegRead(agRoot, MSGU_HOST_SCRATCH_PAD_0);
SA_DBG1(("mpiMsgFreeGet: %d + %d == %d AGSA_RC_BUSY\n",circularQ->producerIdx,bcCount,circularQ->consumerIdx));
return AGSA_RC_BUSY;
}
smTrace(hpDBG_VERY_LOUD,"Zb", (((circularQ->producerIdx & 0xFFF) << 16) | (circularQ->consumerIdx & 0xFFF) ));
offset = circularQ->producerIdx * circularQ->elementSize;
circularQ->producerIdx = (circularQ->producerIdx + bcCount) % circularQ->numElements;
msgHeader = (mpiMsgHeader_t*) (((bit8 *)(circularQ->memoryRegion.virtPtr)) + offset);
SA_DBG3(("mpiMsgFreeGet: msgHeader = %p Offset = 0x%x\n", (void *)msgHeader, offset));
msgHeader->Header = (1<<24);
*messagePtr = ((bit8*)msgHeader) + sizeof(mpiMsgHeader_t);
return AGSA_RC_SUCCESS;
}
#ifdef LOOPBACK_MPI
GLOBAL bit32 mpiMsgFreeGetOQ(mpiOCQueue_t *circularQ, bit16 messageSize, void** messagePtr)
{
bit32 offset;
mpiMsgHeader_t *msgHeader;
bit8 bcCount = 1;
SA_DBG4(("Entering function:mpiMsgFreeGet\n"));
SA_ASSERT(NULL != circularQ, "circularQ cannot be null");
SA_ASSERT(NULL != messagePtr, "messagePtr argument cannot be null");
SA_ASSERT(0 != circularQ->numElements, "The number of elements in this queue is 0");
if(messageSize > circularQ->elementSize)
{
SA_DBG1(("mpiMsgFreeGet: Message Size is not fit in\n"));
return AGSA_RC_FAILURE;
}
if (((circularQ->producerIdx + bcCount) % circularQ->numElements) == circularQ->consumerIdx)
{
*messagePtr = NULL;
return AGSA_RC_BUSY;
}
offset = circularQ->producerIdx * circularQ->elementSize;
circularQ->producerIdx = (circularQ->producerIdx + bcCount) % circularQ->numElements;
msgHeader = (mpiMsgHeader_t*) (((bit8 *)(circularQ->memoryRegion.virtPtr)) + offset);
SA_DBG3(("mpiMsgFreeGet: msgHeader = %p Offset = 0x%x\n", (void *)msgHeader, offset));
msgHeader->Header = (1<<24);
*messagePtr = ((bit8*)msgHeader) + sizeof(mpiMsgHeader_t);
return AGSA_RC_SUCCESS;
}
#endif
#ifdef FAST_IO_TEST
GLOBAL bit32 mpiMsgPrepare(
mpiICQueue_t *circularQ,
void *messagePtr,
mpiMsgCategory_t category,
bit16 opCode,
bit8 responseQueue,
bit8 hiPriority
)
{
mpiMsgHeader_t *msgHeader;
bit32 bc;
bit32 Header = 0;
bit32 hpriority = 0;
SA_DBG4(("Entering function:mpiMsgProduce\n"));
SA_ASSERT(NULL != circularQ, "circularQ argument cannot be null");
SA_ASSERT(NULL != messagePtr, "messagePtr argument cannot be null");
SA_ASSERT(0 != circularQ->numElements, "The number of elements in this queue"
" is 0");
SA_ASSERT(MPI_MAX_OUTBOUND_QUEUES > responseQueue, "oQueue ID is wrong");
msgHeader = (mpiMsgHeader_t*)(((bit8*)messagePtr) - sizeof(mpiMsgHeader_t));
bc = (((msgHeader->Header) >> SHIFT24) & BC_MASK);
SA_DBG6(("mpiMsgProduce: msgHeader bc %d\n", bc));
if (circularQ->priority)
hpriority = 1;
SA_ASSERT(0 != bc, "The message buffer is not in \"allocated\" state "
"(bc == 0)");
Header = ((V_BIT << SHIFT31) | (hpriority << SHIFT30) |
((bc & BC_MASK) << SHIFT24) |
((responseQueue & OBID_MASK) << SHIFT16) |
((category & CAT_MASK) << SHIFT12 ) | (opCode & OPCODE_MASK));
ossaCachePreFlush(circularQ->agRoot,
(void *)circularQ->memoryRegion.appHandle,
(void *)msgHeader, circularQ->elementSize * bc);
OSSA_WRITE_LE_32(circularQ->agRoot, msgHeader, OSSA_OFFSET_OF(mpiMsgHeader_t,
Header), Header);
ossaCacheFlush(circularQ->agRoot, (void *)circularQ->memoryRegion.appHandle,
(void *)msgHeader, circularQ->elementSize * bc);
MPI_DEBUG_TRACE( circularQ->qNumber,
((circularQ->producerIdx << 16 ) | circularQ->consumerIdx),
MPI_DEBUG_TRACE_IBQ,
(void *)msgHeader,
circularQ->elementSize);
ossaLogIomb(circularQ->agRoot,
circularQ->qNumber,
TRUE,
(void *)msgHeader,
circularQ->elementSize);
return AGSA_RC_SUCCESS;
}
GLOBAL bit32 mpiMsgProduce(
mpiICQueue_t *circularQ,
void *messagePtr,
mpiMsgCategory_t category,
bit16 opCode,
bit8 responseQueue,
bit8 hiPriority
)
{
bit32 ret;
ret = mpiMsgPrepare(circularQ, messagePtr, category, opCode, responseQueue,
hiPriority);
if (ret == AGSA_RC_SUCCESS)
{
ossaHwRegWriteExt(circularQ->agRoot,
circularQ->PIPCIBar,
circularQ->PIPCIOffset,
circularQ->producerIdx);
}
return ret;
}
GLOBAL void mpiIBQMsgSend(mpiICQueue_t *circularQ)
{
ossaHwRegWriteExt(circularQ->agRoot,
circularQ->PIPCIBar,
circularQ->PIPCIOffset,
circularQ->producerIdx);
}
#else
GLOBAL FORCEINLINE
bit32
mpiMsgProduce(
mpiICQueue_t *circularQ,
void *messagePtr,
mpiMsgCategory_t category,
bit16 opCode,
bit8 responseQueue,
bit8 hiPriority
)
{
mpiMsgHeader_t *msgHeader;
bit32 bc;
bit32 Header = 0;
bit32 hpriority = 0;
#ifdef SA_FW_TEST_BUNCH_STARTS
#define Need_agRootDefined 1
#endif
#ifdef SA_ENABLE_TRACE_FUNCTIONS
bit32 i;
#define Need_agRootDefined 1
#endif
#ifdef MPI_DEBUG_TRACE_ENABLE
#define Need_agRootDefined 1
#endif
#ifdef Need_agRootDefined
agsaRoot_t *agRoot=circularQ->agRoot;
#ifdef SA_FW_TEST_BUNCH_STARTS
agsaLLRoot_t *saRoot = agNULL;
saRoot = agRoot->sdkData;
#endif
#undef Need_agRootDefined
#endif
SA_DBG4(("Entering function:mpiMsgProduce\n"));
SA_ASSERT(NULL != circularQ, "circularQ argument cannot be null");
SA_ASSERT(NULL != messagePtr, "messagePtr argument cannot be null");
SA_ASSERT(0 != circularQ->numElements, "The number of elements in this queue is 0");
SA_ASSERT(MPI_MAX_OUTBOUND_QUEUES > responseQueue, "oQueue ID is wrong");
smTraceFuncEnter(hpDBG_VERY_LOUD,"22");
msgHeader = (mpiMsgHeader_t*)(((bit8*)messagePtr) - sizeof(mpiMsgHeader_t));
bc = (((msgHeader->Header) >> SHIFT24) & BC_MASK);
SA_DBG6(("mpiMsgProduce: msgHeader bc %d\n", bc));
if (circularQ->priority)
{
hpriority = 1;
}
SA_ASSERT(0 != bc, "The message buffer is not in \"allocated\" state (bc == 0)");
Header = ((V_BIT << SHIFT31) |
(hpriority << SHIFT30) |
((bc & BC_MASK) << SHIFT24) |
((responseQueue & OBID_MASK) << SHIFT16) |
((category & CAT_MASK) << SHIFT12 ) |
(opCode & OPCODE_MASK));
ossaCachePreFlush(circularQ->agRoot, (void *)circularQ->memoryRegion.appHandle, (void *)msgHeader, circularQ->elementSize * bc);
OSSA_WRITE_LE_32(circularQ->agRoot, msgHeader, OSSA_OFFSET_OF(mpiMsgHeader_t, Header), Header);
ossaCacheFlush(circularQ->agRoot, (void *)circularQ->memoryRegion.appHandle, (void *)msgHeader, circularQ->elementSize * bc);
MPI_DEBUG_TRACE( circularQ->qNumber,
((circularQ->producerIdx << 16 ) | circularQ->consumerIdx),
MPI_DEBUG_TRACE_IBQ,
(void *)msgHeader,
circularQ->elementSize);
ossaLogIomb(circularQ->agRoot,
circularQ->qNumber,
TRUE,
(void *)msgHeader,
circularQ->elementSize);
#if defined(SALLSDK_DEBUG)
MPI_IBQ_IOMB_LOG(circularQ->qNumber, (void *)msgHeader, circularQ->elementSize);
#endif
#ifdef SA_ENABLE_TRACE_FUNCTIONS
smTrace(hpDBG_IOMB,"M1",circularQ->qNumber);
for (i=0; i<((bit32)bc*(circularQ->elementSize/4)); i++)
{
smTrace(hpDBG_IOMB,"MD",*( ((bit32 *)((bit8 *)messagePtr - sizeof(mpiMsgHeader_t))) + i));
}
#endif
#ifdef SA_FW_TEST_BUNCH_STARTS
if(saRoot->BunchStarts_Enable)
{
if (circularQ->BunchStarts_QPending == 0)
{
circularQ->BunchStarts_QPendingTick = saRoot->timeTick;
}
circularQ->BunchStarts_QPending++;
saRoot->BunchStarts_Pending++;
SA_DBG1(("mpiMsgProduce: BunchStarts - Global Pending %d\n", saRoot->BunchStarts_Pending));
SA_DBG1(("mpiMsgProduce: BunchStarts - QPending %d, Q-%d\n", circularQ->BunchStarts_QPending, circularQ->qNumber));
smTraceFuncExit(hpDBG_VERY_LOUD, 'a', "22");
return AGSA_RC_SUCCESS;
}
saRoot->BunchStarts_Pending = 0;
circularQ->BunchStarts_QPending = 0;
#endif
ossaHwRegWriteExt(circularQ->agRoot,
circularQ->PIPCIBar,
circularQ->PIPCIOffset,
circularQ->producerIdx);
smTraceFuncExit(hpDBG_VERY_LOUD, 'b', "22");
return AGSA_RC_SUCCESS;
}
#endif
#ifdef SA_FW_TEST_BUNCH_STARTS
void mpiMsgProduceBunch( agsaLLRoot_t *saRoot)
{
mpiICQueue_t *circularQ;
bit32 inq;
for(inq=0; ((inq < saRoot->QueueConfig.numInboundQueues) && saRoot->BunchStarts_Pending); inq++)
{
circularQ= &saRoot->inboundQueue[inq];
if (circularQ->BunchStarts_QPending &&
((circularQ->BunchStarts_QPending >= saRoot->BunchStarts_Threshold) ||
((saRoot->timeTick - circularQ->BunchStarts_QPendingTick) >= saRoot->BunchStarts_TimeoutTicks))
)
{
if(circularQ->qNumber != inq)
{
SA_DBG1(("mpiMsgProduceBunch:circularQ->qNumber(%d) != inq(%d)\n",circularQ->qNumber, inq));
}
SA_DBG1(("mpiMsgProduceBunch: IQ=%d, PI=%d\n", inq, circularQ->producerIdx));
SA_DBG1(("mpiMsgProduceBunch: Qpending=%d, TotPending=%d\n", circularQ->BunchStarts_QPending, saRoot->BunchStarts_Pending));
ossaHwRegWriteExt(circularQ->agRoot,
circularQ->PIPCIBar,
circularQ->PIPCIOffset,
circularQ->producerIdx);
saRoot->BunchStarts_Pending -= circularQ->BunchStarts_QPending;
circularQ->BunchStarts_QPending = 0;
circularQ->BunchStarts_QPendingTick = saRoot->timeTick;
}
}
}
#endif
GLOBAL FORCEINLINE
bit32
mpiMsgConsume(
mpiOCQueue_t *circularQ,
void ** messagePtr1,
mpiMsgCategory_t *pCategory,
bit16 *pOpCode,
bit8 *pBC
)
{
mpiMsgHeader_t *msgHeader;
bit32 msgHeader_tmp;
SA_ASSERT(NULL != circularQ, "circularQ argument cannot be null");
SA_ASSERT(NULL != messagePtr1, "messagePtr1 argument cannot be null");
SA_ASSERT(NULL != pCategory, "pCategory argument cannot be null");
SA_ASSERT(NULL != pOpCode, "pOpCode argument cannot be null");
SA_ASSERT(NULL != pBC, "pBC argument cannot be null");
SA_ASSERT(0 != circularQ->numElements, "The number of elements in this queue is 0");
do
{
if(circularQ->producerIdx != circularQ->consumerIdx)
{
msgHeader = (mpiMsgHeader_t*) ((bit8 *)(circularQ->memoryRegion.virtPtr) + circularQ->consumerIdx * circularQ->elementSize);
#ifdef LOOPBACK_MPI
if (!loopback)
#endif
ossaCacheInvalidate(circularQ->agRoot, (void *)circularQ->memoryRegion.appHandle, (void *)msgHeader, circularQ->elementSize);
OSSA_READ_LE_32(circularQ->agRoot, &msgHeader_tmp, msgHeader, 0);
SA_DBG4(("mpiMsgConsume: process an IOMB, header=0x%x\n", msgHeader_tmp));
SA_ASSERT(0 != (msgHeader_tmp & HEADER_BC_MASK), "The bc field in the header is 0");
#ifdef TEST
if (0 == (msgHeader_tmp & HEADER_BC_MASK))
{
SA_DBG1(("mpiMsgConsume: CI=%d PI=%d msgHeader=%p\n", circularQ->consumerIdx, circularQ->producerIdx, (void *)msgHeader));
circularQ->consumerIdx = (circularQ->consumerIdx + 1) % circularQ->numElements;
ossaHwRegWriteExt(circularQ->agRoot,
circularQ->CIPCIBar,
circularQ->CIPCIOffset,
circularQ->consumerIdx);
return AGSA_RC_FAILURE;
}
#endif
if (0 != (msgHeader_tmp & HEADER_V_MASK))
{
SA_ASSERT(circularQ->consumerIdx <= circularQ->numElements, "Multi-buffer messages cannot wrap around");
if (OPC_OUB_SKIP_ENTRY != (msgHeader_tmp & OPCODE_MASK))
{
*messagePtr1 = ((bit8*)msgHeader) + sizeof(mpiMsgHeader_t);
*pCategory = (mpiMsgCategory_t)(msgHeader_tmp >> SHIFT12) & CAT_MASK;
*pOpCode = (bit16)(msgHeader_tmp & OPCODE_MASK);
*pBC = (bit8)((msgHeader_tmp >> SHIFT24) & BC_MASK);
#ifdef LOOPBACK_MPI
if (!loopback)
#endif
ossaCacheInvalidate(circularQ->agRoot, (void *)circularQ->memoryRegion.appHandle, (void *)msgHeader, (*pBC - 1) * circularQ->elementSize);
#if defined(SALLSDK_DEBUG)
SA_DBG3(("mpiMsgConsume: CI=%d PI=%d msgHeader=%p\n", circularQ->consumerIdx, circularQ->producerIdx, (void *)msgHeader));
MPI_OBQ_IOMB_LOG(circularQ->qNumber, (void *)msgHeader, circularQ->elementSize);
#endif
return AGSA_RC_SUCCESS;
}
else
{
SA_DBG3(("mpiMsgConsume: SKIP_ENTRIES_IOMB BC=%d\n", (msgHeader_tmp >> SHIFT24) & BC_MASK));
circularQ->consumerIdx = (circularQ->consumerIdx + ((msgHeader_tmp >> SHIFT24) & BC_MASK)) % circularQ->numElements;
msgHeader_tmp = 0;
OSSA_WRITE_LE_32(circularQ->agRoot, msgHeader, OSSA_OFFSET_OF(mpiMsgHeader_t, Header), msgHeader_tmp);
ossaHwRegWriteExt(circularQ->agRoot,
circularQ->CIPCIBar,
circularQ->CIPCIOffset,
circularQ->consumerIdx);
OSSA_READ_LE_32(circularQ->agRoot, &circularQ->producerIdx, circularQ->piPointer, 0);
}
}
else
{
#if defined(SALLSDK_DEBUG)
agsaRoot_t *agRoot=circularQ->agRoot;
SA_DBG1(("mpiMsgConsume: V bit not set, PI=%d CI=%d msgHeader=%p\n", circularQ->producerIdx, circularQ->consumerIdx,(void *)msgHeader));
SA_DBG1(("mpiMsgConsume: V bit not set, 0x%08X Q=%d \n", msgHeader_tmp, circularQ->qNumber));
MPI_DEBUG_TRACE(MPI_DEBUG_TRACE_QNUM_ERROR + circularQ->qNumber,
((circularQ->producerIdx << 16 ) | circularQ->consumerIdx),
MPI_DEBUG_TRACE_OBQ,
(void *)(((bit8*)msgHeader) - sizeof(mpiMsgHeader_t)),
circularQ->elementSize);
circularQ->consumerIdx = circularQ->consumerIdx % circularQ->numElements;
circularQ->consumerIdx ++;
OSSA_WRITE_LE_32(circularQ->agRoot, msgHeader, OSSA_OFFSET_OF(mpiMsgHeader_t, Header), msgHeader_tmp);
ossaHwRegWriteExt(agRoot,
circularQ->CIPCIBar,
circularQ->CIPCIOffset,
circularQ->consumerIdx);
MPI_OBQ_IOMB_LOG(circularQ->qNumber, (void *)msgHeader, circularQ->elementSize);
#endif
SA_DBG1(("mpiMsgConsume: V bit is not set!!!!! HW CI=%d\n", ossaHwRegReadExt(circularQ->agRoot, circularQ->CIPCIBar, circularQ->CIPCIOffset) ));
SA_ASSERT(0, "V bit is not set");
return AGSA_RC_FAILURE;
}
}
else
{
OSSA_READ_LE_32(circularQ->agRoot, &circularQ->producerIdx, circularQ->piPointer, 0);
}
} while(circularQ->producerIdx != circularQ->consumerIdx);
#ifdef TEST
SA_DBG4(("mpiMsgConsume: Outbound queue is empty.\n"));
#endif
return AGSA_RC_BUSY;
}
GLOBAL FORCEINLINE
bit32
mpiMsgFreeSet(
mpiOCQueue_t *circularQ,
void *messagePtr1,
bit8 bc
)
{
mpiMsgHeader_t *msgHeader;
SA_DBG4(("Entering function:mpiMsgFreeSet\n"));
SA_ASSERT(NULL != circularQ, "circularQ argument cannot be null");
SA_ASSERT(NULL != messagePtr1, "messagePtr1 argument cannot be null");
SA_ASSERT(0 != circularQ->numElements, "The number of elements in this queue is 0");
msgHeader = (mpiMsgHeader_t*)(((bit8*)messagePtr1) - sizeof(mpiMsgHeader_t));
if ( ((mpiMsgHeader_t*)((bit8*)circularQ->memoryRegion.virtPtr + circularQ->consumerIdx * circularQ->elementSize)) != msgHeader)
{
SA_DBG1(("mpiMsgFreeSet: Wrong CI, Q %d ConsumeIdx = %d msgHeader 0x%08x\n",circularQ->qNumber, circularQ->consumerIdx ,msgHeader->Header));
SA_DBG1(("mpiMsgFreeSet: msgHeader %p != %p\n", msgHeader,((mpiMsgHeader_t*)((bit8*)circularQ->memoryRegion.virtPtr + circularQ->consumerIdx * circularQ->elementSize))));
#ifdef LOOPBACK_MPI
if (!loopback)
#endif
OSSA_READ_LE_32(circularQ->agRoot, &circularQ->producerIdx, circularQ->piPointer, 0);
#if defined(SALLSDK_DEBUG)
SA_DBG3(("mpiMsgFreeSet: ProducerIdx = %d\n", circularQ->producerIdx));
#endif
return AGSA_RC_SUCCESS;
}
circularQ->consumerIdx = (circularQ->consumerIdx + bc) % circularQ->numElements;
msgHeader->Header &= ~HEADER_V_MASK;
SA_ASSERT(circularQ->consumerIdx <= circularQ->numElements, "Multi-buffer messages cannot wrap arround");
#ifdef LOOPBACK_MPI
if (!loopback)
#endif
{
ossaHwRegWriteExt(circularQ->agRoot,
circularQ->CIPCIBar,
circularQ->CIPCIOffset,
circularQ->consumerIdx);
OSSA_READ_LE_32(circularQ->agRoot, &circularQ->producerIdx, circularQ->piPointer, 0);
}
#if defined(SALLSDK_DEBUG)
SA_DBG5(("mpiMsgFreeSet: CI=%d PI=%d\n", circularQ->consumerIdx, circularQ->producerIdx));
#endif
return AGSA_RC_SUCCESS;
}
#ifdef TEST
GLOBAL bit32 mpiRotateQnumber(agsaRoot_t *agRoot)
{
agsaLLRoot_t *saRoot = (agsaLLRoot_t *) (agRoot->sdkData);
bit32 denom;
bit32 ret = 0;
saRoot->IBQnumber++;
denom = saRoot->QueueConfig.numInboundQueues;
if (saRoot->IBQnumber % denom == 0)
{
saRoot->IBQnumber = 0;
}
SA_DBG3(("mpiRotateQnumber: IBQnumber %d\n", saRoot->IBQnumber));
saRoot->OBQnumber++;
denom = saRoot->QueueConfig.numOutboundQueues;
if (saRoot->OBQnumber % denom == 0)
{
saRoot->OBQnumber = 0;
}
SA_DBG3(("mpiRotateQnumber: OBQnumber %d\n", saRoot->OBQnumber));
ret = (saRoot->OBQnumber << SHIFT16) | saRoot->IBQnumber;
return ret;
}
#endif
#ifdef LOOPBACK_MPI
GLOBAL bit32 mpiMsgProduceOQ(
mpiOCQueue_t *circularQ,
void *messagePtr,
mpiMsgCategory_t category,
bit16 opCode,
bit8 responseQueue,
bit8 hiPriority
)
{
mpiMsgHeader_t *msgHeader;
bit32 bc;
bit32 Header = 0;
bit32 hpriority = 0;
SA_DBG4(("Entering function:mpiMsgProduceOQ\n"));
SA_ASSERT(NULL != circularQ, "circularQ argument cannot be null");
SA_ASSERT(NULL != messagePtr, "messagePtr argument cannot be null");
SA_ASSERT(0 != circularQ->numElements, "The number of elements in this queue"
" is 0");
SA_ASSERT(MPI_MAX_OUTBOUND_QUEUES > responseQueue, "oQueue ID is wrong");
smTraceFuncEnter(hpDBG_VERY_LOUD, "2I");
msgHeader = (mpiMsgHeader_t*)(((bit8*)messagePtr) - sizeof(mpiMsgHeader_t));
SA_DBG4(("mpiMsgProduceOQ: msgHeader %p opcode %d pi/ci %d / %d\n", msgHeader, opCode, circularQ->producerIdx, circularQ->consumerIdx));
bc = (((msgHeader->Header) >> SHIFT24) & BC_MASK);
SA_DBG6(("mpiMsgProduceOQ: msgHeader bc %d\n", bc));
if (circularQ->priority)
hpriority = 1;
SA_ASSERT(0 != bc, "The message buffer is not in \"allocated\" state "
"(bc == 0)");
Header = ((V_BIT << SHIFT31) | (hpriority << SHIFT30) |
((bc & BC_MASK) << SHIFT24) |
((responseQueue & OBID_MASK) << SHIFT16) |
((category & CAT_MASK) << SHIFT12 ) | (opCode & OPCODE_MASK));
OSSA_WRITE_LE_32(circularQ->agRoot, msgHeader, OSSA_OFFSET_OF(mpiMsgHeader_t,
Header), Header);
MPI_DEBUG_TRACE( circularQ->qNumber,
((circularQ->producerIdx << 16 ) | circularQ->consumerIdx),
MPI_DEBUG_TRACE_OBQ,
(void *)msgHeader,
circularQ->elementSize);
ossaLogIomb(circularQ->agRoot,
circularQ->qNumber,
TRUE,
(void *)msgHeader,
circularQ->elementSize);
smTraceFuncExit(hpDBG_VERY_LOUD, 'a', "2I");
return AGSA_RC_SUCCESS;
}
#endif