Research · local models · known state

A Known State for Every Local Model

Measured Recipes, Frozen Expectations, and Self-Describing Runs for Eight Quantized LLMs on One RTX 3090

Abstract

Eight quantized language models — a 27 B dense, a 35 B-A3B mixture of experts, a 12 B dense, a 26 B-A4B block-diffusion model and four 4–9 B models — are served one at a time on a single RTX 3090 through a swapping proxy and used by an agent orchestrator. Before this work each model's deployment, call settings and quality evidence lived in three files that drifted independently, and an adversarial review of a planned experiment found that the baseline it needed did not exist. We define a known state per model — one versioned spec holding deployment assertions, a call recipe, behavioural contracts and frozen expectations with explicit tolerances — and a thirteen-probe suite that measures it, including a whole-file edit task modelled on the orchestrator's actual job alongside the usual write-a-function task. A first sweep (200 scored code replies, 50 scored edits, 75 minutes of GPU time) found that the function task is bimodal at temperature 0.2 on three of the four large models (the same configuration scored 8.0, 6.0 and 6.4 on Gemma-4-12B across three runs) while the edit task was 7/7 in every sample on six of eight models; that at temperature 0 the dense models are byte-deterministic but the MoE model is not; that reasoning_effort exists only in one of the eight chat templates, so three "thinking" recipes had been measuring something else; and that the strongest model scores the same with thinking off at 40 % of the tokens. Two method rules came out of the data: freeze tolerances derived from the observed spread, and recipe selection that treats variants within the noise floor as ties broken by cost. Every number is traceable to a run record that embeds the prompts, request extras and container command it was produced with.

Doug (freePerro) with Claude · September 2026 · working draft — results sections are filled from the first full sweep; every number in this paper is traceable to a run record under logs/state/.

1. Introduction

A local model served on consumer hardware is not a checkpoint. It is a checkpoint, a quantization, a serving engine and its flags, a context window chosen by VRAM rather than by the model card, a prompt template with thinking on or off, a sampling configuration, and an output budget. Change any of these and the thing that answers is different. In the setup studied here, eight such models share one RTX 3090 through a swapping proxy, and the software that routes work to them (an agent orchestrator) needs to know, for each one, what it can be relied on to do.

Before this work, that knowledge was distributed across three files that could drift independently — the docker command per model, a shell script with the call flags used for the last measurement, and the orchestrator's per-model profiles — and its quality evidence was three hand-scored samples copied into a results file. An adversarial review of a proposed follow-up experiment (measuring how quality degrades with prompt length) established that the follow-up could not be interpreted, because the baseline it would be measured against was itself unknown: the same model had scored 8/8 in one run and error/4/4 in another with a different prompt; the strongest model's 8/8 ×3 had been obtained with an output budget twice what the proposal assumed; and with three samples per cell an 8-item test cannot support a pass/fail threshold.

This paper describes the remedy — a per-model specification that is the single source of truth, a probe suite with frozen expectations and explicit tolerances, a recipe-selection procedure that chooses call settings by measurement, and run records that carry everything they were produced with — and reports the first full sweep across all eight models. It also reports what the sweep found that the previous measurements had missed.

Contributions:

  1. A definition of "known state" for a locally served model (§4) that ties deployment, call recipe, behavioural contracts and quality floors into one versioned spec.
  2. A thirteen-probe suite (§5) with an executable whole-file edit task alongside the usual write-a-function task; the edit task models the agent orchestrator's actual job (return a whole file with one change) and turned out to behave very differently from the function task.
  3. Recipe selection by measurement (§6) and spread-derived tolerances (§7) — the second forced by the first sweep's data.
  4. Findings (§8–9): the function task is bimodal at temperature 0.2 while the edit task is stable; the dense models are byte-deterministic at temperature 0 and the MoE model is not; reasoning_effort is honoured by one template in eight; thinking off matches thinking on at 40 % of the tokens on the strongest model; a diffusion model's max_tokens behaves as a target, not a cap; two sampling/thinking claims in the previous results file did not reproduce.

2. Background

Executable tests as the metric. Scoring generated code by running hidden tests rather than by string similarity follows HumanEval [1]; we keep the model's own tests as a secondary signal and score only on tests it never saw.

Prompt and sampling sensitivity. Small changes in prompt formatting move benchmark scores by large margins [2]; the "tuned" prompt variant used here (a one-block system prompt plus a stated unit convention, with temperature 0.2) had lifted one model from 6/8 to 8/8 ×3 in an earlier controlled re-test and was assumed to help every model. §8 tests that assumption per model.

Long-context degradation. Position and length effects ("lost in the middle" [3], RULER [4], NoLiMa [5], the Chroma context-rot report [6]) motivated the deferred cliff measurement; this paper establishes the zero-length floor that measurement needs.

Serving. vLLM [7] with paged attention serves every model; weights are 4-bit (AWQ [8], GPTQ [9], AutoRound [10]) except the bf16 small models; one model uses a speculative drafter [11], which is rejection-sampled and therefore does not change the output distribution — we treat it as a speed feature, not a quality confound.

3. Setup

3.1 Hardware

One RTX 3090 (24 GB GDDR6X, Ampere sm_86) power-limited to 250 W. Desktop rendering is pinned to a separate RTX 5060 so that the 3090 holds only the inference engine; this was verified with nvidia-smi immediately before the sweep (one process on the card: VLLM::EngineCore). Host: Linux 7.0, Python 3.14.

3.2 Serving stack

llama-swap v251 listens on 127.0.0.1:11440 and runs one docker run per model, stopping the previous container before starting the next (one resident model; a swap costs 1–5 minutes of container start and graph capture). Seven models run on the stock vllm/vllm-openai:v0.28.0 image; Qwen3.8-27B runs on a third-party image built on a vLLM 0.27.1 fork with a W4A16 requant and a DFlash2 drafter. Every entry sets useModelName (without it llama-swap forwards the alias verbatim and the inner vLLM returns 404 — a fault found the day before this work). Two proxy routes matter: /v1/* (OpenAI and Anthropic APIs) and /upstream/<model>/*, through which /tokenize returns the exact token count and the live max_model_len.

3.3 Models

idcheckpoint / quantparamswindow (--max-model-len)status
qwen3.8-27bQwen3.8-27B, AutoRound W4A16 body + GPTQ-int4 head, DFlash2 W4A16 drafter27 B dense65,536keep
ornith-1.5-35bOrnith-1.5-35B-A3B (Tiel-Coder weights), AutoRound int4, bf16 MTP head35 B MoE, 3 B active32,768keep
gemma-4-12bGemma-4-12B-it, official QAT W4A1612 B dense65,536keep
diffusiongemma-26bDiffusionGemma-26B-A4B-it, AWQ-INT4 (symmetric, g32), block diffusion26 B MoE, 4 B active32,768bench-only
ornith-1.5-9bOrnith-1.5-9B, bf169 B65,536candidate-retire
qwen3.8-9b-distillQwen3.8-9B-Distill, bf169 B65,536candidate-retire
qwen3.5-4bQwen3.5-4B, bf164 B131,072candidate-retire
qwen3.5-4b-awqQwen3.5-4B, AWQ-INT44 B131,072candidate-retire

Windows are VRAM choices (KV-cache budget on a 24 GB card), not checkpoint limits; Qwen3.8-27B is natively 262K. status is an operational label carried in the spec: keep models receive routed work, bench-only is measured but not routed, candidate-retire is measured once so that the decision to drop it is recorded with numbers.

4. What a known state is

For each model, one YAML file (specs/<model>.yaml) holds:

The spec is the only place any of this is typed. The docker configuration is asserted against it, the orchestrator's profiles are derived from it, and every run record embeds the prompts, request extras and verbatim docker command it ran with, so that a record from a month ago can be compared with today's without guessing what changed.

5. Probes and tasks

5.1 Probes

proberequestlocks inpasses when
listedGET /v1/modelsthe model is offeredid present
deploymentreads llama-swap.yamlthe docker cmd matches the specall cmd_contains substrings and the image present; useModelName set
tokenizePOST /upstream/<m>/tokenizelive window = spec; swap timemax_model_len equal, count > 0
short"Reply with exactly: ok" ×2instruction following; warm TTFTreply contains "ok" (or the recorded eos quirk)
thinking"What is 17*23? Answer with the number only."the thinking mode does what it saysoff → 0 reasoning tokens; on → some; finish_reason=stop; 391 present
sampling"Say hi." with temperature 0.2whether sampling params are accepted200, or 400 where the spec says no_sampling_params
over_windowmax_tokens = max_model_len + 1the 400 body names the limit400 and body contains a limit marker
length_capthe code task at max_tokens 16truncation reported as lengthfinish_reason == "length"
code ×N§5.2code-quality floormean within tolerance of frozen
edit ×N§5.3whole-file edit floormean within tolerance of frozen
cache6.1K-token prompt, then a second turnprefill rate; prefix-cache TTFTsecond-turn TTFT ≤ 2× frozen
toolsone tool callOpenAI tool callingright function and argument
anthropicPOST /v1/messagesthe Anthropic routetext returned (or the recorded value)

Contract probes send only the thinking kwargs; task probes send the full recipe. All chat calls are streamed with stream_options.include_usage, so token counts are the server's, and finish_reason is captured from the stream. The over_window and length_cap probes exist because the orchestrator's overflow classifier and its output-floor logic depend on those two server behaviours; a serving-engine upgrade that changed either would be caught here before any work order was affected.

5.2 Code task

Write parse_door_size(s: str) -> tuple[int, int] that parses sizes such as 16x7, 16' x 7', 16 ft by 7 ft, 192" x 84" into inches, with eight pytest cases. This is the task from the earlier bake-off, unchanged, so the scores are comparable. Two prompt variants: plain (the bare request) and tuned (a system prompt demanding exactly one fenced block, no revisions, raw regex strings; a user prompt that states the unit convention; temperature 0.2, top_p 0.95, presence_penalty 1.0). Scoring: every fenced block is joined and written as a module; if that does not parse, the first block that parses and defines the function is used instead; the model's own tests run first, then eight hidden external tests the model never saw. The reported score is hidden passes out of 8; compiles records whether the module parsed and pytest collected.

5.3 Edit task

Given a 60-line door_quote.py (a dataclass, five pure functions and a formatter), add a keyword parameter rush: bool = False to quote(); when true, add a rush_fee line item equal to 12 % of panels + labor + opener, placed after opener and before subtotal, included in the subtotal so that discount and tax apply to it; when false, the returned dict must be exactly what it was; change nothing else; return the entire file in one fenced block.

This models the orchestrator's implementer, which asks a local model for a whole file with one change and replaces the file with the reply. Scoring: the last fenced block that defines quote is written as door_quote.py and run against seven hidden tests — constants unchanged, helpers unchanged, signature, no-rush output identical to before, rush line item present and in the right position, rush × discount × tax arithmetic, validation and formatting unchanged. Two further measurements are recorded: preserved, difflib's line-similarity between the original and the returned file, and Δ lines, the unified-diff line count. The reference solution scores 7/7 with Δ4; the unchanged file scores 4/7, failing exactly the three rush tests.

6. Recipe selection

For each model, refine.py runs the code task five times under each variant listed in the spec — thinking off or reasoning_effort=low, prompt tuned or plain, max_tokens 4096 or 8192 (DiffusionGemma has neither thinking nor sampling variants: vLLM rejects both for diffusion models) — and ranks variants by mean hidden score, then compile rate, then fewest length-capped replies, then fewest completion tokens — with a correction for noise that the first sweep forced (§9): a variant within the best variant's noise floor (max(1.0, 2 × SE of its samples), capped at 2.0) with no worse compile or length-cap rate is a tie, and a tied variant displaces the best only if it needs at least 25 % fewer completion tokens. The winner is written into the spec's recipe; the whole table is kept under refined and in a JSON record. The recipe is chosen on the code task and the edit task is then measured with it; §10 lists this as a limitation.

7. Freezing and tolerances

modeltest.py --freeze writes the run's measurements into expectations. A later run passes a task probe while its mean is at least the frozen mean minus a tolerance, its compile rate is within 0.2 of the frozen rate, and its length-capped rate is not more than 0.2 above; speed passes while median decode is at least 0.8× the frozen median and the cached second turn is at most 2× the frozen value; contract probes must return the recorded value.

The tolerance was initially a fixed 1.0 (one test case, the resolution of an 8-item test with N = 5). The first freeze changed the rule: Ornith-1.5-35B scored 8, 8, 8, 6, 0 in recipe selection and 0, 8, 4, 4, 6 in the freeze run five minutes later with the identical recipe, while its edit task scored 7, 7, 7, 7, 7 in both. A fixed ±1.0 would have called the second run a regression. The tolerance is now max(1.0, 2 × SE) where SE is the standard error of the N samples — 2.65 for that model's code task and 1.0 for its edit task — and the per-sample values and standard deviation are frozen alongside the mean so the spread is visible, not hidden in an average.

8. Results

The sweep ran 2026-08-31 from 20:28 to 21:43 (eight models, refine then freeze, one resident at a time), followed by a fix-up pass to 21:53 that re-judged Qwen's variants under the corrected tie rule, relabelled Gemma's recipe, re-froze both, ran a greedy A/A on the three kept models and re-measured DiffusionGemma's sampling contract per parameter. In total 200 code replies and 50 edit replies were scored by hidden tests. Tables 1–4 are generated by bin/paper_tables.py from the run records; the run id in the last column of Table 1 names the JSON file each row comes from.

Table 1 — known state per model (latest run)

modelstatusrecipe (thinking / prompt / max_tokens)code /8 mean (samples)SDedit /7 mean (samples)preservedtokens/reply (code)decode tok/sprefill tok/scached turnswaprun
qwen3.8-27bkeepoff / tuned / 40968 (8,8,8,8,8)0.07 (7,7,7,7,7)0.9671005184.511610.75 s53.4 s20260831-214346
ornith-1.5-35bkeepoff / tuned / 40964.4 (0,8,4,4,6)2.977 (7,7,7,7,7)0.922352214.966210.31 s0.0 s20260831-203413
gemma-4-12bkeepoff / tuned / 81926.4 (8,0,8,8,8)3.587 (7,7,7,7,7)0.9256877.622330.095 s60.3 s20260831-214607
diffusiongemma-26bbench-onlyoff / tuned / 2048 (no sampling params)3.6 (4,0,8,6,0)3.587 (7,7,7,7,7)0.947440407.319672.041 s0.0 s20260831-204828
ornith-1.5-9bcandidate-retireoff / tuned / 40963.2 (2,4,4,0,6)2.286.8 (7,7,6,7,7)0.94356544.437050.143 s0.0 s20260831-210903
qwen3.8-9b-distillcandidate-retiredefault / tuned / 81921.2 (2,4,0,0,0)1.795.4 (5,6,6,5,5)0.9178144.537090.135 s0.0 s20260831-212017
qwen3.5-4bcandidate-retireoff / tuned / 40961.6 (0,0,8,0,0)3.587 (7,7,7,7,7)0.955110175.563200.085 s0.0 s20260831-213628
qwen3.5-4b-awqcandidate-retireoff / tuned / 40961.8 (3,6,0,0,0)2.687 (7,7,7,7,7)0.942863170.467570.088 s0.0 s20260831-214237
code task /8edit task /7
Per-sample scores of every model on the code and edit tasks, frozen run Code task — hidden tests passed, of 8 0 1 2 3 4 5 6 7 8 qwen3.8-27b keep qwen3.8-27b sample 1: 8/8 qwen3.8-27b sample 2: 8/8 qwen3.8-27b sample 3: 8/8 qwen3.8-27b sample 4: 8/8 qwen3.8-27b sample 5: 8/8 ornith-1.5-35b keep ornith-1.5-35b sample 1: 0/8 ornith-1.5-35b sample 2: 8/8 ornith-1.5-35b sample 3: 4/8 ornith-1.5-35b sample 4: 4/8 ornith-1.5-35b sample 5: 6/8 gemma-4-12b keep gemma-4-12b sample 1: 8/8 gemma-4-12b sample 2: 0/8 gemma-4-12b sample 3: 8/8 gemma-4-12b sample 4: 8/8 gemma-4-12b sample 5: 8/8 diffusiongemma-26b bench-only diffusiongemma-26b sample 1: 4/8 diffusiongemma-26b sample 2: 0/8 diffusiongemma-26b sample 3: 8/8 diffusiongemma-26b sample 4: 6/8 diffusiongemma-26b sample 5: 0/8 ornith-1.5-9b candidate-retire ornith-1.5-9b sample 1: 2/8 ornith-1.5-9b sample 2: 4/8 ornith-1.5-9b sample 3: 4/8 ornith-1.5-9b sample 4: 0/8 ornith-1.5-9b sample 5: 6/8 qwen3.8-9b-distill candidate-retire qwen3.8-9b-distill sample 1: 2/8 qwen3.8-9b-distill sample 2: 4/8 qwen3.8-9b-distill sample 3: 0/8 qwen3.8-9b-distill sample 4: 0/8 qwen3.8-9b-distill sample 5: 0/8 qwen3.5-4b candidate-retire qwen3.5-4b sample 1: 0/8 qwen3.5-4b sample 2: 0/8 qwen3.5-4b sample 3: 8/8 qwen3.5-4b sample 4: 0/8 qwen3.5-4b sample 5: 0/8 qwen3.5-4b-awq candidate-retire qwen3.5-4b-awq sample 1: 3/8 qwen3.5-4b-awq sample 2: 6/8 qwen3.5-4b-awq sample 3: 0/8 qwen3.5-4b-awq sample 4: 0/8 qwen3.5-4b-awq sample 5: 0/8 Edit task — hidden tests passed, of 7 0 1 2 3 4 5 6 7 qwen3.8-27b keep qwen3.8-27b sample 1: 7/7 qwen3.8-27b sample 2: 7/7 qwen3.8-27b sample 3: 7/7 qwen3.8-27b sample 4: 7/7 qwen3.8-27b sample 5: 7/7 ornith-1.5-35b keep ornith-1.5-35b sample 1: 7/7 ornith-1.5-35b sample 2: 7/7 ornith-1.5-35b sample 3: 7/7 ornith-1.5-35b sample 4: 7/7 ornith-1.5-35b sample 5: 7/7 gemma-4-12b keep gemma-4-12b sample 1: 7/7 gemma-4-12b sample 2: 7/7 gemma-4-12b sample 3: 7/7 gemma-4-12b sample 4: 7/7 gemma-4-12b sample 5: 7/7 diffusiongemma-26b bench-only diffusiongemma-26b sample 1: 7/7 diffusiongemma-26b sample 2: 7/7 diffusiongemma-26b sample 3: 7/7 diffusiongemma-26b sample 4: 7/7 diffusiongemma-26b sample 5: 7/7 ornith-1.5-9b candidate-retire ornith-1.5-9b sample 1: 7/7 ornith-1.5-9b sample 2: 7/7 ornith-1.5-9b sample 3: 6/7 ornith-1.5-9b sample 4: 7/7 ornith-1.5-9b sample 5: 7/7 qwen3.8-9b-distill candidate-retire qwen3.8-9b-distill sample 1: 5/7 qwen3.8-9b-distill sample 2: 6/7 qwen3.8-9b-distill sample 3: 6/7 qwen3.8-9b-distill sample 4: 5/7 qwen3.8-9b-distill sample 5: 5/7 qwen3.5-4b candidate-retire qwen3.5-4b sample 1: 7/7 qwen3.5-4b sample 2: 7/7 qwen3.5-4b sample 3: 7/7 qwen3.5-4b sample 4: 7/7 qwen3.5-4b sample 5: 7/7 qwen3.5-4b-awq candidate-retire qwen3.5-4b-awq sample 1: 7/7 qwen3.5-4b-awq sample 2: 7/7 qwen3.5-4b-awq sample 3: 7/7 qwen3.5-4b-awq sample 4: 7/7 qwen3.5-4b-awq sample 5: 7/7
Figure 1. Every sample of the frozen run, per model: five dots per row at the hidden-test score, stacked where equal; the black tick is the mean. Top, the write-a-function task out of 8; bottom, the whole-file edit task out of 7; the model's status label sits at the right. Hover a dot for its run id. The code panel is where the spread lives; the edit panel is a wall of sevens.

Table 2 — recipe selection (code task, 5 samples per variant)

qwen3.8-27b

variantmean /8samplescompilelength-cappedtokensreasoning charstok/s
thinking=low prompt=plain max_tokens=819288,8,8,8,81.00.028366560188.9
thinking=low prompt=tuned max_tokens=81927.68,8,8,6,81.00.023314975194.8
thinking=off prompt=tuned max_tokens=40967.45,8,8,8,81.00.09500178.8
thinking=off prompt=plain max_tokens=40967.26,8,8,8,61.00.013000182.1

chosen: {"thinking": "off", "prompt": "tuned", "max_tokens": 4096} (rule cheap, tie floor 1.0; run 20260831-203446)

ornith-1.5-35b

variantmean /8samplescompilelength-cappedtokensreasoning charstok/s
thinking=off prompt=tuned max_tokens=409668,8,8,6,00.80.04840217.0
thinking=low prompt=tuned max_tokens=81924.40,6,8,8,01.00.0451412228177.2
thinking=off prompt=plain max_tokens=40963.25,0,5,2,40.80.06310207.0
thinking=low prompt=plain max_tokens=81922.60,8,5,0,00.80.4672120141162.2

chosen: {"thinking": "off", "prompt": "tuned", "max_tokens": 4096} (rule best, tie floor None; run 20260831-202801)

gemma-4-12b

variantmean /8samplescompilelength-cappedtokensreasoning charstok/s
thinking=low prompt=tuned max_tokens=819288,8,8,8,81.00.0672076.6
thinking=off prompt=tuned max_tokens=409668,8,6,0,80.80.0805077.1
thinking=off prompt=plain max_tokens=40964.86,8,6,2,21.00.0724077.3

chosen: {"thinking": "low", "prompt": "tuned", "max_tokens": 8192} (rule cheap, tie floor 1.0; run 20260831-204059)

diffusiongemma-26b

variantmean /8samplescompilelength-cappedtokensreasoning charstok/s
thinking=off prompt=tuned max_tokens=204888,8,8,8,81.00.04830330.7
thinking=off prompt=tuned max_tokens=409648,4,8,0,01.00.08680413.6
thinking=off prompt=plain max_tokens=20481.60,8,0,0,00.40.06900348.1

chosen: {"thinking": "off", "prompt": "tuned", "max_tokens": 2048} (rule cheap, tie floor 1.0; run 20260831-204610)

ornith-1.5-9b

variantmean /8samplescompilelength-cappedtokensreasoning charstok/s
thinking=off prompt=tuned max_tokens=40962.45,0,2,5,01.00.0576044.5
thinking=off prompt=plain max_tokens=40961.20,0,0,6,00.40.21881044.2
thinking=default prompt=tuned max_tokens=819200,0,0,0,00.00.675302233244.0

chosen: {"thinking": "off", "prompt": "tuned", "max_tokens": 4096} (rule cheap, tie floor 2.0; run 20260831-204900)

qwen3.8-9b-distill

variantmean /8samplescompilelength-cappedtokensreasoning charstok/s
thinking=off prompt=tuned max_tokens=40963.62,6,4,0,60.80.21516044.5
thinking=default prompt=tuned max_tokens=81923.20,0,0,8,81.00.091671744.5
thinking=off prompt=plain max_tokens=40962.21,0,0,5,50.80.21540044.6

chosen: {"thinking": "default", "prompt": "tuned", "max_tokens": 8192} (rule cheap, tie floor 2.0; run 20260831-211143)

qwen3.5-4b

variantmean /8samplescompilelength-cappedtokensreasoning charstok/s
thinking=off prompt=tuned max_tokens=409640,8,6,6,01.00.0783075.6
thinking=off prompt=plain max_tokens=40961.43,2,2,0,01.00.0870075.2
thinking=default prompt=tuned max_tokens=819200,0,0,0,00.21.081922048474.0

chosen: {"thinking": "off", "prompt": "tuned", "max_tokens": 4096} (rule cheap, tie floor 2.0; run 20260831-212423)

qwen3.5-4b-awq

variantmean /8samplescompilelength-cappedtokensreasoning charstok/s
thinking=off prompt=tuned max_tokens=40961.20,0,0,6,01.00.06470172.0
thinking=off prompt=plain max_tokens=409610,3,0,0,20.80.06440165.8
thinking=default prompt=tuned max_tokens=819200,0,0,0,00.80.4408313973169.9

chosen: {"thinking": "off", "prompt": "tuned", "max_tokens": 4096} (rule cheap, tie floor 2.0; run 20260831-213852)

Table 3 — contract probes (latest run)

modellisteddeploymenttokenizeshortthinkingsamplingover_windowlength_capcachetoolsanthropic
qwen3.8-27b✓ ['qwen3.8-27b']✓ matches✓ 65536✓ ok✓ none/answered✓ accepted (all 5 ac✓ 400+named✓ length✓ 0.75✓ ok✓ ok
ornith-1.5-35b✓ ['ornith-1.5-35b']✓ matches✓ 32768✓ ok✓ none✓ accepted✓ 400+named✓ length✓ 0.31✓ ok✓ ok
gemma-4-12b✓ ['gemma-4-12b']✓ matches✓ 65536✓ ok✓ none/answered✓ accepted (all 5 ac✓ 400+named✓ length✓ 0.09✓ ok✓ ok
diffusiongemma-26b✓ ['diffusiongemma-2✓ matches✓ 32768✗ eos✗ none✗ accepted✓ 400+named✓ length✓ 2.04✓ ok✓ ok
ornith-1.5-9b✓ ['ornith-1.5-9b']✓ matches✓ 65536✓ ok✓ none/answered✓ accepted (all 5 ac✓ 400+named✓ length✓ 0.14✓ ok✓ ok
qwen3.8-9b-distill✓ ['qwen3.8-9b-disti✓ matches✓ 65536✓ ok✓ some/answered✓ accepted (all 5 ac✓ 400+named✓ length✓ 0.13✓ ok✗ no-text
qwen3.5-4b✓ ['qwen3.5-4b']✓ matches✓ 131072✓ ok✓ none/answered✓ accepted (all 5 ac✓ 400+named✓ length✓ 0.09✓ ok✗ no-text
qwen3.5-4b-awq✓ ['qwen3.5-4b-awq']✓ matches✓ 131072✓ ok✓ none/answered✓ accepted (all 5 ac✓ 400+named✓ length✓ 0.09✓ ok✗ no-text

Table 4 — the 2026-08-30 re-test (n=3, tuned, thinking off) against this sweep's tuned/off variant (n=5)

modelre-test n=3this sweep, same variant, n=5meanverdict from n=3verdict from n=5
qwen3.8-27b8,8,85,8,8,8,87.4usable (mean 8)usable (mean 7.4, SD 1.34)
ornith-1.5-35berr,4,48,8,8,6,06unusable (mean 4)usable (mean 6, SD 3.46)
gemma-4-12b8,8,68,8,6,0,86usable (mean 7.3)usable (mean 6, SD 3.46)
diffusiongemma-26b0,0,88,8,8,8,88unusable (mean 2.7)usable (mean 8, SD 0.0)
ornith-1.5-9b5,0,25,0,2,5,02.4unusable (mean 2.3)unusable (mean 2.4, SD 2.51)
qwen3.8-9b-distill2,6,42,6,4,0,63.6unusable (mean 4)unusable (mean 3.6, SD 2.61)
qwen3.5-4b0,8,60,8,6,6,04unusable (mean 4.7)unusable (mean 4, SD 3.74)
qwen3.5-4b-awq2,0,40,0,0,6,01.2unusable (mean 2)unusable (mean 1.2, SD 2.68)

Greedy A/A (temperature 0, top_p 1, five samples, code task). Qwen3.8-27B: 8,8,8,8,8, five byte-identical replies (one md5), 1,122 tokens mean. Gemma-4-12B: 8,8,8,8,8, five byte-identical replies, 525 tokens. Ornith-1.5-35B: 4,0,8,8,8, five different replies (five md5s, 1,239–1,597 bytes, first divergence at byte 89). The same container without MTP speculative decoding (ornith-1.5-35b-nomtp, run ornith-1.5-35b-nomtp/refine-20260831-222154) still produced five different greedy replies, 0,0,8,4,8, at 168 tok/s instead of 215–237. Runs qwen3.8-27b/refine-20260831-214535, gemma-4-12b/refine-20260831-214847, ornith-1.5-35b/refine-20260831-214923.

Chat-template audit (local tokenizer files). reasoning_effort appears in the Qwen3.8-27B template (reasoning_effort|default('xhigh'), accepted values xhigh/medium/low) and in none of the other seven. Gemma-4 (12B and DiffusionGemma): enable_thinking | default(false) — thinking off unless asked. Ornith-1.5 (35B and 9B), Qwen3.8-9B-Distill, Qwen3.5-4B (both): Qwen3-style, enable_thinking is false emits an empty <think> block, otherwise thinking is on by default.

9. Analysis

9.1 The function task is noisy; the edit task is not

Three of the four large models flipped between runs of the same recipe minutes apart: Ornith-1.5-35B 8,8,8,6,0 → 0,8,4,4,6; DiffusionGemma 8,8,8,8,8 → 4,0,8,6,0; Gemma-4-12B 8,8,8,8,8 → 8,8,6,0,8 → 8,0,8,8,8, where the first two runs were labelled "low" and "off" but rendered the identical prompt (§9.3), making them an accidental A/A test: means 8.0, 6.0 and 6.4 from one configuration. The per-sample standard deviations in Table 1 (2.3–3.6 on an 8-point scale) say the same thing. The outcomes are bimodal — a reply is usually a correct program or a broken one — so a mean over five is a coarse estimate and a threshold of one test case cannot separate signal from sampling. Qwen3.8-27B is the exception: 8/8 in 15 of 15 samples at temperature 0.2 under its chosen recipe (5/8 once in the plain-ordering refine table).

The edit task did not flip. Six of eight models scored 7/7 in all five samples, with 92–97 % of the file preserved and diffs of 4–11 lines (the reference solution is Δ4); Ornith-9B scored 7,7,6,7,7 and Qwen3.8-9B-Distill 5,6,6,5,5. Copying a 60-line file and inserting one keyword parameter is a lower-entropy job than writing a parser from a specification: most tokens are constrained by the input, and the free choices are few. That is also the orchestrator's job, which is the point of the task: on this evidence the whole-file Replace step is not where the small models fail, and a 4 B model that scores 1.6/8 on the function task still returned a correct edited file five times out of five.

9.2 Where the variance comes from

At temperature 0 the two dense models produced five byte-identical replies each — the stack (vLLM 0.28.0 and the 0.27.1 fork, W4A16 Marlin kernels, the DFlash2 drafter, prefix caching) is deterministic end to end for them, and all of their temperature-0.2 spread is sampling. Ornith-1.5-35B is not deterministic at temperature 0: five different replies diverging within the first hundred bytes. It is the only kept model that is a mixture of experts (AutoRound int4 with Marlin MoE kernels) and the only one using MTP speculative decoding. Removing MTP did not restore determinism (five different greedy replies without it), so the drafter is exonerated and the source is in the MoE path — expert routing or the int4 Marlin MoE kernels — which is the next isolation experiment (VLLM_MARLIN_USE_ATOMIC_ADD, then prefix caching, one at a time). For the suite this means a greedy regression mode pins the dense models exactly (any change is real) but cannot pin Ornith, which keeps the N = 5, spread-tolerance regime.

9.3 Prompt and thinking effects, per model

The "tuned" prompt (one fenced block, stated unit convention, temperature 0.2) had been adopted on the strength of one model's re-test. Table 2 measures it per model against the plain prompt at the same thinking setting: decisive for DiffusionGemma (8.0 vs 1.6, compile rate 1.0 vs 0.4), large for Ornith (6.0 vs 3.2) and Gemma-4-12B (6.0 vs 4.8), and within noise on Qwen (7.4 vs 7.2 with thinking off; 7.6 vs 8.0 with effort low). It helps the models that need help.

Thinking is a different story per template. On Qwen3.8-27B, whose template honours reasoning_effort, effort=low and thinking-off both reach 8/8 — at 2,502 versus 1,005 completion tokens in the freeze runs — so the recipe is thinking off. On Ornith, whose template has no reasoning_effort, the "low" variants were default-effort thinking: 12–20 K characters of reasoning per reply, two of five replies length-capped at 8,192 tokens, and worse scores (4.4 and 2.6). On Gemma-4-12B the kwarg is silently ignored, which is how the A/A test in §9.1 happened. The deployment probe now reads the chat template and fails any recipe that claims an effort level the template cannot honour; the paper's own first refine tables carry the mislabelled rows, kept as recorded.

9.4 What three samples had concluded

Table 4 puts the 2026-08-30 re-test (three samples, tuned, thinking off) beside the same variant in this sweep (five samples). Ornith-1.5-35B was "err, 4, 4" and read as unusable; five samples gave 8,8,8,6,0. DiffusionGemma was 0, 0, 8 and read as the weakest; five samples gave 8,8,8,8,8 — and the freeze run five minutes later gave 4,0,8,6,0. Both verdicts were sampling. The honest statement is that on these two models the function task's outcome distribution is wide enough that neither three nor five samples locate the mean to within a test case; the frozen expectations carry the per-sample values and a tolerance of two standard errors so that the next run is judged against the spread, not the point.

9.5 Speed, cost and the retire decision

Decode rates (Table 1) confirm the earlier observation that a 27 B W4A16 model on this card is faster than a 9 B bf16 one (185 vs 44–45 tok/s; the bf16 models are bandwidth-bound). Prefill separates the architectures more than the sizes: Ornith 6,600 tok/s, the 4 B models 6,300–6,800, Gemma-12B 2,200, Qwen-27B 1,160. DiffusionGemma decodes at 407 tok/s but its second turn costs 2.0 s (canvas re-encode) and its max_tokens behaves as a generation target — 2,048 gave 8/8 ×5 at 483 tokens, 4,096 gave 8,4,8,0,0 at 868 tokens with the same prompt — a property of block diffusion that a token cap designed for autoregressive models does not anticipate.

The four candidate-retire models scored 1.2–3.2/8 on the function task under their best measured recipe, at 44–170 tok/s. Three of them return a correct whole-file edit 7/7 ×5. Whether that is worth a swap slot is an operational decision; the numbers to make it with are now in the specs.

9.6 What the suite caught without being asked

Four of the eight freeze runs reported FAIL. None was a model regression; each was a probe doing its job on the spec's own claims: Qwen's short probe returned reasoning-only under effort=low at an 8-token budget (probe fixed: 512 tokens when the recipe thinks); Gemma's thinking probe found no reasoning tokens under a recipe labelled "low" (the template finding); DiffusionGemma's sampling probe found temperature, top_p, presence_penalty, seed and min_p all accepted where the spec, copied from the previous results file, said rejected (spec corrected, orchestrator profile and its pinned test updated); and the Qwen3-style models' anthropic probe returned only a thinking block because /v1/messages cannot switch thinking off (frozen as the recorded state). A regression suite that only ever passes has not been pointed at anything.

10. Threats to validity

11. Reproducibility

Everything is in the llm-stack repository: config/llama-swap.yaml, specs/, bin/, docs/, and every run record under logs/state/<model>/ (replies are kept locally, not committed). The exact prompts, hidden tests and payloads are in docs/prompts.md with content hashes that the per-model documents and run records repeat.

bin/modeltest.py <model>              # regression against the frozen spec
bin/modeltest.py <model> --freeze     # re-freeze after an intentional change
bin/refine.py <model> --apply         # re-pick the recipe by measurement
bin/state-all.sh                      # refine + freeze, every model, in order
bin/state_report.py                   # STATE.md
bin/model_docs.py                     # docs/<model>.md and docs/prompts.md
bin/profiles-from-specs.py --write    # orchestrator shipped profiles

Commit hashes for the sweep reported here: llm-stack ebfaf45 (sweep outputs), b415ee5 (fix-up applied); ai-pitlane e55d18c (plan 0007, regression graph, shipped profiles). The paper itself is docs/paper.md in the same repository.

12. Future work

The measurement this floor was built for: pad the same tasks with real source files at 4/8/16/32/48K tokens, with the zero-pad cell taken from the same run, N = 5, a criterion relative to each model's own frozen mean, and the top size set by max_model_len − max_tokens − margin; and the orchestrator-side arm — one real work order with 8/16/32 KB of ground truth, scored on whether the whole-file replacement applies and its tests pass. Also: isolating Ornith's greedy nondeterminism to a kernel or flag now that MTP is excluded, recipe selection on the edit task, KV-cache dtype (fp8) as a way to widen windows without changing the checkpoint, and a test in the orchestrator that its shipped profiles equal what the specs imply.

References

All entries verified against their abstract pages on 2026-08-31.

  1. Chen, M. et al. (2021). Evaluating Large Language Models Trained on Code. arXiv:2107.03374.
  2. Sclar, M., Choi, Y., Tsvetkov, Y., Suhr, A. (2023). Quantifying Language Models' Sensitivity to Spurious Features in Prompt Design. arXiv:2310.11324.
  3. Liu, N. F. et al. (2023). Lost in the Middle: How Language Models Use Long Contexts. arXiv:2307.03172.
  4. Hsieh, C.-P. et al. (2024). RULER: What's the Real Context Size of Your Long-Context Language Models? arXiv:2404.06654.
  5. Modarressi, A. et al. (2025). NoLiMa: Long-Context Evaluation Beyond Literal Matching. arXiv:2502.05167.
  6. Hong, K., Troynikov, A., Huber, J. (2025). Context Rot: How Increasing Input Tokens Impacts LLM Performance. Chroma Research, 14 July 2025. https://www.trychroma.com/research/context-rot
  7. Kwon, W. et al. (2023). Efficient Memory Management for Large Language Model Serving with PagedAttention. SOSP '23. arXiv:2309.06180.
  8. Lin, J. et al. (2023). AWQ: Activation-aware Weight Quantization for LLM Compression and Acceleration. arXiv:2306.00978.
  9. Frantar, E. et al. (2022). GPTQ: Accurate Post-Training Quantization for Generative Pre-trained Transformers. ICLR 2023. arXiv:2210.17323.
  10. Cheng, W. et al. (2023). Optimize Weight Rounding via Signed Gradient Descent for the Quantization of LLMs (AutoRound). arXiv:2309.05516.
  11. Leviathan, Y., Kalman, M., Matias, Y. (2023). Fast Inference from Transformers via Speculative Decoding. ICML 2023. arXiv:2211.17192.