Content originally posted in LPCWare by solsal on Fri Aug 24 02:12:56 MST 2012
Hi,
reading the examples of code_bundle_lpc1768 available at nxp.com
SSP examples ( for keil )
sspdma.uvproj
=================================================================
uint32_t DMAChannel_Init( uint32_t ChannelNum, uint32_t DMAMode )
{
if ( ChannelNum == 0 )
{
SSP0DMADone = 0;
LPC_GPDMA->IntTCClear = 0x01<<0;
LPC_GPDMA->IntErrClr = 0x01<<0;
if ( DMAMode == M2P )
{
/* Ch0 set for M2P transfer from mempry to peripheral. */
LPC_GPDMACH0->CSrcAddr = SSP0_DMA_TX_SRC;
LPC_GPDMACH0->CDestAddr = SSP0_DMA_TX_DST;
/* The burst size is set to 1, source and dest transfer width is
32 bits(word), Terminal Count Int enable */
LPC_GPDMACH0->CControl = (SSP_DMA_SIZE & 0x0FFF)|(0x00 << 12)
|(0x00 << 15)|(0x00 << 18)|(0x00 << 21)|(1 << 26)|0x80000000;
}
else if ( DMAMode == P2M )
{
/* Ch0 set for P2M transfer from peripheral to memory. */
LPC_GPDMACH0->CSrcAddr = SSP0_DMA_RX_SRC;
LPC_GPDMACH0->CDestAddr = SSP0_DMA_RX_DST;
/* The burst size is set to 1. Terminal Count Int enable. */
LPC_GPDMACH0->CControl = (SSP_DMA_SIZE & 0x0FFF)|(0x00 << 12)
|(0x00 << 15)|(0x00 << 18)|(0x00 << 21)|(1 << 27)|0x80000000;
}
else
{
return ( FALSE );
}
}
else if ( ChannelNum == 1 )
{
SSP1DMADone = 0;
LPC_GPDMA->IntTCClear = 0x01<<1;
LPC_GPDMA->IntErrClr = 0x01<<1;
if ( DMAMode == M2P )
{
/* Ch1 set for M2P transfer from mempry to peripheral. */
LPC_GPDMACH1->CSrcAddr = SSP1_DMA_TX_SRC;
LPC_GPDMACH1->CDestAddr = SSP1_DMA_TX_DST;
/* The burst size is set to 1. Terminal Count Int enable. */
LPC_GPDMACH1->CControl = (SSP_DMA_SIZE & 0x0FFF)|(0x00 << 12)
|(0x00 << 15)|(0x00 << 18)|(0x00 << 21)|(1 << 26)|0x80000000;
}
else if ( DMAMode == P2M )
{
/* Ch1 set for P2M transfer from peripheral to memory. */
LPC_GPDMACH1->CSrcAddr = SSP1_DMA_RX_SRC;
LPC_GPDMACH1->CDestAddr = SSP1_DMA_RX_DST;
/* The burst size is set to 1. Terminal Count Int enable. */
LPC_GPDMACH1->CControl = (SSP_DMA_SIZE & 0x0FFF)|(0x00 << 12)
|(0x00 << 15)|(0x00 << 18)|(0x00 << 21)|(1 << 27)|0x80000000;
}
else
{
return ( FALSE );
}
}
else
{
return ( FALSE );
}
return( TRUE );
}
///////////////////////////////////////////////////////////////////////////////
you see !
LPC1768 is capable for only half duplex transfer for SSP/SPI by GPDMA !
only one mode (P2M for receive data from SPI(MISO) to memory) or (M2P for sending data from memory to SPI (MOSI) ) !
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
isn't it confusing ?
SPI is a full duplex peripheral.
and it should be considered in GPDMA design !
we need P2M2P mode for this...
//////////////////////////////////////////////////
I am confused,
it was simply done in old AT91SAM7X256 ....
//////////////////////////////////////////////////
AT91SAM7X256: DOC6120
22. Peripheral DMA Controller (PDC)
22.1 Overview
The Peripheral DMA Controller (PDC) transfers data between on-chip serial peripherals such as
the UART, USART, SSC, SPI, MCI and the on- and off-chip memories. Using the Peripheral
DMA Controller avoids processor intervention and removes the processor interrupt-handling
overhead. This significantly reduces the number of clock cycles required for a data transfer and,
as a result, improves the performance of the microcontroller and makes it more power efficient.
============
The PDC channels are implemented in pairs, each pair being dedicated to a particular peripheral.
=============================== THIS IS FULL DUPLEX ======================================
One channel in the pair is dedicated to the receiving channel and one to the transmitting
channel of each UART, USART, SSC and SPI.
==========================================================================================
The user interface of a PDC channel is integrated in the memory space of each peripheral. It
contains:
• A 32-bit memory pointer register
• A 16-bit transfer count register
• A 32-bit register for next memory pointer
• A 16-bit register for next transfer count
The peripheral triggers PDC transfers using transmit and receive signals. When the programmed
data
==============================================================================================
it seems that :
the GPDMA cannot handle full duplex in SSP/SPI ( sending 1024 bytes array and receiving 1024 bytes array simultaneously )
and I have to build it without GPDMA and by byte transfer interrupts
"10 times per second each 1024 bytes" = 10240 interrupts will be over head to
my full featured heavy and complicated design,
================================================================================
any comment ?
am I wrong ?