C 언어로 구현한 Bitwise CRC 계산 함수
2025년 11월 26일
2021년 12월, 방송신호 자동절체 제어기를 개발하기 위해 CRC(Cyclic Redundancy Check)계산에 대해 공부하며 만들어 본 CRC-5, CRC-7, CRC-8, CRC-10, CRC-16, CRC-32 계산하는 함수. 손으로 계산 하는 방법을 그대로 C 로 구현했다. 공부하느라 만든 것으로 당연히 효율성이나 속도따위는 고려대상이 아니었다.
당연히 기본 제공 라이브러리나, 더 머리 좋은 사람들이 공개한 효율적인 코드들도 존재한다. 하지만 일단, 내가 사용하는 놈이 뭐하는 놈인지와, 어떻게 동작하는지에 대해서는 알고 나서 사용해야 할 것이다.
CRC-5 계산함수
// SAPJIL CRC Calcurator by eqmaker
unsigned char CRC5_Generator(unsigned char *datastream, unsigned int numberofbyte, unsigned char poly)
{
unsigned char rtn=0;
for (unsigned int i=0; i<numberofbyte+1; i++)
{
for (char j= ((i==numberofbyte) ? 4 : 7); j>=0; j--)
{
if (rtn & 1<<4)
{
rtn = rtn << 1;
rtn = (((i==numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
rtn = rtn ^ poly;
}
else
{
rtn = rtn << 1;
rtn = (((i==numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
}
}
}
return rtn & 0b00011111;
}
CRC-7 계산함수
// SAPJIL CRC Calcurator by eqmaker
unsigned char CRC7_Generator(unsigned char *datastream, unsigned int numberofbyte, unsigned char poly)
{
unsigned char rtn=0;
for (unsigned int i=0; i<numberofbyte+1; i++)
{
for (char j= ((i==numberofbyte) ? 6 : 7); j>=0; j--)
{
if (rtn & 1<<6)
{
rtn = rtn << 1;
rtn = (((i==numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
rtn = rtn ^ poly;
}
else
{
rtn = rtn << 1;
rtn = (((i==numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
}
}
}
return rtn & 0b01111111;
}
CRC-8 계산함수
// SAPJIL CRC Calcurator by eqmaker
unsigned char CRC8_Generator(unsigned char *datastream, unsigned int numberofbyte, unsigned char poly)
{
unsigned char rtn=0x00;
for (unsigned int i=0; i<numberofbyte+1; i++)
{
for (char j=7; j>=0; j--)
{
if (rtn & 0x80)
{
rtn = rtn << 1;
rtn = (((i==numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
rtn = rtn ^ poly;
}
else
{
rtn = rtn << 1;
rtn = (((i==numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
}
}
}
return (rtn);
}
CRC-10 계산함수
// SAPJIL CRC Calcurator by eqmaker
void CRC10_Generator(unsigned char *datastream, unsigned int numberofbyte, unsigned int poly)
{
unsigned int rtn=0;
for (unsigned int i=0; i<numberofbyte+2; i++) // 8bit x 2 = 16bit 나머지 (중 10bit 사용)
{
for (char j=((i==numberofbyte+1) ? 1 : 7); j>=0; j--) // 15-6 14-5 13-4 12-3 11-2 10-1 9-0
{
if (rtn & 1<<9)
{
rtn = rtn << 1;
rtn = (((i>=numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
rtn = rtn ^ poly;
}
else
{
rtn = rtn << 1;
rtn = (((i>=numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
}
}
}
rtn = rtn & 0x03ff;
printf("CRC10 : %04X\n", rtn);
}
CRC-16 계산함수
// SAPJIL CRC Calcurator by eqmaker
void CRC16_Generator(unsigned char *datastream, unsigned int numberofbyte, unsigned int poly)
{
unsigned int rtn=0;
for (unsigned int i=0; i<numberofbyte+2; i++) // 8bit x 2 = 16bit 나머지
{
for (char j=7; j>=0; j--)
{
if (rtn & 0x8000)
{
rtn = rtn << 1;
rtn = (((i>=numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
rtn = rtn ^ poly;
}
else
{
rtn = rtn << 1;
rtn = (((i>=numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
}
}
}
rtn = rtn & 0xffff;
printf("CRC16 : %04X\n", rtn);
}
CRC-32 계산함수
// SAPJIL CRC Calcurator by eqmaker
void CRC32_Generator(unsigned char *datastream, unsigned int numberofbyte, unsigned int poly)
{
unsigned int rtn=0;
for (unsigned int i=0; i<numberofbyte+4; i++) // 8bit x 4 = 32bit
{
for (char j=((i==numberofbyte+1) ? 7 : 7); j>=0; j--)
{
if (rtn & 1<<31)
{
rtn = rtn << 1;
rtn = (((i>=numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
rtn = rtn ^ poly;
}
else
{
rtn = rtn << 1;
rtn = (((i>=numberofbyte) ? 0 : datastream[i]) & (1<<j)) ? (rtn | 1) : rtn;
}
}
}
printf("CRC32 : %08X\n", rtn);
}
🔄 갱신 내역
- — 최초 게시
- — 블로그 이전
- — 블로그 이전 및 2차 수정