cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F37x synchronizing ADC & DAC by DMA

jogerh
Associate II
Posted on March 06, 2016 at 22:00

Dear Community,

I am trying to find a way to synchronize DMA2_channel3 + DAC1ch1 and DMA1_Channel1 + ADC1 for analog output of a set of data via the DAC and simultaneously recording a system’s response using the ADC.  What I tried so far was to start the ADC/DMA using the  interrupt handler of DAC1ch1/DMA2ch3. This worked in 1 of 10 trials and in 9 of 10 trials the hard fault handler is triggered (BUS error). Methinks this is because I set up APB2 div @ 2 and APB1 div@1  to enable the ADC (ADC PRESC = 2) to be triggered with the same speed like APB2 devices such as the Timer used to trigger DAC1. (Page 99

http://www.st.com/st-web-ui/static/active/en/resource/technical/document/reference_manual/DM00041563.pdf

).

An ideal solution would be if I could start both devices DAC and ADC at the same time. I would very happy if someone could give a hint.

1 REPLY 1
jogerh
Associate II
Posted on March 10, 2016 at 17:00

Dear Community,

after experimenting a while I found a suitable solution how to synchronize DMA dependent processes:

1.)

   

Use DMA in Normal mode

       DMA_InitStructure.DMA_Mode = DMA_Mode_Normal;

2.)

   

If the IT handler is called disable the DMA, then reset the CNDTR with the BLOCK_SIZE it was initially initialized and e.g. finally re- enable the DMA and don’t forget to clear the TC bit

                DMA_Cmd(DMA1_Channel1, DISABLE);             

                DMA1_Channel1->CNDTR = BLOCK_SIZE; // <--- transaction length     

                (copied   from here:

http://electronics.stackexchange.com/questions/181908/restart-rx-usart-dma-in-stm32l1

)

               DMA_Cmd(DMA1_Channel1, ENABLE);

               

DMA_ClearITPendingBit(DMA1_IT_TC1);

Thus the whole process behaves like a circular one. Now instead re- enabling the DMA inside the IT handler one can perform this also somewhere else e.g. in main. Thus it is possible to enable all the DMA channels which needs to be synchronized at nearly the same time. To avoid the assert- function introduced by stlib (e.g. to save time) one can also access the CCR register directly:

       DMA1_Channel1->CCR |= DMA_CCR_EN;          //Enable