【问题标题】:CRC Calculation in CC中的CRC计算
【发布时间】:2012-05-31 05:50:41
【问题描述】:

我有一个设备,它向我发送带有 CRC 计算的数据。 每 16 个字节有 2 个 CRC 字节。 生成多项式为 x16 + x13 + x12 + x11 + x10 + x8 + x6 + x5 + x2 + 1

我的代码如下所示:

int crc16(unsigned char *addr, int num, int crc)
{
    uint16_t poly = 0x3D65;
    int i;
    for (; num > 0; num--)           /* Step through bytes in memory */
    {
        crc = crc ^ ((unsigned short)*addr++ << 8);         /* Fetch byte from memory, XOR into  CRC top byte*/
        for (i = 0; i < 8; i++)      /* Prepare to rotate 8 bits */
        {
            if (crc & 0x10000)       /* b15 is set... */
                crc = (crc << 1) ^ poly;    /* rotate and XOR with XMODEM polynomic */
            else                     /* b15 is clear... */
                crc <<= 1;           /* just rotate */
        }                            /* Loop for 8 bits */
        crc &= 0xFFFF;               /* Ensure CRC remains 16-bit value */
     }                               /* Loop until num=0 */
     return(crc);                    /* Return updated CRC */
}

我还用其他多项式(如 0x9CB2)尝试了这段代码。我认为代码中存在错误。

【问题讨论】:

  • 而你的问题是......究竟是什么?
  • 您能否详细说明这个问题?告诉我们问题出在哪里……
  • 好的,所以你认为代码中有错误。但你为什么这么认为?究竟是什么不起作用?你得到了哪些不正确的结果?
  • 除了多项式之外,设备的文档如何描述 CRC? CRC 位可以按任意顺序存储,可以有一个不同于零的初始值,并且可以有前置和/或后置条件。你应该阅读ross.net/crc/download/crc_v3.txt
  • 您能否提供一个 16 字节数据和来自设备的 2 字节 crc 的示例?

标签: c crc


【解决方案1】:

您使用的是哪个编译器/平台?您确定 int 数据类型是 32 位吗?用long 试试并比较结果。

另外,如果:

if ( crc & 0x10000 )

并在评论中声明您正在验证第 15 位。不,这不是真的,您将验证第 16 位。第 15 天是( crc &amp; 0x8000 )

【讨论】:

  • 或者直接写if(crc &gt;&gt; 15),这样代码的作用就很明显了。
  • 是的……也不是。我的印象是执行此代码的平台是嵌入式设备中的微处理器。如果是这种情况,则 && 是原子的(一个 CPU 周期)。你的提议,100% 正确,但在某些硬件上,这意味着 15 个 CPU 周期。如果 CPU 是 8 位宽……你可以想象!
  • 编译器很可能能够优化此类平台上的代码。
  • 不太可能。我用来对这类设备进行编程,通常禁用优化以更好地控制时间延迟和恒定执行时间。
  • 嗯...不是吗?我一直在对这类系统进行编程。只有业余爱好者依赖基于操作码的延迟循环,专业人士使用片上硬件定时器,所以这甚至不是问题。至于恒定的执行时间,一旦你完成了对源文件的修改,编译器每次都会以相同的方式优化代码。我刚刚使用旧编译器为 16 位 MCU 进行了测试,它优化了右移以检查 0x8000,正如我预期的那样。 8 位可能在任何 16 位 CRC 上表现不佳,在这种特定情况下,我会使用 CRC 查找表。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-08-09
  • 2014-11-20
  • 2016-09-06
  • 1970-01-01
  • 2017-03-01
  • 2011-11-08
相关资源
最近更新 更多