Merged i2s changes from dev (fixed warnings)

This commit is contained in:
Alex Duchesne 2025-11-07 17:30:06 -05:00
parent e1d4c9f257
commit 7b37da4901
5 changed files with 36 additions and 32 deletions

View File

@ -33,7 +33,7 @@ Note that there are some restrictions on how high the PWM frequency can be, and
#include "rg_system.h" // include configuration from components/retro-go/targets/*/config.h
#ifdef RG_AUDIO_USE_BUZZER_PIN
#if RG_AUDIO_USE_BUZZER_PIN
#include "rg_audio.h"
#ifndef ESP_PLATFORM

View File

@ -11,10 +11,21 @@
#include <driver/gpio.h>
#include <driver/i2s.h>
#if RG_AUDIO_USE_INT_DAC
#include <driver/dac.h>
#ifdef RG_GPIO_SND_AMP_ENABLE_INVERT
#define MUTE_ENABLE 1
#define MUTE_DISABLE 0
#else
#define MUTE_ENABLE 0
#define MUTE_DISABLE 1
#endif
// We can safely assume that no application will submit more than 640 audio frames per call to
// driver_submit (32000/50). Using a single large buffer risks blocking the call needlessly because
// some apps submit more than once per cycle or there could be occasional jitter (early submission).
#define DMA_BUFFER_COUNT 4
#define DMA_BUFFER_LEN 180
static struct {
const char *last_error;
int device;
@ -37,8 +48,8 @@ static bool driver_init(int device, int sample_rate)
.channel_format = I2S_CHANNEL_FMT_RIGHT_LEFT,
.communication_format = I2S_COMM_FORMAT_STAND_MSB,
.intr_alloc_flags = 0, // ESP_INTR_FLAG_LEVEL1
.dma_buf_count = 4, // Goal is to have ~800 samples over 2-8 buffers (3x270 or 5x180 are pretty good)
.dma_buf_len = 180, // The unit is stereo samples (4 bytes) (optimize for 533 usage)
.dma_buf_count = DMA_BUFFER_COUNT,
.dma_buf_len = DMA_BUFFER_LEN,
}, 0, NULL);
if (ret == ESP_OK)
ret = i2s_set_dac_mode(RG_AUDIO_USE_INT_DAC);
@ -58,8 +69,8 @@ static bool driver_init(int device, int sample_rate)
.channel_format = I2S_CHANNEL_FMT_RIGHT_LEFT,
.communication_format = I2S_COMM_FORMAT_STAND_I2S,
.intr_alloc_flags = 0, // ESP_INTR_FLAG_LEVEL1
.dma_buf_count = 4, // Goal is to have ~800 samples over 2-8 buffers (3x270 or 5x180 are pretty good)
.dma_buf_len = 180, // The unit is stereo samples (4 bytes) (optimize for 533 usage)
.dma_buf_count = DMA_BUFFER_COUNT,
.dma_buf_len = DMA_BUFFER_LEN,
#if CONFIG_IDF_TARGET_ESP32
.use_apll = true, // External DAC may care about accuracy
#endif
@ -80,6 +91,11 @@ static bool driver_init(int device, int sample_rate)
state.last_error = "This device does not support external DAC mode!";
#endif
}
#ifdef RG_GPIO_SND_AMP_ENABLE
gpio_reset_pin(RG_GPIO_SND_AMP_ENABLE);
gpio_set_level(RG_GPIO_SND_AMP_ENABLE, MUTE_ENABLE);
gpio_set_direction(RG_GPIO_SND_AMP_ENABLE, GPIO_MODE_OUTPUT);
#endif
return state.last_error == NULL;
}
@ -94,11 +110,7 @@ static bool driver_deinit(void)
if (state.device == 0)
{
#if RG_AUDIO_USE_INT_DAC
if (RG_AUDIO_USE_INT_DAC & I2S_DAC_CHANNEL_RIGHT_EN)
dac_output_disable(DAC_CHANNEL_1);
if (RG_AUDIO_USE_INT_DAC & I2S_DAC_CHANNEL_LEFT_EN)
dac_output_disable(DAC_CHANNEL_2);
dac_i2s_disable();
i2s_set_dac_mode(I2S_DAC_CHANNEL_DISABLE);
#endif
}
else if (state.device == 1)
@ -118,11 +130,9 @@ static bool driver_deinit(void)
static bool driver_submit(const rg_audio_frame_t *frames, size_t count)
{
float volume = state.muted ? 0.f : (state.volume * 0.01f);
rg_audio_frame_t buffer[180];
size_t written = 0;
size_t pos = 0;
bool use_internal_dac = state.device == 0;
rg_audio_frame_t buffer[DMA_BUFFER_LEN];
size_t pos = 0;
for (size_t i = 0; i < count; ++i)
{
@ -131,15 +141,15 @@ static bool driver_submit(const rg_audio_frame_t *frames, size_t count)
if (use_internal_dac)
{
int sample = (left + right) >> 1;
#if RG_AUDIO_USE_INT_DAC == 1
left = sample + 0x8000; // the internal DAC expects unsigned data
left = ((left + right) >> 1) + 0x8000; // the internal DAC expects unsigned data
right = 0;
#elif RG_AUDIO_USE_INT_DAC == 2
left = 0;
right = sample + 0x8000; // the internal DAC expects unsigned data
left = 0;
right = ((left + right) >> 1) + 0x8000; // the internal DAC expects unsigned data
#elif RG_AUDIO_USE_INT_DAC == 3
// In two channel mode we use left and right as a differential mono output to increase resolution.
int sample = (left + right) >> 1;
if (sample > 0x7F00)
{
left = 0x8000 + (sample - 0x7F00);
@ -168,6 +178,7 @@ static bool driver_submit(const rg_audio_frame_t *frames, size_t count)
if (i == count - 1 || ++pos == RG_COUNT(buffer))
{
size_t written;
if (i2s_write(I2S_NUM_0, (void *)buffer, pos * 4, &written, 1000) != ESP_OK)
RG_LOGW("I2S Submission error! Written: %d/%d\n", written, pos * 4);
pos = 0;
@ -179,16 +190,8 @@ static bool driver_submit(const rg_audio_frame_t *frames, size_t count)
static bool driver_set_mute(bool mute)
{
i2s_zero_dma_buffer(I2S_NUM_0);
#if defined(RG_GPIO_SND_AMP_ENABLE)
gpio_set_direction(RG_GPIO_SND_AMP_ENABLE, GPIO_MODE_OUTPUT);
#if defined(RG_TARGET_BYTEBOI_REV1)
gpio_set_level(RG_GPIO_SND_AMP_ENABLE, mute);
#else
gpio_set_level(RG_GPIO_SND_AMP_ENABLE, !mute);
#endif
#elif defined(RG_TARGET_QTPY_GAMER)
rg_i2c_gpio_set_direction(AW_HEADPHONE_EN, 0);
rg_i2c_gpio_set_level(AW_HEADPHONE_EN, !mute);
#ifdef RG_GPIO_SND_AMP_ENABLE
gpio_set_level(RG_GPIO_SND_AMP_ENABLE, mute ? MUTE_ENABLE : MUTE_DISABLE);
#endif
state.muted = mute;
return true;

View File

@ -102,3 +102,4 @@
// #define RG_GPIO_SND_I2S_WS GPIO_NUM_NC
// #define RG_GPIO_SND_I2S_DATA GPIO_NUM_NC
#define RG_GPIO_SND_AMP_ENABLE GPIO_NUM_13
#define RG_GPIO_SND_AMP_ENABLE_INVERT // Uncomment if the mute = HIGH

View File

@ -6,4 +6,4 @@ IDF_TARGET = "esp32s3"
# .fw file format, if supported by the device
FW_FORMAT = "none"
# Default apps to build when none is specified (comment to build all)
# DEFAULT_APPS = "launcher prboom-go"
DEFAULT_APPS = "launcher retro-core prboom-go gwenesis"

View File

@ -6,4 +6,4 @@ IDF_TARGET = "esp32"
# .fw file format, if supported by the device
FW_FORMAT = "none"
# Default apps to build when none is specified (comment to build all)
# DEFAULT_APPS = "launcher prboom-go"
DEFAULT_APPS = "launcher retro-core prboom-go gwenesis"