📄 amperage.asm
字号:
;---------------------------
; 电流检测实例
;功能:通过定时器定时从AD上读取电压数据,将电压数据通过
; 数码管显示出来
;---------------------------
ORG 0000H
LJMP START
ORG 0003H
LJMP EXTERN_INT ; 外中断入口
ORG 000BH
LJMP TIMER0_INT
A_BIT EQU 20h ; 数码管个位数存放内存位置
B_BIT EQU 21h ; 数码管十位数存放内存位置
;-----------------------
;进入初始化程序,初始化各个标志位,定时器
;-----------------------
START:
;-----------------------
;分配内存单元
;-----------------------
MOV SP,#050H ; 设置堆栈
MOV R0,#030H ; 设置AD存储单元初始地址
MOV IE,#0FFH ; 打开所有中断
MOV DPTR,#78FFH ; 采集通道首地址,只使用一路AD就可以
MOV R0,#30H
MOV @R0,#00H ; 清除AD采集来的电流
MOV R0,#31H
MOV @R0,#00H ; 清除发送缓存中的数据
MOV R0,#41H
MOV @R0,#00H ; 清除定时器每500毫秒的选择触发位
MOV R1,#042H
MOV @R0,#00H ; 清除定时器计数器
LCALL TIMER1_INIT ; 初始化定时器0和定时器1
;---------------------------
;进入主循环,如果查询到发送标志位就把采集的数据发送出去
;---------------------------
LOOP:
MOV R0,#30H ; 30H是AD转换的地址,把数据采集后存进30H中
MOV A,@R0
MOV R0,#31H ; 将30H中的数据存放到发送缓存中去
MOV @R0,A ; 将AD转换后的数据存储进发送缓存中去
MOV R0,#41H ; 判断定时器是否来索要数据,
MOV A,@R1
JNZ DISPLAY
MOV R0,#41H ; 清除定时器触发标志位
MOV @R1,#00H
SJMP LOOP ; 如果没有,返回循环继续查询标志位
;----------------------------------
;显示子程序
;----------------------------------
DISPLAY:
MOV A,31H ; 将29H中的十六进制数转换成10进制
MOV B,#10 ; 10进制/10=10进制
DIV AB
MOV B_BIT,A ;十位在A
MOV A_BIT,B ;个位在B
MOV DPTR,#NUMTAB ; 指定查表启始地址
MOV R0,#4
DPL1:
MOV R1,#250 ; 显示1000次
DPLOP:
MOV A,A_BIT ; 取个位数
MOVC A,@A+DPTR ; 查个位数的7段代码
MOV P0,A ; 送出个位的7段代码
CLR P2.0 ; 开个位显示
ACALL D1MS ; 显示1ms
SETB P2.0
MOV A,B_BIT ; 取十位数
MOVC A,@A+DPTR ; 查十位数的7段代码
MOV P0,A ; 送出十位的7段代码
CLR P2.1 ; 开十位显示
ACALL D1MS ;显示1ms
SETB P2.1
DJNZ R1,DPLOP ;100次没完循环
DJNZ R0,DPL1 ;4个100次没完循环
RET
;1MS延时
D1MS:
MOV R7,#80
DJNZ R7,$
RET
;实验板上的7段数码管0~9数字的共阴显示代码
NUMTAB: DB 03FH,06H,5BH,4FH,66H,06DH,07DH,07H,07FH,06FH
;-----------------------
; 初始化定时器,定时器0作为定时的触发
;-----------------------
TIMER1_INIT:
ANL TMOD,#0FH ; 设置定时器1为方式2
ORL TMOD,#10H
MOV TMOD,#21H ; 定时器0工作在方式1
MOV PCON,#080H
CLR TR1 ; 禁止定时器1
SETB EA ; 使能全部定时器
SETB ET1 ; 允许定时器1中断
SETB ET0 ; 允许定时器0中断
SETB PT0 ; 定时器0中断优于其余中断
CLR TF1 ; 清除定时器1中断标志位
MOV TL0,#00H
MOV TH0,#01FH ; 定时器0中断发生时间为62.5毫秒
MOV TH1,#0FFH ; 定时器1波特率的设定为57600bps
SETB TR0 ; 使能定时器0
CLR TF0 ; 清除中断标志位
SETB TR1 ; 使能定时器1
RET
;-----------------------
; 进入定时器中断,每500毫秒设置一次标志位
;-----------------------
TIMER0_INT:
PUSH ACC ; 累加器入栈
PUSH PSW ; 程序状态字入栈
MOV PSW,#10H ; 更换寄存器区域
CLR TF0
CLR TR0
MOV TL0,#00H
MOV TH0,#01FH ; 定时器0中断发生时间为6
CLR TF0 ; 清除溢出中断位
MOV R1,#042H
INC @R1 ; 增加计数器的值,到8为止,这样达到500毫秒
CJNE @R1,#08H,TIMER0_READY
MOV @R1,#00H ; 清除计数器的值
MOV R1,#041H ; 设置标志位,每500毫秒采集一次数据
MOV @R1,#01H
TIMER0_READY:
SETB TR0 ; 使能定时器0
POP PSW ; 程序状态字出栈
POP ACC ; 累加器出栈
RETI
;-----------------------
; 进入外部中断,每进入一次读取ADC的值
;-----------------------
EXTERN_INT:
PUSH ACC ; 累加器入栈
PUSH PSW ; 程序状态字入栈
MOV PSW,#018H ; 更换寄存器区域
MOV DPTR,#78FFH ; AD转换器首地址
MOVX A,@DPTR
MOV R1,#030H ; 存储AD转换器的数据的地址
MOV @R1,A
POP PSW ; 程序状态字出栈
POP ACC ; 累加器出栈
RETI
END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -