作者:未知 来源:89s52.cn
; *************************************
; * 单键遥控码学习控制器 *
; *************************************
;
;**********************************************************************
;* *
;* P1.0 1 40 VCC *
;* P1.1 2 39 P0.0 *
;* P1.2 3 38 P0.1 *
;* P1.3 4 37 P0.2 *
;* P1.4 5 36 P0.3 *
;* P1.5 6 35 P0.4 *
;* STUDYLAMP P1.6 7 34 P0.5 *
;* LAMP P1.7 8 33 P0.6 *
;* RST 9 32 P0.7 *
;* RXD P3.0 10 MCS-51 31 EA VDD *
;* TXD P3.1 11 30 ALE *
;* STUDYKEY INT0 P3.2 12 29 PSEN *
;* INT1 P3.3 13 28 P2.7 *
;* REMOTEIN T0 P3.4 14 27 P2.6 *
;* REMOTEOUT T1 P3.5 15 26 P2.5 *
;* WR P3.6 16 25 P2.4 *
;* RD P3.7 17 24 P2.3 *
;* XTAL2 18 23 P2.2 *
;* XTAL1 19 22 P2.1 *
;* VSS 20 21 P2.0 *
;* *
;**********************************************************************
;
SPBASE EQU 70H ;堆栈基址
IEVAL EQU 00H ;关所有中断
MEMBASE EQU 08H ;工作寄存器基址
MEMS EQU 67H ;工作寄存器个数
;
BITNMB EQU 08H ;一个字节包含八个位
;
KEYFUNFLAG EQU 80H ; 键功能索引
KEYFUNNMB EQU 81H ;键功能号
KEYFUNRW EQU 82H ;遥控信号读写标志
READFLAG EQU 88H ;读标记
WITERFLAG EQU 99H ;写标记
;
TMPHADDR EQU 08H ;读入高电平存放首址
TMPLADDR EQU 90H ;读入低电平存放首址
READTIME EQU 00H ;读入数据指令时间
; LOWH EQU R4 ;起始位存放高地址
; LOWL EQU R5 ;起始位存放低地址
STUDYLAMP EQU P1.6 ;学习指示灯
LAMP EQU P1.7 ;未定义指示灯
STUDYKEY EQU P3.2 ;学习键
;
REMOTEIN EQU P3.4 ;遥控输入
REMOTEOUT EQU P3.5 ;遥控输出
DELAYCONUT EQU 30H ;延时值
DELAYCONUT0 EQU 0FFH ;延时值
T1COUNT EQU 0F3H ;T1计数初值
TMODVAL EQU 22H ;计数模式控制字
TCONVAL EQU 41H ;计数控制寄存器值
PCONVAL EQU 00H ;电源控制寄存器值
T2CONVAL EQU 00H ;T2控制寄存器值
SCONVAL EQU 0F8H ;串口控制寄存器值
IPVAL EQU 01H ;中断优先级控制值
;
;
;*************************************
;* *
;* 主程序和中断程序入口 *
;* *
;*************************************
ORG 0000H ;程序执行开始地址
AJMP START ;跳至START执行
ORG 0003H ;外中断0中断入口地址
AJMP INTEX0 ;跳至INTEX0中断服务程序
ORG 000BH ;定时器T0中断入口地址
RETI ;中断返回(不开中断)
ORG 0013H ;外中断1中断入口地址
RETI ;中断返回(不开中断)
ORG 001BH ;定时器T1中断入口地址
AJMP INTT1 ;跳至INTT1中断服务程序
ORG 0023H ;串行口中断入口地址
RETI ;中断返回(不开中断)
ORG 002BH ;定时器T2中断入口地址
RETI ;中断返回(不开中断)
;
;*************************************
;* *
;* 初始化程序中的各变量 *
;* *
;*************************************
CLEARMEMIO: CLR A ;A清0
DEC A ;A为#FFH
MOV P0,A ;P0口置1
MOV P3,A ;P3口置1
MOV P1,A ;P1口置1
CLR A ;清A(为0)
MOV P2,A ;P2口为0
CLR STUDYLAMP ;关学习灯
CLR LAMP ;关操作灯
CLR REMOTEOUT ;关遥控码输出
SETB REMOTEIN ;遥控接收为输入状态
MOV R0,#MEMBASE ;清工作寄存器,从08H开始
MOV R1,#MEMS ;清内存个数(为103个)
CLEARMEM: MOV @R0,A ;清0开始
INC R0 ;地址加1
DJNZ R1,CLEARMEM ;未清完转CLEARMEM继续
; MOV R0,#KEYFUNRW
; MOV @R0,#READFLAG
MOV SP,#SPBASE ;设堆栈基址(70H)
MOV IE,#IEVAL ;关所有中断
MOV IP,#IPVAL ;置优先级
MOV TMOD,#TMODVAL ;置计数器模式(8位自动重装初值模式)
MOV PCON,#PCONVAL ;波特率不加倍
MOV SCON,#SCONVAL ;串口中断不开
MOV TH1,#T1COUNT ;T1定时器初值(定时值为13微秒)
MOV TL1,#T1COUNT ; T1定时器初值
SETB EX0 ;允许外中断0中断
SETB EA ;开总中断允许
RET ;子程序结束
;
;*************************************
;* *
;* 主 程 序 *
;* *
;*************************************
START: LCALL CLEARMEMIO ;调用上电初始化子程序
; 主体程序
MAIN: LCALL KEYWORK ;调用读键子程序
LJMP MAIN ;跳回MAIN循环
NOP ;PC值出错处理
NOP ;空操作
NOP ;
LJMP START ;重新初始化
;
;*************************************
;* *
;* T1中断服务程序 *
;* *
;*************************************
INTT1: CPL REMOTEOUT ;40kHZ方波输出(红外线调制波)
RETI ;中断返回
;
;*************************************
;* *
;* 载波合成 *
;* *
;*************************************
REMOTETX: MOV R0,#TMPHADDR ;取遥控码高电平存放首址
MOV R1,#TMPLADDR ;取遥控码低电平存放首址
SETB LAMP ;开操作灯
MOV A,R4 ;起始位高8位放入A
MOV R3,A ;放入R3暂存
JZ LOWBACK ;高8位为0转LOWBACK处理低8位
CLR A ;高8位非0处理
DEC A ;A为#FFH
LOWBACKTMP: MOV R2,A ;起始位复原,R2赋初值
LOWBACKTMP0: SETB TR1 ;开启T1
SETB ET1 ;允许T1中断
NOP ;用空操作延时
NOP
NOP
NOP
NOP
NOP
DJNZ R2,LOWBACKTMP0 ;计数值每减1循环时间为约21微秒
DJNZ R3,LOWBACKTMP ;高8位计数值不为0转LOWBACKTMP
LOWBACK: MOV A,R5 ;起始位低8位处理
MOV R2,A ; 起始位低8位数放入R2暂存
LOWBACKTMP1: SETB TR1 ; 开启T1
SETB ET1 ; 允许T1中断
NOP ;用空操作延时
NOP
NOP
NOP
NOP
NOP
DJNZ R2,LOWBACKTMP1 ;低8位计数值不为0转LOWBACKTMP1
TMP0: MOV A,@R0 ;高电平处理开始,取高电平数据
MOV R2,A ;放入R2
TMP1: CLR TR1 ;关闭T1
CLR ET1 ;关闭T1中断允许(关40KHZ红外线)
CLR REMOTEOUT ;关遥控输出
NOP ;空操作延时
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
DJNZ R2,TMP1 ;R2每减1循环时间约为21微秒
INC R0 ;指向下一高电平数据地址
TMPP: MOV A,@R1 ;取低电平数据
MOV R2,A ;放入R2
TMP2: SETB TR1 ;低电平处理,开定时器T1
SETB ET1 ;开T1中断
NOP ;空操作延时
NOP
NOP
NOP
NOP
NOP
DJNZ R2,TMP2 ;减1不为0转TMP2循环(周期为21微秒)
INC R1 ;指向下一低电平数据
MOV A,@R1 ;取数据
JZ OUT ;为0转OUT退出
AJMP TMP0 ;不为0转TMP0执行
OUT: CLR TR1 ;退出程序,关T1
CLR ET1 ;关T1中断
CLR LAMP ;关操作灯
CLR REMOTEOUT ;关遥控输出
RET ;返回
;
;*************************************
;* 遥控数据读取 INT0中断程序 *
;* 高电平存TMPHADDR为首址RAM *
;* 低电平存TMPLADDR为首址RAM *
;*************************************
INTEX0: CLR ET1 ;关T1中断允许
CLR TR1 ;关定时器T1
CLR EX0 ;关外中断0
CLR EA ;关中断总允许
SETB STUDYLAMP ;开学习状态指示灯
CLR LAMP ;关操作灯
MOV R0,#TMPHADDR ;高电平存放首址放入R0(07H)
MOV R1,#TMPLADDR ; 低电平存放首址放入R1(90H)
CLR A ;A清0
MOV DPH,A ;DPTR寄存器清0
MOV DPL,A ;
READHEAD: JNB REMOTEIN,READDATA ;寻找起始位。当输入为0时转READDATA
INC DPTR ;输入为高电平时对DPTR循环计数
NOP ;空操作延时
NOP ;(循环周期约为21微秒)
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
AJMP READHEAD ;跳回循环
;判断是不是遥控码起始位
READDATA: CJNE A,DPH,READDATA00 ;DPTR高8位不为0,是起始位
MOV DPH,A ; DPTR高8位为0,不是起始位
MOV DPL,A ; DPTR清0
AJMP READHEAD ;重新寻找起始位
;
READDATA00: CLR A ;处理起始位开始。清A
MOV DPH,A ;DPTR计数器清0
MOV DPL,A ;
READLOOP01: JB REMOTEIN,READDATA02 ;读起始位,高电平时转READDATA02
INC DPTR ;低电平时对DPTR循环计数
NOP ;空操作延时
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
AJMP READLOOP01 ; 循环,周期约为21微秒
;
READDATA02: CLR LAMP ;关操作灯
MOV R4,DPH ;存起始位(高8位入R4)
MOV R5,DPL ;存起始位(低8位入R5)
MOV DPH,#00H ;清0
MOV DPL,#READTIME ;放入校正值(本设计没校正,值为0)
AJMP READLOOP1 ;转READLOOP1处理高电平程序
;
READDATA1: SETB LAMP ;存高电平数据程序。开操作灯
MOV @R0,DPL ;存入高电平数据(地址在08H-6FH)
INC R0 ;指向下一地址
MOV DPL,#READTIME ; 放入校正值(本设计没校正,值为0)
MOV DPH,#00H ;清0
READLOOP0: JB REMOTEIN,READDATA2 ;读低电平程序。高电平时转READDATA2
INC DPTR ;低电平时对DPTR循环计数
NOP ;空操作延时,循环延时周期为21微秒
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
AJMP READLOOP0 ;延时循环控制
;
READDATA2: CLR LAMP ;存低电平数据程序。关操作灯
MOV @R1,DPL ;存低电平数据(地址在90H-F7H)
INC R1 ;地址加1
MOV DPL,#READTIME ; 计数校正(本设计没校正,值为0)
MOV DPH,#00H ;清0
READLOOP1: JNB REMOTEIN,READDATA3 ;读高电平程序。为0时转READDATA3
INC DPTR ;高电平时对DPTR循环计数
NOP ;空操作延时,循环周期为21微秒
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP
AJMP READLOOP1 ;循环控制
;
READDATA3: CLR A ;
CJNE A,DPH,READDATA4 ;DPH不为0转READDATA4(码读完)
AJMP READDATA1 ;转READDATA1(存高电平数据)
READDATA4: MOV @R0,A ;放结束标志数据
MOV @R1,A ;放结束标志数据
; SETB LAMP ;开操作灯
CLR STUDYLAMP ;关学习灯
SETB REMOTEIN ;遥控输入状态
READEND: JNB STUDYKEY,READEND ;等待键释放
SETB EX0 ;开外中断
SETB EA ;开总中断允许
RETI ;中断返回
;
;*************************************
;* *
;* 键工作子程序 *
;* *
;*************************************
KEYWORK: SETB P1.0 ;置P1.0口为输入状态
JNB P1.0,KEY0 ;为0转KEY0
KEYOUT: RET ;无键按下,返回
;
KEY0: LCALL DL10MS ;延时去抖动
JB P1.0,KEYOUT ;是干扰转KEYOUT返回
LJMP REMOTETX ;有键按下,转REMOTETX发谢遥控码
;
;*************************************
;* *
;* 延时程序( 255 X 2 = 513 us) *
;* *
;*************************************
DELAY: MOV R0,#DELAYCONUT0 ;(#0FFH)
DELAY1: DJNZ R0,DELAY1
RET
;
;
;
;*************************************
;* *
;* 延时约25 ms *
;* *
;*************************************
DL10MS: MOV R1,#DELAYCONUT ;(#30H)
DL10MS1: LCALL DELAY
DJNZ R1,DL10MS1
RET
;
END ;程序结束