feat(decomp): parallel gate — 19 fns across 14 binaries (8 workers)

ov_SC04_000    func_8017F98C
  ov_SC04_015    func_8017E520
  ov_SC03_121    func_8017D8D4 func_80180E64
  ov_SC03_110    func_8018035C
  ov_SC04_011    func_801827DC
  ov_SC03_007    func_801810E4 func_80184AFC
  ov_SC03_105    func_8017F55C func_801831E0
  ov_SC02_003    func_8017F62C
  ov_SC05_001    func_80183C9C
  ov_SC06_024    func_8017E1F0
  ov_SC06_030    func_8017F268 func_80181164
  ov_SC05_010    func_8018340C func_8018388C
  ov_SC04_016    func_8017D118
  ov_SC06_022    func_8017EBE8
This commit is contained in:
Drew T
2026-08-31 14:53:41 -06:00
parent 2b618caf6b
commit c26ddf136d
18 changed files with 2637 additions and 21 deletions
+138 -1
View File
@@ -3271,6 +3271,143 @@ void func_8017F5E4(s32 param_1) {
}
INCLUDE_ASM("asm/ov_SC02_003/nonmatchings/ov_SC02_003_jr_8017EA84", func_8017F62C);
// @class: jtbl-carve + switch binary-tree
// @stuck: none — remapped from the byte-proven twin ov_SC02_000:func_8017F62C (§193-A);
// the two .s bodies are instruction-identical (only the jtbl rodata block differs in
// extraction). All 16 symbols re-verified against THIS target's own relocation lines.
// jtbl_801E69EC = [F7D0, F830, F904, F858, F8B8]; entry 2 aims at the switch-end label,
// which is ALSO the out-of-range (sltiu 5) target => `case 2: break;` literally and NO
// `default:` clause (cookbook §206.2/§206.3). The 0x70 byte test is the neighbour
// func_8017EA84's own spelling ((s32)((u32)*(u16*)(a0+0x70) << 0x10) >> 0x18).
// `t == 0 || (t >= 3 && t <= 4)` folds to beqz + addiu -3 + sltiu 2 (build_range_check).
// Case 0/case 2 of the first switch are written out identically; gcc cross-jumps their
// tails to .L8017F68C by itself (§206.5). The func_8012C51C request block is spelled as
// a local anonymous struct so no engine_types.h definition can collide.
extern s32 func_8012D5E4(s32 a0, s32 a1, s32 a2, s32 a3);
extern void func_8012F214(s32 a0, s32 a1, s32 a2);
extern s32 func_8012C51C(void *a0, s32 a1);
extern void func_8012B2CC(s32 a0);
extern s32 func_8012B8E4(s32 arg0, s32 arg1);
extern s32 func_8012BCCC(s32 a0);
extern s32 func_8012BEE8(s32 a0);
extern void func_8012A828(s32 a0, void *a1);
extern s32 func_8018A660(s32 a0, s32 a1);
void func_8017F62C(s32 a0)
{
extern u16 D_8018E66C[];
extern void (*D_8018E6D4[])(void);
extern u8 D_801A629C;
extern char D_801A6754[];
extern unsigned char D_801A73BC[];
struct {
s16 f0, f2, f4, f6, f8, fA, fC, fE;
s32 f10;
} sp;
s16 vec[4];
s32 t;
switch (*(u16 *)(a0 + 0x34)) {
case 0:
if (*(s32 *)(a0 + 0x1C) == 7) {
func_8012D5E4(a0, (s32) D_8018E6D4, (s32) &D_8018E6D4[2], 0xB);
}
break;
case 2:
if (*(s32 *)(a0 + 0x1C) == 0xA) {
func_8012D5E4(a0, (s32) D_8018E6D4, (s32) &D_8018E6D4[2], 0xB);
}
break;
case 3:
{
s32 p;
if (*(s32 *)(a0 + 0x1C) >= 0x19) {
s32 r = func_8012B8E4(a0, 4);
p = *(s32 *)(a0 + 0x20);
*(u16 *)(p + 0x12) = *(u16 *)(p + 0x12) + r;
}
if (*(s32 *)(a0 + 0x1C) == 0xC) {
s32 o;
func_8012F214(a0, (s32) D_8018E66C, (s32) &vec[0]);
sp.f6 = 0x20;
sp.f8 = 2;
sp.fA = 0;
sp.f10 = 0;
sp.fE = 0;
sp.f0 = vec[0];
sp.f2 = vec[1];
sp.f4 = vec[2];
sp.fC = *(u16 *)(*(s32 *)(a0 + 0x20) + 0x12);
o = func_8012C51C(&sp, a0);
if (o != 0) {
*(u16 *)(*(s32 *)(o + 0x20) + 0x12) = *(u16 *)(*(s32 *)(a0 + 0x20) + 0x12);
func_8012B2CC(o);
}
} else if (*(s32 *)(a0 + 0x1C) == 0xF) {
func_8018A660(a0, (s32) D_8018E66C);
}
break;
}
}
if (func_8012BEE8(a0) != 0) {
switch (*(u16 *)(a0 + 0x34)) {
case 0:
t = (s32) ((u32) *(u16 *)(a0 + 0x70) << 0x10) >> 0x18;
if (t == 0 || (t >= 3 && t <= 4)) {
if (func_8012BCCC(a0) <= 0x4000) {
*(u16 *)(a0 + 2) = 2;
*(u16 *)(a0 + 0x34) = 1;
func_8012A828(a0, &D_801A629C);
*(s32 *)(a0 + 0x1C) = 0xA;
return;
}
}
break;
case 1:
*(u16 *)(a0 + 2) = 2;
*(u16 *)(a0 + 0x34) = 2;
func_8012A828(a0, &D_801A6754);
*(s32 *)(a0 + 0x1C) = 0x18;
return;
case 2:
break;
case 3:
if (++*(u8 *)(a0 + 0x102) >= 3) {
*(u8 *)(a0 + 0x102) = 0;
*(u16 *)(a0 + 0x34) = *(u16 *)(a0 + 0x34) + 1;
func_8012A828(a0, &D_801A73BC);
} else {
*(u16 *)(a0 + 2) = 2;
*(u16 *)(a0 + 0x34) = 3;
func_8012A828(a0, &D_801A72C4);
}
*(s32 *)(a0 + 0x1C) = 0x1E;
return;
case 4:
if (func_8012BEE8(a0) != 0) {
if (func_8012BCCC(a0) <= 0x40000) {
*(u16 *)(a0 + 2) = 2;
*(u16 *)(a0 + 0x34) = 3;
func_8012A828(a0, &D_801A72C4);
*(s32 *)(a0 + 0x1C) = 0x1E;
}
}
break;
}
*(u16 *)(a0 + 0x5C) = 0xAA10;
*(u16 *)(a0 + 2) = 1;
*(u16 *)(a0 + 0x34) = 2;
*(u16 *)(a0 + 0x5E) = 0;
*(s32 *)(a0 + 0x1C) = 0x1E;
func_8012A828(a0, &D_801A6534);
*(u16 *)(a0 + 0xFC) = 0;
}
}
INCLUDE_ASM("asm/ov_SC02_003/nonmatchings/ov_SC02_003_jr_8017EA84", func_8017F950);
+89 -1
View File
@@ -6871,7 +6871,95 @@ void func_80180F4C(s32 a0) {
}
INCLUDE_ASM("asm/ov_SC03_007/nonmatchings/ov_SC03_007_jr_8017AE2C", func_801810E4);
#include "common.h"
extern void func_8012B1B4(s32 a0, s32 a1);
extern s32 func_8012CBCC(s32 a0);
extern s32 func_8012B744(void *a0, void *a1);
extern s32 func_8012B608(s32 a0, s32 a1, s32 a2);
extern void func_8012A828(s32 a0, void *a1);
extern s32 func_800291B4(s32 arg);
extern void func_800291A0(s32, s32);
extern u8 D_8018C03C[];
extern u16 D_8018C054[];
extern u16 D_8018C05C[];
extern u16 D_8018C064[];
extern u16 D_8018C06C[];
extern u8 D_801B0DD4[];
extern u8 D_801B101C[];
extern s16 D_80126CB4;
extern s16 D_80126CB6;
extern s16 D_80126CB8;
void func_801810E4(s32 a0) {
s32 s0;
s32 v0;
s32 v1;
s32 dx;
s32 dz;
s32 ret;
struct { s16 vx, vy, vz, pad; } vec;
s0 = a0;
func_8012B1B4(s0, (s32)D_8018C03C);
v1 = func_8012CBCC(s0);
if (v1 & 0x6000) {
*(s16 *)(s0 + 0x16) = -4;
}
if (v1 & 0x8000) {
v0 = (*(u16 *)(s0 + 0x104) + 1) & 0x3F;
*(u16 *)(s0 + 0x104) = v0;
if (v0 < 0x1F) {
*(u16 *)(*(s32 *)(s0 + 0x20) + 0x12) = *(u16 *)(*(s32 *)(s0 + 0x20) + 0x12) + 0x200;
} else {
*(u16 *)(*(s32 *)(s0 + 0x20) + 0x12) = *(u16 *)(*(s32 *)(s0 + 0x20) + 0x12) - 0x200;
}
}
if (*(s16 *)(s0 + 0xFC)) {
vec.vx = D_8018C064[*(u8 *)(s0 + 0xFE)] + *(u16 *)(s0 + 0xDC);
vec.vy = 0;
vec.vz = D_8018C06C[*(u8 *)(s0 + 0xFE)] + *(u16 *)(s0 + 0xDE);
} else {
vec.vx = D_8018C054[*(u8 *)(s0 + 0xFE)] + *(u16 *)(s0 + 0xDC);
vec.vy = 0;
vec.vz = D_8018C05C[*(u8 *)(s0 + 0xFE)] + *(u16 *)(s0 + 0xDE);
}
ret = func_8012B744((void *)(s0 + 4), &vec);
ret = func_8012B608(*(s16 *)(*(s32 *)(s0 + 0x20) + 0x12), ret, 4);
*(u16 *)(*(s32 *)(s0 + 0x20) + 0x12) = *(u16 *)(*(s32 *)(s0 + 0x20) + 0x12) + ret;
dx = *(s16 *)(s0 + 6) - vec.vx;
dz = *(s16 *)(s0 + 0xE) - vec.vz;
if (dx * dx + dz * dz < 0x400) {
if (*(s16 *)(s0 + 0xFC) != 0) {
if (*(u8 *)(s0 + 0xFF) != 0) {
*(s16 *)(s0 + 2) = 4;
func_8012A828(s0, D_801B0DD4);
*(s32 *)(s0 + 0x1C) = 0xF;
switch (func_800291B4(0xCC) & 0xFF) {
case 2: func_800291A0(0xCC, 3); break;
case 4: func_800291A0(0xCC, 5); break;
case 6: func_800291A0(0xCC, 7); break;
case 8: func_800291A0(0xCC, 9); break;
case 10: func_800291A0(0xCC, 0xB); break;
case 12: func_800291A0(0xCC, 0xD); break;
}
} else {
*(s16 *)(s0 + 2) = 1;
func_8012A828(s0, D_801B101C);
}
} else {
*(s16 *)(s0 + 0xFC) = *(s16 *)(s0 + 0xFC) + 1;
}
}
D_80126CB4 = *(u16 *)(s0 + 6);
D_80126CB6 = *(u16 *)(s0 + 0xA);
D_80126CB8 = *(u16 *)(s0 + 0xE);
}
#include "common.h"
+165 -1
View File
@@ -3956,7 +3956,171 @@ void func_801848BC(s32 a0) {
}
INCLUDE_ASM("asm/ov_SC03_007/nonmatchings/ov_SC03_007_jr_80183894", func_80184AFC);
#include "common.h"
extern void func_8012A828(s32 a0, void * a1);
extern s32 func_80146A6C(s32 a0, void *a1, s32 a2, s32 a3, s32 a4, s32 a5, s32 a6);
extern void func_801858D4(s32 a0, s16 a1, s16 a2);
extern void func_80185948(s16 *a0);
extern s32 func_8012BB3C(s32 arg0, s32 arg1, u32 arg2, s32 arg3);
extern s32 func_80185DD8(void);
extern s32 func_8012BC60(void *a0, void *a1);
extern s32 func_8012B864(s32 a0);
extern s32 func_8012BD14(s32 a0);
extern void func_8012B200(u8 *a0);
extern void func_80185B48(s32 a0);
extern s32 func_8012BDBC(s32 a0, s32 a1);
extern s32 func_80185A24(s32 a0);
extern unsigned char D_8018C750[];
extern void (*D_8018C588[])(void);
extern void (*D_8018C610[])(void);
extern s32 D_801EB14C;
/*
* Three load-bearing details (byte-proven, single-axis A/B, pinned triple):
*
* 1. `s32 dead[4];` -- cookbook §162i1/§164-53 dead BLKmode local reserving the
* target's vars area (frame 0x48). Same device as func_80184E8C above.
*
* 2. `fire = ret + zr;` with `register s32 zr __asm__("$0");` -- cookbook RC-12's
* pin-free zero-register add. The target keeps a REAL `addu $v0,$s2,$zero`
* copy of the flag at the join before `beqz $v0` (reorg then steals it into the
* two `bnez`/`beqz` delay slots that branch there, so it is worth +2 ins and
* shifts every branch offset in the tail). A plain `if (ret != 0)` -- and a
* plain `fire = ret;` temp -- both lose the copy to cse's canon_reg: 226 ins,
* LENGTH-DRIFT/-2, closeness 69. The `+ zr` add is a real RTL insn cse cannot
* fold away. Pinning `ret` itself to `$18` instead REGRESSES (closeness 77).
*
* 3. `ang = -0xE - spd;` hoisted ABOVE the `*(s16 *)(a0 + 0x104) == 0` guard --
* that source position is what makes gcc emit `addiu $v0,$zero,-0xE` early,
* fill the guard's delay slot with `subu $a1,$v0,$s1`, and re-home the
* func_8012B864 result into $a0 (`addu $a0,$v0,$zero`). Computing it inline at
* the call site instead: OPCODE-MIXED, closeness 12.
* Note the two constants really are different: the 0x12 store takes t - 0x800,
* the func_801858D4 argument takes -0xE - spd.
*/
void func_80184AFC(s32 a0) {
s32 dead[4];
s32 ret;
s32 v;
s32 spd;
s32 t;
s16 rc;
register s32 zr __asm__("$0");
s32 fire;
ret = 0;
if ((*(u16 *)(a0 + 0x5C) & 0x200) != 0) {
if ((s16)func_80185DD8() != 0) {
*(u16 *)(a0 + 0x5C) = *(u16 *)(a0 + 0x5C) & 0xFDFF;
}
}
func_80185A24(a0);
v = *(s32 *)(a0 + 0x1C) - 1;
*(s32 *)(a0 + 0x1C) = v;
if (v != 0) {
if ((v & 3) == 0) {
if (func_8012BC60((void *)(a0 + 4), (void *)&D_801EB14C) < 0x900) {
*(s32 *)(a0 + 0x1C) = 1;
}
}
if (*(s16 *)(a0 + 0x106) == 0) {
s32 r;
s32 p;
s32 ang;
r = func_8012BB3C(a0 + 4, (s32)&D_801EB14C,
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12), 8);
p = *(s32 *)(a0 + 0x20);
*(u16 *)(p + 0x12) = *(u16 *)(p + 0x12) + r;
ang = -6 - *(u16 *)(a0 + 0x104);
func_801858D4(a0, (s16)ang, 0);
}
if (*(s16 *)(a0 + 0x104) != 0) {
if (*(s32 *)(a0 + 0x90) == (s32)&D_8018C610 &&
(u32)*(s32 *)(a0 + 0x94) < 0xB) {
*(s32 *)(a0 + 0x94) = *(s32 *)(a0 + 0x94) + 1;
}
if ((*(s32 *)(a0 + 0x1C) & 3) == 0) {
ret = 1;
}
}
} else {
s16 u;
func_8012B200((u8 *)a0);
func_8012A828(a0, (void *)&D_8018C588);
*(s32 *)(a0 + 0x1C) = 0x14 - (*(s16 *)(a0 + 0x104) << 1);
if (func_8012BD14(a0) <= 0x23FFF) {
*(s16 *)(a0 + 0x102) = 0xA - *(u16 *)(a0 + 0x104);
} else {
*(s16 *)(a0 + 0x102) = 0;
}
u = *(s16 *)(a0 + 0x104);
if (u != 0) {
u = u - 4;
*(s16 *)(a0 + 0x104) = u;
if (u < 0) {
*(s16 *)(a0 + 0x104) = 0;
}
}
*(s16 *)(a0 + 2) = 3;
}
rc = (s16)((s32 (*)(s32))func_80185B48)(a0);
if (rc != 0) {
if (rc < 0) {
return;
}
if (*(s16 *)(a0 + 0xFE) == 0) {
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) = -*(u16 *)(a0 + 0x62);
func_801858D4(a0, -0x1E, 0);
func_80185948((s16 *)a0);
*(s16 *)(a0 + 0x104) = 0xA;
ret = 1;
} else {
*(u16 *)(a0 + 0x5C) = *(u16 *)(a0 + 0x5C) & 0xFDFF;
func_8012B200((u8 *)a0);
func_8012A828(a0, (void *)D_8018C750);
*(s32 *)(a0 + 0x1C) = 0x10;
*(s16 *)(a0 + 2) = 0xA;
return;
}
} else {
s32 d = func_8012BD14(a0);
if (d < 0x10000) {
spd = 0;
if (d >= 0x6400) {
spd = (func_8012BDBC(a0, 0x500) != 0) << 2;
} else if (d >= 0x2400) {
if (func_8012BDBC(a0, 0x680) != 0) {
spd = 7;
}
} else {
spd = 0xA;
}
if (spd != 0) {
s32 ang;
func_80185948((s16 *)a0);
t = func_8012B864(a0);
ang = -0xE - spd;
if (*(s16 *)(a0 + 0x104) == 0) {
ret = 1;
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) = t - 0x800;
}
*(s16 *)(a0 + 0x104) = spd;
func_801858D4(a0, ang, 0);
}
}
}
fire = ret + zr;
if (fire != 0) {
func_80146A6C(2, (void *)a0, 0, 0, 0, 3,
((*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) + 0x800) & 0xFFF) | 0x30009000);
}
}
#include "common.h"
+193 -3
View File
@@ -4247,7 +4247,110 @@ void func_8017F234(s32 a0) {
}
INCLUDE_ASM("asm/ov_SC03_105/nonmatchings/ov_SC03_105_jr_8017C8D0", func_8017F55C);
#include "common.h"
extern s32 rand(void);
extern s32 func_8012BEE8(s32 a0);
extern s32 func_8012CBF4(s32 a0);
extern void func_8012AD80(s32 a0);
extern void func_8012C218(void *a0);
extern void func_8012B260(u8 *a0);
extern void func_8012E88C(u8 *a0);
extern void func_8012EC04(s32 param_1, s32 param_2, s32 *param_3);
extern void func_8012F14C(s32 a0, s32 a1, s32 a2);
extern s32 func_80047948(s32 a0);
extern s32 func_8017FA90(s32 a0, s16 a1, s32 a2);
extern void func_8017FAE8(void *a0);
typedef struct { u16 vx, vy, vz, pad; } UVEC_8017F55C;
void func_8017F55C(s32 a0) {
s32 m1[8];
UVEC_8017F55C in;
UVEC_8017F55C out;
s32 flags;
s32 t;
switch (*(u16 *)(a0 + 0x34)) {
case 0:
if (func_8012BEE8(a0) != 0) {
func_8012EC04(*(s32 *)(a0 + 0x64), 0, (s32 *)m1);
in.vx = *(u16 *)(a0 + 0x6);
in.vy = *(u16 *)(a0 + 0xA);
in.vz = *(u16 *)(a0 + 0xE);
func_8012F14C((s32)m1, (s32)&in, (s32)&out);
*(s16 *)(a0 + 0x6) = out.vx;
*(s16 *)(a0 + 0xA) = out.vy;
*(s16 *)(a0 + 0xE) = out.vz;
func_8012B260((u8 *)a0);
func_8012E88C((u8 *)a0);
*(s32 *)(a0 + 0x1C) = 0x80;
*(u16 *)(a0 + 0x34) += 1;
}
break;
case 1:
if (*(s16 *)(a0 + 0x70) & 0x8000) {
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x10) += *(u16 *)(a0 + 0xFC);
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x12) += *(u16 *)(a0 + 0xFE);
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x14) += *(u16 *)(a0 + 0x100);
}
flags = func_8012CBF4(a0);
if ((flags & 0xFF) == 0x19) {
*(s32 *)(a0 + 0x1C) = 8;
*(u16 *)(a0 + 0x34) += 1;
func_8017FA90(a0, (rand() % 3 + 3) << 12, 0xFFFA0000);
func_8017FAE8((void *)a0);
} else if (flags & 0x2000) {
*(s32 *)(a0 + 0x14) = 0xFFF80000;
*(u16 *)(a0 + 0x34) = 4;
*(s32 *)(a0 + 0x1C) = 0x20;
} else {
if (func_8012BEE8(a0) != 0) {
func_8012C218((void *)a0);
}
}
break;
case 2:
t = func_80047948((*(s32 *)(a0 + 0x1C) << 7) & 0x380);
*(s16 *)(a0 + 0x52) = -((t << 3) >> 12);
if (func_8012BEE8(a0) != 0) {
*(s32 *)(a0 + 0x1C) = 0x18;
*(s32 *)(a0 + 0x48) = 0x2000;
*(s32 *)(a0 + 0x10) = 0;
*(s32 *)(a0 + 0x14) = 0;
*(s32 *)(a0 + 0x18) = 0;
*(u16 *)(a0 + 0x34) += 1;
}
break;
case 3:
func_8012AD80(a0);
if (func_8012BEE8(a0) != 0) {
func_8012C218((void *)a0);
}
break;
case 4:
if (*(s16 *)(a0 + 0x70) & 0x8000) {
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x10) += *(u16 *)(a0 + 0xFC);
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x12) += *(u16 *)(a0 + 0xFE);
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x14) += *(u16 *)(a0 + 0x100);
}
flags = func_8012CBF4(a0);
if ((flags & 0xFF) == 0x19) {
*(s32 *)(a0 + 0x1C) = 8;
*(u16 *)(a0 + 0x34) = 2;
func_8017FA90(a0, (rand() % 3 + 3) << 12, 0xFFFC0000);
func_8017FAE8((void *)a0);
} else if (flags & 0x2000) {
func_8012C218((void *)a0);
} else {
if (func_8012BEE8(a0) != 0) {
func_8012C218((void *)a0);
}
}
break;
}
}
void func_8017F864(void) {
}
@@ -4892,7 +4995,7 @@ INCLUDE_ASM("asm/ov_SC03_105/nonmatchings/ov_SC03_105_jr_8017C8D0", func_80182DC
extern u16 D_801BA628;
extern u16 D_801BA62A;
extern u16 D_801BA62C;
extern void func_801831E0(s32 a0);
extern void func_801831E0();
void func_80183174(s32 a0) {
u16 *p = &D_801BA628;
@@ -4911,7 +5014,94 @@ void func_80183174(s32 a0) {
}
INCLUDE_ASM("asm/ov_SC03_105/nonmatchings/ov_SC03_105_jr_8017C8D0", func_801831E0);
#include "common.h"
extern s32 rand(void);
extern s32 func_801850D8();
void func_801831E0(s32 arg0, s32 arg1) {
extern u16 D_801BA6A0[];
extern u16 D_801BA5E8;
extern u16 D_801BA5EA;
extern u16 D_801BA5EC;
extern s32 D_8018E59C[];
u16 *w;
u16 *e;
u16 *m;
s32 ctr;
s32 q;
s32 ret;
s32 t;
w = D_801BA6A0;
switch (arg1) {
case 0:
ctr = 0x17;
do {
w[0] = *(u16 *)(arg0 + 6);
w[1] = *(u16 *)(arg0 + 0xA);
w[2] = *(u16 *)(arg0 + 0xE);
ctr--;
w -= 4;
} while (ctr >= 0);
break;
case 1:
case 3:
D_801BA5E8 = *(u16 *)(arg0 + 6);
D_801BA5EA = *(u16 *)(arg0 + 0xA);
D_801BA5EC = *(u16 *)(arg0 + 0xE);
ctr = 0x17;
do {
m = w + 1;
e = w + 2;
*w = *(w - 4);
*m = *(w - 3);
*e = *(w - 2);
if ((D_800B99DA & 7) == 0 && (ctr & 1) != 0) {
q = rand() % 4096;
if ((rand() & 1) == 0) {
t = -q;
q = t + 0x4000;
} else {
q = q + 0x4000;
}
ret = func_801850D8(5, (s16)q, 0, 0, w, 0, *(s32 *)(((rand() & 1) << 2) + (s32)D_8018E59C), 0);
if (ret != 0) {
*(s32 *)(ret + 0x54) = arg1 - 1;
*(s32 *)(ret + 0x50) = (s32)w;
*(s32 *)(ret + 0x20) |= 0x200000;
}
}
ctr--;
w -= 4;
} while (ctr > 0);
break;
case 2:
ctr = 0x17;
do {
if ((D_800B99DA & 7) == 0 && (ctr & 1) != 0) {
q = rand() % 4096;
if ((rand() & 1) == 0) {
t = -q;
q = t + 0x4000;
} else {
q = q + 0x4000;
}
ret = func_801850D8(5, (s16)q, 0, 0, w, 0, D_8018E59C[rand() & 1], 0);
if (ret != 0) {
*(s32 *)(ret + 0x50) = (s32)w;
*(s32 *)(ret + 0x54) = arg1;
*(s32 *)(ret + 0x20) |= 0x200000;
}
}
ctr--;
w -= 4;
} while (ctr > 0);
break;
}
}
INCLUDE_ASM("asm/ov_SC03_105/nonmatchings/ov_SC03_105_jr_8017C8D0", func_801834A4);
+1 -1
View File
@@ -2895,7 +2895,7 @@ extern s32 func_8018233C(s32 arg0);
extern u16 D_801BA628;
extern u16 D_801BA62A;
extern u16 D_801BA62C;
extern void func_801831E0(s32 a0);
extern void func_801831E0();
extern void func_80183174(s32 a0);
extern s32 func_801850D8();
extern u8 D_8018E47C[];
+141 -1
View File
@@ -3093,7 +3093,147 @@ void func_80180270(s32 param_1) {
}
INCLUDE_ASM("asm/ov_SC03_110/nonmatchings/ov_SC03_110_jr_8017FBC8", func_8018035C);
/* func_8018035C — ov_SC03_110 / ov_SC03_110_jr_8017FBC8
* 196 ins + a 5-entry compiler jump table (jtbl_801A0D90).
* Body is byte-correct in isolation AND in its real TU (rtu probe: MATCH 196/196).
* The 5 emitted .rodata words resolve to 801803BC/80180460/8018052C/80180588/801805AC,
* i.e. exactly the target's jtbl_801A0D90 entries; the surplus 6th word spimdisasm ran
* into that dlabel is not ours (§131 — the `sltiu 5` is ground truth; the planner clamps it).
* REMAINING BLOCKER IS THE CARVE, NOT THE C: jtbl_801A0D90 is still raw asm in
* asm/ov_SC03_110/data/tail18.data.s, so this needs the gate-time §8a tail carve
* (jtbl_carve --probe verdict: "tail — standard §8a carve at gate time", NOT plan-refused).
* House style per the TU neighbour func_8018076C: block-scope externs + the cast call sites. */
void func_8018035C(s32 param_1)
{
extern void func_80180C40(s32);
extern s32 func_8012CC64(s32 a0, void *a1);
extern s32 func_8012CC1C(s32 a0, void *a1);
extern void func_8012B23C(s32 a0);
extern void func_80131C78(s32 a0);
extern s32 func_80143B6C(s32 a0, s32 a1);
extern void func_80131E00(s32 a0, s32 a1);
extern void func_80180D2C();
extern s32 D_8019C004;
s32 iVar1;
if (*(s16 *)(param_1 + 0xa) >= 0x10) {
((void (*)(void *))func_80180C40)((void *)param_1);
return;
}
switch (*(u16 *)(param_1 + 0x34)) {
case 0:
*(s16 *)(*(s32 *)(param_1 + 0x20) + 0x10) -= 0x100;
iVar1 = func_8012CC64(param_1, &D_8019C004);
if ((iVar1 & 0xff) == 0x1a) {
goto EXIT_80658;
}
if ((iVar1 & 0x2000) != 0) {
*(u16 *)(param_1 + 0x34) += 1;
*(s32 *)(param_1 + 0x1c) = 0;
*(s16 *)(*(s32 *)(param_1 + 0x20) + 0x10) = 0;
goto TAIL;
}
if ((iVar1 & 0x4000) == 0) {
goto L_B0;
}
*(u16 *)(param_1 + 0x34) = 4;
*(s32 *)(param_1 + 0x1c) = 0;
*(s16 *)(*(s32 *)(param_1 + 0x20) + 0x10) = 0;
func_8012B23C(param_1);
goto TAIL;
L_B0:
*(s32 *)(param_1 + 0x1c) += 1;
if (*(s32 *)(param_1 + 0x1c) < 0x3c) {
goto TAIL;
}
*(u16 *)(param_1 + 0x34) = 2;
goto TAIL;
case 1:
*(s32 *)(param_1 + 0x10) = *(s32 *)(param_1 + 0x10) * 15 / 16;
*(s32 *)(param_1 + 0x18) = *(s32 *)(param_1 + 0x18) * 15 / 16;
iVar1 = func_8012CC1C(param_1, &D_8019C004);
if ((iVar1 & 0xff) == 0x1a) {
goto EXIT_80658;
}
if ((iVar1 & 0x6000) != 0) {
goto L_160;
}
*(s32 *)(param_1 + 0x1c) = 0;
*(u16 *)(param_1 + 0x34) += 1;
func_8012B23C(param_1);
goto TAIL;
L_160:
if ((*(s32 *)(param_1 + 0x1c) & 3) == 0) {
func_80143B6C(param_1, 1);
}
*(s32 *)(param_1 + 0x1c) += 1;
if (*(s32 *)(param_1 + 0x1c) < 0x10) {
goto TAIL;
}
goto L_25C;
case 2:
iVar1 = func_8012CC64(param_1, &D_8019C004);
if ((iVar1 & 0x2000) != 0) {
func_80143B6C(param_1, 1);
goto L_25C;
}
if ((iVar1 & 0x4000) == 0) {
goto L_288;
}
*(u16 *)(param_1 + 0x34) = 4;
func_80143B6C(param_1, 1);
func_8012B23C(param_1);
goto TAIL;
case 3:
*(s32 *)(param_1 + 0x1c) += 1;
if (*(s32 *)(param_1 + 0x1c) >= 0x10) {
goto L_25C;
}
goto TAIL;
case 4:
iVar1 = func_8012CC1C(param_1, &D_8019C004);
if ((iVar1 & 0xff) != 0x1a) {
goto L_254;
}
EXIT_80658:
((void (*)(void *))func_80180C40)((void *)param_1);
return;
L_254:
if ((iVar1 & 0x2000) == 0) {
goto L_26C;
}
goto L_25C;
L_25C:
func_80131C78(param_1);
goto TAIL;
L_26C:
if ((*(s32 *)(param_1 + 0x1c) & 3) == 0) {
func_80143B6C(param_1, 1);
}
L_288:
*(s32 *)(param_1 + 0x1c) += 1;
if (*(s32 *)(param_1 + 0x1c) < 0x3c) {
goto TAIL;
}
func_80131E00(param_1, 0xd);
}
TAIL:
((s32 (*)(s32))func_80180D2C)(param_1);
if (0x100000 < *(s32 *)(param_1 + 0x14)) {
*(s32 *)(param_1 + 0x14) = 0x100000;
}
}
extern s32 D_8019BFAC;
extern void func_80180D2C();
+167 -1
View File
@@ -3669,7 +3669,173 @@ u32 func_8017D788(s32 arg0, s16 arg1, s16 arg2) {
}
INCLUDE_ASM("asm/ov_SC03_121/nonmatchings/ov_SC03_121_jr_8017BEBC", func_8017D8D4);
/* func_8017D8D4 -- ov_SC03_121, TU ov_SC03_121_jr_8017BEBC.c. MATCH (212 ins)
*
* Per-frame state machine for an entity: a 5-arm `switch` on the u8 substate at
* +0xC2, dispatched through jtbl_801AD92C (`sltiu $v0,$v1,5` == the entry count,
* §206). Arms 0/1 fall through; arms 1 and 2 end in a byte-identical
* `if (D_801AECD0 & 0x8000)` tail that the source DUPLICATES and gcc's cross_jump
* merges back down to .L8017DAD8 (§298/§5a) -- writing it once with a `goto`
* is unnecessary, the duplicate reproduces the `j .L8017DAD8` exactly.
*
* a0 (bound to s0) : entity pointer.
* +0x02 : s16 state code +0x34 : s16 timer
* +0x06 : s16 pos X +0x3A : s16 home/anchor X
* +0x0A : s16 pos Y +0x3E : s16 home/anchor Y
* +0x0E : s16 pos Z +0x42 : s16 home/anchor Z
* +0x08 : s32 spawn/init flag +0xC2 : u8 substate (switch selector)
* +0x10 : s32 velocity X +0x10A : s16 flag cleared on init
* +0x14 : s32 velocity Y +0x18 : s32 velocity Z
* +0x1C : s32 arm-4 frame counter +0x20 : s32* sub-object (+0x12 = u16 angle)
*
* THREE things the .s forced that the Ghidra seed got wrong:
*
* 1. FRAME SIZE (6 of the 13 first-pass residuals). The target frame is 0x38:
* 16 outgoing-arg bytes + 32 bytes of locals + s0/ra. Three SVECTORs at
* sp+0x10 / +0x18 / +0x20 only account for 24, so a FOURTH 8-byte aggregate
* is declared last (sv3) and never referenced -- gcc-2.7.2 gives every
* aggregate local a frame slot whether or not it is used, and MIPS allocates
* them in declaration order upward from STARTING_FRAME_OFFSET, so a trailing
* dead vector is the only thing that lands 8 unused bytes at sp+0x28.
*
* 2. THE lwl/lwr + swl/swr BLOCK IS A PLAIN STRUCT ASSIGNMENT. `sv2 = sv1` on
* an SVECTOR (4x s16 => size 8, ALIGN 2) cannot use lw/sw, so gcc expands the
* inline unaligned move. Ghidra rendered it as hand-written byte arithmetic
* on `auStack_16 + 1`; that whole block is one `=`.
*
* 3. STATEMENT ORDER IN ARM 0 (the last 7 residuals, one contiguous window with
* an identical multiset == pure sched1, cookbook symptom index L29).
* `*(u8 *)(s0 + 0xC2) = 1;` must come FIRST, before the three vector loads --
* the seed put it between vx and vy, which costs 7. Brute-forcing the four
* legal positions of that one statement through match_one found it in 4 runs.
*
* Decls (law 2): func_8012A828 is copied verbatim from this TU (lines 3675/3808)
* and D_8018D8AC from line 3688 (`extern s32`, addressed as `(s32)&D_8018D8AC`,
* exactly as line 3703 does). The rest are absent from this TU above the splice
* point, so the fleet-consensus spelling is used; where the consensus return type
* is `void` but the .s consumes $v0 (func_8012CC64, func_8012CBF4), the value is
* read through the established cast-the-pointer idiom rather than by contradicting
* the fleet prototype. func_8012B23C is called with NO argument: the .s sets up
* no $a0 for it (no `move $a0,$s0` anywhere before that jal, unlike every other
* call here), so an unspecified-parameter-list decl is required -- §SYS law 4.
* D_801AECD0 has no fleet spelling at all; typed raw from its sw/lw width.
* SVECTOR is typedef'd locally with engine_types.h's exact body so the draft
* compiles standalone; harvest_verify strips it on splice (the TU provides it).
*/
#include "common.h"
extern void func_8012B23C();
extern s32 func_8012DBD0(s32 a0, s32 a1, s32 a2, s32 a3);
extern s32 func_8012CEB0(s32 a0, s32 a1, s32 a2);
extern void func_8012CC64(s32 a0, s32 a1);
extern s32 func_80143B6C(s32 a0, s32 a1);
extern void func_8012CBF4(s32 a0);
extern void func_80131C78(s32 a0);
extern void func_8012A828(s32 a0, s32 a1);
extern s32 D_801AECD0;
extern s32 D_8018D8AC;
void func_8017D8D4(s32 a0) {
s32 s0;
SVECTOR sv0;
SVECTOR sv1;
SVECTOR sv2;
SVECTOR sv3;
s32 iVar1;
s0 = a0;
if (*(s32 *)(s0 + 0x8) > 0) {
*(s16 *)(s0 + 0x6) = -0x103;
*(s16 *)(s0 + 0xA) = -0x182;
*(s16 *)(s0 + 0xE) = 0xE8;
*(s16 *)(s0 + 0x2) = 6;
*(s16 *)(s0 + 0x34) = 0;
*(s16 *)(s0 + 0x10A) = 0;
func_8012B23C();
}
sv0.vx = 0;
sv0.vy = 0x30;
sv0.vz = 0;
func_8012DBD0(s0, 0xA, *(s16 *)(*(s32 *)(s0 + 0x20) + 0x12) + 0x800, 0x1D);
switch (*(u8 *)(s0 + 0xC2)) {
case 0:
*(u8 *)(s0 + 0xC2) = 1;
sv1.vx = *(s16 *)(s0 + 0x3A);
sv1.vy = *(s16 *)(s0 + 0x3E);
sv1.vz = *(s16 *)(s0 + 0x42);
sv2 = sv1;
sv2.vx += sv0.vx;
sv2.vy += sv0.vy;
sv2.vz += sv0.vz;
func_8012CEB0((s32)&sv1, (s32)&sv2, 1);
sv2.vx -= sv0.vx;
sv2.vy -= sv0.vy;
sv2.vz -= sv0.vz;
*(s16 *)(s0 + 0x3A) = sv2.vx;
*(s16 *)(s0 + 0x3E) = sv2.vy;
*(s16 *)(s0 + 0x42) = sv2.vz;
*(s16 *)(s0 + 0x6) = sv2.vx;
*(s16 *)(s0 + 0xA) = sv2.vy;
*(s16 *)(s0 + 0xE) = sv2.vz;
/* fallthrough */
case 1:
D_801AECD0 = ((s32 (*)(s32, SVECTOR *))func_8012CC64)(s0, &sv0);
if ((D_801AECD0 & 0x2000) != 0) {
*(u8 *)(s0 + 0xC2) = 2;
func_80143B6C(s0, 1);
*(s32 *)(s0 + 0x14) = 0xFFF30000;
}
if ((D_801AECD0 & 0x8000) != 0) {
*(u8 *)(s0 + 0xC2) = 3;
func_8012A828(s0, (s32)&D_8018D8AC);
}
break;
case 2:
D_801AECD0 = ((s32 (*)(s32, SVECTOR *))func_8012CC64)(s0, &sv0);
if ((D_801AECD0 & 0x2000) != 0) {
func_80143B6C(s0, 1);
*(s32 *)(s0 + 0x14) = 0xFFF60000;
*(u8 *)(s0 + 0xC2) = 3;
}
if ((D_801AECD0 & 0x8000) != 0) {
*(u8 *)(s0 + 0xC2) = 3;
func_8012A828(s0, (s32)&D_8018D8AC);
}
break;
case 3:
*(s32 *)(s0 + 0x10) = *(s32 *)(s0 + 0x10) * 0xF / 0x10;
*(s32 *)(s0 + 0x18) = *(s32 *)(s0 + 0x18) * 0xF / 0x10;
D_801AECD0 = ((s32 (*)(s32))func_8012CBF4)(s0);
if ((D_801AECD0 & 0x2000) != 0) {
*(u8 *)(s0 + 0xC2) = 4;
*(s32 *)(s0 + 0x14) = 0;
*(s32 *)(s0 + 0x1C) = 0;
func_80143B6C(s0, 1);
}
break;
case 4:
*(s32 *)(s0 + 0x10) = *(s32 *)(s0 + 0x10) * 0xF / 0x10;
*(s32 *)(s0 + 0x18) = *(s32 *)(s0 + 0x18) * 0xF / 0x10;
func_8012CBF4(s0);
if ((*(s32 *)(s0 + 0x1C) & 3) == 3) {
func_80143B6C(s0, 1);
}
iVar1 = *(s32 *)(s0 + 0x1C) + 1;
*(s32 *)(s0 + 0x1C) = iVar1;
if (iVar1 > 0x10) {
func_80131C78(s0);
}
break;
}
}
extern void func_8012CBCC(s32 a0);
extern void func_8012A828(s32 a0, s32 a1);
+107 -1
View File
@@ -4168,7 +4168,113 @@ void func_80180B1C(s32 a0) {
}
INCLUDE_ASM("asm/ov_SC03_121/nonmatchings/ov_SC03_121_jr_8017E1D0", func_80180E64);
/* ---- decls copied verbatim from the destination TU (wave law 2) ---------- */
extern u8 D_80078E78[]; /* TU line 390 */
extern s32 D_801151FC; /* TU line 735 */
extern s32 D_80126B58; /* TU line 53 */
extern s32 rand(void); /* TU line 954 */
extern void func_800D0C48(s32 a0); /* TU line 1466 */
extern s32 func_801726AC(s32 *a0); /* TU line 2221 */
extern int func_80178970(void); /* TU line 2533 */
extern s32 func_80178B18(s32 param_1, s32 param_2); /* TU line 2534 */
extern void func_80178D18(void); /* TU line 2541 */
extern int func_8001AAA0(void); /* TU line 2586 */
void func_80180E64(s32 a0) {
extern s32 D_801AECD8[]; /* 5 entity pointers, stride 4 */
extern s32 D_801AECF0; /* single entity pointer */
extern s16 D_8019BBF8; /* param block passed to func_80178B18 */
u8 *p = D_80078E78;
s16 c0;
register s32 f __asm__("$3");
s32 i0;
s32 i1;
s32 i2;
s32 i3;
s32 r;
s32 d;
switch (*(u16 *)(a0 + 0x34)) {
case 0:
if ((rand() & 0x3F) == 0) {
r = rand() % 5;
if (*(u16 *)(D_801AECD8[r] + 2) == 1) {
*(s16 *)(D_801AECD8[r] + 0x10A) = 4;
}
}
if (*(s32 *)(a0 + 0x1C) != 0) {
*(s32 *)(a0 + 0x1C) -= 1;
} else {
c0 = 0;
for (i0 = 0; i0 < 5; i0++) {
if (*(s16 *)(D_801AECD8[i0] + 0x10A) != 0 && *(u8 *)(D_801AECD8[i0] + 0xC1) != 3) {
c0++;
}
}
if (c0 < 3) {
r = rand() % 5;
if (*(u16 *)(D_801AECD8[r] + 2) == 1) {
*(s16 *)(D_801AECD8[r] + 0x10A) = 1;
d = 0x1A4 - *(s16 *)(p + 0x1A);
*(s32 *)(a0 + 0x1C) = d;
if (d < 1) {
*(s32 *)(a0 + 0x1C) = 1;
}
}
}
}
if (*(s16 *)(p + 0x1A) > 0x1A2) {
func_800D0C48(1);
}
if (*(s16 *)(p + 0x1A) > 0x1A3 && func_801726AC(&D_80126B58) == 0) {
*(u16 *)(a0 + 0x34) += 1;
}
break;
case 1:
f = 0;
/* §NNN: the zero-byte `"r"(i1)` keepalive adds the 5th reference to the
loop counter, which lifts its global_alloc priority above the
strength-reduced pointer giv's -- that is what puts the counter in
$a0 and the giv in $a1 (without it they swap). Emits no bytes. */
for (i1 = 0; i1 < 5; i1++) {
__asm__ __volatile__("" :: "r"(i1));
if (*(u16 *)(D_801AECD8[i1] + 2) == 5) {
f = 1;
}
}
if (D_801151FC == 0 && f != 1) {
func_80178B18(a0, (s32)&D_8019BBF8);
for (i2 = 0; i2 < 5; i2++) {
*(s16 *)(D_801AECD8[i2] + 0x10A) = 5;
*(s16 *)(D_801AECD8[i2] + 0x5C) = 0;
*(u8 *)(D_801AECD8[i2] + 0xC1) = 0;
}
*(u16 *)(a0 + 0x34) += 1;
*(s16 *)(D_801AECF0 + 2) = 6;
*(s16 *)(a0 + 0x100) = 1;
((void (*)(s32))func_8001AAA0)(0x42);
}
break;
case 2:
D_801151FC = 0;
if (((s32 (*)(s32))func_80178970)(a0) != 0) {
((void (*)(s32))func_80178D18)(a0);
*(u16 *)(a0 + 0x34) = 0;
*(u16 *)(a0 + 2) += 1;
}
break;
}
if (D_801151FC != 0) {
for (i3 = 0; i3 < 5; i3++) {
*(s16 *)(D_801AECD8[i3] + 0x10A) = 3;
}
}
}
extern void (*D_8019BC80[])(void);
+104 -1
View File
@@ -5184,7 +5184,110 @@ void func_8017F8A0(int param_1)
}
INCLUDE_ASM("asm/ov_SC04_000/nonmatchings/ov_SC04_000_jr_8017BEBC", func_8017F98C);
extern s32 func_8012B744(s32 a0, s32 a1);
extern s32 func_8012B608(s32 a0, s32 a1, s32 a2);
extern void func_8012B2CC(s32 a0);
extern void func_8012B1B4(s32 a0, s32 a1);
extern void func_8012A828(s32, s32);
extern s32 func_8012CBA4(s32 a0);
extern s32 func_8012BA10(s32 a0, s32 a1);
extern void func_800D0C48(s32 a0);
extern void func_8002AC00(s32 arg0);
extern int func_8001AAA0(void);
extern s32 func_801789AC(s32 arg0);
extern void func_80178D18(void);
extern void func_80029514(s32);
extern void func_8012A568(void (*a0)(void));
extern void func_8012C218(void *a0);
extern u8 D_801995A4[];
extern u8 D_801995AC[];
extern u8 D_8019CF08[];
extern u8 D_8019CF90[];
void func_8017ECC8(void);
void func_8017F98C(s32 a0) {
s32 r;
switch (*(u16 *)(a0 + 0x34)) {
case 0:
break;
case 1:
r = func_8012B744(a0 + 4, (s32)D_801995A4);
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) =
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x12)
+ func_8012B608(*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12), r, 4);
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) = *(u16 *)(*(s32 *)(a0 + 0x20) + 0x12) & 0xFFF;
*(s32 *)(a0 + 0x1C) = *(s32 *)(a0 + 0x1C) - 1;
if (*(s32 *)(a0 + 0x1C) == 0) {
*(s16 *)(a0 + 0x34) = *(u16 *)(a0 + 0x34) + 1;
func_8012B2CC(a0);
func_8012B1B4(a0, (s32)D_801995AC);
*(s32 *)(a0 + 0x1C) = 0xF;
func_8012A828(a0, (s32)D_8019CF08);
}
break;
case 2:
func_8012CBA4(a0);
break;
case 3:
func_8012CBA4(a0);
*(s32 *)(a0 + 0x1C) = *(s32 *)(a0 + 0x1C) - 1;
if (*(s32 *)(a0 + 0x1C) == 0) {
*(s32 *)(a0 + 0x1C) = 0xF;
*(s16 *)(a0 + 0x34) = *(u16 *)(a0 + 0x34) + 1;
func_8012A828(a0, (s32)D_8019CF90);
}
break;
case 4:
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) =
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x12) + func_8012BA10(a0, 4);
break;
case 5:
r = func_8012B744(a0 + 4, (s32)D_801995A4);
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) =
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x12)
+ func_8012B608(*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12), r, 4);
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) = *(u16 *)(*(s32 *)(a0 + 0x20) + 0x12) & 0xFFF;
*(s32 *)(a0 + 0x1C) = *(s32 *)(a0 + 0x1C) - 1;
if (*(s32 *)(a0 + 0x1C) == 0) {
*(s16 *)(a0 + 0x34) = *(u16 *)(a0 + 0x34) + 1;
func_8012B2CC(a0);
func_8012B1B4(a0, (s32)D_801995AC);
func_8012A828(a0, (s32)D_8019CF08);
}
break;
case 6:
func_8012CBA4(a0);
if (*(s16 *)(a0 + 0xE) < -0x398) {
*(s16 *)(a0 + 0xE) = -0x600;
*(s16 *)(a0 + 0x34) = *(u16 *)(a0 + 0x34) + 1;
func_800D0C48(1);
*(s32 *)(a0 + 0x1C) = 0x1E;
func_8002AC00(0x17);
}
break;
case 7:
*(s32 *)(a0 + 0x1C) = *(s32 *)(a0 + 0x1C) - 1;
if (*(s32 *)(a0 + 0x1C) == 0) {
*(s16 *)(a0 + 0x34) = 0;
((int (*)(s32))func_8001AAA0)(0x55);
*(u16 *)(a0 + 0xFC) |= 1;
}
break;
}
if (*(s16 *)(a0 + 0xFC) < 2 && func_801789AC(a0) != 0) {
((void (*)(s32))func_80178D18)(a0);
func_80029514(0x2F8);
*(u16 *)(a0 + 0xFC) |= 2;
func_8012A568(func_8017ECC8);
}
if (*(s16 *)(a0 + 0xFC) == 3) {
func_8012C218((void *)a0);
}
}
extern void (*D_80199760[])(void);
+122 -1
View File
@@ -6034,7 +6034,128 @@ void func_801826E4(s32 param_1)
}
INCLUDE_ASM("asm/ov_SC04_011/nonmatchings/ov_SC04_011_jr_8017D494", func_801827DC);
void func_801827DC(s32 param_1)
{
extern void func_80186C1C(void);
extern void func_80183F10(void);
extern void func_8018BA9C(void);
extern void func_80183EA8(void);
extern void func_8018BAC4(void);
extern void func_80182D34(s32 a0);
extern void func_8018AC00(void *a0);
extern void func_8012BEE8(u8 *a0);
extern void func_8013C9C4(void *a0);
extern void func_8018637C(s32 arg0, s32 arg1);
extern void func_8002D4C8(s32 a0, s32 a1);
extern void func_8018B9D4();
extern void func_80182AF8();
/* §183: the TU spells D_80194500 as a flat void*[] elsewhere; reach the
row-of-3 view through an __asm__ label alias -- the TU's own idiom. */
extern void *a4500[][3] __asm__("D_80194500");
extern s32 aFC4C[] __asm__("D_801EFC4C");
extern s32 D_801EFC54;
extern s32 D_801EFC5C;
extern s32 D_801EFC60;
extern s32 D_801EFC64[];
extern s32 D_801EFC68;
extern s32 D_801EFD28;
extern u16 D_801EFD40;
extern u8 D_80190B88[];
s32 r;
s32 obj;
u16 t;
u16 f;
switch (*(u16 *)(param_1 + 0x34)) {
case 0:
case 1:
if (*(s16 *)(param_1 + 0x98) == 0) {
func_8018637C(param_1, (s32)a4500[*(s16 *)(param_1 + 0xE2)][*(u16 *)(param_1 + 0x34) + 1]);
goto incr;
}
goto draw;
case 2:
if (*(s32 *)(param_1 + 0x94) != 0xB) {
goto draw;
}
func_80186C1C();
*(s16 *)(param_1 + 0x76) = 0x64;
*(s32 *)(param_1 + 0x1C) = 0x80;
*(s16 *)(param_1 + 0xF2) = 1;
*(s16 *)(param_1 + 0xE2) = (s16)*(u16 *)(param_1 + 0xE2) >> 1;
func_8013C9C4(D_80190B88);
func_8018AC00((void *)aFC4C[0]);
func_8018AC00((void *)D_801EFC54);
func_8018AC00((void *)D_801EFC5C);
func_8018AC00((void *)D_801EFC60);
func_8018AC00((void *)D_801EFC64[0]);
func_8018AC00((void *)D_801EFC68);
func_8002D4C8(0x907, 0);
incr:
*(u16 *)(param_1 + 0x34) = *(u16 *)(param_1 + 0x34) + 1;
draw:
func_8018B9D4(D_801EFC54, *(s32 *)(param_1 + 0xD0));
return;
case 3:
if (*(s16 *)(param_1 + 0x76) == 0) {
t = *(u16 *)(param_1 + 0xF6) - 1;
*(u16 *)(param_1 + 0xF6) = t;
*(s16 *)&D_801EFD28 = (s16)t * 100;
func_80183F10();
obj = *(s32 *)(param_1 + 0xD0);
if (obj != 0) {
*(u16 *)(obj + 0x1A) = 0x800;
*(u16 *)(obj + 0x18) = 0x800;
}
func_8018BA9C();
*(u16 *)(param_1 + 0x34) = *(u16 *)(param_1 + 0x34) + 1;
if (*(s16 *)(param_1 + 0xF6) == 0) {
f = D_801EFD40;
*(s32 *)(param_1 + 0x1C) = 8;
D_801EFD40 = f | 0x100;
return;
}
*(s32 *)(param_1 + 0x1C) = 0x10;
return;
}
r = ((s32 (*)(s32))func_8012BEE8)((s32)param_1);
if (r == 0) {
if (((*(s32 *)(param_1 + 0x1C) & 0xF) == 0) && (*(s16 *)(param_1 + 0xF2) != 0)) {
*(s16 *)(param_1 + 0xF2) = *(s16 *)(param_1 + 0xF2) - 1;
func_8013C9C4(D_80190B88);
}
func_8018B9D4(D_801EFC54, *(s32 *)(param_1 + 0xD0));
if ((*(s32 *)(param_1 + 0x1C) & 1) != 0) {
return;
}
func_80183EA8();
return;
}
goto L_af8;
case 4:
r = ((s32 (*)(s32))func_8012BEE8)((s32)param_1);
if (r != 0) {
if (*(s16 *)(param_1 + 0xF6) == 0) {
func_80182D34(param_1);
return;
}
L_af8:
func_80182AF8(param_1);
return;
}
obj = *(s32 *)(param_1 + 0xD0);
if (obj != 0) {
t = *(u16 *)(obj + 0x18) + 0x600;
*(u16 *)(obj + 0x18) = t;
*(u16 *)(obj + 0x1A) = t;
}
func_8018BAC4();
return;
default:
return;
}
}
void func_80182AF8(s32 a0) {
extern void func_80186EBC();
+106 -1
View File
@@ -4885,7 +4885,112 @@ void func_8017E4E4(void *a0) {
}
INCLUDE_ASM("asm/ov_SC04_015/nonmatchings/ov_SC04_015_jr_8017AE2C", func_8017E520);
extern void func_8001D074(s32, s32);
extern void func_8001CB00(s32 a0, void *a1, s32 a2, s32 a3);
extern void func_80128EA8(s32 a0, s32 a1, s32 a2);
extern s32 func_80128ED8(s32 param_1, s32 *param_2);
extern s32 func_8004787C(s32 a0);
extern s32 func_80047948(s32 a0);
extern void func_8017E830(s32 a0);
extern u8 D_801885C8[];
extern u8 D_801885D4[];
extern s32 D_801C8B6C;
extern s16 D_801C8B70;
extern s16 D_801C8B74;
void func_8017E520(s32 a0) {
s32 p;
s32 q;
s32 u;
s32 g;
s16 t;
switch ((s16)(*(u16 *)(a0 + 0) - 1)) {
case 0:
p = ((s32 (*)(s32, s32))func_8001D074)(0x3E, 0x7D);
*(s32 *)(a0 + 4) = p;
func_8001CB00(p, D_801885C8, 0x340, 0x100);
*(u8 *)(*(s32 *)(a0 + 4) + 0x27) = 0x2F;
*(s32 *)(*(s32 *)(a0 + 4) + 4) |= 0x50000000;
*(s16 *)(*(s32 *)(a0 + 4) + 0x2C) = 2;
func_80128EA8(*(s32 *)(a0 + 4), a0 + 8, (s32)D_801885D4);
*(s16 *)(a0 + 0x14) = -0x5C;
*(s16 *)(a0 + 0x10) = (*(s16 *)(a0 + 0x18) - 4) * 24 + 0x18;
*(s16 *)(*(s32 *)(a0 + 4) + 0x14) = 0x400;
*(s16 *)(a0 + 0) = 4;
*(s16 *)(a0 + 0xC) = *(u16 *)(a0 + 0x18) & 7;
*(s16 *)(a0 + 2) = *(s16 *)(a0 + 0x18) * 4;
break;
case 1:
if (D_801C8B6C == 0) {
*(s16 *)(a0 + 2) = 8;
*(s16 *)(a0 + 0) = 3;
} else {
t = *(u16 *)(a0 + 2) + 1;
*(s16 *)(a0 + 2) = t;
*(s16 *)(a0 + 0x16) = (u32)func_8004787C((t & 0x3F) << 6) >> 10;
*(s16 *)(a0 + 0x12) = (u32)func_80047948((*(u16 *)(a0 + 2) & 0x3F) << 6) >> 11;
}
break;
case 3:
if (D_801C8B6C == 1) {
*(s16 *)(a0 + 2) = 8;
*(s16 *)(a0 + 0) = 5;
} else {
t = *(u16 *)(a0 + 2) + 1;
*(s16 *)(a0 + 2) = t;
*(s16 *)(a0 + 0x16) = (u32)func_8004787C((t & 0x3F) << 6) >> 10;
*(s16 *)(a0 + 0x12) = (u32)func_80047948((*(u16 *)(a0 + 2) & 0x3F) << 6) >> 11;
*(s16 *)(a0 + 0x16) = *(u16 *)(a0 + 0x16) - 0x40;
}
break;
case 2:
*(s16 *)(a0 + 0x16) = *(u16 *)(a0 + 0x16) - 8;
t = *(u16 *)(a0 + 2) - 1;
*(s16 *)(a0 + 2) = t;
if (t <= 0) {
*(s16 *)(a0 + 2) = 0;
*(s16 *)(a0 + 0) = 4;
}
break;
case 4:
*(s16 *)(a0 + 0x16) = *(u16 *)(a0 + 0x16) + 8;
t = *(u16 *)(a0 + 2) - 1;
*(s16 *)(a0 + 2) = t;
if (t <= 0) {
*(s16 *)(a0 + 2) = 0;
*(s16 *)(a0 + 0) = 2;
}
break;
case 5:
*(s16 *)(a0 + 0) = 7;
*(s16 *)(a0 + 2) = 0x20;
case 6:
t = *(u16 *)(a0 + 2) - 1;
*(s16 *)(a0 + 2) = t;
u = t;
if (u <= 0) {
g = D_801C8B70;
*(s16 *)(a0 + 2) = 0;
*(s16 *)(a0 + 0) = 0;
if (g == 0) {
D_801C8B74 = 1;
}
} else {
q = *(s32 *)(a0 + 4);
*(s16 *)(q + 0x1A) = u << 7;
*(s16 *)(q + 0x18) = u << 7;
*(s16 *)(a0 + 0x12) = (func_80047948((*(u16 *)(a0 + 2) & 0x1F) << 8) * 5) >> 12;
}
break;
}
func_80128ED8(*(s32 *)(a0 + 4), (s32 *)(a0 + 8));
*(s16 *)(*(s32 *)(a0 + 4) + 8) = *(u16 *)(a0 + 0x10) + *(u16 *)(a0 + 0x12);
*(s16 *)(*(s32 *)(a0 + 4) + 0xA) = *(u16 *)(a0 + 0x14) + *(u16 *)(a0 + 0x16);
func_8017E830(a0);
}
extern s32 AddPrim(s32, void *);
extern void *func_80010A08(s32);
+193 -1
View File
@@ -3327,7 +3327,199 @@ void func_8017D0EC(s32 *a0) {
}
INCLUDE_ASM("asm/ov_SC04_016/nonmatchings/ov_SC04_016_jr_8017BEBC", func_8017D118);
#include "common.h"
extern void func_8012C1B8(void);
extern void func_8001C2C4(s32);
extern s32 func_8012C51C(void *arg0, s32 arg1);
extern void func_8001C810(s32 a0, s32 a1);
extern s32 func_8001CA88(s32 a0, void *a1);
extern void func_8001C214(s32 a0, s32 a1);
extern void func_80143994(s32 a0, s32 a1);
extern s32 func_8012A828(void *a0, void *a1);
extern void func_800233CC(void *, unsigned short);
extern void func_8002D4C8(s32 a0, s32 a1);
extern void func_8017DF68(void);
extern void func_8017E6A0(void *a0);
extern s32 D_80190580;
extern u8 D_8018490C;
extern s16 D_80198108;
extern s32 D_801840EC;
extern s32 D_8019E610;
extern s32 D_8018445C;
extern s32 D_801A1CA0;
extern s32 D_80184724;
extern s32 D_801A33C0;
extern s32 D_80180328;
extern unsigned char D_801A6B00;
extern unsigned char D_801A6B01;
extern unsigned char D_801A6B02;
extern unsigned char D_801A6B04;
extern unsigned char D_801A6B05;
extern unsigned char D_801A6B06;
typedef struct {
s16 f0;
s16 f1;
s16 f2;
s16 f3;
s16 f4;
s16 f5;
s16 f6;
s16 f7;
s32 f8;
} St_8017D118;
void func_8017D118(s32 a0) {
St_8017D118 st;
s32 state;
s32 p2;
s32 p3;
s32 val;
s32 t;
unsigned char *pk;
if (*(s16 *)(a0 + 0x70) & 0x8000) {
t = ((s32 (*)(void))func_8012C1B8)();
*(s32 *)(a0 + 0x20) = t;
if (t == 0) {
return;
}
func_8001C2C4(t);
st.f3 = 0x337;
st.f5 = 0;
st.f6 = 0;
st.f7 = 0;
st.f8 = 0;
if (*(s32 *)(a0 + 0xCC) == 0) {
st.f4 = 0;
st.f0 = -0x100;
st.f1 = -0x202;
st.f2 = 0;
*(s32 *)(a0 + 0xCC) = func_8012C51C(&st, a0);
}
if (*(s32 *)(a0 + 0xD4) == 0) {
st.f4 = 2;
st.f0 = -0xF8;
st.f1 = -0x502;
st.f2 = 0x60;
*(s32 *)(a0 + 0xD4) = func_8012C51C(&st, a0);
}
if (*(s32 *)(a0 + 0xD0) == 0) {
st.f4 = 1;
st.f0 = 0x1C0;
st.f1 = -0x202;
st.f2 = 0x160;
*(s32 *)(a0 + 0xD0) = func_8012C51C(&st, a0);
}
if (*(s32 *)(a0 + 0xD8) == 0) {
st.f4 = 3;
st.f0 = -0x100;
st.f1 = -0x202;
st.f2 = 0x60;
*(s32 *)(a0 + 0xD8) = func_8012C51C(&st, a0);
}
if (*(s32 *)(a0 + 0xF8) == 0) {
st.f4 = 4;
st.f0 = -0x100;
st.f1 = -0x202;
st.f2 = 0x60;
*(s32 *)(a0 + 0xF8) = func_8012C51C(&st, a0);
}
if (*(s32 *)(a0 + 0xF4) == 0) {
st.f4 = 5;
st.f0 = -0x100;
st.f1 = -0x252;
st.f2 = 0x60;
*(s32 *)(a0 + 0xF4) = func_8012C51C(&st, a0);
}
if (*(s32 *)(a0 + 0xCC) != 0 && *(s32 *)(a0 + 0xD0) != 0 &&
*(s32 *)(a0 + 0xD4) != 0 && *(s32 *)(a0 + 0xD8) != 0 &&
*(s32 *)(a0 + 0xF8) != 0 && *(s32 *)(a0 + 0xF4) != 0) {
*(u16 *)(a0 + 2) = *(u16 *)(a0 + 2) + 1;
}
} else {
t = ((s32 (*)(void))func_8012C1B8)();
*(s32 *)(a0 + 0x20) = t;
if (t == 0) {
return;
}
switch (*(s16 *)(a0 + 0x70)) {
case 0:
p3 = (s32)&D_80190580;
p2 = (s32)&D_8018490C;
val = 0xC80;
state = 5;
break;
case 1:
p3 = (s32)&D_80198108;
p2 = (s32)&D_801840EC;
val = 0;
state = 6;
break;
case 2:
p3 = (s32)&D_8019E610;
p2 = (s32)&D_8018445C;
val = 0;
state = 7;
break;
case 3:
p3 = (s32)&D_801A1CA0;
p2 = (s32)&D_80184724;
val = 0;
func_8001C810(*(s32 *)(a0 + 0x20), p3);
*(s32 *)(*(s32 *)(a0 + 0x20) + 4) |= 0x50000000;
state = 8;
break;
case 4:
p3 = (s32)&D_801A33C0;
p2 = (s32)&D_80180328;
val = 0xC00;
func_8001C810(*(s32 *)(a0 + 0x20), p3);
*(s32 *)(*(s32 *)(a0 + 0x20) + 4) |= 0x70000000;
state = 9;
break;
case 5:
pk = &D_801A6B00;
D_801A6B02 = 0x20;
*pk = 0x20;
D_801A6B01 = 0x80;
D_801A6B04 = D_801A6B05 = D_801A6B06 = 0;
func_800233CC(pk, 0x30);
func_8001CA88(*(s32 *)(a0 + 0x20), pk);
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x1A) = 0x2000;
*(s32 *)(*(s32 *)(a0 + 0x20) + 4) |= 0x50000000;
val = 0;
p2 = 0;
state = 0xA;
break;
case 6:
func_8017DF68();
func_8017E6A0((void *)a0);
func_8002D4C8(0xB90, 0);
state = 0xC;
break;
case 7:
func_8001C2C4(*(s32 *)(a0 + 0x20));
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) = 0xC00;
state = 0xD;
break;
}
if (*(s16 *)(a0 + 0x70) < 6) {
if (*(s16 *)(a0 + 0x70) < 3) {
func_8001C214(*(s32 *)(a0 + 0x20), p3);
func_80143994(a0, 0x3000);
}
if (p2 != 0) {
func_8012A828((void *)a0, (void *)p2);
}
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) = val;
}
*(s16 *)(a0 + 2) = state;
}
}
void func_8017D588(void *a0) {
extern s32 func_800149E0(s32);
+200 -1
View File
@@ -3192,7 +3192,206 @@ void func_80183BB0(s32 param_1)
}
INCLUDE_ASM("asm/ov_SC05_001/nonmatchings/ov_SC05_001_jr_80183508", func_80183C9C);
#include "common.h"
/* func_80183C9C — ov_SC05_001 `_jr_80183508`, 196 ins, frame 0x18. MATCH (match_one, masked).
*
* .venv/bin/python tools/match_one.py func_80183C9C \
* --c .run/pool_1/opus/func_80183C9C.c \
* --asm-subdir asm/ov_SC05_001/nonmatchings/ov_SC05_001_jr_80183508
*
* Enemy state machine — the SAME shape as func_80183508 in this very TU (:2839):
* the `if (*(s16 *)(p+0xa) >= 0x10) { func_80184580(p); return; }` guard, a 5-entry
* jump table over `*(u16 *)(p + 0x34)`, the goto-label idiom, and the 0x100000 clamp
* tail. This one's tail additionally calls func_8018466C(p) before the clamp, and
* the default arm falls straight into it.
*
* jtbl_801B4850 (asm/ov_SC05_001/data/tail18.data.s:9) — minval 0 / maxval 4, no
* holes, default -> TAIL. Its five words are in strictly ASCENDING address order
* (80183CFC / DA0 / E6C / EC8 / EEC), so the arms are emitted in case order 0..4
* and the source case order is the literal one.
*
* Four labels are reached from more than one arm and therefore MUST be written as
* gotos at exactly these source positions or the block order drifts:
* EXIT (.L80183F10, from cases 0/1 and case 4) -> func_80184580(p); return;
* HITSTUN (.L80183F28, from cases 1/2/3 and case 4) -> func_80131C78(p);
* L_F54 (.L80183F54, from case 2 and case 4)
* TAIL (.L80183F78, from every arm and the default)
* Per §162 the surviving copy of a merged tail is the LATER one, and every one of
* these `j`s is FORWARD into the last-emitted arm (case 4) — consistent with the
* canonical copy living inside case 4, which is how it is spelled below.
*
* ---- THE ONE LEVER (90 mismatched / LENGTH-DRIFT -7 -> MATCH) ---------------
* COOKBOOK §5a — cross-jump tail-merge, and it fires in the direction §5a warns
* about: MY build was SHORTER than the target. Case 1's counter tail
* x = ++p->0x1c; if (x < 0x10) goto TAIL; goto HITSTUN;
* is byte-identical to the WHOLE of case 3's body — same 9 instructions, same two
* exit labels — so gcc-2.7.2's `find_cross_jump` merged them (one copy survives,
* the other arm gets a `j` + delay nop: 18 -> 11, exactly the -7 drift). The
* original binary keeps BOTH copies. There is no `-fno-crossjumping` before gcc
* 3.3, so the only lever is §5a's zero-byte barrier: `find_cross_jump` sets
* `lose = 1` on ANY volatile asm, so one empty `__asm__ __volatile__("")` inside
* one twin makes the two RTL streams unequal and both copies survive.
*
* PLACEMENT IS LOAD-BEARING, and this is the part §5a does not spell out. The
* barrier must sit at the very END of the twin, immediately before the shared
* `goto TAIL` — i.e. INSIDE the `if`. find_cross_jump walks the two streams
* BACKWARD from the converging `j`, so a barrier at the TOP of the block is walked
* past: the seven insns below it still match and gcc merges those instead, leaving
* the drift only slightly smaller. Put at the bottom the walk fails at offset 0
* and the suffix never reaches §50-B's `minimum` floor. Plain `("")` is used, not
* `("" ::: "memory")` — §5a's own note — because the memory clobber would pin the
* store ordering in the arms that schedule `sw 0x1c` against `sh 0x34`.
* Cost: zero bytes. A future reader WILL try to delete it; it is worth 7 ins.
*
* INTEGRATION SURFACE (§161c) — every block-scope decl below AGREES with this TU:
* func_80184580 DEFINED here `void (s32)` TU:3482 (+ file-scope decl TU:3457)
* — note func_80183508 (TU:2841) spells it `void (void *)` at ITS
* own block scope; block scopes do not conflict, and the (s32)
* spelling is the one that agrees with the definition.
* func_8018466C file-scope `s32 ()` TU:3150/3198 (unspecified — §195-A,
* never "fix" it; redeclared here exactly as func_801840AC does)
* func_8012CC64 block-scope `s32 (s32,void*)` TU:3253
* func_8012CC1C block-scope `s32 (s32,void*)` TU:3254
* func_8012B23C block-scope `void (s32)` TU:3256
* func_80131C78 block-scope `void (s32)` TU:3257
* func_80143B6C block-scope `s32 (s32,s32)` TU:3258
* func_80131E00 block-scope `void (s32,s32)` TU:3259 (file-scope `void ()` at
* TU:2781/3146 — compatible, C89 unspecified-vs-prototype)
* D_801AE3A8 block-scope `s32` TU:3260, passed as &D_801AE3A8
*
* SYMBOL AUDIT (law 1c — match_one masks jal/HI16/LO16, so this was checked by
* hand AND by diffing the object's reloc order against the target's):
* 80184580 jtbl D_801AE3A8 8012CC64 8012B23C | D_801AE3A8 8012CC1C 8012B23C
* 80143B6C | D_801AE3A8 8012CC64 80143B6C 80143B6C 8012B23C | D_801AE3A8
* 8012CC1C 80184580 80131C78 80143B6C 80131E00 8018466C — identical, in order.
*/
void func_80183C9C(s32 param_1)
{
extern void func_80184580(s32 a0);
extern s32 func_8018466C();
extern s32 func_8012CC64(s32 a0, void *a1);
extern s32 func_8012CC1C(s32 a0, void *a1);
extern void func_8012B23C(s32 a0);
extern void func_80131C78(s32 a0);
extern s32 func_80143B6C(s32 a0, s32 a1);
extern void func_80131E00(s32 a0, s32 a1);
extern s32 D_801AE3A8;
s32 iVar1;
if (*(s16 *)(param_1 + 0xa) >= 0x10) {
func_80184580(param_1);
return;
}
switch (*(u16 *)(param_1 + 0x34)) {
case 0:
*(u16 *)(*(s32 *)(param_1 + 0x20) + 0x10) -= 0x100;
iVar1 = func_8012CC64(param_1, &D_801AE3A8);
if ((iVar1 & 0xff) == 0x1a) {
goto EXIT;
}
if ((iVar1 & 0x2000) != 0) {
*(u16 *)(param_1 + 0x34) += 1;
*(s32 *)(param_1 + 0x1c) = 0;
*(s16 *)(*(s32 *)(param_1 + 0x20) + 0x10) = 0;
goto TAIL;
}
if ((iVar1 & 0x4000) != 0) {
*(u16 *)(param_1 + 0x34) = 4;
*(s32 *)(param_1 + 0x1c) = 0;
*(s16 *)(*(s32 *)(param_1 + 0x20) + 0x10) = 0;
func_8012B23C(param_1);
goto TAIL;
}
*(s32 *)(param_1 + 0x1c) += 1;
if (*(s32 *)(param_1 + 0x1c) >= 0x3c) {
*(u16 *)(param_1 + 0x34) = 2;
}
goto TAIL;
case 1:
*(s32 *)(param_1 + 0x10) = *(s32 *)(param_1 + 0x10) * 15 / 16;
*(s32 *)(param_1 + 0x18) = *(s32 *)(param_1 + 0x18) * 15 / 16;
iVar1 = func_8012CC1C(param_1, &D_801AE3A8);
if ((iVar1 & 0xff) == 0x1a) {
goto EXIT;
}
if ((iVar1 & 0x6000) == 0) {
*(u16 *)(param_1 + 0x34) += 1;
*(s32 *)(param_1 + 0x1c) = 0;
func_8012B23C(param_1);
goto TAIL;
}
if ((*(s32 *)(param_1 + 0x1c) & 3) == 0) {
func_80143B6C(param_1, 1);
}
*(s32 *)(param_1 + 0x1c) += 1;
if (*(s32 *)(param_1 + 0x1c) < 0x10) {
goto TAIL;
}
goto HITSTUN;
case 2:
iVar1 = func_8012CC64(param_1, &D_801AE3A8);
if ((iVar1 & 0x2000) != 0) {
func_80143B6C(param_1, 1);
goto HITSTUN;
}
if ((iVar1 & 0x4000) == 0) {
goto L_F54;
}
*(u16 *)(param_1 + 0x34) = 4;
func_80143B6C(param_1, 1);
func_8012B23C(param_1);
goto TAIL;
case 3:
*(s32 *)(param_1 + 0x1c) += 1;
if (*(s32 *)(param_1 + 0x1c) < 0x10) {
/* §5a ZERO-BYTE CROSS-JUMP BARRIER — LOAD-BEARING, DO NOT DELETE.
* This whole arm is byte-identical to case 1's counter tail; without
* this line find_cross_jump merges the two and the function comes out
* 7 instructions short. Emits no machine code. See the header. */
__asm__ __volatile__("");
goto TAIL;
}
goto HITSTUN;
case 4:
iVar1 = func_8012CC1C(param_1, &D_801AE3A8);
if ((iVar1 & 0xff) != 0x1a) {
goto L_F20;
}
EXIT:
func_80184580(param_1);
return;
L_F20:
if ((iVar1 & 0x2000) == 0) {
goto L_F38;
}
HITSTUN:
func_80131C78(param_1);
goto TAIL;
L_F38:
if ((*(s32 *)(param_1 + 0x1c) & 3) == 0) {
func_80143B6C(param_1, 1);
}
L_F54:
*(s32 *)(param_1 + 0x1c) += 1;
if (*(s32 *)(param_1 + 0x1c) >= 0x3c) {
func_80131E00(param_1, 0xd);
}
}
TAIL:
func_8018466C(param_1);
if (0x100000 < *(s32 *)(param_1 + 0x14)) {
*(s32 *)(param_1 + 0x14) = 0x100000;
}
}
extern s32 D_801AE350;
extern s32 func_8018466C();
+324 -2
View File
@@ -3359,9 +3359,331 @@ void func_80183274(s32 a0) {
}
INCLUDE_ASM("asm/ov_SC05_010/nonmatchings/ov_SC05_010_jr_80181CDC", func_8018340C);
INCLUDE_ASM("asm/ov_SC05_010/nonmatchings/ov_SC05_010_jr_80181CDC", func_8018388C);
extern void func_8004914C(void *a0);
extern void func_800491AC(void *a0);
extern s32 RotTransPers(s32 a0, s32 a1, s32 *a2, s32 *a3);
extern s32 func_8004787C(s32 a0);
extern s32 D_80126950;
extern void *func_80010A08(s32 size);
extern s32 GetTPage(s32 a0, s32 a1, s32 a2, s32 a3);
extern s32 func_8005A600(s32 a0, s32 a1, s32 a2, s32 a3, s32 a4);
extern s32 AddPrim(s32 ot, void *prim);
extern u8 D_800AF648;
extern s32 D_800A651C[];
extern s16 D_800B9A02;
extern s16 D_80192CC0;
extern s16 D_80192CC4[];
extern u8 D_80192CD0[];
extern u8 D_80192CD1[];
extern u8 D_80192CD2[];
extern u8 D_80192CD3[];
extern u8 D_80192CE0[];
extern u8 D_80192CE1[];
extern u8 D_80192CE2[];
extern u8 D_80192CE3[];
extern u8 D_80192CF0[];
extern u8 D_80192CF1[];
extern u8 D_80192CF2[];
extern u8 D_80192CF3[];
void func_8018340C(void *a0)
{
s32 tags[4]; /* sp+0x18 */
s16 in[4]; /* sp+0x28 */
s16 xs[8]; /* sp+0x30 */
s16 ys[8]; /* sp+0x40 */
struct {
u16 sxy[2]; /* sp+0x50 */
s32 p; /* sp+0x54 */
s32 flag; /* sp+0x58 */
} o;
s32 ot;
s32 m;
s32 d;
s32 e;
s32 x;
s32 y;
s32 t;
s32 u;
s32 ret;
u8 *prim;
u8 *pp;
u8 *base;
s16 *pal;
s32 i;
s32 k;
/* cookbook SS194-A: the zero-byte volatile-asm fence below keeps the
D_80126950 load from being hoisted into the imul latency gap (sched1
priority, map sched.md S3). The three pins split the one collapsed
chain pseudo into the target's $t0/$v0/$a2 triple (local-alloc). */
register s32 aa __asm__("$8");
register s32 bb __asm__("$2");
register s32 cc __asm__("$6");
in[0] = *(s16 *)((s8 *)a0 + 0x06);
in[1] = *(s16 *)((s8 *)a0 + 0x0A);
in[2] = *(s16 *)((s8 *)a0 + 0x0E);
func_8004914C(&D_800AF648);
func_800491AC(&D_800AF648);
ret = RotTransPers((s32)in, (s32)o.sxy, &o.p, &o.flag);
if ((ret > 0) && (o.flag >= 0)) {
ot = *(s32 *)((s8 *)&D_800A651C + (u16)D_800B9A02 * 0x14) + ret * 4;
m = D_80192CC0;
t = func_8004787C(*(s16 *)((s8 *)a0 + 0xDE)) * 3;
if (t < 0) {
t += 7;
}
t = (t >> 3) - 0x800;
if (t < 0) {
u = func_8004787C(*(s16 *)((s8 *)a0 + 0xDE)) * 3;
if (u < 0) {
u += 7;
}
t = 0x800 - (u >> 3);
} else {
t = func_8004787C(*(s16 *)((s8 *)a0 + 0xDE)) * 3;
if (t < 0) {
t += 7;
}
t = (t >> 3) - 0x800;
}
aa = t * m;
bb = aa >> 12;
cc = bb + 8;
__asm__ __volatile__("");
d = cc * (D_80126950 + 500);
d = d / (ret * 4);
x = o.sxy[0];
y = o.sxy[1];
e = (d * 179) >> 8;
xs[2] = x;
ys[2] = y;
xs[0] = x - d;
xs[1] = x - e;
xs[3] = x + e;
xs[4] = x + d;
ys[0] = y - d;
ys[1] = y - e;
ys[3] = y + e;
ys[4] = y + d;
prim = (u8 *)func_80010A08(0x9C);
if (prim != 0) {
s32 tp;
tp = GetTPage(0, 1, 0, 0);
func_8005A600((s32)prim, 0, 1, (u16)tp, 0);
tags[0] = (s32)(prim + 0xC);
pp = prim + 0xC;
pal = D_80192CC4;
base = (u8 *)tags;
k = 0;
tags[1] = (s32)(prim + 0x30);
tags[2] = (s32)(prim + 0x54);
tags[3] = (s32)(prim + 0x78);
do {
i = k * 4;
*(u32 *)(pp + 0x04) = ((u32 *)pal)[D_80192CF0[i]];
*(u32 *)(pp + 0x0C) = ((u32 *)pal)[D_80192CF1[i]];
*(u32 *)(pp + 0x14) = ((u32 *)pal)[D_80192CF2[i]];
*(u32 *)(pp + 0x1C) = ((u32 *)pal)[D_80192CF3[i]];
*(u8 *)(pp + 0x03) = 8;
*(u8 *)(pp + 0x07) = 0x3A;
*(u16 *)(pp + 0x08) = *(u16 *)(base + 0x18 + D_80192CD0[i] * 2);
*(u16 *)(pp + 0x10) = *(u16 *)(base + 0x18 + D_80192CD1[i] * 2);
*(u16 *)(pp + 0x18) = *(u16 *)(base + 0x18 + D_80192CD2[i] * 2);
*(u16 *)(pp + 0x20) = *(u16 *)(base + 0x18 + D_80192CD3[i] * 2);
*(u16 *)(pp + 0x0A) = *(u16 *)(base + 0x28 + D_80192CE0[i] * 2);
*(u16 *)(pp + 0x12) = *(u16 *)(base + 0x28 + D_80192CE1[i] * 2);
*(u16 *)(pp + 0x1A) = *(u16 *)(base + 0x28 + D_80192CE2[i] * 2);
*(u16 *)(pp + 0x22) = *(u16 *)(base + 0x28 + D_80192CE3[i] * 2);
AddPrim(ot, pp);
k += 1;
pp += 0x24;
} while (k < 4);
AddPrim(ot, prim);
}
}
}
#include "common.h"
/* Spellings copied from the destination TU src/ov_SC05_010/ov_SC05_010_jr_80181CDC.c
* (L379 D_801202A0, L1245 func_801746DC, L1461 func_800D0C48, L2529 func_80178B18,
* L2581 func_8001AAA0, L2528 func_80178970, L2536 func_80178D18, L2392 func_80174774,
* L165 func_8014704C, L1785 D_80126B66, L3231 func_8012C218, L51 func_8002D4C8,
* L949 rand) — the `(void)`-declared callees are reached through the TU's own
* ((void (*)(s32))f)(x) cast idiom (func_801844AC L3710). */
extern u8 D_801202A0[];
extern u8 D_801923C4[];
extern void func_801746DC(void);
extern s32 func_80178B18(s32 param_1, s32 param_2);
extern void func_800D0C48(s32 a0);
extern void func_8012C218(void *a0);
extern void func_8002D4C8(s32 a0, s32 a1);
extern s32 rand(void);
extern int func_8001AAA0(void);
extern int func_80178970(void);
extern void func_80178D18(void);
extern s16 func_80174774(void); /* TU decl says s16, but the target has NO
* sll/sra extension before the beqz -> the call site
* is reached through an s32-returning cast (below). */
extern void func_8014704C(s32 *a0);
extern u16 D_80126B66;
/* not declared in the TU */
extern s32 func_8012C588(s32 a0, s32 a1);
extern s32 func_80132EF4(s32 a0, s32 a1);
extern void func_8013373C(s16 a0);
extern void func_8017C068(void);
extern void func_80187874(void);
extern void func_8002AC00(s32 a0);
extern s32 D_801C7E30[];
extern s32 D_801C7E50[]; /* == &D_801C7E30[8]; the target .s relocates against THIS symbol */
extern s32 D_801C7E4C;
extern s32 D_80192D64[];
extern s32 D_80126B58;
extern s32 D_80126B60;
void func_8018388C(s32 param_1) {
s32 i;
s32 obj;
u8 *q;
switch (*(u16 *)(param_1 + 0x34)) {
case 0:
func_80178B18(param_1, (s32)D_801923C4);
func_801746DC();
*(s32 *)(param_1 + 0x1C) = 0x80;
*(u16 *)(param_1 + 0x34) = *(u16 *)(param_1 + 0x34) + 1;
func_800D0C48(4);
q = D_801202A0;
for (i = 0; i < 0x60; i++) {
if (*(u16 *)q == 0x2B5) {
func_8012C218(q);
}
q += 0x10C;
}
*(s32 *)(D_801C7E4C + 0xE0) = 0x10000000;
break;
case 1:
*(s32 *)(param_1 + 0x1C) = *(s32 *)(param_1 + 0x1C) - 1;
if ((*(s32 *)(param_1 + 0x1C) & 0xF) == 0) {
obj = func_8012C588(0x2DE, param_1);
if (obj != 0) {
func_8002D4C8(0x8B8, 0);
*(u16 *)(obj + 0xA) = *(u16 *)(obj + 0xA) + 0x20;
if (*(s32 *)(param_1 + 0x1C) & 0x40) {
*(u16 *)(obj + 0xFC) = (*(s32 *)(param_1 + 0x1C) & 0x30) << 6;
} else {
*(u16 *)(obj + 0xFC) = ((*(s32 *)(param_1 + 0x1C) & 0x30) << 6) + 0x200;
}
*(u16 *)(obj + 0xFC) = *(u16 *)(obj + 0xFC) + (rand() & 0x1FF);
*(u16 *)(obj + 0xFE) = *(s32 *)(param_1 + 0x1C) + 0x60;
}
}
if (*(s32 *)(param_1 + 0x1C) == 0) {
*(s32 *)(param_1 + 0x1C) = 0x10;
*(u16 *)(param_1 + 0x34) = *(u16 *)(param_1 + 0x34) + 1;
}
break;
case 2:
if (*(s32 *)(param_1 + 0x1C) == 0) {
*(s32 *)(param_1 + 0x1C) = 0x3C;
*(u16 *)(param_1 + 0x34) = *(u16 *)(param_1 + 0x34) + 1;
func_8012C588(0x2DC, D_801C7E30[0]);
func_80132EF4(D_801C7E30[0], 0x5F);
func_8002D4C8(0x8B9, 0);
} else {
*(s32 *)(param_1 + 0x1C) = *(s32 *)(param_1 + 0x1C) - 1;
}
break;
case 3:
if (*(s16 *)(param_1 + 0x84) == 0) {
*(s16 *)(param_1 + 0x84) = ((s32 (*)(s32))func_8001AAA0)(0x6D);
}
if (*(s32 *)(param_1 + 0x1C) != 0) {
*(s32 *)(param_1 + 0x1C) = *(s32 *)(param_1 + 0x1C) - 1;
} else {
func_8012C218((void *)D_801C7E30[0]);
D_801C7E30[0] = 0;
for (i = 2; i < 8; i++) {
func_8012C218((void *)*(s32 *)(D_801C7E30[i] + 0x6C));
func_8012C218((void *)D_801C7E30[i]);
D_801C7E30[i] = 0;
}
for (i = 8; i < 12; i++) {
func_8012C218((void *)D_801C7E50[i - 8]);
D_801C7E50[i - 8] = 0;
}
q = D_801202A0;
for (i = 0; i < 0x60; i++) {
if (*(u16 *)q == 0x275) {
func_8012C218(q);
}
q += 0x10C;
}
func_8014704C(&D_80126B58);
func_8013373C(0);
*(s16 *)(param_1 + 0xA) = 0x77;
*(s16 *)(param_1 + 0x6) = 0;
*(s16 *)(param_1 + 0xE) = 0;
D_80126B60 = 0x970000;
D_80126B66 = 0x90;
func_8012C588(0x2F7, param_1);
for (i = 0; i < 0x18; i++) {
obj = func_8012C588(0x2E3, param_1);
if (obj != 0) {
*(s32 *)(*(s32 *)(obj + 0x20) + 0x24) = D_80192D64[i];
}
}
func_8017C068();
func_80187874();
*(u16 *)(param_1 + 0x34) = *(u16 *)(param_1 + 0x34) + 1;
}
break;
case 4:
if (*(s16 *)(param_1 + 0x84) == 0) {
*(s16 *)(param_1 + 0x84) = ((s32 (*)(s32))func_8001AAA0)(0x6D);
}
break;
case 5:
if (((s32 (*)(void))func_80174774)() != 0) {
*(u32 *)(*(s32 *)(param_1 + 0x20) + 4) |= 0x80000000;
*(u16 *)(param_1 + 0x34) = *(u16 *)(param_1 + 0x34) + 1;
func_8002AC00(0x1E);
}
break;
case 6:
break;
}
if (((s32 (*)(s32))func_80178970)(param_1) != 0) {
((void (*)(s32))func_80178D18)(param_1);
*(u16 *)(param_1 + 0x2) = 6;
}
}
extern s32 func_8004787C(s32 a0);
extern void func_8018340C(void *a0);
+138 -1
View File
@@ -4246,7 +4246,144 @@ void func_8017EA6C(s32 p) {
}
INCLUDE_ASM("asm/ov_SC06_022/nonmatchings/ov_SC06_022_jr_8017BEBC", func_8017EBE8);
/* func_8017EBE8 (ov_SC06_022, ov_SC06_022_jr_8017BEBC) — match_one MATCH 252/252.
*
* Three levers, all byte-proven here (closeness 97 -> 9 -> 0 in three compiles):
*
* 1) THE ±d ARM PAIR MUST STORE FROM THE JOIN BLOCK, NOT FROM BOTH ARMS.
* Writing `if (rand()&1) *(s16*)(o+0xE)=v+d; else *(s16*)(o+0xE)=v-d;` leaves the `sh`
* at the bottom of each arm; cross_jump merges them (§193-C) so the arms LOOK right, but
* the merged `sh` then sits in the join block ALONE, ahead of the next statement's
* `lhu $v0,0xA($s2)`, and sched1 cannot hoist that load over a store it has a WAR on ->
* a load-delay `nop` and LENGTH-DRIFT +1. Assigning a temp in both arms and storing ONCE
* after the join puts the `sh` and the `lhu` in one basic block, where sched1 issues
* `lhu $v0,0xA` BEFORE `sh $v1,0xE` and fills the delay for free (idx 166-170).
*
* 2) EACH ±d SITE NEEDS ITS OWN TEMP (w1..w4). One shared `w` is one pseudo, so local-alloc
* gives it ONE hard reg for the whole function; the loop-2 0xE site legitimately needs
* $v1 (its live range overlaps the hoisted `lhu $v0,0xA` from lever 1), and that choice
* then infected the other three sites -> REGALLOC-PERM/$v1>$v0, 9 rows. Four distinct
* locals = four independent live ranges: $v0, $v0, $v0, $v1, exactly as the target.
*
* 3) `if (p->0xE0 != 0) {...} else func_8012C218(p);` — NOT the inverted spelling. The target
* puts the func_8012C218 call LAST (`beqz $v0,.L8017EFA8` + a `j` over it), which is the
* else-arm layout; the == 0 spelling emits the call first.
*
* Field widths read straight off the loads (house style of this TU, cf. func_8017DCA4):
* RMW-by-constant fields (0xA, 0xE in the tail, 0x2, 0x34) are `u16` -> lhu/addiu/sh;
* a field read into a variable that lives across a call (0x6, 0xE in the loops) is `s16` -> lh.
* `& ~0xF` (not `& 0xFFF0`) is what materialises `addiu $v1,$zero,-0x10` + `and`.
*
* Symbols re-checked against the .s relocation lines after MATCH (law 1c): 8 rand + 2
* func_80132EF4 + 6 rand + func_8002D4C8/func_8012BEE8/func_8012E8C4/func_8012BEE8/
* 2x func_8012C658/func_8012E8A8/func_8012C218, in that order; both internal `j`s land on
* the epilogue at +0x3C8 (§195-D — `j` destinations are masked by match_one).
*/
extern s32 rand(void);
extern void func_8002D4C8(s32 a0, s32 a1);
extern s32 func_8012BEE8(s32 a0);
extern s32 func_80132EF4(s32 a0, s32 a1);
extern s32 func_8012C658(s32 a0, s32 a1, s32 a2);
extern void func_8012E8C4(u8 *a0);
extern void func_8012E8A8(u8 *a0);
extern void func_8012C218(void *a0);
void func_8017EBE8(s32 p) {
s32 obj;
s32 i;
s16 n;
s32 x;
s32 y;
s32 d;
s32 v;
s32 w1;
s32 w2;
s32 w3;
s32 w4;
s32 t;
if (*(u16 *)(p + 0x34) == 0) {
if (*(s32 *)(p + 0x1C) >= 0x1F) {
n = rand() % 4;
for (i = 0; i < n; i++) {
obj = func_80132EF4(p, 0x23);
if (obj != 0) {
x = rand();
y = rand();
*(u16 *)(obj + 0x34) = ((x % 0x4000 + 0x2000) & ~0xF) | (y & 1);
*(u16 *)(obj + 0xA) -= 0x70;
d = rand() % 80;
v = *(s16 *)(obj + 6);
if ((rand() & 1) != 0) {
w1 = v + d;
} else {
w1 = v - d;
}
*(s16 *)(obj + 6) = w1;
d = rand() % 144;
v = *(s16 *)(obj + 0xE);
if ((rand() & 1) != 0) {
w2 = v + d;
} else {
w2 = v - d;
}
*(s16 *)(obj + 0xE) = w2;
}
}
n = rand() % 2;
for (i = 0; i < n; i++) {
obj = func_80132EF4(p, 0x22);
if (obj != 0) {
*(u16 *)(obj + 0x34) = rand() % 0x4000 + 0x2000;
d = rand() % 80;
v = *(s16 *)(obj + 6);
if ((rand() & 1) != 0) {
w3 = v + d;
} else {
w3 = v - d;
}
*(s16 *)(obj + 6) = w3;
d = rand() % 144;
v = *(s16 *)(obj + 0xE);
if ((rand() & 1) != 0) {
w4 = v + d;
} else {
w4 = v - d;
}
*(s16 *)(obj + 0xE) = w4;
*(u16 *)(obj + 0xA) -= 0x80;
*(s32 *)(obj + 0x14) = (rand() % 3) * -0x10000;
*(u32 *)(*(s32 *)(obj + 0x20) + 4) |= 0x40000000;
}
}
func_8002D4C8(0x9D6, 0);
}
if (func_8012BEE8(p) != 0) {
*(s32 *)(p + 0x1C) = 0x20;
*(u16 *)(p + 0x34) += 1;
}
} else {
func_8012E8C4((u8 *)p);
if (func_8012BEE8(p) != 0) {
t = func_8012C658(0x32, 1, p);
if (t != 0) {
*(u16 *)(t + 0xE) += 0x30;
}
t = func_8012C658(0x33, 1, p);
if (t != 0) {
*(u16 *)(t + 0xE) -= 0x30;
}
if (*(s32 *)(p + 0xE0) != 0) {
*(u16 *)(p + 2) += 1;
func_8012E8A8((u8 *)p);
*(u16 *)(p + 0x5C) = 0;
} else {
func_8012C218((void *)p);
}
}
}
}
void func_8017EFD8(void) {
}
+146 -1
View File
@@ -4019,7 +4019,152 @@ void func_8017DBFC(s32 arg0)
}
INCLUDE_ASM("asm/ov_SC06_024/nonmatchings/ov_SC06_024_jr_8017BEBC", func_8017E1F0);
extern void func_8002D4C8(s32 a0, s32 a1);
extern void func_80128D60(s32 a0, s32 *a1, s32 *a2);
extern s32 func_80128DB4(s32 a0, s32 *a1);
extern s32 func_8012BEE8(s32 a0);
extern void func_8012EC04(s32 a0, s32 a1, s32 *a2);
extern void func_8012F14C(s32 a0, s32 a1, s32 a2);
extern s32 func_8012C51C(void *a0, s32 a1);
extern s32 func_80132EF4(s32 a0, s32 a1);
extern s32 func_8012B608(s32 a0, s32 a1, s32 a2);
extern s32 rand(void);
extern s32 D_801E1120[];
extern s32 D_80193338;
extern s16 D_80193448[];
extern u8 D_80193530[];
extern s32 D_801E111C;
extern s32 D_801E1158;
void func_8017E1F0(s32 param_)
{
register s32 s1 __asm__("$17");
register s32 ent __asm__("$16");
register s32 i __asm__("$18");
s32 k;
struct {
s16 m[16];
s16 out[4];
s16 ax, ay, az;
s16 w03;
s16 idx;
s16 f06;
s16 f07;
s16 f08;
s32 f09;
} frm;
s32 *pp;
s16 *cp;
s32 cnt;
s32 rnd;
s32 cur;
s32 ret;
s32 idx;
s32 tbl;
s32 tmp;
s1 = param_;
switch (*(u16 *)(s1 + 0x34)) {
case 0:
*(s32 *)(s1 + 0x1C) = 0;
*(u16 *)(s1 + 0x34) = *(u16 *)(s1 + 0x34) + 1;
func_80128D60(0, D_801E1120, &D_80193338);
break;
case 1:
if (func_8012BEE8(s1) != 0) {
func_8002D4C8(0x956, 0);
*(u16 *)(s1 + 0x34) = *(u16 *)(s1 + 0x34) + 1;
}
break;
case 2:
pp = *(s32 **)(s1 + 0x20);
pp = (s32 *)*(s32 *)((s32)pp + 0x20);
i = 3;
cp = (s16 *)pp + 6;
do {
cp[3] = *(u16 *)(s1 + 0xFE);
cp += 6;
} while (--i >= 0);
*(u16 *)(s1 + 0xFE) = *(u16 *)(s1 + 0xFE) + 0x1E;
if (*(s16 *)(s1 + 0xFE) < 0x385) {
break;
}
*(u16 *)(s1 + 0xFE) = 900;
*(s32 *)(s1 + 0x1C) = 0;
*(s32 *)(s1 + 0xE0) = 0;
*(u16 *)(s1 + 0x34) = *(u16 *)(s1 + 0x34) + 1;
func_8002D4C8(4, 0x956);
func_8002D4C8(0x957, 0);
break;
case 3:
if (func_8012BEE8(s1) == 0) {
break;
}
tmp = D_801E1158;
frm.w03 = 0x2D5;
frm.f06 = 0;
frm.f09 = 0;
frm.f08 = 0;
frm.f07 = 0x7FFF;
*(u16 *)(s1 + 0x108) = 0;
func_8012EC04(s1, tmp, (s32 *)frm.m);
k = 0;
while (k < 4) {
func_8012F14C((s32)frm.m, (s32)&D_80193448[k * 4], (s32)frm.out);
frm.idx = k;
frm.ax = frm.out[0];
frm.ay = frm.out[1];
frm.az = frm.out[2];
func_8012C51C(&frm.ax, s1);
ent = func_80132EF4(s1, 0x22);
if (ent != 0) {
*(u16 *)(ent + 0x34) = rand() & 1 | 0x2000;
*(u16 *)(*(s32 *)(ent + 0x20) + 0x2C) = 0xC006U;
frm.out[1] = frm.out[1] - 0x20;
*(s16 *)(ent + 6) = frm.out[0];
*(s16 *)(ent + 0xA) = frm.out[1];
*(s16 *)(ent + 0xE) = frm.out[2];
}
k++;
}
func_8002D4C8(0x953, 0);
cnt = *(s32 *)(s1 + 0xE0) + 1;
*(s32 *)(s1 + 0xE0) = cnt;
if (cnt < 2) {
rnd = rand();
cur = *(s16 *)(*(s32 *)(s1 + 0x20) + 0x12);
idx = rnd % 4;
tbl = cur + *(s16 *)&D_80193530[idx * 2];
*(u16 *)(s1 + 0x34) = 5;
*(s32 *)(s1 + 0x1C) = 0x1E;
D_801E111C = tbl;
} else {
*(s32 *)(s1 + 0x1C) = 0;
*(u16 *)(s1 + 0x34) = *(u16 *)(s1 + 0x34) + 1;
}
break;
case 4:
if (func_8012BEE8(s1) != 0) {
*(u16 *)(s1 + 2) = 4;
*(u16 *)(s1 + 0x34) = 0;
func_8002D4C8(0x958, 0);
}
break;
case 5:
if (func_8012BEE8(s1) != 0) {
ret = func_8012B608(*(s16 *)(*(s32 *)(s1 + 0x20) + 0x12), D_801E111C, 8);
*(u16 *)(*(s32 *)(s1 + 0x20) + 0x12) =
*(u16 *)(*(s32 *)(s1 + 0x20) + 0x12) + ret;
if (ret == 0) {
*(u16 *)(s1 + 0x34) = 3;
}
}
break;
}
func_80128DB4(0, D_801E1120);
}
extern s32 func_80128DB4(s32, s32 *);
extern void func_80128D60(s32, s32 *, s32 *);
+143 -1
View File
@@ -3986,4 +3986,146 @@ void func_8017F0A0(s32 a0) {
}
INCLUDE_ASM("asm/ov_SC06_030/nonmatchings/ov_SC06_030_jr_8017C8D0", func_8017F268);
extern void func_8012A828(s32 a0, void *a1);
extern void func_8004914C(void *a0);
extern void func_800491AC(void *a0);
extern s32 RotTransPers(s32 a0, s32 a1, s32 *a2, s32 *a3);
extern void func_8002D4C8(s32 a0, s32 a1);
extern s32 rand(void);
extern s32 func_8004787C(s32 a0);
extern s32 func_80047948(s32 a0);
extern s32 func_80047D3C(s32 a0);
extern s32 func_8012BA10(s32 a0, s32 a1);
extern s32 func_8012BD14(s32 a0);
extern s32 func_8012B8A4(s32 a0);
extern s32 func_8012D624(s32 a0, s32 a1, s32 a2);
extern s32 func_80143C74(s32 a0, s32 a1);
extern s32 func_8012C658(s32 a0, s32 a1, s32 a2);
extern void func_80128EA8(s32 a0, s32 a1, s32 a2);
extern u8 D_800AF648;
extern u8 D_8019F06C;
extern u8 D_8019EC8C;
extern u8 D_80185AC8;
extern s16 D_80185D62;
extern u16 D_80126B96;
extern s16 D_80126B9A;
/* the repeated RTP + positional-sound block (cookbook §88a: LONGHAND, never factored) */
#define RTP_SND(sndid) \
L.v[0] = *(s32 *)(*(s32 *)(a0 + 0x20) + 0x48); \
L.v[1] = *(s32 *)(*(s32 *)(a0 + 0x20) + 0x4C); \
L.v[2] = *(s32 *)(*(s32 *)(a0 + 0x20) + 0x50); \
{ register void *r4 __asm__("$4"); r4 = &D_800AF648; func_8004914C(r4); } \
{ register void *r4 __asm__("$4"); r4 = &D_800AF648; func_800491AC(r4); } \
RotTransPers((s32)L.v, (s32)L.sxy, &L.z, &L.flag); \
if (L.flag >= 0 && (u32)((L.sxy[0] + 0x9F) & 0xFFFF) < 0x13F \
&& (u32)((L.sxy[1] + 0x77) & 0xFFFF) < 0xEF) { \
s32 vol = ((s16)L.sxy[0] * 0x80 + 0x5000) / 320; \
if (vol < 0) { \
vol = 0; \
} \
if (vol >= 0x80) { \
vol = 0x7F; \
} \
func_8002D4C8(sndid, (vol | 0x2000) & 0xFFFF); \
}
/* the cross-jumped suffix shared by case 1 and case 3 -- written LONGHAND in both */
#define CHK_TAIL \
if (func_8012D624(a0, 0x48, 0x50) != 0) { \
D_80126B96 = 0x4004; \
D_80126B9A = func_8012B8A4(a0); \
}
void func_8017F268(s32 a0) {
s32 t;
struct {
s16 v[3]; /* sp+0x10 */
s16 pad0; /* sp+0x16 */
u16 sxy[2]; /* sp+0x18 */
s32 z; /* sp+0x1C */
s32 flag; /* sp+0x20 */
s32 unused; /* sp+0x24 -- frame padding, vars must be 0x18 */
} L;
switch (*(u16 *)(a0 + 0x34)) {
case 0:
func_8012A828(a0, &D_8019F06C);
*(s16 *)(a0 + 0x34) = 1;
func_8002D4C8(0xA8A, 0);
RTP_SND(0x93F)
break;
case 1:
if (*(s32 *)(a0 + 0x94) >= 0x2C) {
D_80185D62 = 0x20;
func_8002D4C8(0xA8B, 0);
*(s16 *)(a0 + 0x34) = 2;
break;
}
CHK_TAIL
break;
case 2:
if (*(s32 *)(a0 + 0x94) < 0x31) {
*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12) =
*(u16 *)(*(s32 *)(a0 + 0x20) + 0x12) + func_8012BA10(a0, 2);
break;
}
t = func_8012BD14(a0);
if (t <= 0xFFFF) {
*(s16 *)(a0 + 0x34) = 4;
break;
}
t = func_80047D3C(t) - 0x100;
if (t < 0) {
t = 0;
}
*(s32 *)(a0 + 0x10) =
func_8004787C(*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12)) * t * 4;
*(s32 *)(a0 + 0x18) =
func_80047948(*(s16 *)(*(s32 *)(a0 + 0x20) + 0x12)) * t * 4;
*(s16 *)(a0 + 0x34) = 3;
*(s32 *)(a0 + 0x1C) = 0x10;
*(s32 *)(a0 + 0x44) = *(s32 *)(a0 + 0x10) >> 4;
*(s32 *)(a0 + 0x4C) = *(s32 *)(a0 + 0x18) >> 4;
func_8002D4C8(0xC65, 0);
break;
case 3:
*(s32 *)(a0 + 0x04) = *(s32 *)(a0 + 0x04) - *(s32 *)(a0 + 0x10);
*(s32 *)(a0 + 0x10) = *(s32 *)(a0 + 0x10) - *(s32 *)(a0 + 0x44);
*(s32 *)(a0 + 0x0C) = *(s32 *)(a0 + 0x0C) - *(s32 *)(a0 + 0x18);
*(s32 *)(a0 + 0x18) = *(s32 *)(a0 + 0x18) - *(s32 *)(a0 + 0x4C);
t = func_80143C74(a0, 0);
if (t != 0) {
s32 q;
*(s32 *)(t + 0x18) = *(s32 *)(a0 + 0x18);
*(s16 *)(t + 0x16) = -((rand() & 3) + 4);
*(s32 *)(t + 0x10) = *(s32 *)(a0 + 0x10);
q = *(s32 *)(t + 0xCC);
*(s16 *)(q + 0x1A) = 0x6000;
*(s16 *)(q + 0x18) = 0x6000;
func_80128EA8(q, t + 0xD0, (s32)&D_80185AC8);
}
if (--*(s32 *)(a0 + 0x1C) == 0) {
*(s16 *)(a0 + 0x34) = 4;
func_8002D4C8(0x93F, 0);
}
CHK_TAIL
break;
case 4:
func_8012C658(0x3DD, 0, a0);
if (*(s16 *)(a0 + 0x98) == 0) {
*(s16 *)(a0 + 2) = 2;
*(s32 *)(a0 + 0x1C) = 0x1E;
*(s16 *)(a0 + 0xFC) = 0;
func_8012A828(a0, &D_8019EC8C);
D_80185D62 = -0x50;
}
break;
}
}
+160 -1
View File
@@ -3943,7 +3943,166 @@ s32 param_1;
}
INCLUDE_ASM("asm/ov_SC06_030/nonmatchings/ov_SC06_030_jr_8017F65C", func_80181164);
#include "common.h"
#define gte_SetRotMatrix_80181164(r0) __asm__ volatile ( \
"lw $12, 0( %0 );" \
"lw $13, 4( %0 );" \
"ctc2 $12, $0;" \
"ctc2 $13, $1;" \
"lw $12, 8( %0 );" \
"lw $13, 12( %0 );" \
"lw $14, 16( %0 );" \
"ctc2 $12, $2;" \
"ctc2 $13, $3;" \
"ctc2 $14, $4" \
: \
: "r"( r0 ) \
: "$12", "$13", "$14" )
#define gte_SetTransMatrix_80181164(r0) __asm__ volatile ( \
"lw $12, 20( %0 );" \
"lw $13, 24( %0 );" \
"ctc2 $12, $5;" \
"lw $14, 28( %0 );" \
"ctc2 $13, $6;" \
"ctc2 $14, $7" \
: \
: "r"( r0 ) \
: "$12", "$13", "$14" )
/* §202 DEF-SIDE ALIAS: this TU declares `extern void func_80181164(void);`
* at :4223 for its live caller func_80181DD4 (:4226). The target's asm
* proves an incoming $a0 (`lw $v0, 0x20($a0)` at 0x80181188), so a
* `(void)` definition is a `conflicting types` cc1 error. Define under the
* C identifier aF80181164 with __asm__("func_80181164"): the identifiers
* never collide, the emitted symbol is unchanged, and the body stays the
* byte-verified one (match_one MATCH, 265/265). */
void aF80181164(void *a0) __asm__("func_80181164");
void aF80181164(void *a0)
{
extern u8 D_801B4CA4[];
extern u32 D_801B4CAC[];
extern u8 D_801B4CB8[];
extern u8 D_801B4CB9[];
extern u8 D_801B4CBA[];
extern u8 D_801B4CBB[];
extern u8 D_801B4CC8[];
extern u8 D_801B4CC9[];
extern u8 D_801B4CCA[];
extern u8 D_801B4CCB[];
extern u8 D_801B4CD8[];
extern u8 D_801B4CD9[];
extern u8 D_801B4CDA[];
extern u8 D_801B4CDB[];
extern void *func_80010A08(s32);
extern s32 func_8005A600(s32, s32, s32, s32, s32);
extern s32 GetTPage(s32, s32, s32, s32);
extern s32 AddPrim(s32, void *);
extern void func_8004914C(void *a0);
extern void func_800491AC(void *a0);
extern void RotTransSV(void *a0, void *a1, void *a2);
extern s32 RotTransPers(s32 a0, s32 a1, s32 *a2, s32 *a3);
extern s32 D_800A651C;
extern s16 D_800B9A02;
extern u8 D_800AF648;
extern s32 D_80126950;
s32 tags[4]; /* sp+0x18 */
s16 sv[4]; /* sp+0x28 */
s16 xs[8]; /* sp+0x30 */
s16 ys[8]; /* sp+0x40 */
struct {
s32 flag; /* sp+0x50 */
u16 sxy[2]; /* sp+0x54 */
s32 pz; /* sp+0x58 */
} o;
s32 m;
void *pv;
s32 *pflag;
s32 ret;
s32 d;
s32 e;
s32 x;
s32 y;
s32 ot;
u8 *prim;
u8 *pp;
u8 *base;
u32 *pal;
s32 i;
s32 k;
m = *(s32 *)((s32)a0 + 0x20) + 0x34;
gte_SetRotMatrix_80181164(m);
gte_SetTransMatrix_80181164(m);
pv = (void *)sv;
pflag = &o.flag;
RotTransSV(D_801B4CA4, pv, pflag);
func_8004914C(&D_800AF648);
func_800491AC(&D_800AF648);
ret = RotTransPers((s32)pv, (s32)o.sxy, &o.pz, pflag);
if ((ret > 0) && (o.flag >= 0)) {
ret = ret * 4;
d = ((D_80126950 + 0x1F4) * 48) / ret;
x = o.sxy[0];
y = o.sxy[1];
ot = *(s32 *)((s8 *)&D_800A651C + ((u16)D_800B9A02 * 0x14)) + ret;
e = (d * 179) >> 8;
xs[2] = x;
ys[2] = y;
xs[0] = x - d;
xs[1] = x - e;
xs[3] = x + e;
xs[4] = x + d;
ys[0] = y - d;
ys[1] = y - e;
ys[3] = y + e;
ys[4] = y + d;
prim = (u8 *)func_80010A08(0x9C);
if (prim != 0) {
s32 tp;
tp = GetTPage(0, 1, 0, 0);
func_8005A600((s32)prim, 0, 0, (u16)tp, 0);
tags[0] = (s32)(prim + 0xC);
pp = prim + 0xC;
pal = D_801B4CAC;
base = (u8 *)tags;
k = 0;
tags[1] = (s32)(prim + 0x30);
tags[2] = (s32)(prim + 0x54);
tags[3] = (s32)(prim + 0x78);
do {
i = k * 4;
*(u32 *)(pp + 0x04) = pal[D_801B4CD8[i]];
*(u32 *)(pp + 0x0C) = pal[D_801B4CD9[i]];
*(u32 *)(pp + 0x14) = pal[D_801B4CDA[i]];
*(u32 *)(pp + 0x1C) = pal[D_801B4CDB[i]];
*(u8 *)(pp + 0x03) = 8;
*(u8 *)(pp + 0x07) = 0x3A;
*(u16 *)(pp + 0x08) = *(u16 *)(base + 0x18 + D_801B4CB8[i] * 2);
*(u16 *)(pp + 0x10) = *(u16 *)(base + 0x18 + D_801B4CB9[i] * 2);
*(u16 *)(pp + 0x18) = *(u16 *)(base + 0x18 + D_801B4CBA[i] * 2);
*(u16 *)(pp + 0x20) = *(u16 *)(base + 0x18 + D_801B4CBB[i] * 2);
*(u16 *)(pp + 0x0A) = *(u16 *)(base + 0x28 + D_801B4CC8[i] * 2);
*(u16 *)(pp + 0x12) = *(u16 *)(base + 0x28 + D_801B4CC9[i] * 2);
*(u16 *)(pp + 0x1A) = *(u16 *)(base + 0x28 + D_801B4CCA[i] * 2);
*(u16 *)(pp + 0x22) = *(u16 *)(base + 0x28 + D_801B4CCB[i] * 2);
AddPrim(ot, pp);
k += 1;
pp += 0x24;
} while (k < 4);
AddPrim(ot, prim);
}
}
}