Attach default Interupt Vector

Status
Not open for further replies.

luni

Well-known member
I'm attaching an interrupt handler with attachInterruptVector(...). Does anyone know how to re-attach the original default handler? There is a "unused_interrupt_vector" in startup.c but this seems to be static, at least the linker complains about an undefined reference...


Code:
extern void unused_interrupt_vector(void);

myClass::~myClass()
{
   NVIC_DISABLE_IRQ(myIRQ);
   attachInterruptVector(myIRQ, unused_interrupt_vector); //<================

  // further cleanup...

}
 
The code for attach is : static inline void attachInterruptVector(IRQ_NUMBER_t irq, void (*function)(void)) { _VectorsRam[irq + 16] = function; asm volatile("": : :"memory"); }

Was there something there before?

Should work to store : OLD_function = _VectorsRam[irq + 16] and then put it back when done.
 
Does anyone know how to re-attach the original default handler?

You'd need to read the earlier value from the _VectorsRam array before writing your own. Then you could later write it back.

But whether that would actually work also depends on whether you leave the peripheral hardware configured in the same (or similar enough) state that the original driver code was using. Even for seemingly simply peripherals like UARTs, there can be very difficult bugs if you're not very careful. For example, about a year ago a long-standing extremely obscure bug was fixed in the Teensy 3.x Serial1 & Serial2 code, where it would lock up if Serial1.end() was called while the UART's FIFO had captured an incoming byte with a framing error in its stop bit, but had not yet caused an interrupt before you called Serial1.begin(baud) with a new baud rate. After your code has used a peripheral, giving it back to the original driver in a state other than a clean reset is just asking for those sorts of very subtle bugs.

But it "just because you can do a thing" resonates with you, then read the pointer from that array and store it before you write your own ISR function. Then later you can write the original value back.
 
Thanks Paul, I already implemented that after defragsters post.

Your remarks about the sensibility of that are true of course. Thinking of it, it might be better to not pretend to restore things but stick to the original idea and simply put in the pointer to the "unused_interrupt_vector()" in the destructor of my class. I meanwhile found out how to get hold of the function pointer of the default vector (forgot the extern "C"). Here a compiling example in case somebody else needs it:

Code:
#include "Arduino.h"

extern "C"
{
  void unused_interrupt_vector(void);
}


void setup()
{
   attachInterruptVector(IRQ_GPT1, unused_interrupt_vector);
}

void loop(){}
 
Status
Not open for further replies.
Back
Top