#include <Arduino.h>
#include <WiFi.h>
#include <Wire.h>
#include <MPU6050.h>
#include <WebServer.h>
#include <SPI.h>
#include <TinyGPS++.h>
#include "MAX30100_PulseOximeter.h"
#include <HardwareSerial.h>
#include "driver/i2s.h"
#include "AudioFileSourceICYStream.h"
#include "AudioFileSourceBuffer.h"
#include "AudioGeneratorMP3.h"
#include "AudioOutputI2SNoDAC.h"
// Replace with your network credentials
const char* ssid = "";
const char* password = "";
// Create a web server on port 80
WebServer server(80);
MPU6050 mpu;
PulseOximeter pox;
// GPS
#define rxGPS 26
#define txGPS 25
HardwareSerial GPS(1);
TinyGPSPlus gps;
// I2S pins for MAX98357A
#define I2S_BCLK 32 // Bit clock line
#define I2S_LRCLK 33 // Word select (LR clock)
#define I2S_DOUT 19 // Data output (changed to GPIO 19)
const char *URL="http://kvbstreams.dyndns.org:8000/wkvi-am";
AudioGeneratorMP3 *mp3 = nullptr;
AudioFileSourceICYStream *file = nullptr;
AudioFileSourceBuffer *buff = nullptr;
AudioOutputI2SNoDAC *out = nullptr;
// Function declarations
void initMPU();
void initGPS();
void initWiFi();
void handleRoot();
void handleMPUData();
void handleGPSData();
void handlePulseOximeterData();
void playAudio();
void setupAudio();
void cleanupAudioResources();
// Setup function
void setup() {
Serial.begin(115200);
initWiFi();
initMPU();
initGPS();
server.on("/", handleRoot);
server.on("/mpu6050", handleMPUData);
server.on("/gps", handleGPSData);
server.on("/pulseoximeter", handlePulseOximeterData);
server.begin();
// Initialize PulseOximeter
if (!pox.begin()) {
Serial.println("Failed to initialize PulseOximeter");
while(1);
}
setupAudio();
}
// Loop function
void loop() {
server.handleClient();
pox.update(); // Updates the PulseOximeter
playAudio();
}
// Audio metadata callback
void MDCallback(void *cbData, const char *type, bool isUnicode, const char *string) {
const char *ptr = reinterpret_cast<const char *>(cbData);
char s1[32], s2[64];
strncpy_P(s1, type, sizeof(s1));
strncpy_P(s2, string, sizeof(s2));
Serial.printf("METADATA(%s) '%s' = '%s'\n", ptr, s1, s2);
}
// Audio status callback
void StatusCallback(void *cbData, int code, const char *string) {
const char *ptr = reinterpret_cast<const char *>(cbData);
char s1[64];
strncpy_P(s1, string, sizeof(s1));
Serial.printf("STATUS(%s) '%d' = '%s'\n", ptr, code, s1);
}
// Setup audio resources
void setupAudio() {
i2s_pin_config_t pin_config = {
.bck_io_num = I2S_BCLK,
.ws_io_num = I2S_LRCLK,
.data_out_num = I2S_DOUT,
.data_in_num = I2S_PIN_NO_CHANGE
};
i2s_set_pin(I2S_NUM_0, &pin_config);
audioLogger = &Serial;
file = new AudioFileSourceICYStream(URL);
if (!file) {
Serial.println("Failed to allocate memory for AudioFileSourceICYStream.");
return;
}
file->RegisterMetadataCB(MDCallback, (void*)"ICY");
buff = new AudioFileSourceBuffer(file, 2048);
if (!buff) {
Serial.println("Failed to allocate memory for AudioFileSourceBuffer.");
cleanupAudioResources();
return;
}
buff->RegisterStatusCB(StatusCallback, (void*)"buffer");
out = new AudioOutputI2SNoDAC();
if (!out) {
Serial.println("Failed to allocate memory for AudioOutputI2SNoDAC.");
cleanupAudioResources();
return;
}
mp3 = new AudioGeneratorMP3();
if (!mp3) {
Serial.println("Failed to allocate memory for AudioGeneratorMP3.");
cleanupAudioResources();
return;
}
mp3->RegisterStatusCB(StatusCallback, (void*)"mp3");
if (!mp3->begin(buff, out)) {
Serial.println("Failed to start MP3 playback.");
cleanupAudioResources();
}
}
// Play audio
void playAudio() {
static int lastms = 0;
if (mp3 && mp3->isRunning()) {
if (millis() - lastms > 1000) {
lastms = millis();
Serial.printf("Running for %d ms...\n", lastms);
}
if (!mp3->loop()) {
mp3->stop();
cleanupAudioResources();
}
} else {
Serial.println("MP3 done");
delay(1000);
}
}
// Cleanup audio resources
void cleanupAudioResources() {
if (mp3) {
delete mp3;
mp3 = nullptr;
}
if (out) {
delete out;
out = nullptr;
}
if (buff) {
delete buff;
buff = nullptr;
}
if (file) {
delete file;
file = nullptr;
}
}
// Function definitions for other sensors and WiFi
void initMPU() {
Wire.begin(21, 22);
Serial.println("Initializing MPU6050...");
mpu.initialize();
if (!mpu.testConnection()) {
Serial.println("Failed to connect to MPU6050. Please check the connections.");
while (1);
}
Serial.println("MPU6050 connected!");
}
void initGPS() {
GPS.begin(9600, SERIAL_8N1, txGPS, rxGPS);
Serial.println("GPS module initialized.");
}
void initWiFi() {
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, password);
Serial.print("Connecting to WiFi...");
while (WiFi.status() != WL_CONNECTED) {
delay(1000);
Serial.print(".");
}
Serial.println("\nConnected to WiFi!");
Serial.print("ESP32 IP Address: ");
Serial.println(WiFi.localIP());
}
void handleRoot() {
server.send(200, "text/plain", "Hello from ESP32!");
}
void handleMPUData() {
int16_t ax, ay, az;
int16_t gx, gy, gz;
mpu.getMotion6(&ax, &ay, &az, &gx, &gy, &gz);
String json = "{";
json += "\"ax\":" + String(ax) + ",";
json += "\"ay\":" + String(ay) + ",";
json += "\"az\":" + String(az) + ",";
json += "\"gx\":" + String(gx) + ",";
json += "\"gy\":" + String(gy) + ",";
json += "\"gz\":" + String(gz);
json += "}";
server.send(200, "application/json", json);
}
void handleGPSData() {
while (GPS.available()) {
gps.encode(GPS.read());
}
if (gps.location.isValid()) {
String json = "{";
json += "\"latitude\":" + String(gps.location.lat(), 6) + ",";
json += "\"longitude\":" + String(gps.location.lng(), 6) + ",";
json += "\"altitude\":" + String(gps.altitude.meters(), 2);
json += "}";
server.send(200, "application/json", json);
} else {
server.send(200, "application/json", "{\"error\":\"No GPS fix\"}");
}
}
void handlePulseOximeterData() {
String json = "{";
json += "\"heart_rate\":" + String(pox.getHeartRate()) + ",";
json += "\"SpO2\":" + String(pox.getSpO2());
json += "}";
server.send(200, "application/json", json);
}
Log of the error messages:
Rebooting...
ets Jun 8 2016 00:22:57
rst:0xc (SW_CPU_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:2
load:0x3fff0030,len:1184
load:0x40078000,len:13232
load:0x40080400,len:3028
entry 0x400805e4
Connecting to WiFi....
Connected to WiFi!
ESP32 IP Address: 192.168.170.254
Initializing MPU6050...
MPU6050 connected!
GPS module initialized.
Guru Meditation Error: Core 1 panic'ed (LoadProhibited). Exception was unhandled.
Core 1 register dump:
PC : 0x400e898c PS : 0x00060d30 A0 : 0x800d2ff8 A1 : 0x3ffb21c0
A2 : 0x00000000 A3 : 0x3ffb21fc A4 : 0x00000000 A5 : 0x00000021
A6 : 0x00000000 A7 : 0xff000000 A8 : 0x800e892c A9 : 0x00000002
A10 : 0x001fe1df A11 : 0x00000000 A12 : 0xffffffff A13 : 0x00000000
A14 : 0x3ffc43bc A15 : 0xffffffff SAR : 0x00000013 EXCCAUSE: 0x0000001c
EXCVADDR: 0x0000003c LBEG : 0x4008a544 LEND : 0x4008a55a LCOUNT : 0xffffffff
Backtrace: 0x400e8989:0x3ffb21c0 0x400d2ff5:0x3ffb21f0 0x400d3383:0x3ffb2230 0x400e5b42:0x3ffb2290
ELF file SHA256: a23377eab44b148e
Rebooting...
ets Jun 8 2016 00:22:57
rst:0xc (SW_CPU_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:2
load:0x3fff0030,len:1184
load:0x40078000,len:13232
load:0x40080400,len:3028
entry 0x400805e4
Connecting to WiFi....
Connected to WiFi!
ESP32 IP Address: 192.168.170.254
Initializing MPU6050...
MPU6050 connected!
GPS module initialized.
Guru Meditation Error: Core 1 panic'ed (LoadProhibited). Exception was unhandled.
Core 1 register dump:
PC : 0x400e898c PS : 0x00060d30 A0 : 0x800d2ff8 A1 : 0x3ffb21c0
A2 : 0x00000000 A3 : 0x3ffb21fc A4 : 0x00000000 A5 : 0x00000021
A6 : 0x00000000 A7 : 0xff000000 A8 : 0x800e892c A9 : 0x00000002
A10 : 0x001fe1df A11 : 0x00000000 A12 : 0xffffffff A13 : 0x00000000
A14 : 0x3ffc43bc A15 : 0xffffffff SAR : 0x00000013 EXCCAUSE: 0x0000001c
EXCVADDR: 0x0000003c LBEG : 0x4008a544 LEND : 0x4008a55a LCOUNT : 0xffffffff
Backtrace: 0x400e8989:0x3ffb21c0 0x400d2ff5:0x3ffb21f0 0x400d3383:0x3ffb2230 0x400e5b42:0x3ffb2290
ELF file SHA256: a23377eab44b148e
Rebooting...
ets Jun 8 2016 00:22:57
rst:0xc (SW_CPU_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:2
load:0x3fff0030,len:1184
load:0x40078000,len:13232
load:0x40080400,len:3028
entry 0x400805e4
Connecting to WiFi...
I am not sure but this started happening only after installing ESP8266Audio library ,
FYI I am using Esp32 wrover kit E with platform.io
Here is my platformio.ini file
[platformio]
[env:esp-wrover-kit]
platform = espressif32
board = esp-wrover-kit
framework = arduino
board_build.flash_size = 4MB
lib_deps =
adafruit/Adafruit Unified Sensor@^1.1.14
adafruit/Adafruit BusIO@^1.16.1
esphome/AsyncTCP-esphome@^2.1.4
esphome/ESPAsyncWebServer-esphome@^3.2.2
electroniccats/MPU6050@^1.3.1
mikalhart/TinyGPSPlus@^1.1.0
https://github.com/dvarrel/AsyncTCP.git
https://github.com/me-no-dev/ESPAsyncWebServer.git
oxullo/MAX30100lib@^1.2.1
earlephilhower/ESP8266Audio@^1.9.9
And I am using MAX98357A to connect to 4 ohm single speaker
Also the board keeps rebooting indefinitely, but if I interrupt any one of the connections of either MAX30100 / MPU6050 this rebooting stops this error shows up
Here is the error log for that
Initializing MPU6050...
[ 2135][E][Wire.cpp:499] requestFrom(): i2cWriteReadNonStop returned Error 263
[ 4142][E][Wire.cpp:499] requestFrom(): i2cWriteReadNonStop returned Error 263
[ 5684][E][Wire.cpp:499] requestFrom(): i2cWriteReadNonStop returned Error 263
[ 5819][E][Wire.cpp:499] requestFrom(): i2cWriteReadNonStop returned Error 263
[ 5932][E][Wire.cpp:499] requestFrom(): i2cWriteReadNonStop returned Error 263
Failed to connect to MPU6050. Please check the connections.
Please ask for any clarrifications if needed
Thanks in advance