Skip to content

Commit c934776

Browse files
committed
Address issues reported
1 parent 7f2b6a3 commit c934776

File tree

14 files changed

+86
-67
lines changed

14 files changed

+86
-67
lines changed

wled00/FX.h

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -833,8 +833,8 @@ class WS2812FX {
833833
_length(DEFAULT_LED_COUNT),
834834
_transitionDur(750),
835835
_frametime(FRAMETIME_FIXED),
836+
_cumulativeFps(WLED_FPS << FPS_CALC_SHIFT),
836837
_targetFps(WLED_FPS),
837-
_cumulativeFps(WLED_FPS),
838838
_isServicing(false),
839839
_isOffRefreshRequired(false),
840840
_hasWhiteChannel(false),
@@ -845,7 +845,8 @@ class WS2812FX {
845845
_callback(nullptr),
846846
customMappingTable(nullptr),
847847
customMappingSize(0),
848-
_lastShow(0)
848+
_lastShow(0),
849+
_lastServiceShow(0)
849850
{
850851
_mode.reserve(_modeCount); // allocate memory to prevent initial fragmentation (does not increase size())
851852
_modeData.reserve(_modeCount); // allocate memory to prevent initial fragmentation (does not increase size())
@@ -1011,8 +1012,8 @@ class WS2812FX {
10111012
uint16_t _transitionDur;
10121013

10131014
uint16_t _frametime;
1015+
uint16_t _cumulativeFps;
10141016
uint8_t _targetFps;
1015-
uint8_t _cumulativeFps;
10161017

10171018
// will require only 1 byte
10181019
struct {

wled00/FX_2Dfcn.cpp

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@ void WS2812FX::setUpMatrix() {
8686
JsonArray map = pDoc->as<JsonArray>();
8787
gapSize = map.size();
8888
if (!map.isNull() && gapSize >= matrixSize) { // not an empty map
89-
gapTable = static_cast<int8_t*>(w_malloc(gapSize));
89+
gapTable = static_cast<int8_t*>(p_malloc(gapSize));
9090
if (gapTable) for (size_t i = 0; i < gapSize; i++) {
9191
gapTable[i] = constrain(map[i], -1, 1);
9292
}
@@ -113,7 +113,7 @@ void WS2812FX::setUpMatrix() {
113113
}
114114

115115
// delete gap array as we no longer need it
116-
w_free(gapTable);
116+
p_free(gapTable);
117117
resume();
118118

119119
#ifdef WLED_DEBUG
@@ -246,11 +246,11 @@ void Segment::blur2D(uint8_t blur_x, uint8_t blur_y, bool smear) const {
246246
const unsigned cols = vWidth();
247247
const unsigned rows = vHeight();
248248
const auto XY = [&](unsigned x, unsigned y){ return x + y*cols; };
249-
uint32_t lastnew;
249+
uint32_t lastnew; // not necessary to initialize lastnew and last, as both will be initialized by the first loop iteration
250250
uint32_t last;
251251
if (blur_x) {
252252
const uint8_t keepx = smear ? 255 : 255 - blur_x;
253-
const uint8_t seepx = blur_x >> (1 + smear);
253+
const uint8_t seepx = blur_x >> 1;
254254
for (unsigned row = 0; row < rows; row++) { // blur rows (x direction)
255255
uint32_t carryover = BLACK;
256256
uint32_t curnew = BLACK;
@@ -273,7 +273,7 @@ void Segment::blur2D(uint8_t blur_x, uint8_t blur_y, bool smear) const {
273273
}
274274
if (blur_y) {
275275
const uint8_t keepy = smear ? 255 : 255 - blur_y;
276-
const uint8_t seepy = blur_y >> (1 + smear);
276+
const uint8_t seepy = blur_y >> 1;
277277
for (unsigned col = 0; col < cols; col++) {
278278
uint32_t carryover = BLACK;
279279
uint32_t curnew = BLACK;
@@ -584,6 +584,7 @@ void Segment::drawCharacter(unsigned char chr, int16_t x, int16_t y, uint8_t w,
584584
chr -= 32; // align with font table entries
585585
const int font = w*h;
586586

587+
// if col2 == BLACK then use currently selected palette for gradient otherwise create gradient from color and col2
587588
CRGBPalette16 grad = col2 ? CRGBPalette16(CRGB(color), CRGB(col2)) : SEGPALETTE; // selected palette as gradient
588589

589590
for (int i = 0; i<h; i++) { // character height

wled00/FX_fcn.cpp

Lines changed: 16 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1034,10 +1034,10 @@ void Segment::blur(uint8_t blur_amount, bool smear) const {
10341034
}
10351035
#endif
10361036
uint8_t keep = smear ? 255 : 255 - blur_amount;
1037-
uint8_t seep = blur_amount >> (1 + smear);
1037+
uint8_t seep = blur_amount >> 1;
10381038
unsigned vlength = vLength();
10391039
uint32_t carryover = BLACK;
1040-
uint32_t lastnew;
1040+
uint32_t lastnew; // not necessary to initialize lastnew and last, as both will be initialized by the first loop iteration
10411041
uint32_t last;
10421042
uint32_t curnew = BLACK;
10431043
for (unsigned i = 0; i < vlength; i++) {
@@ -1198,7 +1198,12 @@ void WS2812FX::finalizeInit() {
11981198
void WS2812FX::service() {
11991199
unsigned long nowUp = millis(); // Be aware, millis() rolls over every 49 days
12001200
now = nowUp + timebase;
1201-
if (nowUp - _lastShow < MIN_FRAME_DELAY || _suspend) return;
1201+
unsigned long elapsed = nowUp - _lastServiceShow;
1202+
if (_suspend || elapsed <= MIN_FRAME_DELAY) return; // keep wifi alive - no matter if triggered or unlimited
1203+
if (!_triggered && (_targetFps != FPS_UNLIMITED)) { // unlimited mode = no frametime
1204+
if (elapsed < _frametime) return; // too early for service
1205+
}
1206+
12021207
bool doShow = false;
12031208

12041209
_isServicing = true;
@@ -1255,15 +1260,16 @@ void WS2812FX::service() {
12551260
}
12561261

12571262
#ifdef WLED_DEBUG
1258-
if (millis() - nowUp > _frametime) DEBUG_PRINTF_P(PSTR("Slow effects %u/%d.\n"), (unsigned)(millis()-nowUp), (int)_frametime);
1263+
if ((_targetFps != FPS_UNLIMITED) && (millis() - nowUp > _frametime)) DEBUG_PRINTF_P(PSTR("Slow effects %u/%d.\n"), (unsigned)(millis()-nowUp), (int)_frametime);
12591264
#endif
12601265
if (doShow && !_suspend) {
12611266
yield();
12621267
Segment::handleRandomPalette(); // slowly transition random palette; move it into for loop when each segment has individual random palette
1268+
_lastServiceShow = nowUp; // update timestamp, for precise FPS control
12631269
show();
12641270
}
12651271
#ifdef WLED_DEBUG
1266-
if (millis() - nowUp > _frametime) DEBUG_PRINTF_P(PSTR("Slow strip %u/%d.\n"), (unsigned)(millis()-nowUp), (int)_frametime);
1272+
if ((_targetFps != FPS_UNLIMITED) && (millis() - nowUp > _frametime)) DEBUG_PRINTF_P(PSTR("Slow strip %u/%d.\n"), (unsigned)(millis()-nowUp), (int)_frametime);
12671273
#endif
12681274

12691275
_triggered = false;
@@ -1612,8 +1618,8 @@ void WS2812FX::show() {
16121618
if (newBri != _brightness) BusManager::setBrightness(_brightness);
16131619

16141620
if (diff > 0) { // skip calculation if no time has passed
1615-
int fpsCurr = (1000 << FPS_CALC_SHIFT) / diff; // fixed point math (shift left for better precision)
1616-
_cumulativeFps += ((fpsCurr - (_cumulativeFps << FPS_CALC_SHIFT)) / FPS_CALC_AVG + ((1<<FPS_CALC_SHIFT)/FPS_CALC_AVG)) >> FPS_CALC_SHIFT; // simple PI controller over FPS_CALC_AVG frames
1621+
size_t fpsCurr = (1000 << FPS_CALC_SHIFT) / diff; // fixed point math
1622+
_cumulativeFps = (FPS_CALC_AVG * _cumulativeFps + fpsCurr + FPS_CALC_AVG / 2) / (FPS_CALC_AVG + 1); // "+FPS_CALC_AVG/2" for proper rounding
16171623
_lastShow = showNow;
16181624
}
16191625
}
@@ -1653,8 +1659,9 @@ void WS2812FX::waitForIt() {
16531659
};
16541660

16551661
void WS2812FX::setTargetFps(unsigned fps) {
1656-
if (fps > 0 && fps <= 120) _targetFps = fps;
1657-
_frametime = 1000 / _targetFps;
1662+
if (fps <= 250) _targetFps = fps;
1663+
if (_targetFps > 0) _frametime = 1000 / _targetFps;
1664+
else _frametime = MIN_FRAME_DELAY; // unlimited mode
16581665
}
16591666

16601667
void WS2812FX::setCCT(uint16_t k) {

wled00/bus_manager.cpp

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -37,19 +37,21 @@ uint8_t realtimeBroadcast(uint8_t type, IPAddress client, uint16_t length, const
3737
//util.cpp
3838
// PSRAM allocation wrappers
3939
#ifndef ESP8266
40-
void *w_malloc(size_t); // prefer PSRAM over DRAM
41-
void *w_calloc(size_t, size_t); // prefer PSRAM over DRAM
42-
void *w_realloc(void *, size_t); // prefer PSRAM over DRAM
43-
inline void w_free(void *ptr) { heap_caps_free(ptr); }
44-
void *d_malloc(size_t); // prefer DRAM over PSRAM
45-
void *d_calloc(size_t, size_t); // prefer DRAM over PSRAM
46-
void *d_realloc(void *, size_t); // prefer DRAM over PSRAM
47-
inline void d_free(void *ptr) { heap_caps_free(ptr); }
40+
extern "C" {
41+
void *p_malloc(size_t); // prefer PSRAM over DRAM
42+
void *p_calloc(size_t, size_t); // prefer PSRAM over DRAM
43+
void *p_realloc(void *, size_t); // prefer PSRAM over DRAM
44+
inline void p_free(void *ptr) { heap_caps_free(ptr); }
45+
void *d_malloc(size_t); // prefer DRAM over PSRAM
46+
void *d_calloc(size_t, size_t); // prefer DRAM over PSRAM
47+
void *d_realloc(void *, size_t); // prefer DRAM over PSRAM
48+
inline void d_free(void *ptr) { heap_caps_free(ptr); }
49+
}
4850
#else
49-
#define w_malloc malloc
50-
#define w_calloc calloc
51-
#define w_realloc realloc
52-
#define w_free free
51+
#define p_malloc malloc
52+
#define p_calloc calloc
53+
#define p_realloc realloc
54+
#define p_free free
5355
#define d_malloc malloc
5456
#define d_calloc calloc
5557
#define d_realloc realloc

wled00/const.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
#pragma once
12
#ifndef WLED_CONST_H
23
#define WLED_CONST_H
34

@@ -49,6 +50,9 @@
4950
#define WLED_MAX_ANALOG_CHANNELS 5
5051
#define WLED_MIN_VIRTUAL_BUSSES 3 // no longer used for bus creation but used to distinguish S2/S3 in UI
5152
#else
53+
#if !defined(LEDC_CHANNEL_MAX) || !defined(LEDC_SPEED_MODE_MAX)
54+
#include "driver/ledc.h" // needed for analog/LEDC channel counts
55+
#endif
5256
#define WLED_MAX_ANALOG_CHANNELS (LEDC_CHANNEL_MAX*LEDC_SPEED_MODE_MAX)
5357
#if defined(CONFIG_IDF_TARGET_ESP32C3) // 2 RMT, 6 LEDC, only has 1 I2S but NPB does not support it ATM
5458
#define WLED_MAX_DIGITAL_CHANNELS 2
@@ -76,6 +80,7 @@
7680
#undef WLED_MAX_BUSSES
7781
#endif
7882
#define WLED_MAX_BUSSES (WLED_MAX_DIGITAL_CHANNELS+WLED_MAX_ANALOG_CHANNELS)
83+
static_assert(WLED_MAX_BUSSES <= 32, "WLED_MAX_BUSSES exceeds hard limit");
7984

8085
// Maximum number of pins per output. 5 for RGBCCT analog LEDs.
8186
#define OUTPUT_MAX_PINS 5

wled00/fcn_declare.h

Lines changed: 16 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -173,7 +173,8 @@ inline uint32_t color_blend16(uint32_t c1, uint32_t c2, uint16_t b) { return col
173173
CRGBPalette16 generateHarmonicRandomPalette(const CRGBPalette16 &basepalette);
174174
CRGBPalette16 generateRandomPalette();
175175
void loadCustomPalettes();
176-
#define getPaletteCount() (13 + GRADIENT_PALETTE_COUNT + customPalettes.size())
176+
extern std::vector<CRGBPalette16> customPalettes;
177+
inline size_t getPaletteCount() { return 13 + GRADIENT_PALETTE_COUNT + customPalettes.size(); }
177178
inline uint32_t colorFromRgbw(byte* rgbw) { return uint32_t((byte(rgbw[3]) << 24) | (byte(rgbw[0]) << 16) | (byte(rgbw[1]) << 8) | (byte(rgbw[2]))); }
178179
void hsv2rgb(const CHSV32& hsv, uint32_t& rgb);
179180
void colorHStoRGB(uint16_t hue, byte sat, byte* rgb);
@@ -545,19 +546,21 @@ inline uint8_t hw_random8(uint32_t lowerlimit, uint32_t upperlimit) { uint32_t r
545546

546547
// PSRAM allocation wrappers
547548
#ifndef ESP8266
548-
void *w_malloc(size_t); // prefer PSRAM over DRAM
549-
void *w_calloc(size_t, size_t); // prefer PSRAM over DRAM
550-
void *w_realloc(void *, size_t); // prefer PSRAM over DRAM
551-
inline void w_free(void *ptr) { heap_caps_free(ptr); }
552-
void *d_malloc(size_t); // prefer DRAM over PSRAM
553-
void *d_calloc(size_t, size_t); // prefer DRAM over PSRAM
554-
void *d_realloc(void *, size_t); // prefer DRAM over PSRAM
555-
inline void d_free(void *ptr) { heap_caps_free(ptr); }
549+
extern "C" {
550+
void *p_malloc(size_t); // prefer PSRAM over DRAM
551+
void *p_calloc(size_t, size_t); // prefer PSRAM over DRAM
552+
void *p_realloc(void *, size_t); // prefer PSRAM over DRAM
553+
inline void p_free(void *ptr) { heap_caps_free(ptr); }
554+
void *d_malloc(size_t); // prefer DRAM over PSRAM
555+
void *d_calloc(size_t, size_t); // prefer DRAM over PSRAM
556+
void *d_realloc(void *, size_t); // prefer DRAM over PSRAM
557+
inline void d_free(void *ptr) { heap_caps_free(ptr); }
558+
}
556559
#else
557-
#define w_malloc malloc
558-
#define w_calloc calloc
559-
#define w_realloc realloc
560-
#define w_free free
560+
#define p_malloc malloc
561+
#define p_calloc calloc
562+
#define p_realloc realloc
563+
#define p_free free
561564
#define d_malloc malloc
562565
#define d_calloc calloc
563566
#define d_realloc realloc

wled00/file.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -392,7 +392,7 @@ static const uint8_t *getPresetCache(size_t &size) {
392392

393393
if ((presetsModifiedTime != presetsCachedTime) || (presetsCachedValidate != cacheInvalidate)) {
394394
if (presetsCached) {
395-
w_free(presetsCached);
395+
p_free(presetsCached);
396396
presetsCached = nullptr;
397397
}
398398
}
@@ -403,7 +403,7 @@ static const uint8_t *getPresetCache(size_t &size) {
403403
presetsCachedTime = presetsModifiedTime;
404404
presetsCachedValidate = cacheInvalidate;
405405
presetsCachedSize = 0;
406-
presetsCached = (uint8_t*)w_malloc(file.size() + 1);
406+
presetsCached = (uint8_t*)p_malloc(file.size() + 1);
407407
if (presetsCached) {
408408
presetsCachedSize = file.size();
409409
file.read(presetsCached, presetsCachedSize);

wled00/mqtt.cpp

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -68,8 +68,8 @@ static void onMqttMessage(char* topic, char* payload, AsyncMqttClientMessageProp
6868
}
6969

7070
if (index == 0) { // start (1st partial packet or the only packet)
71-
w_free(payloadStr); // release buffer if it exists
72-
payloadStr = static_cast<char*>(w_malloc(total+1)); // allocate new buffer
71+
p_free(payloadStr); // release buffer if it exists
72+
payloadStr = static_cast<char*>(p_malloc(total+1)); // allocate new buffer
7373
}
7474
if (payloadStr == nullptr) return; // buffer not allocated
7575

@@ -94,7 +94,7 @@ static void onMqttMessage(char* topic, char* payload, AsyncMqttClientMessageProp
9494
} else {
9595
// Non-Wled Topic used here. Probably a usermod subscribed to this topic.
9696
UsermodManager::onMqttMessage(topic, payloadStr);
97-
w_free(payloadStr);
97+
p_free(payloadStr);
9898
payloadStr = nullptr;
9999
return;
100100
}
@@ -124,7 +124,7 @@ static void onMqttMessage(char* topic, char* payload, AsyncMqttClientMessageProp
124124
// topmost topic (just wled/MAC)
125125
parseMQTTBriPayload(payloadStr);
126126
}
127-
w_free(payloadStr);
127+
p_free(payloadStr);
128128
payloadStr = nullptr;
129129
}
130130

@@ -196,7 +196,7 @@ bool initMqtt()
196196
if (!mqttEnabled || mqttServer[0] == 0 || !WLED_CONNECTED) return false;
197197

198198
if (mqtt == nullptr) {
199-
void *ptr = w_malloc(sizeof(AsyncMqttClient));
199+
void *ptr = p_malloc(sizeof(AsyncMqttClient));
200200
mqtt = new (ptr) AsyncMqttClient(); // use placement new (into PSRAM), client will never be deleted
201201
if (!mqtt) return false;
202202
mqtt->onMessage(onMqttMessage);

wled00/pin_manager.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
1-
#include "pin_manager.h"
21
#include "wled.h"
2+
#include "pin_manager.h"
33

44
#ifdef ARDUINO_ARCH_ESP32
55
#ifdef bitRead

wled00/pin_manager.h

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,6 @@
33
/*
44
* Registers pins so there is no attempt for two interfaces to use the same pin
55
*/
6-
#include <Arduino.h>
7-
#ifdef ARDUINO_ARCH_ESP32
8-
#include "driver/ledc.h" // needed for analog/LEDC channel counts
9-
#endif
10-
#include "const.h" // for USERMOD_* values
116

127
#ifdef ESP8266
138
#define WLED_NUM_PINS (GPIO_PIN_COUNT+1) // somehow they forgot GPIO 16 (0-16==17)

0 commit comments

Comments
 (0)