minor refactoring of critical sections
- define dummy macros for 8266, to avoid #ifdef ESP32 - small hint for readers who were not able to play arcade games in the 1980's ;-)
This commit is contained in:
@@ -11,7 +11,7 @@
|
|||||||
#include <esp_timer.h> // WLEDMM to get esp_timer_get_time()
|
#include <esp_timer.h> // WLEDMM to get esp_timer_get_time()
|
||||||
#include "freertos/FreeRTOS.h"
|
#include "freertos/FreeRTOS.h"
|
||||||
#include "freertos/portmacro.h"
|
#include "freertos/portmacro.h"
|
||||||
static portMUX_TYPE s_wled_strip_mux = portMUX_INITIALIZER_UNLOCKED; // to protect deleting Segment::_globalLeds
|
WLED_create_spinlock(ledsrgb_mux); // to protect deleting Segment::_globalLeds and Segment::ledsrgb
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -117,18 +117,19 @@ void Segment::allocLeds() {
|
|||||||
if ((size > 0) && (!ledsrgb || size > ledsrgbSize)) { //softhack dont allocate zero bytes
|
if ((size > 0) && (!ledsrgb || size > ledsrgbSize)) { //softhack dont allocate zero bytes
|
||||||
DEBUG_PRINTF("allocLeds (%d,%d to %d,%d), %u from %u\n", start, startY, stop, stopY, size, ledsrgb?ledsrgbSize:0);
|
DEBUG_PRINTF("allocLeds (%d,%d to %d,%d), %u from %u\n", start, startY, stop, stopY, size, ledsrgb?ledsrgbSize:0);
|
||||||
|
|
||||||
|
// DONG - Valkyrie needs food, badly [Gauntlet, 1985]
|
||||||
// WLEDMM this looks a bit over-compilicated, but it makes the re-allocation step an atomic and threadsafe operation
|
// WLEDMM this looks a bit over-compilicated, but it makes the re-allocation step an atomic and threadsafe operation
|
||||||
CRGB* oldLedsRgb = ledsrgb;
|
CRGB* oldLedsRgb = ledsrgb;
|
||||||
|
portENTER_CRITICAL(&ledsrgb_mux);
|
||||||
ledsrgb = nullptr;
|
ledsrgb = nullptr;
|
||||||
|
portEXIT_CRITICAL(&ledsrgb_mux);
|
||||||
|
|
||||||
if (oldLedsRgb) free(oldLedsRgb); // we need a bigger buffer, so free the old one first
|
if (oldLedsRgb) free(oldLedsRgb); // we need a bigger buffer, so free the old one first
|
||||||
CRGB* newLedsRgb = (CRGB*)calloc(1, size); // WLEDMM This is an OS call, so we should not wrap it in portEnterCRITICAL
|
CRGB* newLedsRgb = (CRGB*)calloc(1, size); // WLEDMM This is an OS call, so we should not wrap it in portEnterCRITICAL
|
||||||
#if defined(ARDUINO_ARCH_ESP32)
|
|
||||||
portENTER_CRITICAL(&s_wled_strip_mux);
|
portENTER_CRITICAL(&ledsrgb_mux);
|
||||||
#endif
|
ledsrgb = newLedsRgb;
|
||||||
ledsrgb = newLedsRgb;
|
portEXIT_CRITICAL(&ledsrgb_mux);
|
||||||
#if defined(ARDUINO_ARCH_ESP32)
|
|
||||||
portEXIT_CRITICAL(&s_wled_strip_mux);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
ledsrgbSize = ledsrgb?size:0;
|
ledsrgbSize = ledsrgb?size:0;
|
||||||
if (ledsrgb == nullptr) {
|
if (ledsrgb == nullptr) {
|
||||||
@@ -1885,18 +1886,14 @@ void WS2812FX::finalizeInit(void)
|
|||||||
|
|
||||||
//initialize leds array. TBD: realloc if nr of leds change
|
//initialize leds array. TBD: realloc if nr of leds change
|
||||||
if (Segment::_globalLeds) {
|
if (Segment::_globalLeds) {
|
||||||
// DONG - Valkyrie is about to die
|
// DONG - Valkyrie is about to die [Gauntlet, 1985]
|
||||||
// this is a critical section that will be removed with PR #278 which removes _globalLeds
|
// this is a critical section that will be removed with PR #278 which removes _globalLeds
|
||||||
// problem: suspendStripService provides interlocking, but there’s a window before service() observes it,
|
// problem: suspendStripService provides interlocking, but there’s a window before service() observes it,
|
||||||
// and ESP32 is dual-core. A critical section closes that window so the pointer swap is atomic across cores.
|
// and ESP32 is dual-core. A critical section closes that window so the pointer swap is atomic across cores.
|
||||||
CRGB* oldGLeds = Segment::_globalLeds;
|
CRGB* oldGLeds = Segment::_globalLeds;
|
||||||
#if defined(ARDUINO_ARCH_ESP32)
|
portENTER_CRITICAL(&ledsrgb_mux);
|
||||||
portENTER_CRITICAL(&s_wled_strip_mux);
|
|
||||||
#endif
|
|
||||||
Segment::_globalLeds = nullptr;
|
Segment::_globalLeds = nullptr;
|
||||||
#if defined(ARDUINO_ARCH_ESP32)
|
portEXIT_CRITICAL(&ledsrgb_mux);
|
||||||
portEXIT_CRITICAL(&s_wled_strip_mux);
|
|
||||||
#endif
|
|
||||||
free(oldGLeds);
|
free(oldGLeds);
|
||||||
purgeSegments(true); // WLEDMM moved here, because it seems to improve stability.
|
purgeSegments(true); // WLEDMM moved here, because it seems to improve stability.
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -772,8 +772,9 @@ WLED_GLOBAL SemaphoreHandle_t busDrawMux _INIT(nullptr);
|
|||||||
WLED_GLOBAL SemaphoreHandle_t segmentMux _INIT(nullptr);
|
WLED_GLOBAL SemaphoreHandle_t segmentMux _INIT(nullptr);
|
||||||
#define esp32SemTake(mux,timeout) xSemaphoreTakeRecursive(mux, timeout) // convenience macro that expands to xSemaphoreTakeRecursive
|
#define esp32SemTake(mux,timeout) xSemaphoreTakeRecursive(mux, timeout) // convenience macro that expands to xSemaphoreTakeRecursive
|
||||||
#define esp32SemGive(mux) xSemaphoreGiveRecursive(mux) // convenience macro that expands to xSemaphoreGiveRecursive
|
#define esp32SemGive(mux) xSemaphoreGiveRecursive(mux) // convenience macro that expands to xSemaphoreGiveRecursive
|
||||||
|
#define WLED_create_spinlock(theSname) static portMUX_TYPE theSname = portMUX_INITIALIZER_UNLOCKED
|
||||||
#else
|
#else
|
||||||
// dummy for 8266
|
// dummy semaphores for 8266
|
||||||
#ifndef pdTRUE
|
#ifndef pdTRUE
|
||||||
#define pdTRUE 1
|
#define pdTRUE 1
|
||||||
#endif
|
#endif
|
||||||
@@ -782,6 +783,10 @@ WLED_GLOBAL SemaphoreHandle_t segmentMux _INIT(nullptr);
|
|||||||
#endif
|
#endif
|
||||||
#define esp32SemTake(mux,timeout) (pdTRUE)
|
#define esp32SemTake(mux,timeout) (pdTRUE)
|
||||||
#define esp32SemGive(mux)
|
#define esp32SemGive(mux)
|
||||||
|
// dummy critical section for 8266
|
||||||
|
#define WLED_create_spinlock(sname)
|
||||||
|
#define portENTER_CRITICAL(sname)
|
||||||
|
#define portEXIT_CRITICAL(sname)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifndef ESP8266
|
#ifndef ESP8266
|
||||||
|
|||||||
Reference in New Issue
Block a user