;При нажатии на одну из семи кнопок будет звучать одна из семи мелодий
.include "tn2313def.inc"
.list
.def loop1=r0
.def loop2=r1
.def loop=r21
.def temp=r16
.def temp1=r17
.def count=r18
.def fnota=r19
.def dnota=r20
.cseg
.org 0
start: rjmp init
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
reti
init: ldi temp,ramend
out spl,temp
ldi temp,0x08
out ddrb,temp
out portb,temp
ldi temp,0x7f
out portd,temp
ldi temp,0
out ddrd,temp
ldi temp,0x80
out acsr,temp
ldi temp,0x09 ;включаем режим CTC
out tccr1b,temp
stop: ldi temp,0
out tccr1a,temp ;выключаем звук
main: clr count
in temp,pind
button: lsr temp
brcc prog
inc count
cpi count,7
brne button
rjmp stop
;-------------------Выбор мелодии------------------
prog: mov yl,count ;вычисляем адрес,где
ldi zl,low(tabm*2) ;хранится начало мелодии
ldi zh,high(tabm*2)
rcall addw ;к подпрограмме 16-разрядного сложения
lpm xl,z+ ;извлекаем адреса из таблицы
lpm xh,z ;и помещаем в X
;-------------------Воспроизведение мелодии-----------
play: mov zh,xh ;записываем в Z начало мелодии
mov zl,xl
s1: in temp,pind ;читаем содержимое порта D
cpi temp,0x7f ;проверяем на равенство 7f
breq stop ;если равно(кнопки отпущены)
lpm temp,z ;изслекаем код ноты
cpi temp,0xff ;проверяем,не конец ли мелодии
breq play ;если конец,начинаем мелодию сначала
andi temp,0x1f ;выделяем код тона из кода ноты
mov fnota,temp ;записываем в регистр кода тона
lpm temp,z+ ;еще раз берём код ноты
rol temp ;производим четырёх кратный сдвиг кода ноты
rol temp
rol temp
rol temp
andi temp,0x07 ;выделяем код длительности
mov dnota,temp ;помещаем его в регистр длительности
rcall nota ;вызываем подпрограмму воспроизведения ноты
rjmp s1 ;в начало цикла(следующая нота)
;------------------Подпрограмма 16-ти разрядного сложения--------------
addw: push yh
lsl yl ;Умножение первого слагаемого на 2
ldi yh,0 ;Второй байт первого слагаемого=0
add zl,yl ;складываем 2 слогаемых
adc zh,yh
pop yh
ret
;------------------Подпрограмма исполнения одной ноты-------------------
nota: push zh
push zl
push yl
push temp
cpi fnota,0x00 ;проверка не пауза ли
breq nt1 ;если пауза,переходим к задержке
mov yl,fnota ;вычисляем адрес,где хранится
ldi zl,low(tabkd*2) ;коэфициент деления для текущей ноты
ldi zh,high(tabkd*2)
rcall addw
lpm temp,z+ ;извлекаем мл.разряд КД для текущей ноты
lpm temp1,z ;ст. разряд КД
out ocr1ah,temp1 ;записать в ст.часть регистра совпадения
out ocr1al,temp ;записать в мл.часть регистра совпадения
ldi temp,0x40 ;включить звук
out tccr1a,temp
nt1: rcall wait
ldi temp,0
out tccr1a,temp ;выключить звук
ldi dnota,0 ;сбрасываем задержку для паузы между нотами
rcall wait ;пауза между нотами
pop temp
pop yl
pop zl
pop zh
ret
;--------------------Подпрограмма формирования задержки--------------
wait: push zh
push zl
push yh
push yl
mov yl,dnota ;вычисляем адрес,где хранится
ldi zl,low(tabz*2) ;ножный коэфициент задержки
ldi zh,high(tabz*2)
rcall addw ;к подпрограмме 16-разрядного сложения
lpm yl,z+ ;читаем первый байт коэфициента задержки
lpm yh,z ;читаем второй байт коэфициента задержки
clr zl ;обнуляем регистровую пару
clr zh
w1: ldi loop,255 ;пустой внутренний цикл
w2: dec loop
brne w2
adiw r30,1 ;увеличение регистровой пары Z на единицу
cp yl,zl ;проверка младшего разряда
brne w1
cp yh,zh ;проверка старшего разряда
brne w1
pop yl
pop yh
pop zl
pop zh
ret
;----------------Таблица длительности задержек-----------------------
tabz: .dw 128,256,512,1024,2048,4096,8192
;----------------Таблица коэфициента делеия-------------------------
tabkd: .dw 4748,4480,4228,3992,3768,3556,3356,3168,2990,2822,2664,2514
.dw 2374,2240,2114,1996,1884,1778,1678,1584,1495,1411,1332,1257
.dw 1187,1120,1057,998,942,889,839,792
;----------------Таблица начала всех мелодий-------------------------
tabm: .dw mel1*2,mel2*2,mel3*2,mel4*2,mel5*2,mel6*2,mel7*2
;----------------Таблица мелодий-------------------------------------
;в траве сидел кузнечик
mel1: .db 109,104,109,104,109,108,108,96,108,104
.db 108,104,108,109,109,96,109,104,109,104
.db 109,108,108,96,108,104,108,104,108,141
.db 96,109,111,79,79,111,111,112,80,80
.db 112,112,112,111,109,108,109,109,96,109
.db 111,79,79,111,111,112,80,80,112,112
.db 112,111,109,108,141,128,96,255
;песенка крокодила гены
mel2: .db 109,110,141,102,104,105,102,109,110,141
.db 104,105,107,104,109,110,141,104,105,139
.db 109,110,173,96,114,115,146,109,110,112
.db 109,114,115,146,107,109,110,114,112,110
.db 146,109,105,136,107,105,134,128,128,102
.db 105,137,136,128,104,107,139,137,128,105
.db 109,141,139,128,110,109,176,112,108,109
.db 112,144,142,128,107,110,142,141,128,105
.db 109,139,128,173,134,128,128,109,112,144
.db 142,128,107,110,142,141,128,105,109,139
.db 128,173,146,128,96,255
;в лесу родилась елочка
mel3: .db 132,141,141,139,141,137,132,132,132,141
.db 141,142,139,176,128,144,146,146,154,154
.db 153,151,149,144,153,153,151,153,181,128
.db 96,255
;happy births to you
mel4: .db 107,107,141,139,144,143,128,107,107,141
.db 139,146,144,128,107,107,151,148,146,112
.db 111,149,117,117,148,144,146,144,128,255
;с чего начинается родина
mel5: .db 99,175,109,107,106,102,99,144,111,175
.db 96,99,107,107,107,107,102,104,170,96
.db 99,109,109,109,109,104,106,171,96,99
.db 111,109,107,106,102,99,144,111,143,104
.db 114,114,114,114,109,111,176,96,104,116
.db 112,109,107,106,64,73,143,107,131,99
.db 144,80,80,112,111,64,75,173,128,255
;песня из кинофильма "Весёлые ребята"
mel6: .db 105,109,112,149,116,64,80,148,114,64
.db 78,146,112,96,105,105,109,144,111,64
.db 80,145,112,64,81,178,96,117,117,117
.db 149,116,64,82,146,112,64,79,146,144
.db 96,105,105,107,141,108,109,112,110,102
.db 104,137,128,96,105,105,105,137,102,64
.db 73,142,105,107,109,64,75,137,96,105
.db 105,105,137,102,105,142,112,64,82,180
.db 96,116,116,116,148,114,112,142,109,64
.db 78,146,144,96,105,105,107,141,108,109
.db 112,110,102,104,169,96,96,255
;улыбка
mel7: .db 107,104,141,139,102,105,104,102,164,128
.db 104,107,109,109,109,111,114,112,111,109
.db 144,139,128,109,111,144,96,111,109,104
.db 107,105,173,128,111,109,112,107,111,109
.db 109,107,102,104,134,132,128,100,103,107
.db 107,107,107,139,112,100,103,102,102,102
.db 134,102,103,107,105,107,108,108,108,108
.db 107,105,107,108,144,142,128,112,107,110
.db 140,112,105,108,107,107,107,105,140,139
.db 139,112,103,102,103,105,108,107,105,103
.db 128,112,107,110,108,108,108,140,112,105
.db 108,107,107,107,139,112,103,102,103,105
.db 108,107,105,103,105,139,132,128,96,96
.db 96,255
НАЗАД Assembler PIC Си AVR ДАЛЬШЕ