does anyone know, how one would simulate an interrupt from software on an ATmega328p(same as Arduino Uno).
My externally triggered INT0 interrupt currently works via a pushbutton.
I’d like to trigger the interrupt via software.
• Bit 0 – INT0: External Interrupt Request 0 Enable
When the INT0 bit is set (one) and the I-bit in the Status Register
(SREG) is set (one), the external pin interrupt is enabled.
The Interrupt Sense Control0 bits 1/0 (ISC01 and ISC00) in the
External Interrupt Control Register A (EICRA) define whether the
external interrupt is activated on rising and/or falling edge of the INT0
pin or level sensed. Activity on the pin will cause an interrupt request
even if INT0 is configured as an output. The corresponding interrupt of
External Interrupt Request 0 is executed from the INT0 Interrupt
Activity on the pin will cause an interrupt request even if INT0 is configured as an output.
This part and some forum post from 2007 suggest that a simulation of a software interrupt is actually possible, so I was wondering of someone knows, how one would trigger the INT0 interrupt on an ATmega328p-pu.
The pin is PD2.
Here is some abstract code that I’m trying to run.
InterruptVectorTable is supposed to take care of the function pointers and enable/disable interrupts(and global interrupts) as well as trigger them via software in order to test it.
// toggle the LED
PORTB ^= 1 << PB5; // PB5 = 5
// make port output & HIGH
// our power source
DDRB |= 1 << DDB4;
PORTB |= 1 << PB4;
// make Port B5 output & LOW
// Connected to an LED - Depending on the state of this,
// the LED is either on or off.
DDRB |= 1 << DDB5;
PORTB &= ~(1 << PB5);
// Make Port D2 Input External Interrupt
DDRD &= ~(1 << DDD2);
PORTD |= (1 << PD2);
// external interrupt 0
// on any logical change
// Manual - Page 80
EICRA |= (1 << ISC01);
EICRA &= ~(1 << ISC00);
auto& VectorTable = InterruptVectorTable::getInstance();
It seems that some interrupt are easily triggered by changing the pin states or changing multiple registers + states. but all in all it seems not to be a feasible attempt to simulate all of the possible interrupts for the small benefit it might create.
It seems to be way easier to simply call the ISR functions instead of triggering the interrupts.
The configuration overhead to configure all the interrupts will seemingly bloat the firmware to a not wanted size.
This seems to be a bit old, but certainly, I’ve seen something like this technique on the avr-debugger library and some of its applications.
The main difference is that the trigger by level configuration was used instead of the rising/falling ones. Then, the pin associated with the interrupt was configured as output and finally put to a low level. That way the interrupt was always triggered after one executed instruction of the main program and makes possible to implement the stepping function of the debugger without external hardware. Also, setting the pin to a high state would stop the triggering of the interruption.
This could also be mixed with the input mode, always remembering that by setting the related PORT’s bit to one, the internal pull-up resistor is connected.
Certainly is an interesting feature and can help to test and catch bugs without using any external hardware.