Prhub

#35568 [Bugfix] Fix SM121 (DGX Spark) exclusion from Marlin/CUTLASS FP8 paths

原始 PR 作者 blake-snc 合并时间 2026-05-16 01:59 文件变更 8 提交数 5 评论 21 代码增减 +19 / -14

执行摘要

修复 SM121 被排除在 Marlin/CUTLASS FP8 路径外

SM121(DGX Spark)和SM120(RTX 5090)具有相同的FP8 MMA能力,但被精确匹配的架构守卫排除,导致用户无法使用Marlin/CUTLASS FP8路径(issue #35432, #30163)。

推荐阅读。该PR展示了如何通过有界家族匹配而非精确匹配来处理架构兼容性,是一种可复用的设计模式。同时解决了多个长期未关闭的issue,对Blackwell用户至关重要。

讨论亮点

主要讨论集中在MOE测试失败分析上:blake-snc最初认为失败是预先存在的,后确认fused_marlin_moe在set_current_vllm_config上下文之外调用导致,最终通过添加default_vllm_config fixture修复。mgoin询问失败原因,blake-snc分析了日志并提交修复。社区成员AshtonVaughan在RTX 5090上验证了家族检查逻辑,确认与SM120兼容。DavRodSwede报告在3节点DGX Spark集群上运行patched镜像38天无问题。eugr多次催促合并。

实现拆解

  1. 代码生成脚本csrc/moe/marlin_moe_wna16/generate_kernels.pycsrc/quantization/marlin/generate_kernels.py):将架构判断条件从 arch in [89, 120] 改为 arch == 89 or arch // 10 == 12,使SM121也能生成FP8内核模板。
  2. 运行时CUDA检查csrc/moe/marlin_moe_wna16/ops.cu):将TORCH_CHECK中的精确capability比较改为检查 major_capability == 12
  3. CUTLASS dispatch宏csrc/libtorch_stable/quantization/w8a8/cutlass/c3x/scaled_mm.cuhscaled_mm_sm120_fp8_dispatch.cuh):将 enable_sm120_only 替换为 enable_sm120_family,对应宏条件从 ==1200 改为 >=1200 && <1300
  4. Python端输入验证vllm/model_executor/layers/quantization/utils/marlin_utils.py):将 is_device_capability(120) 替换为 is_device_capability_family(120),并更新错误提示。
  5. 测试文件tests/kernels/moe/test_moe.pytests/kernels/quantization/test_marlin_gemm.py):使用 is_device_capability_family(120) 替换精确匹配;同时为 test_fused_marlin_moe 等三个测试添加 default_vllm_config fixture,修复因缺少配置上下文导致的失败。
文件 模块 状态 重要度
csrc/moe/marlin_moe_wna16/generate_kernels.py MOE 内核 modified 5.31
csrc/quantization/marlin/generate_kernels.py 量化内核 modified 5.31
vllm/model_executor/layers/quantization/utils/marlin_utils.py 量化工具 modified 5.18
tests/kernels/moe/test_moe.py MOE 测试 modified 3.91
tests/kernels/quantization/test_marlin_gemm.py 量化测试 modified 3.58
csrc/moe/marlin_moe_wna16/ops.cu MOE 内核 modified 2.81
csrc/libtorch_stable/quantization/w8a8/cutlass/c3x/scaled_mm.cuh CUTLASS 调度 modified 2.24
csrc/libtorch_stable/quantization/w8a8/cutlass/c3x/scaled_mm_sm120_fp8_dispatch.cuh FP8 调度 modified 2.24

关键符号

get_marlin_input_dtype marlin_mm marlin_moe_generate_valid_test_cases test_fused_marlin_moe test_fused_marlin_moe_with_bias test_fused_marlin_moe_non_gated

关键源码片段

csrc/moe/marlin_moe_wna16/generate_kernels.py core-logic

核心代码生成脚本,控制 MOE Marlin 内核的 FP8 支持架构判断

# 从编译参数中解析架构列表
for arch in sys.argv[1].split(","):
    arch = arch[: arch.index(".") + 2].replace(".", "")
    arch = int(arch)
    # SM89 和 SM12x 系列 (SM120 RTX 5090, SM121 DGX Spark GB10)
    # 完全支持 mma.sync.aligned.m16n8k32.row.col.f32.e4m3.e4m3.f32
    # SM90 和 SM100 可通过 PTX 模拟,但无加速效果。
    # 原代码为 `if arch in [89, 120]`,现在使用有界家族匹配
    if arch == 89 or arch // 10 == 12:
        SUPPORT_FP8 = True
    if arch >= 80:
        SUPPORT_SM80 = True
    if arch == 75:
        SUPPORT_SM75 = True

评论区精华

MOE 测试失败分析及修复 测试

blake-snc 最初分析 CI 失败是预先存在的,后确认是 fused_marlin_moe 在 set_current_vllm_config 上下文之外调用导致。mgoin 要求调查。最终通过添加 default_vllm_config pytest fixture 修复。

结论:在三个测试函数上添加 @pytest.mark.usefixtures('default_vllm_config') · 已解决

SM12x 家族兼容性验证 正确性

AshtonVaughan 在 RTX 5090 (SM12.0) 上验证了家族检查逻辑,确认 is_device_capability_family(120) 正确允许 12.0 和 12.1。

结论:逻辑验证通过,家族检查也覆盖 SM120 · 已解决

社区部署稳定性证据 other

DavRodSwede 报告在 3 节点 DGX Spark 集群上运行 patched 镜像 38 天,未出现相关问题。

结论:补丁在真实生产环境中验证稳定 · 已解决

风险与影响

风险较低。主要风险点:1)新的家族检查(arch // 10 == 12)可能在未来引入SM13x时意外匹配?但PR使用有界检查,不会匹配SM13(130//10=13)。2)测试依赖真实硬件SM121,CI中无对应机型,覆盖率不足。3)添加default_vllm_config fixture可能影响测试独立性,但已与现有模式一致。

对用户:DGX Spark(SM121)用户现在可以正常使用Marlin FP4和CUTLASS FP8路径,此前只能回退到慢速实现或报错。对系统:无性能回退,因为家族检查包含SM120且不引入额外开销。对团队:统一了SM12x架构处理方式,减少了未来添加新变体时的工作量。

依赖真实硬件验证 架构家族边界风险 测试上下文依赖

关联 Issue

#30135 [Bug]: MXFP4 models still fall back to the Marlin kernel for RTX PRO 6000 (Blackwell SM120)
#30163 [Usage]: Help Running NVFP4 model on 2x DGX Spark with vLLM + Ray (multi-node)
#35432 Prebuilt vLLM wheels / official images fail on RTX 50-series (Blackwell, SM120/SM121) — "no kernel image" / "sm_120 not compatible"

完整报告

参与讨论