Skip to content

Commit

Permalink
some cleanup in bg/window/dma3
Browse files Browse the repository at this point in the history
  • Loading branch information
cawtds committed Aug 30, 2024
1 parent 539ed36 commit 2e2e879
Show file tree
Hide file tree
Showing 8 changed files with 93 additions and 83 deletions.
1 change: 1 addition & 0 deletions include/dma3.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

// Maximum amount of data we will transfer in one operation
#define MAX_DMA_BLOCK_SIZE 0x1000
#define MAX_DMA_REQUESTS 128

#define DMA_REQUEST_COPY32 1
#define DMA_REQUEST_FILL32 2
Expand Down
13 changes: 11 additions & 2 deletions include/gba/defines.h
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,8 @@
#define BG_TILE_V_FLIP(n) (0x800 + (n))
#define BG_TILE_H_V_FLIP(n) (0xC00 + (n))

#define NUM_BACKGROUNDS 4

// text-mode BG
#define OBJ_VRAM0 (void *)(VRAM + 0x10000)
#define OBJ_VRAM0_SIZE 0x8000
Expand All @@ -66,11 +68,18 @@

#define ROM_HEADER_SIZE 0xC0

// Dimensions of a tile in pixels
#define TILE_WIDTH 8
#define TILE_HEIGHT 8

#define DISPLAY_WIDTH 240
#define DISPLAY_HEIGHT 160

#define TILE_SIZE_4BPP 32
#define TILE_SIZE_8BPP 64
// Size of different tile formats in bytes
#define TILE_SIZE(bpp)((bpp) * TILE_WIDTH * TILE_HEIGHT / 8)
#define TILE_SIZE_1BPP TILE_SIZE(1) // 8
#define TILE_SIZE_4BPP TILE_SIZE(4) // 32
#define TILE_SIZE_8BPP TILE_SIZE(8) // 64

#define BG_TILE_ADDR_4BPP(n) (void *)(BG_VRAM + (TILE_SIZE_4BPP * (n)))

Expand Down
3 changes: 2 additions & 1 deletion include/global.h
Original file line number Diff line number Diff line change
Expand Up @@ -125,7 +125,8 @@ extern u8 gStringVar4[];

#define DIV_ROUND_UP(val, roundBy)(((val) / (roundBy)) + (((val) % (roundBy)) ? 1 : 0))

#define ROUND_BITS_TO_BYTES(numBits) DIV_ROUND_UP(numBits, 8)
#define BITS_PER_BYTE 8
#define ROUND_BITS_TO_BYTES(numBits) DIV_ROUND_UP(numBits, BITS_PER_BYTE)

#define DEX_FLAGS_NO ROUND_BITS_TO_BYTES(NUM_SPECIES)
#define NUM_FLAG_BYTES ROUND_BITS_TO_BYTES(FLAGS_COUNT)
Expand Down
71 changes: 36 additions & 35 deletions src/bg.c
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
#include "gpu_regs.h"

#define DISPCNT_ALL_BG_AND_MODE_BITS (DISPCNT_BG_ALL_ON | 0x7)
#define MAX_CHAR_BASE_INDEX 4

struct BgControl
{
Expand All @@ -22,7 +23,7 @@ struct BgControl

u8 unknown_2;
u8 unknown_3;
} configs[4];
} configs[NUM_BACKGROUNDS];

u16 bgVisibilityAndMode;
};
Expand All @@ -39,9 +40,9 @@ struct BgConfig2
};

static struct BgControl sGpuBgConfigs;
static struct BgConfig2 sGpuBgConfigs2[4];
static u32 sDmaBusyBitfield[4];
static u8 gpu_tile_allocation_map_bg[0x100];
static struct BgConfig2 sGpuBgConfigs2[NUM_BACKGROUNDS];
static u32 sDmaBusyBitfield[MAX_DMA_REQUESTS / (sizeof(u32) * BITS_PER_BYTE)];
static u8 gpu_tile_allocation_map_bg[MAX_CHAR_BASE_INDEX * BG_CHAR_SIZE / (TILE_SIZE_4BPP * BITS_PER_BYTE)];

bool32 gWindowTileAutoAllocEnabled;

Expand All @@ -56,7 +57,7 @@ void ResetBgs(void)

void SetBgModeInternal(u8 bgMode)
{
sGpuBgConfigs.bgVisibilityAndMode &= 0xFFF8;
sGpuBgConfigs.bgVisibilityAndMode &= ~(0x7);
sGpuBgConfigs.bgVisibilityAndMode |= bgMode;
}

Expand All @@ -71,7 +72,7 @@ void ResetBgControlStructs(void)
struct BgConfig zeroedConfig = sZeroedBgControlStruct;
int i;

for (i = 0; i < 4; i++)
for (i = 0; i < NUM_BACKGROUNDS; i++)
{
bgConfigs[i] = zeroedConfig;
}
Expand All @@ -91,7 +92,7 @@ void SetBgControlAttributes(u8 bg, u8 charBaseIndex, u8 mapBaseIndex, u8 screenS
{
if (charBaseIndex != 0xFF)
{
sGpuBgConfigs.configs[bg].charBaseIndex = charBaseIndex & 0x3;
sGpuBgConfigs.configs[bg].charBaseIndex = charBaseIndex % MAX_CHAR_BASE_INDEX;
}

if (mapBaseIndex != 0xFF)
Expand Down Expand Up @@ -168,10 +169,10 @@ u8 LoadBgVram(u8 bg, const void *src, u16 size, u16 destOffset, u8 mode)
{
switch (mode)
{
case 0x1:
case DISPCNT_MODE_1:
offset = sGpuBgConfigs.configs[bg].charBaseIndex * BG_CHAR_SIZE;
break;
case 0x2:
case DISPCNT_MODE_2:
offset = sGpuBgConfigs.configs[bg].mapBaseIndex * BG_SCREEN_SIZE;
break;
default:
Expand Down Expand Up @@ -296,13 +297,13 @@ int BgTileAllocOp(int bg, int offset, int count, int mode)
case BG_TILE_FIND_FREE_SPACE:
start = GetBgControlAttribute(bg, BG_CTRL_ATTR_CHARBASEINDEX) * (BG_CHAR_SIZE / TILE_SIZE_4BPP);
end = start + 0x400;
if (end > 0x800)
end = 0x800;
if (end > (int)ARRAY_COUNT(gpu_tile_allocation_map_bg) * BITS_PER_BYTE)
end = ARRAY_COUNT(gpu_tile_allocation_map_bg) * BITS_PER_BYTE;
blockSize = 0;
blockStart = 0;
for (i = start, offset = 0; i < end; i++, offset++)
{
if (!((gpu_tile_allocation_map_bg[i / 8] >> (i % 8)) & 1))
if (!((gpu_tile_allocation_map_bg[i / BITS_PER_BYTE] >> (i % BITS_PER_BYTE)) & 1))
{
if (blockSize)
{
Expand All @@ -326,13 +327,13 @@ int BgTileAllocOp(int bg, int offset, int count, int mode)
start = GetBgControlAttribute(bg, BG_CTRL_ATTR_CHARBASEINDEX) * (BG_CHAR_SIZE / TILE_SIZE_4BPP) + offset;
end = start + count;
for (i = start; i < end; i++)
gpu_tile_allocation_map_bg[i / 8] |= 1 << (i % 8);
gpu_tile_allocation_map_bg[i / BITS_PER_BYTE] |= 1 << (i % BITS_PER_BYTE);
break;
case BG_TILE_FREE:
start = GetBgControlAttribute(bg, BG_CTRL_ATTR_CHARBASEINDEX) * (BG_CHAR_SIZE / TILE_SIZE_4BPP) + offset;
end = start + count;
for (i = start; i < end; i++)
gpu_tile_allocation_map_bg[i / 8] &= ~(1 << (i % 8));
gpu_tile_allocation_map_bg[i / BITS_PER_BYTE] &= ~(1 << (i % BITS_PER_BYTE));
break;
}

Expand All @@ -344,14 +345,14 @@ void ResetBgsAndClearDma3BusyFlags(bool32 enableWindowTileAutoAlloc)
int i;
ResetBgs();

for (i = 0; i < 4; i++)
for (i = 0; i < (int)(ARRAY_COUNT(sDmaBusyBitfield)); i++)
{
sDmaBusyBitfield[i] = 0;
}

gWindowTileAutoAllocEnabled = enableWindowTileAutoAlloc;

for (i = 0; i < 0x100; i++)
for (i = 0; i < (int)(ARRAY_COUNT(gpu_tile_allocation_map_bg)); i++)
{
gpu_tile_allocation_map_bg[i] = 0;
}
Expand All @@ -368,7 +369,7 @@ void InitBgsFromTemplates(u8 bgMode, const struct BgTemplate *templates, u8 numT
for (i = 0; i < numTemplates; i++)
{
bg = templates[i].bg;
if (bg < 4) {
if (bg < NUM_BACKGROUNDS) {
SetBgControlAttributes(bg,
templates[i].charBaseIndex,
templates[i].mapBaseIndex,
Expand All @@ -386,7 +387,7 @@ void InitBgsFromTemplates(u8 bgMode, const struct BgTemplate *templates, u8 numT
sGpuBgConfigs2[bg].bg_x = 0;
sGpuBgConfigs2[bg].bg_y = 0;

gpu_tile_allocation_map_bg[(templates[i].charBaseIndex * (BG_CHAR_SIZE / TILE_SIZE_4BPP)) / 8] = 1;
gpu_tile_allocation_map_bg[(templates[i].charBaseIndex * (BG_CHAR_SIZE / TILE_SIZE_4BPP)) / BITS_PER_BYTE] = 1;
}
}
}
Expand All @@ -395,7 +396,7 @@ void InitBgFromTemplate(const struct BgTemplate *template)
{
u8 bg = template->bg;

if (bg < 4)
if (bg < NUM_BACKGROUNDS)
{
SetBgControlAttributes(bg,
template->charBaseIndex,
Expand All @@ -414,7 +415,7 @@ void InitBgFromTemplate(const struct BgTemplate *template)
sGpuBgConfigs2[bg].bg_x = 0;
sGpuBgConfigs2[bg].bg_y = 0;

gpu_tile_allocation_map_bg[(template->charBaseIndex * (BG_CHAR_SIZE / TILE_SIZE_4BPP)) / 8] = 1;
gpu_tile_allocation_map_bg[(template->charBaseIndex * (BG_CHAR_SIZE / TILE_SIZE_4BPP)) / BITS_PER_BYTE] = 1;
}
}

Expand All @@ -425,11 +426,11 @@ u16 LoadBgTiles(u8 bg, const void *src, u16 size, u16 destOffset)

if (GetBgControlAttribute(bg, BG_CTRL_ATTR_PALETTEMODE) == 0)
{
tileOffset = (sGpuBgConfigs2[bg].baseTile + destOffset) * 0x20;
tileOffset = (sGpuBgConfigs2[bg].baseTile + destOffset) * TILE_SIZE_4BPP;
}
else
{
tileOffset = (sGpuBgConfigs2[bg].baseTile + destOffset) * 0x40;
tileOffset = (sGpuBgConfigs2[bg].baseTile + destOffset) * TILE_SIZE_8BPP;
}

cursor = LoadBgVram(bg, src, size, tileOffset, DISPCNT_MODE_1);
Expand All @@ -439,7 +440,7 @@ u16 LoadBgTiles(u8 bg, const void *src, u16 size, u16 destOffset)
return -1;
}

sDmaBusyBitfield[cursor / 0x20] |= (1 << (cursor % 0x20));
sDmaBusyBitfield[cursor / (MAX_DMA_REQUESTS / ARRAY_COUNT(sDmaBusyBitfield))] |= (1 << (cursor % (MAX_DMA_REQUESTS / ARRAY_COUNT(sDmaBusyBitfield))));

if (gWindowTileAutoAllocEnabled == TRUE)
{
Expand All @@ -460,7 +461,7 @@ u16 LoadBgTilemap(u8 bg, const void *src, u16 size, u16 destOffset)
return -1;
}

sDmaBusyBitfield[cursor / 0x20] |= (1 << (cursor % 0x20));
sDmaBusyBitfield[cursor / (MAX_DMA_REQUESTS / ARRAY_COUNT(sDmaBusyBitfield))] |= (1 << (cursor % (MAX_DMA_REQUESTS / ARRAY_COUNT(sDmaBusyBitfield))));

return cursor;
}
Expand All @@ -485,7 +486,7 @@ u16 Unused_LoadBgPalette(u8 bg, const void *src, u16 size, u16 destOffset)
return -1;
}

sDmaBusyBitfield[cursor / 0x20] |= (1 << (cursor % 0x20));
sDmaBusyBitfield[cursor / (s8)(MAX_DMA_REQUESTS / ARRAY_COUNT(sDmaBusyBitfield))] |= (1 << (cursor % (s8)(MAX_DMA_REQUESTS / ARRAY_COUNT(sDmaBusyBitfield))));

return (u8)cursor;
}
Expand All @@ -494,10 +495,10 @@ bool8 IsDma3ManagerBusyWithBgCopy(void)
{
int i;

for (i = 0; i < 0x80; i++)
for (i = 0; i < MAX_DMA_REQUESTS; i++)
{
u8 div = i / 0x20;
u8 mod = i % 0x20;
u8 div = i / (int)(MAX_DMA_REQUESTS / ARRAY_COUNT(sDmaBusyBitfield));
u8 mod = i % (int)(MAX_DMA_REQUESTS / ARRAY_COUNT(sDmaBusyBitfield));

if ((sDmaBusyBitfield[div] & (1 << mod)))
{
Expand Down Expand Up @@ -526,25 +527,25 @@ void SetBgAttribute(u8 bg, u8 attributeId, u8 value)
{
switch (attributeId)
{
case 1:
case BG_ATTR_CHARBASEINDEX:
SetBgControlAttributes(bg, value, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF);
break;
case 2:
case BG_ATTR_MAPBASEINDEX:
SetBgControlAttributes(bg, 0xFF, value, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF);
break;
case 3:
case BG_ATTR_SCREENSIZE:
SetBgControlAttributes(bg, 0xFF, 0xFF, value, 0xFF, 0xFF, 0xFF, 0xFF);
break;
case 4:
case BG_ATTR_PALETTEMODE:
SetBgControlAttributes(bg, 0xFF, 0xFF, 0xFF, value, 0xFF, 0xFF, 0xFF);
break;
case 7:
case BG_ATTR_PRIORITY:
SetBgControlAttributes(bg, 0xFF, 0xFF, 0xFF, 0xFF, value, 0xFF, 0xFF);
break;
case 5:
case BG_ATTR_MOSAIC:
SetBgControlAttributes(bg, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, value, 0xFF);
break;
case 6:
case BG_ATTR_WRAPAROUND:
SetBgControlAttributes(bg, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, value);
break;
}
Expand Down
14 changes: 6 additions & 8 deletions src/dma3_manager.c
Original file line number Diff line number Diff line change
@@ -1,15 +1,13 @@
#include "global.h"
#include "dma3.h"

#define MAX_DMA_REQUESTS 128

static struct {
/* 0x00 */ const u8 *src;
/* 0x04 */ u8 *dest;
/* 0x08 */ u16 size;
/* 0x0A */ u16 mode;
/* 0x0C */ u32 value;
} gDma3Requests[128];
} gDma3Requests[MAX_DMA_REQUESTS];

static volatile bool8 gDma3ManagerLocked;
static u8 gDma3RequestCursor;
Expand Down Expand Up @@ -111,11 +109,11 @@ s16 RequestDma3Copy(const void *src, void *dest, u16 size, u8 mode)
gDma3ManagerLocked = FALSE;
return (s16)cursor;
}
if(++cursor >= 0x80) // loop back to start.
if(++cursor >= MAX_DMA_REQUESTS) // loop back to start.
{
cursor = 0;
}
if(++var >= 0x80) // max checks were made. all resulted in failure.
if(++var >= MAX_DMA_REQUESTS) // max checks were made. all resulted in failure.
{
break;
}
Expand Down Expand Up @@ -149,11 +147,11 @@ s16 RequestDma3Fill(s32 value, void *dest, u16 size, u8 mode)
gDma3ManagerLocked = FALSE;
return (s16)cursor;
}
if(++cursor >= 0x80) // loop back to start.
if(++cursor >= MAX_DMA_REQUESTS) // loop back to start.
{
cursor = 0;
}
if(++var >= 0x80) // max checks were made. all resulted in failure.
if(++var >= MAX_DMA_REQUESTS) // max checks were made. all resulted in failure.
{
break;
}
Expand All @@ -168,7 +166,7 @@ s16 WaitDma3Request(s16 index)

if (index == -1)
{
for (; current < 0x80; current ++)
for (; current < MAX_DMA_REQUESTS; current ++)
if (gDma3Requests[current].size)
return -1;

Expand Down
10 changes: 5 additions & 5 deletions src/help_message.c
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ void DrawHelpMessageWindowTilesById(u8 windowId)
width = (u8)GetWindowAttribute(windowId, WINDOW_WIDTH);
height = (u8)GetWindowAttribute(windowId, WINDOW_HEIGHT);

buffer = (u8 *)Alloc(32 * width * height);
buffer = (u8 *)Alloc(TILE_SIZE_4BPP * width * height);

if (buffer != NULL)
{
Expand All @@ -74,13 +74,13 @@ void DrawHelpMessageWindowTilesById(u8 windowId)
else // Middle row
tileId = 5;
CpuCopy32(
&ptr[tileId * 32],
&buffer[(i * width + j) * 32],
32
&ptr[tileId * TILE_SIZE_4BPP],
&buffer[(i * width + j) * TILE_SIZE_4BPP],
TILE_SIZE_4BPP
);
}
}
CopyToWindowPixelBuffer(windowId, buffer, width * height * 32, 0);
CopyToWindowPixelBuffer(windowId, buffer, width * height * TILE_SIZE_4BPP, 0);
Free(buffer);
}
}
Expand Down
Loading

0 comments on commit 2e2e879

Please sign in to comment.