fix(box): radio sound + add SuperLoustic station
Webradio was silent: the streams are stereo 44.1 kHz MP3, and opening the
ES8311 codec in stereo failed ("i2s_std_set_slot: dma descriptor") because the
stereo I2S DMA no longer fits the tight internal RAM — the podcast path works
only because its files are mono. Downmix the decoded stereo PCM to mono and
open the codec at one channel. Also switch the stream URLs to plain HTTP: the
HTTPS handshake intermittently failed to allocate AES memory, and these mounts
serve identical audio over http with no redirect. Add SuperLoustic (3 stations).
This commit is contained in:
@@ -178,6 +178,7 @@ static void decode_task(void *arg)
|
||||
uint32_t out_cap = DEC_OUT_CAP_INIT;
|
||||
uint8_t *out = malloc(out_cap);
|
||||
bool codec_open = false;
|
||||
int dec_ch = 1; // channels reported by the stream (1 or 2)
|
||||
|
||||
if (!inbuf || !out || !codec) {
|
||||
ESP_LOGE(TAG, "decode buffers/codec unavailable");
|
||||
@@ -225,19 +226,21 @@ static void decode_task(void *arg)
|
||||
}
|
||||
if (frame.decoded_size > 0) {
|
||||
if (!codec_open) {
|
||||
// Open the codec at the rate/channels reported by the stream
|
||||
// on the first decoded PCM, exactly like aac_player.c.
|
||||
esp_audio_simple_dec_info_t info = {0};
|
||||
esp_audio_simple_dec_get_info(dec, &info);
|
||||
ESP_LOGI(TAG, "MP3 %" PRIu32 " Hz %u ch %u bit",
|
||||
dec_ch = (info.channel >= 2) ? 2 : 1;
|
||||
ESP_LOGI(TAG, "MP3 %" PRIu32 " Hz %u ch %u bit -> codec mono",
|
||||
info.sample_rate, info.channel,
|
||||
info.bits_per_sample);
|
||||
lisael_udp_send("RADIO: decoded MP3 %" PRIu32 " Hz %u ch %u bit -> opening codec",
|
||||
info.sample_rate, info.channel, info.bits_per_sample);
|
||||
// Open the codec in MONO regardless of the stream: a stereo
|
||||
// 44.1 kHz I2S slot needs more internal DMA RAM than is free
|
||||
// (it fails "i2s_std_set_slot: dma descriptor"). The podcast
|
||||
// path works precisely because its files are mono. We downmix
|
||||
// stereo PCM below before writing.
|
||||
esp_codec_dev_close(codec);
|
||||
esp_codec_dev_sample_info_t fs = {
|
||||
.bits_per_sample = info.bits_per_sample,
|
||||
.channel = info.channel,
|
||||
.channel = 1,
|
||||
.sample_rate = info.sample_rate,
|
||||
};
|
||||
esp_codec_dev_open(codec, &fs);
|
||||
@@ -245,8 +248,17 @@ static void decode_task(void *arg)
|
||||
(float)lisael_audio_get_volume());
|
||||
codec_open = true;
|
||||
}
|
||||
// Blocking write — this is what paces the whole pipeline.
|
||||
esp_codec_dev_write(codec, frame.buffer, frame.decoded_size);
|
||||
if (dec_ch == 2) {
|
||||
// Downmix interleaved 16-bit stereo to mono, in place.
|
||||
int16_t *pcm = (int16_t *)frame.buffer;
|
||||
int frames = (int)(frame.decoded_size / 4); // 4 bytes/stereo frame
|
||||
for (int i = 0; i < frames; i++) {
|
||||
pcm[i] = (int16_t)(((int)pcm[2 * i] + (int)pcm[2 * i + 1]) / 2);
|
||||
}
|
||||
esp_codec_dev_write(codec, frame.buffer, frames * 2);
|
||||
} else {
|
||||
esp_codec_dev_write(codec, frame.buffer, frame.decoded_size);
|
||||
}
|
||||
}
|
||||
if (raw.consumed == 0 && frame.decoded_size == 0) {
|
||||
break; // no progress on this chunk; fetch more from the network
|
||||
|
||||
+7
-2
@@ -38,9 +38,14 @@ typedef struct {
|
||||
// listen.radioking.com mounts.
|
||||
static const radio_station_t k_stations[] = {
|
||||
// Radio Doudou — comptines & berceuses pour les tout-petits.
|
||||
{ "Radio Doudou", "https://listen.radioking.com/radio/11565/stream/22961" },
|
||||
// Plain HTTP on purpose: the box's internal RAM is too tight to also run the
|
||||
// mbedtls/AES handshake while streaming (TLS failed "esp-aes: alloc"). These
|
||||
// RadioKing mounts serve identical audio over http:// (no 3xx to https).
|
||||
{ "Radio Doudou", "http://listen.radioking.com/radio/11565/stream/22961" },
|
||||
// Radio Pomme d'Api (Bayard) — la radio des 3-7 ans.
|
||||
{ "Pomme d'Api", "https://listen.radioking.com/radio/361753/stream/411352" },
|
||||
{ "Pomme d'Api", "http://listen.radioking.com/radio/361753/stream/411352" },
|
||||
// SuperLoustic — la radio des enfants (chansons, génériques, histoires).
|
||||
{ "SuperLoustic", "http://radio6.pro-fhi.net/radio/9004/stream" },
|
||||
};
|
||||
|
||||
#define K_STATIONS_COUNT ((int)(sizeof(k_stations) / sizeof(k_stations[0])))
|
||||
|
||||
Reference in New Issue
Block a user