Skip to content

Add DeepSeek V4 target-only CPU inference - #165

Merged
JustVugg merged 27 commits into
JustVugg:devfrom
whale-agent-lab:dev
Aug 4, 2026
Merged

Add DeepSeek V4 target-only CPU inference#165
JustVugg merged 27 commits into
JustVugg:devfrom
whale-agent-lab:dev

Conversation

@DrewZt

@DrewZt DrewZt commented Jul 14, 2026

Copy link
Copy Markdown
Contributor

Summary

This PR now contains the DeepSeek V4 target-only CPU engine requested in the latest review. DSpark speculative decoding has been removed from #165 and preserved on DrewZt:pr165-full-dspark-backup for a separate stacked follow-up.

The target engine:

  • loads official sharded DeepSeek V4 safetensors checkpoints;
  • implements target prefill and greedy decode, compressed attention, mHC, routed/shared experts, and RAM-tiered ExpertStore caching;
  • keeps target dense residency independent of DSpark;
  • uses shared st.h for safetensors indexing/range I/O;
  • uses shared quant.h for canonical fmt7 MXFP4 matmul;
  • is wired into coli run, coli chat, coli serve, and coli web;
  • accepts --no-dspark as a compatibility no-op.

Production is consolidated in c/deepseek_v4.c. The standalone c/v4 launcher, DSpark runtime/build units, DSpark fixtures/tests, and committed .safetensors fixtures have been removed.

Shared infrastructure status

Checkpoint path Current implementation Status
Safetensors indexing/range reads shared st.h migrated
fmt7 standard MXFP4 matmul shared quant.h migrated
fmt7 resident rows16 expert cache minimal V4-private layout TODO(upstream-fmt7-rows16): migrate when shared quant exposes a resident rows16 API
fmt8 E4M3 + UE8M0 128x128 scales minimal V4-private decoder TODO(upstream-fmt8-ue8m0): replace when shared fmt8 UE8M0 decode exists

The last two paths remain only to keep the target engine usable and are explicitly marked for migration.

Unified serving

openai_server.py detects deepseek_v4, renders native multi-turn V4 markers, and launches the persistent SUBMIT/DATA/DONE protocol. Serving is target-only, greedy, one KV slot, and rejects tools/grammar. Requests re-prefill context while the engine, dense tensors, head, and expert cache stay warm.

Fixture and CI

The target-only fixture is generated from pinned PyTorch 2.13.0+cpu, Transformers 5.14.1, and safetensors 0.8.0. Its reference comes from official DeepseekV4ForCausalLM; there is no C-engine oracle fallback. Generated safetensors are ignored and not committed.

The V4 CI job checks teacher-forcing and greedy token identity, compressed/long prompts beyond the 64-token prefill boundary, repeated engine/session lifetime, --no-dspark compatibility, and two requests through one persistent server process.

Validation

  • make -C c check on Windows UCRT64: all C tests and 283 Python tests passed (21 platform skips)
  • clean make -C c deepseek-v4 ARCH=x86-64-v3
  • generated target-only tiny oracle: all token-exact checks passed
  • shared st.h pread/mirror and fmt8 loader tests passed
  • unified CLI and OpenAI server tests passed
  • real 48-shard DeepSeek V4 Flash target inference, 64 GiB planner budget:
    • output: The capital of France is Paris.
    • target dense: 43/43 layers resident, 6.266 GiB
    • target expert cache: 55.68 GiB
    • TTFT: 14.161 s
    • post-first-token time: 7.157 s
    • generated: 8 tokens (EOS before the 10-token cap)
    • target_only=1

The real-checkpoint output was also reproduced through c/coli run.

Commit structure

  1. feat(st): support V4 checkpoint metadata
  2. refactor(v4): preserve target-only runtime
  3. feat(cli): route DeepSeek V4 through coli serving
  4. test(v4): generate target-only oracle in CI
  5. docs(v4): describe target-only engine split

Follow-up

The stacked DSpark PR will restore the saved speculative runtime on this target baseline, make --no-dspark a real switch again, restore deterministic DSpark identity tests, and provide on/off performance and acceptance data across high-, medium-, and low-acceptance prompts.

@DrewZt DrewZt changed the title Dev Add DeepSeek V4 Flash CPU inference with NVMe expert streaming Jul 14, 2026
@DrewZt
DrewZt marked this pull request as draft July 14, 2026 14:21

@rajpratham1 rajpratham1 left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a very impressive contribution and clearly represents a significant amount of engineering work. The implementation covers a complete DeepSeek V4 CPU inference pipeline including runtime, expert streaming, quantization, safetensors loading, CLI tooling, documentation, and an extensive unit test suite.

Because this PR introduces an entirely new inference stack across many core components, I'd prefer additional review before approval.

Some areas that would benefit from closer review include:

  • Long-term API stability for the new DeepSeek V4 interfaces.
  • Memory ownership and lifetime throughout the expert streaming/runtime pipeline.
  • Performance characteristics of the NVMe streaming implementation under sustained inference.
  • Cross-platform compatibility (Windows/Linux/macOS) for filesystem and I/O paths.
  • Validation against larger real-world models beyond the included unit tests.

Overall the direction looks very promising, but given the size and architectural impact of this change, I think it should receive another maintainer review before merging.

@DrewZt

DrewZt commented Jul 14, 2026

Copy link
Copy Markdown
Contributor Author

Thanks for the thoughtful review. I agree that another maintainer review is appropriate given the size of the change.

A few clarifications on the areas you mentioned:

API stability: the new interfaces are currently scoped to the DeepSeek V4 engine and should be considered experimental. They are not intended to establish a stable generic model API at this stage.
Memory ownership: the expert-store API uses explicit lookup/release semantics, and the unit tests cover cache reuse and resource accounting. I agree that this area deserves focused review, and I can add more ownership/lifetime documentation where the contracts are not clear enough.
Sustained NVMe performance: the current documentation contains single-run measurements. I still need to add repeated and longer-running tests, including cache behavior, disk throughput, and memory stability over sustained decoding.
Cross-platform support: the DeepSeek V4 engine is intentionally limited to x86-64 Linux and Windows/MSYS2 for now. macOS, PowerPC, and other platforms are gated out of the V4 build and continue to run the existing GLM checks unchanged.
Full-model validation: the engine has been exercised end to end with the actual DeepSeek-V4-Flash-DSpark checkpoint. The current oracle path validates deterministic target-token reproduction and DSpark on/off identity; comparison against the official Transformers implementation is supported by the tooling but still needs broader validation.

I’m happy to address targeted follow-up findings, add more validation, or split parts of the implementation into staged PRs if the maintainers feel that would make review and long-term maintenance easier.

@DrewZt
DrewZt marked this pull request as ready for review July 14, 2026 17:36
@DrewZt

DrewZt commented Jul 14, 2026

Copy link
Copy Markdown
Contributor Author

I pushed a follow-up series through 82e7760 addressing the API-boundary and ownership concerns raised in the review.

The main changes are:

  • the DeepSeek V4 engine/session API is now explicitly marked experimental;
  • implementation-specific safetensors and ExpertStore interfaces have been moved out of the public API;
  • model paths, indexes, expert stores, resident weights, head caches, and DSpark runtime state now have explicit engine ownership;
  • engine/session lifetime accounting is shared by the production and ownership-test paths;
  • partially initialized engines and DSpark runners are cleaned up correctly on failure;
  • the ExpertStore lookup/release lease contract is documented and covered by regression tests;
  • ownership fault-injection hooks and test objects are isolated from production builds;
  • V4 session-owned tokenizer allocations are now released when the session is destroyed;
  • the existing GLM tokenizer loading behavior and GLM runtime paths remain unchanged.

The latest changes pass:

make -C c check -j8

The remaining validation work is focused on sustained NVMe behavior and broader full-model comparison against the official Transformers implementation. Those limitations remain documented in the PR and do not represent unresolved API or resource-lifetime issues.

I’m marking the PR ready for review and would appreciate another maintainer look, particularly at the revised API boundary and ownership model.

@steve-m

steve-m commented Jul 14, 2026

Copy link
Copy Markdown
Contributor

First full-model validation on Linux/x86-64 — plus a build fix and an AVX2 kernel series, branch ready to pull: steve-m/colibri@v4-avx2-kernels (5 commits on top of this PR's dev).

Hardware: Ryzen 9 3900X (Zen 2, 12C/24T, AVX2 no AVX-512), 62 GiB RAM, NVMe ~6 GB/s, Manjaro, gcc 15. Model: DeepSeek-V4-Flash-DSpark, --memory-gb 40.

Build fix you'll want regardless: two amalgam units (BLOCK_HYBRID, GENERATE_STATS) use pthreads without including pthread.h — gcc 14+ (C23) makes implicit declarations hard errors, so make deepseek-v4 fails out of the box on current Linux toolchains. One-line includes, first commit on the branch.

Kernel series (all behind a COLI_V4_AVX2=0 runtime kill-switch, float paths kept as fallbacks):

  • FP4 experts: int8 dot via pshufb-LUT + maddubs (doubled E2M1 values are integers), exact int32 accumulation per 32-block. On random tensors this measures ~4× closer to an fp64 oracle than the shipped float path (rel L2 0.027 vs 0.106).
  • BF16 head: 8-lane exact widening + zero-copy pass over the resident head (the elementwise coli_bf16_decode loop was 0.23 s/token on this box).
  • FP8 attention: fp32 bits built directly from E4M3 fields with a branchless denormal blend; same QDQ-activation math and product grouping as the reference, differs only by summation order.

Measured, 48-token free-form decode, OMP_NUM_THREADS=12: 0.53 tok/s (PR defaults) → 0.62 (threads = physical cores; SMT only adds barrier traffic) → 0.78 (FP4 int8) → 0.99 (head) → 1.12 tok/s (FP8). Verify phase −27%, TTFT 20 → 16.7 s. Validation at every step: your oracle tool's continuation_self_check 8/8 and DSpark on/off identity OK (the batch kernels are bitwise-identical per item to the single matvec by construction, so speculation identity survives), plus a new tests/test_native_quant_avx2.c (fp64-oracle error bounds incl. denormal-only tensors, bitwise dual/batch==single, dispatch kill-switch).

Also on the branch, off by default: a dual-SSD mirror (COLI_V4_MODEL_MIRROR) that hash-routes reads across two model copies at the coli_st_read_at choke point. Honest data point: it's ~5% slower warm (routing splits the OS page cache across two copies) — it's there for cold starts and low-RAM boxes; docs in the commit message.

Happy to split any of this into separate PRs against your dev, or adjust to taste.

@DrewZt

DrewZt commented Jul 15, 2026

Copy link
Copy Markdown
Contributor Author

First full-model validation on Linux/x86-64 — plus a build fix and an AVX2 kernel series, branch ready to pull: steve-m/colibri@v4-avx2-kernels (5 commits on top of this PR's dev).

Hardware: Ryzen 9 3900X (Zen 2, 12C/24T, AVX2 no AVX-512), 62 GiB RAM, NVMe ~6 GB/s, Manjaro, gcc 15. Model: DeepSeek-V4-Flash-DSpark, --memory-gb 40.

Build fix you'll want regardless: two amalgam units (BLOCK_HYBRID, GENERATE_STATS) use pthreads without including pthread.h — gcc 14+ (C23) makes implicit declarations hard errors, so make deepseek-v4 fails out of the box on current Linux toolchains. One-line includes, first commit on the branch.

Kernel series (all behind a COLI_V4_AVX2=0 runtime kill-switch, float paths kept as fallbacks):

  • FP4 experts: int8 dot via pshufb-LUT + maddubs (doubled E2M1 values are integers), exact int32 accumulation per 32-block. On random tensors this measures ~4× closer to an fp64 oracle than the shipped float path (rel L2 0.027 vs 0.106).
  • BF16 head: 8-lane exact widening + zero-copy pass over the resident head (the elementwise coli_bf16_decode loop was 0.23 s/token on this box).
  • FP8 attention: fp32 bits built directly from E4M3 fields with a branchless denormal blend; same QDQ-activation math and product grouping as the reference, differs only by summation order.

Measured, 48-token free-form decode, OMP_NUM_THREADS=12: 0.53 tok/s (PR defaults) → 0.62 (threads = physical cores; SMT only adds barrier traffic) → 0.78 (FP4 int8) → 0.99 (head) → 1.12 tok/s (FP8). Verify phase −27%, TTFT 20 → 16.7 s. Validation at every step: your oracle tool's continuation_self_check 8/8 and DSpark on/off identity OK (the batch kernels are bitwise-identical per item to the single matvec by construction, so speculation identity survives), plus a new tests/test_native_quant_avx2.c (fp64-oracle error bounds incl. denormal-only tensors, bitwise dual/batch==single, dispatch kill-switch).

Also on the branch, off by default: a dual-SSD mirror (COLI_V4_MODEL_MIRROR) that hash-routes reads across two model copies at the coli_st_read_at choke point. Honest data point: it's ~5% slower warm (routing splits the OS page cache across two copies) — it's there for cold starts and low-RAM boxes; docs in the commit message.

Happy to split any of this into separate PRs against your dev, or adjust to taste.

This is extremely helpful — thank you for doing the first independent full-model Linux/x86-64 validation and for documenting the performance progression in such detail. The Ryzen 3900X result directly addresses one of the main remaining validation gaps for this PR, and the 0.53 → 1.12 tok/s breakdown makes it much easier to see where the current bottlenecks are.

I checked the branch history and it looks like v4-avx2-kernels was based on f2ff5ad, which was the PR head when you started, rather than the current head 82e7760. The branches have since diverged, and the optimization branch is missing the API-boundary and resource-ownership follow-ups added after that snapshot.

Those later commits include the revised public/internal API separation, engine/session lifetime accounting, failure-path cleanup, isolated ownership-test objects, and V4 session tokenizer cleanup. The optimization work is still very valuable, but it should be rebased onto 82e7760 before integration so that those ownership changes are not accidentally overwritten or bypassed.

One clarification regarding the pthread build issue: I had already addressed the missing declaration problem in c9b626c, immediately after the snapshot your branch was based on, by adding -pthread -include pthread.h to the Linux V4 build flags. That fix is already present in the current PR head.

Your source-level includes may still be a cleaner and more localized solution, but the issue itself no longer needs a separate build-fix PR. When rebasing, please either drop the overlapping build-fix commit or call out why replacing the current compiler-level include with explicit includes in the two amalgam units would be preferable.

For the remaining work, I suggest splitting it into two focused follow-ups:

  1. AVX2 kernel series

    Please keep the FP4 expert, BF16 head, and FP8 attention kernels together with tests/test_native_quant_avx2.c in a dedicated PR rebased onto 82e7760.

    Keeping the scalar/float fallbacks and the COLI_V4_AVX2=0 runtime kill switch is a good compatibility approach. The fp64 error-bound tests, denormal cases, batch-versus-single checks, and dispatch-disable coverage are especially useful.

  2. Dual-SSD mirror

    I think COLI_V4_MODEL_MIRROR should remain a separate experimental PR. Its expected benefits and tradeoffs differ from the CPU kernels, and the warm-cache regression you measured is important context. It appears most relevant to cold starts and lower-memory systems rather than the default warm-cache configuration.

I also noticed that the branch diff appears to include generated test binaries such as:

c/tests/test_decode_batch
c/tests/test_i4_acc512
c/tests/test_idot

Please drop those artifacts when preparing the follow-up PRs.

After rebasing, please rerun the full-model correctness and performance validation because the runtime and ownership code has changed since f2ff5ad. The most useful checks would be:

make -C c check -j8
make -C c deepseek-v4

continuation_self_check
DSpark on/off identity
COLI_V4_AVX2=0 fallback comparison
48-token benchmark with the same model, RAM cap, and thread count

The current benchmark result is already valuable as independent validation of the earlier implementation. Once the rebased kernel series is reviewed, I’d be happy to add the reproducible Linux/x86-64 measurements to the documentation with credit to you and the exact hardware and commands.

Thanks again — this is a substantial and very useful contribution. Rebasing and splitting it should let us preserve the recent API and ownership work while giving the kernels and storage experiment the focused review they deserve.

@DrewZt

DrewZt commented Jul 15, 2026

Copy link
Copy Markdown
Contributor Author

Follow-up for @JustVugg: head af86de1 closes the remaining validation findings. The safetensors index now requires payload bytes to equal dtype width times shape numel; V4 config integers, floats, and compress ratios now have finite/integer/range checks. I also removed the dense-cache borrowed config pointer in favor of the engine-owned canonical config and made the DSpark oracle require exact output lengths on both paths. Fresh validation passed make check (all C tests plus 71 Python tests), x86-64-v3/native builds, ASan+UBSan+LSan, and the 48-shard MEMORY_GB=32 oracle (19/19 teacher forcing, 8/8 greedy, 8/8 continuation self-check, exact DSpark on/off identity). This supersedes my earlier blocker summary; AVX2 and dual-SSD work remain out of scope. Could you please review when convenient?

@steve-m

steve-m commented Jul 15, 2026

Copy link
Copy Markdown
Contributor

Pushed the rebased AVX2 kernel series to steve-m/colibri:v4-avx2-kernels (force-updated onto the current PR head af86de1, the ownership/API series you pushed after 82e7760) — 3 commits on top. Rebased rather than replayed the old branch, so the public/internal API split, engine/session ownership, failure-path cleanup, and session tokenizer changes are all preserved underneath — make -C c check (incl. the test_v4_ownership suite) passes on top of the series.

Two changes from the old v4-avx2-kernels snapshot:

  • Dropped the pthread build-fix commit. Your -pthread -include pthread.h in the Linux V4 CFLAGS already covers it, so the separate source-include commit is gone — the engine builds clean on gcc 15 without it. (I kept the compiler-flag approach; happy to add explicit #include <pthread.h> to the two amalgam units instead if you'd prefer the localized form, but it's not needed for the build.)
  • Left the dual-SSD mirror out of this series. It's off-by-default and ~5% slower warm on a single-cache box, so it doesn't belong in the kernel PR; I'll keep it on a separate branch if there's interest.

The three commits, all behind the COLI_V4_AVX2=0 runtime kill-switch with the float paths kept as fallbacks:

  1. FP4 experts — int8 dot (pshufb-LUT + maddubs; doubled E2M1 values are integers, exact int32 accumulation per 32-block). Drops in at the link level — native_quant_avx2.c provides coli_fp4_matvec_ref/coli_fp8_matvec_ref and wraps the renamed *_float_ref fallbacks, so no engine call sites change. The native_quant_* files were byte-identical to the snapshot, so this was a clean port.
  2. FP8 attention — E4M3 (fp32 bits built directly from the E4M3 fields with a branchless denormal blend; same QDQ-activation math and product grouping as the reference, differs only by summation order).
  3. BF16 head + zero-copy resident pass. A shared coli_v4_head_row_dot (8-lane exact bf16 widening + FMA across the batch) replaces the per-element coli_bf16_decode loops in both coli_v4_target_head_argmax_batch and the single-token head_argmax; when the head is resident in the engine head cache, it now dots the cached rows in place instead of re-reading per ROWS block.

Validation on the rebased branch — Ryzen 9 3900X (Zen 2, AVX2 no AVX-512), 62 GiB, gcc 16.1.1, DeepSeek-V4-Flash-DSpark, --memory-gb 40:

  • make -C c check — all pass, including test_native_quant_avx2 (fp64-oracle error bounds incl. denormal-only tensors, bitwise dual/batch==single, dispatch kill-switch) and the full test_v4_ownership suite. Builds clean on gcc 16 (only pre-existing warnings in deepseek_v4_dspark.c, none from the kernels).
  • make deepseek-v4-oracle (coli-self): continuation_self_check 8/8, teacher-forcing 19/19 positions, greedy 8/8 tokens, and DSpark on/off identity OK (no_dspark vs fixture, dspark vs fixture, on/off equality all OK). The head is resident (head=resident-bf16), so the zero-copy resident-head path is the one exercised.

Perf — AVX2 on vs the COLI_V4_AVX2=0 float fallback on this rebased head (48-token free-form, OMP_NUM_THREADS=12).

Kernel-only isolation, DSpark disabled (--no-dspark) — both runs issue an identical, deterministic 18318 expert requests, so this is a true A/B with no speculation-acceptance variance:

  • decode 0.76 → 0.98 tok/s (+29%)
  • prefill / TTFT 48.2 s → 31.2 s (−35%)

For reference, DSpark on (same prompt): decode 0.62 → 0.85 tok/s (+36%), TTFT 43.6 → 30.3 s (−30%) — but that pass had asymmetric acceptance (on 3/10 vs off 1/10 speculative tokens), so the isolated --no-dspark figure above is the honest kernel-only claim.

The float-path baseline matches the known physical-cores number, so the kill-switch cleanly isolates the kernel gain. TTFT is stable across the DSpark condition (~31 s on / ~48 s off), as expected — the first token is prefill + first decode, before any speculation. (Absolute tok/s is workload-dependent — this was a heavy ~80 GB-streaming pass; a lighter/warmer pass on this box peaks around 1.12 tok/s. The on/off ratio is the stable claim.)

@DrewZt

DrewZt commented Jul 16, 2026

Copy link
Copy Markdown
Contributor Author

Pushed the rebased AVX2 kernel series to steve-m/colibri:v4-avx2-kernels (force-updated onto the current PR head af86de1, the ownership/API series you pushed after 82e7760) — 3 commits on top. Rebased rather than replayed the old branch, so the public/internal API split, engine/session ownership, failure-path cleanup, and session tokenizer changes are all preserved underneath — make -C c check (incl. the test_v4_ownership suite) passes on top of the series.

Two changes from the old v4-avx2-kernels snapshot:

  • Dropped the pthread build-fix commit. Your -pthread -include pthread.h in the Linux V4 CFLAGS already covers it, so the separate source-include commit is gone — the engine builds clean on gcc 15 without it. (I kept the compiler-flag approach; happy to add explicit #include <pthread.h> to the two amalgam units instead if you'd prefer the localized form, but it's not needed for the build.)
  • Left the dual-SSD mirror out of this series. It's off-by-default and ~5% slower warm on a single-cache box, so it doesn't belong in the kernel PR; I'll keep it on a separate branch if there's interest.

The three commits, all behind the COLI_V4_AVX2=0 runtime kill-switch with the float paths kept as fallbacks:

  1. FP4 experts — int8 dot (pshufb-LUT + maddubs; doubled E2M1 values are integers, exact int32 accumulation per 32-block). Drops in at the link level — native_quant_avx2.c provides coli_fp4_matvec_ref/coli_fp8_matvec_ref and wraps the renamed *_float_ref fallbacks, so no engine call sites change. The native_quant_* files were byte-identical to the snapshot, so this was a clean port.
  2. FP8 attention — E4M3 (fp32 bits built directly from the E4M3 fields with a branchless denormal blend; same QDQ-activation math and product grouping as the reference, differs only by summation order).
  3. BF16 head + zero-copy resident pass. A shared coli_v4_head_row_dot (8-lane exact bf16 widening + FMA across the batch) replaces the per-element coli_bf16_decode loops in both coli_v4_target_head_argmax_batch and the single-token head_argmax; when the head is resident in the engine head cache, it now dots the cached rows in place instead of re-reading per ROWS block.

Validation on the rebased branch — Ryzen 9 3900X (Zen 2, AVX2 no AVX-512), 62 GiB, gcc 16.1.1, DeepSeek-V4-Flash-DSpark, --memory-gb 40:

  • make -C c check — all pass, including test_native_quant_avx2 (fp64-oracle error bounds incl. denormal-only tensors, bitwise dual/batch==single, dispatch kill-switch) and the full test_v4_ownership suite. Builds clean on gcc 16 (only pre-existing warnings in deepseek_v4_dspark.c, none from the kernels).
  • make deepseek-v4-oracle (coli-self): continuation_self_check 8/8, teacher-forcing 19/19 positions, greedy 8/8 tokens, and DSpark on/off identity OK (no_dspark vs fixture, dspark vs fixture, on/off equality all OK). The head is resident (head=resident-bf16), so the zero-copy resident-head path is the one exercised.

Perf — AVX2 on vs the COLI_V4_AVX2=0 float fallback on this rebased head (48-token free-form, OMP_NUM_THREADS=12).

Kernel-only isolation, DSpark disabled (--no-dspark) — both runs issue an identical, deterministic 18318 expert requests, so this is a true A/B with no speculation-acceptance variance:

  • decode 0.76 → 0.98 tok/s (+29%)
  • prefill / TTFT 48.2 s → 31.2 s (−35%)

For reference, DSpark on (same prompt): decode 0.62 → 0.85 tok/s (+36%), TTFT 43.6 → 30.3 s (−30%) — but that pass had asymmetric acceptance (on 3/10 vs off 1/10 speculative tokens), so the isolated --no-dspark figure above is the honest kernel-only claim.

The float-path baseline matches the known physical-cores number, so the kill-switch cleanly isolates the kernel gain. TTFT is stable across the DSpark condition (~31 s on / ~48 s off), as expected — the first token is prefill + first decode, before any speculation. (Absolute tok/s is workload-dependent — this was a heavy ~80 GB-streaming pass; a lighter/warmer pass on this box peaks around 1.12 tok/s. The on/off ratio is the stable claim.)

This looks excellent — thank you for rebasing the series carefully and for preserving the API and ownership work underneath it.

The updated scope is exactly what I was hoping for:

  • the overlapping pthread fix is removed;
  • the dual-SSD experiment is kept separate;
  • the AVX2 work is limited to three focused kernel commits;
  • the float fallbacks and COLI_V4_AVX2=0 escape hatch remain available;
  • the ownership suite and full-model oracle still pass on top of the series.

I also appreciate the distinction between the DSpark-enabled result and the --no-dspark isolation run. The deterministic 18,318-request A/B is the right primary performance claim because it removes speculative-acceptance variance. The resulting figures are both substantial and clearly scoped:

decode:       0.76 → 0.98 tok/s  (+29%)
prefill/TTFT: 48.2 → 31.2 s     (-35%)

The zero-copy resident-head path being exercised by the full-model oracle is also useful confirmation that the new path is covered rather than only compiled.

Since the kernel branch is stacked on top of #165, I think the cleanest next step is to keep the branch as-is for now and open a dedicated follow-up PR after #165 is merged. At that point it can be rebased onto the resulting upstream dev, leaving the follow-up diff limited to the three kernel commits and their tests.

Please preserve the current commit separation and validation details in that PR. In particular, the --no-dspark A/B should be the headline benchmark, with the DSpark-enabled figures included as additional workload-dependent context.

Thanks again — this is a strong follow-up series, and the careful validation and honest performance attribution make it much easier to review.

@DrewZt
DrewZt requested a review from rajpratham1 July 16, 2026 03:44
@DrewZt

DrewZt commented Jul 16, 2026

Copy link
Copy Markdown
Contributor Author

Pushed follow-up stability fix e4f87a8 for two issues found during full-model testing:

  • Fixed prompts longer than the internal 64-token batch limit by chunking target-layer and DSpark prefill while preserving absolute positions.
  • Fixed DSpark sparse-window accounting after speculative position jumps. The previous monotonically incremented valid counter could report more entries than were actually copyable (valid=43 copied=42), resulting in DSpark block failed.
  • Added stage-specific DSpark diagnostics and a regression test for sparse absolute-position window updates.

Validation:

  • The previous 74/76-token failure cases now complete successfully.
  • A near-limit 488-token prompt completed prefill and generated its first token successfully.
  • The DeepSeek V4 unit tests pass.
  • make deepseek-v4 succeeds.

@JustVugg

Copy link
Copy Markdown
Owner

I'm interested in this — DeepSeek V4 Flash on CPU with NVMe expert streaming is squarely what colibrì is for, and I'd like it in.

The one condition is that I need to run it on my own machine first. Not as a gate to be difficult: it's the rule I've had to learn the hard way this week. EXPERT_BUDGET went in on numbers nobody had reproduced and had to be quarantined a few days later (#303) — it turned out to be slower than not using it while claiming a speedup. I'm not going to do that to a second engine. Once something is in main, people run it, and if I can't run it I can't fix it for them.

So: as soon as I can get a checkpoint on this box, I'll test it and we'll work on it together. That's not a "no" parked forever — it's the next thing I want to do on this front.

Two things that would make it land sooner, and I'd rather ask than have you guess:

  1. A path to a small test model. The pattern already in the repo is tools/make_glm_oracle.py, which builds a tiny glm_tiny/ that the engine is scored token-exact against. If DeepSeek V4 can get the same — even a toy — then the engine proves itself on every CI run, on my box and everyone else's, without a 400 GB download. That's the single highest-leverage thing here: it turns "trust me" into "the test is green", and it's what will keep the engine alive in six months when neither of us is looking at it.
  2. Keep simplifying the implementation. 8,704 lines is a lot to carry, and the thinner it gets the faster it moves — for both of us. Anything that can lean on what glm.c already has (the streaming cache, the URING/DIRECT I/O path, compat.h) rather than reimplement it is line I don't have to review and you don't have to maintain. c/compat.h +7 is exactly the right kind of touch.

I saw the stability fix you pushed (e4f87a8) — thank you for staying on it. And CI landed today (#143 + #144): make check now runs on ubuntu/windows/macos for every PR, so you'll get a compile/test verdict in ~2 minutes instead of waiting on me.

Keeping this open. Let's keep going.

@DrewZt

DrewZt commented Jul 17, 2026

Copy link
Copy Markdown
Contributor Author

I'm interested in this — DeepSeek V4 Flash on CPU with NVMe expert streaming is squarely what colibrì is for, and I'd like it in.

The one condition is that I need to run it on my own machine first. Not as a gate to be difficult: it's the rule I've had to learn the hard way this week. EXPERT_BUDGET went in on numbers nobody had reproduced and had to be quarantined a few days later (#303) — it turned out to be slower than not using it while claiming a speedup. I'm not going to do that to a second engine. Once something is in main, people run it, and if I can't run it I can't fix it for them.

So: as soon as I can get a checkpoint on this box, I'll test it and we'll work on it together. That's not a "no" parked forever — it's the next thing I want to do on this front.

Two things that would make it land sooner, and I'd rather ask than have you guess:

  1. A path to a small test model. The pattern already in the repo is tools/make_glm_oracle.py, which builds a tiny glm_tiny/ that the engine is scored token-exact against. If DeepSeek V4 can get the same — even a toy — then the engine proves itself on every CI run, on my box and everyone else's, without a 400 GB download. That's the single highest-leverage thing here: it turns "trust me" into "the test is green", and it's what will keep the engine alive in six months when neither of us is looking at it.
  2. Keep simplifying the implementation. 8,704 lines is a lot to carry, and the thinner it gets the faster it moves — for both of us. Anything that can lean on what glm.c already has (the streaming cache, the URING/DIRECT I/O path, compat.h) rather than reimplement it is line I don't have to review and you don't have to maintain. c/compat.h +7 is exactly the right kind of touch.

I saw the stability fix you pushed (e4f87a8) — thank you for staying on it. And CI landed today (#143 + #144): make check now runs on ubuntu/windows/macos for every PR, so you'll get a compile/test verdict in ~2 minutes instead of waiting on me.

Keeping this open. Let's keep going.

Thanks — this gives me a clear integration path.

I’ll make the tiny DeepSeek V4 fixture the immediate priority. The goal will be a deterministic, independently generated checkpoint and reference that make check can validate without downloading the full model or installing PyTorch/Transformers during CI.

The initial test contract will cover:

  • target teacher forcing against the independent reference;
  • target greedy decoding against the same reference;
  • DSpark-off output matching the target reference exactly;
  • DSpark-on output remaining exactly identical to the target path;
  • compressed-attention and routed-expert execution;
  • a prompt longer than the internal 64-token batch boundary, covering the recent chunked-prefill fix.

The generator will remain available so the fixture is reproducible rather than an opaque committed artifact, while CI itself will use the checked-in tiny checkpoint and reference.

I’ll also continue removing local duplication where that does not change runtime or kernel boundaries. For the deeper shared-I/O work—particularly consolidating the streaming read path with the existing DIRECT/URING infrastructure—I would prefer to do that as a focused follow-up after this base engine and the already prepared AVX2 series land. That keeps the current correctness and performance baselines stable, avoids repeatedly invalidating the AVX2 branch, and lets the tiny token-exact oracle protect the later refactor across both scalar and optimized paths.

I’ll keep AVX2 and the dual-SSD experiment out of this PR, and I’ll document the shortest full-checkpoint smoke-test path for your machine alongside the tiny fixture.

@DrewZt

DrewZt commented Jul 17, 2026

Copy link
Copy Markdown
Contributor Author

Implemented the requested deterministic tiny DeepSeek V4 + DSpark oracle at head dac2f76.

  • Committed fixture size: 1,253,414 bytes (~1.20 MiB), including target and one-stage DSpark checkpoints.
  • Independent reference: official Transformers DeepseekV4ForCausalLM (Transformers 5.14.1), evaluated after the same dense FP8, routed-expert packed FP4, and BF16 round trips loaded by the C runtime. The C engine is never used to generate the reference.
  • Target teacher forcing: token-exact for the short, compressed-attention, and 72-token prompts.
  • Target greedy decode: exact IDs and exact length; truncated-prefix comparisons are explicitly rejected.
  • DSpark identity: drafting is exercised and enabled/disabled outputs exactly match the independent target reference.
  • Long prompt: the 72-token case crosses the internal 64-token prefill boundary for both target and DSpark.
  • Lifecycle: repeated engine/session open, generate, destroy checks pass.
  • CI: Linux x86-64 and Windows UCRT64 run the tiny oracle in make check; macOS passes the normal GLM tests and V4 platform gate. All three jobs passed: https://github.com/whale-agent-lab/colibri/actions/runs/29556719562
  • CI remains offline and does not install PyTorch or Transformers.

Manual local validation (from the repository root):

# Dedicated tiny target + DSpark token-exact oracle
make -C c deepseek-v4-tiny-check ARCH=x86-64-v3

# Or run the complete dependency-free check suite
make -C c check

To exercise the normal runtime explicitly with drafting disabled:

cd c
make deepseek-v4 ARCH=x86-64-v3
./deepseek_v4 deepseek_v4_tiny '<t005><t007><t009>' \
  --raw-prompt --draft-model deepseek_v4_tiny/dspark --no-dspark

The generator and regeneration package versions are documented in docs/deepseek-v4.md. AVX2/native-quant dispatch redesign and shared DIRECT/URING/read-helper consolidation remain out of scope.

@maikelthedev

maikelthedev commented Jul 17, 2026

Copy link
Copy Markdown
Contributor

1.12 tok/s (FP8).

sorry what?! That's impressive for NVMe.

@DrewZt

DrewZt commented Jul 18, 2026

Copy link
Copy Markdown
Contributor Author

1.12 tok/s (FP8).

sorry what?! That's impressive for NVMe.

The prompt 'What is the capital of France' have some uniqueness, the answer token got 100% dspark acceptance rate, that is the fastest speed boost.
For another 0% dspark acceptance rate special case 'hello', decode speed will drop to 0.59tok/s, which is slower than no-dspark situation

@maikelthedev

maikelthedev commented Jul 18, 2026 via email

Copy link
Copy Markdown
Contributor

@DrewZt

DrewZt commented Jul 18, 2026

Copy link
Copy Markdown
Contributor Author

On your own Pc, Vincent, how does it compare to GLM in speed if you don't mind me asking (And what are the specs of yours , and what OS) 🤔From: DrewZt @.>Sent: Saturday, July 18, 2026 12:07:24 pmTo: JustVugg/colibri @.>Cc: Maikel Frias Mosquea @.>; Comment @.>Subject: Re: [JustVugg/colibri] Add DeepSeek V4 Flash CPU inference with NVMe expert streaming (PR #165)DrewZt left a comment (JustVugg/colibri#165)1.12 tok/s (FP8).sorry what?! That's impressive for NVMe.The prompt 'What is the capital of France' have some uniqueness, the answer token got 100% dspark acceptance rate, that is the fastest speed boost. For another 0% dspark acceptance rate special case 'hello', decode speed will drop to 0.59tok/s, which is slower than no-dspark situation—Reply to this email directly, view it on GitHub, or unsubscribe.You are receiving this because you commented.

My pc is ai max 395+128gb ram+6gb/s ssd, tested glm with config think=0 and mtp=1, got around 0.7 tok/s

@JustVugg

Copy link
Copy Markdown
Owner

Status check: dev has moved substantially since this was opened (#391 refactor: glm.c → colibri.c + header modules, plus today's CUDA kernel rework in #298). A DeepSeek engine is very much on the roadmap, so this PR is interesting — but the rebase at this distance is a rewrite-sized job only the author can drive. Are you still working on it? If not I'll close it as superseded when we start the DeepSeek port, with credit for the groundwork.

@DrewZt

DrewZt commented Jul 21, 2026

Copy link
Copy Markdown
Contributor Author

Status check: dev has moved substantially since this was opened (#391 refactor: glm.c → colibri.c + header modules, plus today's CUDA kernel rework in #298). A DeepSeek engine is very much on the roadmap, so this PR is interesting — but the rebase at this distance is a rewrite-sized job only the author can drive. Are you still working on it? If not I'll close it as superseded when we start the DeepSeek port, with credit for the groundwork.

Yes, I’m still actively working on this. Please keep the PR open.

I reviewed the impact of the current dev changes, including the glm.ccolibri.c refactor and the newer build, I/O, tokenizer, and quantization infrastructure. A commit-by-commit rebase would be unnecessarily difficult, but the V4 engine itself does not need to be rewritten: most of the model-specific implementation remains isolated in files that do not exist upstream.

I’m going to treat this as a minimal forward port onto current dev, rather than replaying the old history or combining it with another large refactor.

Work I will complete before merging #165

  1. Port the independent V4 engine onto current dev

    • re-add the target and DSpark engine files on top of the current tree;
    • adapt the build targets, tests, cleanup rules, and platform gates to the current colibri build structure;
    • preserve the existing experimental engine/session API and ownership boundaries.
  2. Reconcile the shared-file changes manually

    • keep the current upstream compat.h as the base and add only V4-specific missing pieces;
    • combine the current tokenizer/o200k changes with the V4 tokenizer lifetime cleanup;
    • preserve the safetensors validation and JSON ownership fixes;
    • avoid replacing newer upstream files with their older Add DeepSeek V4 target-only CPU inference #165 versions.
  3. Keep the V4-specific runtime boundaries stable

    • retain the current V4 safetensors index and tensor I/O layer for this port;
    • retain the native FP4/FP8 quantization interfaces;
    • retain the ExpertStore, head-cache, target, and DSpark interfaces used by the validated implementation.

    The current upstream st.h and quant.h are useful foundations, but they do not yet represent the same tensor metadata or numerical formats as the V4 runtime. Folding those layers together during the port would substantially enlarge the correctness and review surface.

  4. Restore the automated correctness gate first

    • make the committed tiny Transformers oracle pass on Linux and Windows;
    • keep the macOS unsupported-runtime gate and portable infrastructure tests;
    • restore teacher-forcing, greedy, DSpark identity, lifecycle, compressed-attention, and >64-token prompt coverage.
  5. Repeat full-checkpoint validation

    • target teacher forcing;
    • greedy continuation;
    • DSpark enabled/disabled exact identity;
    • long-prompt prefill;
    • sustained decode and memory stability;
    • a fresh scalar --no-dspark performance baseline.
  6. Keep AVX2 and the deeper I/O refactor out of the base port

    • I will not change the native-quant dispatch, head-cache representation, or kernel-facing APIs during the forward port;
    • this keeps Steve’s three AVX2 commits reusable rather than forcing him to redesign the kernels.

I had already done additional local work around redundant expert reads and the streamed I/O path, but I intentionally did not push it onto #165. At that point the branch had a stable correctness baseline and Steve’s AVX2 series was stacked on top of it; changing the I/O and cache boundaries again would have invalidated both his branch and the existing measurements.

Work planned after #165 merges

  1. Steve’s AVX2 follow-up

    • rebase the focused FP4, FP8, and BF16-head kernel series onto the merged dev;
    • keep the scalar fallback and COLI_V4_AVX2=0 kill switch;
    • rerun the tiny oracle, full-model oracle, and deterministic --no-dspark A/B benchmark.
  2. Shared I/O consolidation

    • evaluate the V4 read path against the current st.h, DIRECT I/O, pipeline, and io_uring infrastructure;
    • extract only genuinely shared low-level mechanisms such as full-read handling, direct/buffered fd management, prefetch, and platform diagnostics;
    • preserve the V4-specific tensor metadata, native FP4 layout, compressed attention, and cache semantics where they do not match the GLM engine.
  3. Further implementation simplification

    • reduce duplicated infrastructure under the protection of both the tiny oracle and the AVX2 fallback tests;
    • keep that work in a focused follow-up rather than mixing model correctness, kernel optimization, and I/O refactoring into one review.

So the immediate objective is to restore #165 on current dev with the same validated model behavior and the smallest possible integration diff. Once that base is merged, the AVX2 and shared-I/O work can proceed as separate, measurable follow-ups.

@DrewZt

DrewZt commented Jul 21, 2026

Copy link
Copy Markdown
Contributor Author

The forward port is now pushed.

PR #165 now points to 9824fab, rebuilt as a fresh forward port on the current upstream dev at 4aca059.

The main colibri.c, storage/cache paths, and shared st.h/quant.h infrastructure remain unchanged. Steve’s AVX2 work and the broader I/O consolidation remain separate follow-ups.

Local make check, the tiny token-exact oracle, full-checkpoint validation, long-prompt tests, and sanitizer runs all pass.

The new PR workflows are currently waiting for maintainer approval. Could you approve them so the checks can run?

JustVugg added a commit to khalilswdp/colibri that referenced this pull request Aug 4, 2026
One conflict, in c/coli's cmd_run. dev added the DeepSeek V4 branch (JustVugg#165)
directly after a plain banner("run"); this branch moved that banner below
env_for so it can report the CUDA backend -- banner("run", COLI_CUDA=="1").

Taking dev's hunk verbatim would have reintroduced the plain banner and
printed two. Taking this branch's side would have dropped the V4 path.
Resolved by keeping the V4 branch and giving it its own banner("run"),
since that path sys.exit()s before reaching the CUDA-aware call. Both
intents preserved; neither side loses a line.

`python -m ast` parses the result.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
JustVugg added a commit to khalilswdp/colibri that referenced this pull request Aug 4, 2026
Same conflict as JustVugg#825 and the same resolution, in c/coli's cmd_run.
dev added the DeepSeek V4 branch (JustVugg#165) right after a plain banner("run");
this branch moved that banner below env_for so it can report the backend --
banner("run", COLI_CUDA=="1").

Kept the V4 branch and gave it its own banner("run"), since that path
sys.exit()s before reaching the CUDA-aware call. Taking either side whole
would have printed two banners or dropped the V4 path.

`python -m ast` parses the result.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Kenneth-Javier added a commit to Kenneth-Javier/colibri that referenced this pull request Aug 4, 2026
DeepSeek V4 (JustVugg#165) landed on dev. Two hunks, both "keep both":

- c/Makefile: dev reflowed .PHONY across lines and added the deepseek-v4
  targets plus a separate bench-omp-grain line; this branch had added hip-dll
  to the same list. Took dev's form and re-inserted hip-dll after cuda-dll.
- c/tools/clean.py: both sides appended to the artifact list. Kept both blocks.

Merged rather than rebased so the commit SHAs, the CI results just unblocked
for this PR, and the review comments anchored to them all survive.
ZacharyZcR added a commit to ZacharyZcR/colibri that referenced this pull request Aug 5, 2026
Rebasing on dev turned check-env red, which is the point of it:

  - read by the code but missing from coli_env.h: COLI_MTP_GUARD_PCT
  - read by the code but missing from coli_env.h: COLI_MTP_GUARD_WINDOW
  - read by the code but missing from coli_env.h: COLI_V4_EXPERT_PREFETCH
  - read by the code but missing from coli_env.h: CUDA_EXPERT_LOAD_BALANCE
  - read by the code but missing from coli_env.h: INK_METAL_SHARED
  - read by the code but missing from coli_env.h: V4_PREFIX_LOG

Types come from the call sites, not from the names: the three read
through atoi() are CE_INT, INK_METAL_SHARED and COLI_V4_EXPERT_PREFETCH
are tested as switches so CE_BOOL, and V4_PREFIX_LOG is presence-checked
like the INK_PREFIX_LOG row already in the table, so CE_STR.

Two of them belong to deepseek_v4.c, which JustVugg#165 added and which has no
engine bit here, so add CE_DSV4. It is deliberately NOT folded into
CE_ALL: that flag means the four engines sharing route_trace.h, rans.h
and omp_tune.h, and deepseek_v4.c includes none of the three -- putting
it in CE_ALL would claim every shared-header knob is read by V4 too.

Also refresh the header comment, which had gone stale in the same way the
table would have: 212 -> 220. The "187 scattered getenv() call sites"
figure is removed rather than corrected -- nothing verifies it, so it can
only rot again. `make check-env` prints the live count and is the one
number in that comment that cannot go stale.

check-env: 220 variables, registry matches the sources.
mcollinswisc pushed a commit to mcollinswisc/colibri that referenced this pull request Aug 5, 2026
## The roster said four families; there are five

DeepSeek V4 Flash landed in JustVugg#165 and was tuned in JustVugg#839, but the README still
opened with "Four families run today" and its table stopped at OLMoE. Someone
scanning the front page had no way to learn the engine exists.

It is now in the opening line, in the roster table, and in the hardware table
above it -- ~167 GB on disk, 16 GB of RAM minimum and 22 comfortable, measured
on the reference box rather than estimated.

## The DeepSeek section described a version that no longer exists

It called the path "experimental" and said "DSpark is intentionally kept for a
separate stacked follow-up". DSpark is in, and the honest state is more
interesting than either claim:

  - the checkpoint streams with no conversion -- routed experts stay native fp4,
    dense stays fp8-e4m3 with UE8M0 block scales
  - greedy, one KV slot, no tools or grammar yet: said plainly, because finding
    that out from a rejected request is worse
  - --ram is the knob that matters. 43 x 256 routed experts are ~137 GiB and a
    token touches 301 of them, so the cache hit rate sets tok/s. It changes
    speed only, never output.
  - speculative drafting is implemented, verified, and OFF, with the numbers
    that made that call: 1 accepted in 15 for the markov drafter, 10 in 24 for
    full MTP, and a 14-token answer that took 495 seconds to replay its
    rejected suffixes

That last one is the point of documenting it at all. The code stays, the
measurement stays beside it, and whoever retries this on faster storage starts
from evidence instead of from scratch.

## Repo layout described a tree that has not existed since July

It listed `glm.c`, renamed to `colibri.c` in JustVugg#391 three weeks ago, and no other
engine -- so the file that runs GLM was wrong and the four files that run
everything else were missing. Also absent: quant.h, compat.h, expert_store.h,
route_trace.h, kv_prefix.h, the Metal and Vulkan backends, resource_plan.py,
and docker/.

Every path and every make target in the new listing was checked to exist on
this branch before it was written down.

The rule behind the layout is now stated, because it is the one that keeps
being violated: one .c per model family, over shared single headers. An engine
owns its architecture and nothing else. The recurring defects in this tree --
the OpenMP thread count, the KV prefix reuse, the NaN router guard -- are all
the same shape: a mechanism that landed in one engine and never reached its
siblings.

## Also

`#### Other supported models` now sits where the roster table is, so
`[Full roster ↓](#other-supported-models)` in the opening paragraph resolves to
the table instead of to prose four sections earlier.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
ZacharyZcR added a commit to ZacharyZcR/colibri that referenced this pull request Aug 6, 2026
This is JustVugg#772 rescoped. It was an engine plus its kernels and it would not
start below 145.3 GiB of VRAM, which makes it a threshold -- the one thing
this project does not ship. @jazir555 and @rafpigna said so, @JustVugg
agreed, and the request was not negotiable: a GPU backend here holds the
hot part and falls back for the rest.

The split @JustVugg proposed is the right one. JustVugg#165 landed the DeepSeek V4
engine with the streaming machinery and no CUDA at all; this was the CUDA
with no tier. Neither runs the model on hardware anyone owns. So the engine
file belongs to JustVugg#165 and this keeps only the kernels:

  backend_cuda_dsv4*.{cu,h}   dense matmul, batched attention, routed MoE
  dsv4_mhc.h, dsv4_quant.h    the CPU-side formats the kernels consume
  tests/                      three GPU tests, two pure-CPU unit tests
  tools/                      oracles and probes the kernels are checked against

Dropped from the old branch: c/deepseek_v4.c (JustVugg#165 owns it), and the
c/coli, c/openai_server.py, c/tok.h and docs/api.md edits, which belong to
whichever engine lands rather than to a kernel PR.

The kernels are self-contained by construction -- backend_cuda_dsv4.h
includes only <stdint.h>, and the .cu only its own header and the CUDA
runtime -- so they build and their CPU tests run with no engine present.
That is what makes them usable as a tier: JustVugg#165 calls in, nothing calls out.

Makefile: the kernel rules only. deepseek_v4$(EXE) is gone; the .o rules,
dsv4-cuda-test and the two header unit tests remain. DSV4_CUDA_OBJ is empty
unless CUDA=1. VLLM_MHC/DEEPGEMM/FLASHINFER are marked UNSUPPORTED in place
-- eight configurations, none compiled by CI, each needing an external
checkout -- and DEEPGEMM's flag line appends instead of replacing, so it no
longer discards $(CUDA_GENCODE) and -ccbin.

Verified: colibri, deepseek-v4, cuda-test and bench-omp-grain all still
resolve; dsv4-cuda-test resolves; test_dsv4_mhc and test_dsv4_quant build
and pass on CPU. The GPU tests need a device and are compile-checked only.
ZacharyZcR added a commit to ZacharyZcR/colibri that referenced this pull request Aug 7, 2026
Rebasing on dev turned check-env red, which is the point of it:

  - read by the code but missing from coli_env.h: COLI_MTP_GUARD_PCT
  - read by the code but missing from coli_env.h: COLI_MTP_GUARD_WINDOW
  - read by the code but missing from coli_env.h: COLI_V4_EXPERT_PREFETCH
  - read by the code but missing from coli_env.h: CUDA_EXPERT_LOAD_BALANCE
  - read by the code but missing from coli_env.h: INK_METAL_SHARED
  - read by the code but missing from coli_env.h: V4_PREFIX_LOG

Types come from the call sites, not from the names: the three read
through atoi() are CE_INT, INK_METAL_SHARED and COLI_V4_EXPERT_PREFETCH
are tested as switches so CE_BOOL, and V4_PREFIX_LOG is presence-checked
like the INK_PREFIX_LOG row already in the table, so CE_STR.

Two of them belong to deepseek_v4.c, which JustVugg#165 added and which has no
engine bit here, so add CE_DSV4. It is deliberately NOT folded into
CE_ALL: that flag means the four engines sharing route_trace.h, rans.h
and omp_tune.h, and deepseek_v4.c includes none of the three -- putting
it in CE_ALL would claim every shared-header knob is read by V4 too.

Also refresh the header comment, which had gone stale in the same way the
table would have: 212 -> 220. The "187 scattered getenv() call sites"
figure is removed rather than corrected -- nothing verifies it, so it can
only rot again. `make check-env` prints the live count and is the one
number in that comment that cannot go stale.

check-env: 220 variables, registry matches the sources.
ZacharyZcR added a commit to ZacharyZcR/colibri that referenced this pull request Aug 7, 2026
This is JustVugg#772 rescoped. It was an engine plus its kernels and it would not
start below 145.3 GiB of VRAM, which makes it a threshold -- the one thing
this project does not ship. @jazir555 and @rafpigna said so, @JustVugg
agreed, and the request was not negotiable: a GPU backend here holds the
hot part and falls back for the rest.

The split @JustVugg proposed is the right one. JustVugg#165 landed the DeepSeek V4
engine with the streaming machinery and no CUDA at all; this was the CUDA
with no tier. Neither runs the model on hardware anyone owns. So the engine
file belongs to JustVugg#165 and this keeps only the kernels:

  backend_cuda_dsv4*.{cu,h}   dense matmul, batched attention, routed MoE
  dsv4_mhc.h, dsv4_quant.h    the CPU-side formats the kernels consume
  tests/                      three GPU tests, two pure-CPU unit tests
  tools/                      oracles and probes the kernels are checked against

Dropped from the old branch: c/deepseek_v4.c (JustVugg#165 owns it), and the
c/coli, c/openai_server.py, c/tok.h and docs/api.md edits, which belong to
whichever engine lands rather than to a kernel PR.

The kernels are self-contained by construction -- backend_cuda_dsv4.h
includes only <stdint.h>, and the .cu only its own header and the CUDA
runtime -- so they build and their CPU tests run with no engine present.
That is what makes them usable as a tier: JustVugg#165 calls in, nothing calls out.

Makefile: the kernel rules only. deepseek_v4$(EXE) is gone; the .o rules,
dsv4-cuda-test and the two header unit tests remain. DSV4_CUDA_OBJ is empty
unless CUDA=1. VLLM_MHC/DEEPGEMM/FLASHINFER are marked UNSUPPORTED in place
-- eight configurations, none compiled by CI, each needing an external
checkout -- and DEEPGEMM's flag line appends instead of replacing, so it no
longer discards $(CUDA_GENCODE) and -ccbin.

Verified: colibri, deepseek-v4, cuda-test and bench-omp-grain all still
resolve; dsv4-cuda-test resolves; test_dsv4_mhc and test_dsv4_quant build
and pass on CPU. The GPU tests need a device and are compile-checked only.
ErikTromp pushed a commit to SensAI-PT/aviary that referenced this pull request Aug 9, 2026
…wrong

The site said colibri runs GLM-5.2. It has run four families since v1.3.0, and
two of the model cards contradicted the project outright:

  Inkling   975B MoE - Planned  -> Live   (docs/inkling.md ships; runs on 25 GB)
  Kimi K2   1T MoE   - Planned  -> Kimi K3, 2.8T MoE, Live

Telling visitors that Inkling and Kimi are on the roadmap, while the README
front page says both run today, is the kind of contradiction someone finds in
thirty seconds.

Hero rewritten rather than merely widened. The old line worked because it put
two incompatible things next to each other -- an enormous model, your machine.
Replacing that with a range ('744B to 2.8T') informs and stops landing; the
contradiction was the message. It now reads:

  These models do not fit in your machine. They run in it anyway.

Same rhetorical shape as the copy further down the page ('Weights are not state
to hold. They are data to stage.'), so the page speaks with one voice. The
subtitle now also explains WHY it is possible -- a MoE token touches a small
fraction of the weights -- which was missing entirely and is what turns an
unbelievable claim into an understandable one. The numbers move there, where
they serve the reader who wants detail instead of the one who is skimming.

DeepSeek and Qwen3 deliberately stay 'Planned': JustVugg#165 and JustVugg#712 are not merged,
and the site should not promise what the code does not do.

Text only. No CSS, structure or script changes -- the sole markup edits are the
two cards' buttons becoming real links now that both models are runnable.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
ErikTromp pushed a commit to SensAI-PT/aviary that referenced this pull request Aug 9, 2026
Native fp8 checkpoints write the fmt=8 block scale as one UE8M0 byte per block
rather than one f32. The geometry is identical -- same shape, same meaning, same
multiply -- so the load path now reads the sidecar with st_read_scale_f32, which
accepts either encoding and always yields f32.

matmul_fp8 is untouched and stays a single implementation with no branch in the
hot loop, which is the point of expanding at load rather than decoding per block.

Every other format still goes through st_read_f32_cap exactly as before: fmt
0/1/2/4/5/6 are byte-for-byte unchanged. An f32-scaled fmt=8 container behaves
identically too, since st_read_scale_f32 dispatches to st_read_f32 for an F32
sidecar -- the same call that ran before.

Requested by DrewZt on JustVugg#165, where it was the one shared-infrastructure blocker
for moving the DeepSeek V4 engine onto the common quant path.

Verified against the real DeepSeek-V4-Flash-0731 checkpoint: the attention
sidecars read back as exactly 2^-12 and 2^-11, and the dequantised weights land
at |max| 0.094 / |mean| 0.018. All four engines build; make check 288 tests OK.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
ErikTromp pushed a commit to SensAI-PT/aviary that referenced this pull request Aug 9, 2026
ErikTromp pushed a commit to SensAI-PT/aviary that referenced this pull request Aug 9, 2026
Add DeepSeek V4 Flash target-only CPU inference (@DrewZt)

The engine loads official sharded DeepSeek V4 safetensors, implements
target prefill and greedy decode, compressed attention, mHC, routed and
shared experts, and RAM-tiered ExpertStore caching. It is wired into
`coli run`, `coli chat`, `coli serve` and `coli web`, and reuses the
shared `st.h` indexing and `quant.h` fmt7 MXFP4 matmul.

Merged with one fixup folded into this commit rather than landing a
broken tree: `v4_serve_rss_gb` calls getrusage(RUSAGE_SELF) but the
GENERATE_STATS unit never included <sys/resource.h>, so
COLI_V4_UNIT_GENERATE_STATS.o failed to compile on Linux and took the
tiny-oracle CI job with it. Windows was unaffected because compat.h
already supplies a getrusage shim, which is why only one of the fourteen
checks was red. The include follows the guard the other engines use
(colibri.c:35, inkling.c:31, kimi_k3.c:71).

That CI had never run at all: the workflow sat in `action_required` for
eighteen days, so the first execution on this branch is also the first
signal the author ever received.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
ErikTromp pushed a commit to SensAI-PT/aviary that referenced this pull request Aug 9, 2026
DeepSeek V4 (JustVugg#165) landed on dev. Two hunks, both "keep both":

- c/Makefile: dev reflowed .PHONY across lines and added the deepseek-v4
  targets plus a separate bench-omp-grain line; this branch had added hip-dll
  to the same list. Took dev's form and re-inserted hip-dll after cuda-dll.
- c/tools/clean.py: both sides appended to the artifact list. Kept both blocks.

Merged rather than rebased so the commit SHAs, the CI results just unblocked
for this PR, and the review comments anchored to them all survive.
ErikTromp pushed a commit to SensAI-PT/aviary that referenced this pull request Aug 9, 2026
## The roster said four families; there are five

DeepSeek V4 Flash landed in JustVugg#165 and was tuned in JustVugg#839, but the README still
opened with "Four families run today" and its table stopped at OLMoE. Someone
scanning the front page had no way to learn the engine exists.

It is now in the opening line, in the roster table, and in the hardware table
above it -- ~167 GB on disk, 16 GB of RAM minimum and 22 comfortable, measured
on the reference box rather than estimated.

## The DeepSeek section described a version that no longer exists

It called the path "experimental" and said "DSpark is intentionally kept for a
separate stacked follow-up". DSpark is in, and the honest state is more
interesting than either claim:

  - the checkpoint streams with no conversion -- routed experts stay native fp4,
    dense stays fp8-e4m3 with UE8M0 block scales
  - greedy, one KV slot, no tools or grammar yet: said plainly, because finding
    that out from a rejected request is worse
  - --ram is the knob that matters. 43 x 256 routed experts are ~137 GiB and a
    token touches 301 of them, so the cache hit rate sets tok/s. It changes
    speed only, never output.
  - speculative drafting is implemented, verified, and OFF, with the numbers
    that made that call: 1 accepted in 15 for the markov drafter, 10 in 24 for
    full MTP, and a 14-token answer that took 495 seconds to replay its
    rejected suffixes

That last one is the point of documenting it at all. The code stays, the
measurement stays beside it, and whoever retries this on faster storage starts
from evidence instead of from scratch.

## Repo layout described a tree that has not existed since July

It listed `glm.c`, renamed to `colibri.c` in JustVugg#391 three weeks ago, and no other
engine -- so the file that runs GLM was wrong and the four files that run
everything else were missing. Also absent: quant.h, compat.h, expert_store.h,
route_trace.h, kv_prefix.h, the Metal and Vulkan backends, resource_plan.py,
and docker/.

Every path and every make target in the new listing was checked to exist on
this branch before it was written down.

The rule behind the layout is now stated, because it is the one that keeps
being violated: one .c per model family, over shared single headers. An engine
owns its architecture and nothing else. The recurring defects in this tree --
the OpenMP thread count, the KV prefix reuse, the NaN router guard -- are all
the same shape: a mechanism that landed in one engine and never reached its
siblings.

## Also

`#### Other supported models` now sits where the roster table is, so
`[Full roster ↓](#other-supported-models)` in the opening paragraph resolves to
the table instead of to prose four sections earlier.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

model-support Supporto a nuovi modelli needs-rebase Confligge, serve rebase dell'autore

Projects

None yet

Development

Successfully merging this pull request may close these issues.

9 participants