Электроэнергетический факультет
Кафедра промышленной электроники и
информационно-измерительной техники
КУРСОВОЙ ПРОЕКТ
по дисциплине «Электроника и микропроцессорная техника»
Секундомер
Пояснительная записка
Данный курсовой проект содержит разработку и описание на языке ассемблер функциональных узлов секундомера.
Программа микроконтроллера была написана и отлаживалась с помощью прикладной программы MPLAB IDE.
Проект содержит 10 рисунков, 3 таблицы и 4 приложения.
1 Функциональная спецификация и системные требования
Электронный секундомер является устройством, предназначенным для отсчета времени. Будем считать, что в соответствии с требованиями пользователя секундомер будет отображать текущее время в формате (минуты: секунды: доли секунды) на четырехразрядном цифровом индикаторе.
При включении секундомер будет работать в режиме отсчета времени. Последовательно нажимая на кнопку «Старт–Стоп» можно будет остановить отсчет времени и затем снова перейти в режим отсчета времени. При нажатии на кнопку «Сброс» в любом режиме, пользователь может обнулить значение на индикаторе.
Секундомер должен содержать устройство измерения времени, которое в свою очередь всегда состоит из генератора эталонных интервалов времени и счётчика этих интервалов. Схема устройства измерения времени приведена на рисунке 1.
Рисунок 1 - Функциональная схема устройства измерения времени
В качестве прототипа разрабатываемого устройства предполагается использовать учебно-отладочный стенд, в котором используется кварцевая стабилизация частоты тактового генератора МК. Частота установленного кварцевого резонатора составляет 3.6864 МГц. Длительность машинного цикла МК составляет 4 такта, поэтому тактирование встроенных периферийных модулей происходит с частотой 3.6864 / 4 = 0.9216 МГц. С такой же входной частотой должен будет работать и программно реализованный делитель частоты, так как время выполнения одной команды составляет 4 такта. Тогда для формирования импульсов 0,1 секунды потребуется делитель частоты на 91260. Уточнённая структурная схема разрабатываемого устройства приведена на рисунке 2.
Рисунок 2 -Уточнённая структурная схема устройства измерения времени
Следующий блок, который обязательно должен входить в состав секундомера - это устройство индикации. Выберем в качестве устройства отображения времени светодиодные семисегментные индикаторы (четыре разряда), установленные в учебно-отладочном стенде.
В принципе для управления семисегментными индикаторами можно использовать сам МК. В этом случае для преобразования кода, в котором работает счётчик интервалов времени, в семисегментный код потребуется дешифратор. Функцию дешифратора можно реализовать программно. Чтобы сократить количество линий портов вывода для управления многоразрядными семисегментными индикаторами обычно используют динамическую индикацию. То есть, коды символов всех разрядов выводят поочередно через одни и те же линии порта вывода.
В учебно-отладочном стенде для управления семисегментными индикаторами применен специализированный контроллер MC14489BP. Контроллер MC14489BP принимает от МК в последовательном двоичном коде символы, выполняет преобразование в семисегментный код и управляет работой индикаторов. Таким образом, структура учебно-отладочного стенда предопределяет способ управления семисегментными индикаторами: блок индикации будет состоять из контроллера MC14489BP и собственно индикаторов.
Для управления показаниями времени применим блок управления, который будет состоять из кнопок и автомата для установки внутреннего состояния счётчика интервалов времени. Структурная схема секундомера с учётом блока индикации и блока управления временем приведена на рисунке 3.
Рисунок 3 - Функциональная схема секундомера.
2 Системно-алгоритмическое проектирование
В соответствии с принятыми решениями МК должен выполнять большинство основных функций МПУ, включая:
1) генерацию тактовых импульсов частотой 0.9216 МГц;
2) формирование долей секундных интервалов времени путем деления частоты на 92160;
3) подсчет долей секунд, секунд и минут;
4) вывод информации о текущем времени в последовательном коде в блок индикации;
5) управление текущим временем.
Теперь необходимо решить, какие функции будут выполняться аппаратно периферийными модулями МК, а какие функции будут выполняться программой. Первая функция, несомненно, реализуется аппаратно встроенным в МК тактовым генератором. Вторую функцию можно попытаться возложить как на встроенные таймеры МК, так и на программу. Для функций 3 и 5, скорее всего, подойдет программная реализация. Что касается функции 4, то в МК имеется встроенный синхронный последовательный порт MSSP, но в учебно-отладочном стенде он задействован для работы с внешним EEPROM в режиме I2C. Поэтому вывод информации в блок индикации будет реализован программно. Таким образом, проблема выбора существует только для функции делителя частоты.
Попытаемся использовать для деления частоты встроенные таймеры, так как это позволит существенно упростить программу. В составе МК семейства PIC16F87x имеются три таймера:
- 8-разрядный таймер/счетчик TMR0 с 8-разрядным программируемым предделителем;
- 16-разрядный таймер/счетчик TMR1 с 8-разрядным программируемым предделителем и возможностью подключения внешнего резонатора;
- 8-разрядный таймер/счетчик TMR2 с программируемым предделителем и выходным делителем (по 4 разряда).
Используя таймеры TMR0 или TMR2 можно получить максимальное значение коэффициента деления частоты 216 = 65536. На таймере TMR1 можно построить делитель частоты с максимальным коэффициентом 216 × 23 = 524288. Поэтому выбираем таймер TMR1 и используем его в режиме делителя частоты со значением 92160, принятой для нашей задачи.
3 Разработка аппаратных средств
В задании на курсовой проект тип микроконтроллера задан. Поэтому задача разработки аппаратных средств сводится к разработке принципиальной электрической схемы МПУ и настройке встроенных периферийных модулей МК. Жесткое требование задания, которое касается реализации прототипа МПУ на учебно-отладочном стенде, делает задачу разработки принципиальной схемы тривиальной. Практически все проектные решения уже приняты разработчиками учебно-отладочного стенда и не могут быть пересмотрены. Поэтому разработка принципиальной схемы МПУ сводится к дублированию схемы учебно-отладочного стенда с возможным удалением из нее неиспользуемых элементов и связей.
Выберем из имеющихся в учебно-отладочном стенде элементов и узлов, необходимые для данной задачи. Кроме МК и элементов цепей питания потребуются:
- две кнопки (например, S1- «Старт-Стоп» и S2 - «Сброс»);
- элементы, обеспечивающие работу цифровых индикаторов.
Полученная принципиальная схема МПУ приведена в приложении А.
Данные от МК к контроллеру MC14489BP должны передаваться через синхронный последовательный интерфейс, включающий три линии:
- Data_in – данные;
- Clk - синхроимпульсы;
- CS – выборка кристалла.
В соответствии со схемой МПУ сигналы Data_in и Clk должны формироваться на линиях 1 и 0 порта PORTE, сигнал CS на линии 3 порта PORTB. Поэтому эти линии портов необходимо настроить на вывод. Для настройки модуля PORTE воспользуемся таблицей 1. Настройка линий на ввод-вывод определяется содержимым управляющего регистра TRISB2-TRISB0). Так как линии порта PORTE могут использоваться, как аналоговые входы, то следует также выполнить их настройку для работы в режиме цифровых линий. Настройка выполняется разрядами PCFG3-PCFG0 регистра ADCON1.
Таблица 1 – Регистры и биты, связанные с работой PORTE
Адрес |
Имя |
Бит 7 |
Бит 6 |
Бит 5 |
Бит 4 |
Бит 3 |
Бит 2 |
Бит 1 |
Бит 0 |
09h |
PORTE |
- |
- |
- |
- |
- |
RE2 |
RE1 |
RE0 |
89h |
TRISE |
IBF |
OBF |
IBOV |
PSPMODE |
- |
Рег. напр. данных PORTE |
||
9Fh |
ADCON1 |
ADFM |
- |
- |
- |
PCFG3 |
PCFG2 |
PCFG1 |
PCFG0 |
Сформируем константы для загрузки в управляющие регистры:
- INIT_PORTE = b'00000100' (линии RE1, RE0 на вывод);
- INIT_ADCON1 = b'10001110' (линии RE2-RE0 – цифровые).
Так как к линиям порта PORTB также подключены кнопки, то настройку режимов работы этого порта выполним позже.
Диаграммы сигналов CS, CLK, а также форматы слова конфигурации для MC14489BP и слов данных приведены на рисунке 4. Слово конфигурации длиной один байт определяет:
- режим потребляемой мощности (C0);
- режимы декодирования разрядов (С1 – С7). Определим управляющее слово для отображения символов шестнадцатиричного алфавита в нормальном режиме потребляемой мощности INIT_MC14489=b'00000001'.
Рисунок 4
В соответствии с электрической схемой МПУ кнопки «Старт-Стоп» и «Сброс» подключены к линиям 1 и 2 порта PORTB соответственно. Обозначим соответствующие разряды порта RB1 и RB2. Активному (нажатому) состоянию кнопки соответствует низкий потенциал на линии порта PORTB. Пассивному (отжатому) состоянию кнопки соответствует высокий потенциал, который обеспечивается встроенными подтягивающими резисторами. Включаются подтягивающие резисторы установкой разряда –RBPU=0 в регистре OPTION_REG. Для настройки модуля PORTB воспользуемся таблицей 2. Настройка линий определяется содержимым управляющего регистра TRISB.
Таблица 2 – Регистры и биты, связанные с работой PORTB
Адрес |
Имя |
Бит 7 |
Бит 6 |
Бит 5 |
Бит 4 |
Бит 3 |
Бит 2 |
Бит 1 |
Бит 0 |
06h, 106h |
PORTB |
RB7 |
RB6 |
RB5 |
RB4 |
RB3 |
RB2 |
RB1 |
RB0 |
86h, 186h |
TRISB |
Регистр направления данных PORTB |
|||||||
81h, 181h |
OPTION_REG |
-RBPU |
INTEDG |
T0CS |
T0SE |
PSA |
PS2 |
PS1 |
PS0 |
Сформируем константы для загрузки в управляющие регистры:
- INIT_PORTB = b'11010111' (линии 3, 5 - вывод, остальные ввод);
- INIT_OPTION = b'01000111' (включить подтягивающие резисторы).
Кроме двух портов в проекте используется встроенный таймер TMR1. Функциональная схема модуля TMR1 приведена на рисунке 5.
Рисунок 5
Для получения необходимого коэффициента деления настроим предделитель на коэффициент 8, тогда модуль счета таймера составит 92160/8 = 11520. Разложим найденное значение на сомножители 256 и 243 – модули счета TMR1L и TMR1H соответственно. Для настройки модуля TMR1 воспользуемся таблицей 3.
Таблица 3 – Регистры и биты, связанные с работой TMR1
Адрес |
Имя |
Бит 7 |
Бит 6 |
Бит 5 |
Бит 4 |
Бит 3 |
Бит 2 |
Бит 1 |
Бит 0 |
06h, 106h |
PORTB |
RB7 |
RB6 |
RB5 |
RB4 |
RB3 |
RB2 |
RB1 |
RB0 |
86h, 186h |
TRISB |
Регистр направления данных PORTB |
|||||||
81h, 181h |
OPTION_REG |
-RBPU |
INTEDG |
T0CS |
T0SE |
PSA |
PS2 |
PS1 |
PS0 |
Управляющее слово TMR1 находится в регистре T1CON:
- биты 5-4 T1CKPS1:T1CKPS0 задают коэффициент деления предделителя (11 = 1:8, 10 = 1:4, 01 = 1:2, 00 = 1:1);
- бит 3 T1OSCEN включает тактовый генератор TMR1 (1 = генератор включен, 0 = генератор выключен);
- бит 2 -T1SYNC задает синхронизацию внешнего тактового сигнала
TMR1CS = 1 (1 = не синхронизировать внешний тактовый, 0 = синхронизировать внешний тактовый; при TMR1CS = 0 значение бита игнорируется);
- бит 1 TMR1CS выбирает источник тактового сигнала (1 = внешний источник с вывода RC0/T1OSO/T1CKI, 0 = внутренний источник Fosc/4);
- бит 0 TMR1ON включает модуль TMR1 (1 = включен, 0 = выключен).
Формируем управляющее слово INIT_T1CON=b’00110001’.
4 Разработка программы для МПУ
Сначала следует принять принципиальные решения, определяющие структуру программы. Прежде всего, необходимо определиться, как должен реагировать МК на основные события:
- переполнения таймера через каждые 100 мс;
- нажатия кнопок «Старт-Стоп» и «Сброс» в произвольные моменты времени.
В принципе возможны три варианта реакции МК на эти события:
- программный опрос флага TMR1IF и линий порта ввода;
2) прерывание программы от таймера TMR1 и программный опрос линий порта ввода;
3) прерывание программы от изменения уровней сигналов на линиях порта ввода и программный опрос флага TMR1IF.
Первый и третий варианты в данном случае не подходят, потому что при нажатии на одну из кнопок может быть пропущен момент переполнения таймера. Это приведет к искажению показаний времени. Выбираем второй вариант, при этом программа МК должна содержать подпрограмму обработки прерывания от таймера TMR1.
МК семейства PIC16F87х имеют 14 источников прерываний (рисунок 6). Регистр INTCON содержит флаги отдельных прерываний, биты разрешения этих прерываний и бит глобального разрешения прерываний (таблица 3). Если бит GIE (INTCON<7>) установлен в ‘1’, разрешены все немаскированные прерывания. Если GIE=0, то все прерывания запрещены. Каждое прерывание в отдельности может быть разрешено/запрещено установкой/сбросом соответствующего бита в регистрах INTCON, PIE1 и PIE2.
Рисунок 6
При сбросе микроконтроллера бит GIE сбрасывается в ‘0’. При возвращении из подпрограммы обработки прерывания по команде RETFIE бит GIE аппаратно устанавливается в ‘1’, разрешая все немаскированные прерывания. В регистре INTCON находятся флаги следующих прерываний: внешнего сигнала INT, изменения уровня сигнала на входах RB7:RB4, переполнения TMR0. В регистрах PIR1, PIR2 содержатся флаги прерываний периферийных модулей микроконтроллера, а в регистрах PIE1, PIE2 соответствующие биты разрешения прерываний. В регистре INTCON находится бит разрешения прерываний от периферийных модулей PEIE.
При переходе на подпрограмму обработки прерываний бит GIE аппаратно сбрасывается в ‘0’, запрещая прерывания, адрес возврата из подпрограммы обработки прерываний помещается в стек, а в счетчик команд PC загружается вектор прерывания 0004h. Источник прерываний может быть определен проверкой флагов прерываний, которые должны быть сброшены программно перед разрешением прерываний, чтобы избежать повторного вызова.
Флаги прерываний устанавливаются независимо от состояния соответствующих битов маски и бита GIE.
Если прерывания разрешены (разряды GIE=1, PEIE=1 в регистре INTCON и разряд TMR1IE=1 в регистре PIE1), при переполнении таймера будет взводиться флаг TMR1IF в регистре PIR1. После этого необходимо записывать в регистр TMR1H число (256 – 243) = 13 и сбрасывать флаг TMR1IF. Тогда частота установки флага TMR1IF составит 3.6864×106 /(4 × 8 × 5 × 256) = 10 Гц.
Таким образом, подпрограмма обработки прерывания от таймера TMR1 должна выполнять:
- модификацию TMR1H (загрузка числа 5);
- сброс флага TMR1IF;
- подсчет долей секунд, секунд и минут.
Основная программа должна содержать бесконечный цикл, в теле которого будут реализованы функции:
- вывода информации о текущем времени в последовательном коде в блок индикации;
- опроса линий порта ввода.
Принятое распределение функций можно обосновать тем, что выработка 0,1 секундных отметок времени, а также модификация счетчиков секунд и минут могут происходить только при переполнении таймера. Представим принятые решения в виде схемы программы (рисунок 7).
По данным изготовителя МК операции чтения и записи в регистры таймера TMR1H, TMR1L рекомендуется выполнять после остановки таймера. В противном случае результат может быть непредсказуемым. В нашем случае таймер можно не останавливать, так как самое первое изменение содержимого регистра TMR1H после прерывания произойдет только через 8×256=2048 машинных циклов.
Рисунок 7 – Схема программы
В схеме подпрограммы обработки прерывания INT учтена необходимость сохранения и восстановления контекста (содержимого аккумулятора w и регистра флагов STATUS).
Алгоритмизацию и программирование отдельных функций можно выполнять совместно. Но сначала необходимо выбрать язык программирования.
Языки программирования низкого уровня в настоящее время называются ассемблерами. Основу ассемблера составляют машинные команды процессора в мнемоническом представлении. Кроме машинных команд современные языки ассемблера, как правило, включат директивы, определяющие ход трансляции, а также средства создания макрофункций.
Рассмотрим вариант программирования на языке ассемблера.
Сначала получим детализированный алгоритм подпрограммы обработки прерывания на языке ассемблера. Вектор прерывания МК находится по адресу 0004, поэтому подпрограмму начинаем с директивы ассемблера установки адреса:
ORG 0x004 ; вектор прерывания
Для сохранения контекста используем ячейки w_temp (для сохранения аккумулятора w) и status_temp (для сохранения регистра STATUS):
movwf w_temp ; сохранение W
movf STATUS,w ; сохранение STATUS
bcf STATUS,RP0 ; банк 0
bcf STATUS,RP1;
movwf status_temp
Выполняем проверку, что прерывание вызвано переполнением таймера, иначе выход из подпрограммы:
btfss PIR1,TMR1IF
goto ret
Затем загружаем регистр таймера и сбрасываем флаг прерывания:
movlw .232 ;установка модуля 5 (256-251)
movwf TMR1H ;
bcf PIR1,TMR1IF ;сброс флага прерывания от TMR1.
Счетчики долей секунд, секунд и минут также можно программно реализовать на 8-разрядных регистрах, но при этом счет должен производиться в двоично-десятичном коде (BCD). Или счет может производиться в двоичном коде, но потребуется подпрограмма для преобразования кода. В системе команд МК семейств PIC16 отсутствуют команды работы с двоично-десятичными числами, поэтому используем четыре ячейки для представления времени:
- MSL - счетчик единиц милисекунд;
- SL - счетчик единиц секунд;
- SH - счетчик десятков секунд;
- ML - счетчик единиц милисекунд.
;---------------------- Счетчик сотых доль секунд ------------------------
incf ML,f ;увеличить минуты на 1
movlw -.10 ;
addwf ML,w ;сравнить с числом 10
btfss STATUS,C ;если =10, то
goto ret ;
clrf ML ;обнулить десятки секунд
;---------------------- Счетчик долей секунд -------------------------
incf MSL,f ;увеличить доли секунды на 1
movlw -.10 ;
addwf MSL,w ;сравнить с числом 10
btfss STATUS,C ;если =10, то
goto ret ;
clrf MSL ;обнулить единицы минут
;---------------------- Счетчик единиц секунд ------------------------
incf SL,f ;увеличить единицы cекунды на 1
movlw -.10 ;
addwf SL,w ;сравнить с числом 10
btfss STATUS,C ;если =10, то
goto ret ;
clrf SL ;обнулить единицы секунды
;---------------------- Счетчик десятков секунд --------------------------
incf SH,f ;увеличить десятки секунд на 1
movlw -.6 ;
addwf SH,w ;сравнить с числом 6
btfss STATUS,C ;если = 6, то
goto ret ;
clrf SH ;обнулить десятки секунд
Для управления децимальными точками индикаторов используем ячейку Fig2.
Точка будет отделять разряд долей секунд от остальных разрядов.
movlw b’00010000;
movwf Fig2
Перед возвратом из подпрограммы восстанавливаем контекст:
ret bcf STATUS,RP0; банк 0
movf status_temp,w; восстановление STATUS
movwf STATUS ;
swapf w_temp,f
swapf w_temp,w ; восстановление W
retfie ; возврат.
Теперь перейдем к формированию исходного текста основной программы. Сначала получим основу программы в соответствии со схемой (рисунок 7). Текст программы должен начинаться с директивы установки адреса сброса 0x000. Чтобы использовать средства внутрисхемной отладки, следующей командой должна быть nop. Так как тексты всех подпрограмм принято размещать до ссылок на них в основной программе, то следующей должна быть команда перехода на начало программы. Здесь первой командой должна быть команда запрета прерываний на время инициализации. Необходимо выполнить инициализацию всех используемых встроенных модулей МК, контроллера MC14489 и ячеек памяти. После инициализации необходимо разрешить прерывания от таймера TMR1.
Рассмотренные действия должны выполняться однократно после включения или сброса МПУ. Последующие действия должны повторяться. В теле цикла необходимо формировать и выводить информацию о текущем времени в последовательном коде в блок индикации, опрашивать линии порта ввода, выбирать режим работы и корректировать показания текущего времени. Для вывода информации используем подпрограмму, которую назовем Display.
Так как МПУ должен однократно реагировать на нажатие любой из кнопок, то переход на начало цикла возможен только после отпускания кнопки. Поэтому опрос каждой кнопки должен выполняться дважды: сначала анализ на нажатое состояние, а затем анализ на отжатое состояние. Будем опрашивать состояние кнопок последовательно: сначала кнопку «Старт-Стоп», затем кнопку «Сброс».
Ниже приводится текст основы программы, полученной с учетом принятых решений. Нереализованные операторы пока представлены комментариями:
ORG 0x000 ;вектор сброса
nop
goto Begin ;переход на начало программы
;Здесь будут находиться все подпрограммы
Begin clrf INTCON ;запретить все прерывания
;операторы инициализации модулей МК
;операторы инициализации MC14489
;операторы инициализации ячеек памяти
bsf STATUS,RP0 ;банк 1
bsf PIE1,TMR1IE ;разрешить прерывания от TMR1
bcf STATUS,RP0 ;банк 0
bsf INTCON,PEIE ;включить прерывания
bsf INTCON,GIE
;-------------------------------------- основной цикл -------------------------------------
Main swapf SL,w
iorwf MSL,w
movwf Fig0 ;вывод ед сек и долей сек
swapf ML,w
iorwf SH,w
movwf Fig1 ;вывод десятков сек и минут
movlw 20h
movwf Fig2
Dspl call Display
btfsc RB1 ;опрос кнопки "Старт-Стоп"
goto bt2 ;кнопка "Старт-Стоп" не нажата
bsf STATUS,RP0 ;банк 1
btfsc PIE1,TMR1IF
goto $+3
bsf PIE1,TMR1IF ;разрешить прерывания
goto $+2
bcf PIE1,TMR1IF
bcf STATUS,RP0 ;банк 1
goto Release1
bt2 btfsc RB2 ;опрос кнопки "сброс"
goto Dspl ;кнопка "сброс" не нажата
clrf MSL
clrf SL
clrf SH
clrf ML
goto Release2
;------------------------ опрос кнопок (отжатие) -----------------------
Release1
call Del15ms ;задержка
btfss RB1 ;опрос кнопки "Старт-Стоп"
goto Release1 ;кнопка не отжата
call Del15ms ;задержка
goto Dspl
Release2
call Del15ms ;задержка
btfss RB2 ;опрос кнопки "сброс"
goto Release2 ;кнопка не отжата
call Del15ms ;задержка
goto Dspl
goto Main ;кнопка отжата
end
Информация, выводимая в контроллер индикаторов, должна быть представлена в последовательном коде. Информационное слово состоит из 24 разрядов, из них младшие 20 разрядов (D0 – D19) содержат пять тетрад кода отображаемых символов, разряды D20 – D22 управляют сегментами h (точка), разряд D23 – управляет яркостью свечения сегментов (рисунок 8). Так как используются только четыре индикатора, то разряды D16-D19 можно задавать произвольно.
Рисунок 8
Для вывода на индикаторы необходимо показания минут и часов упаковать в два байта (в BCD), для их хранения используем ячейки:
- Fig0 - разряды долей секунд и единиц секунд ;
- Fig1 - разряды десятков секунд и единиц минут.
Для управления децимальными точками индикаторов используем ячейку Fig2. Так как данные должны передаваться в последовательном коде, необходим буфер данных IndVal, используемый как сдвигающий регистр, и счетчик разрядов CntInd. Тогда вывод одного байта можно свести к загрузке буфера IndVal, инициализации счетчика CntInd и последовательности сдвигов буфера влево, пока CntInd ≠ 0. После сдвига выводимый разряд байта будет находиться в разряде STATUS<C>. При этом каждый сдвиг должен сопровождаться формированием фронта синхроимпульса Clk. При условии, что байт находится в аккумуляторе w, алгоритм вывода можно представить в виде подпрограммы Send8:
Send8 bcf Clk ;Clk:=0
movwf IndVal ;переслать w в буфер
movlw 8 ;загрузить счетчик разрядов
movwf CntInd
sendloop bcf Data_in ;установить 0
rlf IndVal,f ;сдвиг влево
btfsc STATUS,C ;анализ флага С
bsf Data_in ;установить 1, если С=1
bsf Clk ;сформировать импульс
bcf Clk
decfsz CntInd,1 ;уменьшать счетчик до 0
goto sendloop
return
Процесс вывода информации можно представить, как последовательный вывод трех восьмиразрядных слов при выборе контроллера MC14489 (CS=0):
Display bcf CS ;CS:=0
movf Fig2,w ;загрузить Fig2
call Send8 ;вывести на индикатор
movf Fig1,w ;загрузить Fig1
call Send8 ;вывести на индикатор
movf Fig0,w ;загрузить Fig0
call Send8 ;вывести на индикатор
bsf CS ;CS:=1
return
Ранее было принято, что показания разрядов часов и минут для вывода необходимо представить в упакованном BCD виде. Операторы подготовки информации для вывода в контроллер индикаторов:
swapf SL,w
iorwf MSL,w
movwf Fig0 ;BCD 10Х долей и единиц секунд
swapf ML,w
iorwf SH,w
movwf Fig1 ;BCD десятков секунд и единиц минут
Чтобы отделить точкой разряд долей секунд, будем зажигать децимальную точку в разряде единиц секунд. Для этого в соответствии с рисунком 8 в ячейку Fig2 необходимо загружать код 20h:
movlw 20h
movwf Fig2
Все механические кнопки имеют одно негативное свойство, известное как “дребезг контактов”, которое обусловлено колебаниями упругих контактов при их замыкании и размыкании. Длительность колебаний составляет всего насколько миллисекунд. При этом вместо “чистого” прямоугольного импульса получается искаженный импульс или пачка импульсов. Идеальный и реальный сигналы, формируемые при нажатии и отпускании кнопки, представлены на рисунке 10.
Рисунок 10
Известны аппаратные средства подавления «дребезга контактов» (с помощью RS-триггеров, одновибраторов или интегрирующих RC цепочек, устанавливаемых перед триггерами Шмитта). В устройствах на базе МК обычно используют программные способы подавления «дребезга контактов». Простейший из них основан на ограничении минимальных интервалов времени между последовательными операциями чтения порта ввода. Для надежного считывания состояний кнопки величина этих интервалов не должна быть меньше 15 – 30 мс.
Таким образом, для подавления «дребезга контактов» в цикл основной программы достаточно включить подпрограмму задержки:
call Del30ms ;задержка 30 мс
Реализовать подпрограмму задержки можно с использованием свободного таймера TMR0 или программно. Выберем второй вариант и для построения счетчиков используем ячейки:
- Temp1 - счетчик 500 мкс;
- Temp2 - счетчик 30 мс.
Del15ms movlw .80
movwf Temp2
_15ms call Del500us
decfsz Temp2,f
goto _15ms
return
;------------------- подпрограмма задержки 500 мкс --------------------
Del500us movlw .151
movwf Temp1
_500us decfsz Temp1,f
goto _500us
return
Теперь, когда определены все используемые ресурсы МК, можно приступить к программированию операторов инициализации. При использовании операторов инициализации модулей МК необходимо помнить, что все ячейки статической памяти данных МК размещаются в четырех банках. При обращении к регистрам специальных функций следует учитывать, в каком банке они размещаются. С учетом этого операторы инициализации модулей МК:
bsf STATUS,RP0 ;банк 1
bcf STATUS,IRP
bcf STATUS,RP1
movlw INIT_PORTA
movwf TRISA^80h
movlw INIT_PORTB
movwf TRISB^80h
movlw INIT_PORTD
movwf TRISD^80h
movlw INIT_PORTE
movwf TRISE^80h
movlw INIT_OPTION
movwf OPTION_REG^80h
movlw INIT_ADCON1
movwf ADCON1^80h
bcf STATUS,RP0 ;банк 0
movlw INIT_T1CON
movwf T1CON
Операторы инициализации контроллера MC14489:
bsf CS
movlw b'00000001' ;управляющее слово
bcf CS
call Send8
bsf CS
Операторы инициализации ячеек памяти:
clrf Fig0 ;сброс индикаторов
clrf Fig1
clrf Fig2
clrf MSL ;сброс времени
clrf SL
clrf SH
clrf ML
clrf State ;инициализация автомата
5 Автономная отладка программы
Отладка программ микропроцессорной системы проводится, как правило, на тех же ЭВМ, на которых велась разработка программ, и на том же языке программирования, на котором написаны отлаживаемые программы, и может быть начата на ЭВМ даже при отсутствии аппаратуры МПС. При этом в системном программном обеспечении ЭВМ должны находиться программы (интерпретаторы или эмуляторы), моделирующие функции отсутствующих аппаратных средств. Так, разработка и автономная отладка программных средств может вестись на больших ЭВМ, мини-ЭВМ, микро-ЭВМ, система команд которых не совпадает с системой команд используемого микропроцессора. Кроме того, при отладке программ может отсутствовать внешняя среда микропроцессорной системы, ее также необходимо моделировать.
Проверка корректности программ, т.е. проверка соответствия их внешним спецификациям, осуществляется тестированием. Программы проверяются на функционирование с различными исходными данными. Результаты функционирования программ сравниваются с эталонными значениями.
Отладка программ подразделяется на следующие этапы: планирование отладки; составление тестов и задания на отладку; исполнение программ; информирование о результатах исполнения программ по заданным исходным данным; анализ результатов, обнаружение ошибок и локализация неисправностей
В нашем случае, как для разработки программы, так и для автономной ее отладки использовался специализированный пакет программ MPLAB IDE фирмы Microchip.
Для того чтобы проверить наличие прерывания, поставим точку останова после строки вектора прерывания и в окне Stopwatch получил значение до прерывания равное примерно 100 мс, следовательно, таймер настроен правильно.
Далее для отладки программы применим быстрый пошаговый режим прогона программы – Animate, при этом проверялось содержимое регистров Fig0..Fig2
после каждого прерывания от таймера, а также реакция выполнения программы на нажатие кнопок RB1 и RB2, смоделированных в Asynchronous Stimulus Dialog. Так при нажатии 1 кнопки прерывание от таймера запрещалось и содержимое регистров Fig0..Fig2 не изменялось, что соответствовало состоянию остановки секундомера, а при нажатии 2 кнопки содержимое этих регистров обнулялось.
После того, как убедились в правильности выполнения программы в режиме автономной отладки, перешли к комплексной отладке проекта.
6 Комплексная отладка микропроцессорной системы
При комплексной отладке наряду с детерминированным используется статистическое тестирование, при котором МПС проверяется при изменении исходных переменных в соответствии со статистическими законами работы источников информации. Полнота контроля работоспособности проектируемой системы возрастает за счет расширения диапазона возможных сочетаний переменных и соответствующих им логических маршрутов обработки информации.
Существуют пять основных приемов комплексной отладки микропроцессорной системы:
1) останов функционирования системы при возникновении определенного события;
2) чтение (изменение) содержимого памяти или регистров системы;
3) пошаговое отслеживание поведения системы;
4) отслеживание поведения системы в реальном времени;
5) временное согласование программ.
В данном проекте я используем 4 прием комплексной отладки, то есть отслеживание поведения системы в реальном времени. Параметры, по которым можно было определить правильность работы секундомера, являются значения пройденного времени на индикаторах и реакция системы на нажатие первой и второй кнопок.
В ходе проведения комплексной отладки, нарушений в работе секундомера не обнаружено, поэтому делаем вывод, что программа верна.
Список использованных источников
- Хлуденёв А.В. Разработка и отладка устройств на микроконтроллерах: Методические указания. - Оренбург: ОГУ, – 47 с.
Приложение А
(обязательное)
Схема электрическая принципиальная
Приложение Б
(обязательное)
Исходный текст программы
;**********************************************************************
; Секундомер
;**********************************************************************
LIST p=16F877 ; определение процессора
#include "p16f877.inc" ;
;***********************************************************************
; Структура данных
;***********************************************************************
;------------------------------ Переменные -----------------------------
cblock 0x30
MSL ;счетчик единиц милисекунд
SL ;счетчик едтниц секунд
SH ;счетчик десятков секунд
ML ;счетчик сотых доль секунд;
Fig0 ;разряды 1-0 7сегм.
Fig1 ;разряды 3-2 7сегм.
Fig2
IndVal ;слово конфигурации в MC14489
CntInd ;счетчик разрядов MC14489
w_temp ;переменная для хранения АК
status_temp ;переменная для хранения STATUS
State ;состояние конечного автомата
Temp1 ;счетчик 500us
Temp2 ;счетчик 15ms
endc
;------------------------------ Константы ------------------------------
INIT_PORTA EQU b'11111111' ;все ввод
INIT_PORTB EQU b'11010111' ;биты 3,5 - вывод
INIT_PORTD EQU b'11111111' ;все ввод
INIT_PORTE EQU b'00000000' ;все вывод
INIT_OPTION EQU b'01000111' ;настройка TMR0
INIT_INTCON EQU b'11000000' ;настройка прерываний
INIT_T1CON EQU b'00110001' ;настройка TMR1
INIT_ADCON1 EQU b'10001110' ;настройка линий RE2-RE0
;--------------------------- Битовые переменные ------------------------
#define Data_in PORTE,1 ;сигналы MC14489
#define Clk PORTE,0 ;
#define CS PORTB,3 ;
#define RB1 PORTB,1 ;кнопка "Старт-Стоп"
#define RB2 PORTB,2 ;кнопка "Сброс"
;**********************************************************************
ORG 0x000 ; вектор сброса
clrf PCLATH ;
goto Begin ; переход на начало программы
;**********************************************************************
; Подпрограмма обработки прерывания
;**********************************************************************
ORG 0x004 ; вектор прерывания
movwf w_temp ; сохранение W
movf STATUS,w ; сохранение STATUS
bcf STATUS,RP0 ; банк 0
bcf STATUS,RP1 ; -
movwf status_temp ; -
btfss PIR1,TMR1IF
goto ret
movlw .232 ;установка модуля 45 (256-251)
movwf TMR1H ;
bcf PIR1,TMR1IF ;сброс флага прерывания от TMR1
;---------------------- Счетчик сотых доль секунд ------------------------
incf ML,f ;
movlw -.10 ; число -10
addwf ML,w ;прибавить к единицам минут
btfss STATUS,C ;для сравнения
goto ret ;
clrf ML ;обнулить десятки секунд
;---------------------- Счетчик долей секунд -------------------------
incf MSL,f ;
movlw -.10 ; число -10
addwf MSL,w ;прибавить к долям секунд
btfss STATUS,C ;для сравнения
goto ret ;
clrf MSL ;обнулить доли секунд
;---------------------- Счетчик единиц секунд ------------------------
incf SL,f ;
movlw -.10 ; число -10
addwf SL,w ;прибавить к единицам секунд
btfss STATUS,C ;для сравнения
goto ret ;
clrf SL ;обнулить единицы секунд
;---------------------- Счетчик десятков секунд --------------------------
incf SH,f ;
movlw -.6 ; число -6
addwf SH,w ;прибавить к десяткам секунд
btfss STATUS,C ;для сравнения
goto ret ;
clrf SH ;обнулить десятки секунд
;----------------------------- Возврат -------------------------------
ret bcf STATUS,RP0 ; банк 0
movf status_temp,w ; восстановление STATUS
movwf STATUS ;
swapf w_temp,f
swapf w_temp,w ; восстановление W
retfie ; возврат
;***********************************************************************
; Подпрограмма отображ. 7сегм. символов
;***********************************************************************
Display bcf CS
movf Fig2,w
call Send8
movf Fig1,w
call Send8
movf Fig0,w
call Send8
bsf CS
return
;--------------- подпрограмма отображ текущ. символа (W) ---------------
Send8 bcf Clk
movwf IndVal
movlw 8
movwf CntInd
sendloop
bcf Data_in
rlf IndVal,f
btfsc STATUS,C
bsf Data_in
nop
bsf Clk
nop
bcf Clk
decfsz CntInd,1
goto sendloop
return
;**********************************************************************
; Подпрограмма задержки 15 мс
;**********************************************************************
Del15ms movlw .80
movwf Temp2
_15ms call Del500us
decfsz Temp2,1
goto _15ms
return
;------------------- подпрограмма задержки 500 мкс --------------------
Del500us
movlw .151
movwf Temp1
_500us decfsz Temp1,f
goto _500us
return
;***********************************************************************
; Начало программы
;***********************************************************************
Begin clrf INTCON ;запретить все прерывания
nop
;-------------------- Инициализация модулей МК -------------------------
bsf STATUS,RP0 ;банк 1
bcf STATUS,IRP
bcf STATUS,RP1
movlw INIT_PORTA
movwf TRISA^80h
movlw INIT_PORTB
movwf TRISB^80h
movlw INIT_PORTD
movwf TRISD^80h
movlw INIT_PORTE
movwf TRISE^80h
movlw INIT_OPTION
movwf OPTION_REG^80h
movlw INIT_ADCON1
movwf ADCON1^80h
clrf PIE1
bcf STATUS,RP0 ;банк 0
movlw INIT_T1CON
movwf T1CON
;------------------------ Инициализация MC14489 ------------------------
bsf CS
movlw b'00000001' ;управляющее слово
movwf IndVal
bcf CS
movf IndVal,w
call Send8
bsf CS
;--------------------- Инициализация ячеек памяти ----------------------
clrf Fig0 ;сброс индикаторов
clrf Fig1
movlw b'00010000'
movwf Fig2
clrf MSL ;сброс времени
clrf SL
clrf SH
clrf ML
;-----------------------------------------------------------------------------
bsf INTCON,PEIE ;включить прерывания
bsf INTCON,GIE
;-------------------------- основной цикл ------------------------------
Main swapf ML,w
iorwf MSL,w
movwf Fig0 ;вывод ед сек и долей сек
swapf SH,w
iorwf SL,w
movwf Fig1 ;вывод десятков сек и минут
movlw 20h
movwf Fig2
Dspl call Display
;-------------------------- конечный автомат ---------------------------
btfsc RB1 ;опрос кнопки "Старт-Стоп"
goto bt2 ;кнопка "Старт-Стоп" не нажата
bsf STATUS,RP0 ;банк 1
btfsc PIE1,TMR1IE
goto $+3
bsf PIE1,TMR1IE ;разрешить прерывания
goto $+2
bcf PIE1,TMR1IE
bcf STATUS,RP0 ;банк 1
goto Release1
bt2 btfsc RB2 ;опрос кнопки "сброс"
goto Main ;кнопка "сброс" не нажата
clrf MSL
clrf SL
clrf SH
clrf ML
goto Release2
;------------------------ опрос кнопок (отжатие) -----------------------
Release1
call Del15ms ;задержка
btfss RB1 ;опрос кнопки "Старт-Стоп"
goto Release1 ;кнопка не отжата
call Del15ms ;задержка
goto Main
Release2
call Del15ms ;задержка
btfss RB2 ;опрос кнопки "сброс"
goto Release2 ;кнопка не отжата
call Del15ms ;задержка
goto Main ;кнопка отжата
end
Скачать: