1. ホーム
  2. c

[解決済み] C言語でcrc8を計算するには?

2022-03-08 03:11:29

質問

C言語でのcrc8実装を複数見てきましたが、多項式(x8,x5,x4,1)の実装が分かりません。 0x31 と初期化 0xFF .

また、反射入力=False、反射出力=False、最終的なXOR=。 0x00 .

いくつか試してみたところ、以下のようなことが予想されます。 CRC(0x00)=0xACCRC(0xBEEF)=0x92 .

似たような実装を見たことがありますが、実際にうまくいったものはありませんでした。私はここで正確な機能を見ました http://www.sunshine2k.de/coding/javascript/crc/crc_js.html 初期化、入力の反映、出力の反映、そして最終的なXORを与えることができるところ。しかし、誰かが私にCでの実装を指摘することができます。私は最初に我々は0xFFとしてcrcを与える必要があることを理解しているが、何も私のためにこれまでうまくいきませんでした。

試したサンプルコードを添付します。

#include <stdio.h>
#include <stdint.h>

uint8_t crc8(uint16_t input);

int main()
{
    uint8_t temp1;
    uint16_t temp2 = 0xBEEF;

    printf("CRC input is 0x%X\n", temp2);

    temp1 = crc8(temp2);

    printf("CRC output is 0x%X\n", temp1);

    return 0;
}

uint8_t crc8(uint16_t input)
{
    uint8_t crc[8] = { };
    uint8_t i;
    uint8_t inv;
    uint8_t output = 0;

    for(i = 0; i < 16; i++)
    {
        inv = ((((input >> i) & 1) ^ crc[7]) & 1);

        crc[7] = (crc[6] & 1);
        crc[6] = (crc[5] & 1);
        crc[5] = (crc[4] ^ inv & 1);
        crc[4] = (crc[3] ^ inv & 1);
        crc[3] = (crc[2] & 1);
        crc[2] = (crc[1] & 1);
        crc[1] = (crc[0] & 1);
        crc[0] = (inv & 1);
    }

    for(i = 0; i < 8; i++){
        output |= ((crc[i] << i) & (1 << i));
    }


    return output;
}

私が見ているのは

CRC input is 0xBEEF
CRC output is 0x2 //instead of 0x92

解決方法は?

PCやその他のリトルエンディアンプロセッサで動作していると仮定すると、temp2はメモリ上に{0xEF, 0xBE}として格納されています。最適化されていないサンプルコード(テーブルを使用していない)。より高速にするには、jを使った内部ループを256バイトのテーブル検索に置き換えることができます: crc = table[crc ^ data[i]]。

#include <stdio.h>

typedef unsigned char uint8_t;

uint8_t gencrc(uint8_t *data, size_t len)
{
    uint8_t crc = 0xff;
    size_t i, j;
    for (i = 0; i < len; i++) {
        crc ^= data[i];
        for (j = 0; j < 8; j++) {
            if ((crc & 0x80) != 0)
                crc = (uint8_t)((crc << 1) ^ 0x31);
            else
                crc <<= 1;
        }
    }
    return crc;
}

int main()
{
uint8_t data[8] = {0xBE,0xEF,0,0,0,0,0,0};
uint8_t crc;
    crc = gencrc(data, 2);   /* returns 0x92 */
    printf("%1x\n", crc);
    crc = gencrc(data+2, 1); /* returns 0xac */
    printf("%1x\n", crc);
    return 0;
}