gpt4 book ai didi

CRC16-CCITT 结果不正确?

转载 作者:太空宇宙 更新时间:2023-11-04 01:21:19 25 4
gpt4 key购买 nike

我正在制作一个程序,它将与引导加载程序通信以更新微 Controller 的固件。除了CRC 计算,一切都准备就绪。

我使用 here 的 CRC 计算函数计算多项式 x16 + x12 + x5 + 1 (0b10001000000100001) 的 CRC16。

但是输入 0x3304000012345678 的结果是错误的。我检查过这个 website 。此外,我已经仔细检查了我正在 C 中复制的 python 脚本。 python 脚本正确计算了 CRC

这是网站上的代码:

uint16_t crc16(uint8_t *data_p, unsigned length)
{
unsigned char i;
unsigned int data;
unsigned int crc = 0xffff;

if (length == 0)
return (~crc);

do
{
for (i=0, data=(unsigned int)0xff & *data_p++;
i < 8;
i++, data >>= 1)
{
if ((crc & 0x0001) ^ (data & 0x0001))
crc = (crc >> 1) ^ POLY;
else crc >>= 1;
}
} while (--length);

crc = ~crc;
data = crc;
crc = (crc << 8) | (data >> 8 & 0xff);

return (crc);
}

最佳答案

我将您发布的 C 代码与您链接的网站上的算法进行了比较,发现了两个主要区别:

1) 您发布的 C 代码以与网站相反的顺序处理这些位。对于 CRC 计算本身(右移,网站左移)和每个输入字节的处理(首先处理最低有效位,网站首先处理最高有效位)都是如此。

2) C 代码在返回 CRC 值之前将 CRC 值中的所有位取反,并交换低字节和高字节。该网站的算法不包含此类后处理。

我已经更新了您粘贴的 C 代码以匹配网站:

uint16_t crc16(const uint8_t *data_p, unsigned length)
{
unsigned char i;
uint8_t data;
unsigned int crc = 0; // 0xffff;

while (length-- > 0)
{
for (i = 0, data = *data_p++;
i < 8;
i++, data <<= 1)
{
if ((crc >> 15) ^ (data >> 7))
crc = (crc << 1) ^ POLY;
else
crc <<= 1;

crc &= 0xffff;
}
}

return crc;
}

区别:

1) data局部变量现在是 uint8_t 类型.

2) crc正如@AShelly 所建议的那样,变量被初始化为 0 而不是 0xFFFF。该网站特别提到它在开始计算之前将所有寄存器初始化为 0。

3) 我没有单独测试长度 0,而是将循环从“do”循环重组为“while”循环,这样如果“length”它就不会首先进入循环为 0。

4) 在 for 中循环,data向左移动而不是向右移动。这是因为我们想先处理它的 high 位,然后是它右边的位,依此类推——左移将每个后续位移到高位位置。

5) if将进位与输入的新位组合的语句现在将 CRC 的高位 (crc >> 15) 与数据的高位 (data >> 7) 进行比较,而不是将每个位的低位进行比较。其余代码确保 crc不会有位在第16位,data第 8 个位置不会有位,因此这些移位保证只会产生一个位。

6) 实际crc计算向左移动而不是向右移动。

7) 转移后crc在左侧,我屏蔽了位置 16 之后的任何位。这是第 4 点中提到的代码的一部分,它确保 crc >> 15只产生一位。 (这也可以通过将 crc 设为 uint16_t 类型来完成。)

8) 删除了后处理代码。决赛crc循环完成时按原样返回值。

通过这些更改,C 函数生成的 CRC 与网站匹配。

关于CRC16-CCITT 结果不正确?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41881228/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com