找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 4090|回復(fù): 1
打印 上一主題 下一主題
收起左側(cè)

STC12 STC15系列單片機(jī)串口通信的總結(jié)

[復(fù)制鏈接]
跳轉(zhuǎn)到指定樓層
樓主
ID:285461 發(fā)表于 2018-2-25 18:57 | 只看該作者 回帖獎勵 |倒序瀏覽 |閱讀模式
串口通信:
軟件調(diào)試,在調(diào)試過程中需要使用虛擬串口助手。在編程中注意設(shè)計時鐘和波特率。注意程序的串口設(shè)置和串口調(diào)試助手中串口設(shè)置相同。
單串口:
mode com2 9600,0,8,1
assign com2 <sin> sout
stime = 0
多串口:
mode com2 9600,0,8,1
assign com2 <s0in> s0out
0表示單片機(jī)的串口0
編程:
STC12介紹的方法:
接收一個字節(jié)的函數(shù)和發(fā)送字符串的函數(shù),發(fā)送字符串需要知道字符串的長度。對于接收字符串的函數(shù),可以仿照通過調(diào)用接收一個字節(jié)的函數(shù),寫出接收字符串函數(shù)。
void WriteUart(uchar *pucData ,ucharucLength)
{
       if(ucLength== 0)
       {
              return;
       }
       if(UartBuzy== 1)
              return;
       ucSendLength=    ucLength;
       pucSendData= pucData;
       SBUF= *pucSendData;
       UartBuzy= 1;
       ucSendedCount= 0;
}
uchar ReadUart(void)
{
       ucharData;
       Data= ucRecData;
       ucRecData= 0;      
       returnData;
}
Unsigned  char RString(unsigned char *s, unsigned intlen)
{
Unsigned int  i;
For(i =0;i<len ;i++)
{
*s++ = ReadUart();
}
}
void UartIRQ(void) interrupt 4
{
      if(RI)
       {
              RI = 0;
              ucRecData = SBUF;
       }
       if(TI)
       {
              TI = 0;
              ucSendedCount++;
              if(ucSendedCount >= ucSendLength)
              {
                     UartBuzy= 0;
                     return;   
              }
              else
              {
                     SBUF= *(pucSendData + ucSendedCount);
              }
       }
}
STC15:
STC15只給出了發(fā)送函數(shù),且發(fā)送函數(shù)有瑕疵,具體見最后分析。
void UART1_ISR(void) interrupt 4 using 1
{
   if (RI)                   //接收數(shù)據(jù)
    {
       RI = 0;           //清除RI
    }
   if (TI)                   //發(fā)送數(shù)據(jù)
    {
       TI = 0;           //清除TI
       busy = 0; //清忙標(biāo)志
    }
}
void SendData(unsigned char dat)
{
   while (busy);  //等待前面的數(shù)據(jù)發(fā)送完成
   busy = 1;
    SBUF= dat;          //寫數(shù)據(jù)到UART數(shù)據(jù)寄存器
}
void SendString(char *s)
{
   while(*s)               //檢測字符串結(jié)束標(biāo)志
    {
       SendData(*s++);    //發(fā)送當(dāng)前字符
    }
}
SendString()字符串函數(shù),當(dāng)遇到發(fā)送的字符串里面有0x00就會終止,實用性不強(qiáng)。SendData()函數(shù)中三條語句的順序容易引起死機(jī)。
比較好的處理串口接收一個字節(jié)數(shù)據(jù)的方法,不采用中斷處理標(biāo)志位。通過關(guān)中斷,然后處理串口接收標(biāo)志,從而減少在處理過程中因為觸發(fā)中斷而造成的死循環(huán)。修改好的串口接收一個字節(jié)的代碼(這是采用的串口2接收一個字節(jié)數(shù)據(jù)的處理函數(shù),其控制寄存器不支持位操作)如下:
void SendData(BYTE dat)
{
     EA = 0;
       S2BUF= dat;        //SBUF=dat
   while (!(S2CON & S2TI));               //等待前面的數(shù)據(jù)發(fā)送完成  whileTI);
       S2CON&= ~S2TI;  //TI = 0;
       EA= 1;      
}
Unsigned  char SendString(unsigned char *s, unsignedint len)
{
Unsigned int  i;
For(i =0;i<len ;i++)
{
SendData(*s++);
}
}
一個比較好的接收處理框架(利用通信協(xié)議):
void UART1_ISR(void) interrupt 4 using 1
{
        unsigned char sbuffer;   
   if(RI)
    {
       RI = 0;
        sbuffer = SBUF;     
              if(nflag == 0)
                     {
                            REC_MAX     =REC_MAX_NAME ;
                     }
              else
                         REC_MAX     =REC_MAX_DATA;           
       if((sbuffer == CHECK_HEAD) && (Rec_Flag == 0))//如果收到文件頭而且當(dāng)前未接收
       {
           Rec_Flag = 1;
           Rec_Len  = 0;
             uarttext[0]= sbuffer;         // 這里保留了包頭
              }  
       else if(Rec_Flag)                       // 開始接收
       {
           if(Rec_Len < (REC_MAX - 1))  
           {     
                            Rec_Len++;               
                uarttext[Rec_Len] = sbuffer; // 當(dāng)數(shù)據(jù)送緩沖區(qū)                           
           }
           else if(Rec_Len == (REC_MAX - 1)) // 接收完成 
           {
                     /*    if(uarttext[Rec_Len] == CHECK_TAIL) //  表明接收成功未出錯
                {
                            //     
                }
                else  //  有誤碼
                {
                    
                }
                Rec_Flag = 0;// 接收完成,標(biāo)志清0
           }
       }
       }      
       else  if(TI)
       {            
             TI =0;
              busy=0;
              }     
}
分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏 分享淘帖 頂 踩
回復(fù)

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規(guī)則

手機(jī)版|小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術(shù)交流QQ群281945664

Powered by 單片機(jī)教程網(wǎng)

快速回復(fù) 返回頂部 返回列表