cancel
Showing results for 
Search instead for 
Did you mean: 

DAC-USB Implementation Problem

B??el
Associate II

Hi, I am using Nucleo F303re with STM32 HAL Libraries built by STMCubeMX in order to implement an USB Audio player with bulk transfers. I changed the USB-CDC code a little bit to implement my application. I receive the data in the CDC-Receive-FS function and copy the data in there to a buffer used by DAC in DMA Circular mode. But everytime DMA starts to read the buffer from the beginning again i get an error equivelant to 16 samples of data. I am posting the error and the code here. My data is being sent with libusb in 480bytes chunks in regular timing. My array supplied to the DAC on the board is 19200 bytes and even if i change the size of the array it always happens at the beginning of the buffer. If i make it 9600 bytes error happens every 9600 bytes. If i make it 19200 or even 38400 it happens at every 19200 or 38400 bytes.

static int8_t CDC_Receive_FS(uint8_t* Buf, uint32_t *Len)
{
  /* USER CODE BEGIN 6 */
//	if(move_cnt >= PACK_SIZE){
//		move_cnt =0;
//		
//	}
 
//	memcpy(&RxBuf[move_cnt],Buf,*Len);
//	move_cnt += *Len;
	
 
	
	
 
//	
for(uint16_t i =0; i<*Len ; i++){
			
	
	RxBuf[byte_cnt] = Buf[i];
 
 
	byte_cnt++;
		
	if(byte_cnt>=PACK_SIZE){
		byte_cnt=0;
	}
 }
 
 
if(pack_cnt==0){
	rx_cb();
}
pack_cnt++;
 
 
USBD_CDC_SetRxBuffer(&hUsbDeviceFS, &Buf[0]);		  
USBD_CDC_ReceivePacket(&hUsbDeviceFS);
 
	
//	for (uint8_t i =0; i<*Len;i++){
	//		RxBuf[rx_ptr] =Buf[i] ;
	//		rx_ptr++;	
	//	if(rx_ptr>=479){
	//	rx_ptr = 0;
	//}
  //}
 
 
 
 
 
			
	
 
  return (USBD_OK);
  /* USER CODE END 6 */
}
void rx_cb(void){
 
HAL_TIM_Base_Start(&htim6);
HAL_DAC_Start(&hdac1,DAC_CHANNEL_1);
HAL_DAC_Start_DMA(&hdac1,DAC_CHANNEL_1,(uint32_t*)RxBuf,PACK_SIZE,DAC_ALIGN_8B_R);
 
}

4 REPLIES 4
Piranha
Chief II

There is no such thing as regular timing in workstation software. And there are no identical and absolutely stable hardware clocks either. Oscilloscope actually proves it - it can be seen clearly that the device plays previous buffer data - different fraction of the same sine wave.

https://en.wikipedia.org/wiki/USB#Audio_streaming

B??el
Associate II

Thank you for your answer. What do you mean by workstation software and what do you suggest i can do to solve this problem

Piranha
Chief II

By workstation I mean any PC or Mac with Windows, Linux or macOS. And by software I mean userspace software running on any of these big non-realtime operating systems. For audio there are standard USB Audio Class, which You have to implement.

https://github.com/julbouln/stm32f4discovery_soundcard

P.S. By the way, MCUs internal DACs are not for Hi-Fi audio. If You need that, You have to add external DAC by an I2S connection.

B??el
Associate II

Thank you again. I will use i2s if i dont like 8bit or 12 bit resolution data from internal DAC. But maybe the same problem would occur again as I2S also uses DMA as DAC as in this applicaiton. But the problem is i was wrong when i was sayin real time data transfer. Actually im sending 10ms worth of audio data which is 480bytes at 48khz sampling rate at intervals. Like the First data arrives and the second one arrives at 6th ms. And the others start to arrive at 16th 26th.. and so on. So im sending the data in chunks and giving at least 4ms for the transfer and copying to DAC buffer be completed. So the data is always arriving before DAC starts to process that data. So it is not actually real time. And the problem appears always at the beginning of the buffer. If i define a small buffer or a large it always appears at when DMA turns back to the beginning of that buffer and im always supplying that buffer with different data. So maybe the problem can be about something else.