⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 main.asm

📁 我自己写的短距离无线通信系统的收发程序
💻 ASM
字号:
             ORG    0000H           ;主程序入口
             AJMP   START
           ;  ORG    0023H           ;中断服务子程序入口
             AJMP   RECEIVE
             ORG    0030H
START:       MOV    P2,#7FH         ;LED灯全灭,P2.7=0使TXEN=0,模块处于接收状态
             LCALL  DELAY_10ms      ;时间延迟
             MOV    R0,#50H         ;R0(50H)中存放接收数据地址
             ;MOV 
             SETB   TR1             ;启动定时器T1
             SETB   EA              ;开全局中断
             SETB   ES              ;开串行口中断
            ; MOV    R0,#50H         ;R0为接收数据存放地址(50H)
             ;MOV    R2,#01H         ;R1存放命令
             ;MOV    R3,#03H         ;R2存放地址及命令发送次数(3次)
             ;CLR    P2.7            ;设置TXEN=0,使模块处于接收状态
            ; LCALL  DELAY_10ms      ;时间延迟
          ;   SJMP   $                ;等待串口中断
            ; LJMP   MAIN
;***********************************************************************
;串口数据接收中断子程序
RECEIVE:     MOV    R4,#00H                  ;R4为校验和寄存器
             CLR    RI
             MOV    A,SBUF                  ;接收字符
             CJNE   A,#0FFH,RXD_ERR          ;接收是否FFH?不是则跳转
             ADD    A,R4                     ;形成累加校验和
             MOV    R4,A
             JNB    RI,$                     ;接收字符
             CLR    RI
             MOV    A,SBUF
             CJNE   A,#00H,RXD_ERR          ;接收是否00H,不是则跳转
             ADD    A,R4
             MOV    R4,A
             MOV    R6,#00H                  ;R6存放接收次数(6次)
RXSIX:       JNB    RI,$                     ;接收数据
             CLR    RI
             MOV    A,SBUF
             ADD    A,R4                     ;形成校验和
             MOV    R4,A
             CLR    RI
            ; MOV    A,SBUF                   ;接收校验和
            ; SUBB   A,R4                     ;比较校验和是不是正确
           ;  JNZ    RXD_ERR                  ;校验和不正确则跳转
             LCALL  COMPARE                 ;调用比较子程序比较三对地址和命令数据
             MOV    A,P2                     ;判断三对数据是否至少有两对相同
             CJNE   A,#00H,RXD_END           ;不相等(P2=00H)则跳转
            ; MOV    R2,50H                   ;R2存放地址
             MOV    R3,51H                   ;R3存放命令标志
             SJMP   RXD_END
RXD_ERR:     MOV    P2,#00H                  ;数据错,灯全亮
RXD_END:     CLR    EA                       ;关闭中断
             RETI
;***********************************************************************
MAIN:      ;  CLR    EA                       ;关闭中断
             LCALL  PROCESSOR                ;调数据处理子程序
             SETB   EA
             LJMP   MAIN_END
             ;END
;************************************************************************
;数据处理子程序
PROCESSOR:    MOV   A,50H             ;50H存放地址标志
              SUBB  A,#254            ;比较地址标志Ra>=254?
              JC    IDDATA            ;否(小于)则跳转(CY=1有借位,则小于254)
              MOV   A,R3              ;R3(Ri)命令标志
              CJNE  A,#01H,PROCE_1    ;R3=01?不等则跳转
              LCALL REGISTER          ;调报到子程序
              AJMP  PROCE_END         ;返回
PROCE_1:      CJNE  A,#02H,PROCE_2    ;R3=02?不等则跳转
              LCALL FLOOR             ;调发言子程序
              AJMP  PROCE_END         ;返回
PROCE_2:      CJNE  A,#03H,PROCE_ERR  ;R3=03?不等则跳转
              LCALL VOTER             ;调表决子程序
              AJMP  PROCE_END         ;返回
IDDATA:       SUBB  A,R2              ;比较是否为本机地址(R2存放本机地址)
              JNZ   PROCE_ERR         ;不是则跳转
              MOV   A,R3              ;R3(Ri)命令标志
              CJNE  A,#07H,IDDATA_1   ;R3=07?不等则转移
              CLR   P1.5              ;取消发言
              SETB  P2.1              ;
              SETB  P2.2
              AJMP  PROCE_END         ;返回
IDDATA_1:     CJNE  A,#08,PROCE_ERR   ;R3=08?不等则跳转
              SETB  P1.5              ;允许发言
              CLR   P2.1
              CLR   P2.2
              AJMP  PROCE_END         ;返回
PROCE_ERR: ;   MOV   P2,#00H           ;出错处理(LED灯全亮)
PROCE_END:    RET
;**********************************************************************
;报到子程序
REGISTER:     MOV   A,50H             ;50H存放地址命令标志
              CJNE  A,#255,REG_2      ;Ra=255?不等则跳转
              CLR   P2.3              ;报到状态灯亮,允许报到
              SETB  EA                ;开中断
REG_1:        MOV   C,P2.3            ;p2.3是报到状态显示位
              JC    REG_3             ;(P2.3=1)报到取消则转移
              MOV   C,P1.0            ;扫描P1.0,P1.0是S1按键
              LCALL DELAY_10ms        ;延时10ms消抖
              ORL   C,P1.0            ;再读P1.0状态,看两次结果是否都为0
              JC    REG_1             ;(P1.0=1)S1键没有按下则转移重新扫描
              CLR   EA                ;关中断
           ;******************************************************
           ;需要修改的地址Ra和命令Ri
              MOV   R2,#00H           ;R2存放本机地址,需要修改
              MOV   R3,#01H           ;R3存放命令(01代表报到).需要修改
           ;******************************************************
             ; LCALL SEND              ;调发送子程序
              CLR   P2.4              ;已报到灯亮
              AJMP  REG_END            ;返回
REG_2:        CJNE  A,#254,REG_ERR    ;Ra=254?不等则跳转
              SETB  P2.3              ;取消报到状态
              SETB  P2.4
REG_3:        CLR   EA                ;开中断
              AJMP  REG_END           ;返回
REG_ERR:  ;    MOV   P2,#00H           ;出错,灯全亮
REG_END:      RET
;***********************************************************************
;报到子程序
FLOOR:        MOV   A,50H             ;50H存放地址命令标志
              CJNE  A,#255,FLOOR_2    ;Ra=255?不等则跳转
              CLR   P2.0              ;报到状态灯亮,允许报到
              SETB  EA                ;开中断
FLOOR_1:      MOV   C,P2.0            ;p2.0是发言状态显示位
              JC    FLOOR_3           ;(P2.0=1)发言取消则转移
              MOV   C,P1.1            ;扫描P1.1,P1.1是S2按键
              LCALL DELAY_10ms        ;延时10ms消抖
              ORL   C,P1.1            ;再读P1.1状态,看两次结果是否都为0
              JC    FLOOR_1            ;(P1.1=1)S2键没有按下则转移重新扫描
              CLR   EA                ;关中断
           ;******************************************************
           ;需要修改的地址Ra和命令Ri
              MOV   R2,#00H           ;R2存放本机地址,需要修改
              MOV   R3,#02H           ;R3存放命令(02代表发言申请).需要修改
           ;******************************************************
              LCALL SEND              ;调发送子程序
              CLR   P2.1              ;已报到灯亮
              AJMP  FLOOR_END         ;返回
FLOOR_2:      CJNE  A,#254,FLOOR_ERR  ;Ra=254?不等则跳转
              SETB  P2.0              ;取消报到状态
              SETB  P2.1
              SETB  P2.2
FLOOR_3:      CLR   EA                ;关中断
              AJMP  FLOOR_END         ;返回
FLOOR_ERR:  ;  MOV   P2,#00H           ;出错,灯全亮
FLOOR_END:    RET
;***********************************************************************
;报到子程序
VOTER:        MOV   A,50H             ;50H存放地址命令标志
              CJNE  A,#255,VOTER_4    ;Ra=255?不等则跳转
              CLR   P2.5              ;表决状态灯亮,允许表决
              SETB  EA                ;开中断
VOTER_1:      MOV   C,P2.5            ;p2.5是表决状态显示位
              JC    VOTER_5           ;(P2.5=1)表决取消则转移
              MOV   C,P1.2            ;扫描P1.1,P1.1是S2按键
              LCALL DELAY_10ms        ;延时10ms消抖
              ORL   C,P1.2            ;再读P1.1状态,看两次结果是否都为0
              JC    VOTER_2            ;(P1.1=1)S2键没有按下则转移
              CLR   EA                ;关中断
           ;******************************************************
           ;需要修改的地址Ra和命令Ri
              MOV   R2,#00H           ;R2存放本机地址,需要修改
              MOV   R3,#04H           ;R3存放命令(04代表同意).需要修改
           ;******************************************************
              LCALL SEND              ;调发送子程序
              CLR   P2.6              ;已报到灯亮
              AJMP  VOTER_END         ;返回
VOTER_2:      MOV   C,P1.3            ;扫描P1.1,P1.1是S2按键
              LCALL DELAY_10ms        ;延时10ms消抖
              ORL   C,P1.3            ;再读P1.1状态,看两次结果是否都为0
              JC    VOTER_3           ;(P1.1=1)S2键没有按下则转移
              CLR   EA                ;关中断
           ;******************************************************
           ;需要修改的地址Ra和命令Ri
              MOV   R2,#00H           ;R2存放本机地址,需要修改
              MOV   R3,#05H           ;R3存放命令(04代表反对).需要修改
           ;******************************************************
              LCALL SEND              ;调发送子程序
              CLR   P2.6              ;已表决灯亮
              AJMP  VOTER_END         ;返回
VOTER_3:      MOV   C,P1.4            ;扫描P1.1,P1.1是S2按键
              LCALL DELAY_10ms        ;延时10ms消抖
              ORL   C,P1.4            ;再读P1.1状态,看两次结果是否都为0
              JC    VOTER_1           ;
              CLR   EA                ;关中断
           ;******************************************************
           ;需要修改的地址Ra和命令Ri
              MOV   R2,#00H           ;R2存放本机地址,需要修改
              MOV   R3,#06H           ;R3存放命令(06代表弃权).需要修改
           ;******************************************************
              LCALL SEND              ;调发送子程序
              CLR   P2.6              ;已表决灯亮
              AJMP  VOTER_END         ;返回
VOTER_4:      CJNE  A,#254,VOTER_ERR  ;Ra=254?不等则跳转
              SETB  P2.5              ;取消表决状态
              SETB  P2.6
VOTER_5:      CLR   EA                ;开中断
              AJMP  VOTER_END         ;返回
VOTER_ERR: ;   MOV   P2,#00H           ;出错,灯全亮
VOTER_END:    RET
;***********************************************************************
             ;发送子程序
             ;R2中存放本机地址,R1中存放命令
SEND:        SETB   P2.7            ;设置TXEN=1,使模块处于发送状态
             MOV    R4,#00H         ;R5(校验和寄存器)清零
             LCALL  DELAY_10ms      ;时间延迟
             CLR    TI
             MOV    A,#0FFH          ;发送FFH
             MOV    SBUF,A
             JNB    TI,$            
             CLR    TI
             ADD    A,R4             ;形成累加校验和
             MOV    R4,A
             MOV    A,#00H          ;发送00H
             MOV    SBUF,A
             JNB    TI,$
             CLR    TI
             ADD    A,R4             ;形成校验和
             MOV    R4,A
             MOV    R6,#03H          ;R6存放发送次数(3次)
TXTIMES:     MOV    A,R2             ;发送本机地址
             MOV    SBUF,A
             JNB    TI,$
             CLR    TI
             ADD    A,R4            ;形成校验和
             MOV    R4,A
             MOV    A,R3            ;发送命令
             MOV    SBUF,A
             JNB    TI,$
             CLR    TI
             ADD    A,R4             ;形成校验和
             MOV    R4,A
             DJNZ   R6,TXTIMES       ;判断发送次数(3次)
             MOV    A,R4             ;发送校验和
             MOV    SBUF,A
             JNB    TI,$
             CLR    TI
             CLR    P2.7             ;使模块处于接收状态
             RET
;************************************************************************
        ;比较子程序
         ;比较三对数据是否至少有两对想等,数据存放在50H开始数据寄存器
COMPARE:      MOV   A,50H
              SUBB  A,52H         ;50H-52H=0?
              JNZ   C1            ;不等跳转
              MOV   A,51H
              SUBB  A,53H        
              JZ    C4            ;相等退出
C1:           MOV   A,50H
              SUBB  A,54H         
              JNZ   C2
              MOV   A,51H
              SUBB  A,55H         ;51H-55H=0?
              JZ    C4
C2:           MOV   A,52H
              SUBB  A,54H
              JNZ   C3            ;不等跳转
              MOV   A,53H
              SUBB  A,55H         ;53H-55H=0?
              JNZ   C3
              MOV   50H,52H
              MOV   51H,53H
              SJMP  C4             ;退出子程序
C3:           MOV   P2,#00H        ;出错处理,灯全亮
C4:           RET
;***********************************************************************
;延时子程序
DELAY_10ms:  MOV    R7,#32
DEL1:        MOV    R6,#142         
             NOP
DEL2:        DJNZ   R6,DEL2         
             DJNZ   R7,DEL1         
             RET
MAIN_END:    END

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -