Цитата(GetSmart @ Jun 5 2007, 12:30)

Кстати, в обычных прерываниях нельзя разрешать прерывания. По крайней мере в ИАРе так
В SAM7 можно, его контроллер прерываний обеспечивает при разрешенных прерываниях обработку только более приоритетных прерываний, чем выполняемое в данный момент. Правда есть нюанс, связанный с армовской архитектурой. Прерывание переключает режим ядра в IRQ. Для того, чтобы не испортить адрес возврата и флаги, сначала нужно сохранить их в стеке IRQ, а затем переключиться в режим USER или SUPERVISOR, и только после этого разрешить прерывания.
Обработчик IRQ из IAR'овского cstartup для SAM7 отличается от обработчиков для других ARMов.
Код
IRQ_Handler_Entry:
sub LR, LR, #4 ;Сохранение LR_irq в стеке IRQ
stmfd SP!, {LR}
mrs R14, SPSR ;Сохранить SPSR в стеке для вложенных прерываний
stmfd SP!, {R14}
stmfd SP!, {R0} ;Сохранение R0 в стеке IRQ
ldr R14, =AT91C_BASE_AIC ;Считать вектор в R0
ldr R0 , [R14, #AIC_IVR]
msr CPSR_c, #ARM_MODE_SVC ;Разрешить прерывания и переключиться в Supervisor Mode
stmfd SP!, {R1-R3, R12, R14} ;Сохранить используемые регистры в User-стеке
mov LR, PC ;Выполнить процедуру прерывания по вектору из AIC_IVR
bx R0
ldmia SP!, { R1-R3, R12, R14} ;Восстановить используемые регистры из User-стека
msr CPSR_c, #I_BIT | ARM_MODE_IRQ;Запретить прерывания и переключиться назад в IRQ mode
ldr R14, =AT91C_BASE_AIC ;Отметить окончание прерывания в регистре AIC_EOICR
str R14, [R14, #AIC_EOICR]
ldmia SP!, {R0} ;Восстановление SPSR_irq и R0 из стека IRQ
ldmia SP!, {R14}
msr SPSR_cxsf, R14
ldmia SP!, {PC}^ ;Восстановление скорректированного LR_irq из IRQ-стека прямо в PC
Сишные обработчики при этом оформляются не только без слова __nested, но и без interrupt_handler, то есть как обычные процедуры.