1. EP 解决的不是“少算”,而是“专家放在哪里”
稀疏 MoE 层通常把 1 个 dense FFN 替换为大量专家网络和 1 个 router。给定 token hidden state,router 选出少量专家并给出门控权重;这降低了单个 token 的激活计算量,但模型的专家参数仍要存放在某些 GPU 上。Expert Parallelism,简称 EP,把专家 owner 分散到多个 rank,让任意 token 有机会访问整个专家池。
因此 EP 与数据并行不同。DP 复制模型、把请求分开;EP 把不同专家分片、把同一批中的 token 按路由结果交换。token 的目的地每一层都可能变化,而且不同请求、不同位置的 token 分布并不均匀。EP 的性能上限由最慢 owner rank 决定,而不是由平均 token 数决定。
2. 从 router 到专家:先建立正确的数学对象
设 batch 中有 \(N\) 个 token、专家数 \(E\)、top-k 为 \(k\)。router 产生 logits \(z \in \mathbb{R}^{N \times E}\),对每个 token 选择索引集合 \(I_t\) 与权重 \(g_{t,e}\)。输出是被选专家输出的加权和,常附加共享专家或残差支路。这里的稀疏性发生在 token 到专家的连接图,而不是在专家内部的矩阵乘法上。
critical work is controlled by \(\max_e(n_e)\), not \(\operatorname{mean}_e(n_e)\)。
路由器的 top-k 是模型语义的一部分。运行时可以重新排列 token、压缩元数据、异步发送,但不能为了均衡网络负载把 token 改送给另一个专家。负载均衡需由训练时的辅助损失、router 策略或模型规定的冗余路径来完成,不能由 serving scheduler 在无语义保证的情况下擅自完成。
3. Dispatch 与 combine:2 次 all-to-all 的含义
每个 source rank 先按目标 expert owner 对 token 编桶,形成可变长度消息。dispatch all-to-all 将 token hidden state、路由权重或必要的索引发到 owner rank;owner 将各专家的 token 排成适合 grouped GEMM 的布局,算完后再通过 combine all-to-all 把结果送回 source rank。source 依据原始 token 顺序和 gate 进行加权聚合。
all-to-all 的发送计数、接收计数、偏移和排序需要动态生成,与固定大小 all-reduce 的执行形态不同。若计数在 host 上同步,控制路径会吃掉 decode 的预算;若布局不连续,PCIe/NVLink/RDMA 传输和 GEMM 都难以满速。因此高性能实现会尽量把 metadata、token packing、传输和执行留在 GPU 异步路径上。
4. 容量因子与负载不均衡决定长尾
router 可能把大量 token 送向少数专家。训练常使用容量因子限制单 expert 每轮可接收的 token 数;过量 token 可以被丢弃、走备用路径或按模型规则处理。服务侧若假设均匀分布,只按 \(Nk/E\) 预留 buffer,真实热点就会溢出、触发临时分配或让 1 个 rank 成为整个层的 straggler。
应同时观察 expert 粒度与 rank 粒度。多个热点专家若恰好同属 1 个 rank,rank 失衡会比 expert histogram 看起来更严重;反之,专家不均匀但 owner 映射合理时仍可能可接受。prefill 的大量 token 与 decode 的小量 token 也会出现不同模式,不能只在 1 种 batch shape 上调优。
5. DeepEP 的接口思想:把通信当作可调度的算子
DeepEP 提供面向 MoE 的 dispatch/combine 通信,并区分不同拓扑和运行模式。runtime 设计者需要先理解接口边界:输入是 token 布局与路由信息,输出是 owner-local 的可计算布局。通信完成事件和 buffer 生命周期也要明确,才能与 CUDA stream 和专家 GEMM 拼成正确的依赖图。单个版本的 benchmark 不能替代这些接口语义。
1 个通信库若只提供“阻塞地把数据发完”,上层几乎无法隐藏延迟。若它暴露异步 handle、可复用 buffer、可预测的 layout 和完成信号,runtime 才能把下一批的 pack、当前批的传输、上一批的 GEMM 同时推进。性能数字会随 GPU、NIC、SM 配额、消息形状和 commit 改变,因此任何比较都应记录官方版本与命令行。
6. Token layout 是通信与算子的共同契约
专家 GEMM 希望同一专家的 token 连续,以形成较大的矩阵块;网络希望按 destination rank 连续,以形成较少的大消息;原始模型则希望输出回到 token 顺序。1 个好的 layout 通常至少维护 3 组映射:原 token 到发送位置、发送位置到 expert-local 位置、返回位置到原 token。遗漏任一映射都可能造成静默的 token 混淆,而不是显式报错。
量化和多精度会让契约更复杂。FP8 dispatch、BF16 combine 或带 scale 的 payload,都要保证 scale 和数据共享同一索引语义,对齐也不能把无关 token 混进同一块。调试可从小 batch、固定 route 和可打印 token id 开始,确认 round-trip identity 后再接入专家 GEMM。数学正确后才有必要追性能。
7. 通信计算重叠的条件,不是多开 1 条 stream
设一批 token 被切成若干 chunk。理想流水是:chunk 0 dispatch 后立即计算专家;同时 chunk 1 仍在网络上,chunk -1 的 combine 可与后续计算并行。可是重叠只有在 3 个条件同时成立时才有效:chunk 足够细以产生并发,chunk 又不能细到每次传输只剩启动开销;GPU 有足够 SM/复制引擎资源;数据依赖与 buffer 回收不会在某个 barrier 汇合。
而非 \(\sum_{\mathrm{chunks}} \left(T_{\mathrm{dispatch}} + T_{\mathrm{expert}} + T_{\mathrm{combine}}\right)\)。
如果 dispatch 和 grouped GEMM 都需要大量 SM,强行并发会互相降速,最终端到端更慢。若 NIC 与 GPU 的拓扑绕远,网络传输也可能抢占 HBM/NVLink 路径。正确做法是从 trace 中观察重叠区间和资源占用,扫描 chunk size、通信 SM 配额、GEMM tile,而不是只凭“理论可并行”启用重叠。
8. EP 的拓扑要求:对称性、NIC 映射和故障域
EP all-to-all 比 TP all-reduce 更容易暴露网络非对称。1 个 rank 到另一个 rank 的路径、GPU 到 NIC 的亲和性、跨 node 是否经过拥塞域,都会改变最慢消息。把所有专家均匀编号然后随意放到 GPU 上,可能让某些 owner 的高频目的地穿越更弱链路;把热专家与冷专家混排,则有机会降低最大链路负载,但必须在真实 router trace 上验证。
部署清单应包括:每个 global rank 对应的 GPU、NUMA、NIC、NVLink clique、EP group;每个方向的有效带宽与 P99;遭遇单卡或单 NIC 故障时哪些 EP group 整体不可服务。故障边界要按执行 mesh 定义,不能只按“1 个 GPU pod”口头描述。更完整的硬件视角见 Mainline 通信与拓扑。
9. 在线 serving 如何把 EP 纳入调度器
调度器至少知道全局 token budget、KV 可用块和请求 deadline;对于 EP,还应收集每轮 router 输出或其可用预测,记录各 rank 的接收 token 数、dispatch/combine 字节数、等待时间和专家 GEMM 时长。注意这些信息用于排队和容量选择,而不是篡改 route。1 个长 prompt 可能在 prefill 时压垮 EP,而 decode 阶段很平稳,因而需要分别设 P/D 的 token 上限。
有前缀缓存时,路由层面的局部性并不等价于 KV 局部性。把请求迁到空闲 replica 能改善队列,却可能失去已有 KV 或需要昂贵迁移;固守 cache-local replica 又会扩大专家热点。该冲突需要由成本模型权衡,不能用“始终最短队列”或“始终本地命中”这种单条规则处理。
10. 必须采集的 profile,而不是只有 GPU 利用率
- 每层每 EP rank 的 send/recv token 数、字节数和最大/均值比。
- router、pack、dispatch、expert GEMM、combine、unpack 的 P50/P99 时间线。
- 同一 stream 与不同 stream 的依赖边、event wait、空洞与 buffer reuse 次数。
- GPU 到 NIC 的流量方向、链路利用率、重传或拥塞指标,以及对其他 collective 的干扰。
- 按 prefill/decode、短/长上下文、不同 batch size 分桶后的性能与准确度。
- 发生 fallback、容量溢出、临时分配、OOM 或超时的完整请求样本。
这些指标应以 trace id 和运行时版本关联,使 kernel 升级、路由器替换或环境变量变化在后续比较中都有清楚的版本边界。
11. 5 种常见失败模式
12. 从零到生产的实施顺序
- 在单节点、小 batch 下验证 router 索引、token permutation 与 combine 的数值等价性。
- 测量不同 token 数、hidden size、top-k 下的 dispatch/combine 曲线,分别记录单向与双向。
- 将专家 GEMM 接入,确认 layout 连续性、group size 和精度路径没有破坏正确性。
- 增加 stream/chunk 重叠,用 trace 确认临界路径已经缩短,再调整 SM 资源。
- 扩到目标 EP group,验证 GPU-NIC 映射、不同方向、通信竞争和故障边界。
- 最后接入在线 scheduler,以真实到达 trace 扫 SLO goodput,而不是仅做饱和离线 batch。
13. 与 Mainline 的连接
EP 是 Transformer 与 MoE 在分布式系统中的落地形态;它的 token 交换由 GPU 算子 的布局和 stream 决定,又受 并行放置 与 通信拓扑 约束。后续阅读 COMET 时,可把它看作在同一 dispatch/combine 临界路径上进一步挖掘细粒度 overlap 的方案。
14. 一手来源与版本边界
| 来源 | 用途 |
|---|---|
| DeepEP 官方仓库 | 接口、支持平台、benchmark 与版本说明的主入口。 |
| GShard / MoE 系统论文 | 稀疏专家、通信和并行的一手背景资料。 |
| 本档案:COMET 与细粒度 overlap | 本文下一篇独立解释。 |
本页不把某次仓库 benchmark 当作通用吞吐承诺。GPU、通信库、NIC、消息形状和模型 router 的任一变化都可能改变结果。