欧美极品高清xxxxhd,国产日产欧美最新,无码AV国产东京热AV无码,国产精品人与动性XXX,国产传媒亚洲综合一区二区,四库影院永久国产精品,毛片免费免费高清视频,福利所导航夜趣136

標題: 請教單片機如何避免串口接收數據丟失? [打印本頁]

作者: happy2058    時間: 2021-10-13 00:17
標題: 請教單片機如何避免串口接收數據丟失?
單片機與觸控屏通信  按下屏幕下發 AA 79 ** ** 33 cc c3 3c  抬起屏幕下發 AA 78 ** ** 33 cc c3 3c  中間兩個字節用戶定義相同指令
以下部分代碼
uchar buf[16];      //接收緩存區     這里因為上電握手最大長度,所以給了16  下面程序只用到8個字節
uchar rp = 0;       //緩存區地址

void interrupt_uart() interrupt 4 //using 3   //串口接收,定時器2 115200
{
                if (RI)  
                        {  
                        RI = 0 ;               
                        buf[ rp++ ] = SBUF;
                        if(SBUF==0X3C)                      //接收到尾 地址復位
                                rp=0;               
                        }
        }



void key_service()                //放在大循環        while(1) 里一直調用                                                
{        
switch(buf[1])                         //對應該按下 指令 79后進行比較                                       
                        {
                                case 0X79:
                                
                                if(        buf[3]==0x01 && buf[7]==0x3c)             //buf[3]==0x01 是用戶指令01 只判定buf[3]                                       
                                 {
                                        memset(buf, 0, 16)
                                       **********此處省略**********
                                }
                                if(        buf[3]==0x02 && buf[7]==0x3c)                                                
                                {
                                           memset(buf, 0, 16)
                                        **********此處省略**********        
                                }
                                if(        buf[3]==0x03 && buf[7]==0x3c)                                                
                                {        
                                          memset(buf, 0, 16)
                                        **********此處省略**********
                                }
                                if(        buf[3]==0x04 && buf[7]==0x3c)                                                               
                                {
                                          memset(buf, 0, 16)
                                      **********此處省略**********
                                }
                                
                                ......................        
                               總共15個IF判斷
                        
                                break;        
                        
                        case 0X78:             //對應該抬起 指令 78后進行比較        
               
                                if(buf[0]==0xAA && buf[7]==0x3c)               //   接收完成
                        {        
                                for(i=0;i<16;i++)                                   //清空緩存區
                                {
                                        buf[ i]=0;
                                }
                                                               
                                //memset(buf, 0, 16)                              //清空緩存區   感覺這個函數比較費時,所以沒用 ,求指教
                        }
                                
                                  break;  
                                default:break;
                        }
}


目前程序運行正常。
請問,如果數據接收慢,當case 0X79: 跑完了,用戶指令才來,或者我要比較指令01 。但可能跑到03去比較了。這時候 01 才到。那么這一次不執行。退出 case 0X79: 這時候緩存區未被清空,(此處為單次點擊)
當抬起屏幕的時候指令78來了,會覆蓋緩存區 ,然后 switch(buf[1]) 在while(1) 里一直調用。直到清空
(正常操作點擊屏幕按下抬起不作停留 。屏幕下發數據是  AA 79**********   AA 78 ********** 中間有很短的間隔)
這次點擊那就無效了。
如果在case 0X79后面加上while (buf[7]!=0x3c) 防止沒接收完就判斷,會有多大影響。謝謝大家

作者: ucmic    時間: 2021-10-13 07:45
參考宋老師的串口接收部份。百度金沙灘工作室
作者: ly1972001    時間: 2021-10-13 08:00
再加緩存,就不怕buf[]的變化了。當一幀數據接收完畢,置標志位,放入緩存,再進行數據處理。
作者: npn    時間: 2021-10-13 08:09
請提供下波特率和晶振頻率確定是否為誤碼率高。
作者: 18701931930    時間: 2021-10-13 08:21
如果你的單片機處理速度比較慢,那就降低波特率。或者采用閉環控制的方式。
作者: xuyaqi    時間: 2021-10-13 08:35
應該是一幀數據接收完設置標志,再進行判斷,不應該收一個判斷一個。
作者: happy2058    時間: 2021-10-13 09:51
npn 發表于 2021-10-13 08:09
請提供下波特率和晶振頻率確定是否為誤碼率高。

24M 1T  115200
作者: xstong    時間: 2021-10-13 10:16
總體思路:中斷僅緩存接收數據,接收完畢喚醒任務處理數據。
使用一個定時器,每次串口中斷接收到一個字節,緩存數據后更新定時器延后一段時間產生定時器超時中斷,只要串口連續接收到數據,超時中斷不會產生,反之只要定時器發生超時中斷,則判定為一幀連續數據接收完畢。
整個串口數據接收過程,全部由串口和定時器中斷完成,無需任務參與,任務只需要在接收完畢后由定時器中斷喚醒后做數據幀解析處理。
如果其它功能應用對中斷占用時間不敏感,可以直接在定時器超時中斷里面處理數據幀。全程任務完全無需參與了。
作者: npn    時間: 2021-10-13 11:00
happy2058 發表于 2021-10-13 09:51
24M 1T  115200

串口需要用 22.1184Mhz 或 33.1776Mhz 才可以的。
作者: lengrudie    時間: 2021-10-13 11:50
增加數據緩存是比較好的方法,可以的話最好做個環形隊列,先進先出。
作者: 笨笨兔    時間: 2021-10-13 14:12
建議改變整個程序結構,那樣更簡單,更有效。
作者: yzwzfyz    時間: 2021-10-13 17:10
所有的中斷程序處理時間,不大于1個字節的串行拼裝時間,你能做到就可以。
作者: xiao_yyp    時間: 2021-10-13 17:17
加緩存, 數據接收完畢,設置標志位,放入緩存后再進行數據處理

作者: 188610329    時間: 2021-10-13 20:46
做緩沖池,比如你一個指令8個字節,你做一個128字節的緩沖池,最多保存16個指令,那么,應該就沒啥問題了。




歡迎光臨 (http://m.raoushi.com/bbs/) Powered by Discuz! X3.1