返回学习路径

learn

动手:用 tc-taprio 配一张最小 GCL 并验证

在 Linux 上用软件模式 tc-taprio 真正下发一张两窗口的 Gate Control List,并用 tc 计数和抓包验证它确实按时间开关。

第五章:时间感知调度动手实践IEEE 802.1QbvTAS22 分钟

first read

先抓住结论

在 Linux 上用软件模式 tc-taprio 真正下发一张两窗口的 Gate Control List,并用 tc 计数和抓包验证它确实按时间开关。

这节怎么读

先看学习目标和章节目录,再进入正文;后续核心概念会在这里直接暴露参数。

本节学习目标

  • 能在一块普通网卡上用软件模式 tc-taprio 下发一张最小 GCL。
  • 能用 tc qdisc show 和计数器确认调度已生效。
  • 知道软件模式、txtime-assist 和硬件 offload 的适用边界。

建议先读

核心概念

tc-tapriosoftware scheduleCLOCK_TAIgate control list

本章目录

  1. 01GCL、cycle 与窗口:Qbv 的最小心智模型从 Gate Control List 的周期、base time、窗口和队列状态理解 Time-Aware Shaper。
  2. 02guard band 与路径接力:Qbv 真正难在端到端理解普通大帧跨窗、窗口余量、路径传播延迟和多跳接力如何影响 Qbv 可行性。
  3. 03base time 与 offset:窗口从什么时候开始才算对理解 Qbv 调度表里的 base time、cycle offset 和多设备窗口相位,避免每台设备都正确却端到端错位。
  4. 04调度可行性:标准定义机制,不替你求解排表理解 Qbv 真正困难的是多流、多跳、多约束下的可行排表,标准机制本身不会自动产生日程。
  5. 05流量模型与 flow set:排表前先把输入说清楚理解 Qbv 排表需要准确的周期、帧长、deadline、路径和优先级输入,flow set 描述不清会让调度结论失效。
  6. 06运行时更新与切换:新旧 GCL 混用会怎样出错理解 Qbv 配置变更时的 base time、版本一致性和回滚问题,避免多设备更新过程中出现短暂窗口错位。
  7. 07Qbv 调试信号:迟到时先看哪几类证据把 Qbv 失败拆成时间同步、队列映射、窗口相位、guard band、流量模型和设备执行几类证据,形成调试路径。
  8. 08Qbv 概念落地:交换机界面、tc-taprio 与标准对象对照把 cycle time、base time、GCL、guard band、queueMaxSDU 对到真实 TSN 交换机配置字段和 Linux tc-taprio 命令,跨过“学完看不懂配置界面”的最后一公里。
  9. 09动手:用 tc-taprio 配一张最小 GCL 并验证在 Linux 上用软件模式 tc-taprio 真正下发一张两窗口的 Gate Control List,并用 tc 计数和抓包验证它确实按时间开关。

解决什么问题

上一节你能读懂别人的 Qbv 配置了。这一节让你亲手下发一张,并验证它真的按时间开关门。不需要专门的 TSN 交换机,也不需要带硬件 offload 的网卡——`tc-taprio` 有纯软件模式,一块普通网卡(甚至一对 veth)就能建立第一手直觉。

准备:一个能用的 CLOCK_TAI

软件模式 taprio 的内部定时器默认用 `CLOCK_TAI`。在真实部署里,`CLOCK_TAI` 应由 gPTP 喂(见第三章):

# 真实部署:用 802.1AS 把网卡硬件时钟(PHC)同步到 grandmaster
sudo ptp4l -i eth0 -f /etc/linuxptp/gPTP.cfg --step_threshold=1 &
# 再把 PHC 喂给系统 CLOCK_TAI
sudo phc2sys -s eth0 -O 0 -m &

学习阶段只想看 taprio 的行为,可以先不接 PTP——但要记住:没有同步的 `CLOCK_TAI`,`base-time` 这个绝对时刻只在本机有意义,不能跨设备对齐。这正是“为什么 Qbv 依赖 802.1AS”的现场版。

第一步:规划一张最小 GCL

目标:cycle = 1ms,前 300us 只放关键流量(TC6),后 700us 放其余流量。

窗口时长开放的 TCgate mask
关键窗300us只有 TC6`40`(`0100 0000`)
普通窗700usTC0–TC5 + TC7`bf`(`1011 1111`)

cycle = 300000 + 700000 = 1,000,000 ns = 1ms。两段相加自洽(回顾上一节的“cycle 自洽”检查)。

第二步:下发(软件模式)

sudo tc qdisc replace dev eth0 parent root handle 100 taprio \
    num_tc 8 \
    map 0 1 2 3 4 5 6 7 \
    queues 1@0 1@1 1@2 1@3 1@4 1@5 1@6 1@7 \
    base-time 0 \
    sched-entry S 40 300000 \
    sched-entry S bf 700000 \
    clockid CLOCK_TAI

`base-time 0` 是一个过去时刻,taprio 会自动加上整数倍 cycle,对齐到下一个 1ms 边界再启动——所以不必费心算一个“未来”时刻。`clockid CLOCK_TAI` 在软件模式必须写(硬件 offload 才省略)。

第三步:验证它真的生效

下发成功不等于按预期工作。至少做三层验证:

# 1) 表结构对不对:能看到 taprio、cycle-time 与两条 sched-entry
tc qdisc show dev eth0

2) 计数对不对:持续打流时,看每个 TC 的发送计数变化 tc -s qdisc show dev eth0

3) 时序对不对:在对端抓包,确认关键帧只在关键窗口附近出现 sudo tcpdump -ni eth0 --time-stamp-precision=nano -ttt ```

要让帧落到 TC6,发送端要给 socket 设 `SO_PRIORITY`(优先级经 `map` 映射到 TC6)。一个简单做法:

# 让 ping 走优先级 6(再由 map 落到 TC6)
sudo ping -Q 0xC0 <对端IP>      # 0xC0 的 PCP 位对应优先级 6
# 或用支持 --tos/SO_PRIORITY 的压测工具打 TC6 与 TC0 两路流对比

判断标准:关键流(TC6)的抓包时间戳应集中在每个 1ms 周期的前 300us;普通流(TC0)应只在后 700us 出现。只有计数上升不够——它只证明“发出去了”,不证明“准时”;时序证据要靠抓包时间戳。

软件模式 → txtime-assist → 硬件 offload

软件模式适合建立直觉,但精度受内核调度影响。要拿微秒级窗口的真实数据,得换模式:

模式flags精度适用场景
软件(无)受内核调度影响,常有几十 us 抖动学习、功能验证
txtime-assist`0x1`配合 `etf` qdisc 在发送侧排序,较好部分支持 LaunchTime 的网卡
硬件 offload`0x2`网卡硬件循环执行 GCL,最准TSN 网卡 / 交换机(如 SW0)

换到硬件 offload,命令主体不变,去掉 `clockid`、加 `flags 0x2`,并要求网卡支持:

sudo tc qdisc replace dev eth0 parent root handle 100 taprio \
    num_tc 8 map 0 1 2 3 4 5 6 7 queues 1@0 1@1 1@2 1@3 1@4 1@5 1@6 1@7 \
    base-time 0 sched-entry S 40 300000 sched-entry S bf 700000 \
    flags 0x2

到了真实 SW0 这类交换机,你不再敲 `tc`,而是在它的 Qbv 配置页填同样的语义(门控循环时间、循环开始基准时间、GCL 门控列表)——但前提一致:时钟先由 802.1AS 同步好,offload 由硬件执行。

常见报错与排查

  • `Specified qdisc kind is unknown`:内核或 iproute2 太老,缺 taprio 支持,先升级。
  • gate mask 被当十进制 / 报越界:用十六进制,回看上一节的 gate mask 表。
  • `base-time` 给了很久远的过去 + 很大 cycle:对齐计算慢、不直观,给 `0` 或近未来时刻更好。
  • `flags 0x2` 还写了 `clockid`:冲突,硬件 offload 必须省略 `clockid`。
  • 清除配置重来:`sudo tc qdisc del dev eth0 parent root`。

带来了什么新问题

软件模式能让你跑通流程、建立直觉,但它的精度不代表硬件现场。内核调度会给发包时刻带来几十微秒级抖动,所以软件模式适合验证“表对不对、门开没开”,不适合用来证明微秒级窗口的最坏情况。

把同一张表搬到真实部署,还有三件事要补:接上 802.1AS 让 `CLOCK_TAI` 跨设备对齐、选择硬件 offload 拿到稳定精度、为多跳路径重新计算窗口相位和误差预算。换句话说,本地单机验证过的 GCL,到了多设备路径上不能直接照搬——这正好接回前面“base time 与 offset”和“误差预算”两节。

检查点

  • 把关键窗口从 300us 改成 200us、cycle 仍保持 1ms,命令要怎么改?
  • 只看 `tc -s qdisc show` 的计数在上升,能不能证明关键帧“准时”?还缺什么证据?
  • 要在真实 SW0 交换机上落地同一张表,相比软件模式要先满足哪些前提(时钟、offload)?

掌握检查

读完本节后,先用下面这些问题校准自己,而不是只确认“看过了”。

  1. 1能独立写出并下发一张 cycle=1ms、含一个关键窗口的 taprio 配置。
  2. 2能解释验证时为什么要同时看 tc 计数和抓包时间戳。

next steps

读完这一页,下一步可以这样走。