[求助] 新人求助,关于中断及串口的问题

zspzwal   2011-10-6 09:56 楼主
最近在做一个红外解码的程序,要求解码红外并将解码结果通过串口输出,初步构思是先不管红外的标准,直接将接收到的高低电平状态及持续时间输出,当接收到红外时,触发外部中断0,中断函数如下:
  1. void to() interrupt 0//解码输出 外部中断0
    {
    uchar t;
    t = IR;
    TH0 = 0;
    TL0 = 0;
    TR0 = 1;
    EX0 = 0;//故意关闭外部中断0
    while(1)//直到输出完毕
    {
    LED = ~LED;//输出指示灯
    t = IR;
    TH0 = 0;
    TL0 = 0;
    TR0 = 1;//开启定时器0,开始计时
    while(t == IR);//记录电平持续时间
    TR0 = 0;
    if((t == 1)&&((TH0*256+TL0)>50000))//如果电平持续时间
    break;
    dateSend(t);//输出高低电平状态
    dateSend(TH0);
    dateSend(TL0);//输出电平持续时间
    }
    dateSend(0xff);//为了判断中断运行完所加的
    // EX0 = 1;故意注释的,只检测一次
    }

发送数据函数如下:
  1. void dateSend(uchar tempDate)
    {
    SBUF = tempDate;//发送数据
    while(!TI);//未发送完毕
    TI = 0;
    }
但是问题是每次当我按下一次遥控器按钮后,程序会停止在中断里,因为我主程序调用了一个数码管动态扫描函数,8个数码管显示0,但我按一次键,只有一个数码管显示0,并且输出结果里没有我在中断函数里最后加的0xff,更头疼的是,我在中断里一开始就关闭了外部中断0,当第一次输出完毕后再次按下遥控器,串口仍然有输出数据,直到重复按几次后才会看到输出0xff,并且再按键也无反应,既推出中断,输出结果如下:
  1. [接收]00 20 D3 01 04 1E 01 00 D6 01 00 EE 01 04 C0 01 04 D2 01 04 DE 01 04 D2 01 00 CA 01 04 F0 01 00 EE 01 00 A0 01 00 BE 01 00 D6 01 00 EE 01 04 B4 01 85 C6 00 14 56 [接收]01 6B B8 00 14 E0 01 05 08 01 00 A0 01 00 B8 01 04 CC 01 04 D2 01 04 D8 01 04 CC 01 00 C4 01 04 F0 01 00 E2 01 00 A0 01 00 B8 01 00 D0 01 00 E8 01 04 AE [接收]01 85 A8 00 14 8C [接收]01 AE 30 00 14 FE 01 05 20 01 00 B8 01 00 D0 01 04 E4 01 04 EA 01 04 F6 01 04 E4 01 00 E2 01 05 08 01 00 A0 01 00 B8 01 00 D0 01 00 E8 01 00 A0 01 04 C6 01 85 BA 00 14 A4 [接收]FF
接收数据 3位一组,如打头的00 20 D3 ,说明是低电平,持续时间为0x20d3*1.085约等于9ms,11.0592的晶振,但是问题是仔细看后面就发现输出结果只有01的持续时间,就是只有高电平持续时间,由于红外一体化接收输出与发送反相,因此就是说数据0与1中的高电平没有记录输出,而这两者都是0.56ms,因此我觉得是不是因为单片发送数据的时间要大于这段时间,因此导致不能检测出来?还有上面括号中有5个接受最后才是FF,说明我按了5次遥控器才最后输出FF跳出中断,这是为什么?新手,望高手指点一下,谢谢。

回复评论 (2)

if((t == 1)&&((TH0*256+TL0)>50000))//如果电平持续时间

这句是判断高电平时间的,因为平时没有接收到红外时外部中断0那个引脚是高电平,因此当高电平持续较长时间时就认为解码完毕
点赞  2011-10-6 10:05

回复 楼主 zspzwal 的帖子

你程序结构有问题,while(!TI)时间太长了
建议你开个缓冲全存,完后再发
另外定时器可以先开...
点赞  2011-10-8 12:06
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 京公网安备 11010802033920号
    写回复