Files
STM8_Mesh_Control/docs/BOOTLOADER_FACTORY_RECOVERY_TEST.md
T

3.3 KiB
Raw Blame History

汇编 Bootloader 出厂固件恢复验证记录

1. 验证目的

验证当 STM8S003F3P6TR 内部应用 Flash 没有主程序时,汇编 Bootloader 能否从外部 W25Q80BV 读取出厂固件,完成内部应用区恢复,并跳转到主程序执行。

2. 当前地址规划

区域 地址范围 说明
Bootloader 0x8000~0x84FF 固定汇编 Bootloader 区域
主程序 0x8500~0x9FFF 汇编主程序运行区域
出厂固件 W25Q80BV 0x000000~0x001FFF 最大 8KiB
出厂元数据 W25Q80BV 0x002000~0x002FFF 4KiB 区域

3. 外部 Flash 内容验证

独立 SPI 测试固件已经读取并校验出厂镜像,串口输出如下:

SPI TEST START
JEDEC OK
MAGIC: 31434146
LENGTH: 06AE
VERSION: 0100
STORED CRC: DF89
VALID: A5
CALC CRC: DF89
FACTORY IMAGE PASS

因此确认:

  • W25Q80BV JEDEC ID 读取正常;
  • 出厂固件魔数正确;
  • 出厂固件长度为 0x06AE;
  • 出厂固件版本为 0x0100;
  • 元数据保存 CRC 为 0xDF89;
  • Bootloader 有效标志为 0xA5;
  • 单片机重新计算 CRC 后仍为 0xDF89。

4. Bootloader 恢复流程

当前汇编 Bootloader 的出厂恢复流程为:

  1. 设置系统时钟为 16MHz;
  2. 初始化 SPI1;
  3. 读取并检查 W25Q80BV JEDEC ID;
  4. 检查出厂固件元数据;
  5. 按 CRC-16/MODBUS 逐字节校验出厂固件;
  6. 解锁 STM8 程序 Flash;
  7. 对 0x8500~0x9FFF 应用区逐字节擦除;
  8. 从 W25Q80BV 0x000000 开始逐字节搬运到内部 Flash 0x8500;
  9. 回读内部 Flash,并与外部出厂镜像逐字节比较;
  10. 跳转到主程序复位向量执行。

5. 现场验证结果

验证前先清除内部 Flash 的主程序区域,使 0x8500 之后没有有效主程序。重新烧录 Bootloader 并上电后,设备能够自动完成出厂固件搬运,随后主程序正常启动,并输出蓝牙初始化相关信息:

AT+ROLE
AT+ROLE2
AT+ROLE
AT+ROLE2
AT+ROLE

验证结论:

内部 Flash 无主程序时,Bootloader 自动从 W25Q80BV 搬运出厂固件并成功启动主程序,功能验证通过。

6. 调试代码清理

为便于现场确认,曾临时加入 Bootloader UART1 阶段输出。恢复流程验证完成后,已经删除:

  • Bootloader UART1 初始化代码;
  • 临时阶段字符输出;
  • 元数据诊断输出;
  • CRC、擦除、搬运、回读和跳转诊断输出。

正式 Bootloader 不再占用 UART1 发送调试功能。

7. 本次修正的关键问题

7.1 元数据长度解析

固件长度字段是 4 字节高字节在前:

00 00 06 AE

前两个字节必须为 0x00,后两个字节才是实际长度 0x06AE。

7.2 CRC 多项式

CRC-16/MODBUS 反射算法使用多项式 0xA001。在当前两个字节寄存器实现中:

高字节异或:0xA0
低字节异或:0x01

7.3 STM8 Flash 擦除方式

块擦除流程要求连续装载 4 个字节,并且关键步骤需要从 RAM 执行。当前 Bootloader 采用逐字节擦除方式,向应用区每个地址写入 0x00,每次等待 EOP 完成,避免块擦除流程在 Flash 中执行时卡住。

7.4 EOP 标志

当前项目使用的 STM8S003 寄存器定义中,FLASH_IAPSR.EOP 掩码为 0x04,即 bit2。Bootloader 按 bit2 检测擦除和写入完成状态。