【问题标题】:Perl - How to calculate CRC16 of N bytes from array M-dimensional (with N<M) using Digest::CRCPerl - 如何使用 Digest::CRC 从数组 M 维(N<M)计算 N 个字节的 CRC16
【发布时间】:2021-09-19 01:29:21
【问题描述】:

我需要计算从大小为 M(一对 Kb,与我的范围无关)的二进制文件中提取的 N 字节(示例中为 5,为简单起见)的 CRC16。

printf "offset\tvalue\tcrc16\n";
#Read N bytes from file and copy in the container
for my $counter (0 .. 5- 1)
{
    my $oneByte;
    read(FH, $oneByte, 1) or die "Error reading $inFile!";
    my $ctx2 = Digest::CRC->new( type => 'crc16' );
    my $digest2 = ($ctx2->add($oneByte))->hexdigest;
    # PRINT for debugging
    printf "0x%04X\t0x%02X\t0x", $counter, ord $oneByte;
    print $digest2, "\n";
}

考虑到这个二进制输入

我得到结果:

脚本正在逐字节执行 CRC16(顺便说一下正确),但我需要 5 个字节的完整二进制流的 CRC16(预期值应该是 0x6CD6)。 脚本哪里错了?

【问题讨论】:

    标签: perl hash crc16


    【解决方案1】:

    调用hexdigestdigestb64digest 会清除缓冲区并从头开始下一个摘要。 (如果您正在计算多个文件/流的摘要,您不希望来自一个流的数据影响单独流的摘要)。

    所以等到流被完全读取后再调用digest

    ... {
        ...
        $ctx2->add($oneByte);
    }
    print "digest = ", $ctx2->hexdigest, "\n";
    

    或者为了帮助调试,保存流并在每个新字节后重新消化流

    my $manyBytes = "";
    ... {
        ...
        $manyBytes .= $oneByte;
        $digest2 = $ctx2->add($manyBytes)->hexdigest;
        ...
    }
    

    【讨论】:

    • Re "清除缓冲区并开始下一个摘要",是的,但更重要的是 OP 创建了一个全新的对象。这也会重置摘要;)
    • 非常感谢@mob!我已将摘要计算从 for() 循环中取出,现在 CRC16 已在所需的元素字节流上正确计算。
    【解决方案2】:

    您可以使用-&gt;add。您可以一次传递整个字符串、逐块传递或逐个字符传递。

    $ perl -M5.010 -MDigest::CRC -e'
       my $d = Digest::CRC->new( type => "crc16" );
       $d->add("\x49\x34\x49\x31\x31");
       say $d->hexdigest;
    '
    6cd6
    
    $ perl -M5.010 -MDigest::CRC -e'
       my $d = Digest::CRC->new( type => "crc16" );
       $d->add($_) for "\x49", "\x34", "\x49", "\x31", "\x31";
       say $d->hexdigest;
    '
    6cd6
    

    如图所示,使用单个对象,并在调用 -&gt;digest(等)之前添加每个字节,因为这会重置进程。

    【讨论】:

    • 感谢池上,但您的建议未优化;实际上我必须在超过 500kb 的数据上计算 CRC16。如果我必须做$d-&gt;add("\x49\x34\x49\x31\x31......(500kb - 1)"); 代码我有点不可读且没有优化
    • 嗯?你会像现在一样继续从文件中读取它……你为什么认为我建议你对文件进行硬编码???
    猜你喜欢
    • 2016-07-02
    • 2020-03-28
    • 2019-04-01
    • 2021-12-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-05-15
    相关资源
    最近更新 更多