51单片机 串口通信 定时与中断

2019-07-15 10:03发布

各位朋友帮忙看一下
下面是51单片机串口通信的一个数据发送例程,想问一下定时器T0关闭后程序还会继续运行进入中断函数吗?主要是中断函数中,串行接收处理起始位不为零,终止接收那里不太明白,
else                                     //串行接收数据
    {
        if(cnt == 0)                   //处理起始位
        {
            if(!PRXD)                   //起始位为零时,清零接受缓冲器,准备接受数据位
            {
                RxdBuf = 0;
                cnt++;
            }
            else                      //起始位不为零时,终止接收
                TR0 = 0;           //关闭T0
        }
假设遇到干扰信号,一开始PRXD=0,而中断里再次判断时PRXD=1,中断函数就执行上面else那段吧,主函数停留在while(!RxdEnd);   程序怎样继续往下运行呢?我目前想到的是可以再进入中断,但是从哪里开始计时就不明白了,或者其他地方我没考虑到吗,小白入门望指教



#include<reg52.h>
sbit PRXD = P3^0;        //接收引脚定义
sbit PTXD = P3^1;        //发送引脚定义

unsigned char TxdBuf = 0;   //发送缓冲  
unsigned char RxdBuf = 0;    //接收缓冲
bit RxdOrTxd = 0; //指示当前状态是接收还是发送
bit RxdEnd = 0; //接收结束标志
bit TxdEnd = 0; //发送结束标志

void ConfigUART(unsigned int baud);        //配置波特率函数
void StartRXD();
void StartTXD(unsigned char dat);

void main()
{
    EA = 1;                                    //开总中断
    ConfigUART(9600);                  // 设置波特率为9600
     while(1)
    {
        while(PRXD);                   //检测低电平,如果是高电平,会一直等待,直到PRXD=0
        StartRXD();启动接收
        while(!RxdEnd);                   //RxdEnd=1时,十位数据接收完毕
        StartTXD(RxdBuf+1);               //数据接收完毕开始发送
        while(!TxdEnd);                   //TedEnd=1时,十位数据发送完毕
    }
}
void ConfigUART(unsigned int baud) //波特率配置函数
{
    TMOD &= 0xF0;                           //清零T0控制位
    TMOD |= 0x02;                             // T0  设置为自动重装模式
    TH0 = 256-(11059200/12)/baud;       //计算T0重载值
}
void StartRXD()                                 //接收启动函数
{
    TL0 = 256-((256-TH0)>>1);           //接收启动时T0设置为半个波特率周期,以便获得较稳定信号
    ET0 = 1;                                         //使能T0中断
    TR0 = 1;                                        //启动T0
    RxdEnd = 0;                                    // 清零接受结束标志,开始接收数据
    RxdOrTxd = 0;                                //当前状态设置为接收
}
void StartTXD(unsigned char dir)    //数据发送函数
{
    TxdBuf = dir;                                //待发送数据保存到缓冲区
    TL0 = TH0;                                    //定时器初值重载
    ET0 = 1;                                        //使 能T0中断
    TR0 = 1;                                        //启动T0
    TxdEnd = 0;                                 //清零发送结束标志,开始发送数据
    PTXD = 0;                                     //发送起始位
    RxdOrTxd = 1;                              //当前状态设置为发送
}
void Interrupt() interrupt 1               //中断函数
{
    static unsigned char cnt = 0;           //接收或发送计数
    if(RxdOrTxd)              //串行发送数据
    {
        cnt++;
        if(cnt <= 8)                 //低位先依次发送8位数据
        {
            PTXD = TxdBuf & 0x01;
            TxdBuf >>= 1;
        }   
        else if(cnt == 9)            //8位数据发送完毕,停止发送
             PTXD = 1;
        else                            //发送结束
        {
            cnt = 0;                   //复位bit计数器
            TR0 = 0;                   //关闭T0
            TxdEnd = 1 ;              //置发送标志为结束
        }
    }
    else                                     //串行接收数据
    {
        if(cnt == 0)                   //处理起始位
        {
            if(!PRXD)                   //起始位为零时,清零接受缓冲器,准备接受数据位
            {
                RxdBuf = 0;
                cnt++;
            }
            else                      //起始位不为零时,终止接受
                TR0 = 0;           //关闭T0
        }
        else if(cnt<=8)         //处理8位数据位
        {
            RxdBuf >>= 1;                 //低位在先,将之前接受的数据右移
            if(PRXD)                //接受脚为1时缓冲器最高位置1,为零时不处理
                RxdBuf|= 0x80;
            cnt++;
        }
        else停止处理
        {
            cnt = 0;               //复位bit计数器
            TR0 = 0;              //关闭T0
            if(PRXD)               //停止位为1时,方认为数据有效
                RxdEnd =1;               //设置接受结束标志
        }
    }
}
0条回答

一周热门 更多>