Merge branch 'loop_done_enable_isr' into integration

This commit is contained in:
J. Nick Koston
2025-06-18 12:15:24 +02:00
9 changed files with 325 additions and 20 deletions
+19 -4
View File
@@ -148,10 +148,12 @@ void Component::mark_failed() {
App.disable_component_loop_(this);
}
void Component::disable_loop() {
ESP_LOGD(TAG, "%s loop disabled", this->get_component_source());
this->component_state_ &= ~COMPONENT_STATE_MASK;
this->component_state_ |= COMPONENT_STATE_LOOP_DONE;
App.disable_component_loop_(this);
if ((this->component_state_ & COMPONENT_STATE_MASK) != COMPONENT_STATE_LOOP_DONE) {
ESP_LOGD(TAG, "%s loop disabled", this->get_component_source());
this->component_state_ &= ~COMPONENT_STATE_MASK;
this->component_state_ |= COMPONENT_STATE_LOOP_DONE;
App.disable_component_loop_(this);
}
}
void Component::enable_loop() {
if ((this->component_state_ & COMPONENT_STATE_MASK) == COMPONENT_STATE_LOOP_DONE) {
@@ -161,6 +163,19 @@ void Component::enable_loop() {
App.enable_component_loop_(this);
}
}
void IRAM_ATTR HOT Component::enable_loop_soon_from_isr() {
// This method is ISR-safe because:
// 1. Only performs simple assignments to volatile variables (atomic on all platforms)
// 2. No read-modify-write operations that could be interrupted
// 3. No memory allocation, object construction, or function calls
// 4. IRAM_ATTR ensures code is in IRAM, not flash (required for ISR execution)
// 5. Components are never destroyed, so no use-after-free concerns
// 6. App is guaranteed to be initialized before any ISR could fire
// 7. Multiple ISR calls are safe - just sets the same flags to true
// 8. Race condition with main loop is handled by clearing flag before processing
this->pending_enable_loop_ = true;
App.has_pending_enable_loop_requests_ = true;
}
void Component::reset_to_construction_state() {
if ((this->component_state_ & COMPONENT_STATE_MASK) == COMPONENT_STATE_FAILED) {
ESP_LOGI(TAG, "Component %s is being reset to construction state", this->get_component_source());