久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 2472|回復: 0
打印 上一主題 下一主題
收起左側

PC和單片機通過MODBUS RTU通信

[復制鏈接]
跳轉到指定樓層
樓主
ID:504942 發表于 2019-4-4 17:21 | 只看該作者 回帖獎勵 |倒序瀏覽 |閱讀模式
最近研究了一下MODBUS通信,在STC12C5A60S2單片機上實現了MODBUS協議的部分功能,方便上位機從單片機系統上獲取數據,比如由單片機獲取的溫度、濕度、或者控制信號的狀態等。有了MODBUS協議后,上位機的開發就很方便了,可以使用C#等高級語言通過串口通信,或者使用組態王直接通過串口通信而不需要寫代碼,這些都歸功于MODBUS協議的開放性,很多的組態軟件都能提供對他的支持。甚至通過PLC直接可以和單片機通信,比如在PLC系統上沒有AD時,可以使用單片也來進行AD,然后通過MODBUS返回給PLC進行相應的控制。
通過MODBUS協議可以實現主機和多個從機進行通謝,而每個從機有唯一的地址,主機就靠這個地址和從機進行通信。每一幀數據都要通過CRC進行校驗,保證通信的正確性。
在進行多機通信時只需要把每個從機的串口并到一起即可,見后面的圖。
單片機中3號功能的核心代碼如下:
unsigned char createRespond_M(unsigned char *respondMessage,unsigned char* _messageReceived ,unsigned int* _registerData)
{
    unsigned char  i,j;
    unsigned char  numberOfPoints = 0;
    unsigned char_slaveAddress = 0 ;
    unsigned char  bytesToSend = 0;
    unsigned char  startAddress=0;
    unsigned charcrcCalculation[]={0,0,0};
    unsigned int CntHi= _messageReceived[4];  //將其轉換為int型,然后放到高8位。
    CntHi = CntHi<<8;                    
    numberOfPoints = CntHi| _messageReceived[5];
    if(numberOfPoints > MaxnumberOfPoints)
    {
        return  0;
    }
   
    bytesToSend = 2 *numberOfPoints +5;
    _slaveAddress = _messageReceived[0];
    respondMessage[0] =_slaveAddress;
    respondMessage[1] = 3;
    respondMessage[2] =2 * numberOfPoints;
    startAddress = (((unsigned int)(_messageReceived[2])) << 8) |_messageReceived[3];
    j= 0;
    for (i = 0; i< numberOfPoints; i++)
    {
        respondMessage[i + j + 3] = ((_registerData[startAddress + i] >> 8)& 0xff);
        respondMessage[i + j + 4] =(_registerData[startAddress + i] & 0xff);
        j++;
    }
    calculateCRC(respondMessage, bytesToSend - 2,crcCalculation);
    respondMessage[bytesToSend - 2] = crcCalculation[0];
    respondMessage[bytesToSend - 1] = crcCalculation[1];
    return bytesToSend;
}
//對接收的數據進行CRC檢驗,同時判斷是否為Address所指定的從機地址和是否為function3功能。
bitCheckRecData(unsigned char * RecData,unsigned charAddress)
{
    if(RecData[0] ==Address && RecData[1] == 3)   //地址為自己的地址,同時功能碼為3(function3)
    {
        if(checkCRC(RecData,8))
        {
            return 1;
        }
    }
    return 0;
}
本例中每個從機返回80個字節的數據,1號機返回i+1,  2號機返回2*i+1   ,當然在實際運用中只要自己定義所返回的數據的含義即可。比如1,2字節代表溫度,3,4字節代表濕度,接下來的4個字節代表P0,P1,P2,P3端口的狀態等。可以自由定義,很方便。
具體效果見下圖:
把兩塊板的串口通過杜綁線連在一起。
在TEXTBOX中輸入從機的地址,返回相應的數據
如果輸入的地址從機不存在,那么通信將會超時,就會提示通信故障。這個是根據通信超時來判斷的。

評分

參與人數 1黑幣 +50 收起 理由
admin + 50 共享資料的黑幣獎勵!

查看全部評分

分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏 分享淘帖 頂 踩
回復

使用道具 舉報

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

本版積分規則

小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 国产欧美在线 | 亚洲欧美视频在线观看 | 成人免费视频网 | 国产精品国产a | 嫩呦国产一区二区三区av | 久久久女女女女999久久 | 国产成人小视频 | 91免费在线看 | 在线国产一区二区 | 国产精品揄拍一区二区久久国内亚洲精 | 色婷婷亚洲 | 黄色高清视频 | 日韩成人免费视频 | 国产精品一区二区三区久久久 | 国产欧美一区二区精品忘忧草 | 中文字字幕在线中文乱码范文 | 三极网站| 久久网一区二区三区 | 久久精品小视频 | 国产一级片免费视频 | 久久久免费毛片 | 一区二区三区中文字幕 | 日韩欧美三级 | 欧美亚洲国产日韩 | 9191av| 国产999精品久久久久久 | 91大神在线资源观看无广告 | 亚洲福利一区 | 夜夜草视频 | 韩国理论电影在线 | 日韩av一区二区在线观看 | 精品久久久久久国产 | 免费高清成人 | 久久久精品一区二区 | 欧美成人免费在线 | 亚洲视频中文字幕 | 四季久久免费一区二区三区四区 | 亚洲性人人天天夜夜摸 | 91青娱乐在线 | 成人毛片网 | 日本成人中文字幕 |