Логотип

Микроконтроллеры AVR. Основы программирования

материалы в категории

Значение функции RESET в AVR микроконтроллере

Когда контроллер доходит до команды вызова подпрограммы (call или rcall), или в нем происходит прерывание (хотя в векторе и стоит обычное rjmp или jmp, но по сути это тоже вызов подпрограммы), он должен сохранить состояние программного счетчика с тем, чтобы потом знать, куда вернуться. Вот как раз для этого и служит функция reset (сброс).
Это происходит в специальной области памяти, которая называется стек (stack). Потому в любой программе на AVR-ассемблере, допускающей прерывания или просто подпрограммы, первыми после метки reset должны идти следующие строки:

RESET:
ldi temp,low(RAMEND) ;загрузка указателя стека out SPL,temp
ldi temp,high(RAMEND) ;загрузка указателя стека out SPH,temp
 
Этими операторами вы указываете, где компилятору расположить программный стек — а именно, в конце SRAM (что обозначается константой RAMEND, объявленной в соответствующем inc-файле). Для моделей Tiny с аппаратным стеком (ATtiny1x, ATtiny28) эти строки следует опустить (подробнее см. главу 4). Для тех моделей, у которых стек программный, но объем SRAM не превышает 256 байт (модель 2313 во всех ее инкарнациях, ATtiny26 и др.), запись сокращается:
 
RESET:
ldi temp,RAMEND ;загрузка указателя стека out SPL,temp
 
После задания стека желательно поставить следующие строки:
 
ldi temp, 1<<ACD
out ACSR,temp ;выкл. аналог, компаратор
 
Почему желательно, а не обязательно? Потому что по умолчанию аналоговый компаратор всегда включен, и, соответственно, расходует питание. Если вы его не используете, то зачем лишнее потребление? Правда, это практически не скажется на потреблении в нормальном режиме работы — доля компаратора очень мала. Потому критичной вставка этих строк становится только в случае, если задействованы режимы энергосбережения, а в обычных режимах эти команды просто ни на что не повлияют. С другой стороны, если компаратор необходим то, конечно, эти строки нужно исключить.
 
После всего этого в процедуре reset обычно идет секция инициализации, где разрешаются прерывания, устанавливаются состояния выводов портов, инициализируются начальные значения переменных и т. п. Примеры мы еще встретим в тексте этой книги неоднократно. Эта секция, как мы говорили ранее, обязательно должна заканчиваться командой sei — общим разрешением прерываний, т. к. по умолчанию они запрещены.
 
Теперь вроде бы все готово к работе, но что будет делать контроллер в ожидании прерываний? Ведь основная функциональность большинства микропрограмм сосредоточена именно в их обработчиках, и в простейшем случае контроллер попросту ничего не должен делать, пока не придет сигнал очередного прерывания. Поэтому простейшая программа должна заканчиваться пустым циклом: 
 
. . . . . . . . . . .
sei ;разрешаем прерывания
STOP:
rjmp STOP
 
На самом деле в этом цикле можно и делать что-то полезное — например, войти в один из режимов энергосбережения, или отслеживать изменение состояния какого-то вывода, или, например, прихода байта через UART и т. п. — в дальнейшем мы увидим примеры подобных действий. Именно внутри такого цикла работают немногочисленные программы, вообще не использующие прерываний.
 
источникhttp://easymcu.ru

Почта сайта