diff options
author | red031000 <rubenru09@aol.com> | 2020-06-30 14:10:53 +0100 |
---|---|---|
committer | red031000 <rubenru09@aol.com> | 2020-06-30 14:12:05 +0100 |
commit | 1f9c3382c451382756934e0eaf7d35b51ce3b1d4 (patch) | |
tree | ddc326782b6c25a958fbcf6de83a9af8eb0a848a /arm9 | |
parent | 9396b082a208d4fc4375030c38a58ff589c9a72b (diff) |
arm9 MI_dma_gxcommand, remove arm9_itcm.s
Diffstat (limited to 'arm9')
-rw-r--r-- | arm9/arm9.lcf | 2 | ||||
-rw-r--r-- | arm9/asm/MI_dma_gxcommand.s | 246 | ||||
-rw-r--r-- | arm9/asm/arm9_itcm.s | 53 | ||||
-rw-r--r-- | arm9/lib/include/GX_g3x.h | 15 | ||||
-rw-r--r-- | arm9/lib/include/MI_dma_gxcommand.h | 37 | ||||
-rw-r--r-- | arm9/lib/src/MI_dma_gxcommand.c | 153 |
6 files changed, 206 insertions, 300 deletions
diff --git a/arm9/arm9.lcf b/arm9/arm9.lcf index f6a8be67..a23d6184 100644 --- a/arm9/arm9.lcf +++ b/arm9/arm9.lcf @@ -972,7 +972,7 @@ SECTIONS { OS_irqHandler.o (.itcm) OS_reset.o (.itcm) MI_dma.o (.itcm) - arm9_itcm.o (.text) + MI_dma_gxcommand.o (.itcm) . = ALIGN(32); SDK_AUTOLOAD.ITCM.END = .; SDK_AUTOLOAD.ITCM.SIZE = SDK_AUTOLOAD.ITCM.END - SDK_AUTOLOAD.ITCM.START; diff --git a/arm9/asm/MI_dma_gxcommand.s b/arm9/asm/MI_dma_gxcommand.s deleted file mode 100644 index fdf51ac3..00000000 --- a/arm9/asm/MI_dma_gxcommand.s +++ /dev/null @@ -1,246 +0,0 @@ - .include "asm/macros.inc" - .include "global.inc" - - .section .bss - - .global UNK_021D37FC -UNK_021D37FC: ; 0x021D37FC - .space 0x20 - - .text - - arm_func_start MIi_DMAFastCallback -MIi_DMAFastCallback: ; 0x020CDE78 - stmdb sp!, {lr} - sub sp, sp, #0x4 - ldr r0, _020CDEB4 ; =UNK_021D37FC - mov r2, #0x0 - ldr r1, [r0, #0x10] - str r2, [r0, #0x0] - cmp r1, #0x0 - addeq sp, sp, #0x4 - ldr r0, [r0, #0x14] - ldmeqia sp!, {lr} - bxeq lr - blx r1 - add sp, sp, #0x4 - ldmia sp!, {lr} - bx lr - .balign 4 -_020CDEB4: .word UNK_021D37FC - - arm_func_start MI_SendGXCommandAsyncFast -MI_SendGXCommandAsyncFast: ; 0x020CDEB8 - stmdb sp!, {r4-r6,lr} - movs r4, r2 - mov r6, r0 - mov r5, r1 - bne _020CDEE8 - cmp r3, #0x0 - ldmeqia sp!, {r4-r6,lr} - bxeq lr - ldr r0, [sp, #0x10] - blx r3 - ldmia sp!, {r4-r6,lr} - bx lr -_020CDEE8: - ldr r2, _020CDF6C ; =UNK_021D37FC - ldr r0, [r2, #0x0] - cmp r0, #0x0 - bne _020CDEE8 - ldr r12, [sp, #0x10] - mov lr, #0x1 - mov r0, r6 - mov r1, #0x38000000 - str lr, [r2, #0x0] - str r6, [r2, #0x4] - str r3, [r2, #0x10] - str r12, [r2, #0x14] - bl MIi_CheckAnotherAutoDMA - mov r0, r6 - mov r1, r5 - mov r2, r4 - mov r3, #0x0 - bl MIi_CheckDma0SourceAddress - mov r0, r6 - bl MI_WaitDma - mov r0, r6 - ldr r1, _020CDF70 ; =MIi_DMAFastCallback - mov r2, #0x0 - bl OSi_EnterDmaCallback - mov r0, r6 - mov r1, r5 - ldr r2, _020CDF74 ; =0x04000400 - mov r3, #0x3c00000 - rsb r3, r3, #0x0 - orr r3, r3, r4, lsr #0x2 - bl MIi_DmaSetParams - ldmia sp!, {r4-r6,lr} - bx lr - .balign 4 -_020CDF6C: .word UNK_021D37FC -_020CDF70: .word MIi_DMAFastCallback -_020CDF74: .word 0x04000400 - - arm_func_start MIi_DMACallback -MIi_DMACallback: ; 0x020CDF78 - stmdb sp!, {lr} - sub sp, sp, #0x4 - mov r0, #0x200000 - bl OS_DisableIrqMask - ldr r2, _020CDFE4 ; =0x04000600 - ldr r0, _020CDFE8 ; =UNK_021D37FC - ldr r1, [r2, #0x0] - ldr r3, [r0, #0x18] - bic r1, r1, #0xc0000000 - orr r1, r1, r3, lsl #0x1e - str r1, [r2, #0x0] - ldr r1, [r0, #0x1c] - mov r0, #0x200000 - bl OS_SetIrqFunction - ldr r0, _020CDFE8 ; =UNK_021D37FC - mov r2, #0x0 - ldr r1, [r0, #0x10] - str r2, [r0, #0x0] - cmp r1, #0x0 - addeq sp, sp, #0x4 - ldr r0, [r0, #0x14] - ldmeqia sp!, {lr} - bxeq lr - blx r1 - add sp, sp, #0x4 - ldmia sp!, {lr} - bx lr - .balign 4 -_020CDFE4: .word 0x04000600 -_020CDFE8: .word UNK_021D37FC - - arm_func_start MIi_FIFOCallback -MIi_FIFOCallback: ; 0x020CDFEC - stmdb sp!, {r4-r5,lr} - sub sp, sp, #0x4 - ldr r0, _020CE0A4 ; =UNK_021D37FC - ldr r4, [r0, #0xc] - cmp r4, #0x0 - addeq sp, sp, #0x4 - ldmeqia sp!, {r4-r5,lr} - bxeq lr - ldr r0, _020CE0A4 ; =UNK_021D37FC - cmp r4, #0x1d8 - ldr r5, [r0, #0x8] - movcs r4, #0x1d8 - ldr r2, [r0, #0xc] - add r1, r5, r4 - subs r2, r2, r4 - str r2, [r0, #0xc] - str r1, [r0, #0x8] - bne _020CE078 - ldr r0, [r0, #0x4] - ldr r1, _020CE0A8 ; =MIi_DMACallback - mov r2, #0x0 - bl OSi_EnterDmaCallback - mov r0, #0x3bc00000 - rsb r3, r0, #0x0 - ldr r1, _020CE0A4 ; =UNK_021D37FC - ldr r2, _020CE0AC ; =0x04000400 - ldr r0, [r1, #0x4] - mov r1, r5 - orr r3, r3, r4, lsr #0x2 - bl MIi_DmaSetParams - mov r0, #0x200000 - bl OS_ResetRequestIrqMask - add sp, sp, #0x4 - ldmia sp!, {r4-r5,lr} - bx lr -_020CE078: - ldr r3, _020CE0B0 ; =0x84400000 - ldr r0, [r0, #0x4] - ldr r2, _020CE0AC ; =0x04000400 - mov r1, r5 - orr r3, r3, r4, lsr #0x2 - bl MIi_DmaSetParams - mov r0, #0x200000 - bl OS_ResetRequestIrqMask - add sp, sp, #0x4 - ldmia sp!, {r4-r5,lr} - bx lr - .balign 4 -_020CE0A4: .word UNK_021D37FC -_020CE0A8: .word MIi_DMACallback -_020CE0AC: .word 0x04000400 -_020CE0B0: .word 0x84400000 - - arm_func_start MI_SendGXCommandAsync -MI_SendGXCommandAsync: ; 0x020CE0B4 - stmdb sp!, {r4-r5,lr} - sub sp, sp, #0x4 - mov r4, r0 - cmp r2, #0x0 - bne _020CE0EC - cmp r3, #0x0 - addeq sp, sp, #0x4 - ldmeqia sp!, {r4-r5,lr} - bxeq lr - ldr r0, [sp, #0x10] - blx r3 - add sp, sp, #0x4 - ldmia sp!, {r4-r5,lr} - bx lr -_020CE0EC: - ldr r0, _020CE1BC ; =UNK_021D37FC - ldr r0, [r0, #0x0] - cmp r0, #0x0 - bne _020CE0EC - ldr r5, _020CE1C0 ; =0x04000600 -_020CE100: - ldr r0, [r5, #0x0] - and r0, r0, #0x7000000 - mov r0, r0, lsr #0x18 - ands r0, r0, #0x2 - beq _020CE100 - ldr ip, _020CE1BC ; =UNK_021D37FC - ldr lr, [sp, #0x10] - str r3, [r12, #0x10] - mov r5, #0x1 - mov r0, r4 - mov r3, #0x0 - str r5, [r12, #0x0] - str r4, [r12, #0x4] - str r1, [r12, #0x8] - str r2, [r12, #0xc] - str lr, [r12, #0x14] - bl MIi_CheckDma0SourceAddress - mov r0, r4 - bl MI_WaitDma - bl OS_DisableInterrupts - ldr r1, _020CE1C0 ; =0x04000600 - mov r4, r0 - ldr r0, [r1, #0x0] - ldr r1, _020CE1BC ; =UNK_021D37FC - and r0, r0, #0xc0000000 - mov r2, r0, lsr #0x1e - mov r0, #0x200000 - str r2, [r1, #0x18] - bl OS_GetIrqFunction - ldr r1, _020CE1BC ; =UNK_021D37FC - ldr r2, _020CE1C0 ; =0x04000600 - str r0, [r1, #0x1c] - ldr r0, [r2, #0x0] - ldr r1, _020CE1C4 ; =MIi_FIFOCallback - bic r0, r0, #0xc0000000 - orr r3, r0, #0x40000000 - mov r0, #0x200000 - str r3, [r2, #0x0] - bl OS_SetIrqFunction - mov r0, #0x200000 - bl OS_EnableIrqMask - bl MIi_FIFOCallback - mov r0, r4 - bl OS_RestoreInterrupts - add sp, sp, #0x4 - ldmia sp!, {r4-r5,lr} - bx lr - .balign 4 -_020CE1BC: .word UNK_021D37FC -_020CE1C0: .word 0x04000600 -_020CE1C4: .word MIi_FIFOCallback diff --git a/arm9/asm/arm9_itcm.s b/arm9/asm/arm9_itcm.s deleted file mode 100644 index d89e6e77..00000000 --- a/arm9/asm/arm9_itcm.s +++ /dev/null @@ -1,53 +0,0 @@ - .include "asm/macros.inc" - .include "global.inc" - .section .text - - ; MI - arm_func_start MI_SendGXCommand -MI_SendGXCommand: ; 0x01FF8640 - stmdb sp!, {r4, r5, r6, r7, r8, r9, sl, fp, lr} - sub sp, sp, #4 - movs r8, r2 - mov sl, r0 - mov r9, r1 - addeq sp, sp, #4 - ldmeqia sp!, {r4, r5, r6, r7, r8, r9, sl, fp, lr} - bxeq lr - mov r3, #0 - bl MIi_CheckDma0SourceAddress - mov r0, #3 - mul r1, sl, r0 - ldr r0, [pc, #104] ; 0x10b680 - add r1, r1, #2 - add r7, r0, r1, lsl #2 -_01FF867C: - ldr r0, [r7] - ands r0, r0, #-2147483648 ; 0x80000000 - bne _01FF867C - cmp r8, #0 - beq _01FF86C8 - ldr fp, [pc, #76] ; 0x10b684 - mov r5, #472 ; 0x1d8 - ldr r4, [pc, #72] ; 0x10b688 -_01FF869C: - cmp r8, #472 ; 0x1d8 - movhi r6, r5 - movls r6, r8 - mov r0, sl - mov r1, r9 - mov r2, fp - orr r3, r4, r6, lsr #2 - bl MIi_DmaSetParams - subs r8, r8, r6 - add r9, r9, r6 - bne _01FF869C -_01FF86C8: - ldr r0, [r7] - ands r0, r0, #-2147483648 ; 0x80000000 - bne _01FF86C8 - add sp, sp, #4 - ldmia sp!, {r4, r5, r6, r7, r8, r9, sl, fp, lr} - bx lr -_01FF86E0: .word 0x040000B0 -_01FF86E4: .word 0x04000400 -_01FF86E8: .word 0x84400000 diff --git a/arm9/lib/include/GX_g3x.h b/arm9/lib/include/GX_g3x.h index 4bd55831..a0512b28 100644 --- a/arm9/lib/include/GX_g3x.h +++ b/arm9/lib/include/GX_g3x.h @@ -1,6 +1,8 @@ #ifndef GUARD_GX_G3X_H #define GUARD_GX_G3X_H +#include "fx.h" + void GXi_NopClearFifo128_(void *reg); void G3X_Init(); void G3X_ResetMtxStack(); @@ -66,4 +68,17 @@ typedef enum } GXFifoStat; +static inline void G3X_SetFifoIntrCond(GXFifoIntrCond cond) +{ + reg_G3X_GXSTAT = ((reg_G3X_GXSTAT & ~0xc0000000) | + (cond << 30)); +} + +static inline GXFifoStat G3X_GetCommandFifoStatus(void) +{ + return (GXFifoStat)((reg_G3X_GXSTAT & (0x01000000 | + 0x02000000 | + 0x04000000)) >> 24); +} + #endif //GUARD_GX_G3X_H diff --git a/arm9/lib/include/MI_dma_gxcommand.h b/arm9/lib/include/MI_dma_gxcommand.h new file mode 100644 index 00000000..29aa9c72 --- /dev/null +++ b/arm9/lib/include/MI_dma_gxcommand.h @@ -0,0 +1,37 @@ +#ifndef POKEDIAMOND_MI_DMA_GXCOMMAND_H +#define POKEDIAMOND_MI_DMA_GXCOMMAND_H + +#include "consts.h" +#include "MI_dma.h" +#include "GX_g3x.h" + +#define MIi_GX_LENGTH_ONCE (118 * sizeof(u32)) +#define REG_GXFIFO_ADDR 0x4000400 +#define MI_CNT_SEND32(size) (0x84400000 | (size/4)) +#define MI_CNT_SEND32_IF(size) (0xc4400000 | (size/4)) +#define MI_CNT_GXCOPY_IF(size) (0xfc400000 | (size/4)) + +#define OS_IE_GXFIFO 0x200000 + +typedef struct +{ + volatile BOOL isBusy; + + u32 dmaNo; + u32 src; + u32 length; + MIDmaCallback callback; + void *arg; + + GXFifoIntrCond fifoCond; + void (*fifoFunc) (void); +} MIiGXDmaParams; + +void MI_SendGXCommand(u32 dmaNo, const void *src, u32 commandLength); +void MI_SendGXCommandAsync(u32 dmaNo, const void *src, u32 commandLength, MIDmaCallback callback, void *arg); +static void MIi_FIFOCallback(void); +static void MIi_DMACallback(void *); +void MI_SendGXCommandAsyncFast(u32 dmaNo, const void *src, u32 commandLength, MIDmaCallback callback, void *arg); +static void MIi_DMAFastCallback(void *); + +#endif //POKEDIAMOND_MI_DMA_GXCOMMAND_H diff --git a/arm9/lib/src/MI_dma_gxcommand.c b/arm9/lib/src/MI_dma_gxcommand.c new file mode 100644 index 00000000..32f98f60 --- /dev/null +++ b/arm9/lib/src/MI_dma_gxcommand.c @@ -0,0 +1,153 @@ +#include "MI_dma_gxcommand.h" +#include "function_target.h" +#include "OS_interrupt.h" +#include "OS_reset.h" +#include "sections.h" + +static MIiGXDmaParams MIi_GXDmaParams = { FALSE }; + +#pragma section ITCM begin +ARM_FUNC void MI_SendGXCommand(u32 dmaNo, const void *src, u32 commandLength) +{ + vu32 *dmaCntp; + u32 leftLength = commandLength; + u32 currentSrc = (u32)src; + if (!leftLength) + { + return; + } + + MIi_CheckDma0SourceAddress(dmaNo, (u32)src, commandLength, DMA_SRC_INC); + + do + { + dmaCntp = &((vu32 *)REG_ADDR_DMA0SAD)[dmaNo * 3 + 2]; + while (*dmaCntp & 0x80000000) {} + } while(0); + + while (leftLength > 0) + { + u32 length = (leftLength > MIi_GX_LENGTH_ONCE) ? MIi_GX_LENGTH_ONCE : leftLength; + MIi_DmaSetParams(dmaNo, currentSrc, (u32)REG_GXFIFO_ADDR, MI_CNT_SEND32(length)); + leftLength -= length; + currentSrc += length; + } + + do + { + while (*dmaCntp & 0x80000000) {} + } while(0); +} +#pragma section ITCM end + +ARM_FUNC void MI_SendGXCommandAsync(u32 dmaNo, const void *src, u32 commandLength, MIDmaCallback callback, void *arg) +{ + vu32 *dmaCntp; + u32 leftLength = commandLength; + u32 currentSrc = (u32)src; + + if (!commandLength) + { + MIi_CallCallback(callback, arg); + return; + } + + while (MIi_GXDmaParams.isBusy) {} + + while (!(G3X_GetCommandFifoStatus() & GX_FIFOSTAT_UNDERHALF)) {} + + MIi_GXDmaParams.isBusy = TRUE; + MIi_GXDmaParams.dmaNo = dmaNo; + MIi_GXDmaParams.src = (u32)src; + MIi_GXDmaParams.length = commandLength; + MIi_GXDmaParams.callback = callback; + MIi_GXDmaParams.arg = arg; + + MIi_CheckDma0SourceAddress(dmaNo, (u32)src, commandLength, DMA_SRC_INC); + + MI_WaitDma(dmaNo); + { + OSIntrMode lastIntrMode = OS_DisableInterrupts(); + + MIi_GXDmaParams.fifoCond = (GXFifoIntrCond)((reg_G3X_GXSTAT & 0xc0000000) >> 30); + MIi_GXDmaParams.fifoFunc = OS_GetIrqFunction(OS_IE_GXFIFO); + + G3X_SetFifoIntrCond(GX_FIFOINTR_COND_UNDERHALF); + OS_SetIrqFunction(OS_IE_GXFIFO, MIi_FIFOCallback); + (void)OS_EnableIrqMask(OS_IE_GXFIFO); + + MIi_FIFOCallback(); + + (void)OS_RestoreInterrupts(lastIntrMode); + } +} + +ARM_FUNC static void MIi_FIFOCallback(void) +{ + if (!MIi_GXDmaParams.length) + { + return; + } + + u32 length = (MIi_GXDmaParams.length >= MIi_GX_LENGTH_ONCE) ? MIi_GX_LENGTH_ONCE : MIi_GXDmaParams.length; + u32 src = MIi_GXDmaParams.src; + + MIi_GXDmaParams.length -= length; + MIi_GXDmaParams.src += length; + + if (!MIi_GXDmaParams.length) + { + OSi_EnterDmaCallback(MIi_GXDmaParams.dmaNo, MIi_DMACallback, NULL); + MIi_DmaSetParams(MIi_GXDmaParams.dmaNo, src, (u32)REG_GXFIFO_ADDR, MI_CNT_SEND32_IF(length)); + (void)OS_ResetRequestIrqMask(OS_IE_GXFIFO); + } + else + { + MIi_DmaSetParams(MIi_GXDmaParams.dmaNo, src, (u32)REG_GXFIFO_ADDR, MI_CNT_SEND32(length)); + (void)OS_ResetRequestIrqMask(OS_IE_GXFIFO); + } +} + +ARM_FUNC static void MIi_DMACallback(void *) +{ + (void)OS_DisableIrqMask(OS_IE_GXFIFO); + + G3X_SetFifoIntrCond(MIi_GXDmaParams.fifoCond); + OS_SetIrqFunction(OS_IE_GXFIFO, MIi_GXDmaParams.fifoFunc); + + MIi_GXDmaParams.isBusy = FALSE; + + MIi_CallCallback(MIi_GXDmaParams.callback, MIi_GXDmaParams.arg); +} + +ARM_FUNC void MI_SendGXCommandAsyncFast(u32 dmaNo, const void *src, u32 commandLength, MIDmaCallback callback, void *arg) +{ + if (!commandLength) + { + MIi_CallCallback(callback, arg); + return; + } + + while (MIi_GXDmaParams.isBusy) {} + + MIi_GXDmaParams.isBusy = TRUE; + MIi_GXDmaParams.dmaNo = dmaNo; + MIi_GXDmaParams.callback = callback; + MIi_GXDmaParams.arg = arg; + + MIi_CheckAnotherAutoDMA(dmaNo, 0x38000000); + + MIi_CheckDma0SourceAddress(dmaNo, (u32)src, commandLength, DMA_SRC_INC); + + MI_WaitDma(dmaNo); + + OSi_EnterDmaCallback(dmaNo, MIi_DMAFastCallback, NULL); + MIi_DmaSetParams(dmaNo, (u32)src, (u32)REG_GXFIFO_ADDR, MI_CNT_GXCOPY_IF(commandLength)); +} + +ARM_FUNC static void MIi_DMAFastCallback(void *) +{ + MIi_GXDmaParams.isBusy = FALSE; + + MIi_CallCallback(MIi_GXDmaParams.callback, MIi_GXDmaParams.arg); +} |