Иногда нужно перехватить прерывание, которое уже используется системой (например, прерывание таймера 0 используется для millis()). Мы можем создать свой обработчик, который будет вызываться до стандартного.
Техника «векторного перехвата»:
#define __SFR_OFFSET 0x00
#include <avr/io.h>
; Сохраняем оригинальный вектор прерывания
.org 0x001E ; Адрес TIMER0_COMPA_vect
JMP my_timer_handler ; Перехватываем
; Оригинальный обработчик (храним в SRAM)
orig_vector: .word 0
my_timer_handler:
; Сохраняем контекст
PUSH R16
PUSH R17
PUSH R18
; Наш код (например, инкрементируем свой счетчик)
LDS R16, my_counter
INC R16
STS my_counter, R16
; Восстанавливаем контекст
POP R18
POP R17
POP R16
; Вызываем оригинальный обработчик
LDS R16, orig_vector
IJMP