<dfn id="yhprb"><s id="yhprb"></s></dfn><dfn id="yhprb"><delect id="yhprb"></delect></dfn><dfn id="yhprb"></dfn><dfn id="yhprb"><delect id="yhprb"></delect></dfn><dfn id="yhprb"></dfn><dfn id="yhprb"><s id="yhprb"><strike id="yhprb"></strike></s></dfn><small id="yhprb"></small><dfn id="yhprb"></dfn><small id="yhprb"><delect id="yhprb"></delect></small><small id="yhprb"></small><small id="yhprb"></small> <delect id="yhprb"><strike id="yhprb"></strike></delect><dfn id="yhprb"></dfn><dfn id="yhprb"></dfn><s id="yhprb"><noframes id="yhprb"><small id="yhprb"><dfn id="yhprb"></dfn></small><dfn id="yhprb"><delect id="yhprb"></delect></dfn><small id="yhprb"></small><dfn id="yhprb"><delect id="yhprb"></delect></dfn><dfn id="yhprb"><s id="yhprb"></s></dfn> <small id="yhprb"></small><delect id="yhprb"><strike id="yhprb"></strike></delect><dfn id="yhprb"><s id="yhprb"></s></dfn><dfn id="yhprb"></dfn><dfn id="yhprb"><s id="yhprb"></s></dfn><dfn id="yhprb"><s id="yhprb"><strike id="yhprb"></strike></s></dfn><dfn id="yhprb"><s id="yhprb"></s></dfn>
"); //-->

博客專(zhuān)欄

EEPW首頁(yè) > 博客 > 一文搞懂 Modbus RTU 協(xié)議

一文搞懂 Modbus RTU 協(xié)議

發(fā)布人:xiaomaidashu 時(shí)間:2024-05-15 來(lái)源:工程師 發(fā)布文章

大家好,我是麥鴿,以前寫(xiě)過(guò)一篇文章是關(guān)于modbus協(xié)議的,只是簡(jiǎn)單地做了一下介紹,這次對于modbus RTU協(xié)議進(jìn)行了深入的學(xué)習。

背景

介紹modbus rtu之前,我們可以了解到,Modbus是施耐德電氣公司,于1979年發(fā)明的,是全球第一個(gè)真正用于工業(yè)現場(chǎng)的總線(xiàn)協(xié)議。四十多年過(guò)去了,現在仍然被廣泛使用在各個(gè)工業(yè)控制領(lǐng)域。除了這個(gè)協(xié)議很穩定的原因之外:

  1. 免費;
  2. 方便部署和維護;
  3. 對供應商來(lái)說(shuō),修改移動(dòng)本地的比特或字節沒(méi)有很多限制;

modbus 是OSI模型第七層上的應用層報文傳輸協(xié)議,OSI定義了開(kāi)放系統的層次結構、層次之間的相互關(guān)系以及各層所包括的可能的任務(wù),作為一個(gè)框架來(lái)協(xié)調和組織各層所提供的服務(wù)。

OSI參考模型并沒(méi)有提供一個(gè)可以實(shí)現的方法,而是描述了一些概念,用來(lái)協(xié)調進(jìn)程間通信標準的制定。即OSI參考模型并不是一個(gè)標準,而是一個(gè)在制定標準時(shí)所使用的概念性框架。

modbus在OSI模型中,可以描述為下圖;

圖片

modbus osi模型中的位置

EIA485/TIA485就是RS485,隨著(zhù)技術(shù)不斷發(fā)展,485標準目前是電信行業(yè)協(xié)會(huì )(TIA)維護,所以名稱(chēng)為T(mén)IA-485,當然工程師及應用指南仍繼續用RS-485來(lái)稱(chēng)呼也是沒(méi)問(wèn)題的;

下面我們來(lái)介紹一些串行鏈路協(xié)議。

Modbus 串行鏈路協(xié)議

Modbus串行鏈路協(xié)議是一個(gè)主從模式(主機和從機),半雙工的數據傳輸協(xié)議,485標準通常需要兩條線(xiàn),在某一個(gè)確定時(shí)刻,有一個(gè)主機和從機進(jìn)行通訊。

  • 主從模式:通??偩€(xiàn)上有一個(gè)主機和多個(gè)從機,每個(gè)從機有唯一的ID,主機通過(guò)ID進(jìn)行尋址從機,然后進(jìn)行數據傳輸;
  • 半雙工傳輸:相對應半雙工的是全雙工,全雙工運行發(fā)送數據接收數據同時(shí)發(fā)生,所以半雙工就不難理解了,同一時(shí)刻只能進(jìn)行發(fā)送數據,或者只能接收數據;

整體的結構圖如下所示;

圖片一個(gè)485總線(xiàn)的主從模式

這里我們還要明確幾點(diǎn):

  1. 從機無(wú)法主動(dòng)向從機發(fā)送數據,只有在主機發(fā)送數據給從機(發(fā)送請求),然后從機接收到主機發(fā)送的數據之后,再回傳數據給主機;具體如下所示;

圖片主從模式

正如前面所提到的,modbus是半雙工傳輸的,即主機發(fā)送數據的時(shí)候,是不能接收數據的,所以這里總共分為兩步來(lái)進(jìn)行。

  1. 主機發(fā)送數據的方式有兩種,一個(gè)是 1對1,一個(gè)是1對多,也就是我們常說(shuō)的廣播形式,所有從機都可以收到主機發(fā)送的數據;

    1對1 只需要發(fā)送數據給特定地址的從機即可,廣播只需要把發(fā)送地址設置為0即可,所以廣播地址為0;

這里我們已經(jīng)大致了解了主機和從機之間的數據傳輸的情況,下面我們就再來(lái)介紹一下數據傳輸的具體格式;

傳輸模式

圖片

先來(lái)說(shuō)說(shuō)Modbus有兩種傳輸模式,RTU傳輸模式和ASCII傳輸模式;

  • RTU傳輸:Remote Terminal Unit模式在Modbus中消息由十六進(jìn)制組成,數據密度高,吞吐率高;

  • ASCII傳輸:消息由ASCII 字符發(fā)送效率不及RTU模式,無(wú)法使用RTU模式的定時(shí)管理時(shí),使用ASCII模式;

    比如:0x12會(huì )被整合成兩個(gè)字符發(fā)送:0x31和0x32發(fā)送,

    因為 0x31等于字符1;0x32等于字符2

下面我們會(huì )主要介紹modbus RTU。

幀格式

在講幀格式之前,首先我們想象一下,人與人之間的對話(huà),最基本單元是漢字,然后相互交流就用漢字組成的句子,比如下面的對話(huà);

  • 老板問(wèn):中午吃什么?
  • 小樟說(shuō):吃飯吧!

圖片

所以機器之間的通信也是類(lèi)似的,我們可以把字節當作最基本的數據單元,然后由字節組成句子,也就是通信幀;

但是現在情況出現了變化,對話(huà)的人里,除了小樟,還有一個(gè)小紅,這時(shí)候,為了明確和誰(shuí)說(shuō)話(huà),就需要在對話(huà)前面加上名字:

  • 老板:小樟,中午吃面嗎?
  • 小樟:老板,吃飯去吧。
  • 小紅,沒(méi)有叫他,語(yǔ)言柚子;

圖片

所以我們繼續回到modbus的數據幀格式,這里的協(xié)議定義了一個(gè)基礎通信層的簡(jiǎn)單協(xié)議數據單元(PDU),具體如下圖所示;

圖片

所以這里基本分為四個(gè)部分,地址域,功能碼,數據,差錯校驗(CRC/LRC),統稱(chēng)為ADU (Application Data Unit),基本上進(jìn)行傳輸的數據都要滿(mǎn)足這個(gè)格式,作為一個(gè)完整的幀,對照前面老板的對話(huà)內容,我們這里可以簡(jiǎn)單的理解一下:

  • 地址域:可以理解成 具體和誰(shuí)說(shuō)話(huà);
  • 功能碼:可以理解成 具體動(dòng)作,比如 去做,來(lái)拿,去吃 等等;
  • 數據:可以理解成 具體內容,比如 面,飯 等等,也可以是其他,這里配合上下文,所以是吃的東西;
  • 差錯校驗:可以理解成,說(shuō)出來(lái)的話(huà)必須可以讓人理解,不然別人聽(tīng)不懂??;實(shí)際上在協(xié)議中通常使用CRC或LRC保證傳輸的數據沒(méi)有錯誤;

下面我們再深入分析一下;

PDU

Modbus PDU(protocol data unit)格式被定義為一個(gè)功能代碼,后面跟著(zhù)一組關(guān)聯(lián)的數據。

該數據的大小和內容由功能代碼定義,整個(gè)PDU(功能代碼和數據)的大小不能超過(guò)253個(gè)字節。

每個(gè)功能代碼都有一個(gè)特定的行為,從設備可以根據所需的應用程序行為靈活地實(shí)現這些行為。

PDU規范定義了數據訪(fǎng)問(wèn)和操作的核心概念;但是,從設備可能會(huì )以規范中未明確定義的方式處理數據。

地址域

地址域占用一個(gè)字節,所以一般來(lái)說(shuō)尋址范圍是0~255,一般在系統中用1~147,其他地址暫時(shí)保留,另外,同一個(gè)總線(xiàn)上的從機,每個(gè)地址必須唯一。

其中0是廣播地址;

下面是Freemodbus的一個(gè)從機初始化代碼,0x02就是這個(gè)從機的地址,

eMBInit(MB_RTU, 0x023115200, MB_PAR_NONE);
功能碼

功能碼占一個(gè)字節,所以范圍是 0~255,協(xié)議中規定了功能碼分為三類(lèi):公共功能碼,用戶(hù)自定義功能碼,保留功能碼。整體如下所示;

圖片image-20211224223246059

公共功能碼必須保證它的唯一性,這是由Modbus組織已經(jīng)規定好,并且具有一致性測試的功能碼,所以在一定程度上,它保證了協(xié)議的可復用性。

由上表可知,公共功能碼分為四種,分別是:

  • 離散量輸入:只讀類(lèi)型,單位:bit;
  • 線(xiàn)圈:讀寫(xiě)類(lèi)型,單位:bit;
  • 輸入寄存器:只讀類(lèi)型,單位:字節;
  • 保持寄存器:讀寫(xiě)類(lèi)型,單位:字節;

下面是移植Freemodbus協(xié)議,從機上需要對這四個(gè)公共功能碼處理的回調函數:

//輸入寄存器量
eMBErrorCode eMBRegInputCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNRegs )
{
  eMBErrorCode    eStatus = MB_ENOERR;
  return eStatus;
}
//保持寄存器量
eMBErrorCode
eMBRegHoldingCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNRegs,
                 eMBRegisterMode eMode )

{
    eMBErrorCode    eStatus = MB_ENOERR;
    return eStatus;
}

//線(xiàn)圈數量 
eMBErrorCode
eMBRegCoilsCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNCoils,
               eMBRegisterMode eMode )

{
    eMBErrorCode    eStatus = MB_ENOERR;
    return eStatus;
}

//離散輸入數量 
eMBErrorCode
eMBRegDiscreteCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNDiscrete )
{
    eMBErrorCode    eStatus = MB_ENOERR;
    return eStatus;
}

底層如何傳輸

我們先看一下最底層modbus數據是如何發(fā)送的,沒(méi)錯,看到RS485和232,那我們自然想到了串口。

所以最根本的數據格式可以參考一下串口數據的定義,也就是我們說(shuō)的起始位,數據位,校驗位,數據位;具體如下所示;

圖片

所以這里我們可以規定一下:

起始位+數據位+校驗位(可選)+ 停止位 等于一個(gè)字符;因此這里可以通過(guò)串口的波特率去計算出單個(gè)字符所需要的時(shí)間。

然后我們再看一下,modbus幀是如何發(fā)送的?

在RTU模式中,幀之間的間隔至少為3.5個(gè)字符的空閑時(shí)間間隔,以便于表示幀的開(kāi)始和幀的結束,所以如果想自己整一個(gè)modbus rtu就需要一個(gè)定時(shí)器去結算空閑時(shí)間的長(cháng)度。

圖片3.5字符時(shí)間

整個(gè)數據必須以連續的字符流進(jìn)行發(fā)送,如果兩個(gè)字符之間的長(cháng)度等于1.5個(gè)字符時(shí)間,則認為幀消息不完整,則認為設備不該接收該消息,具體如下所示;

圖片1.5字符時(shí)間

這里需要注意的是RTU需要定時(shí)器中斷的參與,所以,1.5字符時(shí)間和3.5字符時(shí)間的檢測,在串口通訊速率很高的時(shí)候,需要高頻率得進(jìn)入中斷,這就會(huì )增加系統開(kāi)銷(xiāo)。

所以通常在波特率低于19200的時(shí)候,可以嚴格遵守1.5和3.5字符時(shí)間的規定。

如果波特率大于19200的時(shí)候,需要滿(mǎn)足兩個(gè)固定時(shí)間即可:

  • 1.5字符時(shí)間:750 us;
  • 3.5字符時(shí)間:1.75ms;
總結

本文簡(jiǎn)單介紹了modbus rtu協(xié)議,包括串行鏈路通信,幀格式以及硬件鏈路層的消息格式,能力有限,本文難免存在錯誤和紕漏,請不吝賜教。篇幅有限本文先到這里,下一篇介紹一下如何移植Freemodbus協(xié)議以及調試協(xié)議的過(guò)程。

如何本文幫到了您,請幫忙點(diǎn)贊鼓勵一下。


*博客內容為網(wǎng)友個(gè)人發(fā)布,僅代表博主個(gè)人觀(guān)點(diǎn),如有侵權請聯(lián)系工作人員刪除。



關(guān)鍵詞: Modbus RTU

相關(guān)推薦

技術(shù)專(zhuān)區

關(guān)閉
国产精品自在自线亚洲|国产精品无圣光一区二区|国产日产欧洲无码视频|久久久一本精品99久久K精品66|欧美人与动牲交片免费播放
<dfn id="yhprb"><s id="yhprb"></s></dfn><dfn id="yhprb"><delect id="yhprb"></delect></dfn><dfn id="yhprb"></dfn><dfn id="yhprb"><delect id="yhprb"></delect></dfn><dfn id="yhprb"></dfn><dfn id="yhprb"><s id="yhprb"><strike id="yhprb"></strike></s></dfn><small id="yhprb"></small><dfn id="yhprb"></dfn><small id="yhprb"><delect id="yhprb"></delect></small><small id="yhprb"></small><small id="yhprb"></small> <delect id="yhprb"><strike id="yhprb"></strike></delect><dfn id="yhprb"></dfn><dfn id="yhprb"></dfn><s id="yhprb"><noframes id="yhprb"><small id="yhprb"><dfn id="yhprb"></dfn></small><dfn id="yhprb"><delect id="yhprb"></delect></dfn><small id="yhprb"></small><dfn id="yhprb"><delect id="yhprb"></delect></dfn><dfn id="yhprb"><s id="yhprb"></s></dfn> <small id="yhprb"></small><delect id="yhprb"><strike id="yhprb"></strike></delect><dfn id="yhprb"><s id="yhprb"></s></dfn><dfn id="yhprb"></dfn><dfn id="yhprb"><s id="yhprb"></s></dfn><dfn id="yhprb"><s id="yhprb"><strike id="yhprb"></strike></s></dfn><dfn id="yhprb"><s id="yhprb"></s></dfn>