新聞中心

        EEPW首頁 > 嵌入式系統 > 設計應用 > 51單片機多機通信協議

        51單片機多機通信協議

        作者: 時間:2016-11-30 來源:網絡 收藏
        做自己以前沒做過的東西,總會有各種躊躇,害怕做不出來,其實要是真的開始去做了,問題就解決大半了。 在家沒網,就開始寫了, 熬了兩夜,加一個半天,總算是完成了通信協議,經調試,可以正常工作。 如果有孩子也要做這個,可以參考一下哈! 別的不多說,貼代碼。


        本文引用地址:http://www.104case.com/article/201611/324031.htm
        //-------------------------------------------------
        //主機程序,主機座控制,用中斷法
        //-----------------------------------------------

        #include "basic.h"


        //---------------------------------------------------
        //宏定義

        #define EN_ADDSEND TB8=1;//發送尋址,搜尋從機
        #define EN_DATASEND TB8=0;//發送數據

        #define M_S 0Xf0//握手后的命令字,主機到從機
        #define S_M 0Xf1//握手后的命令字,從機到主機
        #define M_SOK 0Xf2//主到從準備完成,從機發送的反饋信息
        #define S_MOK 0xf3//從到主準備完成,主機發送的反饋信息
        #define STOP 0xf4//主機到從機發送結束

        #define ERROR 0xf5//錯誤
        #define Response 0xf6//應答信號
        #define CONTINUE 0xf7//接受數據之后給對方發送的反饋,請求繼續
        #define OK 0xf8

        //--------------------------------------------------
        //數據定義
        uchar DATA[20]={0};//從機返回的狀態值

        uchar CMD[20]= {0x44,0x44,0x44,0x55,0x55,0x55,0x47,0x45,0x65,0x35,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,};// 主機給從機發送的命令
        uchar state=0;//狀態值,進行中斷判斷
        uchar Address;//呼叫從機地址
        uchar temp=0;//SBUF緩存
        uchar *Position=0;//數據指針,指定數據更新的位置

        //---------------------------------------------
        //串口1初始化,用于和從機通訊
        void Uart1_Init(void) //9600bps@11.0592MHz
        {
        PCON &= 0x7F; //波特率不倍速
        SCON = 0xD0; //9位數據,可變波特率
        AUXR |= 0x40; //定時器1時鐘為Fosc,即1T
        AUXR &= 0xFE; //串口1選擇定時器1為波特率發生器
        TMOD &= 0x0F; //清除定時器1模式位
        TMOD |= 0x20; //設定定時器1為8位自動重裝方式
        TL1 = 0xDC; //設定定時初值
        TH1 = 0xDC; //設定定時器重裝值
        ET1 = 0; //禁止定時器1中斷
        TR1 = 1; //啟動定時器1
        EA=1; //總中斷啟動
        SM2=0;
        ES=1;
        }

        //------------------------------------------
        //查詢法發送一個數據,TB8=0;
        void SendByte (uchar date)
        {

        //EN_DATASEND;//TB8=0;
        TB8=1;
        SBUF=date;
        while(!TI);
        TI=0;
        }

        //-----------------------------------
        //尋址從機
        void Search(uchar ADD)
        {
        //EN_ADDSEND;
        TB8=1;
        SBUF=ADD;
        while(!TI);
        TI=0;
        }


        //主機向從機發送命令 //因為主機為控制端,為便于控制從機,所以選擇用查詢法而不選用中斷
        void M_S_Protocol(uchar add,uchar *m)//三個參量分別為從機地址,命令的字節數,命令的位置
        {
        state=1;
        ES=1;
        Position=m;
        Search(add);
        }
        //主機接收從機狀態,同樣也為查詢法不用中斷
        void S_M_Protocol(uchar add,uchar *m)//三個參量分別為從機地址,命令的字節數,命令的位置
        {
        state=4;
        ES=1;
        Position=m;
        Search(add);
        }
        void M_S_Send(uchar add,uchar *m)//主機到從機整個過程
        {
        M_S_Protocol(add,m);
        while(state);
        ES=0;
        }
        void S_M_Send(uchar add,uchar *m)//從機到主機的整個過程
        {
        S_M_Protocol(add,m);
        while(state);
        ES=0;
        }
        //-----------------------------
        //主函數,主機主函數主要用于與GPRS和從機之間做橋接
        void main()
        {
        Uart1_Init();
        while(1)
        {
        S_M_Send(0x01,CMD);
        }
        }
        void UART1() interrupt 4
        {
        RI=0;//清除中斷標志
        temp=SBUF;
        if(state)//處于傳輸狀態
        {
        switch(state)
        {
        //-----------------------------------------------------------------
        //---------------------M_S部分--------------------------------
        case 1:
        {
        if(temp==Response)//尋址成功
        {
        SendByte(M_S); //發送M_S命令
        state=2; //轉換狀態
        break;
        }
        /*else//尋址不成功,通信結束,轉換為非通信狀態
        {
        state=0;
        SendByte(STOP);//發送通信停止命令
        break;
        }*/
        break;
        }
        case 2:
        {
        if(temp==M_SOK)//M_S得到回應
        {
        state=3;
        SendByte(*Position);//發送第一字節
        break;
        }
        break;
        }
        case 3:
        {
        if(temp==CONTINUE) //從機繼續要求數據
        {
        if(Position-CMD<19)//數組長度判斷
        {
        Position++;
        SendByte(*Position);//發送數據
        break;

        }
        else//數組溢出,停止通信
        {
        state=0;
        SendByte(STOP);
        break;
        }
        }
        break;
        }
        上一頁 1 2 下一頁

        評論


        技術專區

        關閉
        主站蜘蛛池模板: 肇东市| 普格县| 临城县| 库伦旗| 怀柔区| 曲水县| 巩留县| 循化| 闸北区| 南江县| 泸水县| 屏东县| 肥城市| 商城县| 贞丰县| 凌云县| 兴业县| 阿克| 纳雍县| 郧西县| 定南县| 建阳市| 开鲁县| 尖扎县| 郁南县| 北安市| 江达县| 莆田市| 会泽县| 石城县| 酒泉市| 成都市| 扎鲁特旗| 石楼县| 绩溪县| 通许县| 陵川县| 黔东| 土默特左旗| 浦北县| 神农架林区|