4.6.2 XDMAC Channel Initialization

A DMA channel from the XDMAC module is configured to transfer the audio samples from the main memory buffer to the CLASSD data register. The code snippet below configures the XDMAC channel 0 in a single block – Single Micro Block mode with a micro block length equal to the size of the buffer in bytes, divided by 4. The division factor is set to 4 because the buffer is arranged as an array of 16-bit signed integers with alternating left channel and right channel data. Array index 0 is the left channel data of sample 0, and array index 1 is the right channel data of sample 0, and so on. So, each successive four bytes in the array amount to one audio sample.

/* Enable peripheral clock for XDMAC0 */
PMC->PMC_PCER0 = (1u << ID_XDMAC0);

/* Read the interrupt status register to clear the interrupt flags */
temp = XDMAC0->XDMAC_CHID[0].XDMAC_CIS;

/* Set source address as starting address of audio buffer */
XDMAC0->XDMAC_CHID[0].XDMAC_CSA = (uint32_t)audio_data;

/* Set destination address as CLASSD_THR register */
XDMAC0->XDMAC_CHID[0].XDMAC_CDA = (uint32_t)&CLASSD->CLASSD_THR;

/* Set micro block length */
XDMAC0->XDMAC_CHID[0].XDMAC_CUBC = sizeof(audio_data)/4;

/* Set DMA channel parameters */
XDMAC0->XDMAC_CHID[0].XDMAC_CC = XDMAC_CC_TYPE_PER_TRAN
                                     | XDMAC_CC_MBSIZE_SINGLE
                                     | XDMAC_CC_DSYNC_MEM2PER 
                                     | XDMAC_CC_CSIZE_CHK_1
                                     | XDMAC_CC_DWIDTH_WORD
                                     | XDMAC_CC_SIF_AHB_IF0
                                     | XDMAC_CC_DIF_AHB_IF1
                                     | XDMAC_CC_SAM_INCREMENTED_AM
                                     | XDMAC_CC_DAM_FIXED_AM
                                     | XDMAC_CC_PERID(47);

/* Set all registers related to descriptor to 0 */
XDMAC0->XDMAC_CHID[0].XDMAC_CNDC = 0;
XDMAC0->XDMAC_CHID[0].XDMAC_CBC = 0;
XDMAC0->XDMAC_CHID[0].XDMAC_CDS_MSP = 0;
XDMAC0->XDMAC_CHID[0].XDMAC_CSUS = 0;
XDMAC0->XDMAC_CHID[0].XDMAC_CDUS = 0;

The DMA channel source address is set to the start of the buffer, and the destination address is set to the CLASSD transmit holding register. The transfer size is set to one word (one audio sample per transfer), with the source address incrementing and the destination address fixed for each transfer.

No descriptors are used for the transfer, so the XDMAC registers related to the descriptor configuration are set to zero.