AUDIO DISCO_F769NI audioloop basic example
Dependencies: BSP_DISCO_F769NI
main.cpp
- Committer:
- Jerome Coutant
- Date:
- 2019-11-22
- Revision:
- 2:db1aee306f50
- Parent:
- 1:f849e36f029e
File content as of revision 2:db1aee306f50:
#include "mbed.h"
#include "stm32f769i_discovery.h"
#include "stm32f769i_discovery_audio.h"
static void CopyBuffer(int16_t *pbuffer1, int16_t *pbuffer2, uint16_t BufferSize);
#define SCRATCH_BUFF_SIZE 1024
#define RECORD_BUFFER_SIZE 4096
typedef enum {
BUFFER_OFFSET_NONE = 0,
BUFFER_OFFSET_HALF = 1,
BUFFER_OFFSET_FULL = 2,
} BUFFER_StateTypeDef;
volatile uint32_t audio_rec_buffer_state = BUFFER_OFFSET_NONE;
int32_t Scratch[SCRATCH_BUFF_SIZE];
/* Buffer containing the PCM samples coming from the microphone */
int16_t RecordBuffer[RECORD_BUFFER_SIZE];
/* Buffer used to stream the recorded PCM samples towards the audio codec. */
int16_t PlaybackBuffer[RECORD_BUFFER_SIZE];
int main()
{
uint32_t audio_loop_back_init = RESET ;
printf("\n\nAUDIO LOOPBACK EXAMPLE FOR DISCO-F769NI START:\n");
/* Initialize Audio Recorder with 4 channels to be used */
if (BSP_AUDIO_IN_Init(BSP_AUDIO_FREQUENCY_44K, DEFAULT_AUDIO_IN_BIT_RESOLUTION, 2*DEFAULT_AUDIO_IN_CHANNEL_NBR) == AUDIO_ERROR) {
printf("BSP_AUDIO_IN_Init error\n");
}
/* Allocate scratch buffers */
if (BSP_AUDIO_IN_AllocScratch (Scratch, SCRATCH_BUFF_SIZE) == AUDIO_ERROR) {
printf("BSP_AUDIO_IN_AllocScratch error\n");
}
/* Start Recording */
if (BSP_AUDIO_IN_Record((uint16_t*)&RecordBuffer[0], RECORD_BUFFER_SIZE) == AUDIO_ERROR) {
printf("BSP_AUDIO_IN_Record error\n");
}
uint8_t ChannelNumber = BSP_AUDIO_IN_GetChannelNumber();
audio_rec_buffer_state = BUFFER_OFFSET_NONE;
while (1) {
/* 1st or 2nd half of the record buffer ready for being copied to the playbakc buffer */
if(audio_rec_buffer_state != BUFFER_OFFSET_NONE) {
/* Copy half of the record buffer to the playback buffer */
if(audio_rec_buffer_state == BUFFER_OFFSET_HALF) {
CopyBuffer(&PlaybackBuffer[0], &RecordBuffer[0], RECORD_BUFFER_SIZE/2);
if (audio_loop_back_init == RESET) {
/* Initialize the audio device*/
if (BSP_AUDIO_OUT_Init(OUTPUT_DEVICE_HEADPHONE, 70, BSP_AUDIO_FREQUENCY_44K) == AUDIO_ERROR) {
printf("BSP_AUDIO_OUT_Init error\n");
}
if(ChannelNumber > 2) {
BSP_AUDIO_OUT_SetAudioFrameSlot(CODEC_AUDIOFRAME_SLOT_0123);
} else {
BSP_AUDIO_OUT_SetAudioFrameSlot(CODEC_AUDIOFRAME_SLOT_02);
}
/* Play the recorded buffer */
if (BSP_AUDIO_OUT_Play((uint16_t *) &PlaybackBuffer[0], 2*RECORD_BUFFER_SIZE) == AUDIO_ERROR) {
printf("BSP_AUDIO_OUT_Play error\n");
}
/* Audio device is initialized only once */
audio_loop_back_init = SET;
}
} else { /* if(audio_rec_buffer_state == BUFFER_OFFSET_FULL)*/
CopyBuffer(&PlaybackBuffer[RECORD_BUFFER_SIZE/2], &RecordBuffer[RECORD_BUFFER_SIZE/2], RECORD_BUFFER_SIZE/2);
}
/* Wait for next data */
audio_rec_buffer_state = BUFFER_OFFSET_NONE;
}
}
}
/*-------------------------------------------------------------------------------------
Callbacks implementation:
the callbacks API are defined __weak in the stm32f769i_discovery_audio.c file
and their implementation should be done in the user code if they are needed.
Below some examples of callback implementations.
-------------------------------------------------------------------------------------*/
/**
* @brief Manages the DMA Transfer complete interrupt.
* @param None
* @retval None
*/
void BSP_AUDIO_IN_TransferComplete_CallBack(void)
{
audio_rec_buffer_state = BUFFER_OFFSET_FULL;
}
/**
* @brief Manages the DMA Half Transfer complete interrupt.
* @param None
* @retval None
*/
void BSP_AUDIO_IN_HalfTransfer_CallBack(void)
{
audio_rec_buffer_state = BUFFER_OFFSET_HALF;
}
/**
* @brief Audio IN Error callback function.
* @param None
* @retval None
*/
void BSP_AUDIO_IN_Error_CallBack(void)
{
printf("BSP_AUDIO_IN_Error_CallBack\n");
}
/**
* @brief Copy content of pbuffer2 to pbuffer1
* @param1 BufferOut
* @param2 BufferIn
* @param3 Size
* @retval None
*/
static void CopyBuffer(int16_t *pbuffer1, int16_t *pbuffer2, uint16_t BufferSize)
{
uint32_t i = 0;
for(i = 0; i < BufferSize; i++) {
pbuffer1[i] = pbuffer2[i];
}
}