[ROCm][Perf] Reuse graph-stable attention metadata across Kimi-K3 cache groups - #53301
Closed
JohnQinAMD wants to merge 3 commits into
Closed
JohnQinAMD wants to merge 3 commits into
JohnQinAMD wants to merge 3 commits into
Conversation
JohnQinAMD
requested review from
AndreasKaratzas,
DarkLight1337,
WoosukKwon,
alexm-redhat,
dllehr-amd,
hongxiayang,
njhill,
tjtanaa,
yewentao256,
youkaichao,
ywang96 and
zhuohan123
as code owners
August 21, 2026 17:33
JohnQinAMD
force-pushed
the
upstream-pr/kimi-k3-metadata-reuse
branch
2 times, most recently
from
August 21, 2026 17:41
d751cdb to
d8bf7b9
Compare
JohnQinAMD
marked this pull request as draft
August 21, 2026 18:42
Contributor
|
This pull request has merge conflicts that must be resolved before it can be |
Kimi-K3 has six target MLA cache groups with identical request and query geometry but distinct block tables. Rebuilding the persistent AITER schedule and serially expanding a 327K-token page table for every group consumed about 1 ms per decode step. Full CUDA graphs retain capture-time tensor addresses, so returning the first group metadata object is not safe: later graphs continue reading their own persistent buffers. Share the compatible builders’ read-only numeric schedule tensors before graph capture, then retain group-local page indices and pointer-bearing work metadata. Runtime metadata preparation builds the shared schedule once and only expands each group-specific block table, with long page expansion distributed over token tiles. At TP8 c1 M3 and 327482 tokens, the six-group source microbenchmark improves from 749.364 us to 236.221 us (3.17x, -0.513 ms); three independent minimal-version repeats save 511.2/489.9/508.6 us, median 508.6 us. The full-graph endpoint phase improves MLA metadata from 1.000845 ms to 0.473963 ms per step (-0.526882 ms). Mutated CUDA-graph probes validate shared schedules and group-local page buffers; the two focused test files pass 39 tests. Signed-off-by: Yanyuan Qin <yanyuan.qin@amd.com> Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
Move the Kimi-K3 decode metadata builder to a platform-neutral module and reuse it from ROCm while preserving the ROCm device-side prefill chunk hook. The generic GDN builder spends about 2.69 ms per c1 target step across 14 KDA groups; the specialized builder reduces this to about 1.18 ms in the production endpoint phase measurement. Use num_spec_decodes as the caller contract because the specialized builder intentionally does not materialize spec_sequence_masks. Preserve prefill-only views for mixed regular-decode/prefill batches. Signed-off-by: Yanyuan Qin <yanyuan.qin@amd.com> Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
Kimi-K3 builds the same speculative query offsets and accepted-token counts for 14 KDA cache groups, while only the aligned state indices depend on each group block table. Repeating the full specialized builder therefore leaves more than half a millisecond of c1 pre-target work. Add a V2-only metadata-reuse contract that can fail closed for mixed and prefill batches. Compatible FULL-graph builders share only query-offset and accepted-count buffers before capture. Runtime builds those common values once and launches a small kernel per remaining group to update its graph-local state-index buffer. The legacy block-table update contract remains disabled. At TP8 c1 M3 and sequence length 327482, three independent 14-group source microbenchmarks save 621.1/610.3/597.9 us per step, median 610.3 us, and reduce the specialized builder family by about 3.0x. Mutated FULL-graph replay validates shared common buffers and group-local state buffers; the combined KDA, MLA, and metadata-dispatch test set passes 55 tests. Signed-off-by: Yanyuan Qin <yanyuan.qin@amd.com> Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
JohnQinAMD
force-pushed
the
upstream-pr/kimi-k3-metadata-reuse
branch
from
August 22, 2026 02:21
d8bf7b9 to
8233773
Compare
Contributor
|
This pull request has merge conflicts that must be resolved before it can be |
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.
Purpose
Kimi-K3 on ROCm runs many KV-cache groups over one batch: at TP8, six MLA groups and
fourteen KDA groups. Every group currently builds its own attention metadata, but most
of it describes the batch — query offsets, sequence lengths, speculative offsets, the
split-K schedule — and is identical across groups. Only the page indices and state
indices differ, because only the block table differs.
This builds once per step and, for the remaining groups, redoes only the
block-table-dependent part.
Full CUDA graphs bake tensor addresses at capture, so metadata cannot simply be handed
to another group, and buffers two groups will share must be rebound before capture.
Four hooks, declared on
AttentionMetadataBuilderwith no-op defaults so backends thatdon't opt in are unaffected:
share_reusable_metadata_buffers()— before capture, point compatible groups at oneallocation for the buffers that are read-only during execution.
can_reuse_metadata()— per step; anything it rejects falls back to a normal build.update_block_table()— redo only page/state indices.get_metadata_reuse_key()— extra identity beyond (builder type, kv-cache spec).AITER MLA and Kimi-K3 KDA implement them.
Test Plan
Unit tests, in the upstream image matching this branch's base:
ruff checkandruff format --check(pinned 0.14.0) on the six changed files.Accuracy on 8x MI355X, Kimi-K3 TP8 with a DSpark draft and fp8 KV. Control and candidate
are the same image with only these files swapped in (same approach as #52356); serve
flags follow #51253 / #50619:
Test Result
Unit tests: 72 passed. Two of them are regression tests that fail without this
change: one covers
mamba_cache_mode="none"(the default), where the state column is acontiguous prefix rather than the
alignoffset; the other covers the full-cudagraphbranch of
update_block_table.Lint: clean on all six files.
gsm8k, 200 questions, 5-shot greedy: 0.995 control, 0.995 candidate, both filters.
Metadata build cost (14 KDA groups, 8 requests,
num_speculative_tokens=2),fourteen builds versus one build plus thirteen reuses:
Scope of the claim:
page-index expansion is also flat at ~10.3 us per group from 1K to 262K tokens. It
scales with group count and batch size instead.
num_speculative_tokens=2a step is ~10 ms. Under anum_speculative_tokens=7draft-verify loop a step is ~163 ms and the same saving is ~0.3%.
No serving throughput number is claimed: a single control/candidate pair on this
hardware is within run-to-run drift, and separating them needs alternating arms with a
paired bootstrap.