Modbus协议使用的CRC(循环冗余校验)是一种用于确保数据通信完整性和准确性的差错检测方法。在Modbus RTU通信中,CRC校验过程清晰明确,且被广泛应用于工业通信场景。
一、Modbus协议的CRC校验流程
(一)CRC计算步骤
Modbus RTU模式中的CRC校验采用16位CRC(CRC-16)算法,常用多项式为:
x 16 + x 15 + x 2 + 1 x^{16}+x^{15}+x^2+1 x16+x15+x2+1
具体计算流程如下:
-
初始化CRC寄存器
CRC寄存器通常初始化为0xFFFF
。 -
逐字节处理数据帧
依次取出数据帧中的每个字节,进行以下处理:-
将CRC寄存器与字节做异或(XOR)运算
将取出的数据字节与CRC寄存器低8位进行异或运算,结果存入CRC寄存器。 -
逐位移位并检查
对CRC寄存器执行以下过程8次(对应字节中的8位):-
检查CRC寄存器的最低位(LSB):
- 若LSB = 1,则CRC寄存器右移一位后,与预定义的多项式值
0xA001
进行异或运算; - 若LSB = 0,则仅将CRC寄存器右移一位,无需异或。
- 若LSB = 1,则CRC寄存器右移一位后,与预定义的多项式值
-
-
-
重复上述步骤
重复上述第2步,直至数据帧中所有字节处理完成。 -
最终CRC值
完成所有字节处理后,CRC寄存器中的16位数即为CRC校验码,低8位在前,高8位在后。
(二)CRC校验码添加方式
CRC校验结果采用“低字节先传,高字节后传”的方式附加到数据帧末尾:
例如:
地址 | 功能码 | 数据1 | 数据2 | CRC低字节 | CRC高字节 |
---|---|---|---|---|---|
0x01 | 0x03 | 0x00 | 0x02 | 0xC4 | 0x0B |
(三)接收方的CRC验证过程
接收方收到数据后:
-
将接收到的数据(不含CRC本身)进行CRC计算。
-
计算得到的CRC值与数据帧附加的CRC进行比较:
- 若相同,表示数据有效;
- 若不同,表明传输中出现错误,需要丢弃数据或请求重发。
二、CRC校验流程举例(示例数据)
假设需要发送的数据为:
01 03 00 64 00 02
CRC计算(十六进制):
-
初始CRC寄存器值:
0xFFFF
-
逐字节处理数据(0x01、0x03、0x00、0x64、0x00、0x02),最终得到CRC校验结果:
CRC低字节 = 0x85 CRC高字节 = 0xDB
完整发送数据帧为:
01 03 00 64 00 02 85 DB
接收方验证时,如计算CRC与帧中CRC一致,数据即为有效。
三、CRC校验的优势
Modbus RTU协议选择CRC校验的原因有以下显著优势:
1. 高效的错误检测能力
- CRC对常见的单比特错误、多比特连续错误和突发性错误具有极高的检测能力;
- 能有效降低错误数据被误判为有效数据的概率。
2. 简单性与快速性
- 算法实现简洁,无需复杂计算和处理;
- 易于硬件(单片机、PLC)和软件快速实现,运行速度快,处理效率高。
3. 对数据帧长度无限制
- CRC校验适用于任意长度的数据帧,灵活性极高;
- 适合工业通信中数据包长度不固定的需求。
4. 适用于恶劣环境
- 能很好地检测噪声干扰、传输线故障引起的数据错误;
- 非常适合工业现场中高干扰环境下的数据通信。
5. 成熟且广泛的应用实践
- CRC-16广泛应用于Modbus协议、CAN协议等工业通信领域;
- 拥有成熟的实现方案和大量实际验证,可靠性被充分验证。