Repository navigation
perf: make the CHUNKED_PREFILL_SIZE=1024 default conditional on context > native (+15…23% prefill at 262144) - #15
Conversation
… above it The >native clamp is right and is untouched: chunk 4096 at 300k history froze GB10. The unconditional 1024 *default* is the problem. At native 262144 — the documented opt-out, and the only option if you want bf16/fp8 KV, since a bf16 pool at 1M now trips the issue MiaAI-Lab#8 guard — it costs real prefill throughput for a hazard that is not present. Measured on 2x GB10 TP2 at native context, one variable, medians of 2: prompt chunk 1024 chunk 4096 8K 2,439 t/s 2,799 t/s +15% 32K 2,435 t/s 2,823 t/s +16% 128K 2,065 t/s 2,548 t/s +23% 4096 is also what the model card recipe quoted in this script's own header uses at --context-length 262144, and it is the bottom of a band we measured as indistinguishable (4096/8192/12288 within a +/-8% noise floor), so this is not a reach for the maximum. An explicit CHUNKED_PREFILL_SIZE still wins and is still clamped above native context.
|
Please do not merge this. I'm withdrawing the recommendation — my own follow-up measurement contradicts it. The throughput numbers in the description are real and I stand behind them. What I failed to do before filing was sample output correctness at either setting. Having now done that, Same probe, same 12 seeds, same host,
Fisher's exact, one-tailed: p = 0.0343. So the default you already ship is the safer one, and this PR would have raised the loop rate for every user of the recipe in exchange for prefill throughput. I'd rather say that plainly than leave it sitting in your queue looking reasonable. Two things I want to be careful not to overclaim:
There's also a knock-on for anyone reading our earlier reports: because I changed this knob midway through our Happy to close this myself if you'd prefer — flagging rather than deleting so the measurement and the retraction stay on the record together. If any part of it is still useful to you, the honest residual is narrow: at native context |
The defect
Two separate mechanisms currently share one value:
The clamp is right and this PR does not touch it. Above native context a
4096 chunk froze GB10 at 300k history; 1024 is the safe value and it should stay
enforced.
The unconditional default is the problem.
CONTEXT_LENGTH=262144is adocumented, supported configuration — it is the opt-out this repo tells you to
use (
CHANGELOG: "Opt out withCONTEXT_LENGTH=262144"), and it is the onlyoption at all if you want bf16 or fp8 KV, since a bf16 pool at 1M now trips the
issue #8 pool guard and refuses to boot. Anyone taking that opt-out silently
inherits a chunk size chosen for a hazard that does not exist at native context,
and pays real prefill throughput for it.
start.sh's own recorded provenance already disagrees with its default —the model card recipe it follows, quoted in the header:
4096 at
--context-length 262144. The 1M default arrived and took the chunksize down with it for every context.
What it costs
2× GB10 TP2, native 262,144 context, same pair, same harness, one variable
moved, medians of 2 measured reps (reps tight on both sides):
The shape is what you would expect: the smaller chunk multiplies scheduler
steps, and the penalty grows with prompt length.
Second-order but worth knowing, since it is the same knob: a small chunk at a
long prompt is also what widens the
/metricshandler's blocking window. On a128K prefill we measured 62–77 s of scheduler churn at chunk 1024 versus ~52 s
before, which was long enough for a 10 s metrics scrape to time out and take the
backend briefly out of a router's rotation.
Why 4096 and not higher
An earlier sweep of ours at native context found 4096 / 8192 / 12288
statistically indistinguishable — prefill within 1% above 8K, decode 250.0 vs
245.0 aggregate at c=16 against a ±8% run-to-run noise floor (six repeats,
config held fixed). So 4096 is the bottom of a measured-equivalent band, not
the maximum. Deliberately conservative: it restores the throughput, it matches
the model card, and it keeps the smallest activation footprint of the three (the
larger values also give back a little KV pool — 623,936 tokens at 8192 vs
602,176 at 12288 — which is a reason not to reach for the top of the band).
The change
CHUNKED_PREFILL_SIZEper context: 4096 whenCONTEXT_LENGTH <= YARN_NATIVE_CTX, 1024 above it. The 1M default path isbit-for-bit unchanged.
CHUNKED_PREFILL_SIZE(shell or.env) still wins, and is stillclamped above native context with the existing warning.
.env.example, the--helpheader block, and the CHANGELOG line thatcurrently reads "default 1024" updated to match.
Validation
bash -n start.shclean. Full truth table, driven through the real assignmentand the real clamp block out of the patched script:
Beyond the A/B: the value this PR proposes as the native-context default is what
we already run in production. One of our pairs serves continuously at
CONTEXT_LENGTH=262144+CHUNKED_PREFILL_SIZE=4096, carried as a local.envoverride against this recipe —
/get_server_infoon it right now reportscontext_length=262144,chunked_prefill_size=4096,max_total_num_tokens=1907264,kv_cache_dtype=nvfp4. It is stable there; theoverride is the only reason it is not at 1024.