cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F4 Audio Capture using FatFs SD

muhammaduzairafzal45
Associate III
Posted on December 16, 2014 at 21:02

I am facing problem in capturing and saving audio .wav file to SD card using DMA and SDIO interface. I am using STM32F4 discovery. The loopback works fine. I am using I2S sampling rate of 32k. Problem arrives when writing to SD. I am using buffer size of 1024 now which was initially 8192. I figured out after spending a week that FatFs library work only if i write 512 bytes  on SD.If i write more data like 8k buffer,it randomly skips huge chunks of data. Also i notices that it takes 20ms max to write 512 bytes(write cycle varies from 5ms to 20ms) on SD using SDIO which i think is horribly slow speed.I am now writing 1024 bytes by writing 512 bytes in ping pong method but data is skipping and audio is barely recognized.Note that i am writing to file in main while loop when DMA buffer is filled in ping pong method.I tried to write data in DMA ISR but it SDIO stuck during writes which i think is due to fast speed of incoming data so i moved to while loop.Can somebody tell me why cannot i write more than 512 bytes at once on SD and why is SDIO speed so slow.SD card is of good quality? Basic chunks of code is copied below. Thanks,

int16_t array_pong[512];

/* CODEC_I2S peripheral configuration for master TX */

SPI_I2S_DeInit(CODEC_I2S);

I2S_InitStructure.I2S_AudioFreq = 32000;

I2S_InitStructure.I2S_Standard = I2S_Standard_Phillips;

I2S_InitStructure.I2S_DataFormat = I2S_DataFormat_16b;//extended;

I2S_InitStructure.I2S_CPOL = I2S_CPOL_Low;

I2S_InitStructure.I2S_Mode = I2S_Mode_MasterTx;

I2S_InitStructure.I2S_MCLKOutput = I2S_MCLKOutput_Enable;

/* Initialize the I2S main channel for TX */

I2S_Init(CODEC_I2S, &I2S_InitStructure);

void DMA1_Stream3_IRQHandler(void)

int16_t *src, *dst, sz;

GPIO_ToggleBits(GPIOC, GPIO_Pin_1);

total_time++;

/* Transfer complete interrupt */

if (DMA_GetFlagStatus(AUDIO_I2S_EXT_DMA_STREAM, AUDIO_I2S_EXT_DMA_FLAG_TC) != RESET)

{

/* Point to 2nd half of buffers */

sz = szbuf/2;

src = (int16_t *)(rxbuf) + sz;

dst = (int16_t *)(txbuf) + sz;

WaveCounter += sz;

//I2S_RX_CallBack(src, dst, sz, 0);

  

ping_complete = 1;

/* Clear the Interrupt flag */

DMA_ClearFlag(AUDIO_I2S_EXT_DMA_STREAM, AUDIO_I2S_EXT_DMA_FLAG_TC);

}

/* Half Transfer complete interrupt */

if (DMA_GetFlagStatus(AUDIO_I2S_EXT_DMA_STREAM, AUDIO_I2S_EXT_DMA_FLAG_HT) != RESET)

{

/* Point to 1st half of buffers */

sz = szbuf/2;

src = (int16_t *)(rxbuf);

dst = (int16_t *)(txbuf);

WaveCounter += sz;

//I2S_RX_CallBack(src, dst, sz, 1);

pong_complete = 1;

/* Clear the Interrupt flag */

DMA_ClearFlag(AUDIO_I2S_EXT_DMA_STREAM, AUDIO_I2S_EXT_DMA_FLAG_HT);    

}

}

while(1)

{

if(total_time >= 2000)

{

I2S_Cmd(CODEC_I2S, DISABLE);

I2S_Cmd(CODEC_I2S_EXT, DISABLE);

break;

}

if(ping_complete == 1)

{

f_write (&file, (int16_t*)array_pong+256, 512, (void *)&bw);

ping_complete =0;

}

if(pong_complete == 1)

{

f_write (&file,(int16_t *) array_pong, 512, (void *)&bw);

pong_complete =0;

}

__nop;

__nop;

__nop;

__nop;

__nop;

__nop;

}

#dma #stm32 #fatfs #sdio #sd
0 REPLIES 0