Repository navigation
[Triton/Gluon] Fix MoE routing kernel compile failure - #5558
Conversation
Signed-off-by: Micah Williamson <micah.williamson@amd.com> Co-authored-by: Cursor <cursoragent@cursor.com>
🏷️ CI GuideRuns automatically on every PR:
Extended tests (opt-in via labels):
PR title tags & labels: |
vgokhale
left a comment
There was a problem hiding this comment.
LGTM - perf looks neutral. ASM is identical
There was a problem hiding this comment.
🔵 Needs a closer look
Required architecture-specific regression coverage is missing.
Pull request overview
Fixes Triton compilation failures in the MoE routing stage-2 helpers.
Changes:
- Replaces early returns with guarded blocks.
- Uses local tile-info pointers to avoid compiler issues.
File summaries
| File | Summary |
|---|---|
aiter/ops/triton/_triton_kernels/moe/moe_routing/expt_data.py |
Applies the compiler-safe fix to both routing helpers. Moderate issue: add gfx942 and gfx950 regression coverage for empty-expert branches. |
Review details
Suppressed comments (1)
aiter/ops/triton/_triton_kernels/moe/moe_routing/expt_data.py:77
- [verified] This fixes the shared stage-2 helpers for gfx942/gfx950, but the in-tree routing tests skip gfx942 (
op_tests/triton_tests/moe/test_moe_routing.py:161-162, 446-447, 515-516) and this PR adds no regression test for that architecture or the MXFP4 route. The claimed gfx942 compile failure can therefore regress unnoticed even though gfx950 coverage passes. Author must add or extend a collected routing/MXFP4 test that exercises both empty-expert branches on gfx942 as well as gfx950.
if n_tokens != 0:
BLOCK: tl.constexpr = 8
n_blocks = _cdiv_pow2(n_tokens, tile_dim_log2)
tile_info = TileInfo + tile_start
- Files reviewed: 1/1 changed files
- Comments generated: 0
- Review effort level: Lite
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
Co-authored-by: Cursor <cursoragent@cursor.com>
This reverts commit d78bdfe. Signed-off-by: Micah Williamson <micah.williamson@amd.com>
…ing fixes, fp8 MQA logits split-k and DSv4 tunings (#5573, #5295, #5558, #5603, #5627, #5485) (#5638) Cherry-picks six already-merged `main` PRs onto `release/v0.1.22` for the `v0.1.22.post1` post release. | PR | `main` commit | Backport commit | What | |---|---|---|---| | #5485 | `9252f4672` | `155534984` | Extend the DeepSeek-V4 a8w8 blockscale GEMM tunings for gfx950 (tuning CSV only) | | #5573 | `22d2c7c91` | `6b23ba866` | Pad the MXFP4 A4W4 MoE sort extent to a block_size multiple (fixes a HIP illegal memory access) | | #5295 | `972c8e1fd` | `7d68b0edb` | Skip invalid expert IDs in MoE sorting | | #5558 | `3fdfca11e` | `dd83a9d17` | Fix MoE routing kernel compile failure | | #5603 | `a84bd368c` | `a96461997` | Add split-k support for fp8 MQA logits on gfx950 | | #5627 | `f5ed7dc54` | `a41214712` | Follow-up to #5603: drop chunking when summation folding is unavailable (fixes Triton 3.6 compile) | Original PRs: - #5485: #5485 - #5573: #5573 - #5295: #5295 - #5558: #5558 - #5603: #5603 - #5627: #5627 To be published as `v0.1.22.post1` once merged (tag on the merge commit, release automation builds the wheel set).
#5038 reworked the MoE routing helpers so that _expt_data_compute_stage1 computes the per-expert tile offset and returns it as a small tensor (built from a tl.gather / tl.zeros in an if/else), which is then passed into _expt_data_compute_stage2 and _expt_data_compute_stage2_fused. Those two helpers start with an early return:
This pattern makes the routing kernels fail to compile. Both
_combined_routing(num_tokens > 16) and_combined_routing_fused(num_tokens <= 16) hit it, so any MXFP4 MoE run that goes through this routing path breaks. Reproduced on gfx942 and gfx950, with Triton 3.7.1 (the default in vLLM).The compile aborts inside Triton's ConvertTritonToTritonGPU pass:
(full error log: https://buildkite.com/vllm/amd-ci/builds/12929/list?jid=01a0a157-9fe0-4e1e-b3c7-46d8d32ce602&tab=output#L1425)
This appears to fundamentally be a Triton compiler bug.
Fix: replace the early return with a guarded
if n_tokens != 0:block, and add into a fresh local (tile_info = TileInfo + tile_start) instead of reassigning the TileInfo pointer argument in place. This keeps the value from having to live across the early-return control flow, which is what the conversion pass couldn't handle. The computation and results are unchanged; the previous design that avoided this (loading the offset from a TileStart buffer) confirms the behavior is equivalent.Repro (vLLM):
pytest -v -s tests/kernels/moe/test_ocp_mx_moe.py::test_rocm_mxfp4_moe_oracle[16-256-256-8-4-AITER_TRITON_MXFP4_BF16]