边坡种植池施工方案:那位老兄能给段秒计时器的汇编程序吗?

来源:百度文库 编辑:杭州交通信息网 时间:2024/04/28 21:06:46
小弟需要一段由外部脉冲控制的从0.01--9.99的秒计时器的汇编程序,请
老兄帮忙好吗,我的单片机是MCS-51型的(AT89S51)。
是由外部脉冲触发

老大,能不能说清楚点啊,是计算外部脉冲还是?由外部脉冲触发?
给你个15秒的定时器是可以设定的两位数码管显示你可以修改一下应该就可以达到你的要求
;可预制的倒计时钟,p35个位,p34十位,p32确定
;***************************************************************************
;* E-mail:sxj1974@163.com (51c51 test web) 51测试网,自学单片机的网站 *
;* Create by :石学军 www.51c51.com www.8951.com 更多例程请登陆网站 *
;***************************************************************************
keyok bit 00h ;是否有键按下的标志
startrun bit 01h ;是否开始运行
value equ 21h ;秒计时值
setval equ 22h ;设置的数值
counter equ 23h ;用于显示的计数器
count equ 24h ;秒计数器
keyval equ 25h ;按键寄存器
dispbuf equ 5eh ;显示缓冲区
first bit p2.5 ;第一个数码管控制
second bit p2.6 ;第二个数码管控制
tmrvar equ 60110 ;定时器的初值65536-5000
hidden equ 0ffh ;显示器的消隐
org 0000h
jmp start
org 1*8+3 ;time0中断入口
jmp int_t0 ;到定时器t0中断服务程序的入口
start:
mov sp,#5fh ; 设置堆栈
mov p1,#0ffh ; 所有led熄灭
mov setval,#59 ;初值59
mov value,setval ;开始不运行,按键后运行
clr startrun
clr keyok ;清除有键按下的标志
mov tmod,#01h
mov th0,#HIGH(TMRVAR) ;取tirvar的高8位
MOV TL0,#LOW(TMRVAR) ; 取tirvar的低8位
SETB ET0 ; 开t0中断
SETB TR0 ;定时器开始运行
; CLR SEC
SETB EA ; 开总中断
LOOP:CALL KEY ;调用键盘程序
JB KEYOK,KEYPROC;如果有键盘按下则转键盘处理
NEXT:MOV A,VALUE ;获得秒的数值
MOV B,#10
DIV AB ;二进制转10进制10位个位分别送显示缓冲
NEXT1:MOV DISPBUF,A ;
MOV DISPBUF+1,B ;个位送显示缓冲
JMP LOOP
KEYPROC:MOV A,KEYVAL ;取得键值
JZ KEYRUN ;如果为0转keyrun
DEC A
JZ KEYSTOP ;如果键值1 转stop
DEC A

JZ KEYLEFT ;如果键值2转left
JMP KEYRIGHT ;如果为3转right
KEYRUN:
SETB STARTRUN ;将开始运行的标志送1
JMP LOOP
KEYSTOP:
CLR STARTRUN ;开始运行位送0
JMP LOOP
KEYLEFT: ;键盘处理,10位加1并在0-5循环
CLR STARTRUN ;先停止秒
MOV A,SETVAL ;取设置位
ADD A,#10 ;加10
CJNE A,#60,LEFT0 ;到60了么?
MOV A,#0 ;是则清零
JMP LEFT2 ;转left2
LEFT0:JNC LEFT1 ;比60大么, 是则转left1
JMP LEFT2 ; 转left2
LEFT1:SUBB A,#60 ;减60
LEFT2:MOV SETVAL,A ;处理后的a送回setval
MOV VALUE,SETVAL ; 送显示
JMP LOOP
KEYRIGHT: ; 键盘处理,10位加1并在0-5循环
CLR STARTRUN ;先停止秒
INC DISPBUF+1 ;显示器的低位加1
MOV A,DISPBUF+1 ; 送到a
CJNE A,#10,REFT0 ;与10比较不等于则转移
MOV DISPBUF+1,#0 ; 等于10则送0
REFT0:MOV A,DISPBUF ; 取出显示缓冲的高位
MOV B,#10
MUL AB ;乘10
ADD A,DISPBUF+1 ;加低位
MOV SETVAL,A ;送到setval暂存
MOV VALUE,SETVAL ;送显示
JMP LOOP
KEY: ORL P3,#00111100B ;键盘口先送1
CLR KEYOK ;清key标志
MOV A,P3 ;取p3的值
ORL A,#11000011B ;把无关的4位置位
CPL A ;取反a
JZ KEY_RET ;没有按则所有位都是1 取反则为0
CALL DELAY

MOV A,P3 ;再读p3的值
ORL A,#11000011B
CPL A
JZ KEY_RET
SETB KEYOK ;确实有按下
JNB ACC.2,KEY_1 ;s1没有按转key1
MOV KEYVAL,#0 ;如按下则值为0
JMP KEY_RET
KEY_1:JNB ACC.3,KEY_2 ;s1没有按转key2
MOV KEYVAL,#1 ;如按下则值为1
JMP KEY_RET
KEY_2:JNB ACC.4,KEY_3
MOV KEYVAL,#2
JMP KEY_RET
KEY_3:MOV KEYVAL,#3
KEY_RET:
MOV A,P3
ORL A,#11000011B
CPL A
JNZ KEY_RET ;等按键释放
RET
DELAY: mov r5,#2 ;延时20MS
d1:mov r6,#2

D2:djnz r6,d2
djnz r5,d1
ret

INT_T0: ;定时器t0的中断响应
PUSH ACC
PUSH PSW ;压堆栈
MOV TH0,#HIGH(TMRVAR)
MOV TL0,#LOW(TMRVAR)
INC COUNT ;软件计数器加1
MOV A,COUNT ;
CJNE A,#200,INT_N2
MOV COUNT,#0 ;到了200清除
INT_N1:JNB STARTRUN,INT_N2 ; 停止运转,转
DEC VALUE ;计数器减1
MOV A,VALUE
JNZ INT_N2 ; 不为0则转
MOV VALUE,SETVAL ; 否则再置初值
INT_N2:
SETB FIRST
SETB SECOND ;关显示
MOV A,#DISPBUF ; 显示缓冲的首地址
ADD A,COUNTER
MOV R0,A
MOV A,@R0 ;根据计数器的值取相应缓冲的值
MOV DPTR ,#DISPTAB ;字型表的首地址
MOVC A,@A+DPTR
MOV P0,A ; 送显示
MOV A,COUNTER ;取计数器的值
JZ DISPFIRST ; 如果为0则显示第一位
CLR SECOND ; 否则显示第二位
AJMP DISPNEXT
DISPFIRST:
CLR FIRST ;显示第一位
DISPNEXT:
INC COUNTER ;计数器加1
MOV A,COUNTER
DEC A
DEC A ;如果为2则回0
JZ RSTCOUNT
AJMP DISPEXIT
RSTCOUNT:
MOV COUNTER,#0 ;计数器的值只能为0或者1
DISPEXIT:
POP PSW
POP ACC
RETI
DISPTAB:DB 28H,7EH,0A2H,62H,74H,61H,21H,7AH,20H,60H

END