正如它所说,您的程序正在计算字符串485(字节34 38 35)的CRC,这是数字0x1E5 的十进制字符串表示。同时,网站正在计算字节01 e5 的CRC。我不知道你想要哪一个。
绝对正确的是,该网站没有计算任何类型的 CRC32,因为它的结果不是 32 位长,而且似乎取决于您指定的多项式的大小。
此外,如果您使用 Digest::CRC 指定 type => 'crc32',它将忽略所有其他参数并简单地计算标准 CRC32。
如果您想要一个多项式为 0x2D 的 32 位 CRC,那么您可以尝试
my $ctx = Digest::CRC->new(width => 32, poly => 0x2D);
但是您还需要定义其他几项来指定 CRC,包括(但不限于)位和字节顺序、初始值和结束异或值,并且无法判断这是否会给您在没有看到完整规范的情况下正确校验和。
您肯定有一个文档比“CRC32, polynomial 0x2d” 有更多内容吗?
更新
如何使用Digest::CRC 将数据视为十六进制字节而不是字符串?
-
Digest::CRC 只处理字符串,您需要以这种方式打包数据。在这种情况下,您可能想要my $string = "\x01\xe5"
另外,什么是“end xor value”?
-
end xor 值只是一个与结果进行异或的位模式,作为获得最终 CRC 的最后一步。
此外,如果我理解正确,以下两种方法应该给出相同的结果:
my $ctx1 = Digest::CRC->new(type => "crc32");
my $rr1 = $ctx1->add(pack 'H*', '1e5')->hexdigest;
print "a1=$rr1=\n";
my $ctx2 = Digest::CRC->new(width => 32, poly => 0x04c11db7);
my $rr2 = $ctx2->add(pack 'H*', '1e5')->hexdigest;
print "a2=$rr2=\n";
但是我得到不同的结果:
a1=fef37cd4= a2=758cce0=
你能告诉我我的错误在哪里吗?
- 正如我所说,CRC 有许多说明符。这就是为什么您必须建立所需 CRC 的完整规范,不仅包括宽度和多项式。要显式生成 CRC32 校验和,您需要这个
my $ctx = Digest::CRC->new(width => 32, poly => 0x04c11db7, init => 0xFFFFFFFF, xorout => 0xFFFFFFFF, refin => 1, refout => 1);
这将应用0xFFFFFFFF 的初始值和最终值,并将refin 和refout 设置为true。这反转了处理前后的位顺序(ref 是 reflect 的缩写),是 MSB first 和 LSB first 之间的区别。