Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
E
ESP32-audioI2S
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Analytics
Analytics
Repository
Value Stream
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Commits
Open sidebar
xpstem
ESP32-audioI2S
Commits
a0bc3723
Unverified
Commit
a0bc3723
authored
Dec 01, 2023
by
Wolle
Committed by
GitHub
Dec 01, 2023
Browse files
Options
Browse Files
Download
Plain Diff
Merge pull request #619 from schreibfaul1/ArduinoV3.0
Arduino v3.0 support
parents
43115871
1d2f750d
Changes
2
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
2481 additions
and
1977 deletions
+2481
-1977
src/Audio.cpp
src/Audio.cpp
+2424
-1957
src/Audio.h
src/Audio.h
+57
-20
No files found.
src/Audio.cpp
View file @
a0bc3723
This diff is collapsed.
Click to expand it.
src/Audio.h
View file @
a0bc3723
...
@@ -3,8 +3,8 @@
...
@@ -3,8 +3,8 @@
*
*
* Created on: Oct 28,2018
* Created on: Oct 28,2018
*
*
* Version 3.0.7
c
* Version 3.0.7
s
* Updated on:
Nov 29
.2023
* Updated on:
Dec 01
.2023
* Author: Wolle (schreibfaul1)
* Author: Wolle (schreibfaul1)
*/
*/
...
@@ -17,14 +17,22 @@
...
@@ -17,14 +17,22 @@
#include <SPI.h>
#include <SPI.h>
#include <WiFi.h>
#include <WiFi.h>
#include <WiFiClientSecure.h>
#include <WiFiClientSecure.h>
#include <vector>
#include <driver/i2s.h>
#include <SD.h>
#include <SD.h>
#include <SD_MMC.h>
#include <SD_MMC.h>
#include <SPIFFS.h>
#include <SPIFFS.h>
#include <FS.h>
#include <FS.h>
#include <FFat.h>
#include <FFat.h>
#include <atomic>
#if ESP_IDF_VERSION_MAJOR == 5
#include <driver/i2s_std.h>
#else
#include <driver/i2s.h>
#endif
#ifndef I2S_GPIO_UNUSED
#define I2S_GPIO_UNUSED -1 // = I2S_PIN_NO_CHANGE in IDF < 5
#endif
using
namespace
std
;
using
namespace
std
;
extern
__attribute__
((
weak
))
void
audio_info
(
const
char
*
);
extern
__attribute__
((
weak
))
void
audio_info
(
const
char
*
);
...
@@ -81,6 +89,7 @@ public:
...
@@ -81,6 +89,7 @@ public:
size_t
init
();
// set default values
size_t
init
();
// set default values
bool
isInitialized
()
{
return
m_f_init
;
};
bool
isInitialized
()
{
return
m_f_init
;
};
void
setBufsize
(
int
ram
,
int
psram
);
void
setBufsize
(
int
ram
,
int
psram
);
int32_t
getBufsize
();
void
changeMaxBlockSize
(
uint16_t
mbs
);
// is default 1600 for mp3 and aac, set 16384 for FLAC
void
changeMaxBlockSize
(
uint16_t
mbs
);
// is default 1600 for mp3 and aac, set 16384 for FLAC
uint16_t
getMaxBlockSize
();
// returns maxBlockSize
uint16_t
getMaxBlockSize
();
// returns maxBlockSize
size_t
freeSpace
();
// number of free bytes to overwrite
size_t
freeSpace
();
// number of free bytes to overwrite
...
@@ -134,7 +143,7 @@ public:
...
@@ -134,7 +143,7 @@ public:
bool
setFilePos
(
uint32_t
pos
);
bool
setFilePos
(
uint32_t
pos
);
bool
audioFileSeek
(
const
float
speed
);
bool
audioFileSeek
(
const
float
speed
);
bool
setTimeOffset
(
int
sec
);
bool
setTimeOffset
(
int
sec
);
bool
setPinout
(
uint8_t
BCLK
,
uint8_t
LRC
,
uint8_t
DOUT
,
int8_t
DIN
=
I2S_PIN_NO_CHANGE
,
int8_t
MCK
=
I2S_PIN_NO_CHANGE
);
bool
setPinout
(
uint8_t
BCLK
,
uint8_t
LRC
,
uint8_t
DOUT
,
int8_t
MCK
=
I2S_GPIO_UNUSED
);
bool
pauseResume
();
bool
pauseResume
();
bool
isRunning
()
{
return
m_f_running
;}
bool
isRunning
()
{
return
m_f_running
;}
void
loop
();
void
loop
();
...
@@ -159,9 +168,9 @@ public:
...
@@ -159,9 +168,9 @@ public:
uint32_t
getTotalPlayingTime
();
uint32_t
getTotalPlayingTime
();
uint16_t
getVUlevel
();
uint16_t
getVUlevel
();
esp_err_t
i2s_mclk_pin_select
(
const
uint8_t
pin
);
uint32_t
inBufferFilled
();
// returns the number of stored bytes in the inputbuffer
uint32_t
inBufferFilled
();
// returns the number of stored bytes in the inputbuffer
uint32_t
inBufferFree
();
// returns the number of free bytes in the inputbuffer
uint32_t
inBufferFree
();
// returns the number of free bytes in the inputbuffer
uint32_t
inBufferSize
();
// returns the size of the inputbuffer in bytes
void
setTone
(
int8_t
gainLowPass
,
int8_t
gainBandPass
,
int8_t
gainHighPass
);
void
setTone
(
int8_t
gainLowPass
,
int8_t
gainBandPass
,
int8_t
gainHighPass
);
void
setI2SCommFMT_LSB
(
bool
commFMT
);
void
setI2SCommFMT_LSB
(
bool
commFMT
);
int
getCodec
()
{
return
m_codec
;}
int
getCodec
()
{
return
m_codec
;}
...
@@ -192,6 +201,8 @@ private:
...
@@ -192,6 +201,8 @@ private:
const
char
*
parsePlaylist_PLS
();
const
char
*
parsePlaylist_PLS
();
const
char
*
parsePlaylist_ASX
();
const
char
*
parsePlaylist_ASX
();
const
char
*
parsePlaylist_M3U8
();
const
char
*
parsePlaylist_M3U8
();
const
char
*
m3u8redirection
();
uint64_t
m3u8_findMediaSeqInURL
();
bool
STfromEXTINF
(
char
*
str
);
bool
STfromEXTINF
(
char
*
str
);
void
showCodecParams
();
void
showCodecParams
();
int
findNextSync
(
uint8_t
*
data
,
size_t
len
);
int
findNextSync
(
uint8_t
*
data
,
size_t
len
);
...
@@ -280,14 +291,14 @@ private:
...
@@ -280,14 +291,14 @@ private:
return
true
;
return
true
;
}
}
bool
endsWith
(
const
char
*
base
,
const
char
*
str
)
{
bool
endsWith
(
const
char
*
base
,
const
char
*
searchString
)
{
//fb
int32_t
slen
=
strlen
(
searchString
);
i
nt
slen
=
strlen
(
str
)
-
1
;
i
f
(
slen
==
0
)
return
false
;
const
char
*
p
=
base
+
strlen
(
base
)
-
1
;
const
char
*
p
=
base
+
strlen
(
base
);
while
(
p
>
base
&&
isspace
(
*
p
))
p
--
;
// rtrim
//
while(p > base && isspace(*p)) p--; // rtrim
p
-=
slen
;
p
-=
slen
;
if
(
p
<
base
)
return
false
;
if
(
p
<
base
)
return
false
;
return
(
strncmp
(
p
,
s
tr
,
slen
)
==
0
);
return
(
strncmp
(
p
,
s
earchString
,
slen
)
==
0
);
}
}
int
indexOf
(
const
char
*
base
,
const
char
*
str
,
int
startIndex
=
0
)
{
int
indexOf
(
const
char
*
base
,
const
char
*
str
,
int
startIndex
=
0
)
{
...
@@ -399,7 +410,17 @@ private:
...
@@ -399,7 +410,17 @@ private:
hash
+=
(
str
[
i
]
-
31
)
*
i
*
32
;
hash
+=
(
str
[
i
]
-
31
)
*
i
*
32
;
}
}
return
hash
;
return
hash
;
}
}
char
*
x_strdup
(
const
char
*
str
){
if
(
m_f_psramFound
){
char
*
s
=
(
char
*
)
ps_malloc
(
strlen
(
str
)
+
1
);
strcpy
(
s
,
str
);
return
s
;
}
else
{
return
strdup
(
str
);
}
}
private:
private:
const
char
*
codecname
[
10
]
=
{
"unknown"
,
"WAV"
,
"MP3"
,
"AAC"
,
"M4A"
,
"FLAC"
,
"AACP"
,
"OPUS"
,
"OGG"
,
"VORBIS"
};
const
char
*
codecname
[
10
]
=
{
"unknown"
,
"WAV"
,
"MP3"
,
"AAC"
,
"M4A"
,
"FLAC"
,
"AACP"
,
"OPUS"
,
"OGG"
,
"VORBIS"
};
...
@@ -436,10 +457,21 @@ private:
...
@@ -436,10 +457,21 @@ private:
WiFiClientSecure
clientsecure
;
// @suppress("Abstract class cannot be instantiated")
WiFiClientSecure
clientsecure
;
// @suppress("Abstract class cannot be instantiated")
WiFiClient
*
_client
=
nullptr
;
WiFiClient
*
_client
=
nullptr
;
SemaphoreHandle_t
mutex_audio
;
SemaphoreHandle_t
mutex_audio
;
i2s_config_t
m_i2s_config
=
{};
// stores values for I2S driver
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wmissing-field-initializers"
#if ESP_IDF_VERSION_MAJOR == 5
i2s_chan_handle_t
m_i2s_tx_handle
=
{};
i2s_chan_config_t
m_i2s_chan_cfg
=
{};
// stores I2S channel values
i2s_std_config_t
m_i2s_std_cfg
=
{};
// stores I2S driver values
#else
i2s_config_t
m_i2s_config
=
{};
i2s_pin_config_t
m_pin_config
=
{};
i2s_pin_config_t
m_pin_config
=
{};
std
::
vector
<
char
*>
m_playlistContent
;
// m3u8 playlist buffer
#endif
std
::
vector
<
char
*>
m_playlistURL
;
// m3u8 streamURLs buffer
#pragma GCC diagnostic pop
std
::
vector
<
char
*>
m_playlistContent
;
// m3u8 playlist buffer
std
::
vector
<
char
*>
m_playlistURL
;
// m3u8 streamURLs buffer
std
::
vector
<
uint32_t
>
m_hashQueue
;
std
::
vector
<
uint32_t
>
m_hashQueue
;
const
size_t
m_frameSizeWav
=
1024
;
const
size_t
m_frameSizeWav
=
1024
;
...
@@ -455,7 +487,9 @@ private:
...
@@ -455,7 +487,9 @@ private:
char
*
m_ibuff
=
nullptr
;
// used in audio_info()
char
*
m_ibuff
=
nullptr
;
// used in audio_info()
char
*
m_chbuf
=
NULL
;
char
*
m_chbuf
=
NULL
;
uint16_t
m_chbufSize
=
0
;
// will set in constructor (depending on PSRAM)
uint16_t
m_chbufSize
=
0
;
// will set in constructor (depending on PSRAM)
uint16_t
m_ibuffSize
=
0
;
// will set in constructor (depending on PSRAM)
char
*
m_lastHost
=
NULL
;
// Store the last URL to a webstream
char
*
m_lastHost
=
NULL
;
// Store the last URL to a webstream
char
*
m_lastM3U8host
=
NULL
;
char
*
m_playlistBuff
=
NULL
;
// stores playlistdata
char
*
m_playlistBuff
=
NULL
;
// stores playlistdata
const
uint16_t
m_plsBuffEntryLen
=
256
;
// length of each entry in playlistBuff
const
uint16_t
m_plsBuffEntryLen
=
256
;
// length of each entry in playlistBuff
filter_t
m_filter
[
3
];
// digital filters
filter_t
m_filter
[
3
];
// digital filters
...
@@ -485,10 +519,10 @@ private:
...
@@ -485,10 +519,10 @@ private:
uint8_t
m_vuLeft
=
0
;
// average value of samples, left channel
uint8_t
m_vuLeft
=
0
;
// average value of samples, left channel
uint8_t
m_vuRight
=
0
;
// average value of samples, right channel
uint8_t
m_vuRight
=
0
;
// average value of samples, right channel
int16_t
*
m_outBuff
=
NULL
;
// Interleaved L/R
int16_t
*
m_outBuff
=
NULL
;
// Interleaved L/R
int16_t
m_validSamples
=
0
;
std
::
atomic
<
int16_t
>
m_validSamples
=
{
0
};
// #144
int16_t
m_curSample
=
0
;
std
::
atomic
<
int16_t
>
m_curSample
{
0
};
std
::
atomic
<
uint16_t
>
m_datamode
{
0
};
// Statemaschine
int16_t
m_decodeError
=
0
;
// Stores the return value of the decoder
int16_t
m_decodeError
=
0
;
// Stores the return value of the decoder
uint16_t
m_datamode
=
0
;
// Statemaschine
uint16_t
m_streamTitleHash
=
0
;
// remember streamtitle, ignore multiple occurence in metadata
uint16_t
m_streamTitleHash
=
0
;
// remember streamtitle, ignore multiple occurence in metadata
uint16_t
m_timeout_ms
=
250
;
uint16_t
m_timeout_ms
=
250
;
uint16_t
m_timeout_ms_ssl
=
2700
;
uint16_t
m_timeout_ms_ssl
=
2700
;
...
@@ -514,6 +548,7 @@ private:
...
@@ -514,6 +548,7 @@ private:
bool
m_f_ssl
=
false
;
bool
m_f_ssl
=
false
;
bool
m_f_running
=
false
;
bool
m_f_running
=
false
;
bool
m_f_firstCall
=
false
;
// InitSequence for processWebstream and processLokalFile
bool
m_f_firstCall
=
false
;
// InitSequence for processWebstream and processLokalFile
bool
m_f_firstM3U8call
=
false
;
// InitSequence for m3u8 parsing
bool
m_f_chunked
=
false
;
// Station provides chunked transfer
bool
m_f_chunked
=
false
;
// Station provides chunked transfer
bool
m_f_firstmetabyte
=
false
;
// True if first metabyte (counter)
bool
m_f_firstmetabyte
=
false
;
// True if first metabyte (counter)
bool
m_f_playing
=
false
;
// valid mp3 stream recognized
bool
m_f_playing
=
false
;
// valid mp3 stream recognized
...
@@ -527,6 +562,8 @@ private:
...
@@ -527,6 +562,8 @@ private:
bool
m_f_continue
=
false
;
// next m3u8 chunk is available
bool
m_f_continue
=
false
;
// next m3u8 chunk is available
bool
m_f_ts
=
true
;
// transport stream
bool
m_f_ts
=
true
;
// transport stream
bool
m_f_m4aID3dataAreRead
=
false
;
// has the m4a-ID3data already been read?
bool
m_f_m4aID3dataAreRead
=
false
;
// has the m4a-ID3data already been read?
bool
m_f_psramFound
=
false
;
// set in constructor, result of psramInit()
bool
m_f_timeout
=
false
;
//
uint8_t
m_f_channelEnabled
=
3
;
// internal DAC, both channels
uint8_t
m_f_channelEnabled
=
3
;
// internal DAC, both channels
uint32_t
m_audioFileDuration
=
0
;
uint32_t
m_audioFileDuration
=
0
;
float
m_audioCurrentTime
=
0
;
float
m_audioCurrentTime
=
0
;
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment