AnsweredAssumed Answered

STM8L DAC+DMA+TIM4

Question asked by tarasov.pavel on Oct 23, 2012
Latest reply on Dec 25, 2012 by lowpowermcu
hello, i'm trying to play raw pcm (22050 Hz, 8 bit unsigned, mono) from sd card to DAC through DMA, with ring buffer.
everything works perfectly when i'm using TIM2 as interrupt source (at 22050 Hz) and DAC's software trigger.

but i really need to use DMA because of resource-critical timer's interrupt. so, i used stm8l-discovery's wavegenerator example - initialization code copypasted almost unchanged, except of using DAC's circular mode - i don't use it because of playing data stream, not periodic waveform.

init code

i'm filling ring buffer in eternal cycle in main() when the half_buf flag equals "1". i reset the flag after reading sd sector (512 bytes) and setting the flag in DMA channel 2-3 interrupt when counter i==3 and half transfer interrupt flag is set.

sd read sector code

i had to split dac_buf[512] to for 4 parts - dac_buf[4][128] because DMA can't serve more than 255 blocks at once. every time in DMA interrupt transfer complete flag is set, i disable DMA channel 3, do i++ (upto 3), move to memory0 new address (&dac_buf[i]), enable DMA.

DMA interrupt code

looks like it should work, but it doesn't, just producing scary alien sounds with some periodic noise block near sd reading frequency.

reading function is still ok - i traced storing values step-by-step, it's filling dac_buf with exactly the same as on sd card, and in the same order.

address of dac_buf's current block looks ok too - incrementing by 128 and resetting to begin of buffer.

i suspect it doesn't work because of switching off and on DMA - some jitter, stopping TIM4, etc, but i'm not sure.

does anybody have correct source of with playing stream to DAC through DMA? any help, please - i don't have ideas anymore.

Outcomes