diff --git a/config/boot/functions.tsv b/config/boot/functions.tsv index 0df50487e..e6cd61d48 100644 --- a/config/boot/functions.tsv +++ b/config/boot/functions.tsv @@ -47,7 +47,7 @@ func_00118D98 00118D98 3368 func_00119AC0 00119AC0 264 func_00119BC8 00119BC8 48 func_00119BF8 00119BF8 3072 -func_0011A7F8 0011A7F8 24 +func_0011A7F8 0011A800 16 func_0011A810 0011A810 16 func_0011A820 0011A820 16 func_0011A830 0011A830 16 @@ -194,7 +194,6 @@ func_0011B328 0011B328 164 func_0011B3D0 0011B3D0 124 func_0011B458 0011B458 164 func_0011B500 0011B500 124 -func_0011B580 0011B580 8 func_0011B588 0011B588 104 func_0011B5F0 0011B5F0 104 func_0011B658 0011B658 104 @@ -224,7 +223,6 @@ func_0011C820 0011C820 96 func_0011C880 0011C880 28 func_0011C8A0 0011C8A0 12 func_0011C8B0 0011C8B0 24 -func_0011C8C8 0011C8C8 12 func_0011C8D8 0011C8D8 640 func_0011CB58 0011CB58 52 func_0011CB90 0011CB90 44 @@ -264,13 +262,11 @@ func_0011E4E0 0011E4E0 608 func_0011E740 0011E7A0 136 func_0011E828 0011E828 128 func_0011E8A8 0011E8A8 120 -func_0011E920 0011E920 24 func_0011E938 0011E938 256 func_0011EA38 0011EA38 140 func_0011EAC8 0011EAC8 56 func_0011EB00 0011EB00 520 func_0011ED08 0011ED08 28 -func_0011ED28 0011ED28 56 func_0011ED60 0011ED60 316 func_0011EEA0 0011EEA0 56 func_0011EED8 0011EED8 272 @@ -301,7 +297,6 @@ func_0011F938 0011F938 172 func_0011F9E4 0011F9E8 48 func_0011FA18 0011FA18 8 func_0011FA20 0011FA20 40 -func_0011FA48 0011FA48 8 func_0011FA50 0011FA50 16 func_0011FA60 0011FA60 16 func_0011FA70 0011FA70 56 @@ -355,7 +350,6 @@ func_00123268 00123268 44 func_00123298 00123298 84 func_001232F0 001232F0 268 func_00123400 00123400 144 -func_00123490 00123490 44 func_001234C0 001234C0 44 func_001234F0 001234F0 64 func_00123530 00123530 68 @@ -459,7 +453,6 @@ func_001291A0 001291A0 116 func_00129218 00129218 164 func_001292C0 001292C0 168 func_00129368 00129368 168 -func_00129410 00129410 64 func_00129450 00129450 592 func_001296A0 001296A0 1796 func_00129DA8 00129DA8 1052 @@ -546,7 +539,6 @@ func_0012F690 0012F690 168 func_0012F738 0012F738 520 func_0012F940 0012F940 8 func_0012F948 0012F950 72 -func_0012F998 0012F998 16 func_0012F9A8 0012F9A8 12 func_0012F9B8 0012F9B8 16 func_0012F9C8 0012F9C8 80 @@ -554,7 +546,6 @@ func_0012FA18 0012FA18 84 func_0012FA70 0012FA70 36 func_0012FA98 0012FA98 80 func_0012FAE8 0012FAE8 36 -func_0012FB10 0012FB10 52 func_0012FB48 0012FB48 20 func_0012FB60 0012FB60 12 func_0012FB70 0012FB70 12 @@ -584,7 +575,6 @@ func_00130A70 00130A70 12 func_00130A80 00130A80 12 func_00130A8C 00130A90 12 func_00130AA0 00130AA0 12 -func_00130AAC 00130AAC 4 func_00130AB0 00130AB0 100 func_00130B18 00130B18 100 func_00130B80 00130B80 228 @@ -714,7 +704,6 @@ func_0026F810 0026F840 1068 func_0026FC78 0026FC78 464 func_0026FE48 0026FE48 108 func_0026FEB8 0026FEB8 56 -func_0026FEF0 0026FEF0 20 func_0026FF08 0026FF08 268 func_00270018 00270018 396 func_002701B0 002701B0 92 @@ -745,9 +734,7 @@ func_00272198 00272198 48 func_002721C8 002721C8 184 func_00272280 00272280 228 func_00272368 00272368 472 -func_00272540 00272540 12 func_00272550 00272550 120 -func_002725C8 002725C8 20 func_002725E0 002725E0 956 func_002729A0 002729A0 784 func_00272CB0 00272CB0 1632 @@ -867,7 +854,6 @@ func_00280328 00280328 488 func_00280510 00280510 240 func_00280600 00280600 44 func_00280630 00280630 48 -func_00280660 00280660 12 func_00280670 00280670 160 func_00280710 00280710 484 func_002808F8 002808F8 376 @@ -1044,7 +1030,6 @@ func_00288BB8 00288BB8 48 func_00288BE8 00288BE8 200 func_00288CB0 00288CB0 128 func_00288D30 00288D30 12 -func_00288D40 00288D40 20 func_00288D58 00288D58 16 func_00288D68 00288D68 8 func_00288D70 00288D70 12 @@ -1125,7 +1110,6 @@ func_002900B8 002900B8 1388 func_00290628 00290628 64 func_00290670 00290670 12 func_00290680 00290680 148 -func_00290718 00290718 4 func_00290720 00290720 8 func_00290728 00290728 8 func_00290730 00290730 24 @@ -1246,7 +1230,6 @@ func_00298A20 00298A20 260 func_00298B28 00298B28 72 func_00298B70 00298B70 68 func_00298BB8 00298BB8 340 -func_00298D10 00298D10 20 func_00298D28 00298D28 220 func_00298E08 00298E08 248 func_00298F00 00298F00 7840 @@ -1268,7 +1251,6 @@ func_0029B758 0029B758 40 func_0029B780 0029B780 64 func_0029B7C0 0029B7C0 76 func_0029B810 0029B810 52 -func_0029B848 0029B848 12 func_0029B858 0029B858 48 func_0029B888 0029B888 132 func_0029B910 0029B910 328 @@ -1341,7 +1323,6 @@ func_0029CD20 0029CD20 36 func_0029CD48 0029CD48 240 func_0029CE38 0029CE38 64 func_0029CE80 0029CE80 72 -func_0029CEC8 0029CEC8 12 func_0029CED8 0029CED8 48 func_0029CF08 0029CF08 60 func_0029CF58 0029CF58 32 @@ -1564,7 +1545,6 @@ func_002B0668 002B0668 564 func_002B08A8 002B08A8 104 func_002B0910 002B0910 84 func_002B0990 002B0990 120 -func_002B0A08 002B0A08 12 func_002B0A18 002B0A18 48 func_002B0A48 002B0A48 28 func_002B0A68 002B0A68 428 @@ -1593,11 +1573,9 @@ func_002B39A0 002B39A0 384 func_002B3B20 002B3B20 132 func_002B3BA8 002B3BA8 1152 func_002B4038 002B4038 36 -func_002B4068 002B4068 36 func_002B4090 002B4090 272 func_002B41A8 002B41A8 788 func_002B44C0 002B44C0 1248 -func_002B49A0 002B49A0 12 func_002B49B0 002B49B0 8 func_002B49C0 002B49C0 8 func_002B49C8 002B49C8 20 @@ -1661,10 +1639,8 @@ func_002B7F58 002B7F58 84 func_002B7FB0 002B7FB0 60 func_002B7FF0 002B7FF0 88 func_002B8048 002B8048 108 -func_002B80B8 002B80B8 76 func_002B8108 002B8108 1040 func_002B8518 002B8518 20 -func_002B8530 002B8530 20 func_002B8548 002B8548 176 func_002B85F8 002B85F8 656 func_002B8888 002B8888 100 @@ -2069,7 +2045,6 @@ func_002DF1F8 002DF1F8 232 func_002DF2E0 002DF2E0 160 func_002DF380 002DF380 120 func_002DF3F8 002DF3F8 564 -func_002DF630 002DF630 12 func_002DF640 002DF640 272 func_002DF750 002DF750 84 func_002DF7A8 002DF7A8 144 @@ -2169,17 +2144,12 @@ func_002ED260 002ED260 88 func_002ED2B8 002ED2B8 172 func_002ED368 002ED368 336 func_002ED4B8 002ED4B8 176 -func_002ED570 002ED570 4 func_002ED578 002ED578 244 func_002ED688 002ED688 36 func_002ED6B0 002ED6B0 404 -func_002ED848 002ED848 36 func_002ED870 002ED870 12 -func_002ED880 002ED880 28 func_002ED8A0 002ED8A0 76 -func_002ED8F0 002ED8F0 84 func_002ED948 002ED948 96 -func_002ED9A8 002ED9A8 20 func_002ED9C0 002ED9C0 76 func_002EDA10 002EDA58 1444 func_002EE000 002EE000 564 @@ -2194,7 +2164,6 @@ func_002EE8B0 002EE8B0 108 func_002EE920 002EE920 104 func_002EE988 002EE988 372 func_002EEB00 002EEB00 176 -func_002EEBB0 002EEBB0 20 func_002EEBC8 002EEBC8 320 func_002EED08 002EED08 76 func_002EED58 002EED58 244 @@ -2282,17 +2251,13 @@ func_002FC220 002FC220 96 func_002FC280 002FC280 316 func_002FC3C0 002FC3C0 76 func_002FC410 002FC410 76 -func_002FC460 002FC460 4 func_002FC468 002FC468 164 -func_002FC510 002FC510 4 func_002FC518 002FC518 72 func_002FC560 002FC560 180 -func_002FC618 002FC618 4 func_002FC620 002FC620 284 func_002FC748 002FC748 92 func_002FC7A8 002FC7A8 92 func_002FC808 002FC808 92 -func_002FC868 002FC868 4 func_002FC870 002FC870 92 func_002FC8D0 002FC8D0 188 func_002FC990 002FC990 364 @@ -2447,7 +2412,6 @@ func_00313600 00313600 116 func_00313678 00313678 84 func_003136D0 003136D0 4080 func_003146C0 003146C0 1588 -func_00314CF8 00314CF8 300 func_00314E28 00314E28 420 func_00314FD0 00314FD0 2240 func_003158A8 003158A8 292 @@ -2462,7 +2426,6 @@ func_00316B40 00316B40 136 func_00316BC8 00316BC8 468 func_00316DA0 00316DA0 100 func_00316E08 00316E08 1220 -func_003172D0 003172D0 188 func_00317390 00317390 32 func_003173B0 003173E8 2444 func_00317D78 00317D78 1128 @@ -2499,7 +2462,6 @@ func_0031CDF8 0031CDF8 632 func_0031D070 0031D070 504 func_0031D268 0031D268 156 func_0031D308 0031D308 68 -func_0031D350 0031D350 132 func_0031D3E0 0031D3E0 424 func_0031D588 0031D5A0 1644 func_0031DC18 0031DC18 716 @@ -2508,7 +2470,6 @@ func_0031E2A0 0031E2A0 260 func_0031E3A8 0031E3A8 380 func_0031E528 0031E528 52 func_0031E560 0031E560 372 -func_0031E6D8 0031E6D8 12 func_0031E6E8 0031E6E8 100 func_0031E750 0031E750 136 func_0031E7D8 0031E7D8 288 @@ -2554,7 +2515,6 @@ func_00325EC0 00325EC0 724 func_00326198 003261F0 2080 func_00326A10 00326A10 444 func_00326BD8 00326BD8 208 -func_00326CA8 00326CA8 12 func_00326CB8 00326CB8 212 func_00326D90 00326D90 304 func_00326EC0 00326EC0 376 @@ -2587,7 +2547,7 @@ func_00329CB8 00329CB8 260 func_00329DC0 00329DC0 156 func_00329E60 00329E60 224 func_00329F40 00329F40 496 -func_0032A130 0032A130 16 +func_0032A130 0032A138 8 func_0032A140 0032A140 2104 func_0032A978 0032A978 184 func_0032AA30 0032AA30 400 @@ -2619,7 +2579,6 @@ func_0032E700 0032E708 1052 func_0032EB28 0032EB80 2124 func_0032F3D0 0032F3D0 444 func_0032F598 0032F598 2084 -func_0032FDC0 0032FDC0 12 func_0032FDD0 0032FDD0 216 func_0032FEA8 0032FEA8 304 func_0032FFD8 0032FFD8 376 @@ -2655,12 +2614,10 @@ func_003348A8 003348A8 320 func_003349E8 003349E8 160 func_00334A88 00334A90 1820 func_003351B0 003351B8 184 -func_00335270 00335270 252 func_00335370 00335370 88 func_003353C8 003353C8 88 func_00335438 00335438 364 func_003355A8 003355A8 316 -func_003356E8 003356E8 172 func_00335798 00335798 168 func_00335840 00335840 28 func_00335870 00335870 48 @@ -2743,7 +2700,6 @@ func_00337C10 00337C10 532 func_00337E30 00337E30 104 func_00337E98 00337E98 424 func_00338040 00338040 100 -func_003380A8 003380A8 4 func_003380B0 003380B0 1036 func_003384C0 003384C0 600 func_00338718 00338718 136 @@ -2793,7 +2749,6 @@ func_0033B050 0033B050 88 func_0033B0A8 0033B0A8 8 func_0033B0B8 0033B0B8 164 func_0033B170 0033B170 964 -func_0033B538 0033B538 4 func_0033B540 0033B540 972 func_0033B910 0033B910 1060 func_0033BD38 0033BD38 44 @@ -2985,7 +2940,6 @@ func_00349498 00349498 52 func_003494D0 003494D0 180 func_00349590 00349590 8 func_003495A0 003495A0 20 -func_003495B8 003495B8 4 func_003495C0 003495C0 8 func_003495C8 003495C8 12 func_003495D8 003495D8 52 @@ -3023,7 +2977,6 @@ func_0034CAE8 0034CAE8 160 func_0034CB88 0034CB88 484 func_0034CD70 0034CD70 180 func_0034CE28 0034CE28 96 -func_0034CE88 0034CE88 12 func_0034CE98 0034CE98 8 func_0034CEA0 0034CEA0 3316 func_0034DB98 0034DB98 1088 diff --git a/config/cflags.txt b/config/cflags.txt index 2429de39f..da4de92b4 100644 --- a/config/cflags.txt +++ b/config/cflags.txt @@ -107,6 +107,7 @@ src/game/0029DC58-rc2.c -O2 -G8 -ffunction-sections -fno-builtin src/game/002A7398-rc2.c -O2 -G0 -ffunction-sections -fno-builtin src/game/002A90C8-rc2.c -O2 -G0 -mno-split-addresses -ffunction-sections -fno-builtin src/game/002A9640-rc2.c -O2 -fno-gcse -G0 -ffunction-sections -fno-builtin +src/game/0029F840-nogcse.c -O2 -G0 -ffunction-sections -fno-gcse src/game/002B3670-rc2.c -O2 -G8 -ffunction-sections -fno-builtin src/game/002B7CE0-rc2.c -O2 -G0 -ffunction-sections -fno-builtin src/game/002C1EF0-rc2.c -O2 -G0 -ffunction-sections -fno-builtin @@ -3480,3 +3481,10 @@ src/pal/levels/shared/L01_0039C970-weather-g8.c -O2 -G8 -ffunction-sections -ffa src/pal/levels/01_oozla/L01_003C00F0-debris-g8.c -O2 -G8 -ffunction-sections -g src/pal/levels/shared/L02_00415BD0-g8.c -O2 -G8 -ffunction-sections -frac2-zero-ti-por -g src/pal/levels/03_endako/L03_00421E20-g8.c -O2 -G8 -ffunction-sections -Wa,--r5900-unsigned32-mask=sn +src/levels/shared/L00_00423290-qcopy.c -O2 -G0 -ffunction-sections -frac2-qcopy -frac2-qcopy-barrier +src/levels/shared/L01_00324550-narrowsave.c -O2 -G0 -ffunction-sections -mastra-quad-saves -frac2-narrow-saves-below +src/levels/shared/L08_00389B68-narrowsave.c -O2 -G0 -ffunction-sections -mastra-quad-saves -frac2-narrow-saves-below +src/levels/shared/L00_002FC7A0-00303990-g16.c -O2 -G16 -Wa,-G16 -ffunction-sections +src/levels/shared/L00_003AE900-g8.c -O2 -G8 -ffunction-sections -g -frac2-hazard-labels +src/levels/shared/L03_002AB5C8-state-g8.c -O2 -G8 -ffunction-sections -frac2-hazard-labels -malign-loops=2 +src/game/002F5220-7320.c -O2 -G8 -ffunction-sections -frac2-keep-block-zero-copy diff --git a/config/levels/functions.tsv b/config/levels/functions.tsv index 7e3693053..ffd803cd1 100644 --- a/config/levels/functions.tsv +++ b/config/levels/functions.tsv @@ -639,7 +639,6 @@ func_00288BB8 boot 48 e4d354e43a9df5fd 27 00:002F4220,01:002E9588,02:002F8128,03 func_00288BE8 boot 200 e2702760fec99d9c 27 00:002F4250,01:002E95B8,02:002F8158,03:002F5158,04:00314F98,05:0030C778,06:00333728,07:002EA470,08:002FFF38,09:002F05D0,10:0030EC90,11:00306700,12:002F7AA8,13:002FE8A0,14:002FBDD8,15:0030CD78,16:002ED648,17:002F50C0,18:0030EA58,19:002F1A88,20:003083C8,22:002F9BE0,23:002FE300,24:002F2990,25:00306D48,26:002F44B0,30:002FAFB0 func_00288CB0 boot 128 78adc6813d75279f 27 00:002F4318,01:002E9680,02:002F8220,03:002F5220,04:00315060,05:0030C840,06:003337F0,07:002EA538,08:00300000,09:002F0698,10:0030ED58,11:003067C8,12:002F7B70,13:002FE968,14:002FBEA0,15:0030CE40,16:002ED710,17:002F5188,18:0030EB20,19:002F1B50,20:00308490,22:002F9CA8,23:002FE3C8,24:002F2A58,25:00306E10,26:002F4578,30:002FB078 func_00288D30 boot 12 f44fd4a16adaaf93 27 00:002F4398,01:002E9700,02:002F82A0,03:002F52A0,04:003150E0,05:0030C8C0,06:00333870,07:002EA5B8,08:00300080,09:002F0718,10:0030EDD8,11:00306848,12:002F7BF0,13:002FE9E8,14:002FBF20,15:0030CEC0,16:002ED790,17:002F5208,18:0030EBA0,19:002F1BD0,20:00308510,22:002F9D28,23:002FE448,24:002F2AD8,25:00306E90,26:002F45F8,30:002FB0F8 -func_00288D40 boot 20 7cc9af5e39e13180 25 00:002F43A8,01:002E9710,02:002F82B0,03:002F52B0,04:003150F0,05:0030C8D0,06:00333880,07:002EA5C8,09:002F0728,10:0030EDE8,11:00306858,12:002F7C00,13:002FE9F8,14:002FBF30,15:0030CED0,16:002ED7A0,17:002F5218,18:0030EBB0,20:00308520,22:002F9D38,23:002FE458,24:002F2AE8,25:00306EA0,26:002F4608,30:002FB108 func_00288D58 boot 16 a75da09b651b41e6 27 00:002F43C0,01:002E9728,02:002F82C8,03:002F52C8,04:00315108,05:0030C8E8,06:00333898,07:002EA5E0,08:00300130,09:002F0740,10:0030EE00,11:00306870,12:002F7C18,13:002FEA10,14:002FBF48,15:0030CEE8,16:002ED7B8,17:002F5230,18:0030EBC8,19:002F1C80,20:00308538,22:002F9D50,23:002FE470,24:002F2B00,25:00306EB8,26:002F4620,30:002FB120 func_L00_002F43D0 shared 16 a3234dc79d2b0730 27 00:002F43D0,01:002E9738,02:002F82D8,03:002F52D8,04:00315118,05:0030C8F8,06:003338A8,07:002EA5F0,08:00300140,09:002F0750,10:0030EE10,11:00306880,12:002F7C28,13:002FEA20,14:002FBF58,15:0030CEF8,16:002ED7C8,17:002F5240,18:0030EBD8,19:002F1C90,20:00308548,22:002F9D60,23:002FE480,24:002F2B10,25:00306EC8,26:002F4630,30:002FB130 func_L00_002F43E0 shared 8 94fa2fd9540a9f79 27 00:002F43E0,01:002E9748,02:002F82E8,03:002F52E8,04:00315128,05:0030C908,06:003338B8,07:002EA600,08:00300150,09:002F0760,10:0030EE20,11:00306890,12:002F7C38,13:002FEA30,14:002FBF68,15:0030CF08,16:002ED7D8,17:002F5250,18:0030EBE8,19:002F1CA0,20:00308558,22:002F9D70,23:002FE490,24:002F2B20,25:00306ED8,26:002F4640,30:002FB140 @@ -877,7 +876,6 @@ func_002989B0 boot 112 1cc82cfbdeab32e8 27 00:00309BA8,01:002FF5D8,02:0030DC08,0 func_00298A20 boot 260 8155c7fa3f5c7756 27 00:00309C18,01:002FF648,02:0030DC78,03:0030AED0,04:0032A578,05:00321FE8,06:00349118,07:002FFFD8,08:00316288,09:00305F68,10:003246F0,11:0031BFF0,12:0030D7E0,13:00313EF0,14:00311568,15:003227C0,16:003033E0,17:0030A6A0,18:003241F0,19:00307778,20:0031E138,22:0030F1C8,23:003138E0,24:00307F70,25:0031C340,26:00309DA0,30:00310590 func_00298B28 boot 72 0ab41dd4833d4391 27 00:00309D20,01:002FF750,02:0030DD80,03:0030AFD8,04:0032A680,05:003220F0,06:00349220,07:003000E0,08:00316390,09:00306070,10:003247F8,11:0031C0F8,12:0030D8E8,13:00313FF8,14:00311670,15:003228C8,16:003034E8,17:0030A7A8,18:003242F8,19:00307880,20:0031E240,22:0030F2D0,23:003139E8,24:00308078,25:0031C448,26:00309EA8,30:00310698 func_00298B70 boot 68 e76b288ab529102c 27 00:00309D68,01:002FF798,02:0030DDC8,03:0030B020,04:0032A6C8,05:00322138,06:00349268,07:00300128,08:003163D8,09:003060B8,10:00324840,11:0031C140,12:0030D930,13:00314040,14:003116B8,15:00322910,16:00303530,17:0030A7F0,18:00324340,19:003078C8,20:0031E288,22:0030F318,23:00313A30,24:003080C0,25:0031C490,26:00309EF0,30:003106E0 -func_L00_00309DB0 shared 28 a9a7c64556297f33 27 00:00309DB0,01:002FF7E0,02:0030DE10,03:0030B068,04:0032A710,05:00322180,06:003492B0,07:00300170,08:00316420,09:00306100,10:00324888,11:0031C188,12:0030D978,13:00314088,14:00311700,15:00322958,16:00303578,17:0030A838,18:00324388,19:00307910,20:0031E2D0,22:0030F360,23:00313A78,24:00308108,25:0031C4D8,26:00309F38,30:00310728 func_00298D28 boot 220 77c627edaab8f7ce 27 00:00309DD0,01:002FF800,02:0030DE30,03:0030B088,04:0032A730,05:003221A0,06:003492D0,07:00300190,08:00316440,09:00306120,10:003248A8,11:0031C1A8,12:0030D998,13:003140A8,14:00311720,15:00322978,16:00303598,17:0030A858,18:003243A8,19:00307930,20:0031E2F0,22:0030F380,23:00313A98,24:00308128,25:0031C4F8,26:00309F58,30:00310748 func_00298E08 boot 248 3da0bdb25b0158e8 27 00:00309EB0,01:002FF8E0,02:0030DF10,03:0030B168,04:0032A810,05:00322280,06:003493B0,07:00300270,08:00316520,09:00306200,10:00324988,11:0031C288,12:0030DA78,13:00314188,14:00311800,15:00322A58,16:00303678,17:0030A938,18:00324488,19:00307A10,20:0031E3D0,22:0030F460,23:00313B78,24:00308208,25:0031C5D8,26:0030A038,30:00310828 func_00298F00 boot 7840 86f23a910927a927 27 00:00309FA8,01:002FF9D8,02:0030E008,03:0030B260,04:0032A908,05:00322378,06:003494A8,07:00300368,08:00316618,09:003062F8,10:00324A80,11:0031C380,12:0030DB70,13:00314280,14:003118F8,15:00322B50,16:00303770,17:0030AA30,18:00324580,19:00307B08,20:0031E4C8,22:0030F558,23:00313C70,24:00308300,25:0031C6D0,26:0030A130,30:00310920 @@ -900,7 +898,6 @@ func_0029B758 boot 40 291302a59ff41bc9 27 00:0030C830,01:00302260,02:00310890,03 func_0029B780 boot 64 1427e861cc41e46b 27 00:0030C858,01:00302288,02:003108B8,03:0030DB10,04:0032D1B8,05:00324C28,06:0034BD58,07:00302C18,08:00318EC8,09:00308BA8,10:00327330,11:0031EC30,12:00310420,13:00316B30,14:003141A8,15:00325400,16:00306020,17:0030D2E0,18:00326E30,19:0030A3B8,20:00320D78,22:00311E08,23:00316520,24:0030ABB0,25:0031EF80,26:0030C9E0,30:003131D0 func_0029B7C0 boot 76 8b1fbeb81a3e6632 27 00:0030C898,01:003022C8,02:003108F8,03:0030DB50,04:0032D1F8,05:00324C68,06:0034BD98,07:00302C58,08:00318F08,09:00308BE8,10:00327370,11:0031EC70,12:00310460,13:00316B70,14:003141E8,15:00325440,16:00306060,17:0030D320,18:00326E70,19:0030A3F8,20:00320DB8,22:00311E48,23:00316560,24:0030ABF0,25:0031EFC0,26:0030CA20,30:00313210 func_0029B810 boot 52 26277e90267027ec 27 00:0030C8E8,01:00302318,02:00310948,03:0030DBA0,04:0032D248,05:00324CB8,06:0034BDE8,07:00302CA8,08:00318F58,09:00308C38,10:003273C0,11:0031ECC0,12:003104B0,13:00316BC0,14:00314238,15:00325490,16:003060B0,17:0030D370,18:00326EC0,19:0030A448,20:00320E08,22:00311E98,23:003165B0,24:0030AC40,25:0031F010,26:0030CA70,30:00313260 -func_0029B848 boot 12 d0ab515f5271898e 25 00:0030C920,01:00302350,02:00310980,03:0030DBD8,04:0032D280,05:00324CF0,06:0034BE20,07:00302CE0,09:00308C70,10:003273F8,11:0031ECF8,12:003104E8,13:00316BF8,14:00314270,15:003254C8,16:003060E8,17:0030D3A8,18:00326EF8,20:00320E40,22:00311ED0,23:003165E8,24:0030AC78,25:0031F048,26:0030CAA8,30:00313298 func_L00_0030C930 shared 48 da034f71ee361c9e 27 00:0030C930,01:00302360,02:00310990,03:0030DBE8,04:0032D290,05:00324D00,06:0034BE30,07:00302CF0,08:00318FE8,09:00308C80,10:00327408,11:0031ED08,12:003104F8,13:00316C08,14:00314280,15:003254D8,16:003060F8,17:0030D3B8,18:00326F08,19:0030A4D8,20:00320E50,22:00311EE0,23:003165F8,24:0030AC88,25:0031F058,26:0030CAB8,30:003132A8 func_0029B888 boot 132 9e2e8cec467ddce4 27 00:0030C960,01:00302390,02:003109C0,03:0030DC18,04:0032D2C0,05:00324D30,06:0034BE60,07:00302D20,08:00319018,09:00308CB0,10:00327438,11:0031ED38,12:00310528,13:00316C38,14:003142B0,15:00325508,16:00306128,17:0030D3E8,18:00326F38,19:0030A508,20:00320E80,22:00311F10,23:00316628,24:0030ACB8,25:0031F088,26:0030CAE8,30:003132D8 func_0029B910 boot 328 5ee4e06adbd6720d 27 00:0030C9E8,01:00302418,02:00310A48,03:0030DCA0,04:0032D348,05:00324DE8,06:0034BEE8,07:00302DA8,08:003190A0,09:00308D38,10:003274F0,11:0031EDC0,12:003105B0,13:00316CC0,14:00314338,15:003255C0,16:003061B0,17:0030D470,18:00326FC0,19:0030A590,20:00320F08,22:00311F98,23:003166B0,24:0030AD40,25:0031F140,26:0030CB70,30:00313360 @@ -974,7 +971,6 @@ func_0029CD20 boot 36 b1a38eed6ec77d59 27 00:0030DE28,01:00303858,02:00311E88,03 func_0029CD48 boot 240 c7ed6bee34a1c78d 27 00:0030DE50,01:00303880,02:00311EB0,03:0030F108,04:0032E7B0,05:00326278,06:0034D350,07:00304210,08:0031A508,09:0030A1A0,10:00328980,11:00320228,12:00311A18,13:00318128,14:003157A0,15:00326A50,16:00307618,17:0030E8D8,18:00328428,19:0030B9F8,20:00322370,22:00313400,23:00317B18,24:0030C1A8,25:003205D0,26:0030DFD8,30:003147C8 func_0029CE38 boot 64 39954fe1c04c61ab 27 00:0030DF40,01:00303970,02:00311FA0,03:0030F1F8,04:0032E8A0,05:00326368,06:0034D440,07:00304300,08:0031A5F8,09:0030A290,10:00328A70,11:00320318,12:00311B08,13:00318218,14:00315890,15:00326B40,16:00307708,17:0030E9C8,18:00328518,19:0030BAE8,20:00322460,22:003134F0,23:00317C08,24:0030C298,25:003206C0,26:0030E0C8,30:003148B8 func_0029CE80 boot 72 e99d28063c125cb6 27 00:0030DF88,01:003039B8,02:00311FE8,03:0030F240,04:0032E8E8,05:003263B0,06:0034D488,07:00304348,08:0031A640,09:0030A2D8,10:00328AB8,11:00320360,12:00311B50,13:00318260,14:003158D8,15:00326B88,16:00307750,17:0030EA10,18:00328560,19:0030BB30,20:003224A8,22:00313538,23:00317C50,24:0030C2E0,25:00320708,26:0030E110,30:00314900 -func_0029CEC8 boot 12 c55a3f2cd68b0efb 23 00:0030DFD0,01:00303A00,02:00312030,03:0030F288,04:0032E930,06:0034D4D0,07:00304390,08:0031A688,09:0030A320,11:003203A8,12:00311B98,13:003182A8,14:00315920,16:00307798,17:0030EA58,18:003285A8,19:0030BB78,20:003224F0,22:00313580,23:00317C98,24:0030C328,26:0030E158,30:00314948 func_L00_0030DFE0 shared 48 da034f71ee361c9e 27 00:0030DFE0,01:00303A10,02:00312040,03:0030F298,04:0032E940,05:00326410,06:0034D4E0,07:003043A0,08:0031A698,09:0030A330,10:00328B18,11:003203B8,12:00311BA8,13:003182B8,14:00315930,15:00326BE8,16:003077A8,17:0030EA68,18:003285B8,19:0030BB88,20:00322500,22:00313590,23:00317CA8,24:0030C338,25:00320768,26:0030E168,30:00314958 func_L00_0030E010 shared 60 69b27b9a024d3fc2 27 00:0030E010,01:00303A40,02:00312070,03:0030F2C8,04:0032E970,05:00326440,06:0034D510,07:003043D0,08:0031A6C8,09:0030A360,10:00328B48,11:003203E8,12:00311BD8,13:003182E8,14:00315960,15:00326C18,16:003077D8,17:0030EA98,18:003285E8,19:0030BBB8,20:00322530,22:003135C0,23:00317CD8,24:0030C368,25:00320798,26:0030E198,30:00314988 func_0029CF58 boot 32 a89b04ef259be3a6 27 00:0030E060,01:00303A90,02:003120C0,03:0030F318,04:0032E9C0,05:00326490,06:0034D560,07:00304420,08:0031A718,09:0030A3B0,10:00328B98,11:00320438,12:00311C28,13:00318338,14:003159B0,15:00326C68,16:00307828,17:0030EAE8,18:00328638,19:0030BC08,20:00322580,22:00313610,23:00317D28,24:0030C3B8,25:003207E8,26:0030E1E8,30:003149D8 @@ -1076,7 +1072,6 @@ func_002A7750 boot 60 e3410a4fcb44add9 27 00:0031A658,01:00310418,02:0031E6A0,03 func_002A7790 boot 8 48e89fef3b080e8b 27 00:0031A698,01:00310458,02:0031E6E0,03:0031B960,04:0033B9F0,05:00332A28,06:0035A590,07:00310A08,08:00327798,09:00316998,10:00335130,11:0032CA20,12:0031E210,13:00324920,14:00321F98,15:00333250,16:00313E10,17:0031B0D0,18:003356A8,19:00318280,20:0032F5F0,22:0031FBF8,23:00324310,24:00318918,25:0032CD48,26:0031A7D0,30:00321010 func_002A7798 boot 28 52057157ac08ecfc 27 00:0031A6A0,01:00310460,02:0031E6E8,03:0031B968,04:0033B9F8,05:00332A30,06:0035A598,07:00310A10,08:003277A0,09:003169A0,10:00335138,11:0032CA28,12:0031E218,13:00324928,14:00321FA0,15:00333258,16:00313E18,17:0031B0D8,18:003356B0,19:00318288,20:0032F5F8,22:0031FC00,23:00324318,24:00318920,25:0032CD50,26:0031A7D8,30:00321018 func_L00_0031A6C8 shared 68 ac1429c07dc67499 27 00:0031A6C8,01:00310488,02:0031E710,03:0031B990,04:0033BA20,05:00332A58,06:0035A5C0,07:00310A38,08:003277F8,09:003169C8,10:00335160,11:0032CA50,12:0031E240,13:00324950,14:00321FC8,15:00333280,16:00313E40,17:0031B100,18:003356D8,19:003182E0,20:0032F620,22:0031FC28,23:00324340,24:00318948,25:0032CD78,26:0031A800,30:00321070 -func_L00_0031A710 shared 20 9b5530b036d68e5a 27 00:0031A710,01:003104D0,02:0031E758,03:0031B9D8,04:0033BA68,05:00332AA0,06:0035A608,07:00310A80,08:00327840,09:00316A10,10:003351A8,11:0032CA98,12:0031E288,13:00324998,14:00322010,15:003332C8,16:00313E88,17:0031B148,18:00335720,19:00318328,20:0032F668,22:0031FC70,23:00324388,24:00318990,25:0032CDC0,26:0031A848,30:003210B8 func_002A77E0 boot 60 752eefe39bbc0695 27 00:0031A728,01:003104E8,02:0031E770,03:0031B9F0,04:0033BA80,05:00332AB8,06:0035A620,07:00310A98,08:00327858,09:00316A28,10:003351C0,11:0032CAB0,12:0031E2A0,13:003249B0,14:00322028,15:003332E0,16:00313EA0,17:0031B160,18:00335738,19:00318340,20:0032F680,22:0031FC88,23:003243A0,24:003189A8,25:0032CDD8,26:0031A860,30:003210D0 func_002A7820 boot 84 688b95cb743066f7 27 00:0031A768,01:00310528,02:0031E7B0,03:0031BA30,04:0033BAC0,05:00332AF8,06:0035A660,07:00310AD8,08:00327898,09:00316A68,10:00335200,11:0032CAF0,12:0031E2E0,13:003249F0,14:00322068,15:00333320,16:00313EE0,17:0031B1A0,18:00335778,19:00318380,20:0032F6C0,22:0031FCC8,23:003243E0,24:003189E8,25:0032CE18,26:0031A8A0,30:00321110 func_002A7878 boot 92 0533b520ad58cb39 27 00:0031A7C0,01:00310580,02:0031E808,03:0031BA88,04:0033BB18,05:00332B50,06:0035A6B8,07:00310B30,08:003278F0,09:00316AC0,10:00335258,11:0032CB48,12:0031E338,13:00324A48,14:003220C0,15:00333378,16:00313F38,17:0031B1F8,18:003357D0,19:003183D8,20:0032F718,22:0031FD20,23:00324438,24:00318A40,25:0032CE70,26:0031A8F8,30:00321168 @@ -1363,7 +1358,6 @@ func_002B7F58 boot 84 4b9ab7498ae79d34 27 00:0032E938,01:00324168,02:003353D0,03 func_002B7FB0 boot 60 4dc1aee31e60cb8d 27 00:0032E990,01:003241C0,02:00335428,03:0032FFF0,04:003519B8,05:00341148,06:0036F168,07:00325140,08:0033CAD0,09:0032B158,10:00342EA8,11:00342328,12:00333860,13:003382B0,14:00338820,15:00347098,16:00326AC8,17:00331710,18:00349A98,19:0032BD98,20:00343EE0,22:00331E28,23:00336540,24:003263C0,25:0033B2F0,26:0032E4A0,30:0032F540 func_002B7FF0 boot 88 9b4a4bc151cd164c 27 00:0032E9D0,01:00324200,02:00335468,03:00330030,04:003519F8,05:00341188,06:0036F1A8,07:00325180,08:0033CB10,09:0032B198,10:00342EE8,11:00342368,12:003338A0,13:003382F0,14:00338860,15:003470D8,16:00326B08,17:00331750,18:00349AD8,19:0032BDD8,20:00343F20,22:00331E68,23:00336580,24:00326400,25:0033B330,26:0032E4E0,30:0032F580 func_002B8048 boot 108 720f21e1440eced9 27 00:0032EA28,01:00324258,02:003354C0,03:00330088,04:00351A50,05:003411E0,06:0036F200,07:003251D8,08:0033CB68,09:0032B1F0,10:00342F40,11:003423C0,12:003338F8,13:00338348,14:003388B8,15:00347130,16:00326B60,17:003317A8,18:00349B30,19:0032BE30,20:00343F78,22:00331EC0,23:003365D8,24:00326458,25:0033B388,26:0032E538,30:0032F5D8 -func_002B80B8 boot 76 b57e3f05fadef0e4 15 00:0032EA98,02:00335530,03:003300F8,05:00341250,07:00325248,10:00342FB0,15:003471A0,16:00326BD0,20:00343FE8,22:00331F30,23:00336648,24:003264C8,25:0033B3F8,26:0032E5A8,30:0032F648 func_002B8108 boot 1040 e95c50f4ea3595bc 27 00:0032EAE8,01:00324790,02:00335580,03:00330148,04:00351F88,05:003412A0,06:0036F778,07:00325298,08:0033D0E0,09:0032B768,10:00343000,11:00342938,12:00333E30,13:003384C8,14:00338DF0,15:003471F0,16:00326C20,17:00331D20,18:0034A0A8,19:0032C3A8,20:00344038,22:00331F80,23:00336698,24:00326518,25:0033B448,26:0032E5F8,30:0032F698 func_002B8518 boot 20 358cf4d2b25a8ebe 27 00:0032EEF8,01:00324BA0,02:00335990,03:00330558,04:00352398,05:003416B0,06:0036FB88,07:003256A8,08:0033D4F0,09:0032BB78,10:00343410,11:00342D48,12:00334240,13:003388D8,14:00339200,15:00347600,16:00327030,17:00332130,18:0034A4B8,19:0032C7B8,20:00344448,22:00332390,23:00336AA8,24:00326928,25:0033B858,26:0032EA08,30:0032FAA8 func_L00_0032EF10 shared 160 adc472b577f53c1b 27 00:0032EF10,01:00324BB8,02:003359A8,03:00330570,04:003523B0,05:003416C8,06:0036FBA0,07:003256C0,08:0033D508,09:0032BB90,10:00343428,11:00342D60,12:00334258,13:003388F0,14:00339218,15:00347618,16:00327048,17:00332148,18:0034A4D0,19:0032C7D0,20:00344460,22:003323A8,23:00336AC0,24:00326940,25:0033B870,26:0032EA20,30:0032FAC0 @@ -1910,17 +1904,12 @@ func_002ED368 boot 336 50ae64d7043a3884 27 00:003670F8,01:0035D478,02:0036E808,0 func_002ED4B8 boot 176 bc0fc1c7514ef62b 27 00:00367248,01:0035D5C8,02:0036E958,03:003688A8,04:0038AC40,05:00379698,06:003A8770,07:0035D2D0,08:003757D8,09:003645C8,10:0037B4A8,11:0037BB08,12:0036CB90,13:00370C78,14:003718F8,15:0037FEB8,16:0035F020,17:0036A7E0,18:00383448,19:003652F0,20:0037D2A8,22:0036AAD0,23:0036F1E8,24:0035E7A8,25:003736D8,26:00366BC0,30:00367B48 func_L00_003672F8 shared 16 df716174612d7cad 12 00:003672F8,01:0035D678,02:0036EA08,03:00368958,04:0038ACF0,08:00375888,09:00364678,11:0037BBB8,18:003834F8,19:003653A0,20:0037D358,26:00366C70 func_L00_00367308 shared 276 4792a4b6f9d640da 27 00:00367308,01:0035D688,02:0036EA18,03:00368968,04:0038AD00,05:00379748,06:003A8820,07:0035D380,08:00375898,09:00364688,10:0037B558,11:0037BBC8,12:0036CC40,13:00370D28,14:003719A8,15:0037FF68,16:0035F0D0,17:0036A890,18:00383508,19:003653B0,20:0037D368,22:0036AB80,23:0036F298,24:0035E858,25:00373788,26:00366C80,30:00367BF8 -func_002ED570 boot 4 47be79a1ea98b050 23 00:00367420,01:0035D7A0,02:0036EB30,03:00368A80,04:0038AE18,06:003A8938,07:0035D498,08:003759B0,09:003647A0,11:0037BCE0,12:0036CD58,13:00370E40,14:00371AC0,16:0035F1E8,17:0036A9A8,18:00383620,19:003654C8,20:0037D480,22:0036AC98,23:0036F3B0,24:0035E970,26:00366D98,30:00367D10 func_002ED578 boot 244 09f4b440fb620626 27 00:00367428,01:0035D7A8,02:0036EB38,03:00368A88,04:0038AE20,05:00379870,06:003A8940,07:0035D4A0,08:003759B8,09:003647A8,10:0037B680,11:0037BCE8,12:0036CD60,13:00370E48,14:00371AC8,15:00380090,16:0035F1F0,17:0036A9B0,18:00383628,19:003654D0,20:0037D488,22:0036ACA0,23:0036F3B8,24:0035E978,25:003738B0,26:00366DA0,30:00367D18 func_002ED688 boot 36 9b15f701a714ed25 27 00:00367538,01:0035D8B8,02:0036EC48,03:00368B98,04:0038AF30,05:00379CA0,06:003A8A50,07:0035D5B0,08:00375AC8,09:003648B8,10:0037BA88,11:0037BDF8,12:0036CE70,13:00370F58,14:00371BD8,15:003804E8,16:0035F300,17:0036AAC0,18:00383738,19:003655E0,20:0037D598,22:0036ADB0,23:0036F4C8,24:0035EA88,25:00373CB8,26:00366EB0,30:00367E28 func_002ED6B0 boot 404 5322bea0a656504d 27 00:00367560,01:0035D8E0,02:0036EC70,03:00368BC0,04:0038AF58,05:00379CC8,06:003A8A78,07:0035D5D8,08:00375AF0,09:003648E0,10:0037BAB0,11:0037BE20,12:0036CE98,13:00370F80,14:00371C00,15:00380510,16:0035F328,17:0036AAE8,18:00383760,19:00365608,20:0037D5C0,22:0036ADD8,23:0036F4F0,24:0035EAB0,25:00373CE0,26:00366ED8,30:00367E50 -func_002ED848 boot 36 e93ae62af1dc8ec5 23 00:003676F8,01:0035DA78,02:0036EE08,03:00368D58,04:0038B0F0,06:003A8C10,07:0035D770,08:00375C88,09:00364A78,11:0037BFB8,12:0036D030,13:00371118,14:00371D98,16:0035F4C0,17:0036AC80,18:003838F8,19:003657A0,20:0037D758,22:0036AF70,23:0036F688,24:0035EC48,26:00367070,30:00367FE8 func_L00_00367720 shared 12 ceaacd8dbc655056 27 00:00367720,01:0035DAA0,02:0036EE30,03:00368D80,04:0038B118,05:00379860,06:003A8C38,07:0035D798,08:00375CB0,09:00364AA0,10:0037B670,11:0037BFE0,12:0036D058,13:00371140,14:00371DC0,15:00380080,16:0035F4E8,17:0036ACA8,18:00383920,19:003657C8,20:0037D780,22:0036AF98,23:0036F6B0,24:0035EC70,25:003738A0,26:00367098,30:00368010 -func_002ED880 boot 28 fa4b0329f6fac430 23 00:00367730,01:0035DAB0,02:0036EE40,03:00368D90,04:0038B128,06:003A8C48,07:0035D7A8,08:00375CC0,09:00364AB0,11:0037BFF0,12:0036D068,13:00371150,14:00371DD0,16:0035F4F8,17:0036ACB8,18:00383930,19:003657D8,20:0037D790,22:0036AFA8,23:0036F6C0,24:0035EC80,26:003670A8,30:00368020 func_002ED8A0 boot 76 f50fa26769078085 27 00:00367750,01:0035DAD0,02:0036EE60,03:00368DB0,04:0038B148,05:0037AAC8,06:003A8C68,07:0035D7C8,08:00375CE0,09:00364AD0,10:0037C8B0,11:0037C010,12:0036D088,13:00371170,14:00371DF0,15:00381310,16:0035F518,17:0036ACD8,18:00383950,19:003657F8,20:0037D7B0,22:0036AFC8,23:0036F6E0,24:0035ECA0,25:00374A50,26:003670C8,30:00368040 -func_002ED8F0 boot 84 660cf3e1ece7eb45 23 00:003677A0,01:0035DB20,02:0036EEB0,03:00368E00,04:0038B198,06:003A8CB8,07:0035D818,08:00375D30,09:00364B20,11:0037C060,12:0036D0D8,13:003711C0,14:00371E40,16:0035F568,17:0036AD28,18:003839A0,19:00365848,20:0037D800,22:0036B018,23:0036F730,24:0035ECF0,26:00367118,30:00368090 func_002ED948 boot 96 2e7f6d977748bed2 27 00:003677F8,01:0035DB78,02:0036EF08,03:00368E58,04:0038B1F0,05:0037B660,06:003A8D10,07:0035D870,08:00375D88,09:00364B78,10:0037D4B8,11:0037C0B8,12:0036D130,13:00371218,14:00371E98,15:00381FE0,16:0035F5C0,17:0036AD80,18:003839F8,19:003658A0,20:0037D858,22:0036B070,23:0036F788,24:0035ED48,25:00375508,26:00367170,30:003680E8 -func_002ED9A8 boot 20 84a01a6395fdbcc8 23 00:00367858,01:0035DBD8,02:0036EF68,03:00368EB8,04:0038B250,06:003A8D70,07:0035D8D0,08:00375DE8,09:00364BD8,11:0037C118,12:0036D190,13:00371278,14:00371EF8,16:0035F620,17:0036ADE0,18:00383A58,19:00365900,20:0037D8B8,22:0036B0D0,23:0036F7E8,24:0035EDA8,26:003671D0,30:00368148 func_002ED9C0 boot 76 5dbe38abd55fb984 27 00:00367870,01:0035DBF0,02:0036EF80,03:00368ED0,04:0038B268,05:0037B838,06:003A8D88,07:0035D8E8,08:00375E00,09:00364BF0,10:0037D690,11:0037C130,12:0036D1A8,13:00371290,14:00371F10,15:003821B8,16:0035F638,17:0036ADF8,18:00383A70,19:00365918,20:0037D8D0,22:0036B0E8,23:0036F800,24:0035EDC0,25:003756E0,26:003671E8,30:00368160 func_002EDA10 boot 1444 3911d551b9e99421 23 00:00367908,01:0035DC88,02:0036F018,03:00368F68,04:0038B300,06:003A8E20,07:0035D980,08:00375E98,09:00364C88,11:0037C1C8,12:0036D240,13:00371328,14:00371FA8,16:0035F6D0,17:0036AE90,18:00383B08,19:003659B0,20:0037D968,22:0036B180,23:0036F898,24:0035EE58,26:00367280,30:003681F8 func_002EE000 boot 564 e02434ed982d2727 27 00:00367EB0,01:0035E230,02:0036F5C0,03:00369510,04:0038B8A8,05:0037C708,06:003A93C8,07:0035DF28,08:00376440,09:00365230,10:0037E560,11:0037C770,12:0036D7E8,13:003718D0,14:00372550,15:00383088,16:0035FC78,17:0036B438,18:003840B0,19:00365F58,20:0037DF10,22:0036B728,23:0036FE40,24:0035F400,25:003765B0,26:00367828,30:003687A0 @@ -1935,7 +1924,6 @@ func_002EE8B0 boot 108 39cb94f765fd8735 27 00:00368760,01:0035EAE0,02:0036FE70,0 func_002EE920 boot 104 20c6c5ecec7c54d2 27 00:003687D0,01:0035EB50,02:0036FEE0,03:00369E30,04:0038C1C8,05:0037D378,06:003A9CE8,07:0035E848,08:00376D60,09:00365B50,10:0037F120,11:0037D090,12:0036E108,13:003721F0,14:00372E70,15:00383C48,16:00360598,17:0036BD58,18:003849D0,19:00366878,20:0037E830,22:0036C048,23:00370760,24:0035FD20,25:00377298,26:00368148,30:003690C0 func_002EE988 boot 372 7c3645d3edd48504 27 00:00368838,01:0035EBB8,02:0036FF48,03:00369E98,04:0038C230,05:0037D3E0,06:003A9D50,07:0035E8B0,08:00376DC8,09:00365BB8,10:0037F188,11:0037D0F8,12:0036E170,13:00372258,14:00372ED8,15:00383CB0,16:00360600,17:0036BDC0,18:00384A38,19:003668E0,20:0037E898,22:0036C0B0,23:003707C8,24:0035FD88,25:00377300,26:003681B0,30:00369128 func_002EEB00 boot 176 07f154714e9f2c72 27 00:003689B0,01:0035ED30,02:003700C0,03:0036A010,04:0038C3A8,05:0037D558,06:003A9EC8,07:0035EA28,08:00376F40,09:00365D30,10:0037F300,11:0037D270,12:0036E2E8,13:003723D0,14:00373050,15:00383E28,16:00360778,17:0036BF38,18:00384BB0,19:00366A58,20:0037EA10,22:0036C228,23:00370940,24:0035FF00,25:00377478,26:00368328,30:003692A0 -func_002EEBB0 boot 20 80046512fd4902e8 23 00:00368A60,01:0035EDE0,02:00370170,03:0036A0C0,04:0038C458,06:003A9F78,07:0035EAD8,08:00376FF0,09:00365DE0,11:0037D320,12:0036E398,13:00372480,14:00373100,16:00360828,17:0036BFE8,18:00384C60,19:00366B08,20:0037EAC0,22:0036C2D8,23:003709F0,24:0035FFB0,26:003683D8,30:00369350 func_002EED08 boot 76 ab5eeb96914e323e 27 00:00368A78,01:0035EDF8,02:00370188,03:0036A0D8,04:0038C470,05:0037DD60,06:003A9F90,07:0035EAF0,08:00377008,09:00365DF8,10:0037FBA0,11:0037D338,12:0036E3B0,13:00372498,14:00373118,15:003846C8,16:00360840,17:0036C000,18:00384C78,19:00366B20,20:0037EAD8,22:0036C2F0,23:00370A08,24:0035FFC8,25:00377C78,26:003683F0,30:00369368 func_002EED58 boot 244 3394ab2360b6ec73 27 00:00368AC8,01:0035EE48,02:003701D8,03:0036A128,04:0038C4C0,05:0037DDB0,06:003A9FE0,07:0035EB40,08:00377058,09:00365E48,10:0037FBF0,11:0037D388,12:0036E400,13:003724E8,14:00373168,15:00384718,16:00360890,17:0036C050,18:00384CC8,19:00366B70,20:0037EB28,22:0036C340,23:00370A58,24:00360018,25:00377CC8,26:00368440,30:003693B8 func_002EEE50 boot 128 e7ced99f6bbfe2cf 27 00:00368BC0,01:0035EF40,02:003702D0,03:0036A220,04:0038C5B8,05:0037DEA8,06:003AA0D8,07:0035EC38,08:00377150,09:00365F40,10:0037FCE8,11:0037D480,12:0036E4F8,13:003725E0,14:00373260,15:00384810,16:00360988,17:0036C148,18:00384DC0,19:00366C68,20:0037EC20,22:0036C438,23:00370B50,24:00360110,25:00377DC0,26:00368538,30:003694B0 @@ -2679,7 +2667,7 @@ func_00329CB8 boot 260 82491f892f2f1e90 27 00:003E1CF8,01:003E3470,02:00403F88,0 func_00329DC0 boot 156 4ac8523d5073f212 27 00:003E1E00,01:003E3578,02:00404090,03:003EB060,04:0041C8E0,05:003EA4F8,06:00423648,07:003CC9E8,08:003F06B8,09:003DD720,10:003EAA20,11:0040C3E0,12:003E5B10,13:003E2EF0,14:003EF138,15:003F4718,16:003D13A0,17:003EA9E8,18:003FFBF0,19:003E3AA0,20:00403438,22:003DE4F0,23:003E5A60,24:003C5298,25:003E3198,26:003D25F0,30:003DBD48 func_00329E60 boot 224 8825569e0043745d 27 00:003E1EA0,01:003E3618,02:00404130,03:003EB100,04:0041C980,05:003EA598,06:004236E8,07:003CCA88,08:003F0758,09:003DD7C0,10:003EAAC0,11:0040C480,12:003E5BB0,13:003E2F90,14:003EF1D8,15:003F47B8,16:003D1440,17:003EAA88,18:003FFC90,19:003E3B40,20:004034D8,22:003DE590,23:003E5B00,24:003C5338,25:003E3238,26:003D2690,30:003DBDE8 func_00329F40 boot 496 163226caab62c8f9 27 00:003E1F80,01:003E36F8,02:00404210,03:003EB1E0,04:0041CA60,05:003EA678,06:004237C8,07:003CCB68,08:003F0838,09:003DD8A0,10:003EABA0,11:0040C560,12:003E5C90,13:003E3070,14:003EF2B8,15:003F4898,16:003D1520,17:003EAB68,18:003FFD70,19:003E3C20,20:004035B8,22:003DE670,23:003E5BE0,24:003C5418,25:003E3318,26:003D2770,30:003DBEC8 -func_0032A130 boot 16 92d9c346662e3597 27 00:003E2170,01:003E38E8,02:00404400,03:003EB3D0,04:0041CC50,05:003EA868,06:004239B8,07:003CCD58,08:003F0A28,09:003DDA90,10:003EAD90,11:0040C750,12:003E5E80,13:003E3260,14:003EF4A8,15:003F4A88,16:003D1710,17:003EAD58,18:003FFF60,19:003E3E10,20:004037A8,22:003DE860,23:003E5DD0,24:003C5608,25:003E3508,26:003D2960,30:003DC0B8 +func_0032A130 boot 8 bc6e15da5a72ab85 27 00:003E2178,01:003E38F0,02:00404408,03:003EB3D8,04:0041CC58,05:003EA870,06:004239C0,07:003CCD60,08:003F0A30,09:003DDA98,10:003EAD98,11:0040C758,12:003E5E88,13:003E3268,14:003EF4B0,15:003F4A90,16:003D1718,17:003EAD60,18:003FFF68,19:003E3E18,20:004037B0,22:003DE868,23:003E5DD8,24:003C5610,25:003E3510,26:003D2968,30:003DC0C0 func_L00_003E2180 shared 912 c10da9a183e5018a 27 00:003E2180,01:003E38F8,02:00404798,03:003EB3E0,04:0041CC60,05:003EA878,06:004239C8,07:003CD220,08:003F0A38,09:003DDBE0,10:003EADA0,11:0040C760,12:003E5E90,13:003E3270,14:003EF4B8,15:003F4A98,16:003D1720,17:003EAD68,18:003FFF70,19:003E3E20,20:004037B8,22:003DE870,23:003E5DE0,24:003C5618,25:003E3518,26:003D2CF8,30:003DC0C8 func_L00_003E2510 shared 1724 1d02a6f972ec5d6b 27 00:003E2510,01:003E3C88,02:00404B28,03:003EB770,04:0041CFF0,05:003EAC08,06:00423D58,07:003CD5B0,08:003F0DC8,09:003DDF70,10:003EB130,11:0040CAF0,12:003E6220,13:003E3600,14:003EF848,15:003F4E28,16:003D1AB0,17:003EB0F8,18:00400300,19:003E41B0,20:00403B48,22:003DEC00,23:003E6170,24:003C59A8,25:003E38A8,26:003D3088,30:003DC458 func_L00_003E2BD0 shared 684 85b2451fb7e1fb17 27 00:003E2BD0,01:003E4348,02:004051E8,03:003EBE30,04:0041D6B0,05:003EB2C8,06:00424418,07:003CDC70,08:003F1488,09:003DE630,10:003EB7F0,11:0040D1B0,12:003E68E0,13:003E3CC0,14:003EFF08,15:003F54E8,16:003D2170,17:003EB7B8,18:004009C0,19:003E4870,20:00404208,22:003DF2C0,23:003E6830,24:003C6068,25:003E3F68,26:003D3748,30:003DCB18 @@ -3094,7 +3082,7 @@ func_L00_00424AD8 shared 68 56dec582b1352c2e 27 00:00424AD8,01:00427CE8,02:00450 func_L00_00424B20 shared 36 ab08622a9389d465 27 00:00424B20,01:00427D30,02:00450250,03:00436880,04:00467090,05:0043D028,06:00475D08,07:004213A0,08:004414E8,09:00433950,10:0043EE58,11:00485A20,12:0043AC60,13:00436F68,14:00443008,15:004499C0,16:0042FA78,17:00431510,18:00451FC0,19:004368F0,20:0045BC90,22:00425F20,23:0043B558,24:00404C70,25:0042E1D0,26:00417818,30:00429668 func_L00_00424B48 shared 36 6af8db7ac3d8ba67 27 00:00424B48,01:00427D58,02:00450278,03:004368A8,04:004670B8,05:0043D050,06:00475D30,07:004213C8,08:00441510,09:00433978,10:0043EE80,11:00485A48,12:0043AC88,13:00436F90,14:00443030,15:004499E8,16:0042FAA0,17:00431538,18:00451FE8,19:00436918,20:0045BCB8,22:00425F48,23:0043B580,24:00404C98,25:0042E1F8,26:00417840,30:00429690 func_L00_00424B70 shared 72 6b8116fb9abb08d4 27 00:00424B70,01:00427D80,02:004502A0,03:004368D0,04:004670E0,05:0043D078,06:00475D58,07:004213F0,08:00441538,09:004339A0,10:0043EEA8,11:00485A70,12:0043ACB0,13:00436FB8,14:00443058,15:00449A10,16:0042FAC8,17:00431560,18:00452010,19:00436940,20:0045BCE0,22:00425F70,23:0043B5A8,24:00404CC0,25:0042E220,26:00417868,30:004296B8 -func_L00_00424BB8 shared 72 6b8116fb9abb08d4 27 00:00424BB8,01:00427DC8,02:004502E8,03:00436918,04:00467128,05:0043D0C0,06:00475DA0,07:00421438,08:00441580,09:004339E8,10:0043EEF0,11:00485AB8,12:0043ACF8,13:00437000,14:004430A0,15:00449A58,16:0042FB10,17:004315A8,18:00452058,19:00436988,20:0045BD28,22:00425FB8,23:0043B5F0,24:00404D08,25:0042E268,26:004178B0,30:00429700 +func_L00_00424BB8 shared 72 6b8116fb9abb08d4 27 00:00424BB8,01:00427DC8,02:004502E8,03:00436918,04:00467128,05:0043D0C0,06:00475DA0,07:00421438,08:00441580,09:004339E8,10:0043EEF0,11:00485AB8,12:0043ACF8,13:00437000,14:004430A0,15:00449A58,16:0042FB58,17:004315A8,18:00452058,19:00436988,20:0045BD28,22:00426000,23:0043B638,24:00404D08,25:0042E268,26:004178F8,30:00429700 func_L00_00424C00 shared 40 be6002e7a1fe3fa7 27 00:00424C00,01:00427E10,02:00450330,03:00436960,04:00467170,05:0043D108,06:00475DE8,07:00421480,08:004415C8,09:00433A30,10:0043EF38,11:00485B00,12:0043AD40,13:00437048,14:004430E8,15:00449AA0,16:0042FBA0,17:004315F0,18:004520A0,19:004369D0,20:0045BD70,22:00426048,23:0043B680,24:00404D50,25:0042E2B0,26:00417940,30:00429748 func_L00_00424C28 shared 40 aae0e898ffaaf025 27 00:00424C28,01:00427E38,02:00450358,03:00436988,04:00467198,05:0043D130,06:00475E10,07:004214A8,08:004415F0,09:00433A58,10:0043EF60,11:00485B28,12:0043AD68,13:00437070,14:00443110,15:00449AC8,16:0042FBC8,17:00431618,18:004520C8,19:004369F8,20:0045BD98,22:00426070,23:0043B6A8,24:00404D78,25:0042E2D8,26:00417968,30:00429770 func_L00_00424C60 shared 48 fd57c438f19d737e 27 00:00424C60,01:00427E70,02:00450390,03:004369C0,04:004671D0,05:0043D168,06:00475E48,07:004214E0,08:00441628,09:00433A90,10:0043EF98,11:00485B60,12:0043ADA0,13:004370A8,14:00443148,15:00449B00,16:0042FC00,17:00431650,18:00452100,19:00436A30,20:0045BDD0,22:004260A8,23:0043B6E0,24:00404DB0,25:0042E310,26:004179A0,30:004297A8 @@ -3304,7 +3292,6 @@ func_0033B050 boot 88 ae566b55456422db 27 00:00430980,01:00433988,02:0045BDB8,03 func_0033B0A8 boot 8 b66340e7e4b4ad3e 27 00:004309D8,01:004339E0,02:0045BE10,03:00441948,04:004740A8,05:0044C0D0,06:00482638,07:0042C570,08:0044C8C8,09:0043F6C0,10:0044DC90,11:00492330,12:00447178,13:00444AD0,14:0044ECC8,15:00458D50,16:0043C420,17:0043D4A8,18:0045E1A0,19:00441D80,20:00467B48,22:004313D8,23:00446A10,24:0040F8C0,25:0043D058,26:00422F70,30:004345B0 func_0033B0B8 boot 164 cef2c29f0395319d 27 00:004309E8,01:004339F0,02:0045BE20,03:00441958,04:004740B8,05:0044C0E0,06:00482648,07:0042C580,08:0044C8D8,09:0043F6D0,10:0044DCA0,11:00492340,12:00447188,13:00444AE0,14:0044ECD8,15:00458D60,16:0043C430,17:0043D4B8,18:0045E1B0,19:00441D90,20:00467B58,22:004313E8,23:00446A20,24:0040F8D0,25:0043D068,26:00422F80,30:004345C0 func_0033B170 boot 964 b1d857902db3e481 27 00:00430AA0,01:00433AA8,02:0045BED8,03:00441A10,04:00474170,05:0044C198,06:00482700,07:0042C638,08:0044C990,09:0043F788,10:0044DD58,11:004923F8,12:00447240,13:00444B98,14:0044ED90,15:00458E18,16:0043C4E8,17:0043D570,18:0045E268,19:00441E48,20:00467C10,22:004314A0,23:00446AD8,24:0040F988,25:0043D120,26:00423038,30:00434678 -func_0033B538 boot 4 b88cc87420eed4aa 27 00:00430E68,01:00433E70,02:0045C2A0,03:00441DD8,04:00474538,05:0044C560,06:00482AC8,07:0042CA00,08:0044CD58,09:0043FB50,10:0044E120,11:004927C0,12:00447608,13:00444F60,14:0044F158,15:004591E0,16:0043C8B0,17:0043D938,18:0045E630,19:00442210,20:00467FD8,22:00431868,23:00446EA0,24:0040FD50,25:0043D4E8,26:00423400,30:00434A40 func_0033B540 boot 972 70048804331a0ab2 27 00:00430E70,01:00433E78,02:0045C2A8,03:00441DE0,04:00474540,05:0044C568,06:00482AD0,07:0042CA08,08:0044CD60,09:0043FB58,10:0044E128,11:004927C8,12:00447610,13:00444F68,14:0044F160,15:004591E8,16:0043C8B8,17:0043D940,18:0045E638,19:00442218,20:00467FE0,22:00431870,23:00446EA8,24:0040FD58,25:0043D4F0,26:00423408,30:00434A48 func_0033B910 boot 1060 0552a8156423eca6 27 00:00431240,01:00434248,02:0045C678,03:004421B0,04:00474910,05:0044C938,06:00482EA0,07:0042CDD8,08:0044D130,09:0043FF28,10:0044E4F8,11:00492B98,12:004479E0,13:00445338,14:0044F530,15:004595B8,16:0043CC88,17:0043DD10,18:0045EA08,19:004425E8,20:004683B0,22:00431C40,23:00447278,24:00410128,25:0043D8C0,26:004237D8,30:00434E18 func_L00_00431668 shared 44 d221205177b3720f 27 00:00431668,01:00434670,02:0045CAA0,03:004425D8,04:00474D38,05:0044CD60,06:004832C8,07:0042D200,08:0044D558,09:00440350,10:0044E920,11:00492FC0,12:00447E08,13:00445760,14:0044F958,15:004599E0,16:0043D0B0,17:0043E138,18:0045EE30,19:00442A10,20:004687D8,22:00432068,23:004476A0,24:00410550,25:0043DCE8,26:00423C00,30:00435240 @@ -3496,7 +3483,6 @@ func_00349498 boot 52 90c4f9366d05f9e9 27 00:0043EDC8,01:00441DD0,02:0046A200,03 func_003494D0 boot 180 cdea45d13cf19835 27 00:0043EE00,01:00441E08,02:0046A238,03:0044FD70,04:004824D0,05:0045A4F8,06:00490A60,07:0043A998,08:0045ACF0,09:0044DAE8,10:0045C0B8,11:004A0758,12:004555A0,13:00452EF8,14:0045D0F0,15:00467178,16:0044A848,17:0044B8D0,18:0046C5C8,19:004501A8,20:00475F70,22:0043F800,23:00454E38,24:0041DCE8,25:0044B480,26:00431398,30:004429D8 func_00349590 boot 8 31fcd37f04a168ac 27 00:0043EEC0,01:00441EC8,02:0046A2F8,03:0044FE30,04:00482590,05:0045A5B8,06:00490B20,07:0043AA58,08:0045ADB0,09:0044DBA8,10:0045C178,11:004A0818,12:00455660,13:00452FB8,14:0045D1B0,15:00467238,16:0044A908,17:0044B990,18:0046C688,19:00450268,20:00476030,22:0043F8C0,23:00454EF8,24:0041DDA8,25:0044B540,26:00431458,30:00442A98 func_003495A0 boot 20 04ffc67212d027e8 27 00:0043EED0,01:00441ED8,02:0046A308,03:0044FE40,04:004825A0,05:0045A5C8,06:00490B30,07:0043AA68,08:0045ADC0,09:0044DBB8,10:0045C188,11:004A0828,12:00455670,13:00452FC8,14:0045D1C0,15:00467248,16:0044A918,17:0044B9A0,18:0046C698,19:00450278,20:00476040,22:0043F8D0,23:00454F08,24:0041DDB8,25:0044B550,26:00431468,30:00442AA8 -func_003495B8 boot 4 3d685cd8e4c14f74 27 00:0043EEE8,01:00441EF0,02:0046A320,03:0044FE58,04:004825B8,05:0045A5E0,06:00490B48,07:0043AA80,08:0045ADD8,09:0044DBD0,10:0045C1A0,11:004A0840,12:00455688,13:00452FE0,14:0045D1D8,15:00467260,16:0044A930,17:0044B9B8,18:0046C6B0,19:00450290,20:00476058,22:0043F8E8,23:00454F20,24:0041DDD0,25:0044B568,26:00431480,30:00442AC0 func_003495C0 boot 8 057181dc76824f67 27 00:0043EEF0,01:00441EF8,02:0046A328,03:0044FE60,04:004825C0,05:0045A5E8,06:00490B50,07:0043AA88,08:0045ADE0,09:0044DBD8,10:0045C1A8,11:004A0848,12:00455690,13:00452FE8,14:0045D1E0,15:00467268,16:0044A938,17:0044B9C0,18:0046C6B8,19:00450298,20:00476060,22:0043F8F0,23:00454F28,24:0041DDD8,25:0044B570,26:00431488,30:00442AC8 func_003495C8 boot 12 e1f7ad89507f65b8 27 00:0043EEF8,01:00441F00,02:0046A330,03:0044FE68,04:004825C8,05:0045A5F0,06:00490B58,07:0043AA90,08:0045ADE8,09:0044DBE0,10:0045C1B0,11:004A0850,12:00455698,13:00452FF0,14:0045D1E8,15:00467270,16:0044A940,17:0044B9C8,18:0046C6C0,19:004502A0,20:00476068,22:0043F8F8,23:00454F30,24:0041DDE0,25:0044B578,26:00431490,30:00442AD0 func_003495D8 boot 52 b36c02b8071d414a 27 00:0043EF08,01:00441F10,02:0046A340,03:0044FE78,04:004825D8,05:0045A600,06:00490B68,07:0043AAA0,08:0045ADF8,09:0044DBF0,10:0045C1C0,11:004A0860,12:004556A8,13:00453000,14:0045D1F8,15:00467280,16:0044A950,17:0044B9D8,18:0046C6D0,19:004502B0,20:00476078,22:0043F908,23:00454F40,24:0041DDF0,25:0044B588,26:004314A0,30:00442AE0 @@ -3534,7 +3520,6 @@ func_0034CAE8 boot 160 d4e69711a668804b 27 00:00442418,01:00445420,02:0046D850,0 func_0034CB88 boot 484 6d296443f21d73b5 27 00:004424B8,01:004454C0,02:0046D8F0,03:00453428,04:00485B88,05:0045DBB0,06:00494118,07:0043E050,08:0045E3A8,09:004511A0,10:0045F770,11:004A3E10,12:00458C58,13:004565B0,14:004607A8,15:0046A830,16:0044DF00,17:0044EF88,18:0046FC80,19:00453860,20:00479628,22:00442EB8,23:004584F0,24:004213A0,25:0044EB38,26:00434A50,30:00446090 func_0034CD70 boot 180 39c943fe7ab3e0bf 27 00:004426A0,01:004456A8,02:0046DAD8,03:00453610,04:00485D70,05:0045DD98,06:00494300,07:0043E238,08:0045E590,09:00451388,10:0045F958,11:004A3FF8,12:00458E40,13:00456798,14:00460990,15:0046AA18,16:0044E0E8,17:0044F170,18:0046FE68,19:00453A48,20:00479810,22:004430A0,23:004586D8,24:00421588,25:0044ED20,26:00434C38,30:00446278 func_0034CE28 boot 96 e21c33b017ce3f0a 27 00:00442758,01:00445760,02:0046DB90,03:004536C8,04:00485E28,05:0045DE50,06:004943B8,07:0043E2F0,08:0045E648,09:00451440,10:0045FA10,11:004A40B0,12:00458EF8,13:00456850,14:00460A48,15:0046AAD0,16:0044E1A0,17:0044F228,18:0046FF20,19:00453B00,20:004798C8,22:00443158,23:00458790,24:00421640,25:0044EDD8,26:00434CF0,30:00446330 -func_0034CE88 boot 12 d032aba535f37592 27 00:004427B8,01:004457C0,02:0046DBF0,03:00453728,04:00485E88,05:0045DEB0,06:00494418,07:0043E350,08:0045E6A8,09:004514A0,10:0045FA70,11:004A4110,12:00458F58,13:004568B0,14:00460AA8,15:0046AB30,16:0044E200,17:0044F288,18:0046FF80,19:00453B60,20:00479928,22:004431B8,23:004587F0,24:004216A0,25:0044EE38,26:00434D50,30:00446390 func_L00_004427C8 shared 8 5f01590962e7a75a 27 00:004427C8,01:004457D0,02:0046DC00,03:00453738,04:00485E98,05:0045DEC0,06:00494428,07:0043E360,08:0045E6B8,09:004514B0,10:0045FA80,11:004A4120,12:00458F68,13:004568C0,14:00460AB8,15:0046AB40,16:0044E210,17:0044F298,18:0046FF90,19:00453B70,20:00479938,22:004431C8,23:00458800,24:004216B0,25:0044EE48,26:00434D60,30:004463A0 func_L00_004427D0 shared 8 5f01590962e7a75a 27 00:004427D0,01:004457D8,02:0046DC08,03:00453740,04:00485EA0,05:0045DEC8,06:00494430,07:0043E368,08:0045E6C0,09:004514B8,10:0045FA88,11:004A4128,12:00458F70,13:004568C8,14:00460AC0,15:0046AB48,16:0044E218,17:0044F2A0,18:0046FF98,19:00453B78,20:00479940,22:004431D0,23:00458808,24:004216B8,25:0044EE50,26:00434D68,30:004463A8 func_0034CE98 boot 8 0dbb8687a483dec0 27 00:004427D8,01:004457E0,02:0046DC10,03:00453748,04:00485EA8,05:0045DED0,06:00494438,07:0043E370,08:0045E6C8,09:004514C0,10:0045FA90,11:004A4130,12:00458F78,13:004568D0,14:00460AC8,15:0046AB50,16:0044E220,17:0044F2A8,18:0046FFA0,19:00453B80,20:00479948,22:004431D8,23:00458810,24:004216C0,25:0044EE58,26:00434D70,30:004463B0 @@ -3667,7 +3652,6 @@ func_L01_002C81D0 shared 1112 32c9103c4849315f 4 01:002C81D0,07:002C8A00,11:002E func_L01_002C8990 shared 24 84a2a5424332baa5 8 01:002C8990,04:002F39B0,07:002C91C0,08:002DEFA8,09:002CF268,16:002CC430,18:002EDA30,19:002D0C90 func_L01_002C89A8 shared 24 6b45132fd916ce72 8 01:002C89A8,04:002F39C8,07:002C91D8,08:002DEFC0,09:002CF280,16:002CC448,18:002EDA48,19:002D0CA8 func_L01_002C98B8 shared 84 16ac879f40fb6240 10 01:002C98B8,02:002D75B8,03:002D4BC0,04:002F48D8,08:002DFED0,09:002D0190,12:002D7898,17:002D5140,20:002E8060,30:002DAF38 -func_00280660 boot 12 2c1054e663689292 22 01:002DFDA8,02:002EDC08,03:002EB160,05:003033E0,06:00329CC0,09:002E6738,10:003058E0,11:002FC440,12:002EDCF0,13:002F50C8,15:003039E0,16:002E38B8,17:002EB698,18:00304F68,19:002E84A0,20:002FE6C0,22:002F0830,23:002F4F10,24:002E95F8,25:002FD9B0,26:002EAC78,30:002F17D0 func_L01_002E1510 shared 348 55a78a077cf6b229 13 01:002E1510,02:002EFA00,03:002ECB88,06:0032B7D8,07:002E26C0,08:002F81A0,09:002E80D0,12:002EF718,13:002F6AF0,16:002E52E0,17:002ED030,18:00306900,20:00300058 func_L01_002E1680 shared 416 9c43b8d26395bd91 5 01:002E1680,02:002F0140,03:002ED300,06:0032B948,16:002E5808 func_L01_002E2608 shared 388 2e52620f6c8c4719 4 01:002E2608,02:002F10C8,09:002E95F8,11:002FF678 @@ -3905,7 +3889,6 @@ func_L01_0041C960 level 16 892435a81e3ee6c6 1 01:0041C960 func_L01_0041C970 level 1332 6593b271e41dea1c 1 01:0041C970 func_L01_0042A568 shared 380 0fb94da10a0f6c4a 3 01:0042A568,08:00443D20,09:00436188 func_L01_0042A6F0 shared 132 50f157939ba32647 8 01:0042A6F0,02:00452A98,08:00443EA8,09:00436310,11:00488268,18:00455A20,19:00439138,20:0045E4D8 -func_L01_0042C450 level 12 d307e18564eccf77 1 01:0042C450 func_L01_0042C540 level 920 5f76d9301b50558c 1 01:0042C540 func_L01_0042C8D8 level 1440 2d9082ddb868dbce 1 01:0042C8D8 func_L01_0042CE78 level 108 09b1f78f8f48d1f4 1 01:0042CE78 @@ -4523,7 +4506,7 @@ func_L03_00419C58 shared 72 491f849a4425c9d5 2 03:00419C58,14:00420CE8 func_L03_00419CA0 level 1004 a1c2798395d24262 1 03:00419CA0 func_L03_0041A090 level 1244 3cb82e04030879c7 1 03:0041A090 func_L03_0041A570 level 1088 c753b1399741523e 1 03:0041A570 -func_L03_0041B848 shared 16 bacb80d8a8a76e20 5 03:0041B848,16:0040ECB0,19:00419350,24:003F9DD0,30:0040E190 +func_L03_0041B848 shared 8 bc6e15da5a72ab85 5 03:0041B850,16:0040ECB8,19:00419358,24:003F9DD8,30:0040E198 func_L03_0041BE50 level 3112 d91922fb70b89d59 1 03:0041BE50 func_L03_0041CA78 level 1076 6556f82406902d8e 1 03:0041CA78 func_L03_0041CEB0 level 504 bcff02390acc958c 1 03:0041CEB0 @@ -4839,9 +4822,7 @@ func_L05_00314E28 level 892 391955f0d45ea247 1 05:00314E28 func_L05_00324DB8 shared 48 6c09c7e322c2fc4f 4 05:00324DB8,10:003274C0,15:00325590,25:0031F110 func_L05_003251A0 shared 40 6cab5decfc93b908 4 05:003251A0,10:003278A8,15:00325978,25:0031F4F8 func_L05_003263F8 shared 12 52008d0863ae620f 4 05:003263F8,10:00328B00,15:00326BD0,25:00320750 -func_L05_0033CD40 shared 28 261e6410d33b6cf9 6 05:0033CD40,10:0033EAA0,22:0032AE60,23:0032F578,24:00321FB8,25:00336EE8 func_L05_0033D3A0 shared 1840 5aabb9e0f52fa405 5 05:0033D3A8,10:0033F108,24:00322620,25:00337550,30:0032B460 -func_L05_0033F4A8 shared 156 dfc292e5124853e5 5 05:0033F4A8,10:00341208,24:00324720,25:00339650,30:0032D830 func_L05_00352B28 shared 360 162c615314ebd680 2 05:00352B28,10:00354938 func_L05_00367340 level 272 342c1c32b647fdb6 1 05:00367350 func_L05_00379968 shared 504 8e45051a7f70cab0 4 05:00379968,10:0037B778,15:00380188,25:003739A8 @@ -4877,12 +4858,10 @@ func_L05_0037B280 shared 284 8c80d8d7d42558d0 4 05:0037B280,10:0037D048,15:00381 func_L05_0037B3A0 shared 148 9f639856800e0a66 4 05:0037B3A0,10:0037D168,15:00381BC0,25:00375340 func_L05_0037B440 shared 248 46c4d0c726225dc5 3 05:0037B440,10:0037D298,15:00381DC0 func_L05_0037B538 shared 292 e268379035d983b1 4 05:0037B538,10:0037D390,15:00381EB8,25:003753E0 -func_L05_0037B6C0 shared 12 acd8435708569046 4 05:0037B6C0,10:0037D518,15:00382040,25:00375568 func_L05_0037B6D0 shared 356 b48a41ba8713f007 4 05:0037B6D0,10:0037D528,15:00382050,25:00375578 func_L05_0037B888 shared 188 074e5a0a635cbef1 4 05:0037B888,10:0037D6E0,15:00382208,25:00375730 func_L05_0037B948 shared 480 141355b131c746e8 4 05:0037B948,10:0037D7A0,15:003822C8,25:003757F0 func_L05_0037BB28 shared 80 1847ba6c486ae642 4 05:0037BB28,10:0037D980,15:003824A8,25:003759D0 -func_L05_0037BB78 shared 20 ae8017e88ecc5608 4 05:0037BB78,10:0037D9D0,15:003824F8,25:00375A20 func_L05_0037BB90 shared 40 d49888e7fb4c73ff 4 05:0037BB90,10:0037D9E8,15:00382510,25:00375A38 func_L05_0037BBB8 shared 68 f314cb3e4c5bbc68 4 05:0037BBB8,10:0037DA10,15:00382538,25:00375A60 func_L05_0037BC08 shared 312 0d0660b92e96e730 4 05:0037BC08,10:0037DA60,15:00382588,25:00375AB0 @@ -5646,7 +5625,6 @@ func_L09_003F9D08 shared 888 62dbd05c3c02e148 2 09:003F9D08,20:0041F088 func_L09_003FA080 shared 4512 68ce8924f268dad7 2 09:003FA080,20:0041F400 func_L09_003FB4D0 level 384 7f076b73cba047d6 1 09:003FB4D0 func_L09_003FB650 level 300 9db1faccbdcb90c5 1 09:003FB650 -func_L09_003FB780 shared 4 dc2834da92d18696 3 09:003FB780,22:003B8FE0,23:003BD5D8 func_L09_003FB788 level 216 e4c8e58e6334973d 1 09:003FB788 func_L09_003FB860 level 164 05f35498e2940d7d 1 09:003FB860 func_L09_003FB908 level 240 5ad3f7223d0c4fef 1 09:003FB908 @@ -5763,7 +5741,8 @@ func_L10_00418AD8 level 196 a4f84aac34e37867 1 10:00418AD8 func_L10_00418BA0 level 488 efe1042c999080de 1 10:00418BA0 func_L10_00418D88 shared 868 4dfc9d329ddae9b0 2 10:00418D88,15:0041FF90 func_L10_004190F0 shared 152 ba1c88de52c245a4 2 10:004190F0,15:004202F8 -func_L10_00419188 level 96 741d326f9af76cac 1 10:00419188 +func_L10_00419188 level 88 118d456fa41c7684 1 10:00419188 +func_L10_004191E0 level 8 bc6e15da5a72ab85 1 10:004191E0 func_L10_004191E8 shared 352 365c7aababcf0193 2 10:004191E8,15:00420398 func_L10_00419348 shared 560 62b196008920cabb 2 10:00419348,15:004204F8 func_L10_0041EC10 level 316 5fb3e4d4ef580dbb 1 10:0041EC10 @@ -6441,7 +6420,6 @@ func_L14_004321C8 level 8 bc6e15da5a72ab85 1 14:004321C8 func_L14_004321D0 level 636 774acd0b26518319 1 14:004321D0 func_L14_00432450 level 504 f50eb379a9ead1f1 1 14:00432450 func_L15_00315428 level 1364 ec876b6a18f76f72 1 15:00315428 -func_002B0A08 boot 12 f5734634747b0b7d 3 15:0033E450,19:00323958,26:003258F8 func_L15_0036DAB0 shared 272 82d6fb831e709ac0 2 15:0036DAC0,18:00371100 func_L15_003804B8 level 44 38effbdcc28ad3fd 1 15:003804B8 func_L15_00381CF0 level 208 076916ba408e5a4d 1 15:00381CF0 @@ -6616,7 +6594,7 @@ func_L16_0041F1F0 level 364 a106e4c53e568836 1 16:0041F1F0 func_L16_0041F360 level 576 1085489f5ab59345 1 16:0041F360 func_L16_0041F950 shared 368 2c000a38e014aee3 2 16:0041F950,30:00415740 func_L16_00424B48 level 160 11176b4d7453abba 1 16:00424B50 -func_L16_0042FB58 shared 72 6b8116fb9abb08d4 4 16:0042FB58,22:00426000,23:0043B638,26:004178F8 +func_L16_0042FB10 shared 72 6b8116fb9abb08d4 4 16:0042FB10,22:00425FB8,23:0043B5F0,26:004178B0 func_L16_00435CE8 level 1988 3914b84b303f69c9 1 16:00435CE8 func_L16_004364B0 shared 32 ddd8e32f9e36739a 4 16:004364B0,22:0042B468,23:00440AA0,26:0041CD60 func_L17_00326F38 shared 104 75e1169fb4573d97 2 17:00326F38,18:0033FCA8 @@ -7328,7 +7306,6 @@ func_L23_0041E260 level 44 ef7c5a2acfe4ae55 1 23:0041E260 func_L23_0041E290 level 308 185178c273d9e591 1 23:0041E290 func_L23_0041E3C8 level 76 ae7ce52a1d270c98 1 23:0041E3C8 func_L23_0041E418 level 284 a53d0483ecb7f3ad 1 23:0041E418 -func_L23_0041E538 level 12 34b07fab5514db8f 1 23:0041E538 func_L23_0041E548 level 36 187a50c96ffbc146 1 23:0041E548 func_L23_0041E570 level 64 48bef8eca57e3ae4 1 23:0041E570 func_L23_0041E5B0 level 168 528ef386129f58cd 1 23:0041E5B0 @@ -7380,9 +7357,6 @@ func_L24_00383C30 level 776 5a7d0e2fd5e8e440 1 24:00383C30 func_L24_00389210 level 5868 a7ee82b381b58174 1 24:00389210 func_L24_003B3C38 level 1804 497a6ef48e8d8710 1 24:003B3C38 func_L24_003EFA38 shared 1368 8439c2bb45da83ae 2 24:003EFA40,25:0040F750 -func_L25_00373ED0 level 4 be96ef5f6a9b0a3a 1 25:00373ED0 -func_L25_00373EE0 level 20 97a7ba7bf7023520 1 25:00373EE0 -func_L25_00373F08 level 4 e948bc05cd743d07 1 25:00373F08 func_L25_003752D8 level 104 1a73540a442fc2e3 1 25:003752D8 func_L25_00376FE0 level 120 92f9ed972df6799e 1 25:00376FE0 func_L25_00377608 level 120 92f9ed972df6799e 1 25:00377608 @@ -7412,7 +7386,6 @@ func_L26_003DF7E8 level 784 43b085032a92fa50 1 26:003DF7E8 func_L26_004070F8 level 312 dc976ff74304c418 1 26:004070F8 func_L26_0040C8A8 level 232 a4accbed98c96ba0 1 26:0040C8A8 func_L26_0041C598 level 1988 400889bbcea9d5aa 1 26:0041C598 -func_L30_0032AAF0 level 20 5e3c9c126e52756e 1 30:0032AAF0 func_L30_003557F0 level 272 c9e8cf5cfff7d2c2 1 30:00355800 func_L30_00382EF0 level 28 0aec05893bf71f32 1 30:00382EF0 func_L30_00382F10 level 168 f6638a3f3ba13659 1 30:00382F10 diff --git a/config/pal/boot/functions.tsv b/config/pal/boot/functions.tsv index a6d5c5c2a..fe5145c7c 100644 --- a/config/pal/boot/functions.tsv +++ b/config/pal/boot/functions.tsv @@ -47,7 +47,7 @@ func_00118D98 00118D98 3368 func_00119AC0 00119AC0 264 func_00119BC8 00119BC8 48 func_00119BF8 00119BF8 3072 -func_0011A7F8 0011A7F8 24 +func_0011A7F8 0011A800 16 func_0011A810 0011A810 16 func_0011A820 0011A820 16 func_0011A830 0011A830 16 @@ -194,7 +194,6 @@ func_0011B328 0011B328 164 func_0011B3D0 0011B3D0 124 func_0011B458 0011B458 164 func_0011B500 0011B500 124 -func_0011B580 0011B580 8 func_0011B588 0011B588 104 func_0011B5F0 0011B5F0 104 func_0011B658 0011B658 104 @@ -224,7 +223,6 @@ func_0011C820 0011C820 96 func_0011C880 0011C880 28 func_0011C8A0 0011C8A0 12 func_0011C8B0 0011C8B0 24 -func_0011C8C8 0011C8C8 12 func_0011C8D8 0011C8D8 640 func_0011CB58 0011CB58 52 func_0011CB90 0011CB90 44 @@ -264,13 +262,11 @@ func_0011E4E0 0011E4E0 608 func_0011E740 0011E7A0 136 func_0011E828 0011E828 128 func_0011E8A8 0011E8A8 120 -func_0011E920 0011E920 24 func_0011E938 0011E938 256 func_0011EA38 0011EA38 140 func_0011EAC8 0011EAC8 56 func_0011EB00 0011EB00 520 func_0011ED08 0011ED08 28 -func_0011ED28 0011ED28 56 func_0011ED60 0011ED60 316 func_0011EEA0 0011EEA0 56 func_0011EED8 0011EED8 272 @@ -301,7 +297,6 @@ func_0011F938 0011F938 172 func_0011F9E4 0011F9E8 48 func_0011FA18 0011FA18 8 func_0011FA20 0011FA20 40 -func_0011FA48 0011FA48 8 func_0011FA50 0011FA50 16 func_0011FA60 0011FA60 16 func_0011FA70 0011FA70 56 @@ -355,7 +350,6 @@ func_00123268 00123268 44 func_00123298 00123298 84 func_001232F0 001232F0 268 func_00123400 00123400 144 -func_00123490 00123490 44 func_001234C0 001234C0 44 func_001234F0 001234F0 64 func_00123530 00123530 68 @@ -459,7 +453,6 @@ func_001291A0 001291A0 116 func_00129218 00129218 164 func_001292C0 001292C0 168 func_00129368 00129368 168 -func_00129410 00129410 64 func_00129450 00129450 592 func_001296A0 001296A0 1796 func_00129DA8 00129DA8 1052 @@ -546,7 +539,6 @@ func_0012F690 0012F690 168 func_0012F738 0012F738 520 func_0012F940 0012F940 8 func_0012F948 0012F950 72 -func_0012F998 0012F998 16 func_0012F9A8 0012F9A8 12 func_0012F9B8 0012F9B8 16 func_0012F9C8 0012F9C8 80 @@ -554,7 +546,6 @@ func_0012FA18 0012FA18 84 func_0012FA70 0012FA70 36 func_0012FA98 0012FA98 80 func_0012FAE8 0012FAE8 36 -func_0012FB10 0012FB10 52 func_0012FB48 0012FB48 20 func_0012FB60 0012FB60 12 func_0012FB70 0012FB70 12 @@ -584,7 +575,6 @@ func_00130A70 00130A70 12 func_00130A80 00130A80 12 func_00130A8C 00130A90 12 func_00130AA0 00130AA0 12 -func_00130AAC 00130AAC 4 func_00130AB0 00130AB0 100 func_00130B18 00130B18 100 func_00130B80 00130B80 228 @@ -716,7 +706,6 @@ func_0026F810 0026F6B0 1068 func_0026FC78 0026FAE8 464 func_PAL_0026FCB8 0026FCB8 108 func_0026FEB8 0026FD28 56 -func_0026FEF0 0026FD60 20 func_0026FF08 0026FD78 268 func_00270018 0026FE88 396 func_002701B0 00270020 92 @@ -747,9 +736,7 @@ func_00272198 00272038 48 func_002721C8 00272068 184 func_00272280 00272120 228 func_PAL_00272208 00272208 472 -func_00272540 002723E0 12 func_00272550 002723F0 120 -func_002725C8 00272468 20 func_002725E0 00272480 956 func_002729A0 00272840 784 func_PAL_00272B50 00272B50 1632 @@ -877,7 +864,6 @@ func_00280328 00280BF0 488 func_00280510 00280DD8 240 func_PAL_00280EC8 00280EC8 36 func_00280630 00280EF0 48 -func_00280660 00280F20 12 func_00280670 00280F30 160 func_00280710 00280FD0 484 func_002808F8 002811B8 376 @@ -1054,7 +1040,6 @@ func_00288BB8 002894D0 48 func_00288BE8 00289500 200 func_00288CB0 002895C8 128 func_00288D30 00289648 12 -func_00288D40 00289658 20 func_00288D58 00289670 16 func_00288D68 00289680 8 func_00288D70 00289688 12 @@ -1135,7 +1120,6 @@ func_002900B8 00290938 1388 func_PAL_00290EA8 00290EA8 64 func_00290670 00290EF0 12 func_00290680 00290F00 148 -func_00290718 00290F98 4 func_00290720 00290FA0 8 func_00290728 00290FA8 8 func_00290730 00290FB0 24 @@ -1259,7 +1243,6 @@ func_PAL_00299518 00299518 8 func_PAL_00299520 00299520 24 func_PAL_00299538 00299538 20 func_00298BB8 00299550 340 -func_00298D10 002996A8 20 func_00298D28 002996C0 220 func_PAL_002997A0 002997A0 248 func_PAL_00299898 00299898 7840 @@ -1281,7 +1264,6 @@ func_PAL_0029C0F0 0029C0F0 40 func_PAL_0029C118 0029C118 64 func_PAL_0029C158 0029C158 76 func_PAL_0029C1A8 0029C1A8 52 -func_0029B848 0029C1E0 12 func_PAL_0029C1F0 0029C1F0 48 func_PAL_0029C220 0029C220 132 func_PAL_0029C2A8 0029C2A8 1400 @@ -1598,11 +1580,9 @@ func_002B39A0 002B4530 384 func_002B3B20 002B46B0 132 func_002B3BA8 002B4738 1152 func_002B4038 002B4BC8 36 -func_002B4068 002B4BF8 36 func_002B4090 002B4C20 272 func_PAL_002B4D38 002B4D38 788 func_PAL_002B5050 002B5050 1248 -func_002B49A0 002B5530 12 func_PAL_002B5540 002B5540 40 func_PAL_002B5570 002B5570 8 func_002B49C8 002B5578 20 @@ -1667,10 +1647,8 @@ func_002B7F58 002B8B10 84 func_002B7FB0 002B8B68 60 func_002B7FF0 002B8BA8 88 func_002B8048 002B8C00 108 -func_002B80B8 002B8C70 76 func_002B8108 002B8CC0 1040 func_002B8518 002B90D0 20 -func_002B8530 002B90E8 20 func_002B8548 002B9100 176 func_PAL_002B91B0 002B91B0 656 func_002B8888 002B9440 100 @@ -2073,7 +2051,6 @@ func_002DF1F8 002DFFC8 232 func_002DF2E0 002E00B0 160 func_002DF380 002E0150 120 func_002DF3F8 002E01C8 564 -func_002DF630 002E0400 12 func_002DF640 002E0410 272 func_002DF750 002E0520 84 func_002DF7A8 002E0578 144 @@ -2173,15 +2150,11 @@ func_002ED260 002EE178 88 func_002ED2B8 002EE1D0 172 func_002ED368 002EE280 336 func_002ED4B8 002EE3D0 176 -func_002ED570 002EE488 4 func_PAL_002EE490 002EE490 236 func_002ED688 002EE598 36 func_PAL_002EE5C0 002EE5C0 404 -func_002ED848 002EE758 36 func_002ED870 002EE780 12 -func_002ED880 002EE790 28 func_002ED8A0 002EE7B0 76 -func_002ED8F0 002EE800 84 func_002ED948 002EE858 96 func_PAL_002EE8B8 002EE8B8 16 func_002ED9C0 002EE8C8 76 @@ -2198,7 +2171,6 @@ func_PAL_002EF800 002EF800 108 func_002EE920 002EF870 104 func_002EE988 002EF8D8 372 func_002EEB00 002EFA50 176 -func_002EEBB0 002EFB00 20 func_002EEBC8 002EFB18 320 func_002EED08 002EFC58 76 func_002EED58 002EFCA8 244 @@ -2284,17 +2256,13 @@ func_002FC220 002FD278 96 func_002FC280 002FD2D8 316 func_002FC3C0 002FD418 76 func_002FC410 002FD468 76 -func_002FC460 002FD4B8 4 func_002FC468 002FD4C0 164 -func_002FC510 002FD568 4 func_002FC518 002FD570 72 func_002FC560 002FD5B8 180 -func_002FC618 002FD670 4 func_002FC620 002FD678 284 func_002FC748 002FD7A0 92 func_002FC7A8 002FD800 92 func_002FC808 002FD860 92 -func_002FC868 002FD8C0 4 func_002FC870 002FD8C8 92 func_002FC8D0 002FD928 188 func_002FC990 002FD9E8 364 @@ -2464,7 +2432,6 @@ func_00316B40 00318068 136 func_PAL_003180F0 003180F0 468 func_00316DA0 003182C8 100 func_00316E08 00318330 1220 -func_003172D0 003187F8 188 func_00317390 003188B8 32 func_PAL_003188D8 00318910 2508 func_PAL_003192E0 003192E0 1128 @@ -2510,7 +2477,6 @@ func_PAL_0031F8B8 0031F8B8 260 func_0031E3A8 0031F9C0 380 func_0031E528 0031FB40 52 func_0031E560 0031FB78 372 -func_0031E6D8 0031FCF0 12 func_0031E6E8 0031FD00 100 func_0031E750 0031FD68 136 func_0031E7D8 0031FDF0 288 @@ -2556,7 +2522,6 @@ func_00325EC0 00327628 724 func_PAL_003278FC 00327950 2112 func_00326A10 00328190 444 func_00326BD8 00328358 208 -func_00326CA8 00328428 12 func_PAL_00328438 00328438 252 func_PAL_00328538 00328538 304 func_00326EC0 00328668 376 @@ -2589,7 +2554,7 @@ func_PAL_0032B4A8 0032B4A8 260 func_00329DC0 0032B5B0 156 func_PAL_0032B650 0032B650 224 func_PAL_0032B730 0032B730 496 -func_PAL_0032B920 0032B920 16 +func_PAL_0032B920 0032B928 8 func_PAL_0032B930 0032BB30 1592 func_0032A978 0032C168 184 func_PAL_0032C220 0032C220 400 @@ -2776,7 +2741,7 @@ func_PAL_0033B9F8 0033B9F8 1100 func_PAL_0033BE50 0033BE50 1204 func_PAL_0033C308 0033C308 192 func_0033A4A0 0033C3C8 116 -func_0033A520 0033C448 360 +func_PAL_0033C448 0033C448 360 func_PAL_0033C5B0 0033C5B0 76 func_PAL_0033C600 0033C600 748 func_PAL_0033C8F0 0033C8F0 8 @@ -2796,7 +2761,6 @@ func_PAL_0033CF78 0033CF78 88 func_PAL_0033CFD0 0033CFD0 8 func_PAL_0033CFE0 0033CFE0 164 func_PAL_0033D098 0033D098 964 -func_0033B538 0033D460 4 func_PAL_0033D468 0033D468 972 func_PAL_0033D838 0033D838 1060 func_PAL_0033DC60 0033DC60 44 @@ -2989,7 +2953,6 @@ func_00349498 0034B660 52 func_003494D0 0034B698 180 func_00349590 0034B758 8 func_003495A0 0034B768 20 -func_003495B8 0034B780 4 func_003495C0 0034B788 8 func_003495C8 0034B790 12 func_003495D8 0034B7A0 52 diff --git a/config/pal/levels/functions.tsv b/config/pal/levels/functions.tsv index 153f25924..50306265a 100644 --- a/config/pal/levels/functions.tsv +++ b/config/pal/levels/functions.tsv @@ -652,7 +652,6 @@ func_00288BB8 boot 48 e4d354e43a9df5fd 27 00:002F5868,01:002EA8E8,02:002F97C8,03 func_00288BE8 boot 200 e2702760fec99d9c 27 00:002F5898,01:002EA918,02:002F97F8,03:002F6768,04:003165C8,05:0030DD10,06:00334DC0,07:002EB8E0,08:00301390,09:002F1B58,10:00310228,11:00307C18,12:002F8F38,13:002FFEB8,14:002FD420,15:0030E390,16:002EEB70,17:002F6730,18:00310008,19:002F2E20,20:00309A80,22:002FB160,23:002FF880,24:002F3F28,25:003082E0,26:002F5B48,30:002FC560 func_00288CB0 boot 128 e2afd99b9b936cd9 27 00:002F5960,01:002EA9E0,02:002F98C0,03:002F6830,04:00316690,05:0030DDD8,06:00334E88,07:002EB9A8,08:00301458,09:002F1C20,10:003102F0,11:00307CE0,12:002F9000,13:002FFF80,14:002FD4E8,15:0030E458,16:002EEC38,17:002F67F8,18:003100D0,19:002F2EE8,20:00309B48,22:002FB228,23:002FF948,24:002F3FF0,25:003083A8,26:002F5C10,30:002FC628 func_00288D30 boot 12 f44fd4a16adaaf93 27 00:002F59E0,01:002EAA60,02:002F9940,03:002F68B0,04:00316710,05:0030DE58,06:00334F08,07:002EBA28,08:003014D8,09:002F1CA0,10:00310370,11:00307D60,12:002F9080,13:00300000,14:002FD568,15:0030E4D8,16:002EECB8,17:002F6878,18:00310150,19:002F2F68,20:00309BC8,22:002FB2A8,23:002FF9C8,24:002F4070,25:00308428,26:002F5C90,30:002FC6A8 -func_00288D40 boot 20 7cc9af5e39e13180 25 00:002F59F0,01:002EAA70,02:002F9950,03:002F68C0,04:00316720,05:0030DE68,06:00334F18,07:002EBA38,09:002F1CB0,10:00310380,11:00307D70,12:002F9090,13:00300010,14:002FD578,15:0030E4E8,16:002EECC8,17:002F6888,18:00310160,20:00309BD8,22:002FB2B8,23:002FF9D8,24:002F4080,25:00308438,26:002F5CA0,30:002FC6B8 func_00288D58 boot 16 a75da09b651b41e6 27 00:002F5A08,01:002EAA88,02:002F9968,03:002F68D8,04:00316738,05:0030DE80,06:00334F30,07:002EBA50,08:00301588,09:002F1CC8,10:00310398,11:00307D88,12:002F90A8,13:00300028,14:002FD590,15:0030E500,16:002EECE0,17:002F68A0,18:00310178,19:002F3018,20:00309BF0,22:002FB2D0,23:002FF9F0,24:002F4098,25:00308450,26:002F5CB8,30:002FC6D0 func_L00_002F43D0 shared 16 a3234dc79d2b0730 27 00:002F5A18,01:002EAA98,02:002F9978,03:002F68E8,04:00316748,05:0030DE90,06:00334F40,07:002EBA60,08:00301598,09:002F1CD8,10:003103A8,11:00307D98,12:002F90B8,13:00300038,14:002FD5A0,15:0030E510,16:002EECF0,17:002F68B0,18:00310188,19:002F3028,20:00309C00,22:002FB2E0,23:002FFA00,24:002F40A8,25:00308460,26:002F5CC8,30:002FC6E0 func_L00_002F43E0 shared 8 94fa2fd9540a9f79 27 00:002F5A28,01:002EAAA8,02:002F9988,03:002F68F8,04:00316758,05:0030DEA0,06:00334F50,07:002EBA70,08:003015A8,09:002F1CE8,10:003103B8,11:00307DA8,12:002F90C8,13:00300048,14:002FD5B0,15:0030E520,16:002EED00,17:002F68C0,18:00310198,19:002F3038,20:00309C10,22:002FB2F0,23:002FFA10,24:002F40B8,25:00308470,26:002F5CD8,30:002FC6F0 @@ -897,7 +896,6 @@ func_PAL_L00_0030BA48 shared 8 17b4ae028fe3a32c 27 00:0030BA48,01:00301270,02:00 func_PAL_00299520 boot 24 0f46ab5bc3877e79 27 00:0030BA50,01:00301278,02:0030FB90,03:0030CD60,04:0032C398,05:00323D70,06:0034AF90,07:00301C38,08:00317FD8,09:00307CE8,10:00326478,11:0031DD88,12:0030F4B0,13:00315CF8,14:003133A0,15:003245C8,16:00305100,17:0030C500,18:00325FA8,19:00309300,20:00320080,22:00310F38,23:00315650,24:00309CF8,25:0031E0C8,26:0030BC78,30:00312330 func_PAL_00299538 boot 20 26599166970257eb 27 00:0030BA68,01:00301290,02:0030FBA8,03:0030CD78,04:0032C3B0,05:00323D88,06:0034AFA8,07:00301C50,08:00317FF0,09:00307D00,10:00326490,11:0031DDA0,12:0030F4C8,13:00315D10,14:003133B8,15:003245E0,16:00305118,17:0030C518,18:00325FC0,19:00309318,20:00320098,22:00310F50,23:00315668,24:00309D10,25:0031E0E0,26:0030BC90,30:00312348 func_PAL_L00_0030BA80 shared 340 045ba2f8ea65ab57 27 00:0030BA80,01:003012A8,02:0030FBC0,03:0030CD90,04:0032C3C8,05:00323DA0,06:0034AFC0,07:00301C68,08:00318008,09:00307D18,10:003264A8,11:0031DDB8,12:0030F4E0,13:00315D28,14:003133D0,15:003245F8,16:00305130,17:0030C530,18:00325FD8,19:00309330,20:003200B0,22:00310F68,23:00315680,24:00309D28,25:0031E0F8,26:0030BCA8,30:00312360 -func_L00_00309DB0 shared 28 a9a7c64556297f33 27 00:0030BBD0,01:003013F8,02:0030FD10,03:0030CEE0,04:0032C518,05:00323EF0,06:0034B110,07:00301DB8,08:00318158,09:00307E68,10:003265F8,11:0031DF08,12:0030F630,13:00315E78,14:00313520,15:00324748,16:00305280,17:0030C680,18:00326128,19:00309480,20:00320200,22:003110B8,23:003157D0,24:00309E78,25:0031E248,26:0030BDF8,30:003124B0 func_00298D28 boot 220 77c627edaab8f7ce 27 00:0030BBF0,01:00301418,02:0030FD30,03:0030CF00,04:0032C538,05:00323F10,06:0034B130,07:00301DD8,08:00318178,09:00307E88,10:00326618,11:0031DF28,12:0030F650,13:00315E98,14:00313540,15:00324768,16:003052A0,17:0030C6A0,18:00326148,19:003094A0,20:00320220,22:003110D8,23:003157F0,24:00309E98,25:0031E268,26:0030BE18,30:003124D0 func_PAL_002997A0 boot 248 540bcc86e7aac61f 27 00:0030BCD0,01:003014F8,02:0030FE10,03:0030CFE0,04:0032C618,05:00323FF0,06:0034B210,07:00301EB8,08:00318258,09:00307F68,10:003266F8,11:0031E008,12:0030F730,13:00315F78,14:00313620,15:00324848,16:00305380,17:0030C780,18:00326228,19:00309580,20:00320300,22:003111B8,23:003158D0,24:00309F78,25:0031E348,26:0030BEF8,30:003125B0 func_PAL_00299898 boot 7840 b49e7c0880fbddb6 27 00:0030BDC8,01:003015F0,02:0030FF08,03:0030D0D8,04:0032C710,05:003240E8,06:0034B308,07:00301FB0,08:00318350,09:00308060,10:003267F0,11:0031E100,12:0030F828,13:00316070,14:00313718,15:00324940,16:00305478,17:0030C878,18:00326320,19:00309678,20:003203F8,22:003112B0,23:003159C8,24:0030A070,25:0031E440,26:0030BFF0,30:003126A8 @@ -921,7 +919,6 @@ func_PAL_0029C0F0 boot 40 291302a59ff41bc9 27 00:0030E680,01:00303EA8,02:003127C func_PAL_0029C118 boot 64 1427e861cc41e46b 27 00:0030E6A8,01:00303ED0,02:003127E8,03:0030F9B8,04:0032EFF0,05:003269C8,06:0034DBE8,07:00304890,08:0031AC30,09:0030A940,10:003290D0,11:003209E0,12:00312108,13:00318950,14:00315FF8,15:00327220,16:00307D58,17:0030F158,18:00328C00,19:0030BF58,20:00322CD8,22:00313B90,23:003182A8,24:0030C950,25:00320D20,26:0030E8D0,30:00314F88 func_PAL_0029C158 boot 76 8b1fbeb81a3e6632 27 00:0030E6E8,01:00303F10,02:00312828,03:0030F9F8,04:0032F030,05:00326A08,06:0034DC28,07:003048D0,08:0031AC70,09:0030A980,10:00329110,11:00320A20,12:00312148,13:00318990,14:00316038,15:00327260,16:00307D98,17:0030F198,18:00328C40,19:0030BF98,20:00322D18,22:00313BD0,23:003182E8,24:0030C990,25:00320D60,26:0030E910,30:00314FC8 func_PAL_0029C1A8 boot 52 26277e90267027ec 27 00:0030E738,01:00303F60,02:00312878,03:0030FA48,04:0032F080,05:00326A58,06:0034DC78,07:00304920,08:0031ACC0,09:0030A9D0,10:00329160,11:00320A70,12:00312198,13:003189E0,14:00316088,15:003272B0,16:00307DE8,17:0030F1E8,18:00328C90,19:0030BFE8,20:00322D68,22:00313C20,23:00318338,24:0030C9E0,25:00320DB0,26:0030E960,30:00315018 -func_0029B848 boot 12 d0ab515f5271898e 25 00:0030E770,01:00303F98,02:003128B0,03:0030FA80,04:0032F0B8,05:00326A90,06:0034DCB0,07:00304958,09:0030AA08,10:00329198,11:00320AA8,12:003121D0,13:00318A18,14:003160C0,15:003272E8,16:00307E20,17:0030F220,18:00328CC8,20:00322DA0,22:00313C58,23:00318370,24:0030CA18,25:00320DE8,26:0030E998,30:00315050 func_PAL_L00_0030E780 shared 48 da034f71ee361c9e 27 00:0030E780,01:00303FA8,02:003128C0,03:0030FA90,04:0032F0C8,05:00326AA0,06:0034DCC0,07:00304968,08:0031AD50,09:0030AA18,10:003291A8,11:00320AB8,12:003121E0,13:00318A28,14:003160D0,15:003272F8,16:00307E30,17:0030F230,18:00328CD8,19:0030C078,20:00322DB0,22:00313C68,23:00318380,24:0030CA28,25:00320DF8,26:0030E9A8,30:00315060 func_PAL_0029C220 boot 132 9e2e8cec467ddce4 27 00:0030E7B0,01:00303FD8,02:003128F0,03:0030FAC0,04:0032F0F8,05:00326AD0,06:0034DCF0,07:00304998,08:0031AD80,09:0030AA48,10:003291D8,11:00320AE8,12:00312210,13:00318A58,14:00316100,15:00327328,16:00307E60,17:0030F260,18:00328D08,19:0030C0A8,20:00322DE0,22:00313C98,23:003183B0,24:0030CA58,25:00320E28,26:0030E9D8,30:00315090 func_PAL_0029C2A8 boot 1400 92ec120709b9ed40 23 00:0030E838,01:00304060,02:00312978,03:0030FB48,04:0032F180,06:0034DD78,07:00304A20,08:0031AE08,09:0030AAD0,11:00320B70,12:00312298,13:00318AE0,14:00316188,16:00307EE8,17:0030F2E8,18:00328D90,19:0030C130,20:00322E68,22:00313D20,23:00318438,24:0030CAE0,26:0030EA60,30:00315118 @@ -1090,7 +1087,6 @@ func_002A7750 boot 60 e3410a4fcb44add9 27 00:0031C5B0,01:00312168,02:003206D8,03 func_002A7790 boot 8 48e89fef3b080e8b 27 00:0031C5F0,01:003121A8,02:00320718,03:0031D910,04:0033D930,05:00334900,06:0035C528,07:00312788,08:00329608,09:00318838,10:00337008,11:0032E8D8,12:00320000,13:00326848,14:00323EF0,15:003351A8,16:00315C50,17:0031D050,18:00337580,19:00319F28,20:00331658,22:00321A88,23:003261A0,24:0031A7C0,25:0032EC20,26:0031C7C8,30:00322ED0 func_002A7798 boot 28 52057157ac08ecfc 27 00:0031C5F8,01:003121B0,02:00320720,03:0031D918,04:0033D938,05:00334908,06:0035C530,07:00312790,08:00329610,09:00318840,10:00337010,11:0032E8E0,12:00320008,13:00326850,14:00323EF8,15:003351B0,16:00315C58,17:0031D058,18:00337588,19:00319F30,20:00331660,22:00321A90,23:003261A8,24:0031A7C8,25:0032EC28,26:0031C7D0,30:00322ED8 func_L00_0031A6C8 shared 68 ac1429c07dc67499 27 00:0031C620,01:003121D8,02:00320748,03:0031D940,04:0033D960,05:00334930,06:0035C558,07:003127B8,08:00329668,09:00318868,10:00337038,11:0032E908,12:00320030,13:00326878,14:00323F20,15:003351D8,16:00315C80,17:0031D080,18:003375B0,19:00319F88,20:00331688,22:00321AB8,23:003261D0,24:0031A7F0,25:0032EC50,26:0031C7F8,30:00322F30 -func_L00_0031A710 shared 20 9b5530b036d68e5a 27 00:0031C668,01:00312220,02:00320790,03:0031D988,04:0033D9A8,05:00334978,06:0035C5A0,07:00312800,08:003296B0,09:003188B0,10:00337080,11:0032E950,12:00320078,13:003268C0,14:00323F68,15:00335220,16:00315CC8,17:0031D0C8,18:003375F8,19:00319FD0,20:003316D0,22:00321B00,23:00326218,24:0031A838,25:0032EC98,26:0031C840,30:00322F78 func_002A77E0 boot 60 752eefe39bbc0695 27 00:0031C680,01:00312238,02:003207A8,03:0031D9A0,04:0033D9C0,05:00334990,06:0035C5B8,07:00312818,08:003296C8,09:003188C8,10:00337098,11:0032E968,12:00320090,13:003268D8,14:00323F80,15:00335238,16:00315CE0,17:0031D0E0,18:00337610,19:00319FE8,20:003316E8,22:00321B18,23:00326230,24:0031A850,25:0032ECB0,26:0031C858,30:00322F90 func_002A7820 boot 84 688b95cb743066f7 27 00:0031C6C0,01:00312278,02:003207E8,03:0031D9E0,04:0033DA00,05:003349D0,06:0035C5F8,07:00312858,08:00329708,09:00318908,10:003370D8,11:0032E9A8,12:003200D0,13:00326918,14:00323FC0,15:00335278,16:00315D20,17:0031D120,18:00337650,19:0031A028,20:00331728,22:00321B58,23:00326270,24:0031A890,25:0032ECF0,26:0031C898,30:00322FD0 func_002A7878 boot 92 0533b520ad58cb39 27 00:0031C718,01:003122D0,02:00320840,03:0031DA38,04:0033DA58,05:00334A28,06:0035C650,07:003128B0,08:00329760,09:00318960,10:00337130,11:0032EA00,12:00320128,13:00326970,14:00324018,15:003352D0,16:00315D78,17:0031D178,18:003376A8,19:0031A080,20:00331780,22:00321BB0,23:003262C8,24:0031A8E8,25:0032ED48,26:0031C8F0,30:00323028 @@ -1381,7 +1377,6 @@ func_002B7F58 boot 84 4b9ab7498ae79d34 27 00:00330B18,01:00326140,02:003376B0,03 func_002B7FB0 boot 60 4dc1aee31e60cb8d 27 00:00330B70,01:00326198,02:00337708,03:00332248,04:00353B80,05:00343258,06:003713A8,07:00327148,08:0033ECF0,09:0032D2A0,10:00344FB8,11:00344488,12:003358F8,13:0033A460,14:0033AA00,15:00349278,16:00328B90,17:00333938,18:0034BBF0,19:0032DCC8,20:003461F0,22:00333F40,23:00338658,24:003284A0,25:0033D400,26:00330720,30:00331640 func_002B7FF0 boot 88 9b4a4bc151cd164c 27 00:00330BB0,01:003261D8,02:00337748,03:00332288,04:00353BC0,05:00343298,06:003713E8,07:00327188,08:0033ED30,09:0032D2E0,10:00344FF8,11:003444C8,12:00335938,13:0033A4A0,14:0033AA40,15:003492B8,16:00328BD0,17:00333978,18:0034BC30,19:0032DD08,20:00346230,22:00333F80,23:00338698,24:003284E0,25:0033D440,26:00330760,30:00331680 func_002B8048 boot 108 720f21e1440eced9 27 00:00330C08,01:00326230,02:003377A0,03:003322E0,04:00353C18,05:003432F0,06:00371440,07:003271E0,08:0033ED88,09:0032D338,10:00345050,11:00344520,12:00335990,13:0033A4F8,14:0033AA98,15:00349310,16:00328C28,17:003339D0,18:0034BC88,19:0032DD60,20:00346288,22:00333FD8,23:003386F0,24:00328538,25:0033D498,26:003307B8,30:003316D8 -func_002B80B8 boot 76 b57e3f05fadef0e4 15 00:00330C78,02:00337810,03:00332350,05:00343360,07:00327250,10:003450C0,15:00349380,16:00328C98,20:003462F8,22:00334048,23:00338760,24:003285A8,25:0033D508,26:00330828,30:00331748 func_002B8108 boot 1040 d7e9b92653f01285 27 00:00330CC8,01:00326770,02:00337860,03:003323A0,04:00354158,05:003433B0,06:003719C0,07:003272A0,08:0033F308,09:0032D8B8,10:00345110,11:00344AA0,12:00335ED0,13:0033A678,14:0033AFD8,15:003493D0,16:00328CE8,17:00333F50,18:0034C208,19:0032E2E0,20:00346348,22:00334098,23:003387B0,24:003285F8,25:0033D558,26:00330878,30:00331798 func_002B8518 boot 20 5f6da989bde7d8ee 27 00:003310D8,01:00326B80,02:00337C70,03:003327B0,04:00354568,05:003437C0,06:00371DD0,07:003276B0,08:0033F718,09:0032DCC8,10:00345520,11:00344EB0,12:003362E0,13:0033AA88,14:0033B3E8,15:003497E0,16:003290F8,17:00334360,18:0034C618,19:0032E6F0,20:00346758,22:003344A8,23:00338BC0,24:00328A08,25:0033D968,26:00330C88,30:00331BA8 func_L00_0032EF10 shared 160 5196cf33af1959e9 27 00:003310F0,01:00326B98,02:00337C88,03:003327C8,04:00354580,05:003437D8,06:00371DE8,07:003276C8,08:0033F730,09:0032DCE0,10:00345538,11:00344EC8,12:003362F8,13:0033AAA0,14:0033B400,15:003497F8,16:00329110,17:00334378,18:0034C630,19:0032E708,20:00346770,22:003344C0,23:00338BD8,24:00328A20,25:0033D980,26:00330CA0,30:00331BC0 @@ -1932,11 +1927,8 @@ func_PAL_L00_00369C48 shared 8 47be79a1ea98b050 23 00:00369C48,01:0035FDC8,02:00 func_PAL_002EE490 boot 236 55de0d44490d16a4 27 00:00369C50,01:0035FDD0,02:00371460,03:0036B328,04:0038D658,05:0037BFC8,06:003AB1F0,07:0035FAF0,08:00378248,09:00366F60,10:0037DDD8,11:0037E4B8,12:0036F448,13:00373640,14:003742F8,15:003828B8,16:00361900,17:0036D228,18:00385DD0,19:00367A50,20:0037FDE0,22:0036D440,23:00371B58,24:003610A0,25:00376008,26:00369668,30:0036A460 func_002ED688 boot 36 9b15f701a714ed25 27 00:00369D58,01:0035FED8,02:00371568,03:0036B430,04:0038D760,05:0037C3F0,06:003AB2F8,07:0035FBF8,08:00378350,09:00367068,10:0037E1D8,11:0037E5C0,12:0036F550,13:00373748,14:00374400,15:00382D08,16:00361A08,17:0036D330,18:00385ED8,19:00367B58,20:0037FEE8,22:0036D548,23:00371C60,24:003611A8,25:00376408,26:00369770,30:0036A568 func_PAL_002EE5C0 boot 404 d24f9503842c91d6 27 00:00369D80,01:0035FF00,02:00371590,03:0036B458,04:0038D788,05:0037C418,06:003AB320,07:0035FC20,08:00378378,09:00367090,10:0037E200,11:0037E5E8,12:0036F578,13:00373770,14:00374428,15:00382D30,16:00361A30,17:0036D358,18:00385F00,19:00367B80,20:0037FF10,22:0036D570,23:00371C88,24:003611D0,25:00376430,26:00369798,30:0036A590 -func_002ED848 boot 36 e93ae62af1dc8ec5 23 00:00369F18,01:00360098,02:00371728,03:0036B5F0,04:0038D920,06:003AB4B8,07:0035FDB8,08:00378510,09:00367228,11:0037E780,12:0036F710,13:00373908,14:003745C0,16:00361BC8,17:0036D4F0,18:00386098,19:00367D18,20:003800A8,22:0036D708,23:00371E20,24:00361368,26:00369930,30:0036A728 func_L00_00367720 shared 12 ceaacd8dbc655056 27 00:00369F40,01:003600C0,02:00371750,03:0036B618,04:0038D948,05:0037BFB8,06:003AB4E0,07:0035FDE0,08:00378538,09:00367250,10:0037DDC8,11:0037E7A8,12:0036F738,13:00373930,14:003745E8,15:003828A8,16:00361BF0,17:0036D518,18:003860C0,19:00367D40,20:003800D0,22:0036D730,23:00371E48,24:00361390,25:00375FF8,26:00369958,30:0036A750 -func_002ED880 boot 28 fa4b0329f6fac430 23 00:00369F50,01:003600D0,02:00371760,03:0036B628,04:0038D958,06:003AB4F0,07:0035FDF0,08:00378548,09:00367260,11:0037E7B8,12:0036F748,13:00373940,14:003745F8,16:00361C00,17:0036D528,18:003860D0,19:00367D50,20:003800E0,22:0036D740,23:00371E58,24:003613A0,26:00369968,30:0036A760 func_002ED8A0 boot 76 f50fa26769078085 27 00:00369F70,01:003600F0,02:00371780,03:0036B648,04:0038D978,05:0037D218,06:003AB510,07:0035FE10,08:00378568,09:00367280,10:0037F000,11:0037E7D8,12:0036F768,13:00373960,14:00374618,15:00383B30,16:00361C20,17:0036D548,18:003860F0,19:00367D70,20:00380100,22:0036D760,23:00371E78,24:003613C0,25:003771A0,26:00369988,30:0036A780 -func_002ED8F0 boot 84 660cf3e1ece7eb45 23 00:00369FC0,01:00360140,02:003717D0,03:0036B698,04:0038D9C8,06:003AB560,07:0035FE60,08:003785B8,09:003672D0,11:0037E828,12:0036F7B8,13:003739B0,14:00374668,16:00361C70,17:0036D598,18:00386140,19:00367DC0,20:00380150,22:0036D7B0,23:00371EC8,24:00361410,26:003699D8,30:0036A7D0 func_002ED948 boot 96 2e7f6d977748bed2 27 00:0036A018,01:00360198,02:00371828,03:0036B6F0,04:0038DA20,05:0037DDB0,06:003AB5B8,07:0035FEB8,08:00378610,09:00367328,10:0037FC08,11:0037E880,12:0036F810,13:00373A08,14:003746C0,15:00384800,16:00361CC8,17:0036D5F0,18:00386198,19:00367E18,20:003801A8,22:0036D808,23:00371F20,24:00361468,25:00377C58,26:00369A30,30:0036A828 func_PAL_002EE8B8 boot 16 acd8435708569046 23 00:0036A078,01:003601F8,02:00371888,03:0036B750,04:0038DA80,06:003AB618,07:0035FF18,08:00378670,09:00367388,11:0037E8E0,12:0036F870,13:00373A68,14:00374720,16:00361D28,17:0036D650,18:003861F8,19:00367E78,20:00380208,22:0036D868,23:00371F80,24:003614C8,26:00369A90,30:0036A888 func_002ED9C0 boot 76 5dbe38abd55fb984 27 00:0036A088,01:00360208,02:00371898,03:0036B760,04:0038DA90,05:0037DFB8,06:003AB628,07:0035FF28,08:00378680,09:00367398,10:0037FE10,11:0037E8F0,12:0036F880,13:00373A78,14:00374730,15:00384A08,16:00361D38,17:0036D660,18:00386208,19:00367E88,20:00380218,22:0036D878,23:00371F90,24:003614D8,25:00377E60,26:00369AA0,30:0036A898 @@ -1953,7 +1945,6 @@ func_PAL_002EF800 boot 108 f2458f9338e71efe 27 00:0036AFC0,01:00361140,02:003727 func_002EE920 boot 104 20c6c5ecec7c54d2 27 00:0036B030,01:003611B0,02:00372840,03:0036C708,04:0038EA38,05:0037FB40,06:003AC5D0,07:00360ED0,08:00379628,09:00368340,10:003818E8,11:0037F898,12:00370828,13:00374A20,14:003756D8,15:003864E0,16:00362CE0,17:0036E608,18:003871B0,19:00368E30,20:003811C0,22:0036E820,23:00372F38,24:00362480,25:00379A60,26:0036AA48,30:0036B840 func_002EE988 boot 372 7c3645d3edd48504 27 00:0036B098,01:00361218,02:003728A8,03:0036C770,04:0038EAA0,05:0037FBA8,06:003AC638,07:00360F38,08:00379690,09:003683A8,10:00381950,11:0037F900,12:00370890,13:00374A88,14:00375740,15:00386548,16:00362D48,17:0036E670,18:00387218,19:00368E98,20:00381228,22:0036E888,23:00372FA0,24:003624E8,25:00379AC8,26:0036AAB0,30:0036B8A8 func_002EEB00 boot 176 07f154714e9f2c72 27 00:0036B210,01:00361390,02:00372A20,03:0036C8E8,04:0038EC18,05:0037FD20,06:003AC7B0,07:003610B0,08:00379808,09:00368520,10:00381AC8,11:0037FA78,12:00370A08,13:00374C00,14:003758B8,15:003866C0,16:00362EC0,17:0036E7E8,18:00387390,19:00369010,20:003813A0,22:0036EA00,23:00373118,24:00362660,25:00379C40,26:0036AC28,30:0036BA20 -func_002EEBB0 boot 20 80046512fd4902e8 23 00:0036B2C0,01:00361440,02:00372AD0,03:0036C998,04:0038ECC8,06:003AC860,07:00361160,08:003798B8,09:003685D0,11:0037FB28,12:00370AB8,13:00374CB0,14:00375968,16:00362F70,17:0036E898,18:00387440,19:003690C0,20:00381450,22:0036EAB0,23:003731C8,24:00362710,26:0036ACD8,30:0036BAD0 func_002EEBC8 boot 320 77052426b2e4d437 27 00:0036B2D8,01:00361458,02:00372AE8,03:0036C9B0,04:0038ECE0,05:00380580,06:003AC878,07:00361178,08:003798D0,09:003685E8,10:003823C0,11:0037FB40,12:00370AD0,13:00374CC8,14:00375980,15:00386FB8,16:00362F88,17:0036E8B0,18:00387458,19:003690D8,20:00381468,22:0036EAC8,23:003731E0,24:00362728,25:0037A460,26:0036ACF0,30:0036BAE8 func_002EED08 boot 76 ab5eeb96914e323e 27 00:0036B418,01:00361598,02:00372C28,03:0036CAF0,04:0038EE20,05:003806C0,06:003AC9B8,07:003612B8,08:00379A10,09:00368728,10:00382500,11:0037FC80,12:00370C10,13:00374E08,14:00375AC0,15:003870F8,16:003630C8,17:0036E9F0,18:00387598,19:00369218,20:003815A8,22:0036EC08,23:00373320,24:00362868,25:0037A5A0,26:0036AE30,30:0036BC28 func_002EED58 boot 244 3394ab2360b6ec73 27 00:0036B468,01:003615E8,02:00372C78,03:0036CB40,04:0038EE70,05:00380710,06:003ACA08,07:00361308,08:00379A60,09:00368778,10:00382550,11:0037FCD0,12:00370C60,13:00374E58,14:00375B10,15:00387148,16:00363118,17:0036EA40,18:003875E8,19:00369268,20:003815F8,22:0036EC58,23:00373370,24:003628B8,25:0037A5F0,26:0036AE80,30:0036BC78 @@ -2698,7 +2689,7 @@ func_PAL_0032B4A8 boot 260 9b5669bbf8575342 27 00:003E5F78,01:003E7C28,02:004089 func_00329DC0 boot 156 da41f687ba9be336 27 00:003E6080,01:003E7D30,02:00408AF8,03:003EF710,04:00421498,05:003EE688,06:00427A10,07:003D0928,08:003F4E00,09:003E1B28,10:003EEBC0,11:00411028,12:003E9EB8,13:003E7040,14:003F37D0,15:003F8AD8,16:003D5460,17:003EF520,18:00403EA0,19:003E7EE8,20:00407A80,22:003E2680,23:003E9C30,24:003C9218,25:003E7278,26:003D6880,30:003E0100 func_PAL_0032B650 boot 224 85f45ce77375a73e 27 00:003E6120,01:003E7DD0,02:00408B98,03:003EF7B0,04:00421538,05:003EE728,06:00427AB0,07:003D09C8,08:003F4EA0,09:003E1BC8,10:003EEC60,11:004110C8,12:003E9F58,13:003E70E0,14:003F3870,15:003F8B78,16:003D5500,17:003EF5C0,18:00403F40,19:003E7F88,20:00407B20,22:003E2720,23:003E9CD0,24:003C92B8,25:003E7318,26:003D6920,30:003E01A0 func_00329F40 shared 496 163226caab62c8f9 27 00:003E6200,01:003E7EB0,02:00408C78,03:003EF890,04:00421618,05:003EE808,06:00427B90,07:003D0AA8,08:003F4F80,09:003E1CA8,10:003EED40,11:004111A8,12:003EA038,13:003E71C0,14:003F3950,15:003F8C58,16:003D55E0,17:003EF6A0,18:00404020,19:003E8068,20:00407C00,22:003E2800,23:003E9DB0,24:003C9398,25:003E73F8,26:003D6A00,30:003E0280 -func_PAL_L00_003E63F0 shared 16 aa7d0d9551230ff9 27 00:003E63F0,01:003E80A0,02:00408E68,03:003EFA80,04:00421808,05:003EE9F8,06:00427D80,07:003D0C98,08:003F5170,09:003E1E98,10:003EEF30,11:00411398,12:003EA228,13:003E73B0,14:003F3B40,15:003F8E48,16:003D57D0,17:003EF890,18:00404210,19:003E8258,20:00407DF0,22:003E29F0,23:003E9FA0,24:003C9588,25:003E75E8,26:003D6BF0,30:003E0470 +func_PAL_L00_003E63F0 shared 8 bc6e15da5a72ab85 27 00:003E63F8,01:003E80A8,02:00408E70,03:003EFA88,04:00421810,05:003EEA00,06:00427D88,07:003D0CA0,08:003F5178,09:003E1EA0,10:003EEF38,11:004113A0,12:003EA230,13:003E73B8,14:003F3B48,15:003F8E50,16:003D57D8,17:003EF898,18:00404218,19:003E8260,20:00407DF8,22:003E29F8,23:003E9FA8,24:003C9590,25:003E75F0,26:003D6BF8,30:003E0478 func_PAL_L00_003E6400 shared 912 df6622bde03082af 27 00:003E6400,01:003E80B0,02:00409200,03:003EFA90,04:00421818,05:003EEA08,06:00427D90,07:003D1160,08:003F5180,09:003E1FE8,10:003EEF40,11:004113A8,12:003EA238,13:003E73C0,14:003F3B50,15:003F8E58,16:003D57E0,17:003EF8A0,18:00404220,19:003E8268,20:00407E00,22:003E2A00,23:003E9FB0,24:003C9598,25:003E75F8,26:003D6F88,30:003E0480 func_PAL_L00_003E6790 shared 1724 8a93e7e660651b42 27 00:003E6790,01:003E8440,02:00409590,03:003EFE20,04:00421BA8,05:003EED98,06:00428120,07:003D14F0,08:003F5510,09:003E2378,10:003EF2D0,11:00411738,12:003EA5C8,13:003E7750,14:003F3EE0,15:003F91E8,16:003D5B70,17:003EFC30,18:004045B0,19:003E85F8,20:00408190,22:003E2D90,23:003EA340,24:003C9928,25:003E7988,26:003D7318,30:003E0810 func_PAL_L00_003E6E50 shared 684 cb03200a90336e4c 27 00:003E6E50,01:003E8B00,02:00409C50,03:003F04E0,04:00422268,05:003EF458,06:004287E0,07:003D1BB0,08:003F5BD0,09:003E2A38,10:003EF990,11:00411DF8,12:003EAC88,13:003E7E10,14:003F45A0,15:003F98A8,16:003D6230,17:003F02F0,18:00404C70,19:003E8CB8,20:00408850,22:003E3450,23:003EAA00,24:003C9FE8,25:003E8048,26:003D79D8,30:003E0ED0 @@ -3114,7 +3105,8 @@ func_PAL_L00_00429FC8 shared 68 c5526132f9ca3510 27 00:00429FC8,01:0042D810,02:0 func_L00_00424B20 shared 36 ab08622a9389d465 27 00:0042A010,01:0042D858,02:00456310,03:0043C450,04:0046D2B8,05:00443210,06:0047B700,07:004268B8,08:004473C8,09:00439748,10:00445218,11:0048C450,12:00440860,13:0043C6F8,14:00449018,15:0044FCE0,16:004354B8,17:004373B0,18:00457AA8,19:0043C788,20:00461F10,22:0042B4C8,23:00441080,24:00409E18,25:00433838,26:0041CE58,30:0042F120 func_L00_00424B48 shared 36 6af8db7ac3d8ba67 27 00:0042A038,01:0042D880,02:00456338,03:0043C478,04:0046D2E0,05:00443238,06:0047B728,07:004268E0,08:004473F0,09:00439770,10:00445240,11:0048C478,12:00440888,13:0043C720,14:00449040,15:0044FD08,16:004354E0,17:004373D8,18:00457AD0,19:0043C7B0,20:00461F38,22:0042B4F0,23:004410A8,24:00409E40,25:00433860,26:0041CE80,30:0042F148 func_L00_00424B70 shared 72 6b8116fb9abb08d4 27 00:0042A060,01:0042D8A8,02:00456360,03:0043C4A0,04:0046D308,05:00443260,06:0047B750,07:00426908,08:00447418,09:00439798,10:00445268,11:0048C4A0,12:004408B0,13:0043C748,14:00449068,15:0044FD30,16:00435508,17:00437400,18:00457AF8,19:0043C7D8,20:00461F60,22:0042B518,23:004410D0,24:00409E68,25:00433888,26:0041CEA8,30:0042F170 -func_L00_00424BB8 shared 72 6b8116fb9abb08d4 27 00:0042A0A8,01:0042D8F0,02:004563A8,03:0043C4E8,04:0046D350,05:004432A8,06:0047B798,07:00426950,08:00447460,09:004397E0,10:004452B0,11:0048C4E8,12:004408F8,13:0043C790,14:004490B0,15:0044FD78,16:00435550,17:00437448,18:00457B40,19:0043C820,20:00461FA8,22:0042B560,23:00441118,24:00409EB0,25:004338D0,26:0041CEF0,30:0042F1B8 +func_L00_00424BB8 shared 72 6b8116fb9abb08d4 27 00:0042A0A8,01:0042D8F0,02:004563A8,03:0043C4E8,04:0046D350,05:004432A8,06:0047B798,07:00426950,08:00447460,09:004397E0,10:004452B0,11:0048C4E8,12:004408F8,13:0043C790,14:004490B0,15:0044FD78,16:00435598,17:00437448,18:00457B40,19:0043C820,20:00461FA8,22:0042B5A8,23:00441160,24:00409EB0,25:004338D0,26:0041CF38,30:0042F1B8 +func_L16_0042FB10 shared 72 6b8116fb9abb08d4 4 16:00435550,22:0042B560,23:00441118,26:0041CEF0 func_L00_00424C00 shared 40 be6002e7a1fe3fa7 27 00:0042A0F0,01:0042D938,02:004563F0,03:0043C530,04:0046D398,05:004432F0,06:0047B7E0,07:00426998,08:004474A8,09:00439828,10:004452F8,11:0048C530,12:00440940,13:0043C7D8,14:004490F8,15:0044FDC0,16:004355E0,17:00437490,18:00457B88,19:0043C868,20:00461FF0,22:0042B5F0,23:004411A8,24:00409EF8,25:00433918,26:0041CF80,30:0042F200 func_L00_00424C28 shared 40 aae0e898ffaaf025 27 00:0042A118,01:0042D960,02:00456418,03:0043C558,04:0046D3C0,05:00443318,06:0047B808,07:004269C0,08:004474D0,09:00439850,10:00445320,11:0048C558,12:00440968,13:0043C800,14:00449120,15:0044FDE8,16:00435608,17:004374B8,18:00457BB0,19:0043C890,20:00462018,22:0042B618,23:004411D0,24:00409F20,25:00433940,26:0041CFA8,30:0042F228 func_L00_00424C60 shared 48 fd57c438f19d737e 27 00:0042A150,01:0042D998,02:00456450,03:0043C590,04:0046D3F8,05:00443350,06:0047B840,07:004269F8,08:00447508,09:00439888,10:00445358,11:0048C590,12:004409A0,13:0043C838,14:00449158,15:0044FE20,16:00435640,17:004374F0,18:00457BE8,19:0043C8C8,20:00462050,22:0042B650,23:00441208,24:00409F58,25:00433978,26:0041CFE0,30:0042F260 @@ -3305,7 +3297,7 @@ func_PAL_0033B9F8 boot 1100 69af574e8036549e 27 00:00434BB8,01:004381D0,02:00460 func_PAL_0033BE50 boot 1204 9badf2520571595f 27 00:00435010,01:00438628,02:00461018,03:00446600,04:00479418,05:004515D8,06:00487178,07:00430B70,08:00451890,09:00444600,10:00453350,11:00497EA8,12:0044BEC0,13:004493A8,14:00453E20,15:0045E390,16:00440F48,17:00442490,18:00462D70,19:00446D00,20:0046CF10,22:00435A68,23:0044B620,24:00413B50,25:004419E0,26:00427698,30:00439150 func_PAL_0033C308 boot 192 b5ebd7fa9845644d 27 00:004354C8,01:00438AE0,02:004614D0,03:00446AB8,04:004798D0,05:00451A90,06:00487630,07:00431028,08:00451D48,09:00444AB8,10:00453808,11:00498360,12:0044C378,13:00449860,14:004542D8,15:0045E848,16:00441400,17:00442948,18:00463228,19:004471B8,20:0046D3C8,22:00435F20,23:0044BAD8,24:00414008,25:00441E98,26:00427B50,30:00439608 func_0033A4A0 boot 116 e332baad9fd7f4ff 27 00:00435588,01:00438BA0,02:00461590,03:00446B78,04:00479990,05:00451B50,06:004876F0,07:004310E8,08:00451E08,09:00444B78,10:004538C8,11:00498420,12:0044C438,13:00449920,14:00454398,15:0045E908,16:004414C0,17:00442A08,18:004632E8,19:00447278,20:0046D488,22:00435FE0,23:0044BB98,24:004140C8,25:00441F58,26:00427C10,30:004396C8 -func_0033A520 boot 360 5770489227d41706 27 00:00435608,01:00438C20,02:00461610,03:00446BF8,04:00479A10,05:00451BD0,06:00487770,07:00431168,08:00451E88,09:00444BF8,10:00453948,11:004984A0,12:0044C4B8,13:004499A0,14:00454418,15:0045E988,16:00441540,17:00442A88,18:00463368,19:004472F8,20:0046D508,22:00436060,23:0044BC18,24:00414148,25:00441FD8,26:00427C90,30:00439748 +func_PAL_0033C448 boot 360 5770489227d41706 27 00:00435608,01:00438C20,02:00461610,03:00446BF8,04:00479A10,05:00451BD0,06:00487770,07:00431168,08:00451E88,09:00444BF8,10:00453948,11:004984A0,12:0044C4B8,13:004499A0,14:00454418,15:0045E988,16:00441540,17:00442A88,18:00463368,19:004472F8,20:0046D508,22:00436060,23:0044BC18,24:00414148,25:00441FD8,26:00427C90,30:00439748 func_PAL_0033C5B0 boot 76 8a807e20da101c0f 27 00:00435770,01:00438D88,02:00461778,03:00446D60,04:00479B78,05:00451D38,06:004878D8,07:004312D0,08:00451FF0,09:00444D60,10:00453AB0,11:00498608,12:0044C620,13:00449B08,14:00454580,15:0045EAF0,16:004416A8,17:00442BF0,18:004634D0,19:00447460,20:0046D670,22:004361C8,23:0044BD80,24:004142B0,25:00442140,26:00427DF8,30:004398B0 func_PAL_0033C600 boot 748 eeb41694f695cda4 27 00:004357C0,01:00438DD8,02:004617C8,03:00446DB0,04:00479BC8,05:00451D88,06:00487928,07:00431320,08:00452040,09:00444DB0,10:00453B00,11:00498658,12:0044C670,13:00449B58,14:004545D0,15:0045EB40,16:004416F8,17:00442C40,18:00463520,19:004474B0,20:0046D6C0,22:00436218,23:0044BDD0,24:00414300,25:00442190,26:00427E48,30:00439900 func_PAL_0033C8F0 boot 8 fa944ab4d1efe408 27 00:00435AB0,01:004390C8,02:00461AB8,03:004470A0,04:00479EB8,05:00452078,06:00487C18,07:00431610,08:00452330,09:004450A0,10:00453DF0,11:00498948,12:0044C960,13:00449E48,14:004548C0,15:0045EE30,16:004419E8,17:00442F30,18:00463810,19:004477A0,20:0046D9B0,22:00436508,23:0044C0C0,24:004145F0,25:00442480,26:00428138,30:00439BF0 @@ -3325,7 +3317,6 @@ func_PAL_0033CF78 boot 88 c6c24c7b76f6f979 27 00:00436138,01:00439750,02:0046214 func_PAL_0033CFD0 boot 8 ca765ef3cd00b26c 27 00:00436190,01:004397A8,02:00462198,03:00447780,04:0047A598,05:00452758,06:004882F8,07:00431CF0,08:00452A10,09:00445780,10:004544D0,11:00499028,12:0044D040,13:0044A528,14:00454FA0,15:0045F510,16:004420C8,17:00443610,18:00463EF0,19:00447E80,20:0046E090,22:00436BE8,23:0044C7A0,24:00414CD0,25:00442B60,26:00428818,30:0043A2D0 func_PAL_0033CFE0 boot 164 716936ee6d2ffced 27 00:004361A0,01:004397B8,02:004621A8,03:00447790,04:0047A5A8,05:00452768,06:00488308,07:00431D00,08:00452A20,09:00445790,10:004544E0,11:00499038,12:0044D050,13:0044A538,14:00454FB0,15:0045F520,16:004420D8,17:00443620,18:00463F00,19:00447E90,20:0046E0A0,22:00436BF8,23:0044C7B0,24:00414CE0,25:00442B70,26:00428828,30:0043A2E0 func_PAL_0033D098 boot 964 6b6bbb676cbff229 27 00:00436258,01:00439870,02:00462260,03:00447848,04:0047A660,05:00452820,06:004883C0,07:00431DB8,08:00452AD8,09:00445848,10:00454598,11:004990F0,12:0044D108,13:0044A5F0,14:00455068,15:0045F5D8,16:00442190,17:004436D8,18:00463FB8,19:00447F48,20:0046E158,22:00436CB0,23:0044C868,24:00414D98,25:00442C28,26:004288E0,30:0043A398 -func_0033B538 boot 4 b88cc87420eed4aa 27 00:00436620,01:00439C38,02:00462628,03:00447C10,04:0047AA28,05:00452BE8,06:00488788,07:00432180,08:00452EA0,09:00445C10,10:00454960,11:004994B8,12:0044D4D0,13:0044A9B8,14:00455430,15:0045F9A0,16:00442558,17:00443AA0,18:00464380,19:00448310,20:0046E520,22:00437078,23:0044CC30,24:00415160,25:00442FF0,26:00428CA8,30:0043A760 func_PAL_0033D468 boot 972 70048804331a0ab2 27 00:00436628,01:00439C40,02:00462630,03:00447C18,04:0047AA30,05:00452BF0,06:00488790,07:00432188,08:00452EA8,09:00445C18,10:00454968,11:004994C0,12:0044D4D8,13:0044A9C0,14:00455438,15:0045F9A8,16:00442560,17:00443AA8,18:00464388,19:00448318,20:0046E528,22:00437080,23:0044CC38,24:00415168,25:00442FF8,26:00428CB0,30:0043A768 func_PAL_0033D838 boot 1060 0552a8156423eca6 27 00:004369F8,01:0043A010,02:00462A00,03:00447FE8,04:0047AE00,05:00452FC0,06:00488B60,07:00432558,08:00453278,09:00445FE8,10:00454D38,11:00499890,12:0044D8A8,13:0044AD90,14:00455808,15:0045FD78,16:00442930,17:00443E78,18:00464758,19:004486E8,20:0046E8F8,22:00437450,23:0044D008,24:00415538,25:004433C8,26:00429080,30:0043AB38 func_PAL_L00_00436E20 shared 44 d221205177b3720f 27 00:00436E20,01:0043A438,02:00462E28,03:00448410,04:0047B228,05:004533E8,06:00488F88,07:00432980,08:004536A0,09:00446410,10:00455160,11:00499CB8,12:0044DCD0,13:0044B1B8,14:00455C30,15:004601A0,16:00442D58,17:004442A0,18:00464B80,19:00448B10,20:0046ED20,22:00437878,23:0044D430,24:00415960,25:004437F0,26:004294A8,30:0043AF60 @@ -3518,7 +3509,6 @@ func_00349498 boot 52 90c4f9366d05f9e9 27 00:00444820,01:00447E38,02:00470828,03 func_003494D0 boot 180 cdea45d13cf19835 27 00:00444858,01:00447E70,02:00470860,03:00455E48,04:00488C60,05:00460E20,06:004969C0,07:004403B8,08:004610D8,09:00453E48,10:00462B98,11:004A76F0,12:0045B708,13:00458BF0,14:00463668,15:0046DBD8,16:00450790,17:00451CD8,18:004725B8,19:00456548,20:0047C758,22:004452B0,23:0045AE68,24:00423398,25:00451228,26:00436EE0,30:00448998 func_00349590 boot 8 31fcd37f04a168ac 27 00:00444918,01:00447F30,02:00470920,03:00455F08,04:00488D20,05:00460EE0,06:00496A80,07:00440478,08:00461198,09:00453F08,10:00462C58,11:004A77B0,12:0045B7C8,13:00458CB0,14:00463728,15:0046DC98,16:00450850,17:00451D98,18:00472678,19:00456608,20:0047C818,22:00445370,23:0045AF28,24:00423458,25:004512E8,26:00436FA0,30:00448A58 func_003495A0 boot 20 04ffc67212d027e8 27 00:00444928,01:00447F40,02:00470930,03:00455F18,04:00488D30,05:00460EF0,06:00496A90,07:00440488,08:004611A8,09:00453F18,10:00462C68,11:004A77C0,12:0045B7D8,13:00458CC0,14:00463738,15:0046DCA8,16:00450860,17:00451DA8,18:00472688,19:00456618,20:0047C828,22:00445380,23:0045AF38,24:00423468,25:004512F8,26:00436FB0,30:00448A68 -func_003495B8 boot 4 3d685cd8e4c14f74 27 00:00444940,01:00447F58,02:00470948,03:00455F30,04:00488D48,05:00460F08,06:00496AA8,07:004404A0,08:004611C0,09:00453F30,10:00462C80,11:004A77D8,12:0045B7F0,13:00458CD8,14:00463750,15:0046DCC0,16:00450878,17:00451DC0,18:004726A0,19:00456630,20:0047C840,22:00445398,23:0045AF50,24:00423480,25:00451310,26:00436FC8,30:00448A80 func_003495C0 boot 8 057181dc76824f67 27 00:00444948,01:00447F60,02:00470950,03:00455F38,04:00488D50,05:00460F10,06:00496AB0,07:004404A8,08:004611C8,09:00453F38,10:00462C88,11:004A77E0,12:0045B7F8,13:00458CE0,14:00463758,15:0046DCC8,16:00450880,17:00451DC8,18:004726A8,19:00456638,20:0047C848,22:004453A0,23:0045AF58,24:00423488,25:00451318,26:00436FD0,30:00448A88 func_003495C8 boot 12 e1f7ad89507f65b8 27 00:00444950,01:00447F68,02:00470958,03:00455F40,04:00488D58,05:00460F18,06:00496AB8,07:004404B0,08:004611D0,09:00453F40,10:00462C90,11:004A77E8,12:0045B800,13:00458CE8,14:00463760,15:0046DCD0,16:00450888,17:00451DD0,18:004726B0,19:00456640,20:0047C850,22:004453A8,23:0045AF60,24:00423490,25:00451320,26:00436FD8,30:00448A90 func_003495D8 boot 52 b36c02b8071d414a 27 00:00444960,01:00447F78,02:00470968,03:00455F50,04:00488D68,05:00460F28,06:00496AC8,07:004404C0,08:004611E0,09:00453F50,10:00462CA0,11:004A77F8,12:0045B810,13:00458CF8,14:00463770,15:0046DCE0,16:00450898,17:00451DE0,18:004726C0,19:00456650,20:0047C860,22:004453B8,23:0045AF70,24:004234A0,25:00451330,26:00436FE8,30:00448AA0 @@ -3690,7 +3680,6 @@ func_L01_002C81D0 shared 1112 f8ad934289b037db 4 01:002C8440,07:002C8D80,11:002E func_L01_002C8990 shared 24 3243cfaea13c279f 8 01:002C8C00,04:002F3DD0,07:002C9540,08:002DF3D0,09:002CF678,16:002CC838,18:002EDEF0,19:002D0FF8 func_L01_002C89A8 shared 24 51b93d471b4449f4 8 01:002C8C18,04:002F3DE8,07:002C9558,08:002DF3E8,09:002CF690,16:002CC850,18:002EDF08,19:002D1010 func_PAL_L01_002C9B28 shared 84 7ef9f8ef578b1f55 10 01:002C9B28,02:002D7AE0,03:002D5048,04:002F4CF8,08:002E02F8,09:002D05A0,12:002D7BB0,17:002D5668,20:002E85D0,30:002DB460 -func_00280660 boot 12 2c1054e663689292 22 01:002E1090,02:002EF1A8,03:002EC660,05:00304900,06:0032B2E0,09:002E7BC0,10:00306E00,11:002FD8B0,12:002EF080,13:002F6668,15:00304F80,16:002E4D38,17:002ECC38,18:003064A0,19:002E97C0,20:002FFCA8,22:002F1D38,23:002F6418,24:002EAB18,25:002FEED0,26:002EC298,30:002F2CB0 func_L01_002E1510 shared 348 55a78a077cf6b229 13 01:002E27F8,02:002F0FA0,03:002EE088,06:0032CDF8,07:002E3AB8,08:002F9580,09:002E9558,12:002F0AA8,13:002F8090,16:002E6760,17:002EE5D0,18:00307E38,20:00301640 func_PAL_L01_002E2968 shared 416 f05765ea56614c07 5 01:002E2968,02:002F1768,03:002EE898,06:0032CF68,16:002E6CB8 func_L01_002E2608 shared 388 2e52620f6c8c4719 4 01:002E38F0,02:002F26F0,09:002EAB08,11:00300B18 @@ -3939,7 +3928,6 @@ func_L01_0041C960 level 16 892435a81e3ee6c6 1 01:004221C8 func_PAL_L01_004221D8 level 1444 26fa6aa3bcd63e15 1 01:004221D8 func_L01_0042A568 shared 380 0fb94da10a0f6c4a 3 01:004300E0,08:00449C50,09:0043BFD0 func_L01_0042A6F0 shared 132 937f9f8bb7258e00 8 01:00430268,02:00458BA8,08:00449DD8,09:0043C158,11:0048ECE8,18:0045B558,19:0043F020,20:004647A8 -func_L01_0042C450 level 12 d307e18564eccf77 1 01:00431F78 func_PAL_L01_00432064 level 976 26173079c6efecb3 1 01:00432068 func_PAL_L01_00432438 level 1440 8ecaa260fda0e566 1 01:00432438 func_L01_0042CE78 level 108 09b1f78f8f48d1f4 1 01:004329D8 @@ -4563,7 +4551,7 @@ func_L03_00419C58 shared 72 491f849a4425c9d5 2 03:0041EE90,14:00426108 func_PAL_L03_0041EED8 level 1004 271ffa48174a0122 1 03:0041EED8 func_PAL_L03_0041F2C8 level 1244 e4e8d838a1703be1 1 03:0041F2C8 func_PAL_L03_0041F7A8 level 1088 b97f75ad55f20012 1 03:0041F7A8 -func_L03_0041B848 shared 16 bacb80d8a8a76e20 5 03:00420BA8,16:00413DD8,19:0041E838,24:003FED28,30:004133B0 +func_L03_0041B848 shared 8 bc6e15da5a72ab85 5 03:00420BB0,16:00413DE0,19:0041E840,24:003FED30,30:004133B8 func_PAL_L03_004211B8 level 3176 02c36b5f83a749b9 1 03:004211B8 func_PAL_L03_00421E20 level 1076 de77602f676d9a70 1 03:00421E20 func_PAL_L03_00422258 level 504 58d690d124dd8494 1 03:00422258 @@ -4892,7 +4880,6 @@ func_PAL_L05_00327418 shared 44 c38c87056ed79e67 4 05:00327418,10:00329B20,15:00 func_PAL_L05_00328198 shared 60 fbcf34adfe61c912 4 05:00328198,10:0032A8A0,15:003289F0,25:003224F0 func_PAL_L05_0033ED34 shared 40 6b284fc8c964271d 6 05:0033ED38,10:00340A98,22:0032CE40,23:00331558,24:00323F80,25:00338EE0 func_PAL_L05_0033F3A8 shared 1840 1b635cb12ac609d2 5 05:0033F3B0,10:00341110,24:003245F8,25:00339558,30:0032D458 -func_L05_0033F4A8 shared 156 dfc292e5124853e5 5 05:003414D0,10:00343230,24:00326718,25:0033B678,30:0032F848 func_L05_00352B28 shared 360 162c615314ebd680 2 05:00354F68,10:00356D78 func_L05_00367340 level 272 5d827ff8e4fffc7d 1 05:003696D0 func_L05_00379968 shared 504 8e45051a7f70cab0 4 05:0037C0B8,10:0037DEC8,15:003829A8,25:003760F8 @@ -4928,12 +4915,10 @@ func_PAL_L05_0037D9D0 shared 284 8c80d8d7d42558d0 4 05:0037D9D0,10:0037F798,15:0 func_L05_0037B3A0 shared 148 9f639856800e0a66 4 05:0037DAF0,10:0037F8B8,15:003843E0,25:00377A90 func_PAL_L05_0037DB90 shared 248 46c4d0c726225dc5 3 05:0037DB90,10:0037F9E8,15:003845E0 func_L05_0037B538 shared 292 e268379035d983b1 4 05:0037DC88,10:0037FAE0,15:003846D8,25:00377B30 -func_L05_0037B6C0 shared 12 acd8435708569046 4 05:0037DE10,10:0037FC68,15:00384860,25:00377CB8 func_PAL_L05_0037DE20 shared 408 09772c2aaf0e0486 4 05:0037DE20,10:0037FC78,15:00384870,25:00377CC8 func_L05_0037B888 shared 188 074e5a0a635cbef1 4 05:0037E008,10:0037FE60,15:00384A58,25:00377EB0 func_L05_0037B948 shared 480 141355b131c746e8 4 05:0037E0C8,10:0037FF20,15:00384B18,25:00377F70 func_L05_0037BB28 shared 80 1847ba6c486ae642 4 05:0037E2A8,10:00380100,15:00384CF8,25:00378150 -func_L05_0037BB78 shared 20 ae8017e88ecc5608 4 05:0037E2F8,10:00380150,15:00384D48,25:003781A0 func_L05_0037BB90 shared 40 d49888e7fb4c73ff 4 05:0037E310,10:00380168,15:00384D60,25:003781B8 func_L05_0037BBB8 shared 68 f314cb3e4c5bbc68 4 05:0037E338,10:00380190,15:00384D88,25:003781E0 func_L05_0037BC08 shared 312 0d0660b92e96e730 4 05:0037E388,10:003801E0,15:00384DD8,25:00378230 @@ -5707,7 +5692,6 @@ func_L09_003F9D08 shared 888 6a2f2d51a2f042a0 2 09:003FE778,20:00423CA8 func_PAL_L09_003FEAF0 shared 4832 393331f487f99160 2 09:003FEAF0,20:00424020 func_PAL_L09_00400080 level 384 7f076b73cba047d6 1 09:00400080 func_L09_003FB650 level 300 9db1faccbdcb90c5 1 09:00400200 -func_L09_003FB780 shared 4 dc2834da92d18696 3 09:00400330,22:003BC840,23:003C0E38 func_L09_003FB788 level 216 e4c8e58e6334973d 1 09:00400338 func_L09_003FB860 level 164 05f35498e2940d7d 1 09:00400410 func_L09_003FB908 level 240 5ad3f7223d0c4fef 1 09:004004B8 @@ -5831,7 +5815,8 @@ func_PAL_L10_0041D888 level 196 e8d1d9d0fab67754 1 10:0041D888 func_PAL_L10_0041D950 level 488 8235ec5c344c7364 1 10:0041D950 func_PAL_L10_0041DB38 shared 868 d2d7838a1d524a0a 2 10:0041DB38,15:00424EB0 func_PAL_L10_0041DEA0 shared 152 ba1c88de52c245a4 2 10:0041DEA0,15:00425218 -func_L10_00419188 level 96 741d326f9af76cac 1 10:0041DF38 +func_L10_00419188 level 88 118d456fa41c7684 1 10:0041DF38 +func_L10_004191E0 level 8 bc6e15da5a72ab85 1 10:0041DF90 func_PAL_L10_0041DF98 shared 352 c1cb40409d219171 2 10:0041DF98,15:004252B8 func_PAL_L10_0041E0F8 shared 560 59fa49c4fdfe957c 2 10:0041E0F8,15:00425418 func_PAL_L10_00423AA0 level 316 5199c4e3e942031e 1 10:00423AA0 @@ -6693,7 +6678,6 @@ func_L16_0041F1F0 level 364 a106e4c53e568836 1 16:00424650 func_L16_0041F360 level 576 355ebcb3a8abc9ef 1 16:004247C0 func_L16_0041F950 shared 368 2c000a38e014aee3 2 16:00424DB0,30:0041AAA8 func_PAL_L16_0042A338 level 160 7c6045b7eac976cc 1 16:0042A340 -func_L16_0042FB58 shared 72 6b8116fb9abb08d4 4 16:00435598,22:0042B5A8,23:00441160,26:0041CF38 func_PAL_L16_0043B728 level 1988 68fe1ccbb1936749 1 16:0043B728 func_PAL_L16_0043BEF0 shared 32 ddd8e32f9e36739a 4 16:0043BEF0,22:00430A10,23:004465C8,26:004223A0 func_L17_00326F38 shared 104 75e1169fb4573d97 2 17:00329008,18:00341CC8 @@ -7412,7 +7396,6 @@ func_L23_0041E260 level 44 ef7c5a2acfe4ae55 1 23:00423528 func_L23_0041E290 level 308 1d6c4bb18018ee3d 1 23:00423558 func_L23_0041E3C8 level 76 ae7ce52a1d270c98 1 23:00423690 func_L23_0041E418 level 284 20210ae921bf20ca 1 23:004236E0 -func_L23_0041E538 level 12 34b07fab5514db8f 1 23:00423800 func_L23_0041E548 level 36 187a50c96ffbc146 1 23:00423810 func_PAL_L23_00423838 level 96 b7929f248b0e1563 1 23:00423838 func_PAL_L23_00423898 level 200 4baece70ebc5bd28 1 23:00423898 @@ -7466,9 +7449,6 @@ func_L24_003B3C38 level 1804 2b7afc196151fff3 1 24:003B7870 func_PAL_L24_003F44F8 shared 1372 85a35eee9d5fe988 2 24:003F4500,25:00414370 func_PAL_L24_003FED38 level 2044 f1b4e9c6d1a8894a 1 24:003FED40 func_PAL_L25_00363700 level 272 b72d083c216976c6 1 25:00363710 -func_L25_00373ED0 level 4 be96ef5f6a9b0a3a 1 25:00376620 -func_L25_00373EE0 level 20 97a7ba7bf7023520 1 25:00376630 -func_L25_00373F08 level 4 e948bc05cd743d07 1 25:00376658 func_PAL_L25_00377A28 level 104 1a73540a442fc2e3 1 25:00377A28 func_L25_00376FE0 level 120 92f9ed972df6799e 1 25:003797A8 func_L25_00377608 level 120 92f9ed972df6799e 1 25:00379DD0 @@ -7501,7 +7481,6 @@ func_L26_003DF7E8 level 784 43b085032a92fa50 1 26:003E3C20 func_PAL_L26_0040C130 level 340 a73f2bcd1447003a 1 26:0040C130 func_PAL_L26_00411C98 level 232 a4accbed98c96ba0 1 26:00411C98 func_PAL_L26_00421BD8 level 1988 73b3cab7597763ea 1 26:00421BD8 -func_L30_0032AAF0 level 20 5e3c9c126e52756e 1 30:0032CAD8 func_L30_003557F0 level 272 2b1f17835d160222 1 30:00357B70 func_L30_00382EF0 level 28 0aec05893bf71f32 1 30:00385C10 func_L30_00382F10 level 168 f6638a3f3ba13659 1 30:00385C30 diff --git a/config/pal/not_carried.tsv b/config/pal/not_carried.tsv index 112dd323d..8b2c17054 100644 --- a/config/pal/not_carried.tsv +++ b/config/pal/not_carried.tsv @@ -108,3 +108,4 @@ func_0033FB98 boot: instruction at +0x1D4 differs func_003458F8 boot: instruction at +0x34 differs func_00345B78 boot: instruction at +0x20 differs func_0034E070 boot: instruction differs +func_0033A520 00_aranos_tutorial: instruction at +0x24 differs diff --git a/config/us2/boot/functions.tsv b/config/us2/boot/functions.tsv index 877c782cf..ba14e9f7b 100644 --- a/config/us2/boot/functions.tsv +++ b/config/us2/boot/functions.tsv @@ -47,7 +47,7 @@ func_00118D98 00118D98 3368 func_00119AC0 00119AC0 264 func_00119BC8 00119BC8 48 func_00119BF8 00119BF8 3072 -func_0011A7F8 0011A7F8 24 +func_0011A7F8 0011A800 16 func_0011A810 0011A810 16 func_0011A820 0011A820 16 func_0011A830 0011A830 16 @@ -194,7 +194,6 @@ func_0011B328 0011B328 164 func_0011B3D0 0011B3D0 124 func_0011B458 0011B458 164 func_0011B500 0011B500 124 -func_0011B580 0011B580 8 func_0011B588 0011B588 104 func_0011B5F0 0011B5F0 104 func_0011B658 0011B658 104 @@ -224,7 +223,6 @@ func_0011C820 0011C820 96 func_0011C880 0011C880 28 func_0011C8A0 0011C8A0 12 func_0011C8B0 0011C8B0 24 -func_0011C8C8 0011C8C8 12 func_0011C8D8 0011C8D8 640 func_0011CB58 0011CB58 52 func_0011CB90 0011CB90 44 @@ -264,13 +262,11 @@ func_0011E4E0 0011E4E0 608 func_0011E740 0011E7A0 136 func_0011E828 0011E828 128 func_0011E8A8 0011E8A8 120 -func_0011E920 0011E920 24 func_0011E938 0011E938 256 func_0011EA38 0011EA38 140 func_0011EAC8 0011EAC8 56 func_0011EB00 0011EB00 520 func_0011ED08 0011ED08 28 -func_0011ED28 0011ED28 56 func_0011ED60 0011ED60 316 func_0011EEA0 0011EEA0 56 func_0011EED8 0011EED8 272 @@ -301,7 +297,6 @@ func_0011F938 0011F938 172 func_0011F9E4 0011F9E8 48 func_0011FA18 0011FA18 8 func_0011FA20 0011FA20 40 -func_0011FA48 0011FA48 8 func_0011FA50 0011FA50 16 func_0011FA60 0011FA60 16 func_0011FA70 0011FA70 56 @@ -355,7 +350,6 @@ func_00123268 00123268 44 func_00123298 00123298 84 func_001232F0 001232F0 268 func_00123400 00123400 144 -func_00123490 00123490 44 func_001234C0 001234C0 44 func_001234F0 001234F0 64 func_00123530 00123530 68 @@ -459,7 +453,6 @@ func_001291A0 001291A0 116 func_00129218 00129218 164 func_001292C0 001292C0 168 func_00129368 00129368 168 -func_00129410 00129410 64 func_00129450 00129450 592 func_001296A0 001296A0 1796 func_00129DA8 00129DA8 1052 @@ -546,7 +539,6 @@ func_0012F690 0012F690 168 func_0012F738 0012F738 520 func_0012F940 0012F940 8 func_0012F948 0012F950 72 -func_0012F998 0012F998 16 func_0012F9A8 0012F9A8 12 func_0012F9B8 0012F9B8 16 func_0012F9C8 0012F9C8 80 @@ -554,7 +546,6 @@ func_0012FA18 0012FA18 84 func_0012FA70 0012FA70 36 func_0012FA98 0012FA98 80 func_0012FAE8 0012FAE8 36 -func_0012FB10 0012FB10 52 func_0012FB48 0012FB48 20 func_0012FB60 0012FB60 12 func_0012FB70 0012FB70 12 @@ -584,7 +575,6 @@ func_00130A70 00130A70 12 func_00130A80 00130A80 12 func_00130A8C 00130A90 12 func_00130AA0 00130AA0 12 -func_00130AAC 00130AAC 4 func_00130AB0 00130AB0 100 func_00130B18 00130B18 100 func_00130B80 00130B80 228 @@ -714,7 +704,6 @@ func_0026F810 0026F850 1068 func_0026FC78 0026FC88 464 func_0026FE48 0026FE58 108 func_0026FEB8 0026FEC8 56 -func_0026FEF0 0026FF00 20 func_0026FF08 0026FF18 268 func_00270018 00270028 396 func_002701B0 002701C0 92 @@ -745,9 +734,7 @@ func_00272198 002721A8 48 func_002721C8 002721D8 184 func_00272280 00272290 228 func_US2_00272378 00272378 472 -func_00272540 00272550 12 func_00272550 00272560 120 -func_002725C8 002725D8 20 func_002725E0 002725F0 956 func_002729A0 002729B0 784 func_00272CB0 00272CC0 1632 @@ -873,7 +860,6 @@ func_00280328 00280CE0 488 func_00280510 00280EC8 240 func_US2_00280FB8 00280FB8 36 func_00280630 00280FE0 48 -func_00280660 00281010 12 func_00280670 00281020 160 func_00280710 002810C0 484 func_002808F8 002812A8 376 @@ -1051,7 +1037,6 @@ func_00288BB8 002895E0 48 func_00288BE8 00289610 200 func_00288CB0 002896D8 128 func_00288D30 00289758 12 -func_00288D40 00289768 20 func_00288D58 00289780 16 func_00288D68 00289790 8 func_00288D70 00289798 12 @@ -1132,7 +1117,6 @@ func_US2_00290920 00290920 1404 func_US2_00290EA0 00290EA0 64 func_00290670 00290EE8 12 func_00290680 00290EF8 148 -func_00290718 00290F90 4 func_00290720 00290F98 8 func_00290728 00290FA0 8 func_00290730 00290FA8 24 @@ -1257,7 +1241,6 @@ func_US2_00299960 00299960 8 func_US2_00299968 00299968 24 func_US2_00299980 00299980 20 func_US2_00299998 00299998 356 -func_00298D10 00299B00 20 func_00298D28 00299B18 220 func_00298E08 00299BF8 248 func_US2_00299CF0 00299CF0 7840 @@ -1279,7 +1262,6 @@ func_US2_0029C548 0029C548 40 func_US2_0029C570 0029C570 64 func_US2_0029C5B0 0029C5B0 76 func_US2_0029C600 0029C600 52 -func_0029B848 0029C638 12 func_US2_0029C648 0029C648 48 func_US2_0029C678 0029C678 132 func_US2_0029C700 0029C700 280 @@ -1572,7 +1554,6 @@ func_002B0668 002B14D0 564 func_002B08A8 002B1710 104 func_002B0910 002B1778 84 func_002B0990 002B17F8 120 -func_002B0A08 002B1870 12 func_US2_002B1880 002B1880 48 func_US2_002B18B0 002B18B0 28 func_002B0A68 002B18D0 428 @@ -1603,11 +1584,9 @@ func_002B39A0 002B48B8 384 func_002B3B20 002B4A38 132 func_002B3BA8 002B4AC0 1152 func_002B4038 002B4F50 36 -func_002B4068 002B4F80 36 func_002B4090 002B4FA8 272 func_002B41A8 002B50C0 788 func_002B44C0 002B53D8 1248 -func_002B49A0 002B58B8 12 func_002B49B0 002B58C8 8 func_002B49C0 002B58D8 8 func_002B49C8 002B58E0 20 @@ -1672,10 +1651,8 @@ func_002B7F58 002B8E78 84 func_002B7FB0 002B8ED0 60 func_002B7FF0 002B8F10 88 func_002B8048 002B8F68 108 -func_002B80B8 002B8FD8 76 func_002B8108 002B9028 1040 func_002B8518 002B9438 20 -func_002B8530 002B9450 20 func_002B8548 002B9468 176 func_002B85F8 002B9518 656 func_002B8888 002B97A8 100 @@ -2082,7 +2059,6 @@ func_002DF1F8 002E0010 232 func_002DF2E0 002E00F8 160 func_002DF380 002E0198 120 func_002DF3F8 002E0210 564 -func_002DF630 002E0448 12 func_002DF640 002E0458 272 func_002DF750 002E0568 84 func_002DF7A8 002E05C0 144 @@ -2182,17 +2158,12 @@ func_002ED260 002EE0B8 88 func_002ED2B8 002EE110 172 func_002ED368 002EE1C0 336 func_002ED4B8 002EE310 176 -func_002ED570 002EE3C8 4 func_002ED578 002EE3D0 244 func_002ED688 002EE4E0 36 func_002ED6B0 002EE508 404 -func_002ED848 002EE6A0 36 func_002ED870 002EE6C8 12 -func_002ED880 002EE6D8 28 func_002ED8A0 002EE6F8 76 -func_002ED8F0 002EE748 84 func_002ED948 002EE7A0 96 -func_002ED9A8 002EE800 20 func_002ED9C0 002EE818 76 func_002EDA10 002EE8B0 1444 func_002EE000 002EEE58 564 @@ -2207,7 +2178,6 @@ func_002EE8B0 002EF708 108 func_002EE920 002EF778 104 func_002EE988 002EF7E0 372 func_002EEB00 002EF958 176 -func_002EEBB0 002EFA08 20 func_002EEBC8 002EFA20 320 func_002EED08 002EFB60 76 func_002EED58 002EFBB0 244 @@ -2293,17 +2263,13 @@ func_002FC220 002FD0B0 96 func_002FC280 002FD110 316 func_002FC3C0 002FD250 76 func_002FC410 002FD2A0 76 -func_002FC460 002FD2F0 4 func_002FC468 002FD2F8 164 -func_002FC510 002FD3A0 4 func_002FC518 002FD3A8 72 func_002FC560 002FD3F0 180 -func_002FC618 002FD4A8 4 func_002FC620 002FD4B0 284 func_002FC748 002FD5D8 92 func_002FC7A8 002FD638 92 func_002FC808 002FD698 92 -func_002FC868 002FD6F8 4 func_002FC870 002FD700 92 func_002FC8D0 002FD760 188 func_002FC990 002FD820 364 @@ -2472,7 +2438,6 @@ func_00316B40 00317940 136 func_00316BC8 003179C8 468 func_00316DA0 00317BA0 100 func_00316E08 00317C08 1220 -func_003172D0 003180D0 188 func_00317390 00318190 32 func_003173B0 003181E8 2444 func_00317D78 00318B78 1128 @@ -2518,7 +2483,6 @@ func_0031E2A0 0031F098 260 func_0031E3A8 0031F1A0 380 func_0031E528 0031F320 52 func_0031E560 0031F358 372 -func_0031E6D8 0031F4D0 12 func_0031E6E8 0031F4E0 100 func_0031E750 0031F548 136 func_0031E7D8 0031F5D0 288 @@ -2564,7 +2528,6 @@ func_00325EC0 00326CB8 724 func_US2_00326F90 00326FE8 2080 func_00326A10 00327808 444 func_00326BD8 003279D0 208 -func_00326CA8 00327AA0 12 func_US2_00327AB0 00327AB0 252 func_00326D90 00327BB0 304 func_00326EC0 00327CE0 376 @@ -2597,7 +2560,7 @@ func_00329CB8 0032AAD8 260 func_00329DC0 0032ABE0 156 func_00329E60 0032AC80 224 func_US2_0032AD60 0032AD60 496 -func_0032A130 0032AF50 16 +func_0032A130 0032AF58 8 func_0032A140 0032AF60 2104 func_0032A978 0032B798 184 func_0032AA30 0032B850 400 @@ -2665,7 +2628,6 @@ func_003348A8 003356A0 320 func_003349E8 003357E0 160 func_00334A88 00335888 1820 func_003351B0 00335FB0 184 -func_00335270 00336068 252 func_00335370 00336168 88 func_003353C8 003361C0 88 func_00335438 00336230 364 @@ -2784,7 +2746,7 @@ func_US2_0033AB18 0033AB18 1100 func_US2_0033AF70 0033AF70 1204 func_US2_0033B428 0033B428 192 func_0033A4A0 0033B4E8 116 -func_0033A520 0033B568 360 +func_US2_0033B568 0033B568 360 func_US2_0033B6D0 0033B6D0 76 func_US2_0033B720 0033B720 748 func_US2_0033BA10 0033BA10 8 @@ -2804,7 +2766,6 @@ func_US2_0033C098 0033C098 88 func_US2_0033C0F0 0033C0F0 8 func_US2_0033C100 0033C100 164 func_US2_0033C1B8 0033C1B8 964 -func_0033B538 0033C580 4 func_US2_0033C588 0033C588 972 func_US2_0033C958 0033C958 1060 func_US2_0033CD80 0033CD80 44 @@ -2996,7 +2957,6 @@ func_00349498 0034A1D8 52 func_003494D0 0034A210 180 func_00349590 0034A2D0 8 func_003495A0 0034A2E0 20 -func_003495B8 0034A2F8 4 func_003495C0 0034A300 8 func_003495C8 0034A308 12 func_003495D8 0034A318 52 diff --git a/config/us2/levels/functions.tsv b/config/us2/levels/functions.tsv index f9e0f87c4..192590761 100644 --- a/config/us2/levels/functions.tsv +++ b/config/us2/levels/functions.tsv @@ -647,7 +647,6 @@ func_00288BB8 boot 48 e4d354e43a9df5fd 27 00:002F5000,01:002EA308,02:002F8F88,03 func_00288BE8 boot 200 e2702760fec99d9c 27 00:002F5030,01:002EA338,02:002F8FB8,03:002F6030,04:00315D20,05:0030D558,06:00334608,07:002EB0F0,08:00300C00,09:002F12D0,10:0030FA70,11:00307478,12:002F8718,13:002FF6F8,14:002FCC38,15:0030DB58,16:002EE420,17:002F5F18,18:0030F820,19:002F2640,20:003091A0,22:002FA9C0,23:002FF0E0,24:002F3770,25:00307B28,26:002F5310,30:002FBBD0 func_00288CB0 boot 128 78adc6813d75279f 27 00:002F50F8,01:002EA400,02:002F9080,03:002F60F8,04:00315DE8,05:0030D620,06:003346D0,07:002EB1B8,08:00300CC8,09:002F1398,10:0030FB38,11:00307540,12:002F87E0,13:002FF7C0,14:002FCD00,15:0030DC20,16:002EE4E8,17:002F5FE0,18:0030F8E8,19:002F2708,20:00309268,22:002FAA88,23:002FF1A8,24:002F3838,25:00307BF0,26:002F53D8,30:002FBC98 func_00288D30 boot 12 f44fd4a16adaaf93 27 00:002F5178,01:002EA480,02:002F9100,03:002F6178,04:00315E68,05:0030D6A0,06:00334750,07:002EB238,08:00300D48,09:002F1418,10:0030FBB8,11:003075C0,12:002F8860,13:002FF840,14:002FCD80,15:0030DCA0,16:002EE568,17:002F6060,18:0030F968,19:002F2788,20:003092E8,22:002FAB08,23:002FF228,24:002F38B8,25:00307C70,26:002F5458,30:002FBD18 -func_00288D40 boot 20 7cc9af5e39e13180 25 00:002F5188,01:002EA490,02:002F9110,03:002F6188,04:00315E78,05:0030D6B0,06:00334760,07:002EB248,09:002F1428,10:0030FBC8,11:003075D0,12:002F8870,13:002FF850,14:002FCD90,15:0030DCB0,16:002EE578,17:002F6070,18:0030F978,20:003092F8,22:002FAB18,23:002FF238,24:002F38C8,25:00307C80,26:002F5468,30:002FBD28 func_00288D58 boot 16 a75da09b651b41e6 27 00:002F51A0,01:002EA4A8,02:002F9128,03:002F61A0,04:00315E90,05:0030D6C8,06:00334778,07:002EB260,08:00300DF8,09:002F1440,10:0030FBE0,11:003075E8,12:002F8888,13:002FF868,14:002FCDA8,15:0030DCC8,16:002EE590,17:002F6088,18:0030F990,19:002F2838,20:00309310,22:002FAB30,23:002FF250,24:002F38E0,25:00307C98,26:002F5480,30:002FBD40 func_L00_002F43D0 shared 16 a3234dc79d2b0730 27 00:002F51B0,01:002EA4B8,02:002F9138,03:002F61B0,04:00315EA0,05:0030D6D8,06:00334788,07:002EB270,08:00300E08,09:002F1450,10:0030FBF0,11:003075F8,12:002F8898,13:002FF878,14:002FCDB8,15:0030DCD8,16:002EE5A0,17:002F6098,18:0030F9A0,19:002F2848,20:00309320,22:002FAB40,23:002FF260,24:002F38F0,25:00307CA8,26:002F5490,30:002FBD50 func_L00_002F43E0 shared 8 94fa2fd9540a9f79 27 00:002F51C0,01:002EA4C8,02:002F9148,03:002F61C0,04:00315EB0,05:0030D6E8,06:00334798,07:002EB280,08:00300E18,09:002F1460,10:0030FC00,11:00307608,12:002F88A8,13:002FF888,14:002FCDC8,15:0030DCE8,16:002EE5B0,17:002F60A8,18:0030F9B0,19:002F2858,20:00309330,22:002FAB50,23:002FF270,24:002F3900,25:00307CB8,26:002F54A0,30:002FBD60 @@ -889,7 +888,6 @@ func_00298B70 boot 68 e76b288ab529102c 27 00:0030AF30,01:00300908,02:0030F010,03 func_US2_L00_0030AF78 shared 8 17b4ae028fe3a32c 27 00:0030AF78,01:00300950,02:0030F058,03:0030C330,04:0032B880,05:00323348,06:0034A578,07:003011D8,08:003174E8,09:003071F0,10:00325A50,11:0031D2F0,12:0030E9D0,13:003152C8,14:00312948,15:00323B20,16:00304740,17:0030BA78,18:00325530,19:003088B0,20:0031F490,22:00310528,23:00314C40,24:003092D0,25:0031D6A0,26:0030B180,30:00311730 func_US2_00299968 boot 24 0f46ab5bc3877e79 27 00:0030AF80,01:00300958,02:0030F060,03:0030C338,04:0032B888,05:00323350,06:0034A580,07:003011E0,08:003174F0,09:003071F8,10:00325A58,11:0031D2F8,12:0030E9D8,13:003152D0,14:00312950,15:00323B28,16:00304748,17:0030BA80,18:00325538,19:003088B8,20:0031F498,22:00310530,23:00314C48,24:003092D8,25:0031D6A8,26:0030B188,30:00311738 func_US2_00299980 boot 20 26599166970257eb 27 00:0030AF98,01:00300970,02:0030F078,03:0030C350,04:0032B8A0,05:00323368,06:0034A598,07:003011F8,08:00317508,09:00307210,10:00325A70,11:0031D310,12:0030E9F0,13:003152E8,14:00312968,15:00323B40,16:00304760,17:0030BA98,18:00325550,19:003088D0,20:0031F4B0,22:00310548,23:00314C60,24:003092F0,25:0031D6C0,26:0030B1A0,30:00311750 -func_L00_00309DB0 shared 28 a9a7c64556297f33 27 00:0030AFB0,01:00300988,02:0030F090,03:0030C368,04:0032B8B8,05:00323380,06:0034A5B0,07:00301210,08:00317520,09:00307228,10:00325A88,11:0031D328,12:0030EA08,13:00315300,14:00312980,15:00323B58,16:00304778,17:0030BAB0,18:00325568,19:003088E8,20:0031F4C8,22:00310560,23:00314C78,24:00309308,25:0031D6D8,26:0030B1B8,30:00311768 func_00298D28 boot 220 77c627edaab8f7ce 27 00:0030AFD0,01:003009A8,02:0030F0B0,03:0030C388,04:0032B8D8,05:003233A0,06:0034A5D0,07:00301230,08:00317540,09:00307248,10:00325AA8,11:0031D348,12:0030EA28,13:00315320,14:003129A0,15:00323B78,16:00304798,17:0030BAD0,18:00325588,19:00308908,20:0031F4E8,22:00310580,23:00314C98,24:00309328,25:0031D6F8,26:0030B1D8,30:00311788 func_00298E08 boot 248 3da0bdb25b0158e8 27 00:0030B0B0,01:00300A88,02:0030F190,03:0030C468,04:0032B9B8,05:00323480,06:0034A6B0,07:00301310,08:00317620,09:00307328,10:00325B88,11:0031D428,12:0030EB08,13:00315400,14:00312A80,15:00323C58,16:00304878,17:0030BBB0,18:00325668,19:003089E8,20:0031F5C8,22:00310660,23:00314D78,24:00309408,25:0031D7D8,26:0030B2B8,30:00311868 func_US2_00299CF0 boot 7840 86f23a910927a927 27 00:0030B1A8,01:00300B80,02:0030F288,03:0030C560,04:0032BAB0,05:00323578,06:0034A7A8,07:00301408,08:00317718,09:00307420,10:00325C80,11:0031D520,12:0030EC00,13:003154F8,14:00312B78,15:00323D50,16:00304970,17:0030BCA8,18:00325760,19:00308AE0,20:0031F6C0,22:00310758,23:00314E70,24:00309500,25:0031D8D0,26:0030B3B0,30:00311960 @@ -912,7 +910,6 @@ func_US2_0029C548 boot 40 291302a59ff41bc9 27 00:0030DA30,01:00303408,02:00311B1 func_US2_0029C570 boot 64 1427e861cc41e46b 27 00:0030DA58,01:00303430,02:00311B38,03:0030EE10,04:0032E360,05:00325E28,06:0034D058,07:00303CB8,08:00319FC8,09:00309CD0,10:00328530,11:0031FDD0,12:003114B0,13:00317DA8,14:00315428,15:00326600,16:00307220,17:0030E558,18:00328010,19:0030B390,20:00321F70,22:00313008,23:00317720,24:0030BDB0,25:00320180,26:0030DC60,30:00314210 func_US2_0029C5B0 boot 76 8b1fbeb81a3e6632 27 00:0030DA98,01:00303470,02:00311B78,03:0030EE50,04:0032E3A0,05:00325E68,06:0034D098,07:00303CF8,08:0031A008,09:00309D10,10:00328570,11:0031FE10,12:003114F0,13:00317DE8,14:00315468,15:00326640,16:00307260,17:0030E598,18:00328050,19:0030B3D0,20:00321FB0,22:00313048,23:00317760,24:0030BDF0,25:003201C0,26:0030DCA0,30:00314250 func_US2_0029C600 boot 52 26277e90267027ec 27 00:0030DAE8,01:003034C0,02:00311BC8,03:0030EEA0,04:0032E3F0,05:00325EB8,06:0034D0E8,07:00303D48,08:0031A058,09:00309D60,10:003285C0,11:0031FE60,12:00311540,13:00317E38,14:003154B8,15:00326690,16:003072B0,17:0030E5E8,18:003280A0,19:0030B420,20:00322000,22:00313098,23:003177B0,24:0030BE40,25:00320210,26:0030DCF0,30:003142A0 -func_0029B848 boot 12 d0ab515f5271898e 25 00:0030DB20,01:003034F8,02:00311C00,03:0030EED8,04:0032E428,05:00325EF0,06:0034D120,07:00303D80,09:00309D98,10:003285F8,11:0031FE98,12:00311578,13:00317E70,14:003154F0,15:003266C8,16:003072E8,17:0030E620,18:003280D8,20:00322038,22:003130D0,23:003177E8,24:0030BE78,25:00320248,26:0030DD28,30:003142D8 func_US2_L00_0030DB30 shared 48 da034f71ee361c9e 27 00:0030DB30,01:00303508,02:00311C10,03:0030EEE8,04:0032E438,05:00325F00,06:0034D130,07:00303D90,08:0031A0E8,09:00309DA8,10:00328608,11:0031FEA8,12:00311588,13:00317E80,14:00315500,15:003266D8,16:003072F8,17:0030E630,18:003280E8,19:0030B4B0,20:00322048,22:003130E0,23:003177F8,24:0030BE88,25:00320258,26:0030DD38,30:003142E8 func_US2_0029C678 boot 132 9e2e8cec467ddce4 27 00:0030DB60,01:00303538,02:00311C40,03:0030EF18,04:0032E468,05:00325F30,06:0034D160,07:00303DC0,08:0031A118,09:00309DD8,10:00328638,11:0031FED8,12:003115B8,13:00317EB0,14:00315530,15:00326708,16:00307328,17:0030E660,18:00328118,19:0030B4E0,20:00322078,22:00313110,23:00317828,24:0030BEB8,25:00320288,26:0030DD68,30:00314318 func_US2_0029C700 boot 280 aee5de6fecffa147 27 00:0030DBE8,01:003035C0,02:00311CC8,03:0030EFA0,04:0032E4F0,05:00325FE8,06:0034D1E8,07:00303E48,08:0031A1A0,09:00309E60,10:003286F0,11:0031FF60,12:00311640,13:00317F38,14:003155B8,15:003267C0,16:003073B0,17:0030E6E8,18:003281A0,19:0030B568,20:00322100,22:00313198,23:003178B0,24:0030BF40,25:00320340,26:0030DDF0,30:003143A0 @@ -1085,7 +1082,6 @@ func_002A7750 boot 60 e3410a4fcb44add9 27 00:0031B8D0,01:00311638,02:0031F998,03 func_002A7790 boot 8 48e89fef3b080e8b 27 00:0031B910,01:00311678,02:0031F9D8,03:0031CCD8,04:0033CC10,05:00333CB0,06:0035B908,07:00311B20,08:00328910,09:00317B38,10:003363B8,11:0032DC38,12:0031F318,13:00325C10,14:00323290,15:003344D8,16:00315088,17:0031C3C0,18:00336900,19:003192D0,20:00330860,22:00320E70,23:00325588,24:00319B90,25:0032DFD0,26:0031BAC8,30:003220C8 func_002A7798 boot 28 52057157ac08ecfc 27 00:0031B918,01:00311680,02:0031F9E0,03:0031CCE0,04:0033CC18,05:00333CB8,06:0035B910,07:00311B28,08:00328918,09:00317B40,10:003363C0,11:0032DC40,12:0031F320,13:00325C18,14:00323298,15:003344E0,16:00315090,17:0031C3C8,18:00336908,19:003192D8,20:00330868,22:00320E78,23:00325590,24:00319B98,25:0032DFD8,26:0031BAD0,30:003220D0 func_L00_0031A6C8 shared 68 ac1429c07dc67499 27 00:0031B940,01:003116A8,02:0031FA08,03:0031CD08,04:0033CC40,05:00333CE0,06:0035B938,07:00311B50,08:00328970,09:00317B68,10:003363E8,11:0032DC68,12:0031F348,13:00325C40,14:003232C0,15:00334508,16:003150B8,17:0031C3F0,18:00336930,19:00319330,20:00330890,22:00320EA0,23:003255B8,24:00319BC0,25:0032E000,26:0031BAF8,30:00322128 -func_L00_0031A710 shared 20 9b5530b036d68e5a 27 00:0031B988,01:003116F0,02:0031FA50,03:0031CD50,04:0033CC88,05:00333D28,06:0035B980,07:00311B98,08:003289B8,09:00317BB0,10:00336430,11:0032DCB0,12:0031F390,13:00325C88,14:00323308,15:00334550,16:00315100,17:0031C438,18:00336978,19:00319378,20:003308D8,22:00320EE8,23:00325600,24:00319C08,25:0032E048,26:0031BB40,30:00322170 func_002A77E0 boot 60 752eefe39bbc0695 27 00:0031B9A0,01:00311708,02:0031FA68,03:0031CD68,04:0033CCA0,05:00333D40,06:0035B998,07:00311BB0,08:003289D0,09:00317BC8,10:00336448,11:0032DCC8,12:0031F3A8,13:00325CA0,14:00323320,15:00334568,16:00315118,17:0031C450,18:00336990,19:00319390,20:003308F0,22:00320F00,23:00325618,24:00319C20,25:0032E060,26:0031BB58,30:00322188 func_002A7820 boot 84 688b95cb743066f7 27 00:0031B9E0,01:00311748,02:0031FAA8,03:0031CDA8,04:0033CCE0,05:00333D80,06:0035B9D8,07:00311BF0,08:00328A10,09:00317C08,10:00336488,11:0032DD08,12:0031F3E8,13:00325CE0,14:00323360,15:003345A8,16:00315158,17:0031C490,18:003369D0,19:003193D0,20:00330930,22:00320F40,23:00325658,24:00319C60,25:0032E0A0,26:0031BB98,30:003221C8 func_002A7878 boot 92 0533b520ad58cb39 27 00:0031BA38,01:003117A0,02:0031FB00,03:0031CE00,04:0033CD38,05:00333DD8,06:0035BA30,07:00311C48,08:00328A68,09:00317C60,10:003364E0,11:0032DD60,12:0031F440,13:00325D38,14:003233B8,15:00334600,16:003151B0,17:0031C4E8,18:00336A28,19:00319428,20:00330988,22:00320F98,23:003256B0,24:00319CB8,25:0032E0F8,26:0031BBF0,30:00322220 @@ -1375,7 +1371,6 @@ func_002B7F58 boot 84 4b9ab7498ae79d34 27 00:0032FC68,01:00325440,02:00336780,03 func_002B7FB0 boot 60 4dc1aee31e60cb8d 27 00:0032FCC0,01:00325498,02:003367D8,03:00331420,04:00352C90,05:00342480,06:00370598,07:00326310,08:0033DE08,09:0032C3B0,10:003441E0,11:003435F8,12:00334A20,13:00339658,14:00339BD0,15:003483D8,16:00327DF8,17:00332AB8,18:0034ADA0,19:0032CEA0,20:00345208,22:00333158,23:00337870,24:003276E8,25:0033C628,26:0032F850,30:003306B0 func_002B7FF0 boot 88 9b4a4bc151cd164c 27 00:0032FD00,01:003254D8,02:00336818,03:00331460,04:00352CD0,05:003424C0,06:003705D8,07:00326350,08:0033DE48,09:0032C3F0,10:00344220,11:00343638,12:00334A60,13:00339698,14:00339C10,15:00348418,16:00327E38,17:00332AF8,18:0034ADE0,19:0032CEE0,20:00345248,22:00333198,23:003378B0,24:00327728,25:0033C668,26:0032F890,30:003306F0 func_002B8048 boot 108 720f21e1440eced9 27 00:0032FD58,01:00325530,02:00336870,03:003314B8,04:00352D28,05:00342518,06:00370630,07:003263A8,08:0033DEA0,09:0032C448,10:00344278,11:00343690,12:00334AB8,13:003396F0,14:00339C68,15:00348470,16:00327E90,17:00332B50,18:0034AE38,19:0032CF38,20:003452A0,22:003331F0,23:00337908,24:00327780,25:0033C6C0,26:0032F8E8,30:00330748 -func_002B80B8 boot 76 b57e3f05fadef0e4 15 00:0032FDC8,02:003368E0,03:00331528,05:00342588,07:00326418,10:003442E8,15:003484E0,16:00327F00,20:00345310,22:00333260,23:00337978,24:003277F0,25:0033C730,26:0032F958,30:003307B8 func_002B8108 boot 1040 e95c50f4ea3595bc 27 00:0032FE18,01:00325A70,02:00336930,03:00331578,04:00353268,05:003425D8,06:00370BB0,07:00326468,08:0033E420,09:0032C9C8,10:00344338,11:00343C10,12:00334FF8,13:00339870,14:0033A1A8,15:00348530,16:00327F50,17:003330D0,18:0034B3B8,19:0032D4B8,20:00345360,22:003332B0,23:003379C8,24:00327840,25:0033C780,26:0032F9A8,30:00330808 func_002B8518 boot 20 358cf4d2b25a8ebe 27 00:00330228,01:00325E80,02:00336D40,03:00331988,04:00353678,05:003429E8,06:00370FC0,07:00326878,08:0033E830,09:0032CDD8,10:00344748,11:00344020,12:00335408,13:00339C80,14:0033A5B8,15:00348940,16:00328360,17:003334E0,18:0034B7C8,19:0032D8C8,20:00345770,22:003336C0,23:00337DD8,24:00327C50,25:0033CB90,26:0032FDB8,30:00330C18 func_L00_0032EF10 shared 160 adc472b577f53c1b 27 00:00330240,01:00325E98,02:00336D58,03:003319A0,04:00353690,05:00342A00,06:00370FD8,07:00326890,08:0033E848,09:0032CDF0,10:00344760,11:00344038,12:00335420,13:00339C98,14:0033A5D0,15:00348958,16:00328378,17:003334F8,18:0034B7E0,19:0032D8E0,20:00345788,22:003336D8,23:00337DF0,24:00327C68,25:0033CBA8,26:0032FDD0,30:00330C30 @@ -1924,17 +1919,12 @@ func_002ED368 boot 336 9830285f80d0aac9 27 00:00368360,01:0035E690,02:0036FAF0,0 func_002ED4B8 boot 176 bc0fc1c7514ef62b 27 00:003684B0,01:0035E7E0,02:0036FC40,03:00369C10,04:0038BE58,05:0037A908,06:003A9AE0,07:0035E3D8,08:00376A50,09:00365760,10:0037C718,11:0037CD18,12:0036DC90,13:00371F58,14:00372BE8,15:00381130,16:00360288,17:0036BAC8,18:00384690,19:00366338,20:0037E508,22:0036BD38,23:00370450,24:0035FA08,25:00374948,26:00367EA8,30:00368BF0 func_L00_003672F8 shared 16 df716174612d7cad 12 00:00368560,01:0035E890,02:0036FCF0,03:00369CC0,04:0038BF08,08:00376B00,09:00365810,11:0037CDC8,18:00384740,19:003663E8,20:0037E5B8,26:00367F58 func_L00_00367308 shared 276 4792a4b6f9d640da 27 00:00368570,01:0035E8A0,02:0036FD00,03:00369CD0,04:0038BF18,05:0037A9B8,06:003A9B90,07:0035E488,08:00376B10,09:00365820,10:0037C7C8,11:0037CDD8,12:0036DD40,13:00372008,14:00372C98,15:003811E0,16:00360338,17:0036BB78,18:00384750,19:003663F8,20:0037E5C8,22:0036BDE8,23:00370500,24:0035FAB8,25:003749F8,26:00367F68,30:00368CA0 -func_002ED570 boot 4 47be79a1ea98b050 23 00:00368688,01:0035E9B8,02:0036FE18,03:00369DE8,04:0038C030,06:003A9CA8,07:0035E5A0,08:00376C28,09:00365938,11:0037CEF0,12:0036DE58,13:00372120,14:00372DB0,16:00360450,17:0036BC90,18:00384868,19:00366510,20:0037E6E0,22:0036BF00,23:00370618,24:0035FBD0,26:00368080,30:00368DB8 func_002ED578 boot 244 09f4b440fb620626 27 00:00368690,01:0035E9C0,02:0036FE20,03:00369DF0,04:0038C038,05:0037AAE0,06:003A9CB0,07:0035E5A8,08:00376C30,09:00365940,10:0037C8F0,11:0037CEF8,12:0036DE60,13:00372128,14:00372DB8,15:00381308,16:00360458,17:0036BC98,18:00384870,19:00366518,20:0037E6E8,22:0036BF08,23:00370620,24:0035FBD8,25:00374B20,26:00368088,30:00368DC0 func_002ED688 boot 36 9b15f701a714ed25 27 00:003687A0,01:0035EAD0,02:0036FF30,03:00369F00,04:0038C148,05:0037AF10,06:003A9DC0,07:0035E6B8,08:00376D40,09:00365A50,10:0037CCF8,11:0037D008,12:0036DF70,13:00372238,14:00372EC8,15:00381760,16:00360568,17:0036BDA8,18:00384980,19:00366628,20:0037E7F8,22:0036C018,23:00370730,24:0035FCE8,25:00374F28,26:00368198,30:00368ED0 func_002ED6B0 boot 404 5322bea0a656504d 27 00:003687C8,01:0035EAF8,02:0036FF58,03:00369F28,04:0038C170,05:0037AF38,06:003A9DE8,07:0035E6E0,08:00376D68,09:00365A78,10:0037CD20,11:0037D030,12:0036DF98,13:00372260,14:00372EF0,15:00381788,16:00360590,17:0036BDD0,18:003849A8,19:00366650,20:0037E820,22:0036C040,23:00370758,24:0035FD10,25:00374F50,26:003681C0,30:00368EF8 -func_002ED848 boot 36 e93ae62af1dc8ec5 23 00:00368960,01:0035EC90,02:003700F0,03:0036A0C0,04:0038C308,06:003A9F80,07:0035E878,08:00376F00,09:00365C10,11:0037D1C8,12:0036E130,13:003723F8,14:00373088,16:00360728,17:0036BF68,18:00384B40,19:003667E8,20:0037E9B8,22:0036C1D8,23:003708F0,24:0035FEA8,26:00368358,30:00369090 func_L00_00367720 shared 12 ceaacd8dbc655056 27 00:00368988,01:0035ECB8,02:00370118,03:0036A0E8,04:0038C330,05:0037AAD0,06:003A9FA8,07:0035E8A0,08:00376F28,09:00365C38,10:0037C8E0,11:0037D1F0,12:0036E158,13:00372420,14:003730B0,15:003812F8,16:00360750,17:0036BF90,18:00384B68,19:00366810,20:0037E9E0,22:0036C200,23:00370918,24:0035FED0,25:00374B10,26:00368380,30:003690B8 -func_002ED880 boot 28 fa4b0329f6fac430 23 00:00368998,01:0035ECC8,02:00370128,03:0036A0F8,04:0038C340,06:003A9FB8,07:0035E8B0,08:00376F38,09:00365C48,11:0037D200,12:0036E168,13:00372430,14:003730C0,16:00360760,17:0036BFA0,18:00384B78,19:00366820,20:0037E9F0,22:0036C210,23:00370928,24:0035FEE0,26:00368390,30:003690C8 func_002ED8A0 boot 76 f50fa26769078085 27 00:003689B8,01:0035ECE8,02:00370148,03:0036A118,04:0038C360,05:0037BD38,06:003A9FD8,07:0035E8D0,08:00376F58,09:00365C68,10:0037DB20,11:0037D220,12:0036E188,13:00372450,14:003730E0,15:00382588,16:00360780,17:0036BFC0,18:00384B98,19:00366840,20:0037EA10,22:0036C230,23:00370948,24:0035FF00,25:00375CC0,26:003683B0,30:003690E8 -func_002ED8F0 boot 84 660cf3e1ece7eb45 23 00:00368A08,01:0035ED38,02:00370198,03:0036A168,04:0038C3B0,06:003AA028,07:0035E920,08:00376FA8,09:00365CB8,11:0037D270,12:0036E1D8,13:003724A0,14:00373130,16:003607D0,17:0036C010,18:00384BE8,19:00366890,20:0037EA60,22:0036C280,23:00370998,24:0035FF50,26:00368400,30:00369138 func_002ED948 boot 96 2e7f6d977748bed2 27 00:00368A60,01:0035ED90,02:003701F0,03:0036A1C0,04:0038C408,05:0037C8D0,06:003AA080,07:0035E978,08:00377000,09:00365D10,10:0037E728,11:0037D2C8,12:0036E230,13:003724F8,14:00373188,15:00383258,16:00360828,17:0036C068,18:00384C40,19:003668E8,20:0037EAB8,22:0036C2D8,23:003709F0,24:0035FFA8,25:00376778,26:00368458,30:00369190 -func_002ED9A8 boot 20 84a01a6395fdbcc8 23 00:00368AC0,01:0035EDF0,02:00370250,03:0036A220,04:0038C468,06:003AA0E0,07:0035E9D8,08:00377060,09:00365D70,11:0037D328,12:0036E290,13:00372558,14:003731E8,16:00360888,17:0036C0C8,18:00384CA0,19:00366948,20:0037EB18,22:0036C338,23:00370A50,24:00360008,26:003684B8,30:003691F0 func_002ED9C0 boot 76 5dbe38abd55fb984 27 00:00368AD8,01:0035EE08,02:00370268,03:0036A238,04:0038C480,05:0037CAA8,06:003AA0F8,07:0035E9F0,08:00377078,09:00365D88,10:0037E900,11:0037D340,12:0036E2A8,13:00372570,14:00373200,15:00383430,16:003608A0,17:0036C0E0,18:00384CB8,19:00366960,20:0037EB30,22:0036C350,23:00370A68,24:00360020,25:00376950,26:003684D0,30:00369208 func_002EDA10 boot 1444 3911d551b9e99421 23 00:00368B70,01:0035EEA0,02:00370300,03:0036A2D0,04:0038C518,06:003AA190,07:0035EA88,08:00377110,09:00365E20,11:0037D3D8,12:0036E340,13:00372608,14:00373298,16:00360938,17:0036C178,18:00384D50,19:003669F8,20:0037EBC8,22:0036C3E8,23:00370B00,24:003600B8,26:00368568,30:003692A0 func_002EE000 boot 564 e02434ed982d2727 27 00:00369118,01:0035F448,02:003708A8,03:0036A878,04:0038CAC0,05:0037D978,06:003AA738,07:0035F030,08:003776B8,09:003663C8,10:0037F7D0,11:0037D980,12:0036E8E8,13:00372BB0,14:00373840,15:00384300,16:00360EE0,17:0036C720,18:003852F8,19:00366FA0,20:0037F170,22:0036C990,23:003710A8,24:00360660,25:00377820,26:00368B10,30:00369848 @@ -1949,7 +1939,6 @@ func_002EE8B0 boot 108 39cb94f765fd8735 27 00:003699C8,01:0035FCF8,02:00371158,0 func_002EE920 boot 104 20c6c5ecec7c54d2 27 00:00369A38,01:0035FD68,02:003711C8,03:0036B198,04:0038D3E0,05:0037E5E8,06:003AB058,07:0035F950,08:00377FD8,09:00366CE8,10:00380390,11:0037E2A0,12:0036F208,13:003734D0,14:00374160,15:00384EC0,16:00361800,17:0036D040,18:00385C18,19:003678C0,20:0037FA90,22:0036D2B0,23:003719C8,24:00360F80,25:00378508,26:00369430,30:0036A168 func_002EE988 boot 372 7c3645d3edd48504 27 00:00369AA0,01:0035FDD0,02:00371230,03:0036B200,04:0038D448,05:0037E650,06:003AB0C0,07:0035F9B8,08:00378040,09:00366D50,10:003803F8,11:0037E308,12:0036F270,13:00373538,14:003741C8,15:00384F28,16:00361868,17:0036D0A8,18:00385C80,19:00367928,20:0037FAF8,22:0036D318,23:00371A30,24:00360FE8,25:00378570,26:00369498,30:0036A1D0 func_002EEB00 boot 176 07f154714e9f2c72 27 00:00369C18,01:0035FF48,02:003713A8,03:0036B378,04:0038D5C0,05:0037E7C8,06:003AB238,07:0035FB30,08:003781B8,09:00366EC8,10:00380570,11:0037E480,12:0036F3E8,13:003736B0,14:00374340,15:003850A0,16:003619E0,17:0036D220,18:00385DF8,19:00367AA0,20:0037FC70,22:0036D490,23:00371BA8,24:00361160,25:003786E8,26:00369610,30:0036A348 -func_002EEBB0 boot 20 80046512fd4902e8 23 00:00369CC8,01:0035FFF8,02:00371458,03:0036B428,04:0038D670,06:003AB2E8,07:0035FBE0,08:00378268,09:00366F78,11:0037E530,12:0036F498,13:00373760,14:003743F0,16:00361A90,17:0036D2D0,18:00385EA8,19:00367B50,20:0037FD20,22:0036D540,23:00371C58,24:00361210,26:003696C0,30:0036A3F8 func_002EED08 boot 76 ab5eeb96914e323e 27 00:00369CE0,01:00360010,02:00371470,03:0036B440,04:0038D688,05:0037EFD0,06:003AB300,07:0035FBF8,08:00378280,09:00366F90,10:00380E10,11:0037E548,12:0036F4B0,13:00373778,14:00374408,15:00385940,16:00361AA8,17:0036D2E8,18:00385EC0,19:00367B68,20:0037FD38,22:0036D558,23:00371C70,24:00361228,25:00378EE8,26:003696D8,30:0036A410 func_002EED58 boot 244 3394ab2360b6ec73 27 00:00369D30,01:00360060,02:003714C0,03:0036B490,04:0038D6D8,05:0037F020,06:003AB350,07:0035FC48,08:003782D0,09:00366FE0,10:00380E60,11:0037E598,12:0036F500,13:003737C8,14:00374458,15:00385990,16:00361AF8,17:0036D338,18:00385F10,19:00367BB8,20:0037FD88,22:0036D5A8,23:00371CC0,24:00361278,25:00378F38,26:00369728,30:0036A460 func_002EEE50 boot 128 e7ced99f6bbfe2cf 27 00:00369E28,01:00360158,02:003715B8,03:0036B588,04:0038D7D0,05:0037F118,06:003AB448,07:0035FD40,08:003783C8,09:003670D8,10:00380F58,11:0037E690,12:0036F5F8,13:003738C0,14:00374550,15:00385A88,16:00361BF0,17:0036D430,18:00386008,19:00367CB0,20:0037FE80,22:0036D6A0,23:00371DB8,24:00361370,25:00379030,26:00369820,30:0036A558 @@ -2695,7 +2684,7 @@ func_00329CB8 boot 260 82491f892f2f1e90 27 00:003E3178,01:003E4948,02:004056D0,0 func_00329DC0 boot 156 4ac8523d5073f212 27 00:003E3280,01:003E4A50,02:004057D8,03:003EC6A0,04:0041E000,05:003EBA18,06:00424BD0,07:003CDD08,08:003F1B58,09:003DEB90,10:003EBF40,11:0040DB50,12:003E6EE8,13:003E43E8,14:003F0680,15:003F5C40,16:003D2830,17:003EBFF0,18:00401060,19:003E4D10,20:00404950,22:003DF970,23:003E6EE0,24:003C6710,25:003E46B8,26:003D3B00,30:003DC308 func_00329E60 boot 224 8825569e0043745d 27 00:003E3320,01:003E4AF0,02:00405878,03:003EC740,04:0041E0A0,05:003EBAB8,06:00424C70,07:003CDDA8,08:003F1BF8,09:003DEC30,10:003EBFE0,11:0040DBF0,12:003E6F88,13:003E4488,14:003F0720,15:003F5CE0,16:003D28D0,17:003EC090,18:00401100,19:003E4DB0,20:004049F0,22:003DFA10,23:003E6F80,24:003C67B0,25:003E4758,26:003D3BA0,30:003DC3A8 func_00329F40 shared 496 163226caab62c8f9 27 00:003E3400,01:003E4BD0,02:00405958,03:003EC820,04:0041E180,05:003EBB98,06:00424D50,07:003CDE88,08:003F1CD8,09:003DED10,10:003EC0C0,11:0040DCD0,12:003E7068,13:003E4568,14:003F0800,15:003F5DC0,16:003D29B0,17:003EC170,18:004011E0,19:003E4E90,20:00404AD0,22:003DFAF0,23:003E7060,24:003C6890,25:003E4838,26:003D3C80,30:003DC488 -func_0032A130 boot 16 92d9c346662e3597 27 00:003E35F0,01:003E4DC0,02:00405B48,03:003ECA10,04:0041E370,05:003EBD88,06:00424F40,07:003CE078,08:003F1EC8,09:003DEF00,10:003EC2B0,11:0040DEC0,12:003E7258,13:003E4758,14:003F09F0,15:003F5FB0,16:003D2BA0,17:003EC360,18:004013D0,19:003E5080,20:00404CC0,22:003DFCE0,23:003E7250,24:003C6A80,25:003E4A28,26:003D3E70,30:003DC678 +func_0032A130 boot 8 bc6e15da5a72ab85 27 00:003E35F8,01:003E4DC8,02:00405B50,03:003ECA18,04:0041E378,05:003EBD90,06:00424F48,07:003CE080,08:003F1ED0,09:003DEF08,10:003EC2B8,11:0040DEC8,12:003E7260,13:003E4760,14:003F09F8,15:003F5FB8,16:003D2BA8,17:003EC368,18:004013D8,19:003E5088,20:00404CC8,22:003DFCE8,23:003E7258,24:003C6A88,25:003E4A30,26:003D3E78,30:003DC680 func_L00_003E2180 shared 912 c10da9a183e5018a 27 00:003E3600,01:003E4DD0,02:00405EE0,03:003ECA20,04:0041E380,05:003EBD98,06:00424F50,07:003CE540,08:003F1ED8,09:003DF050,10:003EC2C0,11:0040DED0,12:003E7268,13:003E4768,14:003F0A00,15:003F5FC0,16:003D2BB0,17:003EC370,18:004013E0,19:003E5090,20:00404CD0,22:003DFCF0,23:003E7260,24:003C6A90,25:003E4A38,26:003D4208,30:003DC688 func_L00_003E2510 shared 1724 1d02a6f972ec5d6b 27 00:003E3990,01:003E5160,02:00406270,03:003ECDB0,04:0041E710,05:003EC128,06:004252E0,07:003CE8D0,08:003F2268,09:003DF3E0,10:003EC650,11:0040E260,12:003E75F8,13:003E4AF8,14:003F0D90,15:003F6350,16:003D2F40,17:003EC700,18:00401770,19:003E5420,20:00405060,22:003E0080,23:003E75F0,24:003C6E20,25:003E4DC8,26:003D4598,30:003DCA18 func_L00_003E2BD0 shared 684 cfa44d8aa5fd65ab 27 00:003E4050,01:003E5820,02:00406930,03:003ED470,04:0041EDD0,05:003EC7E8,06:004259A0,07:003CEF90,08:003F2928,09:003DFAA0,10:003ECD10,11:0040E920,12:003E7CB8,13:003E51B8,14:003F1450,15:003F6A10,16:003D3600,17:003ECDC0,18:00401E30,19:003E5AE0,20:00405720,22:003E0740,23:003E7CB0,24:003C74E0,25:003E5488,26:003D4C58,30:003DD0D8 @@ -3113,7 +3102,8 @@ func_L00_00424AD8 shared 68 56dec582b1352c2e 27 00:00425FE8,01:00429278,02:00451 func_L00_00424B20 shared 36 ab08622a9389d465 27 00:00426030,01:004292C0,02:00451AA8,03:00437F68,04:00468850,05:0043EDC0,06:00477330,07:00422760,08:00442B70,09:00434E60,10:00440BA8,11:004874E8,12:0043C0D8,13:00438450,14:004445F8,15:0044B790,16:00430EC0,17:00432BB0,18:004534C0,19:00437DA8,20:0045D1E8,22:00427430,23:0043CA68,24:00406178,25:0042F780,26:00418DC8,30:00429CF8 func_L00_00424B48 shared 36 6af8db7ac3d8ba67 27 00:00426058,01:004292E8,02:00451AD0,03:00437F90,04:00468878,05:0043EDE8,06:00477358,07:00422788,08:00442B98,09:00434E88,10:00440BD0,11:00487510,12:0043C100,13:00438478,14:00444620,15:0044B7B8,16:00430EE8,17:00432BD8,18:004534E8,19:00437DD0,20:0045D210,22:00427458,23:0043CA90,24:004061A0,25:0042F7A8,26:00418DF0,30:00429D20 func_L00_00424B70 shared 72 6b8116fb9abb08d4 27 00:00426080,01:00429310,02:00451AF8,03:00437FB8,04:004688A0,05:0043EE10,06:00477380,07:004227B0,08:00442BC0,09:00434EB0,10:00440BF8,11:00487538,12:0043C128,13:004384A0,14:00444648,15:0044B7E0,16:00430F10,17:00432C00,18:00453510,19:00437DF8,20:0045D238,22:00427480,23:0043CAB8,24:004061C8,25:0042F7D0,26:00418E18,30:00429D48 -func_L00_00424BB8 shared 72 6b8116fb9abb08d4 27 00:004260C8,01:00429358,02:00451B40,03:00438000,04:004688E8,05:0043EE58,06:004773C8,07:004227F8,08:00442C08,09:00434EF8,10:00440C40,11:00487580,12:0043C170,13:004384E8,14:00444690,15:0044B828,16:00430F58,17:00432C48,18:00453558,19:00437E40,20:0045D280,22:004274C8,23:0043CB00,24:00406210,25:0042F818,26:00418E60,30:00429D90 +func_L00_00424BB8 shared 72 6b8116fb9abb08d4 27 00:004260C8,01:00429358,02:00451B40,03:00438000,04:004688E8,05:0043EE58,06:004773C8,07:004227F8,08:00442C08,09:00434EF8,10:00440C40,11:00487580,12:0043C170,13:004384E8,14:00444690,15:0044B828,16:00430FA0,17:00432C48,18:00453558,19:00437E40,20:0045D280,22:00427510,23:0043CB48,24:00406210,25:0042F818,26:00418EA8,30:00429D90 +func_L16_0042FB10 shared 72 6b8116fb9abb08d4 4 16:00430F58,22:004274C8,23:0043CB00,26:00418E60 func_L00_00424C00 shared 40 be6002e7a1fe3fa7 27 00:00426110,01:004293A0,02:00451B88,03:00438048,04:00468930,05:0043EEA0,06:00477410,07:00422840,08:00442C50,09:00434F40,10:00440C88,11:004875C8,12:0043C1B8,13:00438530,14:004446D8,15:0044B870,16:00430FE8,17:00432C90,18:004535A0,19:00437E88,20:0045D2C8,22:00427558,23:0043CB90,24:00406258,25:0042F860,26:00418EF0,30:00429DD8 func_L00_00424C28 shared 40 aae0e898ffaaf025 27 00:00426138,01:004293C8,02:00451BB0,03:00438070,04:00468958,05:0043EEC8,06:00477438,07:00422868,08:00442C78,09:00434F68,10:00440CB0,11:004875F0,12:0043C1E0,13:00438558,14:00444700,15:0044B898,16:00431010,17:00432CB8,18:004535C8,19:00437EB0,20:0045D2F0,22:00427580,23:0043CBB8,24:00406280,25:0042F888,26:00418F18,30:00429E00 func_L00_00424C60 shared 48 fd57c438f19d737e 27 00:00426170,01:00429400,02:00451BE8,03:004380A8,04:00468990,05:0043EF00,06:00477470,07:004228A0,08:00442CB0,09:00434FA0,10:00440CE8,11:00487628,12:0043C218,13:00438590,14:00444738,15:0044B8D0,16:00431048,17:00432CF0,18:00453600,19:00437EE8,20:0045D328,22:004275B8,23:0043CBF0,24:004062B8,25:0042F8C0,26:00418F50,30:00429E38 @@ -3304,7 +3294,7 @@ func_US2_0033AB18 boot 1100 beb727a440a906eb 27 00:00430B30,01:00433BB8,02:0045C func_US2_0033AF70 boot 1204 9badf2520571595f 27 00:00430F88,01:00434010,02:0045C708,03:004420D0,04:00474908,05:0044CF08,06:00482D00,07:0042C9D0,08:0044CFF0,09:0043FC70,10:0044EA80,11:00492E98,12:00447690,13:00445058,14:0044F358,15:00459BC0,16:0043C908,17:0043DBE8,18:0045E740,19:004422D8,20:00468140,22:00431988,23:00446FC0,24:0040FE68,25:0043D6A8,26:004235C0,30:00433CE0 func_US2_0033B428 boot 192 b5ebd7fa9845644d 27 00:00431440,01:004344C8,02:0045CBC0,03:00442588,04:00474DC0,05:0044D3C0,06:004831B8,07:0042CE88,08:0044D4A8,09:00440128,10:0044EF38,11:00493350,12:00447B48,13:00445510,14:0044F810,15:0045A078,16:0043CDC0,17:0043E0A0,18:0045EBF8,19:00442790,20:004685F8,22:00431E40,23:00447478,24:00410320,25:0043DB60,26:00423A78,30:00434198 func_0033A4A0 boot 116 e332baad9fd7f4ff 27 00:00431500,01:00434588,02:0045CC80,03:00442648,04:00474E80,05:0044D480,06:00483278,07:0042CF48,08:0044D568,09:004401E8,10:0044EFF8,11:00493410,12:00447C08,13:004455D0,14:0044F8D0,15:0045A138,16:0043CE80,17:0043E160,18:0045ECB8,19:00442850,20:004686B8,22:00431F00,23:00447538,24:004103E0,25:0043DC20,26:00423B38,30:00434258 -func_0033A520 boot 360 5770489227d41706 27 00:00431580,01:00434608,02:0045CD00,03:004426C8,04:00474F00,05:0044D500,06:004832F8,07:0042CFC8,08:0044D5E8,09:00440268,10:0044F078,11:00493490,12:00447C88,13:00445650,14:0044F950,15:0045A1B8,16:0043CF00,17:0043E1E0,18:0045ED38,19:004428D0,20:00468738,22:00431F80,23:004475B8,24:00410460,25:0043DCA0,26:00423BB8,30:004342D8 +func_US2_0033B568 boot 360 5770489227d41706 27 00:00431580,01:00434608,02:0045CD00,03:004426C8,04:00474F00,05:0044D500,06:004832F8,07:0042CFC8,08:0044D5E8,09:00440268,10:0044F078,11:00493490,12:00447C88,13:00445650,14:0044F950,15:0045A1B8,16:0043CF00,17:0043E1E0,18:0045ED38,19:004428D0,20:00468738,22:00431F80,23:004475B8,24:00410460,25:0043DCA0,26:00423BB8,30:004342D8 func_US2_0033B6D0 boot 76 8a807e20da101c0f 27 00:004316E8,01:00434770,02:0045CE68,03:00442830,04:00475068,05:0044D668,06:00483460,07:0042D130,08:0044D750,09:004403D0,10:0044F1E0,11:004935F8,12:00447DF0,13:004457B8,14:0044FAB8,15:0045A320,16:0043D068,17:0043E348,18:0045EEA0,19:00442A38,20:004688A0,22:004320E8,23:00447720,24:004105C8,25:0043DE08,26:00423D20,30:00434440 func_US2_0033B720 boot 748 eeb41694f695cda4 27 00:00431738,01:004347C0,02:0045CEB8,03:00442880,04:004750B8,05:0044D6B8,06:004834B0,07:0042D180,08:0044D7A0,09:00440420,10:0044F230,11:00493648,12:00447E40,13:00445808,14:0044FB08,15:0045A370,16:0043D0B8,17:0043E398,18:0045EEF0,19:00442A88,20:004688F0,22:00432138,23:00447770,24:00410618,25:0043DE58,26:00423D70,30:00434490 func_US2_0033BA10 boot 8 fa944ab4d1efe408 27 00:00431A28,01:00434AB0,02:0045D1A8,03:00442B70,04:004753A8,05:0044D9A8,06:004837A0,07:0042D470,08:0044DA90,09:00440710,10:0044F520,11:00493938,12:00448130,13:00445AF8,14:0044FDF8,15:0045A660,16:0043D3A8,17:0043E688,18:0045F1E0,19:00442D78,20:00468BE0,22:00432428,23:00447A60,24:00410908,25:0043E148,26:00424060,30:00434780 @@ -3324,7 +3314,6 @@ func_US2_0033C098 boot 88 c6c24c7b76f6f979 27 00:004320B0,01:00435138,02:0045D83 func_US2_0033C0F0 boot 8 ca765ef3cd00b26c 27 00:00432108,01:00435190,02:0045D888,03:00443250,04:00475A88,05:0044E088,06:00483E80,07:0042DB50,08:0044E170,09:00440DF0,10:0044FC00,11:00494018,12:00448810,13:004461D8,14:004504D8,15:0045AD40,16:0043DA88,17:0043ED68,18:0045F8C0,19:00443458,20:004692C0,22:00432B08,23:00448140,24:00410FE8,25:0043E828,26:00424740,30:00434E60 func_US2_0033C100 boot 164 716936ee6d2ffced 27 00:00432118,01:004351A0,02:0045D898,03:00443260,04:00475A98,05:0044E098,06:00483E90,07:0042DB60,08:0044E180,09:00440E00,10:0044FC10,11:00494028,12:00448820,13:004461E8,14:004504E8,15:0045AD50,16:0043DA98,17:0043ED78,18:0045F8D0,19:00443468,20:004692D0,22:00432B18,23:00448150,24:00410FF8,25:0043E838,26:00424750,30:00434E70 func_US2_0033C1B8 boot 964 9dff5ed70b95d6e7 27 00:004321D0,01:00435258,02:0045D950,03:00443318,04:00475B50,05:0044E150,06:00483F48,07:0042DC18,08:0044E238,09:00440EB8,10:0044FCC8,11:004940E0,12:004488D8,13:004462A0,14:004505A0,15:0045AE08,16:0043DB50,17:0043EE30,18:0045F988,19:00443520,20:00469388,22:00432BD0,23:00448208,24:004110B0,25:0043E8F0,26:00424808,30:00434F28 -func_0033B538 boot 4 b88cc87420eed4aa 27 00:00432598,01:00435620,02:0045DD18,03:004436E0,04:00475F18,05:0044E518,06:00484310,07:0042DFE0,08:0044E600,09:00441280,10:00450090,11:004944A8,12:00448CA0,13:00446668,14:00450968,15:0045B1D0,16:0043DF18,17:0043F1F8,18:0045FD50,19:004438E8,20:00469750,22:00432F98,23:004485D0,24:00411478,25:0043ECB8,26:00424BD0,30:004352F0 func_US2_0033C588 boot 972 70048804331a0ab2 27 00:004325A0,01:00435628,02:0045DD20,03:004436E8,04:00475F20,05:0044E520,06:00484318,07:0042DFE8,08:0044E608,09:00441288,10:00450098,11:004944B0,12:00448CA8,13:00446670,14:00450970,15:0045B1D8,16:0043DF20,17:0043F200,18:0045FD58,19:004438F0,20:00469758,22:00432FA0,23:004485D8,24:00411480,25:0043ECC0,26:00424BD8,30:004352F8 func_US2_0033C958 boot 1060 0552a8156423eca6 27 00:00432970,01:004359F8,02:0045E0F0,03:00443AB8,04:004762F0,05:0044E8F0,06:004846E8,07:0042E3B8,08:0044E9D8,09:00441658,10:00450468,11:00494880,12:00449078,13:00446A40,14:00450D40,15:0045B5A8,16:0043E2F0,17:0043F5D0,18:00460128,19:00443CC0,20:00469B28,22:00433370,23:004489A8,24:00411850,25:0043F090,26:00424FA8,30:004356C8 func_US2_L00_00432D98 shared 44 d221205177b3720f 27 00:00432D98,01:00435E20,02:0045E518,03:00443EE0,04:00476718,05:0044ED18,06:00484B10,07:0042E7E0,08:0044EE00,09:00441A80,10:00450890,11:00494CA8,12:004494A0,13:00446E68,14:00451168,15:0045B9D0,16:0043E718,17:0043F9F8,18:00460550,19:004440E8,20:00469F50,22:00433798,23:00448DD0,24:00411C78,25:0043F4B8,26:004253D0,30:00435AF0 @@ -3516,7 +3505,6 @@ func_00349498 boot 52 90c4f9366d05f9e9 27 00:004401F0,01:00443278,02:0046B970,03 func_003494D0 boot 180 cdea45d13cf19835 27 00:00440228,01:004432B0,02:0046B9A8,03:00451370,04:00483BA8,05:0045C1A8,06:00491FA0,07:0043BC70,08:0045C290,09:0044EF10,10:0045DD20,11:004A2138,12:00456930,13:004542F8,14:0045E5F8,15:00468E60,16:0044BBA8,17:0044CE88,18:0046D9E0,19:00451578,20:004773E0,22:00440C28,23:00456260,24:0041F108,25:0044C948,26:00432860,30:00442F80 func_00349590 boot 8 31fcd37f04a168ac 27 00:004402E8,01:00443370,02:0046BA68,03:00451430,04:00483C68,05:0045C268,06:00492060,07:0043BD30,08:0045C350,09:0044EFD0,10:0045DDE0,11:004A21F8,12:004569F0,13:004543B8,14:0045E6B8,15:00468F20,16:0044BC68,17:0044CF48,18:0046DAA0,19:00451638,20:004774A0,22:00440CE8,23:00456320,24:0041F1C8,25:0044CA08,26:00432920,30:00443040 func_003495A0 boot 20 04ffc67212d027e8 27 00:004402F8,01:00443380,02:0046BA78,03:00451440,04:00483C78,05:0045C278,06:00492070,07:0043BD40,08:0045C360,09:0044EFE0,10:0045DDF0,11:004A2208,12:00456A00,13:004543C8,14:0045E6C8,15:00468F30,16:0044BC78,17:0044CF58,18:0046DAB0,19:00451648,20:004774B0,22:00440CF8,23:00456330,24:0041F1D8,25:0044CA18,26:00432930,30:00443050 -func_003495B8 boot 4 3d685cd8e4c14f74 27 00:00440310,01:00443398,02:0046BA90,03:00451458,04:00483C90,05:0045C290,06:00492088,07:0043BD58,08:0045C378,09:0044EFF8,10:0045DE08,11:004A2220,12:00456A18,13:004543E0,14:0045E6E0,15:00468F48,16:0044BC90,17:0044CF70,18:0046DAC8,19:00451660,20:004774C8,22:00440D10,23:00456348,24:0041F1F0,25:0044CA30,26:00432948,30:00443068 func_003495C0 boot 8 057181dc76824f67 27 00:00440318,01:004433A0,02:0046BA98,03:00451460,04:00483C98,05:0045C298,06:00492090,07:0043BD60,08:0045C380,09:0044F000,10:0045DE10,11:004A2228,12:00456A20,13:004543E8,14:0045E6E8,15:00468F50,16:0044BC98,17:0044CF78,18:0046DAD0,19:00451668,20:004774D0,22:00440D18,23:00456350,24:0041F1F8,25:0044CA38,26:00432950,30:00443070 func_003495C8 boot 12 e1f7ad89507f65b8 27 00:00440320,01:004433A8,02:0046BAA0,03:00451468,04:00483CA0,05:0045C2A0,06:00492098,07:0043BD68,08:0045C388,09:0044F008,10:0045DE18,11:004A2230,12:00456A28,13:004543F0,14:0045E6F0,15:00468F58,16:0044BCA0,17:0044CF80,18:0046DAD8,19:00451670,20:004774D8,22:00440D20,23:00456358,24:0041F200,25:0044CA40,26:00432958,30:00443078 func_003495D8 boot 52 b36c02b8071d414a 27 00:00440330,01:004433B8,02:0046BAB0,03:00451478,04:00483CB0,05:0045C2B0,06:004920A8,07:0043BD78,08:0045C398,09:0044F018,10:0045DE28,11:004A2240,12:00456A38,13:00454400,14:0045E700,15:00468F68,16:0044BCB0,17:0044CF90,18:0046DAE8,19:00451680,20:004774E8,22:00440D30,23:00456368,24:0041F210,25:0044CA50,26:00432968,30:00443088 @@ -3688,7 +3676,6 @@ func_L01_002C81D0 shared 1112 32c9103c4849315f 4 01:002C8510,07:002C8C40,11:002E func_L01_002C8990 shared 24 84a2a5424332baa5 8 01:002C8CD0,04:002F3CF8,07:002C9400,08:002DF2F0,09:002CF528,16:002CC7C8,18:002EDDB8,19:002D0EC8 func_L01_002C89A8 shared 24 6b45132fd916ce72 8 01:002C8CE8,04:002F3D10,07:002C9418,08:002DF308,09:002CF540,16:002CC7E0,18:002EDDD0,19:002D0EE0 func_L01_002C98B8 shared 84 16ac879f40fb6240 10 01:002C9BF8,02:002D79D8,03:002D5058,04:002F4C20,08:002E0218,09:002D0450,12:002D7AC8,17:002D5558,20:002E83F8,30:002DB1D8 -func_00280660 boot 12 2c1054e663689292 22 01:002E0AB0,02:002EE9F0,03:002EBFC0,05:00304148,06:0032AB28,09:002E73C0,10:00306648,11:002FD140,12:002EE8E8,13:002F5EA8,15:00304748,16:002E4618,17:002EC478,18:00305CB8,19:002E8FE0,20:002FF420,22:002F1598,23:002F5C78,24:002EA360,25:002FE718,26:002EBA60,30:002F2378 func_L01_002E1510 shared 348 55a78a077cf6b229 13 01:002E2218,02:002F07E8,03:002ED9E8,06:0032C640,07:002E32C8,08:002F8DF0,09:002E8D58,12:002F0310,13:002F78D0,16:002E6040,17:002EDE10,18:00307650,20:00300DB8 func_L01_002E1680 shared 416 9c43b8d26395bd91 5 01:002E2388,02:002F0F28,03:002EE160,06:0032C7B0,16:002E6568 func_L01_002E2608 shared 388 2e52620f6c8c4719 4 01:002E3310,02:002F1EB0,09:002EA280,11:00300378 @@ -3926,7 +3913,6 @@ func_L01_0041C960 level 16 892435a81e3ee6c6 1 01:0041DEE0 func_L01_0041C970 level 1332 6593b271e41dea1c 1 01:0041DEF0 func_L01_0042A568 shared 380 0fb94da10a0f6c4a 3 01:0042BAF8,08:004453A8,09:00437698 func_L01_0042A6F0 shared 132 50f157939ba32647 8 01:0042BC80,02:004542F0,08:00445530,09:00437820,11:00489D30,18:00456F20,19:0043A5F0,20:0045FA30 -func_L01_0042C450 level 12 d307e18564eccf77 1 01:0042D990 func_L01_0042C540 level 920 5f76d9301b50558c 1 01:0042DA80 func_L01_0042C8D8 level 1440 2d9082ddb868dbce 1 01:0042DE18 func_L01_0042CE78 level 108 09b1f78f8f48d1f4 1 01:0042E3B8 @@ -4542,7 +4528,7 @@ func_L03_00419C58 shared 72 491f849a4425c9d5 2 03:0041B318,14:004222A8 func_L03_00419CA0 level 1004 68c570849857709a 1 03:0041B360 func_L03_0041A090 level 1244 3cb82e04030879c7 1 03:0041B750 func_L03_0041A570 level 1088 c753b1399741523e 1 03:0041BC30 -func_L03_0041B848 shared 16 bacb80d8a8a76e20 5 03:0041CF08,16:004100D8,19:0041A670,24:003FB2C8,30:0040E808 +func_L03_0041B848 shared 8 bc6e15da5a72ab85 5 03:0041CF10,16:004100E0,19:0041A678,24:003FB2D0,30:0040E810 func_US2_L03_0041D510 level 3112 d91922fb70b89d59 1 03:0041D510 func_US2_L03_0041E138 level 1076 6556f82406902d8e 1 03:0041E138 func_L03_0041CEB0 level 504 bcff02390acc958c 1 03:0041E570 @@ -4858,9 +4844,7 @@ func_US2_L05_00315A58 level 920 030f2fd6e8a2f041 1 05:00315A58 func_L05_00324DB8 shared 48 6c09c7e322c2fc4f 4 05:00325FB8,10:003286C0,15:00326790,25:00320310 func_L05_003251A0 shared 40 6cab5decfc93b908 4 05:00326370,10:00328A78,15:00326B48,25:003206C8 func_US2_L05_00327640 shared 28 633763349d2d48fd 4 05:00327640,10:00329D48,15:00327E18,25:00321998 -func_L05_0033CD40 shared 28 261e6410d33b6cf9 6 05:0033DFC0,10:0033FD20,22:0032C0D8,23:003307F0,24:00323228,25:00338168 func_L05_0033D3A0 shared 1840 5aabb9e0f52fa405 5 05:0033E6D8,10:00340438,24:00323940,25:00338880,30:0032C5C8 -func_L05_0033F4A8 shared 156 dfc292e5124853e5 5 05:003407E0,10:00342540,24:00325A48,25:0033A988,30:0032E9A0 func_L05_00352B28 shared 360 162c615314ebd680 2 05:00353E60,10:00355C70 func_L05_00367340 level 272 0afef68722a866dc 1 05:00368498 func_L05_00379968 shared 504 8e45051a7f70cab0 4 05:0037ABD8,10:0037C9E8,15:00381400,25:00374C18 @@ -4896,12 +4880,10 @@ func_L05_0037B280 shared 284 8c80d8d7d42558d0 4 05:0037C4F0,10:0037E2B8,15:00382 func_L05_0037B3A0 shared 148 9f639856800e0a66 4 05:0037C610,10:0037E3D8,15:00382E38,25:003765B0 func_L05_0037B440 shared 248 46c4d0c726225dc5 3 05:0037C6B0,10:0037E508,15:00383038 func_L05_0037B538 shared 292 e268379035d983b1 4 05:0037C7A8,10:0037E600,15:00383130,25:00376650 -func_L05_0037B6C0 shared 12 acd8435708569046 4 05:0037C930,10:0037E788,15:003832B8,25:003767D8 func_L05_0037B6D0 shared 356 b48a41ba8713f007 4 05:0037C940,10:0037E798,15:003832C8,25:003767E8 func_L05_0037B888 shared 188 074e5a0a635cbef1 4 05:0037CAF8,10:0037E950,15:00383480,25:003769A0 func_L05_0037B948 shared 480 141355b131c746e8 4 05:0037CBB8,10:0037EA10,15:00383540,25:00376A60 func_L05_0037BB28 shared 80 1847ba6c486ae642 4 05:0037CD98,10:0037EBF0,15:00383720,25:00376C40 -func_L05_0037BB78 shared 20 ae8017e88ecc5608 4 05:0037CDE8,10:0037EC40,15:00383770,25:00376C90 func_L05_0037BB90 shared 40 d49888e7fb4c73ff 4 05:0037CE00,10:0037EC58,15:00383788,25:00376CA8 func_L05_0037BBB8 shared 68 f314cb3e4c5bbc68 4 05:0037CE28,10:0037EC80,15:003837B0,25:00376CD0 func_L05_0037BC08 shared 312 0d0660b92e96e730 4 05:0037CE78,10:0037ECD0,15:00383800,25:00376D20 @@ -5664,7 +5646,6 @@ func_L09_003F9D08 shared 888 62dbd05c3c02e148 2 09:003FB198,20:004205C0 func_L09_003FA080 shared 4512 68ce8924f268dad7 2 09:003FB510,20:00420938 func_L09_003FB4D0 level 384 7f076b73cba047d6 1 09:003FC960 func_L09_003FB650 level 300 9db1faccbdcb90c5 1 09:003FCAE0 -func_L09_003FB780 shared 4 dc2834da92d18696 3 09:003FCC10,22:003BA420,23:003BEA18 func_L09_003FB788 level 216 e4c8e58e6334973d 1 09:003FCC18 func_L09_003FB860 level 164 05f35498e2940d7d 1 09:003FCCF0 func_L09_003FB908 level 240 5ad3f7223d0c4fef 1 09:003FCD98 @@ -5785,7 +5766,8 @@ func_L10_00418AD8 level 196 a4f84aac34e37867 1 10:0041A078 func_L10_00418BA0 level 488 efe1042c999080de 1 10:0041A140 func_L10_00418D88 shared 868 4dfc9d329ddae9b0 2 10:0041A328,15:00421538 func_L10_004190F0 shared 152 ba1c88de52c245a4 2 10:0041A690,15:004218A0 -func_L10_00419188 level 96 741d326f9af76cac 1 10:0041A728 +func_L10_00419188 level 88 118d456fa41c7684 1 10:0041A728 +func_L10_004191E0 level 8 bc6e15da5a72ab85 1 10:0041A780 func_L10_004191E8 shared 352 365c7aababcf0193 2 10:0041A788,15:00421940 func_L10_00419348 shared 560 62b196008920cabb 2 10:0041A8E8,15:00421AA0 func_L10_0041EC10 level 316 5fb3e4d4ef580dbb 1 10:004201B0 @@ -6459,7 +6441,6 @@ func_L14_004321C8 level 8 bc6e15da5a72ab85 1 14:004337A8 func_L14_004321D0 level 636 774acd0b26518319 1 14:004337B0 func_L14_00432450 level 504 f50eb379a9ead1f1 1 14:00433A30 func_US2_L15_00316058 level 1392 965ef0ee3d1cd0eb 1 15:00316058 -func_002B0A08 boot 12 f5734634747b0b7d 3 15:0033F6D8,19:003249A8,26:00326BF0 func_L15_0036DAB0 shared 272 33f9b608293f2353 2 15:0036EC10,18:00372220 func_L15_003804B8 level 44 38effbdcc28ad3fd 1 15:00381730 func_L15_00381CF0 level 208 076916ba408e5a4d 1 15:00382F68 @@ -6639,7 +6620,6 @@ func_L16_0041F1F0 level 364 a106e4c53e568836 1 16:00420628 func_L16_0041F360 level 576 355ebcb3a8abc9ef 1 16:00420798 func_L16_0041F950 shared 368 2c000a38e014aee3 2 16:00420D88,30:00415DC0 func_L16_00424B48 level 160 11176b4d7453abba 1 16:00425F88 -func_L16_0042FB58 shared 72 6b8116fb9abb08d4 4 16:00430FA0,22:00427510,23:0043CB48,26:00418EA8 func_L16_00435CE8 level 1988 7de4e0ba73d38623 1 16:00437110 func_L16_004364B0 shared 32 ddd8e32f9e36739a 4 16:004378D8,22:0042C958,23:00441F90,26:0041E2F0 func_L17_00326F38 shared 104 75e1169fb4573d97 2 17:00328228,18:00340EF8 @@ -7354,7 +7334,6 @@ func_L23_0041E260 level 44 ef7c5a2acfe4ae55 1 23:0041F760 func_L23_0041E290 level 308 185178c273d9e591 1 23:0041F790 func_L23_0041E3C8 level 76 ae7ce52a1d270c98 1 23:0041F8C8 func_L23_0041E418 level 284 a53d0483ecb7f3ad 1 23:0041F918 -func_L23_0041E538 level 12 34b07fab5514db8f 1 23:0041FA38 func_L23_0041E548 level 36 187a50c96ffbc146 1 23:0041FA48 func_L23_0041E570 level 64 48bef8eca57e3ae4 1 23:0041FA70 func_L23_0041E5B0 level 168 528ef386129f58cd 1 23:0041FAB0 @@ -7406,9 +7385,6 @@ func_L24_00383C30 level 776 c7a510fc40a7c859 1 24:00385028 func_L24_00389210 level 5868 33e55b89ba6d3fff 1 24:0038A638 func_L24_003B3C38 level 1804 1d0b85ea78387d2f 1 24:003B5078 func_L24_003EFA38 shared 1368 8439c2bb45da83ae 2 24:003F0F38,25:00410CF0 -func_L25_00373ED0 level 4 be96ef5f6a9b0a3a 1 25:00375140 -func_L25_00373EE0 level 20 97a7ba7bf7023520 1 25:00375150 -func_L25_00373F08 level 4 e948bc05cd743d07 1 25:00375178 func_L25_003752D8 level 104 1a73540a442fc2e3 1 25:00376548 func_L25_00376FE0 level 120 92f9ed972df6799e 1 25:00378250 func_L25_00377608 level 120 92f9ed972df6799e 1 25:00378878 @@ -7438,7 +7414,6 @@ func_L26_003DF7E8 level 784 43b085032a92fa50 1 26:003E0CF8 func_L26_004070F8 level 312 dc976ff74304c418 1 26:00408698 func_L26_0040C8A8 level 232 a4accbed98c96ba0 1 26:0040DE48 func_L26_0041C598 level 1988 2e63af6bac8510ca 1 26:0041DB28 -func_L30_0032AAF0 level 20 5e3c9c126e52756e 1 30:0032BBA8 func_L30_003557F0 level 272 0a5d439688de1ee9 1 30:00356780 func_L30_00382EF0 level 28 0aec05893bf71f32 1 30:00384100 func_L30_00382F10 level 168 f6638a3f3ba13659 1 30:00384120 diff --git a/config/us2/not_carried.tsv b/config/us2/not_carried.tsv index de99cb547..afee57324 100644 --- a/config/us2/not_carried.tsv +++ b/config/us2/not_carried.tsv @@ -71,3 +71,4 @@ func_003458F8 boot: instruction at +0x34 differs func_00345B78 boot: instruction at +0x20 differs func_0034E070 boot: instruction differs func_002CAF18 00_aranos_tutorial: instruction at +0x30 differs +func_0033A520 00_aranos_tutorial: instruction at +0x24 differs diff --git a/docs/COMPILER-NOTES.md b/docs/COMPILER-NOTES.md index 34b65c79b..d856ca393 100644 --- a/docs/COMPILER-NOTES.md +++ b/docs/COMPILER-NOTES.md @@ -192,6 +192,8 @@ wrong profile with extra operations or knowingly false prototypes. | Public SDK/libgcc source differs under game compiler | sdk profile, accurate types and inline declarations | func_00122800, func_00122B00 | | libgcc `_eh.o` (L_eh): preserve the frame at final calls and place the exception-return stub correctly | sdk profile with -fexceptions, as GCC's libgcc Makefile builds _eh.o (rac3-decomp builds its copy the same way) | func_00120A30, func_001208E8; paired throw/rethrow func_00120F00 and func_001210E0 | | Whole GPR save area uses sq/lq | -mastra-quad-saves | func_00119BC8, func_00115F28, func_00115C90 | +| Quad slots: `sd $ra` below `sq $s0` | -mastra-quad-saves -frac2-narrow-saves-below, `register_precision(ra, 64)` | func_L01_00324550, func_L08_00389B68 | +| Copy of a zero set in the same block stays a register copy | -frac2-keep-block-zero-copy | func_002F7320 | | Two-word truncation cannot fill return slot | -mastra-split-trunc-slot | func_0012E8C8 | | SDK unit: a volatile access or sign extension fills a `jal`/`jr` slot | -Wa,--r5900-swap-branch-slots | func_001253A8, func_0012E378, func_0011C000 | | Arguments spilled and branch to common epilogue | Measured -O0 unit, not an invented varargs helper | func_001175F0 | @@ -357,6 +359,34 @@ Witnesses include `func_00119BC8` (48 bytes), `func_00115F28` (80) and `func_00115C90` (92). The last also needs its failure value compared as unsigned `0xFFFFFFFF` to preserve the immediate sequence. +Two variadic level functions mix widths in quad slots: func_L01_00324550 (132 bytes, +11 places; `sd $ra,0x200` below `sq $s0,0x210`) and func_L08_00389B68 (264 bytes, 4 places; +`sd $ra,0x0` below `sq $s0,0x10`), each restoring `lq $s0` before `ld $ra`. A scan of every +catalogue prologue finds one other frame mixing `sq` and `sd` GPR saves, func_L02_00411D18 +(`sq $s2` in a 16-byte slot below 8-byte ones), which this rule does not cover. The stock EE +attribute `register_precision(ra, 64)` on the prototype narrows the `$ra` save to `sd`, but +the save loop still gives `$ra` the top slot. +[narrow_saves_below.py](../tools/compiler/transformers/narrow_saves_below.py) adds +`-frac2-narrow-saves-below`: with `-mastra-quad-saves` the loop walks the registers saved at +the slot's full width first, then the narrower ones, so the narrower save sits below. A frame +whose saves all have one width keeps `$ra` on top, as func_00115C90 and func_00115FC0 do; +without `-mastra-quad-saves` the option has no effect. Forced on in every game unit, it changes +none of 7,572 (144 SDK units use another compiler). `register_precision` sets the mode for the +rest of the unit, so each function has a file of its own. The attribute is an inference from +the save widths, not a recovered source line. + +func_002F7320 (132 bytes, 28 places) starts `daddu $t1,$zero,$zero ... daddu $a3,$t1,$zero` +for `int result = 0; int i = result;`. Stock cse folds that copy to `move $a3,$0`: CONST_INT +costs 0 and a pseudo 1. With the copy alive, result=0 has a dependent, sched1 moves it ahead +of the argument copies and allocation becomes retail's (a0 value, a3 i, t1 result). +[keep_block_zero_copy.py](../tools/compiler/transformers/keep_block_zero_copy.py) adds +`-frac2-keep-block-zero-copy`: cse keeps a copy from one pseudo to another whose value is known +to be 0 when its source is set earlier in the same basic block; the REG_EQUAL note still gives +loop.c the zero start. Without the same-block limit, forced on, it changes one matched body, +func_00349680, where jump1's duplicated loop-exit copy `lo = hi` sees a zero from an earlier +block and retail keeps `move $18,$0`. With the limit, forced on in every game unit, it changes +none of 7,577 others (144 SDK units use another compiler). + Patch 0057 enables `-mastra-split-trunc-slot`: split `truncdisi2` after reload and before scheduling so its second shift can fill the return slot. `func_0012E8C8` changes from 32 to retail's 28 bytes. Dedicated files prevent either option from @@ -1493,6 +1523,7 @@ oracle, and a same-size draft screen is not a match or current progress. | TImode reload count | [test_ti_one_gpr.py](../tests/test_ti_one_gpr.py) | | Inheritance into non-spill registers | [test_reload_reg_used_guard.py](../tests/test_reload_reg_used_guard.py) | | Null-pointer-check pass | [test_no_null_pointer_checks.py](../tests/test_no_null_pointer_checks.py) | +| Width-ordered quad saves | [test_narrow_saves_below.py](../tests/test_narrow_saves_below.py) | | Masks/sign seed | [test_dli_masks.py](../tests/test_dli_masks.py) | | Inline li.d into GPRs | [test_inline_li_d.py](../tests/test_inline_li_d.py) | | Hazard labels | [test_hazard_labels.py](../tests/test_hazard_labels.py), [hazard_labels.s](../tests/fixtures/hazard_labels.s) | diff --git a/docs/MATCHING-BLOCKERS.md b/docs/MATCHING-BLOCKERS.md index 3c003b150..d0b31a6e0 100644 --- a/docs/MATCHING-BLOCKERS.md +++ b/docs/MATCHING-BLOCKERS.md @@ -1515,7 +1515,9 @@ the canonical `D_00189EA0`. Earlier zero/constant labels described a mistaken interpretation of `func_00334710`, which returns this stored vector. Preserve the shared identities without inventing constness or zero initialization at each read. -**Current scope:** func_L00_00424BB8 remains a marker. The 23/27 report is historical; section 34 describes different field offsets. Re-extract the current extents before changing their grouping. +**5 November 2026, resolved:** in all three releases, levels 16, 22, 23 and 26 held the `q + 0x20` body under this name and the `q + 0x60` body under `func_L16_0042FB58`. The audited `IDENTITY_SPLITS` entry in `tools/levels.py` (also run by `carry.py --entries`) regroups the key by the release-independent words after the address pair: `func_L00_00424BB8` is now the `q + 0x60` setter at all 27 levels, `func_L16_0042FB10` the `q + 0x20` one at 4, and `func_L00_00424B70` is unchanged. Retail `jal` targets confirm which callers use which body; the level callers were renamed. Both setters are now C (27/27 and 4/4 in each release). + +**Earlier scope (superseded above):** func_L00_00424BB8 was a marker with a historical 23/27 report. **Signature:** `tools/check.py` reports a partial count (`23 of 27 places match`) and `instruction at +0xNN differs` on an `addiu` **immediate** or a **store displacement** - a word @@ -2440,7 +2442,9 @@ fields at `+0x1C`/`+0x20`); the matching body in level 16 sits at `0x0042FB58` i candidates for the same collision (`func_L01_003BAFB0` against `func_L00_0037E668`, `func_L02_003E9BB0` against `func_L00_003973E8`, `func_L02_00401298` against `func_L00_002E94B8`). It is a `tools/levels.py` fix - the masking of the small immediates on a -non-tainted base - not a C problem. +non-tainted base - not a C problem. **5 November 2026:** this row is resolved by a named, audited +`IDENTITY_SPLITS` entry (section 12). The same screen on today's catalogue finds 92 single-place +rows sharing a multi-place fingerprint; each still needs its own byte-level audit. @@ -2813,7 +2817,7 @@ Words **and operands** matter: qualifying sp-by-sp adjustments, zero moves and n The four-byte residue rule also needs its measured position after a completed return and delay slot. PR #253 now handles five additional specifically audited mixed-instruction residues (section 50), not an opcode-only generalization. -An extent beginning inside a prior epilogue but containing a later real function needs an entry correction, not deletion. Positive stack adjustment is only a clue. Verify call/data/vtable entries, preserve ends and raw bytes, and preserve boot/level identity when regenerating fingerprints. Other mixed boundaries remain open. +An extent beginning inside a prior epilogue but containing a later real function needs an entry correction, not deletion. Positive stack adjustment is only a clue. Verify call/data/vtable entries, preserve ends and raw bytes, and preserve boot/level identity when regenerating fingerprints. Other mixed boundaries remain open. **5 November 2026:** 59 more named residues and four 16-to-8 entry corrections are applied; see section 50. **6 November 2026:** one more residue, one fill-skipping entry correction and one PAL delay slot returned to its function (section 50). One boot example remains open: USA v1.01 callers `func_0027B440` and `func_00291850` enter `0x00126288`, four bytes after the catalogued @@ -2912,6 +2916,19 @@ PR #253 is merged. Generator, catalogue, markers and tests account for these spe **28 October 2026 USA v1.01 follow-up, pending maintainer review:** boot-only `func_002B4068` is 36 bytes, labelled `alabel`, after `func_002B4040`'s completed return at 0x002B4054, delay-slot result operation, and padding. Its body is `sw $zero,0($gp); nop; sw $zero,0($gp); nop; addiu $sp,$sp,0x60; nop; addiu $sp,$sp,0x90; nop; addiu $sp,$sp,0x150; nop`, followed by the next frame at 0x002B4090. It has no local prologue or return. A temporary empty C probe emits 8 bytes and matches 0/1. Keep marker and catalogue row pending maintainer review; do not count it as a match or handwritten function. +**5 November 2026, applied (USA v1.01, PAL, USA v2.00):** 68 unmatched rows of at most 400 bytes without `jr $ra`, plus three lead-reported rows, were re-read at every placement in all three releases. Each placement was checked for its position after a completed return or tail jump and for direct branch/jump targets, aligned loaded words and `lui`/`addiu`-`ori`-load pairs into the extent; hits were classified by section (packed halfword data and coincidental instruction words are not pointers). Results: + +- **Residue, removed** through the named `FUNCTION_RESIDUES` list (59 rows): every row of the 28/29 October follow-ups above, the "Suspected catalogue remnants" row except `func_00131CB0`, `func_003495B8`, `func_0034CE88`, `func_0029B848`, `func_003356E8`, `func_003172D0`, `func_00314CF8`, `func_00335270`, `func_0031D350`, `func_00129410`, `func_0011B580`, `func_0011FA48`, `func_0011C8C8`, `func_0011ED28`, `func_00123490`, `func_0012F998`, `func_00326CA8`, `func_0032FDC0`, `func_0031E6D8`, and the level rows `func_L00_0031A710`, `func_L05_0033CD40`, `func_L05_0033F4A8`, `func_L05_0037B6C0`, `func_L05_0037BB78`, `func_L09_003FB780`, `func_L01_0042C450`, `func_L23_0041E538`, `func_L25_00373ED0`, `func_L25_00373EE0`, `func_L25_00373F08`, `func_L30_0032AAF0`. No witness at any placement; the same names are removed from the PAL/US2 catalogues by `carry.py --entries`. Release-specific rows over the same PAL/US2 bytes (for example `func_PAL_003373BC`, `func_US2_0031E14C`) have other sizes and are not changed. +- **Entry corrections** (`FUNCTION_ENTRY_OFFSETS`, 16 to 8 bytes): `func_0032A130`, `func_L03_0041B848`, `func_PAL_0032B920`, `func_PAL_L00_003E63F0`. Each starts with an 8-byte stack-restore residue; the code builds the address of the `jr $ra; nop` at +8 with `lui`/`addiu` at every placement (28/5/1/27). The callers now pass the symbol without `+ 8`; the four empty callbacks are C. +- **Real functions, kept:** `func_002B9030` (jal thunk), `func_002B9380` (address pair), `func_002A1378` (jump target), `func_002A677C`, `func_002A08A0`, `func_001325E0` (jal), `func_00282848` (returns), `func_00131CB0` (crt0 passes it in `$t0` to the thread syscall). +- **Kept pending:** `func_L00_00309DB0` (PAL copies start in the previous delay slot; the PAL level-20 word is packed halfword data, not a pointer) and `func_L00_00424BB8` (section 34). + +**6 November 2026, applied (all three releases):** + +- `func_L00_00309DB0` is a residue (`FUNCTION_RESIDUES`, 28 bytes). US and US2: all 27 copies follow `jr $ra`, its delay slot and a `nop`. PAL: `func_PAL_L00_0030BA80` (frame `-0x20`) ends on `jr $ra` at all 27 places and the row's first word, `addiu $sp,$sp,0x20`, is that return's delay slot. The new named `FUNCTION_DELAY_SLOTS` table gives the slot back (336 to 340 bytes; `carry.py --entries` checks the `jr $ra`); the other 24 PAL bytes are the same residue. No direct target, aligned loaded word or address pair from the level's own sections enters any placement (boot `.text` hits at those addresses are boot code; the PAL level-20 word is the halfword data above). +- `func_0011A7F8` gets an entry correction (`FUNCTION_ENTRY_OFFSETS`, 24 to 16 bytes). In all three boots 0x11A7F8/0x11A7FC are `0xCDCDCDCD` fill after `jr $ra; addiu $sp,$sp,0x140`; 0x11A800 is `addiu $v1,$zero,0; syscall; jr $ra; nop`. Nothing in the boots or levels enters 0x11A7F8..0x11A800. Like its syscall-stub neighbours (commit eb2811fe) it is `ASM_FUNC`: no C emits `syscall`. + + ## 51. The wave 14 census: a call inside one object, and a screen that was too broad @@ -3382,6 +3399,7 @@ fill-like words before a syscall/return body. It follows the preceding completed stack-adjustment delay slot. The scan of catalogued boot functions and aligned loaded words found no direct/pointer reference to the extent, but computed indirect entries are untraced and the syscall body itself is coherent. Retain the marker pending entry/ABI and compiler review. +**6 November 2026:** the fill is skipped (entry 0x11A800, 16 bytes) and the stub is `ASM_FUNC`; see section 50. A known entry pointer is strong positive evidence; one pointer lookup is not proof that all other entry points or indirect targets are absent. Verify every affected placement and preserve raw bytes. @@ -4351,13 +4369,19 @@ placement report and 382 unit tests passing. No-op callbacks are counted as their real individual entries; no original-assembly classification is involved. Hrugis instead has an 88-byte closed body plus an unreachable 8-byte return pair with no independent scanned entry witness; -do not invent a second function or discard those bytes on that evidence alone. +do not invent a second function or discard those bytes on that evidence alone. **5 November 2026:** a code witness exists. At +`0x00418E1C`/`0x00418E24` (USA v1.01; same code in PAL and US2) `lui`/`addiu` +build `0x004191E0` and pass it as `$a1` to a registration call. The split now +accepts this `text` witness: 88-byte `func_L10_00419188` plus the empty C +callback `func_L10_004191E0`. Its C now matches (1/1 per release) by reading `D_001B251C` through an sda alias inside the loop (section 2). -The retained `func_L00_00309DB0` residue hypothesis also has a PAL exception: +**6 November 2026:** resolved; see section 50. The retained `func_L00_00309DB0` residue hypothesis also had a PAL exception: all 27 PAL copies begin in the preceding return's delay slot, and an aligned loaded word in PAL level 20 equals that address with unproven pointer meaning. Resolve its predecessor extent and that word's provenance before a shared -deletion. Direct or nearby address-pair absence alone is not proof of no entry. +deletion. **5 November 2026:** that word is part of packed halfword data +(`00190000 00190100 00320200`), not a pointer; the predecessor extent is still +open, so the row stays. Direct or nearby address-pair absence alone is not proof of no entry. - Remove diagnostic source controls before comparing meaningful C. The eight overwritten initializers in `func_L02_00412D50`, ten dead initializers in diff --git a/nonmatching/README.md b/nonmatching/README.md index 1133bf8df..5d7e7d1db 100644 --- a/nonmatching/README.md +++ b/nonmatching/README.md @@ -159,7 +159,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_PAL_L00_004266C8`](levels/func_PAL_L00_004266C8.c) | 1916 | Near: $s3/$s4 swap only; PAL copy of `func_L00_004212B8`. | | [`func_PAL_L00_00403780`](levels/func_PAL_L00_00403780.c) | 1744 | Near: spill slots 0xF0/0xF4 swapped only; PAL copy of `func_L00_003FEEA0`. | | [`func_L00_0041EE58`](levels/func_L00_0041EE58.c) | 1812 | 4 November 2026: 1804/1812 bytes; US 0/27, US2 0/27, PAL absent; first size mismatch. Stored-address getters follow their matched signed32 return contracts, with explicit pointer casts at the actual uses. Physical EE widths and argument-bank order are preserved; this repair leaves the retained allocation/scheduling residual unchanged. The first frame-address reaching copy and divisor/angle register roles remain. Historical index notes (superseded where inconsistent): Near 40 lines at 1804/1812, register choice only; header has the analysis. Twin of `func_L00_003E2510`. | -| [`func_L00_00303990`](levels/func_L00_00303990.c) | 3388 | 3392/3388 bytes. Preserve the level loader's heap-pointer return contract. An explicit goto form of the final loop measured 3380 bytes and lost required control-flow/alignment; keep the structured loop. GS-word allocation and macro-load loop padding remain unresolved. US 0/27, US2 absent, PAL absent. | | [`func_L08_00339220`](levels/func_L08_00339220.c) | 568 | 4 November 2026: four definition/view/scope/qcopy forms572 or576 against568 bytes,0/2USA. Sentinel/record scratch allocation remains; earlier568-byte C retained with the observed16-byte vector footprint. | | [`func_L08_003CDB78`](levels/func_L08_003CDB78.c) | 1056 | 2 November 2026: Full collision-resolver C replaces the old screen. All three fallback probes, global contact adjustment, the hero and level-specific response branches, and the truthful int/float callee results are retained. Two complete vectors fit the measured 0xA0 frame. Direct contact symbols improve 1036 to 1044 bytes; ordinary TI copies tie. Hero high-half/base lifetime, saved pointer See retained source for the full constraints. Not linked or counted. | | [`func_L08_003CD708`](levels/func_L08_003CD708.c) | 1068 | 2 November 2026: Full steering-controller C replaces the old screen. Typed measured input and hero prefixes restore the full 0x40 frame and saved s2/high-half lifetime. The mode field has exactly the two reads observed in retail; its volatile qualifier applies to the whole evidenced field. Both integer and FP argument banks and float helper returns are preserved. Progression: 1020, 1048, 1052, then See retained source for the full constraints. Not linked or counted. | @@ -178,7 +177,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_002859C8`](game/func_002859C8.c) | 3436 | 3436/3436 bytes, not exact. Restore func_0027FAA8's integer return and the 64-bit colour argument of func_0028F410. The remaining panel-call scheduling still differs. US 0/28, US2 absent, PAL absent. | | [`func_002900B8`](game/func_002900B8.c) | 1388 | 1372 bytes; it belongs in `0028F948-g8.c` and returns `D_001A8D40`. Retail has seven `mfc1` directly followed by a reader of their target, where this assembler inserts a `nop` (docs/COMPILER-NOTES.md), and cc1 spreads the float calculations where retail keeps the source order | | [`func_002B44C0`](game/func_002B44C0.c) | 1248 | 1192 bytes: the same folded pointer on the two copies at the top, which changes the saved registers holding `self + 0x10` and `target` and the order of the spills at 0xC8-0xEC | -| [`func_0033A520`](game/func_0033A520.c) | 360 | Truthful grouped coordinate setup: 360/360, 0/28 USA, first +0x60. Mutable scale and 300.0 literal load order remains; regional object fields also differ. | | [`func_L22_003D0840`](levels/func_L22_003D0840.c) | 60 | 4; matches size and every other word, but the parameter copy is `daddu $v1,$a0,$zero` against retail's `$a3`. | | [`func_00129410`](core/func_00129410.c) | 64 | 2 November 2026: VU0 sqc2 stores plus unmatched +0xA0 sp release and 12-byte CDCD fill. Corrected R5900 decode at +0x30 to ordinary sq; existing no-incoming-reference evidence, no C candidate. | | [`func_L00_002EDC90`](levels/func_L00_002EDC90.c) | 40 | G8 candidate is 44 bytes; 0/27 places. Separate multiply/add does not reproduce the retail COP1 accumulation sequence. | @@ -187,7 +185,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_L00_0036EF40`](levels/func_L00_0036EF40.c) | 40 | 36-byte polling attempt; retail uses the assembler temporary as a working register, extra nops and a live LUI in the return delay slot. No assembly classification claimed. | | [`func_L00_0036EF68`](levels/func_L00_0036EF68.c) | 248 | 2 November 2026: Fresh us/us2/pal R5900 reads show working at across lw/and/or/sw and trapping addi/add; retained bit-15 flag was incorrect: lui t0,0x8000 is bit31, now corrected to 0x80000000u. Earlier 236/248 C sizes are historical, corrected C uncompiled. | | [`func_L23_0041E538`](levels/func_L23_0041E538.c) | 12 | Catalogue defect: `sltiu $v0,$v0,1` / nop / `sltu $v0,$zero,$v0` at 0x41E538 reads `$v0` (never `$a0`) and has no `jr $ra`; it sits between func_L23_0041E418's epilogue and func_L23_0041E548. No C can be placed. | -| [`func_L00_00309DB0`](levels/func_L00_00309DB0.c) | 28 | 4 November 2026: Boundary hold, no C compile. US/US2 each have 27 orphan copies after completed returns; PAL starts inside the predecessor delay slot, and PAL level 20 has one equal aligned word of unproven pointer provenance. Preserve all rows/markers; qualify that predecessor and loaded word before any release-wide exclusion. Historical index notes (superseded where inconsistent): 2 November 2026: Fresh US surrounding-return and inbound-reference audit: 27/27 US placements follow completed return/delay/padding, then two unmatched positive stack restores and orphan v0 moves. No external direct, aligned literal or nearby LUI-address pair reaches the extent. Private per-placement evidence is boundary-summary.json and boundaries/. | | [`func_L00_0036BE28`](levels/func_L00_0036BE28.c) | 40 | near miss: 9 of 10 instructions (ours 36 bytes, retail 40). Retail loads through $at with hand-placed nops and ends in jr ra + lui ra, 0x7000 (looks like hand asm); plain C gives $v0 and fewer nops. | | [`func_L00_0036C9AC`](levels/func_L00_0036C9AC.c) | 40 | near miss: 9 of 10 instructions (ours 36 bytes, retail 40). Same wait-loop family as func_L00_0036BE28: retail loads through $at, hand-placed nops, jr ra then lui ra, 0x7000. | | [`func_L00_0036C9D4`](levels/func_L00_0036C9D4.c) | 40 | near miss: 9 of 10 instructions (ours 36 bytes, retail 40). Same wait-loop family as func_L00_0036BE28: retail loads through $at, hand-placed nops, jr ra then lui ra, 0x7000. | @@ -202,7 +199,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_0011ED28`](core/func_0011ED28.c) | 56 | Not a function: thirteen stack-pointer adjustments and linker fill, with no `jr $ra` or reference from the boot. A catalogue fragment, not C. | | [`func_0012FB10`](core/func_0012FB10.c) | 52 | Unresolved catalogue-tail hypothesis. USA v1.01 has no direct boot branch/jump target or aligned loaded-word pointer into the row after a completed return; PAL and USA v2.00 reference audits are unavailable. Earlier C probes were non-matches. Keep the row and marker pending maintainer review. | | [`func_00123490`](core/func_00123490.c) | 44 | Catalogue defect: linker fill between libgcc `fp-bit.o` functions, with no `jr $ra`, branch or caller. Rebuilding the three public SDK functions emits no fourth function; no C can be placed. | -| [`func_001325E0`](core/func_001325E0.c) | 236 | The row begins with an 8-byte linker remnant; the real body starts at 0x001325E8. The C reproduces 228 of 236 body bytes; two setup instructions remain differently scheduled. A catalogue split is needed. | | [`func_0012F998`](core/func_0012F998.c) | 16 | Unresolved catalogue-boundary hypothesis. USA v1.01: 8-byte empty-C probe, 0/1; no direct boot branch/jump target or aligned loaded-word pointer reaches the row after `func_0012F948` returns. PAL and USA v2.00 boundaries are unverified; marker and catalogue row remain pending maintainer review. rac1 has the same linker-remnant bytes, as historical corroboration only. | | [`func_0011C8C8`](core/func_0011C8C8.c) | 12 | Not a function: a store, `nop`, and an `addiu` that reads unset `$v0`; the compiler adds a return jump and cannot emit this fragment. | | [`func_0011B580`](core/func_0011B580.c) | 8 | Not a function: `and $a0,$a0,$v0` followed by `0xCDCDCDCD` linker fill; `$v0` is read before anything sets it. The row is between complete functions and is labeled fragment debris in `symbol_addrs`. | @@ -220,19 +216,15 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_003380A8`](game/func_003380A8.c) | 4 | USA v1.01 boot: one store after a completed return, its delay slot and a nop; the next body begins with a new frame. No direct branch/jump, aligned pointer literal or nearby `lui`/low-half address reference found. Candidate catalogue residue pending maintainer review; not added to release-shared `FUNCTION_RESIDUES`. See source. | | [`func_0011FA48`](core/func_0011FA48.c) | 8 | Catalogue remnant: a dead stack-pop word copied from the preceding return delay slot, followed by linker fill; no function body. | | [`func_L01_0034B1C0`](levels/func_L01_0034B1C0.c) | 288 | 2 November 2026: 288-byte row includes 16-byte orphan store/sp-release prefix; fresh US reader confirms jr at +0x118 and delay slot +0x11C, leaving 272 bytes after prefix, correcting prior 276-byte arithmetic. | -| [`func_L00_00424BB8`](levels/func_L00_00424BB8.c) | 23 of 27 | instruction at +0x28 differs: `16_snivelak`, `22_dobbo_orbit`, `23_damosel_orbit` and `26_jamming_array` hold other constants | | [`func_L00_00426C78`](levels/func_L00_00426C78.c) | 908 | 908/908 bytes, 0/27, first +0x48: only $s1/$s2 swap between the transition pointer and the follow camera. Allocno priority needs one more RTL insn in the pointer's range (151 to 152); 6 November 2026: an inline acos helper for `pi/2 - asin(x)` ties (the copy is folded before allocation). | | [`func_L00_0031A710`](levels/func_L00_0031A710.c) | - | Not a C row: catalogue defect. The 20-byte extent is three bare `mul.s` on `$f13` with no prologue, no store and no `jr $ra` - a neighbour's fragment | | [`func_L05_0037B6C0`](levels/func_L05_0037B6C0.c) | - | Not a C row: `lw $v0,0xC($v1)` with `$v1` never set, then restores; dead bytes between func_L05_0037B6D0 and the entry before it | | [`func_L05_0033F4A8`](levels/func_L05_0033F4A8.c) | - | Not a C row: 156 bytes of restores and padding, `addiu $sp,$sp,0x30/0x50/0x70` openers | | [`func_L05_0037BB78`](levels/func_L05_0037BB78.c) | 20 | Not a function: no `jr $ra` and `$v1` is read before anything sets it (`addiu $sp,$sp,0x30; nop; lw $v0,0x8($v1); nop; addiu $sp,$sp,0x20`), the neighbour's tail | | [`func_L01_0042C450`](levels/func_L01_0042C450.c) | - | Not a C row: recycled `sb $zero,0x38($v0)` / `sltiu $v0,$v0,0x1` fragment, `$v0` live-in and never defined, no `jr $ra`; next real body func_L00_004290C0 at row+0x10 | -| [`func_L08_00389B68`](levels/func_L08_00389B68.c) | - | Not a C row: MMI (2 pairs). Screened in wave 7 w09 tour 2. | | [`func_L05_0033CD40`](levels/func_L05_0033CD40.c) | - | Not a C row: restores and padding around a stray `sh $zero,0x1C($a0)`; the entry after the gap is func_002B0A18. Catalogue split | -| [`func_L10_00419188`](levels/func_L10_00419188.c) | 96 | Row is eight bytes too long (real body 0x419188..0x4191E0 = 88 bytes, the trailing `jr $ra; nop` at 0x4191E0 is unreachable and the next row starts at 0x4191E8); re-cut to 0x58. The candidate is now the 88 bytes and matches them instruction for instruction: the sda attribute on D_001B251C leaves the address to the assembler (so it is rebuilt inside the loop), the table entry is read as a u32 and copied with `daddu $a0,$v0,$zero`, and the do-while's post-increment sits in the back branch's delay slot | | [`func_L30_0032AAF0`](levels/func_L30_0032AAF0.c) | 20 | Not a function: `addiu $sp,$sp,0x30` / nop / `addiu $sp,$sp,0x30` / nop / `sh $zero,0x1C($a0)` at 0x32AAF0, the epilogue-fragment shape of func_L00_00341798; no prologue and no `jr $ra` in the extent, needs the real start from the maintainers | | [`func_L25_00373EE0`](levels/func_L25_00373EE0.c) | 20 | Not code: no `jr $ra`, both stores go through `$v0 = 0`, words interleaved with `nop`s, and it clobbers the previous entry delay-slot load. Catalogue entry, not C | -| [`func_L01_00324550`](levels/func_L01_00324550.c) | 132 | 132/132 bytes with game -mastra-quad-saves, but mixed s0/ra save widths and order differ. The SDK profile emits 116/132 and lacks FP spills. The real variadic forwarding body is retained without fabricated frame padding. No strict match. | | [`func_L20_0039BEC8`](levels/func_L20_0039BEC8.c) | 1252 | Retained near miss, 1260/1252 B; us: 0/1 placements; us2: 0/1 placements; pal: 0/1 placements. Profile `-O2 -G32 -Wa,-G32 -ffunction-sections -frac2-qcopy -frac2-qcopy-barrier`. 1260 bytes versus1252; correct1D0 frame, interleaved-table base choices and allocation differ. Reopen: Recover the actual interleaved UV table declarations and independently qualified GP/absolute addressing mechanism. Do not shrink32-byte tables to fitG8. Historical checker results; linked-image equality and semantics unverified. | | [`func_L23_0035CE90`](levels/func_L23_0035CE90.c) | 288 | Catalogue defect: the row starts 16 bytes early, in the padding after the previous function's `jr $ra` at 0x35CE84 (`sw $t3,0x40($v1); nop; addiu $sp,$sp,0x20; nop`); the body is 0x35CEA0-0x35CFAF, 272 bytes, and this C, for the `-g8` sibling, gives 264 (two `nop`s and some order) | | [`func_L03_003C5668`](levels/func_L03_003C5668.c) | 644 | Corrected complete C remains unlinked. 648/644 bytes; see source for measured release coverage, residual differences and reopening conditions. | @@ -246,7 +238,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_00282848`](game/func_00282848.c) | 16 | Catalogue entry corrected: the 72-byte extent had an unreferenced 56-byte prefix of positive stack adjustments/nops after a completed return; its final 16 bytes are the real helper. No branch, jump, address pair or aligned word references the prefix or shortened entry in any of the 28 USA programs. The corrected body shares blocker 4's `lwc1 ; nop ; jr ; mul.s` wall; C emits 12 bytes. Marker remains. See source. | | [`func_L00_003B4560`](levels/func_L00_003B4560.c) | 2340 | Screened, not matched in wave 12 (worker s4): 31 call(s), 13 `$gp`-relative small-data access(es), MMI words [+0x0120:0x7C620000] (the `lq`/`sq` family, which `mode(TI)` reaches), float constants [none]. The body is straight-line code whose register allocation and the materialisation of its constant addresses have to be reproduced word for word; no C was written in this wave. | | [`func_0027BA68`](game/func_0027BA68.c) | 772 | 4 November 2026: 772/772 bytes; US 0/28, US2 0/28, PAL 0/28; first 0x78. func_002A0380 keeps its defined int return even though this caller ignores it. The view-pointer register roles and flag/argument scheduling residual remain unchanged. View-pointer saved-register roles and the flag/argument scheduling window remain. Historical index notes (superseded where inconsistent): Screened, not matched in wave 13 (worker g4): 25 call(s), 0 `$gp`-relative small-data access(es), 15 MMI lq/sq word(s) (the `lq`/`sq` family, which `mode(TI)` reaches), 23 64-bit `daddu` copy(ies) (this cc1 sign-extends with `dsll`/`dsra`), 4 float constant(s). the body carries the MMI lq/sq words (0x78/0x7C/0x7E), which a mode(TI) local reaches, but this cc1 folds the constant offset into the lq/sq where retail materialises the pointer first; it also keeps 23 pointers in 64-bit variables, where retail copies them with daddu $d,$s,$zero and this cc1 sign-extends with dsll/dsra; no C was written in this wave | -| [`func_0029F840`](game/func_0029F840.c) | 288 | 4 November 2026: fabricated always-zero adjustment removed. Three real scale/transform groups288/288 bytes,0/28USA, first+0x10. Correct object/count allocation and first-call setup remain unresolved. | | [`func_00283248`](game/func_00283248.c) | 280 | USA v1.01 retail inspection (29 Oct 2026): `qmtc2.ni` at +0x78 and COP2/VU0 vector operations through +0xFC (`vaddx`, `vmul`, `vmadd*`, `qmfc2.ni`). Evidence supports handwritten assembly; `INCLUDE_ASM` remains pending maintainer agreement for `ASM_FUNC`. | | [`func_0029D398`](game/func_0029D398.c) | 312 | Pending maintainer agreement for `ASM_FUNC`: USA v1.01 boot body transforms vertices using VU0/COP2 (`lqc2`, `qmtc2.ni`, `vitof0`, `vmulax`/`vmadd*`, `vftoi0`, `qmfc2.ni`) and MMI color packing. Plain C cannot emit its VU0 instructions; marker remains. | | [`func_L00_00358B30`](levels/func_L00_00358B30.c) | 544 | Readable C reconstruction retained; see the source for release coverage, profile, residuals and reopening conditions. | @@ -258,9 +249,7 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_002B9380`](game/func_002B9380.c) | 16 | Current-master computed-goto probe: 12 bytes, 0/28 (`lw $v0,0x3C($a0); jr $v0; nop`); retail has a nop between load and jump. The ordinary indirect-call draft is 32 bytes with a frame and `jalr`. No artificial barrier or inline asm. | | [`func_002B9390`](game/func_002B9390.c) | 140 | Current-master USA v1.01 recheck: exact size, 0/28. The 0x40-byte record scan and indexed handler call are represented; cc1 saves `$ra` in a stack frame, while retail uses `$gp+0x2DB8`, a GP-resident end pointer and branch-likely control flow. Five other measured forms were 164, 152, 140, 156 and 152 bytes. Historical PAL/USA v2.00 results were not rerun because those ROMs are absent from this checkout; see source. | -| [`func_L00_00423290`](levels/func_L00_00423290.c) | 360 | 3 November 2026: Baseline, reviewed qcopy_nc and complete camera-prefix forms give identical checker logs: 360/360 bytes, 0/27 USA, first +0x58. Stop this tie; an independent producer-order or lifetime witness is needed. | | [`func_00326CA8`](game/func_00326CA8.c) | 12 | Not a C row: catalogue defect. The 12-byte extent is `daddu $v0,$a1,$zero ; nop ; daddu $v0,$zero,$zero` - two 64-bit moves and no `jr $ra` - between the previous function's `jr $ra` (func_00326BD8, 208 bytes, ends at 0x00326CA8) and the next function's prologue (func_00326CB8 at 0x00326CB8); the same shape as func_0032FDC0. No C can be placed | -| [`func_L01_0031B300`](levels/func_L01_0031B300.c) | 272 | 4 November 2026: real height capture restores the full register map but gives 276/272 bytes,0/5 USA: extra alignment nop at+0x74. Larger real response groups keep276 bytes and lose the register map. Retained complete source, not linked. | | [`func_0029CF78`](game/func_0029CF78.c) | 56 | Wave 5 w05: spin loop on the register at 0x1000D400; volatile read is correct but the best retained candidate is 44/56 bytes. Nine spellings differ in mask/nop order, loop layout and base register. 28 October 2026: an explicit forward-exit/backward-loop `goto` was canonicalized to a 40-byte conditional-backedge loop, still with the mask before three nops (0/28 USA placements). See source and blocker 39. | | [`func_0029CFB0`](game/func_0029CFB0.c) | 160 | the body is hand-written: the 0x70C338E8 word is the MMI `pminw` (this cc1 has no vector type and never emits an MMI word), the retail's `addi`/`add` are the trapping variants where this cc1 emits `addiu`/`addu` and the matched witness func_0012D808 has `addiu $v1,$zero,0x101` and `addu`, the poll loop's three nops sit before the `andi` where this cc1 (and the matched witness func_0012D808) put them after it, the base register is `$at`, and the last branch jumps into the middle of func_0029CBA8 | | [`func_0029D7C0`](game/func_0029D7C0.c) | 72 | Current-master recheck of the retained spin wait: 44 bytes, 0/22 USA v1.01 places. The candidate loads through `$a0`, uses a bottom-tested loop and returns after 44 bytes; retail loads through live-in `$v1`, uses a top-tested loop, then has two `teq $zero,$zero,0` words and a second `jr $ra` after its first return. No strict linked match. | @@ -275,18 +264,14 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_L00_002EDD38`](levels/func_L00_002EDD38.c) | 16 | Wave 8 w06: G8 draft, twin of func_L00_002EDCF0 at gp-0x76D4 (0x001A791C); same `nop`-before-`jr` wall (12 bytes against the retail's 16, 0/27 places). | | [`func_L00_002EDCB8`](levels/func_L00_002EDCB8.c) | 16 | Wave 8 w06: G8 draft; retail `lwc1 $f0,-0x76E0($gp); nop; jr $ra; mul.s $f0,$f0,$f12`. With `extern float D_001A7910 __attribute__((sda));` the load and the `mul.s` operand order match, but the candidate is 12 bytes: the `nop` between the load and the jump is missing (the wall recorded in docs/COMPILER-NOTES.md). Measured this wave: -O0/-O1/-O2/-O3, -G0/-G8, -fno-schedule-insns, -fno-delayed-branch, -ffast-math, a volatile global and a double read all give the compact three-instruction form, and assembling the retail's four instructions with the game's `as` gives 12 bytes too, so the `nop` is not the assembler's. | | [`func_L00_002EE0C0`](levels/func_L00_002EE0C0.c) | 16 | Wave 8 w06: retail `sd $zero,0($a0); nop; jr $ra; sw $zero,8($a0)`, a twelve-byte clear. The struct candidate gives the two stores in the retail's order (the 8-byte store first) but is 12 bytes: the `nop` between the first store and the jump is missing, the same wall as func_L00_002EDCB8 and its three twins. Measured this wave: -O0/-O1/-O2/-O3, -fno-schedule-insns and -fno-delayed-branch (which puts the two stores first and the `nop` in the return slot) never give the retail's 16 bytes; 0/27 places. | -| [`func_L00_00308700`](levels/func_L00_00308700.c) | 288 | Three real RAC1 scan/swap/decode-phase trials give 272 or 276 bytes against 288, 0/27 USA placements. The retained 276-byte owner-view form uses the complete cache representation for age offsets and the measured entry array for data; it avoids stepping beyond a scalar field as an int array. It preserves the miss return and selected-first swap without the donor's dummy increment/decrement. Keeping separate table-base/index values across decode remains unresolved. Older 296-byte measurements below are history. | | [`func_L09_00352150`](levels/func_L09_00352150.c) | 288 | Not a C row: the extent starts with `sw $t3, 0x40($v1)`, and neither register is set in the 288 bytes that follow (the body sets $v1 itself, eight instructions later). Nothing in level 09 calls or points at 0x00352150, and the boot's copy of the same 288 bytes (func_002DB988) starts the same way and is referenced by nothing either. A catalogue fragment - the fix belongs in `tools/levels.py` | | `func_0028A180` | 240 | One 228-byte plain-C draft matched 0/28 in US, PAL, and US2. It used guessed fixed data addresses; no safe shared-source data symbols were established, so the draft was discarded. Reopen with verified data-symbol mapping and retail loop/layout evidence. | -| [`func_0028B160`](game/func_0028B160.c) | 292 | Six actual size/upload/bound-read groups, a page helper and loop-profile trials do not match. The size-only group plus no-strength-reduce gives 292/292 bytes, 0/28 USA, first +0xA8: the full prologue and shift-base/immediate registers agree, but call setup and the shift delay slot differ. Other new forms are 288/292, 300/292, or retain the original register swap. Current RAC1 ui/hud.c uses the same ordinary bank loop. The older best body is retained with complete declarations; the new size-group source remains a diagnostic, not a qualified profile. | -| [`func_002F7320`](game/func_002F7320.c) | 132 | 2 November 2026: 2 November 2026: the signed 32-bit index/result form remains 132/132 bytes, 0/28 US placements. An unsigned index changes the retail signed bound test; a 64-bit result expands to 140 bytes without preserving the required zero copy. Neither is retained. The entry zero-copy/CSE constraint remains; do not repeat width probes without new compiler evidence. Not linked or counted. | | [`func_002F3CF8`](game/func_002F3CF8.c) | 40 | Four checker invocations across USA v1.01, PAL and USA v2.00. Best plain-C form is 44 bytes and matches 0/28 placements in each release. C computes the address in an extra instruction and uses `$v0`; retail uses `$at` as a value register and has three nops between the load and mask, evidence for review under the handwritten-code rule; no ASM_FUNC classification is made. Marker restored; no strict build was run. | -| [`func_L00_003B39D0`](levels/func_L00_003B39D0.c) | 292 | 4 November 2026: real data-read/collision-call groups292/292 bytes,0/27USA, first+0x4. Entry schedule and allocation remain; the complete collision-result form is retained. | | [`func_L00_002CA4E0`](levels/func_L00_002CA4E0.c) | 948 | 3 November 2026: Real captures preserve two complete vectors, their copy ordering and the evidenced choices array. 944/948 bytes, 0/27 USA. Origin/constant hoisting and the sampling numerator remain; no new scalar or flag sweep. | @@ -297,7 +282,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_L02_0032E508`](levels/func_L02_0032E508.c) | 1164 | Retained C: 1208/1164 compiled/retail bytes. See the source header for current release coverage, tested profiles and reopening conditions. | | [`func_L02_003E7B58`](levels/func_L02_003E7B58.c) | 972 | 2 November 2026: Root confirmed live reservation and approved reopening on changed compiler input. Ordinary192-byte aggregate now exactly reproduces the whole quadword copy/prologue. Retained source improves980 to972 bytes and removes obsolete block-copy refusal. Flag snapshot/packet-order variant failed to improve and was reverted. Not linked or counted. | | [`func_L00_002A3B88`](levels/func_L00_002A3B88.c) | 3432 | 4 November 2026: 3428/3432 bytes; US 0/27, US2 absent, PAL absent; first size mismatch. func_002C9C20 and func_002E9268 keep their defined int returns. The one-word delay-slot residual is unchanged. A selected volatile store chosen only to affect scheduling remains unsupported. The selected volatile-store exact probe remains unsupported without an independent access contract. Historical index notes (superseded where inconsistent): Readable C reconstruction retained; see the source for release coverage, profile, residuals and reopening conditions. | -| [`func_L03_003C1BF0`](levels/func_L03_003C1BF0.c) | 5680 | 26 October 2026 (finisher F1, after big8/closer4): 5680 bytes, 1391 of 1420 instructions equal with registers (L03 and L14). Left: state 1's float pair (a local-alloc tie) and state 22's allocation (&other in $s6, the object+0xC0/0xF0 spill slots). See the header. | | [`func_L00_003F6308`](levels/func_L00_003F6308.c) | 1524 | Corrected complete C remains unlinked. 1400/1524 bytes; see source for measured release coverage, residual differences and reopening conditions. | | [`func_002DC3C8`](game/func_002DC3C8.c) | 856 | 3 November 2026: Entry hypothesis held. No +0/+4/+8 entry witness in 28 USA images; the data table contains internal switch cases. Historical 848-byte C does not justify shortening the 856-byte row. PAL/US2 identity absent. Reopen on a traced entry or object-origin proof. | | [`func_00301F18`](game/func_00301F18.c) | 900 | 4 November 2026: US 900/900 bytes, 0/28, first +0x60. A genuine two-vector aggregate changes both stack slots and address pseudos without improving the retained independent vectors. Other releases not rechecked. Reopen on actual position/angle lifetimes; the synthetic pointer-to-local copy remains rejected. Historical index notes (superseded where inconsistent): 26 October 2026 (M4): 900/900 bytes, 0/28; only the $s7/$fp choice for the &position/&angles pseudos differs (8 words). Parent-state if/else-if chain and found-parent arm first are retail's. Declaring angles first fixes the registers but swaps the stack slots. Permuter queued. | @@ -320,7 +304,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_L15_00437B68`](levels/func_L15_00437B68.c) | 1740 | 4 November 2026: 1756/1740 bytes; US 0/1, US2 0/1, PAL 0/1; first size mismatch. Current source/profile reproduces 1756 bytes in all three releases. The older 1716-byte index entry does not describe this retained body. Corner/giv allocation, split-mask reload store and pointer spills remain unresolved. Historical index notes (superseded where inconsistent): Corrected complete C remains unlinked. 1716/1740 bytes; see source for measured release coverage, residual differences and reopening conditions. | | [`func_0029D258`](game/func_0029D258.c) | 320 | Handwritten assembly candidate pending maintainer review: the boot body interleaves COP2/VU0 transform instructions (`lqc2`, `qmtc2`, `vmulax`, `vmadday`, `qmfc2`) with MMI packed integer operations. The marker remains `INCLUDE_ASM`; this is not yet counted as a match. | -| [`func_002EBC70`](game/func_002EBC70.c) | 380 | 28 October 2026 recheck: 380/380 bytes, 0/28 USA v1.01 placements in `-O2 -G8 -ffunction-sections`. The state-entry walk still swaps the previous pointer and index registers; the call sequence and later state updates otherwise match. A pointer-induction form grew to 364/380 and 0/28, reloading the loop count. See source. | | [`func_002B6828`](game/func_002B6828.c) | 152 | Mid worker 13: calls and control flow decoded (D_0014B540 +0x52E0/+0x529C, D_00188660 +0x17A0 slots, func_002B6770 callback), 152 B target; ours folds the +0x17A0 into the symbol relocation (lui/addiu 0x17A0) where retail keeps the plain symbol address and the displacement separate, and builds (index+1)*4 once for the else arm. Not resolved. | | [`func_002933D0`](game/func_002933D0.c) | 228 | Mid worker 13: complete C, right size and instruction sequence; only register assignment differs (retail hdr=t2, count kept live in a3 with the countdown i in t1, off in t0, recs in t4, arg1 in t5; ours hdr=t1, count dies into v0, off in a3, arg1 in t4). Loop shapes (do-while countdown, for(;;) with the sign test on the updated record word before the bump) match retail. | @@ -335,7 +318,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_L00_004003F0`](levels/func_L00_004003F0.c) | 444 | 448B vs 444B. Callee names are the boot copies (func_00336D50, func_00300A00, func_002ED578, func_0027F5B8, func_00115DA8) with real prototypes taken from matched callers. Reads of D_L00_001A904C/001B2704/001B2C10 ... | | [`func_0032F3D0`](game/func_0032F3D0.c) | 444 | Decoded fully (see draft; D_001B0960 sda gate, two func_00300A00 calls, sprintf, func_0027F5B8). Needs -G8 -Wa,-G32 unit. Default flags: 448 vs 444 B: mine hoists 451.0f into a 6th callee-saved FP reg (retail keeps ... | | [`func_L04_00416E38`](levels/func_L04_00416E38.c) | 492 | First-compile draft (472 B vs 492 B). Calls/args all identified (func_3092E8, func_32D030, func_30AAB8 with stack arg 3, func_30A9D8, func_3153B0, func_30A318). Open: retail recomputes (int)(D*263+.5) etc. after each ... | -| [`func_L01_003D6B00`](levels/func_L01_003D6B00.c) | 396 | 396 bytes; 0/2 in us, pal and us2. Right size; the loop body agrees substantially, but the count save/guard prologue and emitter argument schedule differ. A separate decrement-at-start loop grew to 408 bytes; disabling rerun-loop-opt gave 392 with an extra saved pointer and different constant motion; G8 did not fix it. Reopen with a genuine counter lifetime hypothesis. | | [`func_L18_0043FFF8`](shared/func_L18_0043FFF8.c) | 488 | 27 October 2026: 488/488 bytes, 0/3 places in each release at -G0 -g. Five initial flag constant/store words remain; the later vector, lifetime and return sequence agrees. | | [`func_L13_0041AB30`](levels/func_L13_0041AB30.c) | 460 | Game -O2 -G8 -ffunction-sections -frac2-qcopy -g emits 464/460 bytes. US, PAL and US2 each fail 0/2 places; all canonical rows are present. Destination-base hoisting creates an extra saved register. Reopen with pointer-lifetime and allocator evidence. No strict build. | | [`func_00348EC0`](game/func_00348EC0.c) | 644 | 4 November 2026: 644/644 bytes; US 0/28, US2 absent, PAL absent; first 0x98. Stored-address getters follow their matched signed32 return contracts, with explicit pointer casts at the actual uses. Physical EE widths and argument-bank order are preserved; this repair leaves the retained allocation/scheduling residual unchanged. Centering/setup lifetimes remain; descriptor-address reuse regresses. Historical index notes (superseded where inconsistent): 3 November 2026: Full 72-byte text object and 64-bit style retained: 644/644 bytes, 0/28 USA; other canonical releases absent. Reusing its descriptor address regresses to 628 bytes. Centering/setup dependencies remain. | @@ -382,7 +364,6 @@ the placement rules are in `tools/fcheck.py`'s docstring; its tests are | [`func_L20_004441D8`](levels/func_L20_004441D8.c) | 1744 | 4 November 2026: 1740/1744 bytes; US 0/1, US2 0/1, PAL absent; first size mismatch. The event helper returns int and the particle constructor returns a pointer, as in their matched definitions. The health lookup keeps its signed32 stored-address return with explicit pointer conversion. None resolves the increment/group-index scheduling residual. Historical index notes (superseded where inconsistent): 1740/1744 bytes, opcodes aligned: a group-index register, one argument's order, and an increment that reorg moves past two qzero asms. See the file header. | | [`func_L15_00430168`](levels/func_L15_00430168.c) | 1064 | 2 November 2026: Audited actual C callees0027F5B8/0027FB40/L05_00303000/00336D50/00288FB8. Correct void return,32-bit wrapper color and explicit integer-address conversions recover1064/1064 from1072. Final check fails first+0xC, frameD0. Shared constant locals give1020/frameC0; actual-address return declarations tie the corrected baseline. One rejected source-substitution typo counted separately from valid compiles. Not linked or counted. | | [`func_L00_00300618`](levels/func_L00_00300618.c) | 11348 | 3 November 2026: Restore the actual third matrix argument of both transforms, the class centre/radius sphere and dynamic group storage. 11288/11348 bytes, 0/27 USA; other canonical releases absent. Store slots, shrub/moby spills and group loops remain; do not omit real inputs to recover a smaller body. | -| [`func_L00_003AE900`](levels/func_L00_003AE900.c) | 8440 | 8,432/8,440 bytes, US and US2 0/27 each; PAL identity absent. Normal template assignments reproduce both quadword copy loops with the current compiler. Correct collision-state reload and voice-record layout retained; FPR count, held-pose pointers and colour-loop constants still differ. | | [`func_002FB1A0`](game/func_002FB1A0.c) | 3604 | 4 November 2026: 3604/3604 bytes; US 0/28, US2 absent, PAL absent; first 0x150. Stored-address getters follow their matched signed32 return contracts, with explicit pointer casts at the actual uses. Physical EE widths and argument-bank order are preserved; this repair leaves the retained allocation/scheduling residual unchanged. Mode-3 allocation and loop induction remain. Historical index notes (superseded where inconsistent): 3604/3604 bytes, not exact. Restore the actual integer return of func_00288870 even though this caller discards it. The measured mode-3 allocation and loop-induction differences remain. US 0/28, US2 absent, PAL absent. | | [`func_00284268`](game/func_00284268.c) | 2988 | 2996/2988 bytes. Explicit goto alternatives for the two strip loops kept that size and reduced opcode agreement; retain the structured loops. No new volatile access or artificial loop was introduced. The preheader and wide-shift scheduling constraints below remain. US 0/28, US2 0/28, PAL 0/28. | | [`func_0011F364`](core/func_0011F364.c) | 636 | 2 November 2026: Fresh read w03 --version us: 636-byte extent begins with seven CDCDCDCD words (28 bytes); code at 0011F380 uses k0/live at, full context save, CP0, HI1/LO1, mfsa/mtsa, sync.p, eret and later callback/trap fragment. Existing conflicting prefix notes resolved for US. Subsequent fresh PAL/US2 representative reads confirm the same 28-byte prefix and privileged-handler form. | diff --git a/nonmatching/core/func_001325E0.c b/nonmatching/core/func_001325E0.c deleted file mode 100644 index 16ba82a0d..000000000 --- a/nonmatching/core/func_001325E0.c +++ /dev/null @@ -1,53 +0,0 @@ -/* sol-low v0268: rechecked with the pinned v2 toolchain, 0/1 boot places. - * -fno-schedule-insns is byte-neutral. Giving the message a complete extent - * removes s0 and changes the loop; retain the closest 236/236-byte form below. - */ -/* sol-high, b0264: USA v1.01 boot, game -O2 -G8 -ffunction-sections. - * 236/236 bytes, 0/1 places. The entry correction to 0x001325E8 is - * already in the current catalogue. This replaces the stale 228-byte draft. - * The callback-data scalar is volatile, as in current RAC1 989snd, which - * keeps its absolute doubleword store out of the branch delay slot. - * Remaining: the message-address LUI is hoisted before that store instead - * of occupying the branch delay slot. The rest of the body agrees. - * Volatile sentinel, -fno-sched-spec, and sharing the matched BankLoadAsync - * unit do not close this scheduling difference. SDK changes frame/GP/calls. - * Reopen with a qualified address-lifetime/scheduling remedy. - * All required declarations are below. Compile in a -g8.c sibling. - */ -#include "common.h" -extern int D_001A74C8 __attribute__((sda)); -extern int D_001A7488 __attribute__((sda)); -extern int D_001A74F8 __attribute__((sda)); -extern int D_001A74D0 __attribute__((sda)); -extern int D_001A71C0 MACRO_ADDR; -extern unsigned int D_001A7180 MACRO_ADDR; -extern volatile long D_001A74D8 MACRO_ADDR; -extern int D_001A7140 MACRO_ADDR; -extern char D_001A76F8[], D_001A7578[]; -extern void func_00115D48(const void *, ...); -extern void func_00132028(void); -extern void func_0011AEA0(int); -extern int func_0011D810(const void *); -extern int func_0011D620(const void *, int, int, int *, int, unsigned int *, int, int, int); -extern int D_001A71C4 MACRO_ADDR; -extern char D_001A7600[], D_001A7630[]; -extern int func_00133580(int); -void func_001325E0(int a, int c, long d) { - D_001A7488 = 0; - if (D_001A74C8 != 0) { - if (D_001A74F8 != 0) return; - func_00115D48(D_001A76F8); - return; - } - D_001A71C0 = a; - D_001A74D0 = c; - D_001A7180 = -1u; - D_001A74D8 = d; - while (func_0011D810(&D_001A7140)) { - if (D_001A74F8 == 0) func_00115D48(D_001A7578); - func_00132028(); - func_0011AEA0(0); - } - D_001A74C8 = 1; - func_0011D620(&D_001A7140, 0x57, 1, &D_001A71C0, 4, &D_001A7180, 4, 0, 0); -} diff --git a/nonmatching/functional.tsv b/nonmatching/functional.tsv index 857983338..b9868b4f8 100644 --- a/nonmatching/functional.tsv +++ b/nonmatching/functional.tsv @@ -2,14 +2,12 @@ # Each does what the retail function does without matching its bytes; the matching build never reads it. # Files under nonmatching/functional/ are C written for the port only (no matching attempt behind them). # name file -func_001325E0 nonmatching/functional/func_001325E0.c func_00280710 nonmatching/functional/func_00280710.c func_00283CB8 nonmatching/functional/func_00283CB8.c func_00283CF0 nonmatching/functional/func_00283CF0.c func_00284088 nonmatching/functional/func_00284088.c func_00284268 nonmatching/functional/func_00284268.c func_002859C8 nonmatching/functional/func_002859C8.c -func_0028B160 nonmatching/functional/func_0028B160.c func_002933D0 nonmatching/functional/func_002933D0.c func_00294F10 nonmatching/functional/func_00294F10.c func_002B6828 nonmatching/functional/func_002B6828.c @@ -67,7 +65,6 @@ func_00285030 nonmatching/functional/func_00285030.c func_0028A670 nonmatching/functional/func_0028A670.c func_0029CF58 nonmatching/functional/func_0029CF58.c func_0029CF78 nonmatching/functional/func_0029CF78.c -func_0029F840 nonmatching/functional/func_0029F840.c func_002A0488 nonmatching/functional/func_002A0488.c func_002A04B8 nonmatching/functional/func_002A04B8.c func_002B44C0 nonmatching/functional/func_002B44C0.c @@ -78,7 +75,6 @@ func_002CC6B0 nonmatching/functional/func_002CC6B0.c func_002F3CF8 nonmatching/functional/func_002F3CF8.c func_00301F18 nonmatching/functional/func_00301F18.c func_003136D0 nonmatching/functional/func_003136D0.c -func_0033A520 nonmatching/functional/func_0033A520.c func_00340638 nonmatching/functional/func_00340638.c func_00348EC0 nonmatching/functional/func_00348EC0.c func_00349D58 nonmatching/functional/func_00349D58.c @@ -103,7 +99,6 @@ func_L00_00426C78 nonmatching/functional/func_L00_00426C78.c func_L02_0032E508 nonmatching/functional/func_L02_0032E508.c func_L02_003E7B58 nonmatching/functional/func_L02_003E7B58.c func_L02_00412D50 nonmatching/functional/func_L02_00412D50.c -func_L03_003C1BF0 nonmatching/functional/func_L03_003C1BF0.c func_L03_0041DAD0 nonmatching/functional/func_L03_0041DAD0.c func_L04_0040DCA8 nonmatching/functional/func_L04_0040DCA8.c func_L05_0041DF58 nonmatching/functional/func_L05_0041DF58.c @@ -171,7 +166,6 @@ func_L00_002CA4E0 nonmatching/functional/func_L00_002CA4E0.c func_L00_002E2048 nonmatching/functional/func_L00_002E2048.c func_L00_002EC248 nonmatching/functional/func_L00_002EC248.c func_L00_002EC608 nonmatching/functional/func_L00_002EC608.c -func_L00_00308700 nonmatching/functional/func_L00_00308700.c func_L00_0038B208 nonmatching/functional/func_L00_0038B208.c func_L05_0037A5F8 nonmatching/functional/func_L05_0037A5F8.c func_L06_0041EF08 nonmatching/functional/func_L06_0041EF08.c @@ -181,7 +175,6 @@ func_L06_00443A38 nonmatching/functional/func_L06_00443A38.c func_L06_003E5D30 nonmatching/functional/func_L06_003E5D30.c func_L15_00431590 nonmatching/functional/func_L15_00431590.c func_L25_0040DE40 nonmatching/functional/func_L25_0040DE40.c -func_002F7320 nonmatching/functional/func_002F7320.c func_00282C90 nonmatching/functional/func_00282C90.c func_00283360 nonmatching/functional/func_00283360.c func_002836E8 nonmatching/functional/func_002836E8.c @@ -248,7 +241,6 @@ func_L00_00316F60 nonmatching/functional/func_L00_00316F60.c func_L00_002E0200 nonmatching/functional/func_L00_002E0200.c func_002A3110 nonmatching/functional/func_002A3110.c func_002CF5B0 nonmatching/functional/func_002CF5B0.c -func_L00_00423290 nonmatching/functional/func_L00_00423290.c func_L01_003BCEC8 nonmatching/functional/func_L01_003BCEC8.c func_L02_003C43F0 nonmatching/functional/func_L02_003C43F0.c func_L00_00395428 nonmatching/functional/func_L00_00395428.c @@ -290,5 +282,4 @@ func_002EAB18 nonmatching/functional/func_002EAB18.c func_002F5FB8 nonmatching/functional/func_002F5FB8.c func_002CA070 nonmatching/functional/func_002CA070.c func_L00_002A3B88 nonmatching/functional/func_L00_002A3B88.c -func_L00_00303990 nonmatching/functional/func_L00_00303990.c func_L11_004465F8 nonmatching/functional/func_L11_004465F8.c diff --git a/nonmatching/functional/func_001325E0.c b/nonmatching/functional/func_001325E0.c deleted file mode 100644 index 31497bdb3..000000000 --- a/nonmatching/functional/func_001325E0.c +++ /dev/null @@ -1,78 +0,0 @@ -/* functional: high. Same reads, writes and calls in the same order as retail; only instruction scheduling (store order at the loop entry) and register use differ. */ -/* from src/core/00131780-g8.c: the catalogue row is eight bytes too long. - * - * func_001325E0's row (0x001325E0, 244 bytes) opens with - * - * addiu $sp,$sp,0x20 ; nop - * - * that belongs to no function: a linker remnant of the 989snd unit, the kind - * rac1-decomp splits off as core_text/func_0012E1B8, right before its - * cmd-0x57 wrapper func_0012E1C8 (rac1-decomp src/core/989snd.c), which is - * the function this row is. The remnant is dead-stripped code, not part of - * the function, and no C emits a stack-pointer increase at function entry, so - * the row as it stands cannot be matched from C. A tools/levels.py split (the - * row starts at 0x001325E8, 236 bytes) unblocks it. - * - * The C below is the function itself: 228 bytes against retail's 236. What - * agrees is the whole shape - the 0x20 frame, the $s0 and $ra saves, the - * branch out of the "pending" path, the four stores into D_001A71C0, - * D_001A74D0, D_001A7180 and D_001A74D8, the -1 sentinel materialised as - * `lui 0xFFFF` + `ori 0xFFFF`, the wait loop (the busy flag loaded into the - * back edge's delay slot, the pump and the message under it, then - * func_0011D810), the ninth argument of func_0011D620 on the stack at - * 0x0($sp), and the epilogue. What is left is two instructions of scheduling: - * retail keeps the four stores (and three `lui $at`) before the branch into - * the loop, this cc1 sinks the last store into the branch's delay slot and - * reuses $at, and the two stores after the loop come out in the other order. - * - * Unit: the -g8 sibling (the game compiler at -O2 -G8 -ffunction-sections); - * the small globals need __attribute__((sda)) to come out $gp-relative. - * GP is 0x001AEFF0: -0x7B28 is D_001A74C8, -0x7B68 is D_001A7488, -0x7AF8 - * is D_001A74F8 and -0x7B20 is D_001A74D0. - * - * Verified: compiled with the unit's own flags and compared with retail at - * 0x001325E8: 228 of 236 bytes, the first difference at +0x1c (the $gp - * offsets, which the linker fills in). - */ - -extern int D_001A74C8 __attribute__((sda)); /* gp - 0x7B28 */ -extern int D_001A7488 __attribute__((sda)); /* gp - 0x7B68 */ -extern int D_001A74F8 __attribute__((sda)); /* gp - 0x7AF8 */ -extern int D_001A74D0; -extern int D_001A71C0; -extern unsigned int D_001A7180; -extern long long D_001A74D8; -extern int D_001A7140; -extern char D_001A76F8[]; -extern char D_001A7578[]; - -extern void func_00115D48(char *); -extern void func_00132028(void); -extern void func_0011AEA0(int); -extern int func_0011D810(int); -extern void func_0011D620(int, int, int, int, int, int, int, int, int); - -void func_001325E0(int arg0, int arg1, long long arg2) { - D_001A7488 = 0; - if (D_001A74C8 != 0) { - if (D_001A74F8 != 0) { - return; - } - func_00115D48(D_001A76F8); - return; - } else { - D_001A71C0 = arg0; - D_001A74D0 = arg1; - D_001A7180 = 0xFFFFFFFFu; - D_001A74D8 = arg2; - while (func_0011D810((int)&D_001A7140) != 0) { - if (D_001A74F8 == 0) { - func_00115D48(D_001A7578); - } - func_00132028(); - func_0011AEA0(0); - } - D_001A74C8 = 1; - func_0011D620((int)&D_001A7140, 0x57, 1, (int)&D_001A71C0, 4, (int)&D_001A7180, 4, 0, 0); - } -} diff --git a/nonmatching/functional/func_0028B160.c b/nonmatching/functional/func_0028B160.c deleted file mode 100644 index 9cd6b67bd..000000000 --- a/nonmatching/functional/func_0028B160.c +++ /dev/null @@ -1,41 +0,0 @@ -/* functional: medium. Starts from the near-miss draft; same reads, writes and calls in retail order; byte differences are register allocation only. */ -/* Best retained candidate: 280 bytes versus 292; 0/28 in us, pal and us2. */ -extern int *D_001B1888; -extern unsigned int *D_001B1894; -extern int D_001A7308; -extern void func_0028AE88(int); -extern void func_0028F948(int, int, int, int, int, int); - -void func_0028B160(int index, int unused, int param_2) -{ - int offset; - int first; - int last; - int i; - - if (D_001B1888[index + 0x74 / 4] == 0) - func_0028AE88(0); - - offset = D_001A7308; - first = 0; - if (index != 0) - first = D_001B1888[index + 0x34 / 4 - 1]; - last = D_001B1888[index + 0x34 / 4]; - - i = first; - while (i < last) { - int row_offset = i << 3; - unsigned char *row = - (unsigned char *)((unsigned int)D_001B1894 + row_offset); - unsigned char width = row[6]; - unsigned char height = row[7]; - int position = offset >> 8; - int mask = 1 << (width + height); - - i++; - func_0028F948(*(int *)row, position, 0x1B, - width, height, param_2); - offset += mask << 2; - *(short *)((unsigned int)D_001B1894 + row_offset + 4) = position; - } -} diff --git a/nonmatching/functional/func_0029F840.c b/nonmatching/functional/func_0029F840.c deleted file mode 100644 index 3a3faea85..000000000 --- a/nonmatching/functional/func_0029F840.c +++ /dev/null @@ -1,83 +0,0 @@ -/* functional: high. Draft that compiled to retail bytes alone but has not landed in a linked build; the differences left are placement only. */ -/* func_0029F840 - 288 bytes, 28 places (the boot and every level). Tier: Opus 5.5 xhigh, 1 Nov 2026. - Best check.py result: the C below gives 28 of 28 places in USA v1.01, PAL and v2.00. tools/build.py was not - run. No match is claimed and the marker stays in src/: the exact bytes need the `if (out != 0)` arm, whose - `e & 0x100` is always 0 because e is a byte. That is a fake dependency with value-identical arms, whose only - effect is on scheduling and allocation (AGENTS.md "Rules"; WORKER2.md reports such a form as FAILED). - Needs a maintainer's ruling, or the original construct. It has the "real test that vanished" shape of - func_002D3D88, except that its adjustment is an invented always-zero term, not a parameter passed 0. - - Without that arm (the call taking m and the field load directly): 288/288 bytes, 0/28 places, 12 of 72 cdiff - rows differ, all in the first call's setup. - Retail: bne v0,v1 / [move a0,s0]; b / [v0=0]; l.s f12; li.s f20; sll; addu s1; mul.s; move a1,s1; jal - Clean C: bnel v0,v1 / [l.s f12]; b / [v0=0]; sll; li.s f20; addu s1; move a1,s1; move a0,s0; mul.s; jal - - What retail's order requires, measured with cc1 -dS -dR -fsched-verbose-6: - - sched2 sees a block boundary right after l.s. l.s and li.s share the one memory unit, so in one block sll - pairs with l.s; a block starting at li.s gives retail's li.s, sll, addu, mul.s, a1. - - a0 is set before that boundary through a pseudo p. With p = m in both arms of a test, gcse's cprop rewrites - a0 = p to a0 = m and a0 stays late, so p's second set must not be a plain copy until after cprop. - - The test must stay live up to sched2. With a test combine folds (`if (e & 0x100)`, arm p = out; s = 1.0f), - greg has a0 = s0; l.s; jump, but the label is gone by sched2 and the result is the clean C's 12 rows. - How the form below gets there, from the dumps: cse2 still has p = m + t; combine reduces it to p = m; greg - gives a0 = s0 in both places; sched2 keeps the test and the arm, so the boundary holds; jump2 removes the - arm's redundant move and the test, leaving no word. - - Next: a construct with a real reason to be there that collapses after cse2, probably from a macro or inline - helper in the original. Measured, not retail: `int adj = 0; ... m + adj * 16` in the arm (the clean C's 12 - rows); `if (e < 0) p = out;` (movn, 304 bytes); `if (e < 0) { p = out; s = 1.0f; }` (304 bytes, the setup in - retail's order but the test and arm stay); both arms p = m; s = field on `index != 0` (boundary right, a0 - late, s3 and s4 exchanged). - Needs only the externs below. */ -extern void func_00282D60(void *, void *, float); -extern void func_00283098(void *, void *, void *); -extern void func_00282CC0(void *, void *, void *); -extern void func_00283130(void *, unsigned long long); -extern void func_00282D30(void *, void *, float); -int func_0029F840(char *obj, char *m, char *out, int index) { - int hdr = *(int *)(obj + 0x24); - int cnt = *(short *)((char *)hdr + 0x2E); - int tab; - char *rec; - int n; - int i; - int e; - char *dst; - float k; - char *p; - float s; - - if (cnt == 0) { - return 0; - } - tab = hdr + cnt * 16; - index += tab; - e = ((unsigned char *)index)[1]; - if (e == 0xFF) { - return 0; - } - p = m; - s = *(float *)(obj + 0x2C); - if (out != 0) { - p = m + (e & 0x100); - } - k = 0.0009765625f; - rec = (char *)tab + e * 16; - func_00282D60(p, rec, s * k); - rec += 0x10; - func_00283098(m, m, obj + 0xC0); - func_00282CC0(m, m, obj + 0x10); - n = *(short *)(rec + 6); - if (out != 0 && n > 0) { - dst = out; - for (i = n; i != 0;) { - i--; - func_00283130(dst, *(unsigned long long *)rec); - rec += 8; - func_00282D30(dst, dst, *(float *)(obj + 0x2C) * k); - *(float *)(dst + 0xC) = 1.0f; - dst += 0x10; - } - } - return n; -} diff --git a/nonmatching/functional/func_0033A520.c b/nonmatching/functional/func_0033A520.c deleted file mode 100644 index 0010f40df..000000000 --- a/nonmatching/functional/func_0033A520.c +++ /dev/null @@ -1,125 +0,0 @@ -/* functional: medium. Near-miss draft of retail size with the same frame: differences are allocation and scheduling, with some block order; paths the captured calls never take are unproven. */ -/* func_0033A520 (360 bytes, boot + 27 levels, src/game/003399B0.c, default -G0) - near miss. - Opus 5.5 xhigh (opus-1), 31 October 2026: EXACT BYTES IN USA v1.01, NOT CLAIMED AS A MATCH, not - integrated. Two things stop it landing: a do/while (0) wrapper (below), and PAL and v2.00. - - Best check.py results: - - The form below, with the wrapper: 360/360 bytes, 28 of 28 USA v1.01 places. PAL and v2.00: 0 of - 28 each, 8 words differ, all field offsets (0x1F8, 0x1FC, 0x200, 0x204 are +0x10 there, 0x134 and - 0x170 are not). One definition cannot give both; the function needs carry.py --demote or a ruling. - No linked build was run. - - The plain C at the end of this file, which breaks no rule: 360/360 bytes, 0 of 28 places, 25 of - the 90 words differ, all in +0x58..+0xBC, with relocated halves and call targets masked (cdiff.py - shows 34 rows, 8 of them calls; earlier records counted 26). - - The exact form, in place of the INCLUDE_ASM line in src/game/003399B0.c (the file already declares - the typedefs, func_00335F88 and D_001ADC88): - - extern void func_00336710(void *a0, void *a1, void *a2); - extern int *func_00335E20(void *a0); - extern void func_003369A8(void *a0, void *a1, void *a2); - extern int *func_00336DA8(int a0, int a1); - extern int func_00336E40(void *a0); - extern const f32 D_001B23A4 __attribute__((sda)); - - void func_0033A520(unsigned char *obj, void *arg) - { - float v; - float *p; - char *text; - - *(int *)(obj + 0x1F8) = 0; - *(void **)(obj + 0x200) = arg; - if (arg != 0) { - int *alloc = func_00336DA8(16, func_00336E40(arg)); - *(int **)(obj + 0x1FC) = alloc; - alloc[1] = 0; - alloc[2] = 0; - alloc[3] = 0; - alloc[0] = 0; - } - do { - v = (float)(int)(D_001B23A4 * 300.0f + 0.5f); - p = *(float **)(obj + 0x1FC); - p[0] = 70.0f; - } while (0); - text = D_001ADC88; - p = *(float **)(obj + 0x1FC); - p[1] = v; - func_00336710(obj + 0x134, text, *(void **)(obj + 0x200)); - func_00335F88(obj + 0x134, 24.0f, 24.0f, 0.0f, 0.0f); - *func_00335E20(obj + 0x134) = 0x60F0F0B0; - v = 65.0f; - *(float *)(obj + 0x204) = v; - func_003369A8(obj + 0x170, text, *(void **)(obj + 0x200)); - *func_00335E20(obj + 0x170) = 0x80F0F0F0; - func_00335F88(obj + 0x170, 0.7f, 0.7f, 0.0f, 0.0f); - } - - What each part of that form does. The byte effects were measured by taking each part away from the - exact form; the reasons come from the scheduler and allocator dumps and recalled GCC behaviour, as - no compiler source is at hand: - - The wrapper. The LOOP_END note makes `lui $s1` a scheduling barrier, so the argument set-up stays - after the conversion chain and block B comes out as retail's. Without it, 25 words differ. WORKER2.md - rules this wrapper out until the maintainers answer the question in MATCHING-BLOCKERS.md, and no - other construct found gives the same barrier. - - `const` on D_001B23A4. An unchanging read has no anti-dependence on the later store to p[0], so - 300.0f goes first by insn order. Plain `extern float` with a store in the same block loads D first; - scratch compiles of small functions show the same flip. D_001B23A4 is not really constant: 0x335DE0 - writes it. The const is a read-only view in this unit, and a reviewer has to accept that. The sda - attribute stays, for the `lui $at` form at -G0. - - One variable p for both reloads. Two deaths make it a global pseudo, so it is not kept off $v0 by - local-alloc's false-dependency rule at the fix insn. Separate reloads put alloc in $v1 (2 words). - - v reused for 65.0f. Again two deaths, so global, and it gets $f0. Otherwise $f1 (3 words). - - -G8 is not needed: the form also matches 28 of 28 in the -g8 sibling, but no $gp access calls for it. - - This corrects the earlier record, which asked for a real block boundary after the rounding. With const - and both reused variables, `if (obj) { A } else { A }` makes block A exact but leaves 7 words of block B - wrong ($v0 reload before `lui $s1`, then the argument moves). A do/while (0) around an if on the - rounded int, whose loop-end note then sits just before the join label, leaves block B wrong too; the - note seems to count only inside a block. Retail looks like a loop note, not a merged branch. That - rests on these measurements, not on the original source. Plain struct fields (mem/s) do not help: the load order and - interleaving stay, and the clears lose their retail order. Inline helpers with a float parameter give - the same bytes as a direct expression. - - Reopen with a ruling on non-empty do/while (0) wrappers, or evidence of the original construct. */ - -typedef float f32; -typedef unsigned char u8; -typedef int s32; -extern void func_00336710(void *a0, void *a1, void *a2); -extern void func_00335F88(void *a0, f32 a1, f32 a2, f32 a3, f32 a4); -extern int *func_00335E20(void *a0); -extern void func_003369A8(void *a0, void *a1, void *a2); -extern int *func_00336DA8(int a0, int a1); -extern int func_00336E40(void *a0); -extern char D_001ADC88[]; -extern f32 D_001B23A4 __attribute__((sda)); - -void func_0033A520(u8 *obj, void *arg) -{ - f32 v; - char *text; - - *(s32 *)(obj + 0x1F8) = 0; - *(void **)(obj + 0x200) = arg; - if (arg != 0) { - s32 *alloc = func_00336DA8(16, func_00336E40(arg)); - *(s32 **)(obj + 0x1FC) = alloc; - alloc[1] = 0; - alloc[2] = 0; - alloc[3] = 0; - alloc[0] = 0; - } - v = (f32)(s32)(D_001B23A4 * 300.0f + 0.5f); - ((f32 *)*(s32 **)(obj + 0x1FC))[0] = 70.0f; - text = D_001ADC88; - ((f32 *)*(s32 **)(obj + 0x1FC))[1] = v; - func_00336710(obj + 0x134, text, *(void **)(obj + 0x200)); - func_00335F88(obj + 0x134, 24.0f, 24.0f, 0.0f, 0.0f); - *func_00335E20(obj + 0x134) = 0x60F0F0B0; - *(f32 *)(obj + 0x204) = 65.0f; - func_003369A8(obj + 0x170, text, *(void **)(obj + 0x200)); - *func_00335E20(obj + 0x170) = 0x80F0F0F0; - func_00335F88(obj + 0x170, 0.7f, 0.7f, 0.0f, 0.0f); -} diff --git a/nonmatching/functional/func_L00_00303990.c b/nonmatching/functional/func_L00_00303990.c deleted file mode 100644 index 9dcc8f654..000000000 --- a/nonmatching/functional/func_L00_00303990.c +++ /dev/null @@ -1,460 +0,0 @@ -/* functional: high. Unchecked: a loader; retail never returns within the gate's 40M instructions (NOTHING COMPARED). Read against all 851 retail instructions of level 00's copy (0x303990-0x3046C8): every callee is level 00's place of the named function, every data name sits on the address retail forms (lui/addiu or $gp), the GS words (0x1DB08000/0x5C0000000, 0x19B04000/0x580000000, 0xFFA0000000E0, 0x40000400004000) sign-extend as retail's sra/dsll32 do, and the branch senses and loop bounds agree. Fixed: func_0029D4D0 is declared as the port's host routine defines it, int (int, int); func_L00_00300610 is an empty routine (jr ra), declared (void) as src/ defines it and called without the unused (table, count) retail leaves in a0/a1. The rest is the matching draft (3392/3388 bytes: register choice for one GS word, one swapped independent load/copy, one nop). */ -/* - * func_L00_00303990 (3388 bytes): the level loader's driver. With `load`, it - * unpacks the level archive (D_001A7280) into the header and data heap, - * builds the GS texture tables and GIF words, loads the moby and tie - * classes (func_00293890 / func_L00_002FF6A8 / func_L00_002FFAB8), places the - * hero's class bank, relocates spans; then always runs the level-data loader - * func_L00_00300618(load) into LD+0x68, the camera setup, and either - * func_L00_00358B30 (resume) or func_L00_003588A8. Returns 0. - */ -/* Current retained result, 1 November 2026: 3392/3388 bytes. Preserve the level loader's heap-pointer - * return contract. An explicit goto form of the final loop measured 3380 bytes and lost required control- - * flow/alignment; keep the structured loop. GS-word allocation and macro-load loop padding remain - * unresolved. - * Not a functional-port qualification or a complete matching-build result. - * Profile: -O2 -G16 -Wa,-G16 -ffunction-sections. - * Earlier measurements below remain historical where superseded by this note. - */ -/* Retained nonmatching C, Claude Opus 5.5 xhigh, 31 October 2026 (task v1860). - * USA v1.01: 3392/3388 bytes, 0/27 places. Five rows differ, plus one extra nop. - * Unit: src/levels/shared/L00_00303990-g16.c, flags -O2 -G16 -Wa,-G16 -ffunction-sections. - * Declarations are below; the INCLUDE_ASM marker goes away when this unit is added. - * No PAL, v2.00 or linked check was run because USA does not match. - * - * Remaining differences: - * 1. 0x00303AF4: retail ors the first GS word into the low half (or v1,v1,v0; or v1,v1,t4; - * sd v1); here it lands in the high half's register (or v0,v1,v0). In mips.md the first - * operand of (ior:DI (sign_extend:DI ...) ...) is not a register, so local-alloc can only - * tie the result to the second operand. Retail's second word does tie that way (or a0,a1,a0). - * Tried without effect: lo |= hi, hi | lo, an int lo, RAC1's t/u form (transition.c), hi - * shared across blocks. A 64-bit lo with the constant in a variable made it much worse. - * 2. 0x00304350: retail has lw v0,0x30(s2) then daddu a0,s5,zero; here they are swapped. - * The copy is ready in the store's clock, so it issues with the sw and ahead of the load. - * Loading before the store gives lw/daddu/sw, so retail acts as if a scheduling boundary - * follows the sw, but no branch in retail targets 0x00304350. A do/while(0) around the copy - * (61 rows differ) is not that boundary. Reordering statements, base = dst + size, - * -fno-sched-interblock, -frac2-keep-block-order and -frac2-gcse-unsplit-edges all tie. - * 3. 0x00304674: one extra nop before the last loop's bne. Everything else in that loop is - * retail's. Retail's loop is seven words with lui/lw inside. mips_r5900_pad_loops counts - * the macro lw as one insn, so it sees six and pads. Likely a toolchain limit, because - * the pass counts insns and retail's assembler counted words; a word-counting fix is - * untested. Splitting the address does not help: a plain array gets its %hi shared by - * PRE into s1, and a macro entry test through a _1 alias with a split loop test - * (3388 bytes) gets its %hi hoisted into s1 (3 rows). A goto loop was not tried: with no - * loop note it should also lose the alignment nop retail has at 0x0030465C. - * - * Wordings that closed other differences; keep them: - * - (D_00139568[0xA] + D_L00_00262570)->b4 gives retail's add operand order. - * - func_L00_002FE268 takes the class value in a0 (other callers pass an argument too). - * - In loops 2-4 the value goes in a local before the store, so LD's %hi precedes the table's. - * - The slot stores run D_L00_001DD180, D_L00_001DA680, D_L00_001D9F00, which gives retail's - * sll order and registers. - * - D_L00_001B1EA0 is an incomplete MACRO_ADDR array, reloaded with lui/lw at both tests. - * -fno-gcse is far off (808 rows); -g and -frac2-qcopy do not change any differing row. - */ -#include "common.h" - -typedef int TI128 __attribute__((mode(TI))); - -typedef union { unsigned char b[0x400]; short h[0x200]; unsigned short uh[0x200]; int i[0x100]; - char *p[0x100]; unsigned long long d[0x80]; TI128 q[0x40]; } Blk; -typedef struct { int i[0x40]; } Hdr; -typedef struct { - unsigned char pad0[4]; - unsigned char b4; - unsigned char pad5[0xDB]; -} ClassEntry; -typedef struct { - unsigned char pad0[0x1A]; - short h1A; - int i1C; -} Slot32; -typedef struct { char *data; int count; int pad8[2]; } Frame; -typedef struct { - Frame *frames; - unsigned char pad4[2]; - unsigned char b6; - unsigned char b7; - unsigned char pad8[4]; - unsigned char bC; - unsigned char bD; - unsigned char padE[0x28 - 0xE]; - Slot32 *slots; - unsigned char pad2C[0x48 - 0x2C]; - int f48[1]; -} Bank; - -extern int D_L00_001BF140[]; -#define LD ((Blk *)&D_L00_001BF140) -extern int D_L00_001C9340[]; -#define TEXBASE ((Blk *)&D_L00_001C9340) -typedef struct { int stage, busy; int *archive0; int archive1; } ArchiveLoad; -extern ArchiveLoad D_001A7280 MACRO_ADDR; -typedef struct { int offset; unsigned short kind; unsigned short pad6; int pad8[2]; } TexRef; -typedef struct { short off; short count; } Span; -extern int D_001A79F0; -extern int D_001A72F4; -extern int D_001A7304; -extern unsigned char D_0019B2E8[]; -extern unsigned char D_L00_001B1CE0[] MACRO_ADDR; -extern unsigned long long D_L00_001B1CF0[3]; -extern unsigned long long D_L00_001B1D08[3]; -extern int D_L00_001B24D8; -extern int D_L00_001B1E8C; -extern int D_L00_001B2550; -extern int D_L00_001B2410; -extern int D_L00_00225900[]; -extern int D_L00_001DC980[]; -extern int D_L00_0022D200[]; -extern int D_L00_0021FBA0[]; -extern Blk D_00152CD0; -extern Blk D_00152C00; -extern int D_L00_001B1A40; -extern int D_L00_001B2420; -extern int D_L00_001B1A44; -extern int D_L00_001B1A48; -extern unsigned long long D_L00_001C91C0[3]; -extern int D_L00_001A9520[4] __attribute__((sda)); -extern int D_L00_001B1E80; -extern int D_L00_001DD180[]; -extern short D_L00_001DA680[]; -extern Bank *D_L00_001D9F00[]; -extern unsigned char D_L00_001DA860[]; -extern short D_001A7A18; -extern int D_001A7290; -extern int D_001A72C0; -extern int D_001A72C4; -extern unsigned char D_00139568[]; -extern ClassEntry D_L00_00262570[]; -extern int D_L00_00226700[]; -extern int D_L00_0021EA20[]; -extern int D_L00_001B1944; -extern TI128 D_L00_001B1D20 MACRO_ADDR, D_L00_001B1D30 MACRO_ADDR, D_L00_001B1D40 MACRO_ADDR, D_L00_001B1D50 MACRO_ADDR; -extern int D_L00_001B1D60; -extern int D_L00_001B24D4; -extern Slot32 *D_L00_001B19EC; -extern int D_L00_001B19E8; -extern char D_L00_001A95B8[]; -extern char D_L00_001A95D8[]; -extern short D_00152CE4[]; -typedef struct { unsigned char pad0[0xA]; unsigned char enabled; } Global001A7A00; -extern Global001A7A00 D_001A7A00 MACRO_ADDR; -typedef struct { int pad[2]; int f8; } SceneTrigger; -extern SceneTrigger D_L00_001B1AD0 MACRO_ADDR; -extern int D_L00_001B1E9C __attribute__((sda)); -extern int D_L00_001B1EA0[] MACRO_ADDR; -extern int D_L00_001B19C8; - -extern void func_00292888(void); -extern void func_L00_0036ADB0(void); -extern void func_00282B50(void *, void *, int); -extern void func_00282AB0(void *, void *, int); -extern void func_00293000(void *, int, int, void *); -extern void func_0011AEA0(int); -extern int func_0029D4D0(int, int); /* the port's host routine (host/wad.c) takes game addresses as int */ -extern int func_00282A18(int); -extern void func_L00_00300090(char *, void *); -extern void func_00291EC0(char *); -extern void func_L00_00300378(char *); -extern void func_00293890(char *, void *, void *, int); -extern void func_L00_00300438(void *, int, void *); -extern void func_00292328(int); -extern void func_002934B8(Bank *, int); -extern void func_L00_002FE268(int); -extern void func_00293260(Bank *, int); -extern void func_L00_002FF6A8(char *, void *, void *, int); -extern void func_L00_00300610(void); /* retail's body is jr ra; nop: the table and count it is handed are unused */ -extern void func_L00_002FFAB8(char *, void *, void *, void *, int); -extern void func_00291DE0(void *, int); -extern void func_L00_002FD480(char *); -extern void func_00291CA8(void *, char *, void *, int); -extern void func_0026FEB8(const char *, ...); -extern char *func_L00_00300618(int); -extern void func_L00_003032F0(void); -extern void func_L00_00303418(int); -extern void func_L00_00358B30(void); -extern void func_L00_003588A8(void); -extern void func_L00_002E3BA0(int); -extern void func_L00_0032CF60(void); - -int func_L00_00303990(int load, int resume) -{ - Hdr *h = (Hdr *)LD->p[0xC / 4]; - int *f = D_001A7280.archive0; - char *base; - char *end; - int used; - int i; - int c1, c2, c3, c4; - int fx; - int fy; - char *e; - TexRef *t1, *tex, *t3, *t4; - int slot8; - int *list; - int j; - char *tab; - Span *span; - unsigned short *us; - char *q2, *q, *p; - int sq, a3, ci, k; - - if (load) - func_00292888(); - base = LD->p[0x18 / 4]; - if (load) { - func_L00_0036ADB0(); - TEXBASE->i[0] = 0; - func_00282B50(h, (char *)(f[2] + (int)f), f[3]); - func_00282AB0(D_L00_001B1CE0, D_0019B2E8 + D_001A79F0 * 16, 16); - func_00293000((char *)(f[4] + (int)f), h->i[0], h->i[0x84 / 4], (char *)h + h->i[1]); - func_0011AEA0(0); - used = func_0029D4D0(f[0x12] + (int)f, (int)base); - fx = D_001A72F4; - fy = D_001A7304; - LD->p[0x2C / 4] = base + h->i[0x60 / 4]; - { - unsigned long long lo = (unsigned long long)((fy + h->i[0x90 / 4] * 4) >> 8 | 0x1DB08000); - unsigned long long hi = (unsigned long long)((fx + h->i[0x94 / 4]) >> 8) << 37 | 0x5C0000000ULL; - D_L00_001B1CF0[0] = (lo | hi) | 0x8000000000000000ULL; - } - D_L00_001B1CF0[1] = 0xFFA0000000E0ULL; - D_L00_001B1CF0[2] = 0x40000400004000ULL; - { - unsigned long long lo = (unsigned long long)((fy + h->i[0x98 / 4] * 4) >> 8 | 0x19B04000); - unsigned long long hi = (unsigned long long)((fx + h->i[0x9C / 4]) >> 8) << 37 | 0x580000000ULL; - D_L00_001B1D08[0] = (lo | hi) | 0x8000000000000000ULL; - } - D_L00_001B1D08[1] = 0xFFA0000000E0ULL; - D_L00_001B1D08[2] = 0x40000400004000ULL; - - t1 = (TexRef *)((char *)h + h->i[0x34 / 4]); - D_L00_001B24D8 = h->i[0x30 / 4]; - for (c1 = 0; c1 < D_L00_001B24D8; c1++) - D_L00_00225900[c1] = LD->i[0x2C / 4] + t1[c1].offset + (func_00282A18(t1[c1].kind) << 28); - tex = (TexRef *)((char *)h + h->i[0x3C / 4]); - D_L00_001B1E8C = h->i[0x38 / 4]; - for (c2 = 0; c2 < D_L00_001B1E8C; c2++) { - int value = LD->i[0x2C / 4] + tex[c2].offset + (func_00282A18(tex[c2].kind) << 28); - D_L00_001DC980[c2] = value; - } - qcopy(&D_00152CD0, &tex[h->i[0x80 / 4]]); - D_00152CD0.uh[0x10 / 2] = ((unsigned short *)h)[0x80 / 2]; - t3 = (TexRef *)((char *)h + h->i[0x44 / 4]); - D_L00_001B2550 = h->i[0x40 / 4]; - for (c3 = 0; c3 < D_L00_001B2550; c3++) { - int value = LD->i[0x2C / 4] + t3[c3].offset + (func_00282A18(t3[c3].kind) << 28); - D_L00_0022D200[c3] = value; - } - t4 = (TexRef *)((char *)h + h->i[0x4C / 4]); - D_L00_001B2410 = h->i[0x48 / 4]; - for (c4 = 0; c4 < D_L00_001B2410; c4++) { - int value = LD->i[0x2C / 4] + t4[c4].offset + (func_00282A18(t4[c4].kind) << 28); - D_L00_0021FBA0[c4] = value; - } - LD->p[0x1C / 4] = base + h->i[0x8 / 4]; - func_L00_00300090(LD->p[0x1C / 4], (char *)h + h->i[0x34 / 4]); - TEXBASE->p[0x8 / 4] = LD->p[0x1C / 4]; - if (h->i[0xC / 4] != 0) { - char *p = base + h->i[0xC / 4]; - LD->p[0x20 / 4] = p; - D_L00_001B1A40 = (int)p; - } else { - LD->p[0x20 / 4] = 0; - D_L00_001B1A40 = 0; - } - if (h->i[0x10 / 4] != 0) { - char *p = base + h->i[0x10 / 4]; - LD->p[0x24 / 4] = p; - func_00291EC0(p); - } else { - D_L00_001B2420 = 0; - LD->p[0x24 / 4] = 0; - } - { - char *p = base + h->i[0x14 / 4]; - LD->p[0x28 / 4] = p; - func_L00_00300378(p); - } - TEXBASE->p[0x4 / 4] = LD->p[0x28 / 4]; - for (i = 0, q2 = (char *)h + h->i[0x1C / 4]; i < h->i[0x18 / 4]; i++, q2 += 0x20) { - char *p = *(int *)q2 != 0 ? base + *(int *)q2 : 0; - if (*(int *)(q2 + 8) != 0) { - D_L00_001C91C0[0] = D_00152C00.d[0x38 / 8]; - D_L00_001C91C0[1] = 0xFFA0000000E0ULL; - D_L00_001C91C0[2] = 0x40000400004000ULL; - func_00293890(p, 0, D_L00_001A9520, *(int *)(q2 + 4)); - D_L00_001DD180[D_L00_001B1E80 - 1] = 0xFFFC0000; - } else { - func_00293890(p, (char *)h + h->i[0x3C / 4], q2 + 0x10, *(int *)(q2 + 4)); - } - } - LD->p[0x38 / 4] = (char *)D_L00_001D9F00[0]; - func_L00_00300438((char *)h + h->i[0x1C / 4], h->i[0x18 / 4], (char *)h + h->i[0x24 / 4]); - { - int count = D_L00_001B1E80; - D_00152C00.i[0x1C / 4] = count++; - D_L00_001DD180[D_00152C00.i[0x1C / 4]] = 0xFFFC0000; - D_L00_001DA680[D_00152C00.i[0x1C / 4]] = 0xD54; - D_L00_001D9F00[D_00152C00.i[0x1C / 4]] = (Bank *)LD->p[0x70 / 4]; - D_L00_001DA860[0xD54] = D_00152C00.i[0x1C / 4]; - D_00152CD0.h[0x12 / 2] = count; - D_L00_001B1E80 = count + 1; - } - if (D_001A7290 != D_001A7A18) { - func_00292328(D_001A7A18); - D_001A7290 = D_001A7A18; - } - func_002934B8(D_L00_001D9F00[0], LD->i[0x78 / 4]); - D_L00_001DD180[0] = 0xFFFC0000; - slot8 = D_L00_001DA860[0xD54]; - if (slot8 != 0xFF) { - Bank *bank = D_L00_001D9F00[slot8]; - if (bank->b6 != 0) { - Frame *fr = &bank->frames[bank->b7]; - char *pkt = fr->data + fr->count * 16; - *(unsigned long long *)(pkt - 0x20) = D_L00_001B1CF0[0]; - *(unsigned long long *)(pkt - 0x10) = D_L00_001B1CF0[2]; - } - } - { - int want = (D_00139568[0xA] + D_L00_00262570)->b4; - if (D_001A72C0 != want) - func_L00_002FE268(want); - } - { - int hero = D_L00_001DA860[0x47]; - D_001A72C4 = hero; - func_002934B8(D_L00_001D9F00[hero], LD->i[0x74 / 4]); - } - D_L00_001DD180[D_001A72C4] = 0xFFFC0000; - us = (unsigned short *)((char *)h + h->i[0xAC / 4]); - while ((short)*us >= 0) { - int slot = D_L00_001DA860[(short)*us]; - if (slot != 0xFF) - D_L00_001DD180[slot] = 0xFFF00000; - us++; - } - for (sq = 0, p = (char *)h + h->i[0x78 / 4]; sq < D_L00_001D9F00[0]->bC; sq++, p += 4) { - if (*(int *)p != 0) { - D_L00_001D9F00[0]->f48[sq] = (int)(base + *(int *)p); - func_00293260(D_L00_001D9F00[0], sq); - } - } - LD->i[0x44 / 4] = D_L00_001D9F00[0]->f48[0]; - for (i = 0, q2 = (char *)h + h->i[0x24 / 4]; i < h->i[0x20 / 4]; i++, q2 += 0x20) - func_L00_002FF6A8(base + *(int *)q2, (char *)h + h->i[0x44 / 4], q2 + 0x10, *(int *)(q2 + 4)); - if (D_L00_00226700[0] != 0) - LD->i[0x3C / 4] = D_L00_00226700[0]; - func_L00_00300610(); - for (i = 0, q2 = (char *)h + h->i[0x2C / 4]; i < h->i[0x28 / 4]; i++, q2 += 0x30) - func_L00_002FFAB8(base + *(int *)q2, (char *)h + h->i[0x4C / 4], q2 + 0x10, q2 + 0x20, *(int *)(q2 + 4)); - if (D_L00_0021EA20[0] != 0) - LD->i[0x40 / 4] = D_L00_0021EA20[0]; - { - char *p = base + h->i[0x68 / 4]; - LD->p[0x34 / 4] = p; - D_L00_001B1944 = (int)p; - } - func_00291DE0((char *)h + h->i[0x5C / 4], h->i[0x58 / 4]); - if (h->i[0xA4 / 4] != 0) { - func_L00_002FD480(base + h->i[0xA4 / 4]); - } else { - qzero(&D_L00_001B1D20); - qzero(&D_L00_001B1D30); - qzero(&D_L00_001B1D40); - qzero(&D_L00_001B1D50); - D_L00_001B1D60 = 0; - } - if (h->i[0xA8 / 4] != 0) - D_L00_001B1A44 = (int)(base + h->i[0xA8 / 4]); - else - D_L00_001B1A44 = 0; - if (h->i[0xB0 / 4] != 0) - D_L00_001B1A48 = (int)(base + h->i[0xB0 / 4]); - else - D_L00_001B1A48 = 0; - { - char *x1 = base + h->i[0x64 / 4]; - char *x2; - LD->p[0x30 / 4] = x1; - x2 = (char *)h + h->i[0x54 / 4]; - func_00291CA8((char *)h + h->i[0x6C / 4], x1, x2, h->i[0x50 / 4]); - } - base = (char *)((unsigned int)(base + used + 0x3F) & ~0x3F); - if (D_L00_001B24D4 != TEXBASE->i[0x18 / 4]) { - char *dst; - int size; - TEXBASE->p[0x10 / 4] = base; - size = h->i[0x30 / 4] * 16; - dst = base; - base += size; - func_00282B50(dst, (char *)h + h->i[0x34 / 4], size); - TEXBASE->p[0x14 / 4] = base; - base = (char *)(((unsigned int)(base + TEXBASE->i[0x18 / 4] * 2) + 0x7F) & ~0x3F); - } - tab = (char *)h + h->i[0x70 / 4]; - span = (Span *)tab; - { - int nslots = span->count; - D_L00_001B19EC = (Slot32 *)base; - D_L00_001B19E8 = nslots; - func_00282AB0(base, tab + span->off, nslots * 32); - span++; - base += nslots * 32; - } - e = tab + span->off; - for (a3 = 0; a3 < D_L00_001B19E8; a3++) { - if (D_L00_001B19EC[a3].h1A >= span->count) { - func_0026FEB8(D_L00_001A95B8); - D_L00_001B19EC[a3].h1A = -1; - } else { - D_L00_001B19EC[a3].h1A = *(unsigned short *)(e + D_L00_001B19EC[a3].h1A * 4); - } - D_L00_001B19EC[a3].i1C = 0; - } - end = base + 0x3F; - span++; - for (ci = 0, q = (char *)h + h->i[0x1C / 4]; ci < h->i[0x18 / 4]; ci++, span++, q += 0x20) { - int cls = D_L00_001DA860[*(int *)(q + 4)]; - if (D_L00_001DA680[cls] == *(int *)(q + 4)) { - if ((span->count != 0 || D_L00_001D9F00[cls]->bD != 0) && span->count - 1 != D_L00_001D9F00[cls]->bD) - func_0026FEB8(D_L00_001A95D8, D_L00_001DA680[cls], span->count - 1, D_L00_001D9F00[cls]->bD); - { - int first; - e = tab + span->off; - first = *(int *)e; - e += 4; - for (k = 0; k < D_L00_001D9F00[cls]->bD; k++, e += 4) { - D_L00_001D9F00[cls]->slots[k].h1A = *(unsigned short *)e; - D_L00_001D9F00[cls]->slots[k].i1C = first + 1; - } - } - } - } - base = (char *)((unsigned int)end & ~0x3F); - LD->p[0x48 / 4] = base; - } - LD->p[0x68 / 4] = func_L00_00300618(load); - if (load) - D_00152CE4[0] = -1; - if (TEXBASE->i[0xC / 4] != 0) { - if (load) - func_L00_003032F0(); - func_L00_00303418(TEXBASE->i[0]); - } - if (resume) - func_L00_00358B30(); - else - func_L00_003588A8(); - D_L00_001B1AD0.f8 = 0; - if (D_001A7A00.enabled != 0) { - int m; - for (m = D_L00_001B1E9C; m != D_L00_001B1EA0[0]; m += 0x100) - func_L00_002E3BA0(m); - } - func_L00_0032CF60(); - D_L00_001B19C8++; - return 0; -} diff --git a/nonmatching/functional/func_L00_00308700.c b/nonmatching/functional/func_L00_00308700.c deleted file mode 100644 index 93a43d401..000000000 --- a/nonmatching/functional/func_L00_00308700.c +++ /dev/null @@ -1,69 +0,0 @@ -/* functional: high. Same cache lookup, least-recent replacement and entry swap as retail; address arithmetic differs. */ -/* GPT-6.1 Sol high, v0801: 296/288 bytes, 0/27 USA v1.01 places. - * Default -O2 -G0 -ffunction-sections. Compared with the prior 272-byte draft, - * the age-origin view plus grouping the data-word offset recovers the five - * saved registers and the complete scan loop. The byte offset now survives - * the call, but cc1 builds D+0x38 separately, costing two extra instructions. - * The quadword swap still has pointer/value registers permuted. Grouped byte, - * unsigned-address and word-index forms give identical 296-byte code. - * Next: keep the original D base while preventing full selected-pointer CSE; - * then resolve the swap's local allocator roles. No linked build was run. - * Declarations below. - */ -typedef int Q128 __attribute__((mode(TI))); - -typedef union { - struct { - int key; - int age; - unsigned char *data; - int pad; - } s; - Q128 q; -} Ent_308700; - -typedef struct { - unsigned char *base; - short *info; - char pad8[0x28 - 8]; - int active; - int pad2C; - Ent_308700 e[8]; -} Cache_308700; - -extern Cache_308700 D_L00_001C93A0; -extern Ent_308700 D_L00_001C93D0[8]; -extern int D_L00_001B18D8; -extern void func_00297550(unsigned char *, int, unsigned char *, short *); - -int func_L00_00308700(int key) -{ - int found; - int best; - int i; - - if (D_L00_001C93A0.active == 0) - return 0; - found = 0; - best = 0; - for (i = 0; i < 8; i++) { - if (D_L00_001C93A0.e[i].s.key == key) - break; - if (D_L00_001C93A0.e[i].s.age < (&D_L00_001C93A0.e[0].s.age)[best * 4]) - best = i; - } - if (i == 8) { - func_00297550(((unsigned char **)&D_L00_001C93A0)[best * 4 + 14], key, D_L00_001C93A0.base, D_L00_001C93A0.info); - D_L00_001C93A0.e[best].s.key = key; - i = best; - found = 1; - } - if (i != 0) { - Q128 tmp = D_L00_001C93D0[0].q; - Q128 other = D_L00_001C93D0[i].q; - D_L00_001C93D0[i].q = tmp; - D_L00_001C93D0[0].q = other; - } - D_L00_001C93A0.e[0].s.age = D_L00_001B18D8; - return found; -} diff --git a/nonmatching/functional/func_L00_00423290.c b/nonmatching/functional/func_L00_00423290.c deleted file mode 100644 index 8eb974155..000000000 --- a/nonmatching/functional/func_L00_00423290.c +++ /dev/null @@ -1,51 +0,0 @@ -/* functional: high. The near-miss draft (4 scheduling lines off) with the callees under their real names (level 00's 0x2EE0D0/0x2EE108/0x2EE138/0x2EE178/0x2EE1F8 are func_00282C88/CC0/CF0/D30/DB0) and the hero quadwords named by their addresses (0x18A0E0, 0x189EA0); same calls, arguments, copies and order as retail. */ -/* func_L00_00423290 (shared, 27 places): sets up a follow camera's frame from the hero. Unless the - * control's mode halfword (+0x86) is set: the reversed hero facing (0x18A0E0 * -1), the hero position - * (0x189EA0) into state+0x60 and +0xC0, the projection onto the facing into +0x70, clears +0xD0/+0xE0/ - * +0x100, the two offset points +0xB0 / +0xF0 (copied to +0xA0), the aim (+0x160, copied to +0x170) - * towards the control's target (+0x30, copied to +0x00), the look vector +0x210, and clears +0x240. - * From the near-miss draft nonmatching/levels/func_L00_00423290.c. */ -#include "common.h" - -typedef int CamQ __attribute__((mode(TI))); - -extern CamQ D_00189EA0; -extern CamQ D_0018A0E0; - -extern void func_00282C88(void *); -extern void func_00282CC0(void *, void *, void *); -extern void func_00282CF0(void *, void *, void *); -extern void func_00282D30(void *, void *, float); -extern float func_00282DB0(void *, void *); - -void func_L00_00423290(char *a0) -{ - char *obj; - char *pos; - char buf0[16] __attribute__((aligned(16))); - char buf1[16] __attribute__((aligned(16))); - - if (*(short *)(a0 + 0x86) != 0) - return; - - obj = *(char **)(a0 + 0x70); - pos = obj + 0x60; - - func_00282D30(buf0, &D_0018A0E0, -1.0f); - *(CamQ *)pos = D_00189EA0; - *(CamQ *)(obj + 0xC0) = *(CamQ *)pos; - func_00282D30(obj + 0x70, buf0, func_00282DB0(pos, buf0)); - func_00282C88(obj + 0xD0); - func_00282C88(obj + 0xE0); - func_00282C88(obj + 0x100); - func_00282D30(buf1, buf0, *(float *)(obj + 0x190)); - func_00282CC0(obj + 0xB0, buf1, pos); - func_00282D30(buf1, buf0, *(float *)(pos + 0xB0)); - func_00282CC0(obj + 0xF0, buf1, pos); - *(CamQ *)(obj + 0xA0) = *(CamQ *)(obj + 0xF0); - func_00282CF0(obj + 0x160, a0 + 0x30, obj + 0xB0); - *(CamQ *)(obj + 0x170) = *(CamQ *)(obj + 0x160); - *(CamQ *)obj = *(CamQ *)(a0 + 0x30); - func_00282CC0(obj + 0x210, obj + 0xB0, obj + 0x160); - *(int *)(obj + 0x240) = 0; -} diff --git a/nonmatching/game/func_00282848.c b/nonmatching/game/func_00282848.c index ae7d6fa56..9fb559e47 100644 --- a/nonmatching/game/func_00282848.c +++ b/nonmatching/game/func_00282848.c @@ -1,3 +1,4 @@ +/* 6 November 2026, round 6: marked ASM_FUNC in src/ (original assembly, pending maintainer review); see the src comment for the evidence. */ /* func_00282848, 72-byte original extent, 28 placements. A measured tools/levels.py entry correction skips the 56-byte prefix and retains the final 16-byte function. In level 00 the original row starts at diff --git a/nonmatching/game/func_00282A28.c b/nonmatching/game/func_00282A28.c index db902ae28..afe80eb47 100644 --- a/nonmatching/game/func_00282A28.c +++ b/nonmatching/game/func_00282A28.c @@ -1,3 +1,4 @@ +/* 6 November 2026, round 6: marked ASM_FUNC in src/ (original assembly, pending maintainer review); see the src comment for the evidence. */ /* func_00282A28 - 16 bytes, 28 places (the boot and every level), retail at 0x00282A28: teq $zero,$zero,0 ; nop ; jr $ra ; nop. the body starts with a trap (teq $zero,$zero,0), which no C emits. Not matched in wave 12 (worker g1): no C source reproduces the body. diff --git a/nonmatching/game/func_0028B160.c b/nonmatching/game/func_0028B160.c deleted file mode 100644 index c9710a321..000000000 --- a/nonmatching/game/func_0028B160.c +++ /dev/null @@ -1,130 +0,0 @@ -/* 4 November 2026 current-RAC1 source trials; retained, not linked. - * Six actual size/upload/bound-read groups, a page helper and loop-profile trials do not match. - * The size-only group plus no-strength-reduce gives 292/292 bytes, 0/28 USA, first +0xA8: the - * full prologue and shift-base/immediate registers agree, but call setup and the shift delay slot - * differ. Other new forms are 288/292, 300/292, or retain the original register swap. Current - * RAC1 ui/hud.c uses the same ordinary bank loop. The older best body is retained with complete - * declarations; the new size-group source remains a diagnostic, not a qualified profile. - */ -/* func_0028B160 - Opus 5.5 xhigh, v1749: 292/292 bytes, 0/28 USA v1.01 places, first mismatch - * +0x14, under the unit's -O2 -G0 -ffunction-sections (src/game/00288D88.c). Only six words - * differ, all one swap: retail keeps immediate in $s7 and the hoisted constant 1 in $s6. - * The same six words remain under -mno-split-addresses, -g, -fno-sched-interblock, -fno-regmove, - * -fno-sched-spec, -frac2-keep-block-order and -frac2-gcse-unsplit-edges; a single-pointer - * spelling of the header and offset gives them too. - * - * Allocator evidence (tools/regalloc.py): both pseudos have refs 3, but immediate has live - * length 47 and the constant 48 (24 doubled: it carries a REG_EQUIV note, as GCC's - * update_equiv_regs does for a constant), so immediate is allocated first and takes $s6. Retail needs immediate at 49 or more - * (48 ties, and the lower pseudo number wins). Each instruction removed from the loop lowers the - * constant by 2 and immediate by 1, each added before the loop raises immediate by 1: two such - * steps are needed, and the loop has no spare instruction. They must be RTL insns alive at sched1 - * that are gone from the final code. - * - * Measured dead ends: repeating the end read in both arms of the first-index test reaches 49 and - * the right registers, but sched1 orders the arms differently, cross-jumping fails, and it is 8 - * bytes long. Moving the header load and offset shift into both arms of the first if is undone by - * cse (no second shift, 308 bytes). A plain extern for D_001B1888 reaches 48 but keeps %hi in a - * saved register, or breaks the tied lui/lw in the first block when only that read is split. The - * explicit `one` local is worse: the constant is set before the guard, live length 52. Without - * the else arm the first shift is reused (saved in $s1), apparently cse-skip-blocks. - * - * Untried: a second name for D_001B1888 could put the header load in both arms of the first if - * (one step, a tie at 48), which still leaves one step to find. No linked build was run. - * - * Declarations: struct HudTexCounts, HudTexPage and HudState with D_001B1870 sda, and - * func_0028AE88, as above func_0028ACB0 in src/game/00288D88.c. Marker restored in src/. - */ -#include "common.h" - -struct HudTexCounts { - unsigned char pad0[0x14]; - int mid_ends[8]; - int ends[16]; - int loaded[16]; -}; -struct HudBank { - int unk0; - int off4; - int off8; - int offC; - int off10; - unsigned char pad14[0x40]; - int has54; - int size58; - int has5C; - int has60; - int has64; - unsigned char pad68[0x2C]; - int unk94; - int unk98; - int unk9C; - int unkA0; - int unkA4; -}; -struct HudTexPage { - unsigned int source_address; - unsigned short gs_block_offset; - unsigned char width_log2; - unsigned char height_log2; -}; -struct HudState { - int serial; - int unk4; - int unk8; - int z; - int heap_cur; - int heap_end; - union { - struct HudTexCounts *counts; - struct HudBank *bank; - } header; - void *anim_defs; - void *frame_refs; - struct HudTexPage *image_pages; - struct HudTexPage *palette_pages; -}; -extern struct HudState D_001B1870 __attribute__((sda)); -extern void func_0028AE88(int, int); - -extern int D_001A7308 __attribute__((section(".sdata"))); -extern void func_0028F948(unsigned int, int, int, int, int, int); - -/* Uploads the image pages of one HUD bank to GS memory, from the depth buffer address up, and - * records each page's block offset. Carried from rac1-decomp (src/game/hud.c, - * Hud_SendResidentBank). */ -void func_0028B160(int bank, int base, int immediate) -{ - struct HudTexCounts *counts; - int address; - int bank_offset; - int first; - int end; - int i; - int page; - int width_log2; - int height_log2; - int size; - - if (D_001B1870.header.counts->loaded[bank] == 0) { - func_0028AE88(0, base); - address = D_001A7308; - } else { - address = D_001A7308; - } - counts = D_001B1870.header.counts; - bank_offset = bank << 2; - first = bank == 0 ? 0 : counts->ends[bank - 1]; - i = first; - end = *(int *)((unsigned char *)D_001B1870.header.counts + bank_offset + 0x34); /* ends[bank] */ - for (; i < end; i++) { - page = address >> 8; - width_log2 = D_001B1870.image_pages[i].width_log2; - height_log2 = D_001B1870.image_pages[i].height_log2; - size = 1 << (width_log2 + height_log2); - func_0028F948(D_001B1870.image_pages[i].source_address, page, 0x1B, width_log2, - height_log2, immediate); - address += size * 4; - D_001B1870.image_pages[i].gs_block_offset = page; - } -} diff --git a/nonmatching/game/func_0029D7C0.c b/nonmatching/game/func_0029D7C0.c index b35d53589..95db37744 100644 --- a/nonmatching/game/func_0029D7C0.c +++ b/nonmatching/game/func_0029D7C0.c @@ -1,3 +1,4 @@ +/* 6 November 2026, round 6: marked ASM_FUNC in src/ (original assembly, pending maintainer review); see the src comment for the evidence. */ /* func_0029D7C0 - near miss (worker 3, wave 3). * * The retail body is a spin wait: it reads a word, tests bit 0x100 and loops diff --git a/nonmatching/game/func_0029F840.c b/nonmatching/game/func_0029F840.c deleted file mode 100644 index d063767bf..000000000 --- a/nonmatching/game/func_0029F840.c +++ /dev/null @@ -1,89 +0,0 @@ -/* 4 November 2026 current-RAC1 source-method trial; retained, not linked. - * Removed the synthetic always-zero e & 0x100 arm. Three actual scale/setup/first-transform - * groups each give 288/288 bytes, 0/28 USA placements, first +0x10. The object/count registers - * and first-call setup remain different. The retained C is the measured real first-transform - * group; historical exact claims below concern the removed synthetic arm. - */ -/* func_0029F840 - 288 bytes, 28 places (the boot and every level). Tier: Opus 5.5 xhigh, 1 Nov 2026. - Best check.py result: the C below gives 28 of 28 places in USA v1.01, PAL and v2.00. tools/build.py was not - run. No match is claimed and the marker stays in src/: the exact bytes need the `if (out != 0)` arm, whose - `e & 0x100` is always 0 because e is a byte. That is a fake dependency with value-identical arms, whose only - effect is on scheduling and allocation (AGENTS.md "Rules"; WORKER2.md reports such a form as FAILED). - Needs a maintainer's ruling, or the original construct. It has the "real test that vanished" shape of - func_002D3D88, except that its adjustment is an invented always-zero term, not a parameter passed 0. - - Without that arm (the call taking m and the field load directly): 288/288 bytes, 0/28 places, 12 of 72 cdiff - rows differ, all in the first call's setup. - Retail: bne v0,v1 / [move a0,s0]; b / [v0=0]; l.s f12; li.s f20; sll; addu s1; mul.s; move a1,s1; jal - Clean C: bnel v0,v1 / [l.s f12]; b / [v0=0]; sll; li.s f20; addu s1; move a1,s1; move a0,s0; mul.s; jal - - What retail's order requires, measured with cc1 -dS -dR -fsched-verbose-6: - - sched2 sees a block boundary right after l.s. l.s and li.s share the one memory unit, so in one block sll - pairs with l.s; a block starting at li.s gives retail's li.s, sll, addu, mul.s, a1. - - a0 is set before that boundary through a pseudo p. With p = m in both arms of a test, gcse's cprop rewrites - a0 = p to a0 = m and a0 stays late, so p's second set must not be a plain copy until after cprop. - - The test must stay live up to sched2. With a test combine folds (`if (e & 0x100)`, arm p = out; s = 1.0f), - greg has a0 = s0; l.s; jump, but the label is gone by sched2 and the result is the clean C's 12 rows. - How the form below gets there, from the dumps: cse2 still has p = m + t; combine reduces it to p = m; greg - gives a0 = s0 in both places; sched2 keeps the test and the arm, so the boundary holds; jump2 removes the - arm's redundant move and the test, leaving no word. - - Next: a construct with a real reason to be there that collapses after cse2, probably from a macro or inline - helper in the original. Measured, not retail: `int adj = 0; ... m + adj * 16` in the arm (the clean C's 12 - rows); `if (e < 0) p = out;` (movn, 304 bytes); `if (e < 0) { p = out; s = 1.0f; }` (304 bytes, the setup in - retail's order but the test and arm stay); both arms p = m; s = field on `index != 0` (boundary right, a0 - late, s3 and s4 exchanged). - Needs only the externs below. */ -#include "common.h" - -extern void func_00282D60(void *, void *, float); -extern void func_00283098(void *, void *, void *); -extern void func_00282CC0(void *, void *, void *); -extern void func_00283130(void *, unsigned long long); -extern void func_00282D30(void *, void *, float); -int func_0029F840(char *obj, char *m, char *out, int index) { - int hdr = *(int *)(obj + 0x24); - int cnt = *(short *)((char *)hdr + 0x2E); - int tab; - char *rec; - int n; - int i; - int e; - char *dst; - float k; - char *p; - float s; - - if (cnt == 0) { - return 0; - } - tab = hdr + cnt * 16; - index += tab; - e = ((unsigned char *)index)[1]; - if (e == 0xFF) { - return 0; - } - k = 0.0009765625f; - do { - p = m; - s = *(float *)(obj + 0x2C); - rec = (char *)tab + e * 16; - func_00282D60(p, rec, s * k); - } while (0); - rec += 0x10; - func_00283098(m, m, obj + 0xC0); - func_00282CC0(m, m, obj + 0x10); - n = *(short *)(rec + 6); - if (out != 0 && n > 0) { - dst = out; - for (i = n; i != 0;) { - i--; - func_00283130(dst, *(unsigned long long *)rec); - rec += 8; - func_00282D30(dst, dst, *(float *)(obj + 0x2C) * k); - *(float *)(dst + 0xC) = 1.0f; - dst += 0x10; - } - } - return n; -} diff --git a/nonmatching/game/func_002B6658.c b/nonmatching/game/func_002B6658.c index 1969b9093..ee9bd4a53 100644 --- a/nonmatching/game/func_002B6658.c +++ b/nonmatching/game/func_002B6658.c @@ -1,3 +1,13 @@ +/* 6 November 2026 (round 11, w-c5): not matched. Control-flow forms tested against the fixed retail flow: if/else arms that each call, both-arm callback loads, goto to a shared call, goto around the call, `?:` argument, switch on the flag, switch on `update != 0`, for(;;)/while + break, do/while(0) around call + 0x4 test, do/while with a condition after the call. All cross-jump or simplify back to `move a0; jal v1` (slot filled, callback v0); the switch on `update != 0` gives v1 but adds a compare. By construction no C form works: expand emits the a0 move adjacent to the call, and a label there survives only with a jump to it; retail has no branch to 0x2B66AC/0x2B66B0, no division (trap_if), no asm. Retail also leaves the beqz slot empty, so the daddu was unavailable to both slots there. -flive-range: no change. */ +/* 6 November 2026 (round 10, w-c5): not matched. Retail tests v0 (flags & 0x40) in the bnel, not a long-lived value; the sibling-shape lead does not apply. Flags read once into a local (f = t->flags reused) and an early `update = 0` keep v0 and the filled slot. Our reorg (fill_simple_delay_slots backward scan, plus the RAC2 trap_if stop) can only leave the jalr empty at a label, jump, SEQUENCE, asm or trap_if between the a0 move and the call; an unused user label before the call is deleted by jump. v1 needs a non-call-crossing allocno born after func_002A05A8 that conflicts with the callback and prefers v0 (regs_someone_prefers); only t (call-crossing, pruned) exists. */ +/* 6 November 2026 (round 9, w-cc): not matched, no flag. Source: a `void (*volatile vfunc)` member drops the bnel steal (retail steals the lw, so the retail load is not volatile); a `const` callback local is identical (v0, filled slot). Compiler rule: falsified by comparison, not built. Our cc1 output for matched func_L00_002D5940 has the identical pre-reorg shape (beql slot steals `lw $2,100`, label, `beq $2`, `move $4`, `jal $31,$2`) and retail fills that slot with v0, so any reorg rule that empties this jalr slot, or any allocation rule keyed on this shape that gives v1, changes a matched unit. */ +/* 6 November 2026 (round 6, w-c5): not matched. Separate head local (`head = func_002A08A0(); ref = head; for (t = head; ...)`) gives retail's `sw $v0` global store; with `volatile unsigned short flags` and the plain join load the only diffs left are callback v0 (retail v1) and the filled jalr slot. Gas in reorder mode reproduces retail's `beqz; nop; daddu a0; jalr v1; nop` exactly, so retail cc1 left that jalr unfilled; reorg (fill_simple_delay_slots backward scan) only refuses the a0 move for a label/asm/SEQUENCE/trap_if between it or a volatile/length-2 insn, none reachable from C here. greg: callback pseudo conflicts only with t, a0, sp (no v0 conflict). If/else arms that each call the callback, and goto-to-shared-call forms, cross-jump back to the same code. */ +/* 5 November 2026 (round 5, w-cc): not matched, no flag. v1 is reachable: `update = t->vfunc; if ((t->flags & 0x40) == 0) { func_002A05A8(t); update = t->vfunc; }` keeps the callback live over the v0 flag test, so global-alloc gives v1; but reorg then backfills the first lw into a plain bne (retail bnel, stolen from target) and still fills the jalr slot. Census of `move aN; jal; nop` in boot+L00: the matched-C sites checked (func_0027A1D0, func_L00_003F5870) are unfilled because a real cross-jump label sits between the arg move and the jal; no source form here gives such a label, and no principled reorg rule covers only these two sites. */ +/* 5 November 2026 (w-c6): one-pass groups around the callback load, the call, load+call, the 0x40 test, the 0x4 test, the whole body and a grouped `self = t` arg (cse deletes it) all keep v0 and the filled jalr slot. greg shows the callback pseudo conflicts only with t (crosses calls, so its v0 preference is pruned); priority order is irrelevant: v1 needs a real hard conflict with v0 during lw..jalr. */ +/* 5 November 2026 (w-c2): cc1 -dd shows our reorg fills the jalr slot from the backward a0 move; retail census has the same `lw; L: beqz; nop; jalr; daddu a0` shape filled 27 times elsewhere, so only this function and its sibling func_L00_0032CF60 (callback in v1, slot empty) differ. Unprototyped callback, direct member call, int return, -fno-schedule-insns(2)/-fexceptions/-fno-gcse/-fno-sched-interblock all keep v0 and the filled slot. Next: find what makes global-alloc avoid v0 (regs_someone_prefers from a lower-priority conflicting pseudo) - the same RTL cause likely blocks the slot. */ +/* 5 November 2026 (wave 3): not matched. Only these two functions (all 28/27 places) have lw v1;beqz;nop;daddu a0;jalr v1;nop; the 27 FILLED lw v0,0x64(s2) sites are func_L00_002D5940 (C, plain `if (obj->update) obj->update(obj);`). Reorg (reorg.c fill_simple_delay_slots) can only refuse the a0 move if a stopper (label/asm/jump) sits between it and the call: an empty asm after a $4-pinned arg reproduces nop+daddu+jalr+nop exactly, and a $3 pin gives v1, but both are banned. int/ptr/double/long long/char/short returns, switch/goto/cross-jump forms, int-view test, local copy, inline helper with -mastra-sibcall/-mastra-cygnus-cfg, and -O1/-O3/-Os/-fno-* flags all keep v0 and the filled slot. */ +/* 5 November 2026 (wave 2): `volatile unsigned short flags` stops the beql target steal, so the beqz+nop now match retail; still 144/148, 0/28: callback stays in v0 and cc1 fills the jalr slot with the a0 move (retail: v1, a0 move before jalr, nop slot). Tried -g, -frac2-hazard-labels, -frac2-keep-block-order, noreturn/variadic/long/float callback types, inline helper: no change. */ +/* 5 November 2026: pointer-based baseline rechecked at 144/148, 0/28; retail hoists the callback `lw $v1,0x64` into the first bnel slot and leaves nops in both the beqz and jalr slots (a0 move sits between), which the baseline never reproduces. */ /* 4 November 2026 follow-up: nonmatching, not linked. The actual head-cache * store occurs once in the entry branch slot, using the getter's v0; the * loop backedge enters at the current-node state test. Do not add a cache diff --git a/nonmatching/game/func_002B9380.c b/nonmatching/game/func_002B9380.c index b32cd0786..11d42bca9 100644 --- a/nonmatching/game/func_002B9380.c +++ b/nonmatching/game/func_002B9380.c @@ -1,3 +1,4 @@ +/* 6 November 2026, round 6: marked ASM_FUNC in src/ (original assembly, pending maintainer review); see the src comment for the evidence. */ #include "include_asm.h" /* Claude Opus 5.5 xhigh worker, 2026-10-31; retained near miss, not linked. diff --git a/nonmatching/game/func_002B9390.c b/nonmatching/game/func_002B9390.c index b3fd42f08..74f039770 100644 --- a/nonmatching/game/func_002B9390.c +++ b/nonmatching/game/func_002B9390.c @@ -1,3 +1,4 @@ +/* 6 November 2026, round 6: marked ASM_FUNC in src/ (original assembly, pending maintainer review); see the src comment for the evidence. */ #include "include_asm.h" /* func_002B9390: measured plain-C near miss, not linked. diff --git a/nonmatching/game/func_002F7320.c b/nonmatching/game/func_002F7320.c deleted file mode 100644 index 628c0df58..000000000 --- a/nonmatching/game/func_002F7320.c +++ /dev/null @@ -1,47 +0,0 @@ -/* 2 November 2026: the signed 32-bit index/result form remains 132/132 bytes, 0/28 US placements. An unsigned index changes the retail signed bound test; a 64-bit result expands to 140 bytes without preserving the required zero copy. Neither is retained. The entry zero-copy/CSE constraint remains; do not repeat width probes without new compiler evidence. */ -/* - * func_002F7320 (boot 0x002F7320, 132 bytes, 28 places). - * Tier: control flow solved, allocation open. - * Best check.py: 132/132 bytes, 0/28 places, 18 of 33 rows differ; every - * differing row is a register number, plus one zero-copy instruction. - * - * Solved here (do not rework): - * - The plain indexed while is the original shape. jump1 duplicates the exit - * test before the loop, cse1 folds `i < 56` there, thread_jumps sends the - * first test straight past the found-block test, and strength reduction - * makes T[i] the two-step base (la; += 16) with the increment first in the - * loop, which reorg steals for the bnel slot. - * - * Still differs: retail has `daddu a3,t1,zero` (i = result) where this has - * `daddu a3,zero,zero`. With that copy alive, result = 0 has a dependent, so - * sched1 puts it ahead of the argument copies, result conflicts with hard a0, - * and allocation becomes retail's: a0 value, a3 i, t0 base, t1 result, - * t2 field, t3 reach. A probe with an opaque (forbidden) asm zero confirmed - * those registers. - * - * Why the copy is hard: cse folds it (const 0 costs less than a pseudo), and - * reload_cse will not swap a cheap CONST_INT for a register. Yet retail's - * first load and base have no shift, so `i` must be known to be 0 by cse2. - * The copy therefore needs either i = literal-T[0] code plus a label that - * flushes cse through cse2, or a zero cse cannot see that combine folds. - * - * Declarations needed: Func_002F7320Row and ref_L00_002F7320_00, below. - */ -typedef struct { - int key; - int values[3]; -} Func_002F7320Row; - -extern Func_002F7320Row ref_L00_002F7320_00[]; - -int func_002F7320(int value, int key, int field) -{ - int result = 0; - int i = result; - - while (ref_L00_002F7320_00[i].key != 0 && i < 56 && key != ref_L00_002F7320_00[i].key) - i++; - if (ref_L00_002F7320_00[i].key != 0) - result = value == ref_L00_002F7320_00[i].values[field]; - return result; -} diff --git a/nonmatching/game/func_0033A520.c b/nonmatching/game/func_0033A520.c deleted file mode 100644 index 880893c69..000000000 --- a/nonmatching/game/func_0033A520.c +++ /dev/null @@ -1,56 +0,0 @@ -/* 4 November 2026: meaningful coordinate grouping and a complete position - * view reduce this to a 360-byte near miss, 0/28 USA placements, first +0x60. - * The 300.0 literal and mutable screen-scale load still issue in the opposite - * order. Explicit multiplication steps and an incomplete sda array view tie. - * No const claim is made for the scale that the display-mode setter writes. - * US2/PAL also differ at +0x24 because their object fields moved by 16 bytes; - * a future promotion must establish their separate catalogue identities. - * Profile: -O2 -G0 -ffunction-sections. No linked match is claimed. - */ -#include "common.h" - -typedef struct { float x, y, width, height; } TitlePosition; -extern void func_00336710(void *, void *, void *); -extern void func_00335F88(void *, float, float, float, float); -extern int func_00335E20(void *); -extern void func_003369A8(void *, void *, void *); -extern int *func_00336DA8(int, int); -extern int func_00336E40(void *); -extern char D_001ADC88[]; -extern float D_001B23A4[] __attribute__((sda)); - -void func_0033A520(unsigned char *obj, void *arg) -{ - float v; - TitlePosition *p; - char *text; - - *(int *)(obj + 0x1F8) = 0; - *(void **)(obj + 0x200) = arg; - if (arg != 0) { - int *alloc = func_00336DA8(16, func_00336E40(arg)); - *(int **)(obj + 0x1FC) = alloc; - alloc[1] = 0; - alloc[2] = 0; - alloc[3] = 0; - alloc[0] = 0; - } - do { - v = 300.0f; - v *= D_001B23A4[0]; - v = (float)(int)(v + 0.5f); - p = *(TitlePosition **)(obj + 0x1FC); - p->x = 70.0f; - } while (0); - text = D_001ADC88; - p = *(TitlePosition **)(obj + 0x1FC); - p->y = v; - func_00336710(obj + 0x134, text, *(void **)(obj + 0x200)); - func_00335F88(obj + 0x134, 24.0f, 24.0f, 0.0f, 0.0f); - *(int *)func_00335E20(obj + 0x134) = 0x60F0F0B0; - v = 65.0f; - *(float *)(obj + 0x204) = v; - func_003369A8(obj + 0x170, text, *(void **)(obj + 0x200)); - *(int *)func_00335E20(obj + 0x170) = 0x80F0F0F0; - func_00335F88(obj + 0x170, 0.7f, 0.7f, 0.0f, 0.0f); -} diff --git a/nonmatching/levels/func_L00_00308700.c b/nonmatching/levels/func_L00_00308700.c deleted file mode 100644 index 3154cc656..000000000 --- a/nonmatching/levels/func_L00_00308700.c +++ /dev/null @@ -1,90 +0,0 @@ -/* 4 November 2026 current-RAC1 source trials; retained, not linked. - * Three real RAC1 scan/swap/decode-phase trials give 272 or 276 bytes against 288, 0/27 USA - * placements. The retained 276-byte owner-view form uses the complete cache representation for - * age offsets and the measured entry array for data; it avoids stepping beyond a scalar field as - * an int array. It preserves the miss return and selected-first swap without the donor's dummy - * increment/decrement. Keeping separate table-base/index values across decode remains unresolved. - * Older 296-byte measurements below are history. - */ -/* v2133 (Opus 5.5): still the closest draft (296/288, 0/27). Retail keeps - * la D (s0, set in the miss block) and best<<4 (s1) across the call and adds - * them base-first afterwards, so cse never knew the base was a constant. - * Natural forms merge the pre- and post-call &D+best*16 (272). A top-level - * Cache *c used on one side of the call gives unmerged sums and 5 saved regs - * at 284, but the base is the prologue la kept live through the loop and the - * post-call add order is swapped. Reassigning c after the call gives 272/276. - * The swap quads sit in v1/a0 with the pointer in v0 (retail: v0/v1, a0), and - * the tail's %hi goes to v0 (retail shares a0). - */ -/* GPT-6.1 Sol high, v0801: 296/288 bytes, 0/27 USA v1.01 places. - * Default -O2 -G0 -ffunction-sections. Compared with the prior 272-byte draft, - * the age-origin view plus grouping the data-word offset recovers the five - * saved registers and the complete scan loop. The byte offset now survives - * the call, but cc1 builds D+0x38 separately, costing two extra instructions. - * The quadword swap still has pointer/value registers permuted. Grouped byte, - * unsigned-address and word-index forms give identical 296-byte code. - * Next: keep the original D base while preventing full selected-pointer CSE; - * then resolve the swap's local allocator roles. No linked build was run. - * Declarations below. - */ -#include "common.h" - -typedef int Q128 __attribute__((mode(TI))); - -typedef union { - struct { - int key; - int age; - unsigned char *data; - int pad; - } s; - Q128 q; -} Ent_308700; - -typedef struct { - unsigned char *base; - short *info; - char pad8[0x28 - 8]; - int active; - int pad2C; - Ent_308700 e[8]; -} Cache_308700; - -extern Cache_308700 D_L00_001C93A0; -extern int D_001B18D8; -extern void func_00297550(unsigned char *, int, unsigned char *, short *); - -int func_L00_00308700(int key) -{ - int found; - int best; - int i; - - if (D_L00_001C93A0.active == 0) - return 0; - found = 0; - best = 0; - for (i = 0; i < 8; ++i) { - if (D_L00_001C93A0.e[i].s.key == key) - break; - if (D_L00_001C93A0.e[i].s.age < *(int *)((unsigned char *)&D_L00_001C93A0 + 0x34 + best * 16)) - best = i; - } - if (i == 8) { - do { - func_00297550(D_L00_001C93A0.e[best].s.data, key, D_L00_001C93A0.base, D_L00_001C93A0.info); - } while (0); - D_L00_001C93A0.e[best].s.key = key; - i = best; - found = 1; - } - if (i != 0) { - Ent_308700 *base = D_L00_001C93A0.e; - Ent_308700 *other = base + i; - Q128 tmp = other->q; - other->q = base->q; - base->q = tmp; - } - D_L00_001C93A0.e[0].s.age = D_001B18D8; - return found; -} diff --git a/nonmatching/levels/func_L00_00309DB0.c b/nonmatching/levels/func_L00_00309DB0.c deleted file mode 100644 index 1dc44420b..000000000 --- a/nonmatching/levels/func_L00_00309DB0.c +++ /dev/null @@ -1,21 +0,0 @@ -/* 4 November 2026: release qualification changes the boundary conclusion. - * US and US2 each have 27 copies with the retained orphan sequence after - * a completed return/delay/padding; no scanned direct, aligned-literal or - * nearby LUI/low-half reference enters these extents. In every PAL copy, - * however, the first stack adjustment is the preceding jr's delay slot. - * PAL level 20 additionally contains an aligned loaded word at 0x0026A2B8 - * equal to the row's 0x00320200 address. Its role as a pointer is unproven; - * no direct or nearby address-pair reference was found in any PAL copy. - * Preserve every marker and row. Reopen with the PAL predecessor's real - * extent and this loaded-word provenance, rather than applying a blanket - * exclusion from the US-only observation below. No C compile was repeated. - */ -/* Current US catalogue-boundary review, 2026-11-03. - * 27/27 US placements follow completed return/delay/padding, then two unmatched positive stack restores and orphan v0 moves. No external direct, aligned literal or nearby LUI-address pair reaches the extent. - * Direct branch/jump scans cover EE text, excluding VU microcode. - * Aligned loaded-word pointers and nearby LUI+low-half constructions were also inspected. - * Arbitrary computed indirect entries are outside this scan. - * A specifically reviewed residue repair; guessed retained caller was unrelated to the actual words. - * The former guessed/dummy-buffer source is preserved privately and rejected. - * No C candidate or exact-C credit is claimed for the current extent. - */ diff --git a/nonmatching/levels/func_L00_0032CF60.c b/nonmatching/levels/func_L00_0032CF60.c index 446d4ecaa..519821336 100644 --- a/nonmatching/levels/func_L00_0032CF60.c +++ b/nonmatching/levels/func_L00_0032CF60.c @@ -1,3 +1,11 @@ +/* 6 November 2026 (round 11, w-c5): not matched; see func_002B6658 round-11 note. The same control-flow forms (if/else arms each calling, goto to a shared call, do/while(0) group over call + 0x4 test) compiled with -g give the identical filled `jal v1; move a0` and a v0 callback; no C form puts a surviving label, jump or trap_if between the a0 move and the call. */ +/* 6 November 2026 (round 10, w-c5): not matched; see func_002B6658 round-10 note. Retail (0x32D008) also tests v0 in the bnel, so the s0-vs-v0 sibling lead gives no source form; the jalr slot still needs a reorg stopper no C form here produces. */ +/* 6 November 2026 (round 9, w-cc): not matched, no flag; see func_002B6658 round-9 note. A volatile callback member is ruled out by retail itself (the lw is stolen into bnel). Matched func_L00_002D5940 has the same pre-reorg shape with a v0 callback and a filled slot, so no reorg or allocation rule keyed on this shape can be landed. */ +/* 6 November 2026 (round 6, w-c5): not matched; see func_002B6658 note (same blocker). Retail's `beqz; nop; daddu a0; jalr v1; nop` is exactly what gas emits when cc1 leaves both slots unfilled; no C form found that makes reorg refuse the adjacent a0 move, and the callback pseudo has no v0 conflict. */ +/* 5 November 2026 (round 5, w-cc): not matched, no flag; see func_002B6658 note. Same result with the pointer form: a callback read before the 0x40 test plus a reload after func_002A05A8 keeps the callback live over the v0 flag test, so global-alloc gives v1; but reorg then backfills the first lw into a plain bne (retail bnel, stolen from target) and still fills the jalr slot. Census of `move aN; jal; nop` in boot+L00: the matched-C sites checked (func_0027A1D0, func_L00_003F5870) are unfilled because a real cross-jump label sits between the arg move and the jal; no source form here gives such a label, and no principled reorg rule covers only these two sites. */ +/* 5 November 2026 (w-c6): same result as func_002B6658 (see its note): load/call/test groups and both-arm loads keep v0 and the filled slot; v1 needs a hard v0 conflict across lw..jalr, not a priority change. */ +/* 5 November 2026: own -O2 -G8 -g unit with retained body: 256/260. Reading the two post-scan flag tests through `volatile unsigned short *` (0x34) gives retail's `beqz; nop` before the callback (260/260 except below); a volatile callback-pointer load instead blocks the bnel steal (wrong); int-returning callback is neutral. Left: callback pointer in v0 (retail v1) and retail's `daddu a0; jalr v1; nop` unfilled jalr slot (ours fills it with the a0 move). */ +/* 5 November 2026 (wave 3): not matched. Only these two functions (all 28/27 places) have lw v1;beqz;nop;daddu a0;jalr v1;nop; the 27 FILLED lw v0,0x64(s2) sites are func_L00_002D5940 (C, plain `if (obj->update) obj->update(obj);`). Reorg (reorg.c fill_simple_delay_slots) can only refuse the a0 move if a stopper (label/asm/jump) sits between it and the call: an empty asm after a $4-pinned arg reproduces nop+daddu+jalr+nop exactly, and a $3 pin gives v1, but both are banned. int/ptr/double/long long/char/short returns, switch/goto/cross-jump forms, int-view test, local copy, inline helper with -mastra-sibcall/-mastra-cygnus-cfg, and -O1/-O3/-Os/-fno-* flags all keep v0 and the filled slot. */ /* 4 November 2026 bounded source-method review; retained, not linked. * Four new actual read/dispatch/address-word forms under O2/G8/g reach 260/260 bytes but 0/27 USA * places, first +0xA8. A complete measured flags-reload view removes speculative flag-load diff --git a/nonmatching/levels/func_L00_003B39D0.c b/nonmatching/levels/func_L00_003B39D0.c deleted file mode 100644 index 1998f78d8..000000000 --- a/nonmatching/levels/func_L00_003B39D0.c +++ /dev/null @@ -1,78 +0,0 @@ -/* 4 November 2026 current-RAC1 source-method trial; retained, not linked. - * Grouping the actual data read or actual collision-result call gives 292/292 bytes, 0/27 USA - * placements, first +0x4, with the default G0 profile. The entry schedule and subsequent - * allocation remain different; no empty barrier or invented access was used. - */ -/* Claude Opus 5.5 (xhigh), 2026-10-31: code below unchanged, remeasured. - * -fno-schedule-insns: 292/292 bytes, 0/27 places, 11 register/order lines in the arms. - * Default -O2 -G0 -ffunction-sections: 296/292, 0/27; only the entry block differs, and it - * causes the extra word. So sched1 was on in retail (the arms need it); the entry is the blocker. - * sched1 priorities there (-fsched-verbose-5): position 4, f12 4, a2 load 4, data load 3, - * a0 = position 3. f12 and both loads share the one memory unit, so a0 = position issues before - * the data load, the object pseudo overlaps $a0 and takes $v1. Retail needs the load first, so - * the load needs priority >= 4 or a boundary. Ties: float local for 0.25f, true prototype - * (void *, int, void *, float), -g, -frac2-qcopy, -fno-gcse, -fno-expensive-optimizations, - * -fno-strength-reduce, -fno-rerun-loop-opt, -fno-regmove, -fno-rerun-cse-after-loop. - * Diagnostic only, forbidden wrapper: do { } while (0) just before the call gives 292/292 on the - * default profile with the whole body right, but the note also binds sched2, so the prologue - * order still differs: not exact. `if (hero)` keeps a real test. - * Reopen with: an independent reason for the data load to precede a0 = position. - */ -/* GPT-6.1 Sol (high), 2026-10-29. Retained near miss; not linked. - * Profile: -O2 -G0 -ffunction-sections -fno-schedule-insns. - * USA v1.01: 292/292 bytes, 0/27 places. The first scheduling pass caused - * the extra object-pointer copy in the older 296-byte draft. Disabling it - * reproduces the complete retail prologue and first vector operations. - * Remaining: projection/remaining use s0/s1 rather than s1/s0, and both - * func_00283028 calls put the third argument in the delay slot instead of - * retail's first/second argument. Reusing the position variable regresses - * allocation; aggregate temporary storage ties. FP-first collision arguments, - * -fno-force-mem, -fno-sched-spec and -fno-sched-interblock retain 296 bytes. - * The declarations below are complete; the source needs the profile above. - */ -#include "common.h" - -typedef int Quad __attribute__((mode(TI))); -typedef struct { char pad00[0xb0]; float origin[4]; char padc0[0x21d0]; int mask; } CollisionState; -extern CollisionState D_00189E20; -extern Quad D_L00_001BF230[2]; -extern int D_L00_001A8FF0[] __attribute__((sda)); -extern int func_00277258(void *,int,float,void *); -extern void func_00282CF0(float *,void *,void *); -extern void func_00282F20(float *,float *,float); -extern float func_00282DB0(float *,float *); -extern void func_00282D30(float *,float *,float); -extern void func_00283028(void *,void *,void *); -extern void func_00282CC0(void *,void *,void *); - -typedef struct { char pad[0x10]; Quad position; char pad20[0x48]; char *data; } CollisionObject; - -void func_L00_003B39D0(CollisionObject *object) -{ - float normal[4],projection[4],remaining[4]; - char *data=object->data; - void *position=&object->position; - int collided; - do { - collided = func_00277258(position,0,0.25f,(void *)D_00189E20.mask); - } while (0); - if (collided) { - qcopy(position,D_L00_001BF230); - if(D_L00_001A8FF0[0]) { - float dot; - data+=0x30; - func_00282CF0(normal,D_00189E20.origin,position); - func_00282F20(normal,normal,1.0f); - dot=func_00282DB0(normal,(float *)data); - func_00282D30(projection,normal,dot); - func_00282CF0(remaining,data,projection); - func_00283028(data,remaining,&D_L00_001BF230[1]); - func_00282CC0(data,data,projection); - } else { - float vertical=*(float *)(data+0x38); - *(float *)(data+0x38)=0; - func_00283028(data+0x30,data+0x30,&D_L00_001BF230[1]); - *(float *)(data+0x38)=vertical; - } - } -} diff --git a/nonmatching/levels/func_L00_00423290.c b/nonmatching/levels/func_L00_00423290.c deleted file mode 100644 index 825a5199d..000000000 --- a/nonmatching/levels/func_L00_00423290.c +++ /dev/null @@ -1,106 +0,0 @@ -/* 3 November 2026: current RAC1 Camera fields and RAC2 neighbor reviewed. - * The actual input is represented by its id +0x86 / state pointer +0x70 - * prefix. Hero addresses are formed within the incomplete owning byte object, - * without the preceding unused large union bounds. All 16-byte objects, - * original state capture, calls, widths and full transfers are preserved. - * Original G0/qcopy/barrier profile: 360/360 bytes, 0/27 USA, +0x58. - * Baseline, first-copy qcopy_nc and this owning-prefix form produce identical - * complete checker listings. Keep the full-transfer form, not the weakened - * clobber variant. Three equal forms stop this family; the +0x60 advance - * still issues after the first call. No source barrier or fake use is added. - * Reopen on a real pointer lifetime feeding that call. No alternate-release - * or linked build was run for these failed candidates. - */ -/* Historical notes describe the preceding retained source. */ -/* func_L00_00423290 (360 bytes) - near miss (v2142, 3 November 2026): 360/360 bytes, 0/27 places, - * one instruction out of place (was five setup positions with -mno-split-addresses). - * Profile: own unit, -O2 -G0 -ffunction-sections -frac2-qcopy -frac2-qcopy-barrier - * (no -mno-split-addresses: split addresses keep `daddu $a0,$sp` in the first jal's slot). - * `obj = v60;` before `v160 = v60 + 0x160;` gives retail's daddu $s2,$s1 / addiu $s4,$s1,0x160 order. - * Left: `addiu $s1,$s1,0x60` (in-place v60 += 0x60) issues after the first jal instead of before it. - * Cause: its only dependent is the post-call qcopy barrier, so its sched priority is 36 against 37 - * for the a0/a1 argument setups; retail needs the call to depend on it (sched_before_next_call - * needs a call-free source pseudo), but a separate temp for the object copy is folded by cse - * (356 bytes). -fno-schedule-insns grows to 364, -fno-sched-interblock ties. - * Declarations: Hero union view of D_00189E20, TImode V4 type, externs func_00282CF0_2, - * func_00282CC0, func_00282D30, func_00282DB0_1 (float), func_00282C88. - */ -#include "common.h" -/* Camera id/state fields are independently observed at the same offsets - * as the public RAC1 Camera prefix (origin/main 1d8228cc). */ -typedef struct { - unsigned char bytes00[0x70]; - char *state; - unsigned char bytes74[0x12]; - short id; -} CameraInitPrefix; -extern unsigned char D_00189E20[]; - -#include "include_asm.h" - -#ifndef RAC2_T_V4_F0FBA48D3 -#define RAC2_T_V4_F0FBA48D3 -typedef int V4_F0fba48d3 __attribute__((mode(TI))); -#endif - -extern void func_00282CF0_2(void *b, void *c, void *d); - -extern void func_00282CC0(void *c, void *c2, void *s); - -extern void func_00282D30(void *dst, void *src, float k); - -extern float func_00282DB0_1(char *local, char *p); - -extern void func_00282C88(void *a); - - - - - -void func_L00_00423290(CameraInitPrefix *camera) -{ - char *obj; - char *v60; - char *vB0; - char *vF0; - char *v160; - char *hero; - char *pos; - V4_F0fba48d3 *dst; - char buf0[16]; - char buf1[16]; - - if (camera->id != 0) - return; - - hero = (char *)D_00189E20 + 0x2C0; - v60 = camera->state; - obj = v60; - v160 = v60 + 0x160; - v60 += 0x60; - - func_00282D30(buf0, hero, -1.0f); - /* The hero's position, 0x240 below the facing direction the call above uses. */ - hero = hero - 0x240; - *(V4_F0fba48d3 *)v60 = *(V4_F0fba48d3 *)hero; - dst = (V4_F0fba48d3 *)(obj + 0xC0); - *dst = *(V4_F0fba48d3 *)v60; - vB0 = obj + 0xB0; - vF0 = obj + 0xF0; - func_00282D30(obj + 0x70, buf0, func_00282DB0_1(v60, buf0)); - func_00282C88(obj + 0xD0); - func_00282C88(obj + 0xE0); - func_00282C88(obj + 0x100); - func_00282D30(buf1, buf0, *(float *)(v160 + 0x30)); - func_00282CC0(vB0, buf1, v60); - func_00282D30(buf1, buf0, *(float *)(v60 + 0xB0)); - func_00282CC0(vF0, buf1, v60); - dst = (V4_F0fba48d3 *)(obj + 0xA0); - *dst = *(V4_F0fba48d3 *)vF0; - func_00282CF0_2(v160, (char *)camera + 0x30, vB0); - dst = (V4_F0fba48d3 *)(obj + 0x170); - *dst = *(V4_F0fba48d3 *)v160; - *(V4_F0fba48d3 *)obj = *(V4_F0fba48d3 *)((char *)camera + 0x30); - func_00282CC0(obj + 0x210, vB0, v160); - *(int *)(obj + 0x240) = 0; -} diff --git a/nonmatching/levels/func_L00_00424BB8.c b/nonmatching/levels/func_L00_00424BB8.c deleted file mode 100644 index 015414dcf..000000000 --- a/nonmatching/levels/func_L00_00424BB8.c +++ /dev/null @@ -1,26 +0,0 @@ -/* 72 bytes, exact in 23 of 27 places: the four others (16_snivelak, - 22_dobbo_orbit, 23_damosel_orbit, 26_jamming_array) hold other constants, so no one - source form reaches them - retail uses q+0x20 with fields +0x1C/+0x20 there, and - q+0x60 with +0xE4/+0xE8 in the 23 others. The placement then drops the body - everywhere and every program still prints OK, so the loss only shows as - "1 do not match" on the build line. ref_LNN_XXXXXXXX_kk cannot name these: - it gives a symbol value, not an immediate constant. */ -extern char *D_L00_001B8E10; - -void func_L00_00424BB8(float a, float b) -{ - char *p = D_L00_001B8E10; - - if (*(short *)(p + 134) == 0) { - char *q = *(char **)(p + 112); - char *r = q + 0x60; - - if (a != 0.0f) { - *(float *)(r + 228) = a; - } - if (b != 0.0f) { - *(float *)(r + 232) = b; - } - } -} - diff --git a/nonmatching/levels/func_L01_00304270.c b/nonmatching/levels/func_L01_00304270.c index f8ecdf11f..75291776d 100644 --- a/nonmatching/levels/func_L01_00304270.c +++ b/nonmatching/levels/func_L01_00304270.c @@ -1,3 +1,4 @@ +/* 6 November 2026, round 6: marked ASM_FUNC in src/ (original assembly, pending maintainer review); see the src comment for the evidence. */ /* Does not match: the attempt compiles to 36 bytes, retail is 52 (13 instructions). Retail loads its pointer from $v1, a register that is not an argument, and tests with a2; the self-jump (j func_304270) on a 0x100 test suggests a caller-set $v1 or a hand-written spin. Missing: the caller context that sets $v1 (no C parameter reaches $v1). */ void func_L01_00304270(volatile unsigned int *p) { while (*p & 0x100) diff --git a/nonmatching/levels/func_L01_0031B300.c b/nonmatching/levels/func_L01_0031B300.c deleted file mode 100644 index cf49ccc85..000000000 --- a/nonmatching/levels/func_L01_0031B300.c +++ /dev/null @@ -1,74 +0,0 @@ -/* 4 November 2026, real source-group review; retained, not linked. - * Default G0 profile in L01_002A7248.c: a group containing the actual height read restores the - * full retail register map. It is 276/272 bytes, 0/5 USA places: only the alignment nop at +0x74 - * remains (then shifts the following instructions). Including normal preparation or the whole - * response with its real return keeps 276 bytes and loses that register map. The retained best - * group is below with complete declarations and the existing four-word pointer interface; no - * dummy owner reference was used. Reopen with a real height-lifetime/label-alignment witness, not - * padding removal or invented volatility. Older measurements follow as history. - */ -#include "common.h" -typedef struct { char pad[0x18]; void *moby; int count; char gap[0x20]; float normal[4]; } ProbeResult; -extern ProbeResult D_L01_001BF900; -extern int func_002761F8(void *, void *, int, void *, int); -extern void func_00282F20(void *, void *, float); -extern void func_00282CF0(void *, void *, void *); -extern float func_00282DB0(void *, void *); -extern void func_00282CC0(void *, void *, void *); -/* - func_L01_0031B300 (272 bytes, 5 places) - default flags (-O2 -G0), in L01_002A7248.c; right size. - opus-1 (v2139, 2026-11-03), recompiled on v2/c04: 272/272 bytes, 0/5 places, 12 instruction rows differ - (20 counting relocation-only rows): only the saved-register roles of a0 and the global base g are exchanged - (retail a0 -> s2, g -> s3; ours g -> s2, a0 -> s3). Needs the file's ProbeResult/D_L01_001BF900, - func_002761F8, func_00282F20, func_00282CF0, func_00282DB0, func_00282CC0 declarations plus the two below. - Why (measured with tools/regalloc.py and the cc1 source): a0 is pseudo 84, 5 refs over 44 insns after sched1 - (priority 2*5/44 = 0.227); g is pseudo 90, 4 refs over 16 insns after sched1, but its constant-address - REG_EQUIV makes update_equiv_regs double that to 32 (local-alloc.c `REG_LIVE_LENGTH (regno) *= 2`), giving - 2*4/32 = 0.25, so g is allocated first and takes s2. Retail needs a0 > g: a sixth a0 reference, or g live over - at least 18 post-sched1 insns (sched1 puts `a2 = g + 0x20` before the a0/a1 moves of the VecSub call; after - them would be 18), or a0 under 40. - Tied or worse here: g initialised before CollLine (65 rows), struct-field access without g (260 bytes, base - split into %hi/%lo loads), typed `ProbeResult *hit` with direct `return 0` (same priorities), one combined - `p != 0 && (...)` test (same priorities), `w = *(Vector *)(g + 0x40)` instead of qcopy (g gets 6 refs). - Earlier: the permuter reaches 5/5 only with an identical-arm `if (a0)` around the 0xAA load (not allowed); - that is exactly the missing sixth a0 reference. - Reopen with a real construct that references a0 once more (and vanishes) or lengthens g's range. - */ -typedef int TI128 __attribute__((mode(TI))); -typedef union { TI128 q; float f[4]; } Vector; - -extern float func_00282C48(float f12); - -int func_L01_0031B300(void *a0, void *a1, void *a2, void *a3) { - Vector v, w; - float f20; - float f2; - char *g; - char *h; - char *p; - int v1; - - if (func_002761F8(a2, a3, 0x10, a0, 0) == 0) - goto fail; - g = (char *)&D_L01_001BF900; - p = *(char **)(g + 0x18); - if (p != 0) { - v1 = *(short *)(p + 0xAA); - if (v1 == 0x881 || v1 == 0) - return 0; - } - do { - f20 = *(float *)(a0 + 0x18); - } while (0); - qcopy(&w, g + 0x40); - h = g + 0x40; - func_00282F20(w.f, w.f, 1.0f); - func_00282CF0(&v, a3, g + 0x20); - f2 = func_00282C48(func_00282DB0(v.f, w.f)); - func_00282F20(w.f, (float *)h, f2); - func_00282CC0(a0 + 0x10, a0 + 0x10, &w); - *(float *)(a0 + 0x18) = f20; - return 1; -fail: - return 0; -} diff --git a/nonmatching/levels/func_L01_00324550.c b/nonmatching/levels/func_L01_00324550.c deleted file mode 100644 index 77d71663f..000000000 --- a/nonmatching/levels/func_L01_00324550.c +++ /dev/null @@ -1,57 +0,0 @@ -/* opus-1 (v2139, 2026-11-03): FAILED, 132/132 bytes, 0/11 places with -mastra-quad-saves (frame 0x2A0 and the - * varargs spill area exact; 5 save/restore instructions differ), default profile 0x290 frame with sd/ld s0. - * Why s0 is `sq` but ra `sd`: the EE cc1 (stock 2.9-ee mips.c) keeps a per-register save mode, mips_reg_mode[], - * set once in override_options and only widened by mips_check_reg_mode() when an insn sets that GPR in a wider - * mode; it is never reset between functions. So a function compiled EARLIER in the same original unit that set - * $s0 in TImode makes every later function in that unit save $s0 with sq, while $ra stays DImode (sd). - * Measured on this checkout's cc1 with a scratch unit (a TImode value held in $s0 across a call, then this body): - * the default profile then emits `sq $16,512($sp)` / `sd $31,520($sp)` on a 0x290 frame, i.e. the mixed widths - * but 8-byte slot spacing (the sq overlaps ra's slot). Retail uses 16-byte slots with $ra at 0x200 below $s0 at - * 0x210 (0x2A0 frame); -mastra-quad-saves gives the 0x2A0 frame but $s0 at 0x200 and $ra as sq at 0x210. - * Needed: compiler support for 16-byte slots with per-register widths in retail's order (tools change), plus - * the earlier TImode $s0 user of the same unit. Not handwritten: the shape is the compiler's own. - */ - -/* Current retained result, 28 October 2026: 132/132 bytes with game -mastra-quad-saves, but - * mixed s0/ra save widths and order differ. The SDK profile emits 116/132 and lacks FP spills. - * The real variadic forwarding body is retained without fabricated frame padding. No strict - * match. Older diagnostic notes below are historical and do not rule out C. */ - -/* Retained readable C; not matching and no exact-C credit. - * 2026-10-28 bounded retry: Game profile -O2 -G0 -ffunction-sections -mastra-quad-saves: 132/132 bytes, exact varargs forwarding/body but both s0 and ra save width/order differ from retail mixed saves. SDK profile: 116/132 and missing FP argument spills. The register-save area is reached with the existing builtin-next-arg convention; no fabricated frame padding was used. - * Reopen with an independently measured save-profile or allocation witness. - * No strict linked-build claim. Historical screen-only notes follow the source. - */ -#include "common.h" -extern int func_00288FB8(int); -extern void func_L01_00324410(char *, int, void *); -extern void func_0028BCA0(int); -extern void func_0026FEB8(const char *, ...); -extern const char D_001AA590[]; -void func_L01_00324550(int id, ...) -{ - char text[0x200]; - int format = func_00288FB8(id); - if (format) { - /* Retail forwards the seven saved integer argument slots. */ - func_L01_00324410(text, format, (char *)__builtin_next_arg(id) - 0x38); - func_0028BCA0((int)text); - } else func_0026FEB8(D_001AA590, id); -} - -/* func_L01_00324550 (132 bytes, 11 places) - diagnosis only, no C measured this wave. - * - * The body is ordinary: v0 = func_2E99D0(a0); when v0 is nonzero it runs - * func_324410(sp, v0, sp+0x268) then func_2ECB20(sp), otherwise func_2A6CF0(0x001AA590, a0). - * What blocks it is the prologue. Before that first call retail has already stored - * $a1-$a3 and $t0-$t3 to 0x268..0x298($sp) and $f12/$f14/$f16/$f18 to 0x258..0x264($sp) - * on a 0x2A0 frame - the variadic register-save area - and it holds $s0 in a 128-bit slot - * at 0x210($sp) with `sq $s0,0x210($sp)` (0x7FB00210), reading it back with - * `lq $s0,0x210($sp)` (0x7BB00210) in the delay slot of the branch at 0x003245AC and - * storing it again at 0x003245C4. $s0 is an ordinary 64-bit value (`daddu $s0,$a0,$zero` - * in the first delay slot), so the quad slot is the prologue's own register-save shape and - * not a 128-bit object. - * Missing: a C spelling for that variadic prologue (the natural `...` + va_start route was - * not measured here, and the saved-integer area is passed on to func_324410, so the two - * are the same mechanism). ASM_FUNC candidate until a lever appears. - */ diff --git a/nonmatching/levels/func_L01_003D6B00.c b/nonmatching/levels/func_L01_003D6B00.c deleted file mode 100644 index ce0fe4ddd..000000000 --- a/nonmatching/levels/func_L01_003D6B00.c +++ /dev/null @@ -1,43 +0,0 @@ -/* 4 November 2026: independent loop-count capture after the positive guard - * restores its incoming-register test, but hoists the object-position pointer: - * 408/396 bytes. A meaningful vector-add group reduces this to 404, still - * 0/2 USA placements with a different register map. The bank-preserving typed - * emitter interface retains seven integer and four floating arguments. - * Keep the existing 396-byte source below; neither trial is a linked match. - */ -/* Nonmatching C reconstruction. - * Profile: -O2 -G0 -ffunction-sections -frac2-zero-ti-por. - * Compiled 396 bytes; retail 396 bytes. - * Carrying checks: 0/2 in us, pal and us2. No strict linked qualification. - * Right size; the loop body agrees substantially, but the count save/guard prologue and emitter argument schedule differ. A separate decrement-at-start loop grew to 408 bytes; disabling rerun-loop-opt gave 392 with an extra saved pointer and different constant motion; G8 did not fix it. Reopen with a genuine counter lifetime hypothesis. - */ -#include "common.h" -typedef union { int whole __attribute__((mode(TI))); float f[4]; } EffectVector; -extern float func_002A7878(float, float); -extern float func_00283180(float); -extern float func_00283198(float); -extern void func_00282F20(void *, void *, float); -extern void func_00282CC0(void *, void *, void *); -extern void func_L00_003263D0(void *, void *, int, int, void *, unsigned int, void *, float, float, float, float); - -void func_L01_003D6B00(char *object, int count, float low, float high, float radius, float speed) -{ - EffectVector position, velocity; - float angle; - position.whole = 0; - velocity.whole = 0; - if (count > 0) { - do { - angle = func_002A7878(-3.1415927410125732f, 3.1415927410125732f); - position.f[0] = radius * func_00283180(angle); - position.f[1] = radius * func_00283198(angle); - position.f[2] = func_002A7878(0.0f, 1.0f); - func_00282F20(&velocity, &position, func_002A7878(speed * 0.75f, speed * 1.25f)); - position.f[2] = func_002A7878(low, high); - func_00282CC0(&position, object + 0x10, &position); - func_L00_003263D0(object, &position, 1, 1, &velocity, 0x50808040, 0, - 0.0f, 0.0f, 1.0f, 5.5f); - count--; - } while (count != 0); - } -} diff --git a/nonmatching/levels/func_L03_003C1BF0.c b/nonmatching/levels/func_L03_003C1BF0.c deleted file mode 100644 index 6aff52d1e..000000000 --- a/nonmatching/levels/func_L03_003C1BF0.c +++ /dev/null @@ -1,550 +0,0 @@ -/* Claude Opus 5.5 xhigh, task v2114 (2026-11-03): closer near miss; supersedes v1626 below. - * -O2 -G8 -ffunction-sections -frac2-hazard-labels: 5680/5680 bytes, 0 of 2 places (L03/L14). - * Four instruction positions differ apart from relocations: +0x1358..+0x1364, where cc1 - * emits li.s 0.8 (lui/ori/mtc1) before li v0,0x940 and retail reverses them. - * What changed from v1626: - * - State 22 stores both z components in BOTH real switch arms (0x940 and default), - * other.f[2] first in source. jump2 cross-jumps the identical tails after sched2, - * which gives retail's join block (fixes +0x139C..+0x13A8) and point-then-other order. - * - offset = &other after the switch; PRE sets its copy at the end of the dispatch block. - * Remaining tie: sched1 orders lh (birthing), fp, &other, li.s, li 0x940; li.s wins on - * luid. If the switch index is a twice-set local (type, also used in state 1), the lh - * stops being a birthing insn: fp, &other, lh, li 0x940, li.s fixes this, but then - * &other's global priority (8/107) falls just below the 0xF2D loop constant's (3/40), - * so s6/s7 swap (6 positions). Reopen with a way to order li 0x940 before li.s under a - * single-set index, or to cut one RTL insn from &other's range (PRE no-op copies). - * All required declarations are included below. - */ -/* GPT-6.1 Sol high, task v1626 (2026-10-29): retained improved near miss. - * Current toolchain, -O2 -G8 -ffunction-sections -frac2-hazard-labels: - * 5680/5680 bytes; check.py: 0 of 2 USA v1.01 places match (L03/L14), - * first difference +0x1358. Eight instruction positions differ, excluding - * relocation address immediates; this is not a linked match. - * - * Improvements over the historical drafts below: - * - MotionInit's measured fields at +0x134/+0x144, with acceleration assigned - * first, reproduce both initial FPR choices AND retail's load/store order. - * - State 22 uses qzero_nc for both independent, aligned local vectors. The - * second bare clear invalidates CSE's address value, so the second vector's - * address is rebuilt after its clear, as in retail. No surrounding accesses - * depend on either cleared local's old contents. - * - A scoped pointer to other, initialized AFTER other.f[2] = height, keeps - * &other in s6; inline object+0xC0 expressions spill the matrix pointer to - * sp+0x30 and the rotation pointer to sp+0x34, matching retail allocation. - * - Reversing the two final zero assignments reproduces their retail schedule. - * - * Remaining state-22 differences: - * +0x1358..+0x1364: cc1 emits li.s 0.8 before li v0,0x940; retail reverses - * those independent constant preparations. - * +0x139C..+0x13A8: cc1 emits matrix-address add, other.z store, spill store, - * point argument; retail emits other.z store, matrix add, point argument, spill. - * Everything else aligns in check.py's side-by-side disassembly apart from - * unresolved address immediates. Relocation consistency and linked placement - * remain unqualified because the text differs. PAL/US2 and linking not run. - * - * New negative measurements: inline matrix alone was 5668 bytes; an explicit - * vector pointer introduced before its clear disturbed position allocation. - * Initializing that pointer before the class switch uses s7 instead of s6. - * Per-arm height initialization changes switch flow; loading the class into a - * local, a measured class struct field, and named vector component fields each - * tie this retained version. Stopped after 11 source candidates at this tie; - * reopen with a new scheduling hypothesis, not equivalent type spellings. - * All required declarations are included below. Older notes are dated history - * and their residual-difference descriptions are superseded by this block. - */ -#define MACRO_ADDR __attribute__((section(".sdata"))) -/* Finisher F1 (2026-10-26, base f5fab978 with qzero_nc): 1391 of 1420 instructions aligned with - * registers (was 1363 on this head). What moved it: - * - qzero_nc(&point) in state 22 (qzero(&other) keeps the clobber); - * - the hero distance in state 4 through the union view (HERO->f[0x80 / 4], [0x84 / 4]): - * retail addresses D_00189E20 with 0x80/0x84 offsets, not D_00189EA0; - * - cases 19 and 20 read SP(0x358) inline instead of through `target` (its pointer then - * takes $v0 as in retail); - * - state 22's class switch has `case 0x93C:` with the default (0x93C is a class id from - * state 1). A case below 0x940 that goes to the default gives retail's `slti 0x941` test: - * emit_case_nodes only emits the bound test when the root's other child is not a single - * value, and jump deletes the dead 0x93C compare; - * - other.f[2] = height (no reload of point.f[2]); - * - in the member loop the index store comes first (its D_L03_001B2A1C load is then in the - * beqz slot as retail, before the two -1 stores). - * Left: state 0's two float temps (D_L03_001AFEE0 in $f1, 0.0016666667f in $f0 in retail: - * local-alloc tie, swapping the two statements breaks cross-jumping), and state 22's - * allocation: retail keeps &other in $s6 and spills object+0xC0 (sp+0x30) and object+0xF0 - * (sp+0x34); here $s6 is object+0xC0 and the slots are swapped. - * F3 (2026-10-26): same 1391/1420 on 795143e6. State 1's pair after sched1 (lreg): insn 67 - * reg111 = D_L03_001AFEE0, insn 71 reg112 = 0.0016666667f, stores 0x144 (111) then 0x134 - * (112). Both lives are 2 (equal priority), so qty order (birth) gives 111 $f0. Retail needs - * 112 to rank first while sched2 still emits the load first and the 0x144 store first. Tried, - * no change: locals for either value in any order, a comma expression, MACRO_ADDR or an sda - * array for D_L03_001AFEE0. Swapping the stores gives retail's registers but the li.s first. - */ -/* Opus handoff (big8, 2026-10-26): func_L03_003C1BF0, 5680 bytes, 2 places - * (L03 0x003C1BF0, L14 0x003C5250). Built on the earlier corrected draft (5552 bytes, - * 0.66 aligned). Step 0: one function. Two jump tables: jtbl_L03_002A8F40 (9 entries, - * byte +0x95, case 0 explicit) and jtbl_L03_002A8F70 (22 entries, byte +0x20 minus 1). - * Profile: -O2 -G8 -ffunction-sections -frac2-hazard-labels (the label on the hazard nop - * in state 22). Measured in src/levels/shared/L03_003C1BF0.c: 5680 bytes (size equal), - * 1397/1420 opcodes aligned, 1366 with registers; every state but 22 is aligned. - * What moved it from 936 to 1394 aligned: - * - state bodies in retail address order: 1, 2, 4, 3, 5, 6/8, 7, 12, 13, 9, 10, 11, 14, - * 15, 16, 17, 18, 19, 20, 21, 22; states 14, 18 and 20 written out per arm (retail has - * three bodies and cross-jumps their func_002A7750 tails); - * - state 1 is a switch on the moby class (0x940, 0x93C, 0xA59, 0x964/default) and calls - * func_002B38B8 on pvars+0x354; - * - then-arm first where retail falls through (states 4, 10, 11, 15); - * - hero fields through the union view (0x26C, 0x270, +0x80 as base+offset), but - * D_00189E20 + 0x80 as a plain symbol address for func_00282E80 and the 419BD8 test; - * - u16 incomplete arrays for D_0018CB20/38/2C, D_0018CDCC/E4, D_0018CF58 (lui+lhu/sh), - * D_0018CB4C[] and D_L03_001BFDD8[]; (int)object >> 8 (sra); u32 dispatch; - * - MACRO_ADDR for D_L03_001B2548, _1B2A1C, _1B2A20: retail reads them absolutely in - * flow and $gp-relative in delay slots; - * - pvars+0x358 re-read in state 15; state 15's sign test reads back +0x344 after - * zeroing it; the final float clears through a local zero. - * State 22's class switch: 0.8f first, case 0x964 setting 0.3f and falling into case 0x940's - * store, default storing separately (this gave the retail size). - * Still off, all in state 22: retail's tree also tests <0x941 before 0x964 (GCC emits that - * only when the right child is not a single value: a third case or range is missing), - * object+0x10 kept in $fp, object+0xC0 / object+0xF0 spilled to sp+0x30/0x34, -1 and 0xF2D hoisted into s5/s7 for the member loop. - */ -#include "common.h" -typedef struct { - u8 reserved00[0x134]; float acceleration; - u8 reserved138[12]; float max_speed; -} MotionInit; -typedef int Quad __attribute__((mode(TI))); -typedef union { Quad q; float f[4]; } MotionVector; -typedef struct { - u8 reserved00[0x18]; u8 enabled, count, kind; u8 reserved1B[0x65]; u8 payload[1]; -} DispatchContext; -extern float D_00189EA0[], D_00189F00[]; -extern u8 D_00189E20[]; -typedef union { u8 b[0x2600]; u8 *ptr[0x980]; float f[0x980]; } Hero; -#define HERO ((Hero *)D_00189E20) -extern u16 D_0018CB20[], D_0018CB38[], D_0018CDCC[]; -extern u16 D_0018CB2C[], D_0018CF58[], D_0018CDE4[]; -extern int D_0018CB4C[]; -extern int D_L03_001B2548 MACRO_ADDR; -extern u8 *D_L03_001B2A1C MACRO_ADDR; -extern u8 *D_L03_001B2A20 MACRO_ADDR; -extern u8 *D_L03_001BFDD8[]; -extern float D_L03_001AFEE0 __attribute__((sda)); -extern float D_L03_001AFEE4 __attribute__((sda)); -extern float D_L03_001AFEE8 __attribute__((sda)); -extern float D_L03_001AFEEC __attribute__((sda)); -extern float D_L03_001AFEF0 __attribute__((sda)); -extern float D_L03_001AFEF4 __attribute__((sda)); -extern void func_L03_003C3220(u8 *); -extern int func_002B3890(u8 *); -extern int func_002B3868(u8 *); -extern int func_002B38B8(u8 *); -extern void func_002B60B0(u8 *, float, float, float, float); -extern u32 func_002B1C20(void *, DispatchContext *); -extern void func_002A7750(u8 *, s32, s32); -extern int func_00288E18(int, int); -extern int func_002A77E0(int); -extern void func_002A7470(u8 *, int, int, int); -extern void func_L03_003C4368(u8 *, void *); -extern void func_L03_003C4240(u8 *); -extern void func_L03_003C4BD8(u8 *); -extern void func_L03_003C4A10(u8 *, void *); -extern float func_00282E80(void *, void *); -extern int func_L03_00419BD8(u32, void *, void *); -extern float func_002AA340(int *, int, int); -extern int func_L03_003C41B8(u8 *, int, int); -extern int func_L03_003C58F0(u8 *, float *); -extern float func_00283180(float), func_00283198(float), func_00283248(float, float); -extern float func_00283B98(float, float), func_00283BE0(float, float); -extern void func_00282CC0(void *, void *, void *), func_00282CF0(void *, void *, void *); -extern void func_00282F20(void *, void *, float), func_00283098(void *, void *, void *); -extern int func_L01_00322288(int, float); -extern int func_00282948(void *); -extern int func_L03_003C5DC8(u8 *, u8 *); -extern u32 func_L03_004197A8(u8 *); -extern void func_L03_00419818(u8 *, u32); -extern void func_002AFDD8(char *, char *, char *, char *); -extern void func_0029F338(void *); -extern u8 *func_L03_003C4D40(u8 *); -extern void func_L03_003C5B28(u8 *, float); -extern int func_002761F8(void *, void *, int, void *, void *); -extern int func_002AEB60(char *, float); -extern int func_002A8D70(float, float, float, void *, int, int, int, int, int); -extern float func_0029F530(char *); -extern float func_L02_00321C30(void *, void *, float); -extern void func_L03_00419A60(u32, u8 *, s32); -extern int func_L03_003C5CE8(u8 *); -extern u32 func_L03_003CAAC8(u8 *, u8 *); -extern void func_L03_003C5EE8(void *); -extern void func_002AC9F8(float *, float); -extern void func_0029FCC0(char *, int, char *); -extern void func_L03_003CA220(u8 *, float), func_L00_003294F0(u8 *, int); -extern float func_002AA548(void *, void *, float, float, float, float); -extern float func_002A89A8(u8 *, int, float); -extern int func_L03_00419C00(void *, void *, void *); -extern void func_002833F0(void *, void *); -extern void func_002B5258(char *), func_L03_003C4468(u8 *), func_002A677C(u8 *); -#define SF(o) (*(float *)(state + (o))) -#define SI(o) (*(int *)(state + (o))) -#define SP(o) (*(u8 **)(state + (o))) -#define OF(o) (*(float *)(object + (o))) -#define ANIM_FRAMES(off) (*(u8 *)(*(u8 **)(*(u8 **)(object + 0x24) + (off)) + 0x10)) - - -void func_L03_003C1BF0(u8 *object) -{ - MotionVector point, other, delta; - u8 *state = *(u8 **)(object + 0x68); - u8 *target, *parent, *member, *pos, *mtx, *rot; - u32 dispatch; - int type, code, i, entered; - float heading, turn, distance, floor, height; - func_L03_003C3220(object); - switch (object[0x95]) { - case 0: - break; - case 1: - if (func_002B3890(object)) { - func_002B60B0(object, D_L03_001AFEF0 * 0.00027777778f, D_L03_001AFEF4 * 0.016666668f, - 0.0034906589426100254f, 0.10471977293491364f); - ((MotionInit *)state)->acceleration = 0.0016666667f; - ((MotionInit *)state)->max_speed = D_L03_001AFEE0; - } - break; - case 2: - if (func_002B3890(object)) { - func_002B60B0(object, D_L03_001AFEE8 * 0.00027777778f, D_L03_001AFEEC * 0.016666668f, - 0.006981317885220051f, 0.20943954586982727f); - SF(0x144) = 0.0f; SF(0x134) = 0.0055555557f; - } - break; - case 3: - if (func_002B3890(object)) { - func_002B60B0(object, D_L03_001AFEF0 * 0.00027777778f, D_L03_001AFEF4 * 0.016666668f, - 0.006981317885220051f, 0.20943954586982727f); - SF(0x134) = 0.0055555557f; SF(0x144) = 0.1f; - } - break; - case 4: - func_002B60B0(object, D_L03_001AFEF0 * 0.00027777778f, D_L03_001AFEF4 * 0.016666668f, - 0.0034906589426100254f, 0.10471977293491364f); - SF(0x134) = 0.0016666667f; SF(0x144) = 0.4f; - break; - case 5: - func_002B60B0(object, D_L03_001AFEF0 * 0.00027777778f, D_L03_001AFEF4 * 0.016666668f, - 0.0034906589426100254f, 0.10471977293491364f); - SF(0x134) = 0.0016666667f; SF(0x144) = 0.05f; - break; - case 6: - func_002B60B0(object, D_L03_001AFEF0 * 0.00027777778f, D_L03_001AFEF4 * 0.016666668f, - 0.006981317885220051f, 0.20943954586982727f); - SF(0x134) = 0.005f; SF(0x144) = 0.05f; - break; - case 8: - dispatch = func_002B1C20(object, (DispatchContext *)(state + 0x60)); - if (dispatch & 1) { func_0029F338(object); return; } - if (dispatch & 2) func_002A7750(object, 2, 0); - break; - } - { - switch (object[0x20]) { - case 1: - if (func_002B38B8(SP(0x354))) { - type = *(s16 *)(object + 0xAA); - switch (type) { - case 0x940: - if (D_0018CB20[0] == 0) func_00288E18(0x9CF, 0x26); - break; - case 0x93C: - if (D_0018CB38[0] == 0) func_00288E18(0x9D1, 0x28); - break; - case 0xA59: - if (D_0018CDCC[0] == 0) func_00288E18(0xA08, 0x5F); - break; - case 0x964: - default: - if (D_0018CB4C[0] >= 0) func_00288E18(0x9D2, 0x29); - break; - } - func_002A7750(object, 4, 1); - } - break; - case 2: - if (HERO->ptr[0x270 / 4] == object || HERO->ptr[0x26C / 4] == object) - func_L03_003C4368(object, &HERO->b[0x80]); - func_L03_003C4240(object); - if (object[0x31]) func_L03_003C4BD8(object); - break; - case 4: - if (func_002B3868(object)) { - if (object[0x43]) func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 15); - SI(0x380) = 2; qzero(state + 0x1B0); - } - if (HERO->ptr[0x270 / 4] == object || HERO->ptr[0x26C / 4] == object) - func_L03_003C4368(object, &HERO->b[0x80]); - func_L03_003C4240(object); - distance = func_00282E80(object + 0x10, D_00189E20 + 0x80); - if (D_L03_001AFEE4 < distance && func_L03_00419BD8((u32)SI(0x220), object + 0x10, D_00189E20 + 0x80)) { - func_002A7750(object, 3, -1); - if (object[0x43] != 2) func_002A7470(object, 2, func_002A77E0(ANIM_FRAMES(0x50)), 10); - } else { - if (object[0x31] && object[0x42] != 1) { - if (SI(0x380) < 5) func_L03_003C4A10(object, D_00189F00); - else func_L03_003C4BD8(object); - } - } - if ((object[0x60] & 2) && object[0x42] == object[0x43]) { - if (object[0x42] == 1) - func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 15); - else if (!func_002A77E0(SI(0x380))) { - func_002AA340((int *)(state + 0x380), 10, 1); - if (object[0x43] != 1) func_002A7470(object, 1, 0, 15); - } - } - break; - case 3: - if (!func_L03_003C41B8(object, (int)D_00189EA0, 1) || SF(0x1DC) < D_L03_001AFEE0 || - (SI(0x190) > 60 && SF(0x1DC) < D_L03_001AFEE4)) { - func_002A7750(object, 4, -1); - if (object[0x43]) func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 10); - } - if ((D_L03_001B2548 & 15) == (((int)object >> 8) & 15)) - SI(0x360) = func_L03_003C58F0(object, D_00189EA0); - break; - case 5: - if (func_002B3868(object)) { - if (object[0x43] != 2) func_002A7470(object, 2, func_002A77E0(ANIM_FRAMES(0x50)), 20); - SF(0x144) = 0.1f; - } - point.f[0] = func_00283180(SF(0x374)); point.f[1] = func_00283198(SF(0x374)); point.f[2] = 0; - func_00282CC0(&point, &point, object + 0x10); - func_L03_003C41B8(object, (int)&point, 1); - if (*(u16 *)(object + 0x96) >= 61) { - SF(0x144) = D_L03_001AFEE0; - func_002A7750(object, 4, 1); - if (object[0x43]) func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 10); - } - break; - case 6: - case 8: - if (func_002B3868(object)) { - if (object[0x20] == 8) { if (object[0x43] != 7) func_002A7470(object, 7, 0, 20); } - else if (object[0x43] != 3) func_002A7470(object, 3, 0, 20); - } - func_L01_00322288((int)object, func_00283248(HERO->f[0x80 / 4] - OF(0x10), HERO->f[0x84 / 4] - OF(0x14))); - if (object[0x60] & 2) func_002A7750(object, 4, -1); - break; - - case 7: - if (func_002B3868(object)) SF(0x144) = 0.1f; - if (func_00282E80(object + 0x10, state + 0x340) > SF(0x144)) { - func_L03_003C41B8(object, (int)(state + 0x340), 0); - if (object[0x43] != 2) func_002A7470(object, 2, func_002A77E0(ANIM_FRAMES(0x50)), 20); - } else if (object[0x43]) func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 20); - if (func_00282948(state + 0x37C)) func_002A7750(object, 4, -1); - break; - case 12: - func_L03_003C41B8(object, (int)(state + 0x340), 0); - if ((D_L03_001B2548 & 3) == (((int)object >> 8) & 3)) - SF(0x110) = func_L03_003C5DC8(object, state + 0x340) ? 0.11f : 0.15f; - if (!func_L03_004197A8(SP(0x358))) { - func_002A7750(object, 4, 1); - if (object[0x43]) func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 10); - } else if (SF(0x1DC) < SF(0x144)) func_002A7750(object, 13, -1); - break; - case 13: - if (func_002B3868(object)) { - func_L03_00419818(SP(0x358), (u32)object); SF(0x140) = 0.174532949924469f; - func_002AFDD8((char *)SP(0x358), (char *)(state + 0x1B0), (char *)(state + 0x1B0), 0); - SF(0x1B4) = 0; - func_00283098(state + 0x1B0, state + 0x1B0, SP(0x358) + 0xC0); SF(0x110) = 0; - } - func_L03_003C41B8(object, (int)(SP(0x358) + 0x10), 0); - if (func_00282E80(object + 0x10, SP(0x358) + 0x10) < 0.1f) { func_0029F338(object); return; } - break; - case 9: - if ((D_L03_001B2548 & 7) == (((int)object >> 8) & 7)) SP(0x358) = func_L03_003C4D40(object); - parent = SP(0x194); - if (parent) { - if (SP(0x198) && *(s16 *)(SP(0x198) + 0xAA) == 0x97A) heading = OF(0xF8); - else { - heading = func_00283248(*(float *)(parent + 0x10) - OF(0x10), *(float *)(parent + 0x14) - OF(0x14)); - turn = func_00283BE0(heading, OF(0xF8)); - heading = func_00283B98(turn < 0.0f ? -1.5707963705062866f : 1.5707963705062866f, OF(0xF8)); - } - func_L03_003C5B28(object, heading); - } - target = SP(0x358); - if (!target) { - func_002A7750(object, 11, -1); - if (object[0x43]) func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 20); - break; - } - func_L03_003C41B8(object, (int)(target + 0x10), 0); - if ((D_L03_001B2548 & 3) == (((int)object >> 8) & 3)) { - qcopy(&point, object + 0x10); point.f[2] += 0.2f; - func_00282F20(&other, object + 0xC0, 0.3330000042915344f); - func_00282CC0(&other, &other, object + 0x10); other.f[2] += 0.2f; - if (func_002761F8(&point, &other, 0, object, 0) && D_L03_001BFDD8[0] == SP(0x358)) { - func_002A7750(object, 10, -1); - if (object[0x43] != 4) func_002A7470(object, 4, 0, 10); - } - } - break; - case 10: - if (func_002AEB60((char *)object, 14.0f)) - func_002A8D70(0.3330000042915344f, 4.0f, 1.0f, object, 1, 0x10000, 0, 1, 0); - else if (object[0x60] & 2) { - SP(0x358) = func_L03_003C4D40(object); - if (SP(0x358)) { - func_002A7750(object, 9, -1); - if (object[0x43] != 3) func_002A7470(object, 3, func_002A77E0(ANIM_FRAMES(0x54)), 10); - } else { - func_002A7750(object, 11, -1); - if (object[0x43]) func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 10); - } - } - break; - case 11: - if ((D_L03_001B2548 & 7) == (((int)object >> 8) & 7)) SP(0x358) = func_L03_003C4D40(object); - func_L03_003C4BD8(object); - if (SP(0x358)) { - func_002A7750(object, 9, -1); - if (object[0x43] != 3) func_002A7470(object, 3, func_002A77E0(ANIM_FRAMES(0x54)), 20); - } else if (*(u16 *)(object + 0x96) >= 301) { - func_002A7750(object, 4, 1); - if (object[0x43]) func_002A7470(object, 0, func_002A77E0(ANIM_FRAMES(0x48)), 20); - } - break; - case 14: - func_L03_003C41B8(object, (int)(state + 0x340), 0); - if (func_002B3868(object)) D_0018CB2C[0] = -1; - if (SP(0x194)) func_L03_003C5B28(object, func_00283B98(OF(0xF8), 3.141592741012573f)); - if (SI(0x1A4) & 0x80) func_002A7750(object, 15, -1); - break; - case 15: - if (func_002B3868(object)) { - if (object[0x43] != 4) func_002A7470(object, 4, 0, 10); - *(int *)(object + 0x98) = 0; - func_00282CF0(state + 0x340, state + 0x340, SP(0x358) + 0x10); - func_002AFDD8((char *)SP(0x358), (char *)(state + 0x340), (char *)(state + 0x340), 0); - SF(0x344) = 0; - if (SF(0x340) < SF(0x344)) SF(0x340) = -3.8f; - else SF(0x340) = 3.8f; - func_00283098(state + 0x340, state + 0x340, SP(0x358) + 0xC0); - func_00282CC0(state + 0x340, state + 0x340, SP(0x358) + 0x10); - } - heading = func_00283248(*(float *)(SP(0x358) + 0x10) - OF(0x10), *(float *)(SP(0x358) + 0x14) - OF(0x14)); - func_L01_00322288((int)object, heading); - if (func_0029F530((char *)object) > 11.0f) func_L02_00321C30(object + 0x10, state + 0x340, 0.13333334f); - if (object[0x60] & 2) { - func_L03_00419A60(SI(0x220), SP(0x358) + 0x10, 1); - func_002A7750(object, 16, -1); - if (object[0x43] != 5) func_002A7470(object, 5, 0, 5); - func_L00_003294F0(SP(0x358), 1); - } - break; - case 16: - if (func_002B3868(object)) SP(0x198) = 0; - if (func_00282E80(D_00189EA0, SP(0x358) + 0x10) > 12.0f && - !func_L03_003C5CE8(object) && !func_L03_003CAAC8(SP(0x358), D_00189EA0)) - func_L03_003C5EE8(object); - break; - case 17: - func_00282CF0(&point, state + 0x340, object + 0x10); - func_002AC9F8(point.f, 0.4166666865348816f); - func_00282CC0(object + 0x10, object + 0x10, &point); - if (object[0x42] == object[0x43]) { - qcopy(object + 0x10, state + 0x340); - func_002A7750(object, 6, 1); - } - break; - case 18: - func_L03_003C41B8(object, (int)(state + 0x340), 0); - if (SP(0x194)) func_L03_003C5B28(object, func_00283B98(OF(0xF8), 3.141592741012573f)); - if (SI(0x1A4) & 0x80) { - func_002A7750(object, 19, -1); - func_L00_003294F0(SP(0x358), 1); - } - break; - case 19: - if (func_002B3868(object) && object[0x43] != 4) func_002A7470(object, 4, 0, 10); - func_L01_00322288((int)object, func_00283248(*(float *)(SP(0x358) + 0x10) - OF(0x10), *(float *)(SP(0x358) + 0x14) - OF(0x14))); - if (object[0x42] == object[0x43]) { - if (func_0029F530((char *)object) >= 10.0f) { - func_0029FCC0((char *)object, 3, (char *)&point); - func_L03_003CA220(SP(0x358), point.f[2] - OF(0x18)); - } - if (object[0x60] & 2) { - func_002A7750(object, 6, 1); func_L00_003294F0(SP(0x358), 0); - } - } - D_0018CF58[0] = -1; - break; - case 20: - func_L03_003C41B8(object, (int)(state + 0x340), 0); - if (SP(0x194)) func_L03_003C5B28(object, func_00283B98(OF(0xF8), 3.141592741012573f)); - if (SI(0x1A4) & 0x80) func_002A7750(object, 21, -1); - break; - case 21: - if (func_002B3868(object)) { - if (object[0x43] != 5) func_002A7470(object, 5, 0, 10); - D_0018CDE4[0] = -1; - } - func_L01_00322288((int)object, func_00283248(*(float *)(SP(0x358) + 0x10) - OF(0x10), *(float *)(SP(0x358) + 0x14) - OF(0x14))); - if (object[0x60] & 2) func_002A7750(object, 6, 1); - else if (func_002AEB60((char *)object, 20.0f)) func_L00_003294F0(SP(0x358), 1); - break; - case 22: { - MotionVector *offset; - func_00282CC0(object + 0x10, object + 0x10, state + 0x1B0); - qzero_nc(&point); qzero_nc(&other); - height = 0.8f; - switch (*(s16 *)(object + 0xAA)) { - case 0x964: - height = 0.3f; - case 0x940: - other.f[2] = height; - point.f[2] = height; - break; - case 0x93C: - default: - other.f[2] = height; - point.f[2] = height; - break; - } - offset = &other; - func_00283098(&point, &point, object + 0xC0); - if (SF(0x1B8) < 0.0f) { - SF(0x1B8) -= SF(0x398); - if (OF(0xF4) > 0.0f) func_002AA548(object + 0xF4, state + 0x39C, 0, 0.006981317885220051f, 0.006981317885220051f, 0.41887909173965454f); - else OF(0xF4) = func_00283BE0(OF(0xF4), 0.41887909173965454f); - if (OF(0x18) < SF(0x3A0)) { - floor = func_002A89A8(object + 0x10, 0, 0.5f); - if (OF(0x18) <= floor) { - OF(0x18) = floor; func_002A7750(object, 4, 1); - for (member = D_L03_001B2A1C; member <= D_L03_001B2A20; member += 256) { - if (*(s16 *)(member + 0xAA) == 0xF2D && func_L03_00419C00(member, object + 0x10, object + 0x10)) { - SI(0x220) = ((int)member - (int)D_L03_001B2A1C) >> 8; - SI(0x368) = -1; SI(0x36C) = -1; - } - } - } - } - } else { - SF(0x1B8) -= SF(0x394); OF(0xF4) = func_00283BE0(OF(0xF4), 0.41887909173965454f); - } - func_002833F0(object + 0xC0, object + 0xF0); - func_00283098(offset, offset, object + 0xC0); - func_00282CF0(&delta, &point, offset); - func_00282CC0(object + 0x10, object + 0x10, &delta); - break; - } - } - } - code = object[0x20]; - if (code != 22 && code != 1 && code != 15 && code != 16 && (SF(0x1A0) < OF(0x18) - 0.05f || SP(0x198))) { - float zero = 0.0f; - OF(0xF0) = zero; OF(0xF4) = zero; func_002B5258((char *)object); - } - func_L03_003C4468(object); - func_002A677C(object); -} diff --git a/nonmatching/levels/func_L08_00389B68.c b/nonmatching/levels/func_L08_00389B68.c deleted file mode 100644 index ca65d3eef..000000000 --- a/nonmatching/levels/func_L08_00389B68.c +++ /dev/null @@ -1,53 +0,0 @@ -/* Opus-1 v0735, 29 October 2026: recompiled with this cc1 (scratch, both - * profiles): unchanged, 264 bytes; with -mastra-quad-saves only the four - * save/restore words differ (last check.py record: 264/264, 0/4 places). - * New evidence: a scan of every catalogue function's prologue in the boot - * and all 27 levels finds only three frames that mix `sq` and `sd` GPR saves: - * this one, func_L01_00324550 (also a stdarg function; `sq $s0,0x210`, - * `sd $ra,0x200`) and func_L02_00411D18 (`sq $s2` in its own 16-byte slot - * below the 8-byte ones). The two stdarg frames share the shape seen here: - * 16-byte slots, `ra` with `sd` at the lower slot, `s0` (the copy of the - * named count) with `sq` above it. This cc1 has no profile for it: the default - * keeps 8-byte slots (and saves a TImode-holding callee register with `sq` - * into an 8-byte slot, overlapping its neighbour), and -mastra-quad-saves - * widens `ra` too and puts it in the upper slot. The SDK compiler gives a - * different body. va_start yields sp+160 under this cc1, not - * retail's sp+0x68, so the explicit __builtin_next_arg - 0x38 stays. - * Needs a measured compiler model of the stdarg save layout. - */ -/* Sol high v0505, 28 October 2026: rechecked both profiles. Default gives - * 264/264 bytes but a 0x90 frame instead of 0xA0, 0/4 places. Dedicated - * -O2 -G0 -ffunction-sections -mastra-quad-saves reproduces the body and frame, - * leaving the same four save/restore instructions described below. No C - * body operations require the observed mixed-width GPR save convention; - * neither available profile supplies it. Compiler/tool changes are out of scope. - */ -/* Sol low, v0290, 2026-10-28: 264/264 bytes, 0/4 places. - * Profile: -O2 -G0 -ffunction-sections -mastra-quad-saves. - * Body matches apart from relocation values; four save/restore instructions - * differ. Retail sq/lq s0 at sp+0x10, sd/ld ra at sp+0; this profile sq/lq - * s0 at sp+0 and sq/lq ra at sp+0x10. Default uses doubleword saves for both. - * The builtin_next_arg -0x38 accesses the seven saved integer argument words. - * Volatile packet pointer/data are supported by retail's repeated pointer - * loads and ordered packet writes. sda metadata reproduces the macro loads. - * Need a measured mixed-width save remedy; lq/sq alone is not handwritten. - */ -#include "common.h" -extern volatile u32 * volatile ref_L08_00389B68_00 __attribute__((sda)); -extern u32 *ref_L08_00389B68_01 MACRO_ADDR; -extern void func_00282AB0(void *, void *, int); -void func_L08_00389B68(int count, ...) { - if (count) { - ref_L08_00389B68_00[0] = (count + 1) | 0x10000000; - ref_L08_00389B68_00[1] = 0; - ref_L08_00389B68_00[2] = 0; - ref_L08_00389B68_00[3] = (count + 1) | 0x50000000; - ref_L08_00389B68_00[4] = count + 0x8000; - ref_L08_00389B68_00[5] = 0x10000000; - ref_L08_00389B68_00[6] = 14; - ref_L08_00389B68_00[7] = 0; - ref_L08_00389B68_01 = (u32 *)(ref_L08_00389B68_00 + 8); - func_00282AB0(ref_L08_00389B68_01, (char *)__builtin_next_arg(count) - 0x38, count * 16); - ref_L08_00389B68_00 = (u32 *)((char *)ref_L08_00389B68_00 + count * 16); - } -} diff --git a/nonmatching/levels/func_L10_00419188.c b/nonmatching/levels/func_L10_00419188.c deleted file mode 100644 index 0d23ea8ec..000000000 --- a/nonmatching/levels/func_L10_00419188.c +++ /dev/null @@ -1,60 +0,0 @@ -/* 0 of 1 places match - last line: 10_hrugis_cloud: 88 bytes, expected 96. - ROW IS EIGHT BYTES TOO LONG. The candidate walks the same list as func_L10_00417440 with the - store value 2; retail's real body is 88 bytes (0x419188..0x4191E0: `lbu 0x21/$a0`, the - lui/addiu table at 0x1FB1E0, `beqz` to the shared epilogue, then the lhu/lh pair loop). - The row claims 0x419188+0x60 and the extra eight bytes are an UNREACHABLE second epilogue - `jr $ra; nop` at 0x4191E0 - both the `beqz` and the loop exit reach 0x4191D8 - and the next - catalogue row (func_L10_004191E8) starts exactly at 0x4191E8. Maintainer data: re-cut the - row to 0x58. - - The candidate below is the 88-byte body, and it is now byte for byte the retail's 88 bytes: - the table entry is loaded into $v0 and copied with `daddu $a0,$v0,$zero` in the `beqz` - delay slot, the D_001B251C address is rebuilt inside the loop (the declaration carries the - sda attribute, which leaves the address to the assembler), the do-while's post-increment - sits in the back branch's delay slot, and the store keeps the base in $v1 with the - 0x7FFF mask shifted by 8. The four bytes the earlier candidate was short came from - declaring D_001B251C as sda (cc1 then emits the bare symbol and the assembler rebuilds - the address in the loop) and from reading the table entry as a u32 (the copy of the - pointer is then a 64-bit `daddu`). - - Only the eight extra bytes of the row are left, and they are not code this C can reach. - Below: the whole candidate (declarations as used in src/levels/10_hrugis_cloud/L10_003170D0.c). */ - -#include "include_asm.h" - -typedef unsigned char u8; -typedef unsigned short u16; -typedef signed short s16; -typedef unsigned int u32; - -extern u32 D_L10_001FB1E0[]; -extern u8 *D_001B251C __attribute__((sda)); - -void func_L10_00419188(u8 *arg0) -{ - u32 s0 = D_L10_001FB1E0[arg0[0x21]]; - s16 *p; - u8 *q; - - if (s0 == 0) { - return; - } - p = (s16 *)s0; - do { - q = D_001B251C + (((*(u16 *)p & 0x7FFF) << 8)); - *(q + 0x20) = 2; - } while (*p++ >= 0); -} - -/* Later worker (wave 24), same result from a different side. With the sda attribute on - D_001B251C the compiler emits the bare symbol and the assembler rebuilds the %lo half - inside the loop, as the note above says - but the %hi half (`lui $v1,0x1B`) is still - hoisted out of the loop by the loop-invariant motion, so the candidate is 84 bytes - against retail's 88 and the address build is split across the loop head. The same - construct in the sibling func_L10_00417440 (which now matches) keeps both halves - inside its loop, so the difference is what the motion pass does with the two loops. - With the table entry read as u32 the copy of the pointer is the 64-bit `daddu - $a0,$v0,$zero` retail has, and the do-while's post-increment lands in the back - branch's delay slot; the eight extra bytes of the row stay out of reach. - check.py func_L10_00419188: "10_hrugis_cloud: 84 bytes, expected 96" - the row is - still eight bytes too long. */ diff --git a/nonmatching/levels/func_L22_003D0840.c b/nonmatching/levels/func_L22_003D0840.c index d921eb8d5..f66239816 100644 --- a/nonmatching/levels/func_L22_003D0840.c +++ b/nonmatching/levels/func_L22_003D0840.c @@ -1,3 +1,14 @@ +/* 6 November 2026, round 11: still $v1 (60/60, 0/1), 33 compiles. Level 22 vtbl.bin +0x394 lists this function as the update slot of moby class 0xA6C (like matched func_L22_00385F40), so the signature is void (Moby *): no extra parameter and no return value. New, still $v1: a typed Moby struct (u8 state +0x20, u16 modeBits +0x34) with ->state / ->modeBits |= 0x41; int and Moby * return types with no return statement; early `return moby->state` (16 insns); `return state` (18); an unused second parameter; volatile modeBits, volatile state, volatile Moby *; u32 handle and void * parameters; state read into a local and passed as state + 1 / state - 1 (also with `state < 1`, both fold to 1/-1); `moby->state + 1` as the argument (16); switch with default; empty else; ternary/comma; return-in-both-arms; u16 * and u8 * interior pointers; int flags temp; do-while around the whole if (14 insns), around the call or around the flag store (14, no copy). RTL reading (greg: pointer refs 5, conflicts v0 a0 a1 a2 sp): the pointer has the most refs, so it is the first global allocno and takes the first free register; $v1 can only be excluded by a hard register or a local-alloc pseudo that is live with it, and a block-1 local copy used as the call argument is suggested $a0 (free there) by local-alloc, while cse canonicalises every same-mode copy to the parameter. No legal source form found. */ +/* 6 November 2026, round 10: still $v1 (60/60, 0/1). RTL (-dl/-dg, unit flags): only one global pseudo, the object (84), conflicting with $v0 (local 86/88/90), $a0 (call-arg set before the sh), $a1, $a2; no allocno prefers $v1, so find_reg takes $v1. Matched func_L22_00385F40 gives its object pseudo $v1 by the same rule ($v0 holds the case-1 constant, $a0 the switch value), so it adds no new constraint. Retail needs $v1 excluded with no trace: reload_cse_simplify_operands never rewrites register operands (reload1.c), so the only fitting path is a second copy Q of the object in $v1 used only as the call argument (`a0 = Q` becomes a no-op, then flow2 deletes the dead `Q = a0`, flow.c:2732). Q can avoid $a0 only if $a0 is live while Q lives; cse always merges a same-mode copy. A DImode union copy (`union { u8 *p; unsigned long q; }`) does put the object in $a3 but adds dsll/dsrl/and/or insert code. Also still $v1: -flive-range, the sibling flags (-mno-split-addresses, -G8 -malign-loops=2), the two new -frac2 flags, 28 single -f flags, an SImode union copy, a comma expression in the call argument, `while (...) { ...; break; }`. */ +/* 6 November 2026, round 9: compiler-difference hypothesis falsified. Probe cc1 (global.c find_reg, env-gated, all 8893 non-SDK src/ and nonmatching/ units compiled to .s and diffed): (a) a0-a3 before v1 in global alloc only: 2826 src units change; same order also in local alloc (REG_ALLOC_ORDER): 5384; (b) a pseudo with a copy preference for a0-a3 takes a free argument register over v1: 52 src units change; narrowest, a parameter pseudo (incoming a0-a3) takes a free argument register over v1: target becomes $a3 but 20 other matched functions change (12 USA, 6 PAL, 2 US2), including matched func_L22_00385F40 (same level, same `func_002A7750(obj, 1, -1)` call, retail keeps the parameter in $v1). No allocator-order rule explains this $a3; the cause is upstream of global alloc (a conflict or preference retail has that this RTL lacks). */ +/* 6 November 2026, round 8: still $v1 (60/60, 0/1). Donors: RAC4 has many callers of its state setter with (obj, 1, -1) (e.g. overlays/shared/L01_004E5DD0.c switch on +0x20 with case 0 calling it), and the 0x41 flag only as `(f | 0x41) & 0xEFFF` before a different call (L01_00489448.c, L08_004CFDC0.c, RAC2 func_L20_00440460); none has this ori-only shape. RAC1 has `|= 0x41` at +0x34 but no (obj, 1, -1) setter call. New, still $v1: `*(short *)` flags with `|=`; the RAC4 form `void *object` + `switch (*((u8 *)object + 0x20)) { case 0: ...; break; }`. */ +/* 6 November 2026, round 6: still $v1 (60/60, 0/1). Tried: a block-local `self = object` used only as the call argument after a one-pass flag group (cse merges it; the object stays in $a0 with no copy, the sh moves before the call setup); flags in a named u16 set then or-ed; `self` set after an early return; a switch with an empty `case 1`; the callee's mode parameter as `unsigned char` (00300618-state.c precedent); an unused `work = object[0x68]` load. An opaque asm copy (probe only) shows a second global copy just takes $a0 and leaves the object in $v1, so $a3 needs a local in $v1 across the object's life that reload_cse/flow2 then delete; no legal source found. The callee returns void, so an unused return value is not available. */ +/* 5 November 2026, round 5: still $v1. No sched1/allocator tie-break change was found that covers this allocation; the L00 sibling matched through a single-set data pointer (sched1 birthing priority), which has no counterpart here (the pointer is set once already). */ +/* 5 November 2026, round 4: still $v1. `-1` as a `long` argument gives the same addiu and $v1. `state = object[0x20]` with call(object, state + 1, state - 1): cse folds both through the jump equivalence, same bytes. `long`/`u64` flag temps: $a3 but dli/or/andi (DImode ior takes no immediate here). Sibling func_L20_00440460 uses default -G0 flags and the same 3-int callee prototype; its $a3 comes from a second live pointer. Needed: a block-1 local that local-alloc puts in $v1 and reload then deletes (e.g. a constant arg reload_cse turns into li). */ +/* 5 November 2026: still $v1 (60/60, 0/1). global.c prune_preferences counts only lower-priority conflicting allocnos' full prefs; no RTL here names $v1, so none prefers it. Inline helpers, bitfields, -g/qcopy flags: all $v1. Any do-while (update, s=1, flags) is a sched barrier: sh before a0 setup, pointer stays in $a0, 56 B. + * `unsigned long long f` gives $a3 (0x41 lands in $v1 via dli) but adds dli/or/andi. */ +/* 5 November 2026: new, still $v1 (60/60, 0/1): K&R definition; the call through a 4-argument view passing the object again as a3 (64 bytes, still $v1, and a false prototype anyway). Remaining: the object pointer in $v1, retail $a3. */ +/* 5 November 2026: lesson-3 copy (`self = object; object += 0x34; *(u16 *)object |= 0x41; call(self)`) keeps a second pointer but cse/combine do not fold the +0x34 back: 64/60 bytes, still $v1. global.c find_reg skips regs_someone_prefers first, so $a3 needs a conflicting pseudo that prefers $v1 or a block-local copy that local-alloc puts in $v1; no legal source found for either. */ /* 4 November 2026: a real one-pass flag-update/state-change group, as seen * in current RAC1 game C, gives 64/60 bytes and 0/1 USA. The object still * uses v1 rather than a3 and an extra alignment nop remains. No improvement; diff --git a/src/core/001163B0.c b/src/core/001163B0.c index b9d0172d7..90ddb1c72 100644 --- a/src/core/001163B0.c +++ b/src/core/001163B0.c @@ -42,4 +42,4 @@ int func_001163B0(void) { /* func_00118CC8 is defined in 00118CC8.c with quadword saves. */ -INCLUDE_ASM("asm/core", func_0011A7F8); +ASM_FUNC("asm/core", func_0011A7F8); diff --git a/src/core/0011B1E8.c b/src/core/0011B1E8.c index d7cdb7810..545642c53 100644 --- a/src/core/0011B1E8.c +++ b/src/core/0011B1E8.c @@ -43,5 +43,3 @@ ASM_FUNC("asm/core", func_0011B3D0); ASM_FUNC("asm/core", func_0011B458); ASM_FUNC("asm/core", func_0011B500); - -INCLUDE_ASM("asm/core", func_0011B580); diff --git a/src/core/0011C8B0.c b/src/core/0011C8B0.c index 71577a356..3643d5de8 100644 --- a/src/core/0011C8B0.c +++ b/src/core/0011C8B0.c @@ -55,8 +55,6 @@ int func_0011C8B0(int arg0) { return r1_D_00155080[arg0]; } -INCLUDE_ASM("asm/core", func_0011C8C8); - extern int r1_D_00155080[]; extern int r1_D_0012FD04; extern int r1_D_00154F54; diff --git a/src/core/0011E4E0.c b/src/core/0011E4E0.c index a73966090..a0654d19e 100644 --- a/src/core/0011E4E0.c +++ b/src/core/0011E4E0.c @@ -209,5 +209,3 @@ int func_0011E8A8(int value) { return -1; return D_00140180[0]; } - -INCLUDE_ASM("asm/core", func_0011E920); diff --git a/src/core/0011ED08.c b/src/core/0011ED08.c index e778cb626..73088753c 100644 --- a/src/core/0011ED08.c +++ b/src/core/0011ED08.c @@ -8,5 +8,3 @@ int func_0011ED08(int arg0, int arg1, int arg2) { char buf[0x10]; return func_0011EB00(arg0, arg1, arg2, buf); } - -INCLUDE_ASM("asm/core", func_0011ED28); diff --git a/src/core/0011FA20.c b/src/core/0011FA20.c index 855ea2574..e92434b25 100644 --- a/src/core/0011FA20.c +++ b/src/core/0011FA20.c @@ -15,5 +15,3 @@ void func_0011FA20(int status) { func_0011FA18(); r1_func_00118A60(status); } - -INCLUDE_ASM("asm/core", func_0011FA48); diff --git a/src/core/001232F0.c b/src/core/001232F0.c index f7e1cfc46..68a682113 100644 --- a/src/core/001232F0.c +++ b/src/core/001232F0.c @@ -427,8 +427,6 @@ func_00123400 (FLO_union_type * src, fp_number_type * dst) } } -INCLUDE_ASM("asm/core", func_00123490); - extern FLO_type func_001232F0(fp_number_type *); FLO_type func_001234C0(fp_class_type classification, unsigned int sign, int exponent, fractype fraction) { diff --git a/src/core/00128D58.c b/src/core/00128D58.c index f75d5393b..1c5416f45 100644 --- a/src/core/00128D58.c +++ b/src/core/00128D58.c @@ -218,5 +218,3 @@ ASM_FUNC("asm/core", func_00129218); ASM_FUNC("asm/core", func_001292C0); ASM_FUNC("asm/core", func_00129368); - -INCLUDE_ASM("asm/core", func_00129410); diff --git a/src/core/0012F940.c b/src/core/0012F940.c index 425283974..5a65ea76d 100644 --- a/src/core/0012F940.c +++ b/src/core/0012F940.c @@ -26,8 +26,6 @@ int func_0012F948(char *p, unsigned int addr, int size) { return r1_func_0012BDD0(p); } -INCLUDE_ASM("asm/core", func_0012F998); - unsigned int func_0012F9A8(struct IndirectWord *resource) { return *resource->value; diff --git a/src/core/0012F9B8.c b/src/core/0012F9B8.c index ab5b39916..b6cee8605 100644 --- a/src/core/0012F9B8.c +++ b/src/core/0012F9B8.c @@ -120,8 +120,6 @@ void func_0012FAE8(int arg0) { func_0012FA98(arg0, local); } -INCLUDE_ASM("asm/core", func_0012FB10); - /* rac1-decomp src/core/0012AC80.c: func_0012BD28 */ void func_0012FB48(void *arg0, int arg1, int arg2) { int *p = (int *)arg0; diff --git a/src/core/00130AAC.c b/src/core/00130AAC.c index 11c059aae..e8c87da2a 100644 --- a/src/core/00130AAC.c +++ b/src/core/00130AAC.c @@ -1,3 +1 @@ #include "include_asm.h" - -INCLUDE_ASM("asm/core", func_00130AAC); diff --git a/src/core/00131780-g8.c b/src/core/00131780-g8.c index bc4c673f5..cefd2f958 100644 --- a/src/core/00131780-g8.c +++ b/src/core/00131780-g8.c @@ -35,3 +35,33 @@ void func_00133108(void) { D_001A74A8[next] = 0xFFC; } } + +extern int D_001A74C8 __attribute__((sda)); +extern int D_001A7488 __attribute__((sda)); +extern int D_001A74D0 __attribute__((sda)); +extern int D_001A71C0 MACRO_ADDR; +extern unsigned int D_001A7180 MACRO_ADDR; +extern volatile long D_001A74D8 MACRO_ADDR; +extern int D_001A7140 MACRO_ADDR; +extern char D_001A76F8[]; +void func_001325E0(int a, int c, long d) { + D_001A7488 = 0; + if (D_001A74C8 != 0) { + if (D_001A74F8 != 0) return; + func_00115D48(D_001A76F8); + return; + } + do { + D_001A71C0 = a; + D_001A74D0 = c; + D_001A7180 = -1u; + D_001A74D8 = d; + } while (0); + while (func_0011D810(&D_001A7140)) { + if (D_001A74F8 == 0) func_00115D48(D_001A7578); + func_00132028(); + func_0011AEA0(0); + } + D_001A74C8 = 1; + func_0011D620(&D_001A7140, 0x57, 1, &D_001A71C0, 4, (int *)&D_001A7180, 4, 0, 0); +} diff --git a/src/core/00131780.c b/src/core/00131780.c index 9cd822629..8c2a73f5e 100644 --- a/src/core/00131780.c +++ b/src/core/00131780.c @@ -190,7 +190,8 @@ void func_00131CA8(int ignored_status) { func_0011FA20(0); } -INCLUDE_ASM("asm/core", func_00131CB0); +/* Original assembly: `addiu $v1,$zero,0x23; syscall`, a thread-exit stub whose address crt0 passes to the thread syscall; the compiler cannot emit syscall. */ +ASM_FUNC("asm/core", func_00131CB0); /* func_00131D98 is defined in 00131D98.c. */ @@ -200,7 +201,7 @@ INCLUDE_ASM("asm/core", func_00131DE8); /* func_00132318 and func_001326D8 are in 00132318-g8.c. */ -INCLUDE_ASM("asm/core", func_001325E0); +/* func_001325E0 is defined in 00131780-g8.c. */ void func_00132858(int value) { diff --git a/src/game/0026EA00.c b/src/game/0026EA00.c index 08ff23c40..6dacf9595 100644 --- a/src/game/0026EA00.c +++ b/src/game/0026EA00.c @@ -459,8 +459,6 @@ void func_0026FE48(void) void func_0026FEB8(const char *format,...) { } -INCLUDE_ASM("asm/game", func_0026FEF0); - typedef struct { u8 pad[0x3D0]; @@ -805,8 +803,6 @@ void func_00272280(void) /* func_00272CB0 is in 0026EA00-target.c (-g for its nop pair before div.s). */ -INCLUDE_ASM("asm/game", func_00272540); - /* Fills a three-float local through two setup calls, stores a two-argument float helper result into a field, then stores a second helper result into two more fields and returns zero. */ int func_00272550(float *a0) { @@ -825,8 +821,6 @@ int func_00272550(float *a0) return 0; } -INCLUDE_ASM("asm/game", func_002725C8); - /* Draw sixteen lens-flare elements with distance and screen-edge fades. * Corresponds to RAC1 draw_lens_flare, src/game/effects.c (GPL-3.0). */ diff --git a/src/game/0027F128.c b/src/game/0027F128.c index ce4019ebe..6088be1de 100644 --- a/src/game/0027F128.c +++ b/src/game/0027F128.c @@ -198,8 +198,6 @@ void func_00280600(void) { /* func_00280630 -- see src/game/0027F128-g8.c (built with -G8). */ -INCLUDE_ASM("asm/game", func_00280660); - /* The share of a region's pixels whose low 24 bits do not exceed the region's threshold. */ void func_00280670(u32 *pixels, int index) { CopyRegion *region = &D_001B8A10[index]; @@ -220,7 +218,8 @@ ASM_FUNC("asm/game", func_002808F8); /* Original assembly: RAC1 game/render/drawquad.c, func_001F7DD8. */ ASM_FUNC("asm/game", func_00280A70); -INCLUDE_ASM("asm/game", func_00280B30); +/* Original assembly: lqc2/sqc2/vdiv and VU0 vector ops; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_00280B30); ASM_FUNC("asm/game", func_00280B90); @@ -281,24 +280,29 @@ void func_002820C8(void) { } -INCLUDE_ASM("asm/game", func_00282848); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); same body as RAC1 fastfunc func_001F9840, and its neighbours are RAC1 fastfunc original assembly. */ +ASM_FUNC("asm/game", func_00282848); /* Original assembly: RAC1 game/math/fastfunc.c, func_001F9850. */ ASM_FUNC("asm/game", func_00282890); -INCLUDE_ASM("asm/game", func_002828B8); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fastfunc original assembly. */ +ASM_FUNC("asm/game", func_002828B8); /* Original assembly: RAC1 game/math/fastfunc.c, func_001F9850. */ ASM_FUNC("asm/game", func_002828C8); -INCLUDE_ASM("asm/game", func_002828F0); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fastfunc original assembly. */ +ASM_FUNC("asm/game", func_002828F0); /* Original assembly: RAC1 game/math/fastfunc.c, func_001F9850. */ ASM_FUNC("asm/game", func_00282900); -INCLUDE_ASM("asm/game", func_00282928); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fastfunc original assembly. */ +ASM_FUNC("asm/game", func_00282928); -INCLUDE_ASM("asm/game", func_00282938); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fastfunc original assembly. */ +ASM_FUNC("asm/game", func_00282938); ASM_FUNC("asm/game", func_00282948); @@ -307,11 +311,13 @@ ASM_FUNC("asm/game", func_00282978); /* Original assembly: RAC1 overlays/shared/fast_vector_math.c, func_L00_001FEF78. */ ASM_FUNC("asm/game", func_002829A8); -INCLUDE_ASM("asm/game", func_002829D8); +/* Original assembly: $at as a working register and trapping addi/sub; the compiler cannot emit these. */ +ASM_FUNC("asm/game", func_002829D8); ASM_FUNC("asm/game", func_00282A18); -INCLUDE_ASM("asm/game", func_00282A28); +/* Original assembly: an unconditional `teq $zero,$zero,0`; this cc1 has no trap pattern that emits `teq` (only div_trap's bne/break) and rejects __builtin_trap. Same bytes as RAC1 fastfunc func_001F9978 (asm/handwritten). */ +ASM_FUNC("asm/game", func_00282A28); ASM_FUNC("asm/game", func_00282A38); @@ -319,13 +325,15 @@ ASM_FUNC("asm/game", func_00282A60); ASM_FUNC("asm/game", func_00282A88); -INCLUDE_ASM("asm/game", func_00282AB0); +/* Original assembly: trapping add/addi in the copy loops; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_00282AB0); ASM_FUNC("asm/game", func_00282B50); ASM_FUNC("asm/game", func_00282B78); -INCLUDE_ASM("asm/game", func_00282BA8); +/* Original assembly: $at as a working base register (lui/ori $at then sw), sync, and ori after jr; the compiler cannot emit these. */ +ASM_FUNC("asm/game", func_00282BA8); ASM_FUNC("asm/game", func_00282BE0); @@ -343,14 +351,16 @@ f32 func_00282C48(f32 a0) { return __builtin_fabsf(a0); } ASM_FUNC("asm/game", func_00282C58); -INCLUDE_ASM("asm/game", func_00282C68); +/* Original assembly: identical to RAC1 game/math/fastfunc.c func_001F9BB0, which rac1-decomp keeps as handwritten; 16 bytes, so below the identity rule's length. */ +ASM_FUNC("asm/game", func_00282C68); ASM_FUNC("asm/game", func_00282C78); /* Clear one aligned 128-bit object through architectural zero. */ void func_00282C88(TI128 *a0) { *a0 = 0; } -INCLUDE_ASM("asm/game", func_00282C90); +/* Original assembly: sqc2 (COP2 store) in the return delay slot, which the compiler cannot emit. */ +ASM_FUNC("asm/game", func_00282C90); ASM_FUNC("asm/game", func_00282C98); @@ -399,9 +409,11 @@ ASM_FUNC("asm/game", func_00282F20); /* Original assembly: RAC1 game/math/fastfunc.c, func_001F9E10. */ ASM_FUNC("asm/game", func_00282F70); -INCLUDE_ASM("asm/game", func_00282FB8); +/* Original assembly: lqc2/sqc2/vdiv/vwaitq VU0 ops, $at as a working register and trapping addi. */ +ASM_FUNC("asm/game", func_00282FB8); -INCLUDE_ASM("asm/game", func_00283028); +/* Original assembly: lqc2/sqc2/vrsqrt VU0 ops and $at as a working register; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_00283028); ASM_FUNC("asm/game", func_00283098); @@ -410,7 +422,8 @@ ASM_FUNC("asm/game", func_002830C0); ASM_FUNC("asm/game", func_002830F0); -INCLUDE_ASM("asm/game", func_00283108); +/* Original assembly: RAC1 game/math/fastfunc.c, func_001F9F30. */ +ASM_FUNC("asm/game", func_00283108); ASM_FUNC("asm/game", func_00283130); @@ -423,7 +436,8 @@ ASM_FUNC("asm/game", func_00283198); /* Original assembly: RAC1 game/math/fastfunc.c, func_001F9FC0. */ ASM_FUNC("asm/game", func_002831B0); -INCLUDE_ASM("asm/game", func_00283248); +/* Original assembly: lqc2/qmtc2/qmfc2 VU0 ops and trapping add; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_00283248); /* Original assembly: RAC1 game/math/fastfunc.c, func_001FA168. */ ASM_FUNC("asm/game", func_00283360); @@ -448,7 +462,8 @@ ASM_FUNC("asm/game", func_00283678); /* Original assembly: RAC1 game/math/fastfunc.c, func_001FA4A0. */ ASM_FUNC("asm/game", func_00283698); -INCLUDE_ASM("asm/game", func_002836E8); +/* Original assembly: lqc2/sqc2 and VU0 vector ops; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002836E8); /* Original assembly: RAC1 game/math/fastfunc.c, func_001FA4F0. */ ASM_FUNC("asm/game", func_00283738); @@ -458,7 +473,8 @@ ASM_FUNC("asm/game", func_00283788); /* Original assembly: RAC1 game/math/fastfunc.c, func_001FA588. */ ASM_FUNC("asm/game", func_002837D0); -INCLUDE_ASM("asm/game", func_00283810); +/* Original assembly: lqc2/sqc2/vrsqrt VU0 ops and $at as a working register; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_00283810); /* Original assembly: RAC1 overlays/shared/fast_vector_math.c, func_L00_001FFED8. */ ASM_FUNC("asm/game", func_00283898); @@ -469,11 +485,14 @@ ASM_FUNC("asm/game", func_00283958); /* Original assembly: RAC1 game/math/fastfunc.c, func_001FA6C0. */ ASM_FUNC("asm/game", func_002839D0); -INCLUDE_ASM("asm/game", func_00283A58); +/* Original assembly: lqc2/sqc2 and VU0 vector ops; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_00283A58); -INCLUDE_ASM("asm/game", func_00283AF0); +/* Original assembly: qmtc2/vitof/sqc2 VU0 ops with $at as a working register; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_00283AF0); -INCLUDE_ASM("asm/game", func_00283B48); +/* Original assembly: lqc2/sqc2/qmtc2 and VU0 vector ops; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_00283B48); /* Byte-identical 72-byte copy of RAC1 func_001FA748, which RAC1 marks ASM_FUNC. */ ASM_FUNC("asm/game", func_00283B98); @@ -481,12 +500,14 @@ ASM_FUNC("asm/game", func_00283B98); /* Original assembly: RAC1 game/math/fastfunc.c, func_001FA790. */ ASM_FUNC("asm/game", func_00283BE0); -INCLUDE_ASM("asm/game", func_00283C28); +/* Original assembly: $at as a working register and trapping add; the compiler cannot emit these. */ +ASM_FUNC("asm/game", func_00283C28); /* Original assembly: RAC1 game/math/fastfunc.c, func_001FA850. */ ASM_FUNC("asm/game", func_00283C80); -INCLUDE_ASM("asm/game", func_00283CB8); +/* Original assembly: `cvt.s.w` directly after `cvt.w.s` in the FPU; this cc1's only cvt.s.w templates start from mtc1 or l.s, so it cannot emit it. */ +ASM_FUNC("asm/game", func_00283CB8); /* Original assembly: RAC1 overlays/shared/fast_vector_math.c, func_L00_002001D8. */ ASM_FUNC("asm/game", func_00283CC8); @@ -495,7 +516,8 @@ ASM_FUNC("asm/game", func_00283CC8); /* integer-to-float conversion; byte-identical across all 27 levels. */ f32 func_00283CE0(s32 a0) { return (f32)a0; } -INCLUDE_ASM("asm/game", func_00283CF0); +/* Original assembly: identical to RAC1 game/math/fastfunc.c func_001FA898, which rac1-decomp keeps as handwritten; 16 bytes, so below the identity rule's length. */ +ASM_FUNC("asm/game", func_00283CF0); /* Original assembly: RAC1 overlays/shared/fast_vector_math.c, func_L00_00200210. */ ASM_FUNC("asm/game", func_00283D00); @@ -503,7 +525,8 @@ ASM_FUNC("asm/game", func_00283D00); /* Original assembly: RAC1 game/math/fastfunc.c, func_001FA8A8. */ ASM_FUNC("asm/game", func_00283D38); -INCLUDE_ASM("asm/game", func_00283D80); +/* Original assembly: lqc2/VU0 vector ops, $at as a working register and trapping addi/sub. */ +ASM_FUNC("asm/game", func_00283D80); ASM_FUNC("asm/game", func_00283DB8); diff --git a/src/game/00288D30.c b/src/game/00288D30.c index 03c707dc3..1875220bf 100644 --- a/src/game/00288D30.c +++ b/src/game/00288D30.c @@ -6,5 +6,3 @@ int func_00288D30(void) { return ref_L00_002F4398_00 != 0; } - -INCLUDE_ASM("asm/game", func_00288D40); diff --git a/src/game/00288D88.c b/src/game/00288D88.c index 44553b97c..71b803178 100644 --- a/src/game/00288D88.c +++ b/src/game/00288D88.c @@ -444,7 +444,46 @@ void func_0028ACB0(int mode) -INCLUDE_ASM("asm/game", func_0028B160); +extern int D_001A7308 __attribute__((section(".sdata"))); +extern void func_0028F948(unsigned int, int, int, int, int, int); + +void func_0028B160(int bank, int base, int immediate) +{ + struct HudTexCounts *counts; + int address; + int bank_offset; + int first; + int end; + int i; + int page; + int width_log2; + int height_log2; + int size; + + if (D_001B1870.header.counts->loaded[bank] == 0) { + func_0028AE88(0, base); + address = D_001A7308; + } else { + address = D_001A7308; + } + counts = D_001B1870.header.counts; + bank_offset = bank << 2; + first = bank == 0 ? 0 : counts->ends[bank - 1]; + i = first; + end = *(int *)((unsigned char *)D_001B1870.header.counts + bank_offset + 0x34); /* ends[bank] */ + do { + for (; i < end; i++) { + page = address >> 8; + width_log2 = D_001B1870.image_pages[i].width_log2; + height_log2 = D_001B1870.image_pages[i].height_log2; + size = 1 << (width_log2 + height_log2); + func_0028F948(D_001B1870.image_pages[i].source_address, page, 0x1B, width_log2, + height_log2, immediate); + address += size * 4; + D_001B1870.image_pages[i].gs_block_offset = page; + } + } while (0); +} extern char *D_001BAF3C; extern char * volatile D_001B1880 __attribute__((sda)); diff --git a/src/game/00290670.c b/src/game/00290670.c index 95832a577..bfb21df60 100644 --- a/src/game/00290670.c +++ b/src/game/00290670.c @@ -37,8 +37,6 @@ void func_00290680(void) func_0027DDC0(0, 0, 0, r); } -INCLUDE_ASM("asm/game", func_00290718); - extern int D_001A901C __attribute__((sda)); void func_00290720(void) { diff --git a/src/game/00298838.c b/src/game/00298838.c index 815847356..ffd9d6daf 100644 --- a/src/game/00298838.c +++ b/src/game/00298838.c @@ -220,8 +220,6 @@ void func_00298BB8(unsigned char *source) func_00115AC0(D_001A79D0, (int)D_001A7930, 13); } -INCLUDE_ASM("asm/game", func_00298D10); - extern char D_001A9970[]; extern void func_0029B168(char *, int, int *); extern void func_0029B628(void); diff --git a/src/game/0029AE78.c b/src/game/0029AE78.c index de25cadd1..a91439e83 100644 --- a/src/game/0029AE78.c +++ b/src/game/0029AE78.c @@ -178,8 +178,6 @@ int func_0029B780(void) { -INCLUDE_ASM("asm/game", func_0029B848); - extern void func_0034E4B8(void *); void func_0029B858(void) { diff --git a/src/game/0029BCC8.c b/src/game/0029BCC8.c index 2c6e0fc27..f5aba55ca 100644 --- a/src/game/0029BCC8.c +++ b/src/game/0029BCC8.c @@ -470,8 +470,6 @@ void func_0029CE38(void) -INCLUDE_ASM("asm/game", func_0029CEC8); - extern void func_003399B0(void *); void func_0029CED8(void) { @@ -493,21 +491,26 @@ ASM_FUNC("asm/game", func_0029CF58); /* Original assembly: RAC1 game/render/miscproc.c, func_0020C230. */ ASM_FUNC("asm/game", func_0029CF78); -INCLUDE_ASM("asm/game", func_0029CFB0); +/* Original assembly: $at as a working register and trapping addi/add/sub; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_0029CFB0); ASM_FUNC("asm/game", func_0029D050); -INCLUDE_ASM("asm/game", func_0029D0E0); +/* Original assembly: $at as a working register and trapping addi/add; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_0029D0E0); -INCLUDE_ASM("asm/game", func_0029D258); +/* Original assembly: lqc2/qmtc2/qmfc2 VU0 ops, $at as a working register and trapping addi/add. */ +ASM_FUNC("asm/game", func_0029D258); -INCLUDE_ASM("asm/game", func_0029D398); +/* Original assembly: lqc2/qmtc2/qmfc2 VU0 ops, $at as a working register and trapping addi/add. */ +ASM_FUNC("asm/game", func_0029D398); ASM_FUNC("asm/game", func_0029D4D0); ASM_FUNC("asm/game", func_0029D7A0); -INCLUDE_ASM("asm/game", func_0029D7C0); +/* Original assembly: RAC1 game/render/miscproc.c, func_0020C758 (live-in $v1, unconditional `teq` traps; one more nop before the final return). */ +ASM_FUNC("asm/game", func_0029D7C0); extern void *D_0026CA90[]; diff --git a/src/game/0029DE38.c b/src/game/0029DE38.c index 4f7c982fe..1f2bd596f 100644 --- a/src/game/0029DE38.c +++ b/src/game/0029DE38.c @@ -289,9 +289,6 @@ void func_0029F6A0( *(float *)(dest + 12) = Ff2d8e5ad_FUN_00282E48(dest, m0); } -INCLUDE_ASM("asm/game", func_0029F840); - - void func_0029F978(u8 *a0,u32 a1,u8 *a2) { u8 *p; if(a2[1]!=0) return; diff --git a/src/game/0029F840-nogcse.c b/src/game/0029F840-nogcse.c new file mode 100644 index 000000000..f95775cf9 --- /dev/null +++ b/src/game/0029F840-nogcse.c @@ -0,0 +1,83 @@ +/* SPDX-License-Identifier: MIT + * MIT License + * + * Copyright (c) 2026 RC2 decomp contributions + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ +#include "common.h" + +extern void func_00282D60(void *, void *, float); +extern void func_00283098(void *, void *, void *); +extern void func_00282CC0(void *, void *, void *); +extern void func_00283130(void *, unsigned long long); +extern void func_00282D30(void *, void *, float); +int func_0029F840(char *obj, char *m, char *out, int index) { + char *p = *(char **)(obj + 0x24); + int cnt = *(short *)(p + 0x2E); + int tab; + char *rec; + int n; + int i; + int e; + char *dst; + float k; + float s; + + if (cnt == 0) { + goto fail; + } + tab = (int)p + cnt * 16; + index += tab; + e = ((unsigned char *)index)[1]; + p = m; + if (e == 0xFF) { + do { +fail: + return 0; + } while (0); + } + do { + s = *(float *)(obj + 0x2C); + } while (0); + k = 0.0009765625f; + do { + e *= 16; + } while (0); + rec = (char *)tab + e; + func_00282D60(p, rec, s * k); + rec += 0x10; + func_00283098(m, m, obj + 0xC0); + func_00282CC0(m, m, obj + 0x10); + do { + n = *(short *)(rec + 6); + } while (0); + if (out != 0 && n > 0) { + dst = out; + for (i = n; i != 0;) { + i--; + func_00283130(dst, *(unsigned long long *)rec); + rec += 8; + func_00282D30(dst, dst, *(float *)(obj + 0x2C) * k); + *(float *)(dst + 0xC) = 1.0f; + dst += 0x10; + } + } + return n; +} diff --git a/src/game/002A0430.c b/src/game/002A0430.c index 45d1dec22..d44e3f323 100644 --- a/src/game/002A0430.c +++ b/src/game/002A0430.c @@ -52,9 +52,11 @@ ASM_FUNC("asm/game", func_002A0558); words in an encoding the compiler never emits. */ ASM_FUNC("asm/game", func_002A05A8); -INCLUDE_ASM("asm/game", func_002A08A0); +/* Original assembly: VU0 lqc2 ops, scratchpad base in $t7 and trapping addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002A08A0); -INCLUDE_ASM("asm/game", func_002A0A28); +/* Original assembly: $at as a working register and trapping add/addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002A0A28); ASM_FUNC("asm/game", func_002A0B88); @@ -66,11 +68,13 @@ ASM_FUNC("asm/game", func_002A0C68); trapping addi/add and $at as a working register. */ ASM_FUNC("asm/game", func_002A0F48); -INCLUDE_ASM("asm/game", func_002A10E8); +/* Original assembly: lqc2/vmove VU0 ops and trapping addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002A10E8); INCLUDE_ASM("asm/game", func_002A1130); -INCLUDE_ASM("asm/game", func_002A1378); +/* Original assembly: VU0 lqc2/sqc2 ops and trapping addi/add with $at as a working register; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002A1378); /* Original assembly: 32 trapping add/addi/sub, $at as a working register, and no return: it leaves by jumps, like func_002A1130. */ @@ -96,7 +100,8 @@ ASM_FUNC("asm/game", func_002A4E68); ASM_FUNC("asm/game", func_002A6640); -INCLUDE_ASM("asm/game", func_002A677C); +/* Original assembly: $ra kept in $t9 and trapping addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002A677C); diff --git a/src/game/002B00B0.c b/src/game/002B00B0.c index e72ce470e..6226fcdf3 100644 --- a/src/game/002B00B0.c +++ b/src/game/002B00B0.c @@ -197,8 +197,6 @@ void func_002B0990(void *a0, float *a1, float f12, int a2, int a3) } } -INCLUDE_ASM("asm/game", func_002B0A08); - void func_002B0A18(int first, int second) { extern int func_00288FB8(int); diff --git a/src/game/002B3868.c b/src/game/002B3868.c index cad6baaa0..90014e0f9 100644 --- a/src/game/002B3868.c +++ b/src/game/002B3868.c @@ -82,8 +82,6 @@ int func_002B4038(int value, int index) { return D_00240450[index].value == value; } -INCLUDE_ASM("asm/game", func_002B4068); - typedef int PoseVector128 __attribute__((mode(TI))); typedef struct { PoseVector128 initial, previous, current, delta; @@ -120,8 +118,6 @@ void func_002B4090(char *self, PoseVector128 *point, float x, float y, float z) INCLUDE_ASM("asm/game", func_002B44C0); -INCLUDE_ASM("asm/game", func_002B49A0); - extern int D_001AA0F0 __attribute__((sda)); void func_002B49B0(int value) { diff --git a/src/game/002B7E28.c b/src/game/002B7E28.c index a7f04ce73..ac48820fc 100644 --- a/src/game/002B7E28.c +++ b/src/game/002B7E28.c @@ -291,8 +291,6 @@ void func_002B8048(int value, long address) } } -INCLUDE_ASM("asm/game", func_002B80B8); - /* func_002B8108 is in 002B7E28-g8.c. */ void func_002B8518(void) { @@ -300,8 +298,6 @@ void func_002B8518(void) { D_00138180.value = 0; } -INCLUDE_ASM("asm/game", func_002B8530); - /* func_002B85F8 is in 002B7E28-g8.c. */ void func_002B8888(u8 *a0) { @@ -321,22 +317,27 @@ void func_002B9000(void) { func_002B85F8(&D_00138500); } -INCLUDE_ASM("asm/game", func_002B9030); +/* Original assembly: a `j` with a trapping `addi $a1,$zero,0` in its delay slot; the compiler emits only addiu. */ +ASM_FUNC("asm/game", func_002B9030); ASM_FUNC("asm/game", func_002B9038); /* Original assembly: RAC1 overlays/shared/particle_create_kill.c, func_L00_002688A8. */ ASM_FUNC("asm/game", func_002B9180); -INCLUDE_ASM("asm/game", func_002B9288); +/* Original assembly: lqc2/qmtc2/vitof VU0 ops and trapping addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002B9288); -INCLUDE_ASM("asm/game", func_002B9380); +/* Original assembly: `lw; nop; jr $v0` keeps a load-delay nop before an indirect tail jump; cc1 never emits the nop and has no indirect sibling call (MATCHING-BLOCKERS 4). */ +ASM_FUNC("asm/game", func_002B9380); -INCLUDE_ASM("asm/game", func_002B9390); +/* Original assembly: RAC1 game/render/partproc.c, func_00218A80; $ra saved at $gp+0x2DB8, $at as a working register and trapping add/addi. */ +ASM_FUNC("asm/game", func_002B9390); ASM_FUNC("asm/game", func_002B9420); -INCLUDE_ASM("asm/game", func_002BA048); +/* Original assembly: qmfc2 VU0 op and trapping add/addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002BA048); INCLUDE_ASM("asm/game", func_002BA0E0); diff --git a/src/game/002DF1B8.c b/src/game/002DF1B8.c index 8e85b8057..fb2af11df 100644 --- a/src/game/002DF1B8.c +++ b/src/game/002DF1B8.c @@ -18,8 +18,6 @@ int func_002DF1D0(void) { /* func_002DF3F8 is in 002DF1B8-capture.c. */ -INCLUDE_ASM("asm/game", func_002DF630); - /* func_002DF7A8 is matched in 002DF1B8-g8.c (-G8 small data). */ @@ -37,7 +35,8 @@ ASM_FUNC("asm/game", func_002E0408); ASM_FUNC("asm/game", func_002E0558); -INCLUDE_ASM("asm/game", func_002E0BA8); +/* Original assembly: lqc2/sqc2/vdiv VU0 ops and trapping addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002E0BA8); ASM_FUNC("asm/game", func_002E0C40); diff --git a/src/game/002E10B8.c b/src/game/002E10B8.c index 7cf623697..92de14431 100644 --- a/src/game/002E10B8.c +++ b/src/game/002E10B8.c @@ -126,9 +126,11 @@ ASM_FUNC("asm/game", func_002E2988); ASM_FUNC("asm/game", func_002E2C38); -INCLUDE_ASM("asm/game", func_002E31E8); +/* Original assembly: lqc2/qmfc2 VU0 ops, $at as a working register and trapping addi. */ +ASM_FUNC("asm/game", func_002E31E8); -INCLUDE_ASM("asm/game", func_002E3360); +/* Original assembly: $at as a working register and trapping add/addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002E3360); @@ -209,7 +211,8 @@ ASM_FUNC("asm/game", func_002E40C8); ASM_FUNC("asm/game", func_002E425C); -INCLUDE_ASM("asm/game", func_002E4388); +/* Original assembly: lqc2/qmfc2 VU0 ops and trapping addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002E4388); void func_002E4478(void *object) { diff --git a/src/game/002E7018.c b/src/game/002E7018.c index 6eea9e0ac..545d28356 100644 --- a/src/game/002E7018.c +++ b/src/game/002E7018.c @@ -225,7 +225,7 @@ int func_002EB158(int index) /* func_002EBAA8 is in 002EBAA8-g8.c (-G8 small data). */ -INCLUDE_ASM("asm/game", func_002EBC70); +/* func_002EBC70 is in 002EBC70-g8.c (-G8 small data). */ /* func_002EBDF0 is matched in 002EBDF0-g8.c. */ diff --git a/nonmatching/game/func_002EBC70.c b/src/game/002EBC70-g8.c similarity index 53% rename from nonmatching/game/func_002EBC70.c rename to src/game/002EBC70-g8.c index 2bf8e28b1..a6937f64d 100644 --- a/nonmatching/game/func_002EBC70.c +++ b/src/game/002EBC70-g8.c @@ -1,34 +1,3 @@ -/* Near miss (opus-2, Claude Opus 5.5 xhigh, task v2098, 3 November 2026; - * earlier opus-1 v2078): 380/380 bytes, 0 of 28 places. Only the - * entry-relinking loop's registers differ (about 13 words); the call - * sequence, the stores before func_002B9000/func_0027BD70/func_002EBAA8, - * the base copy `daddu a2,a0,zero` and the tail (int func_001261F0) match. - * - * Build: its own unit with -O2 -G8 -ffunction-sections (for example - * src/game/002EBC70-g8.c), replacing the INCLUDE_ASM in src/game/002E7018.c. - * Compare: python3 /workspace/rac2-orch/v2/cdiff.py func_002EBC70 - * - * Names are now right: retail's absolute words are lui 0x1B + 0x8BB0/0x8BB8 - * = D_001A8BB0/D_001A8BB8, and the final `sw zero` is the same D_001A8BB0 - * through $gp (D_001A8BB0_GP SDATA view). - * - * Remaining: retail previous=$v1, base/cursor=$a0, i=$a1; this build gives - * previous=$a0, base/cursor=$a1, i=$v1. Global queue here: i (pseudo 87, - * 7 refs / 15 insns) > previous (85, 7/17) > cursor (125, 7/22). The - * cursor's 22 is 11 doubled by update_equiv_regs: cse2 gives the giv init - * `cursor = base_copy + 396` a REG_EQUAL (const (plus D_001B8840 396)). - * Retail needs previous first and the cursor (or base 89) ahead of i. - * With 7 refs each that needs i live > 22 insns (impossible: the only - * earlier code is the func_002EB7E8 call), so retail's flow-time ref counts - * must differ (e.g. i 5 refs and born one insn earlier, or previous and the - * cursor both above 7). Tried without effect: i = 0 before the previous - * load, nested ifs, `continue` form; a SceneFrame *frame local drops the - * base copy; a `list = entries` local adds an addiu; repeated - * D_001B8840.entries[i] accesses raise the cursor to 9 refs (it then wins - * $v1) but leave a reload after the store. Pass-1 preferences - * (regs_someone_prefers) cannot help: every local pseudo near the loop - * is in $v0. - */ #include "common.h" /* One frame of the level transition loop: it re-links the queued entries to @@ -82,11 +51,13 @@ int func_002EBC70(int unused) i = 0; if (i < D_001B8840.count) { do { - entry = D_001B8840.entries[i]; - if (entry != 0 && prev != entry) { - entry->previous = prev; - prev = entry; - } + do { + entry = D_001B8840.entries[i]; + if (entry != 0 && prev != entry) { + entry->previous = prev; + prev = entry; + } + } while (0); i++; } while (i < D_001B8840.count); } diff --git a/src/game/002ED260.c b/src/game/002ED260.c index 7977d0b48..b0beefb55 100644 --- a/src/game/002ED260.c +++ b/src/game/002ED260.c @@ -119,5 +119,3 @@ void func_002ED4B8(void) offset += 80; } } - -INCLUDE_ASM("asm/game", func_002ED570); diff --git a/src/game/002ED578.c b/src/game/002ED578.c index 596bcc7a3..a20e212c6 100644 --- a/src/game/002ED578.c +++ b/src/game/002ED578.c @@ -47,20 +47,12 @@ s32 func_002ED688(u8 *a0) { /* func_002ED6B0 is in 002ED6B0.c: its call to func_002ED870 has to be an external one. */ -INCLUDE_ASM("asm/game", func_002ED848); - unsigned int func_002ED870(void) { return D_00214FCC; } -INCLUDE_ASM("asm/game", func_002ED880); - - -INCLUDE_ASM("asm/game", func_002ED8F0); - -INCLUDE_ASM("asm/game", func_002ED9A8); extern int D_00214F90[]; diff --git a/src/game/002EEB00.c b/src/game/002EEB00.c index 664897210..085384704 100644 --- a/src/game/002EEB00.c +++ b/src/game/002EEB00.c @@ -93,8 +93,6 @@ int func_002EEB00(int *a0) return s2; } -INCLUDE_ASM("asm/game", func_002EEBB0); - void func_002EED08(void) { @@ -210,9 +208,11 @@ ASM_FUNC("asm/game", func_002F0218); ASM_FUNC("asm/game", func_002F0468); -INCLUDE_ASM("asm/game", func_002F0B78); +/* Original assembly: lqc2/qmtc2/qmfc2 VU0 ops, $at as a working register and trapping addi. */ +ASM_FUNC("asm/game", func_002F0B78); -INCLUDE_ASM("asm/game", func_002F0D00); +/* Original assembly: $at as a working register and trapping add/addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002F0D00); void func_002F0E08(void) { @@ -272,11 +272,14 @@ INCLUDE_ASM("asm/game", func_002F3300); ASM_FUNC("asm/game", func_002F35B0); -INCLUDE_ASM("asm/game", func_002F3CF8); +/* Original assembly: $at as a working register (lw $at,off($a0)); the compiler cannot emit it. */ +ASM_FUNC("asm/game", func_002F3CF8); -INCLUDE_ASM("asm/game", func_002F3D20); +/* Original assembly: qmtc2 VU0 ops, $at as a working register and trapping addi/add. */ +ASM_FUNC("asm/game", func_002F3D20); -INCLUDE_ASM("asm/game", func_002F3E40); +/* Original assembly: qmtc2 VU0 op and trapping addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002F3E40); ASM_FUNC("asm/game", func_002F3E78); @@ -284,4 +287,5 @@ ASM_FUNC("asm/game", func_002F4F78); ASM_FUNC("asm/game", func_002F4FA0); -INCLUDE_ASM("asm/game", func_002F5118); +/* Original assembly: $at as a working register and trapping add/addi; the compiler cannot emit them. */ +ASM_FUNC("asm/game", func_002F5118); diff --git a/src/game/002F5220-7320.c b/src/game/002F5220-7320.c new file mode 100644 index 000000000..3f0e98b61 --- /dev/null +++ b/src/game/002F5220-7320.c @@ -0,0 +1,21 @@ +/* func_002F7320: needs -frac2-keep-block-zero-copy (cse keeps `i = result`); see docs/COMPILER-NOTES.md. */ +#include "common.h" + +typedef struct { + int key; + int values[3]; +} Func_002F7320Row; + +extern Func_002F7320Row ref_L00_002F7320_00[]; + +int func_002F7320(int value, int key, int field) +{ + int result = 0; + int i = result; + + while (ref_L00_002F7320_00[i].key != 0 && i < 56 && key != ref_L00_002F7320_00[i].key) + i++; + if (ref_L00_002F7320_00[i].key != 0) + result = value == ref_L00_002F7320_00[i].values[field]; + return result; +} diff --git a/src/game/002F5220.c b/src/game/002F5220.c index 5846594ce..5041a74a1 100644 --- a/src/game/002F5220.c +++ b/src/game/002F5220.c @@ -386,7 +386,6 @@ int func_002F6510(void) return result; } -INCLUDE_ASM("asm/game", func_002F7320); extern unsigned char D_001A7AB8[] MACRO_ADDR; extern unsigned char D_001A7AF8[] MACRO_ADDR; diff --git a/src/game/002FC3C0.c b/src/game/002FC3C0.c index 33e1e5ae4..836996806 100644 --- a/src/game/002FC3C0.c +++ b/src/game/002FC3C0.c @@ -48,12 +48,8 @@ void func_002FC410(Rac2Native_4e44694cc39e7084_u32 data_address, Rac2Native_4e44 ref_L00_0037B3B8_00 += 16; } -INCLUDE_ASM("asm/game", func_002FC460); - /* func_002FC468 is matched in 002FC468.c (-G0: D_001B22A8 is loaded absolutely). */ -INCLUDE_ASM("asm/game", func_002FC510); - void func_002FC518(Rac2Native_ae24050903bcaa08_u32 final_word) { *(Rac2Native_ae24050903bcaa08_u32 *)(ref_L00_0037B4C0_00 + 0) = 0x10000000u; @@ -79,16 +75,12 @@ void func_002FC560(Rac2Native_9da4b6b15b3cf4a0_RecordWord180 final_word, Rac2Nat ref_L00_0037B508_00 += 48; } -INCLUDE_ASM("asm/game", func_002FC618); - /* func_002FC620 is matched in 002FC620.c (-G0: its globals are read absolutely). */ -INCLUDE_ASM("asm/game", func_002FC868); - void func_002FC870(void) { *(Rac2Native_3646a0ca5397f72d_u32 *)(ref_L00_0037B818_00 + 0) = 0x3000000bu; diff --git a/src/game/0030F7B0.c b/src/game/0030F7B0.c index 6ee469f31..17b12b398 100644 --- a/src/game/0030F7B0.c +++ b/src/game/0030F7B0.c @@ -517,8 +517,6 @@ INCLUDE_ASM("asm/game", func_003136D0); /* func_003146C0 is in 0030F7B0-ball-g8.c. */ -INCLUDE_ASM("asm/game", func_00314CF8); - /* func_00314FD0 is in 0030F7B0-throw.c. */ @@ -693,6 +691,3 @@ void func_00316DA0(Vec16_Fc936841d *object, int index) Fc936841d_FUN_00282CF0(local, (char *)&object[index - 2], (char *)&object[index - 3]); Fc936841d_FUN_00282CC0((char *)&object[index - 1], (char *)&object[index - 2], local); } - - -INCLUDE_ASM("asm/game", func_003172D0); diff --git a/src/game/003173B0.c b/src/game/003173B0.c index e60b7bcc7..ff150f7f5 100644 --- a/src/game/003173B0.c +++ b/src/game/003173B0.c @@ -750,8 +750,6 @@ void func_0031D268(char *arg0) { /* func_0031D308 is in the -G8 sibling. */ -INCLUDE_ASM("asm/game", func_0031D350); - /* func_0031D3E0 is in 0031D3E0.c. */ /* func_0031D588 is in 0031D588-g8.c. */ @@ -905,8 +903,6 @@ void func_0031DEE8(char *owner) /* func_0031E560 is defined in 0031E560-dbg.c (-g). */ -INCLUDE_ASM("asm/game", func_0031E6D8); - void func_0031E750(char *p) diff --git a/src/game/0031F210.c b/src/game/0031F210.c index b344a710e..962030e51 100644 --- a/src/game/0031F210.c +++ b/src/game/0031F210.c @@ -593,8 +593,6 @@ INCLUDE_ASM("asm/game", func_00326A10); -INCLUDE_ASM("asm/game", func_00326CA8); - /* negates two floats read from a fixed global table, clamps each to [-1,1] into an object reached through the parameter's +104 pointer, packs the pair into a two-float stack buffer, passes it to two callees and stores the second callee's float return value at object+48 */ void func_00326CB8(char *obj) { diff --git a/src/game/00327038.c b/src/game/00327038.c index 827959d0c..117c9ac96 100644 --- a/src/game/00327038.c +++ b/src/game/00327038.c @@ -510,7 +510,9 @@ void func_00329F40(char *self) } } -INCLUDE_ASM("asm/game", func_0032A130); +void func_0032A130(void) +{ +} INCLUDE_ASM("asm/game", func_0032A140); diff --git a/src/game/00329768-g8.c b/src/game/00329768-g8.c index 69fc466ca..72c4af77c 100644 --- a/src/game/00329768-g8.c +++ b/src/game/00329768-g8.c @@ -139,6 +139,5 @@ void func_00329768(char *self) } break; } - /* The catalogue extent includes eight bytes before this return callback. */ - func_0027CFD0((char *)func_0032A130 + 8, self); + func_0027CFD0(func_0032A130, self); } diff --git a/src/game/0032EB28.c b/src/game/0032EB28.c index 461620f10..0cdf1fa70 100644 --- a/src/game/0032EB28.c +++ b/src/game/0032EB28.c @@ -190,8 +190,6 @@ INCLUDE_ASM("asm/game", func_0032F3D0); INCLUDE_ASM("asm/game", func_0032F598); -INCLUDE_ASM("asm/game", func_0032FDC0); - /* func_0032FEA8 uses small data in 0032EB28-g8.c. */ @@ -464,8 +462,6 @@ int func_003351B0(char *self, void *src, void *dst, int mode) return ret; } -INCLUDE_ASM("asm/game", func_00335270); - /* func_00335370 is defined in 00335370-copy.c. */ /* func_003353C8 uses the quadword-copy profile in 0032EB28-qcopy.c. */ @@ -506,8 +502,6 @@ void func_003355A8(int mode) } } -INCLUDE_ASM("asm/game", func_003356E8); - void func_00335840(void) { func_002704D0(); } diff --git a/src/game/00336A78.c b/src/game/00336A78.c index 3af7c0efb..ea7498b7c 100644 --- a/src/game/00336A78.c +++ b/src/game/00336A78.c @@ -374,8 +374,6 @@ void func_00338040(int object, int value, int count) func_00337E98_1((void *)inner, 1, limit, 255.0f, 80.0f); } -INCLUDE_ASM("asm/game", func_003380A8); - /* Formats text (with up to three extra strings) into a buffer, lays it out in the box with the font routine chosen by mode, optionally centres the box vertically on the screen, then draws a padded backing rectangle and frame behind it and lays the text out again on top. */ diff --git a/src/game/003399B0.c b/src/game/003399B0.c index a52ef32c1..4398a0a44 100644 --- a/src/game/003399B0.c +++ b/src/game/003399B0.c @@ -197,7 +197,52 @@ void *func_0033A4A0(char *p) } -INCLUDE_ASM("asm/game", func_0033A520); +typedef struct { float x, y, width, height; } TitlePosition; +extern void func_00336710(void *, void *, void *); +extern int func_00335E20(void *); +extern void func_003369A8(void *, void *, void *); +extern int *func_00336DA8(int, int); +extern int func_00336E40(void *); +extern float D_001B23A4 __attribute__((sda)); +/* Allocate the title position (scaled y, rounded) and set up its two labels. + * The scale is read after the x store: retail issues 300.0 before it. */ +void func_0033A520(unsigned char *obj, void *arg) +{ + float v; + TitlePosition *p; + char *text; + + *(int *)(obj + 0x1F8) = 0; + *(void **)(obj + 0x200) = arg; + if (arg != 0) { + int *alloc = func_00336DA8(16, func_00336E40(arg)); + *(int **)(obj + 0x1FC) = alloc; + alloc[1] = 0; + alloc[2] = 0; + alloc[3] = 0; + alloc[0] = 0; + } + do { + float position; + int y; + p = *(TitlePosition **)(obj + 0x1FC); + p->x = 70.0f; + position = 300.0f; + y = (int)(D_001B23A4 * position + 0.5f); + v = y; + } while (0); + text = D_001ADC88; + p = *(TitlePosition **)(obj + 0x1FC); + p->y = v; + func_00336710(obj + 0x134, text, *(void **)(obj + 0x200)); + func_00335F88(obj + 0x134, 24.0f, 24.0f, 0.0f, 0.0f); + *(int *)func_00335E20(obj + 0x134) = 0x60F0F0B0; + v = 65.0f; + *(float *)(obj + 0x204) = v; + func_003369A8(obj + 0x170, text, *(void **)(obj + 0x200)); + *(int *)func_00335E20(obj + 0x170) = 0x80F0F0F0; + func_00335F88(obj + 0x170, 0.7f, 0.7f, 0.0f, 0.0f); +} /* func_0033A688 is matched in 003399B0-g8.c (-G8 small data). */ diff --git a/src/game/0033AE20.c b/src/game/0033AE20.c index cf462291d..db39386d4 100644 --- a/src/game/0033AE20.c +++ b/src/game/0033AE20.c @@ -123,8 +123,6 @@ char *func_0033B0B8(char *object) /* func_0033B170 is matched in 0033AE20-g8.c (-G8 small data). */ -INCLUDE_ASM("asm/game", func_0033B538); - /* func_0033B540 is matched in 0033AE20-g8.c (-G8 small data). */ diff --git a/src/game/00345358.c b/src/game/00345358.c index d02c93675..1d6fc4563 100644 --- a/src/game/00345358.c +++ b/src/game/00345358.c @@ -494,8 +494,6 @@ float func_003495A0(Value_3495A0 *object) { return previous; } -INCLUDE_ASM("asm/game", func_003495B8); - /* Measured target: byte-identical across all 27 levels. */ void func_003495C0(u8 *a0, s32 a1) { *(s32 *)(a0 + 0x80) = a1; } @@ -951,8 +949,6 @@ void func_0034CE28(int *self, int value) } } -INCLUDE_ASM("asm/game", func_0034CE88); - /* Measured target: byte-identical across all 27 levels. */ void func_0034CE98(u8 *a0, s32 a1) { *(s32 *)(a0 + 0x2bc) = a1; } diff --git a/src/levels/01_oozla/L01_003DA740.c b/src/levels/01_oozla/L01_003DA740.c index 1d0144863..5a114da83 100644 --- a/src/levels/01_oozla/L01_003DA740.c +++ b/src/levels/01_oozla/L01_003DA740.c @@ -520,8 +520,6 @@ void func_L01_0041C960(u8 *a0) { /* func_L01_0041C970 is in L01_003DA740-g8.c. */ -INCLUDE_ASM("asm/levels", func_L01_0042C450); - /* func_L01_0042C540 is in L01_003DA740-campath-g8.c. */ /* func_L01_0042C8D8 is in L01_0042C8D8-g8.c. */ diff --git a/src/levels/10_hrugis_cloud/L10_003170D0.c b/src/levels/10_hrugis_cloud/L10_003170D0.c index cb4aa9d04..a41f928aa 100644 --- a/src/levels/10_hrugis_cloud/L10_003170D0.c +++ b/src/levels/10_hrugis_cloud/L10_003170D0.c @@ -517,7 +517,28 @@ void func_L10_00418AD8(u8 *arg0) { } -INCLUDE_ASM("asm/levels", func_L10_00419188); +extern u32 D_L10_001FB1E0[]; +extern u8 *D_001B251C_base[] __asm__("D_001B251C") __attribute__((sda)); + +void func_L10_00419188(u8 *arg0) +{ + u32 s0 = D_L10_001FB1E0[arg0[0x21]]; + s16 *p; + u8 *q; + + if (s0 == 0) { + return; + } + p = (s16 *)s0; + do { + q = D_001B251C_base[0] + (((*(u16 *)p & 0x7FFF) << 8)); + *(q + 0x20) = 2; + } while (*p++ >= 0); +} + +void func_L10_004191E0(void) +{ +} extern void func_L10_0041ED50(u8 *arg0); extern void func_L10_0041EE00(u8 *arg0); diff --git a/src/levels/16_snivelak/L16_00435CE8-g-g8.c b/src/levels/16_snivelak/L16_00435CE8-g-g8.c index c5d17c300..8f0b58bd5 100644 --- a/src/levels/16_snivelak/L16_00435CE8-g-g8.c +++ b/src/levels/16_snivelak/L16_00435CE8-g-g8.c @@ -163,10 +163,10 @@ extern f32 func_L01_002C81D0(f32, f32, f32); extern s32 func_00283CF0(f32); -extern void func_L16_0042FB58(f32, f32); - extern void func_L00_00424BB8(f32, f32); +extern void func_L16_0042FB10(f32, f32); + extern void func_L00_00424A88(s32, f32, f32); extern void func_L00_00424A08(s32, f32, f32); @@ -215,7 +215,7 @@ void func_L16_00435CE8(Moby_004402D8 *moby) break; } if (func_002ACBC8(D_00189E20.f80, vars->f28[i]) != 0) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); func_L00_00424A08(0, vars->f40, 0.003f); func_L00_00424A50(vars->f44, 0.003f); return; @@ -250,8 +250,8 @@ void func_L16_00435CE8(Moby_004402D8 *moby) } if (D_00189E20.f2294 == 0x5B && (D_00189E20.f49E == 0 || n >= 20)) { func_L00_00424B70(0.5f, 1.0f); - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); func_L00_00424A88(0, D_L23_001B1F14, 0.005f); func_L00_00424A08(1, D_L23_001B1F08, 0.01f); func_L00_00424A50(D_L23_001B1F0C, 0.01f); @@ -265,9 +265,9 @@ void func_L16_00435CE8(Moby_004402D8 *moby) func_L00_00424A88(0, D_L23_001B1F10, 0.03f); if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } d = func_00282E48(D_00189E20.f80, D_00189E20.fB0) - vars->f24; if (D_L23_001B1EEC < d) { @@ -287,8 +287,8 @@ void func_L16_00435CE8(Moby_004402D8 *moby) D_L23_001B234C = 0; } } else if (D_00189E20.f2294 == 0x81) { - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); if (D_001A79F0 == 16) { func_L00_00424A88(0, 0.5f, 0.04f); func_L00_00424A08(0, 4.0f, 0.002f); @@ -300,9 +300,9 @@ void func_L16_00435CE8(Moby_004402D8 *moby) } } else { if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } if (D_00189E20.f229C == 5) { func_L00_00424A08(0, 4.0f, 0.003f); diff --git a/src/levels/22_dobbo_orbit/L22_0042ACA0-g-g8.c b/src/levels/22_dobbo_orbit/L22_0042ACA0-g-g8.c index 1f28d092a..dfe3ab1e6 100644 --- a/src/levels/22_dobbo_orbit/L22_0042ACA0-g-g8.c +++ b/src/levels/22_dobbo_orbit/L22_0042ACA0-g-g8.c @@ -163,10 +163,10 @@ extern f32 func_L00_002D2A10(f32, f32, f32); extern s32 func_00283CF0(f32); -extern void func_L16_0042FB58(f32, f32); - extern void func_L00_00424BB8(f32, f32); +extern void func_L16_0042FB10(f32, f32); + extern void func_L00_00424A88(s32, f32, f32); extern void func_L00_00424A08(s32, f32, f32); @@ -215,7 +215,7 @@ void func_L22_0042ACA0(Moby_004402D8 *moby) break; } if (func_002ACBC8(D_00189E20.f80, vars->f28[i]) != 0) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); func_L00_00424A08(0, vars->f40, 0.003f); func_L00_00424A50(vars->f44, 0.003f); return; @@ -250,8 +250,8 @@ void func_L22_0042ACA0(Moby_004402D8 *moby) } if (D_00189E20.f2294 == 0x5B && (D_00189E20.f49E == 0 || n >= 20)) { func_L00_00424B70(0.5f, 1.0f); - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); func_L00_00424A88(0, D_L23_001B1F14, 0.005f); func_L00_00424A08(1, D_L23_001B1F08, 0.01f); func_L00_00424A50(D_L23_001B1F0C, 0.01f); @@ -265,9 +265,9 @@ void func_L22_0042ACA0(Moby_004402D8 *moby) func_L00_00424A88(0, D_L23_001B1F10, 0.03f); if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } d = func_00282E48(D_00189E20.f80, D_00189E20.fB0) - vars->f24; if (D_L23_001B1EEC < d) { @@ -287,8 +287,8 @@ void func_L22_0042ACA0(Moby_004402D8 *moby) D_L23_001B234C = 0; } } else if (D_00189E20.f2294 == 0x81) { - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); if (D_001A79F0 == 16) { func_L00_00424A88(0, 0.5f, 0.04f); func_L00_00424A08(0, 4.0f, 0.002f); @@ -300,9 +300,9 @@ void func_L22_0042ACA0(Moby_004402D8 *moby) } } else { if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } if (D_00189E20.f229C == 5) { func_L00_00424A08(0, 4.0f, 0.003f); diff --git a/src/levels/23_damosel_orbit/L23_0041E418.c b/src/levels/23_damosel_orbit/L23_0041E418.c index fc06176e2..296a2b09b 100644 --- a/src/levels/23_damosel_orbit/L23_0041E418.c +++ b/src/levels/23_damosel_orbit/L23_0041E418.c @@ -8,8 +8,6 @@ extern void func_00282DD8(float *, float *, float *); /* func_L23_0041E418 is defined in L23_0041E418-g8.c (this unit has no $gp access for it). */ -INCLUDE_ASM("asm/levels", func_L23_0041E538); - /* func_L23_0041E5B0 is defined in its dedicated source unit. */ char *func_L23_00422540(char *pos, char *dir, float *damage) { diff --git a/src/levels/23_damosel_orbit/L23_004402D8-g8.c b/src/levels/23_damosel_orbit/L23_004402D8-g8.c index cac570ce2..1555e0a8a 100644 --- a/src/levels/23_damosel_orbit/L23_004402D8-g8.c +++ b/src/levels/23_damosel_orbit/L23_004402D8-g8.c @@ -160,10 +160,10 @@ extern f32 func_L00_002D2A10(f32, f32, f32); extern s32 func_00283CF0(f32); -extern void func_L16_0042FB58(f32, f32); - extern void func_L00_00424BB8(f32, f32); +extern void func_L16_0042FB10(f32, f32); + extern void func_L00_00424A88(s32, f32, f32); extern void func_L00_00424A08(s32, f32, f32); @@ -210,7 +210,7 @@ void func_L23_004402D8(Moby_004402D8 *moby) break; } if (func_002ACBC8(D_00189E20.f80, vars->f28[i]) != 0) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); func_L00_00424A08(0, vars->f40, 0.003f); func_L00_00424A50(vars->f44, 0.003f); return; @@ -245,8 +245,8 @@ void func_L23_004402D8(Moby_004402D8 *moby) } if (D_00189E20.f2294 == 0x5B && (D_00189E20.f49E == 0 || n >= 20)) { func_L00_00424B70(0.5f, 1.0f); - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); func_L00_00424A88(0, D_L23_001B1F14, 0.005f); func_L00_00424A08(1, D_L23_001B1F08, 0.01f); func_L00_00424A50(D_L23_001B1F0C, 0.01f); @@ -260,9 +260,9 @@ void func_L23_004402D8(Moby_004402D8 *moby) func_L00_00424A88(0, D_L23_001B1F10, 0.03f); if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } d = func_00282E48(D_00189E20.f80, D_00189E20.fB0) - vars->f24; if (D_L23_001B1EEC < d) { @@ -282,8 +282,8 @@ void func_L23_004402D8(Moby_004402D8 *moby) D_L23_001B234C = 0; } } else if (D_00189E20.f2294 == 0x81) { - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); if (D_001A79F0 == 16) { func_L00_00424A88(0, 0.5f, 0.04f); func_L00_00424A08(0, 4.0f, 0.002f); @@ -295,9 +295,9 @@ void func_L23_004402D8(Moby_004402D8 *moby) } } else { if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } if (D_00189E20.f229C == 5) { func_L00_00424A08(0, 4.0f, 0.003f); diff --git a/src/levels/25_wupash_nebula/L25_00373ED0.c b/src/levels/25_wupash_nebula/L25_00373ED0.c index b22bffc1c..d8d35ad8e 100644 --- a/src/levels/25_wupash_nebula/L25_00373ED0.c +++ b/src/levels/25_wupash_nebula/L25_00373ED0.c @@ -1,11 +1,5 @@ #include "include_asm.h" -INCLUDE_ASM("asm/levels", func_L25_00373ED0); - -INCLUDE_ASM("asm/levels", func_L25_00373EE0); - -INCLUDE_ASM("asm/levels", func_L25_00373F08); - /* func_L25_003752D8, func_L25_00376FE0 and func_L25_00377608 live in the sibling small-data unit (L25_00373ED0-g8.c): their loop counts are read through $gp. */ diff --git a/src/levels/26_jamming_array/L26_0041C598-g-g8.c b/src/levels/26_jamming_array/L26_0041C598-g-g8.c index ec418a755..6a3aec406 100644 --- a/src/levels/26_jamming_array/L26_0041C598-g-g8.c +++ b/src/levels/26_jamming_array/L26_0041C598-g-g8.c @@ -163,10 +163,10 @@ extern f32 func_L00_002D2A10(f32, f32, f32); extern s32 func_00283CF0(f32); -extern void func_L16_0042FB58(f32, f32); - extern void func_L00_00424BB8(f32, f32); +extern void func_L16_0042FB10(f32, f32); + extern void func_L00_00424A88(s32, f32, f32); extern void func_L00_00424A08(s32, f32, f32); @@ -215,7 +215,7 @@ void func_L26_0041C598(Moby_004402D8 *moby) break; } if (func_002ACBC8(D_00189E20.f80, vars->f28[i]) != 0) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); func_L00_00424A08(0, vars->f40, 0.003f); func_L00_00424A50(vars->f44, 0.003f); return; @@ -250,8 +250,8 @@ void func_L26_0041C598(Moby_004402D8 *moby) } if (D_00189E20.f2294 == 0x5B && (D_00189E20.f49E == 0 || n >= 20)) { func_L00_00424B70(0.5f, 1.0f); - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); func_L00_00424A88(0, D_L23_001B1F14, 0.005f); func_L00_00424A08(1, D_L23_001B1F08, 0.01f); func_L00_00424A50(D_L23_001B1F0C, 0.01f); @@ -265,9 +265,9 @@ void func_L26_0041C598(Moby_004402D8 *moby) func_L00_00424A88(0, D_L23_001B1F10, 0.03f); if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } d = func_00282E48(D_00189E20.f80, D_00189E20.fB0) - vars->f24; if (D_L23_001B1EEC < d) { @@ -287,8 +287,8 @@ void func_L26_0041C598(Moby_004402D8 *moby) D_L23_001B234C = 0; } } else if (D_00189E20.f2294 == 0x81) { - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); if (D_001A79F0 == 16) { func_L00_00424A88(0, 0.5f, 0.04f); func_L00_00424A08(0, 4.0f, 0.002f); @@ -300,9 +300,9 @@ void func_L26_0041C598(Moby_004402D8 *moby) } } else { if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } if (D_00189E20.f229C == 5) { func_L00_00424A08(0, 4.0f, 0.003f); diff --git a/src/levels/30_insomniac_museum/L30_0032AAF0.c b/src/levels/30_insomniac_museum/L30_0032AAF0.c index 48b87ec23..b73a51ff5 100644 --- a/src/levels/30_insomniac_museum/L30_0032AAF0.c +++ b/src/levels/30_insomniac_museum/L30_0032AAF0.c @@ -101,8 +101,6 @@ extern D00138180_View D_00138180; extern float func_321018(float); -INCLUDE_ASM("asm/levels", func_L30_0032AAF0); - diff --git a/src/levels/shared/L00_002D7940.c b/src/levels/shared/L00_002D7940.c index 76ec756af..5ff4642bb 100644 --- a/src/levels/shared/L00_002D7940.c +++ b/src/levels/shared/L00_002D7940.c @@ -183,7 +183,8 @@ ASM_FUNC("asm/levels", func_L00_002E0200); /* func_L00_002E2048 (packed status field) is a near miss: nonmatching/levels/func_L00_002E2048.c */ -INCLUDE_ASM("asm/levels", func_L00_002E2048); +/* Original assembly: trapping addi; the compiler cannot emit it. */ +ASM_FUNC("asm/levels", func_L00_002E2048); INCLUDE_ASM("asm/levels", func_L00_002E2958); diff --git a/src/levels/shared/L00_002E5918.c b/src/levels/shared/L00_002E5918.c index 2c4854018..288a0a8f0 100644 --- a/src/levels/shared/L00_002E5918.c +++ b/src/levels/shared/L00_002E5918.c @@ -264,19 +264,23 @@ void func_L00_002ED808(void) { /* Original assembly: RAC1 game/math/fastfunc.c, func_001F9850. */ ASM_FUNC("asm/levels", func_L00_002EDC90); -INCLUDE_ASM("asm/levels", func_L00_002EDCB8); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fast_vector_math original assembly. */ +ASM_FUNC("asm/levels", func_L00_002EDCB8); /* Original assembly: RAC1 game/math/fastfunc.c, func_001F9850. */ ASM_FUNC("asm/levels", func_L00_002EDCC8); -INCLUDE_ASM("asm/levels", func_L00_002EDCF0); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fast_vector_math original assembly. */ +ASM_FUNC("asm/levels", func_L00_002EDCF0); /* Original assembly: RAC1 game/math/fastfunc.c, func_001F9850. */ ASM_FUNC("asm/levels", func_L00_002EDD00); -INCLUDE_ASM("asm/levels", func_L00_002EDD28); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fast_vector_math original assembly. */ +ASM_FUNC("asm/levels", func_L00_002EDD28); -INCLUDE_ASM("asm/levels", func_L00_002EDD38); +/* Original assembly: `lwc1; nop; jr $ra; mul.s` keeps a load-delay nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fast_vector_math original assembly. */ +ASM_FUNC("asm/levels", func_L00_002EDD38); /* func_L00_002EE050 (the two-argument float maximum) is matched in its own unit, src/levels/shared/L00_002EE050.c: it needs the -O1 -ffast-math @@ -286,7 +290,8 @@ ASM_FUNC("asm/levels", func_L00_002EE058); ASM_FUNC("asm/levels", func_L00_002EE078); -INCLUDE_ASM("asm/levels", func_L00_002EE0C0); +/* Original assembly: `sd; nop; jr $ra; sw` keeps a nop before the return that this cc1 never emits (MATCHING-BLOCKERS 4); its neighbours are RAC1 fast_vector_math original assembly. */ +ASM_FUNC("asm/levels", func_L00_002EE0C0); ASM_FUNC("asm/levels", func_L00_002EE290); diff --git a/nonmatching/levels/func_L00_00303990.c b/src/levels/shared/L00_002FC7A0-00303990-g16.c similarity index 77% rename from nonmatching/levels/func_L00_00303990.c rename to src/levels/shared/L00_002FC7A0-00303990-g16.c index e32442ef7..41961da89 100644 --- a/nonmatching/levels/func_L00_00303990.c +++ b/src/levels/shared/L00_002FC7A0-00303990-g16.c @@ -1,48 +1,6 @@ -/* Current retained result, 1 November 2026: 3392/3388 bytes. Preserve the level loader's heap-pointer - * return contract. An explicit goto form of the final loop measured 3380 bytes and lost required control- - * flow/alignment; keep the structured loop. GS-word allocation and macro-load loop padding remain - * unresolved. - * Not a functional-port qualification or a complete matching-build result. - * Profile: -O2 -G16 -Wa,-G16 -ffunction-sections. - * Earlier measurements below remain historical where superseded by this note. - */ -/* Retained nonmatching C, Claude Opus 5.5 xhigh, 31 October 2026 (task v1860). - * USA v1.01: 3392/3388 bytes, 0/27 places. Five rows differ, plus one extra nop. - * Unit: src/levels/shared/L00_00303990-g16.c, flags -O2 -G16 -Wa,-G16 -ffunction-sections. - * Declarations are below; the INCLUDE_ASM marker goes away when this unit is added. - * No PAL, v2.00 or linked check was run because USA does not match. - * - * Remaining differences: - * 1. 0x00303AF4: retail ors the first GS word into the low half (or v1,v1,v0; or v1,v1,t4; - * sd v1); here it lands in the high half's register (or v0,v1,v0). In mips.md the first - * operand of (ior:DI (sign_extend:DI ...) ...) is not a register, so local-alloc can only - * tie the result to the second operand. Retail's second word does tie that way (or a0,a1,a0). - * Tried without effect: lo |= hi, hi | lo, an int lo, RAC1's t/u form (transition.c), hi - * shared across blocks. A 64-bit lo with the constant in a variable made it much worse. - * 2. 0x00304350: retail has lw v0,0x30(s2) then daddu a0,s5,zero; here they are swapped. - * The copy is ready in the store's clock, so it issues with the sw and ahead of the load. - * Loading before the store gives lw/daddu/sw, so retail acts as if a scheduling boundary - * follows the sw, but no branch in retail targets 0x00304350. A do/while(0) around the copy - * (61 rows differ) is not that boundary. Reordering statements, base = dst + size, - * -fno-sched-interblock, -frac2-keep-block-order and -frac2-gcse-unsplit-edges all tie. - * 3. 0x00304674: one extra nop before the last loop's bne. Everything else in that loop is - * retail's. Retail's loop is seven words with lui/lw inside. mips_r5900_pad_loops counts - * the macro lw as one insn, so it sees six and pads. Likely a toolchain limit, because - * the pass counts insns and retail's assembler counted words; a word-counting fix is - * untested. Splitting the address does not help: a plain array gets its %hi shared by - * PRE into s1, and a macro entry test through a _1 alias with a split loop test - * (3388 bytes) gets its %hi hoisted into s1 (3 rows). A goto loop was not tried: with no - * loop note it should also lose the alignment nop retail has at 0x0030465C. - * - * Wordings that closed other differences; keep them: - * - (D_00139568[0xA] + D_L00_00262570)->b4 gives retail's add operand order. - * - func_L00_002FE268 takes the class value in a0 (other callers pass an argument too). - * - In loops 2-4 the value goes in a local before the store, so LD's %hi precedes the table's. - * - The slot stores run D_L00_001DD180, D_L00_001DA680, D_L00_001D9F00, which gives retail's - * sll order and registers. - * - D_L00_001B1EA0 is an incomplete MACRO_ADDR array, reloaded with lui/lw at both tests. - * -fno-gcse is far off (808 rows); -g and -frac2-qcopy do not change any differing row. - */ +/* Level loader: unpacks the level archive, uploads textures, builds the GS template words and + * the class/texture tables, and returns the next free heap pointer. The LD store goes before the + * fx/fy loads so combine keeps the first GS word's low half a DI register (retail's or tie). */ #include "common.h" typedef int TI128 __attribute__((mode(TI))); @@ -154,13 +112,13 @@ extern void func_002934B8(Bank *, int); extern void func_L00_002FE268(int); extern void func_00293260(Bank *, int); extern void func_L00_002FF6A8(char *, void *, void *, int); -extern void func_L00_00300610(); +extern void ref_L00_00303990_00(); extern void func_L00_002FFAB8(char *, void *, void *, void *, int); extern void func_00291DE0(void *, int); extern void func_L00_002FD480(char *); extern void func_00291CA8(void *, char *, void *, int); extern void func_0026FEB8(const char *, ...); -extern char *func_L00_00300618(int); +extern int func_L00_00300618(int); extern void func_L00_003032F0(void); extern void func_L00_00303418(int); extern void func_L00_00358B30(void); @@ -201,21 +159,15 @@ int func_L00_00303990(int load, int resume) func_00293000((char *)(f[4] + (int)f), h->i[0], h->i[0x84 / 4], (char *)h + h->i[1]); func_0011AEA0(0); used = func_0029D4D0((char *)(f[0x12] + (int)f), base); + LD->p[0x2C / 4] = base + h->i[0x60 / 4]; fx = D_001A72F4; fy = D_001A7304; - LD->p[0x2C / 4] = base + h->i[0x60 / 4]; - { - unsigned long long lo = (unsigned long long)((fy + h->i[0x90 / 4] * 4) >> 8 | 0x1DB08000); - unsigned long long hi = (unsigned long long)((fx + h->i[0x94 / 4]) >> 8) << 37 | 0x5C0000000ULL; - D_L00_001B1CF0[0] = (lo | hi) | 0x8000000000000000ULL; - } + D_L00_001B1CF0[0] = (int)((fy + h->i[0x90 / 4] * 4) >> 8) | 0x1DB08000 | ((long long)0xB800 << 19) | + ((long long)((fx + h->i[0x94 / 4]) >> 8) << 37) | 0x8000000000000000LL; D_L00_001B1CF0[1] = 0xFFA0000000E0ULL; D_L00_001B1CF0[2] = 0x40000400004000ULL; - { - unsigned long long lo = (unsigned long long)((fy + h->i[0x98 / 4] * 4) >> 8 | 0x19B04000); - unsigned long long hi = (unsigned long long)((fx + h->i[0x9C / 4]) >> 8) << 37 | 0x580000000ULL; - D_L00_001B1D08[0] = (lo | hi) | 0x8000000000000000ULL; - } + D_L00_001B1D08[0] = (int)((fy + h->i[0x98 / 4] * 4) >> 8) | 0x19B04000 | ((long long)0xB000 << 19) | + ((long long)((fx + h->i[0x9C / 4]) >> 8) << 37) | 0x8000000000000000LL; D_L00_001B1D08[1] = 0xFFA0000000E0ULL; D_L00_001B1D08[2] = 0x40000400004000ULL; @@ -337,7 +289,7 @@ int func_L00_00303990(int load, int resume) func_L00_002FF6A8(base + *(int *)q2, (char *)h + h->i[0x44 / 4], q2 + 0x10, *(int *)(q2 + 4)); if (D_L00_00226700[0] != 0) LD->i[0x3C / 4] = D_L00_00226700[0]; - func_L00_00300610((char *)h + h->i[0x24 / 4], h->i[0x20 / 4]); + ref_L00_00303990_00((char *)h + h->i[0x24 / 4], h->i[0x20 / 4]); for (i = 0, q2 = (char *)h + h->i[0x2C / 4]; i < h->i[0x28 / 4]; i++, q2 += 0x30) func_L00_002FFAB8(base + *(int *)q2, (char *)h + h->i[0x4C / 4], q2 + 0x10, q2 + 0x20, *(int *)(q2 + 4)); if (D_L00_0021EA20[0] != 0) @@ -376,9 +328,12 @@ int func_L00_00303990(int load, int resume) if (D_L00_001B24D4 != TEXBASE->i[0x18 / 4]) { char *dst; int size; - TEXBASE->p[0x10 / 4] = base; - size = h->i[0x30 / 4] * 16; + do { + TEXBASE->p[0x10 / 4] = base; + size = h->i[0x30 / 4]; + } while (0); dst = base; + size *= 16; base += size; func_00282B50(dst, (char *)h + h->i[0x34 / 4], size); TEXBASE->p[0x14 / 4] = base; @@ -426,7 +381,7 @@ int func_L00_00303990(int load, int resume) base = (char *)((unsigned int)end & ~0x3F); LD->p[0x48 / 4] = base; } - LD->p[0x68 / 4] = func_L00_00300618(load); + LD->i[0x68 / 4] = func_L00_00300618(load); if (load) D_00152CE4[0] = -1; if (TEXBASE->i[0xC / 4] != 0) { diff --git a/src/levels/shared/L00_002FC7A0.c b/src/levels/shared/L00_002FC7A0.c index fabab5001..9854080cc 100644 --- a/src/levels/shared/L00_002FC7A0.c +++ b/src/levels/shared/L00_002FC7A0.c @@ -761,7 +761,7 @@ int func_L00_00303388(unsigned char *object) /* func_L00_00303530 is defined in its own unit. */ -INCLUDE_ASM("asm/levels", func_L00_00303990); +/* func_L00_00303990 is defined in its own unit. */ /* Reads a record count from a per-level data root, indexes a fixed 332-byte-stride table with it, and when the int after position index is greater than the one at position index calls two helpers with the entry value added to a per-level base; returns 1. */ int func_L00_003046D0(int index) @@ -816,7 +816,75 @@ void func_L00_00308408(int x, int y0, int w, int h) { /* func_L00_00308538 is defined in its own unit. */ -INCLUDE_ASM("asm/levels", func_L00_00308700); +typedef int Q128 __attribute__((mode(TI))); + +typedef union { + struct { + int key; + int age; + unsigned char *data; + int pad; + } s; + Q128 q; +} Ent_308700; + +typedef struct { + unsigned char *base; + short *info; + char pad8[0x28 - 8]; + int active; + int pad2C; + Ent_308700 e[8]; +} Cache_308700; + +extern Cache_308700 D_L00_001C93A0; +extern int D_L00_001B18D8[] __attribute__((sda)); +extern void func_00297550(unsigned char *, int, unsigned char *, short *); + +int func_L00_00308700(int key) +{ + int found; + int best; + int i; + + if (D_L00_001C93A0.active == 0) + return 0; + do { + found = 0; + best = 0; + for (i = 0; i < 8; ++i) { + if (D_L00_001C93A0.e[i].s.key == key) + break; + if (D_L00_001C93A0.e[i].s.age < *(int *)((unsigned char *)&D_L00_001C93A0 + 0x34 + best * 16)) + best = i; + } + do { + if (i == 8) { + Cache_308700 *c = &D_L00_001C93A0; + unsigned char **dp = &c->e[0].s.data; + Ent_308700 *e; + Ent_308700 *e0; + int off = best << 4; + func_00297550(*(unsigned char **)((char *)dp + off), key, D_L00_001C93A0.base, c->info); + e0 = c->e; + e = (Ent_308700 *)((char *)e0 + off); + e->s.key = key; + i = best; + found = 1; + } + } while (0); + if (i != 0) { + Ent_308700 *base = D_L00_001C93A0.e; + Ent_308700 *other = base + i; + Q128 tmp = other->q; + other->q = base->q; + base->q = tmp; + } + } while (0); + D_L00_001C93A0.e[0].s.age = D_L00_001B18D8[0]; + return found; +} + /* rac1-decomp src/overlays/shared/menu_00249720.c: func_L00_0024B1B0 */ /* stores a value into a table slot chosen by the current index */ @@ -832,8 +900,6 @@ void func_L00_00309368(void) { } -INCLUDE_ASM("asm/levels", func_L00_00309DB0); - /* Call the registered handler with a table pointer built from one module base word plus the constant 36808, forwarding the incoming argument; do nothing when the base word is zero. */ void func_L00_0030C710(int argument) { diff --git a/src/levels/shared/L00_00316F60.c b/src/levels/shared/L00_00316F60.c index 1bd5dd5bf..b54009175 100644 --- a/src/levels/shared/L00_00316F60.c +++ b/src/levels/shared/L00_00316F60.c @@ -195,8 +195,6 @@ f32 func_L00_0031A6C8(f32 value, s32 count) { return 1.0f - product; } -INCLUDE_ASM("asm/levels", func_L00_0031A710); - /* func_L00_0031AA28 is defined in L00_0031AA28-curve.c. */ /* Blends a value toward a target: helper(second,first) halved, scaled by (1 - helper(third*pi)); the first argument and that product go to a two-float helper whose float result is returned. */ diff --git a/src/levels/shared/L00_00358D98.c b/src/levels/shared/L00_00358D98.c index ebd485501..0230b5dd6 100644 --- a/src/levels/shared/L00_00358D98.c +++ b/src/levels/shared/L00_00358D98.c @@ -383,19 +383,26 @@ int func_L00_00367720(void) { -INCLUDE_ASM("asm/levels", func_L00_0036BE28); +/* Original assembly: $at as a working register (lw $at,off($a0)) and lui $ra in the return delay slot. */ +ASM_FUNC("asm/levels", func_L00_0036BE28); -INCLUDE_ASM("asm/levels", func_L00_0036C9AC); +/* Original assembly: $at as a working register (lw $at,off($a0)) and lui $ra in the return delay slot. */ +ASM_FUNC("asm/levels", func_L00_0036C9AC); -INCLUDE_ASM("asm/levels", func_L00_0036C9D4); +/* Original assembly: $at as a working register (lw $at,off($a0)) and lui $ra in the return delay slot. */ +ASM_FUNC("asm/levels", func_L00_0036C9D4); -INCLUDE_ASM("asm/levels", func_L00_0036D274); +/* Original assembly: $at as a working register (lw $at,off($a0)) and lui $ra in the return delay slot. */ +ASM_FUNC("asm/levels", func_L00_0036D274); -INCLUDE_ASM("asm/levels", func_L00_0036D29C); +/* Original assembly: $at as a working register (lw $at,off($a0)) and lui $ra in the return delay slot. */ +ASM_FUNC("asm/levels", func_L00_0036D29C); -INCLUDE_ASM("asm/levels", func_L00_0036EF40); +/* Original assembly: $at as a working register (lw $at,off($a0)) and lui $ra in the return delay slot. */ +ASM_FUNC("asm/levels", func_L00_0036EF40); -INCLUDE_ASM("asm/levels", func_L00_0036EF68); +/* Original assembly: $at as a working register and trapping add/addi; the compiler cannot emit them. */ +ASM_FUNC("asm/levels", func_L00_0036EF68); unsigned int func_L00_0036F480(void) { diff --git a/src/levels/shared/L00_003A8E28.c b/src/levels/shared/L00_003A8E28.c index 49386d22c..7a5f4f1ba 100644 --- a/src/levels/shared/L00_003A8E28.c +++ b/src/levels/shared/L00_003A8E28.c @@ -334,7 +334,6 @@ int func_L00_003AE550(char *motion, char *object, int mode) return 0; } -INCLUDE_ASM("asm/levels", func_L00_003AE900); /* func_L00_003B0A28 is defined in L00_003B0A28-g8.c. */ diff --git a/nonmatching/levels/func_L00_003AE900.c b/src/levels/shared/L00_003AE900-g8.c similarity index 89% rename from nonmatching/levels/func_L00_003AE900.c rename to src/levels/shared/L00_003AE900-g8.c index 903f8c5e2..f1a4fbeb1 100644 --- a/nonmatching/levels/func_L00_003AE900.c +++ b/src/levels/shared/L00_003AE900-g8.c @@ -1,20 +1,5 @@ -/* Per-frame update of the hero-steered bot (class 0x81E): flight, collision, - * attachment, idle effects and self-destruct burst. Not functional-gated. - * USA v1.01/v2.00: 8,432/8,440 bytes, 0/27 placements in each, 2026-11-01. - * Compile separately as L00_003AE900-g8.c: -O2 -G8 -ffunction-sections. - * Earlier retained source: 8,412 bytes. Normal assignments of the aligned - * 0x50-byte templates use the current compiler's quadword block moves; both copy - * loops now reproduce retail. Keep the full templates and real matrix buffers. - * The collision test and following state-4 test are separate: the call may change - * the state. The old nested-if/else form incorrectly skipped the reload on failure. - * Sound slots have a 0x70-byte stride after the runtime's 0x70-byte header. - * Remaining: one FPR save/frame size, held-pose matrix pointer allocation, colour - * constant folding in the spray loops, and sound-index register allocation. - * Byte-sized colour locals do not resolve the constants. Diagnostic regalloc - * dumps reproduce the normal object; none of this qualifies the complete body. - * Earlier trials with flat matrix arrays, pointer locals and one/two-level inline - * helpers did not settle the held-pose registers; do not repeat them unchanged. - */ +/* Per-frame update of the hero-steered bot (class 0x81E): flight, collision, attachment, + idle effects and self-destruct burst. Own unit: it reaches the level's globals through $gp. */ #include "common.h" typedef int TI128_AE900 __attribute__((mode(TI))); @@ -119,7 +104,7 @@ typedef struct { } HitAE900; /* 0xE0-byte weapon record: +4 upgraded flag, +0x70 a rate. */ -typedef struct { char pad00[4]; unsigned char upgraded; char pad05[0x6B]; float rate; char pad74[0x6C]; } WeaponAE900; +typedef struct { char pad00[4]; unsigned char upgraded; char pad05[0x6B]; float rate; char pad74[0x6C]; } WeaponAE900 __attribute__((aligned(16))); /* Sound state has a 0x70-byte header followed by 52 0x70-byte voices. */ typedef struct { @@ -128,9 +113,9 @@ typedef struct { char unknown05[0x13]; MobyAE900 *owner; char unknown1C[0x54]; -} SlotAE900; +} SlotAE900 __attribute__((aligned(16))); typedef struct { char header[0x70]; SlotAE900 slots[52]; } SoundAE900; -#define SLOT_AE900(i) (&D_00188660.slots[(i)]) +#define SLOT_AE900(i) (D_00188660.slots[(i)]) /* 0x50-byte effect template copied to the stack for func_00312B70. */ typedef struct { VecAE900 v; char rest[0x40]; } TemplateAE900; @@ -141,7 +126,7 @@ typedef struct { float v[4]; } RatesAE900; /* Camera shake record: +0x160 amount, +0x168 frames, +0x16C counter. */ typedef struct { char pad000[0x160]; float amount; char pad164[4]; int frames; int counter; } ShakeAE900; -#define WEAPON_AE900 (D_00262570[D_00139568[0x22]]) +#define WEAPON_AE900 (*(D_00262570 + D_00139568[0x22])) extern HeroAE900 D_00189E20; extern unsigned char D_00139568[]; @@ -223,7 +208,7 @@ extern float func_00283B98(float, float); extern void func_002A9850(void *, void *, void *, int, int, int, int, int, float, float, float); extern float func_002A8A20(void *); extern int func_002AAFA0(unsigned int, int); -extern char *func_002BCB00(float, void *, void *, int, int, int, int, int, int, int); +extern char *func_002BCB00(void *, void *, int, int, float, int, int, int, int, int); extern void func_002ABBB8(void *, void *, void *, float, float, int, int, int, float, float, float, float, int, float, int, int, int, int, int); extern int func_00283CF0(float); extern char *func_002BCF18(void *, void *, int, int, float, int, int); @@ -233,25 +218,33 @@ extern void func_002A9288(void *, float); /* Leaves the current state: stops the owned sound and resets the fall. */ #define DETACH_AE900() \ - do { \ + { \ int sound; \ moby->state = 0; \ sound = vars->sound; \ if (sound != -1) { \ - if (SLOT_AE900(sound)->owner == moby && SLOT_AE900(sound)->active) \ + if (SLOT_AE900(sound).owner == moby && SLOT_AE900(sound).active) \ func_002E59F8(sound); \ } \ vars->sound = -1; \ vars->timer34 = 0x78; \ vars->vel.f[2] = 0.0f; \ - } while (0) + } -/* Packs a particle colour (0xAABBGGRR); the components are not folded before the loops hoist them. */ -static __inline__ int RgbaAE900(int r, int g, int b, int a) +/* Rotation matrix for half a turn about X. */ +static __inline__ void HalfTurnAE900(VecAE900 *m) { - int c = (a << 24) | (g << 8) | (b << 16); + VecAE900 turn; - return c | r; + turn.q = 0; + turn.f[0] = PI_AE900; + func_00283410(m, &turn); +} + +/* Copies the owner's matrix into dst. */ +static __inline__ void OwnerMatrixAE900(VecAE900 *dst, MobyAE900 *owner) +{ + func_00283658(dst, owner->matrix); } /* While held (state 1): the bot's matrix is its owner's, turned half a turn about X. */ @@ -259,14 +252,14 @@ static __inline__ void AlignToOwnerAE900(MobyAE900 *moby, VarsAE900 *vars) { VecAE900 m1[4]; VecAE900 m2[4]; - VecAE900 turn; - - turn.q = 0; - turn.f[0] = PI_AE900; - func_00283410(m1, &turn); - func_00283658(m2, vars->owner->matrix); - func_00283788(m1, m2, m1); - func_00283678(moby->matrix, m1); + VecAE900 *rot = m1; + VecAE900 *own; + + HalfTurnAE900(rot); + own = m2; + OwnerMatrixAE900(own, vars->owner); + func_00283788(rot, own, rot); + func_00283678(moby->matrix, rot); } void func_L00_003AE900(MobyAE900 *moby) @@ -405,8 +398,6 @@ void func_L00_003AE900(MobyAE900 *moby) func_002BFB38(&t120, &t130, func_002A77E0(2), life); } } else if (vars->inWater != 0 || func_00278E78() != 0) { - MobyAE900 *hitMoby; - if (D_L00_001BF200.hit) { if (func_002ABB78(D_L00_001BF200.hit) || (D_L00_001BF200.hit->flags & 0x1000)) { if (D_L00_001BF200.hit->oClass != moby->oClass && D_L00_001BF200.hit != D_00189E20.moby @@ -420,9 +411,8 @@ void func_L00_003AE900(MobyAE900 *moby) } } } - hitMoby = D_L00_001BF200.hit; - if (hitMoby && hitMoby->oClass == moby->oClass) { - func_00282CF0(&D_L00_001BF200.normal, &moby->pos, &hitMoby->pos); + if (D_L00_001BF200.hit && D_L00_001BF200.hit->oClass == moby->oClass) { + func_00282CF0(&D_L00_001BF200.normal, &moby->pos, &D_L00_001BF200.hit->pos); if (vars->vel.f[2] < -9.8f * FRAME_AE900) { moby->bBC = 1; qcopy(&moby->pos, &D_L00_001BF200.point); @@ -440,7 +430,7 @@ void func_L00_003AE900(MobyAE900 *moby) qcopy(&t130, &D_L00_001BF200.normal); goto align; } - } else if ((hitMoby && hitMoby != D_00189E20.moby && hitMoby != vars->owner) || D_L00_001BF200.count > 0) { + } else if ((D_L00_001BF200.hit && D_L00_001BF200.hit != D_00189E20.moby && D_L00_001BF200.hit != vars->owner) || D_L00_001BF200.count > 0) { if (vars->inWater != 0 || func_00278E78() == 0 || vars->vel.f[2] < -9.8f * FRAME_AE900) { moby->bBC = 1; qcopy(&moby->pos, &D_L00_001BF200.point); @@ -460,9 +450,15 @@ void func_L00_003AE900(MobyAE900 *moby) func_00282D30(&vars->vel, &vars->vel, 0.6f); vars->vel.f[2] *= 0.5f; if (vars->amp == 0.0f) { + float ph; + vars->amp = func_00282C48(t150.f[2]) * 2.0f; - vars->phase = (t150.f[2] > 0.0f) ? 45.0f * DEG_AE900 : -135.0f * DEG_AE900; + ph = -2.3561947f; + if (0.0f < t150.f[2]) { + ph = 0.78539824f; + } vars->frame = D_L00_001B19C8; + vars->phase = ph; } func_00282F20(&t120, &D_L00_001BF200.normal, 1.0f); if (func_00282DB0(&t120, &up) > 0.707f) { @@ -668,6 +664,12 @@ void func_L00_003AE900(MobyAE900 *moby) if (vars->inWater != 0) { float surface; int i; + int j; + int l; + int cb; + int cg; + int cr; + int c; t120.q = moby->pos.q; t120.f[2] += 3.5f; @@ -681,36 +683,45 @@ void func_L00_003AE900(MobyAE900 *moby) func_00282F20(&t130, &t130, func_002A7878(4.0f * FRAME_AE900, 8.0f * FRAME_AE900)); func_002BF728(&moby->pos, &t130, func_002A7878(0.05f, 0.1f) * 210000.0f, surface); } - { - int low = 0x60; - int high = 0x7F; - - for (i = 0; i < 150; i++) { - float r; - float a; + cr = 0x60; + cg = 0x60; + cb = 0x7F; + for (j = 0; j < 150; j++) { + float rr; + float ang; + float half; + int c1; + int c2; t140.q = 0; t140.f[0] = func_002A7878(-0.75f * FRAME_AE900, 0.75f * FRAME_AE900); t140.f[1] = func_002A7878(-0.75f * FRAME_AE900, 0.75f * FRAME_AE900); t140.f[2] = func_002A7878(4.0f * FRAME_AE900, 16.0f * FRAME_AE900); t130.q = t140.q; - r = func_002A7878(0.0f, 0.35f); - a = func_002A7940(); - t140.f[0] = func_00283180(a) * r; - t140.f[1] = func_00283198(a) * r; + rr = func_002A7878(0.0f, 0.35f); + half = 0.5f; + ang = func_002A7940(); + t140.f[0] = func_00283180(ang) * rr; + t140.f[1] = func_00283198(ang) * rr; t140.f[2] = 0.0f; func_00282CC0(&t140, &t140, &moby->pos); - t140.f[2] = surface + 0.5f; - t130.f[2] -= r * (8.0f * FRAME_AE900); + t140.f[2] = surface + half; + t130.f[2] -= rr * (8.0f * FRAME_AE900); + c1 = (0x16 << 24) | (cb << 16) | (cg << 8); + c2 = (cb << 16) | (cg << 8); func_L00_0033AA40(&t140, &t130, 0, func_002A7878(0.35f, 1.25f), surface, - RgbaAE900(low, low, high, 0x16), 1.0f / 180.0f, RgbaAE900(low, low, high, 0), 1); + c1 | cr, 1.0f / 180.0f, c2 | cr, 1); } - for (i = 0; i < 20; i++) { - int c1; - int c2; + c = (0x7F << 24) | (cb << 16) | (cg << 8); + for (l = 0; l < 20; l++) { + int c1 = func_L00_0031C998(0x7F000000, c | cr, func_002A7878(0.25f, 1.0f)); + int c2 = func_L00_0031C998(0, ((cb / 2) << 16) | ((cg / 2) << 8) | (cr / 2), + func_002A7878(0.5f, 1.0f)); + float sz; + int life; + char **defs; + int tex; - c1 = func_L00_0031C998(0x7F000000, RgbaAE900(low, low, high, high), func_002A7878(0.25f, 1.0f)); - c2 = func_L00_0031C998(0, RgbaAE900(low >> 1, low >> 1, high >> 1, 0), func_002A7878(0.5f, 1.0f)); t140.f[0] = func_002A7878(-3.0f, 3.0f); t140.f[1] = func_002A7878(-3.0f, 3.0f); t140.f[2] = func_002A7878(4.0f * FRAME_AE900, 14.0f * FRAME_AE900); @@ -720,9 +731,11 @@ void func_L00_003AE900(MobyAE900 *moby) t130.f[2] = surface; c1 = func_002AAFA0(c1, WEAPON_AE900.upgraded != 0); c2 = func_002AAFA0(c2, WEAPON_AE900.upgraded != 0); - func_002BCB00(func_002A7878(0.15f * 210000.0f, 0.25f * 210000.0f), &t130, &t140, c1, c2, - func_002A7820(90, 150), 1, *(unsigned char *)*(char **)(D_L00_001FE940 + 0x2C), -1, 0); - } + sz = func_002A7878(0.15f * 210000.0f, 0.25f * 210000.0f); + life = func_002A7820(90, 150); + defs = (char **)D_L00_001FE940; + tex = *(unsigned char *)defs[11]; + func_002BCB00(&t130, &t140, c1, c2, sz, life, 1, tex, -1, 0); } } else if (water + 2.0f < moby->pos.f[2]) { func_00282C88(&t120); @@ -770,13 +783,15 @@ void func_L00_003AE900(MobyAE900 *moby) break; } case 2: { - int color = 0x5FF8F8F8; + int color; int c1; int c2; float f; + int roll = func_002A77E0(100); - if (func_002A77E0(100) > 39) - color = 0x2F486078; + color = 0x2F486078; + if (roll <= 39) + color = 0x5FF8F8F8; c1 = func_002AAFA0(color, WEAPON_AE900.upgraded != 0); c2 = func_002AAFA0(0x0F000020, WEAPON_AE900.upgraded != 0); f = scale * 150000.0f; diff --git a/src/levels/shared/L00_003B3158-collide.c b/src/levels/shared/L00_003B3158-collide.c new file mode 100644 index 000000000..215b6163f --- /dev/null +++ b/src/levels/shared/L00_003B3158-collide.c @@ -0,0 +1,44 @@ +#include "common.h" + +typedef int Quad __attribute__((mode(TI))); +typedef struct { char pad00[0xb0]; float origin[4]; char padc0[0x21d0]; int mask; } CollisionState; +extern CollisionState D_00189E20; +extern Quad D_L00_001BF230[2]; +extern int D_L00_001A8FF0[] __attribute__((sda)); +extern int func_00277258(void *,int,float,void *); +extern void func_00282CF0(float *,void *,void *); +extern void func_00282F20(float *,float *,float); +extern float func_00282DB0(float *,float *); +extern void func_00282D30(float *,float *,float); +extern void func_00283028(void *,void *,void *); +extern void func_00282CC0(void *,void *,void *); + +typedef struct { char pad[0x10]; Quad position; char pad20[0x48]; char *data; } CollisionObject; + +void func_L00_003B39D0(CollisionObject *object) +{ + float normal[4],projection[4],remaining[4]; + char *data=object->data; + void *position=&object->position; + int collided; + collided = func_00277258(position,0,0.25f,(void *)D_00189E20.mask); + if (collided) { + qcopy(position,D_L00_001BF230); + if(D_L00_001A8FF0[0]) { + float dot; + char *vector=data+0x30; + func_00282CF0(normal,D_00189E20.origin,position); + func_00282F20(normal,normal,1.0f); + dot=func_00282DB0(normal,(float *)vector); + func_00282D30(projection,normal,dot); + func_00282CF0(remaining,vector,projection); + func_00283028(vector,remaining,&D_L00_001BF230[1]); + func_00282CC0(vector,vector,projection); + } else { + float vertical=*(float *)(data+0x38); + *(float *)(data+0x38)=0; + func_00283028(data+0x30,data+0x30,&D_L00_001BF230[1]); + *(float *)(data+0x38)=vertical; + } + } +} diff --git a/src/levels/shared/L00_003B3158.c b/src/levels/shared/L00_003B3158.c index 28542fabb..661099047 100644 --- a/src/levels/shared/L00_003B3158.c +++ b/src/levels/shared/L00_003B3158.c @@ -100,7 +100,6 @@ extern void func_310440(); -INCLUDE_ASM("asm/levels", func_L00_003B39D0); diff --git a/src/levels/shared/L00_004224D0-main-g8.c b/src/levels/shared/L00_004224D0-main-g8.c index 1ca9645c7..896b59dea 100644 --- a/src/levels/shared/L00_004224D0-main-g8.c +++ b/src/levels/shared/L00_004224D0-main-g8.c @@ -125,7 +125,7 @@ extern void func_00282CC0(void *,void *,void *), func_00282CF0(void *,void *,voi extern int func_00277F48(void *,int,int,int,float); extern char *func_002AB1F0(char *); extern void func_L00_00423038(int); -/* func_L00_00424BB8 in most levels; its twin func_L16_0042FB58 in levels 16, 22, 23 and 26. */ +/* func_L00_00424BB8 in every level; levels 16, 22, 23 and 26 also have the q+0x20 setter func_L16_0042FB10. */ extern void ref_L00_004224D0_00(float,float); extern void func_L00_00424B20(float); extern void func_L00_00424C60(void),func_L00_00424C28(void),func_L00_00424C00(void); diff --git a/src/levels/shared/L00_004224D0.c b/src/levels/shared/L00_004224D0.c index 0b118d64a..79f64d29b 100644 --- a/src/levels/shared/L00_004224D0.c +++ b/src/levels/shared/L00_004224D0.c @@ -120,7 +120,6 @@ void func_L00_00423038(int reposition) /* func_L00_00423038 is in a separate compilation unit. */ -INCLUDE_ASM("asm/levels", func_L00_00423290); /* func_L00_004233F8 is in L00_004233F8-g8.c. */ @@ -301,7 +300,22 @@ void func_L00_00424B70(float a, float b) } } -INCLUDE_ASM("asm/levels", func_L00_00424BB8); +void func_L00_00424BB8(float a, float b) +{ + char *p = D_L00_001B8E10; + + if (*(short *)(p + 134) == 0) { + char *q = *(char **)(p + 112); + char *r = q + 0x60; + + if (a != 0.0f) { + *(float *)(r + 228) = a; + } + if (b != 0.0f) { + *(float *)(r + 232) = b; + } + } +} void func_L00_00424C00(void) { diff --git a/src/levels/shared/L00_00423290-qcopy.c b/src/levels/shared/L00_00423290-qcopy.c new file mode 100644 index 000000000..d4da5ddd0 --- /dev/null +++ b/src/levels/shared/L00_00423290-qcopy.c @@ -0,0 +1,80 @@ +#include "common.h" +/* Camera id/state fields are independently observed at the same offsets + * as the public RAC1 Camera prefix (origin/main 1d8228cc). */ +typedef struct { + unsigned char bytes00[0x70]; + char *state; + unsigned char bytes74[0x12]; + short id; +} CameraInitPrefix; +extern unsigned char D_00189E20[]; + + +#ifndef RAC2_T_V4_F0FBA48D3 +#define RAC2_T_V4_F0FBA48D3 +typedef int V4_F0fba48d3 __attribute__((mode(TI))); +#endif + +extern void func_00282CF0_2(void *b, void *c, void *d); + +extern void func_00282CC0(void *c, void *c2, void *s); + +extern void func_00282D30(void *dst, void *src, float k); + +extern float func_00282DB0_1(char *local, char *p); + +extern void func_00282C88(void *a); + + + + + +void func_L00_00423290(CameraInitPrefix *camera) +{ + char *obj; + char *v60; + char *vB0; + char *vF0; + char *v160; + char *hero; + char *pos; + char *hpos; + V4_F0fba48d3 *dst; + char buf0[16]; + char buf1[16]; + + if (camera->id != 0) + return; + + hero = (char *)D_00189E20 + 0x2C0; + pos = camera->state; + v160 = pos + 0x160; + v60 = pos + 0x60; + obj = pos; + pos = buf0; + + func_00282D30(pos, hero, -1.0f); + /* The hero's position, 0x240 below the facing direction the call above uses. */ + hpos = hero - 0x240; + *(V4_F0fba48d3 *)v60 = *(V4_F0fba48d3 *)hpos; + dst = (V4_F0fba48d3 *)(obj + 0xC0); + *dst = *(V4_F0fba48d3 *)v60; + vB0 = obj + 0xB0; + vF0 = obj + 0xF0; + func_00282D30(obj + 0x70, buf0, func_00282DB0_1(v60, buf0)); + func_00282C88(obj + 0xD0); + func_00282C88(obj + 0xE0); + func_00282C88(obj + 0x100); + func_00282D30(buf1, buf0, *(float *)(v160 + 0x30)); + func_00282CC0(vB0, buf1, v60); + func_00282D30(buf1, buf0, *(float *)(v60 + 0xB0)); + func_00282CC0(vF0, buf1, v60); + dst = (V4_F0fba48d3 *)(obj + 0xA0); + *dst = *(V4_F0fba48d3 *)vF0; + func_00282CF0_2(v160, (char *)camera + 0x30, vB0); + dst = (V4_F0fba48d3 *)(obj + 0x170); + *dst = *(V4_F0fba48d3 *)v160; + *(V4_F0fba48d3 *)obj = *(V4_F0fba48d3 *)((char *)camera + 0x30); + func_00282CC0(obj + 0x210, vB0, v160); + *(int *)(obj + 0x240) = 0; +} diff --git a/src/levels/shared/L01_002A7248.c b/src/levels/shared/L01_002A7248.c index 2bac90e4f..1dbd530db 100644 --- a/src/levels/shared/L01_002A7248.c +++ b/src/levels/shared/L01_002A7248.c @@ -874,7 +874,8 @@ INCLUDE_ASM("asm/levels", func_L01_002F1588); -INCLUDE_ASM("asm/levels", func_L01_00304270); +/* Original assembly: level copy of func_0029D7C0 (RAC1 miscproc func_0020C758): live-in $v1 and unconditional `teq` traps. */ +ASM_FUNC("asm/levels", func_L01_00304270); /* Defined in L01_00310BC0.c. */ @@ -1115,7 +1116,44 @@ void func_L01_0031AB20(char *m, MotionState *state, int path, float height, floa } } -INCLUDE_ASM("asm/levels", func_L01_0031B300); +typedef int TI128 __attribute__((mode(TI))); +typedef union { TI128 q; float f[4]; } Vector; +extern float func_00282C48(float f12); + +int func_L01_0031B300(void *a0, void *a1, void *a2, void *a3) { + Vector v, w; + float f20; + float f2; + char *g; + char *h; + char *p; + int v1; + + if (func_002761F8(a2, a3, 0x10, a0, 0) == 0) + goto fail; + g = (char *)&D_L01_001BF900; + p = *(char **)(g + 0x18); + if (p != 0) { + v1 = *(short *)(p + 0xAA); + if (v1 == 0x881 || v1 == 0) + return 0; + f20 = *(float *)(a0 + 0x18); + } else { + f20 = *(float *)(a0 + 0x18); + } + qcopy(&w, g + 0x40); + h = g + 0x40; + func_00282F20(w.f, w.f, 1.0f); + func_00282CF0(&v, a3, g + 0x20); + f2 = func_00282C48(func_00282DB0(v.f, w.f)); + func_00282F20(w.f, (float *)h, f2); + func_00282CC0(a0 + 0x10, a0 + 0x10, &w); + *(float *)(a0 + 0x18) = f20; + return 1; +fail: + return 0; +} + int func_L01_0031BC68(int a0, int a1, float phase) { float v = func_00283198(phase); @@ -1299,7 +1337,7 @@ void func_L01_00324410(char *out, char *src, int *nums) } -INCLUDE_ASM("asm/levels", func_L01_00324550); +/* func_L01_00324550 is in L01_00324550-narrowsave.c. */ /* func_L01_003245E0 is defined in L01_002A7248-g8.c (this unit has no $gp access for it). */ diff --git a/src/levels/shared/L01_00324550-narrowsave.c b/src/levels/shared/L01_00324550-narrowsave.c new file mode 100644 index 000000000..0a9ce0e8e --- /dev/null +++ b/src/levels/shared/L01_00324550-narrowsave.c @@ -0,0 +1,19 @@ +/* func_L01_00324550: variadic, built with -mastra-quad-saves and -frac2-narrow-saves-below. + register_precision keeps $ra's save at 64 bits; the narrower save takes the lower slot. */ +#include "common.h" +extern int func_00288FB8(int); +extern void func_L01_00324410(char *, char *, int *); +extern void func_0028BCA0(int); +extern void func_0026FEB8(const char *, ...); +extern const char D_001AA590[]; +void func_L01_00324550(int id, ...) __attribute__((register_precision(ra, 64))); +void func_L01_00324550(int id, ...) +{ + char text[0x200]; + char *format = (char *)func_00288FB8(id); + if (format) { + /* The seven saved integer argument slots are forwarded. */ + func_L01_00324410(text, format, (int *)((char *)__builtin_next_arg(id) - 0x38)); + func_0028BCA0((int)text); + } else func_0026FEB8(D_001AA590, id); +} diff --git a/src/levels/shared/L01_00397110.c b/src/levels/shared/L01_00397110.c index 33b210a21..49e7c6f2f 100644 --- a/src/levels/shared/L01_00397110.c +++ b/src/levels/shared/L01_00397110.c @@ -111,7 +111,28 @@ void func_L01_003BD178(char *m, void *position, int count, -INCLUDE_ASM("asm/levels", func_L01_003D6B00); +typedef union { int whole __attribute__((mode(TI))); float f[4]; } EffectVector; +extern void func_L00_003263D0(void *, void *, float, int, int, void *, float, float, unsigned int, void *, float); + +void func_L01_003D6B00(char *object, int count, float low, float high, float radius, float speed) +{ + EffectVector position, velocity; + float angle; + int i; + position.whole = 0; + velocity.whole = 0; + for (i = 0; i < count; i++) { + angle = func_002A7878(-3.1415927410125732f, 3.1415927410125732f); + position.f[0] = radius * func_00283180(angle); + position.f[1] = radius * func_00283198(angle); + position.f[2] = func_002A7878(0.0f, 1.0f); + func_00282F20(&velocity, &position, func_002A7878(speed * 0.75f, speed * 1.25f)); + position.f[2] = func_002A7878(low, high); + func_00282CC0(&position, object + 0x10, &position); + func_L00_003263D0(object, &position, 0.0f, 1, 1, &velocity, 0.0f, 1.0f, + 0x50808040, 0, 5.5f); + } +} extern int func_002A9640(char *, int, int); diff --git a/nonmatching/functional/func_L03_003C1BF0.c b/src/levels/shared/L03_002AB5C8-state-g8.c similarity index 74% rename from nonmatching/functional/func_L03_003C1BF0.c rename to src/levels/shared/L03_002AB5C8-state-g8.c index 5ccb2e2af..002020472 100644 --- a/nonmatching/functional/func_L03_003C1BF0.c +++ b/src/levels/shared/L03_002AB5C8-state-g8.c @@ -1,95 +1,5 @@ -/* functional: medium. Near-miss draft of retail size with the same frame: differences are allocation and scheduling, with some block order; paths the captured calls never take are unproven. */ -/* GPT-6.1 Sol high, task v1626 (2026-10-29): retained improved near miss. - * Current toolchain, -O2 -G8 -ffunction-sections -frac2-hazard-labels: - * 5680/5680 bytes; check.py: 0 of 2 USA v1.01 places match (L03/L14), - * first difference +0x1358. Eight instruction positions differ, excluding - * relocation address immediates; this is not a linked match. - * - * Improvements over the historical drafts below: - * - MotionInit's measured fields at +0x134/+0x144, with acceleration assigned - * first, reproduce both initial FPR choices AND retail's load/store order. - * - State 22 uses qzero_nc for both independent, aligned local vectors. The - * second bare clear invalidates CSE's address value, so the second vector's - * address is rebuilt after its clear, as in retail. No surrounding accesses - * depend on either cleared local's old contents. - * - A scoped pointer to other, initialized AFTER other.f[2] = height, keeps - * &other in s6; inline object+0xC0 expressions spill the matrix pointer to - * sp+0x30 and the rotation pointer to sp+0x34, matching retail allocation. - * - Reversing the two final zero assignments reproduces their retail schedule. - * - * Remaining state-22 differences: - * +0x1358..+0x1364: cc1 emits li.s 0.8 before li v0,0x940; retail reverses - * those independent constant preparations. - * +0x139C..+0x13A8: cc1 emits matrix-address add, other.z store, spill store, - * point argument; retail emits other.z store, matrix add, point argument, spill. - * Everything else aligns in check.py's side-by-side disassembly apart from - * unresolved address immediates. Relocation consistency and linked placement - * remain unqualified because the text differs. PAL/US2 and linking not run. - * - * New negative measurements: inline matrix alone was 5668 bytes; an explicit - * vector pointer introduced before its clear disturbed position allocation. - * Initializing that pointer before the class switch uses s7 instead of s6. - * Per-arm height initialization changes switch flow; loading the class into a - * local, a measured class struct field, and named vector component fields each - * tie this retained version. Stopped after 11 source candidates at this tie; - * reopen with a new scheduling hypothesis, not equivalent type spellings. - * All required declarations are included below. Older notes are dated history - * and their residual-difference descriptions are superseded by this block. - */ -#define MACRO_ADDR __attribute__((section(".sdata"))) -/* Finisher F1 (2026-10-26, base f5fab978 with qzero_nc): 1391 of 1420 instructions aligned with - * registers (was 1363 on this head). What moved it: - * - qzero_nc(&point) in state 22 (qzero(&other) keeps the clobber); - * - the hero distance in state 4 through the union view (HERO->f[0x80 / 4], [0x84 / 4]): - * retail addresses D_00189E20 with 0x80/0x84 offsets, not D_00189EA0; - * - cases 19 and 20 read SP(0x358) inline instead of through `target` (its pointer then - * takes $v0 as in retail); - * - state 22's class switch has `case 0x93C:` with the default (0x93C is a class id from - * state 1). A case below 0x940 that goes to the default gives retail's `slti 0x941` test: - * emit_case_nodes only emits the bound test when the root's other child is not a single - * value, and jump deletes the dead 0x93C compare; - * - other.f[2] = height (no reload of point.f[2]); - * - in the member loop the index store comes first (its D_L03_001B2A1C load is then in the - * beqz slot as retail, before the two -1 stores). - * Left: state 0's two float temps (D_L03_001AFEE0 in $f1, 0.0016666667f in $f0 in retail: - * local-alloc tie, swapping the two statements breaks cross-jumping), and state 22's - * allocation: retail keeps &other in $s6 and spills object+0xC0 (sp+0x30) and object+0xF0 - * (sp+0x34); here $s6 is object+0xC0 and the slots are swapped. - * F3 (2026-10-26): same 1391/1420 on 795143e6. State 1's pair after sched1 (lreg): insn 67 - * reg111 = D_L03_001AFEE0, insn 71 reg112 = 0.0016666667f, stores 0x144 (111) then 0x134 - * (112). Both lives are 2 (equal priority), so qty order (birth) gives 111 $f0. Retail needs - * 112 to rank first while sched2 still emits the load first and the 0x144 store first. Tried, - * no change: locals for either value in any order, a comma expression, MACRO_ADDR or an sda - * array for D_L03_001AFEE0. Swapping the stores gives retail's registers but the li.s first. - */ -/* Opus handoff (big8, 2026-10-26): func_L03_003C1BF0, 5680 bytes, 2 places - * (L03 0x003C1BF0, L14 0x003C5250). Built on the earlier corrected draft (5552 bytes, - * 0.66 aligned). Step 0: one function. Two jump tables: jtbl_L03_002A8F40 (9 entries, - * byte +0x95, case 0 explicit) and jtbl_L03_002A8F70 (22 entries, byte +0x20 minus 1). - * Profile: -O2 -G8 -ffunction-sections -frac2-hazard-labels (the label on the hazard nop - * in state 22). Measured in src/levels/shared/L03_003C1BF0.c: 5680 bytes (size equal), - * 1397/1420 opcodes aligned, 1366 with registers; every state but 22 is aligned. - * What moved it from 936 to 1394 aligned: - * - state bodies in retail address order: 1, 2, 4, 3, 5, 6/8, 7, 12, 13, 9, 10, 11, 14, - * 15, 16, 17, 18, 19, 20, 21, 22; states 14, 18 and 20 written out per arm (retail has - * three bodies and cross-jumps their func_002A7750 tails); - * - state 1 is a switch on the moby class (0x940, 0x93C, 0xA59, 0x964/default) and calls - * func_002B38B8 on pvars+0x354; - * - then-arm first where retail falls through (states 4, 10, 11, 15); - * - hero fields through the union view (0x26C, 0x270, +0x80 as base+offset), but - * D_00189E20 + 0x80 as a plain symbol address for func_00282E80 and the 419BD8 test; - * - u16 incomplete arrays for D_0018CB20/38/2C, D_0018CDCC/E4, D_0018CF58 (lui+lhu/sh), - * D_0018CB4C[] and D_L03_001BFDD8[]; (int)object >> 8 (sra); u32 dispatch; - * - MACRO_ADDR for D_L03_001B2548, _1B2A1C, _1B2A20: retail reads them absolutely in - * flow and $gp-relative in delay slots; - * - pvars+0x358 re-read in state 15; state 15's sign test reads back +0x344 after - * zeroing it; the final float clears through a local zero. - * State 22's class switch: 0.8f first, case 0x964 setting 0.3f and falling into case 0x940's - * store, default storing separately (this gave the retail size). - * Still off, all in state 22: retail's tree also tests <0x941 before 0x964 (GCC emits that - * only when the right child is not a single value: a third case or range is missing), - * object+0x10 kept in $fp, object+0xC0 / object+0xF0 spilled to sp+0x30/0x34, -1 and 0xF2D hoisted into s5/s7 for the member loop. - */ +/* Per-frame state machine for the L03/L14 moby with class switch 0x940/0x964 (states 1..22). + Own unit: -G8 globals, the hazard-nop branch label and -malign-loops=2 for the store group. */ #include "common.h" typedef struct { u8 reserved00[0x134]; float acceleration; @@ -232,7 +142,8 @@ void func_L03_003C1BF0(u8 *object) switch (object[0x20]) { case 1: if (func_002B38B8(SP(0x354))) { - switch (*(s16 *)(object + 0xAA)) { + type = *(s16 *)(object + 0xAA); + switch (type) { case 0x940: if (D_0018CB20[0] == 0) func_00288E18(0x9CF, 0x26); break; @@ -480,19 +391,20 @@ void func_L03_003C1BF0(u8 *object) MotionVector *offset; func_00282CC0(object + 0x10, object + 0x10, state + 0x1B0); qzero_nc(&point); qzero_nc(&other); + type = *(s16 *)(object + 0xAA); height = 0.8f; - switch (*(s16 *)(object + 0xAA)) { + switch (type) { case 0x964: height = 0.3f; case 0x940: - point.f[2] = height; - break; case 0x93C: default: - point.f[2] = height; + do { + point.f[2] = height; + } while (0); + other.f[2] = height; break; } - other.f[2] = height; offset = &other; func_00283098(&point, &point, object + 0xC0); if (SF(0x1B8) < 0.0f) { diff --git a/src/levels/shared/L03_002AB5C8.c b/src/levels/shared/L03_002AB5C8.c index 8bd9d364c..48e196fad 100644 --- a/src/levels/shared/L03_002AB5C8.c +++ b/src/levels/shared/L03_002AB5C8.c @@ -603,7 +603,6 @@ void func_L03_00393228(unsigned char *a0) { int func_L03_003A4978(unsigned char *p) { return p[0x20] == 1; } -INCLUDE_ASM("asm/levels", func_L03_003C1BF0); float func_L03_003C5AB8(unsigned char *); diff --git a/src/levels/shared/L03_003C5B28.c b/src/levels/shared/L03_003C5B28.c index 24502af86..55bdf17e1 100644 --- a/src/levels/shared/L03_003C5B28.c +++ b/src/levels/shared/L03_003C5B28.c @@ -570,7 +570,9 @@ s32 func_L03_00419C58(u32 a0, f32 *a1) { return out; } -INCLUDE_ASM("asm/levels", func_L03_0041B848); +void func_L03_0041B848(void) +{ +} /* func_L03_00424C40 is in L03_00424C40-g8.c (-G8, -fno-gcse). */ diff --git a/src/levels/shared/L05_003008C0.c b/src/levels/shared/L05_003008C0.c index cfd2eb051..a04e99a8c 100644 --- a/src/levels/shared/L05_003008C0.c +++ b/src/levels/shared/L05_003008C0.c @@ -40,15 +40,11 @@ void func_L05_0030C930(int a0, int a1) { -INCLUDE_ASM("asm/levels", func_L05_0033CD40); - /* func_L05_0033D3A0 is in L05_003008C0-reaction-g8.c. */ -INCLUDE_ASM("asm/levels", func_L05_0033F4A8); - /* func_L05_00352B28 lives in L05_00352B28.c: its grouped vector copy and debug division labels need a per-file profile. */ diff --git a/src/levels/shared/L05_0037AEC0.c b/src/levels/shared/L05_0037AEC0.c index 299bfa15b..8640e918a 100644 --- a/src/levels/shared/L05_0037AEC0.c +++ b/src/levels/shared/L05_0037AEC0.c @@ -70,5 +70,3 @@ int func_L05_0037AFD0(char *object, int flag) /* func_L05_0037B538 is defined in L05_0037B538.c. */ - -INCLUDE_ASM("asm/levels", func_L05_0037B6C0); diff --git a/src/levels/shared/L05_0037B6D0.c b/src/levels/shared/L05_0037B6D0.c index dfed635e9..2503a84a1 100644 --- a/src/levels/shared/L05_0037B6D0.c +++ b/src/levels/shared/L05_0037B6D0.c @@ -215,8 +215,6 @@ void func_L05_0037BB28(char *object) p->f10 = 0; } -INCLUDE_ASM("asm/levels", func_L05_0037BB78); - int func_L05_0037BB90(char *obj) { int *p = (int *)func_002ED688(obj); diff --git a/src/levels/shared/L08_002F2D10.c b/src/levels/shared/L08_002F2D10.c index 678a48c9b..b55bad649 100644 --- a/src/levels/shared/L08_002F2D10.c +++ b/src/levels/shared/L08_002F2D10.c @@ -338,7 +338,7 @@ void func_L08_0033CD18(s32 a0, s32 a1, ...) { -INCLUDE_ASM("asm/levels", func_L08_00389B68); +/* func_L08_00389B68 is in L08_00389B68-narrowsave.c. */ void func_L08_0039DBE8(unsigned char *obj) { struct { diff --git a/src/levels/shared/L08_00389B68-narrowsave.c b/src/levels/shared/L08_00389B68-narrowsave.c new file mode 100644 index 000000000..a721ddfca --- /dev/null +++ b/src/levels/shared/L08_00389B68-narrowsave.c @@ -0,0 +1,23 @@ +/* func_L08_00389B68: variadic, built with -mastra-quad-saves and -frac2-narrow-saves-below. + register_precision keeps $ra's save at 64 bits; the narrower save takes the lower slot. + The packet pointer is reloaded at every store in retail. */ +#include "common.h" +extern volatile u32 * volatile ref_L08_00389B68_00 __attribute__((sda)); +extern u32 *ref_L08_00389B68_01 MACRO_ADDR; +extern void func_00282AB0(void *, void *, int); +void func_L08_00389B68(int count, ...) __attribute__((register_precision(ra, 64))); +void func_L08_00389B68(int count, ...) { + if (count) { + ref_L08_00389B68_00[0] = (count + 1) | 0x10000000; + ref_L08_00389B68_00[1] = 0; + ref_L08_00389B68_00[2] = 0; + ref_L08_00389B68_00[3] = (count + 1) | 0x50000000; + ref_L08_00389B68_00[4] = count + 0x8000; + ref_L08_00389B68_00[5] = 0x10000000; + ref_L08_00389B68_00[6] = 14; + ref_L08_00389B68_00[7] = 0; + ref_L08_00389B68_01 = (u32 *)(ref_L08_00389B68_00 + 8); + func_00282AB0(ref_L08_00389B68_01, (char *)__builtin_next_arg(count) - 0x38, count * 16); + ref_L08_00389B68_00 = (u32 *)((char *)ref_L08_00389B68_00 + count * 16); + } +} diff --git a/src/levels/shared/L09_003F9468.c b/src/levels/shared/L09_003F9468.c index 6c92744cc..1cbbd7e8c 100644 --- a/src/levels/shared/L09_003F9468.c +++ b/src/levels/shared/L09_003F9468.c @@ -134,5 +134,3 @@ void func_L09_004051F8(NativeAngleOwner *owner) { /* func_L09_00410BC8 lives in L09_00410BC8-sprites.c. */ /* func_L09_0041A700 lives in the sibling small-data unit (L09_003F9468-g8.c). */ - -INCLUDE_ASM("asm/levels", func_L09_003FB780); diff --git a/src/levels/shared/L16_002B5EE0.c b/src/levels/shared/L16_002B5EE0.c index 63f2683e1..685b720f4 100644 --- a/src/levels/shared/L16_002B5EE0.c +++ b/src/levels/shared/L16_002B5EE0.c @@ -80,18 +80,18 @@ extern char *D_L16_001B2B1C __attribute__((sda)); extern char *D_L16_001B9B50; /* pushes the two axis values onto the linked node, unless the node is inert or a value is zero */ -void func_L16_0042FB58(float x, float y) +void func_L16_0042FB10(float x, float y) { char *st = D_L16_001B9B50; char *p; if (*(s16 *)(st + 0x86) != 0) return; - p = *(char **)(st + 0x70) + 0x60; + p = *(char **)(st + 0x70) + 0x20; if (x != 0.0f) - *(float *)(p + 0xE4) = x; + *(float *)(p + 0x1C) = x; if (y != 0.0f) - *(float *)(p + 0xE8) = y; + *(float *)(p + 0x20) = y; } extern void func_L16_00435CE8(void); diff --git a/src/pal/game/0032AF58-sw-g8.c b/src/pal/game/0032AF58-sw-g8.c index b439a6a48..3386305eb 100644 --- a/src/pal/game/0032AF58-sw-g8.c +++ b/src/pal/game/0032AF58-sw-g8.c @@ -139,6 +139,5 @@ void func_PAL_0032AF58(char *self) } break; } - /* The catalogue extent includes eight bytes before this return callback. */ - func_0027CFD0((char *)func_PAL_0032B920 + 8, self); + func_0027CFD0(func_PAL_0032B920, self); } diff --git a/src/pal/game/0032B650.c b/src/pal/game/0032B650.c index 3695d5731..359723723 100644 --- a/src/pal/game/0032B650.c +++ b/src/pal/game/0032B650.c @@ -110,6 +110,8 @@ void func_PAL_0032B730(char *self) } -INCLUDE_ASM("asm/pal/game", func_PAL_0032B920); +void func_PAL_0032B920(void) +{ +} INCLUDE_ASM("asm/pal/game", func_PAL_0032B930); diff --git a/src/pal/game/0033C448.c b/src/pal/game/0033C448.c new file mode 100644 index 000000000..d41a3bfa1 --- /dev/null +++ b/src/pal/game/0033C448.c @@ -0,0 +1,3 @@ +#include "include_asm.h" + +INCLUDE_ASM("asm/pal/game", func_PAL_0033C448); diff --git a/src/pal/levels/16_snivelak/L16_0043B728-g-g8.c b/src/pal/levels/16_snivelak/L16_0043B728-g-g8.c index 9d77c9e58..5c242f9a6 100644 --- a/src/pal/levels/16_snivelak/L16_0043B728-g-g8.c +++ b/src/pal/levels/16_snivelak/L16_0043B728-g-g8.c @@ -102,8 +102,8 @@ extern s32 func_00282948(void *); extern void func_L00_00424F00(void *, f32, f32); extern f32 func_L01_002C81D0(f32, f32, f32); extern s32 func_00283CF0(f32); -extern void func_L16_0042FB58(f32, f32); extern void func_L00_00424BB8(f32, f32); +extern void func_L16_0042FB10(f32, f32); extern void func_L00_00424A88(s32, f32, f32); extern void func_L00_00424A08(s32, f32, f32); extern void func_L00_00424A50(f32, f32); @@ -148,7 +148,7 @@ void func_PAL_L16_0043B728(Moby_004402D8 *moby) break; } if (func_002ACBC8(D_00189E20.f80, vars->f28[i]) != 0) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); func_L00_00424A08(0, vars->f40, 0.003f); func_L00_00424A50(vars->f44, 0.003f); return; @@ -183,8 +183,8 @@ void func_PAL_L16_0043B728(Moby_004402D8 *moby) } if (D_00189E20.f2294 == 0x5B && (D_00189E20.f49E == 0 || n >= 17)) { func_L00_00424B70(0.5f, 1.0f); - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); func_L00_00424A88(0, D_L23_001B1F14, 0.005f); func_L00_00424A08(1, D_L23_001B1F08, 0.01f); func_L00_00424A50(D_L23_001B1F0C, 0.01f); @@ -198,9 +198,9 @@ void func_PAL_L16_0043B728(Moby_004402D8 *moby) func_L00_00424A88(0, D_L23_001B1F10, 0.03f); if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } d = func_00282E48(D_00189E20.f80, D_00189E20.fB0) - vars->f24; if (D_L23_001B1EEC < d) { @@ -220,8 +220,8 @@ void func_PAL_L16_0043B728(Moby_004402D8 *moby) D_L23_001B234C = 0; } } else if (D_00189E20.f2294 == 0x81) { - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); if (D_001A79F0 == 16) { func_L00_00424A88(0, 0.5f, 0.04f); func_L00_00424A08(0, 4.0f, 0.002f); @@ -233,9 +233,9 @@ void func_PAL_L16_0043B728(Moby_004402D8 *moby) } } else { if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } if (D_00189E20.f229C == 5) { func_L00_00424A08(0, 4.0f, 0.003f); diff --git a/src/pal/levels/22_dobbo_orbit/L22_00414080-g-g8.c b/src/pal/levels/22_dobbo_orbit/L22_00414080-g-g8.c index 08bc05576..cb5d8e048 100644 --- a/src/pal/levels/22_dobbo_orbit/L22_00414080-g-g8.c +++ b/src/pal/levels/22_dobbo_orbit/L22_00414080-g-g8.c @@ -102,8 +102,8 @@ extern s32 func_00282948(void *); extern void func_L00_00424F00(void *, f32, f32); extern f32 func_L00_002D2A10(f32, f32, f32); extern s32 func_00283CF0(f32); -extern void func_L16_0042FB58(f32, f32); extern void func_L00_00424BB8(f32, f32); +extern void func_L16_0042FB10(f32, f32); extern void func_L00_00424A88(s32, f32, f32); extern void func_L00_00424A08(s32, f32, f32); extern void func_L00_00424A50(f32, f32); @@ -148,7 +148,7 @@ void func_PAL_L22_00430248(Moby_004402D8 *moby) break; } if (func_002ACBC8(D_00189E20.f80, vars->f28[i]) != 0) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); func_L00_00424A08(0, vars->f40, 0.003f); func_L00_00424A50(vars->f44, 0.003f); return; @@ -183,8 +183,8 @@ void func_PAL_L22_00430248(Moby_004402D8 *moby) } if (D_00189E20.f2294 == 0x5B && (D_00189E20.f49E == 0 || n >= 17)) { func_L00_00424B70(0.5f, 1.0f); - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); func_L00_00424A88(0, D_L23_001B1F14, 0.005f); func_L00_00424A08(1, D_L23_001B1F08, 0.01f); func_L00_00424A50(D_L23_001B1F0C, 0.01f); @@ -198,9 +198,9 @@ void func_PAL_L22_00430248(Moby_004402D8 *moby) func_L00_00424A88(0, D_L23_001B1F10, 0.03f); if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } d = func_00282E48(D_00189E20.f80, D_00189E20.fB0) - vars->f24; if (D_L23_001B1EEC < d) { @@ -220,8 +220,8 @@ void func_PAL_L22_00430248(Moby_004402D8 *moby) D_L23_001B234C = 0; } } else if (D_00189E20.f2294 == 0x81) { - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); if (D_001A79F0 == 16) { func_L00_00424A88(0, 0.5f, 0.04f); func_L00_00424A08(0, 4.0f, 0.002f); @@ -233,9 +233,9 @@ void func_PAL_L22_00430248(Moby_004402D8 *moby) } } else { if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } if (D_00189E20.f229C == 5) { func_L00_00424A08(0, 4.0f, 0.003f); diff --git a/src/pal/levels/23_damosel_orbit/L23_004302F8-g82.c b/src/pal/levels/23_damosel_orbit/L23_004302F8-g82.c index b0e7e4bdf..3e238c4cc 100644 --- a/src/pal/levels/23_damosel_orbit/L23_004302F8-g82.c +++ b/src/pal/levels/23_damosel_orbit/L23_004302F8-g82.c @@ -101,8 +101,8 @@ extern s32 func_00282948(void *); extern void func_L00_00424F00(void *, f32, f32); extern f32 func_L00_002D2A10(f32, f32, f32); extern s32 func_00283CF0(f32); -extern void func_L16_0042FB58(f32, f32); extern void func_L00_00424BB8(f32, f32); +extern void func_L16_0042FB10(f32, f32); extern void func_L00_00424A88(s32, f32, f32); extern void func_L00_00424A08(s32, f32, f32); extern void func_L00_00424A50(f32, f32); @@ -146,7 +146,7 @@ void func_PAL_L23_00445E00(Moby_004402D8 *moby) break; } if (func_002ACBC8(D_00189E20.f80, vars->f28[i]) != 0) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); func_L00_00424A08(0, vars->f40, 0.003f); func_L00_00424A50(vars->f44, 0.003f); return; @@ -181,8 +181,8 @@ void func_PAL_L23_00445E00(Moby_004402D8 *moby) } if (D_00189E20.f2294 == 0x5B && (D_00189E20.f49E == 0 || n >= 17)) { func_L00_00424B70(0.5f, 1.0f); - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); func_L00_00424A88(0, D_L23_001B1F14, 0.005f); func_L00_00424A08(1, D_L23_001B1F08, 0.01f); func_L00_00424A50(D_L23_001B1F0C, 0.01f); @@ -196,9 +196,9 @@ void func_PAL_L23_00445E00(Moby_004402D8 *moby) func_L00_00424A88(0, D_L23_001B1F10, 0.03f); if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } d = func_00282E48(D_00189E20.f80, D_00189E20.fB0) - vars->f24; if (D_L23_001B1EEC < d) { @@ -218,8 +218,8 @@ void func_PAL_L23_00445E00(Moby_004402D8 *moby) D_L23_001B234C = 0; } } else if (D_00189E20.f2294 == 0x81) { - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); if (D_001A79F0 == 16) { func_L00_00424A88(0, 0.5f, 0.04f); func_L00_00424A08(0, 4.0f, 0.002f); @@ -231,9 +231,9 @@ void func_PAL_L23_00445E00(Moby_004402D8 *moby) } } else { if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } if (D_00189E20.f229C == 5) { func_L00_00424A08(0, 4.0f, 0.003f); diff --git a/src/pal/levels/26_jamming_array/L26_0040C130-g-g8.c b/src/pal/levels/26_jamming_array/L26_0040C130-g-g8.c index d3b982cfc..58fe54bb4 100644 --- a/src/pal/levels/26_jamming_array/L26_0040C130-g-g8.c +++ b/src/pal/levels/26_jamming_array/L26_0040C130-g-g8.c @@ -102,8 +102,8 @@ extern s32 func_00282948(void *); extern void func_L00_00424F00(void *, f32, f32); extern f32 func_L00_002D2A10(f32, f32, f32); extern s32 func_00283CF0(f32); -extern void func_L16_0042FB58(f32, f32); extern void func_L00_00424BB8(f32, f32); +extern void func_L16_0042FB10(f32, f32); extern void func_L00_00424A88(s32, f32, f32); extern void func_L00_00424A08(s32, f32, f32); extern void func_L00_00424A50(f32, f32); @@ -148,7 +148,7 @@ void func_PAL_L26_00421BD8(Moby_004402D8 *moby) break; } if (func_002ACBC8(D_00189E20.f80, vars->f28[i]) != 0) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); func_L00_00424A08(0, vars->f40, 0.003f); func_L00_00424A50(vars->f44, 0.003f); return; @@ -183,8 +183,8 @@ void func_PAL_L26_00421BD8(Moby_004402D8 *moby) } if (D_00189E20.f2294 == 0x5B && (D_00189E20.f49E == 0 || n >= 17)) { func_L00_00424B70(0.5f, 1.0f); - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); func_L00_00424A88(0, D_L23_001B1F14, 0.005f); func_L00_00424A08(1, D_L23_001B1F08, 0.01f); func_L00_00424A50(D_L23_001B1F0C, 0.01f); @@ -198,9 +198,9 @@ void func_PAL_L26_00421BD8(Moby_004402D8 *moby) func_L00_00424A88(0, D_L23_001B1F10, 0.03f); if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } d = func_00282E48(D_00189E20.f80, D_00189E20.fB0) - vars->f24; if (D_L23_001B1EEC < d) { @@ -220,8 +220,8 @@ void func_PAL_L26_00421BD8(Moby_004402D8 *moby) D_L23_001B234C = 0; } } else if (D_00189E20.f2294 == 0x81) { - func_L16_0042FB58(0.05f, 0.2f); - func_L00_00424BB8(0.04f, 0.0f); + func_L00_00424BB8(0.05f, 0.2f); + func_L16_0042FB10(0.04f, 0.0f); if (D_001A79F0 == 16) { func_L00_00424A88(0, 0.5f, 0.04f); func_L00_00424A08(0, 4.0f, 0.002f); @@ -233,9 +233,9 @@ void func_PAL_L26_00421BD8(Moby_004402D8 *moby) } } else { if (D_00189E20.f229C == 2) { - func_L16_0042FB58(0.04f, 0.2f); + func_L00_00424BB8(0.04f, 0.2f); } else { - func_L16_0042FB58(0.015f, 0.2f); + func_L00_00424BB8(0.015f, 0.2f); } if (D_00189E20.f229C == 5) { func_L00_00424A08(0, 4.0f, 0.003f); diff --git a/src/pal/levels/shared/L00_003E63F0.c b/src/pal/levels/shared/L00_003E63F0.c index ac6a743de..df10fe58b 100644 --- a/src/pal/levels/shared/L00_003E63F0.c +++ b/src/pal/levels/shared/L00_003E63F0.c @@ -1,6 +1,8 @@ #include "include_asm.h" -INCLUDE_ASM("asm/pal/levels", func_PAL_L00_003E63F0); +void func_PAL_L00_003E63F0(void) +{ +} diff --git a/src/us2/game/0032A588-sw-g8.c b/src/us2/game/0032A588-sw-g8.c index 1c048e2cc..a81816ff6 100644 --- a/src/us2/game/0032A588-sw-g8.c +++ b/src/us2/game/0032A588-sw-g8.c @@ -139,6 +139,5 @@ void func_US2_0032A588(char *self) } break; } - /* The catalogue extent includes eight bytes before this return callback. */ - func_0027CFD0((char *)func_0032A130 + 8, self); + func_0027CFD0(func_0032A130, self); } diff --git a/src/us2/game/0033B568.c b/src/us2/game/0033B568.c new file mode 100644 index 000000000..7bf125bba --- /dev/null +++ b/src/us2/game/0033B568.c @@ -0,0 +1,3 @@ +#include "include_asm.h" + +INCLUDE_ASM("asm/us2/game", func_US2_0033B568); diff --git a/tests/fixtures/keep_block_zero_copy.c b/tests/fixtures/keep_block_zero_copy.c new file mode 100644 index 000000000..7f448b980 --- /dev/null +++ b/tests/fixtures/keep_block_zero_copy.c @@ -0,0 +1,31 @@ +/* Authored controls for the optional same-block zero copy; no game code. */ +extern int table[]; +extern void touch(void); + +/* The zero and its copy share a block: with the option `i = result` stays a register copy. */ +int same_block(int value, int key) +{ + int result = 0; + int i = result; + + while (table[i] != 0 && i < 8 && table[i] != key) + i++; + if (table[i] != 0) + result = value == table[i + 1]; + return result; +} + +/* Control: a call ends the block between the zero and the copy, so it is folded either way. */ +int other_block(int value, int key) +{ + int result = 0; + int i; + + touch(); + i = result; + while (table[i] != 0 && i < 8 && table[i] != key) + i++; + if (table[i] != 0) + result = value == table[i + 1]; + return result; +} diff --git a/tests/fixtures/narrow_saves_below.c b/tests/fixtures/narrow_saves_below.c new file mode 100644 index 000000000..88a4f3924 --- /dev/null +++ b/tests/fixtures/narrow_saves_below.c @@ -0,0 +1,16 @@ +/* Authored controls for the optional width-ordered quad-slot saves; no game code. */ +extern int call(int); + +/* Control: $s0 and $ra are both saved at the slot's full width, so $ra stays on top. + It comes first: register_precision changes the save mode for the rest of the unit. */ +int same_width(int x) +{ + return call(x) + x; +} + +/* $ra is narrowed to 64 bits: with the option its save goes below the $s0 save. */ +int narrow_ra(int x) __attribute__((register_precision(ra, 64))); +int narrow_ra(int x) +{ + return call(x) + x; +} diff --git a/tests/test_keep_block_zero_copy.py b/tests/test_keep_block_zero_copy.py new file mode 100644 index 000000000..0a79d25d3 --- /dev/null +++ b/tests/test_keep_block_zero_copy.py @@ -0,0 +1,113 @@ +"""The opt-in -frac2-keep-block-zero-copy: transformer drift and EE compiler-output regressions.""" +import importlib.util +import os +from pathlib import Path +import re +import subprocess +import tempfile +import unittest + +ROOT = Path(__file__).resolve().parent.parent +spec = importlib.util.spec_from_file_location("keep_block_zero_copy", + ROOT / "tools/compiler/transformers/keep_block_zero_copy.py") +transformer = importlib.util.module_from_spec(spec) +spec.loader.exec_module(transformer) + +OPTION = "rac2-keep-block-zero-copy" +FUNCTIONS = ("same_block", "other_block") +PROFILES = {"default": [], "enabled": ["-f" + OPTION], "disabled": ["-f" + OPTION, "-fno-" + OPTION]} + + +def function_text(asm: str, name: str) -> str: + """The function's assembly, its local labels renumbered in order of appearance.""" + body = re.search(r"(?ms)^" + name + r":.*?\.end\s+" + name, asm).group() + labels = {} + return re.sub(r"\$L\d+", lambda m: labels.setdefault(m.group(), f"$L{len(labels)}"), body) + + +def moves(body: str) -> list: + """The register moves, as (destination, source).""" + return re.findall(r"\tmove\t(\$\d+),(\$\d+)", body) + + +class TransformerTests(unittest.TestCase): + def sources(self, root: Path, **override) -> dict: + files = {"cse.c": "a\n" + transformer.HELPER_OLD + "\nb\n" + transformer.CHOICE_OLD, + "toplev.c": transformer.DEFINITION_OLD + transformer.OPTION_OLD, + "flags.h": transformer.DECLARATION_OLD} + files.update(override) + for name, contents in files.items(): + (root / name).write_text(contents) + return files + + def test_each_insertion_point_is_used_once(self): + with tempfile.TemporaryDirectory() as d: + root = Path(d) + self.sources(root) + transformer.patch(root) + cse = (root / "cse.c").read_text() + self.assertEqual(cse.count("rac2_set_in_block_p (insn, reg)"), 1) + self.assertIn("if (flag_rac2_keep_block_zero_copy", cse) + top = (root / "toplev.c").read_text() + self.assertIn("int flag_rac2_keep_block_zero_copy = 0;", top) + self.assertIn('{"' + OPTION + '", &flag_rac2_keep_block_zero_copy, 1,', top) + self.assertIn("extern int flag_rac2_keep_block_zero_copy;", (root / "flags.h").read_text()) + with self.assertRaisesRegex(ValueError, "already present"): + transformer.patch(root) + + def test_source_drift_is_rejected_before_any_file_is_written(self): + with tempfile.TemporaryDirectory() as d: + root = Path(d) + files = self.sources(root, **{"flags.h": "unexpected declaration"}) + with self.assertRaisesRegex(ValueError, "option declaration"): + transformer.patch(root) + self.assertEqual({name: (root / name).read_text() for name in files}, files) + + +class CompilerOutputTests(unittest.TestCase): + @classmethod + def setUpClass(cls): + compiler = Path(os.environ.get("RAC2_COMPILER_ROOT", ROOT / "build/compiler/tools")) + if not all((compiler / name).is_file() for name in ("cpp", "cc1", "as")): + if "RAC2_COMPILER_ROOT" in os.environ: + raise RuntimeError("RAC2_COMPILER_ROOT must contain the newly built cpp, cc1 and as") + raise unittest.SkipTest("EE compiler absent; tools/compiler/build.sh runs these checks after building it") + cls.outputs = {} + with tempfile.TemporaryDirectory() as d: + root = Path(d) + source = root / "input.c" + source.write_bytes((ROOT / "tests/fixtures/keep_block_zero_copy.c").read_bytes()) + with (root / "input.i").open("w") as out: + try: + subprocess.run([str(compiler / "cpp"), str(source)], stdout=out, check=True) + except OSError: + if "RAC2_COMPILER_ROOT" in os.environ: + raise + raise unittest.SkipTest("EE compiler not runnable on this host; tools/compiler/build.sh " + "runs these checks in its build environment") + for label, options in PROFILES.items(): + asm = root / (label + ".s") + subprocess.run([str(compiler / "cc1"), "-quiet", "-O2", "-G0", "-ffunction-sections", + *options, str(root / "input.i"), "-o", str(asm)], check=True) + subprocess.run([str(compiler / "as"), "-o", str(root / (label + ".o")), str(asm)], check=True) + text = asm.read_text() + cls.outputs[label] = {name: function_text(text, name) for name in FUNCTIONS} + + def test_disabled_option_restores_default_for_every_function(self): + self.assertEqual(self.outputs["default"], self.outputs["disabled"]) + + def test_default_folds_the_copy_to_zero(self): + self.assertEqual(sum(source == "$0" for _, source in moves(self.outputs["default"]["same_block"])), 2) + + def test_option_keeps_the_same_block_copy(self): + enabled = moves(self.outputs["enabled"]["same_block"]) + self.assertEqual(sum(source == "$0" for _, source in enabled), 1) + zero = next(dest for dest, source in enabled if source == "$0") + self.assertIn(zero, [source for _, source in enabled]) + + def test_control_across_a_call_is_unchanged(self): + self.assertEqual(self.outputs["default"]["other_block"], self.outputs["enabled"]["other_block"]) + + +if __name__ == "__main__": + unittest.main() diff --git a/tests/test_narrow_saves_below.py b/tests/test_narrow_saves_below.py new file mode 100644 index 000000000..69d2b029f --- /dev/null +++ b/tests/test_narrow_saves_below.py @@ -0,0 +1,120 @@ +"""The opt-in -frac2-narrow-saves-below: transformer drift and EE compiler-output regressions.""" +import importlib.util +import os +from pathlib import Path +import re +import subprocess +import tempfile +import unittest + +ROOT = Path(__file__).resolve().parent.parent +spec = importlib.util.spec_from_file_location("narrow_saves_below", + ROOT / "tools/compiler/transformers/narrow_saves_below.py") +transformer = importlib.util.module_from_spec(spec) +spec.loader.exec_module(transformer) + +OPTION = "rac2-narrow-saves-below" +FUNCTIONS = ("same_width", "narrow_ra") +PROFILES = {"plain": [], "plain_enabled": ["-f" + OPTION], + "default": ["-mastra-quad-saves"], "enabled": ["-mastra-quad-saves", "-f" + OPTION], + "disabled": ["-mastra-quad-saves", "-f" + OPTION, "-fno-" + OPTION]} + + +def function_text(asm: str, name: str) -> str: + """The function's assembly, its local labels renumbered in order of appearance.""" + body = re.search(r"(?ms)^" + name + r":.*?\.end\s+" + name, asm).group() + labels = {} + return re.sub(r"\$L\d+", lambda m: labels.setdefault(m.group(), f"$L{len(labels)}"), body) + + +def saves(body: str) -> list: + """The $16/$31 stack saves and restores as (op, register, offset), sorted.""" + return sorted(re.findall(r"\t(sq|sd|lq|ld)\s+(\$16|\$31),(\d+)\(\$sp\)", body)) + + +class TransformerTests(unittest.TestCase): + def sources(self, root: Path, **override) -> dict: + files = {"config/mips/mips.c": "a\n" + transformer.SCOPE_OLD + "b\n" + transformer.LOOP_OLD, + "toplev.c": transformer.DEFINITION_OLD + transformer.OPTION_OLD, + "flags.h": transformer.DECLARATION_OLD} + files.update(override) + (root / "config/mips").mkdir(parents=True, exist_ok=True) + for name, contents in files.items(): + (root / name).write_text(contents) + return files + + def test_each_insertion_point_is_used_once(self): + with tempfile.TemporaryDirectory() as d: + root = Path(d) + self.sources(root) + transformer.patch(root) + mips = (root / "config/mips/mips.c").read_text() + self.assertEqual(mips.count("rac2_width_pass < (rac2_by_width ? 2 : 1)"), 1) + self.assertIn("flag_rac2_narrow_saves_below && mips_astra_quad_saves", mips) + top = (root / "toplev.c").read_text() + self.assertIn("int flag_rac2_narrow_saves_below = 0;", top) + self.assertIn('{"' + OPTION + '", &flag_rac2_narrow_saves_below, 1,', top) + self.assertIn("extern int flag_rac2_narrow_saves_below;", (root / "flags.h").read_text()) + with self.assertRaisesRegex(ValueError, "already present"): + transformer.patch(root) + + def test_source_drift_is_rejected_before_any_file_is_written(self): + with tempfile.TemporaryDirectory() as d: + root = Path(d) + files = self.sources(root, **{"flags.h": "unexpected declaration"}) + with self.assertRaisesRegex(ValueError, "option declaration"): + transformer.patch(root) + self.assertEqual({name: (root / name).read_text() for name in files}, files) + + +class CompilerOutputTests(unittest.TestCase): + @classmethod + def setUpClass(cls): + compiler = Path(os.environ.get("RAC2_COMPILER_ROOT", ROOT / "build/compiler/tools")) + if not all((compiler / name).is_file() for name in ("cpp", "cc1", "as")): + if "RAC2_COMPILER_ROOT" in os.environ: + raise RuntimeError("RAC2_COMPILER_ROOT must contain the newly built cpp, cc1 and as") + raise unittest.SkipTest("EE compiler absent; tools/compiler/build.sh runs these checks after building it") + cls.outputs = {} + with tempfile.TemporaryDirectory() as d: + root = Path(d) + source = root / "input.c" + source.write_bytes((ROOT / "tests/fixtures/narrow_saves_below.c").read_bytes()) + with (root / "input.i").open("w") as out: + try: + subprocess.run([str(compiler / "cpp"), str(source)], stdout=out, check=True) + except OSError: + if "RAC2_COMPILER_ROOT" in os.environ: + raise + raise unittest.SkipTest("EE compiler not runnable on this host; tools/compiler/build.sh " + "runs these checks in its build environment") + for label, options in PROFILES.items(): + asm = root / (label + ".s") + subprocess.run([str(compiler / "cc1"), "-quiet", "-O2", "-G0", "-ffunction-sections", + *options, str(root / "input.i"), "-o", str(asm)], check=True) + subprocess.run([str(compiler / "as"), "-o", str(root / (label + ".o")), str(asm)], check=True) + text = asm.read_text() + cls.outputs[label] = {name: function_text(text, name) for name in FUNCTIONS} + + def test_disabled_option_restores_default_for_every_function(self): + self.assertEqual(self.outputs["default"], self.outputs["disabled"]) + + def test_option_has_no_effect_without_quad_saves(self): + self.assertEqual(self.outputs["plain"], self.outputs["plain_enabled"]) + + def test_default_keeps_ra_in_the_top_slot(self): + self.assertEqual(saves(self.outputs["default"]["narrow_ra"]), + sorted([("sd", "$31", "16"), ("sq", "$16", "0"), ("ld", "$31", "16"), ("lq", "$16", "0")])) + + def test_option_puts_the_narrower_ra_save_below(self): + self.assertEqual(saves(self.outputs["enabled"]["narrow_ra"]), + sorted([("sq", "$16", "16"), ("sd", "$31", "0"), ("lq", "$16", "16"), ("ld", "$31", "0")])) + + def test_control_keeps_ra_on_top(self): + self.assertEqual(self.outputs["default"]["same_width"], self.outputs["enabled"]["same_width"]) + self.assertEqual(saves(self.outputs["enabled"]["same_width"]), + sorted([("sq", "$31", "16"), ("sq", "$16", "0"), ("lq", "$31", "16"), ("lq", "$16", "0")])) + + +if __name__ == "__main__": + unittest.main() diff --git a/tests/test_tools.py b/tests/test_tools.py index 94f8ab89f..a33435941 100644 --- a/tests/test_tools.py +++ b/tests/test_tools.py @@ -280,6 +280,155 @@ def test_catalogue_keeps_equal_byte_families_and_unrelated_old_extents(self): self.assertEqual((boot.read_bytes(),catalogue.read_bytes()),snapshot) +class CodeWitnessedSplit(unittest.TestCase): + """The 5 November 2026 boundary audit: a code-built callback address is an entry witness.""" + + def fixture(self, root, pairs=1, target_offset=8): + name, child, address = "func_L10_00419188", "func_L10_00419190", 0x2000 + body = code(0x24020001, 0) + code(0x03E00008, 0) + caller = [] + for _ in range(pairs): + caller += [lui(5, (address + target_offset + 0x8000) >> 16), 0, + addiu(5, 5, (address + target_offset) & 0xFFFF)] + text = body + code(*caller) + directory = root / levels.level_dir(10) + directory.mkdir(parents=True) + (directory / "manifest.json").write_text(json.dumps({"sections": [ + {"name": "text", "address": address, "size": len(text), "type": 1}]})) + (directory / "text.bin").write_bytes(text) + fp = levels.fingerprint(body, address) + spec = {name: (fp, "level", 1, "text", 1, ((name, 8), (child, 8)))} + return [(name, "level", 16, fp, [(10, address)])], spec + + def test_code_witness_splits_and_replays(self): + with tempfile.TemporaryDirectory() as d: + rows, spec = self.fixture(Path(d)) + with patch.object(levels, "DUMP", Path(d)), patch.object(levels, "LEVEL_FUNCTION_SPLITS", spec): + split = levels.split_level_rows(rows) + self.assertEqual(levels.split_level_rows(split), split) + self.assertEqual([(r[0], r[2], r[4]) for r in split], + [("func_L10_00419188", 8, [(10, 0x2000)]), ("func_L10_00419190", 8, [(10, 0x2008)])]) + + def test_missing_extra_or_misaimed_code_witness_is_rejected(self): + for pairs, offset in ((0, 8), (2, 8), (1, 4), (1, 0)): + with self.subTest(pairs=pairs, offset=offset), tempfile.TemporaryDirectory() as d: + rows, spec = self.fixture(Path(d), pairs, offset) + with patch.object(levels, "DUMP", Path(d)), patch.object(levels, "LEVEL_FUNCTION_SPLITS", spec), \ + self.assertRaises(ValueError): + levels.split_level_rows(rows) + + def test_address_pair_needs_the_same_register(self): + text = code(lui(5, 0x42), addiu(6, 4, 0x91E0), lui(4, 0x42), addiu(4, 4, -0x6E20)) + self.assertEqual(levels.code_address_pairs(text, 0, 0x4191E0), 1) + self.assertEqual(levels.code_address_pairs(text, 0, 0x4291E0), 0) + + def test_audited_rows_keep_real_entries_and_the_pal_exception(self): + # Referenced or returning rows of the audit stay functions. + for name in ("func_002B9030", "func_002B9380", "func_002A1378", "func_002A677C", "func_002A08A0", + "func_00282848", "func_001325E0", "func_00131CB0"): + with self.subTest(name=name): + self.assertNotIn(name, levels.FUNCTION_RESIDUES) + for name in ("func_0032A130", "func_L03_0041B848", "func_PAL_0032B920", "func_PAL_L00_003E63F0"): + with self.subTest(name=name): + self.assertEqual(levels.FUNCTION_ENTRY_OFFSETS[name], (16, 8)) + self.assertEqual(levels.function_extent(name, 0x32A130, 16), (0x32A138, 8)) + self.assertEqual(levels.function_extent(name, 0x32A138, 8), (0x32A138, 8)) + + +class DelaySlotBoundary(unittest.TestCase): + """6 November 2026: a fill-prefixed syscall stub and a PAL row that left its delay slot behind.""" + + def test_named_corrections(self): + self.assertEqual(levels.function_extent("func_0011A7F8", 0x11A7F8, 24), (0x11A800, 16)) + self.assertEqual(levels.function_extent("func_0011A7F8", 0x11A800, 16), (0x11A800, 16)) + self.assertTrue(levels.function_residue("func_L00_00309DB0", 28)) + with self.assertRaises(ValueError): + levels.function_residue("func_L00_00309DB0", 24) + name = "func_PAL_L00_0030BA80" + self.assertEqual(levels.function_extent(name, 0x30BA80, 336), (0x30BA80, 340)) + self.assertEqual(levels.function_extent(name, 0x30BA80, 340), (0x30BA80, 340)) + with self.assertRaises(ValueError): + levels.function_extent(name, 0x30BA80, 344) + + def fixture(self, root, ret): + import carry + address = 0x2000 + text = code(0x27BDFFE0, ret, 0x27BD0020, 0, 0x0000102D, 0) + directory = root / levels.level_dir(0) + directory.mkdir(parents=True) + (directory / "manifest.json").write_text(json.dumps({"sections": [ + {"name": "text", "address": address, "size": len(text), "type": 1}]})) + (directory / "text.bin").write_bytes(text) + rows = [("pred", "shared", 8, levels.fingerprint(text[:8], address), [(0, address)]), + ("res", "shared", 16, "x", [(0, address + 8)])] + with patch.object(levels, "DUMP", root), patch.object(levels, "FUNCTION_DELAY_SLOTS", {"pred": 8}), \ + patch.object(levels, "FUNCTION_RESIDUES", {"res": 16}): + return carry.correct_level_entries(rows), text + + def test_slot_returns_to_its_function_and_the_rest_is_residue(self): + with tempfile.TemporaryDirectory() as d: + out, text = self.fixture(Path(d), 0x03E00008) + self.assertEqual(out, [("pred", "shared", 12, levels.fingerprint(text[:12], 0x2000), [(0, 0x2000)])]) + + def test_slot_needs_a_return_before_it(self): + with tempfile.TemporaryDirectory() as d, self.assertRaises(ValueError): + self.fixture(Path(d), 0) + + +class AuditedIdentitySplit(unittest.TestCase): + """Section 34: a fingerprint shared by two bodies is regrouped only by audited digests.""" + + def fixture(self, root): + import hashlib + a = code(0x3C02001C, 0x8C430000, 0x24420060, 0xE44C00E4) + b = code(0x3C02001C, 0x8C430000, 0x24420020, 0xE44C001C) + texts = {0: a, 16: b + a} + for number, text in texts.items(): + directory = root / levels.level_dir(number) + directory.mkdir(parents=True) + (directory / "manifest.json").write_text(json.dumps({"sections": [ + {"name": "text", "address": 0x1000, "size": len(text), "type": 1}]})) + (directory / "text.bin").write_bytes(text) + digest = lambda body: hashlib.sha256(body[8:]).hexdigest()[:16] + spec = {("fp", 16): (8, (("func_A", digest(a)), ("func_B", digest(b))), ("func_old",))} + # the historical grouping: the first copy of each level in one row, the second in another + rows = [("func_A", "shared", 16, "fp", [(0, 0x1000), (16, 0x1000)]), + ("func_old", "level", 16, "fp", [(16, 0x1010)]), + ("other", "level", 8, "x", [(0, 0x2000)])] + return rows, spec + + def test_mixed_rows_are_regrouped_by_body_and_replay(self): + with tempfile.TemporaryDirectory() as d: + rows, spec = self.fixture(Path(d)) + with patch.object(levels, "DUMP", Path(d)), patch.object(levels, "IDENTITY_SPLITS", spec): + out = levels.split_identities(rows) + self.assertEqual(levels.split_identities(out), out) + self.assertEqual(out, [("func_A", "shared", 16, "fp", [(0, 0x1000), (16, 0x1010)]), + ("func_B", "level", 16, "fp", [(16, 0x1000)]), + ("other", "level", 8, "x", [(0, 0x2000)])]) + + def test_unaudited_name_unknown_body_and_double_copies_fail(self): + for change in ("name", "body", "double"): + with self.subTest(change=change), tempfile.TemporaryDirectory() as d: + rows, spec = self.fixture(Path(d)) + if change == "name": + rows[1] = ("func_new",) + rows[1][1:] + elif change == "body": + (Path(d) / levels.level_dir(16) / "text.bin").write_bytes(code(0, 0, 0, 0) * 2) + else: + text = Path(d) / levels.level_dir(16) / "text.bin" + text.write_bytes(text.read_bytes()[16:] * 2) + with patch.object(levels, "DUMP", Path(d)), patch.object(levels, "IDENTITY_SPLITS", spec), \ + self.assertRaises(ValueError): + levels.split_identities(rows) + + def test_real_split_names_the_two_setters(self): + skip, parts, retired = levels.IDENTITY_SPLITS[("6b8116fb9abb08d4", 72)] + self.assertEqual(skip, 8) + self.assertEqual([n for n, _ in parts], ["func_L00_00424B70", "func_L00_00424BB8", "func_L16_0042FB10"]) + self.assertEqual(retired, ("func_L16_0042FB58",)) + + class Filler(unittest.TestCase): """The linker's filler between the bodies: stack adjustments and nops only.""" @@ -857,11 +1006,15 @@ def test_linked_code_sums_the_complete_units(self): units={u["name"]:u["measures"]["complete_code"] for u in report["units"]} self.assertEqual(units,{"game/done":"12","game/open":"0","Shared level code":"0"}) - def release(self, functions, flags=(), where=None, source=None): + def release(self, functions, flags=(), where=None, source=None, not_carried=()): import progress with tempfile.TemporaryDirectory() as d: root = Path(d) path = root / "report.json" + if not_carried: + listed = root / levels.VERSIONS["pal"]["config"] / "not_carried.tsv" + listed.parent.mkdir(parents=True) + listed.write_text("# header\n" + "".join(f"{n}\tmeasured\n" for n in not_carried)) path.write_text(json.dumps({"units":[{"functions":functions}]})) before = path.read_bytes() with patch.object(progress,"ROOT",root), \ @@ -936,11 +1089,43 @@ def test_split_does_not_hide_other_missing_entries_or_duplicate_rows(self): where["other"] = (0x2000,8,"boot",None) self.release(functions, where=where) - def test_split_tolerance_does_not_hide_a_retired_row(self): + def test_identity_split_retires_its_matched_name_only_with_its_parts(self): + spec = {("fp", 8): (0, (("kept", "a"), ("part", "b")), ("old",))} + with patch.object(levels, "IDENTITY_SPLITS", spec): + where = {"kept":(0x1000,8,"boot",None), "part":(0x2000,8,"boot",None)} + self.release([{"name":"kept","fuzzy_match_percent":0.0}, + {"name":"old","fuzzy_match_percent":100.0}], where=where) + for extra in ({"other":(0x3000,8,"boot",None)}, {}): + with self.subTest(extra=extra), self.assertRaises(SystemExit): + w = dict(where, **extra) if extra else {"kept":where["kept"]} + self.release([{"name":"kept","fuzzy_match_percent":0.0}, + {"name":"old","fuzzy_match_percent":100.0}] + ([] if extra else + [{"name":"stray","fuzzy_match_percent":0.0}]), where=w) + + def test_split_tolerance_accepts_only_a_measured_unmatched_retired_row(self): functions, where = self.split_fixture() - functions.append({"name":"retired", "fuzzy_match_percent":0.0}) + self.release(functions + [{"name":"retired", "fuzzy_match_percent":0.0}], where=where) + for extra in ({"name":"retired", "fuzzy_match_percent":100.0}, {"name":"unknown", "fuzzy_match_percent":0.0}): + with self.subTest(extra=extra), self.assertRaises(SystemExit): + self.release(functions + [extra], where=where) with self.assertRaises(SystemExit): - self.release(functions, where=where) + self.release(functions + [{"name":"retired", "fuzzy_match_percent":0.0}], where=where, flags=("--strict",)) + + def test_demoted_rename_is_accepted_only_as_listed_unmatched_and_same_address(self): + old = {"name":"func_0033A520", "fuzzy_match_percent":0.0, + "metadata":{"virtual_address":str(0x0033C448)}} + where = {"kept":(0x1000,8,"boot",None), "func_PAL_0033C448":(0x0033C448,360,"boot",None)} + kept = {"name":"kept", "fuzzy_match_percent":0.0} + self.release([kept, old], where=where, not_carried=["func_0033A520"]) + for change in ("unlisted", "matched", "address", "strict"): + with self.subTest(change=change), self.assertRaises(SystemExit): + f = copy.deepcopy(old) + listed, flags = ["func_0033A520"], () + if change == "unlisted": listed = [] + elif change == "matched": f["fuzzy_match_percent"] = 100.0 + elif change == "address": f["metadata"]["virtual_address"] = "0" + elif change == "strict": flags = ("--strict",) + self.release([kept, f], where=where, not_carried=listed, flags=flags) def test_old_merged_main_with_a_reported_tail_is_rejected(self): functions, where = self.split_fixture() @@ -1055,7 +1240,7 @@ def test_level_split_rejects_wrong_current_layout_and_partial_children(self): where[child]=tuple(row) elif change=="reported child": functions.append({"name":child,"size":"8","fuzzy_match_percent":0.0}) elif change=="unknown missing": where["other"]=(0x300000,8,"level",13) - else: functions.append({"name":"retired","fuzzy_match_percent":0.0}) + else: functions.append({"name":"unmeasured","fuzzy_match_percent":0.0}) self.release(functions,where=where) def test_refreshed_level_split_rows_need_no_exception(self): diff --git a/tools/carry.py b/tools/carry.py index 3e9708dc3..6dd36e89c 100644 --- a/tools/carry.py +++ b/tools/carry.py @@ -479,6 +479,9 @@ def correct_level_entries(rows: list[tuple]) -> list[tuple]: if lv not in texts: texts[lv] = levels.level_text(levels.DUMP / levels.level_dir(lv)) base, data = texts[lv] + if name in levels.FUNCTION_DELAY_SLOTS and \ + levels.words(data[a - base + n - 8:a - base + n - 4]) != (JR_RA,): + raise ValueError(f"{name}: level {lv} has no return before its delay slot") keys.add((levels.fingerprint(data[a - base:a - base + n], a), n)) if len(keys) != 1: raise ValueError(f"{name}: corrected level copies differ") @@ -572,7 +575,7 @@ def refresh_entries() -> None: if not levels.function_residue(name, n): a, n = levels.function_extent(name, a, n) boot.append((name, a, n)) - rows = correct_level_entries(levels.split_level_rows(levels.read_catalogue())) + rows = levels.split_identities(correct_level_entries(levels.split_level_rows(levels.read_catalogue()))) # Validate both catalogues completely before writing either output. write_catalogues(boot, rows) print(f"entry repairs: {len(boot)} boot functions, {len(rows)} level rows; identities retained") diff --git a/tools/compiler/README.md b/tools/compiler/README.md index 69e620741..2340d8d43 100644 --- a/tools/compiler/README.md +++ b/tools/compiler/README.md @@ -211,7 +211,24 @@ block (func_L20_002CD928 case 0x7C). It is off by default, enabled per unit in `tests/test_no_null_pointer_checks.py` covers the anchors, the default/disabled equality and an authored check the pass deletes. +`narrow_saves_below.py` adds `-frac2-narrow-saves-below`: with `-mastra-quad-saves`, the GPR +saves at the slot's full width take the upper slots and the saves narrowed by the stock +`register_precision` attribute the lower ones, so `sd $ra` sits below `sq $s0` +(func_L01_00324550, func_L08_00389B68). A frame with one save width is unchanged, and without +`-mastra-quad-saves` the option does nothing. It is off by default, enabled per unit in +`config/cflags.txt`, and `-fno-rac2-narrow-saves-below` disables it; +`tests/test_narrow_saves_below.py` covers the anchors, the default/disabled equality, a +mixed-width frame and a one-width control. + +`keep_block_zero_copy.py` adds `-frac2-keep-block-zero-copy`: cse keeps a copy from one +pseudo to another whose value is known to be 0 when the source is set earlier in the same +basic block, instead of folding it to `move $rd,$0` (func_002F7320: `daddu $a3,$t1,$zero`). +A zero learnt in an earlier block is folded as before. It is off by default, enabled per unit +in `config/cflags.txt`, and `-fno-rac2-keep-block-zero-copy` disables it; +`tests/test_keep_block_zero_copy.py` covers the anchors, the default/disabled equality, the +kept copy and a control across a call. + `build.sh` stops unless `mips.c`, `mips.h`, `mips.md`, `toplev.c`, `flags.h`, -`haifa-sched.c`, `gcse.c`, `flow.c`, `reorg.c` and `tc-mips.c` hash as it +`haifa-sched.c`, `gcse.c`, `flow.c`, `reorg.c`, `reload1.c`, `loop.c`, `cse.c` and `tc-mips.c` hash as it lists. The binaries' own hashes depend on the build host and path, so check a compiler by its output: `tools/build.py` compiles every matched function to the retail bytes. diff --git a/tools/compiler/build.sh b/tools/compiler/build.sh index b9ccac543..359109124 100755 --- a/tools/compiler/build.sh +++ b/tools/compiler/build.sh @@ -80,19 +80,22 @@ python3 $T/trap_delay_barrier.py gcc/reorg.c python3 $T/trap_redundant_barrier.py gcc/reorg.c python3 $T/count_asm_words.py gcc/config/mips/mips.c python3 $T/no_recombine_givs.py gcc/loop.c +python3 $T/narrow_saves_below.py gcc +python3 $T/keep_block_zero_copy.py gcc sha256sum --check --quiet <<'SUMS' -067fa4c4588fc22d0887d1f33019f04f6553df67109d395b01f6d58ccc0870d8 gcc/config/mips/mips.c +91ac97768f907db2c50b5e04c150b7c7d72c2da3f15d21f0a7f4e802ba8378fb gcc/config/mips/mips.c e25f1a54bfdcc6c96e1c8ba9c9b977f15738ca8554393920e6af33c2d3a3f7bc gcc/config/mips/mips.h 790a54f4772853284ab43a7afc9f592913da8f012b46d43abf5f2a3660467eef gcc/config/mips/mips.md -d75635500f55f4c7c626e925f6e8146c4e33d3865314eca4ae9bb3860fe7eeab gcc/toplev.c +9cc8cc607cdd8a315b67ef3d342ff4779aef414c0ae954743e1b74534aeaf4b7 gcc/toplev.c 3098888cc26ac83c936a8d505662b6ba1aa9039811e89c534f4ea8f1a851e7d6 gcc/haifa-sched.c 656c2b9546b5c38d96cfe25b02620cce02b625f5637ecad6386f0a4d89f3e0fe gcc/reorg.c -5bc40b011473cd756c2a6128b6106fd2e96569c8e92bba1a8f9bc00f166feac2 gcc/flags.h +692efc7f9e569ed16a1a132c835f478fd47be251ae19e4b3cc2e23e8318ac936 gcc/flags.h feb3bd29dd08e1d1b1db78861d580c55f161a55e63cedd368e873c48bc36982d gcc/gcse.c ba947e44256e3d5144e353a4976aac931a4941acc8dcb1dc0fda99fa8b7b504a gcc/flow.c d4031dbfc5e08005b6bdfd23685e02bdde46bf711236c419ebca655ba2f542a9 gas/config/tc-mips.c 6d4c688bdf8517a1da1b35a04bb1e3b6137093a6224b3ed52666581e3a7bd557 gcc/reload1.c 2f6ffa23d379d620ec38db4e527b2cbd5583865195cd8b364aa2c1ce07433faf gcc/loop.c +a2dd997196a573b94aef15338115cfdb1c2a7e29f3dc1857597695f1a0bf9b20 gcc/cse.c SUMS # bison 1.28: the 1999 grammars need its skeleton. @@ -142,6 +145,8 @@ RAC2_COMPILER_ROOT="$OUT" python3 "$ROOT/tests/test_zero_ti_por.py" RAC2_COMPILER_ROOT="$OUT" python3 "$ROOT/tests/test_ti_one_gpr.py" RAC2_GCC_SOURCE="$W/src/gcc/reload1.c" RAC2_COMPILER_ROOT="$OUT" python3 "$ROOT/tests/test_reload_reg_used_guard.py" RAC2_COMPILER_ROOT="$OUT" python3 "$ROOT/tests/test_no_null_pointer_checks.py" +RAC2_COMPILER_ROOT="$OUT" python3 "$ROOT/tests/test_narrow_saves_below.py" +RAC2_COMPILER_ROOT="$OUT" python3 "$ROOT/tests/test_keep_block_zero_copy.py" python3 "$ROOT/tests/test_qcopy_rtl.py" RAC2_COMPILER_ROOT="$OUT" python3 "$ROOT/tests/test_dli_masks.py" RAC2_COMPILER_ROOT="$OUT" python3 "$ROOT/tests/test_hazard_labels.py" diff --git a/tools/compiler/transformers/keep_block_zero_copy.py b/tools/compiler/transformers/keep_block_zero_copy.py new file mode 100644 index 000000000..25b8bea67 --- /dev/null +++ b/tools/compiler/transformers/keep_block_zero_copy.py @@ -0,0 +1,99 @@ +#!/usr/bin/env python3 +"""Add the opt-in -frac2-keep-block-zero-copy: cse keeps a copy of a register zeroed in its block. + +Stock cse_insn (cse.c) puts a register copy `(set (reg B) (reg A))` in the equivalence class +of A, and when A is known to hold CONST_INT 0 the constant wins: MIPS CONST_COSTS gives every +CONST_INT cost 0 and a pseudo costs 1, so the copy becomes `B = 0` (`move B,$0`). +func_002F7320 (132 bytes, 28 places) shows the retail compiler kept such a copy: its entry is +`daddu $t1,$zero,$zero ... daddu $a3,$t1,$zero` for `int result = 0; int i = result;`. The +live copy gives result=0 a dependent, so sched1 puts it before the argument copies and the +allocation becomes retail's (a0 value, a3 i, t0 base, t1 result). + +With this option cse keeps the register source of a pseudo-to-pseudo copy whose known value is +CONST_INT 0 when that register is set earlier in the same basic block (no label, jump or call +between the two); the REG_EQUAL note cse adds still tells loop.c the copy is 0. A zero learnt +in an earlier block on the cse path is folded as before: forced on in every game unit, the +same-block limit leaves func_00349680 (jump1's duplicated loop-exit copy `lo = hi`, retail +`move $18,$0`) unchanged, and only func_002F7320's unit changes. + +The option is off by default, enabled per unit in config/cflags.txt, and +-fno-rac2-keep-block-zero-copy disables it again. tests/test_keep_block_zero_copy.py covers +the anchors, the default/disabled equality, the kept copy and a cross-block control. +See docs/COMPILER-NOTES.md. + +Usage: keep_block_zero_copy.py (the one holding toplev.c) +""" +import sys +from pathlib import Path + +CHOICE_OLD = (" /* If this was an indirect jump insn, a known label will really be\n" + "\t cheaper even though it looks more expensive. */\n") +CHOICE_NEW = (" /* RAC2: -frac2-keep-block-zero-copy keeps a pseudo-to-pseudo copy whose\n" + "\t value is known to be 0 when its source is set earlier in this block. */\n" + " if (flag_rac2_keep_block_zero_copy\n" + "\t && sets[i].src && GET_CODE (sets[i].src) == REG\n" + "\t && REGNO (sets[i].src) >= FIRST_PSEUDO_REGISTER\n" + "\t && GET_CODE (dest) == REG && REGNO (dest) >= FIRST_PSEUDO_REGISTER\n" + "\t && src_const == const0_rtx\n" + "\t && rac2_set_in_block_p (insn, sets[i].src))\n" + "\tsrc = sets[i].src, src_cost = -1;\n" + "\n" + CHOICE_OLD) +HELPER_OLD = "\nstatic void\ncse_insn (insn, libcall_insn)" +HELPER_NEW = ("\n/* RAC2: nonzero if REG is set by an insn between the start of INSN's basic\n" + " block (a label, jump or call) and INSN. */\n" + "static int\n" + "rac2_set_in_block_p (insn, reg)\n" + " rtx insn, reg;\n" + "{\n" + " rtx p;\n" + "\n" + " for (p = PREV_INSN (insn); p; p = PREV_INSN (p))\n" + " {\n" + " if (GET_CODE (p) == CODE_LABEL || GET_CODE (p) == JUMP_INSN\n" + "\t || GET_CODE (p) == CALL_INSN)\n" + "\treturn 0;\n" + " if (GET_CODE (p) == INSN && reg_set_p (reg, p))\n" + "\treturn 1;\n" + " }\n" + " return 0;\n" + "}\n" + HELPER_OLD) +DEFINITION_OLD = "int flag_rac2_narrow_saves_below = 0;\n" +DEFINITION_NEW = ("int flag_rac2_narrow_saves_below = 0;\n" + "\n" + "/* RAC2: opt-in, cse keeps a copy of a register zeroed in its block. */\n" + "int flag_rac2_keep_block_zero_copy = 0;\n") +OPTION_OLD = ' "Put quad-slot GPR saves narrower than the slot below the full-width ones"},\n' +OPTION_NEW = (OPTION_OLD + + ' {"rac2-keep-block-zero-copy", &flag_rac2_keep_block_zero_copy, 1,\n' + ' "Keep a copy of a register set to zero earlier in the same block"},\n') +DECLARATION_OLD = "extern int flag_rac2_narrow_saves_below;\n" +DECLARATION_NEW = ("extern int flag_rac2_narrow_saves_below;\n" + "\n" + "/* RAC2: cse keeps a copy of a register zeroed in its block. */\n" + "extern int flag_rac2_keep_block_zero_copy;\n") + + +def replace_once(text: str, before: str, after: str, label: str) -> str: + if text.count(before) != 1: + raise ValueError(f"{label}: expected one insertion point, found {text.count(before)}") + return text.replace(before, after) + + +def patch(root: Path) -> None: + cse, top, flags = root / "cse.c", root / "toplev.c", root / "flags.h" + sources = {path: path.read_text(encoding="utf-8") for path in (cse, top, flags)} + if any("flag_rac2_keep_block_zero_copy" in text for text in sources.values()): + raise ValueError("keep-block-zero-copy option already present") + folded = replace_once(sources[cse], CHOICE_OLD, CHOICE_NEW, "cse source choice") + folded = replace_once(folded, HELPER_OLD, HELPER_NEW, "cse_insn definition") + driver = replace_once(sources[top], DEFINITION_OLD, DEFINITION_NEW, "option definition") + driver = replace_once(driver, OPTION_OLD, OPTION_NEW, "option table") + declarations = replace_once(sources[flags], DECLARATION_OLD, DECLARATION_NEW, + "option declaration") + # Check every anchor before writing any source: drift must leave the tree intact. + for path, contents in ((cse, folded), (top, driver), (flags, declarations)): + path.write_text(contents, encoding="utf-8", newline="") + + +if __name__ == "__main__": + patch(Path(sys.argv[1])) diff --git a/tools/compiler/transformers/narrow_saves_below.py b/tools/compiler/transformers/narrow_saves_below.py new file mode 100644 index 000000000..1c5bd3b53 --- /dev/null +++ b/tools/compiler/transformers/narrow_saves_below.py @@ -0,0 +1,93 @@ +#!/usr/bin/env python3 +"""Add the opt-in -frac2-narrow-saves-below: full-width GPR saves above narrower ones. + +With -mastra-quad-saves every GPR save slot is a TImode slot and save_restore_insns (mips.c) +walks the saved registers from $31 down, so $ra always takes the top slot and each lower +register the next slot below. The stock EE attribute `register_precision` narrows one +register's save mode (mips_reg_mode[]) but not its place: a register narrowed to DImode +still sits in the slot its number gives it. + +Retail has exactly two quad-slot frames that mix widths, both variadic level functions: +func_L01_00324550 (`sq $s0,0x210` above `sd $ra,0x200`) and func_L08_00389B68 (`sq $s0,0x10` +above `sd $ra,0x0`), each restoring `lq $s0` before `ld $ra`. Every retail frame whose saves +all have one width (func_00115C90, func_00115FC0 and the other -mastra-quad-saves units) +keeps $ra on top. With this option the save loop runs twice over the same descending +register order: first the registers saved at the slot's full width, then the narrower ones, +so a narrower save takes a lower slot. A frame whose saves all have the slot's width is +emitted exactly as before, and without -mastra-quad-saves the option has no effect. + +The option is off by default, enabled per unit in config/cflags.txt (with -mastra-quad-saves), +and -fno-rac2-narrow-saves-below disables it again. tests/test_narrow_saves_below.py covers +the anchors, the default/disabled equality, an authored mixed-width frame and a control. +See docs/COMPILER-NOTES.md. + +Usage: narrow_saves_below.py (the one holding toplev.c) +""" +import sys +from pathlib import Path + +LOOP_OLD = (" for (regno = mips_astra_quad_saves ? GP_REG_LAST : GP_REG_FIRST;\n" + " \t mips_astra_quad_saves ? regno >= GP_REG_FIRST : regno <= GP_REG_LAST;\n" + " \t mips_astra_quad_saves ? regno-- : regno++)\n" + " \tif (BITSET_P (mask, regno - GP_REG_FIRST))\n") +LOOP_NEW = (" /* RAC2: -frac2-narrow-saves-below (with -mastra-quad-saves) takes the\n" + " registers saved at the slot's full width first, then the narrower\n" + " ones, so a register_precision-narrowed save sits below. */\n" + " for (rac2_width_pass = 0;\n" + " rac2_width_pass < (rac2_by_width ? 2 : 1);\n" + " rac2_width_pass++)\n" + " for (regno = mips_astra_quad_saves ? GP_REG_LAST : GP_REG_FIRST;\n" + " \t mips_astra_quad_saves ? regno >= GP_REG_FIRST : regno <= GP_REG_LAST;\n" + " \t mips_astra_quad_saves ? regno-- : regno++)\n" + " \tif (BITSET_P (mask, regno - GP_REG_FIRST)\n" + " \t && (! rac2_by_width\n" + " \t\t|| ((GET_MODE_SIZE (mips_reg_mode[regno])\n" + " \t\t < GET_MODE_SIZE (mips_reg_mode[0])) == rac2_width_pass)))\n") +SCOPE_OLD = (" int rac2_save_pass;\n" + " base_reg_rtx = 0;\n") +SCOPE_NEW = (" int rac2_save_pass;\n" + " int rac2_width_pass;\n" + " int rac2_by_width = flag_rac2_narrow_saves_below && mips_astra_quad_saves != 0;\n" + " base_reg_rtx = 0;\n") +DEFINITION_OLD = "int flag_rac2_no_null_pointer_checks = 0;\n" +DEFINITION_NEW = ("int flag_rac2_no_null_pointer_checks = 0;\n" + "\n" + "/* RAC2: opt-in, quad-slot GPR saves narrower than the slot go below. */\n" + "int flag_rac2_narrow_saves_below = 0;\n") +OPTION_OLD = (' "Do not run the null-pointer-check pass, as GCC 2.95"},\n' + ' {"thread-jumps", &flag_thread_jumps, 1,\n') +OPTION_NEW = (' "Do not run the null-pointer-check pass, as GCC 2.95"},\n' + ' {"rac2-narrow-saves-below", &flag_rac2_narrow_saves_below, 1,\n' + ' "Put quad-slot GPR saves narrower than the slot below the full-width ones"},\n' + ' {"thread-jumps", &flag_thread_jumps, 1,\n') +DECLARATION_OLD = "extern int flag_rac2_no_null_pointer_checks;\n" +DECLARATION_NEW = ("extern int flag_rac2_no_null_pointer_checks;\n" + "\n" + "/* RAC2: quad-slot GPR saves narrower than the slot go below. */\n" + "extern int flag_rac2_narrow_saves_below;\n") + + +def replace_once(text: str, before: str, after: str, label: str) -> str: + if text.count(before) != 1: + raise ValueError(f"{label}: expected one insertion point, found {text.count(before)}") + return text.replace(before, after) + + +def patch(root: Path) -> None: + mips, top, flags = root / "config/mips/mips.c", root / "toplev.c", root / "flags.h" + sources = {path: path.read_text(encoding="utf-8") for path in (mips, top, flags)} + if any("flag_rac2_narrow_saves_below" in text for text in sources.values()): + raise ValueError("narrow-saves-below option already present") + saves = replace_once(sources[mips], LOOP_OLD, LOOP_NEW, "GP save loop") + saves = replace_once(saves, SCOPE_OLD, SCOPE_NEW, "save pass scope") + driver = replace_once(sources[top], DEFINITION_OLD, DEFINITION_NEW, "option definition") + driver = replace_once(driver, OPTION_OLD, OPTION_NEW, "option table") + declarations = replace_once(sources[flags], DECLARATION_OLD, DECLARATION_NEW, + "option declaration") + # Check every anchor before writing any source: drift must leave the tree intact. + for path, contents in ((mips, saves), (top, driver), (flags, declarations)): + path.write_text(contents, encoding="utf-8", newline="") + + +if __name__ == "__main__": + patch(Path(sys.argv[1])) diff --git a/tools/levels.py b/tools/levels.py index 836f1553a..eb2f388ba 100644 --- a/tools/levels.py +++ b/tools/levels.py @@ -998,6 +998,24 @@ def level_extent(number: int, address: int, size: int) -> tuple[int, int]: "func_US2_L19_00353D38": (288, 16), "func_US2_L19_003DEC48": (3336, 8), "func_US2_L19_004131DC": (596, 4), + # Stack-restore residue, then an empty callback whose address is built with + # lui/addiu at every placement (US/PAL/US2); 5 November 2026. + "func_0032A130": (16, 8), + "func_L03_0041B848": (16, 8), + "func_PAL_0032B920": (16, 8), + "func_PAL_L00_003E63F0": (16, 8), + # Two 0xCDCDCDCD fill words after the previous return, then a syscall-0 + # stub; nothing enters the fill in US/PAL/US2; 6 November 2026. + "func_0011A7F8": (24, 8), +} + + +# Rows measured one word short: the catalogued extent ends on the body's last +# `jr $ra` and leaves its delay slot to the next row. Give the slot back. +FUNCTION_DELAY_SLOTS = { + # PAL only: `jr $ra; addiu $sp,$sp,0x20` restores its own -0x20 frame at + # all 27 placements; the rest of the old next row is a residue. + "func_PAL_L00_0030BA80": 336, } @@ -1009,7 +1027,6 @@ def level_extent(number: int, address: int, size: int) -> tuple[int, int]: "func_PAL_L17_00388C38": (1088, -4), "func_PAL_L18_00438248": (608, -4), "func_PAL_L00_002A7D48": (5628, 4), - "func_PAL_L00_0030BA80": (336, 4), "func_PAL_L00_0039BE70": (424, 4), "func_PAL_L00_003C64E8": (1604, 4), "func_PAL_L00_003E1488": (964, 4), @@ -1026,6 +1043,11 @@ def level_extent(number: int, address: int, size: int) -> tuple[int, int]: def function_extent(name: str, address: int, size: int) -> tuple[int, int]: """Apply a named, measured entry correction once; reject unexpected extents.""" + if name in FUNCTION_DELAY_SLOTS: + short = FUNCTION_DELAY_SLOTS[name] + if size not in (short, short + 4): + raise ValueError(f"{name}: {size} bytes, expected {short} or {short + 4}") + return address, short + 4 if name in FUNCTION_END_EXTRA and size == FUNCTION_END_EXTRA[name][0]: size += FUNCTION_END_EXTRA[name][1] if name not in FUNCTION_ENTRY_OFFSETS: @@ -1071,6 +1093,72 @@ def function_extent(name: str, address: int, size: int) -> tuple[int, int]: "func_002DE7F0": 28, "func_002E3E50": 4, "func_00335E28": 12, + # 5 November 2026 audit: each follows a completed return (or tail jump) and + # delay slot; no direct branch/jump, aligned loaded word or lui/addiu pair + # enters it at any placement of USA v1.01, PAL or USA v2.00 carrying the name. + "func_0033B538": 4, + "func_003495B8": 4, + "func_0034CE88": 12, + "func_L00_0031A710": 20, + "func_0029B848": 12, + "func_00288D40": 20, + "func_002ED570": 4, + "func_0029CEC8": 12, + "func_002ED9A8": 20, + "func_002EEBB0": 20, + "func_002ED880": 28, + "func_002ED848": 36, + "func_002ED8F0": 84, + "func_00280660": 12, + "func_002B80B8": 76, + "func_L05_0033CD40": 28, + "func_L05_0033F4A8": 156, + "func_002B0A08": 12, + "func_L05_0037B6C0": 12, + "func_L05_0037BB78": 20, + "func_L09_003FB780": 4, + "func_00130AAC": 4, + "func_00290718": 4, + "func_002FC460": 4, + "func_002FC510": 4, + "func_002FC618": 4, + "func_002FC868": 4, + "func_003380A8": 4, + "func_L25_00373ED0": 4, + "func_L25_00373F08": 4, + "func_0011B580": 8, + "func_0011FA48": 8, + "func_0011C8C8": 12, + "func_00272540": 12, + "func_002B49A0": 12, + "func_002DF630": 12, + "func_0031E6D8": 12, + "func_00326CA8": 12, + "func_0032FDC0": 12, + "func_L01_0042C450": 12, + "func_L23_0041E538": 12, + "func_0012F998": 16, + "func_0026FEF0": 20, + "func_002725C8": 20, + "func_00298D10": 20, + "func_002B8530": 20, + "func_L25_00373EE0": 20, + "func_L30_0032AAF0": 20, + "func_0011E920": 24, + "func_002B4068": 36, + "func_00123490": 44, + "func_0012FB10": 52, + "func_0011ED28": 56, + "func_00129410": 64, + "func_0031D350": 132, + "func_003356E8": 172, + "func_003172D0": 188, + "func_00335270": 252, + "func_00314CF8": 300, + # 6 November 2026: two stack restores and orphan $v0 moves after a completed + # return at all 27 placements of each release (in PAL the first word is the + # predecessor's delay slot, see FUNCTION_DELAY_SLOTS); no reference enters it. + "func_L00_00309DB0": 28, } @@ -1192,15 +1280,91 @@ def level_text(directory: Path) -> tuple[int, bytes]: (("func_L13_0043E8C0", 8), ("func_L13_0043E8C8", 8), ("func_L13_0043E8D0", 8))), "func_L06_0047C1D0": ("d456d82bfa98afa7", "shared", 7, "camvtbl", 1, (("func_L06_0047C1D0", 8), ("func_L06_0047C1D8", 8), ("func_L06_0047C1E0", 8))), + # Hrugis: an 88-byte closed body, then an empty callback whose address the + # level's own code builds with lui/addiu and passes to a registration call. + "func_L10_00419188": ("741d326f9af76cac", "level", 1, "text", 1, + (("func_L10_00419188", 88), ("func_L10_004191E0", 8))), +} + + +# Audited fingerprint collisions (docs/MATCHING-BLOCKERS.md section 34): the +# fingerprint masks these field offsets with the address halves, so two bodies +# share one key. The words after the leading SKIP bytes (the release-specific +# address pair) are the same in every release and tell the bodies apart. Retired +# names are the former rows that held a mixture of both bodies. +IDENTITY_SPLITS = { + # Levels 16, 22, 23 and 26 also hold a `q + 0x20` setter (fields +0x1C/+0x20) + # beside the `q + 0x60` one (fields +0xE4/+0xE8) of all 27 levels; the third + # body under this key, 0x48 bytes earlier, was already grouped correctly. + ("6b8116fb9abb08d4", 72): (8, (("func_L00_00424B70", "7f473cd36e239055"), + ("func_L00_00424BB8", "cd3f4bff2deda94a"), + ("func_L16_0042FB10", "8ad3e57cf77c5195")), + ("func_L16_0042FB58",)), } +def split_identities(rows: list[tuple]) -> list[tuple]: + """Regroup the places of an audited colliding fingerprint by their unmasked words. + + Every place must carry one of the measured bodies, and no level may hold one + body twice; anything else fails before a catalogue is written.""" + out, groups, at = [], {}, {} + for row in rows: + key = (row[3], row[2]) + if key not in IDENTITY_SPLITS: + out.append(row) + continue + groups.setdefault(key, []).append(row) + at.setdefault(key, len(out)) + for key in sorted(at, key=at.get, reverse=True): + skip, parts, retired = IDENTITY_SPLITS[key] + known = {name for name, _ in parts} | set(retired) + places = {digest: [] for _, digest in parts} + for name, _, size, _, locations in groups[key]: + if name not in known: + raise ValueError(f"{name}: unaudited row with split fingerprint {key[0]}") + for lv, a in locations: + base, text = level_text(DUMP / level_dir(lv)) + if not base <= a or a + size > base + len(text): + raise ValueError(f"{name}: level {lv} split body outside EE text") + digest = hashlib.sha256(text[a - base + skip:a - base + size]).hexdigest()[:16] + if digest not in places: + raise ValueError(f"{name}: level {lv} body is not one of the audited bodies") + places[digest].append((lv, a)) + split = [] + for name, digest in parts: + found = sorted(places[digest]) + if not found: + raise ValueError(f"{name}: audited body has no place") + if len({lv for lv, _ in found}) != len(found): + raise ValueError(f"{name}: two copies of one body in a level") + split.append((name, "level" if len(found) == 1 else "shared", key[1], key[0], found)) + out[at[key]:at[key]] = split + return out + + +def code_address_pairs(text: bytes, base: int, target: int) -> int: + """How many `lui r,hi` + `addiu r2,r,lo` pairs (within eight words) in TEXT build TARGET.""" + w, count = words(text), 0 + for i, x in enumerate(w): + if x >> 26 != 0x0F: + continue + rt, hi = (x >> 16) & 31, (x & 0xFFFF) << 16 + for y in w[i + 1:i + 9]: + if y >> 26 == 0x09 and (y >> 21) & 31 == rt: + lo = y & 0xFFFF + if (hi + (lo - 0x10000 if lo & 0x8000 else lo)) & 0xFFFFFFFF == target: + count += 1 + break + return count + + def split_level_rows(rows: list[tuple]) -> list[tuple]: """Apply only the named splits, verifying every complete body and dispatch witness. Both merged and fully split inputs are accepted. Partial, overlapping or - divergent metadata fails before any catalogue is written. Hrugis's unentered - tail is deliberately excluded: return-looking bytes alone are not an entry. + divergent metadata fails before any catalogue is written. Hrugis's tail is split + only with its measured code witness: return-looking bytes alone are not an entry. """ by_name = {r[0]: r for r in rows} if len(by_name) != len(rows): @@ -1237,6 +1401,16 @@ def split_level_rows(rows: list[tuple]) -> list[tuple]: for level, p in locations if level == lv): raise ValueError(f"{name}: another level extent overlaps the split") selected_table = table.get(lv, table.get("default")) if isinstance(table, dict) else table + if selected_table == "text" and len(parts) == 2: + # A code witness: the level's own text builds the second entry's + # address with a lui/addiu pair (e.g. to register it as a callback). + if code_address_pairs(text, base, address + parts[0][1]) != witnesses: + raise ValueError(f"{name}: level {lv} code entry witnesses differ") + offset = 0 + for i, (_, length) in enumerate(parts): + keys[i].add(fingerprint(body[offset:offset + length], address + offset)) + offset += length + continue if selected_table not in ("camvtbl", "vtbl"): raise ValueError(f"{name}: unknown dispatch table") raw = (DUMP / level_dir(lv) / f"{selected_table}.bin").read_bytes() @@ -1560,6 +1734,7 @@ def remember_entry(name, a, n, read, kind): name = f"func_L{number:02d}_{a:08X}" kind = "level" if len({p[0] for p in places}) == 1 else "shared" rows.append((name, kind, e["size"], fp, places)) + rows = split_identities(rows) rows.sort(key=lambda r: r[4][0]) BOOT_FUNCTIONS.parent.mkdir(parents=True, exist_ok=True) BOOT_FUNCTIONS.write_text("# name\taddress\tsize\n" + diff --git a/tools/progress.py b/tools/progress.py index 83965fb42..9736b756a 100644 --- a/tools/progress.py +++ b/tools/progress.py @@ -123,7 +123,10 @@ def check() -> None: c_names = {n for fns in source_functions().values() for n, c in fns if c} by_hand = handwritten() in_c = c_names | by_hand - gone = sorted(matched - in_c) + # Names an audited identity split retired (levels.IDENTITY_SPLITS): the report + # keeps them until a maintainer regenerates it on master. + renamed = {n for spec in levels.IDENTITY_SPLITS.values() for n in spec[2]} + gone = sorted(matched - in_c - renamed) if gone: sys.exit(f"progress/report.json counts {len(gone)} function(s) that are not C in src/, e.g. " f"{', '.join(gone[:5])}: run tools/build.py all, then tools/progress.py") @@ -290,6 +293,30 @@ def pending_level_splits(functions: list[dict], where: dict) -> set[str] | None: return missing +def demoted_renames(version: str, functions: list, retired: set, missing: set, where: dict) -> dict: + """Retired report rows that tools/carry.py --demote renamed for the release: each is + listed in config//not_carried.tsv, is unmatched in the report, and has exactly + one missing catalogue row of the release's own name at its reported address.""" + path = ROOT / levels.VERSIONS[version]["config"] / "not_carried.tsv" + listed = set() + if path.is_file(): + listed = {line.split("\t", 1)[0] for line in path.read_text().splitlines() + if line and not line.startswith("#")} + prefix = f"func_{levels.VERSIONS[version]['tag']}_" + out = {} + for f in functions: + name = f["name"] + if name not in retired or name not in listed or f["fuzzy_match_percent"] != 0.0: + continue + address = f.get("metadata", {}).get("virtual_address") + if address is None: + continue + found = [m for m in missing if m.startswith(prefix) and where[m][0] == int(address)] + if len(found) == 1: + out[name] = found[0] + return out + + def release_check(version: str, report_path: Path) -> None: """CI's check for another release, without the disc: the report counts only functions of the release's catalogues that are C (or ASM_FUNC) in src/ and src//, and every @@ -300,7 +327,8 @@ def release_check(version: str, report_path: Path) -> None: c_names = {n for fns in source_functions(version).values() for n, c in fns if c} by_hand = handwritten(version) in_c = c_names | by_hand - gone = sorted(matched - (in_c & set(where))) + renamed = {n for spec in levels.IDENTITY_SPLITS.values() for n in spec[2]} + gone = sorted(matched - (in_c & set(where)) - renamed) if gone: sys.exit(f"{report_path.relative_to(ROOT)} counts {len(gone)} function(s) that are not C in src/, e.g. " f"{', '.join(gone[:5])}: run tools/build.py all --version {version}, then tools/progress.py --version {version}") @@ -328,12 +356,21 @@ def release_check(version: str, report_path: Path) -> None: # are tolerated. Unknown missing entries and duplicate compensation fail. explained = (level_splits | ({"func_00131DE8"} if split else set()) | ({"func_00115E38"} if assertion_split else set())) - known_split = bool(missing) and missing == explained and not retired - known_boundary = ((retired or known_split) and retired <= set(levels.FUNCTION_RESIDUES) + # A name retired by an audited identity split explains its unreported parts. + explained |= {n for spec in levels.IDENTITY_SPLITS.values() if set(spec[2]) & retired + for n, _ in spec[1] if n not in reported} + # A demoted v1.01 name (config//not_carried.tsv), unmatched in the report, + # explains exactly one missing release-named row at the same address. + demoted = demoted_renames(version, functions, retired, missing, where) + explained |= set(demoted.values()) + # Measured residues may retire in the same tree as exactly explained splits. + known_split = bool(missing) and missing == explained + known_boundary = ((retired or known_split) + and retired <= set(levels.FUNCTION_RESIDUES) | renamed | set(demoted) and (not missing or known_split) and total == len(where) + len(retired) - len(missing) and all(f["fuzzy_match_percent"] == 0.0 for f in functions - if f["name"] in retired)) + if f["name"] in retired - renamed)) if not known_boundary or "--strict" in sys.argv: sys.exit(f"{report_path.relative_to(ROOT)} has {total} functions, the catalogues {len(where)}: " f"regenerate it with tools/progress.py --version {version}")