mlx-bun 0.5.0 → 1.0.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 +1449 -109
- package/THIRD_PARTY_NOTICES.md +882 -0
- package/bin/mlx-bun.convert.mjs +4 -0
- package/bin/mlx-bun.fuse.mjs +4 -0
- package/bin/mlx-bun.generate.mjs +4 -0
- package/bin/mlx-bun.lora.mjs +4 -0
- package/bin/mlx-bun.mjs +13 -21
- package/bin/mlx-bun.server.mjs +4 -0
- package/bin/mlx-bun.upload.mjs +4 -0
- package/dist/web/app.js +9584 -0
- package/package.json +50 -53
- package/src/cli/ane-install.ts +76 -0
- package/src/cli/args.ts +179 -0
- package/src/cli/engine-entry.ts +68 -0
- package/src/cli/inference.ts +214 -0
- package/src/cli/job-entry.ts +97 -0
- package/src/cli/library-host.ts +117 -0
- package/src/cli/main.ts +57 -0
- package/src/cli/memory-engine.ts +163 -0
- package/src/cli/memory.ts +36 -0
- package/src/cli/mlx-lm-aliases.ts +309 -0
- package/src/cli/model-choice.ts +33 -0
- package/src/cli/model-selection.ts +84 -0
- package/src/cli/module-host.ts +11 -0
- package/src/cli/module-verbs.ts +50 -0
- package/src/cli/numerical-policy.ts +12 -0
- package/src/cli/perplexity.ts +89 -0
- package/src/cli/serve-host.ts +423 -0
- package/src/cli/serve-isolated.ts +217 -0
- package/src/cli/serve-options.ts +106 -0
- package/src/cli/serve-state.ts +205 -0
- package/src/cli/serve.ts +500 -0
- package/src/cli/served-model-host.ts +102 -0
- package/src/cli/server-entry.ts +148 -0
- package/src/cli/serving-unit.ts +177 -0
- package/src/{tui.ts → cli/terminal.ts} +13 -8
- package/src/cli/worker-adapters.ts +34 -0
- package/src/cli/worker-entry.ts +272 -0
- package/src/cli/worker-unit.ts +179 -0
- package/src/engine/adapter-operation.ts +26 -0
- package/src/engine/cache-services.ts +114 -0
- package/src/engine/completion.ts +39 -0
- package/src/engine/generation-gateway.ts +358 -0
- package/src/engine/index.ts +59 -0
- package/src/engine/kv-budget.ts +120 -0
- package/src/engine/media-preparation.ts +232 -0
- package/src/engine/model-binding.ts +24 -0
- package/src/engine/model-host.ts +513 -0
- package/src/engine/model-serving.ts +89 -0
- package/src/{serve → engine}/preparation.ts +7 -5
- package/src/{serve → engine}/session-completion-engine.ts +6 -6
- package/src/engine/telemetry.ts +109 -0
- package/src/hub/downloads.ts +116 -0
- package/src/jobs/db.ts +16 -7
- package/src/jobs/events.ts +29 -0
- package/src/jobs/executable.ts +5 -0
- package/src/jobs/host.ts +51 -0
- package/src/jobs/in-process.ts +55 -0
- package/src/{contracts/jobs.ts → jobs/protocol.ts} +7 -9
- package/src/jobs/runner.ts +150 -231
- package/src/jobs/service.ts +75 -0
- package/src/jobs/sse.ts +59 -23
- package/src/jobs/worker-memory.ts +46 -0
- package/src/jobs/worker-process.ts +163 -0
- package/src/jobs/worker-supervisor.ts +258 -0
- package/src/modules.ts +58 -0
- package/src/publishing/catalog-hub.ts +18 -0
- package/src/publishing/credentials.ts +31 -0
- package/src/publishing/upload.ts +37 -0
- package/src/residency/leased-adapters.ts +21 -0
- package/src/residency/local-records.ts +16 -0
- package/src/residency/model-residency.ts +405 -0
- package/src/residency/record-index.ts +28 -0
- package/src/residency/resident-estimate.ts +50 -0
- package/src/{anthropic.ts → server/anthropic.ts} +3 -81
- package/src/server/cache-routes.ts +36 -0
- package/src/{serve → server}/chat-request.ts +10 -10
- package/src/{serve → server}/chat-stage.ts +14 -14
- package/src/{client.ts → server/client.ts} +28 -2
- package/src/{serve → server}/completion-executor.ts +33 -41
- package/src/server/decision-body.ts +55 -0
- package/src/server/decision-routes.ts +134 -0
- package/src/server/decision-wire.ts +228 -0
- package/src/{serve → server}/discovery-routes.ts +25 -82
- package/src/{serve → server}/http.ts +25 -13
- package/src/{serve → server}/inference-request.ts +5 -5
- package/src/server/job-routes.ts +20 -0
- package/src/server/media-prompt.ts +63 -0
- package/src/server/memory-completion-client.ts +46 -0
- package/src/server/model-routes.ts +192 -0
- package/src/{serve → server}/openai-wire.ts +3 -2
- package/src/{serve → server}/pipeline.ts +1 -1
- package/src/server/prompt-builder.ts +13 -0
- package/src/server/prompt-contracts.ts +17 -0
- package/src/server/proxy-routes.ts +187 -0
- package/src/server/publishing-routes.ts +41 -0
- package/src/{serve → server}/request-plan.ts +6 -8
- package/src/{serve → server}/request-prep.ts +47 -50
- package/src/{serve → server}/responses-client.ts +30 -13
- package/src/{responses.ts → server/responses.ts} +12 -93
- package/src/server/routes.ts +205 -0
- package/src/server/start.ts +72 -0
- package/src/server/status-routes.ts +108 -0
- package/src/{serve → server}/text-completion-stage.ts +25 -4
- package/src/server/text-prompt.ts +12 -0
- package/src/{serve → server}/token-streams.ts +36 -38
- package/src/server/worker-routes.ts +311 -0
- package/src/storage/paths.ts +61 -0
- package/src/web/assets.ts +37 -0
- package/src/web/{src → browser}/api.ts +5 -23
- package/src/web/browser/chat-host.ts +17 -0
- package/src/web/browser/installed-panels.ts +6 -0
- package/src/web/browser/main.ts +55 -0
- package/src/web/browser/markdown.ts +279 -0
- package/src/web/browser/memory-panel.ts +9 -0
- package/src/web/browser/palette.ts +64 -0
- package/src/web/browser/protocol.ts +13 -0
- package/src/web/browser/shell.ts +467 -0
- package/src/web/{src → browser}/status.ts +32 -36
- package/src/web/build.ts +51 -0
- package/src/web/public/app.html +1054 -0
- package/src/web/{sw.js → public/sw.js} +4 -3
- package/src/web/{vendor → public/vendor}/hljs-theme.css +2 -2
- package/src/web/{vendor → public/vendor}/hljs.js +2 -2
- package/THIRD_PARTY_LICENSES.md +0 -51
- package/docs/README.md +0 -107
- package/docs/archive/hlg-sampling.md +0 -350
- package/docs/archive/investigations/audio-input-plan.md +0 -356
- package/docs/archive/investigations/benchmark-ledger-through-v0.4.0.md +0 -3617
- package/docs/archive/investigations/chunk-finetune-experiment.md +0 -84
- package/docs/archive/investigations/colibri-glm52-port.md +0 -1486
- package/docs/archive/investigations/colibri-oracle-pin.md +0 -1284
- package/docs/archive/investigations/curve-bisector-routing.md +0 -123
- package/docs/archive/investigations/decode-roofline-lookagain.md +0 -348
- package/docs/archive/investigations/diffusion-gemma-port.md +0 -602
- package/docs/archive/investigations/dspark-handoff.md +0 -224
- package/docs/archive/investigations/expert-offload-single-user-moe.md +0 -292
- package/docs/archive/investigations/faithful-l1-consolidation.md +0 -310
- package/docs/archive/investigations/hlg-sampling-investigation.md +0 -970
- package/docs/archive/investigations/indexshare-performance-spike.md +0 -357
- package/docs/archive/investigations/kernel-perf-review-2026-07.md +0 -171
- package/docs/archive/investigations/lab-build-journal.md +0 -157
- package/docs/archive/investigations/minicpm5-decode-megakernel.md +0 -489
- package/docs/archive/investigations/openjarvis-fit.md +0 -198
- package/docs/archive/investigations/openwiki-evaluation.md +0 -249
- package/docs/archive/investigations/optimization_plan.md +0 -346
- package/docs/archive/investigations/orpo-base-uf-experiment-and-directions.md +0 -120
- package/docs/archive/investigations/orpo-flash-cce-pin-leak.md +0 -167
- package/docs/archive/investigations/orpo-uf-testing-handoff.md +0 -126
- package/docs/archive/investigations/pareto-specialized-runtime-findings.md +0 -92
- package/docs/archive/investigations/pi-builtin-investigation.md +0 -308
- package/docs/archive/investigations/pre-colibri-stabilization.md +0 -329
- package/docs/archive/investigations/qwen38-27b-campaign-log.md +0 -1092
- package/docs/archive/investigations/segmented-backward-handoff.md +0 -148
- package/docs/archive/investigations/starter-model-port-handoff.md +0 -342
- package/docs/archive/investigations/steel-flash-cce-handoff.md +0 -489
- package/docs/archive/investigations/the-dreaming-handoff.md +0 -141
- package/docs/archive/investigations/trainer-validation-experiment.md +0 -173
- package/docs/archive/planning/chat-ui-vision-memory-first.md +0 -199
- package/docs/archive/planning/chat-ui-vision.md +0 -50
- package/docs/archive/planning/chunk-task-roadmap.md +0 -77
- package/docs/archive/planning/curve-sampler-research-plan.md +0 -331
- package/docs/archive/planning/journal.md +0 -316
- package/docs/archive/planning/memory-docs-and-dag-plan.md +0 -194
- package/docs/archive/planning/pi-integration-review.md +0 -178
- package/docs/archive/planning/release-notes-v0.0.10.md +0 -57
- package/docs/archive/planning/release-notes-v0.0.11.md +0 -239
- package/docs/archive/planning/release-notes-v0.0.12.md +0 -80
- package/docs/archive/planning/release-notes-v0.0.13.md +0 -77
- package/docs/archive/planning/release-notes-v0.0.9.md +0 -122
- package/docs/archive/planning/release-notes-v0.2.0.md +0 -49
- package/docs/archive/planning/release-notes-v0.3.0.md +0 -35
- package/docs/archive/planning/release-notes-v0.4.0.md +0 -45
- package/docs/archive/planning/release-notes-v0.5.0.md +0 -37
- package/docs/archive/planning/web-ui-pass-plan.md +0 -213
- package/docs/archive/planning/website-readme-pass-plan.md +0 -224
- package/docs/design/batching.md +0 -2054
- package/docs/design/decode-speed-program.md +0 -2404
- package/docs/design/dreaming-nightly-pipeline.md +0 -684
- package/docs/design/generic-model-support.md +0 -821
- package/docs/design/kv-cache.md +0 -993
- package/docs/design/orpo-training.md +0 -680
- package/docs/design/speculative-decoding.md +0 -2129
- package/docs/design/turboquant.md +0 -2225
- package/docs/design/unified-engine-frontier-plan.md +0 -1987
- package/docs/design/web-chat-redesign.md +0 -695
- package/docs/planning/PRODUCT_ROADMAP.md +0 -593
- package/docs/planning/ResearchTopics.md +0 -119
- package/docs/planning/public-readiness-handoff.md +0 -244
- package/docs/planning/public-readiness.md +0 -149
- package/docs/planning/video-series.md +0 -421
- package/docs/reference/benchmarks.md +0 -3587
- package/docs/reference/cli.md +0 -646
- package/docs/reference/distribution.md +0 -380
- package/docs/reference/environment.md +0 -494
- package/docs/reference/glossary.md +0 -39
- package/docs/reference/library-api.md +0 -688
- package/docs/reference/memory.md +0 -260
- package/docs/reference/models.md +0 -346
- package/docs/reference/server-api.md +0 -1945
- package/docs/reference/server-config.md +0 -973
- package/docs/reference/training.md +0 -462
- package/docs/reference/troubleshooting.md +0 -158
- package/src/admission-plan.ts +0 -18
- package/src/audio/audiotoolbox.ts +0 -112
- package/src/audio/conformer.ts +0 -655
- package/src/audio/decode.ts +0 -133
- package/src/audio/features.ts +0 -202
- package/src/audio/mic-capture.ts +0 -98
- package/src/audio/silero-vad.ts +0 -379
- package/src/audio/transcode.ts +0 -67
- package/src/audio/whisper-decode.ts +0 -774
- package/src/audio/whisper-fast.ts +0 -732
- package/src/audio/whisper-format.ts +0 -73
- package/src/audio/whisper-mel.ts +0 -185
- package/src/audio/whisper-timing.ts +0 -274
- package/src/audio/whisper-tokenizer.ts +0 -239
- package/src/audio/whisper-transcribe.ts +0 -410
- package/src/backends/mlx/assistant-target.ts +0 -46
- package/src/backends/mlx/autoregressive-draft-rows.ts +0 -120
- package/src/backends/mlx/autoregressive.ts +0 -129
- package/src/backends/mlx/batch-group.ts +0 -1874
- package/src/backends/mlx/cache-attachment.ts +0 -67
- package/src/backends/mlx/cache-layout.ts +0 -31
- package/src/backends/mlx/checkpoint-state.ts +0 -53
- package/src/backends/mlx/continuation-persistence.ts +0 -107
- package/src/backends/mlx/continuation-request.ts +0 -43
- package/src/backends/mlx/continuation.ts +0 -77
- package/src/backends/mlx/diffusion.ts +0 -39
- package/src/backends/mlx/draft-target.ts +0 -32
- package/src/backends/mlx/encoder-cache.ts +0 -25
- package/src/backends/mlx/evaluation.ts +0 -105
- package/src/backends/mlx/fill-append.ts +0 -58
- package/src/backends/mlx/fill-group.ts +0 -497
- package/src/backends/mlx/full-kv-row-append.ts +0 -32
- package/src/backends/mlx/full-kv-row-donor.ts +0 -54
- package/src/backends/mlx/full-transitioning-kv-rows.ts +0 -65
- package/src/backends/mlx/gateway-binding.ts +0 -174
- package/src/backends/mlx/graph.ts +0 -38
- package/src/backends/mlx/kv-codec.ts +0 -9
- package/src/backends/mlx/kv-maintenance.ts +0 -161
- package/src/backends/mlx/kv-tensor-rows.ts +0 -212
- package/src/backends/mlx/memory-client.ts +0 -189
- package/src/backends/mlx/methods.ts +0 -90
- package/src/backends/mlx/mixed-iteration.ts +0 -62
- package/src/backends/mlx/model-prompt.ts +0 -178
- package/src/backends/mlx/model-serving.ts +0 -80
- package/src/backends/mlx/paged-cache-codec.ts +0 -27
- package/src/backends/mlx/prefill-cohort.ts +0 -100
- package/src/backends/mlx/prefill-policy.ts +0 -26
- package/src/backends/mlx/prefill-rows.ts +0 -244
- package/src/backends/mlx/prefill.ts +0 -33
- package/src/backends/mlx/projected-context-rows.ts +0 -72
- package/src/backends/mlx/prompt-input.ts +0 -29
- package/src/backends/mlx/qwen-prompt-input.ts +0 -40
- package/src/backends/mlx/request-policy.ts +0 -20
- package/src/backends/mlx/request-state-policy.ts +0 -54
- package/src/backends/mlx/rollback.ts +0 -92
- package/src/backends/mlx/row-sampling.ts +0 -49
- package/src/backends/mlx/serial-executor.ts +0 -251
- package/src/backends/mlx/speculative-group.ts +0 -438
- package/src/backends/mlx/speculative-round.ts +0 -161
- package/src/backends/mlx/speculative.ts +0 -131
- package/src/backends/mlx/state-rows.ts +0 -104
- package/src/backends/mlx/state-views.ts +0 -46
- package/src/backends/mlx/target-layout-capability.ts +0 -35
- package/src/backends/mlx/text-engine.ts +0 -73
- package/src/backends/mlx/transitioning-kv-rows.ts +0 -173
- package/src/chat-template.ts +0 -382
- package/src/cli.ts +0 -3490
- package/src/config.ts +0 -399
- package/src/contracts/completion.ts +0 -16
- package/src/contracts/execution.ts +0 -70
- package/src/contracts/generation.ts +0 -103
- package/src/contracts/host.ts +0 -7
- package/src/contracts/object-cache.ts +0 -8
- package/src/contracts/pi-provider.ts +0 -30
- package/src/contracts/pi.ts +0 -261
- package/src/contracts/prefix-cache.ts +0 -33
- package/src/contracts/resources.ts +0 -25
- package/src/contracts/sampling.ts +0 -23
- package/src/contracts/scheduling.ts +0 -54
- package/src/contracts/tsconfig.json +0 -14
- package/src/dataset/generators.ts +0 -1087
- package/src/dataset/index.ts +0 -12
- package/src/dataset/job.ts +0 -81
- package/src/dataset/llm.ts +0 -71
- package/src/dataset/registry.ts +0 -528
- package/src/diffusion/diffusion-generate.ts +0 -507
- package/src/download.ts +0 -505
- package/src/embed.ts +0 -77
- package/src/engine/admission.ts +0 -59
- package/src/engine/cancellation.ts +0 -38
- package/src/engine/engine.ts +0 -56
- package/src/engine/execution-coordinator.ts +0 -70
- package/src/engine/execution-plan.ts +0 -64
- package/src/engine/execution-tasks.ts +0 -44
- package/src/engine/namespaced-cache.ts +0 -13
- package/src/engine/resources.ts +0 -53
- package/src/engine/scheduler.ts +0 -92
- package/src/engine/session.ts +0 -247
- package/src/eval/README.md +0 -130
- package/src/eval/ifeval.ts +0 -81
- package/src/eval/kl-prompts.ts +0 -29
- package/src/eval/kl.ts +0 -590
- package/src/eval/perplexity.ts +0 -164
- package/src/eval/quality-db.ts +0 -92
- package/src/eval/reference-logits.ts +0 -207
- package/src/eval/runner.ts +0 -124
- package/src/eval/score.ts +0 -49
- package/src/eval/tasks/bfcl.ts +0 -535
- package/src/eval/tasks/gsm8k.ts +0 -98
- package/src/eval/tasks/hashhop.ts +0 -139
- package/src/eval/tasks/humaneval.ts +0 -275
- package/src/eval/tasks/ifeval.ts +0 -525
- package/src/eval/tasks/mmlu.ts +0 -157
- package/src/eval/ultrafeedback.ts +0 -60
- package/src/evaldb.ts +0 -199
- package/src/expert-io.ts +0 -393
- package/src/expert-offload-build.ts +0 -77
- package/src/expert-offload.ts +0 -76
- package/src/expert-residency.ts +0 -1134
- package/src/expert-usage.ts +0 -415
- package/src/fill/echo-index.ts +0 -188
- package/src/fill/fill-session.ts +0 -463
- package/src/fill/proposal.ts +0 -68
- package/src/fill/schema-rows.ts +0 -506
- package/src/fill/tool-boundary.ts +0 -103
- package/src/fit.ts +0 -249
- package/src/generate.ts +0 -1352
- package/src/grammar.ts +0 -604
- package/src/harness-pi.ts +0 -184
- package/src/hf-push.ts +0 -628
- package/src/hub-rest.ts +0 -242
- package/src/index.ts +0 -63
- package/src/inference/denoising.ts +0 -17
- package/src/inference/draft-acceptance.ts +0 -41
- package/src/inference/draft-output.ts +0 -49
- package/src/inference/graph.ts +0 -33
- package/src/inference/prefill.ts +0 -45
- package/src/inference/rollback.ts +0 -7
- package/src/jobs/index.ts +0 -31
- package/src/jobs/job-entry.ts +0 -107
- package/src/jobs/task-client.ts +0 -19
- package/src/jobs/types.ts +0 -2
- package/src/kv-scheme.ts +0 -279
- package/src/kv-store.ts +0 -1135
- package/src/lab/README.md +0 -22
- package/src/lab/curve/curve-designer.html +0 -303
- package/src/lab/curve/curve-sampler.ts +0 -122
- package/src/lab/expert-trace/expert-trace.ts +0 -69
- package/src/lab/paged-kv/paged-attention.ts +0 -117
- package/src/lab/paged-kv/paged-kv-rows.ts +0 -111
- package/src/lab/paged-kv/paged-kv.ts +0 -336
- package/src/library.ts +0 -40
- package/src/lora.ts +0 -408
- package/src/md-modules.d.ts +0 -54
- package/src/media-fetch.ts +0 -442
- package/src/memory/article.ts +0 -558
- package/src/memory/chunk-validation.ts +0 -150
- package/src/memory/chunk.ts +0 -318
- package/src/memory/cluster.ts +0 -351
- package/src/memory/coverage.ts +0 -134
- package/src/memory/crosslink.ts +0 -0
- package/src/memory/db.ts +0 -253
- package/src/memory/entity.ts +0 -203
- package/src/memory/gate.ts +0 -187
- package/src/memory/history.ts +0 -152
- package/src/memory/ingest.ts +0 -335
- package/src/memory/model.ts +0 -183
- package/src/memory/normalize.ts +0 -671
- package/src/memory/parse.ts +0 -22
- package/src/memory/pipeline.ts +0 -275
- package/src/memory/prompts.ts +0 -65
- package/src/memory/query.ts +0 -334
- package/src/memory/reconcile.ts +0 -734
- package/src/memory/redirect.ts +0 -108
- package/src/memory/reindex.ts +0 -325
- package/src/memory/resolve.ts +0 -307
- package/src/memory/rest.ts +0 -245
- package/src/memory/route.ts +0 -272
- package/src/memory/schedule.ts +0 -165
- package/src/memory/stages.ts +0 -777
- package/src/memory/synthesize.ts +0 -1638
- package/src/memory/tools.ts +0 -749
- package/src/memory/vault.ts +0 -1194
- package/src/memory/wikify.ts +0 -1064
- package/src/mlx/array.ts +0 -425
- package/src/mlx/autograd.ts +0 -304
- package/src/mlx/checkpoint.ts +0 -149
- package/src/mlx/compile.ts +0 -168
- package/src/mlx/custom-vjp.ts +0 -188
- package/src/mlx/ffi.ts +0 -531
- package/src/mlx/materialize.ts +0 -23
- package/src/mlx/metal-kernel.ts +0 -159
- package/src/mlx/normalized-argmax.ts +0 -116
- package/src/mlx/ops.ts +0 -1108
- package/src/mlx/quantized-rows.ts +0 -36
- package/src/mlx/token-bitmask.ts +0 -52
- package/src/mlx/turboquant-kv-decode.ts +0 -82
- package/src/mlx/turboquant-kv-inverse.ts +0 -122
- package/src/mlx/turboquant-ops.ts +0 -861
- package/src/mlx/turboquant-tables.ts +0 -237
- package/src/mmap.ts +0 -90
- package/src/model/artifact-identity.ts +0 -73
- package/src/model/batched-kv.ts +0 -235
- package/src/model/batched-mask.ts +0 -279
- package/src/model/batched-quant.ts +0 -212
- package/src/model/batched-quantized-kv.ts +0 -144
- package/src/model/batched-rotating-quant.ts +0 -353
- package/src/model/batched-rotating-state.ts +0 -149
- package/src/model/batched-rotating.ts +0 -338
- package/src/model/batched-row-storage.ts +0 -179
- package/src/model/batched-ssm.ts +0 -52
- package/src/model/batched-turboquant-kv.ts +0 -94
- package/src/model/compiled-decode.ts +0 -712
- package/src/model/decoded-kv-donor.ts +0 -12
- package/src/model/delayed-quantized-kv.ts +0 -72
- package/src/model/delayed-rotating-quantized-kv.ts +0 -93
- package/src/model/delayed-turboquant-kv.ts +0 -57
- package/src/model/diffusion-gemma.ts +0 -1026
- package/src/model/factory.ts +0 -215
- package/src/model/fingerprint.ts +0 -45
- package/src/model/flash-attention.ts +0 -694
- package/src/model/full-prefill-padding.ts +0 -56
- package/src/model/full-prefill-row.ts +0 -105
- package/src/model/gemma4-base.ts +0 -2370
- package/src/model/gemma4.ts +0 -1395
- package/src/model/generated/gemma4-12b.ts +0 -429
- package/src/model/generated/gemma4-26b.ts +0 -448
- package/src/model/generated/gemma4-e4b.ts +0 -717
- package/src/model/generated/index.ts +0 -18
- package/src/model/glm52-atlas.ts +0 -511
- package/src/model/glm52-cache.ts +0 -792
- package/src/model/glm52-config.ts +0 -262
- package/src/model/glm52-container.ts +0 -305
- package/src/model/glm52-coupling.ts +0 -388
- package/src/model/glm52-dsa.ts +0 -606
- package/src/model/glm52-expert-layout.ts +0 -253
- package/src/model/glm52-layout.ts +0 -152
- package/src/model/glm52-memory.ts +0 -500
- package/src/model/glm52-mla.ts +0 -792
- package/src/model/glm52-moe.ts +0 -223
- package/src/model/glm52-pilot.ts +0 -537
- package/src/model/glm52-reference.ts +0 -445
- package/src/model/glm52-residency.ts +0 -557
- package/src/model/glm52-resident-weights.ts +0 -135
- package/src/model/glm52-streamed-experts.ts +0 -453
- package/src/model/glm52-streamed-metal.ts +0 -610
- package/src/model/glm52-weights.ts +0 -503
- package/src/model/glm52.ts +0 -1132
- package/src/model/implementation.ts +0 -69
- package/src/model/kv-attention-view.ts +0 -70
- package/src/model/minicpm5.ts +0 -376
- package/src/model/profile.ts +0 -468
- package/src/model/quantized-append-attention.ts +0 -31
- package/src/model/qwen-append.ts +0 -12
- package/src/model/qwen-conv.ts +0 -52
- package/src/model/qwen3-delta-state.ts +0 -74
- package/src/model/qwen3-delta.ts +0 -451
- package/src/model/qwen3-moe.ts +0 -404
- package/src/model/qwen3-mrope.ts +0 -250
- package/src/model/qwen3.ts +0 -277
- package/src/model/qwen3_5-checkpoint.ts +0 -164
- package/src/model/qwen3_5.ts +0 -881
- package/src/model/rotating-kv-donor.ts +0 -35
- package/src/model/rotating-kv-layout.ts +0 -262
- package/src/model/rotating-row-transaction.ts +0 -35
- package/src/model/speculative-rotating-kv.ts +0 -101
- package/src/model/ssm-prefill-padding.ts +0 -39
- package/src/model/support.ts +0 -110
- package/src/model/token-groups.ts +0 -66
- package/src/model/trellis-balanced-scatter.ts +0 -51
- package/src/model/trellis-linear.ts +0 -672
- package/src/model/trellis-shared-m.ts +0 -151
- package/src/model/trellis-shared-scatter.ts +0 -144
- package/src/model/trellis-splitk-prefill.ts +0 -158
- package/src/model/trellis-tiled-prefill.ts +0 -136
- package/src/model/trellis-vector-expand.ts +0 -62
- package/src/model/trellis-wide-prefill.ts +0 -94
- package/src/model/turboquant-codec.ts +0 -89
- package/src/model/universal/archs.ts +0 -332
- package/src/model/universal/dense.ts +0 -612
- package/src/model/universal/modules.ts +0 -170
- package/src/model/universal/rope.ts +0 -381
- package/src/model/whisper.ts +0 -435
- package/src/native/expert_io.c +0 -523
- package/src/native/frame_extract.swift +0 -140
- package/src/native/mic_capture.swift +0 -92
- package/src/native-pack.ts +0 -163
- package/src/pi-provider.ts +0 -53
- package/src/pi-session.ts +0 -81
- package/src/pi-terminal.ts +0 -274
- package/src/pi-web.ts +0 -1940
- package/src/preflight.ts +0 -158
- package/src/prompt-cache.ts +0 -682
- package/src/quantize/allocator.ts +0 -627
- package/src/quantize/atomic-output.ts +0 -38
- package/src/quantize/calibration.ts +0 -181
- package/src/quantize/config-writer.ts +0 -145
- package/src/quantize/index.ts +0 -84
- package/src/quantize/job.ts +0 -162
- package/src/quantize/quantizer.ts +0 -666
- package/src/quantize/rotate.ts +0 -603
- package/src/quantize/safetensors-writer.ts +0 -249
- package/src/quantize/sensitivity.ts +0 -216
- package/src/quantize/trellis.ts +0 -586
- package/src/quantize/weight-transform.ts +0 -292
- package/src/registry.ts +0 -602
- package/src/runtime-config.ts +0 -77
- package/src/safetensors.ts +0 -165
- package/src/sampler.ts +0 -1012
- package/src/serve/admin-routes.ts +0 -184
- package/src/serve/assets/curve-terrain.html +0 -105
- package/src/serve/assets/training-inference-map.html +0 -575
- package/src/serve/audio-routes.ts +0 -323
- package/src/serve/aux-routes.ts +0 -132
- package/src/serve/batch-scheduler.ts +0 -8
- package/src/serve/checkpoint-identity.ts +0 -64
- package/src/serve/generation-gateway.ts +0 -537
- package/src/serve/isolate.ts +0 -609
- package/src/serve/kv-budget.ts +0 -14
- package/src/serve/lab-routes.ts +0 -341
- package/src/serve/lane-registry.ts +0 -45
- package/src/serve/model-admin-routes.ts +0 -155
- package/src/serve/model-binding.ts +0 -49
- package/src/serve/model-host.ts +0 -511
- package/src/serve/parent-application.ts +0 -56
- package/src/serve/prompt-response-trace.ts +0 -161
- package/src/serve/response-lease.ts +0 -24
- package/src/serve/session-search.ts +0 -326
- package/src/serve/static-routes.ts +0 -101
- package/src/serve/transcription-server.ts +0 -64
- package/src/serve/transcription-service.ts +0 -502
- package/src/server.ts +0 -1282
- package/src/spec/assistant-rows.ts +0 -93
- package/src/spec/assistant-source.ts +0 -126
- package/src/spec/cache-identity.ts +0 -22
- package/src/spec/deepspec-rows.ts +0 -29
- package/src/spec/deepspec-source.ts +0 -145
- package/src/spec/dflash-source.ts +0 -149
- package/src/spec/drafter.ts +0 -304
- package/src/spec/dspark/ab-stats.ts +0 -136
- package/src/spec/dspark/calibration.ts +0 -112
- package/src/spec/dspark/data-dflash.ts +0 -156
- package/src/spec/dspark/data.ts +0 -201
- package/src/spec/dspark/deepspec-module.ts +0 -776
- package/src/spec/dspark/generate-dflash.ts +0 -245
- package/src/spec/dspark/generate.ts +0 -290
- package/src/spec/dspark/loader.ts +0 -23
- package/src/spec/dspark/loss.ts +0 -213
- package/src/spec/dspark/module-dflash.ts +0 -560
- package/src/spec/dspark/module.ts +0 -540
- package/src/spec/dspark/quantize-drafter.ts +0 -91
- package/src/spec/dspark/sample.ts +0 -112
- package/src/spec/generate.ts +0 -276
- package/src/spec/glm52-mtp-graph.ts +0 -29
- package/src/spec/glm52-mtp-rows.ts +0 -132
- package/src/spec/glm52-mtp-source.ts +0 -318
- package/src/spec/glm52-mtp-state.ts +0 -33
- package/src/spec/ngram-source.ts +0 -226
- package/src/spec/projected-draft-rows.ts +0 -73
- package/src/spec/qwen-mtp-module.ts +0 -171
- package/src/spec/qwen-mtp-rows.ts +0 -230
- package/src/spec/qwen-mtp-source.ts +0 -386
- package/src/spec/qwen-mtp-state.ts +0 -30
- package/src/spec/serve-loop.ts +0 -587
- package/src/spec/source.ts +0 -228
- package/src/spec/two-model-rows.ts +0 -62
- package/src/spec/two-model.ts +0 -113
- package/src/ssd-cache.ts +0 -431
- package/src/ssd-durability.ts +0 -209
- package/src/storage/host-buffer.ts +0 -24
- package/src/storage/kv-writer.ts +0 -83
- package/src/storage/kv-writer.worker.js +0 -264
- package/src/storage/retention-policy.ts +0 -37
- package/src/tiered-prompt-cache.ts +0 -45
- package/src/tokenizer.ts +0 -335
- package/src/tool-approvals.ts +0 -131
- package/src/tool-call.ts +0 -695
- package/src/train/dataset.ts +0 -484
- package/src/train/diffusion-lora.ts +0 -216
- package/src/train/export.ts +0 -32
- package/src/train/flash-cce.ts +0 -1234
- package/src/train/forward.ts +0 -266
- package/src/train/fuse.ts +0 -243
- package/src/train/index.ts +0 -46
- package/src/train/job.ts +0 -205
- package/src/train/lora-params.ts +0 -254
- package/src/train/loss.ts +0 -1591
- package/src/train/merge.ts +0 -195
- package/src/train/optimizer.ts +0 -183
- package/src/train/prefix-shared.ts +0 -490
- package/src/train/rank.ts +0 -137
- package/src/train/segmented.ts +0 -1828
- package/src/train/steel-qmm-header.ts +0 -1461
- package/src/train/trainer.ts +0 -1221
- package/src/train/watch.ts +0 -542
- package/src/vision/diffusion-vision.ts +0 -620
- package/src/vision/embedder.ts +0 -176
- package/src/vision/preprocess.ts +0 -247
- package/src/vision/prompt.ts +0 -409
- package/src/vision/qwen3vl-preprocess.ts +0 -409
- package/src/vision/qwen3vl-prompt.ts +0 -233
- package/src/vision/qwen3vl-tower.ts +0 -566
- package/src/vision/siglip.ts +0 -607
- package/src/vision/video-frames.ts +0 -148
- package/src/web/app.html +0 -2155
- package/src/web/app.js +0 -5863
- package/src/web/skills/memory/SKILL.md +0 -120
- package/src/web/skills/web-research/SKILL.md +0 -46
- package/src/web/skills.ts +0 -97
- package/src/web/src/adapters-panel.ts +0 -288
- package/src/web/src/assistant.ts +0 -451
- package/src/web/src/chat.ts +0 -1060
- package/src/web/src/composer.ts +0 -962
- package/src/web/src/dataset.ts +0 -132
- package/src/web/src/finetune.ts +0 -267
- package/src/web/src/hub.ts +0 -428
- package/src/web/src/main.ts +0 -98
- package/src/web/src/markdown.ts +0 -0
- package/src/web/src/memory-panel.ts +0 -572
- package/src/web/src/model-picker.ts +0 -159
- package/src/web/src/palette.ts +0 -346
- package/src/web/src/protocol.ts +0 -26
- package/src/web/src/quantize.ts +0 -167
- package/src/web/src/rag.ts +0 -274
- package/src/web/src/sessions.ts +0 -469
- package/src/web/src/shell.ts +0 -804
- package/src/web/src/ui-catalog.ts +0 -78
- package/src/web/src/voice.ts +0 -141
- package/src/web/vendor/README.md +0 -61
- package/src/web-assets.ts +0 -47
- package/src/web-tools.ts +0 -478
- package/src/weights.ts +0 -255
- /package/src/{serve → server}/completion-sink.ts +0 -0
- /package/src/{serve → server}/generated-token-history.ts +0 -0
- /package/src/web/{icon.svg → public/icon.svg} +0 -0
- /package/src/web/{manifest.webmanifest → public/manifest.webmanifest} +0 -0
- /package/src/web/{vendor → public/vendor}/hljs-LICENSE +0 -0
|
@@ -1,112 +0,0 @@
|
|
|
1
|
-
// Sampling support for DSpark speculative decoding at temperature > 0.
|
|
2
|
-
//
|
|
3
|
-
// Lossless speculative SAMPLING (Leviathan/Chen): a drafted token x sampled
|
|
4
|
-
// from draft dist q is accepted w.p. min(1, p(x)/q(x)) where p is the target
|
|
5
|
-
// dist; on rejection x is resampled from the residual norm(relu(p − q)); if the
|
|
6
|
-
// whole block is accepted a bonus token is sampled from p. The emitted stream is
|
|
7
|
-
// then distributed EXACTLY as if the target sampled token-by-token from p —
|
|
8
|
-
// independent of q (q only moves the acceptance rate τ). This is the
|
|
9
|
-
// temperature analog of the greedy longest-prefix gate.
|
|
10
|
-
//
|
|
11
|
-
// `p` and `q` must be the SAME processing applied to target/draft logits — so we
|
|
12
|
-
// reuse the server sampler's exact top-p/top-k/temperature path (sampler.ts).
|
|
13
|
-
// HLG/curve samplers are out of scope here; the caller rejects them.
|
|
14
|
-
|
|
15
|
-
import { MlxArray } from "../../mlx/array";
|
|
16
|
-
import { Dtype } from "../../mlx/ffi";
|
|
17
|
-
import * as ops from "../../mlx/ops";
|
|
18
|
-
import { applyTopP, applyTopK, toLogprobs } from "../../sampler";
|
|
19
|
-
|
|
20
|
-
export interface DSparkSampleConfig {
|
|
21
|
-
/** temperature > 0 enables sampling; 0 ⇒ greedy (handled by the caller). */
|
|
22
|
-
temperature: number;
|
|
23
|
-
topP?: number;
|
|
24
|
-
topK?: number;
|
|
25
|
-
seed?: number;
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
const GOLDEN = 0x9e3779b97f4a7c15n;
|
|
29
|
-
const U64 = 0xffffffffffffffffn;
|
|
30
|
-
|
|
31
|
-
/** Seeded stream of mlx random keys — reproducible draws without sharing global
|
|
32
|
-
* RNG state (same derivation as sampler.ts stepKey). */
|
|
33
|
-
export class KeyStream {
|
|
34
|
-
#seed: bigint;
|
|
35
|
-
#ctr = 0;
|
|
36
|
-
constructor(seed = 0) { this.#seed = BigInt(seed >>> 0); }
|
|
37
|
-
next(): MlxArray {
|
|
38
|
-
const mixed = (this.#seed ^ ((BigInt(this.#ctr++) + 1n) * GOLDEN)) & U64;
|
|
39
|
-
return ops.randomKey(mixed);
|
|
40
|
-
}
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
/**
|
|
44
|
-
* Processed categorical logits for one position: logits [1,V] → masked +
|
|
45
|
-
* temperature-scaled logits [1,V] (the input to randomCategorical;
|
|
46
|
-
* softmax(·) is the sampling distribution). Mirrors makeSampler's top-p/top-k/
|
|
47
|
-
* temperature path exactly. temperature must be > 0.
|
|
48
|
-
*/
|
|
49
|
-
export function processLogits(logits: MlxArray, cfg: DSparkSampleConfig): MlxArray {
|
|
50
|
-
if (cfg.temperature <= 0) throw new Error("processLogits requires temperature > 0");
|
|
51
|
-
const lp = toLogprobs(logits); // [1,V]
|
|
52
|
-
let cur = lp;
|
|
53
|
-
const owned: MlxArray[] = [lp];
|
|
54
|
-
if (cfg.topP && cfg.topP > 0 && cfg.topP < 1) { cur = applyTopP(cur, cfg.topP); owned.push(cur); }
|
|
55
|
-
if (cfg.topK && cfg.topK > 0) { cur = applyTopK(cur, cfg.topK); owned.push(cur); }
|
|
56
|
-
const scaled = ops.mulScalar(cur, 1 / cfg.temperature);
|
|
57
|
-
for (const a of owned) a.dispose();
|
|
58
|
-
return scaled;
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
/** softmax of processed logits → probability vector [1,V]. */
|
|
62
|
-
export function probsOf(scaled: MlxArray): MlxArray {
|
|
63
|
-
return ops.softmaxAxis(scaled, 1, true);
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
/** Sample one token id from processed logits [1,V] (∝ softmax). */
|
|
67
|
-
export function sampleToken(scaled: MlxArray, key: MlxArray): number {
|
|
68
|
-
const t = ops.randomCategorical(scaled, key); // [1] uint32
|
|
69
|
-
const id = ops.itemUint32(t);
|
|
70
|
-
t.dispose();
|
|
71
|
-
return id;
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
/** Probability mass a [1,V] distribution assigns to token id (host scalar). */
|
|
75
|
-
export function probAtToken(probs: MlxArray, id: number): number {
|
|
76
|
-
const sl = probs.slice([0, id], [1, id + 1]); // [1,1]
|
|
77
|
-
const v = sl.toFloat32()[0]!;
|
|
78
|
-
sl.dispose();
|
|
79
|
-
return v;
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
/** Sample one token from the residual norm(relu(p − q)) over [1,V]. Falls back
|
|
83
|
-
* to sampling from p if the residual is degenerate (mass ≈ 0). */
|
|
84
|
-
export function sampleResidual(p: MlxArray, q: MlxArray, key: MlxArray): number {
|
|
85
|
-
const diff = ops.sub(p, q);
|
|
86
|
-
const zero = MlxArray.fromFloat32(new Float32Array([0]), []);
|
|
87
|
-
const relu = ops.maximum(diff, zero);
|
|
88
|
-
diff.dispose(); zero.dispose();
|
|
89
|
-
const mass = ops.sumAxis(relu, 1, true); // [1,1]
|
|
90
|
-
const massV = mass.toFloat32()[0]!;
|
|
91
|
-
if (!(massV > 1e-12)) {
|
|
92
|
-
// degenerate (p ⪯ q everywhere) — sample from p directly.
|
|
93
|
-
relu.dispose(); mass.dispose();
|
|
94
|
-
const lp = ops.log(p);
|
|
95
|
-
const id = sampleToken(lp, key);
|
|
96
|
-
lp.dispose();
|
|
97
|
-
return id;
|
|
98
|
-
}
|
|
99
|
-
const resid = ops.div(relu, mass); // normalized [1,V]
|
|
100
|
-
relu.dispose(); mass.dispose();
|
|
101
|
-
// randomCategorical samples ∝ exp(logits) → feed log(resid).
|
|
102
|
-
const eps = MlxArray.fromFloat32(new Float32Array([1e-30]), []);
|
|
103
|
-
const safe = ops.add(resid, eps);
|
|
104
|
-
resid.dispose(); eps.dispose();
|
|
105
|
-
const logits = ops.log(safe);
|
|
106
|
-
safe.dispose();
|
|
107
|
-
const id = sampleToken(logits, key);
|
|
108
|
-
logits.dispose();
|
|
109
|
-
return id;
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
export { Dtype };
|
package/src/spec/generate.ts
DELETED
|
@@ -1,276 +0,0 @@
|
|
|
1
|
-
// Speculative decoding loop — port of optiq runtime/spec/runtime.py
|
|
2
|
-
// (γ-draft / verify-in-one-pass / accept-longest-prefix / rollback).
|
|
3
|
-
//
|
|
4
|
-
// Correctness oracle: OPTIQ's spec_generate, NOT stock decode. Assistant-
|
|
5
|
-
// drafter speculation is an optiq feature (mlx-lm has only generic
|
|
6
|
-
// two-model spec, and can't drive a KV-borrowing drafter). Both optiq AND
|
|
7
|
-
// mlx-lm BATCH the verify lm-head (one matmul over the whole γ+1 window,
|
|
8
|
-
// then argmax per position) — so neither is bit-exact to stock token-at-
|
|
9
|
-
// a-time decode; they diverge from it at bf16 knife-edges. We do the same
|
|
10
|
-
// (picksBatched): greedy spec is bit-exact to optiq's spec, and agrees
|
|
11
|
-
// with stock only on tie-free prompts (where batched == per-position).
|
|
12
|
-
// An earlier version verified per-position to stay bit-exact to STOCK —
|
|
13
|
-
// that matched no real oracle and cost an extra γ× read of the lm-head
|
|
14
|
-
// weight per step; superseded. See docs/design/speculative-decoding.md.
|
|
15
|
-
//
|
|
16
|
-
// Limitation (same as the reference): partial-accept rollback requires
|
|
17
|
-
// trimmable caches; RotatingKVCache loses trimability once its ring
|
|
18
|
-
// wraps (offset ≥ sliding_window). We throw, as the reference does.
|
|
19
|
-
|
|
20
|
-
import { MlxArray } from "../mlx/array";
|
|
21
|
-
import * as ops from "../mlx/ops";
|
|
22
|
-
import { Gemma4Model, type Cache } from "../model/gemma4";
|
|
23
|
-
import type { GemmaAssistantDrafter } from "./drafter";
|
|
24
|
-
|
|
25
|
-
export interface SpecOptions {
|
|
26
|
-
gamma?: number;
|
|
27
|
-
maxTokens?: number;
|
|
28
|
-
eosTokenIds?: number[];
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
export interface SpecStats {
|
|
32
|
-
emitted: number;
|
|
33
|
-
drafted: number;
|
|
34
|
-
accepted: number;
|
|
35
|
-
targetCalls: number;
|
|
36
|
-
decodeMs: number;
|
|
37
|
-
prefillMs: number;
|
|
38
|
-
acceptanceRate: number;
|
|
39
|
-
decodeTps: number;
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
export interface SpecResult {
|
|
43
|
-
tokens: number[];
|
|
44
|
-
stats: SpecStats;
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
/** Single greedy pick from one hidden position [1,1,H] (lm-head + argmax).
|
|
48
|
-
* Used for the NON-speculative prefill token (matches stock there). */
|
|
49
|
-
function pickFromHidden(model: Gemma4Model, hidden: MlxArray, pos: number): number {
|
|
50
|
-
const H = hidden.shape[2]!;
|
|
51
|
-
const hSl = hidden.slice([0, pos, 0], [1, pos + 1, H]);
|
|
52
|
-
const logits = model.logitsFromHidden(hSl);
|
|
53
|
-
hSl.dispose();
|
|
54
|
-
const V = logits.shape[2]!;
|
|
55
|
-
const flat = ops.reshape(logits, [1, V]);
|
|
56
|
-
logits.dispose();
|
|
57
|
-
const am = ops.argmaxAxis(flat, -1);
|
|
58
|
-
flat.dispose();
|
|
59
|
-
const t = ops.itemUint32(am);
|
|
60
|
-
am.dispose();
|
|
61
|
-
return t;
|
|
62
|
-
}
|
|
63
|
-
|
|
64
|
-
/** optiq-faithful batched verify: ONE lm-head over the whole γ+1 window
|
|
65
|
-
* (reads the lm-head weight ONCE, as optiq and mlx-lm both do), then
|
|
66
|
-
* argmax per position. This is what makes greedy spec bit-exact to
|
|
67
|
-
* optiq's spec_generate. argmax is invariant to the logsumexp shift and
|
|
68
|
-
* to the monotone final-logit softcap, so raw-logit argmax here picks the
|
|
69
|
-
* same token optiq does. */
|
|
70
|
-
function picksBatched(model: Gemma4Model, hidden: MlxArray, count: number): number[] {
|
|
71
|
-
const logits = model.logitsFromHidden(hidden); // [1, L, V] — one matmul
|
|
72
|
-
const V = logits.shape[2]!;
|
|
73
|
-
const out: number[] = [];
|
|
74
|
-
for (let k = 0; k < count; k++) {
|
|
75
|
-
const sl = logits.slice([0, k, 0], [1, k + 1, V]);
|
|
76
|
-
const flat = ops.reshape(sl, [1, V]);
|
|
77
|
-
sl.dispose();
|
|
78
|
-
const am = ops.argmaxAxis(flat, -1);
|
|
79
|
-
flat.dispose();
|
|
80
|
-
out.push(ops.itemUint32(am));
|
|
81
|
-
am.dispose();
|
|
82
|
-
}
|
|
83
|
-
logits.dispose();
|
|
84
|
-
return out;
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
/** Donor caches: the target's LAST sliding and LAST full cache owners
|
|
88
|
-
* (port of optiq kv_view.find_donor_layers). */
|
|
89
|
-
function donorIndices(model: Gemma4Model): { sliding: number; full: number } {
|
|
90
|
-
let sliding = -1;
|
|
91
|
-
let full = -1;
|
|
92
|
-
for (let i = 0; i < model.numDonors; i++) {
|
|
93
|
-
if (model.layers[i]!.layerType === "sliding_attention") sliding = i;
|
|
94
|
-
else full = i;
|
|
95
|
-
}
|
|
96
|
-
if (sliding < 0 || full < 0) throw new Error("missing donor layer type");
|
|
97
|
-
return { sliding, full };
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
export function specGenerate(
|
|
101
|
-
model: Gemma4Model,
|
|
102
|
-
drafter: GemmaAssistantDrafter,
|
|
103
|
-
promptTokens: number[],
|
|
104
|
-
options: SpecOptions = {},
|
|
105
|
-
): SpecResult {
|
|
106
|
-
const { gamma = 2, maxTokens = 256, eosTokenIds = model.config.eosTokenIds } = options;
|
|
107
|
-
if (gamma < 1) throw new Error("gamma must be >= 1");
|
|
108
|
-
|
|
109
|
-
const caches = model.makeCache();
|
|
110
|
-
const donors = donorIndices(model);
|
|
111
|
-
const stats: SpecStats = {
|
|
112
|
-
emitted: 0, drafted: 0, accepted: 0, targetCalls: 0,
|
|
113
|
-
decodeMs: 0, prefillMs: 0, acceptanceRate: 0, decodeTps: 0,
|
|
114
|
-
};
|
|
115
|
-
const out: number[] = [];
|
|
116
|
-
|
|
117
|
-
const embedScaled = (token: number): MlxArray => {
|
|
118
|
-
const ids = ops.fromInt32([token], [1, 1]);
|
|
119
|
-
const e = model.embed.encode(ids);
|
|
120
|
-
ids.dispose();
|
|
121
|
-
const s = ops.mulScalar(e, model.embedScale);
|
|
122
|
-
e.dispose();
|
|
123
|
-
return s;
|
|
124
|
-
};
|
|
125
|
-
|
|
126
|
-
const readDonors = () => ({
|
|
127
|
-
sliding: (caches[donors.sliding] as never as { temporalView(): [MlxArray, MlxArray] }).temporalView(),
|
|
128
|
-
full: (caches[donors.full] as never as { temporalView(): [MlxArray, MlxArray] }).temporalView(),
|
|
129
|
-
});
|
|
130
|
-
|
|
131
|
-
// Round/prefill scratch tensors, hoisted so the finally frees them on a
|
|
132
|
-
// mid-round throw (the 2f not-trimmable throw, or any mlx op) — try-body
|
|
133
|
-
// locals are invisible to the finally. Each is nulled at its normal
|
|
134
|
-
// disposal, so the finally never double-frees. Same discipline as
|
|
135
|
-
// src/spec/serve-loop.ts / generate-dflash.ts (2026-07-06 review fix);
|
|
136
|
-
// see memory [[mlx-inline-slice-leak-pattern]].
|
|
137
|
-
let prefillH: MlxArray | null = null;
|
|
138
|
-
let lastHidden: MlxArray | null = null;
|
|
139
|
-
let vHidden: MlxArray | null = null;
|
|
140
|
-
|
|
141
|
-
try {
|
|
142
|
-
// 1. prefill — FULL-prompt single forward, deliberately. Per-oracle
|
|
143
|
-
// convention (2026-07-07 re-anchor): mlx-lm's speculative path drains to
|
|
144
|
-
// len-1 with no step-0 (the SERVE loop, whose oracle it is, now mirrors
|
|
145
|
-
// that — src/spec/serve-loop.ts); THIS loop's oracle is optiq
|
|
146
|
-
// spec_generate, which prefills the whole prompt in one forward and
|
|
147
|
-
// samples token0 from it (runtime/spec/runtime.py:162-170, read from the
|
|
148
|
-
// installed oracle venv) — the 2026-06-14 bit-exact gate was established
|
|
149
|
-
// against exactly that shape. Do not tail-split here.
|
|
150
|
-
const t0 = performance.now();
|
|
151
|
-
const ids = ops.fromInt32(promptTokens, [1, promptTokens.length]);
|
|
152
|
-
prefillH = model.forwardHidden(ids, caches);
|
|
153
|
-
ids.dispose();
|
|
154
|
-
stats.targetCalls++;
|
|
155
|
-
const H = prefillH.shape[2]!;
|
|
156
|
-
const Lp = prefillH.shape[1]!;
|
|
157
|
-
let next = pickFromHidden(model, prefillH, Lp - 1);
|
|
158
|
-
lastHidden = prefillH.slice([0, Lp - 1, 0], [1, Lp, H]);
|
|
159
|
-
prefillH.dispose();
|
|
160
|
-
prefillH = null;
|
|
161
|
-
stats.prefillMs = performance.now() - t0;
|
|
162
|
-
|
|
163
|
-
// EOS convention: an EOS id stops generation and counts toward
|
|
164
|
-
// stats.emitted (reference-faithful: optiq runtime.py counts it) but
|
|
165
|
-
// is NOT part of the returned content — matching our generate(),
|
|
166
|
-
// which never yields EOS. optiq's spec yields it only as a stream
|
|
167
|
-
// EVENT (clients see the stop); its token array role here is content.
|
|
168
|
-
const nextIsEos = eosTokenIds.includes(next);
|
|
169
|
-
if (!nextIsEos) out.push(next);
|
|
170
|
-
stats.emitted++;
|
|
171
|
-
if (nextIsEos) return { tokens: out, stats };
|
|
172
|
-
|
|
173
|
-
// 2. outer loop
|
|
174
|
-
const tDecode = performance.now();
|
|
175
|
-
outer: while (stats.emitted < maxTokens) {
|
|
176
|
-
const position = caches[0]!.offset - 1;
|
|
177
|
-
const shared = readDonors();
|
|
178
|
-
|
|
179
|
-
// 2a. draft γ tokens against the frozen donor views. try/finally so a
|
|
180
|
-
// mid-draft throw still frees the chained hiddens + donor views + the
|
|
181
|
-
// in-flight emb (assistant-source.ts draft() discipline).
|
|
182
|
-
const drafts: number[] = [];
|
|
183
|
-
let dTok = next;
|
|
184
|
-
let dHid = lastHidden!; // borrowed for k=0
|
|
185
|
-
const ownedHiddens: MlxArray[] = [];
|
|
186
|
-
let emb: MlxArray | null = null;
|
|
187
|
-
try {
|
|
188
|
-
for (let k = 0; k < gamma; k++) {
|
|
189
|
-
emb = embedScaled(dTok);
|
|
190
|
-
const step = drafter.forward(emb, dHid, shared, position + k);
|
|
191
|
-
emb.dispose();
|
|
192
|
-
emb = null;
|
|
193
|
-
drafts.push(step.token);
|
|
194
|
-
stats.drafted++;
|
|
195
|
-
ownedHiddens.push(step.nextHidden);
|
|
196
|
-
dTok = step.token;
|
|
197
|
-
dHid = step.nextHidden;
|
|
198
|
-
}
|
|
199
|
-
} finally {
|
|
200
|
-
emb?.dispose();
|
|
201
|
-
for (const a of ownedHiddens) a.dispose();
|
|
202
|
-
for (const [k, v] of [shared.sliding, shared.full]) {
|
|
203
|
-
k.dispose();
|
|
204
|
-
v.dispose();
|
|
205
|
-
}
|
|
206
|
-
}
|
|
207
|
-
|
|
208
|
-
// 2b. verify all γ drafts (+ the pending token) in one forward
|
|
209
|
-
const vIds = ops.fromInt32([next, ...drafts], [1, gamma + 1]);
|
|
210
|
-
vHidden = model.forwardHidden(vIds, caches);
|
|
211
|
-
vIds.dispose();
|
|
212
|
-
stats.targetCalls++;
|
|
213
|
-
|
|
214
|
-
// 2c. accept the longest matching prefix. Batched verify lm-head
|
|
215
|
-
// (optiq-faithful — see picksBatched).
|
|
216
|
-
const gt = picksBatched(model, vHidden, gamma + 1);
|
|
217
|
-
let kAccept = 0;
|
|
218
|
-
while (kAccept < gamma && drafts[kAccept] === gt[kAccept]) kAccept++;
|
|
219
|
-
stats.accepted += kAccept;
|
|
220
|
-
|
|
221
|
-
// 2d. emit accepted drafts
|
|
222
|
-
for (let k = 0; k < kAccept; k++) {
|
|
223
|
-
const isEos = eosTokenIds.includes(drafts[k]!);
|
|
224
|
-
if (!isEos) out.push(drafts[k]!);
|
|
225
|
-
stats.emitted++;
|
|
226
|
-
if (isEos || stats.emitted >= maxTokens) {
|
|
227
|
-
vHidden.dispose();
|
|
228
|
-
vHidden = null;
|
|
229
|
-
break outer;
|
|
230
|
-
}
|
|
231
|
-
}
|
|
232
|
-
|
|
233
|
-
// 2e. emit the correction (or bonus when all accepted)
|
|
234
|
-
const emit = gt[kAccept]!;
|
|
235
|
-
const emitIsEos = eosTokenIds.includes(emit);
|
|
236
|
-
if (!emitIsEos) out.push(emit);
|
|
237
|
-
stats.emitted++;
|
|
238
|
-
|
|
239
|
-
// 2f. roll back rejected entries
|
|
240
|
-
if (kAccept < gamma) {
|
|
241
|
-
const n = gamma - kAccept;
|
|
242
|
-
for (const c of caches) {
|
|
243
|
-
if (!c.isTrimmable())
|
|
244
|
-
throw new Error(`${c.constructor.name} not trimmable — context exceeded the sliding window during spec decode`);
|
|
245
|
-
c.trim(n);
|
|
246
|
-
}
|
|
247
|
-
}
|
|
248
|
-
|
|
249
|
-
if (emitIsEos || stats.emitted >= maxTokens) {
|
|
250
|
-
vHidden.dispose();
|
|
251
|
-
vHidden = null;
|
|
252
|
-
break;
|
|
253
|
-
}
|
|
254
|
-
|
|
255
|
-
// 2g. chain state
|
|
256
|
-
next = emit;
|
|
257
|
-
lastHidden!.dispose();
|
|
258
|
-
lastHidden = vHidden.slice([0, kAccept, 0], [1, kAccept + 1, H]);
|
|
259
|
-
vHidden.dispose();
|
|
260
|
-
vHidden = null;
|
|
261
|
-
}
|
|
262
|
-
stats.decodeMs = performance.now() - tDecode;
|
|
263
|
-
lastHidden.dispose();
|
|
264
|
-
lastHidden = null;
|
|
265
|
-
} finally {
|
|
266
|
-
// Survivors of a mid-round throw (each nulled at its normal disposal).
|
|
267
|
-
prefillH?.dispose();
|
|
268
|
-
lastHidden?.dispose();
|
|
269
|
-
vHidden?.dispose();
|
|
270
|
-
for (const c of caches) c.dispose();
|
|
271
|
-
}
|
|
272
|
-
|
|
273
|
-
stats.acceptanceRate = stats.drafted ? stats.accepted / stats.drafted : 0;
|
|
274
|
-
stats.decodeTps = stats.decodeMs ? ((stats.emitted - 1) / stats.decodeMs) * 1000 : 0;
|
|
275
|
-
return { tokens: out, stats };
|
|
276
|
-
}
|
|
@@ -1,29 +0,0 @@
|
|
|
1
|
-
import type { MlxArray } from "../mlx/array";
|
|
2
|
-
import * as ops from "../mlx/ops";
|
|
3
|
-
import type { Glm52DecoderLayer, Glm52Model } from "../model/glm52";
|
|
4
|
-
import type { MLACache } from "../model/glm52-cache";
|
|
5
|
-
import { rmsNormF32Mlx } from "../model/glm52-mla";
|
|
6
|
-
|
|
7
|
-
/** Native MTP numerical graph. Tokens, anchor hidden and compressed state may
|
|
8
|
-
* have one or several rows; sampling and state retention belong to callers. */
|
|
9
|
-
export class Glm52MtpGraph {
|
|
10
|
-
constructor(readonly model: Glm52Model, readonly layer: Glm52DecoderLayer) {}
|
|
11
|
-
|
|
12
|
-
async forward(ids: MlxArray, hidden: MlxArray, cache: MLACache): Promise<MlxArray> {
|
|
13
|
-
const { glmConfig: config, weights } = this.model;
|
|
14
|
-
const prefix = `model.layers.${config.numHiddenLayers}`;
|
|
15
|
-
using embedded = weights.embedding(ids, "model.embed_tokens.weight", config.vocabSize, config.hiddenSize);
|
|
16
|
-
using embeddedNorm = rmsNormF32Mlx(embedded, weights.tensor(`${prefix}.enorm.weight`), config.rmsNormEps);
|
|
17
|
-
using hiddenNorm = rmsNormF32Mlx(hidden, weights.tensor(`${prefix}.hnorm.weight`), config.rmsNormEps);
|
|
18
|
-
using joined = ops.concatAxis([embeddedNorm, hiddenNorm], 2);
|
|
19
|
-
using projected = weights.linear(joined, `${prefix}.eh_proj.weight`, config.hiddenSize, 2 * config.hiddenSize);
|
|
20
|
-
return await this.layer.forwardAsync(projected, cache, null);
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
project(hidden: MlxArray): MlxArray {
|
|
24
|
-
const { glmConfig: config, weights } = this.model;
|
|
25
|
-
using normalized = rmsNormF32Mlx(hidden,
|
|
26
|
-
weights.tensor(`model.layers.${config.numHiddenLayers}.shared_head.norm.weight`), config.rmsNormEps);
|
|
27
|
-
return this.model.logitsFromHidden(normalized);
|
|
28
|
-
}
|
|
29
|
-
}
|
|
@@ -1,132 +0,0 @@
|
|
|
1
|
-
import type { MlxArray } from "../mlx/array";
|
|
2
|
-
import * as ops from "../mlx/ops";
|
|
3
|
-
import { Dtype } from "../mlx/ffi";
|
|
4
|
-
import { materializeCopy } from "../mlx/materialize";
|
|
5
|
-
import { MLACache } from "../model/glm52-cache";
|
|
6
|
-
import { toLogprobs } from "../sampler";
|
|
7
|
-
import { applyStateChanges, disposeResources } from "../engine/resources";
|
|
8
|
-
import type { PreparedStateChange } from "../contracts/resources";
|
|
9
|
-
import type { DraftRowSampling } from "./source";
|
|
10
|
-
import type { Glm52MtpGraph } from "./glm52-mtp-graph";
|
|
11
|
-
|
|
12
|
-
export interface Glm52MtpRowState {
|
|
13
|
-
readonly cache: MLACache;
|
|
14
|
-
readonly hidden: MlxArray;
|
|
15
|
-
readonly processedTokens: number;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
/** Native Colibri draft history starts empty, independently of target prompt
|
|
19
|
-
* length. Accepted draft rows are rebuilt from true target hidden states. */
|
|
20
|
-
export class Glm52MtpRows {
|
|
21
|
-
#cache: MLACache;
|
|
22
|
-
#hidden: MlxArray | null = null;
|
|
23
|
-
#processed: number[] = [];
|
|
24
|
-
#drafts: number[][] = [];
|
|
25
|
-
#depth = 0;
|
|
26
|
-
|
|
27
|
-
constructor(readonly graph: Glm52MtpGraph, readonly sampling: DraftRowSampling | null) {
|
|
28
|
-
this.#cache = this.makeCache();
|
|
29
|
-
}
|
|
30
|
-
makeCache(): MLACache {
|
|
31
|
-
const c = this.graph.model.glmConfig;
|
|
32
|
-
return new MLACache({ kvLoraRank: c.kvLoraRank, ropeHeadDim: c.qkRopeHeadDim,
|
|
33
|
-
maxTokens: c.maxPositionEmbeddings, role: "mtp" });
|
|
34
|
-
}
|
|
35
|
-
get rowCount(): number { return this.#processed.length; }
|
|
36
|
-
append(states: readonly (Glm52MtpRowState | null)[]): void {
|
|
37
|
-
applyStateChanges([() => this.prepareAppend(states)]);
|
|
38
|
-
}
|
|
39
|
-
prepareAppend(states: readonly (Glm52MtpRowState | null)[]): PreparedStateChange {
|
|
40
|
-
if (!states.length) return { commit() {}, dispose() {} };
|
|
41
|
-
let cache: MLACache | null = this.makeCache(), hidden: MlxArray | null = null;
|
|
42
|
-
const held: { dispose(): void }[] = [];
|
|
43
|
-
const processed = [...this.#processed, ...states.map(state => state?.processedTokens ?? 0)];
|
|
44
|
-
try {
|
|
45
|
-
cache.mergeRows([...(this.rowCount ? [this.#cache] : []), ...states.map(state => {
|
|
46
|
-
if (state) return state.cache;
|
|
47
|
-
const empty = this.makeCache(); held.push(empty); return empty;
|
|
48
|
-
})]);
|
|
49
|
-
hidden = ops.concatAxis([...(this.#hidden ? [this.#hidden] : []), ...states.map(state => {
|
|
50
|
-
if (state) return state.hidden;
|
|
51
|
-
const zero = ops.zeros([1, 1, this.graph.model.glmConfig.hiddenSize], Dtype.float32);
|
|
52
|
-
held.push(zero); return zero;
|
|
53
|
-
})], 0);
|
|
54
|
-
} catch (error) { cache.dispose(); hidden?.dispose(); throw error; }
|
|
55
|
-
finally { disposeResources(held); }
|
|
56
|
-
return {
|
|
57
|
-
commit: () => {
|
|
58
|
-
const priorCache = this.#cache, priorHidden = this.#hidden;
|
|
59
|
-
this.#cache = cache!; this.#hidden = hidden; this.#processed = processed;
|
|
60
|
-
cache = priorCache; hidden = priorHidden;
|
|
61
|
-
},
|
|
62
|
-
dispose: () => { cache?.dispose(); hidden?.dispose(); cache = null; hidden = null; },
|
|
63
|
-
};
|
|
64
|
-
}
|
|
65
|
-
prefill(tokens: MlxArray, context: MlxArray): void {
|
|
66
|
-
const [batch, length] = tokens.shape as [number, number];
|
|
67
|
-
using tail = context.slice([0, length - 1, 0], [batch, length, context.shape[2]!]);
|
|
68
|
-
const hidden = materializeCopy(tail);
|
|
69
|
-
this.#hidden?.dispose(); this.#hidden = hidden;
|
|
70
|
-
this.#processed = this.#processed.map(count => count + length);
|
|
71
|
-
}
|
|
72
|
-
materialize(): void {
|
|
73
|
-
ops.evalAll([...this.#cache.state(), ...(this.#hidden ? [this.#hidden] : [])]);
|
|
74
|
-
}
|
|
75
|
-
filterRows(keep: readonly number[]): void {
|
|
76
|
-
if (!keep.length) { this.dispose(); return; }
|
|
77
|
-
using indices = ops.fromInt32([...keep], [keep.length]);
|
|
78
|
-
const hidden = ops.takeAxis(this.#hidden!, indices, 0);
|
|
79
|
-
try { this.#cache.filterRows(keep); } catch (error) { hidden.dispose(); throw error; }
|
|
80
|
-
this.#hidden!.dispose(); this.#hidden = hidden;
|
|
81
|
-
this.#processed = keep.map(row => this.#processed[row]!);
|
|
82
|
-
}
|
|
83
|
-
async draft(pending: readonly number[], depth: number, steps: readonly number[]): Promise<number[][]> {
|
|
84
|
-
const B = pending.length, tokens: MlxArray[] = [];
|
|
85
|
-
let ids: MlxArray | null = ops.fromInt32([...pending], [B, 1]), chained: MlxArray | null = null;
|
|
86
|
-
this.#cache.specRoundBegin();
|
|
87
|
-
try {
|
|
88
|
-
for (let position = 0; position < depth; position++) {
|
|
89
|
-
const hidden = await this.graph.forward(ids!, chained ?? this.#hidden!, this.#cache);
|
|
90
|
-
chained?.dispose(); chained = hidden;
|
|
91
|
-
using logits = this.graph.project(hidden);
|
|
92
|
-
using flat = ops.reshape(logits, [B, logits.shape.at(-1)!]);
|
|
93
|
-
using logprobs = toLogprobs(flat);
|
|
94
|
-
const next = this.sampling!.sample(logprobs, steps.map(step => step + position));
|
|
95
|
-
tokens.push(next); ids!.dispose(); ids = ops.reshape(next, [B, 1]);
|
|
96
|
-
}
|
|
97
|
-
using packed = depth ? ops.concatAxis(tokens, 0) : null;
|
|
98
|
-
const read = packed?.toIntTokens() ?? [];
|
|
99
|
-
this.#drafts = Array.from({ length: B }, (_, row) =>
|
|
100
|
-
Array.from({ length: depth }, (_, position) => read[position * B + row]!));
|
|
101
|
-
this.#depth = depth; return this.#drafts;
|
|
102
|
-
} finally { ids?.dispose(); chained?.dispose(); disposeResources(tokens); }
|
|
103
|
-
}
|
|
104
|
-
async commit(accepted: readonly number[], context: MlxArray): Promise<void> {
|
|
105
|
-
const B = accepted.length, width = Math.max(...accepted);
|
|
106
|
-
if (this.#depth) this.#cache.specRoundRollback(1);
|
|
107
|
-
else this.#cache.specRoundCommit();
|
|
108
|
-
if (width) {
|
|
109
|
-
using ids = ops.fromInt32(this.#drafts.flatMap(tokens => Array.from({ length: width }, (_, i) => tokens[i] ?? 0)), [B, width]);
|
|
110
|
-
using hidden = context.slice([0, 0, 0], [B, width, context.shape[2]!]);
|
|
111
|
-
this.#cache.specRoundBegin();
|
|
112
|
-
using output = await this.graph.forward(ids, hidden, this.#cache);
|
|
113
|
-
output.eval(); this.#cache.specRoundRollback(accepted);
|
|
114
|
-
}
|
|
115
|
-
using positions = ops.fromInt32([...accepted], [B, 1, 1]);
|
|
116
|
-
const hidden = ops.takeAlongAxis(context, positions, 1);
|
|
117
|
-
this.#hidden!.dispose(); this.#hidden = hidden;
|
|
118
|
-
this.#processed = this.#processed.map((count, row) => count + 1 + accepted[row]!);
|
|
119
|
-
this.#drafts = []; this.#depth = 0;
|
|
120
|
-
}
|
|
121
|
-
extractRow(row: number): Glm52MtpRowState {
|
|
122
|
-
const cache = this.#cache.extractRow(row);
|
|
123
|
-
try {
|
|
124
|
-
using hidden = this.#hidden!.slice([row, 0, 0], [row + 1, 1, this.#hidden!.shape[2]!]);
|
|
125
|
-
return { cache, hidden: materializeCopy(hidden), processedTokens: this.#processed[row]! };
|
|
126
|
-
} catch (error) { cache.dispose(); throw error; }
|
|
127
|
-
}
|
|
128
|
-
dispose(): void {
|
|
129
|
-
this.#cache.dispose(); this.#hidden?.dispose(); this.#hidden = null;
|
|
130
|
-
this.#processed = []; this.#drafts = []; this.#depth = 0;
|
|
131
|
-
}
|
|
132
|
-
}
|