Optimise DMA functions

This commit is contained in:
Ryan Dwyer
2023-05-19 21:20:08 +10:00
parent 9bd41837ad
commit a45acb282b
2 changed files with 8 additions and 74 deletions
+1 -1
View File
@@ -73,7 +73,7 @@ ROM_SIZE := 32
# When enabled, press C-up and C-down simultaneously to toggle the debug menu.
# Note that some emulators have problems displaying the crash screen text.
DEBUG = 0
DEBUG = 1
# ANTIALIAS
#
+7 -73
View File
@@ -5,97 +5,31 @@
#include "data.h"
#include "types.h"
volatile u32 g_DmaNumSlotsBusy;
OSIoMesg g_DmaIoMsgs[32];
volatile u8 g_DmaSlotsBusy[32];
OSMesg g_DmaMesgs[32];
OSIoMesg g_DmaIoMsgs[1];
OSMesg g_DmaMesgs[1];
OSMesgQueue g_DmaMesgQueue;
static void dmaWait(void);
void dmaInit(void)
{
s32 i;
for (i = 0; i < ARRAYCOUNT(g_DmaSlotsBusy); i++) {
g_DmaSlotsBusy[i] = 0;
}
g_DmaNumSlotsBusy = 0;
osCreateMesgQueue(&g_DmaMesgQueue, g_DmaMesgs, ARRAYCOUNT(g_DmaMesgs));
}
static void dmaStart(void *memaddr, u32 romaddr, u32 len, bool priority)
{
u32 numiterations;
u32 remainder;
s32 i;
if (g_DmaNumSlotsBusy) {
dmaWait();
}
if (len < 0x4000 * ARRAYCOUNT(g_DmaIoMsgs)) {
numiterations = len / 0x4000;
remainder = len % 0x4000;
} else {
// DMA size is 0x80000 or more. It won't fit in the queue, so do it
// all in one call to osPiStartDma using the remainder variable.
numiterations = 0;
remainder = len;
}
osInvalDCache(memaddr, len);
for (i = 0; i != numiterations; i++) {
g_DmaSlotsBusy[i] = true;
g_DmaNumSlotsBusy++;
osPiStartDma(&g_DmaIoMsgs[i], priority, 0, romaddr, memaddr, 0x4000, &g_DmaMesgQueue);
romaddr += 0x4000;
memaddr = (void *)((u32)memaddr + 0x4000);
}
if (remainder) {
g_DmaSlotsBusy[i] = true;
g_DmaNumSlotsBusy++;
osPiStartDma(&g_DmaIoMsgs[i], priority, 0, romaddr, memaddr, remainder, &g_DmaMesgQueue);
}
}
static void dmaWait(void)
{
u32 stack;
OSIoMesg *msg;
s32 i;
while (g_DmaNumSlotsBusy) {
osRecvMesg(&g_DmaMesgQueue, (OSMesg) &msg, OS_MESG_BLOCK);
for (i = 0; i < ARRAYCOUNT(g_DmaIoMsgs); i++) {
if (&g_DmaIoMsgs[i] == msg) {
break;
}
}
g_DmaSlotsBusy[i] = false;
g_DmaNumSlotsBusy--;
}
osInvalDCache(memaddr, len);
osPiStartDma(&g_DmaIoMsgs[0], priority, 0, romaddr, memaddr, len, &g_DmaMesgQueue);
osRecvMesg(&g_DmaMesgQueue, (OSMesg) &msg, OS_MESG_BLOCK);
}
void dmaExec(void *memaddr, u32 romaddr, u32 len)
{
dmaStart(memaddr, romaddr, len, false);
dmaWait();
dmaStart(memaddr, romaddr, len, OS_MESG_PRI_NORMAL);
}
void dmaExecHighPriority(void *memaddr, u32 romaddr, u32 len)
{
dmaStart(memaddr, romaddr, len, true);
dmaWait();
dmaStart(memaddr, romaddr, len, OS_MESG_PRI_HIGH);
}
/**