Как работают алгоритмы CRC для CCITT16 и как получить один для CCITT8 - PullRequest
3 голосов
/ 03 апреля 2012

Я пытаюсь реализовать контрольную сумму CRC-8 - и при чтении CRC в целом я столкнулся с этим алгоритмом для CCITT-16 (полином X X 16 + X ^ 12 + X ^ 5 + 1):

unsigned char ser_data;
static unsigned int crc;

crc  = (unsigned char)(crc >> 8) | (crc << 8);
crc ^= ser_data;
crc ^= (unsigned char)(crc & 0xff) >> 4;
crc ^= (crc << 8) << 4;
crc ^= ((crc & 0xff) << 4) << 1;

В качестве макроса:

#define crc16(chk, byte)                                   \
        {                                                  \
          chk = (unsigned char) (chk >> 8) | (chk << 8);   \
          chk ^= byte;                                     \
          chk ^= (unsigned char)(chk & 0xFF) >> 4;         \
          chk ^= (chk << 8) << 4;                          \
          chk ^= ((chk & 0xFF) << 4) << 1;                 \
        }

У меня здесь два вопроса:

  1. Как этот алгоритм выводится из полинома?
  2. Существует ли аналогичный простой алгоритм для CCITT8 (полином X ^ 8 + Х ^ 2 + Х + 1)?

Ответы [ 3 ]

3 голосов
0 голосов
/ 22 мая 2015

эта веб-страница: https://decibel.ni.com/content/docs/DOC-11072 содержит ссылку на файл .zip для каждого из распространенных (включая те, которые вы запрашиваете) алгоритмов для вычисления crc.

0 голосов
/ 21 мая 2015

Вот реализация C CRC8-CCITT на C, основанная на коде из этого ответа (https://stackoverflow.com/a/15171925/1628701):

uint8_t crc8_ccitt(uint8_t crc, const uint8_t *data, size_t dataLength){
    static const uint8_t POLY = 0x07;
    const uint8_t *end = data + dataLength;

    while(data < end){
        crc ^= *data++;
        crc = crc & 0x80 ? (crc << 1) ^ POLY : crc << 1;
        crc = crc & 0x80 ? (crc << 1) ^ POLY : crc << 1;
        crc = crc & 0x80 ? (crc << 1) ^ POLY : crc << 1;
        crc = crc & 0x80 ? (crc << 1) ^ POLY : crc << 1;
        crc = crc & 0x80 ? (crc << 1) ^ POLY : crc << 1;
        crc = crc & 0x80 ? (crc << 1) ^ POLY : crc << 1;
        crc = crc & 0x80 ? (crc << 1) ^ POLY : crc << 1;
        crc = crc & 0x80 ? (crc << 1) ^ POLY : crc << 1;
    }

    return crc;
}
...