Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 11 additions & 11 deletions .agents/NOW.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ benchmark record. Budget: 100 lines.

## Live claims

Work: exact-chunks on main `1ce0d662b`; sm_120 measured at `3d2581551`.
Work: #127 rebased on main `c05cee1d2`; opt-in post-conv and K4 conv follow-ons.

| Claim / track | State | Next command or step |
|---|---|---|
Expand All @@ -19,7 +19,7 @@ Work: exact-chunks on main `1ce0d662b`; sm_120 measured at `3d2581551`.
| MiniMax-H3 lane | **bf16 shards STREAM both towers (DiT + encoder); Q4_K_M enc cond cos 0.9975, 3.5° med, DIFFUSE** | render A/B on saved embeds |
| Kimi-Linear-48B | **ROW 7 fold LANDS (#122 §21): engine==CLI 128/128; golden 122/128; SACRED green; v13 tokens ABI** | ACTIVE: 19.0 tok/s vs vLLM ~21 (~0.90×) |
| 35B fresh grid | **BOUND** @`1ea26427`: 0.93-1.03x, c16 0.93x. INTAKE + Option A both NEGATIVE | Lever left: prefill glue (#61) |
| Qwen3.5-4B sm_120 | Exact chunks ON: rebased-main reprofile 3.072x kernel / +2.272% run; sealed-vLLM throughput 1.021x PASS. Latency/VRAM OPEN | Spike residual 1.609x conv gap |
| Qwen3.5-4B sm_120 | Exact chunks ON 3.072x. Post-conv tile 1.859x. K4 conv arm 1 opt-in: exact, 6.44%; 256-channel arm falsified | Repeat A/B; 27B/35B gates unavailable |
| RPi5 A76 CPU | **R5 asm GREEN; llama NOT MET**: 0.461x pf, 0.653x dec, RSS -24% | W6: BF16 GEMM |
| MXFP4 parity | c1 1.020, c2-c8 0.962-0.969. **#82 CLOSED: ptxas-lineage REFUTED (A/B ties our+vLLM PTX all ptxas/JIT; +10us=engine context, not codegen)** | TERMINAL: at parity |
| ROW-SERVE-ASYNC-DENSE-MIRROR | **LANDED+dgx-VERIFIED** (`f9c969ae`): async mirror on classic dense Qwen3; SACRED 184/184 | Residual: sibling scope one-liner |
Expand All @@ -45,18 +45,19 @@ both gate models, reproduced 2–3x on an idle box. See [gates.md](gates.md) and

## Next actions

0. **`ROAD-V1-MEM`** KV auto-sizing spike LANDED (`specs/kv-sizing.md`, `READY`).
0. **`ROAD-V1-MEM` M1+M2 LANDED:** `--kv-cache-memory` + group-aware divisor;
M3 profile run is dgx-gated.
1. **Spike the Parakeet encoder row** (vLLM carries it inside
`nano_nemotron_vl.py`; the transducer half is NOT in vLLM: separate call).
2. **Qwen3.5-4B sm_120:** rebased branch is GREEN and reprofiled. Spike the
residual 1.609x conv gap; latency/VRAM and gate models stay open.
2. **Merge the invocation-parity prevention** (CI guard + AGENTS.md checklist);
2. **Qwen3.5-4B sm_120:** post-conv and K4 conv are exact/local-positive but
opt-in; repeat A/B or divide the remaining causal-conv residual further.
3. **Merge the invocation-parity prevention** (CI guard + AGENTS.md checklist);
CUDA build-verify the byte-exact `kGemvHeuristicAlgos` refactor on dgx.
3. **Same-tool re-verify deepseek_v4's bf16 resident tower** (the one other
4. **Same-tool re-verify deepseek_v4's bf16 resident tower** (the one other
f32-out caller) once the Laguna fix proves the mechanism.
4. **Restore `local-ai-worker`** on dgx when the GPU campaign ends
5. **Restore `local-ai-worker`** on dgx when the GPU campaign ends
(`docker update --restart=always` + `docker start`).
5. **Protocol substrate — partly done.** Triage/audit + `STATUS.md` ratchet +
6. **Protocol substrate — partly done.** Triage/audit + `STATUS.md` ratchet +
`AGENTS.md` tiering DONE. REMAINING: anchor backfill (6 model rows need a
DECISION); record-era rollover BLOCKED on `DONE` rows bound to
`parity-ledger.md` LINE anchors (re-anchor by ROW ID).
Expand All @@ -81,7 +82,6 @@ rows**; llama.cpp's 11 extra devices IN SCOPE, spike-gated (`ROAD-V1-D6`).
- Mirror vLLM; never ask how a feature should behave.
- `nsys` BOTH sides, SAME tool, before any perf claim; cross-tool comparisons
never establish invocation parity; whole-run sums mix prefill.
- GPU: park `local-ai-worker`, flock `$HOME/gpu.lock`, single-load
steady-state, never reload per rep, named tmux.
- GPU: flock `/tmp/gpu`; use the 22/25 GiB user-systemd scope; single-load reps.
- Never weaken a checker to pass; repair the record.
- Feature code needs a `row/*` PR (enforced); integration paths push direct.
115 changes: 115 additions & 0 deletions .agents/benchmark-record.md
Original file line number Diff line number Diff line change
Expand Up @@ -16054,3 +16054,118 @@ Rollback is 1728 calls / 718.704016 ms / 415.917 us; exact is 1728 /
27-commit main advance; against the sealed vLLM conv trace the residual is
**1.60881x**. Trace SHA-256: rollback `6a5dde18e...f97c47`, exact
`f47fb9cc...7aecf9`; both token files `83fcdc45...453545`.

## 2026-08-08 — sm_120 fused GDN post-conv 16-token tile: 1.859x kernel, byte-exact

**Disposition:** IMPLEMENTED as opt-in `VT_GDN_POSTCONV_TOKEN_TILE=1`.
Locally positive and token-safe; default and release-model gates remain open.

**Selection and falsification.** On exact-chunks `c3bb0f39a`, the accepted
Qwen3.5-4B/c32/1,280-block graph-node trace measured fast megablock
228.150171 ms and the existing per-V-head split 448.364941 ms across 1,728
calls. Both token files were identical. The split is 1.965x slower and the
enclosing run 0.97% slower, so V-only launch decomposition is rejected.
Pinned vLLM's same-tool `_fused_post_conv_kernel` is 108.034870 ms across 1,923
calls. Source comparison instead selected vLLM/FLA's 16-token, per-head,
four-warp schedule and Q/K register reuse.

**Implementation and numerical mutant.** `GdnPostConvTokenTileKernel` maps one
block to `(16 tokens, one Q/K or V head)` and one warp to four tokens. Each Q/K
lane retains features `lane+{0,32,64,96}` across normalization. The first
implementation summed those four squares sequentially before a warp reduction:
kernel time improved 227.731960→122.472980 ms and enclosing throughput
6731.69→6773.85 tok/s, but the tile token SHA
`1d496ff0f989978155d8e900c7a5500a43db26816dead8e035310d0bf9cb9756`
did not match fast `83fcdc45...453545`; REJECTED. Reproducing the current
128-lane tree exactly—`(i+i+64)`, then `(i+i+32)`, then shuffle offsets
16/8/4/2/1—restored byte identity without restoring the reload/barrier costs.

**Final same-binary profile.** One `/tmp/gpu` lock, 22/25 GiB user-systemd
scope, `--cuda-graph-trace=node`, identical production workload and binary:

| Axis | fast megablock | token tile | change |
|---|---:|---:|---:|
| post-conv GPU total, 1,728 calls | 227.887066 ms | **122.587027 ms** | **1.858982x faster** |
| mean post-conv call | 131.879 us | **70.942 us** | **46.21% lower** |
| total throughput | 6734.82 tok/s | **6770.62 tok/s** | **+0.532%** |
| output throughput | 744.72 tok/s | **748.68 tok/s** | **+0.532%** |
| TTFT | 1024.14 ms | **1015.43 ms** | **-0.850%** |
| TPOT / ITL | 35.01 ms | **34.85 ms** | **-0.457%** |
| E2E | 5469.87 ms | **5440.81 ms** | **-0.531%** |

The vLLM kernel residual is now **1.134699x**, down from 2.112x. Final token
files are identical, full SHA-256
`83fcdc45f79ddb06a634c7d7d95eba3384543b3cd781a45a8db1fc4e2a453545`.
Portable flag/grid tests pass 6/6·50; CUDA GDN passes 67/67·4384 including
partial/exact tiles, packed BA non-zero views/wider row strides, byte-exact five
outputs, finiteness and norms; cached Qwen3.5-4B passes 3/3·1672.

**Evidence.** Final fast/tile traces
`/tmp/qwen35-postconv-tile-exact-{fast,tile}.nsys-rep`, SHA-256
`c75e2cb...bcadc` / `a0eb1808...f418`; token files beside them. Rejected
arithmetic traces `/tmp/qwen35-postconv-tile-wip-{fast,tile}.nsys-rep`, SHA-256
`c2d8872e...b774` / `1c42d489...d66b`. Selection traces and exact recipes are
in [the spike/result](specs/sm120-qwen35-postconv-token-tile-2026-08-08.md).
One local profile is not extrapolated to the unavailable Qwen3.6-27B/35B gates;
the flag therefore remains opt-in.

## 2026-08-08 — sm_120 causal-conv residual: K=4 specialization wins; 256-channel tile falsified

**Disposition:** arm 1 is IMPLEMENTED, byte-exact and locally positive behind
`VT_CONV_CHANNEL_TILE=1`; arm 2 (`=2`) is retained as an explicit falsified
experiment. Unset/`0` remains the default pending repeated and release-model
gates.

**Divide-and-conquer selection.** Fresh current-main/post-conv tracing measured
causal conv 234.255 ms versus pinned-vLLM 145.532 ms, while post-conv's
remaining excess was only 14.476 ms. Grouping causal-conv launches by grid
showed the 279/280-program waves consumed 136.189 ms (58.1%). Local used 64
feature blocks and runtime width at 43 registers/thread; vLLM used `BLOCK_N=256`,
32 feature blocks and compile-time width at 32 registers/thread. The spike split
those differences into arm 1 (compile-time K=4, unchanged 64 blocks) and arm 2
(K=4 plus two channels/thread, 32 blocks).

**Correctness/review finding.** A serial-stripe arm 2 corrupted the second
stripe when an exact final-chunk block wrote state before stripe 2 loaded initial
history; the CUDA matrix caught it and the accepted kernel preloads both stripes.
Fresh mutation review then found byte comparisons could stay green when a whole
specialized dispatch branch was deleted. A fresh fix routes production through
the same portable callback dispatcher the tests mutate. Scoped re-review killed
arm-1 deletion, arm-2 deletion, relaxed arm-2 parsing and removed non-K4 fallback.
Final gates: portable 9/9·88, CUDA GDN 67/67·4631, paged-forward 4/4·8.

**VOID series.** `/tmp/qwen35-conv-arm{0,1,2}-565a26fcc.*` is invalid for
selection: the test executables had rebuilt but `vllm-bench` had not relinked.
All three traces proved the old runtime kernel/grid/registers ran. This was
caught structurally before timing interpretation.

**Accepted rebuilt same-binary profile.** One GPU lock, 22/25 GiB user-systemd
scope, exact c32 workload and `--cuda-graph-trace=node`:

| Axis | arm 0 runtime | arm 1 K4x1 | arm 2 K4x2 |
|---|---:|---:|---:|
| kernel / grid / registers | runtime / 64 / 43 | K4<1> / 64 / 52 | K4<2> / 32 / 58 |
| causal-conv total, 1,728 calls | 234.604587 ms | **219.506425 ms** | 228.400830 ms |
| 279-program mean | 149.546 us | **140.133 us** | 145.586 us |
| 280-program mean | 149.480 us | **139.982 us** | 145.468 us |
| total throughput | 6759.39 tok/s | **6767.62 tok/s** | 6757.19 tok/s |
| output throughput | 747.43 tok/s | **748.34 tok/s** | 747.19 tok/s |
| TTFT | 1016.69 ms | **1013.82 ms** | 1017.61 ms |
| TPOT / ITL | 34.91 ms | **34.88 ms** | 34.91 ms |
| E2E | 5449.87 ms | **5443.16 ms** | 5451.66 ms |

Arm 1 improves conv **6.4356%**, with every enclosing axis positive but small.
It leaves a **1.5083x** same-tool vLLM conv residual. Register count rises rather
than falls, falsifying the occupancy rationale; compile-time removal of runtime
width work is the supported cause. Arm 2 improves only 2.6443% versus baseline,
is **4.0520% slower than arm 1**, and is neutral/slightly negative end to end:
halving blocks does not repay duplicated channel-local register state on sm_120.

All accepted token files SHA-256
`83fcdc45f79ddb06a634c7d7d95eba3384543b3cd781a45a8db1fc4e2a453545`.
Report SHA-256 arm0/arm1/arm2:
`39d383dd878fc340a3cfaaee79a4addcb4eccb181439e9b4725f724f4569a6eb`,
`c8799ac0b4cdf997d383fe8a690b223be882dce3b1ee1a6fff35a62d75f7cf85`,
`3d38793571539864b23688fd9a85966debbf1e7c48fe8a1a2509438a45ee0452`.
Full recipe and decision:
[structured spike/result](specs/sm120-qwen35-conv-channel-tile-2026-08-08.md).
23 changes: 23 additions & 0 deletions .agents/kernel-matrix.md
Original file line number Diff line number Diff line change
Expand Up @@ -172,6 +172,29 @@ and the profiled enclosing workload improves **2.272%**; pinned vLLM remains
Lifecycle stays `INVENTORIED` because generic Mamba coverage and the 27B/35B
release gates are unchanged. [Spec and evidence](specs/sm120-qwen35-conv-chunking-2026-08-07.md).

**2026-08-08 `KERNEL-SSM-MAMBA` checkpoint.** The opt-in
`VT_GDN_POSTCONV_TOKEN_TILE` path ports vLLM/FLA's 16-token, per-head,
four-warp post-conv schedule for 128-wide Q/K/V heads. It preserves the current
128-lane reduction tree exactly while retaining Q/K values in registers.
Qwen3.5-4B sm_120 graph-node time is **227.887→122.587 ms (1.859x)** with
byte-identical production tokens and every enclosing axis positive; the
same-tool vLLM residual is **1.135x**. Portable 6/6, CUDA GDN 67/67·4384 and
cached 4B 3/3·1672 pass. It remains opt-in pending repeated and 27B/35B gates;
generic Mamba lifecycle stays `INVENTORIED`.
[Spike and result](specs/sm120-qwen35-postconv-token-tile-2026-08-08.md).

**2026-08-08 `KERNEL-SSM-MAMBA` causal-conv residual checkpoint.** The
opt-in width-four, one-channel arm removes runtime-width work at the unchanged
64-block feature grid and is byte-exact. Qwen3.5-4B sm_120 graph-node time is
**234.605→219.506 ms (-6.44%)**; dominant waves improve about 149.5→140.1 us
and every observed enclosing axis is slightly positive. CUPTI registers rise
43→52, so the win is not occupancy. The separately measured 256-channel arm
halves the grid but rises to 58 registers and is 4.05% slower than the K4
one-channel arm; that hypothesis is falsified. Portable 9/9·88, CUDA GDN
67/67·4631 and paged-forward 4/4·8 pass. Arm 1 remains opt-in; generic Mamba
lifecycle stays `INVENTORIED`.
[Spike and result](specs/sm120-qwen35-conv-channel-tile-2026-08-08.md).

## Count invariants

- This table has exactly 35 practical kernel-family rows.
Expand Down
2 changes: 2 additions & 0 deletions .agents/parity-ledger.md
Original file line number Diff line number Diff line change
Expand Up @@ -932,3 +932,5 @@ Columns:
| 2026-08-06 (`KERNEL-CPU-A76-Q8-DOT` R4-R5; `CLAIM-KERNEL-CPU-A76-Q8-DOT`; physical RPi5 Cortex-A76; closing commit: this checkpoint) | Adds an exact-order ACLE SDOT control and an original AAPCS64 two-block Q8_0×Q8_0 leaf behind Linux DotProd/MIDR dispatch. `auto` selects assembly only on Cortex-A76+DotProd; x86, non-DotProd and other Arm CPUs retain portable dispatch. Explicit `portable`/`sdot`/`a76-asm` same-binary controls remain. ARM64 builds/tests locally through buildx/QEMU; Pi is execution-only. | The integer structure is informed by llama.cpp `237ad9b96` `ggml/src/ggml-cpu/arch/arm/quants.c:1076-1160`, while this port deliberately retains the local portable function's per-block f32 reduction order. vLLM `555967922` supplies Qwen3.5 semantics, not a corresponding CPU microkernel. Local anchors: `src/vt/cpu/cpu_quant_dot_{sdot.cpp,a76.S}`, Q8 dispatch in `cpu_quant_dot.cpp`, direct tests in `tests/vt/test_ops_quant_dot.cpp`, and [immutable evidence](../docs/bench-evidence/rpi5-a76-q8-dot-20260806.md). | **PASS for the compiler-gap/component gate; row `GATING`, `benchmark_binding=true`.** Final binaries `9eb57cf...`/`a94dad30...`; QEMU focused suite 20/20, 150258 assertions; physical-Pi checksums exact. Assembly vs compiler SDOT wall/cycles/instructions: M1/T1 +3.66%/+3.17%/+10.10%, M128/T1 +5.08%/+4.61%/+10.24%, M128/T4 +3.69%/+3.69%/+9.74%. M1/T4 is an explicit −2.43% wall/−4.32% cycles residual despite 8.77% fewer instructions. All 64 Qwen tokens equal the x86 golden in all nine runs; median assembly vs SDOT TTFT −1.55%, TPOT −0.05% neutral, E2E −0.13%. Disassembly proves GCC's framed dependent one-block loop versus the stack-free independent two-block schedule. Same-file Pi llama.cpp, peak memory and concurrency remain `PENDING`; no competitor-floor binding is claimed. |
| 2026-08-06 (`KERNEL-CPU-A76-Q8-DOT` R6 competitor checkpoint; physical RPi5 Cortex-A76; lifecycle remains `GATING`; closing commit: this checkpoint) | Measures the separate four-core A76 same-file llama.cpp floor after the assembly leaf became default. No production code changes. The vllm.cpp nominal p16 request measures 17 input tokens, so the binding competitor uses pp17/tg64/pp17+tg64. A same-text CLI arm verifies 64-token greedy output equality. | Official llama.cpp tag b9892 `ee445f93d` reconstructed under QEMU because historical recorded fork object `237ad9b96` is unavailable; exact recorded anchors match (`quants.c:400`, `arch/arm/quants.c:1076`, `repack.cpp:2725`, `qwen35.cpp`). Local evidence: [Pi competitor record](../docs/bench-evidence/rpi5-a76-llamacpp-20260806.md). | **CORRECTNESS PASS, PERFORMANCE NOT MET, `benchmark_binding=true`.** Three clean unthrottled vllm.cpp reps: prefill 12.81 tok/s, decode 2.55 tok/s, output-equivalent E2E 2.46 tok/s, E2E 26,018.39 ms. llama.cpp three-sample p17/tg64/combined: 27.77 / 3.91 / 3.77 tok/s, E2E 16,998.49 ms. vllm.cpp ratios 0.461x prefill / 0.653x decode+E2E; peak RSS wins 2.841 vs 3.747 GiB (24.2% less). Same-text normalized output SHA `a5a630d7...` equal; all vllm performance tokens retain golden SHA `0ec98e...`. Intrusive 50 ms forked sampler run VOID; accepted timing has no sampler, RSS sampled separately at 1 Hz. Next lever: fresh both-engine profile, then BF16 GEMM; M1/T4 and concurrency remain. |
| 2026-08-07 (`SERVE-CLI-BENCH` + `KERNEL-SSM-MAMBA`; clean sm_120 exact-chunk transplant; local-4B binding only) | Makes the benchmark use production `AsyncLLM`, then ports vLLM's exact `(sequence, BLOCK_M=8 token chunk)` descriptors into shared GDN step metadata and maps one CUDA register-kernel program to each descriptor. `VT_CONV_EXACT_CHUNKS` defaults ON with a same-binary `=0` rollback; `VT_CONV_REG=0` retains tiled/scalar. | Pinned vLLM engine-core queued dispatch `vllm/v1/engine/core.py:200-231,622-669` and causal-conv descriptor mapping `causal_conv1d.py:15-28,71-79,123-124`; local anchors `examples/bench/bench_core.h`, `gdn_attn.{h,cpp}`, `qwen3_5.cpp`, `ops.{h,cpp}`, `cuda_gdn.cu`; [spike/result](specs/sm120-qwen35-conv-chunking-2026-08-07.md). | **ACCEPTED + REBASED-MAIN REPRODUCED.** Contained rebuild; CPU 6/6, CUDA GDN 66/66·4300, cached 4B 3/3·1672; exact/rollback token files identical. On `3d2581551` over `upstream/main` `48a54141f`, same-binary `nsys` reproduces conv **718.704→233.955 ms = 3.072x** and profiled total **6589.65→6739.34 tok/s = +2.272%**; vLLM 145.421 ms leaves **1.609x**. Binding three-pair A/B remains total/output **+2.152%**, TTFT **-2.945%**, TPOT **-1.920%**, E2E **-2.118%**, VRAM unchanged. Sealed-vLLM throughput **1.021246x PASS**; latency/VRAM OPEN. No gate-model extrapolation. [Evidence](../docs/bench-evidence/qwen35-4b-sm120-main-20260807.md). |
| 2026-08-08 (`KERNEL-SSM-MAMBA`; sm_120 post-conv tile; local-4B only) | Adds opt-in `GdnPostConvTokenTileKernel`: vLLM/FLA's 16-token, per-head, four-warp schedule for 128-wide heads, retaining Q/K in registers while reproducing the shipped 128-lane reduction tree byte-exactly. `VT_GDN_POSTCONV_TOKEN_TILE=1`; unset/`0` keeps the fast megablock. | Pinned FLA `fused_gdn_prefill_post_conv.py:57-149,208-245` and upstream `tests/kernels/test_fused_gdn_post_conv.py:60-208`; local `cuda_gdn.cu`, `gdn_prefill_conv.h`, portable and CUDA tests; [spike/result](specs/sm120-qwen35-postconv-token-tile-2026-08-08.md). | **IMPLEMENTED OPT-IN.** The first faster reduction changed tokens and was rejected. Accepted same-binary graph trace is byte-exact and **227.887→122.587 ms = 1.859x**, leaving **1.135x** to same-tool vLLM 108.035 ms; total/output +0.532%, TTFT -0.850%, TPOT -0.457%, E2E -0.531%. Tests: portable 6/6·50, CUDA GDN 67/67·4384, cached 4B 3/3·1672. Default/repeated and 27B/35B gates OPEN; no extrapolation. |
| 2026-08-08 (`KERNEL-SSM-MAMBA`; sm_120 causal-conv K4/channel-tile residual; local-4B only) | Adds same-binary K=4 causal-conv arms: `VT_CONV_CHANNEL_TILE=1` specializes width at the current 128-channel tile; `=2` also gives each thread two channels/256-channel tile. Unset/`0` keeps the runtime-width kernel. A shared portable/production dispatcher is mutation-gated. | Pinned vLLM `_causal_conv1d_fwd_kernel` compile-time `KERNEL_WIDTH`, `BLOCK_M=8`, `BLOCK_N=256` in `causal_conv1d.py:16-63,78-79,692-742`; local `cuda_gdn.cu`, `gdn_prefill_conv.h`, portable/CUDA tests; [spike/result](specs/sm120-qwen35-conv-channel-tile-2026-08-08.md). | **ARM 1 IMPLEMENTED OPT-IN; ARM 2 FALSIFIED.** Byte-exact rebuilt same-binary trace: arm 1 **234.605→219.506 ms (-6.44%)**, enclosing total/output +0.122%, TTFT -0.282%, TPOT -0.086%; vLLM residual **1.508x**. Arm 2 is 228.401 ms, 4.05% slower than arm 1 and enclosing-neutral/negative. Registers 43→52→58 refute the occupancy thesis. Portable 9/9·88, CUDA GDN 67/67·4631, paged-forward 4/4·8; default/repeated and 27B/35B gates OPEN. |
Loading
Loading