看着视频,学着大神的贴子对于“魔改SGLANG支持7900XTX 双卡TP”的坎坷学习路。
-
看着视频,学着大神的贴子对于“魔改SGLANG支持7900XTX 双卡TP”的坎坷学习路,还是总结了一下,指点。活都是ai做的,我就是跟在ai操作下学习一下方法。哈。下面是正文
【踩坑实录】双 7900XTX 跑 SGLang TP=2 —— 从物理挪卡到裸机 LXC 验证,X99 平台 TP 死局全记录
2026-09-07 ~ 2026-09-09 · 三天折腾,结论:平台死,不是软件锅
硬件:X99-T8D 双路 E5-2696v3 + 2× RX 7900 XTX + PVE 9.2
目标:双卡张量并行(TP=2)跑 SGLang 魔改 fork(gfx1100 分支)
一、结果先讲
TP=2 方向关闭。死因:Intel X99 root complex 不支持 GPU 间 P2P 路由。
软件栈全装通了(ROCm 7.14 + torch 2.11 + fork 编译 + 模型加载都过了),死在最后一关:双卡通信实测
hipDeviceCanAccessPeer = NO。不是 VFIO 的问题(LXC 验证了),不是虚拟化层的问题(LXC 等价裸机也验证了),是 Intel 平台硬件本身就没有这个能力。
二、踩坑顺序(重点:我走的路径全是错的顺序)
阶段 0(错):先装软件,后查硬件
这是最大的坑。我花了一天时间装 ROCm 7.14、torch 2.11、SGLang fork 编译,结果最后 5 分钟就能查出来的问题,让我先走了几天弯路。
正确的顺序应该是:先查硬件 P2P 能力,再决定要不要装软件。
5 分钟硬件预检命令:
# 1. 两卡是否在同一个 CPU socket 下? lspci -D | grep -iE "vga|3d controller" # 看 bus 号:0x:xx = CPU0 域,8x:xx = CPU1 域 # 如果一张 04:00 一张 86:00 → 跨 CPU socket,TP 直接判死 # 2. IOMMU group 是否独立? for d in <gpu1_bdf> <gpu2_bdf>; do echo "$d -> group $(basename $(readlink /sys/bus/pci/devices/$d/iommu_group))" done # 如果两张卡在不同的 IOMMU group → 没有 peer DMA 路径这两个检查如果一开始就做了,三天变三小时。
阶段 1:初始报错 —— 双卡不在同一 CPU
VM104 里装好了 ROCm 7.14 + fork,启动 SGLang TP=2,直接报错:
RCCL error: communication failure between GPUs当时的误判:以为是软件配置问题,开始查 RCCL 环境变量、torch 版本匹配、编译参数。
实际原因:两张卡分别在 CPU0(bus 04)和 CPU1(bus 86)下,跨 socket 通信走 QPI/UPI,PVE 直通下没有 peer DMA 路径。
阶段 2:物理挪卡 —— 同一 CPU 下还不行
操作:把原来挂在 CPU1 侧的卡拔下来,插到 CPU0 侧空着的 x16 槽里。
验证(重启后):
- 卡1:
04:00.0→ CPU0-Port2(Gen3 x16) - 卡2:
07:00.0→ CPU0-Port3(Gen3 x16)
两张卡都挂在 CPU0 下了。但 TP=2 还是不通。
为什么同 CPU 还不够?
两张卡虽然在同一 CPU,但:
- 各挂一个独立的 root port(00:02.0 和 00:03.0)
- 各属一个独立的 IOMMU group(54 和 58)
- 每张卡还经过板载 Navi10 PCIe 交换芯片(板上的 retimer)
IOMMU 的 peer DMA 隔离是按 group 切的,跨 group 默认拒绝。要两卡同 group,必须挂在同一个 PCIe switch 的下游(x8+x8 拆分),X99-T8D 的布局做不到。
教训:同 CPU 是 P2P 的必要条件,不是充分条件。还需要同 IOMMU group(同 PCIe switch 下游)。
阶段 3:怀疑虚拟化层(VFIO)
当时的逻辑(后来被 hermes 验证是对的推理方向):
- vfio-pci 直通本身不做跨设备 peer DMA
- guest 内核看到的 PCIe 拓扑是 QEMU 伪造的(BDF 重编成 01:00/02:00,不是物理 BDF)
- 所以 VM 里测试 NO 不能证明物理机也 NO
验证方案:不重装系统(代价太大),用 LXC 容器代替。
为什么 LXC 能模拟裸机?
- LXC 容器共享宿主内核,没有自己的内核
- GPU 不需要 vfio 直通,宿主直接用 amdgpu 驱动
- 容器里的 ROCm 用户态通过
/dev/kfd+/dev/dri访问 GPU - KFD 看到的是宿主真实的 PCIe 拓扑
- 等价于裸机的硬件条件
操作步骤:
- 改宿主 modprobe 配置:GPU 从 vfio-pci 切回 amdgpu
- 重启宿主(冷启动,不能热切!)
- 建 LXC 200(Ubuntu 24.04),放行
/dev/kfd+/dev/dri - 容器内装 ROCm 7.14 用户态
- 跑 HIP 测试程序
LXC 实测结果:
hipDeviceCanAccessPeer(0→1) = NO hipDeviceCanAccessPeer(1→0) = NO KFD p2p_links 目录为空 跨卡 memcpy = 3.1 GB/s(纯主机内存中转)结论:虚拟化不是原因。Intel X99 root complex 本身就不提供 GPU 间 P2P/原子路由。
BIOS 能救吗? 不能。
- Above 4G Decoding(大 BAR)已开(唯一的前提条件)
- Intel X99 平台没有 "enable P2P" 选项(这类选项不存在于 Intel 平台)
- root port 的 AtomicOpsCap = Routing-(实测),这是芯片能力,BIOS 改不了
三、最终根因
Intel Haswell-EP 的 root complex 没有 GPU 间 peer DMA 路由能力。
- AMD 平台的 GMI/infinity fabric 北桥原生支持 peer 路由
- Intel 平台的 RC 不支持(或支持极弱)
- 两张卡的数据路径必须穿过 root complex
- Intel RC 不提供 GPU 间直连路由
对照成功案例:所有 GPU P2P 跑通的案例都是:
- AMD 单路平台(AM4/AM5/TRX40/TRX50),GMI 原生 peer 路由
- 或加 PLX 交换卡,两卡挂到同一 switch 下游(绕开 RC)
Intel X99/Z270 等消费/工作站平台:无成功先例。
四、必须避的坑(按重要性排序)
坑 1:先装软件再查硬件(最大坑)
错误:装了一天的 ROCm + fork,才去查硬件
正确:5 分钟跑完硬件预检,再决定要不要装软件# 5 分钟预检脚本 echo "=== GPU BDF 和 CPU socket 归属 ===" lspci -D | grep -iE "vga|3d" for d in $(lspci -D | grep -iE "vga|3d" | awk '{print $1}'); do bus=${d%%:*} if [[ $bus < 0x80 ]]; then echo "$d → CPU0 域" else echo "$d → CPU1 域" fi done echo "=== IOMMU group ===" for d in $(lspci -D | grep -iE "vga|3d" | awk '{print $1}'); do grp=$(basename $(readlink /sys/bus/pci/devices/$d/iommu_group) 2>/dev/null) echo "$d → group $grp" done如果两卡跨 CPU 或跨 IOMMU group,直接停止,TP 方向关闭。
坑 2:同 CPU ≠ 有 P2P
错误:以为把两张卡挪到同一 CPU 就能通
正确:同 CPU 是必要条件,还需要同 IOMMU groupX99-T8D 的两个独立 root port(00:02.0 和 00:03.0)分属两个 IOMMU group,
即使物理位置都挂在 CPU0 侧,照样没有 peer DMA。坑 3:VFIO 直通天然不支持 peer DMA
错误:以为 VM 里 P2P 不通是虚拟化层的锅,去折腾 VFIO 配置
正确:VFIO 直通设计上就不支持跨设备 peer DMA,这不是配置问题即使物理机能通,VM 直通也通不了(除非用 vIOMMU + 特殊内核支持,PVE 不支持)。
坑 4:LXC 能模拟裸机,但不救平台
LXC 验证的意义是排除虚拟化层的干扰,确认"裸机也不行"。
但如果平台本身不支持 P2P(如 Intel X99),LXC 也救不了。坑 5:驱动热切换会锁卡
错误:vfio → amdgpu 热切换(echo "..." > /sys/bus/pci/drivers/vfio-pci/unbind)
正确:必须冷启动(改 modprobe 配置后重启)热切换可能导致 GPU 进入 D3hot 状态无法唤醒,PCI reset 都救不了,只能重启宿主。
坑 6:PCIe 速率看错位置
错误:看 GPU 端点的 lspci 输出(显示 16GT/s x16)
正确:看 root port 侧(真实槽速)GPU 端点显示的速率是"卡内 switch → 卡"那一段,不是端到端速率。
真实瓶颈在 root port 侧(8GT/s Gen3),以 root port 的LnkSta为准。坑 7:ROCm 版本和源(装软件阶段)
如果决定装软件,注意:
- ROCm 7.14 的源在
repo.amd.com/rocm/packages-multi-arch/ubuntu2404 - 包名带版本后缀:
amdrocm-core-dev7.14-gfx1100 - torch wheel 要 curl 直接下(flat 目录不是 pip 索引),不能
pip install --index-url
坑 8:PVE 双卡直通 romfile 冲突
错误:两张卡共用同一个 romfile
正确:必须复制一份异名的 rom(如 7900XTX_dump.rom和7900XTX_dump2.rom)
五、排查正确顺序(建议存为 checklist)
双卡 TP 可行性排查(5 分钟版): 1. CPU socket 检查 lspci -D | grep -iE "vga|3d" → 两卡 bus 号一个 0x:xx 一个 8x:xx? → YES = 跨 CPU,TP 判死,停止 2. IOMMU group 检查 for d in <gpu1> <gpu2>; do basename $(readlink /sys/bus/pci/devices/$d/iommu_group) done → 不同 group? → YES = 无 peer DMA 路径,TP 判死,停止 3. 平台检查 主板是 Intel X99/Z270/X299 等? → YES = 无 P2P 成功先例,TP 判死,停止 4. (以上全通过才继续) 装软件 → 实测 hipDeviceCanAccessPeer走完前三步,能省掉 90% 的无谓折腾。
六、那这两张卡还能干嘛?
TP 死局,但两张卡不是废铁:
-
双实例并行(推荐)
每张卡各跑一个独立的单卡推理服务,互不通信- VM102 跑模型 A
- VM103 跑模型 B
- 两卡各自满载,总吞吐 = 2× 单卡吞吐
- 这是当前拓扑下性价比最高的用法
-
llama.cpp 分层并行(
--split-mode layer)
各卡独立计算不同层,卡间只传激活值(走 CPU 内存中转)- 不要求 P2P,3.1 GB/s 够用
- 社区有 5×7900XTX 长期稳定运行的先例
- 双卡 48GB 显存可跑 ~48GB 权重模型
-
换平台(如果有 TP 刚需)
- AMD AM5 单路(X670E 等),双卡 x8+x8,GMI 原生 peer 路由
- 或加 PLX PEX 交换卡(成本高,X99 槽位/散热不友好)
七、总结
阶段 操作 结果 教训 1 装 ROCm + fork 编译过,import 过 顺序错了,应先查硬件 2 VM104 启动 SGLang RCCL 通信崩 跨 CPU socket,无 P2P 3 物理挪卡到同 CPU 还是不通 同 CPU 不够,还要同 IOMMU group 4 怀疑 VFIO 层 LXC 验证 虚拟化不是原因 5 LXC 原生 amdgpu 还是 NO 平台本身不支持 6 查 root port 能力 AtomicOpsCap = Routing- Intel RC 无 peer 路由 核心教训:
- 先硬件后软件,5 分钟预检省三天弯路
- 双路主板跨 socket 无 P2P,结构性死局
- 同 CPU 同 IOMMU group 是 P2P 的两个必要条件,缺一不可
- Intel 消费/工作站平台无成功先例
- 换平台(AMD 单路)是最实际的解法
本文已脱敏(无 IP、无具体用户名、无内部系统标识),可直接发技术社区。 现在ai真是贴心。
- 卡1:
-
周末三天折腾总结得很到位,结论完全成立:X99 root complex 不支持 GPU P2P,SGLang 走 RCCL 张量并行在这平台就是死局。这也跟论坛之前的结论对上了——RDNA 卡在 SGLang 用 RCCL 做 TP,要么 stock 版根本没启用(RCCL 默认关),要么就算打通了也常是负优化(TID:1438 实测 TP 无 P2P 硬崩,要 NCCL_PROTO=Simple 才从 0.94 拉到 23,绕一大圈)。
补一个你踩坑里可能没注意到、其实更省事的分叉点:TP 不是双卡加速的唯一路径,对 RDNA3 来说甚至不一定是最优路径。关键看你要的是"单个模型跑更快"还是"显存容量翻倍":
- llama.cpp Vulkan tensor-split 不需要 P2P。它按层把权重分到两张卡,层间走标准 PCIe,根本不需要 peer DMA。所以双 7900XTX 用 Vulkan tensor-split,不需要同 IOMMU group、不需要 PCIe switch 下游,X99 也能跑。大模型 decode 是带宽驱动,权重按层分出去后等效带宽叠上去,实测能拿 1.5× 左右的单模型提升。
- SGLang 的 RCCL 张量并行才真正依赖 P2P,你的 X99-T8D 给不出来,所以这条路在你这台机就是死,不用再试了。
所以:目标如果是"双 7900XTX 跑 27B 更快",别再折腾 SGLang TP,直接 llama.cpp + tensor-split 就能见效,平台不用换;如果非得上 SGLang 那套(长上下文 prefix cache、多 agent 并发),才需要换 EPYC/B650+ 这类能 P2P 的平台,或走你参考的魔改 fork 那条线(TID:1532)。
你那两个硬件预检命令(lspci 看 bus、查 iommu_group)写得很实用,建议再加一句:装软件前先跑这两个检查,真能三天变三小时。