
- •Встраиваемые микроконтроллеры avr-8
- •Санкт-Петербург 2013 Содержание
- •Часть 1. Архитектура мк (л2, л3)
- •Понятия мк для встраиваемых приложений и семейства мк. Семейство avr-8
- •Структура и архитектура мк
- •Тактирование, процессор и арифметико-логическая группа команд
- •Структура и адресация памяти программ. Ветвления, циклы, подпрограммы, и группа команд передачи управления
- •Структура и адресация памяти данных. Группа команд передачи данных
- •Порты ввода/вывода. Типовая схема включения мк. Структура управляющей программы, поллинг.
- •Часть 2. Процесс проектирования устройств на мк (л4, л5)
- •2.1. Этапы процесса проектирования устройств на мк
- •2.2.Техническое задание и разработка алгоритма (блок-схемы)
- •2.3. Языки программирования и синтаксическая проверка проекта
- •2.4. Средства загрузки кодов программ и данных (программаторы)
- •2.5. Средства отладки для выявления логических и схемотехнических ошибок
- •2.6. Подключение индикаторов и клавиатуры
- •Часть 3. Ввод/вывод в мпу
- •3.1. Понятие и характеристики интерфейса
- •3.2. Внутрисистемные интерфейсы в мпу
- •3.3 Параллельный порт avr
- •3.4. Внешняя магистраль памяти данных avr мк
- •3.5. Принцип и средства ввода/вывода по прерываниям.
- •3.6. Принцип прямого доступа к памяти
- •Часть 4. Прерывания (л8)
- •4.1. Механизм прерываний в avr и его программирование
- •4.2. Входы прерываний inTx и pcinTx.
- •Часть 5. Таймеры/счетчики
- •5.1. Задачи формирования и измерения временных интервалов
- •5.2. Принципы программного формирования/измерения временного интервала
- •5.3. Таймер/счетчик с прерыванием по переполнению
- •5.4. Таймер/счетчик с дополнительными узлами захвата и сравнения
- •Часть 6. Задачи и устройства аналогового ввода/вывода (л12, л13)
- •6.1. Задачи аналогового ввода и вывода
- •6.2. Встроенный аналоговый компаратор
- •6.3. Встроенный многоканальный ацп
- •6.4. Встроенный цап
- •6.5. Терморегулятор
- •Часть 7. Задачи и устройства последовательного интерфейса (л14, л15)
- •7.1. Принципы и преимущества последовательного интерфейса
- •7.2. Функции встроенного контроллера последовательного интерфейса
- •7.3. Протокол и контроллер трехпроводного синхронного пи (spi)
- •7.4. Устройство контроллера i2c и его применение
- •7.5 Цап с последовательным интерфейсом
- •7.6. Устройство контроллера u(s)art и его применение
- •7.7. Сетевые протоколы и их стандартизация
- •7.8. Открытый протокол Modbus
- •История
- •Введение
- •Категории кодов функций
- •Модель данных
- •Стандартные функции протокола Modbus
- •Запись одного значения
- •Запись нескольких значений
- •Контроль ошибок в протоколе Modbus rtu
- •Rtu фрейм
- •Логические ошибки
- •Стандартные коды ошибок
4.2. Входы прерываний inTx и pcinTx.
Внешние прерывания
Внешние прерывания в МК серии AVR ранних моделей состоят только из альтернативных функций INTx. Они поддерживают аппаратное выявление фронта, среза, пр. и формирование индивидуального запроса прерывания, такими функциями оснащались от 2-х до 8-ми отдельных выводов портов. В более поздних моделях к этим функциям добавились функции аппаратного выявления изменения состояния вывода PCINTn [Pin Change INTerrupt], которыми оснащаются все выводы портов.
Оба механизма ориентированы на автоматизацию обслуживания входов, то есть контроля состояния внешних сигналов. Но это не мешает использовать их для контроля изменения состояния выводов в режиме выхода, то есть формировать программно управляемые прерывания.
В МК AT90S8515 имеется два входа прерывания INT0/PD2, INT1/PD3. Событием может быть (табл. 4.1): низкий уровень, фронт, срез, либо любое изменение (фронт/срез). Тип события задается программно битами ISCX1, ISCX0 в регистре MCUCR (табл. 4.2).
Таблица 4.1. Внешние прерывания МК at90s8515
Источник |
Вектор |
Флаг |
Маска |
Выбор формы сигнала |
INT0 / PD2 |
INT0_vect = 0x02 |
GIFR:INTF0 |
GIMSK:INT0 |
MCUCR:ISC01, ISC00 |
INT1 / PD3 |
INT1_vect = 0x04 |
GIFR:INTF1 |
GIMSK:INT1 |
MCUCR:ISC11, ISC10 |
Таблица 4.2. Настройка регистра MCUCR на событие на входах INT0, INT1
ISCх1 |
ISCх0 |
Форма прерывающего сигнала |
0 |
0 |
Низкий уровень |
0 |
1 |
Резерв |
1 |
0 |
Срез (переход от 1 к 0) |
1 |
1 |
Фронт (переход от 0 к 1) |
Прерывание по фронту или срезу устанавливает флаг в регистре GIFR, его сброс выполняется автоматически при вызове подпрограммы прерывания (ISR), если данное прерывание запрещено флаг следует сбросить программно записью единицы в бит флага.
Прерывание по низкому уровню отличается от других отсутствием триггера запоминания, поэтому это прерывание активно все время, пока на входе присутствует низкий уровень, и «забывается», если к моменту предоставления прерывания уровень стал высоким.
Программное обеспечение прерываний состоит из подготовки (инициализации) и собственно ISR. На этапе инициализации программируются регистры маски [GIMSK], настройки на событие [MCUCR], настройки соответствующего вывода на вход [DDRD]. Последним действием этапа инициализации обычно выполняется команда общего разрешения прерывания [sei].
Обязательными элементами ISR являются целевые действия и команда выхода из прерывания [reti].
Ниже приведен пример использования входов прерывания INT0 и INT1 с реализацией на ассемблере и на GNU-C, схема примера и результаты измерений в симуляторе AVR-Studio, находятся в папке Primer / p2 Interrupt & TimerCounter / Int0cnt.
//INT0/PD2 – счет импульсов, если частота выше порога 200 Гц, то включить красный светодиод на выходе PD4, иначе переключать светодиод с частотой 10 Гц
//INT1/PD3 – по срезу кнопки на этом входе переключать зеленый светодиод на выходе PD0
Пример на Ассемблере |
Пример на GNU-С |
.include <8515def.inc> .macro LOAD ;@0, @1 ldi r16,@1 out @0,r16 .endm .def cnt = r17 .def tmp_int0 = r0 .equ N = 10 rjmp START .org INT0addr rjmp ISR_INT0 rjmp ISR_INT1 .org INT_VECTORS_SIZE START: LOAD SPL,LOW(RAMEND) LOAD SPH,HIGH(RAMEND) LOAD DDRD,(1<<PD0)|(1<<PD4) LOAD PORTD, (1<<PD3)|(1<<PD0) LOAD GIMSK, (1<<INT0)|(1<<INT1) LOAD MCUCR, (1<<ISC11)|(1<<ISC01)|(1<<ISC00) clr cnt sei LOOP: ldi r18, 100 rcall WAIT_ms cpi cnt, N brlo LL sbi PORTD,PD0 rjmp MM LL: sbic PORTD,PD0 rjmp BB sbi PORTD,PD0 rjmp MM BB: cbi PORTD,PD0 MM: clr cnt rjmp LOOP ; *********************************** ISR_INT0: in tmp_int0,SREG inc cnt out SREG,tmp_int0 reti ; =================================== ISR_INT1: sbic PORTD,PD4 rjmp AA sbi PORTD,PD4 reti AA: cbi PORTD,PD4 reti ; =================================== |
#include <avr/io.h> #include <avr/interrupt.h> #include <avr/delay.h> #define N 10 char cnt; ISR(INT0_vect) { cnt++; }
ISR(INT1_vect) { if(PORTD & (1<<PD4)) PORTD &= ~(1<<PD4); else PORTD |= (1<<PD4); }
int main() { DDRD = (1<<PD0)|(1<<PD4); PORTD = (1<<PD3)|(1<<PD0); GIMSK = (1<<INT0)|(1<<INT1); MCUCR = (1<<ISC11)|(1<<ISC01)|(1<<ISC00); GIFR = (1<<INTF1)|(1<<INTF0); sei(); while(1) { _delay_ms(100); if(cnt > N) { PORTD |= (1<<PD0); } else { if(PORTD & (1<<PD0)) PORTD &= ~(1<<PD0); else PORTD |= (1<<PD0); } cnt=0; } } //***********************************
Fclk = 1 МГц |
Задержка выполнения действия в ISR_INT0: 10 мкс, 10 м.ц. в ISR_INT1: 7 мкс, 7 м.ц. Время выполнения в ISR_INT0: 16 мкс, 16 м.ц. в ISR_INT1: 15 мкс, 15 м.ц. Период основного цикла 100318 мкс |
Задержка выполнения действия в ISR_INT0: 23 мкс, 23 м.ц. в ISR_INT1: 33 мкс, 33 м.ц. Время выполнения в ISR_INT0: 48 мкс, 48 м.ц. в ISR_INT1: 85 мкс, 85 м.ц. Период основного цикла 103540 мкс |
Задержка выполнения измерялась от изменения состояния PIND.2 / PIND.3 до первой команды / оператора, выполняющей заданное действие (или выбор действия), то есть время реакции на событие. Время выполнения показывает задержку основного цикла на обслуживание данного прерывания.
Преимущество варианта на ассемблере перед свободно распространяемым транслятором GNU-C (avr-gcc) объясняется оптимальным расходом на сохранение/восстановление контекста.
Любопытные могут увидеть машинный код в файле листинга <*.lss>.и сравнить его с ассемблерным вариантом. Подпрограмма ISR_INT0 использует в качестве ячейки «глобальной» памяти РОН, для сохранения регистра состояния используется еще один РОН. Любой транслятор поместит «глобальную» ячейку в SRAM, для сохранения контекста использует стек в SRAM. Подпрограмма ISR_INT1 использует команды, которые не используют РОН и не меняют содержимое регистра состояния.
В МК более поздних разработок (ATmega48/88/168/328 и др.) входы прерывания INTх имеют расширенный набор выявляемых событий, все выводы параллельных портов оснащены функцией выявления изменения состояния [PCINT0…23].
Отличия в работе входов прерывания INTх сводятся к использованию ранее зарезервированной комбинации битов выбора события (ISCx1 = 0, ISCx0 = 1) для выявления любого изменения вывода, а также к смене символьных имен регистров [MCUCR, GIFR, GIMSK] на соответствующие им [EICRA, EIFR, EIMSK].
Механизм аппаратного выявления изменения состояния входа PCINTn выявляет изменение сигнала на выводе МК, но не выявляет тип (фронт или срез). В МК указанных выше серий такой функцией оснащены 24 вывода трех параллельных портов. Прерывания представлены тремя векторами PCINT0,1,2, один вектор на группу из 8 входов, общим на группу является и флаг PCIFR. Маскирование прерываний выполняется как общее на группу (например, PCICR.PCIE0 – для PCINT0…7), так и индивидуальное (PCMSK0.PCINT0).
Рассмотрим подробнее состав и назначение регистров механизма PCINTn.
Регистр PCICR [Pin Change Interrupt Control Register] содержит три бита: PCIE0 [.. Interrupt Enable] – разрешение прерывания при изменении состояния на 8 выводах PCINT0…7, PCIE1 – на выводах PCINT8…15, PCIE1 – на выводах PCINT16…23.
Регистр PCIFR [Pin Change Interrupt Flag Register] содержит три бита PCIF0 [Pin Change Interrupt Flag] – флаг прерывания по выводам PCINT0…7, PCIF1 – на выводах PCINT8…15, PCIF2 – на выводах PCINT16…23.
Регистры PCMSK0, 1, 2 [Pin Change Mask Register] содержит биты PCINT0..7 [Pin Change Enable Mask], PCINT8..15, PCINT16..23 соответственно для индивидуального разрешения прерываний по каждому выводу.
Данный механизм ориентирован для сравнительно медленных сигналов. Для уточнения причины прерывания: фронт или срез и на каком из 8 выводов группы произошло изменение состояния, необходимо иметь память предыдущего состояния текущего порта и затратить время на анализ. Эти действия не нужны, если разрешен только один из 8 выводов данной группы и не имеет значение тип события (фронт или срез), тогда временные затраты не отличаются от механизма INTx.