26
26
#include " ets_sys.h"
27
27
#include " user_interface.h"
28
28
#include " core_esp8266_waveform.h"
29
+ #include " interrupts.h"
29
30
30
31
extern " C" {
31
32
@@ -109,8 +110,9 @@ typedef void (*voidFuncPtrArg)(void*);
109
110
110
111
typedef struct {
111
112
uint8_t mode;
112
- void (*fn)( void ) ;
113
+ voidFuncPtr fn ;
113
114
void * arg;
115
+ bool functional;
114
116
} interrupt_handler_t ;
115
117
116
118
// duplicate from functionalInterrupt.h keep in sync
@@ -125,11 +127,11 @@ typedef struct {
125
127
void * functionInfo;
126
128
} ArgStructure;
127
129
128
- static interrupt_handler_t interrupt_handlers[16 ];
130
+ static interrupt_handler_t interrupt_handlers[16 ] = { { 0 , 0 , 0 , 0 }, } ;
129
131
static uint32_t interrupt_reg = 0 ;
130
132
131
- void ICACHE_RAM_ATTR interrupt_handler (void *arg) {
132
- ( void ) arg;
133
+ void ICACHE_RAM_ATTR interrupt_handler (void *)
134
+ {
133
135
uint32_t status = GPIE;
134
136
GPIEC = status;// clear them interrupts
135
137
uint32_t levels = GPI;
@@ -144,34 +146,49 @@ void ICACHE_RAM_ATTR interrupt_handler(void *arg) {
144
146
if (handler->fn &&
145
147
(handler->mode == CHANGE ||
146
148
(handler->mode & 1 ) == !!(levels & (1 << i)))) {
147
- // to make ISR compatible to Arduino AVR model where interrupts are disabled
148
- // we disable them before we call the client ISR
149
- uint32_t savedPS = xt_rsil (15 ); // stop other interrupts
150
- ArgStructure* localArg = (ArgStructure*)handler->arg ;
151
- if (localArg && localArg->interruptInfo )
152
- {
153
- localArg->interruptInfo ->pin = i;
154
- localArg->interruptInfo ->value = __digitalRead (i);
155
- localArg->interruptInfo ->micro = micros ();
156
- }
157
- if (handler->arg )
158
- {
159
- ((voidFuncPtrArg)handler->fn )(handler->arg );
160
- }
161
- else
162
- {
163
- handler->fn ();
149
+ // to make ISR compatible to Arduino AVR model where interrupts are disabled
150
+ // we disable them before we call the client ISR
151
+ esp8266::InterruptLock irqLock; // stop other interrupts
152
+ if (handler->functional )
153
+ {
154
+ ArgStructure* localArg = (ArgStructure*)handler->arg ;
155
+ if (localArg && localArg->interruptInfo )
156
+ {
157
+ localArg->interruptInfo ->pin = i;
158
+ localArg->interruptInfo ->value = __digitalRead (i);
159
+ localArg->interruptInfo ->micro = micros ();
160
+ }
161
+ }
162
+ if (handler->arg )
163
+ {
164
+ ((voidFuncPtrArg)handler->fn )(handler->arg );
165
+ }
166
+ else
167
+ {
168
+ handler->fn ();
169
+ }
164
170
}
165
- xt_wsr_ps (savedPS);
166
- }
167
171
}
168
172
ETS_GPIO_INTR_ENABLE ();
169
173
}
170
174
171
175
extern void cleanupFunctional (void * arg);
172
176
173
- extern void ICACHE_RAM_ATTR __attachInterruptArg (uint8_t pin, voidFuncPtr userFunc, void *arg, int mode) {
177
+ static void set_interrupt_handlers (uint8_t pin, voidFuncPtr userFunc, void * arg, uint8_t mode, bool functional)
178
+ {
179
+ interrupt_handler_t * handler = &interrupt_handlers[pin];
180
+ handler->mode = mode;
181
+ handler->fn = userFunc;
182
+ if (handler->functional && handler->arg ) // Clean when new attach without detach
183
+ {
184
+ cleanupFunctional (handler->arg );
185
+ }
186
+ handler->arg = arg;
187
+ handler->functional = functional;
188
+ }
174
189
190
+ extern void __attachInterruptFunctionalArg (uint8_t pin, voidFuncPtrArg userFunc, void * arg, int mode, bool functional)
191
+ {
175
192
// #5780
176
193
// https://github.com./esp8266/esp8266-wiki/wiki/Memory-Map
177
194
if ((uint32_t )userFunc >= 0x40200000 )
@@ -183,14 +200,7 @@ extern void ICACHE_RAM_ATTR __attachInterruptArg(uint8_t pin, voidFuncPtr userFu
183
200
184
201
if (pin < 16 ) {
185
202
ETS_GPIO_INTR_DISABLE ();
186
- interrupt_handler_t *handler = &interrupt_handlers[pin];
187
- handler->mode = mode;
188
- handler->fn = userFunc;
189
- if (handler->arg ) // Clean when new attach without detach
190
- {
191
- cleanupFunctional (handler->arg );
192
- }
193
- handler->arg = arg;
203
+ set_interrupt_handlers (pin, (voidFuncPtr)userFunc, arg, mode, functional);
194
204
interrupt_reg |= (1 << pin);
195
205
GPC (pin) &= ~(0xF << GPCI);// INT mode disabled
196
206
GPIEC = (1 << pin); // Clear Interrupt for this pin
@@ -200,31 +210,32 @@ extern void ICACHE_RAM_ATTR __attachInterruptArg(uint8_t pin, voidFuncPtr userFu
200
210
}
201
211
}
202
212
203
- extern void ICACHE_RAM_ATTR __attachInterrupt (uint8_t pin, voidFuncPtr userFunc, int mode )
213
+ extern void __attachInterruptArg (uint8_t pin, voidFuncPtrArg userFunc, void * arg, int mode)
204
214
{
205
- __attachInterruptArg (pin, userFunc, 0 , mode);
215
+ __attachInterruptFunctionalArg (pin, userFunc, arg , mode, false );
206
216
}
207
217
208
218
extern void ICACHE_RAM_ATTR __detachInterrupt (uint8_t pin) {
209
- if (pin < 16 ) {
210
- ETS_GPIO_INTR_DISABLE ();
211
- GPC (pin) &= ~(0xF << GPCI);// INT mode disabled
212
- GPIEC = (1 << pin); // Clear Interrupt for this pin
213
- interrupt_reg &= ~(1 << pin);
214
- interrupt_handler_t *handler = &interrupt_handlers[pin];
215
- handler->mode = 0 ;
216
- handler->fn = 0 ;
217
- if (handler->arg )
218
- {
219
- cleanupFunctional (handler->arg );
220
- }
221
- handler->arg = 0 ;
222
- if (interrupt_reg)
223
- ETS_GPIO_INTR_ENABLE ();
224
- }
219
+ if (pin < 16 )
220
+ {
221
+ ETS_GPIO_INTR_DISABLE ();
222
+ GPC (pin) &= ~(0xF << GPCI);// INT mode disabled
223
+ GPIEC = (1 << pin); // Clear Interrupt for this pin
224
+ interrupt_reg &= ~(1 << pin);
225
+ set_interrupt_handlers (pin, nullptr , nullptr , 0 , false );
226
+ if (interrupt_reg)
227
+ {
228
+ ETS_GPIO_INTR_ENABLE ();
229
+ }
230
+ }
231
+ }
232
+
233
+ extern void __attachInterrupt (uint8_t pin, voidFuncPtr userFunc, int mode)
234
+ {
235
+ __attachInterruptFunctionalArg (pin, (voidFuncPtrArg)userFunc, 0 , mode, false );
225
236
}
226
237
227
- void initPins () {
238
+ extern void initPins () {
228
239
// Disable UART interrupts
229
240
system_set_os_print (0 );
230
241
U0IE = 0 ;
@@ -243,6 +254,7 @@ extern void pinMode(uint8_t pin, uint8_t mode) __attribute__ ((weak, alias("__pi
243
254
extern void digitalWrite (uint8_t pin, uint8_t val) __attribute__ ((weak, alias(" __digitalWrite" )));
244
255
extern int digitalRead (uint8_t pin) __attribute__ ((weak, alias(" __digitalRead" )));
245
256
extern void attachInterrupt (uint8_t pin, voidFuncPtr handler, int mode) __attribute__ ((weak, alias(" __attachInterrupt" )));
257
+ extern void attachInterruptArg (uint8_t pin, voidFuncPtrArg handler, void * arg, int mode) __attribute__((weak, alias(" __attachInterruptArg" )));
246
258
extern void detachInterrupt (uint8_t pin) __attribute__ ((weak, alias(" __detachInterrupt" )));
247
259
248
260
};
0 commit comments