phase-36: S104 s104_e6 — func_80189A84 banked at 0 through the whole-object gate + propagated — 2 pins → 0: the reused register-named temps substituted in place (a 5-death v0 is refused, local-alloc.c:472)

This commit is contained in:
Drew T
2026-09-11 01:27:27 -06:00
parent d737200579
commit 817cafc4d1
10 changed files with 539 additions and 221 deletions
@@ -0,0 +1,56 @@
void func_8017E710(s32 a0) {
extern void ApplyMatrixSV(void *a0, void *a1, void *a2);
extern s32 ratan2(s32 a0, s32 a1);
extern s16 D_801152B0;
extern s16 D_801152B4;
extern s32 func_80133784(s32 a0, void *a1, s32 a2);
extern s32 func_8012CEB0(s32 a0, s32 a1, s32 a2);
extern void RotMatrixY(s32 a0, void *a1);
extern Mtx8_8017DE10_8017E710 D_800AE620;
u8 in[8];
u8 out[8];
Mtx8_8017DE10_8017E710 m;
s32 base;
s32 ang;
s16 arg;
s32 d;
*(s16 *)(in + 0) = *(u16 *)(a0 + 0x6) + *(u16 *)(a0 + 0x12);
*(s16 *)(in + 2) = *(u16 *)(a0 + 0xA) + 8;
*(s16 *)(in + 4) = *(u16 *)(a0 + 0xE) + *(u16 *)(a0 + 0x1A);
*(s16 *)(out + 0) = *(u16 *)(a0 + 0x6);
*(s16 *)(out + 2) = *(u16 *)(a0 + 0xA) + 8;
*(s16 *)(out + 4) = *(u16 *)(a0 + 0xE);
if ((func_80133784(1, &in[0], (s32)&out[0]) & 0xC000) != 0) {
base = ratan2(D_801152B0, D_801152B4) & 0xFFF;
ang = ratan2(*(s32 *)(a0 + 0x10), *(s32 *)(a0 + 0x18)) & 0xFFF;
d = ang - base;
d <<= 16;
if (d < 0) {
ang += 0x480;
} else {
ang -= 0x480;
}
arg = base - ang;
ang = *(u16 *)(a0 + 0x6);
*(s16 *)(in + 0) = ang;
*(s16 *)(in + 2) = *(u16 *)(a0 + 0xA);
*(s16 *)(in + 4) = *(u16 *)(a0 + 0xE);
m = D_800AE620;
RotMatrixY(arg, &m);
*(s16 *)(out + 0) = *(u16 *)(a0 + 0x12);
*(s16 *)(out + 2) = *(u16 *)(a0 + 0x16);
*(s16 *)(out + 4) = *(u16 *)(a0 + 0x1A);
ApplyMatrixSV(&m, &out[0], &out[0]);
*(s16 *)(out + 0) = *(u16 *)(a0 + 0x6) + ((s16)*(u16 *)(out + 0) >> 1);
*(s16 *)(out + 2) = *(u16 *)(a0 + 0xA) + ((s16)*(u16 *)(out + 2) >> 1);
d = (s16)*(u16 *)(out + 4) >> 1;
*(s16 *)(out + 4) = *(u16 *)(a0 + 0xE) + d;
if ((func_8012CEB0((s32)&in[0], (s32)&out[0], 0) & 0x2000) != 0) {
*(s16 *)(a0 + 0x6) = *(u16 *)(out + 0);
*(s16 *)(a0 + 0xA) = *(u16 *)(out + 2);
*(s16 *)(a0 + 0xE) = *(u16 *)(out + 4);
}
}
}
@@ -0,0 +1,82 @@
# func_8017E710 (ov_SC03_006_jr_8017AE2C.c) — e6, P36 T7 S104
**Result: score 0, ZERO levers** (1 lever before → 0 after: the `ang` pin `$2`). Body: `PACK/body.c` (= `scratch/q2/q2_t3.c`).
**The same text closes the whole class — 13 functions, every one proven 0 with `--try`** (list below).
## (a) The residual, in one sentence
The lever-free body puts the `(s16)(ang - base) < 0` compare temps in `$v0` and pushes `ang` (the second `ratan2`
result, which the ±0x480 arms and the join read) to `$v1`; the target keeps `ang` in `$v0` and the compare in `$v1`
(REG, 9 → 7 after the sweep; every single move plateaued at 7).
## (b) The pass and the decision (read in `scratch/dumps_free`, `dumps_w2`, `dumps_fin`; all proven on bytes)
- `ang` spans blocks 1–4 (it is read in both arms and at the join) → refused by local-alloc (`local-alloc.c:472`,
`reg_basic_block[i] >= 0 && reg_n_deaths[i] == 1`) → global. The compare's `subu` (r101) and `sll` (r103) are
one-block one-death pseudos → local-alloc allocates them FIRST, and `$2` is free there (the call's `$v0` died at the
`andi`), so both take `$2` (`.lreg` `;; Register 101 in 2.`). Global-alloc then records `$2` as a hard conflict of `ang`
(`global.c:1256/1291`, `.greg` `74 conflicts: … 2 …`) and `find_reg` gives it `$3`.
- **No local may be alive in `$2` across the compare while `ang` is.** Any block-1 local overlapping the compare also
overlaps `ang`, so the compare temps must stop being locals: make the compare's destination a USER variable that is
(i) GLOBAL — reused in another block, so `local-alloc.c:472` refuses it — and (ii) the destination of BOTH the
`subu` and the `sll`, so there is no anonymous shift temp left to be local (`d <<= 16` sets `d` in place; `(s16)d < 0`
creates a sign-extension temp that goes local → `$2` again, 11, `scratch/f/f_cast.c`).
- With both global, `allocno_compare` (`global.c:594-610`) orders `ang` (r74, pri 27000: 9 refs / live 10) before `d`
(r76, 24000: 6/5). `ang` takes its preference `$2` (set_preference from `(and (reg 2) 4095)`, `global.c:1535`), `d`
its preference `$3` (the tail `sra`). `.greg` of the close: `4 regs to allocate: 74 76 72 73`, `74 preferences: 2`,
`76 preferences: 3`.
- `ang`'s priority needs the join's `ang = *(u16 *)(a0 + 0x6)` reuse that `body_free.c` already carried: without it
`ang` drops to 7 refs (14000), `d` is allocated first, and the fresh join-block `lhu` local in `$v0` overlaps `ang`,
which goes to `$a0` (5, `scratch/f/f_noanglhu.c`). That reuse is also what the function header's note asked for.
## (c) The moves (JOINT — each alone scores 7–11)
1. Declare `s32 d;` and write the compare as `d = ang - base; d <<= 16; if (d < 0) {` (the sign of the low halfword).
2. Reuse `d` for the third tail term: `d = (s16)*(u16 *)(out + 4) >> 1; *(s16 *)(out + 4) = *(u16 *)(a0 + 0xE) + d;`
(the target keeps that term in `$v1` — `lhu v1,28(sp); sll; sra v1,v1,17` — which is `d`'s register).
3. Keep `body_free.c`'s `ang = *(u16 *)(a0 + 0x6); *(s16 *)(in + 0) = ang;` reuse (and drop the pin).
Probes (`scratch/f/`): 1 without 2 → 7; 1+2 with `(s16)d` → 11; `d = (ang - base) << 16` → 11; 1+2 without 3 → 5;
2 on the first tail term instead of the third → 7 (COUNT: it re-plans the tail schedule).
Search path that found it: `scratch/r/` (48 reuse spellings; the lhu reuse of `d` scored 2 = the register was right
everywhere but the lhu) then `scratch/q2/` (d's second life moved to each `$v1` site of the target: only `t3` → 0).
## Other copies of the class — all 0 (`scratch/ports/`, made by `scratch/port.py` from each tree body)
`src/ov_SC03_118/ov_SC03_118_jr_8017AE2C.c` func_8017EA24 · `src/ov_SC05_004/ov_SC05_004_jr_8017BEBC.c` func_8017DB00 ·
`src/ov_SC02_031/ov_SC02_031_jr_8017AE2C.c` func_8017EE3C · `src/ov_SC03_028/ov_SC03_028_jr_8017AE2C.c` func_8017D370 ·
`src/ov_SC03_024/ov_SC03_024_jr_8017DF84.c` func_8017FBC8 · `src/ov_SC02_011/ov_SC02_011_jr_8017AE2C.c` func_8017DE10 ·
`src/ov_SC03_113/ov_SC03_113_jr_8017C294.c` func_8017E878 · `src/ov_SC03_111/ov_SC03_111_jr_8017AE2C.c` func_8017C95C (each `--try … --body`, 0);
the shared header `src/shared/ov/func_8017D0BC__4f23330c.h` (func_8017D0BC) — `--body` cannot splice an `#include`d
definition, so each of its four TUs was scored as a WHOLE TU with the `#include` line replaced by the ported text:
`scratch/ports/tu_ov_SC03_002.c`, `tu_ov_SC03_125.c`, `tu_ov_SC05_018.c`, `tu_ov_SC04_020.c` → 0 in all four. The ported
body is `scratch/ports/shared_func_8017D0BC.c` (its `Mtx8_8017DE10_8017D0BC` type name kept).
## (d) GENERATOR PROPOSAL
**R-new "globalise the compare temp":** when a REG residual swaps a multi-block variable V (the loser) with the temps
of a sign/compare chain computed from V in the same block (`subu; sll; bgez` / `(s16)(V - W) < 0`), rewrite the test
as an in-place user temp `t = V - W; t <<= 16; if (t < 0)` and give `t` a second life at each later site whose target
register equals the compare's target register (a load/shift term in another block), trying every site (`--try`
enumerates them); keep any existing reuse that raises V's refs. Precondition check: `.lreg` shows the compare temps
local in V's desired register and `.greg` lists V with that register as a conflict.
## (e) What did not work (bytes)
- widths/types of `ang`/`base` (s32/u32/int/u16, `s16` → 131 ins), `>=` polarity, `<< 16` spelling, `arg = -(ang - base)`:
128 variants, none below 7 (`scratch/enum/`).
- a local `t` + `ang = t` copy (`scratch/w*.c`, `m/`): sched1 hoists the copy above the compare (a multi-set dest is
not birthing, `sched.c:2469/2540`; `.sched` T-2 `107 (3) 109 (7f000001)`), then local-alloc's `optimize_reg_copy_1`
(`local-alloc.c:700`, call `:1007`) rebases the compare onto the copy — `(minus (reg 76) …)` in `.sched`,
`(minus (reg 74) …)` in `.lreg`. A single-set copy is merged by cse instead. The copy route is closed in plain C.
- reusing `arg` for the compare (`x1`): combine folds `arg`'s first life into the compare, no second allocno.
- the free sweep's best 7 was `R6 inline ang` = dropping the lhu reuse (the very reuse the close needs, move 3).
## (f) Where the method fell short
- Nothing in steps 12–15 covers "make a LOCAL temp GLOBAL on purpose" — every listed move either splits a reused temp
(S103 c1/c8, d15) or merges per-block locals (S103 c18). Here the answer was the inverse of d15: a reused temp is the
CURE, because the target's register for `ang` is only reachable if nothing local sits in `$2` across the compare.
Worth a step: "if a multi-block variable loses its register to a same-block local chain, the chain must become a
global user variable — reuse its name at the target's same-register sites."
- The residual (REG-caller) hid that the target's `$v1` appears again in the tail: listing every target site that
uses the compare's register (block by block, step 1 of METHOD) gave the candidate reuse sites directly.
## (g) Structs answer
Not the channel. The lever held a register against a local-alloc vs global-alloc ORDER decision (`local-alloc.c:472`
+ `global.c:594-610`), not an aliasing or address-folding decision; no memory access in the residual block changes
with a struct type. A struct for `a0` (`s16 x@6, y@0xA, z@0xE; s32 dx@0x10, dz@0x18; s16 vx@0x12, vy@0x16, vz@0x1A`)
and `SVECTOR in/out` would make the body readable but leaves the `ang`/compare allocation untouched. Not tested on
bytes (reasoned: the residual block contains no loads or stores).
@@ -0,0 +1,63 @@
s32 func_80182F4C(s32 a0, s16 a1)
{
u8 *base;
s16 val;
u16 c0;
u16 c1;
u16 outerIdx;
u16 innerIdx;
u16 diff;
s32 prod;
u16 temp2;
u16 idx2;
u16 *tbl;
s32 p1;
s32 list;
s32 p2;
s32 p3;
u16 dx;
u16 n;
u16 sample;
s32 addr;
s16 cur;
u16 v;
base = D_801AD31C;
c0 = 0xF800;
val = (s16)a0;
do {
c1 = 0xFA00;
outerIdx = (c0 + 0x8000) >> 7 & 0x1FF;
do {
innerIdx = (c1 + 0x8000) >> 7 & 0x1FF;
diff = innerIdx - *(u16 *)(base + 2);
prod = diff * *(u16 *)(base + 4);
list = *(s32 *)(base + 0x14);
p2 = *(s32 *)(base + 0x18);
p3 = *(s32 *)(base + 0x1C);
temp2 = outerIdx - *(u16 *)(base + 0);
tbl = *(u16 **)(base + 0x8);
idx2 = (prod + temp2) * 2;
dx = tbl[idx2];
n = tbl[idx2 + 1];
p1 = list + dx;
while (n--) {
sample = *(u16 *)p1;
if (!(sample & 0x8000)) {
addr = p2 + sample * 18;
} else {
v = sample & 0x7FFF;
addr = p3 + v * 22;
}
cur = *(s16 *)addr;
if (cur == val) {
*(s16 *)addr = a1;
}
p1 += 2;
}
c1 += 0x80;
} while (c1 <= 0xFDFF);
c0 += 0x80;
} while (c0 <= 0xFBFF);
}
@@ -0,0 +1,60 @@
# func_80182F4C (ov_SC03_006_jr_8017AE2C.c) — e6, P36 T7 S104
**Result: score 0, ZERO levers** (1 lever before → 0 after: the `p1` pin `$4`). Body: `PACK/body.c` (= `scratch/p/pb.c`,
the temp renamed `list`). One line changed from `body_free.c`, one added: the cell-list pointer is loaded into its
own local and `p1` is formed from it — `list = *(s32 *)(base + 0x14); … p1 = list + dx;` (instead of `p1 = …; … p1 += dx;`).
No other copy of the class exists in `src/` (grepped `0xFA00`, the `>> 7 & 0x1FF` index, the `* 22` record stride).
## (a) The residual, in one sentence
A whole-function register rotation (29, REG-caller): the target puts the walked pointer `p1` in `$a0` (freed by the
entry `sll a0,a0,16`) and everything allocated after it one register lower (base t0, p3 t1, p2 t2, c0 t3, 0xffff t4,
outerIdx t5, val t6, c1 a3); the free body gives `$a0` to `val` (the hoisted `(s16)a0`) and pushes `p1` to `$a3`.
## (b) The pass and the decision (`scratch/dumps_free`, `dumps_u16`, `dumps_fin`; proven on bytes)
All 15 contenders are GLOBAL (loop-carried). Order (`.greg`): `91 92 90 82 86(p1) 78 75 88 87 77 130 79 149(val) 73 97`.
- `val` (r149) = `(ashiftrt r150 16)` with r150 the local `sll` result in `$4` → `set_preference` (`global.c:1535-1573`,
first operand of a non-copy SET, renumbered to the local's hard reg) gives `val` a preference for `$a0`.
- `find_reg` pass 0 (`global.c:950-953`) excludes `regs_someone_prefers` — built by `prune_preferences` from the
preferences of LOWER-priority conflicting allocnos — so `n` (r90), `p1` (r86), `c1`… all skip `$a0` (and `$a1`, `a1`'s
preference): `n → a2`, `p1 → a3`, …; `val`, allocated 13th, takes its `$a0`.
- The target's `p1` in `$a0` needs (i) `$a0` removed from `val`'s preferences and (ii) `$a0` preferred by `p1` itself.
Loading the list pointer into a separate local does both: `list` (r87) is one-block/one-death → local-alloc gives it
the first free register, `$4` (`.lreg` `;; Register 87 in 4.`), so every global live in that block (`n`, `c1`, `base`,
`c0`, `outerIdx`, `val`, `a1`, the 0x8000 constant) records `$4` as a hard conflict and `prune_preferences` strips
`val`'s `$a0` preference (`.greg` of the close: no `150 preferences` line); `p1 = list + dx` gives `p1` a preference for
`list`'s `$4` (`;; 86 preferences: 4`), and `p1` does not conflict with `list` (born where `list` dies). `p1` is then the
first allocno that can take `$a0`, and the rest shift down by one — exactly the target map.
## (c) The move
`p1 = *(s32 *)(base + 0x14);` → `list = *(s32 *)(base + 0x14);` (new `s32 list;`), and `p1 += dx;` → `p1 = list + dx;`.
Probes (`scratch/p/`): folding the load into the add (`p1 = *(s32 *)(base + 0x14) + dx;`) → 4 (COUNT: the load is no
longer scheduled early); `p1 = dx + *(…)` → 3. The temp must be a separate statement at the load's position.
## (d) GENERATOR PROPOSAL
**R-new "seed a preference through a load temp":** when a REG rotation shows the target giving a pointer P the
argument register that a parameter copy vacated (and the free body gives it to the parameter-derived value), split
`P = LOAD; … P += X;` into `T = LOAD; … P = T + X;` — the load temp is local-allocated to the first free register
and turns into both a hard conflict for the block's other globals and a `set_preference` for P. Test on every
`P = LOAD; … P op= …` pair in the function (cheap: one `--try` each).
## (e) What did not work (bytes)
- `s16 a0` parameter (signature change, the TU's two later `extern`s rewritten, `scratch/trytu.sh`) → 29; a first-declared
`s16 val = a0;` → 29 (the d15 prologue-order move is not this residual: the copy order is already right).
- reusing the parameter `a0` as `p1` (`scratch/b1_p1_is_a0.c`) → 29: combine folds the entry copy into the `sll`, so no
copy preference survives.
- the sweep's best 8 (`free_083.c`, `u16 p1`) truncates a pointer and adds an `andi` — a compensating error; it
reached the right map by the same channel (a HImode `p1` makes the load a separate local in `$a0`), which is what
pointed here.
## (f) Where the method fell short
- The allocation table prints `prefers a0` on `val` but not WHY the target's other allocnos avoid `$a0`; the deciding
fact was `find_reg`'s pass-0 exclusion of `regs_someone_prefers` (a lower-priority allocno's preference steals a
register from every higher-priority one it conflicts with). Worth a column in `alloc_table.py`: for each allocno, the
registers excluded in pass 0 by others' preferences.
- The compensating-error candidate (`u16 p1`) was the best clue: diffing ITS `.greg`/`.lreg` against the free body's
showed a new local in `$4` — read the sweep's best candidate's dumps even when the candidate is not honest.
## (g) Structs answer
No. Tested on bytes with a body-local `struct Grid_80182F4C { u16 x0, y0, stride, pad6; u16 *tbl; u8 padC[8]; s32 cells,
recA, recB; } *base;` and field accesses: the close stays 0 (`scratch/st/st_close.c`) and the free body stays 29
(`scratch/st/st_free.c`). The lever was a global-alloc preference decision, not an aliasing or address-folding one.
@@ -0,0 +1,17 @@
void func_80189A84(s32 a0)
{
if ((*(s32 *)(a0 + 0xDC) & 0x2) != 0) {
if (*(s32 *)(a0 + 0x1C) >= 0x15) {
s32 p = *(s32 *)(a0 + 0x20);
*(s16 *)(p + 0x10) = *(u16 *)(p + 0x10) - 0x28;
}
}
if (*(s32 *)(a0 + 0x1C) < 0x11) {
*(s32 *)(*(s32 *)(a0 + 0x20) + 0x4) ^= 0x80000000;
}
if (func_8012BEE8(a0) != 0) {
func_8002AC00(0xB);
func_80130D48(a0);
func_8018A05C(a0);
}
}
@@ -0,0 +1,62 @@
# func_80189A84 (ov_SC03_006_jr_8017AE2C.c) — e6, P36 T7 S104
**Result: score 0, ZERO levers** (2 levers before → 0 after: pin `$2`, pin `$3`). Closed on the FIRST `--try`.
Body: `PACK/body.c` (= `scratch/a2.c`): the decompiler's two reused temps `v0`/`v1` deleted, every read written in place.
## (a) The residual, in one sentence
The free body's `v0` (one variable carrying the 0xDC flags, the 0x1C counter twice and the 0x20 pointer) came out in
`$v1` instead of `$v0` (score 30); the COUNT-looking tail is a knock-on — with the counter left in `$v1` past `slti v0`,
reorg's `redundant_insn` deletes the skip path's reload of `28(s0)` and threads the branch past it (mine `bnez → ecb4`,
target `bnez → eca8`, which reloads).
## (b) The pass and the decision (read in `scratch/dumps_free/free.i.lreg`, proven on bytes)
- `.lreg`: `Register 73 used 11 times across 13 insns; dies in 5 places` = the `v0` variable; it spans blocks 0–4, so
`local-alloc.c:472` (`reg_basic_block[i] >= 0 && reg_n_deaths[i] == 1`) refuses it and it goes to global-alloc.
- Local-alloc runs first and gives every block-local quantity `$2` — including reg 81, the `lui 0x8000` mask in block 4
(`;; Register 81 in 2.`), which is live while `v0` holds the `0x20` pointer. Global-alloc's conflict set for reg 73 then
contains hard reg `$2` (`global.c:1256/1291`, `record_conflicts`), so `find_reg` gives it `$3`, and `v1` (reg 74) `$4`.
- In the target every value is its own one-block, one-death pseudo: local-alloc ties each load to its `andi`/`slti` result
in `$2`, the mask goes to `$a0`, the pointer to `$v0`, the xor value to `$v1`.
## (c) The moves
- Delete the reused `v0`/`v1`; write the reads in place: `if ((*(s32 *)(a0 + 0xDC) & 2) != 0) { if (*(s32 *)(a0 + 0x1C) >= 0x15) { s32 p = …; *(s16 *)(p + 0x10) = *(u16 *)(p + 0x10) - 0x28; } }`
and `if (*(s32 *)(a0 + 0x1C) < 0x11) *(s32 *)(*(s32 *)(a0 + 0x20) + 4) ^= 0x80000000;` → 0.
- Probes (all `scratch/`): only the SECOND if-block rewritten (a fresh block-local `ptr/val/mask`, the first block's
`v0`/`v1` kept) → 0 (`a3.c`); only the FIRST block rewritten, the second keeping `v0` → 7 (`a4.c`). The deciding
defect is the `v0` reuse reaching into block 4, where the mask holds `$2`. The sibling `func_8018993C` (same TU,
related.txt) is spelled exactly like the fixed second block — the shape was one `related.txt` read away.
## Other copies of the class (all proven 0 with `--try`, texts in `scratch/`)
Same text with the per-overlay delta / tail (`*_direct.c` = the body.c shape; the un-suffixed files, the sibling's
`mask/ptr/val` shape, also 0):
- `src/ov_SC02_017/ov_SC02_017_jr_8017DF34.c` `func_8018590C` (the listed 2nd copy; tail `func_80185EE4`) — `scratch/SC02_017_func_8018590C_direct.c`
- The `0x1E` / `D_800B99DA & 0x1F` variant — five more, each 0:
`src/ov_SC05_001/ov_SC05_001_jr_8017BEBC.c` `func_80182600` — `scratch/SC05_001_func_80182600_direct.c`
`src/ov_SC03_107/ov_SC03_107_jr_801789AC.c` `func_8017E7C0` — `scratch/SC03_107_func_8017E7C0_direct.c`
(the tree's definition is K&R `func_8017E7C0(a0) s32 a0;`; the prototype-style text compiled and scored 0)
`src/ov_SC03_112/ov_SC03_112_jr_8017C294.c` `func_801808D8` — `scratch/SC03_112_func_801808D8_direct.c`
`src/ov_SC05_007/ov_SC05_007_jr_8017BEBC.c` `func_8017EE80` — `scratch/SC05_007_func_8017EE80_direct.c`
`src/ov_SC03_115/ov_SC03_115_jr_8017BEBC.c` `func_8017E8D0` — `scratch/SC03_115_func_8017E8D0_direct.c`
Each keeps its tree's own tail call spelling (casts, `(void *)a0`).
## (d) GENERATOR PROPOSAL
**R-new "inline the decompiler temp":** when a body's locals are named after hard registers (`v0`, `v1`, `a1`…) and
`.lreg` shows one of them "dies in N>1 places" across several blocks, rewrite each `vK = E; … use(vK) …` group with
`vK` substituted by `E` (a load used once) or by a fresh block-local name (a pointer used twice) — per if-block, all
at once. The sweep's R6 `inline v0` inlines ONE occurrence and R23 splits by statement group but kept the
`v0 = *(a0 + 0x20)` pointer role in the shared name (history: every single move stops at 3).
## (e) What did not work
The sweep's best 3 (`free_032.c`, R9 swap) reached 3 by breaking the xor's data flow — a compensating error, not a
shape. Rewriting only the first block (`a4.c`) → 7.
## (f) Where the method fell short
Nothing — step 13's (d15) "temp reused for several values → store each directly" and `related.txt`'s sibling
`func_8018993C` both pointed at it. The residual's "COUNT" class was misleading: the instruction counts are equal
(46/46); the missing reload is reorg deleting a redundant load because of the register choice (step 2, COUNT FIRST).
## (g) Structs answer
Not the channel: the defect was a multi-block reused temp (a local-alloc refusal), not an aliasing decision. A struct
type for `a0` (`flags@0xDC`, `state@0x1C`, `sub@0x20`) and for the sub-object (`flags@4`, `s16 y@0x10`) would make the
in-place spelling the natural one, so it removes this defect as a matter of style, but it changes no pass decision.
Not tested on bytes (the plain text already closes).
+185 -185
View File
@@ -1,7 +1,7 @@
{
"head": "fd8fc7363",
"head": "d73720057",
"stamp": "15956e4a96c4",
"generated": "2026-09-11 01:16",
"generated": "2026-09-11 01:26",
"aliases": [
"main",
"ov_SC03_014",
@@ -21,207 +21,207 @@
"main": {
"objects": 85,
"identical": 85,
"seconds": 11.353000000000002,
"seconds": 11.365000000000004,
"mean_s": 0.134
},
"ov_SC03_014": {
"objects": 32,
"identical": 32,
"seconds": 7.000999999999999,
"mean_s": 0.219
"seconds": 6.642000000000001,
"mean_s": 0.208
},
"ov_SC03_015": {
"objects": 32,
"identical": 32,
"seconds": 6.676000000000002,
"mean_s": 0.209
"seconds": 6.909999999999998,
"mean_s": 0.216
},
"ov_SC04_011": {
"objects": 28,
"identical": 28,
"seconds": 6.2059999999999995,
"mean_s": 0.222
"seconds": 5.934000000000001,
"mean_s": 0.212
}
},
"per_object_seconds": {
"build/src/800.o": 0.949,
"build/src/800_b.o": 0.124,
"build/src/800_b_2.o": 0.529,
"build/src/800_b_o0a.o": 0.1,
"build/src/800_c.o": 0.327,
"build/src/800b2.o": 0.167,
"build/src/apicard1.o": 0.152,
"build/src/apicard2.o": 0.179,
"build/src/apicard3.o": 0.095,
"build/src/apicard4.o": 0.143,
"build/src/apicard5.o": 0.078,
"build/src/apicard6.o": 0.074,
"build/src/apicard7.o": 0.11,
"build/src/boot.o": 0.125,
"build/src/gap.o": 0.132,
"build/src/libapi1.o": 0.117,
"build/src/libapi2.o": 0.107,
"build/src/libc2_1.o": 0.117,
"build/src/libc2_2.o": 0.098,
"build/src/libcd1.o": 0.144,
"build/src/libcd2.o": 0.082,
"build/src/libetc.o": 0.091,
"build/src/libgpu.o": 0.142,
"build/src/libgpu2.o": 0.211,
"build/src/libgs1.o": 0.099,
"build/src/libgs2.o": 0.072,
"build/src/libgs3.o": 0.137,
"build/src/libgs4.o": 0.114,
"build/src/libgs5.o": 0.146,
"build/src/libgs6.o": 0.148,
"build/src/libgs7.o": 0.08,
"build/src/libgs8.o": 0.092,
"build/src/libgte1.o": 0.108,
"build/src/libgte10.o": 0.113,
"build/src/libgte11.o": 0.138,
"build/src/libgte12.o": 0.188,
"build/src/libgte13.o": 0.124,
"build/src/libgte14.o": 0.091,
"build/src/libgte15.o": 0.152,
"build/src/libgte16.o": 0.087,
"build/src/libgte17.o": 0.096,
"build/src/libgte18.o": 0.111,
"build/src/libgte19.o": 0.08,
"build/src/libgte2.o": 0.112,
"build/src/libgte20.o": 0.141,
"build/src/libgte21.o": 0.124,
"build/src/libgte22.o": 0.079,
"build/src/libgte23.o": 0.102,
"build/src/libgte24.o": 0.105,
"build/src/libgte25.o": 0.106,
"build/src/libgte26.o": 0.086,
"build/src/libgte27.o": 0.073,
"build/src/libgte28.o": 0.073,
"build/src/libgte29.o": 0.075,
"build/src/libgte3.o": 0.135,
"build/src/libgte30.o": 0.106,
"build/src/libgte4.o": 0.126,
"build/src/libgte5.o": 0.084,
"build/src/libgte6.o": 0.111,
"build/src/libgte7.o": 0.081,
"build/src/libgte8.o": 0.122,
"build/src/libgte9.o": 0.117,
"build/src/libmcrd1.o": 0.123,
"build/src/800.o": 1.0,
"build/src/800_b.o": 0.167,
"build/src/800_b_2.o": 0.477,
"build/src/800_b_o0a.o": 0.14,
"build/src/800_c.o": 0.303,
"build/src/800b2.o": 0.16,
"build/src/apicard1.o": 0.114,
"build/src/apicard2.o": 0.085,
"build/src/apicard3.o": 0.116,
"build/src/apicard4.o": 0.107,
"build/src/apicard5.o": 0.1,
"build/src/apicard6.o": 0.126,
"build/src/apicard7.o": 0.17,
"build/src/boot.o": 0.162,
"build/src/gap.o": 0.187,
"build/src/libapi1.o": 0.107,
"build/src/libapi2.o": 0.118,
"build/src/libc2_1.o": 0.112,
"build/src/libc2_2.o": 0.111,
"build/src/libcd1.o": 0.095,
"build/src/libcd2.o": 0.105,
"build/src/libetc.o": 0.092,
"build/src/libgpu.o": 0.08,
"build/src/libgpu2.o": 0.163,
"build/src/libgs1.o": 0.112,
"build/src/libgs2.o": 0.104,
"build/src/libgs3.o": 0.111,
"build/src/libgs4.o": 0.098,
"build/src/libgs5.o": 0.137,
"build/src/libgs6.o": 0.115,
"build/src/libgs7.o": 0.107,
"build/src/libgs8.o": 0.088,
"build/src/libgte1.o": 0.089,
"build/src/libgte10.o": 0.16,
"build/src/libgte11.o": 0.108,
"build/src/libgte12.o": 0.081,
"build/src/libgte13.o": 0.079,
"build/src/libgte14.o": 0.097,
"build/src/libgte15.o": 0.089,
"build/src/libgte16.o": 0.115,
"build/src/libgte17.o": 0.103,
"build/src/libgte18.o": 0.13,
"build/src/libgte19.o": 0.113,
"build/src/libgte2.o": 0.099,
"build/src/libgte20.o": 0.139,
"build/src/libgte21.o": 0.088,
"build/src/libgte22.o": 0.148,
"build/src/libgte23.o": 0.097,
"build/src/libgte24.o": 0.082,
"build/src/libgte25.o": 0.113,
"build/src/libgte26.o": 0.126,
"build/src/libgte27.o": 0.131,
"build/src/libgte28.o": 0.11,
"build/src/libgte29.o": 0.096,
"build/src/libgte3.o": 0.118,
"build/src/libgte30.o": 0.125,
"build/src/libgte4.o": 0.16,
"build/src/libgte5.o": 0.098,
"build/src/libgte6.o": 0.083,
"build/src/libgte7.o": 0.128,
"build/src/libgte8.o": 0.154,
"build/src/libgte9.o": 0.093,
"build/src/libmcrd1.o": 0.146,
"build/src/libmcrd2.o": 0.118,
"build/src/libpad1.o": 0.083,
"build/src/libpad2.o": 0.142,
"build/src/sgap.o": 0.144,
"build/src/sgap_2.o": 0.122,
"build/src/sgap_3.o": 0.099,
"build/src/sgap_4.o": 0.104,
"build/src/sgap_5.o": 0.11,
"build/src/sgap_6.o": 0.116,
"build/src/sgap_8.o": 0.113,
"build/src/snd1.o": 0.127,
"build/src/snd10.o": 0.142,
"build/src/snd11.o": 0.114,
"build/src/snd12.o": 0.153,
"build/src/snd2.o": 0.146,
"build/src/snd3.o": 0.121,
"build/src/snd4.o": 0.09,
"build/src/snd5.o": 0.163,
"build/src/snd6.o": 0.132,
"build/src/snd7.o": 0.183,
"build/src/snd8.o": 0.08,
"build/src/snd9.o": 0.101,
"build/src/ov_SC03_014/ov_SC03_014.o": 0.163,
"build/src/ov_SC03_014/ov_SC03_014_after.o": 0.663,
"build/src/ov_SC03_014/ov_SC03_014_jr_8012ACE0.o": 0.535,
"build/src/ov_SC03_014/ov_SC03_014_jr_80135888.o": 0.132,
"build/src/ov_SC03_014/ov_SC03_014_jr_80135A4C.o": 0.115,
"build/src/ov_SC03_014/ov_SC03_014_jr_80135D20.o": 0.242,
"build/src/ov_SC03_014/ov_SC03_014_jr_801380E0.o": 0.22,
"build/src/ov_SC03_014/ov_SC03_014_jr_8013C98C.o": 0.197,
"build/src/ov_SC03_014/ov_SC03_014_jr_8013F350.o": 0.159,
"build/src/ov_SC03_014/ov_SC03_014_jr_8013FFD8.o": 0.106,
"build/src/ov_SC03_014/ov_SC03_014_jr_80140608.o": 0.308,
"build/src/ov_SC03_014/ov_SC03_014_jr_8015444C.o": 0.095,
"build/src/ov_SC03_014/ov_SC03_014_jr_80154C24.o": 0.262,
"build/src/ov_SC03_014/ov_SC03_014_jr_801588CC.o": 0.131,
"build/src/ov_SC03_014/ov_SC03_014_jr_80159C84.o": 0.142,
"build/src/ov_SC03_014/ov_SC03_014_jr_8015A3C8.o": 0.103,
"build/src/ov_SC03_014/ov_SC03_014_jr_8015AE2C.o": 0.159,
"build/src/ov_SC03_014/ov_SC03_014_jr_8015C32C.o": 0.675,
"build/src/ov_SC03_014/ov_SC03_014_jr_8016AB6C.o": 0.42,
"build/src/ov_SC03_014/ov_SC03_014_jr_80171B4C.o": 0.148,
"build/src/ov_SC03_014/ov_SC03_014_jr_801734BC.o": 0.328,
"build/src/ov_SC03_014/ov_SC03_014_jr_801789AC.o": 0.085,
"build/src/ov_SC03_014/ov_SC03_014_jr_80178D40.o": 0.146,
"build/src/ov_SC03_014/ov_SC03_014_jr_8017A4AC.o": 0.125,
"build/src/ov_SC03_014/ov_SC03_014_jr_8017AE2C.o": 0.226,
"build/src/ov_SC03_014/ov_SC03_014_jr_8017EB7C.o": 0.26,
"build/src/ov_SC03_014/ov_SC03_014_jr_80184440.o": 0.087,
"build/src/ov_SC03_014/ov_SC03_014_jr_801848E4.o": 0.354,
"build/src/ov_SC03_014/ov_SC03_014_o0b.o": 0.143,
"build/src/ov_SC03_014/ov_SC03_014_o0c.o": 0.09,
"build/src/ov_SC03_014/ov_SC03_014_o0d.o": 0.082,
"build/src/ov_SC03_014/ov_SC03_014_o0e.o": 0.1,
"build/src/ov_SC03_015/ov_SC03_015.o": 0.182,
"build/src/ov_SC03_015/ov_SC03_015_after.o": 0.673,
"build/src/ov_SC03_015/ov_SC03_015_jr_8012ACE0.o": 0.551,
"build/src/ov_SC03_015/ov_SC03_015_jr_80135888.o": 0.157,
"build/src/ov_SC03_015/ov_SC03_015_jr_80135A4C.o": 0.122,
"build/src/ov_SC03_015/ov_SC03_015_jr_80135D20.o": 0.208,
"build/src/ov_SC03_015/ov_SC03_015_jr_801380E0.o": 0.255,
"build/src/ov_SC03_015/ov_SC03_015_jr_8013C98C.o": 0.2,
"build/src/ov_SC03_015/ov_SC03_015_jr_8013F350.o": 0.103,
"build/src/ov_SC03_015/ov_SC03_015_jr_8013FFD8.o": 0.129,
"build/src/ov_SC03_015/ov_SC03_015_jr_80140608.o": 0.241,
"build/src/ov_SC03_015/ov_SC03_015_jr_8015444C.o": 0.115,
"build/src/ov_SC03_015/ov_SC03_015_jr_80154C24.o": 0.246,
"build/src/ov_SC03_015/ov_SC03_015_jr_801588CC.o": 0.132,
"build/src/ov_SC03_015/ov_SC03_015_jr_80159C84.o": 0.09,
"build/src/ov_SC03_015/ov_SC03_015_jr_8015A3C8.o": 0.108,
"build/src/ov_SC03_015/ov_SC03_015_jr_8015AE2C.o": 0.163,
"build/src/ov_SC03_015/ov_SC03_015_jr_8015C32C.o": 0.609,
"build/src/ov_SC03_015/ov_SC03_015_jr_8016AB6C.o": 0.369,
"build/src/ov_SC03_015/ov_SC03_015_jr_80171B4C.o": 0.13,
"build/src/ov_SC03_015/ov_SC03_015_jr_801734BC.o": 0.261,
"build/src/ov_SC03_015/ov_SC03_015_jr_801789AC.o": 0.086,
"build/src/ov_SC03_015/ov_SC03_015_jr_80178D40.o": 0.136,
"build/src/ov_SC03_015/ov_SC03_015_jr_8017A4AC.o": 0.12,
"build/src/ov_SC03_015/ov_SC03_015_jr_8017AE2C.o": 0.21,
"build/src/ov_SC03_015/ov_SC03_015_jr_8017EB7C.o": 0.29,
"build/src/ov_SC03_015/ov_SC03_015_jr_80184440.o": 0.081,
"build/src/ov_SC03_015/ov_SC03_015_jr_801848E4.o": 0.345,
"build/src/ov_SC03_015/ov_SC03_015_o0b.o": 0.078,
"build/src/ov_SC03_015/ov_SC03_015_o0c.o": 0.094,
"build/src/ov_SC03_015/ov_SC03_015_o0d.o": 0.078,
"build/src/ov_SC03_015/ov_SC03_015_o0e.o": 0.114,
"build/src/ov_SC04_011/ov_SC04_011.o": 0.172,
"build/src/ov_SC04_011/ov_SC04_011_after.o": 0.612,
"build/src/ov_SC04_011/ov_SC04_011_jr_8012ACE0.o": 0.542,
"build/src/ov_SC04_011/ov_SC04_011_jr_80135888.o": 0.092,
"build/src/libpad1.o": 0.112,
"build/src/libpad2.o": 0.155,
"build/src/sgap.o": 0.118,
"build/src/sgap_2.o": 0.1,
"build/src/sgap_3.o": 0.152,
"build/src/sgap_4.o": 0.133,
"build/src/sgap_5.o": 0.099,
"build/src/sgap_6.o": 0.126,
"build/src/sgap_8.o": 0.104,
"build/src/snd1.o": 0.132,
"build/src/snd10.o": 0.117,
"build/src/snd11.o": 0.137,
"build/src/snd12.o": 0.088,
"build/src/snd2.o": 0.112,
"build/src/snd3.o": 0.09,
"build/src/snd4.o": 0.111,
"build/src/snd5.o": 0.104,
"build/src/snd6.o": 0.112,
"build/src/snd7.o": 0.134,
"build/src/snd8.o": 0.099,
"build/src/snd9.o": 0.145,
"build/src/ov_SC03_014/ov_SC03_014.o": 0.173,
"build/src/ov_SC03_014/ov_SC03_014_after.o": 0.68,
"build/src/ov_SC03_014/ov_SC03_014_jr_8012ACE0.o": 0.534,
"build/src/ov_SC03_014/ov_SC03_014_jr_80135888.o": 0.072,
"build/src/ov_SC03_014/ov_SC03_014_jr_80135A4C.o": 0.106,
"build/src/ov_SC03_014/ov_SC03_014_jr_80135D20.o": 0.173,
"build/src/ov_SC03_014/ov_SC03_014_jr_801380E0.o": 0.266,
"build/src/ov_SC03_014/ov_SC03_014_jr_8013C98C.o": 0.179,
"build/src/ov_SC03_014/ov_SC03_014_jr_8013F350.o": 0.119,
"build/src/ov_SC03_014/ov_SC03_014_jr_8013FFD8.o": 0.118,
"build/src/ov_SC03_014/ov_SC03_014_jr_80140608.o": 0.213,
"build/src/ov_SC03_014/ov_SC03_014_jr_8015444C.o": 0.118,
"build/src/ov_SC03_014/ov_SC03_014_jr_80154C24.o": 0.235,
"build/src/ov_SC03_014/ov_SC03_014_jr_801588CC.o": 0.132,
"build/src/ov_SC03_014/ov_SC03_014_jr_80159C84.o": 0.087,
"build/src/ov_SC03_014/ov_SC03_014_jr_8015A3C8.o": 0.084,
"build/src/ov_SC03_014/ov_SC03_014_jr_8015AE2C.o": 0.152,
"build/src/ov_SC03_014/ov_SC03_014_jr_8015C32C.o": 0.645,
"build/src/ov_SC03_014/ov_SC03_014_jr_8016AB6C.o": 0.322,
"build/src/ov_SC03_014/ov_SC03_014_jr_80171B4C.o": 0.172,
"build/src/ov_SC03_014/ov_SC03_014_jr_801734BC.o": 0.267,
"build/src/ov_SC03_014/ov_SC03_014_jr_801789AC.o": 0.123,
"build/src/ov_SC03_014/ov_SC03_014_jr_80178D40.o": 0.162,
"build/src/ov_SC03_014/ov_SC03_014_jr_8017A4AC.o": 0.094,
"build/src/ov_SC03_014/ov_SC03_014_jr_8017AE2C.o": 0.26,
"build/src/ov_SC03_014/ov_SC03_014_jr_8017EB7C.o": 0.262,
"build/src/ov_SC03_014/ov_SC03_014_jr_80184440.o": 0.078,
"build/src/ov_SC03_014/ov_SC03_014_jr_801848E4.o": 0.351,
"build/src/ov_SC03_014/ov_SC03_014_o0b.o": 0.12,
"build/src/ov_SC03_014/ov_SC03_014_o0c.o": 0.101,
"build/src/ov_SC03_014/ov_SC03_014_o0d.o": 0.111,
"build/src/ov_SC03_014/ov_SC03_014_o0e.o": 0.133,
"build/src/ov_SC03_015/ov_SC03_015.o": 0.173,
"build/src/ov_SC03_015/ov_SC03_015_after.o": 0.648,
"build/src/ov_SC03_015/ov_SC03_015_jr_8012ACE0.o": 0.515,
"build/src/ov_SC03_015/ov_SC03_015_jr_80135888.o": 0.111,
"build/src/ov_SC03_015/ov_SC03_015_jr_80135A4C.o": 0.113,
"build/src/ov_SC03_015/ov_SC03_015_jr_80135D20.o": 0.2,
"build/src/ov_SC03_015/ov_SC03_015_jr_801380E0.o": 0.215,
"build/src/ov_SC03_015/ov_SC03_015_jr_8013C98C.o": 0.176,
"build/src/ov_SC03_015/ov_SC03_015_jr_8013F350.o": 0.125,
"build/src/ov_SC03_015/ov_SC03_015_jr_8013FFD8.o": 0.124,
"build/src/ov_SC03_015/ov_SC03_015_jr_80140608.o": 0.235,
"build/src/ov_SC03_015/ov_SC03_015_jr_8015444C.o": 0.145,
"build/src/ov_SC03_015/ov_SC03_015_jr_80154C24.o": 0.258,
"build/src/ov_SC03_015/ov_SC03_015_jr_801588CC.o": 0.134,
"build/src/ov_SC03_015/ov_SC03_015_jr_80159C84.o": 0.083,
"build/src/ov_SC03_015/ov_SC03_015_jr_8015A3C8.o": 0.086,
"build/src/ov_SC03_015/ov_SC03_015_jr_8015AE2C.o": 0.157,
"build/src/ov_SC03_015/ov_SC03_015_jr_8015C32C.o": 0.655,
"build/src/ov_SC03_015/ov_SC03_015_jr_8016AB6C.o": 0.388,
"build/src/ov_SC03_015/ov_SC03_015_jr_80171B4C.o": 0.178,
"build/src/ov_SC03_015/ov_SC03_015_jr_801734BC.o": 0.274,
"build/src/ov_SC03_015/ov_SC03_015_jr_801789AC.o": 0.111,
"build/src/ov_SC03_015/ov_SC03_015_jr_80178D40.o": 0.127,
"build/src/ov_SC03_015/ov_SC03_015_jr_8017A4AC.o": 0.112,
"build/src/ov_SC03_015/ov_SC03_015_jr_8017AE2C.o": 0.288,
"build/src/ov_SC03_015/ov_SC03_015_jr_8017EB7C.o": 0.249,
"build/src/ov_SC03_015/ov_SC03_015_jr_80184440.o": 0.066,
"build/src/ov_SC03_015/ov_SC03_015_jr_801848E4.o": 0.425,
"build/src/ov_SC03_015/ov_SC03_015_o0b.o": 0.077,
"build/src/ov_SC03_015/ov_SC03_015_o0c.o": 0.138,
"build/src/ov_SC03_015/ov_SC03_015_o0d.o": 0.156,
"build/src/ov_SC03_015/ov_SC03_015_o0e.o": 0.168,
"build/src/ov_SC04_011/ov_SC04_011.o": 0.164,
"build/src/ov_SC04_011/ov_SC04_011_after.o": 0.616,
"build/src/ov_SC04_011/ov_SC04_011_jr_8012ACE0.o": 0.478,
"build/src/ov_SC04_011/ov_SC04_011_jr_80135888.o": 0.074,
"build/src/ov_SC04_011/ov_SC04_011_jr_80135A4C.o": 0.081,
"build/src/ov_SC04_011/ov_SC04_011_jr_80135D20.o": 0.197,
"build/src/ov_SC04_011/ov_SC04_011_jr_801380E0.o": 0.225,
"build/src/ov_SC04_011/ov_SC04_011_jr_8013C98C.o": 0.168,
"build/src/ov_SC04_011/ov_SC04_011_jr_8013F350.o": 0.121,
"build/src/ov_SC04_011/ov_SC04_011_jr_8013FFD8.o": 0.098,
"build/src/ov_SC04_011/ov_SC04_011_jr_80140608.o": 0.253,
"build/src/ov_SC04_011/ov_SC04_011_jr_8015444C.o": 0.091,
"build/src/ov_SC04_011/ov_SC04_011_jr_80154C24.o": 0.266,
"build/src/ov_SC04_011/ov_SC04_011_jr_801588CC.o": 0.147,
"build/src/ov_SC04_011/ov_SC04_011_jr_80159C84.o": 0.102,
"build/src/ov_SC04_011/ov_SC04_011_jr_8015A3C8.o": 0.088,
"build/src/ov_SC04_011/ov_SC04_011_jr_8015AE2C.o": 0.159,
"build/src/ov_SC04_011/ov_SC04_011_jr_8015C32C.o": 0.554,
"build/src/ov_SC04_011/ov_SC04_011_jr_8016AB6C.o": 0.325,
"build/src/ov_SC04_011/ov_SC04_011_jr_80171B4C.o": 0.127,
"build/src/ov_SC04_011/ov_SC04_011_jr_801734BC.o": 0.284,
"build/src/ov_SC04_011/ov_SC04_011_jr_801789AC.o": 0.115,
"build/src/ov_SC04_011/ov_SC04_011_jr_80178D40.o": 0.159,
"build/src/ov_SC04_011/ov_SC04_011_jr_8017A4AC.o": 0.133,
"build/src/ov_SC04_011/ov_SC04_011_jr_8017AE2C.o": 0.161,
"build/src/ov_SC04_011/ov_SC04_011_jr_8017D494.o": 0.748,
"build/src/ov_SC04_011/ov_SC04_011_o0b.o": 0.086,
"build/src/ov_SC04_011/ov_SC04_011_o0c.o": 0.1
"build/src/ov_SC04_011/ov_SC04_011_jr_80135D20.o": 0.142,
"build/src/ov_SC04_011/ov_SC04_011_jr_801380E0.o": 0.232,
"build/src/ov_SC04_011/ov_SC04_011_jr_8013C98C.o": 0.186,
"build/src/ov_SC04_011/ov_SC04_011_jr_8013F350.o": 0.099,
"build/src/ov_SC04_011/ov_SC04_011_jr_8013FFD8.o": 0.128,
"build/src/ov_SC04_011/ov_SC04_011_jr_80140608.o": 0.246,
"build/src/ov_SC04_011/ov_SC04_011_jr_8015444C.o": 0.143,
"build/src/ov_SC04_011/ov_SC04_011_jr_80154C24.o": 0.287,
"build/src/ov_SC04_011/ov_SC04_011_jr_801588CC.o": 0.136,
"build/src/ov_SC04_011/ov_SC04_011_jr_80159C84.o": 0.111,
"build/src/ov_SC04_011/ov_SC04_011_jr_8015A3C8.o": 0.101,
"build/src/ov_SC04_011/ov_SC04_011_jr_8015AE2C.o": 0.143,
"build/src/ov_SC04_011/ov_SC04_011_jr_8015C32C.o": 0.515,
"build/src/ov_SC04_011/ov_SC04_011_jr_8016AB6C.o": 0.324,
"build/src/ov_SC04_011/ov_SC04_011_jr_80171B4C.o": 0.136,
"build/src/ov_SC04_011/ov_SC04_011_jr_801734BC.o": 0.27,
"build/src/ov_SC04_011/ov_SC04_011_jr_801789AC.o": 0.088,
"build/src/ov_SC04_011/ov_SC04_011_jr_80178D40.o": 0.142,
"build/src/ov_SC04_011/ov_SC04_011_jr_8017A4AC.o": 0.104,
"build/src/ov_SC04_011/ov_SC04_011_jr_8017AE2C.o": 0.141,
"build/src/ov_SC04_011/ov_SC04_011_jr_8017D494.o": 0.661,
"build/src/ov_SC04_011/ov_SC04_011_o0b.o": 0.079,
"build/src/ov_SC04_011/ov_SC04_011_o0c.o": 0.107
},
"ok": true,
"seconds": 3.8
"seconds": 3.6
}
+2
View File
@@ -29376,3 +29376,5 @@
{"ts": "2026-09-11 01:12:29", "label": "s104_e7", "rung": "E", "calib": {"head": "8310031fe", "stamp": "15956e4a96c4"}, "tu": "src/ov_SC02_017/ov_SC02_017_jr_8017DF34.c", "fn": "func_80181E98", "addr": 2149064344, "aliases": null, "header": false, "includers": 0, "nhash_before": "3d2f4d8627845e45e8d3c4211c817ee299ce5948", "nhash_after": "103d754522a45718d2ae866e015793e2292eec19", "source": ".run/P36/agents/ov_SC02_017__func_80181E98/body.c", "verdict": "LEVER-FREE", "sites": [], "compiles": 1, "seconds": 0.324, "objects": ["build/src/ov_SC02_017/ov_SC02_017_jr_8017DF34.o"], "before_text": "s32 func_80181E98_impl(void *arg)\n{\n extern void func_8012F214(s32 a0, s32 a1, s32 a2);\n extern s32 func_80013478(s32 a0, s32 a1);\n extern void func_8002D4C8(s32 a0, s32 a1);\n extern s32 D_8018E564;\n extern u8 D_800AF648;\n extern u8 D_80126B5C;\n\n struct {\n s16 in0[4];\n s16 in1[4];\n s16 sxy[2];\n s32 flag;\n } w;\n s32 t;\n s32 r;\n s32 k;\n\n func_8012F214((s32)arg, (s32)&D_8018E564, (s32)w.in0);\n gte_SetRotMatrix(&D_800AF648);\n gte_SetTransMatrix(&D_800AF648);\n gte_ldv0(w.in0);\n gte_rtps();\n gte_stsxy(w.sxy);\n gte_stflg(&w.flag);\n if (w.flag & 0xFFFFEFFF) {\n goto ret0;\n }\n t = w.sxy[0];\n if (t < 0) {\n t = -t;\n }\n if (t < 0xAB) {\n if (w.sxy[1] >= 0) {\n if (w.sxy[1] >= 0x83) {\n goto second;\n }\n goto pass;\n } else {\n if (-w.sxy[1] < 0x83) {\n goto pass;\n }\n }\n }\nsecond:\n w.in1[0] = *(s16 *)((s32)arg + 6);\n w.in1[1] = *(s16 *)((s32)arg + 10);\n w.in1[2] = *(s16 *)((s32)arg + 14);\n gte_ldv0(w.in1);\n gte_rtps();\n gte_stsxy(w.sxy);\n gte_stflg(&w.flag);\n if (w.flag & 0xFFFFEFFF) {\n goto ret0;\n }\n t = w.sxy[0];\n if (t < 0) {\n t = -t;\n }\n if (t >= 0x105) {\n goto ret0;\n }\n if (w.sxy[1] >= 0) {\n if (w.sxy[1] >= 0x8D) {\n goto ret0;\n }\n /* zero-byte cross_jump fence (jump.c find_cross_jump): without an insn\n here the two |sxy[1]| arms share the suffix `slti 0x8D; beq ret0`\n and cross_jump merges them into a single conditional-negate (-5 ins). */\n __asm__ __volatile__(\"\"); // !FAKE: barrier \u2014 NEEDED DIFFERS (P36 rung B tus8)\n goto pass;\n } else {\n if (-w.sxy[1] >= 0x8D) {\n goto ret0;\n }\n }\npass:\n r = func_80013478((s32)&D_80126B5C, (s32)w.in0);\n k = 0x5A0;\n if (r <= 0x41010) {\n k = 0x59F;\n }\n func_8002D4C8(k, 0);\n return 1;\nret0:\n return 0;\n}\n", "after_text": "s32 func_80181E98_impl(void *arg)\n{\n extern void func_8012F214(s32 a0, s32 a1, s32 a2);\n extern s32 func_80013478(s32 a0, s32 a1);\n extern void func_8002D4C8(s32 a0, s32 a1);\n extern s32 D_8018E564;\n extern u8 D_800AF648;\n extern u8 D_80126B5C;\n\n struct {\n s16 in0[4];\n s16 in1[4];\n s16 sxy[2];\n s32 flag;\n } w;\n s32 t;\n s32 r;\n s32 k;\n\n func_8012F214((s32)arg, (s32)&D_8018E564, (s32)w.in0);\n gte_SetRotMatrix(&D_800AF648);\n gte_SetTransMatrix(&D_800AF648);\n gte_ldv0(w.in0);\n gte_rtps();\n gte_stsxy(w.sxy);\n gte_stflg(&w.flag);\n if (w.flag & 0xFFFFEFFF) {\n return 0;\n }\n t = w.sxy[0];\n if (t < 0) {\n t = -t;\n }\n if (t >= 0xAB || (w.sxy[1] >= 0 ? w.sxy[1] >= 0x83 : -w.sxy[1] >= 0x83)) {\n w.in1[0] = *(s16 *)((s32)arg + 6);\n w.in1[1] = *(s16 *)((s32)arg + 10);\n w.in1[2] = *(s16 *)((s32)arg + 14);\n gte_ldv0(w.in1);\n gte_rtps();\n gte_stsxy(w.sxy);\n gte_stflg(&w.flag);\n if (w.flag & 0xFFFFEFFF) {\n return 0;\n }\n t = w.sxy[0];\n if (t < 0) {\n t = -t;\n }\n if (t >= 0x105 || (w.sxy[1] >= 0 ? w.sxy[1] >= 0x8D : -w.sxy[1] >= 0x8D)) {\n return 0;\n }\n }\n r = func_80013478((s32)&D_80126B5C, (s32)w.in0);\n k = 0x5A0;\n if (r <= 0x41010) {\n k = 0x59F;\n }\n func_8002D4C8(k, 0);\n return 1;\n}\n"}
{"ts": "2026-09-11 01:13:05", "label": "s104_e7", "rung": "E", "calib": {"head": "a4378aa04", "stamp": "15956e4a96c4"}, "tu": "src/ov_SC02_011/ov_SC02_011_jr_80183178.c", "fn": "func_80188034", "addr": 2149089332, "aliases": null, "header": false, "includers": 0, "nhash_before": "10fb258db655381af24190437b259c2a85277ac3", "nhash_after": "a2fce7d011636169a2a6de6823cc647232f7b831", "source": ".run/P36/agents/ov_SC02_017__func_801831FC/scratch/sib3.c", "verdict": "LEVER-FREE", "sites": [], "compiles": 1, "seconds": 0.194, "objects": ["build/src/ov_SC02_011/ov_SC02_011_jr_80183178.o"], "before_text": "void func_80188034(s32 a0) {\n s32 idx;\n u8 *s0;\n s32 base;\n s16 buf[2];\n s16 sVar1;\n register s32 iVar3 __asm__(\"$2\"); // !FAKE: pin $2 \u2014 NEEDED DIFFERS (P36 rung B tus9)\n s32 a1v;\n\n idx = *(s16 *)(a0 + 0xFC);\n s0 = D_80195FC8 + idx * 8;\n base = (s32)&D_80126B58;\n\n if (*(s16 *)(s0 + 6) != 0 && (s16)D_80126B62 >= -0x8FF) {\n func_80015978(base + 4, (s32 *)buf);\n buf[1] = *(u16 *)(s0 + 2);\n sVar1 = (s16)func_80013294((void *)buf, (void *)s0);\n if (sVar1 < 0x800) {\n iVar3 = (0x800 - sVar1) * 0x7F;\n if (iVar3 < 0) {\n iVar3 += 0x7FF;\n }\n iVar3 = iVar3 >> 11;\n a1v = iVar3;\n if (iVar3 < 0) {\n a1v = 0;\n }\n if ((s16)a1v >= 0x80) {\n a1v = 0x7F;\n }\n func_8002D4C8(*(u16 *)(s0 + 6), (a1v | 0x1000) & 0xffff);\n }\n }\n}\n", "after_text": "void func_80188034(s32 a0) {\n s32 idx;\n u8 *s0;\n s32 base;\n s16 buf[2];\n s16 sVar1;\n s32 q;\n s16 a1v;\n\n idx = *(s16 *)(a0 + 0xFC);\n s0 = D_80195FC8 + idx * 8;\n base = (s32)&D_80126B58;\n\n if (*(s16 *)(s0 + 6) != 0 && (s16)D_80126B62 >= -0x8FF) {\n func_80015978(base + 4, (s32 *)buf);\n buf[1] = *(u16 *)(s0 + 2);\n sVar1 = (s16)func_80013294((void *)buf, (void *)s0);\n if (sVar1 < 0x800) {\n q = (0x800 - sVar1) * 0x7F / 0x800;\n if (q < 0) {\n a1v = 0;\n } else {\n a1v = q;\n }\n if (a1v >= 0x80) {\n a1v = 0x7F;\n }\n func_8002D4C8(*(u16 *)(s0 + 6), (u16)(a1v | 0x1000));\n }\n }\n}\n"}
{"ts": "2026-09-11 01:17:10", "label": "s104_e2", "rung": "E", "calib": {"head": "fd8fc7363", "stamp": "15956e4a96c4"}, "tu": "src/800_b_2.c", "fn": "func_800348A8", "addr": 2147698856, "aliases": null, "header": false, "includers": 0, "nhash_before": "fcf18ccc90c05a0db9bfb0547c0730afef4c7eea", "nhash_after": "eeb62cbb4042d7e340442ca3b07478f780c47b63", "source": ".run/P36/agents/main__func_800348A8/body.c", "verdict": "LEVER-FREE", "sites": [], "compiles": 1, "seconds": 0.24, "objects": ["build/src/800_b_2.o"], "before_text": "s32 func_800348A8(u32 arg0) {\n u16 *p;\n u16 *q;\n s32 i;\n u32 lo;\n u32 hi;\n s32 five;\n\n p = D_800A46E8;\n i = 0;\n five = 5;\n lo = arg0 & 0xFFFF;\n hi = arg0 >> 16;\n q = p + 3;\n do {\n __asm__ (\"\" :: \"r\"(i), \"r\"(i)); // !FAKE: keepalive \u2014 NEEDED DIFFERS (P36 rung B tus9)\n if (p[0] == five && q[-1] == lo) {\n if (hi == 0 || q[0] == hi) {\n return i + 1;\n }\n }\n i++;\n q += 0x2A;\n p += 0x2A;\n } while (i < 8);\n return 0;\n}\n", "after_text": "s32 func_800348A8(u32 arg0) {\n u16 *p;\n s32 i;\n\n p = D_800A46E8;\n for (i = 0; i < 8; i++, p += 0x2A) {\n if (p[0] == 5 && p[2] == (arg0 & 0xFFFF) && ((arg0 >> 16) == 0 || p[3] == (arg0 >> 16))) {\n return ++i;\n }\n }\n return 0;\n}\n"}
{"ts": "2026-09-11 01:27:03", "label": "s104_e6", "rung": "E", "calib": {"head": "d73720057", "stamp": "15956e4a96c4"}, "tu": "src/ov_SC03_006/ov_SC03_006_jr_8017AE2C.c", "fn": "func_80189A84", "addr": 2149096068, "aliases": null, "header": false, "includers": 0, "nhash_before": "1a606a05ec083834d1578d6f8008f955803a9d00", "nhash_after": "ea98daf010413a7b5c48f0591d9bdbb1c1589d83", "source": ".run/P36/agents/ov_SC03_006__func_80189A84/body.c", "verdict": "LEVER-FREE", "sites": [], "compiles": 1, "seconds": 0.533, "objects": ["build/src/ov_SC03_006/ov_SC03_006_jr_8017AE2C.o"], "before_text": "void func_80189A84(s32 a0)\n{\n register s32 v0 __asm__(\"$2\"); // !FAKE: pin $2 \u2014 NEEDED DIFFERS (P36 rung B tus7)\n register s32 v1 __asm__(\"$3\"); // !FAKE: pin $3 \u2014 NEEDED DIFFERS (P36 rung B tus7)\n\n v0 = *(s32 *)(a0 + 0xDC);\n if ((v0 & 0x2) != 0) {\n v0 = *(s32 *)(a0 + 0x1C);\n if (v0 >= 0x15) {\n v1 = *(s32 *)(a0 + 0x20);\n v0 = *(u16 *)(v1 + 0x10);\n *(s16 *)(v1 + 0x10) = v0 - 0x28;\n }\n }\n\n v0 = *(s32 *)(a0 + 0x1C);\n if (v0 < 0x11) {\n v0 = *(s32 *)(a0 + 0x20);\n v1 = *(s32 *)(v0 + 0x4);\n v1 = v1 ^ 0x80000000;\n *(s32 *)(v0 + 0x4) = v1;\n }\n\n if (func_8012BEE8(a0) != 0) {\n func_8002AC00(0xB);\n func_80130D48(a0);\n func_8018A05C(a0);\n }\n}\n", "after_text": "void func_80189A84(s32 a0)\n{\n if ((*(s32 *)(a0 + 0xDC) & 0x2) != 0) {\n if (*(s32 *)(a0 + 0x1C) >= 0x15) {\n s32 p = *(s32 *)(a0 + 0x20);\n *(s16 *)(p + 0x10) = *(u16 *)(p + 0x10) - 0x28;\n }\n }\n if (*(s32 *)(a0 + 0x1C) < 0x11) {\n *(s32 *)(*(s32 *)(a0 + 0x20) + 0x4) ^= 0x80000000;\n }\n if (func_8012BEE8(a0) != 0) {\n func_8002AC00(0xB);\n func_80130D48(a0);\n func_8018A05C(a0);\n }\n}\n"}
{"ts": "2026-09-11 01:27:22", "label": "s104_e6", "rung": "E", "calib": {"head": "d73720057", "stamp": "15956e4a96c4"}, "tu": "src/ov_SC02_017/ov_SC02_017_jr_8017DF34.c", "fn": "func_8018590C", "addr": 2149079308, "aliases": null, "header": false, "includers": 0, "nhash_before": "1a606a05ec083834d1578d6f8008f955803a9d00", "nhash_after": "ea98daf010413a7b5c48f0591d9bdbb1c1589d83", "source": "propagate:src/ov_SC03_006/ov_SC03_006_jr_8017AE2C.c:func_80189A84", "verdict": "LEVER-FREE", "sites": [], "compiles": 1, "seconds": 0.241, "objects": ["build/src/ov_SC02_017/ov_SC02_017_jr_8017DF34.o"], "before_text": "void func_8018590C(s32 a0)\n{\n register s32 v0 __asm__(\"$2\"); // !FAKE: pin $2 \u2014 NEEDED DIFFERS (P36 rung B tus8)\n register s32 v1 __asm__(\"$3\"); // !FAKE: pin $3 \u2014 NEEDED DIFFERS (P36 rung B tus8)\n\n v0 = *(s32 *)(a0 + 0xDC);\n if ((v0 & 0x2) != 0) {\n v0 = *(s32 *)(a0 + 0x1C);\n if (v0 >= 0x15) {\n v1 = *(s32 *)(a0 + 0x20);\n v0 = *(u16 *)(v1 + 0x10);\n *(s16 *)(v1 + 0x10) = v0 - 0x28;\n }\n }\n\n v0 = *(s32 *)(a0 + 0x1C);\n if (v0 < 0x11) {\n v0 = *(s32 *)(a0 + 0x20);\n v1 = *(s32 *)(v0 + 0x4);\n v1 = v1 ^ 0x80000000;\n *(s32 *)(v0 + 0x4) = v1;\n }\n\n if (func_8012BEE8(a0) != 0) {\n func_8002AC00(0xB);\n func_80130D48(a0);\n func_80185EE4(a0);\n }\n}\n", "after_text": "void func_8018590C(s32 a0)\n{\n if ((*(s32 *)(a0 + 0xDC) & 0x2) != 0) {\n if (*(s32 *)(a0 + 0x1C) >= 0x15) {\n s32 p = *(s32 *)(a0 + 0x20);\n *(s16 *)(p + 0x10) = *(u16 *)(p + 0x10) - 0x28;\n }\n }\n if (*(s32 *)(a0 + 0x1C) < 0x11) {\n *(s32 *)(*(s32 *)(a0 + 0x20) + 0x4) ^= 0x80000000;\n }\n if (func_8012BEE8(a0) != 0) {\n func_8002AC00(0xB);\n func_80130D48(a0);\n func_80185EE4(a0);\n }\n}\n"}
+6 -18
View File
@@ -7885,27 +7885,15 @@ extern void func_80185EE4(s32 a0);
void func_8018590C(s32 a0)
{
register s32 v0 __asm__("$2"); // !FAKE: pin $2 — NEEDED DIFFERS (P36 rung B tus8)
register s32 v1 __asm__("$3"); // !FAKE: pin $3 — NEEDED DIFFERS (P36 rung B tus8)
v0 = *(s32 *)(a0 + 0xDC);
if ((v0 & 0x2) != 0) {
v0 = *(s32 *)(a0 + 0x1C);
if (v0 >= 0x15) {
v1 = *(s32 *)(a0 + 0x20);
v0 = *(u16 *)(v1 + 0x10);
*(s16 *)(v1 + 0x10) = v0 - 0x28;
if ((*(s32 *)(a0 + 0xDC) & 0x2) != 0) {
if (*(s32 *)(a0 + 0x1C) >= 0x15) {
s32 p = *(s32 *)(a0 + 0x20);
*(s16 *)(p + 0x10) = *(u16 *)(p + 0x10) - 0x28;
}
}
v0 = *(s32 *)(a0 + 0x1C);
if (v0 < 0x11) {
v0 = *(s32 *)(a0 + 0x20);
v1 = *(s32 *)(v0 + 0x4);
v1 = v1 ^ 0x80000000;
*(s32 *)(v0 + 0x4) = v1;
if (*(s32 *)(a0 + 0x1C) < 0x11) {
*(s32 *)(*(s32 *)(a0 + 0x20) + 0x4) ^= 0x80000000;
}
if (func_8012BEE8(a0) != 0) {
func_8002AC00(0xB);
func_80130D48(a0);
+6 -18
View File
@@ -12879,27 +12879,15 @@ extern void func_8018A05C(s32 a0);
void func_80189A84(s32 a0)
{
register s32 v0 __asm__("$2"); // !FAKE: pin $2 — NEEDED DIFFERS (P36 rung B tus7)
register s32 v1 __asm__("$3"); // !FAKE: pin $3 — NEEDED DIFFERS (P36 rung B tus7)
v0 = *(s32 *)(a0 + 0xDC);
if ((v0 & 0x2) != 0) {
v0 = *(s32 *)(a0 + 0x1C);
if (v0 >= 0x15) {
v1 = *(s32 *)(a0 + 0x20);
v0 = *(u16 *)(v1 + 0x10);
*(s16 *)(v1 + 0x10) = v0 - 0x28;
if ((*(s32 *)(a0 + 0xDC) & 0x2) != 0) {
if (*(s32 *)(a0 + 0x1C) >= 0x15) {
s32 p = *(s32 *)(a0 + 0x20);
*(s16 *)(p + 0x10) = *(u16 *)(p + 0x10) - 0x28;
}
}
v0 = *(s32 *)(a0 + 0x1C);
if (v0 < 0x11) {
v0 = *(s32 *)(a0 + 0x20);
v1 = *(s32 *)(v0 + 0x4);
v1 = v1 ^ 0x80000000;
*(s32 *)(v0 + 0x4) = v1;
if (*(s32 *)(a0 + 0x1C) < 0x11) {
*(s32 *)(*(s32 *)(a0 + 0x20) + 0x4) ^= 0x80000000;
}
if (func_8012BEE8(a0) != 0) {
func_8002AC00(0xB);
func_80130D48(a0);