Culong数组操作CRC32

momone50

当C附带时,我真的很生锈,我需要了解基于CRC32的另一位开发人员编写的代码。我有一个ulong数组

static const ulong crc32_table[256] =
{
      0x00000000ul, 0x04c11db7ul, 0x09823b6eul, 0x0d4326d9ul,
      0x130476dcul, 0x17c56b6bul, 0x1a864db2ul, 0x1e475005ul,
      0x2608edb8ul, 0x22c9f00ful, 0x2f8ad6d6ul, 0x2b4bcb61ul,
      0x350c9b64ul, 0x31cd86d3ul, 0x3c8ea00aul, 0x384fbdbdul,
      ...
};

然后,通过以下方式将此数组用于加密数据:

void CRC32(const byte *buf, uint len, const byte init[4], byte crc[4]) {
    memcpy(crc, init, 4);
    while (len--) {
        const byte * tmp = (const byte *)(crc32_table + (crc[3] ^ *buf));
        crc[3] = crc[2] ^ tmp[3];
        crc[2] = crc[1] ^ tmp[2];
        crc[1] = crc[0] ^ tmp[1];
        crc[0] = tmp[0];
        ++buf;
    }
}

我不明白的是线:

const byte * tmp = (const byte *)(crc32_table + (crc[3] ^ *buf));

似乎整个数组是另外使用的,并强制转换为字节(实际上是uint),但是我不习惯这种操作。

有人能帮我吗?

我需要编写一个等效于CRC32函数的代码,但在C#中可以正常工作:

            uint[] crc = sharedkey;
            uint[] buff = new uint[] { 0x4fu, 0xaeu, 0x07u, 0x0bu, 0x68u, 0x56u, 0x34u, 0x12u };

            for(int i=0; i < len; i++)
            {
                byte[] tmp = BitConverter.GetBytes(crc32_table[(int)(crc[3] ^ buff[i])]);            

                crc[3] = crc[2] ^ tmp[3];
                crc[2] = crc[1] ^ tmp[2];
                crc[1] = crc[0] ^ tmp[1];
                crc[0] = tmp[0];
            } 

  
h0r53

让我们剖析整个功能。该函数声明如下:

void CRC32(const byte *buf, uint len, const byte init[4], byte crc[4]) 

const byte *buf -正在为其计算CRC的输入缓冲区

uint len -要计算的CRC长度

const byte init[4] -CRC的初始化向量

byte crc[4] -CRC计算的输出/结果

我们首先在中看到将crc其初始化为初始化向量。memcpy(crc, init, 4);然后我们有一个循环迭代len时间的循环在此循环结束时,buf指针以递增++buf

现在,您很难理解。

与的每个字节进行bufXORcrc[3]运算,其结果用作的偏移量crc32_table结果值存储在tmp其中,然后用于对的四个字节进行加扰crc这项工作背后的关键因素包括crc32_table有256个条目,并且一个字节有256个可能的值(这是您试图了解的操作的结果)。因此,偏移量索引始终有效。

其余的操作只是进一步加扰的XOR crc

更新

尽管我已经剖析了该函数,但主要的困惑涉及一个称为指针算术的概念。在C语言中,未索引数组(例如crc32_table)的值是指向存储位置的指针,该存储位置基于数组类型和长度存储连续类型的数据。例如,

假设我们ulong crc32_table[256]在内存位置具有以下数组0x400000

随后的值crc32_table0x400000

此外,&crc32_table[0]也是0x400000(这会转换为crc32_table数组中第一个条目的地址)。

但是,&crc32_table[1]0x400008(如果您的系统上的sizeof(ulong)是8个字节)

这是有趣的部分。

crc32_table + 1也是0x400008,(与相同&crc32_table[1])。

这称为指针算术,它与您提供的CRC代码中使用的概念相同。该代码只是将偏移量0-255计算为大小为256的数组,因此每个可能的偏移量都是有效的,并转换为适当的数组索引。

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章