夜雨聆风学习资料网

ARTICLE · 1326558

YMODEM 串口升级协议技术文档

YMODEM 串口升级协议技术文档

1概述

1.1协议简介

YMODEM 是由 Chuck Forsberg 于 1985 年在 XMODEM 基础上改进提出的一种面向串行链路的文件传输协议。它在 XMODEM 的帧格式之上引入了 1024 字节大块、CRC-16 校验、文件名与文件大小传输以及批量文件传输(YMODEM Batch)等能力,至今仍是嵌入式设备通过 UART/RS-232/USB 虚拟串口进行固件升级(Bootloader OTA)最常用的协议之一。

协议本质是“停等式”(stop-and-wait)滑动窗口协议:发送方每发一个数据块,必须等待接收方回复 ACK 后才能继续发下一块;任何一块出错或超时未应答,发送方重发当前块。这种机制实现简单、可靠,对底层链路要求低,非常适合 MCU 片上 Bootloader。

1.2典型应用场景

YMODEM 在工业控制、伺服驱动、变频器、仪器仪表等设备的串口固件升级中被广泛采用。典型上位机工具包括 Tera Term、SecureCRT、Xshell、minicom、sz/rz 命令行等,设备侧则由 Bootloader 实现接收端逻辑。

1.3主要特点

(1)数据块长度可选:128 字节(SOH 头)或 1024 字节(STX 头),长块显著提升吞吐率。

(2)校验方式:默认采用 CRC-16(CCITT 多项式 0x1021),替代了早期 XMODEM 的累加和校验,误检率极低。

(3)文件信息随附:第 0 块携带文件名、文件大小、修改时间,接收方可据此分配缓冲区或擦除 Flash 区域。

(4)支持批量传输:一次会话可连续传送多个文件,以空第 0 块作为批结束标志。

(5)实现成本低:Bootloader 侧只需实现串口收发、CRC 计算和简单状态机,代码量通常在 1~3 KB。

2物理层与传输参数

YMODEM 本身不规定物理层,它运行在任意字节透明的串行通道之上。嵌入式升级中常见配置如下:

参数

典型取值

说明

物理接口

UART TTL /   RS-232 / RS-485 / USB-CDC

要求全双工或可切换方向的半双工链路

数据位

8

标准 8N1

校验位

None

链路层校验由 YMODEM 自身 CRC 完成

停止位

1

8N1 配置

波特率

9600 / 115200 /   460800 / 921600

Bootloader 与上位机必须一致

流控

通常不使用硬件流控

依靠协议层 ACK/NAK 做停等

表 1典型串口参数

3控制字符定义

YMODEM 协议使用一组固定的单字节控制符,它们同时也是 ASCII 控制字符,取值不可与数据域混淆(数据域中的相同字节由上层保证不会与帧首冲突)。

符号

十六进制

ASCII 含义

方向

作用

SOH

0x01

Start of Heading

发送方→接收方

标识本块数据长度为 128 字节

STX

0x02

Start of Text

发送方→接收方

标识本块数据长度为 1024 字节

EOT

0x04

End of Transmission

发送方→接收方

文件内容发送完毕

ACK

0x06

Acknowledge

接收方→发送方

上一块正确接收,请继续下一块

NAK

0x15

Negative Acknowledge

接收方→发送方

上一块出错(CRC 错),请重发

CAN

0x18

Cancel

双向

取消当前传输(连发两次 CAN 才生效)

C

0x43

ASCII 'C'

接收方→发送方

请求以 CRC-16 模式启动传输

表 2YMODEM 控制字符一览

注意:早期 XMODEM 以 NAK(0x15)作为启动符,表示请求累加和校验;YMODEM 统一改用字符 “C”(0x43)作为启动符,表示请求 CRC-16 校验。Bootloader 上电后应循环发送 “C” 等待上位机发起传输。

4帧结构

4.1通用帧格式

YMODEM 的每个数据块(Block)由 6 个部分组成,总长为:头(1) + 块号(1) + 补码块号(1) + 数据(N) + CRC16(2)。

字段

长度(字节)

取值说明

Header

1

SOH(0x01) 表示   128 字节数据;STX(0x02) 表示   1024 字节数据

Block Number

1

块号,从 0 开始;数据块从 1 开始;8 位无符号,超过 255 后回绕到 0

~Block Number

1

块号的按位取反(即 255 - Block Number),用于校验帧头同步

Data

128 或 1024

负载数据;不足长度时按协议规则填充

CRC High

1

CRC-16 高字节(先发送)

CRC Low

1

CRC-16 低字节(后发送)

表 3YMODEM 数据帧结构

整帧长度示意(以 1024 字节块为例):

| SOH/STX | BlockNo | ~BlockNo | Data[1024] | CRC_H | CRC_L |

1B1B1B1024B1B1B= 1029 B

4.2块号规则

块号是协议层排序与去重的核心:

(1)第 0 块(Block 0)专用于携带文件名、文件大小等元信息,不携带固件数据。

(2)固件数据从第 1 块(Block 1)开始编号。

(3)块号为 8 位无符号整数,递增加 1;到达 255 后下一块为 0(回绕)。

(4)接收方若收到“预期块号不一致”的块(例如重复块),仍应回复 ACK,但丢弃数据,以维持同步。

(5)补码块号字段用于检测帧头错位:若 BlockNo 与 ~BlockNo 之和不等于 0xFF,说明链路字节错位,应直接 NAK 或丢弃该帧。

4.3CRC-16 校验

YMODEM 使用 CCITT 标准 CRC-16,多项式为 0x1021,初始值为 0x0000(注意:不是 Modbus 常用的 0xFFFF 初始值)。计算范围覆盖整个 Data 字段(128 或 1024 字节),不包含 Header、块号与 CRC 字段本身。

CRC 以“高字节在前、低字节在后”的顺序追加在数据域之后,这一点与 Modbus RTU 的低字节在前不同,实现时需特别注意。

CRC-16/CCITT 参数:多项式= 0x1021初始值= 0x0000输入反射 = False输出反射 = False异或输出 = 0x0000

5块类型详解

5.1第 0 块:文件信息头块

第 0 块在整个传输流程中承担“握手 + 文件元信息”的作用。数据域布局如下:

偏移

长度

内容

说明

0

变长

文件名

ASCIZ 字符串(以 0x00 结尾),通常为固件名如 app.bin

紧随文件名

变长

文件大小

十进制 ASCII 数字字符串,如“123456”,以   0x00 结尾

紧随大小

变长

修改时间

可选,Unix 时间戳八进制 ASCII,以   0x00 结尾

紧随时间

变长

文件模式

可选,八进制 ASCII,如“0644”

剩余

填充

0x00

数据域剩余字节全部填 0

表 4第 0 块数据域布局

示例:一个大小为 0x1E000(122880 字节)、文件名为 app.bin 的头块数据域前若干字节为:

61 70 70 2E 62 69 6E 00 31 32 32 38 38 30 00 00 00 ...|"app.bin"| | "122880" | 后续全部 0x00 填充

批传输结束标志:当一个第 0 块的数据域第一个字节就是 0x00(即文件名为空),表示当前没有更多文件可传,接收方据此结束整个会话。

5.2数据块(Block 1 起)

从 Block 1 开始,数据域直接承载固件二进制内容。关于块长度与填充规则:

(1)默认使用 1024 字节长块(STX),以提高吞吐;128 字节短块(SOH)用于低速或不可靠链路。

(2)最后一个数据块若不足 1024 字节,剩余字节必须以 0x1A(Ctrl+Z)填充,这是 YMODEM 与 XMODEM 兼容的历史约定;接收方在写入 Flash 时应按第 0 块声明的文件大小截断,丢弃填充字节。

(3)接收方每收到一个正确数据块,应立即将数据写入目标 Flash 地址,再回复 ACK;这种“边收边写”策略可避免占用大块 RAM。

5.3EOT 结束

发送方发完最后一个数据块并收到 ACK 后,发送单字节 EOT(0x04)。接收方收到 EOT 后,第一次应回复 NAK(0x15),发送方随后再次发送 EOT,接收方再回复 ACK。这种“EOT → NAK → EOT → ACK”的两次握手是 YMODEM的标准约定,用于防止 EOT 字节在链路中丢失而导致死等。

5.4批传输结束空块

单文件升级场景中,Bootloader 收到 EOT 的 ACK 后即可直接跳转应用。若上位机支持批量传输,则 EOT 流程结束后,上位机会再发送一个第 0 块(数据域全 0),接收方回复 ACK 后整个会话结束。Bootloader 通常只实现单文件模式,收到空第 0 块后直接结束即可。

6完整升级流程

6.1时序总览

以下以 Bootloader 为接收方、上位机(如Tera Term)为发送方,描述一次完整的单文件 YMODEM 升级时序:

Bootloader(接收)上位机(发送)|||--- "C" (循环发送, 每 1~3s) -->||| 收到 "C"|<-- SOH Blk0 ~Blk0 "app.bin 122880" CRC --||解析文件名/大小, 擦除 Flash||--- ACK ----------------------->||--- "C" ------------------------>||| 开始发数据|<-- STX Blk1 ~Blk1 data[1024] CRC ---||写 Flash, 校验通过||--- ACK ----------------------->||<-- STX Blk2 ~Blk2 data[1024] CRC ---||--- ACK ----------------------->||... 重复 ...||<-- STX BlkN ~BlkN data[剩余+0x1A] CRC||--- ACK ----------------------->||||<-- EOT (0x04) ------------------||--- NAK (0x15) ----------------->||<-- EOT (0x04) ------------------||--- ACK ------------------------>||--- "C" (可选, 等下一文件) ----->||<-- SOH Blk0 全 0 (批结束) -------||--- ACK ------------------------>||校验固件, 跳转应用|

6.2启动阶段

(1)设备上电或复位后,Bootloader 先判断是否进入升级模式(例如检测某 GPIO 为低电平、按键按下、或应用区标志位无效)。

(2)进入升级模式后,Bootloader 通过串口循环发送字符 “C”(0x43),发送间隔通常为 1~3 秒,持续若干次(例如 10 次),超时则放弃升级、跳转应用。

(3)上位机在收到第一个 “C” 后,立即发送第 0 块(文件信息块)。

6.3文件头传输

(1)Bootloader 接收第 0 块,校验 SOH 标志、块号 0 / ~0 = 0xFF、CRC-16。

(2)解析数据域:提取文件名(ASCIZ)与文件大小(十进制ASCII)。文件大小是后续写入Flash 的关键依据。

(3)根据文件大小擦除目标 Flash 扇区,准备接收数据。

(4)回复 ACK,并再次发送 “C”,通知上位机开始发送数据块。

6.4数据块传输

(1)Bootloader 进入“等块号 1”状态。

(2)收到一帧后依次检查:帧头(SOH/STX)、块号是否等于预期值、~块号、CRC-16。

(3)全部通过:将数据写入 Flash(按声明的文件大小截断),预期块号加 1(回绕),回复 ACK。

(4)CRC 错误:不写 Flash,回复 NAK,请求重发同一号块。

(5)块号重复(例如 ACK 丢失导致发送方重发):不写 Flash,直接回复 ACK,不推进预期块号。

6.5结束阶段

(1)收到 EOT:回复 NAK,等待第二次 EOT。

(2)再次收到 EOT:回复 ACK,表示文件接收完成。

(3)(可选)继续发送 “C” 等待下一文件;若收到全 0 的第 0 块,则回复 ACK 后结束会话。

(4)Bootloader 对刚写入的固件做完整性校验(例如 CRC 或 SHA),通过后设置启动标志并跳转应用入口。

7错误处理与重传机制

异常情况

接收方动作

发送方动作

CRC 校验失败

不写 Flash,回复 NAK

重发当前号块

块号不匹配(非预期块)

丢弃数据,回复 ACK

收到下一 ACK 后推进

ACK 丢失

已回复 ACK 但发送方未收到

超时后重发当前号块;接收方识别为重复块并回 ACK

EOT 丢失

未收到 EOT,持续等待

超时后重发 EOT

连续 NAK 超过上限(如   10 次)

放弃传输,回复 CAN 两次

收到双 CAN 后终止

接收方等待超时(如 3 min 无数据)

自动跳转应用或进入空闲

—

用户主动取消

连发两次 CAN

收到双 CAN 后终止传输

表 5错误处理与重传策略

CAN 必须连发两次(0x18 0x18)才被视为有效取消命令,这是为了避免链路上偶然出现的单个 0x18 字节被误判为取消。

8Bootloader 状态机设计

Bootloader 侧的 YMODEM 接收逻辑可建模为以下有限状态机,各状态与转移条件清晰,便于在 MCU 上实现:

状态

进入条件

主要动作

退出转移

WAIT_C

进入升级模式

循环发“C”,超时计数

收到第 0 块 ->   WAIT_FILE_ACK

WAIT_FILE_ACK

收到第 0 块

解析文件名/大小,擦 Flash

发 ACK + “C” -> WAIT_DATA

WAIT_DATA

准备好接收数据

收帧、校验、写 Flash、回 ACK/NAK

收到 EOT -> WAIT_EOT2

WAIT_EOT2

第一次收到 EOT

回 NAK

再次收到 EOT -> END

END

第二次 EOT 已回 ACK

校验固件、跳转应用

—

ABORT

任意状态出错超限或双 CAN

恢复串口,跳转应用

—

表 6Bootloader YMODEM 接收状态机

9XMODEM / YMODEM / YMODEM-G 对比

特性

XMODEM

YMODEM

YMODEM-G

数据块长度

128 字节

128 / 1024 字节

1024 字节

校验方式

累加和

CRC-16

CRC-16

启动字符

NAK (0x15)

'C' (0x43)

'C' (0x43)

文件名/大小

无

第 0 块携带

第 0 块携带

停等 ACK

是

是

否(连续发送)

批量文件

不支持

支持

支持

适用场景

低速不可靠链路

通用串口升级

可靠链路(如 USB-CDC)

典型吞吐

~900 B/s @9600

~8 KB/s @115200

接近波特率上限

表 7XMODEM 家族主要协议对比

10嵌入式实现要点

10.1缓冲区设计

(1)必须为 1024 字节长块准备完整接收缓冲区。RAM 紧张的 MCU 可采用 DMA 双缓冲或边收边写 Flash 的流式方案。

(2)帧的 1029 字节必须在一个连续接收窗口内收齐,串口超时(如 1 秒未收到新字节)即视为帧不完整,应丢弃并 NAK。

10.2Flash 写入策略

(1)先按第 0 块声明的文件大小擦除对应扇区,避免边擦边写导致的数据丢失。

(2)每收到一个正确数据块,立即写入 Flash 当前偏移地址,并推进写指针。

(3)最后一块按文件大小截断写入,0x1A 填充字节不得写入 Flash。

10.3超时与看门狗

(1)Bootloader 进入升级模式后,应设置整体超时(例如 3 分钟),超时未完成则自动跳转应用,避免设备变砖。

(2)长时间写 Flash 或等待 ACK 期间需喂狗,否则看门狗复位会导致升级中断。

10.4健壮性建议

(1)串口接收使用环形缓冲区 + 中断,避免轮询丢字节。

(2)对块号、补码、CRC 做三重校验,任何一项失败都按帧错误处理。

(3)升级完成后必须对固件区做整体 CRC 校验,校验失败则保留旧固件并跳转应用。

(4)建议在 Bootloader 中预留“升级失败回滚”机制:双备份 Flash 或启动标志位。

11上位机调试要点

(1)Tera Term:菜单“File → Transfer → YMODEM → Send...”,选择固件文件即可;串口设置为 8N1,波特率与 Bootloader 一致。

(2)命令行 sz/rz:在 Linux/minicom 下使用 `rz -b`(二进制模式)发送文件,接收端会自动发起 YMODEM 握手。

(3)调试时建议先用 115200 波特率调通流程,再根据可靠性提升到 460800 或 921600。

(4)若出现“发完第 0 块后无响应”,通常是 Bootloader 未正确解析文件名/大小或 Flash 擦除失败;可用串口示波器或逻辑分析仪抓取字节流定位。

(5)若出现“一直重发同一块”,优先检查 CRC-16 多项式与初始值是否正确(Bootloader 与上位机必须一致:多项式 0x1021,初始值 0x0000)。

12附录:典型字节流示例

以下为一次升级的关键字节流(HEX),供对照实现:

Bootloader -> Host:43; "C" 请求 CRCHost -> Boot:01 00 FF 61 70 70 2E 62 69 6E 00 ...; SOH Blk0Boot -> Host:06; ACKBoot -> Host:43; "C"Host -> Boot:02 01 FE <data[1024]> CRC_H CRC_L; STX Blk1Boot -> Host:06; ACK...Host -> Boot:02 NN ~NN <data> CRC_H CRC_LBoot -> Host:06Host -> Boot:04; EOTBoot -> Host:15; NAKHost -> Boot:04; EOTBoot -> Host:06; ACKBoot -> Host:43; "C" (等下一文件)Host -> Boot:01 00 FF 00 ...; SOH Blk0 全 0 (批结束)Boot -> Host:06; ACK

回首页,搜索你想要的文档

在首页搜索框输入关键词,快速定位资料

文库首页搜索指引 立即搜索

相关学习资料