📄 comm485.asm
字号:
EXTRN BIT(FSCF,CRCF,TSN,RSN,TFS,RFS,WXYF,JSCF,STNO,MUTE,SOUND,SECFLG)
EXTRN DATA(CRC1,CRC2,CFCS,DEST,NETNO,SPT,TPT,ONLPT,BCOUNT,WXYCOUNT,B2BTIME)
EXTRN DATA(RPT,RRPT,ONLRPT,MONTH,DAY,HOUR,MIN,SEC,SECTIMER)
EXTRN XDATA(FIRENUM,FIREFIRST,FAULTNUM,FAULTFIRST,STARTNUM,STARTFIRST,FIRE,FAULT,START)
EXTRN CODE(MAIN,SELFTEST,?C_STARTUP)
PUBLIC RS485,SIOT,DEL,_DELAY
WDT EQU P1.6
DRV485 EQU P1.4
TABH EQU 07H
CODE485 SEGMENT CODE
DATA485 SEGMENT XDATA
RSEG DATA485
ORG 0000H
REBUF: DS 400H
ORG 0400H
TRBUF: DS 400H
TMPBUF: DS 2
TMPNUM: DS 2
TMPFST: DS 2
;入口:无
;出口:无
;功能:完成对485接收缓冲区的处理,根据不同的信息帧进行相应的任务
RSEG CODE485 ;选择可重定位代码段
RS485: CPL WDT ;对接收缓冲区进行处理
CLR C
MOV C,WXYF ;TRANSFORM TASK
ORL C,FSCF
W005: ORL C,CRCF
ORL C,JSCF
JC W002 ;判断是否有传输错误(C=1指有错转到W002,C=0指无错)
LJMP W100
W002: SETB SM2 ;出现传输错误时的处理
CLR DRV485 ;使485口处于接收状态
INC CFCS ;增加重发次数
CLR TSN ;将TSN、TFS、RSN、RFS清零
CLR TFS
CLR RSN
CLR RFS
MOV C,WXYF
ORL C,FSCF
JC TREROR ;C=1表示是发送错或无响应(转到TREROR),C=0表示接收错或CRC校验错
CLR CRCF ;C=0时将CRCF和JSCF清零
CLR JSCF
JB STNO,W000 ;结束RS485子程序
SETB F0
TREROR: CLR WXYF ;C=1时将WXYF、FSCF、CRCF、JSCF清零transfer error or no response
CLR FSCF
CLR CRCF
CLR JSCF
;ANL TPT,#7FH
MOV ONLPT,TPT ;出现发送错或无响应错误时,将在线发送指针ONLPT指向上一次;发送帧的起始位置(TPT)
MOV ONLPT+01H,TPT+01H
CPL WDT
W000: RET
W100: JB RFS,W104 ;接收完毕标志RFS=1(表示一帧接收完毕)时转到W104,
CPL WDT
RET ;对接收缓冲区进行处理;RFS=0时退出RS485子程序
W104: CPL WDT
;MOV R0,#REBUF+1
;MOV A,@R0
MOV DPTR,#REBUF
MOV A,RRPT+01H
ADD A,DPL
MOV A,RRPT
ADDC A,DPH
MOV DPH,A
INC DPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
CJNE A,DEST,W002 ;将所接收的源地址与DEST比较,若不等则表示接收错
;MOV R0,#REBUF+2
;MOV A,@R0
INC DPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
CJNE A,#3,IOIO ;将所接收的长度与3比较
IOIO: JNC PLC0
MOV RRPT,RPT
MOV RRPT+01H,RPT+01H
AJMP W002 ;长度小于3时表示接收错
PLC0: ;MOV R0,#REBUF+3 ;TYPE
;MOV A,@R0
INC DPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
JNZ W105 ;类型不为0时(查询帧)转到W105
LCALL SETRRPT
AJMP W106 ;类型为0时(查询帧)转到W106
W101: JB STNO,W106
ANL ONLPT,#7FH
MOV TPT,ONLPT
W106: MOV A,SPT ;SPT=TPT时(无需要发送的数据)调用应答程序,SPT≠TPT
MOV B,A ;时(还有需要发送的数据)转到W102
;ANL TPT,#7FH
MOV A,TPT
CJNE A,B,W102
MOV B,SPT+01H
MOV A,TPT+01H
CJNE A,B,W102
CPL WDT
LCALL ANSWER ;ANSWER
W102: CLR RFS ;清接收完毕标志RFS
MOV CFCS,#0 ;请重发次数
LCALL TRANS ;调用发送子程序(发送第一位)
W103: CPL WDT
RET
W105: CJNE A,#5,W110 ;类型为5时(重发帧)转到W106,不为重发帧时转到W110
LCALL SETRRPT
LJMP W106
W110: CPL WDT
CJNE A,#1,W120 ;类型不为1时(应答帧)转到W120
LCALL SETRRPT
CLR TFS ;类型为1时(应答帧)清发送完毕标志TFS
;ANL ONLPT,#7FH
MOV TPT,ONLPT ;将ONLPT的值赋给TPT,让TPT指向下一帧的起始位置
MOV TPT+01H,ONLPT+01H
CLR RFS ;清接收完毕标志
MOV CFCS,#0 ;清重发次数
JB STNO,W103 ;结束
W120: CJNE A,#3,W130 ;类型不为3时(未用帧)转到W130(EVENT DIST TABLE)
LCALL SETRRPT
LCALL W106 ;类型为3时(未用帧)调用W106
CPL WDT
RET
W130: CJNE A,#4,W140 ;类型不为4时(联动帧)转到W140
LCALL SETRRPT
RET ;类型为4时(联动帧)结束
W0909: LJMP W002
W140: CJNE A,#2,W0909 ;类型不为2时(数据帧)转到W002结束RS485子程序
;MOV R0,#REBUF ;类型为2时(数据帧)先验证所接收的目的地址是否为
;MOV A,@R0 ;7F,若不等则转到G103,
MOV DPTR,#REBUF
MOV A,RRPT+01H
ADD A,DPL
MOV DPL,A
MOV A,RRPT
ADDC A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
CJNE A,#7FH,G103
CLR RFS ;清接收完毕标志
;MOV R0,#REBUF+4
;MOV A,@R0
INC DPTR
INC DPTR
INC DPTR
INC DPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
CPL WDT
MOVX A,@DPTR
CJNE A,#0D0H,G104 ;@4E04=D0时调用自检程序3次SELF TEST
LCALL SELFTEST
LCALL SELFTEST
LCALL SELFTEST
LCALL SETRRPT
W1400: RET
G104: CJNE A,#6AH,G105 ;@4E04=6A时禁止中断重新开始主程序SOFT RESET
CLR EA
LJMP ?C_STARTUP ;0000H
G105: CJNE A,#69H,G106
SETB MUTE
CLR SOUND
LCALL SETRRPT
RET
G106: CJNE A,#0F3H,W1400
CPL WDT
MOV A,#04H
MOV B,#00H
LCALL ADDDPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
MOV MONTH,A
INC DPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
MOV DAY,A
INC DPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
MOV HOUR,A
INC DPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
MOV MIN,A
INC DPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
MOV SEC,A
MOV SECTIMER,#00H
CLR SECFLG
LCALL SETRRPT
RET
G103: CPL WDT
PUSH DPH
PUSH DPL
LCALL W101
POP DPL
POP DPH
MOV A,#04H
MOV B,#00H
LCALL ADDDPTR
MOV A,DPH
ANL A,#03H
MOV DPH,A
MOVX A,@DPTR
CJNE A,#31H,G1031
G1031: JNC G1032
LCALL SETRRPT
RET
G1032: CJNE A,#40H,G1033
G1033: JC G1034
LCALL SETRRPT
RET
G1034: CJNE A,#3DH,G1035
AJMP G1036
G1035: CJNE A,#3EH,G1037
G1036: MOV DPTR,#FIRENUM
CPL WDT
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPNUM
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPNUM+01H
MOV A,R0
MOVX @DPTR,A
MOV DPTR,#FIRE
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPBUF
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPBUF+01H
MOV A,R0
MOVX @DPTR,A
MOV DPTR,#FIREFIRST
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPFST
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPFST+01H
MOV A,R0
MOVX @DPTR,A
LCALL PROCBUF
RET
G1037: CJNE A,#31H,G103C
AJMP G103D
G103C: CJNE A,#32H,G103E
G103D: MOV DPTR,#STARTNUM
CPL WDT
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPNUM
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPNUM+01H
MOV A,R0
MOVX @DPTR,A
MOV DPTR,#START
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPBUF
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPBUF+01H
MOV A,R0
MOVX @DPTR,A
MOV DPTR,#STARTFIRST
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPFST
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPFST+01H
MOV A,R0
MOVX @DPTR,A
LCALL PROCBUF
RET
G103E: MOV DPTR,#FAULTNUM
CPL WDT
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPNUM
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPNUM+01H
MOV A,R0
MOVX @DPTR,A
MOV DPTR,#FAULT
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPBUF
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPBUF+01H
MOV A,R0
MOVX @DPTR,A
MOV DPTR,#FAULTFIRST
MOV R1,DPH
MOV R0,DPL
MOV DPTR,#TMPFST
MOV A,R1
MOVX @DPTR,A
MOV DPTR,#TMPFST+01H
MOV A,R0
MOVX @DPTR,A
LCALL PROCBUF
RET
;入口;R7信息段首字节,R5信息字节
;出口;无
;功能;向发送缓冲区装配信息帧
;_SW485: CLR EA
; CPL WDT
; MOV R6,#05H ;对发送缓冲区进行处理(将按键信息送入发送缓冲区)
; ;ANL SPT,#7FH ;读出发送缓冲写入指针SPT的内容
; ;MOV A,#TRBUF
; MOV DPTR,#TRBUF
; MOV A,DPL
; ADD A,SPT+01H
; MOV DPL,A
; MOV A,DPH
; ADDC A,SPT
; MOV DPH,A
; MOV A,DEST
; MOVX @DPTR,A
;
; ADD A,SPT
; MOV R0,A
; MOV A,DEST ;将目的地址送入SPT指向的发送缓冲区的首位地址
; MOV @R0,A
; INC SPT
; ANL SPT,#7FH
; MOV A,#TRBUF
; ADD A,SPT
; MOV R0,A
; MOV A,NETNO
; MOV @R0,A ;将源地址(本站号)送入第2位地址
; INC SPT
; ANL SPT,#7FH
; MOV A,#TRBUF
; ADD A,SPT
; MOV R0,A
; MOV A,R6
; MOV @R0,A ;将长度=5送入第3位地址(有效数据位为2位)
; INC SPT
; ANL SPT,#7FH
; MOV A,#TRBUF
; ADD A,SPT
; MOV R0,A
; MOV A,#02H ;将类型=2送入第4位地址
; MOV @R0,A
; INC SPT
; ANL SPT,#7FH
; MOV A,#TRBUF
; ADD A,SPT
; MOV R0,A
; MOV A,R7 ;将R7送入第5位地址
; MOV @R0,A
; INC SPT
; ANL SPT,#7FH
; MOV A,#TRBUF
; ADD A,SPT
; MOV R0,A
; MOV A,R5
; MOV @R0,A
; INC SPT
; ANL SPT,#7FH
; CPL WDT
; SETB EA
; RET
FRAMF: CPL WDT
;ANL SPT,#7FH
;MOV TPT,SPT ;将SPT的内容放入TPT
MOV TPT,SPT
MOV TPT+01H,SPT+01H
MOV CFCS,#0 ;清重发次数
FRRET: RET
;发送缓冲区首位发送子程序
TRANS: CPL WDT
;ANL TPT,#7FH
;MOV A,TPT ;发送缓冲区首位发送子程序
;ANL A,#7FH ;TPT所指的首位数值与DEST若不同则转向FRAMF
;ADD A,#TRBUF
MOV DPTR,#TRBUF
MOV A,TPT+01H
ADD A,DPL
MOV DPL,A
MOV A,TPT
ADDC A,DPH
MOV DPH,A
MOVX A,@DPTR
CJNE A,DEST,FRAMF
INC DPTR ;第2位数值与NETNO若不同则转向FRAMF
MOV A,DPH
ANL A,#03H
ORL A,#04H
MOV DPH,A
MOVX A,@DPTR
CJNE A,NETNO,FRAMF
INC DPTR ;第3位数值若<3则转向FRAMF
MOV A,DPH
ANL A,#03H
ORL A,#04H
MOV DPH,A
MOVX A,@DPTR
CJNE A,#3,TLCK
TLCK: CPL WDT
JC FRAMF
JB RSN,FRRET ;接收标志和接收完毕标志若为1(一帧接收完毕但还未对其进行
JB RFS,FRRET ;处理则结束
CLR ES ;关闭串行中断sio int
SETB DRV485 ;485口置发送状态
LCALL DEL ;调用延时子程序
LCALL DEL
LCALL DEL
LCALL DEL
SETB TB8 ;TB8=1表示传送地址位
SETB SM2 ;SM2=1表示接收地址位
SETB TSN ;发送标志TSN置1
SETB TR1 ;启动定时器1(波特率发生器)
CLR TFS ;清发送完毕标志TFS
CLR A
MOV CRC1,A ;将CRC1、CRC2清零
MOV CRC2,A
;ANL TPT,#7FH
;MOV A,TPT ;将发送指针的内容送入A
;PUSH ACC
MOV DPH,TPT
MOV DPL,TPT+01H
PUSH DPH
PUSH DPL
INC DPTR
ANL DPH,#03H
MOV ONLPT,DPH
MOV ONLPT+01H,DPL
;ANL A,#7FH
;MOV ONLPT,A ;将第2位地址送入ONLPT(DATA ORG POINT TO #4F02H)
INC DPTR
ANL DPH,#03H
MOV B,DPH
MOV A,DPL
MOV DPTR,#TRBUF
ADD A,DPL
MOV DPL,A
MOV A,B
ADDC A,DPH
MOV DPH,A
MOVX A,@DPTR
;ANL A,#7FH
;ADD A,#TRBUF ;将本帧的信息长度送入A
;MOV R0,A
;MOV A,@R0
CLR RS0 ;选取2区工作寄存器
SETB RS1
MOV R6,A ;将本帧的信息长度送入R6(DATA LENTH TO R6)
MOV R2,#00H ;R2为发送位寄存器(TRANS POINT)
POP DPL
POP DPH
MOV B,DPH
MOV A,DPL
MOV DPTR,#TRBUF
ADD A,DPL
MOV DPL,A
MOV A,B
ADDC A,DPH
MOV DPH,A
MOVX A,@DPTR
;ANL A,#7FH
;ADD A,#TRBUF
;MOV R0,A
;MOV A,@R0 ;将目的地址读出
PUSH ACC
LCALL CPCRC ;将目的地址进行CRC校验
POP ACC
RL A ;将目的地址进行*2+1的运算(ADD * 2 +01H)
ORL A,#01H
MOV R5,A ;R5中存放所要发送的首位数据
CLR RS1 ;选取0区工作寄存器
CLR RS0
SETB ES ;允许串行中断
MOV SBUF,A ;将首位进行发送
CPL WDT
RET
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -