📄 memory_game.asm
字号:
.include "riscmcu.inc".def temp = r16.def times = r17.def num = r18.def stack = r19.def counter = r20.def life = r22.def level = r23.def temp2 = r24.cseg rjmp reset reti retireset: ldi counter,5 ser temp out ddrb,temp ; Port B direction as OUTPUT out ddrd,temp ; Port D direction as OUTPUT out portc,temp out portd,temp ldi temp,1 out tccr0,temp ; set clock as timer clock source ldi temp,$0F out ddrc,temp ; PinC[3..0] output, [7..4] inputstart: ldi life,3 ldi level,1 clt ; T = 0, start with correct rcall getinput ; hit any key to start the game rcall showlife out portB,level ; output level to display rcall holding ; release? nextlevel: rcall delay ; wait a while before the game is started rcall showled ; show the LEDs and save it in buffernlife: rcall check ; get input and check brts wrong rcall greenled inc level ; when win, level <- level + 1 out portB,level ; output level to display rjmp nextlevelwrong: rcall redled rcall delay dec life rcall showlife out portb,level rcall delay cpi life,0 breq start rcall playback clt rjmp nlife;*******************************************; show lifeshowlife: mov temp,life sbr temp,$f0 out portb,temp rcall delay rcall delay ret;*******************************************; on red ledsredled: clr temp out portc,temp rcall delay ser temp out portc,temp ret;*******************************************; on green ledgreenled: cbi portd,7 rcall delay sbi portd,7 ret;*******************************************; play back the last sequence when wrongplayback: rcall initw10: ld temp,Z+ out portC,temp rcall delay ser temp ; OFF out portC,temp ldi counter,1 rcall delay dec times brne w10 ret ;*******************************************; Show sequence of LEDs (base on times), save in buffershowled: rcall initsnext: rcall random ; return in NUM st Z+,num out portC,num ; display the LED rcall delay ser temp ; OFF out portC,temp ldi counter,1 rcall delay dec times brne snext ret;*******************************************; wait for input and check; return T = 0 when corrert, T = 1 when wrongcheck: rcall init nextkey: rcall holding sei rcall getinput ; return in NUM cli ld temp,Z+ cpse num,temp set ; Set T flag if one key is wrong rcall holding rcall sdelay dec times brne nextkey ret;*******************************************; still holding the key ?holding: in temp,pinc cbr temp,$0F cpi temp,$F0 brne holding ret;*******************************************; getinputgetinput:g15: in num,pinc cbr num,$0F ; clear lower nibble cpi num,$F0 breq g15 rcall sdelay in temp,pinc cbr temp,$0F cp temp,num brne g15 swap num ret ;*******************************************; 1. Load level to times; 2. ZP point to start of bufferinit: mov times,level ; times <- level ldi ZP,buffer ; ZP <- buffer ret ;*******************************************; Generate Random Num, return in NUMrandom: in num,tcnt0ran: cpi num,4 brlo rnext subi num,4 rjmp ranrnext: cpi num,0 brne r10 ldi num,0b1110 rjmp rendr10: cpi num,1 brne r20 ldi num,0b1101 rjmp rendr20: cpi num,2 brne r30 ldi num,0b1011 rjmp rendr30: ldi num,0b0111rend: in temp,tcnt0 ror temp ror temp out tcnt0,temp ret;******************************************* delay: mov stack,ZPdel: ldi ZP,count ld temp,Z dec temp st Z,temp brne del ldi ZP,count+1 ld temp,Z dec temp st Z,temp brne del dec counter brne del ldi counter,5 mov ZP,stack retsdelay: clr tempsd5: dec temp brne sd5 ret;*******************************************.dsegcount: .byte 2buffer: .byte 20
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -