Repository navigation
[ROCm] Swap the unified-attention 2D grid order on gfx1151 - #1289
Closed
roberteg16 wants to merge 1 commit into
Closed
roberteg16 wants to merge 1 commit into
roberteg16 wants to merge 1 commit into
Conversation
gfx1151 schedules the 2D kernel better when the KV head is the fastest varying grid axis rather than the query block. The kernel gains a USE_SWAPPED_GRID constexpr, defaulting to False, so every other platform compiles and launches exactly what it does today. head_size 64 regresses under the swapped order, so _use_swapped_grid draws the line at 80. The swap only relabels which grid axis carries which index: every program still computes the same (q_block, kv_head) pair and accumulates over KV in the same order, so the result is unchanged bit for bit. Verified on a 3968 token Qwen3-8B-shaped prefill, torch.equal over the full output tensor. Measured on gfx1151 (Radeon 8060S) with benchmarks/attention_benchmarks, against the same tree with the swap disabled. This is a kernel-level harness on synthetic tensors: the configs carry only head geometry, no weights are loaded, and the model names below are shorthand for that geometry. Attention kernel time, 20 repeats after 10 warm-up iterations: Qwen3-1.7B q8k 14.80 ms -> 11.28 ms +31.1% Llama-2-7B q8k 107.54 ms -> 93.59 ms +14.9% Qwen2.5-7B-AWQ q3968s4096 5.59 ms -> 4.99 ms +12.0% Qwen3-1.7B q3968s4k 3.15 ms -> 2.96 ms +6.4% Qwen3-8B q3968s4096 6.19 ms -> 5.90 ms +5.0% Qwen3-Omni-30B q8k 36.33 ms -> 34.71 ms +4.7% A second independent A/B pass reproduced these within about a percentage point, except Qwen3-1.7B q8k, which came out at +40.9% with a much wider spread; the +31.1% above is the conservative reading. The Qwen3-8B geometry is present in the matrix twice under two names, so it is really four measurements spanning +3.8% to +5.0%. Two shapes lose. Llama-2-7B at q1920s2k costs 2.3% (4.7% on the second pass), while the same model at q8k gains 15%: the win needs a long enough sequence to amortise the reordered scheduling. Qwen3-4B-AWQ at q4000s4128 is 1.4% down, inside the noise band but consistent across both passes, and it sits exactly on the head_size 80 boundary. Everything else is flat, decode included: the swap is gated on the 2D path. Co-authored-by: Claude <noreply@anthropic.com> Signed-off-by: Robert Esclapez Garcia <robert.garcia@amd.com>
roberteg16
force-pushed
the
rocm-swapped-grid
branch
from
September 10, 2026 10:15
d0b2eb5 to
9bc3ddc
Compare
Author
|
Upstream PR vllm-project#56253 |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
On gfx1151 the 2D unified-attention kernel schedules better when the KV head is the fastest varying grid axis rather than the query block. This launches the 2D grid as
(kv_heads, q_blocks)there, worth up to 31% of attention kernel time on long prefill.The kernel gains a
USE_SWAPPED_GRIDconstexpr defaulting toFalse, so every other platform compiles and launches exactly what it does today. The whole change is 2 lines of existing code plus the new gating helper.Base
This is stacked on
rocm-2d-launch-config, so the diff here shows only the swap. It is textually independent of that series — they share no hunks — but the swap is only meaningful on top of it: without the 2D launch tuning gfx11 does not route toTRITON_ATTNat all, and thehead_size >= 80boundary is the one that series already established.Output is unchanged, bit for bit
The swap only relabels which grid axis carries which index. Every program still computes the same
(q_block, kv_head)pair and accumulates over KV in the same order, so there is no reassociation and no change in results — unlike the tile/block-size tuning in the base series, which does alter reduction blocking.Verified rather than asserted: a 3968-token Qwen3-8B-shaped prefill run with the swap on and off produces outputs that are
torch.equalover the full[3968, 32, 128]tensor (max abs diff 0.0, zero differing elements).Results
These are kernel microbenchmarks.
benchmarks/attention_benchmarksoperates on synthetic tensors; the configs carry only head geometry (num_q_heads,num_kv_heads,head_dim,block_size) and load no weights. The model names are shorthand for that geometry — quantization labels in particular have no effect here.q8kq8kq3968s4096q3968s4kq3968s4096q8kq1920s2kq4000s4128Testing
AI assistance
This change was prepared with AI assistance (Claude). Every line was reviewed by the submitter, and the measurements above were run and checked by hand.