C51 modbus rtu crc下面这段代码校验结果总是不对,请高手指教,不胜感激!

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C51 modbus rtu crc下面这段代码校验结果总是不对,请高手指教,不胜感激!相关的知识,希望对你有一定的参考价值。

uint CRC16(uint address) //计算校验码

uint CRC;
uchar i;
CRC=0xFFFF;
for(i=0;i<8;i++)

CRC=CRC^address; //异域
if((CRC&1)!=0) //检测最低位是否为1
CRC=(CRC>>1)^0xA001; //如果为1右移一位后须异域0xA001
else
CRC=CRC>>1; //如果移出位为0,只须右移一位

TX_com[0]=(CRC&0x00FF); //校验结果低8位
TX_com[1]=(CRC&0xFF00)>>8; //检验结果高8位

return CRC;

这个函数的问题在于:
1、每次只能计算1个字节数据的CRC值,若有多个字节,须调用多次;
2、字节数据,应把(uint address)改为(uchar address)
3、应计算完全部字节数据的CRC值之后,再把CRC值高、低字节对调,所以代码中提前处理了低8位、高8位,导致结果错误。
参考技术A 看看 CRC 的原理

然后再读解这个程序

Modbus RTU CRC校验码计算方法

在CRC计算时只用8个数据位,起始位及停止位,如有奇偶校验位也包括奇偶校验位,都不参与CRC计算。

CRC计算方法是:

1、  加载一值为0XFFFF的16位寄存器,此寄存器为CRC寄存器。

2、  把第一个8位二进制数据(即通讯信息帧的第一个字节)与16位的CRC寄存器的相异或,异或的结果仍存放于该CRC寄存器中。

3、  把CRC寄存器的内容右移一位,用0填补最高位,并检测移出位是0还是1。

4、  如果移出位为零,则重复第三步(再次右移一位);如果移出位为1,CRC寄存器与0XA001进行异或。

5、  重复步骤3和4,直到右移8次,这样整个8位数据全部进行了处理。

6、  重复步骤2和5,进行通讯信息帧下一个字节的处理。

7、  将该通讯信息帧所有字节按上述步骤计算完成后,得到的16位CRC寄存器的高、低字节进行交换

8、  最后得到的CRC寄存器内容即为:CRC校验码

以上是关于C51 modbus rtu crc下面这段代码校验结果总是不对,请高手指教,不胜感激!的主要内容,如果未能解决你的问题,请参考以下文章

VB Modbus RTU CRC 校验

计算 Modbus RTU CRC 16

modbus rtu校验方法

Modbus RTU CRC校验码计算方法

求 c# 基于ModBus RTU的CRC算法

51单片机MODBUS通讯,RTU中的CRC校验