news 2026/10/2 6:57:30

STM32对函数进行CRC校验

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
STM32对函数进行CRC校验

STM32F4xx 内置了硬件CRC 计算单元(CRC-32 以太网多项式 0x4C11DB7),可在运行期快速计算软件签名,与链接时生成并存放在指定存储单元的参考签名比较,用于验证 Flash 完整性。其计算方法为:复位 CRC 模块(置 CRC_CR=0x01,余数初始化为 0xFFFFFFFF),把数据按 32 位写入 CRC_DR,最后读回结果。

方案一:上电时对整个 Flash 区域做 CRC32 校验(最常用)

第 1 步:在程序 Flash 中预留 CRC 参考值存储区
把应用区起始地址、大小、CRC 参考值地址定义好。CRC 参考值通常由编译后处理工具在烧录时写入。

#define FLASH_APP_START_ADDR 0x08002000U /* 应用程序起始地址 */ #define FLASH_APP_SIZE 0x0003C000U /* 应用程序大小 */ #define FLASH_CRC_REF_ADDR 0x0803E000U /* CRC 参考值存储地址 */

第 2 步——用软件/硬件 CRC 计算 Flash 内容

// 硬件 CRC 方式(利用 STM32F4 内置 CRC 外设) uint32_t calculate_flash_crc(uint32_t *addr, uint32_t len_words) { uint32_t crc; // 复位 CRC 单元 CRC->CR = CRC_CR_RESET; for (uint32_t i = 0; i < len_words; i++) { CRC->DR = addr[i]; } crc = CRC->DR; return crc; }

或软件 CRC32(不依赖外设,便于 bootloader 使用):

uint32_t calculate_crc32(uint32_t *data, uint32_t length) { uint32_t crc = 0xFFFFFFFF; for (uint32_t i = 0; i < length; i++) { crc ^= data[i]; for (int j = 0; j < 32; j++) { crc = (crc & 0x80000000) ? (crc << 1) ^ 0x04C11DB7 : crc << 1; } } return crc; }

第 3 步——上电校验并在跳转主应用前执行

void verify_flash_integrity(void) { uint32_t stored_crc = *(volatile uint32_t *)FLASH_CRC_REF_ADDR; uint32_t calc_crc = calculate_crc32((uint32_t *)FLASH_APP_START_ADDR, FLASH_APP_SIZE / 4); if (calc_crc != stored_crc) { // CRC 不匹配!Flash 可能被位翻转/破坏,进入安全状态 error_handler(); } // 校验通过,正常跳转主应用 jump_to_app(); }

校验函数必须在跳转到主应用之前调用,一旦校验失败就停止启动并进入安全状态。去除未使用的函数、保证整个 Flash 区域计算结果与参考值一致是方案要点。

方案二:只校验关键函数(针对性保护)

单粒子翻转通常是小概率、随机的,对全部 Flash 做完整校验耗时较长。可以只对关键函数(如安全关断、中断处理)所在段做 CRC 保护,配合上文的__attribute__((section))分段机制:

  1. 把关键函数放入单独段(如.func_crc);
  2. 用链接脚本的__START__/__END__符号标记该段起止地址;
  3. 用同段内 CRC 与该段的参考值比对。
关键函数定位到固定段 → extern uint32_t __func_crc_start, __func_crc_end; uint32_t len_words = (uint32_t)&__func_crc_end - (uint32_t)&__func_crc_start; crc = calculate_crc32((uint32_t*)&__func_crc_start, len_words);

方案三:运行时周期自检(持续防护)

单粒子翻转可能在上电后的运行中发生,因此周期性(由定时器触发)对运行代码区重新计算 CRC比对,是更完整的防护。注意:

  • 自检期间避免同时执行被校验区代码,或选用短小的临界区段;
  • 校验本身使用的函数应放在 CRC 保护区之外,避免"以被篡改的代码验证被篡改的代码";
  • 翻转本质是位翻转检测,检测到后应转入安全状态(停机、进入安全模式、复位),因为多数场合无法在运行中纠正 Flash 内容(需要重新烧写/从备份区恢复)。

关键注意事项汇总

  1. 参考值需与内容严格一致:CRC 参考值必须是在链接后基于最终烧录内容的计算结果,否则无法匹配——一般由编译后脚本(如 srec_cat、Python 脚本)在生成 bin 后计算并追加到预留地址。
  2. 硬件 CRC 速度优势:STM32F4 硬件 CRC 每 4 个 AHB 周期完成一次 32 位输入计算,远快于软件实现,适合运行期自检。
  3. KEEP/满引用函数:固定分段函数若未被调用需__attribute__((used))或KEEP保留,否则链接器会剔除,导致地址/CRC 不匹配。
  4. 覆盖范围:CRC 校验应覆盖.text + .rodata + .data 初始值等程序区,以及关键配置数据,避免遗漏。
  5. 无法自修复:SEU 翻转基本是破坏性的(可擦除 Flash 但难以原位纠错),所以工程上通常是检测并进入安全态,配合备份机制(双分区 A/B、从备份区恢复)提升可靠性。
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/10/2 6:57:23

养老金资格认证平台:不只是每年刷个脸

养老金资格认证平台&#xff1a;不只是"每年刷个脸" 文章目录养老金资格认证平台&#xff1a;不只是"每年刷个脸"一、问题二、平台架构&#xff1a;七个模块认证管理生存认证 H5 平台自助终端认证系统查询统计分析社会化管理数据监管数据同步接口档案信息管…

作者头像 李华
网站建设 2026/10/2 6:57:23

WorldAuditBench:面向多模态智能体的交互式三维世界审计评测基准

WorldAuditBench&#xff1a;面向多模态智能体的交互式三维世界审计评测基准 arXiv编号&#xff1a;arXiv:2609.40325v1 [cs.AI] 摘要 交互式三维虚拟世界越来越多地被用于智能行为研究&#xff0c;如何高效识别仿真环境中的各类异常&#xff08;物体漂浮、可穿透墙体、物体随视…

作者头像 李华
网站建设 2026/10/2 6:57:20

POC测试评分表:技术交付的可量化契约与自动化验证指南

简介&#xff1a;本资源是一份标准化的POC测试评分表&#xff08;Word文档&#xff09;&#xff0c;面向企业IT架构师、系统集成工程师及业务需求分析师&#xff0c;用于在概念验证阶段科学评估解决方案的功能适配性与系统集成能力。表格聚焦功能满足程度与接口满足程度两大核心…

作者头像 李华
网站建设 2026/10/2 6:57:17

电影购票系统(协同过滤算法影片推荐、ECharts 影院经营数据看板、影片排片与可视化选座、座位锁定及超时自动释放、支付宝沙箱支付、订单退票申请审核、影片与影院收藏、影片评论点赞及回复)

系统亮点&#xff1a;协同过滤算法影片推荐、ECharts 影院经营数据看板、影片排片与可视化选座、座位锁定及超时自动释放、支付宝沙箱支付、订单退票申请审核、影片与影院收藏、影片评论点赞及回复&#xff1b;一、项目概述电影购票系统采用前后端分离架构&#xff0c;面向普通…

作者头像 李华
网站建设 2026/10/2 6:57:16

给AI改名,改的是定价权

《给AI改名&#xff0c;改的是定价权》 ——名字可以先到未来&#xff0c;能力得一步一步走过去一个词&#xff0c;两个字母&#xff0c;不到十天&#xff0c;让两位市值最高公司的掌门人当众改了口。事情说来像段子。九月二十二日&#xff0c;美国总统站在联合国讲台上说&…

作者头像 李华
网站建设 2026/10/2 6:57:09

家庭影院K歌音响的音质优势与性价比分析

在家搭建兼具观影和K歌功能的音响系统时&#xff0c;很多人会混淆家庭影院音质和K歌音响音质的评判标准&#xff0c;也容易陷入“音质好一定贵”“低价产品肯定效果差”的误区。实际上&#xff0c;家庭影院K歌音响的音质表现和性价比&#xff0c;都可以通过固定维度拆解&#x…

作者头像 李华