Skip to content

model : support Kimi-K3 recurrent-state rollback - #28466

Open
soulmachine wants to merge 5 commits into
ggml-org:masterfrom
soulmachine:kimi-k3-rs-rollback
Open

model : support Kimi-K3 recurrent-state rollback#28466
soulmachine wants to merge 5 commits into
ggml-org:masterfrom
soulmachine:kimi-k3-rs-rollback

Conversation

@soulmachine

@soulmachine soulmachine commented Sep 6, 2026

Copy link
Copy Markdown

Overview

Enable bounded recurrent-state rollback for Kimi-K3 during speculative decoding. Kimi-K3 currently has rollback disabled and stores only the final KDA state and Q/K/V convolution windows. Enabling rollback without changing those stores would restore unwritten snapshot groups after rejecting draft tokens.

Save the convolution windows for each rollback position, use the existing build_recurrent_attn helper to save KDA state snapshots, and add Kimi-K3 to llm_arch_supports_rs_rollback.

Closes #28461.

Related: #28019 reports multi-sequence rollback corruption for qwen4exp. The connection to Kimi-K3's missing snapshots is an inference, not a maintainer-confirmed diagnosis. This change is limited to Kimi-K3 and does not resolve that issue.

Additional information

Validation:

  • tests/CMakeLists.txt registers the generated Kimi-K3 model with the existing rollback test. Each registered model runs both zero-filled and 0x3e-filled cache passes in the test executable.
  • CPU Release build on macOS with Apple clang passed. GGML_SCHED_DEBUG_REALLOC=1 ctest --test-dir build-cpu -R 'recurrent-state-rollback' --output-on-failure: 5/5 passed, including model generation and the four rollback tests.
  • NVIDIA Vulkan Debug build on RTX PRO 6000 Blackwell passed the same 5/5 checks with GGML_SCHED_NO_REALLOC=ON and fatal warnings enabled.
  • Both passes passed checkpoint restoration, multi-sequence split replay, and sequence-isolation checks for Qwen3.5, Nemotron-H, DeepSeek-V4, and Kimi-K3. Logit comparisons reject NaN and infinity; sequence-isolation checks matched exactly.

The nonzero pass uses the existing state-writing interface to collect and fill cache buffers entirely within the test. Buffer discovery decodes a full micro-batch to preserve Vulkan's prefill allocation sizes. Production cache initialization uses zeros; the LLAMA_RS_DEBUG_FILL hook has been removed. With only the Kimi-K3 allowlist change, the zero pass succeeded but the nonzero pass failed split replay (max logit difference 2.35e-6, tolerance 1e-7). Both passes succeed with the snapshot writes. Full CI was not run in this targeted validation.

Real-model measurements on September 5 used Kimi-K3 UD-IQ2_XXS on 8x RTX PRO 6000 Blackwell GPUs, with four server slots and seven draft tokens. The RadixArk DSpark draft shared GPU 7 with the target's output weights. These runs used a RelWithDebInfo build based on 4d91760; DSpark also required a separate t_layer_inp registration patch, outside this PR. Throughput is in tok/s:

Workload No speculation DSpark + host checkpoints DSpark + rollback
Rewrite 12.88 17.7-19.6 22.19
Knowledge 12.81 11.9-12.4 15.75
Code 12.62 10.2-10.9 15.65
Benchmark, concurrency 1 (1024 input / 256 output tokens) 10.14 Unavailable 13.98
Benchmark, concurrency 4 18.30 Unavailable 14.92

The rollback configuration was 13-25% faster on rewrite, 27-32% on knowledge, and 44-53% on code than the recorded host-checkpoint ranges. However, fit margins and model placement differed: the target's host model buffer was 5419.75 MiB with host checkpoints and 11010.12 MiB with rollback. These gains are not from a placement-controlled A/B.

Host-checkpoint results are unavailable for the concurrency benchmarks, so those rows cannot isolate rollback's contribution. Compared with no speculation, the combined DSpark and rollback configuration reduced TPOT from 77.7 to 49.2 ms at concurrency 1, but increased it from 134.5 to 220.6 ms at concurrency 4. These runs used random token inputs, disabled prompt caching, and four requests per concurrency slot.

Greedy outputs matched between DSpark with host checkpoints and DSpark with rollback on the three probe prompts. The rewrite output differed from the no-speculation run; knowledge and code outputs matched all three configurations. This does not establish output equivalence between DSpark and no speculation.

Snapshot storage multiplies recurrent-state memory by 1 + n_rs_seq: the recorded four-slot cache grew from 1772.44 to 14179.50 MiB with seven rollback positions.

Requirements

  • I have read and agree with the contributing guidelines
  • AI usage disclosure: YES - AI assisted with implementation, investigation, and validation. Codex drafted the commit message and this description from the patch and recorded results.

@github-actions github-actions Bot added model Model specific testing Everything test related labels Sep 6, 2026
Enable Kimi-K3 in the recurrent-rollback allowlist.
Save Q/K/V convolution windows for each rollback position.
Reuse the recurrent-attention helper to snapshot KDA state.

Refs: ggml-org#28461
@CISC

CISC commented Sep 6, 2026

Copy link
Copy Markdown
Member

Thank you, reduce the comments though please.

Comment thread tests/CMakeLists.txt Outdated
@soulmachine

Copy link
Copy Markdown
Author

@CISC Shortened the code comments in eff6894, keeping the rollback invariant and test rationale.

Comment thread src/llama-memory-recurrent.cpp Outdated
@soulmachine

soulmachine commented Sep 7, 2026

Copy link
Copy Markdown
Author

@ggerganov Could you review the latest fix and approve the pending CI runs when you have a chance? The Vulkan test failure is fixed in 1ffc6ac; targeted CPU and NVIDIA Vulkan checks pass (5/5 each). Thanks!

A one-token cache-discovery decode made Vulkan reallocate during the larger multi-sequence prefill, triggering GGML_SCHED_NO_REALLOC. Decode a full runtime ubatch before collecting and filling cache buffers.

CPU and NVIDIA Vulkan rollback checks pass (5/5 each) with the reallocation guard enabled. The nonzero-fill pass still catches the original missing-snapshot implementation.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

model Model specific testing Everything test related

Projects

None yet

Development

Successfully merging this pull request may close these issues.

model: support bounded recurrent-state rollback for Kimi-K3

3 participants