Saturday, July 16, 2011

A Simple Tutorial On Nintendo GBA Programming

This post is intended as a simple introduction to Nintendo GameBoy Advance Programming. The language used for this tutorial will be plain old ANSI C. Firstly , download the GBDK  , The HAM SDK or just the GNU GCC-ARM compiler (and compile from the command line yourself).

                                                              HARDWARE:
Unlike PC programming (in a fairly high-level language); programming for consoles and embedded systems requires a thorough knowledge of the underlying hardware, so here is a brief overview of the Hardware of the Nintendo GBA.

-> The GBA has a 32-bit 16.78 MHz ARM CPU (ARM7TDMI to be exact).
-> The GBA has 96 KB Video Memory.
-> The GBA has 256 KB external RAM
-> The GBA has 32 KB of internal RAM
-> The GBA has 6 VIDEO MODES. (for this tutorial we will be working with MODE 3)

                                               SETTING UP YOUR IMAGE.

For this turorial , we will blit a bitmap onto the screen.

->Firstly you will need to get a tool that converts Windows BMPs (or any image format) to C code (or ASM code). I reccommend Gfx2Gba which is a free tool available with the HAM SDK and can be also downloaded individually.

-> Make an image (or convert one) to a 16-color or 256-color Bitmap as Gfx2Gba only supports there formats. And resize it to 240x160 resolution .

-> Put the image in the same directory as your source code and use Gfx2Gba to convert it.
     Use the command:          gfx2gba   -fsrr  -c32k    yourimage.bmp

-> This will generate a C source file called "yourimage.raw.c" (here yourimage is assumed to be the name of your image).

                                                             CODE:

/* CODE BEGINS HERE  (main.c) */

/*Include the bitmap*/
#include "miata.raw.c"

/*Video Mode 3*/
#define MODE_3 0x3  

/*The Screen */
#define SCREEN_W 240  
#define SCREEN_H 160

/*Memory Register for Video Modes*/
#define REG_MODE *(unsigned long*) 0x4000000  

/*Setting the Mode*/
#define SET_MODE(mode) REG_MODE=mode

/*Enabling Background 4*/
#define BG2_ENABLE 0x400


unsigned short* VideoBuffer = (unsigned short*) 0x6000000 /*Address of Video Memory) NOTE: We treat this as an array when blitting */


/* The Blit Pixel function , sets the color of pixels on the
   screen */

void BlitPixel(int x, int y, unsigned short color)
{
    /*Pointer Arithmetic... (The greatness of C) */

    VideoBuffer[y*SCREEN_W+x] = color;
}

/* Now for the main function */

int main (void)                       /* No arguments...*/
{
    int X , Y;  /*Screen Co-ordinates*/
    
    SET_MODE(BG2_ENABLE|MODE_3);

    /*Move through the entire screen and copy the color
      of every pixel of miata.bmp to the corresponding 
      pixel on the screen... */

    for (Y=0; Y < SCREEN_H; Y++)
    { 
        for (X=0; X < SCREEN_W; X++)
              BlitPixel(X ,Y, miata_Bitmap[ Y * SCREEN_W + X]);
    }

    while (1) {}   /*Main Loop*/
    return 0;
}




I Understand That Console Programming Is Not For The Faint Of Heart. But if you give it a try you'll find it to be a lot of fun especially GBA. And you will find that the experience and knowledge you gained by programming for consoles was worth all the hard work. Also you don't need to code everything from scratch, there are many third-party libraries to make like easier. I recommend using the HAM Library , as it is free for both commercial and non-commercial uses , (see HAM License) and has a good design.