4. USB中断传输原理

4.1 中断传输的定义与特性

USB中断传输(Interrupt Transfer)是一种保证轮询延迟的传输类型,适用于小数据量、周期性、低延迟的通信场景。在电池供电设备中,中断传输是传感器数据上报、按键状态变化、HID设备报告等交互的核心承载方式。

特性 描述
传输方向 单向(IN 或 OUT),由端点描述符固定
数据载荷 全速 ≤ 64 字节,高速 ≤ 1024 字节,超高速 ≤ 1024 字节
延迟保证 主机保证在 bInterval 指定的时间间隔内至少轮询一次
错误重试 数据错误时自动重试,直到成功或超时
带宽预留 全速/高速下,中断传输可预留最多 90% 的帧/微帧带宽
典型应用 鼠标、键盘、游戏手柄、传感器数据流、中断事件通知
低功耗设计要点: 中断传输的轮询间隔 bInterval 直接影响设备唤醒频率。在电池供电设备中,应尽量将 bInterval 设置为满足功能需求的最大值(如 8ms 或 16ms),以减少主机轮询次数,降低设备平均功耗。

4.2 中断端点类型与描述符

中断端点使用 端点描述符(Endpoint Descriptor) 中的 bmAttributes 字段标识传输类型为中断传输。主机在枚举阶段读取端点描述符,获取轮询间隔、最大包长等信息。

// USB 端点描述符结构(中断端点示例)
typedef struct {
    uint8_t  bLength;          // 描述符长度:7
    uint8_t  bDescriptorType;  // 描述符类型:0x05(端点)
    uint8_t  bEndpointAddress; // 端点地址:0x81(IN端点1)
    uint8_t  bmAttributes;     // 属性:0x03(中断传输)
    uint16_t wMaxPacketSize;   // 最大包长:0x0040(64字节)
    uint8_t  bInterval;        // 轮询间隔:0x0A(10ms)
} __attribute__((packed)) usb_endpoint_descriptor_t;
字段 值示例 说明
bEndpointAddress 0x81 Bit7=1(IN方向),Bit3-0=1(端点1)
bmAttributes 0x03 Bit1-0=11(中断传输)
wMaxPacketSize 0x0040 全速下最大64字节
bInterval 0x0A 轮询间隔10ms(全速单位:ms)
端点类型对比: 中断端点与批量端点最大的区别在于延迟保证。批量端点没有固定轮询周期,而中断端点由主机在每帧/微帧中按 bInterval 调度,保证最坏情况延迟。

4.3 中断传输的事务格式

每个中断传输事务由三个阶段组成:令牌包(Token Packet) → 数据包(Data Packet) → 握手包(Handshake Packet)。对于 IN 方向中断传输,事务流程如下:

  1. 主机发送 IN 令牌包:包含端点地址和设备地址,通知设备准备发送数据。
  2. 设备返回数据包:设备在收到 IN 令牌后,在指定时间内返回 DATA0/DATA1 数据包。
  3. 主机发送握手包:主机正确接收数据后,返回 ACK 握手包;如果数据错误,返回 NAK 或 STALL。
中断传输事务格式(IN方向) 主机 设备 阶段1:令牌包 IN (端点地址) 阶段2:数据包 DATA0/DATA1 阶段3:握手包 ACK / NAK / STALL 说明:主机发起IN令牌 → 设备返回数据 → 主机确认握手,完成一次中断传输事务

4.4 令牌包详解

令牌包由主机发送,标识事务的类型和方向。中断传输使用 IN 令牌(主机读取设备数据)或 OUT 令牌(主机发送数据给设备)。令牌包格式固定为 4 字节:

字段 长度 说明
PID 1 字节 包标识符:IN=0x69, OUT=0xE1, SETUP=0x2D
ADDR 7 位 设备地址(0~127)
ENDP 4 位 端点号(0~15)
CRC5 5 位 对 ADDR+ENDP 的校验
常见错误: 在电池供电设备中,如果设备在收到 IN 令牌后没有数据可发送,应返回 NAK 握手包,而不是 STALL。STALL 表示端点发生不可恢复错误,会导致主机停止轮询该端点,影响后续通信。

4.5 数据包详解

数据包携带实际传输的数据负载。中断传输使用 DATA0 和 DATA1 两种数据包 PID 进行交替切换,实现数据同步和错误检测。

  • DATA0 PID:0xC3,事务开始时使用
  • DATA1 PID:0x4B,与 DATA0 交替使用
  • 数据字段:0~1024 字节(取决于速度)
  • CRC16:对数据字段进行 16 位循环冗余校验

数据包切换规则:每个成功完成的事务(收到 ACK)后,数据包 PID 翻转。如果事务失败(收到 NAK 或超时),PID 不翻转,主机重试时使用相同 PID。

数据包PID切换机制 主机 设备 事务1:DATA0 → ACK 事务2:DATA1 → ACK 事务3:DATA0 → NAK(重试)

4.6 握手包详解

握手包是事务的最后一个阶段,用于报告传输状态。握手包仅包含 1 字节 PID,无数据字段和 CRC。

握手包类型 PID 值 含义 发送方
ACK 0xD2 数据正确接收,事务成功完成 主机(IN)或设备(OUT)
NAK 0x5A 设备暂时无法发送/接收数据,请重试 设备
STALL 0x1E 端点发生错误,无法继续通信 设备
NYET 0x96 设备尚未准备好(高速/超高速专用) 设备
低功耗优化策略: 在电池供电设备中,频繁返回 NAK 会增加总线活动和功耗。建议在设备没有数据时,让 USB 控制器进入 挂起状态 或 选择性挂起,而不是持续返回 NAK。当有数据需要上报时,通过远程唤醒信号通知主机恢复通信。

4.7 中断传输在电池供电设备中的调度

主机在每帧(全速 1ms)或每微帧(高速 125μs)中,按照端点描述符中的 bInterval 值调度中断传输。调度算法遵循以下规则:

  • 全速设备:bInterval 取值范围 1~255,单位 ms。主机每 bInterval ms 轮询一次。
  • 高速设备:bInterval 取值范围 1~16,实际轮询间隔为 2^(bInterval-1) × 125μs。
  • 超高速设备:bInterval 取值范围 1~16,实际轮询间隔为 2^(bInterval-1) × 125μs,支持服务间隔的微调。
中断传输轮询调度示例(全速,bInterval=4ms) 时间 帧0 帧1 帧2 帧3 帧4 轮询 轮询 轮询 唤醒 唤醒 唤醒 说明:主机每4ms轮询一次中断端点。设备在轮询间隔内可进入低功耗模式,仅在轮询前唤醒准备数据 优化策略:将bInterval从1ms增大到4ms,设备唤醒频率降低75%,显著延长电池续航

4.8 中断传输与低功耗设计的结合

在电池供电设备中,中断传输的优化需要从以下三个层面入手:

优化层面 具体措施 功耗收益
轮询间隔 增大 bInterval 到满足延迟要求的最大值 减少主机轮询次数,降低设备唤醒频率
数据聚合 将多次采样数据合并为一次中断传输上报 减少事务次数,降低总线活动功耗
选择性挂起 无数据时进入 USB 挂起状态,通过远程唤醒恢复 挂起电流可降至微安级
NAK 管理 避免频繁返回 NAK,使用挂起代替 减少总线握手开销
实践建议: 对于电池供电的传感器节点,推荐将 bInterval 设置为 8ms~16ms,并在设备固件中实现 事件驱动上报 机制:仅在数据变化或达到阈值时唤醒并响应轮询,否则保持挂起状态。这样可以在不丢失数据的前提下,将平均功耗降低 60%~80%。