Commit 5b12ce5a authored by Stefan Seyfried's avatar Stefan Seyfried

AudioBuffer: allow setting size of RAM and PSRAM buffer

instead of the fixed buffer size of 300000 for PSRAM and 8000 for
non-PSRAM setup, allow to configure the buffer sizes, example code
for that is
    audio.setBuffersize(32768, 0);
which will set the RAM buffer size to 32k and disable PSRAM usage.
I am investigating "bad WiFi throughput with PSRAM" issues and disabling
PSRAM is one workaround I found.
parent 0a415271
......@@ -35,22 +35,26 @@ AudioBuffer::~AudioBuffer() {
m_buffer = NULL;
}
void AudioBuffer::setBufsize(int ram, int psram) {
if (ram > -1) // -1 == default / no change
m_buffSizeRAM = ram;
if (psram > -1)
m_buffSizePSRAM = psram;
}
size_t AudioBuffer::init() {
if(m_buffer) free(m_buffer);
m_buffer = NULL;
if(psramInit()) {
if(psramInit() && m_buffSizePSRAM > 0) {
// PSRAM found, AudioBuffer will be allocated in PSRAM
m_f_psram = true;
m_buffSize = m_buffSizePSRAM;
if(m_buffer == NULL) {
m_buffer = (uint8_t*) ps_calloc(m_buffSize, sizeof(uint8_t));
m_buffSize = m_buffSizePSRAM - m_resBuffSizePSRAM;
if(m_buffer == NULL) {
// not enough space in PSRAM, use ESP32 Flash Memory instead
m_buffer = (uint8_t*) calloc(m_buffSize, sizeof(uint8_t));
m_buffSize = m_buffSizeRAM - m_resBuffSizeRAM;
}
}
} else { // no PSRAM available, use ESP32 Flash Memory"
m_buffer = (uint8_t*) ps_calloc(m_buffSize, sizeof(uint8_t));
m_buffSize = m_buffSizePSRAM - m_resBuffSizePSRAM;
}
if(m_buffer == NULL) {
// PSRAM not found, not configured or not enough available
m_f_psram = false;
m_buffSize = m_buffSizeRAM;
m_buffer = (uint8_t*) calloc(m_buffSize, sizeof(uint8_t));
m_buffSize = m_buffSizeRAM - m_resBuffSizeRAM;
......@@ -205,20 +209,24 @@ Audio::Audio(bool internalDAC /* = false */, i2s_dac_mode_t channelEnabled /* =
}
}
//---------------------------------------------------------------------------------------------------------------------
void Audio::setBufsize(int rambuf_sz, int psrambuf_sz) {
if(InBuff.isInitialized()) {
ESP_LOGE(TAG, "Audio::setBufsize must not be called after audio is initialized");
return;
}
InBuff.setBufsize(rambuf_sz, psrambuf_sz);
};
void Audio::initInBuff() {
if(!InBuff.isInitialized()) {
size_t size = InBuff.init();
if(size == m_buffSizeRAM - m_resBuffSizeRAM) {
AUDIO_INFO(sprintf(chbuf, "PSRAM not found, inputBufferSize: %u bytes", size - 1);)
m_f_psram = false;
}
if(size == m_buffSizePSRAM - m_resBuffSizePSRAM) {
AUDIO_INFO(sprintf(chbuf, "PSRAM found, inputBufferSize: %u bytes", size - 1);)
m_f_psram = true;
if (size > 0) {
AUDIO_INFO(sprintf(chbuf, "PSRAM %sfound, inputBufferSize: %u bytes", InBuff.havePSRAM()?"":"not ", size - 1);)
}
}
changeMaxBlockSize(1600); // default size mp3 or aac
}
//---------------------------------------------------------------------------------------------------------------------
esp_err_t Audio::I2Sstart(uint8_t i2s_num) {
// It is not necessary to call this function after i2s_driver_install() (it is started automatically),
......@@ -3043,7 +3051,7 @@ void Audio::processWebStream() {
int16_t bytesAddedToBuffer = 0;
if(m_f_psram) if(bytesCanBeWritten > 4096) bytesCanBeWritten = 4096; // PSRAM throttle
if(InBuff.havePSRAM()) if(bytesCanBeWritten > 4096) bytesCanBeWritten = 4096; // PSRAM throttle
if(m_f_webfile){
// normally there is nothing to do here, if byteCounter == contentLength
......
......@@ -114,6 +114,7 @@ public:
~AudioBuffer(); // frees the buffer
size_t init(); // set default values
bool isInitialized() { return m_f_init; };
void setBufsize(int ram, int psram);
void changeMaxBlockSize(uint16_t mbs); // is default 1600 for mp3 and aac, set 16384 for FLAC
uint16_t getMaxBlockSize(); // returns maxBlockSize
size_t freeSpace(); // number of free bytes to overwrite
......@@ -126,10 +127,11 @@ public:
uint32_t getWritePos(); // write position relative to the beginning
uint32_t getReadPos(); // read position relative to the beginning
void resetBuffer(); // restore defaults
bool havePSRAM() { return m_f_psram; };
protected:
const size_t m_buffSizePSRAM = 300000; // most webstreams limit the advance to 100...300Kbytes
const size_t m_buffSizeRAM = 1600 * 5;
size_t m_buffSizePSRAM = 300000; // most webstreams limit the advance to 100...300Kbytes
size_t m_buffSizeRAM = 1600 * 5;
size_t m_buffSize = 0;
size_t m_freeSpace = 0;
size_t m_writeSpace = 0;
......@@ -143,6 +145,7 @@ protected:
uint8_t* m_endPtr = NULL;
bool m_f_start = true;
bool m_f_init = false;
bool m_f_psram = false; // PSRAM is available (and used...)
};
//----------------------------------------------------------------------------------------------------------------------
......@@ -153,6 +156,7 @@ class Audio : private AudioBuffer{
public:
Audio(bool internalDAC = false, i2s_dac_mode_t channelEnabled = I2S_DAC_CHANNEL_LEFT_EN); // #99
~Audio();
void setBufsize(int rambuf_sz, int psrambuf_sz);
bool connecttohost(const char* host, const char* user = "", const char* pwd = "");
bool connecttospeech(const char* speech, const char* lang);
bool connecttoFS(fs::FS &fs, const char* path);
......@@ -454,7 +458,6 @@ private:
bool m_f_playing = false; // valid mp3 stream recognized
bool m_f_webfile = false; // assume it's a radiostream, not a podcast
bool m_f_tts = false; // text to speech
bool m_f_psram = false; // set if PSRAM is availabe
bool m_f_loop = false; // Set if audio file should loop
bool m_f_forceMono = false; // if true stereo -> mono
bool m_f_internalDAC = false; // false: output vis I2S, true output via internal DAC
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment