Optimization: stop to constantly search for the bus

Adding a caching mechanism to the Bus Manager - up to 30% faster especially when many led pins are used.
This commit is contained in:
Frank
2024-04-20 21:57:04 +02:00
parent 59752adc3b
commit 657259acc2
2 changed files with 41 additions and 5 deletions

View File

@@ -175,7 +175,7 @@ void IRAM_ATTR BusDigital::setPixelColor(uint16_t pix, uint32_t c) {
PolyBus::setPixelColor(_busPtr, _iType, pix, c, co); PolyBus::setPixelColor(_busPtr, _iType, pix, c, co);
} }
uint32_t BusDigital::getPixelColor(uint16_t pix) { uint32_t IRAM_ATTR_YN BusDigital::getPixelColor(uint16_t pix) {
if (reversed) pix = _len - pix -1; if (reversed) pix = _len - pix -1;
else pix += _skip; else pix += _skip;
uint8_t co = _colorOrderMap.getPixelColorOrder(pix+_start, _colorOrder); uint8_t co = _colorOrderMap.getPixelColorOrder(pix+_start, _colorOrder);
@@ -724,6 +724,10 @@ int BusManager::add(BusConfig &bc) {
} else { } else {
busses[numBusses] = new BusPwm(bc); busses[numBusses] = new BusPwm(bc);
} }
// WLEDMM clear cached Bus info
lastBus = nullptr;
laststart = 0;
lastend = 0;
return numBusses++; return numBusses++;
} }
@@ -734,6 +738,10 @@ void BusManager::removeAll() {
while (!canAllShow()) yield(); while (!canAllShow()) yield();
for (uint8_t i = 0; i < numBusses; i++) delete busses[i]; for (uint8_t i = 0; i < numBusses; i++) delete busses[i];
numBusses = 0; numBusses = 0;
// WLEDMM clear cached Bus info
lastBus = nullptr;
laststart = 0;
lastend = 0;
} }
void BusManager::show() { void BusManager::show() {
@@ -749,11 +757,24 @@ void BusManager::setStatusPixel(uint32_t c) {
} }
void IRAM_ATTR BusManager::setPixelColor(uint16_t pix, uint32_t c, int16_t cct) { void IRAM_ATTR BusManager::setPixelColor(uint16_t pix, uint32_t c, int16_t cct) {
if ((pix >= laststart) && (pix < lastend ) && (lastBus != nullptr)) {
// WLEDMM same bus as last time - no need to search again
lastBus->setPixelColor(pix - laststart, c);
return;
}
for (uint_fast8_t i = 0; i < numBusses; i++) { // WLEDMM use fast native types for (uint_fast8_t i = 0; i < numBusses; i++) { // WLEDMM use fast native types
Bus* b = busses[i]; Bus* b = busses[i];
uint_fast16_t bstart = b->getStart(); uint_fast16_t bstart = b->getStart();
if (pix < bstart || pix >= bstart + b->getLength()) continue; if (pix < bstart || pix >= bstart + b->getLength()) continue;
busses[i]->setPixelColor(pix - bstart, c); else {
// WLEDMM remember last Bus we took
lastBus = b;
laststart = bstart;
lastend = bstart + b->getLength();
b->setPixelColor(pix - bstart, c);
break; // WLEDMM found the right Bus -> so we can stop searching
}
} }
} }
@@ -772,12 +793,23 @@ void BusManager::setSegmentCCT(int16_t cct, bool allowWBCorrection) {
Bus::setCCT(cct); Bus::setCCT(cct);
} }
uint32_t BusManager::getPixelColor(uint_fast16_t pix) { // WLEDMM use fast native types uint32_t IRAM_ATTR BusManager::getPixelColor(uint_fast16_t pix) { // WLEDMM use fast native types, IRAM_ATTR
if ((pix >= laststart) && (pix < lastend ) && (lastBus != nullptr)) {
// WLEDMM same bus as last time - no need to search again
return lastBus->getPixelColor(pix - laststart);
}
for (uint_fast8_t i = 0; i < numBusses; i++) { for (uint_fast8_t i = 0; i < numBusses; i++) {
Bus* b = busses[i]; Bus* b = busses[i];
uint_fast16_t bstart = b->getStart(); uint_fast16_t bstart = b->getStart();
if (pix < bstart || pix >= bstart + b->getLength()) continue; if (pix < bstart || pix >= bstart + b->getLength()) continue;
return b->getPixelColor(pix - bstart); else {
// WLEDMM remember last Bus we took
lastBus = b;
laststart = bstart;
lastend = bstart + b->getLength();
return b->getPixelColor(pix - bstart);
}
} }
return 0; return 0;
} }

View File

@@ -427,8 +427,12 @@ class BusManager {
private: private:
uint8_t numBusses = 0; uint8_t numBusses = 0;
Bus* busses[WLED_MAX_BUSSES+WLED_MIN_VIRTUAL_BUSSES]; Bus* busses[WLED_MAX_BUSSES+WLED_MIN_VIRTUAL_BUSSES] = {nullptr}; // WLEDMM init array
ColorOrderMap colorOrderMap; ColorOrderMap colorOrderMap;
// WLEDMM cache last used Bus -> 20% to 30% speedup when using many LED pins
Bus *lastBus = nullptr;
unsigned laststart = 0;
unsigned lastend = 0;
inline uint8_t getNumVirtualBusses() { inline uint8_t getNumVirtualBusses() {
int j = 0; int j = 0;