modbus crc16校验码的算法
转自另一个大神给写的,非常简洁,我也测试非常OK,如果换成其它校验,可以更改下初始值和多项式。(下面代码的初始值0xffff 即10进制的65535,多项式为0xA001即10进制的40961。把它贴到这里,方便大家查找使用。先写下一般算法原理:
(1)、预置1个16位的寄存器值0xFFFF,称此寄存器为CRC寄存器;
(2)、把第一个8位二进制数据(既通讯信息帧的第一个字节)与16位的CRC寄存器的低
8位相异或,把结果放于CRC寄存器,高八位数据不变;
(3)、把CRC寄存器的内容右移一位(朝高位)用0填补最高位,并检查右移后的移出位;
(4)、如果移出位为0:重复第3步(再次右移一位);如果移出位为1,CRC寄存器与一多
项式(A001)进行异或;
(5)、重复步骤3和4,直到右移8次,这样整个8位数据全部进行了处理;
(6)、重复步骤2到步骤5,进行通讯信息帧下一个字节的处理;
(7)、将该通讯信息帧所有字节按上述步骤计算完成后,得到的16位CRC寄存器的高、低
字节进行交换;
(8)、最后得到的CRC寄存器内容即为:CRC码。下面是E4A的源码:过程 到八位无符号(传址 数据 为 整数型)
如果 数据 < 0 则
数据 = 数据 + 256
结束 如果
结束 过程
函数 ModBUS_CRC16(data 为 字节型()) 为 整数型
变量 crc 为 整数型,i 为 整数型,x 为 整数型,数据 为 整数型
crc = 65535 'CRC初始值 其它CRC可更改成对应的
判断循环首 x < 取数组成员数(data)
数据 = data(x)
到八位无符号(数据) '最主要的是这句 必须转成无符号
crc = crc 异或 数据
i = 0
判断循环首 i < 8
如果 (crc 且 1) 则
crc = crc \ 2 '无符号右移1位
crc = crc 异或 40961 '0xA001其它CRC可更改成对应的
否则
crc = crc \ 2 '无符号右移1位
结束 如果
i = i + 1
判断循环尾
x = x + 1
判断循环尾
ModBUS_CRC16 = crc
结束 函数
这个厉害! {:4_86:}{:4_86:} 明晨-紫月QQ:2240973822
欢迎加入安卓开发交流群:691958084 告诉对方就是根据施工技术犯规 正瞌睡来个枕头 这个做出来后要进行高低字节交换,不交换一般不识别
页:
[1]