📄 mytasks.c
字号:
//// Output Parameters:
//// pExdD_io - The Expected Data Buffer (pointer)
//// pRecvD_io - The Received Data Buffer (pointer)
//// pSendD_io - The Send Data Buffer (pointer)
////
//// Return Value(s) : none
////
//////////////////////////////////////////////////////////////////////////////
static void _ReleaseBuffers(Ptr *pExpD_io,
Ptr *pRecvD_io,
Ptr *pSendD_io )
{
extern tMyBufInfo g_oBufInfo;
LOG_printf(&trace, "Releasing the buffers ...");
//---------------------------------------
// Return/free the Expected Data buffer
//---------------------------------------
if (*pExpD_io != NULL)
{
BUF_free(g_oBufInfo.hBufPool, *pExpD_io);
}
//---------------------------------------
// Return/free the Received Data buffer
//---------------------------------------
if (*pRecvD_io != NULL)
{
BUF_free(g_oBufInfo.hBufPool, *pRecvD_io);
}
//---------------------------------------
// Return/free the (to) Send Data buffer
//---------------------------------------
if (*pSendD_io != NULL)
{
BUF_free(g_oBufInfo.hBufPool, *pSendD_io);
}
} // END _ReleaseBuffers()
//////////////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////
////
//// Name: _InitPciRequests
////
//// Purpose: This routine initializes 2 pci-request structures -- one for
//// reading and the other for writing. These structures are
//// used to send read and write requests thru the DM642 device
//// driver and across the PCI bus.
////
//// Input Parameters: none
////
//// Output Parameters:
//// pReadReq_o - Structure used to request PCI reads to the DM642
//// pWriteReq_o - Structure used to request PCI writes from the DM642
////
//// Return Value(s) : none
////
//////////////////////////////////////////////////////////////////////////////
static void _InitPciRequests( Ptr pReadReq_o,
Ptr pWriteReq_o )
{
extern tMyPciXferInfo g_oXferInfo;
C64XX_PCI_Request *pReadReq = (C64XX_PCI_Request *)pReadReq_o;
C64XX_PCI_Request *pWriteReq = (C64XX_PCI_Request *)pWriteReq_o;
if (pReadReq != NULL)
{
pReadReq->srcAddr = (char *)g_oXferInfo.pPciAddr;
pReadReq->dstAddr = (char *)g_oXferInfo.pDspRxAddr;
pReadReq->byteCnt = g_oXferInfo.nCountB;
pReadReq->options = 0;
pReadReq->options = \
C64XX_PCI_SETXFERMODE(pReadReq->options, PCI_READ_NOPREF);
}
if (pWriteReq != NULL)
{
pWriteReq->srcAddr = (char *)g_oXferInfo.pDspTxAddr;
pWriteReq->dstAddr = (char *)g_oXferInfo.pPciAddr;
pWriteReq->byteCnt = g_oXferInfo.nCountB;
pWriteReq->options = 0;
pWriteReq->options = \
C64XX_PCI_SETXFERMODE(pWriteReq->options, PCI_WRITE);
}
} // END _InitPciRequests()
//////////////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////
////
//// Name: ProcessTask
////
//// Purpose: This routine implements the main body of the Target-side
//// application described in Exhibit #2.
////
//// The routine is a DSP/BIOS task (or Task Thread).
//// The routine WILL NOT RETURN.
////
//// The routine finishes the initialization process, and then
//// notifies the Host that it is ready by writing a local address
//// into DSPMA. The routine then enters is main processing
//// loop.
////
//// In the main loop, which is infinite, the routine Pends on a
//// semaphore. This semaphore is Posted in the DM642 device
//// driver's ISR when the Host raises HOSTSW. The routine then
//// reads the data thru the DM642 PCI device driver, compares
//// received vs. expected, writes its own data out thru the
//// driver, notifies the Host via the PCI interrupt, and then
//// Pends on the above semaphore once again.
////
//// Any errors cause either a System Abort or a System Exit.
////
//// Input Parameters:
//// nIdArg - Task ID ##, passed in by DSP/BIOS.
//// NOT USED.
////
//// Output Parameters: none
////
//// Return Value(s) : none
////
//////////////////////////////////////////////////////////////////////////////
Void ProcessTask(Arg nIdArg)
{
extern tMyPciXferInfo g_oXferInfo;
extern Ptr g_pMyGio;
Ptr pExpectedData;
Ptr pRecvdData;
Ptr pDataToSend;
C64XX_PCI_Request oPciReadReq;
C64XX_PCI_Request oPciWriteReq;
Uint32 nIterCntE, nIterCntO;
Uint32 nIterCnt;
//------------------------------------
// Tell the log that we got here ...
//------------------------------------
LOG_printf(&trace, "Entered ProcessTask!");
//-------------------------------------------------------------------
// Get our three buffers from the Buffer Pool, and initialize them
// as necessary.
//-------------------------------------------------------------------
if (_GrabBuffers(&pExpectedData, &pRecvdData, &pDataToSend) < 0)
{
LOG_printf(&trace, "ProcessTask(): ERROR grabbing buffers!");
goto ExitTask;
}
_InitBuffers(pExpectedData, pRecvdData, pDataToSend);
//------------------------------------------------------------------
// Initialize the data-structs used to control our PCI transfers
// (via the GIO module)
//------------------------------------------------------------------
g_oXferInfo.pDspRxAddr = pRecvdData;
g_oXferInfo.pDspTxAddr = pDataToSend;
_InitPciRequests(&oPciReadReq, &oPciWriteReq);
//------------------------------------------------------------------
// This is the ACK back to the Host in response to it setting the
// PCIMA and PCIMC[CNT] registers. The registers were checked
// in main().
//------------------------------------------------------------------
LOG_printf( &trace, "Setting DSPMA[ADDRMA] to ... %04x_%04x",
(((LgUns)g_oXferInfo.pDspRxAddr) >> 16),
((LgUns)g_oXferInfo.pDspRxAddr & 0x0000FFFF));
PCI_RSET(DSPMA, (((LgUns)g_oXferInfo.pDspRxAddr) & _PCI_DSPMA_ADDRMA_MASK));
//************************************************************************
////////////////////////////////////////////
//
// The main processing LOOP.
//
////////////////////////////////////////////
for ( nIterCntE = 0, nIterCntO = 1, nIterCnt = 0;
;
nIterCntE += 2, nIterCntO += 2, nIterCnt++ )
{
Uns nSize;
int nStatus;
//---------------------------------------------------------
// Wait for the Host to signal that data is available ...
//---------------------------------------------------------
SEM_pend(&PciDmaDataAvail, SYS_FOREVER);
//-----------------------------------------------------------
// Put the iteration count(s) into the 1st 4 bytes of the
// appropriate buffers.
// We expect to receive counts of 0,2,4,...
// We will send counts of 1,3,5,...
//-----------------------------------------------------------
memcpy(pExpectedData, &nIterCntE, sizeof(nIterCntE));
memcpy(pDataToSend, &nIterCntO, sizeof(nIterCntO));
//-------------------------------------------------------------
// Read the available data (from the Host) into DSP memory
// (the pRecvData buffer)
//-------------------------------------------------------------
nSize = 0;
nStatus = GIO_read(g_pMyGio, &oPciReadReq, &nSize);
if(nStatus < 0)
{
LOG_printf(&trace, "ProcessTask: ERROR -> GIO_read. Status == %d; Size == %u",
nStatus, nSize);
}
//-----------------------------------------------------------
// Compare what was received vs. what was expected ...
// If a mismatch occurs, print an error message and bail.
//-----------------------------------------------------------
if ( _CompareBuffers(pRecvdData, pExpectedData, 4) < 0 )
{
LOG_printf(&trace, "ERROR: Data mismatch on iteration %u", nIterCnt);
SYS_abort("ProcessTasks:Mismatch");
}
//-----------------------------------------------
// Write data to the Host ...
//-----------------------------------------------
nSize = 0;
nStatus = GIO_write(g_pMyGio, &oPciWriteReq, &nSize);
if(nStatus < 0)
{
LOG_printf(&trace, "ProcessTask: ERROR -> GIO_write. Status == %d;%u",
nStatus, nSize);
}
//-------------------------------------------------------------
// Trigger the DSP->to->Host interrupt.
// Doing so tells the Host that it has data to read.
//
// Clearing the interrupt 1st forces it to 'fire', even if
// an interrupt condition had already existed.
//-------------------------------------------------------------
GIO_control(g_pMyGio, C64XX_PCI_DSP_INT_REQ_CLEAR, NULL);
GIO_control(g_pMyGio, C64XX_PCI_DSP_INT_REQ_SET, NULL);
//----------------------------------------------------------
// "Print out" the iteration count every 10,000 iterations
//----------------------------------------------------------
if ((nIterCnt % 10000) == 0)
{
LOG_printf(&trace, "ProcessTask(): Iteration Count == 0x%04x_%04x",
(MdUns)(nIterCnt >> 16), (MdUns)nIterCnt);
}
}
//************************************************************************
ExitTask:
//------------------------------------------
// Return the buffers to the Buffer Pool.
//------------------------------------------
_ReleaseBuffers(&pExpectedData, &pRecvdData, &pDataToSend);
SYS_exit(0);
} // END ProcessTask()
//############################################################################
// End of Functions
//############################################################################
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -