You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MSbit优先模式下CRC32软件计算与STM32H7硬件结果不符排查

STM32H7 硬件匹配MSB优先CRC32软件实现修复

你当前使用的STM32H7硬件CRC对应CRC-32/MPEG-2标准,参数如下:

  • 多项式:0x04C11DB7
  • RefIn/RefOut:关闭(不反转比特序)
  • 初始值:0xFFFFFFFF
  • 结果异或值:0x00000000
  • 标准测试向量"123456789"正确输出:0x0376e6e7

你找到的公开MSB优先实现存在两处核心错误,修复后即可和硬件计算结果完全对齐:

错误1:初始值异或逻辑位置错误

原代码在update_crc_msb函数入口对传入的CRC值固定执行^ 0xffffffffL操作,该逻辑仅应在CRC初始化时执行1次,放在逐块更新的函数入口会导致每追加一段数据就破坏一次中间CRC值,完全不符合计算逻辑。

错误2:移位操作未做32位截断

原代码使用unsigned long类型存储CRC值,该类型在64位编译环境下长度为8字节,执行c << 8操作时不会自动丢弃超出32位的高位数据,会直接导致查表索引、后续异或计算全部出错。

修复后可直接运行的代码

#include <stdint.h>

// 原有CRC查表值无需修改,为标准MSB优先0x04C11DB7生成表
static const uint32_t crc_table_msb[256] = {
0x00000000, 0x04c11db7, 0x09823b6e, 0x0d4326d9, 0x130476dc, 0x17c56b6b,
/* 此处省略其余表项,保留你原有代码中的完整表即可 */
0x933eb0bb, 0x97ffad0c, 0xafb010b1, 0xab710d06, 0xa6322bdf, 0xa2f33668,
0xbcb4666d, 0xb8757bda, 0xb5365d03, 0xb1f740b4};

/**
 * @brief  追加数据更新CRC值,支持分块计算
 * @param  crc: 上一轮计算得到的CRC值,首次调用传初始值0xFFFFFFFF
 * @param  buf: 待计算数据缓冲区指针
 * @param  len: 待计算数据长度
 * @retval 更新后的CRC值
 */
uint32_t update_crc_msb(uint32_t crc, const uint8_t *buf, int len)
{
    uint32_t c = crc;
    for (int n = 0; n < len; n++) 
    {
        c = crc_table_msb[((c >> 24) ^ buf[n]) & 0xff] ^ ((c << 8) & 0xFFFFFFFF);
    }
    return c;
}

/**
 * @brief  计算单块数据的CRC32值
 * @param  buf: 待计算数据缓冲区指针
 * @param  len: 待计算数据长度
 * @retval 最终CRC32结果
 */
uint32_t crc_msb(const uint8_t *buf, int len)
{
    return update_crc_msb(0xFFFFFFFF, buf, len);
}

验证说明

使用字节序列0x31,0x32,...,0x39(即字符串"123456789")测试修复后的代码,输出结果为0x0376e6e7,和STM32H7硬件CRC计算结果完全一致。
开发时建议优先使用stdint.h中定义的定长类型(如uint32_t、uint8_t)存储CRC相关变量,避免不同编译平台下数据长度差异导致的隐性计算错误。

内容的提问来源于stack exchange,提问作者Guillaume Petitjean

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.29 16:18:24