循环冗余校验再单片机的通讯数据传输环节用得比较多,目的是方式电讯号干扰导致得误传。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define u8 unsigned char
#define u16 unsigned short
#define u32 unsigned int
void CalclationCRC16(u8 *dat, u8 datLen, u8* crc16)
{
u8 i = 0;
u16 r = 0x0000; //存储CRC 结果
u16 p = 0x1021; //CRC因子
u8 t = 0;
while (datLen--)
{
t = *(dat++);
r ^= t << 8;
for (i = 0; i < 8; i++)
{
if (r & 0x8000)
{
r <<= 1;
r ^= p;
}
else
{
r <<= 1;
}
}
}
crc16[1] = r >> 8;
crc16[0] = r % 256;
}
void CRC_CCITT_FALSE(u8 *dat, u8 datLen, u8* crc16)
{
u8 i = 0;
u16 r = 0xFFFF; //存储CRC 结果
u16 p = 0x1021; //CRC因子
u8 t = 0;
while (datLen--)
{
t = *(dat++);
r ^= t << 8;
for (i = 0; i < 8; i++)
{
if (r & 0x8000)
{
r <<= 1;
r ^= p;
}
else
{
r <<= 1;
}
}
}
crc16[1] = r >> 8;
crc16[0] = r % 256;
}
u32 crc_chk(u8 *crcbuf, u8 n)
{
u8 i, j, tt;
u32 CRCX = 0xffff;
for (i = 0; i < n; i++)
{
CRCX = CRCX ^ crcbuf[i];
for (j = 0; j < 8; j++)
{
tt = CRCX & 1;
CRCX = CRCX >> 1;
CRCX = CRCX & 0X7fff;
if (tt == 1)
CRCX = CRCX ^ 0xa001;
CRCX = CRCX & 0xffff;
}
}
return CRCX;
}
int main()
{
u8 dat[7] = { 0x12,0x47,0x09,0x23,0x01,0x09,0x13 };
u8 dat2[11] = { 0x00 ,0x00 ,0x07 ,0xF5 ,0x12,0x47,0x09,0x23,0x01,0x09,0x13 };
u8 r[2];
u32 r1;
CalclationCRC16(dat, 7, r);
printf("%02X%02X\n", r[1], r[0]);
CalclationCRC16(dat2, 11, r);
printf("%02X%02X\n", r[1], r[0]);
return 0;
}