Repository navigation
Conversation
Signed-off-by: Johnny-Liou <a897111@gmail.com>
…che, write_pos) Signed-off-by: Johnny-Liou <a897111@gmail.com>
Signed-off-by: Johnny-Liou <a897111@gmail.com>
Signed-off-by: Johnny-Liou <a897111@gmail.com>
…ySSM The GDN ring shape and dtype came from combined helpers that each model branched into on both the layer path and the config path, the pattern the Mamba2 sub-PR removed. Replace them with append_gated_delta_net_replayssm_ring on each calculator, called by both paths so the config-path page size cannot drift from the layer-path allocation. The five-tensor shape and dtypes are unchanged. Add the SupportsReplaySSM capability to the Qwen3.5 GDN classes so validate_mamba_cached_kernel admits cached decode: Qwen3_5ForCausalLMBase for the text-only dense/MoE arches and Qwen3_5ForConditionalGeneration for the multimodal ones, each with MoE inheriting. Both config paths append the ring, matching the layer path they share. Reword the rejection message that named only Nemotron-H and extend the registry test to all four arches. Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Co-authored-by: Claude Opus 5 <noreply@anthropic.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
The GDN builder derived write_pos from num_prompt_tokens_cpu, which the Mamba2 sub-PR dropped after finding the value wrong across preemption: a resumed request replays prompt+generated through prefill and writes a fresh checkpoint state, so counting write_pos from the prompt boundary folds a stale ring onto a current checkpoint and corrupts the output. Read replayssm_decode_base_cpu, which anchors at the ring's last full-state write, so a resumed request decodes from write_pos 0. The shared plumbing arrived with the rebase; only the GDN builder consumed the old field. Add write_pos cases to test_gdn_metadata_builder.py covering fresh, flush-boundary, wrap, and the resume re-anchor. Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
The cached decode kernel derived its flush flag from write_pos == L - 1, which only materializes the checkpoint on a full buffer. Prefix caching in align mode needs the exact state at each mamba block boundary, so make is_flush a per-row kernel input. The metadata builder re-anchors the ring at each block start (effective_base = max(decode_base, block_start)) and forces a flush on the step that completes a block; the flush branch already rebuilds from the committed ring window, so a mid-buffer flush is correct. A single-token prompt step replayed as decode (num_computed < decode_base) now takes a one-token flush off the checkpoint instead of raising, matching the baseline decode for that row. Extends the GDN kernel and metadata-builder tests to cover is_flush, the align re-anchor, the block-boundary flush, and the leftover-prompt row. Signed-off-by: Johnny-Liou <a897111@gmail.com>
Signed-off-by: Johnny-Liou <a897111@gmail.com>
Rename the GDN mixer and metadata-builder attributes to match the two config flags: use_cache_kernel / use_cached_kernel become use_replayssm, and max_cache_len becomes replayssm_buffer_len (None when ReplaySSM is off). The leaf kernel op keeps its local max_cache_len parameter. Refresh the launch-config module docstring, which named only the Mamba2 kernel, and document the GDN config tuple (block_v, num_warps, num_stages, nk). Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
Under use_replayssm the GDN builder splits with treat_short_extends_as_decodes=False, which sends a still-prefilling single-token row to the prefill group. FULL-cudagraph dispatch is shape-based, so a batch of all-1-token queries containing a final 1-token prefill chunk still replays the decode graph, while num_prefills > 0 skips the persistent-buffer refresh. The replayed graph then reads last step's state indices, ring cursor, and flush flag, which corrupts the output and the checkpoint without raising. Clear is_prefilling for single-token rows that have prior state before the split, as mamba_attn.py does. Those rows stay decodes, num_prefills stays 0, and the write-position derivation turns them into one-token flushes off the exact checkpoint, which matches the baseline because a row that has never decoded has an empty ring. Rows with seq_lens == 1 have no prior state and stay prefills. Add two builder cases: a full-cudagraph batch mixing a decode with a final 1-token prefill chunk, asserting the row lands in the decode group and the cursors come from the captured buffers, and a first-token prefill that must stay a prefill. Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
Every align-mode write_pos case used block_size == replayssm_buffer_len == 16, so the block anchor and the ring period were indistinguishable. Parameterize block_size per case and add one with block_size 64: decode_base wins over the block start while the prefill ended mid-block, the block-completing step flushes mid-ring, and the next step re-anchors once that boundary holds the checkpoint. Mid-block prefill ends became reachable when vllm-project#50000 replaced the align-mode block_size <= max_num_batched_tokens assert with sub-block progress, so note why the anchor takes the max rather than the block start. Co-authored-by: Claude Opus 5 <noreply@anthropic.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
Use sequence and query lengths for ring positions. Handle five-tensor GDN caches, reject FlashInfer GDN replay, and keep KDA RecoverSSM separate. Co-authored-by: OpenAI Codex <noreply@openai.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
Cover one-token flushes and use production FP16 ring storage in BF16 tests. Account for BF16 state rounding between flushes. Co-authored-by: OpenAI Codex <noreply@openai.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
Use the supported runner in parity tests and benchmarks. Keep FlashInfer V2 tests on Mamba2 and add GDN prefix-cache parity at TP2. Co-authored-by: OpenAI Codex <noreply@openai.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Signed-off-by: Johnny-Liou <a897111@gmail.com>
Forward the batch-ordered prefill endpoint to the existing GDN metadata builder so V2 can derive ReplaySSM ring positions without GPU host reads. Preserve other-model guards and cover compiled V2 with regression tests. Depends on vllm-project#62004. The parent keeps the original authors' ReplaySSM commits unchanged; this commit adds only the V2 adapter. Co-authored-by: Codex <noreply@openai.com> Signed-off-by: wunnii9 <1515543516@qq.com>
|
Documentation preview: https://vllm--64699.org.readthedocs.build/en/64699/ |
|
👋 Hi! Thank you for contributing to the vLLM project. 💬 Join our developer Slack at https://slack.vllm.ai to discuss your PR in PRs do not trigger a full CI run by default. Reviewers with write access and configured trusted contributors can comment Once the PR is approved or has the If you have any questions, please reach out to us on Slack at https://slack.vllm.ai. Agent GuidelinesIMPORTANT: 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. 🚀 |
|
This pull request has merge conflicts that must be resolved before it can be |
Overview
Enable Qwen3.5 GDN standard-decode ReplaySSM on Model Runner V2 by forwarding each request's decode origin to the existing GDN metadata builder.
Stacked on #62004 at
3c8678368a6358cea60db7841a5cca7c3263ce69; draft until that dependency lands. Only the final commit is new. All preceding ReplaySSM commits retain their original authors and SHAs. This adapter adds no ReplaySSM kernel or Skinny GEMM implementation.Claims
qwen3_5_text, preserving the guard for other models.prefill_len_np, including resumed-request endpoints, asreplayssm_decode_base_cpu; zero-fill graph padding.Validation
Single GB10 (SM121), Qwen3.5-4B BF16, FP32 state, TP=1, L16, no speculative decoding or prefix caching.
The proposed branch is tested on the real #62004 head. Offline fixtures use the available local checkpoint configuration; submitted tests contain no local paths. Test commands:
On the final dependency-head branch: 128 passed, 551 deselected; full
pre-commit runand commit hooks pass. The compiled V2 engine comparison ran withVLLM_GPU_SYNC_CHECK=error. Tests completed without failures. The earlier standalone checkout had 131 passing cases; the count changes because the real dependency head contains a different upstream test revision.The V2 engine case explicitly uses compilation mode 3, Breakable off, graph capture size 4, and two prompts with up to 32 output tokens, exercising L16 flushes. It uses the existing parity helper: identical greedy tokens, or mutual top-five membership at the first divergence. This is a limited output regression, not full-vocabulary equivalence or GSM8K/MMLU evaluation.
Earlier standalone validation also passed 24/24 arithmetic checks, C1/C8 generation, and 32/32 mixed requests under GPU sync checking. Historical experiment on main
a9fe30e9f6plus #62004, both runners compiled with Breakable off, 512 input / 128 output tokens:Three rounds per condition, one startup per runner; C1 four requests per round and C64 one burst of 64. TPOT ranges: C1 V1 48.184–48.368 / V2 48.056–48.130; C64 V1 77.369–77.761 / V2 75.083–75.260 ms. These historical measurements support the compiled V2 path on this workload; they are not a fresh benchmark of this exact dependency-head branch. That benchmark build contained a disabled Skinny hook, absent here.
Details
Relaxing the V2 configuration guard alone leaves the GDN builder without its required CPU decode base. V2 already gathers the prefill endpoint in batch order and refreshes it after preemption. Forwarding a per-step CPU snapshot supplies the builder's existing cursor calculation while keeping request-state ownership in V2. Tests cover a flush boundary, resume origin, final single-token prompt chunk, null graph padding, and persistent device-buffer reuse.
This extends #62004, whose stated scope excludes V2. Related RecoverSSM speculative decoding and Mamba2 FlashInfer lifecycle PRs address different paths. Duplicate searches on 2026-10-30 (
62004 in:body,ReplaySSM V2, and GDN standard-decode keywords) found no existing open PR implementing this adapter. #62004 explicitly lists Model Runner V2 as out of scope.Standard decoding on one GB10 is validated. Other models, TP>1, V2 align-mode prefix caching, and speculative decoding remain outside this validation. The adapter preserves the kernel mathematics and existing compilation defaults.
AI assistance was used: OpenAI Codex assisted with investigation, implementation, test execution, and this description. Tests were executed by Codex at the submitter's explicit request.
Pull Request Checklist
/pr-checklistskill. (Mandatory for agents, optional for humans).