/* * dma.c * this program demonstrates DMA on the GBA */ /* the number of times to transfer the eagle */ #define TIMES 100 /* the width and height of the screen */ #define WIDTH 240 #define HEIGHT 160 /* include the actual image file data */ #include "image.h" /* the screen is simply a pointer into memory at a specific address this * * pointer points to 16-bit colors of which there are 240x160 */ volatile unsigned short* screen = (volatile unsigned short*) 0x6000000; /* the display control pointer points to the gba graphics register */ volatile unsigned long* display_control = (volatile unsigned long*) 0x4000000; /* these identifiers define different bit positions of the display control */ #define MODE3 0x0003 #define BG2 0x0400 /* copy data with a loop */ void memcpy16(unsigned short* dest, unsigned short* source, int amount) { for (int i = 0; i < amount; i++) { dest[i] = source[i]; } } /* pointer to the DMA source location */ volatile unsigned int* dma_source = (volatile unsigned int*) 0x40000D4; /* pointer to the DMA destination location */ volatile unsigned int* dma_destination = (volatile unsigned int*) 0x40000D8; /* pointer to the DMA count/control */ volatile unsigned int* dma_count = (volatile unsigned int*) 0x40000DC; /* flag for turning on DMA */ #define DMA_ENABLE 0x80000000 /* flags for the sizes to transfer, 16 or 32 bits */ #define DMA_16 0x00000000 #define DMA_32 0x04000000 /* copy data using DMA */ void memcpy16_dma(unsigned short* dest, unsigned short* source, int amount) { *dma_source = (unsigned int) source; *dma_destination = (unsigned int) dest; *dma_count = amount | DMA_16 | DMA_ENABLE; } /* the main function */ int main() { /* we set the mode to mode 3 with bg2 on */ *display_control = MODE3 | BG2; /* transfer with a loop */ //for (int t = 0; t < TIMES; t++) { //memcpy16((unsigned short*) screen, (unsigned short*) image_data, WIDTH * HEIGHT); //} /* transfer with DMA */ for (int t = 0; t < TIMES; t++) { memcpy16_dma((unsigned short*) screen, (unsigned short*) image_data, WIDTH * HEIGHT); } /* set the screen to black, so we know when it's done */ for (int r = 0; r < HEIGHT; r++) { for (int c = 0; c < WIDTH; c++) { screen[r * WIDTH + c] = 0; } } /* we now loop forever displaying the image */ while (1) { /* do nothing */ } }