(STM32) Use DAC to output WAVE audio waveform

Publisher:xinyi9008Latest update time:2018-07-24 Source: eefocusKeywords:STM32 Reading articles on mobile phones Scan QR code
Read articles on your mobile phone anytime, anywhere

notes:

I originally wanted to use PWM to output audio, but no matter how I debugged it, the frequency of the PWM audio was always wrong. Later, I used DAC instead.

Configuration:

Chip: STM32F103VET

DAC: DAC channel 2 (8-bit right-aligned), timer TIM7 interrupt changes DAC value

WAVE data: stored on the chip in const form (8kHz sampling, 8bit, mono)

 

detour:

(1) Use TIM7 to control DAC output, use TRIG mode, and transfer data to DAC write register through DMA2 channel => No waveform output

(2) It is not necessary to use a timer that is consistent with the DAC channel as a driver, so TIM3 is used. TIM3 is set to work at 8K frequency, and IT_UPDATE is allowed. The DAC value is changed in the TIM3 timer interrupt. The DMA2 channel is not used. => There is a waveform signal output, but the frequency is too high. One second of audio is output in about 50ms.

(3) Do not use TIM3, use TIM7 corresponding to DAC channel 2. Configure TIM7 to 8K operating frequency, allow IT_UPDATE, change the DAC value in the TIM7 timer interrupt, and drive the DAC normally. It is estimated that detour (2) is caused by the fact that the operating frequency of TIM7 is not configured, resulting in abnormal DAC frequency, but it has not been confirmed.

(4) Use the timer in step (3) and DMA to transfer data => DAC cannot output audio normally [Due to time constraints, this problem will not be solved for the time being]

Routine:

void DACInit(void)

{

DAC_InitTypeDef   DAC_InitStructure;

TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;

 

// 1. Configure TIM7

TIM_DeInit(TIM7);

/* Time base configuration */

TIM_TimeBaseStructure.TIM_Period = GetARRValue(8000); // Reset period

TIM_TimeBaseStructure.TIM_Prescaler = 0; // Frequency division

TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1; // Clock division

TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Down; // Counting mode

TIM_TimeBaseInit(TIM7, &TIM_TimeBaseStructure);

// Enable TIM7 update interrupt 

TIM_ITConfig(TIM7, TIM_IT_Update, ENABLE);

 

// 2. Configure DAC

DAC_DeInit();

/* DAC channel1 Configuration */

DAC_InitStructure.DAC_Trigger = DAC_Trigger_None;        // 

DAC_InitStructure.DAC_WaveGeneration = DAC_WaveGeneration_None;

DAC_InitStructure.DAC_LFSRUnmask_TriangleAmplitude = DAC_LFSRUnmask_Bits8_0;

DAC_InitStructure.DAC_OutputBuffer = DAC_OutputBuffer_Enable;

// DA channel 2 initialization

DAC_Init(DAC_Channel_2, &DAC_InitStructure);

/* Enable DAC Channel1: Once the DAC channel1 is enabled, PA.04 is 

automatically connected to the DAC converter. */

DAC_Cmd(DAC_Channel_2, ENABLE);

 

// 3. Start TIM7

TIM_Cmd(TIM7, ENABLE);

}

 

 

void TIM7_IRQHandler(void)

{

INT16U tmpCap;

 

if (TIM_GetITStatus(TIM7, TIM_IT_Update) != RESET)

{

if( wavecount < wave0Length )

{

tmpCap = wave0[wavecount];

wavecount++;

/* Set DAC Channel1 DHR register */

DAC_SetChannel2Data(DAC_Align_8b_R,tmpCap);                        

}

else

{

// Complete the transfer and turn off the interrupt

wavecount = 0;

TIM_ITConfig(TIM7, TIM_IT_Update, DISABLE);

TIM_Cmd(TIM7, DISABLE);

// Need to turn off DAC, otherwise there will be noise when there is no sound

DAC_Cmd(DAC_Channel_2, DISABLE);

}

}

 

/* Clear TIM6 update interrupt */

TIM_ClearITPendingBit(TIM7, TIM_IT_Update);

}

  

// Get the timer automatically according to the sampling rate

// Extracted from waveplayer.c

INT16U GetARRValue(INT16U sample)

{

INT16U arrValue;

/* Update OCA value to match .WAV file sampling rate */

switch (sample)

{

case SAMPLE_RATE_8000 :

   arrValue = (uint16_t)(72000000/8000);

   break; /* 8KHz = 2x36MHz / 9000 */

case SAMPLE_RATE_11025:

   arrValue = (uint16_t)(72000000/11025);

   break; /* 11.025KHz = 2x36MHz / 6531 */

case SAMPLE_RATE_16000:

    arrValue = (uint16_t)(72000000/16000);

   break; /* 16KHz = 2x36MHz / 4500 */

case SAMPLE_RATE_22050:

   arrValue = (uint16_t)(72000000/22050);

   break; /* 22.05KHz = 2x36MHz / 2365 */

case SAMPLE_RATE_44100:

   arrValue = (uint16_t)(72000000/44100);

   break; /* 44.1KHz = 2x36MHz / 1633 */

case SAMPLE_RATE_48000:

   arrValue = (uint16_t)(72000000/48000);

   break; /* 48KHz = 2x36MHz / 1500 */

default:

   arrValue = 0;

   break;

}

return arrValue;

}


Keywords:STM32 Reference address:(STM32) Use DAC to output WAVE audio waveform

Previous article:STM32 PCM1770 debugging
Next article:STM32F4 FFT music spectrum is not too easy!

Latest Microcontroller Articles
Change More Related Popular Components

EEWorld
subscription
account

EEWorld
service
account

Automotive
development
circle

About Us Customer Service Contact Information Datasheet Sitemap LatestNews


Room 1530, 15th Floor, Building B, No.18 Zhongguancun Street, Haidian District, Beijing, Postal Code: 100190 China Telephone: 008610 8235 0740

Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved 京ICP证060456号 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号