Modbus 續篇一:ASCII&RTU兩種傳輸方式整理!

我們所說的 ASCII或 RTU方式,僅適用於標準的 Modbus網絡,它定義了在這些網絡上連續傳輸的消息段的每一位,以及決定怎樣將信息打包成消息域及如何解碼。

下表是ASCII協議和RTU協議進行的比較:

Modbus 續篇一:ASCII&RTU兩種傳輸方式整理!

通過比較可以看到,ASCII 協議擁有開始和結束標記,因此在進行程序處理時能更加方便,傳輸的都是可見的ASCII字符,所以進行調試時就更加的直觀,它的 LRC校驗也比較容易。

但因傳輸的都是可見的ASCII字符,RTU傳輸的數據每一個字節 ASCII都要用兩個字節來傳輸,比如 RTU傳輸一個十六進制數 0xF9,ASCII 就需要傳輸’F’’9’的 ASCII碼 0x39和0x46兩個字節,這樣它的傳輸的效率就比較低。

所以一般來說,如果所需要傳輸的數據量較小可以考慮使用ASCII協議,如果所需傳輸的數據量比較大,最好能使用RTU協議。

ASCII 模式

當控制器設為在 Modbus網絡上以ASCII(美國標準信息交換代碼)模式通信,在消息中的每個 8Bit字節都作為兩個 ASCII字符發送。這種方式的主要優點是字符發送的時間間隔可達到1秒而不產生錯誤。

代碼系統:

· 十六進制,ASCII字符0...9,A...F

· 消息中的每個ASCII字符都是一個十六進制字符組成

每個字節的位:

· 1個起始位

· 7個數據位,最小的有效位先發送

· 1個奇偶校驗位,無校驗則無

LRC 域是一個包含一個8位二進制值的字節。LRC 值由傳輸設備來計算並放到消息幀中,接收設備在接收消息的過程中計算 LRC,並將它和接收到消息中 LRC域中的值比較,如果兩值不等,說明有錯誤。

LRC 校驗比較簡單,它在 ASCII協議中使用,檢測了消息域中除開始的冒號及結束的回車換行號外的內容。它僅僅是把每一個需要傳輸的數據按字節疊加後取反加1即可。

下面是它的VC代碼:

BYTE GetCheckCode(const char * pSendBuf, int nEnd)//獲得校驗碼

{

BYTE byLrc = 0;

char pBuf[4];

int nData = 0;

for(i=1; i

{

//每兩個需要發送的ASCII碼轉化為一個十六進制數

pBuf [0] = pSendBuf [i];

pBuf [1] = pSendBuf [i+1];

pBuf [2] = '/0';

sscanf(pBuf,"%x",& nData);

byLrc += nData;

}

byLrc = ~ byLrc;

byLrc ++;

return byLrc;

}

CRC 校驗

CRC域是兩個字節,包含一16位的二進制值。它由傳輸設備計算後加入到消息中。接收設備重新計算收到消息的CRC,並與接收到的CRC域中的值比較,如果兩值不同,則有誤。

CRC添加到消息中時,低字節先加入,然後高字節。

編程方法如下:

①裝如一個16位寄存器,所有數位均為1。

②該16位寄存器的高位字節與開始8位字節進行“異或”運算。運算結果放入這個16位寄存器。

③把這個16寄存器向右移一位。

④若向右(標記位)移出的數位是1,則生成多項式1010000000000001和這個寄存器進行“異或”運算;若向右移出的數位是0,則返回③。

⑤重複③和④,直至移出8位。

⑥另外8位與該十六位寄存器進行“異或”運算。

⑦重複③~⑥,直至該報文所有字節均與16位寄存器進行“異或”運算,並移位8次。

⑧這個16位寄存器的內容即2字節CRC錯誤校驗,被加到報文的最高有效位。

CRC添加到消息中時,低字節先加入,然後高字節。下面是它的VC代碼:

WORD GetCheckCode(const char * pSendBuf, int nEnd)//獲得校驗碼

{

WORD wCrc = WORD(0xFFFF);

for(int i=0; i

{

wCrc ^= WORD(BYTE(pSendBuf[i]));

for(int j=0; j<8; j++)

{

if(wCrc & 1)

{

wCrc >>= 1;

wCrc ^= 0xA001;

}

else

{

wCrc >>= 1;

}

}

}

return wCrc;

}

對於一條RTU協議的命令可以簡單的通過以下的步驟轉化為ASCII協議的命令:

1、 把命令的CRC校驗去掉,並且計算出LRC校驗取代。

2、 把生成的命令串的每一個字節轉化成對應的兩個字節的ASCII碼,比如0x03轉化成0x30,0x33(0的ASCII碼和3的ASCII碼)。

3、 在命令的開頭加上起始標記“:”,它的ASCII碼為0x3A。

4、 在命令的尾部加上結束標記CR嗎,LF(0xD,0xA),此處的CR,LF表示回車和換行的ASCII碼。

Modbus 續篇一:ASCII&RTU兩種傳輸方式整理!


分享到:


相關文章: