summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--asm/link.s135
-rw-r--r--common_syms/link.txt1
-rw-r--r--data/link.s16
-rw-r--r--include/gba/io_reg.h17
-rw-r--r--include/librfu.h2
-rw-r--r--include/link.h4
-rw-r--r--include/main.h1
-rw-r--r--ld_script.txt2
-rw-r--r--src/link.c69
9 files changed, 91 insertions, 156 deletions
diff --git a/asm/link.s b/asm/link.s
index 291f71a57..d4b76a96e 100644
--- a/asm/link.s
+++ b/asm/link.s
@@ -5,141 +5,6 @@
.text
- thumb_func_start sub_80093CC
-sub_80093CC: @ 80093CC
- push {lr}
- bl sub_800B488
- bl sub_800E700
- bl sub_800BEC0
- ldr r1, =0x00008001
- cmp r0, r1
- beq _080093F4
- bl sub_800B4A4
- bl sub_80097E8
- bl RestoreSerialTimer3IntrHandlers
- movs r0, 0
- b _080093FE
- .pool
-_080093F4:
- bl rfu_REQ_stopMode
- bl rfu_waitREQComplete
- movs r0, 0x1
-_080093FE:
- pop {r1}
- bx r1
- thumb_func_end sub_80093CC
-
- thumb_func_start sub_8009404
-sub_8009404: @ 8009404
- push {lr}
- lsls r0, 24
- lsrs r0, 24
- bl DestroyTask
- pop {r0}
- bx r0
- thumb_func_end sub_8009404
-
- thumb_func_start sub_8009414
-sub_8009414: @ 8009414
- push {r4-r7,lr}
- mov r7, r8
- push {r7}
- adds r5, r0, 0
- ldr r4, [sp, 0x18]
- lsls r5, 24
- lsrs r5, 24
- lsls r1, 24
- lsrs r1, 24
- mov r8, r1
- lsls r2, 24
- lsrs r6, r2, 24
- lsls r3, 24
- lsrs r7, r3, 24
- lsls r4, 16
- lsrs r4, 16
- ldr r0, =gLinkTestDigitsPal
- lsls r1, r5, 4
- movs r2, 0x20
- bl LoadPalette
- ldr r3, =0x040000d4
- ldr r0, =gLinkTestDigitsGfx
- str r0, [r3]
- lsls r2, r7, 14
- lsls r0, r4, 5
- movs r1, 0xC0
- lsls r1, 19
- adds r0, r1
- adds r2, r0
- str r2, [r3, 0x4]
- ldr r0, =0x80000110
- str r0, [r3, 0x8]
- ldr r0, [r3, 0x8]
- ldr r0, =gUnknown_03003130
- str r6, [r0]
- str r5, [r0, 0x4]
- str r4, [r0, 0x8]
- mov r0, r8
- cmp r0, 0x2
- beq _0800949E
- cmp r0, 0x2
- bgt _08009484
- cmp r0, 0x1
- beq _0800948C
- b _080094C0
- .pool
-_08009484:
- mov r0, r8
- cmp r0, 0x3
- beq _080094B0
- b _080094C0
-_0800948C:
- lsls r1, r6, 8
- movs r0, 0x1
- orrs r1, r0
- lsls r0, r7, 2
- orrs r1, r0
- movs r0, 0xA
- bl SetGpuReg
- b _080094C0
-_0800949E:
- lsls r1, r6, 8
- movs r0, 0x1
- orrs r1, r0
- lsls r0, r7, 2
- orrs r1, r0
- movs r0, 0xC
- bl SetGpuReg
- b _080094C0
-_080094B0:
- lsls r1, r6, 8
- movs r0, 0x1
- orrs r1, r0
- lsls r0, r7, 2
- orrs r1, r0
- movs r0, 0xE
- bl SetGpuReg
-_080094C0:
- mov r0, r8
- lsls r4, r0, 2
- adds r0, r4, 0
- adds r0, 0x10
- lsls r0, 24
- lsrs r0, 24
- movs r1, 0
- bl SetGpuReg
- adds r4, 0x12
- lsls r4, 24
- lsrs r4, 24
- adds r0, r4, 0
- movs r1, 0
- bl SetGpuReg
- pop {r3}
- mov r8, r3
- pop {r4-r7}
- pop {r0}
- bx r0
- thumb_func_end sub_8009414
-
thumb_func_start sub_80094EC
sub_80094EC: @ 80094EC
push {r4-r6,lr}
diff --git a/common_syms/link.txt b/common_syms/link.txt
new file mode 100644
index 000000000..22e3081ee
--- /dev/null
+++ b/common_syms/link.txt
@@ -0,0 +1 @@
+gUnknown_03003130
diff --git a/data/link.s b/data/link.s
index d9cf886c5..578ae0256 100644
--- a/data/link.s
+++ b/data/link.s
@@ -5,22 +5,6 @@
.section .rodata
- .align 2
-gWirelessLinkDisplayPal:: @ 82EC86C
- .incbin "graphics/interface/wireless_link_display.gbapal"
-
-gWirelessLinkDisplayGfx:: @ 82EC88C
- .incbin "graphics/interface/wireless_link_display.4bpp.lz"
-
-gWirelessLinkDisplayTilemap:: @ 82ECD34
- .incbin "graphics/interface/wireless_link_display.bin.lz"
-
-gLinkTestDigitsPal:: @ 82ECF20
- .incbin "graphics/interface/link_test_digits.gbapal"
-
-gLinkTestDigitsGfx:: @ 82ECF40
- .incbin "graphics/interface/link_test_digits.4bpp"
-
.string "{HIGHLIGHT TRANSPARENT}{COLOR WHITE}$"
.align 2
diff --git a/include/gba/io_reg.h b/include/gba/io_reg.h
index f86f2434c..998e68e16 100644
--- a/include/gba/io_reg.h
+++ b/include/gba/io_reg.h
@@ -584,6 +584,23 @@
#define TIMER_INTR_ENABLE 0x40
#define TIMER_ENABLE 0x80
+// BGCNT
+#define BGCNT_PRIORITY(n) (n) // Values 0 - 3. Lower priority BGs will be drawn on top of higher priority BGs.
+#define BGCNT_CHARBASE(n) ((n) << 2) // Values 0 - 3. Base block for tile pixel data.
+#define BGCNT_MOSAIC 0x0040
+#define BGCNT_16COLOR 0x0000 // 4 bits per pixel
+#define BGCNT_256COLOR 0x0080 // 8 bits per pixel
+#define BGCNT_SCREENBASE(n) ((n) << 8) // Values 0 - 31. Base block for tile map.
+#define BGCNT_WRAP 0x2000 // Only affects affine BGs. Text BGs wrap by default.
+#define BGCNT_TXT256x256 0x0000 // Internal screen size size of text mode BG in pixels.
+#define BGCNT_TXT512x256 0x4000
+#define BGCNT_TXT256x512 0x8000
+#define BGCNT_TXT512x512 0xC000
+#define BGCNT_AFF128x128 0x0000 // Internal screen size size of affine mode BG in pixels.
+#define BGCNT_AFF256x256 0x4000
+#define BGCNT_AFF512x512 0x8000
+#define BGCNT_AFF1024x1024 0xC000
+
// serial
#define SIO_ID 0x0030 // Communication ID
diff --git a/include/librfu.h b/include/librfu.h
index dbc8a41a6..0cf781d73 100644
--- a/include/librfu.h
+++ b/include/librfu.h
@@ -106,3 +106,5 @@ struct RfuIntrStruct
extern struct RfuStruct *gRfuState;
void STWI_init_all(struct RfuIntrStruct *interruptStruct, IntrFunc *interrupt, bool8 copyInterruptToRam);
+void rfu_REQ_stopMode(void);
+void rfu_waitREQComplete(void);
diff --git a/include/link.h b/include/link.h
index 7a6563144..64bb8ff47 100644
--- a/include/link.h
+++ b/include/link.h
@@ -193,4 +193,8 @@ u8 sub_800ABAC(void);
u8 sub_800ABBC(void);
void sub_800AC34(void);
+void sub_80097E8(void);
+
+extern IWRAM_DATA u32 gUnknown_03003130[3]; // common
+
#endif // GUARD_LINK_H
diff --git a/include/main.h b/include/main.h
index e283d1754..46c8fd681 100644
--- a/include/main.h
+++ b/include/main.h
@@ -60,5 +60,6 @@ void SetSerialCallback(IntrCallback callback);
void InitFlashTimer(void);
void DoSoftReset(void);
void ClearPokemonCrySongs(void);
+void RestoreSerialTimer3IntrHandlers(void);
#endif // GUARD_MAIN_H
diff --git a/ld_script.txt b/ld_script.txt
index c8d31c846..34b9a7722 100644
--- a/ld_script.txt
+++ b/ld_script.txt
@@ -51,6 +51,7 @@ SECTIONS {
src/text.o(.text);
src/sprite.o(.text);
src/string_util.o(.text);
+ src/link.o(.text);
asm/link.o(.text);
src/rtc.o(.text);
asm/main_menu.o(.text);
@@ -327,6 +328,7 @@ SECTIONS {
src/sprite.o(.rodata);
data/io_reg.o(.rodata);
src/string_util.o(.rodata);
+ src/link.o(.rodata);
data/link.o(.rodata);
src/rtc.o(.rodata);
data/main_menu.o(.rodata);
diff --git a/src/link.c b/src/link.c
index ae2cd1992..0b7002124 100644
--- a/src/link.c
+++ b/src/link.c
@@ -1,6 +1,11 @@
// Includes
#include "global.h"
+#include "librfu.h"
+#include "gpu_regs.h"
+#include "palette.h"
+#include "task.h"
+#include "link.h"
// Static type declarations
@@ -31,17 +36,17 @@ IWRAM_DATA u32 gUnknown_03000D54;
IWRAM_DATA u8 gUnknown_03000D58;
IWRAM_DATA u32 gUnknown_03000D5C;
IWRAM_DATA u32 gUnknown_03000D60;
-IWRAM_DATA u8 gUnknown_03000D64[4]; // not really, but won't match otherwise
-IWRAM_DATA u8 gUnknown_03000D68[4];
+IWRAM_DATA u8 gUnknown_03000D64;
+ALIGNED() IWRAM_DATA u8 gUnknown_03000D68[4];
IWRAM_DATA u8 gUnknown_03000D6C;
IWRAM_DATA bool8 gUnknown_03000D6D;
IWRAM_DATA u16 gUnknown_03000D6E;
IWRAM_DATA u16 gUnknown_03000D70;
IWRAM_DATA u8 gUnknown_03000D72;
IWRAM_DATA u8 gUnknown_03000D73;
-IWRAM_DATA u8 gUnknown_03000D74[4]; // not really, but won't match otherwise
-IWRAM_DATA u8 gUnknown_03000D78[8]; // not really, but won't match otherwise
-IWRAM_DATA u8 gUnknown_03000D80[16];
+IWRAM_DATA u8 gUnknown_03000D74;
+ALIGNED() IWRAM_DATA u8 gUnknown_03000D78;
+ALIGNED(8) IWRAM_DATA u8 gUnknown_03000D80[16];
IWRAM_DATA u16 gUnknown_03000D90[8];
IWRAM_DATA u32 gUnknown_03000DA0;
IWRAM_DATA u32 gUnknown_03000DA4;
@@ -51,6 +56,60 @@ IWRAM_DATA bool32 gUnknown_03000DB0;
// Static ROM declarations
+void sub_800E700(void);
+u32 sub_800BEC0(void);
+void sub_800B4A4(void);
+
// .rodata
+ALIGNED(4) const u16 gWirelessLinkDisplayPal[] = INCBIN_U16("graphics/interface/wireless_link_display.gbapal");
+const u8 gWirelessLinkDisplayGfx[] = INCBIN_U8("graphics/interface/wireless_link_display.4bpp.lz");
+const u8 gWirelessLinkDisplayTilemap[] = INCBIN_U8("graphics/interface/wireless_link_display.bin.lz");
+const u16 gLinkTestDigitsPal[] = INCBIN_U16("graphics/interface/link_test_digits.gbapal");
+const u16 gLinkTestDigitsGfx[] = INCBIN_U16("graphics/interface/link_test_digits.4bpp");
+
// .text
+
+bool8 sub_80093CC(void)
+{
+ sub_800B488();
+ sub_800E700();
+ if (sub_800BEC0() == 0x8001)
+ {
+ rfu_REQ_stopMode();
+ rfu_waitREQComplete();
+ return TRUE;
+ }
+ sub_800B4A4();
+ sub_80097E8();
+ RestoreSerialTimer3IntrHandlers();
+ return FALSE;
+}
+
+void sub_8009404(u8 taskId)
+{
+ DestroyTask(taskId);
+}
+
+void sub_8009414(u8 a0, u8 a1, u8 a2, u8 a3, u16 a4)
+{
+ LoadPalette(gLinkTestDigitsPal, a0 * 16, 0x20);
+ DmaCopy16(3, gLinkTestDigitsGfx, (u16 *)BG_CHAR_ADDR(a3) + (16 * a4), sizeof gLinkTestDigitsGfx);
+ gUnknown_03003130[0] = a2;
+ gUnknown_03003130[1] = a0;
+ gUnknown_03003130[2] = a4;
+ switch (a1)
+ {
+ case 1:
+ SetGpuReg(REG_OFFSET_BG1CNT, BGCNT_SCREENBASE(a2) | BGCNT_PRIORITY(1) | BGCNT_CHARBASE(a3));
+ break;
+ case 2:
+ SetGpuReg(REG_OFFSET_BG2CNT, BGCNT_SCREENBASE(a2) | BGCNT_PRIORITY(1) | BGCNT_CHARBASE(a3));
+ break;
+ case 3:
+ SetGpuReg(REG_OFFSET_BG3CNT, BGCNT_SCREENBASE(a2) | BGCNT_PRIORITY(1) | BGCNT_CHARBASE(a3));
+ break;
+ }
+ SetGpuReg(REG_OFFSET_BG0HOFS + a1 * 4, 0);
+ SetGpuReg(REG_OFFSET_BG0VOFS + a1 * 4, 0);
+}