- binary-aware crack wave (new tools/workflows/wave_binary.js): 8-target calibration
over ov_SC06_018 substantial stubs, 7/8 match_one MATCH
- func_801365B8 (155, reach 133): cracked FRESH in ov_SC06_018, swept 132/132 siblings
via family_sweep --hseq --source ov_SC06_018 --allow-pins -- SESSION-10 refused this
family 0/133 from an ov077 exemplar. THESIS CONFIRMED (fresh exemplar unlocks it).
- func_80133AB0 (137, reach 137): cracked fresh + banked x1 (+ a byte-neutral s17a-1
cast reconcile of banked caller func_801343C4), but the family sweep FAILED 0/136 even
from the fresh exemplar (reverted clean) -- THESIS REFUTED for this family.
- FINDING (R14/R31 -> decision-log): the fresh-exemplar sweep is FAMILY-SPECIFIC, not a
blanket mechanical x137. A fresh crack is necessary but not sufficient; the byte-gate
arbitrates each family (~50% on this 2-family sample -> discount the ~1.5pp estimate).
- tooling (R33): family_sweep --source override now searches matched_members (a fresh
member leaves 'members' after a sig-regen); cdecl._depth0_spans consumes backslash
line-continuations so a raw-draft #define macro no longer trips audit-cdecl.
- R22 clean-fleet 140/140 byte-identical; tools-health green (dedup 1849/0, C1 234615);
0 NON_MATCHING. fleet 78.4->78.5% instr / 67.1->67.5% distinct / 88.14->88.18% fn-count.
gate_stage._jtbl_prepare carried the SAME config-only undo as harvest_verify's did,
and ate the tree again on the first ladder run: 5 orphan region files, truncated
TUs, `undefined reference to func_80192F64`. That INVALIDATED the run's 0/10, so it
was re-measured rather than reported (R35 — a probe from a broken tool is not
evidence). Tree restored from HEAD and re-verified byte-identical first.
DELETED, not patched (R33 — the best outcome is a deleted stage). It was wrong on
two independent axes:
1. §61b already byte-proved THE CARVE MUST FOLLOW THE SPLICE. A batch pre-pass
carving unspliced functions reports "prepared" and yields a spec that fails
once the body lands — which is why it banked nothing.
2. Its undo snapshotted only config/, while jr_isolate_all rewrites region 0 back
over the ORIGINAL src/<ov>/<nm>.c truncated.
harvest_verify's per-draft prep is the correct mechanism, snapshots the full source
set, and undoes per function. Two implementations of one capability, the outer one
ineffective AND destructive.
THE HONEST RE-MEASUREMENT (clean tree; tree verified clean after):
- 0/10 bank, but 9/10 now COMPILE and land as whole-binary byte-DIFF; 1/10 plumbing.
- match_one close=0 on several (the function's own bytes exact) and rtu_match says
MATCH-in-real-TU for func_80135888 — while func_801299C8's transformed draft does
not compile in its real TU at all. The residual is MIXED, not uniform; at least one
is an IMAGE-level effect rather than the draft or its TU decl context (prime
suspect: jtbl/rodata carve placement). NOT generalized from one data point.
- This PRICES Task 14 stages 2-3 by measurement: the existing ladder converts 0 of
10, so they are not "wire in normalize_self_decls + the type-lift and collect ten
banks" — the projection error §57a already caught once this phase.
- R22 clean-fleet 140/140 BYTE-IDENTICAL with the giant func_8018F694 banked and the
func_80135A4C family swept 138/138
- cookbook §61d (the tree-eating undo in two tools; the constant-label defect; the
re-probe + ladder measurements; the general rule: an undo whose scope is narrower
than its write scope destroys work no byte-gate can see)
- decision-log + CURRENT_PHASE updated (R30/R31)
Ultracode wave, 12 agents (~2M tokens), over freshly-prefetched ov_SC06_018 exemplars.
11 MATCH / 1 near, INCLUDING ALL THREE GIANTS (710/673/478 ins). Whole-binary gate: ZERO.
Splicing each failure individually (the gate's own label is §58's memcpy red-herring) gave
THREE DISTINCT blockers, none of which the ladder clears:
(1) §8e-2 jtbl table-count drift -- 10 of 12. "more rodata .align directives than pad specs".
STRUCTURAL FINDING: fresh crack fuel in a well-matched overlay CONCENTRATES in jtbl-carved
TUs (the non-carved ones were harvested first), so §8e-2 GATES the next tranche of
substantial cracking rather than being a straggler.
(2) §57 self-decl conflict -- the 2 plain-TU drafts ("argument 'arg2' doesn't match prototype").
normalize_self_decls exists, is wired into family_sweep, and is NOT in gate_stage -- the
same gap the arity pre-pass had.
(3) local-type redefinition (from the Task-14 diagnosis set) -- wants the type-lift.
So gate_stage needs THREE stages; only the arity pre-pass landed today.
All 12 drafts PRESERVED at .run/giants/t5wave_* (R20): genuine cracks with per-function lever
notes (cross-jump barrier placement, MEM_IN_STRUCT_P store/load ordering, §43 K&R s16 params,
$s-pins, CSE-break barriers). Do NOT re-draft -- they bank the moment the stages exist.
METHOD NOTE: `make build | grep -i error` missed the real failure TWICE (the jtbl_rodata_pads
line contains no "error" token; and the build failed at a later stage than the warnings I read).
Check rc, read the tail unfiltered -- a filtered build log is a selection tool, and every
selection tool here has eventually lied (R32/R35).
Tree reverted clean; nothing banked. cookbook §61a.
DIAGNOSED, not assumed. The 12-draft integration probe banked 1/12 and reported the SAME
label for 10 of the 11 failures: `conflicting types for built-in function 'memcpy'` — the
§58 red-herring (a WARNING, from an unrelated TU position). Splicing three top-reach
failures individually and reading real cc1 stderr gave the actual causes:
conflicting types for `func_XXXX' 3/3 <- loose-typing ARITY conflict
redefinition of `struct V8' <- a SECOND class (type-lift), stage 2
A banked shared caller macro in engine_core.h declares the function with FEWER params than
its byte-true definition takes (the original calls K&R-style with fewer args than the callee
reads); a C89 prototype makes that a hard error. tools/fix_arity_callers.py --any-proto
already fixes it and was simply NEVER WIRED into gate_stage's ladder (only family_sweep
carried §57). Now wired as a TU-side pre-pass.
MEASURED: 2 of 7 top integration candidates banked (func_8016EFC8, func_80164418, both
reach-138) vs the 1/12 old-ladder baseline. R22 140/140; tools-health OK (dedup 1848/0).
INCIDENT — this stage BROKE 138/140 AND R22 CAUGHT IT (nothing was ever committed):
pairing `--apply --any-proto` with `--revert` for the unbanked drafts corrupted declarations
fleet-wide. `--revert` rewrites ()->(void), which inverts a PLAIN apply but NOT --any-proto,
so an unbanked fn whose real decl was `extern void func_801708B0(void *a0)` came back as
`(void)` — in engine_core.h (included by all 138 overlays) and 6 sites in ov_SC01_077's own
sources. harvest_verify --binary ov_SC01_077 reported BYTE-IDENTICAL and was RIGHT about that
binary; the other 137 were structurally invisible to it. Repaired to the exact lines.
ROOT CAUSE FIXED: the ladder now snapshots every file the pre-pass touches and undoes by
RESTORE + re-apply-for-the-banked-set-only — exact by construction, cannot invent a signature.
NEW HARD CONSTRAINT (cookbook §61): any ladder stage mutating SHARED state must be undone by
snapshot restore, never an inverse transform, and validated FLEET-WIDE (R22) rather than by
the per-binary gate that authorised it. §55b's propagation law, one level down. The planned
type-lift stage edits engine_types.h and inherits it by default.
ALSO FIXED: the first wiring passed only --drafts (the narrow-param FILTER) without the
required --funcs, so the stage exited `no funcs given` as a SILENT NO-OP and the gate reported
0/6 as though diagnosed. sh() does not raise on non-zero exit -> explicit rc check added.
The hindsight-study §7 taxonomy predicts plateaus decompose into missing-transform (the
"highest-value bucket and the whole point"), seed-structural, and genuine-wall. Run against
real plateaus this class produced NO missing-transforms, and the answer needed no LLM.
MEASURED: `length` probe, 20 targets, 1 win. tail 1/6; partial 0/12.
AUTOPSY (read directly from the bytes, 3 partial plateaus):
- func_8017F0C0 / func_801806C8: target has `sltiu $v0,$v0,1` = gcc's codegen for `!x`/`x==0`;
the drafts wrote `(u32)(D_x ^ 1)` which emits `xori`. No local mutation crosses that.
- func_8017FF90: draft stores to arg0+8, target stores to a GLOBAL. Different function.
=> these are WRONG DRAFTS wearing a small closeness, i.e. seed-structural, not a mutation gap.
THE FIX IS THE OPPOSITE OF "ADD TRANSFORMS" — a tighter ADMISSION rule:
- _drift_route: permuter only when |d|<=2 AND explains=="tail" (the shape that measurably
converts). length pool 339 -> 34; permuter bucket 389 -> 84.
- SIZE-MISMATCH: added a PROPORTIONAL test (|d| >= 0.5*nt). max(2,0.15*nt) is far too
permissive on a tiny target — a 2-ins draft vs a 4-ins target read as a near-miss.
permuter_weights needs NO extension for this class.
Transferable (cookbook §60b): raising a search-closer's yield is at least as often about
refusing it unreachable work as widening its mutation set. Same knife as Task-13A's
targeting fix, one cut finer. Drafter idiom recorded: `sltiu rd,rs,1` => `!x`, never `x^1`.
17 unit tests green; corpus re-collected (1654 rows, closeness cross-check clean).
PROPAGATION (§55b, its own targeted batch): dedup_propagate --addr 0x80141B90 --recover
-> "138 overlays byte-identical after propagation"; 117 remaining stubs -> 0; 1 new
dedup group. This was the ONLY one of the 21 directed-run banks worth propagating.
THE REPRICING (R14 — measure a bucket's VALUE, not just its conversion rate):
the directed run converted 27% (21/77) but moved the fleet ~0.03pp, because h_exact
reach of the 21 is: func_80141B90=138, TEN at reach-1 (nothing to propagate), rest 2-10.
Instruction-weighted, the ENTIRE permuter bucket is worth ~0.36pp at 100% conversion.
The mechanism is validated; the fuel was small. Priced frontier (ins-weighted / 13.08M):
LENGTH-DRIFT |d|<=2 472,178 ~3.6pp (339 fns) <- the real permuter-adjacent lever
integration 419,162 ~3.2pp (305 fns) <- Task 14's ladder
WIDTH 71,593 ~0.55pp (45)
permuter (current) 46,571 ~0.36pp (74)
BRANCH-POLARITY 9,462 ~0.07pp (22)
So WIDTH/BRANCH-POLARITY are NOT worth prioritizing; my earlier "~200 candidates"
framing undersold LENGTH-DRIFT 10x and oversold WIDTH.
NEW: permuter_weights._LENGTH profile (perm_temp_for_expr/perm_expand_expr are the only
passes that change instruction COUNT; the reorder/decl-order levers that dominate the
regalloc+schedule profiles cannot, so they are down-weighted here) + residual_class
._drift_route (|d|<=2 -> permuter/`length`, larger stays structural — same class,
opposite tool) + classify() accepts a PROFILE NAME directly (the measured profile beats
re-parsing a free-text label). 17 unit tests green.
grinder: --profile filter (probe ONE residual class's conversion) + a PERSISTENT attempt
ledger. `tried` was in-process only, so every fresh --once run re-permuted the previous
run's losers — the permuter is deterministic given (base.c, target.o), so that CPU can
never produce a new win. Measured: a 20-target probe drew 19 already-tried targets.
Keyed by draft_sig so an improved draft legitimately re-opens the function.
First run of the Task-13A-targeted grinder (--once --batch 8 --permute-secs 90):
targeting: ON — 1665 classified; only bucket=permuter is admitted
targeting skipped 1601 non-permuter candidates
{redraft 707, structural 583, integration 305, unclassified 4, unknown 2}
permuter WON func_80181F78 @ ov_SC03_014 (close was 1) [~6 min]
BANKED 2 (both whole-binary byte-gated, R22 clean-fleet 140/140):
- func_80181F78 (8 ins) — classified DELAY-SLOT / schedule
- func_80141B90 (29 ins) — classified IMM-VALUE / cse
Both were classified bucket=permuter by residual_class BEFORE the run: the classifier
predicted a search-closer could reach them, and one did. First end-to-end validation of
the targeting thesis.
THREE latent defects, all pre-existing, all unreachable while the grinder banked nothing
since Phase 21 — the fix made it win and every one fired at once (cookbook §60a):
1. gate_stage commit path crashed on src=None. `src` is DELIBERATELY never defaulted
(Phase 26-A: a default silently PINS the gate to the main .c), but the commit did
`git add src …` unconditionally -> every caller that omits it (grinder, orchestrator,
idiom_hunt) crashes THE MOMENT IT BANKS. Now `git add -u src/`, which also retires the
`src/ov_*/*.c` filename glob that once omitted 4 R22-verified banks from a commit.
2. _xform ladder dirs (-cn/-cast/-rc/-uni) ACCUMULATE across runs: they held 34 stale
drafts, so the gate processed 34 when the grinder submitted 1, and banked one function
it was never asked to try — which would have been committed under a message naming a
different one. Nothing wrong entered the tree (G3/P9 held; the gate banks only
byte-identical output) but report and work had diverged. Now cleared per run.
3. grinder called gate_stage with the default propagate=True = `dedup_propagate
--auto-from`, the §55b fleet-wide path that timed out at 3600s and left 90/140 overlays
broken — and being INSIDE the gate it takes the banks down with it. Now propagate=False;
banks commit cheap, propagation is its own targeted --addr batch (§55b law).
R22: make clean && extract-all && check-all -> 140 passed, 0 failed of 140.
tools-health OK (dedup 1847/0, C1 234343/234343); 0 NON_MATCHING (G4).
TASK 3 COMPLETE (both deliverables):
(a) jr cores: a 2nd ultracode wave cracked all four giants at match_one — func_8013F350 (490),
func_80131340 (424, verified TWICE: standalone AND in-TU cc1 rc=0), func_80159C84 (337),
func_8013C414 (329, -O0). ALL FOUR gate-rejected on INTEGRATION (def-sig / §8a rodata island /
decl conflict), not codegen; each blocker NAMED. func_8013C414 matched ONLY because of the new
worker_wave --o0 fix (a -O0 target self-checked at -O2 can never match — the §53/§54 wrong-build-step
trap that produced Phase-28's "~3%" artifact).
(b) §53 has_mid_jr INTERLOCK: built + negative-control-proven (commit:0670).
PRESERVED (R20 — ~2.6M agent tokens to reproduce; bank them, do NOT re-draft):
.run/giants/p29t3_*.c (12 drafts) + p29t3_README.md — every draft is match_one-MATCH or a
characterized near-miss, with its exact blocker + a cheapest-first bank order. Best value:
func_8013FAF8 (312, MATCH, pure def-sig plumbing); then func_80131340 (in-TU-proven);
func_8013F350 (§30#2 macro-widen void->s32); func_8013C414 (§8a rodata-island carve).
Permuter fuel: func_80177940 (close=5), func_801670E4 (16 — strip pins first, permuter can't
ingest them), func_8014D820 (33), func_80140958 (116).
SESSION CHECKPOINT — safe to open a fresh session:
140/140 byte-identical; tools-health OK; dedup 1843/0; 0 NON_MATCHING (G4); main 143dbb89.
Fleet 68.9 -> 71.4% instr / 49.5 -> 53.3% distinct-code / 83.94 -> 86.42% fn-count.
Tasks 1,2,3,6 DONE. Remaining: T4 (member harvest + grinder warm-start/bug-fixes), T5 (Ghidra-C
prefetch, needs /mcp), T7 (burn-down + ROI close). Carried: the 2 local-type-blocked cores
(func_8014E284, func_80137DD4) need the build_engine_types type-lift to propagate x137.
Ultracode wave: 16 isolated drafters over the resident's non-jtbl stubs (the 5 jtbl deferred —
they need the rodata-island carve, §53). Drafts only; the whole-binary byte-gate arbitrated after.
- BANKED 7/16, byte-gated: func_800CEFD0(77) func_800D0D7C(45) func_800D1B80(22) func_800D1E28(37)
func_800D1FC8(62) func_800D29F8(172) func_800D2D10(39).
Resident REAL 122 -> 129, stubs 21 -> 14, byte-ident 124/145 (85.52%) -> 131/145 (90.34%).
FLEET instr 9017152 -> 9017606 (+454 ins). R22 make clean && extract-all && check-all ->
140 passed, 0 failed of 140 (the first R22 was killed by a terminal crash and RE-RUN, not assumed).
Ground truth on 14 agrees 3 ways: source grep, splat-emitted stub .s count, progress.py.
- §52b's LAW, MEASURED AGAIN INDEPENDENTLY: the agents self-reported 11 match_one MATCH; the
whole-binary gate banked 7 (64%). All 4 blocked MATCHes died on `conflicting types`
(D_8010EDEC / D_80115110 / func_800D1984 / cdFileLocTable) — the loose-typing def-side wall, NOT
codegen. gate_stage's recovery banked 0/5 on them. A match_one MATCH is a CANDIDATE (G3/P9).
- FIX — match_one's isolation was FAKE, and its own docstring was the false spec. It promises
"Fully isolated (own temp dir) so many run in PARALLEL with no shared build -- a real asm-differ
loop for an agent to iterate against", while `--work` defaulted to the SHARED '.run/match': every
concurrent caller compiled into the same t.c/t.o. FOUND BY AN AGENT MID-WAVE, the only way it can
be found — it read another agent's function out of its own scratch ("found another agent's
func_800D2650 in my t.c") and reported it. Every other agent steered by a loop that could hand it
someone else's compile: a CONFIDENT WRONG verdict, worse than a crash. Default is now a private
.run/match/<fn>.<pid>; the default IS the promise. (Some agents had already worked around it by
passing --work themselves.) The byte-gate was never at risk — it is the sole arbiter — but the
iteration loop the agents steer by absolutely was.
- The 14 remaining: 5 PLUMBING (loose-typing) + 4 DIFF (genuine codegen: func_800D2650 close=4,
func_800CFAD0 close=5, func_800D0E30 close=12, func_800D27DC close=48) + 5 jtbl deferred.
Dossier next (T5b) — the agents' per-function residual analyses are the durable asset (R30).
- worklist --assert-partition: the audit's literal R32 prescription (tooling-audit.md:1173) —
enumerate live stubs from corpus.stubs (the invariant, R33), assert the fuel manifest partitions
its source overlay's stubs, exactly one row each. Scoped honestly (worklist's universe is ONE
overlay ~223 stubs, not the fleet's 53k — a fleet partition is a scope change, not a flag). PROVEN:
it caught 5 stale rows (pin-free cores Phase-26 banked, manifest never re-derived) -> FAIL exit 1.
- honest re-scan: build_fuel_manifest on the fixed tools + 140 binaries. Giants re-verified reach-138
(was 134 — the SC07 overlays now counted). Partition PASSES 223==223 after refresh.
- ledger corruption fixed: func_80178004's 2 false `close=0 "MATCH"` records (a Phase-26-retracted
myth — the seed's best was 5 pinned, and a real close=0 whole-binary match BANKS; it is still a
stub) -> corrected to the honest close=91 regalloc wall. func_8012E364 already honest (close=23 —
the "stale closeness" flag was itself stale). No real duplicate rows (load_best dedups by addr;
the uniq hits were func names in where_stuck prose). docs/worklist.md + docs/backlog.md regenerated.
- the 1,670-untriaged near-miss triage SCOPED TO P29 (P5d): Phase-21 automation leftovers whose class
labels re-derive at harvest, and the pin-crash finding re-buckets the PINS class — an Ultracode
fan-out buys low-durable labels; the gate's residue map is the partition + the class summary, done.
Re-gated all 958 closeness-0 open-stub backlog drafts through the FIXED gate
across 135 binaries in parallel: banked=0, near=957, failed=71. The closeness-0
backlog is genuine whole-binary near-misses, NOT tooling misses -- match_one's
isolated closeness==0 systematically overstates whole-binary bankability, and the
repaired gate recovers none. P9: a re-confirmed wall is as valuable as a dissolved
one. (The audit's tooling-walls were already banked by A3f/g/h + A9b, +2.1% instr.)
backlog.py: env-gated BACKLOG_NO_RENDER so parallel workers skip the render race
(append is atomic) -- backward-compatible parallel-safety. backlog.md refreshed
with the re-test's whole-binary-informed scores.
The payoff of A3e, byte-verified. These 33 sat in the backlog at closeness==0 -- match_one said
their bodies were BYTE-EXACT -- and the whole-binary gate rejected them, so they were logged as
`near`/`failed`, i.e. AS MATCHING PROBLEMS, and filed as intrinsic compiler residuals.
They were not hard. They were UNREACHABLE. gate_stage passed `--src src/<ov>/<ov>.c`
unconditionally, which restricts the byte-gate to ONE translation unit -- and every one of these
functions has its stub in a SPLIT TU. Look at where they landed:
src/ov_SC01_077/ov_SC01_077_a.c
src/ov_SC01_077/ov_SC01_077_after.c
src/ov_SC01_077/ov_SC01_077_jr_8012ACE0.c
src/ov_SC01_077/ov_SC01_077_jr_8015AE2C.c
src/ov_SC01_077/ov_SC01_077_jr_8016AB6C.c
src/ov_SC01_077/ov_SC01_077_jr_801734BC.c
src/ov_SC01_077/ov_SC01_077_jr_80178D40.c
src/ov_SC01_077/ov_SC01_077_jr_80182268.c
8 files. SEVEN of them are _jr_/_a/_after carves. NOT ONE is the main .c -- the only file the gate
was ever allowed to look at.
gate: 63 drafts -> banked 33, near 30, FAILED 0 (--no-propagate; the gate and the propagation
are different jobs, and letting an experiment tow an unbounded fleet-wide propagation is
what broke the tree an hour ago)
R22 CLEAN-FLEET: make clean + extract-all + check-all -> 136 passed, 0 failed of 136
dedup-check: 1823 validated, 0 failed | C1 coverage 224933/224933
METRICS, ×1, HONESTLY (no propagation yet -- the multiplier is still ahead):
functions byte-identical 284,526 -> 284,559 (+33)
instructions 8,470,381 -> 8,471,912 (+1,531)
fn-count % 82.79% -> 82.80%
instr-weighted % 66.7% -> 66.7% (flat: ×1 banks do not move the headline)
WHAT THIS MEASURES, beyond the 33: the backlog holds 1,588 entries at closeness==0. 1,215 have been
banked since by other paths. 373 ARE STILL OPEN STUBS WITH BYTE-EXACT BODIES. 63 of them were in
ov_SC01_077 and 33 banked -- a 52% rate on functions the ledger calls unrecoverable. The other 310
are spread across the remaining overlays: same class, same fix, not yet attempted.
Cookbook §51g LAW 11 -- a fix is not landed until its caller stops overriding it. And the reason
this hid for 26 phases, which belongs in the posterity doc: A TOOL THAT CANNOT BANK A FUNCTION IS
INDISTINGUISHABLE, IN EVERY LOG THIS PROJECT KEEPS, FROM A FUNCTION THAT CANNOT BE BANKED.
- batch-3: the 3 _o0 giants 3/3 isolation-MATCH at -O0 (new tools/match_one.py --o0 flag);
0 banked — an -O0 in-context byte-diff (canon_sig_reconcile's void->s32 is NOT byte-neutral
at -O0) -> deferred to T7. Frontier 125/127 draftable exemplars measured.
- R14 correction: the mechanical reconcile-sweep is NOT the clean 51-target x134 win first
hoped. The frontier "match" status carried un-verified agent claims (5-sample spot-check
= 3/5 genuine); ~19/51 have clean engine_core.h canonicals (the reliable canon_sig_reconcile
tier), the rest hit VARIED walls (callee-sig conflicts, non-identical types Vec3/SVEC,
macro-local data) -> this is the genuine Fable5/T6 residual, not a mechanical sweep.
- docs/phase25-t6-fable-brief.md: the grounded Step-B input package for the fresh Fable5Max
session to author the crack curriculum (95-stub worklist by wall-class + tools + 5 swing
questions). CURRENT_PHASE: T6 hand-off (fresh session, Fable5Max, read the brief). Phase OPEN.
- housekeeping: deleted stale root gccdump.lreg (gcc default -da RTL dump, dumpbase
"gccdump"; a one-off RTL-inspection run at root CWD, NOT a committed tool). Practice:
RTL dumps go to a .run/ CWD or -dumpbase .run/gccdump (R12)
- make sig-overlays (134 sigs); worklist.py --refresh -> build_fuel_manifest + backlog
render: docs/worklist.md + docs/backlog.md regenerated (stale Jun-26 ranking killed;
the banked whale func_80144B9C dropped from backlog, P9)
- fix tools/sig_image.py docstring: h_norm is the live norm_stream normalizer, not a
"T5 placeholder" (R21/R30)
- CURRENT_PHASE.md: Phase-25 plan-of-record + T0 frontier survey (R14): h_norm 2,764
multi-member families / 11.1 MB; 46% of large solo monsters (3,989/8,670) are family
members; reach-134 h_exact warm-up = 130 classes / 4.11 MB
find_site + dedup_propagate --recover + build_engine_types fixes, then re-bank
the 13 recover_integration leaf-MATCHes and propagate each across all 134 overlays.
- find_site: match INDENTED inline defs (was column-0 only, silently dropping every
recover_integration-banked def from propagation — T6 blocker 1). Unit-tested:
indented defs match; indented call-exprs (if/assign/bare/return) correctly rejected.
- dedup_propagate --recover: on a straggler byte-gate failure, FIRST no-proto that
overlay's conflicting caller extern + re-gate (Part B, byte-neutral, same lever as
fix_arity_callers --any-proto); else EXCLUDE only that overlay (Part A, ×N-1) rather
than the historical all-or-nothing drop. Wired into gate_stage.
- build_engine_types: comment-aware find_defs/find_typedefs (blank_comments). The
generated header's own "...typedef lift" comment was captured as a bogus `typedef
vec`, self-colliding and blocking every --strip. NOTE: full --strip still conflicts
with the _a/_o0 split files, so split-file overlays need a TARGETED lift.
- banked + propagated 13 fns ×134: func_8014F74C 801542A4 8015BE94 8015F380 80160F00
801653B8 80166244 8016E778 801732C4 8017331C 80173374 80174554 801745AC.
func_8014F74C needed PosT/MoveT lifted to engine_types.h (targeted, byte-neutral).
- dedup 1784→1797 groups (0 failed). CLEAN fleet check-all 136/136 BYTE-IDENTICAL (R22:
make clean && extract-all && check-all). Fleet REAL 224073, byte-identical 65.40%.
R14: the confounding stale-asm/ tree (13 missing .s) that masked the first --recover
test is fixed by re-extract; the 3 pre-existing --auto-from stragglers (0x80174650/
8012A018/80165CA0) are pin/asm + uncaptured-local-macro (SHB) bodies, correctly dropped.
Both concerns byte-verified from a fully-clean tree (ov_SC01_077 d19c9580, ov_SC07_009 2a6499b6
+ 133 overlays). Fleet is 135/136 — the 1 remaining failure is `main`, a SEPARATE pre-existing
Phase-21 breakage (62 dangling INCLUDE_ASM refs, tracked in CURRENT_PHASE, fix in progress),
NOT introduced by this commit.
[FIX (partial) — pre-existing Phase-21 latent breakage, found during T5b's fleet verify]
- A genuinely-clean `make check-all` failed 135/136 (overlays: `undefined reference to func_80058B40`;
main: dozens of `can't open asm/nonmatchings/800c3/func_*.s`). This commit fixes the OVERLAY side.
- Root cause: Phase-21 xdedup renamed func_80058B40 -> GetTPage in symbols.us.txt (one of the
+62 PsyQ names) but did NOT update the two shared engine_core.h macros that CALL it
(DEFINE_func_80139680, DEFINE_func_8012E28C — in all 134 overlays + ov_SC01_077_a). Since
Phase 21 a clean rebuild couldn't link; incremental builds reused stale .o's and masked it
(the R22 failure mode) — every "check-all 136/136" Phase 21->23 was incrementally-stale.
- Scope = exactly 1 symbol (static scan of all func_/D_ refs in the shared headers vs symbols).
- Fix: rename the 4 occurrences -> GetTPage (byte-neutral, same addr 0x80058b40 -> identical jal;
G6 curated-name). ov_SC07_009 link-fail -> byte-identical 2a6499b6.
- Lesson: a symbols.us.txt rename must be propagated to shared-macro bodies AND verified by a
genuinely clean (make clean + full re-extract) check-all, never incremental.
[FEAT — T5b: the S11 class crack, Fable5 spike]
- The S11 LUID(x)alloc "intrinsic" verdict was MAP-INCOMPLETENESS. func_8014E048 (143 ins,
reach-134; "not source-steerable" since the map wave; 28-off even after T5's directed permuter)
-> MATCH (143/143) -> whole-binary BANKED (ov_SC01_077 d19c9580). Derived by reading gcc-2.7.2
source + RTL dumps (12 experiments .run/gccmap/exp/e1a..e1k.c).
- NEW LEVERS (byte-proven): S12 reused-s32-temp fence (u16 temps DON'T work — combine folds the
unpromoted-HI zext temps away); S13 head-skip escape (body-local param copies conflict-steer the
scratch contest; volatile-asm dead-read wedge fence; multi-input dead-read K2 rebalance);
cse-opaque asm-copy; RC-4b pinned store-temp; RC-10 preference-cascade mechanics.
- Integration reconciles (both T6 classes): engine_core.h caller decl s16*->u16* (codegen-neutral)
+ canonical data decls w/ *(u16*) casts (D_801152A8 u8[] / D_801152AC s16). x134 lift blocked by
dedup_propagate self-containment (pins/asm) -> T6 target (joins func_80132784).
- Distilled (R30/R16): sched.md §6 (S12/S13) + regalloc.md §F (RC-10 + RC-6/S11 downgrade) +
cookbook §31 triage update; backlog re-logged (capped); memory updated.
The grinder/backlog pipeline was ov_SC01_077-hardcoded 5 layers deep (same class as the
T7 lora_grind bug). Fixed all so the permuter grinder can process a non-077 near-miss:
1. gate_stage.append_record stores the source "binary"
2. backlog.FIELDS keeps it (else append_record dropped it)
3. backlog.load_best/_open_stubs is fleet-aware: a fn matched in ov_SC01_077 but
propagation-stuck stays OPEN in its overlay, so it surfaces via that record instead
of being dropped as "matched" (the grinder must SEE it to grind it)
4. p16_permute.setup takes the target binary's asm-subdir (was hardcoded 077)
5. grinder resolves per-binary asm + gates grouped by binary + allows unknown nins
Backward-compatible: legacy records (no binary) default ov_SC01_077.
Validated end-to-end: the 3 fresh reach-134 close=1 ov_SC01_000 fns now surface, resolve
to ov_SC01_000's asm, and gate via ov_SC01_000.
TWO byte-evidenced findings (redirect the fuel strategy):
- the reach>=2 close=1 fuel is MODEL semantic-misses, not permuter fuel: func_8012E27C's
target is "return 1" but the 7B drafted an empty "void f(void){}" (corpus overfit
empty-leaf); func_8012BF4C/AD64 are trivial sw/sh setters drafted empty. A corrected
draft banks them (+3 byte-identical via the fixed gate, @commit:0326); the permuter cannot
add a missing return/store. Lever = corpus-v3 leaf variety, not the permuter.
- x reach is propagation-capped: the 3 are inline-matched in ov_SC01_077_a.c (the stuck-
local cap) -> dedup_propagate "nothing to propagate" -> banked x1. Lever = dedup-collapse.
check-all 136/136 throughout. docs/gen2-mips-matching-model.md + CURRENT_PHASE updated.
The 500-fn calibration banked 0/222 across the binary rotation. Root-caused (R14, by
reading the code + the run's own backlog — resolving a flat contradiction between two
scout agents) to TWO independent bugs in lora_grind's use of gate_stage.run_gate, NOT
model quality:
- Bug A: good_sha() passed the sha1sum line "<sha> <name>" vs harvest_verify's bare
sha1() -> 0 banks for EVERY binary incl. 077 (so the "0/12" was a bug artifact, not
an exhausted tail)
- Bug B: the gate call left src/asm/out at the hardcoded ov_SC01_077 defaults -> non-077
drafts dropped at the 077 stub-filter, silently (and the asm mis-resolution contaminated
the backlog near-miss classification)
Fix (tools/gate_stage.py): run_gate resolves src/asm/out/good_sha from `binary` when unset
(binary-agnostic, no silent ov_SC01_077 default an overlay inherits; good_sha bare-hash
normalized) + a loud negative-control guard (0-overlap binary/src mismatch warns, so a 0
can never again masquerade as 'nothing matched'). tools/lora_grind.good_sha fixed at source.
Byte-neutral: make check-all 136/136.
Proof: ov_SC01_000 spot-run banked 7/15 (47%) byte-identical (@commit:0322); reach-2
func_8017CE24 propagated x2. ROI finding: 6/7 banks are reach-1 (overlay-unique) -> broad
rotation is high bank-RATE / low fleet-% ROI; the fleet lever is reach>=2 targeting (T9) +
corpus-v3 (T8). Backlog now correctly classified (4x close=1 = grinder fuel).
- docs/gen2-mips-matching-model.md: T7 RESULT section
- phase-ends/CURRENT_PHASE.md: T7 done; next = T8 corpus-v3 / T9 reach>=2 selection
The fine-tuned 7B (bfm-match-7b-v2) drafted real OPEN ov_SC01_077 stubs; whole-binary gate banked 4
(func_80160B34 func_8015CC74 func_8016084C func_801705C0). Sample: 9/22 match_one proxy -> 4/22
whole-binary banked (18%; the proxy->gate gap is the TU-plumbing wall). Model is format-robust (raw .s
== normalized). api_draft: NORMALIZE_ASM bridge (unused — model handles raw .s) + ghidra_c-empty fix.
- from-scratch giant func_801372B0 (207): structurally cracked at xHigh (206/207 ins,
logic 100%%) but byte-blocked by the gcc list-scheduler/regalloc last-mile (§27/§17);
banked the structural draft to backlog as a future permuter head-start
- xHigh finding (Drew's test): giants reach structural match fast — the wall is gcc
determinism, not reasoning depth; xHigh sufficient for this work
- session total: 16 functions ×134 (2 giants type-lift + 14 close=0), fleet 63.22%->63.66%
- docs/{worklist,backlog,progress.fleet}.md regenerated after the func_8015126C x134 bank
- CURRENT_PHASE.md: RESUME HERE block (T2 giant queue + levers + op gotchas) for a fresh session
- grinder stopped (STOP sentinel set); tree clean except R23 db churn