Skip to content

[Bugfix][DSv4] SM12x Triton fallback for fp8_einsum / o_proj (#43743) - #52357

Closed
ajwharton wants to merge 1 commit into
vllm-project:mainfrom
ajwharton:fix/dsv4-sm12x-fp8-einsum-43743
Closed

ajwharton wants to merge 1 commit into
vllm-project:mainfrom
ajwharton:fix/dsv4-sm12x-fp8-einsum-43743

Conversation

@ajwharton

Copy link
Copy Markdown

Purpose

Fixes #43743.

We're trying to intuit where you are already going on SM12x / GB10 and help
out with a small, reviewable slice — not a parallel stack.

On current main, DSv4 o_proj always calls DeepGEMM fp8_einsum.
compute_fp8_einsum_recipe() treats cap.major >= 10 as the SM100
(1, 1, 128) layout. GB10 / RTX 50 report major=12, so they take that
recipe and die on the first forward (layout.hpp scale-factor assert —
the same class as "Unknown SF transformation").

#41834 already fixed tf32_hc_prenorm_gemm. This PR is the follow-up
pasta-paul described in #43743: port jasl's Triton SM12x fp8_einsum
fallback and dispatch it with a per-kernel predicate (capability,
equation, recipe, scale dtype), not support_deep_gemm() |= family(120).

That last point is deliberate. We tried the blunt family-120 DeepGEMM
enable on a dual GB10 box; MoE selected DEEPGEMM_MXFP4, then linear
o_proj hit layout.hpp:97. The gate comment on CudaPlatform was
right. This PR does not open that gate.

What this does / does not

Does:

  • SM12x uses the SM90-shaped recipe (1, 128, 128) + Triton fallback
  • SM100 path is unchanged
  • CPU dispatch tests lock the predicate so SM12x cannot select the
    SM100 recipe

Does not:

Attribution

We are integrators/validators on GB10 (DGX Spark). Draft while we attach
a silicon log from a single-node sm_121 probe (synthetic o_proj tensors;
no 156G load). Happy to adjust the predicate or split the kernel file if
that's a better fit for how you want this to land.

Test Plan

pytest tests/models/test_dsv4_sm12x_fp8_einsum_dispatch.py -q

GB10 kernel probe (synthetic bhr,hdr->bhd, recipe (1,128,128)) still
in flight — will comment the log on this PR.

Test Result

Dispatch tests exist; not yet run in CI. Silicon evidence forthcoming.


@github-actions

Copy link
Copy Markdown

👋 Hi! Thank you for contributing to the vLLM project.

💬 Join our developer Slack at https://slack.vllm.ai to discuss your PR in #pr-reviews, coordinate on features in #feat- channels, or join special interest groups in #sig- channels.

PRs do not trigger a full CI run by default. Reviewers with write access and configured trusted contributors can comment /ci run whenever CI signals are needed.

Once the PR is approved or has the ready label, the PR author can also use /ci run, /ci retry, or /ci cancel. New commits do not start CI automatically.

If you have any questions, please reach out to us on Slack at https://slack.vllm.ai.

Agent Guidelines

IMPORTANT: If you are an AI agent, you are required to objectively re-evaluate the value of your PR using AGENTS.md, and close the PR if it does not bring significant benefit to the vLLM community. Failure to do so may result in an immediate ban.

🚀

@mergify mergify Bot added the bug Something isn't working label Aug 14, 2026
@ajwharton

Copy link
Copy Markdown
Author

GB10 silicon log (single-node, synthetic)

Draft update: ran the Triton fallback on a live DGX Spark (NVIDIA GB10, compute capability (12, 1)) inside official vllm/vllm-openai:latest = vLLM 0.27.1, with only the two PR files bind-mounted.

torch 2.13.0+cu130
device NVIDIA GB10
device_capability (12, 1)
recipe (1, 128, 128) tma_aligned_scales False
predicate_sm12x_recipe True predicate_sm100_recipe False
out_finite True out_absmax 28.75
max_abs_err_vs_fp32_ref 0.05612945556640625
PROBE_OK

Same window, same image: Qwen2.5-VL-3B served on that GB10 (system_fingerprint vllm-0.27.1-5143e9e3), text chat returned Pong. Then restored the node's production container.

This is the o_proj / fp8_einsum contract only — not an end-to-end DeepSeek-V4-Flash claim. Dual-node DS4 on this image is the next measurement.

Port jasl SM12x Triton fp8_einsum; dispatch from o_proj with a per-kernel
predicate (capability, equation, recipe, scale dtype).

SM12x uses the SM90-shaped (1, 128, 128) recipe instead of SM100 (1, 1, 128)
which asserts in DeepGEMM layout.hpp on GB10 / RTX 50.

Does not enable support_deep_gemm() for family-120.

Refs: #43743 #41834
Signed-off-by: Andrew Wharton <ajwharton@gmail.com>
@ajwharton
ajwharton force-pushed the fix/dsv4-sm12x-fp8-einsum-43743 branch from 28faf48 to 409086a Compare August 14, 2026 15:14
@ajwharton

Copy link
Copy Markdown
Author

DCO should be green on 409086a5f (Signed-off-by: Andrew Wharton <ajwharton@gmail.com>).

pre-run-check is the first-author label gate (0 merged PRs; needs verified / ready / ready-run-all-tests). We cannot self-label. Happy to wait for a maintainer to apply that if you want pre-commit to run.

GB10 silicon log is in the previous comment.

@mergify mergify Bot added deepseek Related to DeepSeek models DSv4 labels Aug 19, 2026
@maci0

maci0 commented Aug 23, 2026

Copy link
Copy Markdown

Field report from 2x DGX Spark GB10 (SM 12.1), TP=2, deepseek-ai/DeepSeek-V4-Flash-0731.

compute_fp8_einsum_recipe() treating cap.major >= 10 as SM100 packed INT32 is the bug we hit. GB10 reports major 12, so fused_inv_rope_fp8_quant emitted packed UE8M0 and o_proj became noise.

This PR's SM12x recipe (1, 128, 128) / tma_aligned_scales=False is the right split. Main still has the major <= 9 / else SM100 branch.

On this box Triton w8a8_triton_block_scaled_mm dies with KeyError: 'float8_e8m0fnu', so we used B12x linear plus a Python dequant fp8_einsum fallback with the same SM90-shaped recipe. Isolated einsum is fine. Live greedy "The capital of France is" (temperature=0, max_tokens=32) is " Paris. The capital of Spain is Madrid...", first token ' Paris' logprob -0.244.

Happy to re-test this branch on the same pair if useful.

@TurboTheTurtle

Copy link
Copy Markdown

End-to-end GB10 follow-up on current head 409086a5f588d155ffbddd4bb7b917c96333ed3c.

I used this PR's two runtime files byte-for-byte in a vLLM 0.27.1 adaptation:

  • fp8_einsum.py: 176421dff581a957520445305d2443473cb044772901792cb765fd96d6556b35
  • o_proj.py: 085142bd5d8742c3e5ca5a3d4dd96901226e85acbe2044f49e263bb489601172

The serving test was 2× DGX Spark / GB10 (SM121), TP=2, with an FP4 DeepSeek-V4-Flash-0731 checkpoint, MXFP4 B12X experts, FlashInfer sparse MLA, NVFP4 DS-MLA KV, probabilistic DSpark k=5, 532,288 max context, and CUDA graphs.

The full model loaded 79.48 GiB per rank, allocated 746,430 KV tokens, completed sparse-MLA autotuning and graph capture, and reached API readiness. A six-part functional run passed model listing, thinking-off, reasoning, exact tool-call JSON, streaming, and 48,033-token retrieval. Both ranks remained restart-zero and OOM-free, with no Xid, CUDA/NCCL fatal, EngineDeadError, traceback, or failed post-readiness response.

Scope note: this validates the two runtime files from this PR as part of a complete SM12x serving stack, not the PR's test file or a standalone cherry-pick. Additional SM12x MHC/MQA and FlashInfer sparse-MLA shape fixes were also required for the full serve.

@ajwharton

Copy link
Copy Markdown
Author

Closing this draft. Decision made 2026-08-23: upstream vLLM is continuing down the SM12x/DeepGEMM path on its own, so this fork-side Triton-fallback slice is no longer worth maintaining. The commit (and full fork history) is preserved in a local bundle. Thanks to jasl/#41834 and #43743 for the groundwork — we'll pick this up through official channels when it matures.

@maci0

maci0 commented Aug 24, 2026

Copy link
Copy Markdown

Main still takes the SM100 packed-INT32 recipe whenever cap.major >= 10, so GB10 (major 12) still packs UE8M0. We are not reviving the Triton fp8_einsum path here (torch.float8_e8m0fnu dies on this stack).

Recipe-only follow-up: #53521

cursor Bot pushed a commit to asterayx/vllm that referenced this pull request Aug 28, 2026
Compiled DeepGEMM einsum asserts m/n/k on GB10. Keep the Hopper
(1, 128, 128) recipe and dispatch o_proj to the vllm-project#52357 Triton
fallback. Do not Marlin/Humming-pack is_bmm wo_a weights.

Co-authored-by: Cursor Grok 4.6
Signed-off-by: Cursor Agent <cursoragent@cursor.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working deepseek Related to DeepSeek models DSv4

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[DSv4] [SM 12.0] fp8_einsum has no SM 12.0 fallback — blocks mainline serve on consumer Blackwell (follow-up to #41834)

3 participants