So for the last week, I have been dealing with an issue with my ESP32. For background information, I am working on a Music Meter project. My goal is to have the ESP32 sample two audio signals, and have two set of LED strings react to the two respective audio signals. The issue that I have been having when I'm using both cores at the same time (with the Arduino IDE), one of the cores often freezes when I'm sampling audio. I know the core is freezing and it isn't getting stuck in the loop since I placed a condition to where one of the LED's will change colors if there hasn't been any activity for a extended period of time, and it never changed color.
What's also strange is as a baseline test, I wanted to see if I could just control the LED's but having a simple for loop turn each strip on and off, and that worked just fine. It's only when I start to sample audio on multiple cores and have the LED's react is where it becomes a problem. If I do each core individually, then the core never freezes, and it works the way I want it to.
/* This is in Core 1 */
for (int i = 0; i < MIDDLE_LED_COUNT; i++) {
middle_strip.setPixelColor(i, color);
middle_strip.show();
}
for (int i = (MIDDLE_LED_COUNT - 1); i >= 0 ; i--) {
middle_strip.setPixelColor(i, 0, 0, 0, 0);
middle_strip.show();
}
/* This is in Core 0 */
for (int i = 0; i < LOWER_LED_COUNT; i++) {
lower_strip.setPixelColor(i, color);
lower_strip.show();
}
for (int i = (LOWER_LED_COUNT - 1); i >= 0 ; i--) {
lower_strip.setPixelColor(i, 0, 0, 0, 0);
lower_strip.show();
}
Other things to note: WiFi has been disconnected when the ESP is in "Music Visualizer" mode via WiFi.mode( WIFI_MODE_NULL ). I've set all of my variables that are subject to change as volatile just to see if that would make it better. It slightly improved it, but it didn't fix the issue.
At this point, I am running out of rope, and I have no idea how to fix the problem. My current code is included below:
/* Core 1 */
void musicVisualizer(void) {
middle_strip.clear();
upper_strip.clear();
middle_strip.show();
upper_strip.show();
WiFi.mode( WIFI_MODE_NULL );
delay(100);
// Add code to tell Core 0 to wait until LED's are cleared.
while (vu_meter) {
tweeter_prev = tweeter;
if (analogRead(tweeter_sample) <= 490)
tweeter_adc = 0;
else {
tweeter_adc = (analogRead(tweeter_sample) - 490);
if (tweeter_adc < 0)
tweeter_adc = 0; // Filter for changing reference voltage
}
tweeter_filter.Filter(tweeter_adc);
tweeter = tweeter_filter.Current() * 4; // 6 scaler is for when Alexa is at Volume Level 4
/* LED's turning on and off in response to audio */
if ((tweeter > tweeter_prev) && (tweeter < MIDDLE_LED_COUNT)) {
for (int x = tweeter_prev; x <= tweeter; x++) {
middle_strip.setPixelColor(x, 0, 0, middle_strip.gamma32(BRIGHTNESS));
}
middle_strip.setPixelColor(0, 0, 0, middle_strip.gamma32(BRIGHTNESS)); // Removes status LED if active
tweeter_count = 0;
middle_strip.show();
}
else if (tweeter_prev > tweeter) {
for (int x = tweeter_prev; x >= tweeter; x--) {
middle_strip.setPixelColor(x, 0, 0, 0);
}
middle_strip.setPixelColor(0, 0, 0, middle_strip.gamma32(BRIGHTNESS)); // Removes status LED if active
tweeter_count = 0;
middle_strip.show();
}
else {
tweeter_count += 1;
if (tweeter_count < 1000)
middle_strip.setPixelColor(0, middle_strip.gamma32(BRIGHTNESS), 0, 0, 0);
else
middle_strip.setPixelColor(0, 0, 0, 0, middle_strip.gamma32(BRIGHTNESS));
middle_strip.show();
}
// Blynk.run();
}
/* Leaving VU Meter, returning to current lamp color set */
if (led_on) {
if (!color_white) {
for (int i = 0; i < LOWER_LED_COUNT; i++) {
lower_strip.setPixelColor(i, color);
lower_strip.show();
}
for (int i = 0; i < MIDDLE_LED_COUNT; i++) {
middle_strip.setPixelColor(i, color);
middle_strip.show();
}
for (int i = 0; i < UPPER_LED_COUNT; i++) {
upper_strip.setPixelColor(i, color);
upper_strip.show();
}
}
else {
for (int i = 0; i < LOWER_LED_COUNT; i++) {
lower_strip.setPixelColor(i, 0, 0, 0, lower_strip.gamma32(BRIGHTNESS));
lower_strip.show();
}
for (int i = 0; i < MIDDLE_LED_COUNT; i++) {
middle_strip.setPixelColor(i, 0, 0, 0, middle_strip.gamma32(BRIGHTNESS));
middle_strip.show();
}
for (int i = 0; i < UPPER_LED_COUNT; i++) {
upper_strip.setPixelColor(i, 0, 0, 0, upper_strip.gamma32(BRIGHTNESS));
upper_strip.show();
}
}
}
else {
upper_strip.clear();
middle_strip.clear();
lower_strip.clear();
upper_strip.show();
middle_strip.show();
lower_strip.show();
}
}
/* Core 0 */
void vu_meter_sub(void * parameter) {
while (true) {
esp_task_wdt_init(30, false);
if (vu_meter) {
lower_strip.clear();
lower_strip.show();
while (vu_meter) {
sub_prev = sub;
sub_adc = analogRead(sub_sample);
sub_filter.Filter(sub_adc);
sub = sub_filter.Current();
if ((sub > sub_prev) && (sub < LOWER_LED_COUNT)) {
for (int x = sub_prev; x <= sub; x++) {
lower_strip.setPixelColor(x, 0, lower_strip.gamma32(BRIGHTNESS), 0);
}
lower_strip.setPixelColor(0, 0, lower_strip.gamma32(BRIGHTNESS), 0);
sub_count = 0;
lower_strip.show();
}
else if (sub_prev > sub) {
for (int x = sub_prev; x >= sub; x--) {
lower_strip.setPixelColor(x, 0, 0, 0);
}
lower_strip.setPixelColor(0, 0, lower_strip.gamma32(BRIGHTNESS), 0);
sub_count = 0;
lower_strip.show();
}
else {
sub_count += 1;
if (sub_count < 1000)
lower_strip.setPixelColor(0, lower_strip.gamma32(BRIGHTNESS), 0, 0, 0);
else
lower_strip.setPixelColor(0, 0, 0, 0, lower_strip.gamma32(BRIGHTNESS));
lower_strip.show();
}
}
}
}
}