Spec-Zone.ru › GCC 14

6.33.6 Атрибуты функций AVR

Эти атрибуты функций поддерживаются бэкендом AVR:

signal
interrupt

Функция является обработчиком прерывания (ISR). Компилятор генерирует последовательности входа и выхода из функции, подходящие для использования в обработчике прерывания, когда один из атрибутов присутствует.

Аппаратное обеспечение AVR глобально отключает прерывания при выполнении прерывания.

  • Обработчики прерываний с атрибутом signal не восстанавливают разрешение прерываний. Безопасно разрешить прерывания в обработчике signal. Это «безопасность» относится только к коду, сгенерированному компилятором, а не к структуре IRQ приложения, которая является обязанностью приложения.
  • Обработчики прерываний с атрибутом interrupt восстанавливают разрешение прерываний. Первая инструкция процедуры — это инструкция SEI для глобального разрешения прерываний.

Рекомендуемый способ использования этих атрибутов — с помощью макроса ISR, предоставляемого avr/interrupt.h из AVR-LibC:

#include <avr/interrupt.h>

ISR (INT0_vect) // Uses the "signal" attribute.
{
    // Code
}

ISR (ADC_vect, ISR_NOBLOCK) // Uses the "interrupt" attribute.
{
    // Code
}

Когда для одной и той же функции указаны как signal, так и interrupt, то signal игнорируется.

naked

Этот атрибут позволяет компилятору сконструировать необходимую декларацию функции, при этом тело функции может быть кодом ассемблера. Указанная функция не будет иметь пролога/эпилога, сгенерированных компилятором. В функции «naked» безопасно включать только базовые asm операторы (см. Basic Asm — Инструкции ассемблера без операндов). Использование расширенного asm или смешанного кода asm и C-кода может казаться работающим, но его нельзя гарантировать, и он не поддерживается.

no_gccisr

Не используйте __gcc_isr псевдоинструкцию в функции с атрибутом interrupt или signal (т.е. обработчик прерывания ISR). Используйте этот атрибут, если преамбула пролога ISR всегда должна выглядеть как

push  __zero_reg__
push  __tmp_reg__
in    __tmp_reg__, __SREG__
push  __tmp_reg__
clr   __zero_reg__

и аналогично для постэмбулы эпилога — независимо от того, используются ли упомянутые регистры в ISR или нет. Ситуации, в которых вам может потребоваться использовать этот атрибут:

  • Код, который (фактически) перезаписывает биты SREG кроме I-флага, записывая в ячейку памяти SREG.
  • Код, использующий встроенный ассемблер для перехода в другую функцию, которая ожидает (часть) кода пролога, как описано выше.

Для отключения генерации __gcc_isr для всего модуля компиляции существует опция -mno-gas-isr-prologues, см. Опции AVR.

OS_main
OS_task

В AVR функции с атрибутом OS_main или OS_task не сохраняют/восстанавливают какие-либо сохраненные при вызове регистры в своем прологе/эпилоге.

Атрибут OS_main может быть использован, когда гарантируется, что прерывания отключены в момент входа в функцию. Это экономит ресурсы, когда указатель стека должен быть изменен для создания стекового кадра для локальных переменных.

Атрибут OS_task может быть использован, когда нет гарантии, что прерывания отключены в момент входа в функцию, например, для функций задач в многопоточной операционной системе. В этом случае изменение указателя стека защищено сохранением/обнулением/восстановлением флага глобального разрешения прерываний.

Различия с атрибутом функции naked:

  • Функции naked не имеют инструкции возврата, тогда как функции OS_main и OS_task имеют инструкцию возврата RET или RETI.
  • Функции naked не создают кадр для локальных переменных или указателя кадра, в то время как функции OS_main и OS_task делают это по мере необходимости.

© Free Software Foundation
Licensed under the GNU Free Documentation License, Version 1.3.
https://gcc.gnu.org/onlinedocs/gcc-14.2.0/gcc/AVR-Function-Attributes.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API