Программа для отображения цифр от F до 0 на семисегментном индикаторе (ATmega16)

В данной статье представлен пример программы на языке ассемблера для микроконтроллера ATmega16. Задача программы — последовательное отображение цифр от F до 0 на семисегментном индикаторе в порядке убывания. Особенностью алгоритма является динамическое изменение временного интервала между сменой цифр: с каждым шагом счета задержка уменьшается в два раза. В материале приводится полный листинг кода с комментариями, поясняющими работу с EEPROM, таймерами и прерываниями.

Постановка задачи

Необходимо написать программу для отображения на семисегментном индикаторе цифр по убыванию от F до 0. При этом временной интервал между цифрами с каждым счетом должен уменьшаться в 2 раза.

Комментарии к коду

Знак ; обозначает комментарий строки и не влияет на работу программы.

Знак : обозначает метку — именное обозначение адреса, используемое для перехода на данную строчку программы из любой другой части кода.

Начало программы и векторы прерываний

.include "m16def.inc" ; директива подгрузки файла с директивами для микроконтроллера ATmega16

; таблица векторов (адреса размещения подпрограмм обработки прерываний)
rjmp reset
.org $00E ; выбираются исходя из используемых событий для прерывания.
rjmp TIMER1_COMPB

Инициализация стека

reset:  ldi r16, high(ramend) ;установка стека (необходимо для корректной 
out sph, r16 ;работы переходов по меткам.
ldi r16, low(ramend)
out spl, r16

Все логические и математические операции производятся только с регистрами общего назначения (R0-R31). Для произведения операций с другими регистрами и типами памяти необходимо выполнять их в регистрах общего назначения, а затем результат записывать в необходимый регистр/ячейку памяти. Непосредственная запись числа возможна только в регистры R16-R31.

Запись в EEPROM чисел от F до 0

ldi r16, 0b01110001 ; F
call eeprom_write
inc r17
ldi r16, 0b01111001 ; E
call eeprom_write
inc r17
ldi r16, 0b01011110 ; d
call eeprom_write
inc r17
ldi r16, 0b00111001 ; C
call eeprom_write
inc r17
ldi r16, 0b01111100 ; b
call eeprom_write
inc r17
ldi r16, 0b01110111 ; A
call eeprom_write
inc r17
ldi r16, 0b01101111 ; 9
call eeprom_write
inc r17
ldi r16, 0b01111111 ; 8
call eeprom_write
inc r17
ldi r16, 0b00000111 ; 7
call eeprom_write
inc r17
ldi r16, 0b01111101 ; 6
call eeprom_write
inc r17
ldi r16, 0b01101101; 5
call eeprom_write
inc r17
ldi r16, 0b01100110 ; 4
call eeprom_write
inc r17
ldi r16, 0b01001111 ; 3
call eeprom_write
inc r17
ldi r16, 0b01011011 ; 2
call eeprom_write
inc r17
ldi r16, 0b00000110 ; 1
call eeprom_write
inc r17
ldi r16, 0b00111111 ; 0
call eeprom_write

Настройка портов и таймера

ldi r16, 0xff
out DDRA, r16 ; порт А на вывод данных

ldi r16, 0b00001000
out timsk, r16 ; прерывание от T1 по сравнению B

ldi r16, 0b00000011
out tccr1b, r16 ; скорость счета = f/64

Начальные условия и основной цикл

m0: ldi r31, 0xff
ldi r30, 0xff
out ocr1bh, r31 ; запись начального условия в регистр сравнения В Таймера1
out ocr1bl, r30

ldi r16, 0b01110001 ; F – начальное условие
clr r17

sei ;установка флага "i", разрешающего прерывания работы МК.

main: out PortA, r16 ; основная программа МК. Выполняется циклично.  
jmp main ;(может состоять только из команды зацикливания)

Подпрограмма обработки прерывания

TIMER1_COMPB: 
cpi r31, 0
breq m1
lsr r31 ; Логический сдвиг вправо (заменяет деление на 2)
out OCR1BH, r31
jmp m2
m1: lsr r30 
out OCR1Bl, r30
m2: inc r17
cpi r17, 0x10
breq m0 ; возврат к начальному условию
call eeprom_read
out tcnt1h, r18
out tcnt1l, r18 ; обнуление таймера
reti

Подпрограмма чтения из EEPROM

Чтение ячейки EEPROM (адрес ячейки указывается в регистрах R18:R17) в регистр R16.

eeprom_read: 
sbic eecr, eewe
rjmp eeprom_read
out eearh, r18
out eearl, R17
sbi eecr, eere
in r16, eedr
ret

Подпрограмма записи в EEPROM

Запись из регистра R16 в ячейку EEPROM (адрес ячейки указывается в регистрах R18:R17).

eeprom_write: 
sbic eecr, eewe
rjmp eeprom_write
out eearh, r18
out eearl, r17
out eedr, r16
sbi eecr, eemwe
sbi eecr, eewe
ret

Оцените статью
Сессия под ключ дистанционно
Добавить комментарий

Заявка на расчет