2015-03-09 07:01 AM
using the SPC560B-DIS board I'm having trouble with eDMA.
I've got a very basic function set up to write a succession of 32bit words from one array to another using the eDMA. but it doesn't seem to ever get on to the second (or subsiquent) major loop iterations (as in CITER decriments the once but then not again) If i manually reset the TCD.START, the next iteration happens (and if I keep doing this the iterations continue till CITER is zero and the done flag is activated) However I assume that subsiquent 'loops' should be started by hardware. Any help with this would be appreciated. #discovery #iter #dmaSolved! Go to Solution.
2015-03-10 10:35 AM
Hello Patrick ,
If you want to use eDMA Hardware , you should take care of : TCD.D_REQ Disable hardware request. If this flag is set, the eDMA hardware automatically clears the corresponding EDMA_ERQRL bit when the current major iteration count reaches zero. 0 The channel’s EDMA_ERQRL bit is not affected. 1 The channel’s EDMA_ERQRL bit is cleared when the outer major loop is comple in SPC5studio , there is a nice example of edma settings made by Giovanni ;) DSPI Applications spi and edma (cf spc5_edma.c and spi_lld.c)/**
* @brief EDMA driver initialization.
*
* @special
*/
void
edmaInit(
void
) {
unsigned i;
SPC5_EDMA.CR.R = SPC5_EDMA_CR_SETTING;
SPC5_EDMA.ERQRL.R = 0x00000000;
SPC5_EDMA.EEIRL.R = 0x00000000;
SPC5_EDMA.IRQRL.R = 0xFFFFFFFF;
SPC5_EDMA.ERL.R = 0xFFFFFFFF;
#if SPC5_EDMA_NCHANNELS > 32
SPC5_EDMA.ERQRH.R = 0x00000000;
SPC5_EDMA.EEIRH.R = 0x00000000;
SPC5_EDMA.IRQRH.R = 0xFFFFFFFF;
SPC5_EDMA.ERH.R = 0xFFFFFFFF;
#endif
/* Initializing all the channels with a different priority withing the
channels group.*/
for
(i = 0; i < 16; i++) {
SPC5_EDMA.CPR[i].R = g0[i];
#if SPC5_EDMA_NCHANNELS > 16
SPC5_EDMA.CPR[i + 16].R = g1[i];
#endif
#if SPC5_EDMA_NCHANNELS > 32
SPC5_EDMA.CPR[i + 32].R = g2[i];
SPC5_EDMA.CPR[i + 48].R = g3[i];
#endif
}
/**
* @brief Starts or restarts an EDMA channel.
*
* @param[in] channel the channel number
*
* @api
*/
#define edmaChannelStart(channel) (SPC5_EDMA.SERQR.R = (channel))
/**
* @brief Stops an EDMA channel.
*
* @param[in] channel the channel number
*
* @api
*/
#define edmaChannelStop(channel) { \
SPC5_EDMA.CERQR.R = (channel); \
SPC5_EDMA.CDSBR.R = (channel); \
}
Best regards
Erwan
2015-03-10 09:20 AM
(Reference Manual RM0037) Has a section under EDMA_ERQRL saying
''Both the eDMA request input signal and this enable request flag must be asserted before a channel’s hardware service request is accepted.'' But I can't find any other references to a 'request input signal' other than ''Setting bit 1 (CERQ[0]) provides a global clear function, forcing the entire contents of the EDMA_ERQRL to be zeroed, disabling all eDMA request inputs.''
Which suggests that they are the same thing?? If not, should I have to do anything to let it produce Hardware requests? (BTW: I'm trying to run SPI via DMA but seem to be having exactly the same issues both with and without the SPI code, so am currently assuming it's a DMA problem)2015-03-10 10:35 AM
Hello Patrick ,
If you want to use eDMA Hardware , you should take care of : TCD.D_REQ Disable hardware request. If this flag is set, the eDMA hardware automatically clears the corresponding EDMA_ERQRL bit when the current major iteration count reaches zero. 0 The channel’s EDMA_ERQRL bit is not affected. 1 The channel’s EDMA_ERQRL bit is cleared when the outer major loop is comple in SPC5studio , there is a nice example of edma settings made by Giovanni ;) DSPI Applications spi and edma (cf spc5_edma.c and spi_lld.c)/**
* @brief EDMA driver initialization.
*
* @special
*/
void
edmaInit(
void
) {
unsigned i;
SPC5_EDMA.CR.R = SPC5_EDMA_CR_SETTING;
SPC5_EDMA.ERQRL.R = 0x00000000;
SPC5_EDMA.EEIRL.R = 0x00000000;
SPC5_EDMA.IRQRL.R = 0xFFFFFFFF;
SPC5_EDMA.ERL.R = 0xFFFFFFFF;
#if SPC5_EDMA_NCHANNELS > 32
SPC5_EDMA.ERQRH.R = 0x00000000;
SPC5_EDMA.EEIRH.R = 0x00000000;
SPC5_EDMA.IRQRH.R = 0xFFFFFFFF;
SPC5_EDMA.ERH.R = 0xFFFFFFFF;
#endif
/* Initializing all the channels with a different priority withing the
channels group.*/
for
(i = 0; i < 16; i++) {
SPC5_EDMA.CPR[i].R = g0[i];
#if SPC5_EDMA_NCHANNELS > 16
SPC5_EDMA.CPR[i + 16].R = g1[i];
#endif
#if SPC5_EDMA_NCHANNELS > 32
SPC5_EDMA.CPR[i + 32].R = g2[i];
SPC5_EDMA.CPR[i + 48].R = g3[i];
#endif
}
/**
* @brief Starts or restarts an EDMA channel.
*
* @param[in] channel the channel number
*
* @api
*/
#define edmaChannelStart(channel) (SPC5_EDMA.SERQR.R = (channel))
/**
* @brief Stops an EDMA channel.
*
* @param[in] channel the channel number
*
* @api
*/
#define edmaChannelStop(channel) { \
SPC5_EDMA.CERQR.R = (channel); \
SPC5_EDMA.CDSBR.R = (channel); \
}
Best regards
Erwan
2015-03-12 03:33 AM
Erwan thanks for the reply,
I was (/am) already using that code as a reference, and in general finding it very useful. Turns out the issue I was having was with my linking of the DMA channel to the source with the DMA_MUX. I've fixed it now, so thankyou for the assist. Patrick