The dragoon-window provenance bullet still said the zealot arm owed a
measurement — it does not: the numbers are recovered and in the fetch script and
runbook. Adds the frank-tts phase-1 entry (naming law, port 7772, voice-pack law,
384/384 suite, PR #4 merged as 49c4e19, and the measured Gitea merge-field law).
Phase 1 of the voice-over goal (Gitea issue #2). One stdlib-only HTTP facade in
front of whichever TTS engine wins the engine decision: POST /v1/audio/speech
with voice=<name> answers audio in THAT voice, where a name is real exactly when
/voices/<name>/reference.wav exists — an unknown name is a 400 listing the
voices that are, never a silent fallback (a wrong-voice endpoint stays wrong for
weeks). voice_id works as the alias the omp harness sends; response_format=mp3
is really mp3 (ffmpeg re-encode); oversized input is refused with 414 instead of
half-narrated; /health reports the backend and the resolved voice list.
Two backends behind the one surface, chosen by TTS_BACKEND: omni-http forwards to
an OpenAI-shaped upstream carrying the voice as base64 reference_audio, and
llama-tts-cli runs a local binary per request with --tts-speaker-file at nice 19
so narration never starves the text endpoints. Both are driven in the seam
through stubs — no GPU, no containers.
Named frank-tts, a first-class fleet model endpoint: port 7772 in the 7770/7771
family, alias naming per the StarCraft law, rootless boot-persistent self-healing
quadlet with a read-only /home/dank/voices mount. Voice-pack law recorded in the
env header: reference.wav PLUS the engine's own speaker artifact (required, so a
voice is reusable in other runtimes), plus manifest.json provenance with offsets
always past the first 10 s of the source file.
Not deployed: the engine decision, the pack builder, deployer/homepage/Prometheus
registration and the omp models.yml runner row are phase 2.
Frank's 02:36 instruction (archive 01a14c93) ordered the 27B PTQ1_0 arm at
2 x 200,704 with the Q8 mmproj and batch/ubatch 3072/1536; it served
production 03:14:39-03:38:57 (pid 191358, journal type ptq1_0: 402 tensors).
Recovered its numbers from that process's own print_timing lines: ~48 t/s
single-stream decode, 25-27 t/s per stream at two streams, prefill 1,295 t/s
at 30,637 -> 943 at 97,856 -> 801 at 141,365. It bought the promised 1,201 MiB
and lost 37% of decode against the PQ2_0 record, so the publisher's Ampere
warning generalizes to GA102; Frank scratched the 27B plan at 03:33 for the 9B.
Every 'unfinished experiment' claim is re-keyed, and the AGENTS.md law gains
the durable lesson: a bench verdict that never reaches the repo is
indistinguishable from a rogue arm.
Post-deploy probe on frank-dragoon: one 101,987-token prompt through
/v1/chat/completions took 81.5 s cold (1,251 t/s of prefill) and 0.3 s on two
repeats — HALOGEN_CACHE_INPLACE=1 keeps the KV rows in the pool, so doubling the
pool evicted nothing the prompt cache needed. The RAM price is still real:
MemAvailable 26 -> 22 GiB.
Census of the same engine's surface corrected the Benchmarking Policy, which
quoted llama.cpp instruments at a halogen endpoint: frank-dragoon answers
/health, /metrics, /v1/models and POST /v1/chat/completions and 404s /ping,
/props, /completion and /tokenize, and no response carries Server-Timing. The
/completion `timings` object and the ttft;dur= header are frank-zealot's; on
frank-dragoon the instrument is wall clock plus usage.prompt_tokens.
Deployed 2026-10-18 (e2e 33/33). The boot ledger prints
`reserving the KV pool, 401408 positions (about 11.0 GiB)` and
`62.9 GiB of weights locked … 11.0 GiB of KV pool, 5.7 GiB of working memory,
79.6 GiB in all`, so the ~10.8 GiB that every page quoted from the
~28 KiB/position arithmetic is replaced by the reservation the engine actually
makes (11.0) and its preflight bill (11.3). Host MemAvailable fell 26 -> 22 GiB
across the raise: the FLAGS.md collision (pool RAM is n-gram page cache) paid in
full, so the warm prompt-cache ratio is flagged as the number to watch.
All "committed but not yet deployed" clauses retired: AGENTS.md topology row,
KV-pool law and memory ledger, frank-dragoon.env lore, both index pages, the
iommu page, and the runbook chronology (third production boot recorded).
The sweep also caught the LLM index still describing frank-zealot as
Bonsai-2-27B at 2 x 200,704 in its intro and topology diagram - re-keyed to the
live 9B: 8 full-attention + 24 Gated DeltaNet + blk.32 MTP, 3 x 262,144,
tensor type 141.
The cutover deploy's FIRST boot was not the shipped payload: a stale
frank-zealot.service.d/ptq1.conf from the bench window still pointed
FRANK_ZEALOT_ENV_FILE at /tmp/zealot-arm-current.env, so the unit booted the
unmeasured 27B PTQ1_0 arm (3 slots of 133,888, 21,188 MiB) while /health
answered 200, /v1/models echoed the alias and the e2e gate passed 33/33.
Drop-in retired to ~/.AGENTTRASH/20261018-zealot-ptq1-arm/; the 13:19 restart
is the shape the docs now quote (n_ctx_slot 262144, KV 13,056.00 MiB,
settled 17,922/6,203).
Corrections the production ledger forced:
- RS buffer is 150.75 MiB (3 cells) on the shipped spec-off shape; 452.25 MiB
belongs to the SPEC-ARMED arms, where MTP depth 2 bills three seqs per slot.
The drafter triples the recurrent state on top of its 3,072 MiB of f16 KV.
- Decode measured 168.4-168.7 t/s single-stream and ~300 t/s aggregate over
three streams (102.8 each). Wall-clock timing of a generation that stops on
its own reads 4x low (72 t/s for a 24-token countdown) - measure with
ignore_eos and read the engine's timings.
- OpenWebUI stores both decoration values inside JSON columns (params/meta),
and frank-dragoon's context.length had drifted to 262,144 against its own
200,704 ceiling; both re-keyed in the live DB.
New law in AGENTS.md: after deploying a recently-benched LLM service, check
DropInPaths, then /proc/<pid>/cmdline, then the ledger. Health checks cannot
see the payload.
The docs-fact census wave re-read the live hosts and re-keyed every page
it could: runtime/payload identities, ports, sizes, ledger figures, unit
state, and the retirement banners that drifted as the fleet moved. The
wave was interrupted mid-run, so this commit carries only what passed the
integrity gates: every touched page parses (front matter or H1+status
convention intact, balanced fences, no truncated tables, trailing
newline), the docs_completeness and link-integrity seams are green, and
bats is 384/384.
Numbers that this session proved on live hosts are keyed to the measured
value, not the page's earlier claim.
Swap the 3090 endpoint from Ternary-Bonsai-2-27B PQ2_0 (2 x 200,704,
fork build 10754) to Ternary-Bonsai-2-9B PQ2_0 with the MTP head IN the
file, three conversations at the trained 262,144 window
(--ctx-size 786432 --parallel 3), on vendor fork build 10777 -- the
minimum build that pairs MTP with a quantized V cache. q8_0 K + q8_0 V
is the only KV that fits: 13,056 MiB against a 26,112 MiB f16 pair.
Settled boot 17,876 used / 6,249 free.
MTP is armed and then DECLINED by measurement: the draft context bills
its own f16 KV over the whole pool (3,072 MiB) and at UBATCH_SIZE=2048
that halves decode (167.2 -> 109.2 t/s). The documented MTP arm
(SPEC_TYPE=draft-mtp + UBATCH_SIZE=1024, 213.5 t/s) is recorded in the
env header rather than left to rediscovery.
Two bugs the trial caught: ${SPEC_PRESENCE_PENALTY:=0.0} was a
default-assignment, so the env value always won and the no-presence-penalty
MTP arm was unreachable (now ${VAR=0.0}); and the Q8_0 mmproj is the
publisher's requirement for concurrent image requests, which matters at
--parallel 3.
contextWindow is now 262144 -- the widest in the fleet -- so :7771 is the
compaction hub. 27B runbook re-banned RETIRED with its bench-window
section closed; indexes, homepage card, OpenWebUI doc and the worklog
re-keyed.
frank-dragoon's total in-flight context was HALF frank-zealot's: zealot runs
one 401,408-position pool split into two 200,704 conversations, while dragoon
ran ONE 200,704-position pool behind its two slots, so a single maximum-length
request filled it and two long conversations had to stay under ~100k each.
HALOGEN_KV_POOL_POSITIONS 200704 -> 401408 = slots x ctx, the top of the seam's
legal band (ctx <= pool <= slots * ctx). The PER-REQUEST ceiling does not move:
HALOGEN_CTX stays 200704, because the checkpoint's native window is 262,144 and
the engine's own 400 text refuses to exceed it without HALOGEN_ROPE_YARN. What
this buys is concurrency, not a longer conversation, which is why the harness
contextWindow (155648 = ceiling - 45056) is untouched.
Cost: ~10.8 GiB of KV where 200,704 cost 5.5 (262,144 cost 7.2; the
2026-10-06 shape's 524,288 measured 14.6), taken from the page cache the 51.2 GB
n-gram table reads through — the warm prompt-cache ratio is the number to
re-measure after the boot. Engine-side total goes 74.1 -> ~79.4 GiB of 121.2.
Also carries scripts/download-frank-zealot-bonsai2-ptq1.sh: the PTQ1_0 candidate
payload fetcher (5,946,648,928 B, LFS sha256-verified, mmproj hardlinked), with
the publisher's own throughput table in its header — the packing is smaller but
the card measures it SLOWER on Ampere, so the swap is decided on our card, not
on the card's A100 row.
The scrape has never worked: lastError is "server returned HTTP status 501 Not
Implemented" on http://host.containers.internal:7771/metrics, and the oldest
retained sample of up{job="frank-zealot"} (2026-10-11) is already 0 -- the target
has been red across four payload generations while /health answered 200 the whole
time, keeping the critical LlmEndpointDown alert permanently active. llama.cpp
gates /metrics behind --metrics; halogen serves it natively, which is why the
asymmetry looked like a 3090-only problem.
METRICS=1 in the shipped env, --metrics reaches the argv through EXTRA_ARGS, and
the seam asserts both directions (default ships the flag, METRICS=0 strips it).
Diagnosed via /api/v1/targets lastError rather than the alert list, which is also
the lesson: Alertmanager here has no persistence, so a reboot re-stamps startsAt
and a weeks-old fault looks fresh.
Window 01:24-01:35. Byte-identical A/B (rebuild proved it: same 1,287,656 B corpus,
same billed token counts 59,024 / 21,568): cold prefill 1,585.1 -> 1,616.0 t/s
(+2.0 %), warm 208,531 -> 214,131, needle hit/hit both boots. The 13-16 % that
justified amd_iommu=off since 2026-09-11 does not exist on this host; the decode
delta (-9.7 %) is instrument noise -- three repeats of one request on the same boot
gave 31.8/46.9/47.8 t/s.
NPU precondition restored: amdxdna bound 0000:c6:00.1 (driver 0.7.0, firmware
amdnpu/17f0_11/npu_7.sbin), group 26 identity, PASID width 10, /dev/accel/accel0
root:render with dank in render. No endpoint deployed, so frank-npu stays retired
-- only its rationale changes. Gates: 0 failed units, 32 groups (31 identity + the
SD reader's DMA quirk), iGPU c5:00.0 identity with ATS, dragoon ledger unchanged
(74.1 GiB, no clamp, listening at 39.8 s).
Deferred on purpose: the pp_dpm_fclk pin (changes iGPU timing for everyone, nothing
co-runs yet) and PerfOpt (7.0.0-38 has zero perfopt symbols, 26.04 caps at 7.0.0-38.38).
Re-keyed: decision record banner/front matter/verification/revert + new execution
section, frank-npu rationale, AGENTS key lesson, both index pages.
/tmp is tmpfs: the 2026-10-18 IOMMU reboot deleted /tmp/halogen-eval mid-A/B and
the off-arm numbers nearly went unreproducible. One command restores the corpus
(wikitext-2 raw test, blanks dropped, 2891 lines / 1287656 B -- the byte count is
the identity check because battery.py sizes haystacks in characters), the 512px
probe PNG, and battery.py itself; WARM=1 also pre-reads the 51.2 GB n-gram table
so a cold page cache cannot masquerade as a measured regression. Must run through
a login shell: uv lives in ~/.local/bin.
The pending-entry grep anchored on "menuentry 'Ubuntu'" with -A4 and matched no
linux line, so the script printed nothing where it should have shown the next
boot's command line; the PENDING line then said "is in grub.cfg" when the loop
only ever compared the tracked file against /proc/cmdline. Now the default
entry's linux line is parsed with awk (first linux line of the first Ubuntu
menuentry, which is what GRUB_DEFAULT=0 selects), its iommu token is printed,
and a mismatch against the tracked file warns by name.
The 2026-09-11 trade bought a vendor-claimed 13-16% prefill figure that was
never measured here; the 2026-10-18 research (same decision record) shows what
identity mode actually costs the iGPU is the 1:1 page walk plus ATS/PRI/PASID/
GCR3 -- worth 2-4% on this silicon class, and removable outright by AMD PerfOpt
when the distro ships Linux 7.4. Meanwhile pt is what err=-19 asks for: the
XDNA2 NPU binds its own IOPT_TYPE_SVA domain and only needs the IOMMU enabled.
Measured off-vs-pt prefill arms follow in the docs commit; frank-archon
(Dankserver) is untouched.
/etc/default/grub was host-only state while the IOMMU boot line was the most
consequential kernel decision on the box (the 2026-09-11 amd_iommu=off adoption
lived only in the decision record). Fetched byte-exact (1581 B) and paired with
scripts/set-dankclaw-bootline.sh: refuses any host but dankclaw, shows the diff,
installs 0644 root:root, runs update-grub, names the pending token, and reboots
only on --reboot. The deployer plans nothing under dankclaw/host/ by design —
kernel state is not a container restart.
Reading patch v2 1/2 verbatim: amd_iommu_enable_perfopt() rehoming needs the
device ALREADY on the identity domain and switches ATS/PRI/PASID/GCR3 off via
the skip_caps path. So an iGPU in identity mode still pays a 1:1 page walk plus
those four capabilities until PerfOpt exists -- iommu=pt recovers most of the
gap, PerfOpt the last part. The first pass claimed pt alone already avoids the
cost; that was wrong and is retracted here and in the posted issue comment
(edit 23).
Also re-keys frank-npu.md, which carried the dead law 'iommu=pt is not a middle
ground' as its retirement rationale: identity mode + SVA is exactly the revival
path (amdxdna binds its own IOPT_TYPE_SVA domain), and the cost is single-digit
percent on this silicon class. Procedure step 2 now demands a local off-vs-pt
measurement instead of inheriting the vendor's 13-16%, whose slow-arm boot line
our record never identified.
Records the 2026-10-18 answer to 'does a recent kernel change retire
amd_iommu=off': PerfOpt (iommu tree 2026-09-24, Linux 7.4) stops GPA->SPA
translation for the privileged iGPU while the IOMMU stays enabled for every
other device, the NPU included. Local census proves the fix is absent here
(zero perfopt symbols in System.map-7.0.0-38, archive caps at 7.0.0-38.38),
and the September 13-16% figure was translated-domain cost, not strict-flush
cost -- lazy DMA is the Ubuntu default, so iommu=pt already avoids it. The
corrected procedure therefore flips to iommu=pt now and treats PerfOpt as a
2-4% later bonus on this silicon class (Phoronix desktop arm), with the NPU
legal under identity mode because amdxdna binds its own SVA domain.
Re-keys the AGENTS.md key-lesson bullet; no host change.
The full-suite re-run after the reset fix came back "1 flaky": 12-crawl reached
plex.franksdank.cloud, the guard cleared, and Plex Web — signed out in the
qa-e2e profile — handed the browser to its own hosted sign-in surface, so the
hostname never settled on the vhost (60 s poll, Expected plex.franksdank.cloud /
Received app.plex.tv). settleThroughGuard now takes a HANDOFFS landing list per
vhost; only plex.franksdank.cloud gets one, every other host still has to land on
its own vhost, and the guard assertions (Anubis cleared, no authentik uidField,
status < 500) are unchanged. Worklog and E2E gotcha 6 carry both symptoms: the
ERR_ABORTED reset and the hand-off.
Two faces of the same verification round.
12-crawl returned to the homepage between links with a bare page.goto, and Plex
Web (signed out, so it renders its own sign-in iframe for its Plex-account flow)
keeps redirecting the top frame: Chromium cancelled our goto with
net::ERR_ABORTED, outside the try, so the whole crawl died — once as a 420 s
timeout in the deploy gate, once at 5.4 s on the same link. backHome() tolerates
that one error class and re-issues; any other error still propagates, and the
per-app verdict (guard settled, hostname, no authentik uidField, status < 500)
is unchanged. Plex was healthy throughout (container up 2 days, 32400 answering
HTTPS 401 / plain-HTTP empty reply), so this was app behaviour, not a fault —
recorded as gotcha 6 on the E2E page.
The 200,704 boot printed 5.5 GiB reserved and 74.1 GiB in all (not the ~5.4/~74
my arithmetic predicted), so every prose figure is re-keyed to the ledger, and
the runbook gains the second production-boot section: marker revision, pool
reservation, shape line, prompt-cache entry size, and the refusal contract at the
new ceiling (400 in 0.86 s naming 200704 and the 96,405-token overage, before any
prefill). Cost stated (two maximum-length conversations never coexist; the 180k
compaction target is unreachable inside a 155,648 window) and purchase stated
(1.7 GiB of page cache, 9.1 GiB against the 2026-10-06 shape).
Frank's call the same evening as the native-payload cutover: HALOGEN_CTX and
HALOGEN_KV_POOL_POSITIONS both 262144 -> 200704 (a multiple of 4096, the rung
frank-zealot already runs). The checkpoint's native window is 262,144 and the
engine serves anything below it, so this is a RAM decision, not a capability
limit: the KV reservation drops 7.2 GiB -> ~5.4 (the 2026-10-06 pool measured
14.6), and by the FLAGS.md law -- RAM the pool takes is RAM that n-gram table
loses -- the freed positions become page cache for the 47.68 GiB table that
long prompts read. Engine-side total ~74 GiB instead of 75.8.
The 400-zone law is invariant to the value, so the harness moves WITH the
ceiling: models.yml contextWindow 217088 -> 155648 = ceiling - 45056, keeping
the gap that absorbs the chars/4 under-count (worst-case request ~156.2k vs
the 200,704 ceiling, ~44k margin). Compaction now fires at 85% = 132,300 est
(~136k measured); the 180k target of the 262,144 era is unreachable because
the window itself is 155,648. maxTokens 45056 and the coupled
cap/timeout 65536/7200 are untouched.
Cost stated plainly: with pool == ctx, ONE maximum-length request fills the
pool, so two long conversations never coexist (two of <=100k do). Acceptable
because frank-dragoon carries only the slow role and the security-reviewer
subagent, not the interactive workhorse.
Seam re-keyed: the fit-law test now proves the invariant at the new pair, and
the pool law (ctx <= pool <= slots * ctx) still holds with pool == ctx.
Deploy verification for fcd7630 (22:20): healthy in ~12 s, e2e 33/33, and the
boot ledger settles the shape — 62.9 GiB weights locked (0.8 vision) + 7.2 GiB
KV in ONE 262,144-position pool (6,656 MiB, two slots) + 5.7 GiB working =
75.8 GiB in all, n-gram 47.68 GiB read from disk, prompt cache ON (12 entries),
MTP depth-2, no clamp line. Live probes: 27*59 -> 1593, tool call, red PNG ->
Red. The two KV figures are reconciled (engine preflight FORMULA 7.4 GiB
includes block scratch + per-slot O(1) state; the RESERVATION is 7.2).
Also corrects two stale claims: the retired swift15 rows named 200,192 ctx
(raised to 262,144 on 2026-10-07 inside that same era), and the OpenWebUI
frank-dragoon row's description is now re-keyed in the live DB (backup
webui.db.bak-20261017b).
New LLM/frank-dragoon-flash-server-v2-native.md carries the shape with the
three deliberate deviations from the card (served id, SPEC_ADAPT=0, engine
pin 0.16.2), the memory ledger with the PIN_TRUNK rejection, the full
measured A/B table, and the companion law (hardlinked stock peonist files,
engine-tool certified). The swift15 page is re-banned RETIRED 2026-10-06 →
10-17 with its rollback terms; both indexes and AGENTS.md (topology table,
service section, runbook index) are re-keyed, and the root index also stops
describing the halogen-27B page as ACTIVE.
The three artifacts that produced the native-vs-swift15 verdict, so the next
payload swap starts from instruments instead of ad-hoc scripts:
census-frank-dragoon.sh — the engine's own checkpoint tools (verify/ppl/niah)
over BOTH payloads under one knob set; the pool stays 524288 deliberately
because the ppl pass scores 297,053 ids as two 262,144-token sequences.
battery-frank-dragoon.py — behavior battery against the live service: refusal
census, thinking-token census, tool-call turns, the red-PNG vision probe,
needle-in-haystack, decode/prefill/prompt-cache rates; discards the
post-boot warmup request and records the engine's 400 body (which names the
exact token overage) instead of dying on it.
trial-frank-dragoon.sh — the guarded candidate window: fetch gate, verify,
stop+mask, census, boot through a transient FRANK_DRAGOON_ENV_FILE drop-in,
battery, trap-guarded restore.
Quat3rnion/halogen-qwen3.8-flash-next-v2-abliterated is now the NATIVE
2026-10-11 v2 conversion of orcarouter's pinned BF16 (66,687,678,432 B,
LFS sha256 b5bd925f...) — 32 bytes smaller than the writer transplant it
used to ship under the same filename. The n-gram table, vision tower and
tokenizer are the stock peonist companions, hardlinked out of the swift15
payload dir: the release publishes only the main file and no source-matched
pair exists, so the engine's own tools are the referee (niah 18/18, ppl
3.968 with mean KL 0.155 against the swift15 logits, 2026-10-17).
Memory saving, per the card: HALOGEN_KV_POOL_POSITIONS 524288 -> 262144,
one pool behind both slots (boot ledger: 7.2 GiB, where the old pool
measured 14.6). HALOGEN_CTX stays 262144 so the per-request ceiling and the
harness contract (contextWindow 217088) do not move; only two MAXIMUM-length
conversations lose the ability to coexist.
Measured against the swift15 boot on identical traffic: cold prefill
+12.6 %, decode 50.0 vs 46.8 t/s, NIAH 18/18 vs 17/18, PPL +2.3 %, thinking
tokens x1.9 (the finetune's reasoning compression is gone), refusals 0/5 on
both.
Quat3rnion/halogen-qwen3.8-flash-next-v2-abliterated @main replaced the file
on 2026-10-11: a complete HIP native-v2 conversion of orcarouter's pinned
BF16 (66,687,678,432 B, sha256 b5bd925f), not the r1/r2 writer transplant
the filename used to carry. The release publishes ONLY the main file, and its
card states that the stock peonist n-gram/vision companions are NOT established
as interchangeable (source-derived table would be 51,200,246,084 B against
peonist's 51,200,246,144 B), so the script hardlinks the verified peonist trio
into the new payload dir — a hardlink is a regular file, so the serve gate's
no-symlink law holds and 47.7 GiB is not copied — and leaves the companion
question to the engine's own verify/ppl/niah tools plus the boot ledger.
Left uncommitted by the deploy session: the production decode rate (75.8 t/s,
within 1% of the trial arm), the shipped boot ledger, the live probe census,
and the picker-row law (OpenWebUI meta.description is live DB state a swap
must follow into the database, written without restarting open-webui).
The Swift1.5 w4dn8 .rad, the GLM-4.7 GGUF, and every derived model cache
were purged from dankserver (trash-staged, emptied with approval; 763 GiB
free). Rollback of the iq4r swap is now an HF re-download of the
byte-exact frank8465 mirror (LFS sha256 09dd9306...). Corrects the w4dn8
runbook header (still said LIVE) and rebuilds both Rollback sections;
log.md carries the purge record.
- production boot reproduced the census (22,664/1,461, fit 21,439 leaving
2,119 >= 1,872, KV 13,328.00 MiB at n_ctx_seq 200,704, n_slots 2), live
probes green (pong + reasoning_content, tool_calls, 512px -> Red, 75.8 t/s),
e2e 33/33
- records the two live-path stragglers the swap had to catch: the serve
script's retired-payload DEFAULTS and the OpenWebUI model row description
(live DB state, re-keyed with a backup, no forced restart)
- serve script: header + every fallback default re-keyed to the Bonsai-2 trio
(vendor LLAMA_BIN, PQ2_0 MODEL_FILE, Q8_0 MMPROJ) and CACHE_TYPE_*:=q8_0 —
a defaulted run must land on the shipped shape, never on the retired 9B/f16
pair (the trial window proved a silent default is how a swap goes wrong)
- unit Description now names the payload + KV dtype that `systemctl status`
will show during the next incident
- OpenWebUI decoration-row description re-keyed, with the law that the row is
live DB state a swap must follow into the database
- card/docs: prism-ml payload link, PQ2_0 spec, ~77 t/s (measured single
stream, replacing the 9B's ~95)
- warning re-keyed: zealot is no longer an uncensored endpoint, so the card
carries the base-alignment notice and points uncensored work at dragoon;
the test's "common uncensored text" equality (zealot==dragoon) is retired
with the payload it described — dragoon alone carries the legal warning
- env: Bonsai2 payload pair, CACHE_TYPE_K/V=q8_0 (f16 OOMs at 2x200,704:
34 KiB vs 64 KiB/token over the 16 full-attention layers), measured boot
ledger 22,664 used / 1,461 free incl. the 873 MiB mmproj that lands AFTER
the engine fit check, q4_0 fallback rung, CRACK one-line MODEL_FILE swap
- deployer: runtime/model/mmproj gates re-keyed to the PrismML vendor build
(the only loader for GGML tensor type 142 + prism.hadamard.* metadata)
- seam: payload trio pinned; KV argv assertions now derived from CACHE_TYPE_*
in the env file — the wrong-var-name f16 fallback that produced the first
failed trial window can no longer pass silently
kv_attn 26.00 KiB fp8 pages at 607,740 tokens (identical to the w4dn8
boot), slab 17,610/17,658 slots per rank (above w4dn8's 17,548 — ten
bf16-protected experts per layer pack more of the 4-bit table), sampler
9 rows, MTP 2/step, KV lending 4.22 GiB, prefix tier recovered 900,176
blocks across the payload swap. Vision probe green (reasoning read the
solid-red PNG; empty content at 64 tokens = the thinking-budget law).
e2e gate RED on three dankclaw specs: Marreta was down since the 01:41
dankclaw reboot (marreta-browser dependency-failed at boot beside
gluetun, not re-armed); pair restarted manually, redeploy rerunning
the gate.
New runbook frank-archon-radiance-qwen38-iq4r.md (publisher container,
payload chain, shape-verbatim cutover record with the boot-ledger and
measurement slots left open for the first boot, rollback). LLM index,
root vault index, and AGENTS.md (fleet table row, section, runbook
index: iq4r ACTIVE, w4dn8 RETIRED/on-disk, fp8-native deleted). Full
suite green.
Model swap on the radiance endpoint: MODEL_FILE moves from the in-house
qwen4exp-swift15-w4dn8-i8-hc8m.rad (116,416 MiB) to the engine author's
published qwen3.8-next-flash-fp8-iq4r-moe.rad (116,322 MiB, official
Qwen3.8-Flash-Next bf16 -> 4-bit non-uniform codebook experts + int8
trunk, card KL 0.0789 / top-1 92.85 % vs bf16). NO argument changed:
25600/5120 vram pair, 44928 host pool, fp8 KV, 3 x 200000, MTP depth 2,
wht6, MNBT 2048, froggeric v22.5 — the 2026-10-13 shape carries verbatim.
New fetch script scripts/download-frank-archon-iq4r.sh (hfget + exact
byte count 121,969,901,568 + LFS sha256, --verify-only default, ungated,
no token on the command line). Unit/serve/deployer lore re-keyed; the
seam pins the new payload id + sha256 and keeps the w4dn8 rollback
provenance. Homepage card points at the publisher repo.
Rollback: revert this commit (w4dn8 .rad stays on disk). The fp8-native
rad was deleted from dankserver 2026-10-15 (Frank's one-time rm, volume
for this payload); rebuild path documented.
Measured, 512 tokens, greedy, cold, at the deployed 3 x 200,000 fp8 shape:
prefill 22,208 -> 3,397, 24,000 -> 3,290, 25,600 -> 3,290 t/s at 43.5k —
the third slab step bought nothing, so the slab is a threshold whose cliff is
the 2026-10-11 arm at 26,071 (4,379), not a slope. Decode ladder: 99.0 t/s
single-stream at 43.5k, 93.3 at 197k (nearly window-free), and 3 concurrent
streams 113.9/43.3/10.9 = 18.4 t/s aggregate — the slot count is paid in
decode concurrency, the axis the shape hunt never measured because probe leg
B generates 24 tokens. probe-frank-archon-kv.py gains leg D (N-stream decode,
512 tokens, per-stream + aggregate) so no resize is priced on prefill alone.
Measured A/B on the shipped pair 25600/5120: A-cold 43.5k prefill 3,290 ->
3,584 t/s (+8.9 %) and the 3-way 197k aggregate 3,051 -> 3,589 t/s (+17.6 %,
wall 193.7 -> 164.5 s). The prediction I shipped with the arm -- slab is a
threshold below ~26 GiB, so 1,600 MiB buys ~0 -- is falsified by the measurement
it asked for. Two slab points inside noise of EACH OTHER (22,208 / 24,000) are
not a plateau. The cliff is above 25,600: 26,071 measured 4,379 t/s.
Ceiling re-derived from the engine's own budget table (card 32,624 MiB, pair at
29,120 settling 2,058 MiB free against its 209.19 MiB floor => 30,969 claimable).
The 29,120 bound was my 1 GiB \`keep free\` reserve; the seam now derives the
number, so the next resize starts from the engine's arithmetic.
Ledger for the record: slab 16,235 -> 17,548 slots while the pinned host pool
hands the same experts back (8,893 -> 7,580) -- the transfer is the mechanism,
the pinned pool is the slow path. Capacity contract live-verified at 3 slots:
3 x 199,984-token prompts accepted (599,952 tokens), fourth refused as too
large to ever fit.
Probe law learned: the oversized-prompt refusal names the prompt's token count
BEFORE prefill (free calibration) and fires on prompt tokens ALONE, not on
prompt + max_tokens; the window is ~514,286 chars at 2.5714 chars/token.
The 2 GiB/card that \`rocm-smi\` shows free is not idle: the engine's budget
table calls it driver context + the 896 MiB activation arena + 96 MiB headroom,
and says the rest is `throughput on the floor`. Its own settle line is the
number that matters — `card 0 settled at 2.01 GiB free against 209.19 MiB (the
96.00 MiB --gpu-headroom-mib and 113.19 MiB kept for the static region)` — so
1,849 MiB above the ENGINE's floor is claimable and the real ceiling is 30,969
MiB, not the 29,120 my 1 GiB reserve invented on 2026-10-11.
Shipped pair 25600/5120 = 30,720: +1,600 MiB of slab, ~458 MiB above the floor.
The slab is already saturated at 24,000 (mover took all of it, 451 KiB slack),
so this is the only direction left — KV is at its 3-slot floor (5,063 needed of
5,120).
Named prediction, because today's two points say the slab is a THRESHOLD and not
a slope (22,208 -> 3,397 t/s, 24,000 -> 3,290 t/s at 43.5k single-stream): this
arm buys ~1,600 resident expert slots and ~0 prefill. The point that moves
prefill is 26,071 (2026-10-11: 4,379 t/s), fundable only at two slots. Prefill
moving > +-3 % here falsifies the threshold reading.
Seam: the ceiling gate now derives from the engine's budget table (30,969) and
is the single owner of the pair arithmetic; the duplicate I put in the shape
test is removed.
Frank's call: three slots, and spend the KV the third slot doesn't need on
resident experts. `--max-num-seqs 3`, `--vram-kv-mib 6912 -> 5120`,
`--vram-weights-mib 22208 -> 24000` — the pair is still exactly the measured
29,120 MiB/card ceiling. The pool funds 608,027 tokens against the 600,000-token
contract (3 x 200,000, +1.3 %), and the slab gains 8.1 %.
The direction is the 2026-10-11 A/B: prefill is slab-limited, KV beyond the
contract buys nothing. At fp8 the slab curve measured on this host is
22,208 -> 3,397 t/s and 26,071 -> 4,379 t/s at 43.5k, i.e. ~0.25 t/s per MiB, so
24,000 predicts ~3,850 t/s single-stream. Falsifiable; the probe is the check.
The cost is named, not hidden: a FOURTH full-height conversation no longer fits
(4 x 200,000 needs 6,601 MiB of pool) and is refused as too large to ever fit —
radiance never truncates. Reverting to four slots is one env pair.
Seam: two new arithmetic gates, because both failures are boot-then-400 shape
faults that no flag check catches — the pair must respect the per-card ceiling,
and the pool must back seqs x max-model-len at the dtype's measured rate plus
the dtype-independent terms (110 MiB a sequence of recurrent state, 448 MiB of
prefix checkpoints).
Probe on the live service: four concurrent 196,960-token chats, 4/4 exact
marker retrieval, 787,842 tokens in 238.4 s (3,305 t/s aggregate prefill = the
single-stream ceiling, so the four streams shared one pipeline and the KV pool
never ran short); prefix-cache repeat answered in 1.0 s with cache_n=43008.
Recorded with the caveat that 8 generated tokens do not make a decode rate.
Runbook gains the 2026-10-13 section (symptom signature, the runtime-knob law,
the shape arithmetic, the boot ledger that confirms it: 843,276 tokens =
4 x 200,000, 12 all-reduce rows, 5.87 GiB of KV lent to the slab). AGENTS.md
gains the fleet-row update, the KV dtype law at four slots, the sysfs-raise
lesson under Key Lessons, and the pinned-RAM paragraph now points at
scripts/ttm-preflight.sh as the repair. LLM index entry + topology node match.