4

我正在尝试与第 3 方系统交互,他们提供了一个代码示例来在发送文本数据时计算 CRC 值。

供应商提供的 C 代码如下所示:

#define CRCRES 0xf0b8  /* residue for good verify */ 
#define DEBUG 

unsigned crctbl[] = {0x0000, 0x1081, 0x2102, 0x3183, 
                     0x4204, 0x5285, 0x6306, 0x7387, 
                     0x8408, 0x9489, 0xa50a, 0xb58b, 
                     0xc60c, 0xd68d, 0xe70e, 0xf78f}; 

/* 
 * This uses a 32 byte table to lookup the crc 4 bits at a time. 
 * The CRC CCITT is used. 
 */ 


unsigned short calc_crc(unsigned char *ptr, unsigned length) 

{ 
  unsigned short crc; 
  unsigned short i; 
  unsigned char pos,ch; 

  crc = 0xffff;  /* precondition crc */ 
  for (i = 0; i < length; i++,ptr++) { 
    ch = *ptr; 
    pos = (crc ^ ch) & 15; 
    crc = ((crc >> 4) & 0x0fff) ^ crctbl[pos]; 
    ch >>= 4; 
    pos = (crc^ch) & 15; 
    crc = ((crc >> 4) & 0xffff) ^ crctbl[pos]; 
  } 
  crc = ~crc;  /* post condition */ 
  crc = (crc << 8) | (crc >> 8); /* bytewise reverse */ 
  return crc; 
} 


/* 
 * tests the block of code containing the crc to verify it's 
 * content.  This compares to the reversed and inverted 
 * residue. 
 */ 

int test_crc(unsigned char *ptr, unsigned length) 

{ 
  unsigned short crc; 
  unsigned char arr [] = {'X','Y','Z'}; 

  crc = calc_crc(arr,3); 
  printf("Calced crc of test to be %04x, (should be 470f)\n", crc); 
  return (crc == 0x470f); 
} 

我已经复制了这段代码并放入了一个示例 C 程序。test_crc 方法没有计算 CRC 为 470f(它计算为 DD7A)。

我希望有人可以验证此代码是否像供应商所说的那样不起作用,或者帮助我让 test_crc 返回正确的值。

谢谢您的帮助。

4

3 回答 3

4

问题解决了。供应商的规格不正确。XYZ 的正确校验和是 DD7A。文档不正确。

再加上这样一个事实,即在他们解释要传递给 calc_crc 方法以获取实际消息的 crc 的数据之前的页面上也是不正确的,这使它成为一个棘手的项目。

谢谢您的帮助。

于 2009-02-23T23:11:36.347 回答
3

就其结果而言,计算并没有显示出我想到的任何错误。只需再次查看算法。特别是在寻找可能的问题时,请注意在算法的不同部分进行与运算的常数是0x0fff0xffff。也许应该是0x0fff并且0xfff0更加对称......有时我们认为真正的问题可能来自另一个地方,而忘记仔细检查明显的事情...... :)

于 2009-02-23T15:09:20.627 回答
2

硬件平台是否相同?可能是你有不同的字节顺序吗?(例如,您有 x86,他们有 68000 cpu。)

于 2009-02-23T14:30:51.217 回答