Modbus RTU通信協議詳解以及與Modbus TCP通信協議之間的區別和聯系


Modbus通信協議由Modicon公司(現已經為施耐德公司並購,成為其旗下的子品牌)於1979年發明的,是全球最早用於工業現場的總線規約。由於其免費公開發行,使用該協議的廠家無需繳納任何費用,Modbus通信協議采用的是主從通信模式(即Master/Slave通信模式),其在分散控制方面應用極其廣泛,從而使得Modbus協議在全球得到了廣泛的應用。

Modbus通信協議具有多個變種,其具有支持串口(主要是RS-485總線),以太網多個版本,其中最著名的是Modbus RTU,Modbus ASCII和Modbus TCP三種。其中Modbus RTU與Modbus ASCII均為支持RS-485總線的通信協議,其中Modbus RTU由於其采用二進制表現形式以及緊湊數據結構,通信效率較高,應用比較廣泛。而Modbus ASCII由於采用ASCII碼傳輸,並且利用特殊字符作為其字節的開始與結束標識,其傳輸效率要遠遠低於Modbus RTU協議,一般只有在通信數據量較小的情況下才考慮使用Modbus ASCII通信協議,在工業現場一般都是采用Modbus RTU協議,一般而言,大家說的基於串口通信的Modbus通信協議都是指Modbus RTU通信協議。

在此我們着重討論Modbus RTU協議,而Modbus TCP協議則是在RTU協議上加一個MBAP報文頭,由於TCP是基於可靠連接的服務,RTU協議中的CRC校驗碼就不再需要,所以在Modbus TCP協議中是沒有CRC校驗碼,用一句比較通俗的話說就是:Modbus TCP協議就是Modbus RTU協議在前面加上五個0以及一個6,然后去掉兩個CRC校驗碼字節就OK.雖然這句話說得不是特別准確,但是也基本上把RTU與TCP之間的區別說得比較清楚了。

RTU協議中的指令由地址碼(一個字節),功能碼(一個字節),起始地址(兩個字節),數據(N個字節),校驗碼(兩個字節)五個部分組成,其中數據又由數據長度(兩個字節,表示的是寄存器個數,假定內容為M)和數據正文(M乘以2個字節)組成,而RTU協議是采用3.5個字節的空閑時間作為指令的起始和結束,一般而言,只有當從機返回數據或者主機寫操作的時候,才會有數據正文,而其他時候比如主機讀操作指令的時候,沒有數據正文,只需要數據長度即可。(本章的討論只涉及寄存器的讀寫,其他比如線圈的讀寫指令我們暫時不涉及)。在此我們通過兩個指令(0x03H:讀多個寄存器指令以及0x10H:寫多個寄存器指令)來解釋Modbus RTU協議。在此我們使用的RTU設備是深圳市國科偉業通信技術有限公司的ND-1084型485總線I/O模塊

ND-1084型485總線I/O模塊采用RS-485總線通信,支持四路開關量輸出以及八路開關量輸入,我們只講述讀取開關量輸出的狀態以及通過寫指令控制開關量的輸出。其中儲存開關量輸出狀態的四個寄存器分別:0x18E,0x18F,0x190,0x191。在此我們假設模塊的地址為默認的0x01,當我們要去讀取開關量輸出對應的四個寄存器的狀態的時候,我們下發的十六進制的指令為:“01 03 01 8E 00 04 25 DE”,其中“01”為模塊的地址碼,“03”為功能碼,即表示讀寄存器,“01 8E”為寄存器地址,即從該寄存器地址開始讀取數據,“00 04”則表示讀取4個寄存器,而“25 DE”則為前面“01 03 01 8E 00 04”的CRC校驗碼,該數值通過CRC16校驗算法計算出來的,我們會在其他文章中闡述。該指令的完整解讀就是,在地址碼為“01”的模塊中,從“01 8E”寄存器開始,讀取4個寄存器的數據返回至主機。在此,我們可以看到,讀取指令中並沒有什么數據正文,因為它只是讀取相應數量的寄存器,並不需要數據正文,而寫操作指令則相反,我們會在后面講到。

模塊返回的指令是:“01 03 08 00 01 00 01 00 01 00 01 28 D7”,返回的指令內容解讀就是:“01”表示模塊的地址碼,“03”表示該指令是讀操作返回的指令,“08”表示數據長度,在此表示的是8個字節數據正文(即4個寄存器,每個寄存器兩個字節表示),“00 01 00 01 00 01 00 01”是數據正文,表示四個寄存器的狀態,“28 D7”就是CRC16校驗碼。

同樣的當我們執行寫操作的是,我們舉例寫第一個開關量輸出,即寄存器“0x18E”,主機下發的指令為:“01 10 01 8e 00 01 02 00 00 A8 7E”,該指令的解讀就是:“01”表示模塊的地址,“10”表示該指令為寫寄存器,“01 8E”表示從該寄存器地址開始執行寫操作指令“00 01”表示寫多少個寄存器,在此為寫1個寄存器,“02”表示數據長度,表示數據長度為兩個字節,“00 00”表示寫入寄存器的數據,在此表示連通,“A8 7E”為CRC校驗碼。模塊返回的指令和讀取寄存器的返回的指令類似。

前文所述,Modbus TCP協議是在RTU協議前面添加MBAP報文頭,共七個字節長度,其分別的意義是:1.傳輸標志,兩個字節長度,標志Modbus詢問/應答的傳輸,一般默認是00 00。2.協議標志,兩個字節長度,0表示是Modbus,1表示UNI-TE協議,一般默認也是00 00。3.后續字節計數,兩個字節長度,其實際意義就是后面的字節長度,具體情況詳見下文。4.單元標志,一個字節長度,一般默認為00,單元標志對應於Modbus RTU協議中的地址碼,當RTU與TCP之間進行協議轉換的時候,特別是Modbus網關轉換協議的時候,在TCP協議中,該數據就是對應RTU協議中的地址碼,具體情況詳見下文。

通過上面的描述我們差不多能夠理解Modbus RTU協議,我們再說說Modbus TCP通信協議,前面就已經說過TCP協議就是在RTU協議的基礎上去掉校驗碼以及加上五個0和一個6,當是讀取相關寄存器的時候,該說法是沒有錯的,比如上文的“01 03 01 8E 00 04 25 DE”讀取指令,用TCP協議來表述的話,指令是“00 00 00 00 00 06 00 03 01 8E 00 04”,由於TCP是基於TCP連接的,不存在所謂的地址碼,所以06后面一般都是“00”(當其作為Modbus網關服務器掛接多個RTU設備的時候,數值從01-FF).即“00 03 01 8E 00 04”對應的是RTU中去掉校驗碼的指令,前面則是五個0以及一個6。其中6表示的是數據長度,即“00 03 01 8E 00 04”有6個字節長度。而當其為寫操作指令的時候,其指令是“00 00 00 00 00 09 01 10 01 8e 00 01 02 00 00”,其中“00 09”表示后面有9個字節。

Modbus RTU與Modbus TCP讀指令對比

 
MBAP報文頭
地址碼
功能碼
寄存器地址
寄存器數量
CRC校驗
Modbus RTU
01
03
01 8E
00 04
25 DE
Modbus TCP
00 00 00 00 00 06 00
03
01 8E
00 04

指令的涵義:從地址碼為01(TCP協議單元標志為00)的模塊0x18E(01 8E)寄存器地址開始讀(03)四個(00 04)寄存器。

Modbus RTU與Modbus TCP寫指令對比

 
MBAP報文頭
地址碼
功能碼
寄存器地址
寄存器數量
數據長度
正文
CRC校驗
RTU
01
10
01 8E
00 01
02
00 00
A8 7E
TCP
00 00 00 00 00 09 00
10
01 8E
00 01
02
00 00

指令的涵義:從地址碼為01(TCP協議單元標志為00)的模塊0x18E(01 8E)寄存器地址開始寫(10)一個(00 01)寄存器,具體數據長度為2個字節(02),數據正文內容為00 00(00 00)。

來源:https://www.cnblogs.com/woxihuadabai/p/8043188.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM