如何使用sse4.2 x86扩展的CRC32C指令为C中的字符串实现哈希函数?

时间:2018-12-20 14:56:16

标签: c hash sse crc crc32

问题

我正在尝试使用sse4.2 x86扩展中的crc32c指令为简单的哈希表实现哈希函数。但是我对这类问题还不太满意,所以我有一些问题。

我已经查找到有一个函数unsigned int _mm_crc32_u8 (unsigned int crc, unsigned char v)(源:https://software.intel.com/sites/landingpage/IntrinsicsGuide/#techs=SSE4_2&expand=1283),该函数接收未签名的char并返回哈希值。根据我的理解,crc变量用于与我无关的前导位的错误检查目的(我可以将其设置为0或0xffffffff,而不管它)。

但是我有一个字符串char *s,想计算它的哈希值。

问题

(重要性顺序)

  1. 如何使用_mm_crc32_u8对整个字符串进行哈希处理?我是否应该分别对s中的所有字符进行散列并按位对结果进行XOR?我真的没有头绪。
  2. 函数_mm_crc32_u8接受未签名的字符。在这种情况下,可以仅将未签名的char转换为char以便像(unsigned char)s[0]那样转换吗?据我所知,这是因为ASCII字符的值只有0到127,所以它在转换过程中不会溢出。
  3. 在多个字节(_mm_crc32_u{16,32,64})上也有函数,我是否应该使用这些函数以获得更好的性能,因为它们可以一次哈希多达4个字节?

详细信息

#include <nmmintrin.h>提供上述功能。我正在使用clang标志-msse4.2

对其进行编译

1 个答案:

答案 0 :(得分:2)

我认为,您误解了这些功能的工作方式。预计将为需要计算CRC的字符串中的每个字符依次调用它们(如果使用较大的参数版本,则应为单词,应该使用该词)。

但是想法仍然是相同的:首先将CRC初始化为0,然后在循环中调用CRC函数,在第一个参数中给出CRC的先前值,在第二个参数中给出散列的值。您将结果存储在CRC中,保持镇静并继续。

这是代码示例:

finish();