Repository navigation
Prefill 8bit prompt windows - #3280
Open
scchumbletech wants to merge 6 commits into
Open
scchumbletech wants to merge 6 commits into
scchumbletech wants to merge 6 commits into
Conversation
… Mac ashhart#2851 gates the 16-row-block prompt path on Ultras; an M5 Max falls back to one 16-row window a dispatch and streams the whole weight slab per dispatch. Open the path on tensor units at large, Ultras keeping their long keys. Receipt (Apple M5 Max 40-core, 128 GB, Qwen3.8-27B-MLX-8bit, 8k salted unique-prefix prompt, streaming TTFT, 3-run median, --drafter z-lab/Qwen3.8-27B-DFlash2, --parallel 4, --context 262144): - main 09a9eb3: 336 tok/s cold 8-bit prefill - this change: 531 tok/s (+58%), replies byte-identical on the measured prompts - 4-bit unchanged (842-858 tok/s stock-level across runs)
The dispatch test held every non-Ultra Mac to 16 rows a dispatch; on a tensor-unit Mac the change takes the row blocks ashhart#2851 gave Ultras. The non-tensor-unit expectation stays.
Owner
|
Thanks @scchumbletech. The existing row-block dispatch is reused, with decode and the reg path preserved; all 35 host checks pass. Please shorten the two-line explanatory comment to one purpose line: it adds one lean finding on current main. The M5 Max receipt is useful. We will run the device check on our side, retaining the Ultra control separately from the newly enabled hardware.
|
Per review: the two-line explanatory comment above the row-block gate read as one purpose line; it is one line now, and the lean checker is back to 342.
The gate-comment commit mistyped deinit's lanes loop as `it`; this restores `lane_it`. The tree is the benchmarked build with the one-line gate comment.
Author
Owner
|
Thanks @scchumbletech. The gate comment is now one purpose line, the accidental iterator change is gone, and all 35 host checks pass with zero new lean findings. We will run the device check on our side on M5 Ultra as the unchanged-path control, keeping your M5 Max evidence separate for the newly enabled path.
|
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What this changes
#2851 takes a non-reg prompt chunk's 16-row blocks in one dispatch on Ultras only (
longPromptends with " Ultra"). On other tensor-unit Macs — an M5 Max here — the same chunks fall back to one 16-row window a dispatch, and each dispatch re-reads the projection's whole weight slab: a Qwen3.8-27B MLX 8-bit 8k prompt streams ~517 slab reads and sits at the memory bus. This opens the same row-block path on tensor units at large (k.device.tensorUnits()), Ultras keeping their long-key behavior exactly.atc overlap --json: not run (atc is not installed here); by hand, no open PR touches these gate lines.Checks on this head
zig build test— 844/848 steps, 3215/3246 tests passed, 29 skipped, 2 failed; both failures are pre-existing on main on this machine (PDF message normalization insrc/server/messages.zig:371, unrelated to quant). The updated dispatch test passes on tensor units and keeps the 128-dispatch expectation on non-tensor-unit devices.k.device.tensorUnits()), unreachable from those backends.Receipt
Main against branch, Apple M5 Max 40-core GPU, 128 GB, macOS 26.x, Zig 0.17.0, Xcode Metal toolchain 27B47 (Metal 32023.922), checkpoint
TensorFold/Qwen3.8-27B-MLX-8bit, serve string--drafter z-lab/Qwen3.8-27B-DFlash2 --parallel 4 --context 262144 --thinking --reasoning-effort xhigh --thinking-budget 131072, 8k salted unique-prefix prompt (fresh KV, no prefix retention), streaming TTFT-based rate, 3-run median, fresh server per run:Replies byte-identical main against branch on the measured prompts (5/5 greedy prompts, drafted and non-drafted paths). GPU pegged at 1620 MHz during passes.
4-bit unchanged: 842–858 tok/s stock-level across runs (the reg path is untouched).
Decode: unchanged — prompt gating only; the decode/verify path keeps its 16-row keys.
New switch: none. Non-reg prompt chunks on tensor-unit Macs take the row-block path automatically; every other caller keeps main's schedule.
Paths reached: Metal qwen27 non-reg widths (8/6/5/3/2-bit, oQ mixes) on any tensor-unit Mac. Could not run: Ultra (no hardware) — behavior there is main's.
Exactness: drafted = plain, byte-for-byte, on all measured prompts.
Prompt speed: the numbers above. Decode speed: n/a (unchanged code path).
Licence of new weights or drafters: n/a.
Checklist
"draft": false, a resumed prompt equals a fresh one, and concurrent equals solo (byte-identical on the measured prompts; the dispatch change does not alter any arithmetic).--drafter, no slower than without it, greedy and sampled