From 3cd9bd9ed9db2410f29abe5d3729bf52cff98a5e Mon Sep 17 00:00:00 2001 From: "Dirk O. Kaar" Date: Fri, 21 Jun 2019 13:57:05 +0200 Subject: [PATCH] Refactor FunctionalInterrupt, undo removal of attachInterrupt() for functional arguments. --- .../examples/Functional/Functional.ino | 18 ++-- .../src/FunctionalInterrupt.cpp | 98 ++++++++++--------- .../src/FunctionalInterrupt.h | 31 ++---- 3 files changed, 67 insertions(+), 80 deletions(-) diff --git a/libraries/FunctionalInterrupt/examples/Functional/Functional.ino b/libraries/FunctionalInterrupt/examples/Functional/Functional.ino index ec8bf382b5..22785a01d1 100644 --- a/libraries/FunctionalInterrupt/examples/Functional/Functional.ino +++ b/libraries/FunctionalInterrupt/examples/Functional/Functional.ino @@ -1,6 +1,10 @@ #include #include +#ifndef IRAM_ATTR +#define IRAM_ATTR ICACHE_RAM_ATTR +#endif + #if defined(ESP32) #define BUTTON1 16 #define BUTTON2 17 @@ -35,22 +39,12 @@ class Button { detachFunctionalInterrupt(PIN); } -#if defined(ESP8266) - void ICACHE_RAM_ATTR isr() -#elif defined(ESP32) - void IRAM_ATTR isr() -#endif - { + void IRAM_ATTR isr() { numberKeyPresses += 1; pressed = true; } -#if defined(ESP8266) - static void ICACHE_RAM_ATTR isr_static(Button* const self) -#elif defined(ESP32) - static void IRAM_ATTR isr_static(Button* const self) -#endif - { + static void IRAM_ATTR isr_static(Button* const self) { self->isr(); } diff --git a/libraries/FunctionalInterrupt/src/FunctionalInterrupt.cpp b/libraries/FunctionalInterrupt/src/FunctionalInterrupt.cpp index c69f94dd7b..fd3fddfb0d 100644 --- a/libraries/FunctionalInterrupt/src/FunctionalInterrupt.cpp +++ b/libraries/FunctionalInterrupt/src/FunctionalInterrupt.cpp @@ -1,65 +1,73 @@ -#include +#include "FunctionalInterrupt.h" #include -#include "Arduino.h" +#include -// Duplicate typedefs from core_esp8266_wiring_digital_c -typedef void (*voidFuncPtr)(void); -typedef void (*voidFuncPtrArg)(void*); +namespace { -// Helper functions for Functional interrupt routines -extern "C" void __attachInterruptFunctionalArg(uint8_t pin, voidFuncPtr userFunc, void*fp, int mode, bool functional); + struct ArgStructure + { + std::function function = nullptr; + }; + void ICACHE_RAM_ATTR interruptFunctional(void* arg) + { + ArgStructure* localArg = static_cast(arg); + localArg->function(); + } -void ICACHE_RAM_ATTR interruptFunctional(void* arg) -{ - ArgStructure* localArg = (ArgStructure*)arg; - if (localArg->functionInfo->reqScheduledFunction) - { - schedule_function(std::bind(localArg->functionInfo->reqScheduledFunction,InterruptInfo(*(localArg->interruptInfo)))); - } - if (localArg->functionInfo->reqFunction) - { - localArg->functionInfo->reqFunction(); - } -} + void cleanupFunctional(void* arg) + { + ArgStructure* localArg = static_cast(arg); + delete localArg; + } -extern "C" -{ - void cleanupFunctional(void* arg) - { - ArgStructure* localArg = (ArgStructure*)arg; - delete (FunctionInfo*)localArg->functionInfo; - delete (InterruptInfo*)localArg->interruptInfo; - delete localArg; - } } void attachInterrupt(uint8_t pin, std::function intRoutine, int mode) { - // use the local interrupt routine which takes the ArgStructure as argument - - InterruptInfo* ii = nullptr; + void* localArg = detachInterruptArg(pin); + if (localArg) + { + cleanupFunctional(localArg); + } - FunctionInfo* fi = new FunctionInfo; - fi->reqFunction = intRoutine; + if (intRoutine) + { + ArgStructure* arg = new ArgStructure; + arg->function = std::move(intRoutine); - ArgStructure* as = new ArgStructure; - as->interruptInfo = ii; - as->functionInfo = fi; - - __attachInterruptFunctionalArg(pin, (voidFuncPtr)interruptFunctional, as, mode, true); + attachInterruptArg(pin, interruptFunctional, arg, mode); + } } void attachScheduledInterrupt(uint8_t pin, std::function scheduledIntRoutine, int mode) { - InterruptInfo* ii = new InterruptInfo; + void* localArg = detachInterruptArg(pin); + if (localArg) + { + cleanupFunctional(localArg); + } - FunctionInfo* fi = new FunctionInfo; - fi->reqScheduledFunction = scheduledIntRoutine; + if (scheduledIntRoutine) + { + ArgStructure* arg = new ArgStructure; + arg->function = [scheduledIntRoutine = std::move(scheduledIntRoutine), pin]() + { + InterruptInfo interruptInfo(pin); + interruptInfo.value = digitalRead(pin); + interruptInfo.micro = micros(); + schedule_function([scheduledIntRoutine, interruptInfo]() { scheduledIntRoutine(std::move(interruptInfo)); }); + }; - ArgStructure* as = new ArgStructure; - as->interruptInfo = ii; - as->functionInfo = fi; + attachInterruptArg(pin, interruptFunctional, arg, mode); + } +} - __attachInterruptFunctionalArg(pin, (voidFuncPtr)interruptFunctional, as, mode, true); +void detachFunctionalInterrupt(uint8_t pin) +{ + void* localArg = detachInterruptArg(pin); + if (localArg) + { + cleanupFunctional(localArg); + } } diff --git a/libraries/FunctionalInterrupt/src/FunctionalInterrupt.h b/libraries/FunctionalInterrupt/src/FunctionalInterrupt.h index 968793e499..b51ef93f53 100644 --- a/libraries/FunctionalInterrupt/src/FunctionalInterrupt.h +++ b/libraries/FunctionalInterrupt/src/FunctionalInterrupt.h @@ -1,35 +1,20 @@ #ifndef FUNCTIONALINTERRUPT_H #define FUNCTIONALINTERRUPT_H -#include -#include #include -extern "C" { -#include "c_types.h" -#include "ets_sys.h" -} - // Structures for communication -struct InterruptInfo { - uint8_t pin = 0; - uint8_t value = 0; - uint32_t micro = 0; -}; - -struct FunctionInfo { - std::function reqFunction = nullptr; - std::function reqScheduledFunction = nullptr; -}; - -struct ArgStructure { - InterruptInfo* interruptInfo = nullptr; - FunctionInfo* functionInfo = nullptr; +struct InterruptInfo +{ + InterruptInfo(uint8_t _pin) : pin(_pin) {} + const uint8_t pin; + uint8_t value = 0; + uint32_t micro = 0; }; void attachInterrupt(uint8_t pin, std::function intRoutine, int mode); void attachScheduledInterrupt(uint8_t pin, std::function scheduledIntRoutine, int mode); +void detachFunctionalInterrupt(uint8_t pin); - -#endif //INTERRUPTS_H +#endif //FUNCTIONALINTERRUPT_H