📄 theapp.c
字号:
//--------------------------------------------------------------
// If the inputs are OK, reset the DM642, then open up a DMA
// channel to it.
//--------------------------------------------------------------
if (kNoError == nStatus)
{
//-------------------------------------------------------
// Setup for Contiguous-Buffered DMA on DMA channel 0.
//-------------------------------------------------------
nStatus = DM642DmaOpen(hDM642, &hDma, kDmaBufType_Contig, NULL, BUFSIZE, kDmaChan_0);
if (kNoError != nStatus)
{
printf("ERROR opening DMA => %d\n", nStatus);
}
}
#ifdef _USE_WINEVENTS_
if (kNoError == nStatus)
{
//-----------------------------------------------------------
// Create the Pci-Interrupt-Occured Event
// default security/access
// manual reset only (ie, no Windows auto-magic reset
// initial state is non-signalled
// name == "EvPciInt"
//-----------------------------------------------------------
hPciIntEvent = CreateEvent(NULL, TRUE, FALSE, g_strIntEventName);
if (NULL == hPciIntEvent)
{
printf("ERROR obtaining W32 event.\n");
nStatus = -1;
}
}
#endif
if (kNoError == nStatus)
{
//-------------------------------------------------------------
// Write the starting address (in PCI space) and the size of
// our DMA region out to the DSP card. We are writing these
// directly to the PCI-DMA addr/control registers ...
// But NOT triggering any DMA, yet.
//-------------------------------------------------------------
DM642DmaSetPciAddrFromOffs(hDM642, hDma, 0);
DM642DmaIOCTLStartTransfer(hDM642,
DM642DmaGetSizeofRegion(hDma),
0);
//-------------------------------------------------------------------
// Fill local buffer with the host test data
// Sans the iteration count.---
// Fill another buffer with what we expect to receive
// from the DSP. Sans the iteration count.
//
// The fill operations were moved up here for "speed optimization".
// The DSP will be concurrently checking and setting its DSPMA reg.
//-------------------------------------------------------------------
_FillBufferWithPattern(pDataToSend, 4, 0, 2);
_FillBufferWithPattern(pExpectedData, 4, 1, 2);
//---------------------------------------------
// Wait for an ACK from the DM642 card ...
//---------------------------------------------
nStatus = _WaitForDspMasterAddrToChange(hDM642, 0);
if (nStatus < 0)
{
printf("ERROR waiting for DSPMA to change (to non-reset)!\n");
}
}
if (kNoError == nStatus)
{
//-------------------------------------------------
// Setup our PCI (INTA) interrupt handler stuff.
//-------------------------------------------------
DM642IntEnable(hDM642, MyPciInterruptCallback);
//------------------------------------------------------------------------
// LOOP CONTROL: The behavior of the following for-loop is determined at
// compile-time by the defined constant NLOOPS.
// If NLOOPS is zero (0), then the loop will be infinite.
// If NLOOPS is NOT zero, the loop will repeat a
// number of times equal to NLOOPS, and then terminate
//------------------------------------------------------------------------
for (nIterCnt = 0, nIterCntEven = 0, nIterCntOdd = 1;
#if (0 == NLOOPS)
; // Infinite loop
#else
nIterCnt < (unsigned)NLOOPS; // Loop only NLOOPS times
#endif
nIterCnt++, nIterCntEven += 2, nIterCntOdd += 2)
{
//-------------------------------------------------------------
// Put the even + odd iteration counts into the 1st four bytes
// of the appropriate buffers...
//-------------------------------------------------------------
memcpy(&pDataToSend[0], &nIterCntEven, sizeof(nIterCntEven));
memcpy(&pExpectedData[0], &nIterCntOdd, sizeof(nIterCntOdd));
//------------------------------------------------
// Copy our local buffer into Host DMA space ...
// I.E, copy to the Host DMA buffer
//------------------------------------------------
DM642DmaCopyBufToDmaSpace(hDma, (unsigned int *)pDataToSend, (BUFSIZE/4), 0);
#ifdef _USE_WINEVENTS_
//------------------------------------------------------
// Reset/Clear the event in prep for waiting on it ...
//------------------------------------------------------
ResetEvent(hPciIntEvent);
#endif
//---------------------------------------------------------------
// Clear out any pending (spurrious) interrupts from the DSP.
//---------------------------------------------------------------
DM642ClearIntD2H(hDM642);
//------------------------------------------------
// Interrupt the DSP -> via HDCR[DSPINT] <- 1
//------------------------------------------------
DM642TriggerIntH2D(hDM642);
//-------------------------------------------------
// Wait for (PCI) interrupt OR DMA-done-event ...
//-------------------------------------------------
#ifdef _USE_WINEVENTS_
//----------------------------------------------
// ... Using Windows events and function(s) ...
//----------------------------------------------
if ( WAIT_OBJECT_0 != WaitForSingleObject(hPciIntEvent, INFINITE) )
{
printf("ERROR on wait-for-event!\n");
nStatus = -3;
break;
}
#else
//-------------------------------------------
// ... Using a simple busy-wait loop ....
//-------------------------------------------
while(FALSE == g_fHasPciIntOccured)
{
Sleep(5);
}
#endif
//---------------------------------------------------------------------
// Copy the data from the Host's DMA space into a local buffer .....
// I.E, copy FROM the Host DMA buffer
//---------------------------------------------------------------------
DM642DmaCopyBufFromDmaSpace(hDma, (unsigned int *)pRecvdData, (BUFSIZE/4), 0);
//-----------------------------------------------------------
// And then compare the received vs. the expected data ...
//-----------------------------------------------------------
if (_CompareBuffers(pRecvdData, pExpectedData, 4) < 0)
{
nStatus = -4;
break;
}
//--------------------------------------------
// print the counter every 10,000 iterations
//--------------------------------------------
if ((nIterCnt % 10000) == 0)
{
printf("Iteration Count == %u\n", nIterCnt);
}
} // End main NLOOPS for-loop
} // End enclosing if (kNoError == nStatus)
//--------------------------------
// Clean-up our resources ...
//--------------------------------
#ifdef _USE_WINEVENTS_
if (hPciIntEvent != NULL)
{
CloseHandle(hPciIntEvent);
}
#endif
if (hDma != NULL)
{
DM642DmaClose(hDM642, &hDma);
}
printf("Exitting RunApp() with Iteration Count == %d\n", nIterCnt);
return (nStatus);
} // END RunApp()
////////////////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////
////
//// Name: MyPciInterruptCallback
////
//// Purpose: This routine is the User-Level callback that will get
//// executed in response to a DSP->Host interrupt. The routine
//// is NOT the ISR, but a defferred processin routine.
////
//// This routine has conditionally-compiled sections. It will
//// either set a flag OR signal a Win32 Event, depending on
//// the state of the _USE_WINEVENTS_ constant at compile-time.
////
//// Input Parameters:
//// hDM642 - Handle of the currently-open DM642 board/card
//// pStatus - Pointer to the int-status structure.
////
//// Output Parameters: none
////
//// Return Value(s) : none
////
//////////////////////////////////////////////////////////////////////////////
void MyPciInterruptCallback( DM642_HANDLE hDM642,
tDM642InterruptStatus *pStatus )
{
#ifdef _USE_WINEVENTS_
HANDLE hPciIntEv;
#endif
// ------------------------------------------------------------
// Since we are not in the acutal ISR, we can take the
// time to clear out the interrupt source, as opposed to
// simply de-asserting PCI INTA (which is what the ISR does).
//
// NOTE: clearing the int-source requires us to write to
// memory-mapped register(s) on the DSP.
// ------------------------------------------------------------
DM642ClearIntD2H(hDM642);
#ifdef _USE_WINEVENTS_
//--------------------------------------------------------------
// We can also take the time trigger Win32 events ...
// If this part is compiled in (ie, _USE_WINEVENTS_ is defined)
//--------------------------------------------------------------
hPciIntEv = OpenEvent(EVENT_ALL_ACCESS, FALSE, g_strIntEventName);
SetEvent(hPciIntEv);
CloseHandle(hPciIntEv);
#else
//--------------------------------------------------------------
// If _USE_WINEVENTS_ is not defined, set a flag for somebody
// else to check.
//--------------------------------------------------------------
g_fHasPciIntOccured = TRUE;
#endif
} // END MyPciInterruptCallback()
//############################################################################
// End of Functions
//############################################################################
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -