What is the difference between DONE and BSY flag of DMA controller?

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

What is the difference between DONE and BSY flag of DMA controller?

729 Views
johntt
Contributor II

Hi,

I have a question about BSY and DONE flags of DMA controller in KL25Z microcontroller. I've read datasheet but unfortunately I cannot understand completely differences between them. So, I've made a simple project with DAC and when I want to turn off the DAC signal then I check BSY or DONE flag and stop generating requests. On oscilloscope I found that when BSY is checked then all data samples of signal are transferred, but when DONE is checked then not always all signal samples are transferred. Is this correct?

Labels (1)
0 Kudos
2 Replies

536 Views
martynhunt
NXP Employee
NXP Employee

Hi,

If possible could you post some of your code for me to see how you are initializing the modules and checking the BSY and DONE bits? The BSY flag is set the first time the channel is enabled after a transfer is initiated and cleared when the DMA has finished the last transaction. The DONE flag is set either when the BCR has reached zero, or when an error condition exists. Are you seeing any error flags when checking the DONE flag?

Best regards,

Martyn

0 Kudos

536 Views
johntt
Contributor II

  // Turn on DAC  

  DAC0_C0 |= DAC_C0_DACEN_MASK;

  // DMA configuration

  DMA0->DMA[0].SAR = (uint32_t) g_samples; // Set source address

  DMA0->DMA[0].DAR = (uint32_t) &(DAC0->DAT[0]); // Set destination address

  DMA0->DMA[0].DCR = 0; // Clear DCR register

  DMA0->DMA[0].DCR |= DMA_DCR_SINC_MASK; // Increment SAR after a successful transfer

  DMA0->DMA[0].DCR &= ~(uint32_t)(DMA_DCR_DINC_MASK); // No change to the DAR after a successful transfer

  DMA0->DMA[0].DCR |= DMA_DCR_SSIZE(2); // Source data size is 16 bit

  DMA0->DMA[0].DCR |= DMA_DCR_DSIZE(2); // Destination data size is 16 bit

  DMA0->DMA[0].DCR |= DMA_DCR_CS_MASK; // Force a single read/write transfer per request

  DMA0->DMA[0].DCR |= DMA_DCR_ERQ_MASK; // Enable peripheral request to initiate transfer

  DMA0->DMA[0].DCR |= DMA_DCR_EINT_MASK; // Enable interrupt on completion of transfer

  DMA0->DMA[0].DSR_BCR = g_nr_of_samples*2; // Set number of bytes to transfer (# of words x 2)

  // Turn on TPM

  TPM0->SC |= TPM_SC_CMOD(1);

Then I want to stop generating signal by waiting for end

  // Disable interrupt on completion of transfer

  DMA0->DMA[0].DCR &= ~((uint32_t)DMA_DCR_EINT_MASK);

  // Wait for completion of transfer

  while(DMA0->DMA[0].DSR_BCR & DMA_DSR_BCR_BSY_MASK);

  // Turn off TPM counter

  TPM0->SC &= ~(uint32_t)TPM_SC_CMOD_MASK;

  // Clear DMA status bits by writing a '1' to the DONE bit

  DMA0->DMA[0].DSR_BCR = DMA_DSR_BCR_DONE_MASK;

  // Clear status register

  DMA0->DMA[0].DSR_BCR = 0;

0 Kudos