汇编串口中断出现问题

hd12   2007-5-8 14:52 楼主
为什么我写的串口中断接受程序,烧到51里就一直执行中断服务程序,而我根本没有产生中断,然后我把串口线拔下问题还是如此,代码如下:

;单片机内存分配申明!
TEMPER_L EQU         29H;用于保存读出温度的低8位
TEMPER_H EQU         28H;用于保存读出温度的高8位
BYT_DLY         EQU         39H
DQ          EQU         p2.7
FLAG1          EQU         38H;是否检测到DS18B20标志位
COUNT          EQU         3BH;是否检测到DS18B20标志位

     ORG 0000H
     AJMP START
    ORG 0023H
    AJMP RECE
     ORG 0030H
START:        
        MOV    SP,#60H
        MOV     IE, #00H ;禁止cpu中断,禁止串口中断       
        MOV         SCON,#50H        ;设置成串口1方式,SM2=1,REN=1
        MOV         TMOD,#20H        ;波特率发生器T1工作在模式2上
        MOV         PCON,#80H
        MOV         TH1,#0faH        ;预置初值(按照波特率9600BPS预置初值)
        SETB         TR1        ;启动定时器T1
        MOV     IE, #90H;允许cpu中断,允许串口中断
        CLR RI
MAIN:
       LCALL         GET_TEMPER;调用读温度子程序
        MOV        SBUF,#7EH
        JNB        TI,$
        CLR         TI
       
        MOV        SBUF,#7EH
        JNB        TI,$
        CLR         TI       
       
        MOV        SBUF,28H
        JNB        TI,$
        CLR         TI       
       
        MOV        SBUF,29H
        JNB        TI,$
        CLR         TI
        AJMP   MAIN
       
;这是DS18B20复位初始化子程序
INIT_1820:
        SETB         DQ
        NOP
        CLR         DQ       
        MOV         BYT_DLY,#220
        LCALL         DELAY1;480us                       
        SETB         DQ        ;然后拉高数据线       
        MOV         BYT_DLY,#15
        LCALL         DELAY1;36us               
        MOV         R0,#10
TSR2:        JNB         DQ,TSR3 ;等待DS18B20回应
        DJNZ         R0,TSR2
        LJMP         TSR4 ;延时
TSR3:        SETB         FLAG1 ;置标志位,表示DS1820存在
        ;CLR         P1.7;检查到DS18B20就点亮P1.7LED
        LJMP         TSR5
TSR4:        CLR         FLAG1 ;清标志位,表示DS1820不存在
        ;CLR         P1.2
        LJMP         TSR7       
TSR5:        MOV         BYT_DLY,#192
        LCALL         DELAY1;420us       
TSR7:        SETB         DQ
        RET

; 读出转换后的温度值
GET_TEMPER:
        SETB         DQ
        LCALL         INIT_1820;先复位DS18B20
        JB         FLAG1,TSS2
        ;CLR         P1.2
        RET         ;判断DS1820是否存在?若DS18B20不存在则返回
TSS2:        ;CLR         P1.3;DS18B20已经被检测到!!!!!!!!!!!!!!!!!
        MOV         A,#0CCH ;跳过ROM匹配
        LCALL         WRITE_1820
        MOV         A,#44H ;发出温度转换命令
        LCALL         WRITE_1820

        ;等待AD转换结束,12位的话750微秒
        MOV         BYT_DLY,#130
        LCALL         DELAY3;118ms       
       
       
        LCALL         INIT_1820;准备读温度前先复位
        MOV         A,#0CCH ;跳过ROM匹配
        LCALL         WRITE_1820
        MOV         A,#0BEH ;发出读温度命令
        LCALL         WRITE_1820
        LCALL         READ_18200;将读出的温度数据保存到35H/36H        
        RET

;写DS18B20的子程序(有具体的时序要求)
WRITE_1820:
        MOV         R2,#8;一共8位数据
        CLR         C
WR1:        CLR         DQ
       
        MOV         BYT_DLY,#5
        LCALL         DELAY1;15us
                               
        RRC         A
        MOV         DQ,C       
        MOV         BYT_DLY,#19
        LCALL         DELAY1;45us
        SETB         DQ
        NOP       
        DJNZ         R2,WR1
        SETB         DQ
        RET

;读DS18B20的程序,从DS18B20中读出两个字节的温度数据
READ_18200:
        MOV         R4,#2 ;将温度高位和低位从DS18B20中读出
        MOV         R1,#29H ;低位存入29H(TEMPER_L),
                    ;高位存入28H(TEMPER_H)
RE00:        MOV         R2,#8;数据一共有8位
RE01:        CLR         C       
        CLR         DQ
        NOP
        NOP
        NOP
        SETB         DQ       
        MOV         BYT_DLY,#5
        LCALL         DELAY1;15us               
        MOV         C,DQ       
        MOV         BYT_DLY,#19
        LCALL         DELAY1;45us       
        RRC         A
        DJNZ         R2,RE01
        MOV         @R1,A
        DEC         R1
        SETB         DQ
        NOP
        NOP
        NOP
        DJNZ         R4,RE00
        RET
       
DELAY1: DJNZ    BYT_DLY,DELAY1
        RET
               
DELAY2: PUSH    BYT_DLY
DELM1:  DJNZ    BYT_DLY,DELM1
        POP     BYT_DLY
        DJNZ    BYT_DLY,DELAY2
        RET                
        
DELAY3: PUSH    BYT_DLY
DEL31:  PUSH    BYT_DLY
DEL32:  DJNZ    BYT_DLY,DEL32
        POP     BYT_DLY
        DJNZ    BYT_DLY,DEL31
        POP     BYT_DLY
        DJNZ    BYT_DLY,DELAY3
        RET
DELAY:        MOV R5,#20                       
D1:        MOV R6,#20
D2:        MOV R7,#248
        DJNZ R7,$
        DJNZ R6,D2
        DJNZ R5,D1
        RET

RECE:       
      MOV IE, #00h ;禁止cpu中断,禁止串口中断
              CLR RI
       MOV a, SBUF
       MOV COUNT,100   
ALARM:
        CLR P2.0
        LCALL DELAY
        SETB P2.0
        LCALL DELAY
        DJNZ COUNT ,ALARM
      MOV     IE, #90h;允许cpu中断,允许串口中断   
    RETI
END


回复评论 (7)

可能是你发的时候跳进中断里了

在你的串口服务里加入,识别确认是收的中断

    JNB RI,XX

    ;你的接收处理

  XX:RETI
点赞  2007-5-8 15:58
我按你的做法做了
不过又有新问题了,现在程序一烧到里面不会产生中断,但我在PC上向51发一个数据产生中断后,又会死在中断服务程序里,出不来!
点赞  2007-5-8 16:47
具体死在哪块知道不??

点赞  2007-5-8 17:19
死在中断服务程序里啊!
点赞  2007-5-9 10:03
先这样:你把发送相关的全都去了,看看还有没有中断触发,如果还有那就看一下硬件的连接了...

串口相关部分,独立的调一下串口
点赞  2007-5-9 10:24
可我用c写的串口收发程序是正常的,所以硬件应该没有问题!
点赞  2007-5-9 13:55
串行中断的执行时间太长了,一般中断程序的设计原则是快进快出,复杂事务在中断外出理。
你在中断中总共循环了100*(2*(20*20*248)))次,假定每次循环时间是3uS,总共执行时间需要59.52s,问题可能就是出在这儿。
点赞  2007-5-23 14:42
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 京公网安备 11010802033920号
    写回复