|
;******************; ; 定時(shí)器程序 ; ; 采用89c2051 ; ;******************; ; ;****************** ; 偽定義 ; ;****************** SL EQU 30H ;SL存放秒的個(gè)位數(shù) SH EQU 31H ;SH存放秒的十位數(shù) ML EQU 32H ;ML存放分的個(gè)位數(shù) MH EQU 33H ;MH存放分的十位數(shù) HL EQU 34H ;HL存放時(shí)的個(gè)位數(shù) HH EQU 35H ;HH存放時(shí)的十位數(shù) ; L0 EQU 36H ;L0~L3:顯示數(shù)據(jù)存儲(chǔ)器 L1 EQU 37H L2 EQU 38H L3 EQU 39H DSPLYP EQU 3AH ;顯示數(shù)據(jù)指針(DISPLAY-POINT) PLYTS EQU 3BH ;顯示次數(shù)計(jì)數(shù)器(DISPLAY-TIMES) ; LPLMOD BIT 39H ;低兩位顯示方式(LOW-PLAY-MOD) HPLMOD BIT 3AH ;高兩位顯示方式(HIGH-PLAY-MOD) BRIGHT BIT 3BH ;DISPLAY子程序參數(shù):亮滅指示位 ; TCOUNT EQU 3CH ;時(shí)間計(jì)數(shù)器(TIME-COUNT) ; ADDRES EQU 3DH ;加1子程序參數(shù) MAX EQU 3EH ;加1子程序參數(shù) IFDEC BIT 20H ;BCD加法子程序參數(shù) ; R_MOD EQU 3FH ;響鈴方式參數(shù) ; LED4 BIT 30H ;發(fā)光管狀態(tài)位 BELL BIT P1.7 ;蜂鳴器 SWITCH BIT P3.7 ;繼電器 FKEY BIT P3.0 ;功能鍵 (S1) MKEY BIT P3.1 ;修改鍵 (S2) ; WORKIN BIT 38H ;工作狀態(tài)指示位 ; ;****************** ; 中斷入口 ; ;****************** ORG 0000H START: LJMP MAIN ; 0000H 引向主程序 LJMP ERR ; 0003H NOP NOP LJMP ERR ; 引向出錯(cuò)處理程序 LJMP PGT0 ; 000BH 引向中斷處理程序PGT0 NOP NOP LJMP ERR ; 引向出錯(cuò)處理程序 LJMP ERR ; 0013H INT1 NOP NOP LJMP ERR LJMP ERR ; 001BH T1 NOP NOP LJMP ERR LJMP ERR ; 0023H NOP NOP LJMP ERR LJMP ERR ; 002BH NOP NOP ; ;************ ; 主程序 ; ;************ MAIN: MOV IE, #00H ;關(guān)中斷 MOV SP, #57H ;設(shè)置堆棧指針 MOV PSW, #00H ;選用寄存器組0 MOV TMOD, #11H ;設(shè)定中斷工作方式為T0和T1 ; MOV A, 56H CJNE A, #0AAH, CSTART ;判上電復(fù)位標(biāo)志,無標(biāo)志轉(zhuǎn)冷啟動(dòng) MOV A, 57H CJNE A, #55H, CSTART ; 無標(biāo)志轉(zhuǎn)冷啟動(dòng) AJMP HSTART ;有上電復(fù)位標(biāo)志轉(zhuǎn)熱啟動(dòng) NOP NOP LJMP ERR ;軟件陷阱,引向出錯(cuò)處理程序 CSTART: MOV P1, #0FFH ;冷啟動(dòng),全面初始化 MOV P3, #0FFH MOV TCON, #00H ;計(jì)時(shí)停止 MOV TL0, #0B0H ;賦中斷T0初值 MOV TH0, #3CH MOV TCOUNT, #0AH ;賦定時(shí)器初值 MOV R5, #00H ;R5為一空單元(備用) MOV R4, #00H ; R4 為工作模式選擇寄存器 MOV SL, #00H ;定時(shí)單元清零 MOV SH, #00H ;秒 MOV ML, #00H ; MOV MH, #00H ;分 MOV HL, #00H ; MOV HH, #00H ;時(shí) MOV PLYTS, #64H ;賦顯示次數(shù)初值為100次 MOV DSPLYP, #L0 ;顯示指針指向顯存單元 MOV L0, #0AH ;送顯示數(shù)據(jù)"-----" MOV L1, #0AH MOV L2, #0AH MOV L3, #04H SETB LED4 ;LED4為數(shù)碼管之間的發(fā)光二極管 SETB LPLMOD ;設(shè)定顯示方式為閃爍 SETB HPLMOD ; SETB BRIGHT ;允許顯示 CLR WORKIN ;清工作標(biāo)志 , 待命 AJMP SETUP ;轉(zhuǎn)開始工作 NOP NOP LJMP ERR ;軟件陷阱 HSTART: MOV SCON, #00H ; 有上電標(biāo)志,熱啟動(dòng),清串行口控制寄存器 MOV IP, #00H ; 清中斷優(yōu)先控制寄存器 SETB FKEY ;重設(shè)按鍵 SETB MKEY SETB EA ;開中斷 AJMP BEGIN ;轉(zhuǎn)向繼續(xù)工作 NOP NOP LJMP ERR ;軟件陷阱 SETUP: SETB EA ;開中斷 ; MAIN1: ACALL DISPLY ;調(diào)用顯示 JB FKEY, JUDGE ;按鍵掃描 ACALL KEYDLY ;延時(shí)消抖動(dòng) JB FKEY, JUDGE ;無鍵按下轉(zhuǎn)向判斷是否到點(diǎn) CLR ET0 ;功能鍵被按下,則 CLR TR0 ;暫停計(jì)時(shí) ACALL MENU ; 調(diào)用菜單設(shè)置程序 BEGIN: SETB WORKIN ;置工作標(biāo)志位,開始工作 SETB ET0 ;開中斷 SETB TR0 ;開始計(jì)時(shí) MOV A, R4 ;移入工作模式選擇 RL A ;指針放大 MOV DPTR, #M_TAB JMP @A+DPTR ;根據(jù)工作模式跳轉(zhuǎn)到相應(yīng)程序段 M_TAB: AJMP WORK1 AJMP WORK2 AJMP WORK3 AJMP WORK4 NOP NOP LJMP ERR ;軟件陷阱 WORK1: ; WORK2: CLR SWITCH ;工作方式1和2:開繼電器 AJMP MAIN2 NOP NOP LJMP ERR ;軟件陷阱 WORK3: ; WORK4: SETB SWITCH ;工作方式3和4:不開繼電器 MAIN2: CLR BELL ;蜂鳴器短鳴一聲,以示開始工作 ACALL DL05S SETB BELL JUDGE: JNB WORKIN, MAIN1 ;判斷是否在定時(shí)之中 MOV A, SL ;判斷秒是否為零 JNZ MAIN1 MOV A, SH ;判斷秒是否為零 JNZ MAIN1 MOV A, ML ;判斷分是否為零 JNZ MAIN1 MOV A, MH ;判斷分是否為零 JNZ MAIN1 MOV A, HL ;判斷時(shí)是否為零 JNZ MAIN1 MOV A, HH ;判斷時(shí)是否為零 JNZ MAIN1 ;若時(shí)分秒全為零則 CLR ET0 ; 停止計(jì)時(shí) CLR TR0 ; ACALL ACTION ; 調(diào)用到點(diǎn)工作子程序 AJMP MAIN ; 返回 NOP NOP LJMP ERR ;軟件陷阱 ; ;****************** ; 倒計(jì)時(shí)程序 ; ;****************** PGT0: CLR EA ;關(guān)中斷 PUSH ACC ;保護(hù)現(xiàn)場 PUSH PSW PUSH DPL PUSH DPH MOV PSW, #08H ;選用寄存器組1 CLR TR0 ;暫停計(jì)時(shí) MOV A,#0B7H ;中斷同步修正 ADD A,TL0 MOV TL0,A MOV A,#3CH ADD A,TH0 MOV TH0,A SETB TR0 ;恢復(fù)計(jì)時(shí) DEC TCOUNT ;定時(shí)器T0每50 000毫秒溢出一次,則 MOV A, TCOUNT ; 溢出10次為0.5秒 JNZ OUTT0 ;判斷是否到半秒 MOV TCOUNT, #0AH ; CPL LED4 ; 若到半秒LED取反 JNB LED4, OUTT0 ;LED每閃爍一次是一秒 MOV R0, #SH ;移入秒位的地址 SETB IFDEC ;BCD子程序參數(shù),使其做減法 ACALL ADDBCD ;調(diào)用BCD子程序, 秒減1 CJNE R3, #99H, OUTT0 ;判斷秒要否借位 MOV SH, #05H ;要借位則 MOV SL, #09H ; 送數(shù)據(jù)59(否則顯示99) MOV R0, #MH ;移入分位的地址 ACALL ADDBCD ;分減1 CJNE R3, #99H, OUTT0 ;判斷分要否借位 MOV MH, #05H MOV ML, #09H MOV R0, #HH ACALL ADDBCD OUTT0: POP DPH ;恢復(fù)現(xiàn)場 POP DPL POP PSW POP ACC SETB EA RETI ;中斷返回 NOP NOP LJMP ERR ;軟件陷阱 ; ; ;************************** ; BCD子程序(加1或減1 ) ; ;************************** ADDBCD: MOV A, @R0 ;移入被操作數(shù)的高位 DEC R0 ;指針減一 SWAP A ORL A, @R0 ;移入被操作數(shù)的低位 MOV B, #01H ;B寄存器送立即數(shù)#01H MOV C, IFDEC ;若 減法標(biāo)志位為1,則 MOV B.3, C ; MOV B.4, C ; B寄存器的值被改為#99H MOV B.7, C ; ADD A, B ; 對(duì)一個(gè)壓縮的BCD碼加#99H等于對(duì)其減一 DA A ;BCD碼調(diào)整 MOV R3, A ;暫存結(jié)果 ANL A, #0FH ;取低位碼 MOV @R0, A ;存數(shù) MOV A, R3 ;取回結(jié)果 INC R0 ;指針加一 SWAP A ;交換 ANL A, #0FH ;取結(jié)果數(shù)的高位 MOV @R0, A ;存數(shù) RET NOP NOP LJMP ERR ;軟件陷阱 ; ;************** ; 加1程序 ; ;************** ADDONE: MOV R0, ADDRES ;移入被加數(shù)單元的地址 CLR IFDEC ;設(shè)定BCD子程序做加法 ACALL ADDBCD ;調(diào)用BCD子程序 CLR C ;判斷被加數(shù)是否大于 MOV A, R3 ;最大值"MAX" CJNE A, MAX, JGOVER JGOVER: JC ENDADO CLR A ;若大于"MAX",則清零 MOV @R0, A DEC R0 MOV @R0, A ENDADO: RET NOP NOP LJMP ERR ;軟件陷阱 ; ;****************** ; 調(diào)時(shí)快進(jìn)程序 ; ;****************** QUICK: CLR LPLMOD ;設(shè)定顯示方式不閃爍 CLR HPLMOD ACALL ADDONE ;調(diào)用加1子程序 MOV L0, R4 ;將工作模式選擇數(shù)移入顯存 INC L0 ;加1轉(zhuǎn)化成顯示值 ACALL KEYDLY ;延時(shí) ACALL DL100 JNB MKEY, QUICK ;判斷鍵是否松開 SETB LPLMOD ;若松開則恢復(fù)閃爍顯示方式 CJNE R6, #02H, ENDQUK SETB HPLMOD CLR LPLMOD ENDQUK: RET NOP NOP LJMP ERR ;軟件陷阱 ; ; ;****************** ; 功能菜單程序 ; ;****************** MENU: MOV R6, #00H ; 初始化; R6 計(jì)功能鍵按鍵次數(shù) MOV ADDRES, #05H ; 將 R5 的地址送入,以便于改變 R4 的值 MOV MAX, #04H ; 定義工作模式選擇寄存器R4 的最大值 MOV DSPLYP, #L0 ;定義顯示指針指向顯存 SETB LPLMOD ;設(shè)定低兩位數(shù)閃爍 CLR HPLMOD MOV L0, R4 ;送顯示數(shù)據(jù)"F-0X" INC L0 MOV L1, #00H MOV L2, #0BH MOV L3, #00H SETB LED4 ; WAITFK: ACALL DISPLY ;等待F鍵釋放 JNB FKEY, WAITFK MENU1: ACALL DISPLY JB MKEY, JGFKEY ;M鍵掃描 ACALL KEYDLY ;延時(shí)消抖動(dòng) JB MKEY, JGFKEY ; 未按下則轉(zhuǎn)F鍵掃描 CJNE R6, #00H, NEXT1 ; MOV SL, #00H ;若中途改變定時(shí)方式,則清除原計(jì)時(shí)數(shù)據(jù) MOV SH, #00H MOV ML, #00H MOV MH, #00H MOV HL, #00H MOV HH, #00H NEXT1: MOV R2, #00H ;R2用于判斷按鍵時(shí)間是否超過0.5秒 NEXT2: ACALL ADDONE ;調(diào)用加1程序 MOV L0, R4 ;移入工作方式選擇數(shù) INC L0 ; WAITMK: ACALL DISPLY ;等待M鍵釋放 INC R2 ;R2自增一 CLR C CJNE R2, #0C8H, JGQUIC ;若R2大于等于200則調(diào)用快進(jìn)子程序 JGQUIC: JC WATMK1 ACALL QUICK WATMK1: JNB MKEY, WAITMK ; R2小于200則等待M鍵釋放 ; JGFKEY: JB FKEY, MENU1 ;功能(F)鍵掃描 ACALL KEYDLY ;延時(shí)消抖動(dòng) JB FKEY, MENU1 ;鍵未按下則轉(zhuǎn)修改(M)鍵掃描 INC R6 ;F鍵按鍵次數(shù)加1 MOV A, R6 ;移入按鍵次數(shù) RL A ;指針放大 MOV DPTR, #FUNTAB JMP @A+DPTR ;根據(jù)按鍵次數(shù)跳轉(zhuǎn)到相應(yīng)的程序段 FUNTAB: AJMP WAITFK AJMP SETLOW AJMP SETHI AJMP ENDMEN NOP NOP AJMP ENDMEN ;STWKMD: ;工作模式設(shè)定,不需另外改變菜單 ; SETLOW: MOV MAX, #60H ;設(shè)置低位(秒位或分位) MOV A, R4 ;移入工作模式選擇數(shù) RL A ;指針放大 MOV DPTR, #FTAB1 JMP @A+DPTR ;根據(jù)工作模式選擇數(shù)跳轉(zhuǎn)到相應(yīng)的程序段 FTAB1: AJMP SETSS AJMP SETM60 AJMP SETSS AJMP SETM60 NOP NOP AJMP WAITFK SETSS: MOV DSPLYP, #SL ;設(shè)定顯示區(qū)域?yàn)?/FONT>MM:SS MOV ADDRES, #SH AJMP WAITFK SETM60: MOV DSPLYP, #ML ; 設(shè)定顯示區(qū)域?yàn)?/FONT>HH:MM MOV ADDRES, #MH AJMP WAITFK ; SETHI: CLR LPLMOD ;設(shè)置高位(分位或時(shí)位) SETB HPLMOD ;高兩位數(shù)碼管閃爍 MOV MAX, #31H ;最大數(shù)為30 MOV A, R4 ;移入工作模式選擇數(shù) RL A ;指針放大 MOV DPTR, #FTAB2 ;移入表首地址 JMP @A+DPTR ;根據(jù)工作模式選擇數(shù)跳轉(zhuǎn)到相應(yīng)的程序段 FTAB2: AJMP SETM30 AJMP SETHH AJMP SETM30 AJMP SETHH NOP NOP AJMP WAITFK ;返回等待鍵釋放 SETM30: MOV ADDRES, #MH ;移入分位的地址 AJMP WAITFK ;轉(zhuǎn)向等待鍵釋放 SETHH: MOV ADDRES, #HH ;移入時(shí)位的地址 AJMP WAITFK ;轉(zhuǎn)向等待鍵釋放 ; ENDMEN: CLR HPLMOD ;恢復(fù)不閃爍顯示方式 RET NOP NOP LJMP ERR ;軟件陷阱 ; ;**************** ; 到點(diǎn)工作程序 ; ;**************** ACTION: MOV L0, R4 ;移入工作模式選擇數(shù)
|