音乐
暂未播放
DeepEP 完全拆解:DeepSeek 开源通信库如何把 MoE 推理的 dispatch/combine 压到硬件极限
DeepEP(DeepEveryParallel)是 DeepSeek 于 2025 年 2 月 25 日(开源周第二天)开源的通信库,MIT 协议,仓库在 deepseek-ai/DeepEP。它是第一个专门为 MoE(Mixture of Experts)与专家并行(Expert Parallelism, EP)设计的开源通信库,提供高吞吐、低延迟的 all-to-all GPU kernel——也就是 MoE 中的 dispatch(分发)与 combine(合并)两个核心通信算子。要真正理解 DeepSeek 的推理系统为什么快、vLLM 和 SGLang 为什么都接入了这个库,必须先理解 DeepEP。这篇文章从 MoE 通信问题的根源讲起,把两类 kernel 的设计、0-SM 重叠机制、FP8 精度策略、性能数据以及 V2 的重构全部拆开。
背景:MoE 推理中的通信之墙#
专家并行(EP):把专家摊到多张 GPU 上#
先复习一下 MoE 层的推理过程。一个 MoE 层包含一个路由器(router/gating network)和一组专家 FFN。对每个输入 token,路由器计算它对每个专家的评分,选出 top-k 个专家,token 的隐藏状态被送到这些专家里各自过一遍 FFN,最后按路由权重加权求和。用符号表示:设 token 数为 B,专家数为 N,每个 token 选 K 个专家(top-k),隐藏维度为 H。
在单张 GPU 上,所有 N 个专家都在这张卡里,路由只是计算,不需要通信。但模型大到一定程度(比如 DeepSeek-V3 的 256 个专家、671B 参数),一张 GPU 装不下全部专家,就必须把专家分布到多张 GPU 上——这就是专家并行(EP)。EP 下,任意一个 token 的 top-k 专家很可能分布在不同的 GPU 上,token 数据就必须在 GPU 之间搬运。
EP 组里的每张 GPU(一个 rank)要做两件事:
- dispatch(分发):把本 rank 上的 token 按路由结果发送到持有对应专家的远程 rank;
- combine(合并):专家计算完后,把结果按路由权重加权求和,送回 token 原本所在的 rank。
vLLM MoE 实践指南(AMD ROCm 博客的 vLLM MoE Playbook)把整个 MoE 层的数据流画得很清楚:注意力层每个 GPU 各自处理自己的请求,到专家层时通过 AllToAll(dispatch)把 token 重分布到持有专家的 GPU,专家算完后再 AllToAll(combine)送回:

实际部署中 MoE 层还常与张量并行(TP)混合使用:注意力层和 dense 层按 TP 切分(每卡算 1/8,层间 AllReduce 同步),专家层则按 EP 摊到各卡——这样每个 token 的 KV 计算走 TP、专家计算走 EP,两种并行模式的通信模式完全不同(AllReduce 是”大家算一部分、结果汇总”,all-to-all 是”数据按路由重分布”):

通信量有多大:一个公式算出账单#
每层每张卡要搬多少数据?dispatch 阶段,每个 token 要发给 K 个专家,每个专家的输入是隐藏向量 x∈RH。假设每个 rank 上平均有 b 个 token,数据类型占 s 字节(BF16 为 2,FP8 为 1),那么每个 rank 单层需要发出的逻辑数据量约为:
Vdispatch=b×K×H×s字节combine 阶段数据量相同(每个专家输出也是 H 维向量,且要附带路由权重)。以 DeepSeek-V3 生产配置为例:解码阶段每个 rank 约 128 个 token、K=8、H=7168、FP8 分发(s=1):
V=128×8×7168×1=7,340,032 字节≈7.3 MB7.3 MB 看起来不大,但注意这是每一层的通信量,而一个 MoE 大模型有几十上百个 MoE 层,每个 token 每层都要搬一次。更重要的是:这 7.3 MB 必须在极短时间内搬完。如果预算 80 微秒,需要的带宽就是约 95 GB/s——而一张 H800 连的单张 InfiniBand CX7 网卡只有 400 Gb/s(约 50 GB/s)。也就是说,通信几乎是物理上不可能的,除非把架构设计到极致,或者想办法减少真正跨网络的流量。这个矛盾就是 DeepEP 存在的全部理由。
带宽不对称:NVLink 与 RDMA 之间的鸿沟#
MoE 通信横跨两个带宽截然不同的域:
| 通信域 | 典型硬件 | 单向带宽量级 |
|---|---|---|
| 节点内 | NVLink(H800 实测约 160 GB/s) | 10² GB/s |
| 节点间 | InfiniBand RDMA(CX7 400 Gb/s 约 50 GB/s) | 10¹ GB/s |
NVLink 比 RDMA 快 3 倍以上。把数据从 NVLink 域搬到 RDMA 域(或反过来)的速度,由慢的那一端决定——这就像从宽 160 米的路拐进宽 50 米的路,车流不可能超过 50 米路的容量。所以任何好的 MoE 通信设计都必须回答同一个问题:如何让数据在昂贵的 RDMA 链路上少跑,在便宜的 NVLink 链路上多跑?
DeepSeek-V3 的 group-limited gating 让问题更特殊#
DeepSeek-V3 的 MoE 路由(DeepSeek-V3 论文)采用分组受限门控(group-limited gating):256 个专家被分成 128 组,每组 2 个专家;路由器先选 top-4 组,再在这 4 组里选出 top-8 个专家。部署时,同一组的两个专家会被尽量放在同一节点上。这样一来,每个 token 的 8 个专家都集中在少数几个节点——跨节点的数据量小但集中,节点内的转发需求大。
这个特性直接催生了 DeepEP 的第一个设计点:常规 kernel 专门针对”非对称域带宽转发”(asymmetric-domain bandwidth forwarding)优化,也就是数据从 NVLink 域转发到 RDMA 域、或从 RDMA 域转发回 NVLink 域的场景。比如某个节点收到跨节点来的 token 后,还要通过 NVLink 转发给节点内持有不同专家的其他 GPU。
朴素 all-to-all 的三个问题#
在 DeepEP 之前,MoE 的跨节点通信一般用 NCCL 的 AllToAll,它有三个明显的浪费:
- 重复发送:一个 token 被路由到同一节点上的多个专家(group-limited gating 下这很常见),朴素实现会对每个专家各发一份跨节点数据,同一份数据在 RDMA 上反复传输;
- 不利用 NVLink:节点内转发没有跟跨节点传输联动,慢速链路成了瓶颈;
- 同步开销大:collective 通信需要全局同步点,rank 之间互相等待,长尾效应严重——通信耗时取决于数据量最大的那个连接。
DeepEP 的每个设计几乎都是针对这三条逐个击破的。
DeepEP 全景:两个 kernel 家族,一个共同目标#
DeepEP 把 MoE 通信分成两个差异极大的场景,分别提供 kernel:
| 常规 kernel(Normal) | 低延迟 kernel(Low-latency) | |
|---|---|---|
| 适用阶段 | 训练、prefill(预填充) | decode(解码,逐 token 生成) |
| 目标 | 高吞吐 | 低延迟 |
| 通信路径 | NVLink + RDMA,非对称转发 | 纯 RDMA,不做 NVLink 转发 |
| 计算-通信重叠 | 通过 SM 数量控制(占 SM) | 通过 hook 机制(0 SM 占用) |
| 典型 batch | 上千 token | 几十到两百多 token |
这两个家族共享底层基础设施:基于 NVSHMEM 的对称内存(V1),支持 FP8 低精度传输,kernel 运行时 JIT 编译(安装不需要 CUDA 编译)。DeepSeek 官方推理系统(DeepSeek-V3/R1 推理系统博客)中,跨节点 all-to-all 通信正是基于 NVSHMEM 与 IBGDA 的自研内核,DeepEP 就是这套代码整理开源后的形态。vLLM、SGLang、Megatron-LM 都接入了 DeepEP 作为 EP 通信后端。
常规 kernel:为 prefill 的高吞吐而设计#
非对称带宽转发与两阶段通信#
常规 kernel 的完整数据流可以概括为两阶段:节点内聚合,节点间单次传输。
以 dispatch 为例。设一个节点上有 4 张 GPU(rank 0-3),每个 token 的 top-8 专家可能落在本节点或其他节点。DeepEP 的做法是:
- 阶段一(节点内):每个 rank 通过 NVLink 把需要发给同一远程节点的 token 数据汇总(聚合/去重)到该节点的一个”出口” rank;
- 阶段二(节点间):出口 rank 通过 RDMA 把聚合后的数据一次发给目标节点;
- 目标节点收到后,再通过 NVLink 把数据转发给节点内持有对应专家的各个 GPU。
去重的效果立竿见影:一个 token 被路由到同一节点上的多个专家时,跨节点只传一份数据,到达后再复制。combine 方向反过来做分层归约(hierarchical reduction):同一 token 在多个专家上的输出,先在节点内通过 NVLink 加权求和归约成一份,再把这一份结果通过 RDMA 送回原 rank——跨节点流量同样被大幅压缩。
这就是”非对称域带宽转发”的全部含义:让慢速的 RDMA 只承载”每个 token 每节点一份”的最小流量,让快速的 NVLink 承担聚合、复制与转发。带宽不对称问题被结构性地规避了。
SM 数量控制:把通信 kernel 塞进少量 SM#
常规 kernel 支持通过 Buffer.set_num_sms(N) 显式控制参与通信的 SM 数量。为什么需要这个?因为通信 kernel 和计算 kernel 共用 GPU 的 SM,如果通信 kernel 独占所有 SM,计算就没法同时进行;如果只给它一小部分 SM,它就有足够多的空闲周期,可以和计算并行推进。DeepSeek-V3 训练中,H800 上最多约 20 个 SM 被分配给通信相关操作(README 示例代码默认 set_num_sms(24)),剩余 110+ 个 SM 专心做 GEMM。这就是”用 SM 数换重叠度”的思路:通信慢一点没关系,只要它在计算的阴影里完成,总时间就是两者取 max 而不是相加。
隐式的 CPU 等待:dispatch 里的一个微妙设计#
常规 kernel 的 dispatch 有个细节:调用方一开始不知道本 rank 会收到多少 token(取决于全局路由结果)。所以 dispatch 内部有一个隐式的 CPU 等待:GPU 端先跑一个计数内核,算出每个 rank 的接收 token 数,把信号发回 CPU,CPU 等这个信号到达后再分配接收缓冲、启动真正的数据搬运。官方文档用下面这张图描述这个流程:

这个”CPU 等 GPU 信号”的设计意味着常规 kernel 不兼容 CUDA graph(除非在节点内场景指定 num_worst_tokens,用最坏情况预留缓冲)。这正是低延迟 kernel 存在的另一个理由——解码阶段必须兼容 CUDA graph。
性能数据:逼近 NVLink 与 RDMA 的极限#
官方在 H800(NVLink 约 160 GB/s)+ CX7 400 Gb/s 网卡(约 50 GB/s)上、按 DeepSeek-V3 预训练配置(4096 token/批、hidden 7168、top-4 组、top-8 专家、FP8 分发、BF16 合并)测得:
| 场景 | Dispatch #EP | 瓶颈带宽 | Combine #EP | 瓶颈带宽 |
|---|---|---|---|---|
| 节点内 | 8 | 153 GB/s(NVLink) | 8 | 158 GB/s(NVLink) |
| 节点间 | 16 | 43 GB/s(RDMA) | 16 | 43 GB/s(RDMA) |
| 节点间 | 32 | 58 GB/s(RDMA) | 32 | 57 GB/s(RDMA) |
| 节点间 | 64 | 51 GB/s(RDMA) | 64 | 50 GB/s(RDMA) |
节点内 153–158 GB/s 意味着 NVLink 利用率超过 95%(按官方标注的 160 GB/s 峰值算)。节点间最有趣的是 EP32 反而比 EP16 高(58 vs 43 GB/s)——EP 规模增大时,每个 rank 的发送目标变多,聚合效应更强,跨节点流量分布更均匀,直到 EP64 才因更多 rank 之间的同步开销回落。这也解释了生产环境把 EP 组规模取在 32-64 这个区间:组太小聚合效应不足,组太大同步开销会吃掉收益。
低延迟 kernel:解码阶段的 0-SM 重叠#
为什么解码阶段需要完全不同的设计#
解码(decode)阶段和 prefill 有本质区别:每个 rank 每轮只有几十到两百多个 token(KV 缓存注意力逐个生成),对延迟极度敏感——每多 100 微秒,用户感知的 TTFT/TPOT 就多 100 微秒。这时候:
- 高吞吐 kernel 的 NVLink 转发路径多一跳,延迟高;
- 占 SM 的通信 kernel 会挤占计算资源,拖慢 GEMM;
- CPU 参与同步会引入不可控的抖动。
所以低延迟 kernel 做了三个激进选择:纯 RDMA(不做 NVLink 转发)、SM 只负责发指令然后立即退出、用 hook 实现计算-通信重叠。
纯 RDMA:为延迟砍掉转发路径#
低延迟 kernel 完全走 RDMA,节点内转发被去掉。代价是节点内的流量也走网卡(所以官方要求 QP 数量必须等于本地专家数,每个专家对应一个 Queue Pair 以保证并发度),以及缓冲内存消耗巨大(官方建议 num_max_dispatch_tokens_per_rank 小于 256,否则显存扛不住)。这是典型的”用显存和带宽换延迟”。
hook 机制:RDMA 在后台跑,GPU 一个 SM 都不占#
这是 DeepEP 最精妙的设计。调用 low_latency_dispatch(..., return_recv_hook=True) 后,kernel 做的事只是:SM 把 RDMA 工作请求(WQE)提交出去,然后立刻退出。真正的数据传输由网卡异步完成,完全不占用 SM。提交动作本身只花微秒级时间,而传输时间(几十到几百微秒)全部躲进了计算阶段的阴影里。
等待接收数据的时机由调用方通过 hook 控制:hook() 被调用时才真正消费接收缓冲。官方文档用下面这张图说明双微批(double-batch)重叠的用法——每个微批的注意力/分发/专家计算/合并四段交错,RDMA 流量在后台持续流动:

这正是 DeepSeek-V3/R1 推理系统”双批重叠”机制的底层实现(系统层面还叠加了 DualPipe 的跨层流水线)。vLLM 的 EP 解码路径、SGLang 的 DeepEP 后端都用这个 hook 接口。由于 kernel 提交后立即返回、没有 CPU 等待 GPU 信号,低延迟模式兼容 CUDA graph(replay 时需恢复 buffer 状态)。
为什么 combine 比 dispatch 慢?#
先看数据。官方在 H800 + CX7 上、按生产配置(128 token/批、hidden 7168、top-8 专家、FP8 分发、BF16 合并)测得:
| Dispatch #EP | 延迟 | RDMA 带宽 | Combine #EP | 延迟 | RDMA 带宽 |
|---|---|---|---|---|---|
| 8 | 77 µs | 98 GB/s | 8 | 114 µs | 127 GB/s |
| 16 | 118 µs | 63 GB/s | 16 | 195 µs | 74 GB/s |
| 32 | 155 µs | 48 GB/s | 32 | 273 µs | 53 GB/s |
| 64 | 173 µs | 43 GB/s | 64 | 314 µs | 46 GB/s |
| 128 | 192 µs | 39 GB/s | 128 | 369 µs | 39 GB/s |
| 256 | 194 µs | 39 GB/s | 256 | 360 µs | 40 GB/s |
几个值得解释的点:
- combine 延迟约是 dispatch 的 1.5 倍。combine 除了传输,还要做加权求和(乘以 top-k 权重再累加),并且跨节点的归约涉及 RDMA 原子操作(fetch-and-add 类),原子操作在 InfiniBand 上的开销远高于普通 put/get。dispatch 是纯数据搬运,combine 是”搬运 + 归约”,天然更重。
- 表格里的”RDMA 带宽”是逻辑带宽口径。V2 README 的注释明确说明:“这些结果是逻辑带宽,例如 EP 8×2 场景下的 90 GB/s 实际包含了本 rank 内的流量”。低延迟模式中,被路由到本 rank 本地专家的 token 不走网卡,但仍计入数据量;所以 EP8 的 98 GB/s 和 127 GB/s 都不能直接跟单网卡 50 GB/s 峰值比较。真实网卡流量低于表格数字,这是评估任何这类 benchmark 都要注意的口径。
- EP 规模越大延迟越高(77 µs → 194 µs),因为数据要发往更多 rank、每个 rank 的同步与原子操作变多;EP256 时延迟与 EP128 基本持平,说明此时已经完全是带宽受限(39-40 GB/s 接近网卡上限)。
- 对照前面算的账:EP8 场景下 7.3 MB 逻辑数据在 77 µs 内完成,等效约 95 GB/s——与官方 98 GB/s 吻合,说明 dispatch 是纯带宽受限的,kernel 本身的开销已经被压到接近零。
计算-通信重叠的两种模式:SM 控制 vs hook#
DeepEP 提供了两套完全不同的重叠哲学:
- 常规 kernel:占 SM 的重叠。通信 kernel 占用一部分 SM(如 20-24 个),与计算 kernel 并行执行。重叠度通过 SM 数量调节,SM 越多通信越快但计算越慢,需要针对 workload 调优(README 建议在自己的集群上跑测试做 auto-tuning)。
- 低延迟 kernel:0-SM 的重叠。SM 只提交指令、立即退出,传输交给网卡,重叠完全由 hook 控制。官方提供
EventOverlap接口管理通信流与计算流之间的依赖(previous_event参数把计算流事件传给通信 kernel 作为依赖,event.current_stream_wait()等待通信完成)。
低延迟内核提交 RDMA 指令有两条路径:IBRC(SM 把指令通过 CPU 提交给网卡)和 IBGDA(InfiniBand GPUDirect Async,GPU 直接向网卡提交工作请求,绕过 CPU)。IBGDA 需要 NVIDIA 驱动开启 NVreg_EnableStreamMemOPs=1、PeerMappingOverride=1(或 GDRCopy 内核模块)。无论哪条路径,SM 都只花微秒级时间在提交上——这正是”不占 SM”的实现本质。
顺带一个工程彩蛋:为了极致性能,DeepEP 用了一条未定义行为的 PTX 指令——用只读加载 ld.global.nc.L1::no_allocate.L2::256B 去读易变(volatile)数据。文档解释:Hopper 架构上非相干缓存与 L1 统一,.L1::no_allocate 这个修饰符是强约束而非提示,L1 里没有脏数据,所以正确性有保证,性能比常规 volatile 读好得多。如果 kernel 在其他平台上行为异常,可以加 DISABLE_AGGRESSIVE_PTX_INSTRS=1 关闭这条路径。这是读 DeepEP 源码时最容易被吓到的地方,也侧面说明追求极限带宽时连缓存一致性语义都可以谈条件。
FP8 与精度:低精度传输的完整策略#
MoE 通信有个天然的低精度机会:dispatch 只是把数据从一处搬到另一处,专家计算前的量化误差可以用缩放因子恢复。DeepEP 的策略:
- dispatch 用 FP8:数据以 FP8 传输,同时把每 token 的缩放因子(scale)一并传输(FP8 数据与 scale 分开打包),接收端反量化;
- combine 用 BF16:专家输出与路由权重的加权归约需要精度,归约在 BF16 下进行;
- 低延迟模式还支持 UE8M0(指数格式,用于传输 scale)与 LogFMT(10-bit 对数格式压缩 combine 数据)等专用格式。
数值上这是有取舍的:节点内预归约用 BF16,精度低于 FP32 归约,且引入非确定性(浮点加法的顺序依赖)。这正是 DeepSeek 团队”以少量精度换 1.6 倍以上通信带宽”的工程权衡——FP8 让 dispatch 数据量直接减半,而恢复精度的成本只是传输一个很小的 scale 张量。
DeepEP 在 DeepSeek 生产系统中的表现#
DeepSeek-V3/R1 推理系统的官方博客披露了生产环境的数字:在 16-128 张 GPU 的 EP 组规模下,DeepEP 的 dispatch/combine 每 GPU 带宽超过 40 GB/s,几乎打满 400 Gb/s 网卡。结合系统级的双批重叠与负载均衡,整个集群(226 节点、1808 张 GPU)才能支撑起 DeepSeek 的对外服务。
值得注意的还有:DeepEP 是推理与训练共用的库(常规 kernel 服务训练和 prefill,低延迟 kernel 服务 decode),这在当时是很少见的——大多数框架的通信层要么为训练优化要么为推理优化。vLLM、SGLang、Megatron-LM 都选择接入它,很大程度上是因为”一个库同时满足两个阶段”。
DeepEP V2:用 NCCL Gin 重写后的 2026 版本#
DeepEP 当前 main 分支是 2026 年的 V2 重构版(此前稳定版为 2025-09-16 发布的 v1.2.1)。V2 最核心的变化是把底层从 NVSHMEM 换成 NCCL Gin 后端(header-only、轻量、可复用已有 NCCL communicator),并做了一次彻底的 API 统一。
统一接口与解析式资源计算#
V1 里高吞吐和低延迟是两套 API(Buffer + 手动指定 SM 数),V2 统一成单个 ElasticBuffer 接口,SM 数与 QP 数不再需要手动调优,而是用 get_theoretical_num_sms() 按带宽模型解析式计算——输入节点内/节点间带宽(sm_read_gbs、rdma_gbs、nvlink_gbs 等)与是否重叠的标志,直接算出最优 SM 数。官方 README 给出示例:
1_buffer = ElasticBuffer(2 group,3 num_max_tokens_per_rank=num_max_tokens_per_rank,4 hidden=hidden,5 num_topk=num_topk,6 use_fp8_dispatch=use_fp8_dispatch,7)8# V2 解析式计算最优 SM 数,无需再手动调优9_num_comm_sms = _buffer.get_theoretical_num_sms(num_experts, num_topk)V2 的性能与代价#
| Arch | NIC | 拓扑 | Dispatch 瓶颈带宽 | Combine 瓶颈带宽 | SM 数 |
|---|---|---|---|---|---|
| SM90 (Hopper) | CX7 | EP 8×2 | 90 GB/s (RDMA) | 81 GB/s (RDMA) | 12 |
| SM90 | CX7 | EP 8×4 | 61 GB/s (RDMA) | 61 GB/s (RDMA) | 6 |
| SM100 (Blackwell Ultra) | CX7 | EP 8×2 | 90 GB/s (RDMA) | 91 GB/s (RDMA) | 12 |
| SM100 | 无 | EP 8 | 726 GB/s (NVLink) | 740 GB/s (NVLink) | 64(最大性能) |
| SM100 | 无 | EP 8 | 643 GB/s (NVLink) | 675 GB/s (NVLink) | 24(最少 SM) |
相比 V1:峰值性能最高提升 1.3 倍,SM 占用最多节省 4 倍——V3 风格训练场景的通信 SM 从 24 个降到 4-6 个,性能持平或更好。EP 规模上限从几十扩展到 EP2048。
V2 还新增了三个”0 SM”实验特性:Engram(远程内存访问)、PP(流水线并行通信)、CP(上下文并行,用 Copy Engine)。代价也很明确:缓冲内存消耗比 V1 大;V1 的 0-SM 纯 RDMA 低延迟模式在 V2 中不再支持(低延迟路径并入 Elastic kernel,占用少量 SM)。另外社区反馈的已知问题:ld.global.nc 这类激进 PTX 仍在使用(可用环境变量关闭),部分场景下逻辑带宽口径依旧。
生态、后续优化与局限#
集成与社区分支#
- 推理框架:vLLM 与 SGLang 都以 DeepEP 作为 EP 后端;Megatron-LM 也提供接入。
- 零拷贝分支:腾讯网络平台部的 PR 去掉了 PyTorch tensor 与通信 buffer 之间的拷贝,显著降低常规 kernel 的 SM 占用(zero-copy PR)。
- hybrid-ep 分支:用 TMA 指令实现最小 SM 占用、支持更大 NVLink 域、单 batch 细粒度重叠,还支持无 NVLink 环境的 PCIe kernel 与 NVFP4 数据类型。
- AntGroup-opt 分支:Normal-SMFree(把 SM 从 RDMA 路径中彻底摘除)、LL-SBO(用信号机制把 Down GEMM 与 combine 发送重叠)、LL-Layered(跨节点低延迟算子用 rail 优化转发)。
- MORI:AMD 团队基于 ROCm 的 MORI 后端让 DeepEP 在 AMD GPU 上跑通(低延迟模式)。
腾讯 TRMT 的三层优化#
腾讯云在其技术博客(腾讯云社区《万字详解大模型推理加速核心原理》)中披露了对 DeepEP 的深度改造:控制面用 IBGDA 内存语义 API 把计算与通信封装为统一 kernel,消除 kernel 启动开销,控制面延迟从 3 µs 降到 0.5 µs;数据面通过 PTX 指令精细控制数据在 HBM 与 L1/L2 之间的搬移,避免通信流量冲刷掉模型权重与 KV 缓存(bypass L2);传输层构建全互联架构,用动态 QP 端口分配让双端口网卡同时跑满带宽,弥补 DeepEP 只考虑单网卡的不足。整体通信算子耗时减少约 60%。
局限#
- 硬件绑定:V1 依赖 NVSHMEM + IBGDA,且要求 mlx5 网卡驱动,可移植性差(社区论文对比中,主机代理(host-proxy)方案在 EFA 等网络上更通用);
- 精度与确定性:节点内 BF16 预归约带来精度损失与非确定性,对要求逐位复现的训练场景是隐患;
- RoCE 兼容:官方只在 InfiniBand 上充分测试,RoCE 是”理论上兼容”;
- V2 的取舍:缓冲内存更大、0-SM RDMA 低延迟模式被移除。
小结#
把 DeepEP 的所有设计串起来,核心就一句话:MoE 通信的本质矛盾是 NVLink 与 RDMA 的带宽不对称,DeepEP 的所有 kernel 都在做同一件事——让慢速链路只传最小必要流量,让快速链路和网卡异步机制把剩下的延迟藏进计算里。具体手段有四条:dispatch 去重与 combine 分层归约(减少 RDMA 流量)、非对称域带宽转发(结构上绕开带宽不对称)、SM 数量控制与 hook 重叠(通信躲进计算的阴影)、FP8/UE8M0 等低精度格式(数据量减半)。这些设计叠加起来,把 dispatch/combine 从”MoE 推理的性能瓶颈”变成了”带宽受限的纯搬运”,EP8 解码 dispatch 77 µs 的成绩基本就是硬件极限本身。
对研零阶段、刚接触 CUDA 的读者来说,DeepEP 是理解三个方向的绝佳教材:一是分布式通信的工程全景(NVLink/RDMA/IBGDA/QP 这些概念在这里第一次有了具体用途);二是”用 SM 换重叠、用精度换带宽”这类体系结构层面的权衡方法论;三是生产级通信库的代码组织(buffer 管理、事件流、CUDA graph 兼容性)。如果顺着源码继续读,kRDMASender/kNVLReceiver 这些 warp 角色分工(每个 SM 上 7 个 warp 发 RDMA、1 个协调、若干 warp 做 NVLink 转发)还能看到一整套精细的并行分工,那是另一篇文章的容量了。
参考资料#
- DeepEP GitHub 仓库(官方 README,V2)
- DeepEP V1 官方文档(legacy.md,含全部性能数据与架构图)
- DeepEP 官方网站
- DeepSeek-V3/R1 推理系统官方博客(双批重叠与生产部署)
- DeepSeek-V3 技术报告(group-limited gating)
- AMD ROCm《The vLLM MoE Playbook》(EP 数据流图)
- MarkTechPost:DeepSeek AI Releases DeepEP
- 腾讯云社区《万字详解大模型推理加速核心原理》(含 TRMT 对 DeepEP 的优化)
- 腾讯新闻:DeepSeek 开源周 Day2 首个 MoE 开源通信库
- DeepWiki:deepseek-ai/DeepEP 源码结构分析
文章分享
如果这篇文章对你有帮助,欢迎分享给更多人!
部分内容可能已过时
评论区
分享你的想法,与大家交流讨论
音乐
暂未播放



