OWI_ComputeCRC16 返回值 0

OWI_ComputeCRC16 returning value 0

我正在检查此函数 OWI_ComputeCRC16(),当我使用 OWI_ComputeCRC16(0 >> 8, 0) 测试该函数时,return 值为 0。

/**
* @brief    Compute the CRC16 value of a data set.
* @details  This function will compute the CRC16 of inData using seed as inital value for the CRC.
* @note     Setting seed to 0 computes the crc16 of the inData.
* @note     Constantly passing the return value of this function as the seed argument computes the CRC16 value of a longer string of data.
* @bug      N/A
* @warning  N/A
* @param    unsigned char inData: One byte of data to compute CRC from.
* @param    unsigned short seed: The starting value of the CRC.
* @return   The CRC16 of inData with seed as initial value.
*/
unsigned short OWI_ComputeCRC16(unsigned char inData, unsigned short seed)
{
    unsigned char bitsLeft;
    unsigned char temp;

    for (bitsLeft = 8; bitsLeft > 0; bitsLeft--)
    {
        temp = ((seed ^ inData) & 0x01);
        if (temp == 0)
        {
            seed >>= 1;
        }
        else
        {
            seed ^= 0x4002;
            seed >>= 1;
            seed |= 0x8000;
        }
        inData >>= 1;
    }
    return seed;
}

这在遗留代码中造成了一些我必须解决的问题,其中此函数也与参数 0、0 一起使用,然后使用计算出的 CRC 值的 SUM。

示例:

a) 我有一些关于示例 position = 0 with key = 0 的数据 ... => OWI_ComputeCRC16(0 >> 8, 0) returns 0.

b) 我在示例位置 = 0 上有一些数据,密钥 = 0 ... crc = 0。我在示例位置 = 1 上有另一个数据记录,密钥 = 1 ... OWI_ComputeCRC16 (1 >> 8, 1) returns 49345.

如果我对这个 returned CRC 值进行 SUM,我将不知道是否包含来自位置 0 的数据。

好的,我认为这是逻辑错误,我可以解决。

问题是:函数是否可以,应该计算 return CRC 值,return 值 0(对于任何可能的给定输入值)?

p.s.: 这是我关于Whosebug的第一个问题,所以如果我做错了什么或者不明白,请告诉我。谢谢

The question is: is it ok for function, that should calculate and return CRC value, to return value 0 (for any possible given input values)?

不是任何,但对于某些字节序列,您将获得零 return 值。事实上,对于 16 位 CRC,您应该期望获得零 CRC,平均而言,您尝试的每 65536 个随机序列中就有一个。

这个特定的 CRC,没有预或 post 条件,将为空序列和任何零序列给出零 CRC。

顺便说一下,这是一个奇怪的实现,其操作比需要的多得多。它应该被替换为:

unsigned short OWI_ComputeCRC16(unsigned char inData, unsigned short seed)
{
    seed ^= inData;
    for (int k = 0; k < 8; k++)
        seed = seed & 1 ? (seed >> 1) ^ 0xa001 : seed >> 1;
    return seed;
}

这也不会混淆 CRC 多项式,在此版本中是熟悉的(反映的)0xa001 或(未反映的)多项式 0x8005,即 x16+x 15+x2+1。 更快的仍然是 byte-wise 或 word-wise table-driven 版本。有关示例,请参阅 crcany.c