mlx-bun 0.0.12 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +40 -24
- package/bin/mlx-bun.mjs +1 -1
- package/docs/{design → archive}/hlg-sampling.md +3 -3
- package/docs/{investigations → archive/investigations}/hlg-sampling-investigation.md +1 -1
- package/docs/archive/investigations/pareto-specialized-runtime-findings.md +92 -0
- package/docs/{planning → archive/planning}/chat-ui-vision.md +1 -1
- package/docs/archive/planning/release-notes-v0.0.13.md +77 -0
- package/docs/{planning → archive/planning}/release-notes-v0.0.9.md +1 -1
- package/docs/{planning → archive/planning}/website-readme-pass-plan.md +1 -1
- package/docs/design/colibri-glm52-port.md +8 -1
- package/docs/design/compat-cli-surface-design.md +1 -1
- package/docs/design/decode-speed-program.md +1 -1
- package/docs/design/docs-reorg-plan.md +1 -1
- package/docs/design/dspark-serving-program.md +1 -1
- package/docs/design/dspark-speculative-decoding.md +53 -3
- package/docs/design/grammar-spec-batching-integration.md +1 -1
- package/docs/design/mlx-lm-serving-execution-seam.md +81 -0
- package/docs/design/orpo-dynamic-lambda.md +1 -1
- package/docs/design/orpo-future-enhancements.md +1 -1
- package/docs/design/orpo-training.md +2 -2
- package/docs/design/parity-tier-dag.md +1 -1
- package/docs/design/repo-cleanup-plan.md +46 -4
- package/docs/design/segmented-backward-training.md +2 -2
- package/docs/design/ssd-kv-cold-tier.md +127 -0
- package/docs/design/turboquant-weights.md +467 -0
- package/docs/design/w4a16-compute-precision-spike.md +1 -1
- package/docs/design/web-chat-redesign.md +5 -5
- package/docs/planning/chunk-task-roadmap.md +1 -1
- package/docs/planning/curve-sampler-research-plan.md +4 -4
- package/docs/planning/memory-docs-and-dag-plan.md +1 -1
- package/docs/planning/release-notes-v0.2.0.md +49 -0
- package/docs/planning/video-series.md +421 -0
- package/docs/reference/cli.md +15 -4
- package/docs/reference/distribution.md +1 -0
- package/docs/reference/features-matrix.md +3 -1
- package/docs/reference/library-api.md +41 -1
- package/docs/reference/models.md +33 -0
- package/docs/reference/server-api.md +86 -19
- package/docs/reference/server-config.md +57 -33
- package/package.json +2 -2
- package/src/anthropic.ts +92 -3
- package/src/chat-template.ts +34 -1
- package/src/cli.ts +131 -36
- package/src/config.ts +10 -0
- package/src/eval/kl.ts +27 -20
- package/src/eval/runner.ts +23 -4
- package/src/eval/tasks/bfcl.ts +2 -1
- package/src/eval/tasks/gsm8k.ts +2 -1
- package/src/eval/tasks/hashhop.ts +2 -1
- package/src/eval/tasks/humaneval.ts +5 -4
- package/src/eval/tasks/ifeval.ts +2 -1
- package/src/eval/tasks/mmlu.ts +2 -1
- package/src/expert-io.ts +3 -1
- package/src/expert-offload.ts +3 -1
- package/src/expert-trace.ts +3 -1
- package/src/fit.ts +24 -43
- package/src/flags.ts +7 -9
- package/src/generate.ts +107 -92
- package/src/grammar.ts +2 -1
- package/src/harness-pi.ts +1 -1
- package/src/index.ts +20 -0
- package/src/jobs/job-entry.ts +3 -2
- package/src/kv-scheme.ts +199 -0
- package/src/kv-store.ts +370 -205
- package/src/media-fetch.ts +19 -3
- package/src/memory/model.ts +2 -1
- package/src/memory/vault.ts +2 -1
- package/src/memory-plan.ts +18 -0
- package/src/mlx/ffi.ts +8 -11
- package/src/mlx/ops.ts +31 -6
- package/src/model/batched-mask.ts +1 -1
- package/src/model/batched-quant.ts +1 -1
- package/src/model/batched-rotating-quant.ts +43 -97
- package/src/model/batched-rotating-state.ts +73 -0
- package/src/model/batched-rotating.ts +56 -105
- package/src/model/batched-row-storage.ts +127 -0
- package/src/model/compiled-decode.ts +3 -2
- package/src/model/factory.ts +44 -49
- package/src/model/gemma4-base.ts +163 -10
- package/src/model/generated/gemma4-12b.ts +50 -146
- package/src/model/generated/gemma4-26b.ts +32 -92
- package/src/model/generated/gemma4-e4b.ts +26 -74
- package/src/model/glm52-cache.ts +19 -9
- package/src/model/glm52-memory.ts +28 -1
- package/src/model/minicpm5.ts +2 -1
- package/src/model/profile.ts +433 -0
- package/src/model/qwen3-delta.ts +98 -2
- package/src/model/qwen3-mrope.ts +252 -0
- package/src/model/qwen3_5.ts +217 -25
- package/src/native/frame_extract.swift +140 -0
- package/src/native-pack.ts +13 -6
- package/src/pi-web.ts +6 -5
- package/src/prompt-cache.ts +2 -2
- package/src/quantize/atomic-output.ts +38 -0
- package/src/quantize/calibration.ts +2 -1
- package/src/quantize/config-writer.ts +6 -0
- package/src/quantize/index.ts +28 -1
- package/src/quantize/job.ts +11 -0
- package/src/quantize/quantizer.ts +265 -100
- package/src/quantize/rotate.ts +603 -0
- package/src/quantize/safetensors-writer.ts +79 -1
- package/src/quantize/sensitivity.ts +41 -59
- package/src/quantize/weight-transform.ts +292 -0
- package/src/responses.ts +102 -2
- package/src/runtime-config.ts +67 -0
- package/src/sampler.ts +272 -0
- package/src/serve/admin-routes.ts +184 -0
- package/src/serve/aux-routes.ts +132 -0
- package/src/serve/batch-scheduler.ts +200 -87
- package/src/serve/completion-executor.ts +346 -0
- package/src/serve/completion-sink.ts +157 -0
- package/src/serve/discovery-routes.ts +205 -0
- package/src/serve/generation-gateway.ts +116 -109
- package/src/serve/kv-budget.ts +14 -0
- package/src/serve/lab-routes.ts +338 -0
- package/src/serve/model-admin-routes.ts +153 -0
- package/src/serve/prompt-response-trace.ts +147 -0
- package/src/serve/request-plan.ts +158 -0
- package/src/serve/static-routes.ts +101 -0
- package/src/server.ts +768 -1367
- package/src/spec/dflash-source.ts +2 -1
- package/src/spec/dspark/module-dflash.ts +1 -1
- package/src/spec/glm52-mtp-source.ts +8 -0
- package/src/spec/qwen-mtp-source.ts +431 -0
- package/src/spec/serve-loop.ts +36 -68
- package/src/ssd-cache.ts +17 -14
- package/src/ssd-durability.ts +195 -0
- package/src/train/flash-cce.ts +12 -11
- package/src/train/forward.ts +32 -1
- package/src/train/loss.ts +2 -1
- package/src/train/segmented.ts +4 -3
- package/src/train/trainer.ts +3 -2
- package/src/vision/preprocess.ts +1 -1
- package/src/vision/prompt.ts +47 -1
- package/src/vision/qwen3vl-preprocess.ts +409 -0
- package/src/vision/qwen3vl-prompt.ts +196 -0
- package/src/vision/qwen3vl-tower.ts +513 -0
- package/src/vision/video-frames.ts +148 -0
- package/src/web/app.js +10 -3
- package/src/web/src/chat.ts +12 -5
- package/src/weights.ts +81 -26
- /package/docs/{investigations → archive/investigations}/chunk-finetune-experiment.md +0 -0
- /package/docs/{investigations → archive/investigations}/colibri-oracle-pin.md +0 -0
- /package/docs/{investigations → archive/investigations}/curve-bisector-routing.md +0 -0
- /package/docs/{investigations → archive/investigations}/curve-runs/bisector-route.json +0 -0
- /package/docs/{investigations → archive/investigations}/curve-runs/bisector-trace.json +0 -0
- /package/docs/{investigations → archive/investigations}/curve-runs/curve-terrain.json +0 -0
- /package/docs/{investigations → archive/investigations}/curve-runs/curve-terrain.svg +0 -0
- /package/docs/{investigations → archive/investigations}/curve-terrain.html +0 -0
- /package/docs/{investigations → archive/investigations}/decode-roofline-lookagain.md +0 -0
- /package/docs/{investigations → archive/investigations}/dspark-handoff.md +0 -0
- /package/docs/{investigations → archive/investigations}/expert-offload-single-user-moe.md +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-ab.html +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-explorer.html +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-figs/cliff.svg +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-figs/cross.svg +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-figs/edges.svg +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-figs/k20-grids.svg +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-figs/k20-peaks.svg +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-figs/lw-curve.svg +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-figs/terrain.svg +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-report.html +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-ab.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-blind-prompts.md +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-blind.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-cliff.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-cross.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-edge.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-eval1.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-frontier.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-grid.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-grid2.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-lw-coarse.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/hlg-map.json +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/run0-original.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runA-recommended.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runAA-cliff-cpm5.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runAB-grid2-e4b.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runAC-peak-e4b-partial.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runAD-ab-samples.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runAE-edge-e4b.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runAF-logit-calibration.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runAG-eval-config2.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runB-gain-variants.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runC-pivots.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runD-oetf.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runE-eotf.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runF-shaper-working.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runG-shaper-sweep.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runH-wsweep.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runI-asweep.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runJ-knobmap.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runK-frontier.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runL-widemap.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runM-frontier-emb.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runN-verify.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runO-frontier-seed5000.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runP-grid-AxSm.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runQ-grid-tgW.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runR-blind-transcript.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runS-cross-coherence.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runT-cross-cpm5.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runU-cross-12b.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runV-lw-e4b.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runW-lw-12b.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runX-lw-cpm5.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runY-cliff-e4b.log +0 -0
- /package/docs/{investigations → archive/investigations}/hlg-runs/runZ-cliff-12b.log +0 -0
- /package/docs/{investigations → archive/investigations}/indexshare-performance-spike.md +0 -0
- /package/docs/{investigations → archive/investigations}/kernel-perf-review-2026-07.md +0 -0
- /package/docs/{investigations → archive/investigations}/lab-build-journal.md +0 -0
- /package/docs/{investigations → archive/investigations}/openwiki-evaluation.md +0 -0
- /package/docs/{investigations → archive/investigations}/orpo-base-uf-experiment-and-directions.md +0 -0
- /package/docs/{investigations → archive/investigations}/orpo-flash-cce-pin-leak.md +0 -0
- /package/docs/{investigations → archive/investigations}/orpo-uf-testing-handoff.md +0 -0
- /package/docs/{investigations → archive/investigations}/pi-builtin-investigation.md +0 -0
- /package/docs/{investigations → archive/investigations}/segmented-backward-handoff.md +0 -0
- /package/docs/{investigations → archive/investigations}/starter-model-port-handoff.md +0 -0
- /package/docs/{investigations → archive/investigations}/steel-flash-cce-handoff.md +0 -0
- /package/docs/{investigations → archive/investigations}/trainer-validation-experiment.md +0 -0
- /package/docs/{planning → archive/planning}/chat-ui-vision-memory-first.md +0 -0
- /package/docs/{planning → archive/planning}/journal.md +0 -0
- /package/docs/{planning → archive/planning}/release-notes-v0.0.10.md +0 -0
- /package/docs/{planning → archive/planning}/release-notes-v0.0.11.md +0 -0
- /package/docs/{planning → archive/planning}/release-notes-v0.0.12.md +0 -0
- /package/docs/{planning → archive/planning}/web-ui-pass-plan.md +0 -0
|
@@ -0,0 +1,467 @@
|
|
|
1
|
+
# TurboQuant weights — rotation-folded quantization (design)
|
|
2
|
+
|
|
3
|
+
Status: active. Fold recipes and artifact-pipeline integration are implemented;
|
|
4
|
+
quality/release gates remain in PLAN.md "TurboQuant weights". Companion to
|
|
5
|
+
docs/design/turboquant-kv.md (the landed KV leg).
|
|
6
|
+
|
|
7
|
+
## What it is
|
|
8
|
+
|
|
9
|
+
Fold an orthogonal rotation R offline into producer/consumer weight
|
|
10
|
+
pairs so every weight matrix is quantized in a rotated basis where
|
|
11
|
+
outlier channels are smeared into near-Gaussian marginals — then
|
|
12
|
+
quantize with mlx's EXISTING formats (affine / mxfp4 / nvfp4). Zero
|
|
13
|
+
runtime cost, zero new kernels, output loadable by stock mlx-lm. The
|
|
14
|
+
QuaRot/SpinQuant family; composes with (does not replace) per-layer
|
|
15
|
+
allocation (OptiQ-style) and calibration.
|
|
16
|
+
|
|
17
|
+
Target: `Qwen3.8-27B-MTP-turbo` beating OptiQ-4bit / plain 4bit at
|
|
18
|
+
equal effective bpw (gate: ppl + frozen 6-task eval, eval DB rows).
|
|
19
|
+
|
|
20
|
+
## Oracle chain
|
|
21
|
+
|
|
22
|
+
"The oracle is whoever ships it": the folding mechanics come from the
|
|
23
|
+
reference repos, read 2026-08-17 (agent fan-out, full-file reads):
|
|
24
|
+
|
|
25
|
+
- **QuaRot** (arXiv:2404.00456, github spcl/QuaRot):
|
|
26
|
+
`fake_quant/rotation_utils.py` (fuse_ln_linear, fuse_layer_norms,
|
|
27
|
+
rotate_model), `fake_quant/hadamard_utils.py` (get_hadK, matmul_hadU,
|
|
28
|
+
random_hadamard_matrix), `fake_quant/model_utils.py`.
|
|
29
|
+
- **SpinQuant** (arXiv:2405.16406, github facebookresearch/SpinQuant):
|
|
30
|
+
`utils/fuse_norm_utils.py` (a copy of QuaRot's γ-fold),
|
|
31
|
+
`eval_utils/rotation_utils.py` (R1/R2 folds), `optimize_rotation.py`
|
|
32
|
+
(Cayley-SGD learned R — deferred to W5).
|
|
33
|
+
|
|
34
|
+
Weight layout: torch and MLX `nn.Linear` are both `[out, in]`,
|
|
35
|
+
`y = x @ W.T` — their fold table transfers verbatim.
|
|
36
|
+
|
|
37
|
+
## The recipe (weight-only, fully offline)
|
|
38
|
+
|
|
39
|
+
Order matters: γ-fold FIRST (R1 commutes only with gain-free RMSNorm),
|
|
40
|
+
then R1, then R2, then quantize.
|
|
41
|
+
|
|
42
|
+
**0. Untie embeddings** if `tie_word_embeddings` (clone into a separate
|
|
43
|
+
lm_head, set the flag false). Required: step 1 transforms lm_head but
|
|
44
|
+
not embed_tokens. (SpinQuant `ptq.py` does exactly this.)
|
|
45
|
+
|
|
46
|
+
**1. γ-fold (norm fusion)** — for each RMSNorm feeding linears,
|
|
47
|
+
`W' = W · diag(γ)` on the INPUT dim (columns of [out,in]), then set that
|
|
48
|
+
norm's γ to ones (keep the module + its eps — do NOT copy QuaRot's
|
|
49
|
+
replacement RMSN, which hardcodes eps=1e-5; our subjects use 1e-6):
|
|
50
|
+
- input_layernorm → q/k/v_proj
|
|
51
|
+
- post_attention_layernorm → gate/up_proj
|
|
52
|
+
- final norm → lm_head
|
|
53
|
+
|
|
54
|
+
**2. R1 residual fold** — one hidden-size orthogonal R1:
|
|
55
|
+
|
|
56
|
+
| matrix | transform | reason |
|
|
57
|
+
|---|---|---|
|
|
58
|
+
| embed_tokens | `W @ R1` | writes residual (rows are embeddings) |
|
|
59
|
+
| q/k/v_proj | `W @ R1` | reads residual (input dim) |
|
|
60
|
+
| o_proj (+bias) | `R1ᵀ @ W` | writes residual (output dim) |
|
|
61
|
+
| gate/up_proj | `W @ R1` | reads residual |
|
|
62
|
+
| down_proj (+bias) | `R1ᵀ @ W` | writes residual |
|
|
63
|
+
| lm_head | `W @ R1` | reads residual |
|
|
64
|
+
|
|
65
|
+
Q/K outputs untouched → RoPE unaffected. Input-side folds never touch
|
|
66
|
+
biases (bias lives on the output).
|
|
67
|
+
|
|
68
|
+
**3. R2 per-head v/o fold — SpinQuant's version, NOT QuaRot's.** Per
|
|
69
|
+
layer, one head_dim-sized orthogonal R2 applied block-diagonally:
|
|
70
|
+
v_proj output blocks get R2ᵀ, o_proj input blocks get R2; softmax
|
|
71
|
+
weights are R2-invariant so it cancels exactly, incl. under GQA (same
|
|
72
|
+
R2 for all heads; repeat_kv replicates whole heads). QuaRot's variant
|
|
73
|
+
folds a FULL Hadamard into o_proj and needs an ONLINE cross-head
|
|
74
|
+
Hadamard (`online_partial_had`) to cancel — folding its v-side alone
|
|
75
|
+
breaks the network. Skip QuaRot's pairing entirely.
|
|
76
|
+
|
|
77
|
+
**4. Quantize** the folded weights with the stock convert path
|
|
78
|
+
(affine g64 / mxfp4 / nvfp4 arms).
|
|
79
|
+
|
|
80
|
+
Implementation seam (2026-08-20): `WeightTransform` separates pure tensor-name
|
|
81
|
+
planning from lazy tensor application. Llama, Qwen3.5 trunk, and Qwen MTP are
|
|
82
|
+
adapters over that contract; `quantizeModelDir` applies the selected plan in its
|
|
83
|
+
existing module walk. `mlx-bun convert --rotate-weights` selects the adapter,
|
|
84
|
+
and `optiq_metadata.json` records the transform id, family, seed, and deviations.
|
|
85
|
+
Mixed-precision calibration receives a `ProbeSource`; its default builds an
|
|
86
|
+
8-bit probe through the lower-level writer instead of recursively re-entering
|
|
87
|
+
the top-level quantizer.
|
|
88
|
+
|
|
89
|
+
### Deviations from the references (decided, with reasons)
|
|
90
|
+
|
|
91
|
+
- **No embedding mean-centering.** Their `fuse_layer_norms`
|
|
92
|
+
mean-centers embedding rows (SliceGPT LayerNorm→RMSNorm trick). For
|
|
93
|
+
RMSNorm models this is NOT an exact-invariance (RMSNorm doesn't
|
|
94
|
+
subtract means) — they do it anyway; we don't, because W0's exit
|
|
95
|
+
criterion is logit parity of the folded bf16 model.
|
|
96
|
+
- **Delete the hidden R4 half-fold.** BOTH repos'
|
|
97
|
+
`rotate_mlp_output` unconditionally applies a full Hadamard to
|
|
98
|
+
down_proj's input dim right after the R1ᵀ fold — that is the offline
|
|
99
|
+
HALF of R4 and requires the runtime `online_full_had` on down_proj's
|
|
100
|
+
activation. Weight-only must skip both halves together (their line:
|
|
101
|
+
QuaRot rotation_utils.py:173 / SpinQuant eval_utils/rotation_utils.py
|
|
102
|
+
98-100). The `R1ᵀ @ W_down` part stays.
|
|
103
|
+
- **No R3.** Post-RoPE Q/K rotation exists only for KV-cache quant
|
|
104
|
+
(their code registers it only when k_bits < 16). Our KV story is the
|
|
105
|
+
landed TurboQuant KV codec — online rotation remains KV-only.
|
|
106
|
+
- **Fold precision: fp32, not fp64.** References fold in fp64 (fp16-era
|
|
107
|
+
caution). Our weights are bf16 (8-bit mantissa); fp32 accumulation at
|
|
108
|
+
n≲6k leaves ample headroom. Escape hatch if the W0 parity gate fails:
|
|
109
|
+
generate fold goldens in the oracle venv (mlx CPU float64).
|
|
110
|
+
|
|
111
|
+
### R generation
|
|
112
|
+
|
|
113
|
+
- Random-Hadamard R1 = `diag(±1 signs) · H_n / √n` (QuIP#-style).
|
|
114
|
+
Non-pow-2 n via Kronecker: n = K·2^m with hardcoded H_K, K ∈ {12, 20,
|
|
115
|
+
28, 36, 40, 44, 52, 60, 108, 140, 156, 172}; else n must be pow-2.
|
|
116
|
+
QR-of-Gaussian `random` mode works for any n (fold-time only, speed
|
|
117
|
+
irrelevant).
|
|
118
|
+
- R2 default: plain Hadamard of head_dim (must be pow-2) or any
|
|
119
|
+
orthogonal.
|
|
120
|
+
- Seed-pin and persist R1/R2 (sidecar JSON in the output snapshot) for
|
|
121
|
+
reproducible artifacts; R is never needed at runtime.
|
|
122
|
+
- W5 (only if random-R wins first): SpinQuant Cayley-SGD learned R1 +
|
|
123
|
+
per-layer R2, folded identically afterward.
|
|
124
|
+
|
|
125
|
+
## W1 — Qwen3.8 (qwen3_5) corridor map (2026-08-18, from src/model/qwen3_5.ts
|
|
126
|
+
+ src/spec/qwen-mtp-source.ts + src/vision/qwen3vl-tower.ts + tensor dumps)
|
|
127
|
+
|
|
128
|
+
**R2 is architecturally OFF for this family:** full attention computes
|
|
129
|
+
`o_proj(attention_output · σ(gate))` — q_proj emits 2×head_dim per head and
|
|
130
|
+
the gate multiplies the attention output ELEMENTWISE in head space. An
|
|
131
|
+
elementwise gate does not commute with a per-head rotation, so only γ+R1
|
|
132
|
+
apply. hidden 5120 = 20·256 — mlx's hadamard_transform takes it natively
|
|
133
|
+
(m·2^k, m ∈ {1,12,20,28}; verified live).
|
|
134
|
+
|
|
135
|
+
Trunk corridors (prefix `language_model.`):
|
|
136
|
+
- readers (@R1 input dim, γ folded in): self_attn.q/k/v_proj,
|
|
137
|
+
linear_attn.in_proj_{qkv,z,b,a}, mlp.gate/up_proj, lm_head (γ = model.norm)
|
|
138
|
+
- writers (R1ᵀ output dim): self_attn.o_proj, linear_attn.out_proj,
|
|
139
|
+
mlp.down_proj
|
|
140
|
+
- vision: `vision_tower.merger.linear_fc2` weight+bias is the ONLY
|
|
141
|
+
vision→residual seam (deepstack is empty for qwen3_5 and not ported) —
|
|
142
|
+
output-dim fold; everything else in the tower passes through bf16
|
|
143
|
+
- untouched internal bases: q_norm/k_norm (head-space), linear_attn.{norm,
|
|
144
|
+
A_log, conv1d, dt_bias} (post-projection), rotary
|
|
145
|
+
- 27B trunk is untied; the 0.8B proof subject is tied (untie step exercised)
|
|
146
|
+
|
|
147
|
+
MTP companion (separate artifact, same seed/R1 — shared residual basis):
|
|
148
|
+
- `fc [H,2H]`: input block 0 = embedding stream (γ = pre_fc_norm_embedding),
|
|
149
|
+
block 1 = hidden stream (γ = pre_fc_norm_hidden) — per-block γ+@R1 — plus
|
|
150
|
+
an output-dim R1ᵀ fold; both pre-fc norms → ones
|
|
151
|
+
- `layers.0`: standard full-attention corridor treatment
|
|
152
|
+
- **final `norm` γ is DROPPED (→ ones):** it feeds the SHARED trunk lm_head,
|
|
153
|
+
which already carries the trunk's final γ. Draft logits therefore see
|
|
154
|
+
γ_trunk instead of γ_mtp — draft-quality-only (the verified target path is
|
|
155
|
+
exact); revisit lever = ship a private folded head inside the companion.
|
|
156
|
+
|
|
157
|
+
Small-scale proof (0.8B, dequantized from OptiQ-4bit since no bf16 is
|
|
158
|
+
published; fold-parity on dequant-vs-folded-dequant tests the fold exactly):
|
|
159
|
+
teacher-forced logits through STOCK mlx-lm (also the W2 cross-stack check) —
|
|
160
|
+
worst per-position KL 0.00353, argmax flips 2/42 positions BOTH at reference
|
|
161
|
+
margin 0.0 (exact ties). scripts/experiments/{dequant-model,fold-qwen35}.ts +
|
|
162
|
+
tq-fold-parity.py.
|
|
163
|
+
|
|
164
|
+
Quantization packaging (CORRECTED 2026-08-18: OptiQ does NOT fully strip
|
|
165
|
+
vision — its main weights omit it but `optiq/optiq_vision.safetensors`
|
|
166
|
+
carries it, and `optiq/mtp.safetensors` bundles MTP; their artifact also
|
|
167
|
+
publishes `optiq/sensitivity.json` — per-layer KL sensitivities for
|
|
168
|
+
{4,8}-bit g64 against the SAME bf16 trunk, the ready-made allocation
|
|
169
|
+
input for a GPTQ+sensitivity mixed pass. No kv_config.json is published.)
|
|
170
|
+
Our packaging: language modules quantize uniformly (embed + lm_head
|
|
171
|
+
included), `vision_tower.*` is predicate-excluded and stays bf16 both
|
|
172
|
+
IN-MAIN (mlx-vlm compatible — OptiQ's sidecar-only vision is not) and as
|
|
173
|
+
the `optiq/` sidecar, so one self-contained artifact serves text+vision
|
|
174
|
+
across stacks.
|
|
175
|
+
|
|
176
|
+
## Subject models
|
|
177
|
+
|
|
178
|
+
- **W0/W3: mlx-community/Llama-3.2-1B-Instruct-bf16** (~2.5 GB; the
|
|
179
|
+
reference repos' literal target family; 4bit sibling already proven
|
|
180
|
+
in our engine; TIED embeddings → exercises step 0). MiniCPM5-1B has
|
|
181
|
+
no published mlx bf16 (would need a dtype-convert of openbmb's torch
|
|
182
|
+
weights) — alternate subject if Llama surprises us; its geometry is
|
|
183
|
+
fold-friendly too (model_type llama, untied, head_dim 128,
|
|
184
|
+
hidden 1536 = had12 ⊗ H128, eps 1e-6).
|
|
185
|
+
- **W4: mlx-community/Qwen3.8-27B-bf16** (11 shards, 54.7 GB) +
|
|
186
|
+
`Qwen3.8-27B-MTP-bf16` companion (~850 MB, local). The companion
|
|
187
|
+
shares the trunk's residual basis → must fold consistently (W1
|
|
188
|
+
decision). DeltaNet linear-attention corridors: folding math not in
|
|
189
|
+
the papers; derive or fall back to allocation-only for those blocks
|
|
190
|
+
(community quants mark exactly those projections sensitive).
|
|
191
|
+
|
|
192
|
+
## W3/W4 measured curve (2026-08-18, RTN affine g64, ppl via stock mlx-lm
|
|
193
|
+
on the local UF-derived corpus, seq 512; M1 Max 32 GB)
|
|
194
|
+
|
|
195
|
+
**Headline: rotation-only + RTN does NOT beat plain RTN at the 4-bit
|
|
196
|
+
operating point; it wins decisively at 3-bit — the paper's law, reproduced.**
|
|
197
|
+
Per-module function-space Frobenius error is a wash at 4-bit (~0.091 all
|
|
198
|
+
arms, scripts/experiments/tq-quant-error.py — γs are tame, 0.7–2.7, no
|
|
199
|
+
module class is the culprit); the 4-bit regression is the anisotropy story
|
|
200
|
+
(isotropic rotated error vs activation-aligned plain error), which is
|
|
201
|
+
exactly what GPTQ-style calibration fixes — the composition the paper and
|
|
202
|
+
this doc already name as the real win.
|
|
203
|
+
|
|
204
|
+
0.8B lab (dequant-OptiQ source; PAIRED arms; bf16 anchor 6.41, 48×512):
|
|
205
|
+
|
|
206
|
+
| arm | bpw | ppl |
|
|
207
|
+
|---|---|---|
|
|
208
|
+
| plain 4-bit | 4.50 | 7.01 |
|
|
209
|
+
| TQ(R1+γ) 4-bit | 4.50 | 7.39 ← regression, reproduces 27B |
|
|
210
|
+
| plain 3-bit | 3.50 | 19.19 ← RTN collapse |
|
|
211
|
+
| **TQ 3-bit** | 3.50 | **14.54** ← rotation −24% ppl |
|
|
212
|
+
| plain mixed (3-bit MLP, 4-bit attn/embed) | 4.15 | 9.69 |
|
|
213
|
+
| **TQ mixed (same profile)** | 4.24 | **9.22** ← paired rotation win |
|
|
214
|
+
|
|
215
|
+
27B (32×512, same corpus): plain 4-bit 4.659 ±0.093 (4.50 bpw, 15.0 GB) ·
|
|
216
|
+
TQ 4-bit 4.923 ±0.102 (+5.7%, consistent with the lab) · **TQ-mixed
|
|
217
|
+
(4-bit attn/embed + 3-bit MLP) 4.932 ±0.098 at 3.86 bpw / 13.9 GB** —
|
|
218
|
+
matches rotated-uniform-4-bit quality at −0.64 bpw; the artifact of
|
|
219
|
+
record for the 14z M4-Pro fit lever.
|
|
220
|
+
|
|
221
|
+
AWQ-style equalization spike (norm-carried per-channel scales, α=0.5,
|
|
222
|
+
function-preservation verified at KL 0.0037/0 flips): TQ+eq 7.363 (≈no
|
|
223
|
+
change), plain+eq 7.809 (HURT — per-channel scales inside a g64 group
|
|
224
|
+
widen group ranges; real AWQ grid-searches a far gentler α and the real
|
|
225
|
+
4-bit fix is GPTQ-style compensated rounding). Scripts kept:
|
|
226
|
+
tq-collect-actstats.py + tq-equalize.ts.
|
|
227
|
+
|
|
228
|
+
**End-to-end validation of the TQ-mixed 27B artifact (2026-08-18, M1
|
|
229
|
+
Max, busy box — correctness only):** server chat with correct arithmetic
|
|
230
|
+
reasoning (thinking → `reasoning` field); vision through the folded
|
|
231
|
+
merger + sidecar correctly identifies the gradient fixture's colors over
|
|
232
|
+
HTTP; MTP via the 14g harness with the same-seed folded companion: 71%
|
|
233
|
+
acceptance, 2.40 tok/target-forward, arms token-identical (losslessness),
|
|
234
|
+
ON/OFF 0.726× (consistent with the stock 0.821× correct-but-slower
|
|
235
|
+
verdict; MTP stays opt-in).
|
|
236
|
+
|
|
237
|
+
Consequences for the release recipe: do NOT ship rotated uniform-4-bit
|
|
238
|
+
(loses to the trivial baseline); the shipping artifact is the TQ-mixed
|
|
239
|
+
≤4 bpw band where rotation is decisively ahead (paired no-rotation
|
|
240
|
+
control worse; uniform-3-bit −24% ppl). The 4.5-bpw flagship win waits
|
|
241
|
+
for the calibration composition (GPTQ on ROTATED weights — the W5 leg).
|
|
242
|
+
|
|
243
|
+
## W5a corrected-GPTQ matrix (2026-08-18; 0.8B lab, 4.5 bpw arms, 48×512
|
|
244
|
+
ppl, anchor = dequant-OptiQ 6.41 — verified lossless: original OptiQ
|
|
245
|
+
scores 6.4077)
|
|
246
|
+
|
|
247
|
+
mlx-lm's shipped GPTQ (`mlx_lm/quant/gptq.py`) has TWO real defects that
|
|
248
|
+
partially cancel: the in-loop update window is `k:k+j` (over-propagates
|
|
249
|
+
past the block edge; must be `k:j` — the k term itself writes the
|
|
250
|
+
quantized value since e·Hinv[k,k] = w−q) and `err[..., k:k+1]` indexes a
|
|
251
|
+
group-local buffer with the GLOBAL k (mlx out-of-range slice assignment
|
|
252
|
+
silently no-ops → cross-group propagation lost after block 0). Fixing
|
|
253
|
+
only err DOUBLE-compensates [j, k+j) and REGRESSES below RTN (measured:
|
|
254
|
+
7.22/7.50); fixing both = paper GPTQ. Worth an upstream report.
|
|
255
|
+
Fork: scripts/experiments/tq-gptq.py (also restricts GPTQ+fallback to
|
|
256
|
+
language modules — vision H is a zero scalar and stays bf16).
|
|
257
|
+
|
|
258
|
+
| arm | ppl |
|
|
259
|
+
|---|---|
|
|
260
|
+
| **plain + GPTQ (fixed)** | **6.741** |
|
|
261
|
+
| TQ(R1) + GPTQ (fixed) | 6.847 |
|
|
262
|
+
| plain RTN | 7.010 |
|
|
263
|
+
| TQ RTN | 7.390 |
|
|
264
|
+
|
|
265
|
+
**Verdict: calibration is the main course; rotation SUBTRACTS at the
|
|
266
|
+
4-bit band even under GPTQ on this family** (gap −1.6%; GPTQ closes half
|
|
267
|
+
the RTN→anchor gap). Rotation remains the sub-4-bpw lever (−24% at
|
|
268
|
+
3-bit). Flagship recipe = plain + GPTQ 4-bit; TQ-mixed stays the
|
|
269
|
+
small-footprint variant. 27B needs a chunked Hessian/GPTQ driver (stock
|
|
270
|
+
flow = whole bf16 model + all Hessians resident; down_proj H = 1.2 GB
|
|
271
|
+
f32 each).
|
|
272
|
+
|
|
273
|
+
## W5c 27B production results (2026-08-18)
|
|
274
|
+
|
|
275
|
+
**v2 run (uniform GPTQ-4): BROKEN artifact (ppl 306k).** Root cause,
|
|
276
|
+
evidence-backed: the compensation loop DIVERGED on layers with
|
|
277
|
+
rank-deficient calibration Hessians (layer-0 down_proj group scales grew
|
|
278
|
+
0.003 → 27 monotonically across columns, max 2.8e7; cosine ~0 vs source;
|
|
279
|
+
neighbors healthy). Early layers see low-rank activations (layer-0 input
|
|
280
|
+
= raw embeddings; rank ≤ distinct calibration tokens), so 5120 dims
|
|
281
|
+
outran the standard 1% damping — the 0.8B (1024 dims) never hit it,
|
|
282
|
+
which is why validation passed there.
|
|
283
|
+
|
|
284
|
+
**v3 fixes (all landed):** divergence guard in `gptq_one_guarded`
|
|
285
|
+
(GPTQ scales vs 4× the RTN scale ceiling per matrix; damping escalation
|
|
286
|
+
1e-2→10; RTN fallback = never worse than RTN); 4× calibration (128×512);
|
|
287
|
+
sensitivity-driven per-module bits from OptiQ's published
|
|
288
|
+
sensitivity.json (semantics: `sensitivities[b]` = measured KL GAIN at b
|
|
289
|
+
bits — first read had the sign flipped and allocated 0 modules); greedy
|
|
290
|
+
benefit-per-param to `--target-bpw`. v3 27B: 169 modules @8-bit,
|
|
291
|
+
4.80 bpw, 17.0 GB, ZERO guard triggers (the calibration bump fixed
|
|
292
|
+
conditioning outright), 64 layers in 166 min, per-layer checkpoints.
|
|
293
|
+
|
|
294
|
+
**27B ppl ladder (73×512, UF corpus, stock mlx-lm):** plain RTN-4
|
|
295
|
+
4.570 ±0.060 · OptiQ 5.14 bpw 4.574 ±0.061 · GPTQ+sens 4.80 bpw
|
|
296
|
+
4.618 ±0.061. **At 27B every sane ≥4.5-bpw recipe SATURATES this
|
|
297
|
+
instrument** — OptiQ's +0.6 bpw buys nothing measurable, and GPTQ shows
|
|
298
|
+
a small consistent deficit (likely calibration-domain mismatch:
|
|
299
|
+
calibration_v5 vs chat-flavored eval text). This contradicts the 0.8B
|
|
300
|
+
lab ordering (GPTQ clearly won there) — quantization robustness grows
|
|
301
|
+
with scale. Decision moves to task benchmarks: MMLU-100 + GSM8K-50
|
|
302
|
+
across {GPTQ-v3, plain4, OptiQ, TQ-mixed}, eval DB rows.
|
|
303
|
+
|
|
304
|
+
## FINAL BOARD + DECISION (2026-08-18 night 2)
|
|
305
|
+
|
|
306
|
+
Task evals (lean mlx-lm runner, paired items; in-engine sweep swap-thrashed
|
|
307
|
+
the box — 73 GB swap at 0.7 GB resident — killed, gap recorded below):
|
|
308
|
+
|
|
309
|
+
| arm | bpw | GB | ppl(73×512) | MMLU-100 | GSM8K-50 |
|
|
310
|
+
|---|---|---|---|---|---|
|
|
311
|
+
| **GPTQ+sens v3 (SHIPPED as mjriii/Qwen3.8-27B)** | 4.80 | 16.3 | 4.618 | 87 | **96** |
|
|
312
|
+
| plain RTN 4-bit | 4.50 | 15.0 | **4.570** | 88 | 94 |
|
|
313
|
+
| OptiQ published | 5.14 | 18.1 | 4.574 | **89** | 92 |
|
|
314
|
+
| TQ-mixed (staged, small-footprint variant) | 3.86 | 13.0 | 4.93 | 82 | 96 |
|
|
315
|
+
|
|
316
|
+
All ≥4.5-bpw arms statistically tied on every instrument — 27B quality
|
|
317
|
+
SATURATES at 4-bit; recipes differentiate below 4 bpw and on
|
|
318
|
+
completeness. THE artifact = v3 (never trails; protective recipe;
|
|
319
|
+
one-repo vision+video+MTP; additive to the ecosystem where plain-4bit
|
|
320
|
+
already exists publicly). Serve gauntlet on THE artifact through OUR
|
|
321
|
+
engine: text ✓ (23×19), image ✓ ("Green and pink"), video ✓ (gradient
|
|
322
|
+
motion described; AVFoundation chain), MTP harness 76% accept /
|
|
323
|
+
2.53 tok-per-forward with an output-divergence flag vs plain greedy
|
|
324
|
+
(consistent with verify-width reduction-order near-ties, 12B step-0
|
|
325
|
+
class — margin analysis queued; NOT claimed lossless on the card).
|
|
326
|
+
|
|
327
|
+
## Territory-mapping campaign (2026-08-18/19, Josh-directed: "map all the
|
|
328
|
+
levers before concluding TQ-off")
|
|
329
|
+
|
|
330
|
+
**sens3 arm (Josh's recipe: rotated 3-bit base + sensitivity-driven 8-bit,
|
|
331
|
+
4.26 bpw / 15.25 GB incl. vision):** ppl 4.630 ±0.058 — TIED with the
|
|
332
|
+
4.80-bpw flagship (4.618) at −0.54 bpw, and a full recovery over
|
|
333
|
+
unprotected TQ-mixed (4.93). GSM8K 46/50 = 92% (plateau band). **MMLU
|
|
334
|
+
83/100 — the 3-bit-base dip persists** (TQ-mixed scored 82): two
|
|
335
|
+
independent 3-bit-base arms at 82–83 vs the 87–89 plateau → the
|
|
336
|
+
knowledge-recall damage is SMEARED across the MLP long tail; KL-derived
|
|
337
|
+
sensitivity shields fluency, not recall. Lever under test next: rotated
|
|
338
|
+
4-bit g128 (4.25 bpw — same size, 4-bit granularity everywhere).
|
|
339
|
+
|
|
340
|
+
Perplexity proxy calibration (from our own table): deltas <~0.1 ppl are
|
|
341
|
+
task-invisible; ~0.3+ coincides with visible MMLU damage; ppl's
|
|
342
|
+
remaining role is catastrophe detection + screening. mlx kernel bound:
|
|
343
|
+
group_size ∈ {32, 64, 128} — 256+ needs custom kernels (non-goal).
|
|
344
|
+
|
|
345
|
+
**Group-size lab (0.8B ppl) + 27B g128 arm:** rotation does NOT buy
|
|
346
|
+
coarse-group tolerance at 4-bit (tax +4.7% rotated vs +4.2% plain); at
|
|
347
|
+
3-bit the dividend is real but partial (+29% vs +47%; rotated 3.25 bpw ≈
|
|
348
|
+
plain 3.5 bpw). 27B plain-4bit-g128 (4.25 bpw): ppl 4.714 (+3%), MMLU 88
|
|
349
|
+
(plateau!), **GSM8K 62% — COLLAPSE via generation-behavior damage**
|
|
350
|
+
(eyeballed: correct-but-rambling truncations + instant-EOS empty
|
|
351
|
+
outputs; single-forward instruments blind to it). Lessons: (1) ppl deltas
|
|
352
|
+
DO NOT bound task damage (+0.14 ppl ↔ −32 GSM8K pts) — the earlier
|
|
353
|
+
"~0.3 ppl = visible damage" calibration is WRONG; every finalist needs
|
|
354
|
+
generative tasks; (2) g128 disqualified for generative work.
|
|
355
|
+
|
|
356
|
+
**Run B — the full suite (rotation + GPTQ + sensitivity, 4.80 bpw,
|
|
357
|
+
17.0 GB, zero guard triggers):** ppl **4.5965** (best quantized arm,
|
|
358
|
+
tied w/ plain-4bit) · MMLU 84 · raw-completion GSM8K **24% — and the
|
|
359
|
+
collapse is a FORMAT CLIFF, not a reasoning failure**: when it answers
|
|
360
|
+
it is flawless, but 3/4 raw few-shot prompts get INSTANT EOS; under the
|
|
361
|
+
native chat template it always answers (3/5 correct at a tight token
|
|
362
|
+
cap). g128's 62% was the same failure at lower frequency. **Methodology
|
|
363
|
+
consequence: the raw-completion GSM8K column conflates math ability
|
|
364
|
+
with EOS-cliff robustness** — different quant-noise realizations
|
|
365
|
+
displace a razor-thin answer-vs-stop margin at token 0. The map now
|
|
366
|
+
carries TWO generative columns: templated GSM8K (serving-path
|
|
367
|
+
reasoning, re-run across all live arms) and raw-completion GSM8K
|
|
368
|
+
(format-robustness probe). Neither ppl nor MMLU sees any of this.
|
|
369
|
+
|
|
370
|
+
## THE FRONTIER (campaign complete, 2026-08-19 — map:
|
|
371
|
+
reports/frontier-map-2026-08-19.html)
|
|
372
|
+
|
|
373
|
+
| arm | bpw | GB | ppl | MMLU | tGSM | rawGSM | tok/s* | Pareto |
|
|
374
|
+
|---|---|---|---|---|---|---|---|---|
|
|
375
|
+
| **rot+sens48 RTN (Josh's recipe)** | 4.79 | 17.0 | 4.680 | **90** | 94 | 84 | **11.80** | **YES** |
|
|
376
|
+
| GPTQ+sens (staged flagship) | 4.80 | 17.0 | 4.618 | 87 | 94 | **96** | 11.42 | — |
|
|
377
|
+
| rot+GPTQ+sens (full suite) | 4.80 | 17.0 | **4.597** | 84 | 94 | 24 | 11.77 | — |
|
|
378
|
+
| OptiQ published | 5.14 | 18.1 | 4.574 | 89 | 94 | 92 | 8.92 | — (dominated) |
|
|
379
|
+
| **TQ-mixed** | 3.86 | 13.0 | 4.932 | 82 | 82 | 96 | 10.94 | **YES** |
|
|
380
|
+
| bf16 ceiling (streamed eval) | 16 | 54.4 | 4.552 | 87 | n/a | n/a | n/a | ref |
|
|
381
|
+
|
|
382
|
+
*busy-box, spreads 8–34% — directional until quiet benchmark.sh.
|
|
383
|
+
|
|
384
|
+
Findings of record: (1) the ≥4.5-bpw band sits AT the bf16 ceiling (ppl
|
|
385
|
+
within ~1%, MMLU within noise — a quant scoring 90 vs ceiling 87 proves
|
|
386
|
+
±3 noise); (2) BOTH Pareto points are ROTATED — rotation at 4-bit is
|
|
387
|
+
competitive exactly when paired with sensitivity allocation (the earlier
|
|
388
|
+
uniform-rotation loss concentrated in the sensitive modules, as Josh
|
|
389
|
+
hypothesized), and mandatory below 4 bpw; (3) OptiQ is dominated on all
|
|
390
|
+
three axes (its extra 0.34 bpw buys nothing and costs ~25% decode);
|
|
391
|
+
(4) GPTQ's measurable 27B contribution is ppl-only — it buys no task
|
|
392
|
+
quality at this scale and (with rotation) costs raw-format robustness;
|
|
393
|
+
(5) 3-bit kernels pay an unpack tax that eats their bandwidth win
|
|
394
|
+
(TQ-mixed slower than 4-bit arms despite −4 GB); (6) cross-engine parity
|
|
395
|
+
CERTIFIED (byte-identical greedy, ours vs stock mlx-lm, on the staged
|
|
396
|
+
flagship). Remaining before publish: promote+package the chosen artifact,
|
|
397
|
+
its serve gauntlet, quiet-box TPS, M4 Pro 24 GB cut (Josh-gated).
|
|
398
|
+
|
|
399
|
+
## Known engine gaps found in passing (not TQ defects)
|
|
400
|
+
|
|
401
|
+
- `mlx-bun perplexity` cannot score qwen3_5: it routes through
|
|
402
|
+
`trainForward`, whose cache stub lacks the DeltaNet `SSMCache.advance`
|
|
403
|
+
(`qwen3_5.ts:226` throws on BOTH plain and TQ arms identically).
|
|
404
|
+
27B ppl therefore runs through stock mlx-lm
|
|
405
|
+
(scripts/experiments/tq-ppl.py) — which doubles as the cross-stack
|
|
406
|
+
load check for the release artifact.
|
|
407
|
+
- bf16 (unquantized) qwen3_5 trunks don't load in our engine:
|
|
408
|
+
`QuantizedEmbedding.load`/`QuantizedLinear.load` hard-require `.scales`.
|
|
409
|
+
The small-scale fold proof ran through stock mlx-lm instead.
|
|
410
|
+
- `scripts/eval.ts` capability tasks at 27B swap-thrash a 32 GB box
|
|
411
|
+
(73 GB swapfiles, process 95% paged out) where the mlx-lm scoring path
|
|
412
|
+
is fine — investigate the in-engine eval memory profile.
|
|
413
|
+
- Qwen MTP via the HTTP serve lane 500s with `[slice] Invalid number of
|
|
414
|
+
indices or strides for array with dimension 3` — REPRODUCES WITH STOCK
|
|
415
|
+
ARTIFACTS (plain-4bit trunk + original mlx-community MTP companion,
|
|
416
|
+
`serve --draft-model <companion> --draft-kind mtp`, any chat request),
|
|
417
|
+
so it is a pre-existing serving-path bug, not TQ. The 14g harness path
|
|
418
|
+
(specServeRun via scripts/experiments/qwen38-mtp-ab.ts) is the green
|
|
419
|
+
gate; TQ MTP was validated through that.
|
|
420
|
+
|
|
421
|
+
## Non-goals
|
|
422
|
+
|
|
423
|
+
Mirrors the PLAN.md phase: no custom weight format / new qmm kernels,
|
|
424
|
+
no activation quant, no runtime weight rotation, no GGUF/AWQ export.
|
|
425
|
+
|
|
426
|
+
## M4 Pro 24 GB speed row (2026-08-20, mlx-bun, winner artifact)
|
|
427
|
+
|
|
428
|
+
Measured on the second reference machine (M4 Pro, 24 GB, ~273 GB/s) with
|
|
429
|
+
`sysctl iogpu.wired_limit_mb=21504` and the DeltaNet leak fix (37de0d0):
|
|
430
|
+
|
|
431
|
+
| prompt | prefill tok/s | TTFT | decode tok/s | notes |
|
|
432
|
+
|---|---|---|---|---|
|
|
433
|
+
| 1,024 | 127 | 8.1 s | 14.66 (1.1%) | chunk 2048 |
|
|
434
|
+
| 8,192 | 124 | 66 s | 14.13 (1.3%) | chunk 2048 |
|
|
435
|
+
| 32,768 | 114 | 288 s | 12.77 | chunk 1024 (peak 19.3 GB) |
|
|
436
|
+
|
|
437
|
+
- **Compute-bound decode confirmed cross-machine:** 14.7 tok/s here vs
|
|
438
|
+
11.8 on the M1 Max (400 GB/s) — the machine with 68% of the bandwidth
|
|
439
|
+
is 25% FASTER. Decode is dequant-ALU-bound, not weight-streaming-bound
|
|
440
|
+
(supporting M1 telemetry: GPU 100% @ ~266 GB/s of 400). Kernel headroom
|
|
441
|
+
to the ~24 tok/s bandwidth roofline is a future perf program.
|
|
442
|
+
- **Decode-at-depth is nearly flat** (−13% at 32× context): only 16 of 64
|
|
443
|
+
layers grow KV; DeltaNet state is constant.
|
|
444
|
+
- **Prefill transient scales with chunk × offset** (~2.8 GB at 24k with
|
|
445
|
+
2048-chunks; measured via MLX_BUN_PREFILL_MEM_LOG): on 24 GB the 32k row
|
|
446
|
+
needs 1024-token chunks (−8% prefill). Engine follow-up: serve should
|
|
447
|
+
scale prefillChunkSize from fit.ts headroom automatically.
|
|
448
|
+
- Prefill absolute rate (~125 tok/s) is the weak axis — suspected
|
|
449
|
+
DeltaNet per-token recurrence during prefill; compare against mlx-lm
|
|
450
|
+
same-box before treating as our bug (oracle-gap rule).
|
|
451
|
+
|
|
452
|
+
### Compact sibling on the M4 (same protocol, chunk 1024 all rows)
|
|
453
|
+
|
|
454
|
+
| prompt | prefill tok/s | TTFT | decode tok/s (spread) |
|
|
455
|
+
|---|---|---|---|
|
|
456
|
+
| 1,024 | 117 | 8.8 s | **17.14** (0.7%) |
|
|
457
|
+
| 8,192 | 124 | 66 s | 16.05 (2.4%) |
|
|
458
|
+
| 32,768 | 85 | 6.4 min | 13.80 (2.9%) |
|
|
459
|
+
|
|
460
|
+
**The 3-bit speed verdict is GPU-generation-dependent:** on M1 Max the
|
|
461
|
+
3-bit-heavy artifact decoded SLOWER than the 4/8 winner (10.94 vs 11.80 —
|
|
462
|
+
unpack ALU dominates); on M4 Pro it decodes FASTER (17.14 vs 14.66 —
|
|
463
|
+
newer ALU absorbs the unpack, fewer bytes win). Card guidance: M1-class →
|
|
464
|
+
winner fastest; M4-class → compact is smaller AND faster. Compact 32k
|
|
465
|
+
prefill (85 tok/s) is its weak axis. Peak not instrumented this run;
|
|
466
|
+
estimated ~16 GB at 32k (likely fits the DEFAULT 24 GB wired limit —
|
|
467
|
+
untested).
|
|
@@ -226,7 +226,7 @@ fwd `:174–270`, SG bwd `:561–726`, gates `:732`/`:739`/`:1034`/`:1130`; stag
|
|
|
226
226
|
|
|
227
227
|
**Cross-links:** [[flash-cce-metal-kernel-prototype]] · [[three-level-fidelity-tree-model]]
|
|
228
228
|
· [[opssdpa-dk-vjp-bug]] · [[e4b-forward-length-sensitivity]] ·
|
|
229
|
-
[[verify-benchmarks-against-evaldb-not-docs]] · `docs/investigations/steel-flash-cce-handoff.md`.
|
|
229
|
+
[[verify-benchmarks-against-evaldb-not-docs]] · `docs/archive/investigations/steel-flash-cce-handoff.md`.
|
|
230
230
|
|
|
231
231
|
**Sibling deferred lever** (queued together, post-run): `docs/design/orpo-future-enhancements.md`
|
|
232
232
|
→ "Deferred levers" (expose `--grad-accum`).
|
|
@@ -4,10 +4,10 @@ Status: proposed · Owner: web/chat surface · Scope: `src/web/app.html`, `src/p
|
|
|
4
4
|
|
|
5
5
|
This document merges three independent design visions, ten market-research
|
|
6
6
|
briefs, and a line-level audit of the current UI and backend into one
|
|
7
|
-
execution plan. It supersedes `docs/planning/chat-ui-vision.md` and
|
|
8
|
-
`docs/planning/chat-ui-vision-memory-first.md` as the working plan (keep
|
|
7
|
+
execution plan. It supersedes `docs/archive/planning/chat-ui-vision.md` and
|
|
8
|
+
`docs/archive/planning/chat-ui-vision-memory-first.md` as the working plan (keep
|
|
9
9
|
those two as historical inputs; this is the doc that gets executed against).
|
|
10
|
-
It also absorbs and re-prioritizes every item in `docs/planning/web-ui-pass-plan.md`
|
|
10
|
+
It also absorbs and re-prioritizes every item in `docs/archive/planning/web-ui-pass-plan.md`
|
|
11
11
|
— those bug-fixes are folded into Phase 0/1 below by number.
|
|
12
12
|
|
|
13
13
|
---
|
|
@@ -161,7 +161,7 @@ Ranked by severity, from the three-part current-state audit:
|
|
|
161
161
|
2737 lines, no documented keyboard shortcuts beyond Enter/Shift+Enter,
|
|
162
162
|
no chat search, generic non-personalized hero/empty-state.**
|
|
163
163
|
|
|
164
|
-
Plus the full tactical list already catalogued in `docs/planning/web-ui-pass-plan.md`
|
|
164
|
+
Plus the full tactical list already catalogued in `docs/archive/planning/web-ui-pass-plan.md`
|
|
165
165
|
(queue-bar array-truthiness bug, library staleness, `[object Object]` adapter
|
|
166
166
|
error, dead `status-page.html`, Routes-tab 404 in the compiled binary, stale
|
|
167
167
|
vision copy, etc.) — folded into Phase 0/1 below by number, not repeated in
|
|
@@ -814,7 +814,7 @@ bugs fixed as part of the IA move (§9 Phase 1).
|
|
|
814
814
|
## 9. Phased roadmap
|
|
815
815
|
|
|
816
816
|
Each phase is independently shippable and includes the relevant tactical
|
|
817
|
-
fixes from `docs/planning/web-ui-pass-plan.md` by number. Ordered by
|
|
817
|
+
fixes from `docs/archive/planning/web-ui-pass-plan.md` by number. Ordered by
|
|
818
818
|
effort/reward, starting with free wins, ending with differentiator
|
|
819
819
|
features. The [beat matrix](web-chat-beat-matrix.md) is the coverage
|
|
820
820
|
checklist across all phases: at any release point, every matrix row is
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
Where the MiniCPM5 chunking adapter stands and what raises real segmentation
|
|
4
4
|
quality. Companion to the chunk-eval metric vs. accuracy finding (score = well-formedness, not gold accuracy) and
|
|
5
|
-
[`docs/investigations/chunk-finetune-experiment.md`](../investigations/chunk-finetune-experiment.md).
|
|
5
|
+
[`docs/archive/investigations/chunk-finetune-experiment.md`](../investigations/chunk-finetune-experiment.md).
|
|
6
6
|
|
|
7
7
|
## Where we are
|
|
8
8
|
|
|
@@ -250,8 +250,8 @@ diversity; the audit below as methods material).
|
|
|
250
250
|
|
|
251
251
|
## 6. Why the old data is not trusted — audit of the prior experiments
|
|
252
252
|
|
|
253
|
-
Committed artifacts checked: `docs/investigations/curve-runs/*.json`,
|
|
254
|
-
`docs/investigations/hlg-runs/*`, harness sources. Severity: **INVALIDATES** /
|
|
253
|
+
Committed artifacts checked: `docs/archive/investigations/curve-runs/*.json`,
|
|
254
|
+
`docs/archive/investigations/hlg-runs/*`, harness sources. Severity: **INVALIDATES** /
|
|
255
255
|
**WEAKENS** / cosmetic.
|
|
256
256
|
|
|
257
257
|
- **F1 — INVALIDATES (the old distinctness claim).** The curve-temp family
|
|
@@ -327,5 +327,5 @@ Committed artifacts checked: `docs/investigations/curve-runs/*.json`,
|
|
|
327
327
|
- Witness probe: `scripts/experiments/curve-distinctness.ts`.
|
|
328
328
|
- Assessment: `reports/curve-designer-paper-assessment-2026-07-01.md`.
|
|
329
329
|
- Prior investigations (superseded on the points in §6):
|
|
330
|
-
`docs/investigations/hlg-sampling-investigation.md`,
|
|
331
|
-
`docs/investigations/curve-bisector-routing.md`.
|
|
330
|
+
`docs/archive/investigations/hlg-sampling-investigation.md`,
|
|
331
|
+
`docs/archive/investigations/curve-bisector-routing.md`.
|
|
@@ -21,7 +21,7 @@ are treated as the direction of record and untouched.
|
|
|
21
21
|
| `docs/design/bucketing-stage.md` | Classify-stage design (2026-06-26) | **No banner.** Core content (embeddings as candidate-narrower) is dead under "no embeddings anywhere"; the binary-question ladder survives inside the nightly BUCKET stage | **Needs a SUPERSEDED banner** (same shape as memory-synthesis's): dead = embedding narrower + silhouette; survives = capacity-by-decomposition, one-binary-question-at-a-time. |
|
|
22
22
|
| `docs/design/write-pipeline-entity.md` | Entity-keyed routing design (2026-06-26); itself "supersedes bucket-centric routing" | **No banner.** Half-dead: pure entity ROUTE (no bucket layer) is replaced by BUCKET→RESOLVE; the personal-notability checklist is dead. Survives: articles-are-THINGS, name/alias/category lookup, no-embeddings routing | **Needs a PARTIALLY SUPERSEDED banner** mapping survives/dead — otherwise its own "supersedes bucketing" claim inverts the actual chain for a newcomer. |
|
|
23
23
|
| `docs/design/memory-system.md` | M0 substrate design (vault, read tools, CLI, scheduling, consent) | **Status header is FALSE**: "synthesize is currently a safe no-op stub", "stage modules throw if called" — the pipeline is built and has produced 677+ articles. Directly contradicts `docs/reference/memory.md`. The four-adapter table + "Next implementation steps" describe the abandoned M1 sketch | **Fix the header + scope it down.** Retitle scope to "M0 substrate: vault + read path (landed)"; delete or banner the "Synthesis pipeline design (M1/M2)" and "Next implementation steps" sections, pointing at dreaming-nightly-pipeline. The substrate half (storage layout, tools, skill, scheduling, consent) is still the best writeup of the read side — keep it. |
|
|
24
|
-
| `docs/design/memory-inference-path.md` | Inference-path rework: design + measured verification | Accurate, self-bannered (BUILT + VERIFIED; batching measured a loss). It's really an investigation record | Fine as-is. Optional (low priority): move to `docs/investigations/` where measured-experiment records live. |
|
|
24
|
+
| `docs/design/memory-inference-path.md` | Inference-path rework: design + measured verification | Accurate, self-bannered (BUILT + VERIFIED; batching measured a loss). It's really an investigation record | Fine as-is. Optional (low priority): move to `docs/archive/investigations/` where measured-experiment records live. |
|
|
25
25
|
| `docs/reference/memory.md` | User-facing reference | Mostly current (synthesize description matches as-built stages; status truth fixed 2026-07-01). **But** the "Synthesis roadmap" section still tells the old four-named-LoRA / HF-adapter-pack story (memory-bucket/memory-synthesis/memory-editor LoRAs "distributed from Hugging Face") — not the plan of record (`memory-<stage>` convention, only `memory-chunk` exists, base+policy otherwise) | **Rewrite the roadmap section** to the as-built stage list + the `memory-<stage>` adapter convention; update stage names again when BUCKET/RESOLVE land. |
|
|
26
26
|
| `STATUS.md` § THE DREAMING | Live state | Current and correct (batch default 1, third-person fix merged, import paused at cursor 900/2096, inference-path landed) | Keep as the ONLY live-state location. |
|
|
27
27
|
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
# mlx-bun v0.2.0
|
|
2
|
+
|
|
3
|
+
Version 0.2.0 is the first release with the complete Qwen3.8 serving path:
|
|
4
|
+
text, images, video, thinking controls, tool calls, and native MTP speculation.
|
|
5
|
+
It also ships the serving and memory work completed since v0.0.13.
|
|
6
|
+
|
|
7
|
+
## Highlights
|
|
8
|
+
|
|
9
|
+
- Qwen3.8 image input now runs through the dedicated vision tower and mRoPE
|
|
10
|
+
path. Video content parts decode through the bundled AVFoundation helper,
|
|
11
|
+
sample frames at 2 fps, and use the gated Qwen video pipeline.
|
|
12
|
+
- Qwen native MTP can mount from a separate companion or an artifact's `mtp/`
|
|
13
|
+
directory. Rejected drafts restore recurrent DeltaNet state correctly.
|
|
14
|
+
- The default continuous scheduler now shares request planning, sampling,
|
|
15
|
+
usage accounting, cache selection, and protocol events with the strict
|
|
16
|
+
serial executor. `--batch 1` remains the explicit serial pin.
|
|
17
|
+
- Memory admission treats `max_tokens` as a ceiling. If the prompt fits, the
|
|
18
|
+
server caps generation to the safe remaining context instead of rejecting a
|
|
19
|
+
broad client default.
|
|
20
|
+
- `convert --rotate-weights` folds supported rotations before quantization.
|
|
21
|
+
The offline pipeline also gained streamed shard handling, 3-bit GPTQ, and
|
|
22
|
+
atomic output publication.
|
|
23
|
+
|
|
24
|
+
## Reliability and performance fixes
|
|
25
|
+
|
|
26
|
+
- Large Qwen models now enter the same wired-memory scope as mlx-lm during
|
|
27
|
+
serial and continuous execution. This removes the token-zero residency
|
|
28
|
+
stall on machines whose recommended working set grew beyond the old cutoff.
|
|
29
|
+
- DeltaNet prefill and batch-row extraction now copy owned cache state instead
|
|
30
|
+
of pinning whole chunk buffers.
|
|
31
|
+
- SSD prompt-cache snapshots stay dirty until atomic storage completes.
|
|
32
|
+
`POST /admin/cache/flush` and normal SIGINT/SIGTERM shutdown provide an
|
|
33
|
+
explicit durability boundary.
|
|
34
|
+
- Rotating-cache batch joins now dispatch by cache capability and preserve the
|
|
35
|
+
correct rotating signature.
|
|
36
|
+
- Qwen and GLM MTP sampling no longer passes a rank-3 logits tensor into the
|
|
37
|
+
rank-2 sampler.
|
|
38
|
+
|
|
39
|
+
## Distribution
|
|
40
|
+
|
|
41
|
+
- macOS on Apple Silicon remains the supported platform.
|
|
42
|
+
- Source and npm installs require Bun 1.4.0 or newer.
|
|
43
|
+
- Direct downloads and Homebrew use the signed, notarized self-contained
|
|
44
|
+
archive.
|
|
45
|
+
- npm and `bunx` use native pack v0.3.0, which includes MLX, the bounded expert
|
|
46
|
+
I/O helper, and the AVFoundation frame extractor.
|
|
47
|
+
|
|
48
|
+
Upgrade with `brew upgrade joshuarossi/tap/mlx-bun`, `bun update -g mlx-bun`,
|
|
49
|
+
or rerun the direct installer.
|