(中煤科工集團(tuán)重慶研究院有限公司,重慶 400039)
工業(yè)領(lǐng)域中,設(shè)備儀器儀表采用RS485通信協(xié)議進(jìn)行通信時,報文大致可以分為三類,通信握手類、指令類和數(shù)據(jù)類。通信握手報文一般用于診斷設(shè)備是否在線,獲取設(shè)備當(dāng)前的狀態(tài)等。而指令類報文則包含讀、寫兩種指令,一般通過上位機(jī)發(fā)出,讓設(shè)備完成相應(yīng)的動作。數(shù)據(jù)類報文則包括關(guān)鍵的數(shù)據(jù)信息,如加氣機(jī)的加氣交易等等信息。數(shù)據(jù)類報文在以上三種報文中長度最長,優(yōu)先級最高,傳輸中所占用的資源也最多。
加氣機(jī)完整的離線交易信息包括交易流水號、IC卡卡號、氣品種類(CNG/LNG)、加氣槍號、加氣時長、加氣氣量、單價、金額、折扣等信息。離線狀態(tài)下,加氣機(jī)加完一筆氣將會存儲以下信息如表1所示,交易信息是消費(fèi)、記賬、扣款的唯一依據(jù),所以必須保證所有記錄在加氣機(jī)恢復(fù)通訊后立即上傳至后臺。
當(dāng)鏈路恢復(fù)之后,主機(jī)PC會下發(fā)索取離線交易的命令,如表2所示。
由于交易流水號必須保證唯一性,所以這里引入了交易計數(shù)器的概念,是為了合理的利用存儲區(qū)資源并且進(jìn)行離線交易的管理。
以基于STM32處理器的加氣機(jī)主板為例,用鐵電保存交易計數(shù)器的值, 將W25的存儲區(qū)按照交易數(shù)據(jù)的大小等量劃分為1萬個存儲區(qū),每個存儲區(qū)存儲1組如上表2中的交易信息,編號從0~9999,用NextRecord/SendRecord標(biāo)識。NextRecord的值表示下一條交易緩存區(qū)的編號,而SendRecord的值表示未上傳交易緩存區(qū)的位置。
表1 加氣機(jī)離線交易格式
表2 PC機(jī)獲取加氣機(jī)離線交易格式
未有交易產(chǎn)生時,NextRecord/SendRecord初始化為0。當(dāng)?shù)谝粭l交易記錄產(chǎn)生后,NextRecord的值為1,當(dāng)此條交易記錄上傳至加氣機(jī)后,NoSdRecord的值加1遞增,表示第0個緩存區(qū)的記錄已經(jīng)上傳,第1個緩沖區(qū)的記錄還未上傳。第二個交易產(chǎn)生后NextRecord++,上傳PC成功后NoSdRecord++,以此類推,待數(shù)值達(dá)到10000時歸零,以前的交易將被覆蓋,存儲區(qū)循環(huán)利用。
這樣當(dāng)離線交易產(chǎn)生時,NextRecord會持續(xù)累加,而NoSdRecord會保持不變,所以離線交易數(shù)目N可以用如下公式計算出來。
N=|NextRecord - NoSdRecord|
這里NextRecord+1 ≠ NoSdRecord,若相等表示緩存區(qū)已滿,必須停止加氣交易,待交易記錄上傳,緩存區(qū)騰出空間后,才能繼續(xù)存儲交易記錄。
以一臺加氣機(jī)存儲的最多離線交易記錄條數(shù)(2萬條)為例,RS485通信中常規(guī)的波特率是9600 bps,那么傳輸萬2萬條離線交易的時間大約為1個小時。
以上是信道滿負(fù)荷最優(yōu)情況下理論計算出的數(shù)據(jù)傳輸時間,最優(yōu)是指單個設(shè)備與單個主機(jī)進(jìn)行通訊,設(shè)備持續(xù)發(fā)送,主機(jī)持續(xù)接收,無錯誤報文出現(xiàn)。
而實(shí)際設(shè)備與主機(jī)進(jìn)行通信時,為了保障數(shù)據(jù)的有效傳輸,往往引入了應(yīng)答機(jī)制。也就是主機(jī)每次正確接收設(shè)備傳輸來的數(shù)據(jù)后,都要回復(fù)ACK應(yīng)答包,設(shè)備收到了主機(jī)傳輸來的ACK應(yīng)答包后,才開始下一個報文的上送。
圖1 RS485數(shù)據(jù)傳輸應(yīng)答示例
按照上文所述加氣機(jī)2萬條交易記錄為例,傳輸所占的時長大約為2個小時,信道的利用率(不含ACK應(yīng)答)約為50%。所以,當(dāng)批量傳輸數(shù)據(jù)的時候,RS485的這種簡單詢問應(yīng)答的傳輸機(jī)制會產(chǎn)生大量的時間成本,嚴(yán)重影響系統(tǒng)的實(shí)時性和可靠性。然而,TCP的滑動窗口技術(shù)能有效的解決數(shù)據(jù)傳輸中的時間冗余,提高信道的利用率。
滑動窗口協(xié)議,是TCP使用的一種流量控制方法。該協(xié)議允許發(fā)送方在停止并等待確認(rèn)前可以連續(xù)發(fā)送多個分組。發(fā)送方不必每發(fā)一個分組就停下來等待確認(rèn)[1]?;瑒哟翱趨f(xié)議具有加速數(shù)據(jù)傳輸、糾錯控制和流量控制功能。
滑動窗口協(xié)議的基本原理就是在任意時刻,發(fā)送方都維持了一個連續(xù)的允許發(fā)送的幀的序號,稱為發(fā)送窗口;同時,接收方也維持了一個連續(xù)的允許接收的幀的序號,稱為接收窗口[2]。發(fā)送窗口和接收窗口的序號的上下界不一定要一樣,甚至大小也可以不同。不同的滑動窗口協(xié)議窗口大小一般不同。發(fā)送方窗口內(nèi)的序列號代表了那些已經(jīng)被發(fā)送,但是還沒有被確認(rèn)的幀,或者是那些可以被發(fā)送的幀[6]。
TCP是全雙工協(xié)議,發(fā)送方和接收方是對等的。對于TCP會話的發(fā)送方,任何時候在其發(fā)送緩存內(nèi)的數(shù)據(jù)都可以分為4類[3]:
(1)已經(jīng)發(fā)送并得到對方ACK的數(shù)據(jù)包;
(2)已經(jīng)發(fā)送但還未收到對方ACK的數(shù)據(jù)包;
(3)未發(fā)送但對方允許發(fā)送的數(shù)據(jù)包;
(4)未發(fā)送且對方不允許發(fā)送的數(shù)據(jù)包。
已經(jīng)發(fā)送但還未收到對方ACK的數(shù)據(jù)包和未發(fā)送但對方允許發(fā)送的數(shù)據(jù)包這兩部分?jǐn)?shù)據(jù)稱之為發(fā)送窗口。
TCP建立連接的初始,接收方會告訴發(fā)送方自己接收窗口大小,比如10。
圖3 TCP滑動窗口數(shù)據(jù)收到正序的數(shù)據(jù)
如圖3所示,滑動窗口包含已發(fā)送但未收到確認(rèn)的字節(jié)和允許發(fā)送但尚未發(fā)送的字節(jié)[4]。當(dāng)上圖中紅色的區(qū)域數(shù)據(jù)都被接收到之后,那么滑動窗口將會向右移動。窗口兩個邊沿的相對運(yùn)動增加或減少窗口的大小從而讓網(wǎng)絡(luò)數(shù)據(jù)傳輸避免了擁堵。
數(shù)據(jù)的接收可以分為正序或者亂序,正序是指接收方按發(fā)送方正常的發(fā)送序列接收到數(shù)據(jù),而亂序是指接收方?jīng)]有按照發(fā)送方正常的發(fā)送序列接收數(shù)據(jù),也就是存在丟包[5]。對于丟包的亂序數(shù)據(jù),接收方暫時存儲起來,避免網(wǎng)絡(luò)重復(fù)傳輸。
圖4 TCP滑動窗口收到亂序的數(shù)據(jù)
如圖4所示,字節(jié)(序號6、7)比字節(jié)(序號5)先收到接收方的確認(rèn),那么待字節(jié)5收到接收方的確認(rèn)后,滑動窗口才會右移。
圖5 RS485 OSI模型結(jié)構(gòu)圖
RS485協(xié)議的網(wǎng)絡(luò)層和傳輸層是開放式的,沒有統(tǒng)一的標(biāo)準(zhǔn),需要根據(jù)實(shí)際的情況自定義。由于傳輸是PC和加氣機(jī)點(diǎn)對點(diǎn)的通信,網(wǎng)絡(luò)層和數(shù)據(jù)鏈路層比較簡單。同時針對加氣機(jī)離線交易數(shù)據(jù)量大,占用時間多的實(shí)際情況,將TCP滑動窗口的協(xié)議引入了RS485的傳輸層,主要是基于提高數(shù)據(jù)傳輸速率,保障數(shù)據(jù)傳輸可靠性的考慮。
在傳統(tǒng)RS485通信協(xié)議中,物理層、數(shù)據(jù)鏈路層、網(wǎng)絡(luò)層、傳輸層遠(yuǎn)沒有TCP強(qiáng)大,因?yàn)闆]有強(qiáng)大的底層協(xié)議做支撐,RS485一般在傳輸層實(shí)現(xiàn)簡單的單次數(shù)據(jù)包發(fā)送的停等協(xié)議。
如上圖1所示,PC機(jī)索取加氣機(jī)離線交易,加氣機(jī)上傳單條離線交易后隨即進(jìn)入等待PC機(jī)發(fā)回確認(rèn)ACK包的狀態(tài)。
對比TCP協(xié)議中的滑動窗口,RS485發(fā)送方和接收方同時維護(hù)了一個發(fā)送緩存和接收緩存,窗口大小可以看作為1,代表1個數(shù)據(jù)包。由于發(fā)送方接收到第N個數(shù)據(jù)包的響應(yīng)后,才開始第N+1個數(shù)據(jù)包的發(fā)送,那么接收方接收到的數(shù)據(jù)包必定是正序的。為了提高數(shù)據(jù)的傳輸速率,減少停止等待的時間浪費(fèi),有必要提高窗口的大小。
假設(shè)RS485應(yīng)用層的數(shù)據(jù)傳輸協(xié)議采用TCP滑動窗口的方式,窗口的大小調(diào)整為N,與TCP 不同的是這里的N指的是N個數(shù)據(jù)包,而非字節(jié)數(shù)。
圖6 RS485數(shù)據(jù)傳輸采用TCP滑動窗口模式
還以加氣機(jī)離線交易數(shù)據(jù)上傳為例,假設(shè)在通信效率很高的情況下,也就是主機(jī)發(fā)出的數(shù)據(jù)包,設(shè)備都能夠有效響應(yīng),并且響應(yīng)一次主機(jī)就能收到ACK。
圖6(1)中是設(shè)備連續(xù)收到N包數(shù)據(jù)后,回復(fù)N個ACK的示例。由于RS485常用的是半雙工的通信方式,所以圖6(1)中,主機(jī)在收到設(shè)備的離線交易數(shù)據(jù)之后,設(shè)備線程必須停止發(fā)送數(shù)據(jù)等待主機(jī)下發(fā)的ACK響應(yīng),這種模式與圖2提到的發(fā)送應(yīng)答模式在效率上并無多大區(qū)別。
實(shí)際的ACK應(yīng)答包很短,有效數(shù)據(jù)很少,所以完全可以用一個ACK應(yīng)答包來涵蓋Data(0)至Data(N-1)N包數(shù)據(jù)的應(yīng)答響應(yīng),如圖5中(2)所示。這種模式下ACK響應(yīng)的數(shù)量從N個減為1個,效率大大提高了[8]。
表1 RS485 采用TCP滑動窗口模式ACK報文格式包頭主機(jī)ID設(shè)備IDACK(0), ACK(1),…,ACK(8)ACK(N-1)包尾。
設(shè)備在發(fā)送N個數(shù)據(jù)包至主機(jī)后,立即啟動定時器等待主機(jī)返回的ACK,在定時器超時之前接收到ACK組合后便對ACK包進(jìn)行解析。假設(shè)N個數(shù)據(jù)包的ACK全部收到,則滑動窗口右移,進(jìn)行下一組數(shù)據(jù)包的發(fā)送。如果N個數(shù)據(jù)包中,有個別數(shù)據(jù)包沒有收到,則發(fā)送相應(yīng)的數(shù)據(jù)包,并啟動定時器接收主機(jī)發(fā)送的下一個ACK組合。
同時為了保證RS485數(shù)據(jù)傳輸?shù)目煽啃?,引入流控、糾錯的機(jī)制。
圖7 RS485數(shù)據(jù)傳輸采用的糾錯和流控機(jī)
RS485數(shù)據(jù)傳輸受環(huán)境因素(閃電、電磁干擾)等的影響,傳輸過程中會出現(xiàn)錯包、丟包現(xiàn)象,為了保障數(shù)據(jù)的完整性引入錯誤重傳機(jī)制即糾錯機(jī)制。如果窗口較大,同時有多個加氣機(jī)上傳離線交易,PC機(jī)疲于應(yīng)付的情況下,則有必要進(jìn)行流量的控制。
圖7(a)為本文所闡述的RS485數(shù)據(jù)傳輸?shù)募m錯原理圖,主機(jī)和設(shè)備同時維護(hù)一個數(shù)據(jù)包為N的窗口。
(1)主機(jī)請求設(shè)備上送數(shù)據(jù),發(fā)出Req(Req包含當(dāng)前窗口序列號Q,窗口大小N,需要設(shè)備發(fā)送的數(shù)據(jù)包序列號0…N-1等),當(dāng)Req發(fā)出后立即啟動數(shù)據(jù)接收超時定時器,當(dāng)定時器超時時觸發(fā)數(shù)據(jù)包接收機(jī)制,接收機(jī)制用來統(tǒng)計接收到的有效數(shù)據(jù)包的個數(shù)[7]。
(2)主機(jī)接收機(jī)制判斷當(dāng)前的窗口Q未接收到完整的數(shù)據(jù)包,丟失了其中D(N-2)、D(N-1)兩個數(shù)據(jù)包,立即啟動重傳機(jī)制再次發(fā)出Req(此時的Req僅包含需要重傳的數(shù)據(jù)包D(N-2)、D(N-1))。
(3)當(dāng)主機(jī)收到當(dāng)前窗口Q所有的數(shù)據(jù)包后,發(fā)出Ack(ALL)指令,表明當(dāng)前的數(shù)據(jù)包全部被有效接收,此時當(dāng)前的窗口傳輸完成。
PC端和DEVICE同時維護(hù)一個值相同的Receive_map和Send_map[9],PC端不斷查詢Receive_map并把值發(fā)給DEVICE端,DEVICE端查詢接收到的Receive_map(這里等于Send_map),并發(fā)送給DEVICE端[10]。當(dāng)所有bitmap里面代表的當(dāng)前窗口的數(shù)據(jù)包發(fā)送完成后,當(dāng)次數(shù)據(jù)傳輸完成。為了方便起見,本例的bitmap設(shè)置為0xFFFFFFFF,每位代表一個數(shù)據(jù)包,共標(biāo)志32個數(shù)據(jù)包的發(fā)送接收狀態(tài)。此時的窗口大小也為32。
圖7(b)為流量控制機(jī)制,當(dāng)主機(jī)收到加氣機(jī)發(fā)送的三個離線數(shù)據(jù)包后,出現(xiàn)了網(wǎng)絡(luò)擁堵的緊急情況,主機(jī)立即發(fā)出Flow(4)流控包讓對應(yīng)的加氣機(jī)停止上傳離線交易數(shù)據(jù),待網(wǎng)絡(luò)恢復(fù)之后,重新發(fā)送請求報Req恢復(fù)離線交易的上傳。
為了更好地闡述RS485應(yīng)用滑動窗口的思想,用狀態(tài)機(jī)表示以上的算法如圖8所示。
圖8 狀態(tài)機(jī)表示RS485滑動窗口技術(shù)
這樣傳輸N個數(shù)據(jù)包,只有1個ACK總應(yīng)答包,在通信良好的情況下,信道的利用率大大提高了[11]。主機(jī)接收從機(jī)發(fā)送數(shù)據(jù)等待的時間大大減少了。并且該機(jī)制引入了糾錯以及流控機(jī)制,有效避免了差錯引起的擁堵以及冗余時間成本的浪費(fèi)[12]。
RS485采用滑動窗口模式上傳離線交易的協(xié)議與傳統(tǒng)單數(shù)據(jù)包的停等協(xié)議相比,在效率上具有較大的優(yōu)勢,且滑動窗口越大效率愈發(fā)明顯。
滑動窗口大小為Wn,數(shù)據(jù)包大小為S(字節(jié)),波特率為Boud(字節(jié)/秒)。如圖9所示:
T1:主機(jī)發(fā)送數(shù)據(jù)包的等待時間
T2:數(shù)據(jù)包的傳輸時間
T3:數(shù)據(jù)包ACK的發(fā)送準(zhǔn)備時間
T4:設(shè)備應(yīng)答ACK的傳輸時間
按照圖9(a)傳統(tǒng)停等協(xié)議下,發(fā)送N個數(shù)據(jù)包,所需要的時間為:
TL=N*(T1+T2+T3+T4)
(1)
其中:T1遠(yuǎn)小于T2,而T3又遠(yuǎn)小于T4。T2和T4按照實(shí)際傳輸?shù)淖止?jié)數(shù)計算時間。9 600 bps波特率下,1秒鐘傳輸1200字節(jié)數(shù)據(jù)。
按照圖9(b)滑動窗口模式下,發(fā)送N個數(shù)據(jù)包所需要的時間為:
圖9 兩種模式離線交易上傳時間統(tǒng)計
TH=N*(T1+T2) +T3'+T4'
(2)
其中:T1遠(yuǎn)小于T2,而T3又遠(yuǎn)小于T4',隨著窗口的增大,由于T4'包含了窗口所有數(shù)據(jù)包的ACK,所以T4'將會遠(yuǎn)大于T2。
RS485信道優(yōu)良的理想情況下(傳輸無錯包或者丟包),滑動窗口模式與傳統(tǒng)停等應(yīng)答模式對比,節(jié)省的時間大約T' =TH-TL:
T'=N*(T3+T4)-(T3'+T4')
(3)
單片機(jī)一個while(1)大循環(huán)約為12 ms,每次大循環(huán)都發(fā)送一次離線交易(數(shù)據(jù)通過DMA傳送)且系統(tǒng)其他部件需要占用的時間至少為10 ms,等待ACK占用的時間大約為10 ms。那么T3至少應(yīng)該為20 ms。
在滑動窗口模式下,無需等待ACK響應(yīng),系統(tǒng)可以以最快的速度發(fā)送數(shù)據(jù)包,省去了中間ACK的響應(yīng)時間,最后一個ACK響應(yīng)包包含了之前所有的數(shù)據(jù)包的響應(yīng)。
由于波特率較低,RS485的數(shù)據(jù)包一般不易過長,過長在傳輸中勢必影響整個系統(tǒng)的可靠性,離線交易每條大約120字節(jié),傳輸時間為100 ms。傳輸數(shù)據(jù)包的個數(shù)N與節(jié)省的時間T'函數(shù)曲線如圖10所示。
圖10 傳輸數(shù)據(jù)包個數(shù)N與節(jié)省時間T'坐標(biāo)圖
如圖10所示,T'≈0.8 N,每發(fā)送一個數(shù)據(jù)包節(jié)省大概8 ms 的時間(DMA緩存開的足夠大),可見數(shù)據(jù)包個數(shù)越多系統(tǒng)的效率就越高。
綜上所述,可見工業(yè)設(shè)備數(shù)據(jù)通信領(lǐng)域,特別是RS485協(xié)議上層應(yīng)用借鑒TCP滑動窗口協(xié)議可以極大地提高數(shù)據(jù)傳輸效率,有效的解決因通信速率低引起的數(shù)據(jù)堵塞,數(shù)據(jù)冗余,以及傳輸時間成本過高的問題。本文在TCP滑動窗口協(xié)議的基礎(chǔ)上將糾錯流控機(jī)制加入到RS485的傳輸協(xié)議當(dāng)中,可以有效的提高數(shù)據(jù)傳輸?shù)目煽啃砸约皩?shí)時性。