diff options
Diffstat (limited to 'src/pokenav.c')
-rw-r--r-- | src/pokenav.c | 621 |
1 files changed, 609 insertions, 12 deletions
diff --git a/src/pokenav.c b/src/pokenav.c index 42114a4b2..1912e7e57 100644 --- a/src/pokenav.c +++ b/src/pokenav.c @@ -28,6 +28,33 @@ enum #define UNKNOWN_OFFSET 100000 +struct UnknownSubSubStruct_0203CF40 { + u8 bg; + u8 unk1; + u8 unk2; + u8 unk3; + u8 unk4; + u8 unk5; + u16 unk6; + u8 windowId; + u8 unk9; + u16 unkA; + u16 unkC; + u16 unkE; +}; + +struct UnknownSubSubStruct_81C81D4 { + u16 unk0; + u16 unk2; + u16 unk4; + u16 unk6; + u16 unk8; + u16 unkA; + u32 unkC; + u32 unk10; +}; + +// Generally at index 0. struct UnknownSubStruct_0203CF40 { void (*unk0)(u32); @@ -39,7 +66,32 @@ struct UnknownSubStruct_0203CF40 struct Sprite *unk18; struct Sprite *unk1C[2]; struct Sprite *unk24[2]; - u8 tilemapBuffer[0x1000]; + u8 tilemapBuffer[0x800]; +}; + +// Generally at index 0x11 (17) +struct UnknownSubStruct_81C81D4 +{ + struct UnknownSubSubStruct_0203CF40 unk0; + u32 unk10; + u32 unk14; + u32 unk18; + u32 unk1C; + s32 unk20; + s32 unk24; + u32 unk28; + s32 unk2C; + u32 unk30; + void (*unk34)(u32, char*); + void (*unk38)(u16, u32, u32); + u32 unk3C; + u32 unk40; + u32 unk44; + char unk48[0x40]; + u8 tilemapBuffer[0x800]; + struct UnknownSubSubStruct_81C81D4 unk888; + u32 unk89C; + u32 unk8A0; }; #define SUBSTRUCT_COUNT 19 @@ -51,7 +103,7 @@ struct UnknownStruct_0203CF40 u16 mode; u16 fieldA; bool32 hasAnyRibbons; - struct UnknownSubStruct_0203CF40 *field10[SUBSTRUCT_COUNT]; + void *field10[SUBSTRUCT_COUNT]; }; extern u32 sub_81C9430(void); @@ -59,6 +111,7 @@ extern void sub_81CAADC(void); extern u32 sub_81C99D4(void); extern void sub_8199D98(void); extern void sub_81C7D28(void); +extern void sub_81C8FE0(void); extern u32 sub_81C9298(void); extern u32 sub_81C941C(void); extern u32 sub_81C9924(void); @@ -116,7 +169,22 @@ extern u32 sub_81D04B8(void); extern u32 sub_81D09F4(void); extern u32 sub_81CFA04(void); extern u32 sub_81CFE08(void); - +extern u32 sub_81C91AC(struct UnknownSubStruct_81C81D4 *a0, const void *a1, void *a2, s32 a3); +extern u32 sub_81C9160(struct UnknownSubSubStruct_81C81D4 *a0, void *a1); +extern void sub_81C8ED0(void); +extern void sub_81C8EF8(struct UnknownSubSubStruct_81C81D4 *a0, struct UnknownSubSubStruct_0203CF40 *a1); +extern u32 sub_81C8870(s32 a0); +extern u32 sub_81C8958(s32 a0); + +u32 sub_81C85A0(s32); +void sub_81C8568(s32 a0, struct UnknownSubStruct_81C81D4 *a1); +u32 sub_81C83F0(s32); +bool32 sub_81C83E0(void); +void sub_81C83AC(u32 a0, u32 a1, u32 a2, u32 a3, u32 a4, struct UnknownSubStruct_81C81D4 *a5); +void sub_81C837C(struct UnknownSubSubStruct_81C81D4 *a0, struct UnknownSubStruct_81C81D4 *a1); +void sub_81C835C(struct UnknownSubSubStruct_0203CF40 *a0); +void sub_81C82E4(struct UnknownSubStruct_81C81D4 *a0); +u32 sub_81C8254(s32); u32 sub_81C791C(s32 a0); bool32 sub_81C756C(u32 a0); bool32 sub_81C76C4(void); @@ -382,7 +450,7 @@ const struct CompressedSpriteSheet gUnknown_0861FA64 = extern struct UnknownStruct_0203CF40 *gUnknown_0203CF40; extern u8 gUnknown_0203CF3C; extern const struct SpriteTemplate gUnknown_0861FB04; - +extern u32 gUnknown_0203CF44; // code u32 sub_81C7078(u32 (*func)(s32), u32 priority) { @@ -412,14 +480,14 @@ bool32 sub_81C70D8(u32 a0) return FALSE; } -bool32 sub_81C7124(u32 a0) +bool32 sub_81C7124(u32 (*a0)(s32)) { s32 i; for (i = 0; i < NUM_TASKS; i++) { if (gTasks[i].isActive && (gTasks[i].func == sub_81C7170 || gTasks[i].func == sub_81C71E4) - && GetWordTaskArg(i, 1) == a0) + && (void *)GetWordTaskArg(i, 1) == a0) return TRUE; } return FALSE; @@ -718,7 +786,7 @@ void *AllocSubstruct(u32 index, u32 size) return gUnknown_0203CF40->field10[index] = Alloc(size); } -struct UnknownSubStruct_0203CF40 *GetSubstructPtr(u32 index) +void *GetSubstructPtr(u32 index) { return gUnknown_0203CF40->field10[index]; } @@ -760,7 +828,9 @@ bool32 CanViewRibbonsMenu(void) bool32 sub_81C76C4(void) { - struct UnknownSubStruct_0203CF40 *structPtr = AllocSubstruct(0, 0x82C); + struct UnknownSubStruct_0203CF40 *structPtr; + + structPtr = AllocSubstruct(0, sizeof(struct UnknownSubStruct_0203CF40)); if (structPtr == NULL) return FALSE; @@ -1422,12 +1492,539 @@ void sub_81C817C(struct Sprite *sprite) } } -/* -bool32 sub_81C81D4(const void *arg0, void *arg1, s32 arg3) +bool32 sub_81C81D4(const void *arg0, void *arg1, s32 arg2) { - struct UnknownSubStruct_0203CF40 *structPtr = AllocSubstruct(0x11, 0x8A4); + u32 v1; + struct UnknownSubStruct_81C81D4 *structPtr; + + structPtr = AllocSubstruct(0x11, sizeof(struct UnknownSubStruct_81C81D4)); if (structPtr == NULL) return FALSE; + + sub_81C9160(&structPtr->unk888, arg1); + + v1 = sub_81C91AC(structPtr, arg0, arg1, arg2); + if (v1 == 0) + return FALSE; + + sub_81C7078(sub_81C8254, 6); + return TRUE; +} + +bool32 sub_81C8224(void) +{ + return sub_81C7124(sub_81C8254); +} + +void sub_81C8234(void) +{ + struct UnknownSubStruct_81C81D4 *structPtr; + + structPtr = GetSubstructPtr(0x11); + sub_81C8FE0(); + RemoveWindow(structPtr->unk0.windowId); + FreeSubstruct(0x11); +} + +u32 sub_81C8254(s32 a0) +{ + struct UnknownSubStruct_81C81D4 *structPtr; + + if (IsDma3ManagerBusyWithBgCopy()) + return 2; + + structPtr = GetSubstructPtr(0x11); + + switch (a0) + { + case 0: + sub_81C82E4(structPtr); + return 0; + case 1: + sub_81C835C(&structPtr->unk0); + return 0; + case 2: + sub_81C837C(&structPtr->unk888, structPtr); + return 0; + case 3: + if (sub_81C83E0()) + { + return 2; + } + else + { + sub_81C8ED0(); + return 1; + } + case 4: + sub_81C8EF8(&structPtr->unk888, &structPtr->unk0); + return 4; + default: + return 4; + } +} + +void sub_81C82E4(struct UnknownSubStruct_81C81D4 *a0) +{ + u16 v1 = (a0->unk0.unk1 << 12) | a0->unk0.unk6; + // TODO: When #553 is merged, use a PALETTE_NUM_TO_FILL_VALUE(1) macro here... + sub_8199DF0(a0->unk0.bg, 0x11, a0->unk0.unk6, 1); + // ...and PALETTE_NUM_TO_FILL_VALUE(4) here. + sub_8199DF0(a0->unk0.bg, 0x44, a0->unk0.unk6 + 1, 1); + SetBgTilemapBuffer(a0->unk0.bg, a0->tilemapBuffer); + FillBgTilemapBufferRect_Palette0(a0->unk0.bg, v1, 0, 0, 32, 32); + ChangeBgY(a0->unk0.bg, 0, 0); + ChangeBgX(a0->unk0.bg, 0, 0); + ChangeBgY(a0->unk0.bg, a0->unk0.unk3 << 11, 2); + CopyBgTilemapBufferToVram(a0->unk0.bg); +} + +void sub_81C835C(struct UnknownSubSubStruct_0203CF40 *a0) +{ + // TODO: When #553 is merged, use a PALETTE_NUM_TO_FILL_VALUE(1) macro here. + FillWindowPixelBuffer(a0->windowId, 0x11); + PutWindowTilemap(a0->windowId); + CopyWindowToVram(a0->windowId, 1); +} + +void sub_81C837C(struct UnknownSubSubStruct_81C81D4 *a0, struct UnknownSubStruct_81C81D4 *a1) +{ + s32 v1; + s32 v2; + + // TODO: Clean this up. + v1 = a0->unk2 - a0->unk0; + v2 = a0->unk8; + if (v1 > a0->unk8) + v1 = v2; + sub_81C83AC(a0->unk10, a0->unk0, v1, a0->unkC, 0, a1); } -*/ + +void sub_81C83AC(u32 a0, u32 a1, u32 a2, u32 a3, u32 a4, struct UnknownSubStruct_81C81D4 *a5) +{ + if (a2 == 0) + return; + + a5->unk1C = a0 + a1 * a3; + a5->unk18 = a3; + a5->unk0.unkC = 0; + a5->unk0.unkE = a2; + a5->unk14 = a1; + a5->unk10 = a4; + sub_81C7078(sub_81C83F0, 5); +} + +bool32 sub_81C83E0(void) +{ + return sub_81C7124(sub_81C83F0); +} + +u32 sub_81C83F0(s32 a0) +{ + struct UnknownSubStruct_81C81D4 *structPtr; + u32 v1; + + structPtr = GetSubstructPtr(0x11); + switch (a0) + { + case 0: + v1 = (structPtr->unk0.unkA + structPtr->unk0.unkC + structPtr->unk10) & 0xF; + structPtr->unk34(structPtr->unk1C, structPtr->unk48); + if (structPtr->unk38 != NULL) + // Accessing unk0.windowId as if it were a u16...? + // It's accessed as a u8 again in the very next line... + structPtr->unk38(*(u16*)(&structPtr->unk0.windowId), structPtr->unk14, v1); + + AddTextPrinterParameterized(structPtr->unk0.windowId, structPtr->unk0.unk5, structPtr->unk48, 8, (v1 << 4) | 1, 255, (void (*)(struct TextPrinterTemplate*, u16))a0); + + if (++structPtr->unk0.unkC >= structPtr->unk0.unkE) + { + if (structPtr->unk38 != NULL) + CopyWindowToVram(structPtr->unk0.windowId, 3); + else + CopyWindowToVram(structPtr->unk0.windowId, 2); + return 0; + } + else + { + structPtr->unk1C += structPtr->unk18; + structPtr->unk14++; + return 3; + } + case 1: + if (IsDma3ManagerBusyWithBgCopy()) + return 2; + else + return 4; + default: + return 4; + } +} + +bool32 sub_81C84A4(void) +{ + u16 v1; + s32 v2; + struct UnknownSubStruct_81C81D4 *structPtr; + structPtr = GetSubstructPtr(0x11); + + return structPtr->unk888.unk0 != 0; +} + +bool32 sub_81C84C0(void) +{ + struct UnknownSubSubStruct_81C81D4 *subPtr; + struct UnknownSubStruct_81C81D4 *structPtr; + structPtr = GetSubstructPtr(0x11); + subPtr = &structPtr->unk888; + + return subPtr->unk0 + subPtr->unk8 < subPtr->unk2; +} + + +#ifdef NONMATCHING +// This has some register renaming issues (r4, r5, and r6 are all switched around), and +// for some reason it's creating two copies of subPtr->unk0. +void sub_81C84E8(s32 a0, s32 a1) +{ + s32 v1; + struct UnknownSubSubStruct_81C81D4 *subPtr; + struct UnknownSubStruct_81C81D4 *structPtr; + structPtr = GetSubstructPtr(0x11); + subPtr = &structPtr->unk888; + + if (a0 < 0) + { + // This is where the issue is. subPtr->unk0 is being stored in r1 and then copied to + // r2... and then r2 is read for the if statement, r1 is read for the function call, + // and then both are clobbered as expected. Between those two uses, no writes to r1/r2 + // happen; it doesn't need to be duplicated/moved at all. + if (subPtr->unk0 + a0 < 0) + v1 = -1 * subPtr->unk0; + else + v1 = a0; + if (a1 != 0) + sub_81C83AC(subPtr->unk10, subPtr->unk0 + v1, v1 * -1, subPtr->unkC, v1, structPtr); + } + else if (a1 != 0) + { + + gUnknown_0203CF44 = subPtr->unk0 + subPtr->unk8; + if ((s32)(gUnknown_0203CF44) + a0 >= (s32)subPtr->unk2) + v1 = subPtr->unk2 - gUnknown_0203CF44; + else + v1 = a0; + + sub_81C83AC(subPtr->unk10, gUnknown_0203CF44, v1, subPtr->unkC, subPtr->unk8, structPtr); + // Needed to prevent GCC from combining the two sub_81C83AC calls. + asm(""); + } + else + { + v1 = a0; + } + + sub_81C8568(v1, structPtr); + subPtr->unk0++; +} +#else +NAKED +void sub_81C84E8(s32 a0, s32 a1) +{ + asm(".syntax unified\n\ + push {r4-r7,lr}\n\ + sub sp, 0x8\n\ + adds r6, r0, 0\n\ + adds r4, r1, 0\n\ + movs r0, 0x11\n\ + bl GetSubstructPtr\n\ + adds r7, r0, 0\n\ + ldr r0, =0x00000888\n\ + adds r5, r7, r0\n\ + cmp r6, 0\n\ + bge _081C8524\n\ + ldrh r1, [r5]\n\ + adds r0, r1, r6\n\ + cmp r0, 0\n\ + bge _081C850A\n\ + negs r6, r1\n\ +_081C850A:\n\ + cmp r4, 0\n\ + beq _081C854E\n\ + ldr r0, [r5, 0x10]\n\ + adds r1, r6\n\ + negs r2, r6\n\ + ldr r3, [r5, 0xC]\n\ + str r6, [sp]\n\ + str r7, [sp, 0x4]\n\ + bl sub_81C83AC\n\ + b _081C854E\n\ + .pool\n\ +_081C8524:\n\ + cmp r4, 0\n\ + beq _081C854E\n\ + ldr r2, =gUnknown_0203CF44\n\ + ldrh r1, [r5]\n\ + ldrh r0, [r5, 0x8]\n\ + adds r4, r1, r0\n\ + str r4, [r2]\n\ + adds r0, r4, r6\n\ + ldrh r1, [r5, 0x2]\n\ + cmp r0, r1\n\ + blt _081C853C\n\ + subs r6, r1, r4\n\ +_081C853C:\n\ + ldr r0, [r5, 0x10]\n\ + ldr r3, [r5, 0xC]\n\ + ldrh r1, [r5, 0x8]\n\ + str r1, [sp]\n\ + str r7, [sp, 0x4]\n\ + adds r1, r4, 0\n\ + adds r2, r6, 0\n\ + bl sub_81C83AC\n\ +_081C854E:\n\ + adds r0, r6, 0\n\ + adds r1, r7, 0\n\ + bl sub_81C8568\n\ + ldrh r0, [r5]\n\ + adds r0, r6\n\ + strh r0, [r5]\n\ + add sp, 0x8\n\ + pop {r4-r7}\n\ + pop {r0}\n\ + bx r0\n\ + .pool\n\ + .syntax divided"); +} +#endif + +void sub_81C8568(s32 a0, struct UnknownSubStruct_81C81D4 *a1) +{ + a1->unk20 = GetBgY(a1->unk0.bg); + a1->unk24 = a1->unk20 + (a0 << 12); + if (a0 > 0) + a1->unk30 = 1; + else + a1->unk30 = 2; + a1->unk2C = a0; + a1->unk28 = sub_81C7078(sub_81C85A0, 6); +} + +u32 sub_81C85A0(s32 a0) +{ + s32 y; + s32 v1; + bool32 flag; + struct UnknownSubStruct_81C81D4 *structPtr; + structPtr = GetSubstructPtr(0x11); + + switch (a0) + { + case 0: + if (sub_81C83E0() == FALSE) + return 1; + else + return 2; + case 1: + flag = FALSE; + y = GetBgY(structPtr->unk0.bg); + v1 = ChangeBgY(structPtr->unk0.bg, 0x1000, structPtr->unk30); + if (structPtr->unk30 == 2) + { + if ((y > structPtr->unk24 || y <= structPtr->unk20) && v1 <= structPtr->unk24) + { + flag = TRUE; + } + } + else + { + if ((y < structPtr->unk24 || y >= structPtr->unk20) && v1 >= structPtr->unk24) + { + flag = TRUE; + } + } + if (flag) + { + structPtr->unk0.unkA = (structPtr->unk0.unkA + structPtr->unk2C) & 0xF; + ChangeBgY(structPtr->unk0.bg, structPtr->unk24, 0); + return 4; + } + else + { + return 2; + } + default: + return 4; + } +} + +bool32 sub_81C8630(void) +{ + struct UnknownSubStruct_81C81D4 *structPtr; + structPtr = GetSubstructPtr(0x11); + return sub_81C70D8(structPtr->unk28); +} + +struct UnknownSubSubStruct_81C81D4 *sub_81C8644(void) +{ + struct UnknownSubStruct_81C81D4 *structPtr; + structPtr = GetSubstructPtr(0x11); + return &structPtr->unk888; +} + +u32 sub_81C8658(void) +{ + struct UnknownSubSubStruct_81C81D4 *structPtr; + structPtr = sub_81C8644(); + + // Using unk6 as a timer. + if (structPtr->unk6 != 0) + { + structPtr->unk6--; + return 1; + } + else + { + if (sub_81C84A4()) + { + sub_81C84E8(-1, 1); + return 2; + } + else + { + return 0; + } + } +} + +u32 sub_81C868C(void) +{ + struct UnknownSubSubStruct_81C81D4 *structPtr; + structPtr = sub_81C8644(); + + if (structPtr->unk0 + structPtr->unk6 < structPtr->unk2 - 1) + { + if (structPtr->unk6 < structPtr->unk8 - 1) + { + structPtr->unk6++; + return 1; + } + else if (!sub_81C84C0()) + { + return 0; + } + } + else + { + return 0; + } + sub_81C84E8(1, 1); + return 2; +} + +u32 sub_81C86CC(void) +{ + struct UnknownSubSubStruct_81C81D4 *structPtr; + s32 v1; + + structPtr = sub_81C8644(); + if (sub_81C84A4()) + { + if (structPtr->unk0 >= structPtr->unk8) + v1 = structPtr->unk8; + else + v1 = structPtr->unk0; + sub_81C84E8(v1 * -1, 1); + return 2; + } + else if (structPtr->unk6 != 0) + { + structPtr->unk6 = 0; + return 1; + } + else + { + return 0; + } +} + +u32 sub_81C870C(void) +{ + struct UnknownSubSubStruct_81C81D4 *structPtr; + structPtr = sub_81C8644(); + + if (sub_81C84C0()) + { + s32 v1; + s32 v2; + s32 v3; + v2 = structPtr->unk0 + structPtr->unk8; + v1 = structPtr->unk4 - structPtr->unk0; + if (v2 <= structPtr->unk4) + v1 = structPtr->unk8; + sub_81C84E8(v1, 1); + return 2; + } + else + { + s32 v1; + s32 v2; + if (structPtr->unk2 >= structPtr->unk8) + { + v1 = structPtr->unk6; + v2 = structPtr->unk8; + } + else + { + v1 = structPtr->unk6; + v2 = structPtr->unk2; + } + v2 -= 1; + if (v1 >= v2) + { + return 0; + } + else + { + structPtr->unk6 = v2; + return 1; + } + } +} + +u32 sub_81C875C(void) +{ + struct UnknownSubSubStruct_81C81D4 *structPtr; + structPtr = sub_81C8644(); + + return structPtr->unk0 + structPtr->unk6; +} + +u32 sub_81C8770(void) +{ + struct UnknownSubSubStruct_81C81D4 *structPtr; + structPtr = sub_81C8644(); + + return structPtr->unk0; +} + +void sub_81C877C(void) +{ + struct UnknownSubStruct_81C81D4 *structPtr; + structPtr = GetSubstructPtr(0x11); + structPtr->unk89C = 0; + structPtr->unk8A0 = sub_81C7078(sub_81C8870, 6); +} + +void sub_81C87AC(u16 a0) +{ + u16 temp; + struct UnknownSubStruct_81C81D4 *structPtr; + structPtr = GetSubstructPtr(0x11); + temp = structPtr->unk888.unk0; + temp += a0; + structPtr->unk888.unk0 = temp; + structPtr->unk89C = 0; + structPtr->unk8A0 = sub_81C7078(sub_81C8958, 6); +}
\ No newline at end of file |