SEO技术

SEO技术

Products

当前位置:首页 > SEO技术 >

STM32F103_AB_OTA教程如何从零开始?

96SEO 2026-09-08 05:27 33


在 STM32F103 系列上实现 OTA升级,看似简单却隐藏着不少技术细节和坑点。本教程从最基础的概念出发,逐步带你搭建 Bootloader、两份 App、还有串口通信协议。并通过 Qt 图形上位机完成 A→B、B→A 的升级流程。就在这个时候我在每个关键环节都标注了开发者常遇到的痛点,让你在实践中一目了然。按理说,

先把几个概念分清

三种“程序”

痛点: 很多人误认为 STM32 内置 Bootloader 就能直接用 OTA;你必须自行实现 UART IAP 并与上位机协议匹配,否则会出现“烧写失败”“无 Banner”等现象。

STM32F103_AB_OTA教程如何从零开始?

UART IAP 与联网 OTA

当前数据链路是:Windows 上位机 — USB‑TTL / USART1 — 使用者 Flash Bootloader。若未来让 4G/Wi‑Fi/蓝牙模块透明传输完全相同字节流,即可称为 OTA。仓库目前没有 TCP/HTTP/MQTT 或无线驱动。

逻辑 A/B 不等于硬件 Dual‑Bank

STM32F103xE 的这里没有使用硬件 Bank Swap。Slot A、Slot B 是同一片 Flash 中的两段地址。Bootloader 通过'SCB->VTOR',MSP 和 Reset_Handler 手动选择运行哪一段。

CRC 不是签名

  • CRC16: 发现单帧传输误码;不防篡改,
  • 从CRC32来看,比对 PC 与 Flash 是否一致;一样不防篡改或验证发布者身份。
  • 量产设备需签名、公钥验证、版本策略和密钥管理。

硬件、软件与芯片核验

推荐硬件清单

  • SSTM32F103RET6 最小程序板或自制板;
  • S-T-Link V2/V3;
  • ZUSB‑TTL;
  • Dupont线;
  • 稳定的 5V 电源;
  • SSD1306 OLED 模块,用于07_ret6_oled 示例。

No direct ±RS‑电平接到 PA9/PA10。USB‑TTL 必须使用 5V 电平。而且 MCU 共地,否则通讯会出现奇怪错误。

RET6 与 ZET6 区别检查建议:

  1. 打开 CubeMX 每个 .ioc;
  2. `
  3. 将器件改为实际型号和 LQFP144 封装;
  4. `
  5. 重新核对 LED、USART、OLED、晶振等引脚;
  6. `
  7. 不要仅因 Flash/SRAM 容量相同就直接沿用 RET6 接线方案。怎么说呢,` ` ` ` ` ` ` ` ` ` `

    Pain Point: 很多人把 ZET6 的引脚布局直接复制到 RET6 上板。却因为封装不同导致某些外设失效,例如 OLED 无显示或 LED 灯不亮。请务必按照实际器件修改 .ioc 并核对原理图!.

    Windows 软件工具推荐:

    • S STM32CubeProgrammer – 用来烧录 HEX 首次部署时最使用较稳定;
    • A arm-none-eabi-gcc – 确保命令行工具可用;话说回来,li>
    • CMake + Ninja – 简化建立流程;li>
    • P Python – 用来跑 ota_gui.py / ota.py;不过,li>
    • CLion / VS Code – 开发环境。`

      Pain Point: No PATH config → arm-none-eabi-gcc 未能识别导致编译报错!请确认已加入 PATH 或按官方手册设置环境变量。.

      . 读懂工程目录和 Flash 地图

      工程结构快速导航

      stm32_ab_ota/ ├── bootloader/ │ └── Core/Src/ │ ├── main.c // OTA入口与状态机 │ ├── boot_protocol.c // AA55 帧和命令 │ ├── boot_flash.c // 页擦除、半字写入 │ ├── boot_jump.c // 镜像检查 & 跳转 │ ├── boot_metadata.c // Metadata read/write │ └── boot_crc.c // CRC16 / CRC32 ├── app/app/ │ └── ├── 07_ret6_oled/ └── tools/ ├── ota.py // CLI 协议实现 └── ota_gui.py // Qt 图形上位机 `boot_config.h` 定义所有分区起始地址。怎么说呢,c **Flash 分区图**
名称存放位置谁提供本项目如何进入
STM32 ROM/System Memory Bootloader 芯片程序存储区。由 ST 出厂固化,进入方式通过 BOOT 配置;协议见 AN2606/AN3155。
Bootloader 使用者 Flash(0x08000000);每次复位先运行,
本项目自定义帧以 A A 55 开头,不是 ST ROM Bootloader 的 AN3155 协议。
UART 上位机与 CubeProgrammer 使用不同协议。
Application Slot A / B 同一源码链接成 A/B 两份;Bootloader 校验向量表后跳转。
分区 起始地址 结束地址 大小
Bootloader 0x08000000 0x08007FFF 8 KiB
Slot A 0x08008000 0x0803FFFF 224 KiB
Slot B 0x08040000 0x08077FFF 224 KiB
Metadata 0x08078000 0x0807FFFF 8 KiB

Metadata 虽预留 8 KiB当前只写前面几百字节用于存储 CRC & 状态。


为什么每槽都是 KiB?

Flash 页大小是 1 KiB所有分区起始地址都必须页对齐,以避免擦写错误。


从常见错误提示来看,

  • “Invalid vector table”:起始地址不在 Slot A/B 范围内或 MSR 越界。其实,
  • “Bootloader missing”:Bootloader 被误删导致 MCU无法启动。
  • “CRC mismatch”:文件损坏或传输过程中出现噪声。

推荐检查方式

bash arm-none-eabi-nm --size-sort --print-size app/app/build/Debug/app_a.elf \ --reverse -C -t dS \ | grep '^*$'

此命令可快速定位向量表是否正确放置。


Cortex-M³ 跳转机制

向量表前两个字段

c /* offset +0×00 : initial MSP */ p = SRAM_TOP;不过,/* offset +0×04 : Reset_Handler 地址 */ p = &Reset_Handler;

Bootloader 在跳转前会做以下检查:

  1. 起始地址必须是 Slot A 或 B;
  2. 镜像长度至少 256 字节 且不越过槽边界;
  3. MSP 位于合法 SRAM 范围且四字节对齐;不过,
  4. Reset_Handler 地址最低位为 Thumb;
  5. 清除 Thumb 位后的地址仍落在镜像内。

跳转步骤

c _disableirq;HALDeInit;SysTick->CTRL = SysTickCTRLCLKSOURCEMsk;SysTick->LOAD = SysTickLOADRELOADMsk;SysTick->VAL = SysTickVALCURRENTMsk; 按理说,

SCB->VTOR = appaddress;_DSB;__ISB,

_setMSP;appresethandler);

再看注意,Bootloader 在跳转后不会 开启全局中断。如果忘记执行 #define __enable_irq 则会导致 HAL_Delay 卡死。


同一 App 必须生成 appa 与 appb

由于 STM32 没有 MMU,链接器根据 决定向量表及代码位置。我们必须分别为 Slot A 与 B 建立两份二进制:

c

addexecutable addexecutable

targetlinkoptions targetlinkoptions

如何避免混淆?

  • 用 app_a.bin 烧到 Slot A,用 app_b.bin 烧到 Slot B。
  • 如果想验证 OLED 示例,请烧录专门的 <07_ret6_oled.bin> 到 Slot B。

建立流程

bash

cmake --preset Debug -S bootloader && cmake --build build/Debug --target bootloader

cmake --preset Debug -S app/app && cmake --build build/Debug --target appa appb

cmake --preset Debug -S 07ret6oled && cmake --build build/Debug --target defaultTargetNameHere

检查产物位置

text bootloader/build/Debug: ├─ bootloader.hex │ bin │ elf app/app/build/Debug: ├─ app_a.hex │ bin │ elf ├─ app_b.hex │ bin │ elf


第一次用 ST-Link 部署

最低连线要求

如果你看到「Mass Erase」被勾选后启动时闪退。那说明你误删了 Bootloader —— 一定要先烧录 BootLoader,再烧录 App。

串口连接 & OTA 模式入口

连接方式这方面,text STM32 PA9 ---- USB‑TTL RX STM32 PA10 <---- USB‑TTL TX GND ---- GND 波特率固定:115200 bps,无奇偶校验,一停止位,无流控。

OTA 启动细节:

  • 第一次收到 ASCII 'U' 时才进入 OTA 循环。
  • 若首字节是噪声,则后续任何 <‘U’> 都无效——这正是许多新手报错原因之一。话说回来,
  • 上位机会每毫秒发送一次 <‘U’>最多持续三秒。按理说,正确流程如下的观点是。
    1. 打开串口并点击「连接设备」;话说回来,
    2. MCU 按 RESET 或重电源后等待提示「请复位」;
    3. 按下 RESET 并立即观察日志出现 OK: Enter OTA mode.

Qt 图形上位机完成 A→B 升级

启动 GUI:`py ota_gui.py`. 从操作顺序来看,1️⃣ 刷新 → COM 接口选择 → 波特率保持默认 2️⃣ 打开串口 → 点击「连接设备」 3️⃣ MCU 重置 → 等待日志 ``OK: Enter OTA mode`` 4️⃣ 点击「查询信息」获取 Flash 布局 GUI 会自动判断目标槽与回滚槽。例如升级至 B 时回滚槽推导为 A。如果你刚更改默认槽或者手工烧过 flash,请勿随意点击「确定」。过程主要包含的观点是,
  • ERASE → DATA × N → VERIFY → MARK_PENDING → BOOT
  • GUI 会 校验 CRC 与本地计算值是否一致。再发送 CONFIRM 命令确认新镜像有效。

验证后确认新固件

完成后在 B slot 正常运行,再回到 GUI 点击「确认新固件」。此时 GUI 将 发送 ``CONFIRM`` 并等待响应,接下来再触发 ``BOOT`` 跳转至新的 confirmed 镜像。如果你没按下 Reset 而直接进入 OTAloop,那么 MCU 将继续停留在 OTAloop 而不是切换至新的应用。怎么说呢,

完成 B→A 的反向升级

确保 B 已经经过 CONFIRM 并能正常运行。接下来: 1️⃣ MCU 重置进入 BootLoader 2️⃣ 在 GUI 中选择 ``app_a.bin`` 并指定目标槽 A 3️⃣ 回滚槽自动识别为 B 4️⃣ 开始升级并确认即可恢复旧版本。如果你把 B 写到了 A 或者把 A 写到了 B,上位机会因为 Vector Table 检查失败而拒绝操作——这就是为什么有些人收到错误码 “invalid target address”。按理说,

四次复位回滚实验

实验假设当前状态:Slot A 已经 confirmed。并准备将 new 固件写入 Slot B,但未执行 CONFIRM 步骤。按下下面步骤可以验证跨复位回滚逻辑是否正常工作: 1️⃣ 完成 A→B 升级,但 **不要点击「确认新固件」**。此时 MCU 已切换至 B,但 metadata 状态仍为 PENDING。2️⃣ 第一次普通复位 —— 启动 Log 中应显示 ``count>= X+1``。此时仍继续运行 B,并不会立刻回滚。3️⃣ 第二次普通复位 —— 一样保持 PENDING 状态并继续运行 B。不过,4️⃣ 第三次普通复位 —— 此时 metadata 判断 count 超阈值,于是自动回滚至 confirmed 槽即 Slot A,并打印日志 ``Recovered to confirmed slot``. 如果在第 n 次重启后还停留在新的镜像,而不是回滚。那么可能存在以下问题:
  • metadata 未正确更新
  • IWDG 未启用导致硬故障未强制重启
  • 硬件供电波动导致 flash 写失效

协议细则 & 元数据原理

自定义帧结构

text 其中 LEN 是 payload 长度 u16 小端,最大值为 DATA 最大块大小。CRC16 覆盖 CMD+SEQ+LEN+PAYLOAD,本身以小端发送。
命令列表示例
LNK SWDIO SWDCLK 
CMD 名称 值 请求 payload 成功响应 payload
INFO 01 无 固件版本 / Flash / Slots
ERASE 02 address:u32 + size:u32 status:u8
DATA 03 address:u32 + data status:u8
VERIFY 04 …

所有 u64 字段均采用小端格式。这一点非常关键,否则 PC 与 MCU 会产生 CRC mismatch 报错!

为什么 DATA 每块固定512字节?

为了兼容 STM32 HAL 半字写入还有保持协议整齐性。每块最大送达512字节——若最终一块不足则填补为空白且保持偶数长度,否则主机会直接拒绝上传而非隐式补齐。这也是许多人上传奇数长度 BIN 后出现“不完整包”的根源所在!

Metadata 定义

c typedef struct { uint32_t magic;uint32_t state;uint32_t confirmed_slot;uint32_t pending_slot;uint32_t boot_count;uint32_t crc;uint32_t size;} __attribute__) boot_metadata_t; Metadata 存放于 Flash 最终一页 (BOTHSLOTSEND + PAGESIZE - METADATAPAGE_SIZE)。该结构仅记录全局状态,不针对每个 slot 独立维护 EMPTY/INVALID 标记。所以任何更改都需重写整个 page,以保证原子性。


命令行工具用法

至于查看帮助,

bash py ota.py --help

从典型上传命令来看,

bash py ota.py ..\app\app\build\Debug\app_b.bin \ --port COM5 \ --target 0x08040000 \ --confirmed 0x08008000

CLI 当前只负责升级,不提供 confirm 子命令,请使用 GUI 或自行发送 CMD_CONFIRM.


常见故障排查 Cheat Sheet

现象可能原因排查方法/解决办法)

No banner。LED doesn't run after Mass Erase.

...


当前边界与量产化路线建议

已实现功能 vs 待完善功能 ❌

✓ 两份 App 链接独立镜像 ✓ 自定义 UART IAP 帧及 CRC ✓ 单槽边界擦写保护 ✓ PENDING/CONFIRMED 状态及跨复位计数 ✓ 主机侧向量检查 ✓ 手工 Confirm 与四次回滚实验验证

❌ 固件数字签名、公钥验证 ❌ anti‑rollback 策略与版本控制 ❌ 数据包重试/窗口/去重/断点续传 ❌ App 自动健康检测 ❌ Metadata 双副本与事务提交

建议优先实现 Metadata 双页副本++结构 CRC,接下来引入公钥签名验证,还有 IWDG+App 健康检测形成完整流程。按理说,如需网络下载,可考虑 TLS 加密通道并结合设备身份管理。实现真正使用较稳定的大规模 OTA 部署。


快速代码导览 & 官方资料引用

主题文件 / 函数列表说明

参考文献包括 STM32201 数据手册、RM0008 等官方文档,还有开源项目如 MCUboot/wolfBoot 对比学习。但请记住本仓库采用自定义协议和元数据模型。与这些成熟方案存在差异,需要自行适配才能迁移或合并代码。


标签: 教程

SEO优化服务概述

作为专业的SEO优化服务提供商,我们致力于通过科学、系统的搜索引擎优化策略,帮助企业在百度、Google等搜索引擎中获得更高的排名和流量。我们的服务涵盖网站结构优化、内容优化、技术SEO和链接建设等多个维度。

百度官方合作伙伴 白帽SEO技术 数据驱动优化 效果长期稳定

SEO优化核心服务

网站技术SEO

  • 网站结构优化 - 提升网站爬虫可访问性
  • 页面速度优化 - 缩短加载时间,提高用户体验
  • 移动端适配 - 确保移动设备友好性
  • HTTPS安全协议 - 提升网站安全性与信任度
  • 结构化数据标记 - 增强搜索结果显示效果

内容优化服务

  • 关键词研究与布局 - 精准定位目标关键词
  • 高质量内容创作 - 原创、专业、有价值的内容
  • Meta标签优化 - 提升点击率和相关性
  • 内容更新策略 - 保持网站内容新鲜度
  • 多媒体内容优化 - 图片、视频SEO优化

外链建设策略

  • 高质量外链获取 - 权威网站链接建设
  • 品牌提及监控 - 追踪品牌在线曝光
  • 行业目录提交 - 提升网站基础权威
  • 社交媒体整合 - 增强内容传播力
  • 链接质量分析 - 避免低质量链接风险

SEO服务方案对比

服务项目 基础套餐 标准套餐 高级定制
关键词优化数量 10-20个核心词 30-50个核心词+长尾词 80-150个全方位覆盖
内容优化 基础页面优化 全站内容优化+每月5篇原创 个性化内容策略+每月15篇原创
技术SEO 基本技术检查 全面技术优化+移动适配 深度技术重构+性能优化
外链建设 每月5-10条 每月20-30条高质量外链 每月50+条多渠道外链
数据报告 月度基础报告 双周详细报告+分析 每周深度报告+策略调整
效果保障 3-6个月见效 2-4个月见效 1-3个月快速见效

SEO优化实施流程

我们的SEO优化服务遵循科学严谨的流程,确保每一步都基于数据分析和行业最佳实践:

1

网站诊断分析

全面检测网站技术问题、内容质量、竞争对手情况,制定个性化优化方案。

2

关键词策略制定

基于用户搜索意图和商业目标,制定全面的关键词矩阵和布局策略。

3

技术优化实施

解决网站技术问题,优化网站结构,提升页面速度和移动端体验。

4

内容优化建设

创作高质量原创内容,优化现有页面,建立内容更新机制。

5

外链建设推广

获取高质量外部链接,建立品牌在线影响力,提升网站权威度。

6

数据监控调整

持续监控排名、流量和转化数据,根据效果调整优化策略。

SEO优化常见问题

SEO优化一般需要多长时间才能看到效果?
SEO是一个渐进的过程,通常需要3-6个月才能看到明显效果。具体时间取决于网站现状、竞争程度和优化强度。我们的标准套餐一般在2-4个月内开始显现效果,高级定制方案可能在1-3个月内就能看到初步成果。
你们使用白帽SEO技术还是黑帽技术?
我们始终坚持使用白帽SEO技术,遵循搜索引擎的官方指南。我们的优化策略注重长期效果和可持续性,绝不使用任何可能导致网站被惩罚的违规手段。作为百度官方合作伙伴,我们承诺提供安全、合规的SEO服务。
SEO优化后效果能持续多久?
通过我们的白帽SEO策略获得的排名和流量具有长期稳定性。一旦网站达到理想排名,只需适当的维护和更新,效果可以持续数年。我们提供优化后维护服务,确保您的网站长期保持竞争优势。
你们提供SEO优化效果保障吗?
我们提供基于数据的SEO效果承诺。根据服务套餐不同,我们承诺在约定时间内将核心关键词优化到指定排名位置,或实现约定的自然流量增长目标。所有承诺都会在服务合同中明确约定,并提供详细的KPI衡量标准。

SEO优化效果数据

基于我们服务的客户数据统计,平均优化效果如下:

+85%
自然搜索流量提升
+120%
关键词排名数量
+60%
网站转化率提升
3-6月
平均见效周期

行业案例 - 制造业

  • 优化前:日均自然流量120,核心词无排名
  • 优化6个月后:日均自然流量950,15个核心词首页排名
  • 效果提升:流量增长692%,询盘量增加320%

行业案例 - 电商

  • 优化前:月均自然订单50单,转化率1.2%
  • 优化4个月后:月均自然订单210单,转化率2.8%
  • 效果提升:订单增长320%,转化率提升133%

行业案例 - 教育

  • 优化前:月均咨询量35个,主要依赖付费广告
  • 优化5个月后:月均咨询量180个,自然流量占比65%
  • 效果提升:咨询量增长414%,营销成本降低57%

为什么选择我们的SEO服务

专业团队

  • 10年以上SEO经验专家带队
  • 百度、Google认证工程师
  • 内容创作、技术开发、数据分析多领域团队
  • 持续培训保持技术领先

数据驱动

  • 自主研发SEO分析工具
  • 实时排名监控系统
  • 竞争对手深度分析
  • 效果可视化报告

透明合作

  • 清晰的服务内容和价格
  • 定期进展汇报和沟通
  • 效果数据实时可查
  • 灵活的合同条款

我们的SEO服务理念

我们坚信,真正的SEO优化不仅仅是追求排名,而是通过提供优质内容、优化用户体验、建立网站权威,最终实现可持续的业务增长。我们的目标是与客户建立长期合作关系,共同成长。

提交需求或反馈

Demand feedback