summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDiegoisawesome <diego@domoreaweso.me>2017-09-09 19:46:19 -0500
committerDiegoisawesome <diego@domoreaweso.me>2017-09-09 19:46:19 -0500
commit001d1027e38059654480707e90927ce0245faf29 (patch)
tree3a529f91bb25d98a00bec298e4b7f4c52c2cce6a
parent6c6ebd9268e3905e5df719e6abfa00261c517fa3 (diff)
Finish bg.s, 6 nonmatching
-rw-r--r--asm/bg.s944
-rw-r--r--include/gba/defines.h5
-rw-r--r--ld_script.txt1
-rw-r--r--src/bg.c599
4 files changed, 584 insertions, 965 deletions
diff --git a/asm/bg.s b/asm/bg.s
deleted file mode 100644
index 4e5ca7c18..000000000
--- a/asm/bg.s
+++ /dev/null
@@ -1,944 +0,0 @@
- .include "asm/macros.inc"
- .include "constants/constants.inc"
-
- .syntax unified
-
- .text
-
- thumb_func_start CopyRectToBgTilemapBufferRect
-@ void CopyRectToBgTilemapBufferRect(u8 bg, void *src, u8 srcX, u8 srcY, u8 srcWidth, u8 srcHeight, u8 destX, u8 destY, u8 rectWidth, u8 rectHeight, u8 palette1, u16 tileOffset, u16 palette2)
-CopyRectToBgTilemapBufferRect: @ 800251C
- push {r4-r7,lr}
- mov r7, r10
- mov r6, r9
- mov r5, r8
- push {r5-r7}
- sub sp, 0x40
- str r1, [sp, 0x8]
- ldr r1, [sp, 0x60]
- ldr r4, [sp, 0x68]
- ldr r5, [sp, 0x6C]
- ldr r6, [sp, 0x70]
- ldr r7, [sp, 0x74]
- mov r8, r7
- ldr r7, [sp, 0x78]
- mov r9, r7
- ldr r7, [sp, 0x7C]
- mov r10, r7
- ldr r7, [sp, 0x80]
- mov r12, r7
- lsls r0, 24
- lsrs r0, 24
- str r0, [sp, 0x4]
- lsls r2, 24
- lsrs r2, 24
- str r2, [sp, 0xC]
- lsls r3, 24
- lsrs r3, 24
- str r3, [sp, 0x10]
- lsls r1, 24
- lsrs r7, r1, 24
- lsls r4, 24
- lsrs r4, 24
- str r4, [sp, 0x14]
- lsls r5, 24
- lsrs r5, 24
- lsls r6, 24
- lsrs r6, 24
- str r6, [sp, 0x18]
- mov r0, r8
- lsls r0, 24
- lsrs r4, r0, 24
- mov r1, r9
- lsls r1, 24
- lsrs r1, 24
- str r1, [sp, 0x1C]
- mov r2, r10
- lsls r2, 16
- lsrs r2, 16
- str r2, [sp, 0x20]
- mov r0, r12
- lsls r0, 16
- lsrs r0, 16
- str r0, [sp, 0x24]
- ldr r0, [sp, 0x4]
- bl IsInvalidBgDuplicate
- cmp r0, 0
- beq _08002592
- b _080026EE
-_08002592:
- ldr r0, [sp, 0x4]
- bl IsTileMapOutsideWram
- cmp r0, 0
- beq _0800259E
- b _080026EE
-_0800259E:
- ldr r0, [sp, 0x4]
- movs r1, 0x4
- bl GetBgControlAttribute
- lsls r0, 16
- lsrs r0, 16
- str r0, [sp, 0x30]
- ldr r0, [sp, 0x4]
- movs r1, 0x1
- bl GetBgMetricTextMode
- lsls r0, 21
- lsrs r0, 16
- str r0, [sp, 0x28]
- ldr r0, [sp, 0x4]
- movs r1, 0x2
- bl GetBgMetricTextMode
- lsls r0, 21
- lsrs r0, 16
- str r0, [sp, 0x2C]
- ldr r0, [sp, 0x4]
- bl GetBgType
- cmp r0, 0
- beq _080025D8
- cmp r0, 0x1
- beq _08002674
- b _080026EE
-_080025D8:
- ldr r1, [sp, 0x10]
- adds r0, r1, 0
- muls r0, r7
- ldr r2, [sp, 0xC]
- adds r0, r2
- lsls r0, 1
- ldr r1, [sp, 0x8]
- adds r6, r1, r0
- adds r0, r5, r4
- cmp r5, r0
- blt _080025F0
- b _080026EE
-_080025F0:
- ldr r2, [sp, 0x18]
- subs r2, r7, r2
- str r2, [sp, 0x34]
- str r0, [sp, 0x38]
-_080025F8:
- ldr r4, [sp, 0x14]
- ldr r7, [sp, 0x18]
- adds r0, r4, r7
- adds r1, r5, 0x1
- str r1, [sp, 0x3C]
- cmp r4, r0
- bge _0800265A
- ldr r2, [sp, 0x4]
- lsls r0, r2, 4
- ldr r1, =gUnknown_030008FC
- adds r0, r1
- mov r10, r0
- ldr r7, [sp, 0x20]
- lsls r7, 16
- mov r9, r7
- ldr r1, [sp, 0x24]
- lsls r0, r1, 16
- asrs r0, 16
- mov r8, r0
-_0800261E:
- ldr r2, [sp, 0x2C]
- str r2, [sp]
- adds r0, r4, 0
- adds r1, r5, 0
- ldr r2, [sp, 0x30]
- ldr r3, [sp, 0x28]
- bl GetTileMapIndexFromCoords
- lsls r0, 16
- lsrs r0, 15
- mov r7, r10
- ldr r1, [r7]
- adds r1, r0
- mov r0, r8
- str r0, [sp]
- adds r0, r6, 0
- ldr r2, [sp, 0x1C]
- mov r7, r9
- asrs r3, r7, 16
- bl CopyTileMapEntry
- adds r6, 0x2
- adds r0, r4, 0x1
- lsls r0, 16
- lsrs r4, r0, 16
- ldr r1, [sp, 0x14]
- ldr r2, [sp, 0x18]
- adds r0, r1, r2
- cmp r4, r0
- blt _0800261E
-_0800265A:
- ldr r5, [sp, 0x34]
- lsls r0, r5, 1
- adds r6, r0
- ldr r7, [sp, 0x3C]
- lsls r0, r7, 16
- lsrs r5, r0, 16
- ldr r0, [sp, 0x38]
- cmp r5, r0
- blt _080025F8
- b _080026EE
- .pool
-_08002674:
- ldr r1, [sp, 0x10]
- adds r0, r1, 0
- muls r0, r7
- ldr r2, [sp, 0xC]
- adds r0, r2
- ldr r1, [sp, 0x8]
- adds r6, r1, r0
- ldr r0, [sp, 0x4]
- movs r1, 0x1
- bl GetBgMetricAffineMode
- lsls r0, 16
- lsrs r0, 16
- mov r9, r0
- adds r0, r5, r4
- cmp r5, r0
- bge _080026EE
- ldr r2, [sp, 0x18]
- subs r2, r7, r2
- str r2, [sp, 0x34]
- str r0, [sp, 0x38]
- ldr r7, =gUnknown_030008FC
- mov r10, r7
- ldr r0, [sp, 0x4]
- lsls r0, 4
- mov r8, r0
-_080026A8:
- ldr r4, [sp, 0x14]
- ldr r1, [sp, 0x18]
- adds r0, r4, r1
- adds r2, r5, 0x1
- str r2, [sp, 0x3C]
- cmp r4, r0
- bge _080026DE
- mov r3, r8
- add r3, r10
- mov r7, r9
- muls r7, r5
- mov r12, r7
- adds r2, r0, 0
-_080026C2:
- ldr r1, [r3]
- mov r5, r12
- adds r0, r5, r4
- adds r1, r0
- ldrb r0, [r6]
- ldr r7, [sp, 0x20]
- adds r0, r7
- strb r0, [r1]
- adds r6, 0x1
- adds r0, r4, 0x1
- lsls r0, 16
- lsrs r4, r0, 16
- cmp r4, r2
- blt _080026C2
-_080026DE:
- ldr r0, [sp, 0x34]
- adds r6, r0
- ldr r1, [sp, 0x3C]
- lsls r0, r1, 16
- lsrs r5, r0, 16
- ldr r2, [sp, 0x38]
- cmp r5, r2
- blt _080026A8
-_080026EE:
- add sp, 0x40
- pop {r3-r5}
- mov r8, r3
- mov r9, r4
- mov r10, r5
- pop {r4-r7}
- pop {r0}
- bx r0
- .pool
- thumb_func_end CopyRectToBgTilemapBufferRect
-
- thumb_func_start FillBgTilemapBufferRect_Palette0
-@ void FillBgTilemapBufferRect_Palette0(u8 bg, u16 tileNum, u8 x, u8 y, u8 width, u8 height)
-FillBgTilemapBufferRect_Palette0: @ 8002704
- push {r4-r7,lr}
- mov r7, r10
- mov r6, r9
- mov r5, r8
- push {r5-r7}
- sub sp, 0x4
- ldr r4, [sp, 0x24]
- ldr r5, [sp, 0x28]
- lsls r0, 24
- lsrs r6, r0, 24
- lsls r1, 16
- lsrs r1, 16
- mov r8, r1
- lsls r2, 24
- lsrs r2, 24
- mov r10, r2
- lsls r3, 24
- lsrs r7, r3, 24
- lsls r4, 24
- lsrs r4, 24
- mov r9, r4
- lsls r5, 24
- lsrs r5, 24
- adds r0, r6, 0
- bl IsInvalidBgDuplicate
- cmp r0, 0
- bne _080027F0
- adds r0, r6, 0
- bl IsTileMapOutsideWram
- cmp r0, 0
- bne _080027F0
- adds r0, r6, 0
- bl GetBgType
- cmp r0, 0
- beq _08002756
- cmp r0, 0x1
- beq _080027A0
- b _080027F0
-_08002756:
- adds r3, r7, 0
- adds r5, r3, r5
- cmp r3, r5
- bge _080027F0
- adds r7, r5, 0
- lsls r1, r6, 4
- ldr r0, =gUnknown_030008FC
- adds r1, r0
- mov r12, r1
-_08002768:
- mov r2, r10
- mov r1, r9
- adds r0, r2, r1
- adds r6, r3, 0x1
- cmp r2, r0
- bge _08002790
- mov r5, r12
- ldr r4, [r5]
- lsls r3, 5
- adds r1, r0, 0
-_0800277C:
- adds r0, r3, r2
- lsls r0, 1
- adds r0, r4
- mov r5, r8
- strh r5, [r0]
- adds r0, r2, 0x1
- lsls r0, 16
- lsrs r2, r0, 16
- cmp r2, r1
- blt _0800277C
-_08002790:
- lsls r0, r6, 16
- lsrs r3, r0, 16
- cmp r3, r7
- blt _08002768
- b _080027F0
- .pool
-_080027A0:
- adds r0, r6, 0
- movs r1, 0x1
- bl GetBgMetricAffineMode
- lsls r0, 16
- lsrs r0, 16
- str r0, [sp]
- adds r3, r7, 0
- adds r5, r3, r5
- cmp r3, r5
- bge _080027F0
- adds r7, r5, 0
- lsls r6, 4
- mov r12, r6
-_080027BC:
- mov r2, r10
- mov r1, r9
- adds r0, r2, r1
- adds r6, r3, 0x1
- cmp r2, r0
- bge _080027E8
- ldr r5, =gUnknown_030008FC
- add r5, r12
- ldr r1, [sp]
- adds r4, r3, 0
- muls r4, r1
- adds r3, r0, 0
-_080027D4:
- ldr r0, [r5]
- adds r1, r4, r2
- adds r0, r1
- mov r1, r8
- strb r1, [r0]
- adds r0, r2, 0x1
- lsls r0, 16
- lsrs r2, r0, 16
- cmp r2, r3
- blt _080027D4
-_080027E8:
- lsls r0, r6, 16
- lsrs r3, r0, 16
- cmp r3, r7
- blt _080027BC
-_080027F0:
- add sp, 0x4
- pop {r3-r5}
- mov r8, r3
- mov r9, r4
- mov r10, r5
- pop {r4-r7}
- pop {r0}
- bx r0
- .pool
- thumb_func_end FillBgTilemapBufferRect_Palette0
-
- thumb_func_start FillBgTilemapBufferRect
-@ void FillBgTilemapBufferRect(u8 bg, u16 tileNum, u8 x, u8 y, u8 width, u8 height, u8 palette)
-FillBgTilemapBufferRect: @ 8002804
- push {r4-r6,lr}
- sub sp, 0x10
- ldr r4, [sp, 0x20]
- ldr r5, [sp, 0x24]
- ldr r6, [sp, 0x28]
- lsls r0, 24
- lsrs r0, 24
- lsls r1, 16
- lsrs r1, 16
- lsls r2, 24
- lsrs r2, 24
- lsls r3, 24
- lsrs r3, 24
- lsls r4, 24
- lsrs r4, 24
- lsls r5, 24
- lsrs r5, 24
- lsls r6, 24
- lsrs r6, 24
- str r4, [sp]
- str r5, [sp, 0x4]
- str r6, [sp, 0x8]
- movs r4, 0
- str r4, [sp, 0xC]
- bl WriteSequenceToBgTilemapBuffer
- add sp, 0x10
- pop {r4-r6}
- pop {r0}
- bx r0
- thumb_func_end FillBgTilemapBufferRect
-
- thumb_func_start WriteSequenceToBgTilemapBuffer
-@ void WriteSequenceToBgTilemapBuffer(u8 bg, u16 firstTileNum, u8 x, u8 y, u8 width, u8 height, u8 paletteSlot, u16 tileNumDelta)
-WriteSequenceToBgTilemapBuffer: @ 8002840
- push {r4-r7,lr}
- mov r7, r10
- mov r6, r9
- mov r5, r8
- push {r5-r7}
- sub sp, 0x2C
- ldr r4, [sp, 0x4C]
- ldr r5, [sp, 0x50]
- ldr r6, [sp, 0x54]
- ldr r7, [sp, 0x58]
- mov r8, r7
- lsls r0, 24
- lsrs r0, 24
- mov r9, r0
- add r0, sp, 0x4
- strh r1, [r0]
- lsls r2, 24
- lsrs r2, 24
- str r2, [sp, 0x8]
- lsls r3, 24
- lsrs r7, r3, 24
- lsls r4, 24
- lsrs r4, 24
- mov r10, r4
- lsls r5, 24
- lsrs r4, r5, 24
- lsls r6, 24
- lsrs r6, 24
- str r6, [sp, 0xC]
- mov r0, r8
- lsls r0, 16
- lsrs r0, 16
- str r0, [sp, 0x10]
- mov r0, r9
- bl IsInvalidBgDuplicate
- cmp r0, 0
- beq _0800288E
- b _080029D4
-_0800288E:
- mov r0, r9
- bl IsTileMapOutsideWram
- cmp r0, 0
- beq _0800289A
- b _080029D4
-_0800289A:
- mov r0, r9
- movs r1, 0x4
- bl GetBgControlAttribute
- lsls r0, 16
- lsrs r0, 16
- str r0, [sp, 0x1C]
- mov r0, r9
- movs r1, 0x1
- bl GetBgMetricTextMode
- lsls r0, 21
- lsrs r0, 16
- str r0, [sp, 0x14]
- mov r0, r9
- movs r1, 0x2
- bl GetBgMetricTextMode
- lsls r0, 21
- lsrs r0, 16
- str r0, [sp, 0x18]
- mov r0, r9
- bl GetBgType
- cmp r0, 0
- beq _080028D4
- cmp r0, 0x1
- beq _0800295C
- b _080029D4
-_080028D4:
- adds r5, r7, 0
- adds r0, r5, r4
- cmp r5, r0
- bge _080029D4
- str r0, [sp, 0x24]
- add r7, sp, 0x4
-_080028E0:
- ldr r4, [sp, 0x8]
- mov r1, r10
- adds r0, r4, r1
- adds r2, r5, 0x1
- mov r8, r2
- cmp r4, r0
- bge _08002944
- mov r3, r9
- lsls r1, r3, 4
- ldr r0, =gUnknown_030008FC
- adds r6, r1, r0
-_080028F6:
- ldr r0, [sp, 0x18]
- str r0, [sp]
- adds r0, r4, 0
- adds r1, r5, 0
- ldr r2, [sp, 0x1C]
- ldr r3, [sp, 0x14]
- bl GetTileMapIndexFromCoords
- lsls r0, 16
- lsrs r0, 15
- ldr r1, [r6]
- adds r1, r0
- movs r0, 0
- str r0, [sp]
- add r0, sp, 0x4
- ldr r2, [sp, 0xC]
- movs r3, 0
- bl CopyTileMapEntry
- ldrh r0, [r7]
- movs r2, 0xFC
- lsls r2, 8
- adds r1, r2, 0
- adds r2, r0, 0
- ands r2, r1
- ldr r3, [sp, 0x10]
- adds r0, r3
- ldr r3, =0x000003ff
- adds r1, r3, 0
- ands r0, r1
- adds r2, r0
- strh r2, [r7]
- adds r0, r4, 0x1
- lsls r0, 16
- lsrs r4, r0, 16
- ldr r0, [sp, 0x8]
- add r0, r10
- cmp r4, r0
- blt _080028F6
-_08002944:
- mov r1, r8
- lsls r0, r1, 16
- lsrs r5, r0, 16
- ldr r2, [sp, 0x24]
- cmp r5, r2
- blt _080028E0
- b _080029D4
- .pool
-_0800295C:
- mov r0, r9
- movs r1, 0x1
- bl GetBgMetricAffineMode
- lsls r0, 16
- lsrs r0, 16
- str r0, [sp, 0x20]
- adds r5, r7, 0
- adds r0, r5, r4
- cmp r5, r0
- bge _080029D4
- str r0, [sp, 0x24]
- mov r3, r9
- lsls r3, 4
- mov r12, r3
-_0800297A:
- ldr r4, [sp, 0x8]
- mov r7, r10
- adds r0, r4, r7
- adds r1, r5, 0x1
- mov r8, r1
- cmp r4, r0
- bge _080029C8
- ldr r2, =gUnknown_030008FC
- add r2, r12
- str r2, [sp, 0x28]
- ldr r7, [sp, 0x20]
- adds r3, r5, 0
- muls r3, r7
- add r2, sp, 0x4
- movs r1, 0xFC
- lsls r1, 8
- mov r9, r1
- ldr r7, =0x000003ff
- adds r5, r7, 0
- adds r6, r0, 0
-_080029A2:
- ldr r0, [sp, 0x28]
- ldr r1, [r0]
- adds r0, r3, r4
- adds r1, r0
- ldrh r0, [r2]
- strb r0, [r1]
- ldrh r0, [r2]
- mov r1, r9
- ands r1, r0
- ldr r7, [sp, 0x10]
- adds r0, r7
- ands r0, r5
- adds r1, r0
- strh r1, [r2]
- adds r0, r4, 0x1
- lsls r0, 16
- lsrs r4, r0, 16
- cmp r4, r6
- blt _080029A2
-_080029C8:
- mov r1, r8
- lsls r0, r1, 16
- lsrs r5, r0, 16
- ldr r2, [sp, 0x24]
- cmp r5, r2
- blt _0800297A
-_080029D4:
- add sp, 0x2C
- pop {r3-r5}
- mov r8, r3
- mov r9, r4
- mov r10, r5
- pop {r4-r7}
- pop {r0}
- bx r0
- .pool
- thumb_func_end WriteSequenceToBgTilemapBuffer
-
- thumb_func_start GetBgMetricTextMode
-@ u16 GetBgMetricTextMode(u8 bg, u8 whichMetric)
-GetBgMetricTextMode: @ 80029EC
- push {r4,r5,lr}
- lsls r0, 24
- lsrs r0, 24
- lsls r1, 24
- lsrs r4, r1, 24
- adds r5, r4, 0
- movs r1, 0x4
- bl GetBgControlAttribute
- lsls r0, 24
- lsrs r0, 24
- cmp r4, 0x1
- beq _08002A2C
- cmp r4, 0x1
- bgt _08002A10
- cmp r4, 0
- beq _08002A16
- b _08002A52
-_08002A10:
- cmp r5, 0x2
- beq _08002A3E
- b _08002A52
-_08002A16:
- cmp r0, 0x2
- bgt _08002A24
- cmp r0, 0x1
- bge _08002A4E
-_08002A1E:
- cmp r0, 0
- beq _08002A46
- b _08002A52
-_08002A24:
- cmp r0, 0x3
- bne _08002A52
- movs r0, 0x4
- b _08002A54
-_08002A2C:
- cmp r0, 0x1
- beq _08002A4E
- cmp r0, 0x1
- ble _08002A1E
- cmp r0, 0x2
- beq _08002A46
- cmp r0, 0x3
- bne _08002A52
- b _08002A4E
-_08002A3E:
- cmp r0, 0
- blt _08002A52
- cmp r0, 0x1
- bgt _08002A4A
-_08002A46:
- movs r0, 0x1
- b _08002A54
-_08002A4A:
- cmp r0, 0x3
- bgt _08002A52
-_08002A4E:
- movs r0, 0x2
- b _08002A54
-_08002A52:
- movs r0, 0
-_08002A54:
- pop {r4,r5}
- pop {r1}
- bx r1
- thumb_func_end GetBgMetricTextMode
-
- thumb_func_start GetBgMetricAffineMode
-@ u16 GetBgMetricAffineMode(u8 bg, u8 whichMetric)
-GetBgMetricAffineMode: @ 8002A5C
- push {r4,lr}
- lsls r0, 24
- lsrs r0, 24
- lsls r1, 24
- lsrs r4, r1, 24
- movs r1, 0x4
- bl GetBgControlAttribute
- lsls r0, 24
- lsrs r1, r0, 24
- adds r0, r1, 0
- cmp r4, 0
- beq _08002A84
- cmp r4, 0
- blt _08002AAC
- cmp r4, 0x2
- bgt _08002AAC
- movs r0, 0x10
- lsls r0, r1
- b _08002AAE
-_08002A84:
- cmp r1, 0x1
- beq _08002AA0
- cmp r1, 0x1
- bgt _08002A92
- cmp r1, 0
- beq _08002A9C
- b _08002AAC
-_08002A92:
- cmp r0, 0x2
- beq _08002AA4
- cmp r0, 0x3
- beq _08002AA8
- b _08002AAC
-_08002A9C:
- movs r0, 0x1
- b _08002AAE
-_08002AA0:
- movs r0, 0x4
- b _08002AAE
-_08002AA4:
- movs r0, 0x10
- b _08002AAE
-_08002AA8:
- movs r0, 0x40
- b _08002AAE
-_08002AAC:
- movs r0, 0
-_08002AAE:
- pop {r4}
- pop {r1}
- bx r1
- thumb_func_end GetBgMetricAffineMode
-
- thumb_func_start GetTileMapIndexFromCoords
-@ u32 GetTileMapIndexFromCoords(u32 x, u32 y, u32 screenSize, u32 screenWidth, u32 screenHeight)
-GetTileMapIndexFromCoords: @ 8002AB4
- push {r4,lr}
- adds r4, r0, 0
- ldr r0, [sp, 0x8]
- subs r3, 0x1
- ands r4, r3
- subs r0, 0x1
- ands r1, r0
- cmp r2, 0x1
- beq _08002AD8
- cmp r2, 0x1
- ble _08002AE0
- cmp r2, 0x2
- beq _08002AE0
- cmp r2, 0x3
- bne _08002AE0
- cmp r1, 0x1F
- ble _08002AD8
- adds r1, 0x20
-_08002AD8:
- cmp r4, 0x1F
- ble _08002AE0
- subs r4, 0x20
- adds r1, 0x20
-_08002AE0:
- lsls r0, r1, 5
- adds r0, r4
- pop {r4}
- pop {r1}
- bx r1
- thumb_func_end GetTileMapIndexFromCoords
-
- thumb_func_start CopyTileMapEntry
-@ void CopyTileMapEntry(u16 *src, u16 *dest, s32 palette1, u16 tileOffset, u32 palette2)
-CopyTileMapEntry: @ 8002AEC
- push {r4-r6,lr}
- adds r4, r0, 0
- adds r6, r1, 0
- ldr r5, [sp, 0x10]
- cmp r2, 0x10
- beq _08002B14
- cmp r2, 0x10
- bgt _08002B34
- cmp r2, 0
- blt _08002B34
- ldrh r0, [r4]
- adds r0, r3
- ldr r3, =0x00000fff
- adds r1, r3, 0
- ands r0, r1
- adds r1, r2, r5
- lsls r1, 12
- b _08002B3A
- .pool
-_08002B14:
- ldrh r1, [r6]
- movs r0, 0xFC
- lsls r0, 8
- ands r1, r0
- lsls r2, r5, 12
- adds r2, r1, r2
- ldrh r0, [r4]
- adds r0, r3
- ldr r3, =0x000003ff
- adds r1, r3, 0
- ands r0, r1
- orrs r0, r2
- b _08002B3C
- .pool
-_08002B34:
- ldrh r0, [r4]
- adds r0, r3
- lsls r1, r5, 12
-_08002B3A:
- adds r0, r1
-_08002B3C:
- lsls r0, 16
- lsrs r1, r0, 16
- strh r1, [r6]
- pop {r4-r6}
- pop {r0}
- bx r0
- thumb_func_end CopyTileMapEntry
-
- thumb_func_start GetBgType
-@ u16 GetBgType(u8 bg)
-GetBgType: @ 8002B48
- push {r4,r5,lr}
- lsls r0, 24
- lsrs r4, r0, 24
- adds r5, r4, 0
- bl GetBgMode
- lsls r0, 24
- lsrs r0, 24
- cmp r4, 0x2
- beq _08002B76
- cmp r4, 0x2
- ble _08002B66
- cmp r4, 0x3
- beq _08002B86
- b _08002B8E
-_08002B66:
- cmp r5, 0
- blt _08002B8E
- cmp r0, 0x1
- bgt _08002B8E
- cmp r0, 0
- blt _08002B8E
-_08002B72:
- movs r0, 0
- b _08002B90
-_08002B76:
- cmp r0, 0
- beq _08002B72
- cmp r0, 0
- blt _08002B8E
- cmp r0, 0x2
- bgt _08002B8E
-_08002B82:
- movs r0, 0x1
- b _08002B90
-_08002B86:
- cmp r0, 0
- beq _08002B72
- cmp r0, 0x2
- beq _08002B82
-_08002B8E:
- ldr r0, =0x0000ffff
-_08002B90:
- pop {r4,r5}
- pop {r1}
- bx r1
- .pool
- thumb_func_end GetBgType
-
- thumb_func_start IsInvalidBgDuplicate
-@ bool8 IsInvalidBgDuplicate(u8 bg)
-IsInvalidBgDuplicate: @ 8002B9C
- push {lr}
- lsls r0, 24
- lsrs r0, 24
- cmp r0, 0x3
- bhi _08002BAA
- movs r0, 0
- b _08002BAC
-_08002BAA:
- movs r0, 0x1
-_08002BAC:
- pop {r1}
- bx r1
- thumb_func_end IsInvalidBgDuplicate
-
- thumb_func_start IsTileMapOutsideWram
-@ bool8 IsTileMapOutsideWram(u8 bg)
-IsTileMapOutsideWram: @ 8002BB0
- push {lr}
- lsls r0, 24
- ldr r1, =gUnknown_030008F8
- lsrs r0, 20
- adds r1, 0x4
- adds r0, r1
- ldr r1, [r0]
- ldr r0, =0x03008000
- cmp r1, r0
- bhi _08002BD4
- cmp r1, 0
- beq _08002BD4
- movs r0, 0
- b _08002BD6
- .pool
-_08002BD4:
- movs r0, 0x1
-_08002BD6:
- pop {r1}
- bx r1
- thumb_func_end IsTileMapOutsideWram
-
- .align 2, 0 @ Don't pad with nop.
diff --git a/include/gba/defines.h b/include/gba/defines.h
index 0f7f06755..66e5efcd1 100644
--- a/include/gba/defines.h
+++ b/include/gba/defines.h
@@ -15,6 +15,11 @@
#define INTR_CHECK (*(u16 *)0x3007FF8)
#define INTR_VECTOR (*(void **)0x3007FFC)
+#define EWRAM_START 0x02000000
+#define EWRAM_END (EWRAM_START + 0x40000)
+#define IWRAM_START 0x03000000
+#define IWRAM_END (IWRAM_START + 0x8000)
+
#define PLTT 0x5000000
#define PLTT_SIZE 0x400
diff --git a/ld_script.txt b/ld_script.txt
index 6668cf5d6..6cb2814fa 100644
--- a/ld_script.txt
+++ b/ld_script.txt
@@ -43,7 +43,6 @@ SECTIONS {
src/dma3_manager.o(.text);
src/gpu_regs.o(.text);
src/bg.o(.text);
- asm/bg.o(.text);
asm/blit.o(.text);
src/window.o(.text);
src/text.o(.text);
diff --git a/src/bg.c b/src/bg.c
index 430c9599e..e4083fbcf 100644
--- a/src/bg.c
+++ b/src/bg.c
@@ -50,18 +50,19 @@ extern struct BgConfig2 gUnknown_030008F8[4]; // gGpuBgConfigs2
extern u32 gUnknown_03000938[4];
extern u32 gUnneededFireRedVariable;
extern struct BgConfig gZeroedBgControlStruct;
-extern bool32 IsInvalidBgDuplicate(u8 bg);
+extern bool32 IsInvalidBg32(u8 bg);
void ResetBgControlStructs();
u16 GetBgMetricTextMode(u8 bg, u8 whichMetric);
-u16 GetBgMetricAffineMode(u8 bg, u8 whichMetric);
+u32 GetBgMetricAffineMode(u8 bg, u8 whichMetric);
u32 GetBgType(u8 bg);
void SetTextModeAndHideBgs();
bool8 IsInvalidBg(u8 bg);
bool32 IsTileMapOutsideWram(u8 bg);
void CopyRectToBgTilemapBufferRect(u8 bg, void *src, u8 srcX, u8 srcY, u8 srcWidth, u8 srcHeight, u8 destX, u8 destY, u8 rectWidth, u8 rectHeight, u8 palette1, u16 tileOffset, u16 palette2);
-void CopyTileMapEntry(u16 *src, u16 *dest, s32 palette1, u16 tileOffset, u32 palette2);
-u32 GetTileMapIndexFromCoords(u32 x, u32 y, u32 screenSize, u32 screenWidth, u32 screenHeight);
+void CopyTileMapEntry(u16 *src, u16 *dest, s32 palette1, u32 tileOffset, u32 palette2);
+u32 GetTileMapIndexFromCoords(s32 x, s32 y, s32 screenSize, u32 screenWidth, u32 screenHeight);
+void WriteSequenceToBgTilemapBuffer(u8 bg, u16 firstTileNum, u8 x, u8 y, u8 width, u8 height, u8 paletteSlot, s16 tileNumDelta);
extern void SetGpuReg(u8 regOffset, u16 value);
extern void SetGpuReg_ForcedBlank(u8 regOffset, u16 value);
@@ -437,7 +438,7 @@ u16 Unused_LoadBgPalette(u8 bg, void *src, u16 size, u16 destOffset)
u16 unk_1;
s8 cursor;
- if (IsInvalidBgDuplicate(bg) == FALSE)
+ if (IsInvalidBg32(bg) == FALSE)
{
unk_1 = (gUnknown_030008F8[bg].unk_2 * 0x20) + (destOffset * 2);
cursor = RequestDma3Copy(src, (void*)(unk_1 + BG_PLTT), size, 0);
@@ -623,7 +624,7 @@ u32 ChangeBgX(u8 bg, u32 value, u8 op)
u8 mode;
u32 temp1;
- if (IsInvalidBgDuplicate(bg) != FALSE || GetBgControlAttribute(bg, 1) == 0)
+ if (IsInvalidBg32(bg) != FALSE || GetBgControlAttribute(bg, 1) == 0)
{
return -1;
}
@@ -691,7 +692,7 @@ u32 ChangeBgX(u8 bg, u32 value, u8 op)
lsl r2, #24\n\
lsr r5, r2, #24\n\
add r0, r4, #0\n\
- bl IsInvalidBgDuplicate\n\
+ bl IsInvalidBg32\n\
cmp r0, #0\n\
bne _08001D28\n\
add r0, r4, #0\n\
@@ -838,7 +839,7 @@ _08001E34:\n\
u32 GetBgX(u8 bg)
{
- if (IsInvalidBgDuplicate(bg) != FALSE)
+ if (IsInvalidBg32(bg) != FALSE)
return -1;
if (GetBgControlAttribute(bg, 0x1) == 0)
return -1;
@@ -851,7 +852,7 @@ u32 ChangeBgY(u8 bg, u32 value, u8 op)
u8 mode;
u32 temp1;
- if (IsInvalidBgDuplicate(bg) != FALSE || GetBgControlAttribute(bg, 1) == 0)
+ if (IsInvalidBg32(bg) != FALSE || GetBgControlAttribute(bg, 1) == 0)
{
return -1;
}
@@ -921,7 +922,7 @@ u32 ChangeBgY(u8 bg, u32 value, u8 op)
lsl r2, #24\n\
lsr r5, r2, #24\n\
add r0, r4, #0\n\
- bl IsInvalidBgDuplicate\n\
+ bl IsInvalidBg32\n\
cmp r0, #0\n\
bne _08001EA0\n\
add r0, r4, #0\n\
@@ -1072,7 +1073,7 @@ u32 ChangeBgY_ScreenOff(u8 bg, u32 value, u8 op)
u8 mode;
u16 temp1;
- if (IsInvalidBgDuplicate(bg) != FALSE || GetBgControlAttribute(bg, 1) == 0)
+ if (IsInvalidBg32(bg) != FALSE || GetBgControlAttribute(bg, 1) == 0)
{
return -1;
}
@@ -1143,7 +1144,7 @@ u32 ChangeBgY_ScreenOff(u8 bg, u32 value, u8 op)
lsl r2, #24\n\
lsr r5, r2, #24\n\
add r0, r4, #0\n\
- bl IsInvalidBgDuplicate\n\
+ bl IsInvalidBg32\n\
cmp r0, #0\n\
bne _08001FDC\n\
add r0, r4, #0\n\
@@ -1290,7 +1291,7 @@ _080020E8:\n\
u32 GetBgY(u8 bg)
{
- if (IsInvalidBgDuplicate(bg) != FALSE)
+ if (IsInvalidBg32(bg) != FALSE)
return -1;
if (GetBgControlAttribute(bg, 0x1) == 0)
return -1;
@@ -1379,7 +1380,7 @@ u8 Unused_AdjustBgMosaic(u8 a1, u8 a2)
void SetBgTilemapBuffer(u8 bg, void *tilemap)
{
- if (IsInvalidBgDuplicate(bg) == FALSE && GetBgControlAttribute(bg, 0x1) != 0x0)
+ if (IsInvalidBg32(bg) == FALSE && GetBgControlAttribute(bg, 0x1) != 0x0)
{
gUnknown_030008F8[bg].tilemap = tilemap;
}
@@ -1387,7 +1388,7 @@ void SetBgTilemapBuffer(u8 bg, void *tilemap)
void UnsetBgTilemapBuffer(u8 bg)
{
- if (IsInvalidBgDuplicate(bg) == FALSE && GetBgControlAttribute(bg, 0x1) != 0x0)
+ if (IsInvalidBg32(bg) == FALSE && GetBgControlAttribute(bg, 0x1) != 0x0)
{
gUnknown_030008F8[bg].tilemap = NULL;
}
@@ -1395,7 +1396,7 @@ void UnsetBgTilemapBuffer(u8 bg)
void* GetBgTilemapBuffer(u8 bg)
{
- if (IsInvalidBgDuplicate(bg) != FALSE)
+ if (IsInvalidBg32(bg) != FALSE)
return NULL;
if (GetBgControlAttribute(bg, 0x1) == 0)
return NULL;
@@ -1404,7 +1405,7 @@ void* GetBgTilemapBuffer(u8 bg)
void CopyToBgTilemapBuffer(u8 bg, void *src, u16 mode, u16 destOffset)
{
- if (IsInvalidBgDuplicate(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
+ if (IsInvalidBg32(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
{
if (mode != 0)
{
@@ -1421,7 +1422,7 @@ void CopyBgTilemapBufferToVram(u8 bg)
{
u16 sizeToLoad;
- if (IsInvalidBgDuplicate(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
+ if (IsInvalidBg32(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
{
switch (GetBgType(bg))
{
@@ -1446,7 +1447,7 @@ void CopyToBgTilemapBufferRect(u8 bg, void* src, u8 destX, u8 destY, u8 width, u
u16 destY16;
u16 mode;
- if (IsInvalidBgDuplicate(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
+ if (IsInvalidBg32(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
{
switch (GetBgType(bg))
{
@@ -1479,6 +1480,7 @@ void CopyToBgTilemapBufferRect_ChangePalette(u8 bg, void *src, u8 destX, u8 dest
{
CopyRectToBgTilemapBufferRect(bg, src, 0, 0, rectWidth, rectHeight, destX, destY, rectWidth, rectHeight, palette, 0, 0);
}
+// Skipping for now, it probably uses structs passed by value
/*
void CopyRectToBgTilemapBufferRect(u8 bg, void* src, u8 srcX, u8 srcY, u8 srcWidth, u8 srcHeight, u8 destX, u8 destY, u8 rectWidth, u8 rectHeight, u8 palette1, u16 tileOffset, u16 palette2)
{
@@ -1490,7 +1492,7 @@ void CopyRectToBgTilemapBufferRect(u8 bg, void* src, u8 srcX, u8 srcY, u8 srcWid
u16 destX16;
u16 destY16;
- if (IsInvalidBgDuplicate(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
+ if (IsInvalidBg32(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
{
attribute = GetBgControlAttribute(bg, 0x4);
mode = GetBgMetricTextMode(bg, 0x1) * 0x20;
@@ -1521,3 +1523,560 @@ void CopyRectToBgTilemapBufferRect(u8 bg, void* src, u8 srcX, u8 srcY, u8 srcWid
}
}
}*/
+__attribute__((naked))
+void CopyRectToBgTilemapBufferRect(u8 bg, void* src, u8 srcX, u8 srcY, u8 srcWidth, u8 srcHeight, u8 destX, u8 destY, u8 rectWidth, u8 rectHeight, u8 palette1, u16 tileOffset, u16 palette2)
+{
+ asm("push {r4-r7,lr}\n\
+ mov r7, r10\n\
+ mov r6, r9\n\
+ mov r5, r8\n\
+ push {r5-r7}\n\
+ sub sp, #0x40\n\
+ str r1, [sp, #0x8]\n\
+ ldr r1, [sp, #0x60]\n\
+ ldr r4, [sp, #0x68]\n\
+ ldr r5, [sp, #0x6C]\n\
+ ldr r6, [sp, #0x70]\n\
+ ldr r7, [sp, #0x74]\n\
+ mov r8, r7\n\
+ ldr r7, [sp, #0x78]\n\
+ mov r9, r7\n\
+ ldr r7, [sp, #0x7C]\n\
+ mov r10, r7\n\
+ ldr r7, [sp, #0x80]\n\
+ mov r12, r7\n\
+ lsl r0, #24\n\
+ lsr r0, #24\n\
+ str r0, [sp, #0x4]\n\
+ lsl r2, #24\n\
+ lsr r2, #24\n\
+ str r2, [sp, #0xC]\n\
+ lsl r3, #24\n\
+ lsr r3, #24\n\
+ str r3, [sp, #0x10]\n\
+ lsl r1, #24\n\
+ lsr r7, r1, #24\n\
+ lsl r4, #24\n\
+ lsr r4, #24\n\
+ str r4, [sp, #0x14]\n\
+ lsl r5, #24\n\
+ lsr r5, #24\n\
+ lsl r6, #24\n\
+ lsr r6, #24\n\
+ str r6, [sp, #0x18]\n\
+ mov r0, r8\n\
+ lsl r0, #24\n\
+ lsr r4, r0, #24\n\
+ mov r1, r9\n\
+ lsl r1, #24\n\
+ lsr r1, #24\n\
+ str r1, [sp, #0x1C]\n\
+ mov r2, r10\n\
+ lsl r2, #16\n\
+ lsr r2, #16\n\
+ str r2, [sp, #0x20]\n\
+ mov r0, r12\n\
+ lsl r0, #16\n\
+ lsr r0, #16\n\
+ str r0, [sp, #0x24]\n\
+ ldr r0, [sp, #0x4]\n\
+ bl IsInvalidBg32\n\
+ cmp r0, #0\n\
+ beq _08002592\n\
+ b _080026EE\n\
+_08002592:\n\
+ ldr r0, [sp, #0x4]\n\
+ bl IsTileMapOutsideWram\n\
+ cmp r0, #0\n\
+ beq _0800259E\n\
+ b _080026EE\n\
+_0800259E:\n\
+ ldr r0, [sp, #0x4]\n\
+ mov r1, #0x4\n\
+ bl GetBgControlAttribute\n\
+ lsl r0, #16\n\
+ lsr r0, #16\n\
+ str r0, [sp, #0x30]\n\
+ ldr r0, [sp, #0x4]\n\
+ mov r1, #0x1\n\
+ bl GetBgMetricTextMode\n\
+ lsl r0, #21\n\
+ lsr r0, #16\n\
+ str r0, [sp, #0x28]\n\
+ ldr r0, [sp, #0x4]\n\
+ mov r1, #0x2\n\
+ bl GetBgMetricTextMode\n\
+ lsl r0, #21\n\
+ lsr r0, #16\n\
+ str r0, [sp, #0x2C]\n\
+ ldr r0, [sp, #0x4]\n\
+ bl GetBgType\n\
+ cmp r0, #0\n\
+ beq _080025D8\n\
+ cmp r0, #0x1\n\
+ beq _08002674\n\
+ b _080026EE\n\
+_080025D8:\n\
+ ldr r1, [sp, #0x10]\n\
+ add r0, r1, #0\n\
+ mul r0, r7\n\
+ ldr r2, [sp, #0xC]\n\
+ add r0, r2\n\
+ lsl r0, #1\n\
+ ldr r1, [sp, #0x8]\n\
+ add r6, r1, r0\n\
+ add r0, r5, r4\n\
+ cmp r5, r0\n\
+ blt _080025F0\n\
+ b _080026EE\n\
+_080025F0:\n\
+ ldr r2, [sp, #0x18]\n\
+ sub r2, r7, r2\n\
+ str r2, [sp, #0x34]\n\
+ str r0, [sp, #0x38]\n\
+_080025F8:\n\
+ ldr r4, [sp, #0x14]\n\
+ ldr r7, [sp, #0x18]\n\
+ add r0, r4, r7\n\
+ add r1, r5, #0x1\n\
+ str r1, [sp, #0x3C]\n\
+ cmp r4, r0\n\
+ bge _0800265A\n\
+ ldr r2, [sp, #0x4]\n\
+ lsl r0, r2, #4\n\
+ ldr r1, =gUnknown_030008FC\n\
+ add r0, r1\n\
+ mov r10, r0\n\
+ ldr r7, [sp, #0x20]\n\
+ lsl r7, #16\n\
+ mov r9, r7\n\
+ ldr r1, [sp, #0x24]\n\
+ lsl r0, r1, #16\n\
+ asr r0, #16\n\
+ mov r8, r0\n\
+_0800261E:\n\
+ ldr r2, [sp, #0x2C]\n\
+ str r2, [sp]\n\
+ add r0, r4, #0\n\
+ add r1, r5, #0\n\
+ ldr r2, [sp, #0x30]\n\
+ ldr r3, [sp, #0x28]\n\
+ bl GetTileMapIndexFromCoords\n\
+ lsl r0, #16\n\
+ lsr r0, #15\n\
+ mov r7, r10\n\
+ ldr r1, [r7]\n\
+ add r1, r0\n\
+ mov r0, r8\n\
+ str r0, [sp]\n\
+ add r0, r6, #0\n\
+ ldr r2, [sp, #0x1C]\n\
+ mov r7, r9\n\
+ asr r3, r7, #16\n\
+ bl CopyTileMapEntry\n\
+ add r6, #0x2\n\
+ add r0, r4, #0x1\n\
+ lsl r0, #16\n\
+ lsr r4, r0, #16\n\
+ ldr r1, [sp, #0x14]\n\
+ ldr r2, [sp, #0x18]\n\
+ add r0, r1, r2\n\
+ cmp r4, r0\n\
+ blt _0800261E\n\
+_0800265A:\n\
+ ldr r5, [sp, #0x34]\n\
+ lsl r0, r5, #1\n\
+ add r6, r0\n\
+ ldr r7, [sp, #0x3C]\n\
+ lsl r0, r7, #16\n\
+ lsr r5, r0, #16\n\
+ ldr r0, [sp, #0x38]\n\
+ cmp r5, r0\n\
+ blt _080025F8\n\
+ b _080026EE\n\
+ .pool\n\
+_08002674:\n\
+ ldr r1, [sp, #0x10]\n\
+ add r0, r1, #0\n\
+ mul r0, r7\n\
+ ldr r2, [sp, #0xC]\n\
+ add r0, r2\n\
+ ldr r1, [sp, #0x8]\n\
+ add r6, r1, r0\n\
+ ldr r0, [sp, #0x4]\n\
+ mov r1, #0x1\n\
+ bl GetBgMetricAffineMode\n\
+ lsl r0, #16\n\
+ lsr r0, #16\n\
+ mov r9, r0\n\
+ add r0, r5, r4\n\
+ cmp r5, r0\n\
+ bge _080026EE\n\
+ ldr r2, [sp, #0x18]\n\
+ sub r2, r7, r2\n\
+ str r2, [sp, #0x34]\n\
+ str r0, [sp, #0x38]\n\
+ ldr r7, =gUnknown_030008FC\n\
+ mov r10, r7\n\
+ ldr r0, [sp, #0x4]\n\
+ lsl r0, #4\n\
+ mov r8, r0\n\
+_080026A8:\n\
+ ldr r4, [sp, #0x14]\n\
+ ldr r1, [sp, #0x18]\n\
+ add r0, r4, r1\n\
+ add r2, r5, #0x1\n\
+ str r2, [sp, #0x3C]\n\
+ cmp r4, r0\n\
+ bge _080026DE\n\
+ mov r3, r8\n\
+ add r3, r10\n\
+ mov r7, r9\n\
+ mul r7, r5\n\
+ mov r12, r7\n\
+ add r2, r0, #0\n\
+_080026C2:\n\
+ ldr r1, [r3]\n\
+ mov r5, r12\n\
+ add r0, r5, r4\n\
+ add r1, r0\n\
+ ldrb r0, [r6]\n\
+ ldr r7, [sp, #0x20]\n\
+ add r0, r7\n\
+ strb r0, [r1]\n\
+ add r6, #0x1\n\
+ add r0, r4, #0x1\n\
+ lsl r0, #16\n\
+ lsr r4, r0, #16\n\
+ cmp r4, r2\n\
+ blt _080026C2\n\
+_080026DE:\n\
+ ldr r0, [sp, #0x34]\n\
+ add r6, r0\n\
+ ldr r1, [sp, #0x3C]\n\
+ lsl r0, r1, #16\n\
+ lsr r5, r0, #16\n\
+ ldr r2, [sp, #0x38]\n\
+ cmp r5, r2\n\
+ blt _080026A8\n\
+_080026EE:\n\
+ add sp, #0x40\n\
+ pop {r3-r5}\n\
+ mov r8, r3\n\
+ mov r9, r4\n\
+ mov r10, r5\n\
+ pop {r4-r7}\n\
+ pop {r0}\n\
+ bx r0\n\
+ .pool\n");
+}
+
+void FillBgTilemapBufferRect_Palette0(u8 bg, u16 tileNum, u8 x, u8 y, u8 width, u8 height)
+{
+ u16 x16;
+ u16 y16;
+ u16 mode;
+
+ if (IsInvalidBg32(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
+ {
+ switch (GetBgType(bg))
+ {
+ case 0:
+ for (y16 = y; y16 < (y + height); y16++)
+ {
+ for (x16 = x; x16 < (x + width); x16++)
+ {
+ ((u16*)gUnknown_030008F8[bg].tilemap)[((y16 * 0x20) + x16)] = tileNum;
+ }
+ }
+ break;
+ case 1:
+ mode = GetBgMetricAffineMode(bg, 0x1);
+ for (y16 = y; y16 < (y + height); y16++)
+ {
+ for (x16 = x; x16 < (x + width); x16++)
+ {
+ ((u8*)gUnknown_030008F8[bg].tilemap)[((y16 * mode) + x16)] = tileNum;
+ }
+ }
+ break;
+ }
+ }
+}
+
+void FillBgTilemapBufferRect(u8 bg, u16 tileNum, u8 x, u8 y, u8 width, u8 height, u8 palette)
+{
+ WriteSequenceToBgTilemapBuffer(bg, tileNum, x, y, width, height, palette, 0);
+}
+
+void WriteSequenceToBgTilemapBuffer(u8 bg, u16 firstTileNum, u8 x, u8 y, u8 width, u8 height, u8 paletteSlot, s16 tileNumDelta)
+{
+ u16 mode;
+ u16 mode2;
+ u16 attribute;
+ u16 mode3;
+
+ u16 x16;
+ u16 y16;
+
+ if (IsInvalidBg32(bg) == FALSE && IsTileMapOutsideWram(bg) == FALSE)
+ {
+ attribute = GetBgControlAttribute(bg, 0x4);
+ mode = GetBgMetricTextMode(bg, 0x1) * 0x20;
+ mode2 = GetBgMetricTextMode(bg, 0x2) * 0x20;
+ switch (GetBgType(bg))
+ {
+ case 0:
+ for (y16 = y; y16 < (y + height); y16++)
+ {
+ for (x16 = x; x16 < (x + width); x16++)
+ {
+ CopyTileMapEntry(&firstTileNum, &((u16*)gUnknown_030008F8[bg].tilemap)[(u16)GetTileMapIndexFromCoords(x16, y16, attribute, mode, mode2)], paletteSlot, 0, 0);
+ firstTileNum = (firstTileNum & 0xFC00) + ((firstTileNum + tileNumDelta) & 0x3FF);
+ }
+ }
+ break;
+ case 1:
+ mode3 = GetBgMetricAffineMode(bg, 0x1);
+ for (y16 = y; y16 < (y + height); y16++)
+ {
+ for (x16 = x; x16 < (x + width); x16++)
+ {
+ ((u8*)gUnknown_030008F8[bg].tilemap)[(y16 * mode3) + x16] = firstTileNum;
+ firstTileNum = (firstTileNum & 0xFC00) + ((firstTileNum + tileNumDelta) & 0x3FF);
+ }
+ }
+ break;
+ }
+ }
+}
+
+u16 GetBgMetricTextMode(u8 bg, u8 whichMetric)
+{
+ u8 attribute;
+
+ attribute = GetBgControlAttribute(bg, 0x4);
+
+ switch (whichMetric)
+ {
+ case 0:
+ switch (attribute)
+ {
+ case 0:
+ return 1;
+ case 1:
+ case 2:
+ return 2;
+ case 3:
+ return 4;
+ }
+ break;
+ case 1:
+ switch (attribute)
+ {
+ case 0:
+ return 1;
+ case 1:
+ return 2;
+ case 2:
+ return 1;
+ case 3:
+ return 2;
+ }
+ break;
+ case 2:
+ switch (attribute)
+ {
+ case 0:
+ case 1:
+ return 1;
+ case 2:
+ case 3:
+ return 2;
+ }
+ break;
+ }
+ return 0;
+}
+
+u32 GetBgMetricAffineMode(u8 bg, u8 whichMetric)
+{
+ u8 attribute;
+
+ attribute = GetBgControlAttribute(bg, 0x4);
+
+ switch (whichMetric)
+ {
+ case 0:
+ switch (attribute)
+ {
+ case 0:
+ return 0x1;
+ case 1:
+ return 0x4;
+ case 2:
+ return 0x10;
+ case 3:
+ return 0x40;
+ }
+ break;
+ case 1:
+ case 2:
+ return 0x10 << attribute;
+ }
+ return 0;
+}
+
+u32 GetTileMapIndexFromCoords(s32 x, s32 y, s32 screenSize, u32 screenWidth, u32 screenHeight)
+{
+ x = x & (screenWidth - 1);
+ y = y & (screenHeight - 1);
+
+ switch (screenSize)
+ {
+ case 0:
+ case 2:
+ break;
+ case 3:
+ if (y >= 0x20)
+ y += 0x20;
+ case 1:
+ if (x >= 0x20)
+ {
+ x -= 0x20;
+ y += 0x20;
+ }
+ }
+ return (y * 0x20) + x;
+}
+
+#ifdef NONMATCHING // This one has some weird switch statement cases that refuse to cooperate
+void CopyTileMapEntry(u16 *src, u16 *dest, s32 palette1, u32 tileOffset, u32 palette2)
+{
+ u16 test;
+ switch (palette1)
+ {
+ case 0x0 ... 0x10:
+ if (palette1 != 0x10)
+ test = ((*src + tileOffset) & 0xFFF) + ((palette1 + palette2) << 12);
+ else
+ test = ((*dest & 0xFC00) + (palette2 << 12)) | ((*src + tileOffset) & 0x3FF);
+ break;
+ default:
+ test = *src + tileOffset + (palette2 << 12);
+ break;
+ }
+
+ *dest = test;
+}
+#else
+__attribute__((naked))
+void CopyTileMapEntry(u16 *src, u16 *dest, s32 palette1, u32 tileOffset, u32 palette2)
+{
+ asm("push {r4-r6,lr}\n\
+ add r4, r0, #0\n\
+ add r6, r1, #0\n\
+ ldr r5, [sp, #0x10]\n\
+ cmp r2, #0x10\n\
+ beq _08002B14\n\
+ cmp r2, #0x10\n\
+ bgt _08002B34\n\
+ cmp r2, #0\n\
+ blt _08002B34\n\
+ ldrh r0, [r4]\n\
+ add r0, r3\n\
+ ldr r3, =0x00000fff\n\
+ add r1, r3, #0\n\
+ and r0, r1\n\
+ add r1, r2, r5\n\
+ lsl r1, #12\n\
+ b _08002B3A\n\
+ .pool\n\
+_08002B14:\n\
+ ldrh r1, [r6]\n\
+ mov r0, #0xFC\n\
+ lsl r0, #8\n\
+ and r1, r0\n\
+ lsl r2, r5, #12\n\
+ add r2, r1, r2\n\
+ ldrh r0, [r4]\n\
+ add r0, r3\n\
+ ldr r3, =0x000003ff\n\
+ add r1, r3, #0\n\
+ and r0, r1\n\
+ orr r0, r2\n\
+ b _08002B3C\n\
+ .pool\n\
+_08002B34:\n\
+ ldrh r0, [r4]\n\
+ add r0, r3\n\
+ lsl r1, r5, #12\n\
+_08002B3A:\n\
+ add r0, r1\n\
+_08002B3C:\n\
+ lsl r0, #16\n\
+ lsr r1, r0, #16\n\
+ strh r1, [r6]\n\
+ pop {r4-r6}\n\
+ pop {r0}\n\
+ bx r0\n");
+}
+#endif // NONMATCHING
+
+u32 GetBgType(u8 bg)
+{
+ u8 mode;
+
+ mode = GetBgMode();
+
+
+ switch (bg)
+ {
+ case 0:
+ case 1:
+ switch (mode)
+ {
+ case 0:
+ case 1:
+ return 0;
+ }
+ break;
+ case 2:
+ switch (mode)
+ {
+ case 0:
+ return 0;
+ case 1:
+ case 2:
+ return 1;
+ }
+ break;
+ case 3:
+ switch (mode)
+ {
+ case 0:
+ return 0;
+ case 2:
+ return 1;
+ }
+ break;
+ }
+
+ return 0xFFFF;
+}
+
+bool32 IsInvalidBg32(u8 bg)
+{
+ if (bg > 3)
+ return TRUE;
+ return FALSE;
+}
+
+bool32 IsTileMapOutsideWram(u8 bg)
+{
+ if (gUnknown_030008F8[bg].tilemap > (void*)IWRAM_END)
+ return TRUE;
+ if (gUnknown_030008F8[bg].tilemap == 0x0)
+ return TRUE;
+ return FALSE;
+}