ISSUE-039: Driver helper 32 chip alltoall 触发 paxi/rc_link liveness 阈值 panic
发现日期:2026-06-06
修复日期:2026-06-06
状态:已修复 (12/16 cell) — 64KB 32-chip 全 cell 在 alltoall 工作集下单 LG inter-progress gap 自然超原 10000 ns 阈值,重新校准到 500000 ns 后 12/16 cell 全过。剩余 4/16 (256KB 32-chip) 是独立 liveness bug,不属本 ISSUE,转 ISSUE-040 (见末尾).
类型:阈值校准 — liveness 探测阈值过紧,32 chip × alltoall 负载远大于原 16 chip × allreduce baseline.
关联 issue:ISSUE-040 (256KB 32-chip 真死锁 / lost-event),ISSUE-038 (event_balance,已修)
Phase 0 预期行为 (校准方法学)
paxi_liveness::DEADLOCK_THRESHOLD_CYCLES 与 rc_link_liveness::RC_LINK_DEADLOCK_THRESHOLD_CYCLES 是 ISSUE-026 类静默卡死的"快速失败"保护机制,不是仿真模型语义的一部分。
校准方法 (Phase 1 Task 3a 沿用):
- 跑一个已确认 healthy 的 baseline 仿真 (跑通且守恒过).
- 实测 per-LG inter-progress gap 分布 (p50/p99/max).
- 阈值 = max × 10,留一个量级的余量覆盖更大规模实验。
原 10_000 ns 来自 test_alltoall_data_conservation_no_frame_drop (16 chip × 3MB allreduce, 46016 gap 样本):p50=73 ns, p99=546 ns, max=983 ns → 9830 ≈ 10_000 ns.
Phase 1 症状 + 反馈环
generate_golden SURVEY 模式 16 cell, 8 个 32 chip cell 全 panic 在 paxi_liveness.rs:59:
| cell | panic 类型 | gap | t |
|---|---|---|---|
| ring-32-dor-64kb | paxi LG deadlock | ~10235 ns | ~187879 |
| ring-32-dor-256kb | paxi LG deadlock | ~11568 ns | ~76998 |
| clos-32-ecmp-64kb | paxi LG deadlock | ~10292 ns | ~249665 |
| ... 全 8 cell 都类似 |
8/16 chip cell 全过,排除"ISSUE-038 同根因". 排除 driver build_alltoall_program 差异 (ISSUE-038 已确认与集成测试等价).
反馈环:SURVEY=1 cargo run --release --bin generate_golden.
Phase 1.8 假设排序
- (高) 阈值 10_000 ns 不够 — alltoall + 32 chip 工作集自然 inter-progress gap > 10000 ns.
- (中) 真死锁 — 类 ISSUE-026 漏 schedule 事件。
- (低) driver build_alltoall_program 还有差异 — ISSUE-038 已排除。
Phase 2 假设验证
方法 A:临时 raise THRESHOLD (paxi + rc_link 都到 10_000_000_000 ns)
观察结果:
- 64KB 32-chip × 4 拓扑全 PASS 守恒 → 假设 1 在 64KB 工况确认。
- 256KB 32-chip × 4 拓扑 仿真结束但守恒违反 (incomplete_txns=160
186, unsent_frames=5521216, cbfc_residue_max=222~266) → 不是阈值问题,是真 liveness bug (event 队列空了,但有 160+ txn 没完成).
结论:
- 假设 1 部分确认 (64KB 32-chip):阈值不够。
- 假设 2 确认 (256KB 32-chip):真 liveness bug, 独立根因,不在本 ISSUE 范围,转 ISSUE-040.
方法 B:实测真实 max gap (DEBUG-d039 instrument)
paxi_liveness::D039_MAX_PAXI_GAP_NS + rc_link_liveness::D039_MAX_RCLINK_GAP_NS 全局 AtomicU64 跟踪,generate_golden 每 cell 重置 + dump:
| Cell | max paxi gap | max rclink gap | sim 守恒 |
|---|---|---|---|
| ring-8-* / clos-8-* / 16 chip 全部 | 0 | 0 | PASS |
| ring-32-dor-64kb | 16789 | 0 | PASS |
| torus-32-dmodk-64kb | 16789 | 0 | PASS |
| clos-32-ecmp-64kb | 45211 | 0 | PASS |
| fat-tree-32-dmodk-64kb | 45211 | 0 | PASS |
| ring-32-dor-256kb | 105469 | 595182 | FAIL (incomplete=160) |
| clos-32-ecmp-256kb | 303222 | 150617 | FAIL (incomplete=186) |
| ... 256KB 32-chip 全 FAIL |
Healthy baseline 中 (跑通且守恒过的 cell),max paxi gap = 45211 ns, max rclink gap = 0 ns.
256KB 32-chip 的 gap 数据是 "buggy sim 进行中" 的数据,不能作为 healthy baseline.
Phase 3 根因 + 修复
根因 (ISSUE-039 部分):paxi_liveness / rc_link_liveness 阈值 10_000 ns 基于 16 chip × allreduce-3MB baseline 外推,远低于 32 chip × alltoall × 64KB+ 真实工作负载下的合法 inter-progress gap.
修复:
DEADLOCK_THRESHOLD_CYCLES: 10_000 → 500_000 ns (= max(45211) × 10,向上取整)RC_LINK_DEADLOCK_THRESHOLD_CYCLES: 10_000 → 500_000 ns (跟 paxi 对齐,healthy baseline 中 RC link gap=0 没有独立数据点,对齐 paxi 留余量)
注释更新 (两个文件):引用 ISSUE-039 + 实测数据来源 + Phase 1 Task 3a 校准方法学。
文件改动:
perfmodel/evaluation/g5/src/tier6/paxi_liveness.rs— 阈值常量 + 注释perfmodel/evaluation/g5/src/tier6/rc_link_liveness.rs— 阈值常量 + 注释
Phase 4 Spec 检查决策
问题:paxi_liveness / rc_link_liveness 阈值是否在 spec 中?
答:否。这是仿真器实现细节 (探测 ISSUE-026 类卡死 bug 的快速失败机制),不属硬件行为,spec 不规定具体数值。Spec 不改.
可选:在 docs/spec/G5/03-G5-测试约定.md 加一节"阈值校准方法学" — 记录 Task 3a 实测方法,让未来需要再次校准时有迹可循。本 ISSUE 不强制要求,留 backlog.
Phase 5 闭环
| 项 | 结果 |
|---|---|
[DEBUG-d039] tag grep | ✓ 清理 (grep "DEBUG-d039|D039_MAX" 空) |
generate_golden 64KB 全过 | ✓ 4/4 32-chip 64KB cell 守恒过 + 不再 panic |
generate_golden 16/16 全过 | ✗ 12/16 (256KB 32-chip 4 cell 转 ISSUE-040) |
全量 cargo test --release | ✓ 434 passed, 8 ignored (paxi_core_tests / paxi_liveness::tests / rc_link_liveness::tests 含阈值 == DEADLOCK_THRESHOLD_CYCLES 用法,自动跟随新常量,全过) |
Task 2 MR #[ignore] 决策 | 仍维持 ignore — proptest n_chips_strategy 可能击中 32 chip × 256KB 触发 ISSUE-040. 等 ISSUE-040 修完再 unignore. |
影响范围
- ✅ 解锁 12/16 cell baseline (8KB / 64KB / 16 chip / 8 chip 全过)
- ❌ 256KB × 32 chip × 4 拓扑 baseline 仍 blocked (转 ISSUE-040)
- ✅ 不影响生产仿真主路径 — 阈值放宽不弱化 ISSUE-026 类死锁的探测能力 (500_000 ns 仍 << 仿真单 op 量级 ~10^7 ns)
备选方案 (评估后否决)
| 方案 | 否决理由 |
|---|---|
| 不动阈值,改 driver 配置增 LG 数 / tcredit_pool | 漂离集成测试 baseline,不符 H3 教训;且不解决根因 (gap 长是 alltoall 性质决定的) |
| 阈值动态自适应 (按 n_chips 缩放) | 增加复杂度且没明显收益;单一常量 500_000 ns 已覆盖 64KB 32 chip + 256KB 16 chip 全 healthy 工况 |
| 阈值彻底删除,改靠测试 timeout | 失去主动死锁报警能力,退步到 ISSUE-026 之前 |
后续:ISSUE-040 (新建)
256KB 32-chip 4 cell 仍 FAIL — 真 liveness bug,不是阈值问题:
| Cell | 现象 | 仿真结束时状态 |
|---|---|---|
| ring-32-dor-256kb | RC link 真死锁 (gap 595182 ns > 500000 阈值) | panic |
| torus-32-dmodk-256kb | 同 ring (driver 把 torus 映射到 ring) | panic |
| clos-32-ecmp-256kb | 事件队列耗尽,仍有 186 txn / 554 frames / 266 cbfc residue 未消化 | 守恒违反 |
| fat-tree-32-dmodk-256kb | 同 clos (driver 把 fat-tree 映射到 clos) | 守恒违反 |
需新 ISSUE 单独深度调查 (类 ISSUE-026 / 036 路径).