cscg22-gearboy

CSCG 2022 Challenge 'Gearboy'
git clone https://git.sinitax.com/sinitax/cscg22-gearboy
Log | Files | Refs | sfeed.txt

hardware.h (16358B)


      1/** @file gb/hardware.h
      2    Defines that let the GB's hardware registers be accessed
      3    from C.
      4
      5    See the @ref Pandocs for more details on each register.
      6*/
      7#ifndef _HARDWARE_H
      8#define _HARDWARE_H
      9
     10#include <types.h>
     11
     12#define __BYTES extern UBYTE
     13#define __BYTE_REG extern volatile UBYTE
     14#define __REG extern volatile SFR
     15
     16/** Memoty map */
     17
     18__BYTES _VRAM[];
     19__BYTES _VRAM8000[];
     20__BYTES _VRAM8800[];
     21__BYTES _VRAM9000[];
     22__BYTES _SCRN0[];
     23__BYTES _SCRN1[];
     24__BYTES _SRAM[];
     25__BYTES _RAM[];
     26__BYTES _RAMBANK[];
     27__BYTES _OAMRAM[];
     28__BYTE_REG _IO[];
     29__BYTE_REG _AUD3WAVERAM[];
     30__BYTE_REG _HRAM[];
     31
     32/** MBC5 registers */
     33
     34__BYTE_REG rRAMG;
     35__BYTE_REG rROMB0;
     36__BYTE_REG rROMB1;
     37__BYTE_REG rRAMB;
     38
     39/** IO Registers */
     40
     41__REG P1_REG;           /**< Joystick: 1.1.P15.P14.P13.P12.P11.P10 */
     42#define rP1 P1_REG
     43
     44#define P1F_5 0b00100000
     45#define P1F_4 0b00010000
     46#define P1F_3 0b00001000
     47#define P1F_2 0b00000100
     48#define P1F_1 0b00000010
     49#define P1F_0 0b00000001
     50
     51#define P1F_GET_DPAD P1F_5
     52#define P1F_GET_BTN  P1F_4
     53#define P1F_GET_NONE (P1F_4 | P1F_5)
     54
     55__REG SB_REG;           /**< Serial IO data buffer */
     56#define rSB SB_REG
     57__REG SC_REG;           /**< Serial IO control register */
     58#define rSC SC_REG
     59__REG DIV_REG;          /**< Divider register */
     60#define rDIV DIV_REG
     61__REG TIMA_REG;         /**< Timer counter */
     62#define rTIMA TIMA_REG
     63__REG TMA_REG;          /**< Timer modulo */
     64#define rTMA TMA_REG
     65__REG TAC_REG;          /**< Timer control */
     66#define rTAC TAC_REG
     67
     68#define TACF_START  0b00000100
     69#define TACF_STOP   0b00000000
     70#define TACF_4KHZ   0b00000000
     71#define TACF_16KHZ  0b00000011
     72#define TACF_65KHZ  0b00000010
     73#define TACF_262KHZ 0b00000001
     74
     75#define SIOF_CLOCK_EXT  0b00000000 /**< Serial IO: Use External clock */
     76#define SIOF_CLOCK_INT  0b00000001 /**< Serial IO: Use Internal clock */
     77#define SIOF_SPEED_1X   0b00000000 /**< Serial IO: If internal clock then 8KHz mode, 1KB/s (16Khz in CGB high-speed mode, 2KB/s) */
     78#define SIOF_SPEED_32X  0b00000010 /**< Serial IO: **CGB-Mode ONLY** If internal clock then 256KHz mode, 32KB/s (512KHz in CGB high-speed mode, 64KB/s) */
     79#define SIOF_XFER_START 0b10000000 /**< Serial IO: Start Transfer. Automatically cleared at the end of transfer */
     80#define SIOF_B_CLOCK      0
     81#define SIOF_B_SPEED      1
     82#define SIOF_B_XFER_START 7
     83
     84__REG IF_REG;           /**< Interrupt flags: 0.0.0.JOY.SIO.TIM.LCD.VBL */
     85#define rIF IF_REG
     86
     87__REG NR10_REG;         /**< Sound Channel 1 Sweep */
     88#define rAUD1SWEEP NR10_REG
     89#define AUD1SWEEP_UP        0b00000000
     90#define AUD1SWEEP_DOWN      0b00001000
     91#define AUD1SWEEP_TIME(x)   ((x) << 4)
     92#define AUD1SWEEP_LENGTH(x) (x)
     93__REG NR11_REG;         /**< Sound Channel 1 Sound length/Wave pattern duty */
     94#define rAUD1LEN NR11_REG
     95__REG NR12_REG;         /**< Sound Channel 1 Volume Envelope */
     96#define rAUD1ENV NR12_REG
     97__REG NR13_REG;         /**< Sound Channel 1 Frequency Low */
     98#define rAUD1LOW NR13_REG
     99__REG NR14_REG;         /**< Sound Channel 1 Frequency High */
    100#define rAUD1HIGH NR14_REG
    101
    102__REG NR21_REG;         /**< Sound Channel 2 Tone */
    103#define rAUD2LEN NR21_REG
    104__REG NR22_REG;         /**< Sound Channel 2 Volume Envelope */
    105#define rAUD2ENV NR22_REG
    106__REG NR23_REG;         /**< Sound Channel 2 Frequency data Low */
    107#define rAUD2LOW NR23_REG
    108__REG NR24_REG;         /**< Sound Channel 2 Frequency data High */
    109#define rAUD2HIGH NR24_REG
    110
    111__REG NR30_REG;         /**< Sound Channel 3 Sound on/off */
    112#define rAUD3ENA NR30_REG
    113__REG NR31_REG;         /**< Sound Channel 3 Sound Length */
    114#define rAUD3LEN NR31_REG
    115__REG NR32_REG;         /**< Sound Channel 3 Select output level */
    116#define rAUD3LEVEL NR32_REG
    117__REG NR33_REG;         /**< Sound Channel 3 Frequency data Low */
    118#define rAUD3LOW NR33_REG
    119__REG NR34_REG;         /**< Sound Channel 3 Frequency data High */
    120#define rAUD3HIGH NR34_REG
    121
    122__REG NR41_REG;         /**< Sound Channel 4 Sound Length */
    123#define rAUD4LEN NR41_REG
    124__REG NR42_REG;         /**< Sound Channel 4 Volume Envelope */
    125#define rAUD4ENV NR42_REG
    126__REG NR43_REG;         /**< Sound Channel 4 Polynomial Counter */
    127#define rAUD4POLY NR43_REG
    128#define AUD4POLY_WIDTH_15BIT 0x00
    129#define AUD4POLY_WIDTH_7BIT  0x08
    130__REG NR44_REG;         /**< Sound Channel 4 Counter / Consecutive and Inital  */
    131#define rAUD4GO NR44_REG
    132
    133__REG NR50_REG;         /**< Sound Channel control / ON-OFF / Volume */
    134#define rAUDVOL NR50_REG
    135
    136#define AUDVOL_VOL_LEFT(x)  ((x) << 4)
    137#define AUDVOL_VOL_RIGHT(x) ((x))
    138#define AUDVOL_VIN_LEFT         0b10000000
    139#define AUDVOL_VIN_RIGHT        0b00001000
    140
    141__REG NR51_REG;         /**< Sound Selection of Sound output terminal */
    142#define rAUDTERM NR51_REG
    143
    144#define AUDTERM_4_LEFT  0b10000000
    145#define AUDTERM_3_LEFT  0b01000000
    146#define AUDTERM_2_LEFT  0b00100000
    147#define AUDTERM_1_LEFT  0b00010000
    148#define AUDTERM_4_RIGHT 0b00001000
    149#define AUDTERM_3_RIGHT 0b00000100
    150#define AUDTERM_2_RIGHT 0b00000010
    151#define AUDTERM_1_RIGHT 0b00000001
    152
    153__REG NR52_REG;         /**< Sound Master on/off */
    154#define rAUDENA NR52_REG
    155
    156#define AUDENA_ON    0b10000000
    157#define AUDENA_OFF   0b00000000
    158
    159__BYTE_REG AUD3WAVE[16];
    160__BYTE_REG PCM_SAMPLE[16];
    161
    162__REG LCDC_REG;         /**< LCD control */
    163#define rLCDC LCDC_REG
    164
    165#if defined(__TARGET_ap)
    166#define LCDCF_OFF       0b00000000
    167#define LCDCF_ON        0b00000001
    168#define LCDCF_WIN9800   0b00000000
    169#define LCDCF_WIN9C00   0b00000010
    170#define LCDCF_WINOFF    0b00000000
    171#define LCDCF_WINON     0b00000100
    172#define LCDCF_BG8800    0b00000000
    173#define LCDCF_BG8000    0b00001000
    174#define LCDCF_BG9800    0b00000000
    175#define LCDCF_BG9C00    0b00010000
    176#define LCDCF_OBJ8      0b00000000
    177#define LCDCF_OBJ16     0b00100000
    178#define LCDCF_OBJOFF    0b00000000
    179#define LCDCF_OBJON     0b01000000
    180#define LCDCF_BGOFF     0b00000000
    181#define LCDCF_BGON      0b10000000
    182#define LCDCF_B_ON      0
    183#define LCDCF_B_WIN9C00 1
    184#define LCDCF_B_WINON   2
    185#define LCDCF_B_BG8000  3
    186#define LCDCF_B_BG9C00  4
    187#define LCDCF_B_OBJ16   5
    188#define LCDCF_B_OBJON   6
    189#define LCDCF_B_BGON    7
    190#elif defined(__TARGET_duck)
    191#define LCDCF_OFF       0b00000000
    192#define LCDCF_ON        0b10000000
    193#define LCDCF_WIN9800   0b00000000
    194#define LCDCF_WIN9C00   0b00001000
    195#define LCDCF_WINOFF    0b00000000
    196#define LCDCF_WINON     0b00100000
    197#define LCDCF_BG8800    0b00000000
    198#define LCDCF_BG8000    0b00010000
    199#define LCDCF_BG9800    0b00000000
    200#define LCDCF_BG9C00    0b00000100
    201#define LCDCF_OBJ8      0b00000000
    202#define LCDCF_OBJ16     0b00000010
    203#define LCDCF_OBJOFF    0b00000000
    204#define LCDCF_OBJON     0b00000001
    205#define LCDCF_BGOFF     0b00000000
    206#define LCDCF_BGON      0b01000000
    207#define LCDCF_B_ON      7
    208#define LCDCF_B_WIN9C00 3
    209#define LCDCF_B_WINON   5
    210#define LCDCF_B_BG8000  4
    211#define LCDCF_B_BG9C00  2
    212#define LCDCF_B_OBJ16   1
    213#define LCDCF_B_OBJON   0
    214#define LCDCF_B_BGON    6
    215#else
    216#define LCDCF_OFF       0b00000000 /**< LCD Control: Off */
    217#define LCDCF_ON        0b10000000 /**< LCD Control: On */
    218#define LCDCF_WIN9800   0b00000000 /**< Window Tile Map: Use 9800 Region */
    219#define LCDCF_WIN9C00   0b01000000 /**< Window Tile Map: Use 9C00 Region */
    220#define LCDCF_WINOFF    0b00000000 /**< Window Display: Hidden */
    221#define LCDCF_WINON     0b00100000 /**< Window Display: Visible */
    222#define LCDCF_BG8800    0b00000000 /**< BG & Window Tile Data: Use 8800 Region */
    223#define LCDCF_BG8000    0b00010000 /**< BG & Window Tile Data: Use 8000 Region */
    224#define LCDCF_BG9800    0b00000000 /**< BG Tile Map: use 9800 Region */
    225#define LCDCF_BG9C00    0b00001000 /**< BG Tile Map: use 9C00 Region */
    226#define LCDCF_OBJ8      0b00000000 /**< Sprites Size: 8x8 pixels */
    227#define LCDCF_OBJ16     0b00000100 /**< Sprites Size: 8x16 pixels */
    228#define LCDCF_OBJOFF    0b00000000 /**< Sprites Display: Hidden */
    229#define LCDCF_OBJON     0b00000010 /**< Sprites Display: Visible */
    230#define LCDCF_BGOFF     0b00000000 /**< Background Display: Hidden */
    231#define LCDCF_BGON      0b00000001 /**< Background Display: Visible */
    232#define LCDCF_B_ON      7          /**< Bit for LCD On/Off Select */
    233#define LCDCF_B_WIN9C00 6          /**< Bit for Window Tile Map Region Select */
    234#define LCDCF_B_WINON   5          /**< Bit for Window Display On/Off Control */
    235#define LCDCF_B_BG8000  4          /**< Bit for BG & Window Tile Data Region Select */
    236#define LCDCF_B_BG9C00  3          /**< Bit for BG Tile Map Region Select */
    237#define LCDCF_B_OBJ16   2          /**< Bit for Sprites Size Select */
    238#define LCDCF_B_OBJON   1          /**< Bit for Sprites Display Visible/Hidden Select */
    239#define LCDCF_B_BGON    0          /**< Bit for Background Display Visible/Hidden Select */
    240#endif
    241
    242__REG STAT_REG;         /**< LCD status */
    243#define rSTAT STAT_REG
    244
    245#if defined(__TARGET_ap)
    246#define STATF_LYC       0b00000010
    247#define STATF_MODE10    0b00000100
    248#define STATF_MODE01    0b00001000
    249#define STATF_MODE00    0b00010000
    250#define STATF_LYCF      0b00100000
    251#define STATF_HBL       0b00000000
    252#define STATF_VBL       0b10000000
    253#define STATF_OAM       0b01000000
    254#define STATF_LCD       0b11000000
    255#define STATF_BUSY      0b01000000
    256#define STATF_B_LYC     1
    257#define STATF_B_MODE10  2
    258#define STATF_B_MODE01  3
    259#define STATF_B_MODE00  4
    260#define STATF_B_LYCF    5
    261#define STATF_B_VBL     7
    262#define STATF_B_OAM     6
    263#define STATF_B_BUSY    6
    264#else
    265#define STATF_LYC     0b01000000  /**< STAT Interrupt: LYC=LY Coincidence Source Enable */
    266#define STATF_MODE10  0b00100000  /**< STAT Interrupt: Mode 2 OAM Source Enable */
    267#define STATF_MODE01  0b00010000  /**< STAT Interrupt: Mode 1 VBlank Source Enable */
    268#define STATF_MODE00  0b00001000  /**< STAT Interrupt: Mode 0 HBlank Source Enable  */
    269#define STATF_LYCF    0b00000100  /**< LYC=LY Coincidence Status Flag, Set when LY contains the same value as LYC */
    270#define STATF_HBL     0b00000000  /**< Current LCD Mode is: 0, in H-Blank */
    271#define STATF_VBL     0b00000001  /**< Current LCD Mode is: 1, in V-Blank */
    272#define STATF_OAM     0b00000010  /**< Current LCD Mode is: 2, in OAM-RAM is used by system (Searching OAM) */
    273#define STATF_LCD     0b00000011  /**< Current LCD Mode is: 3, both OAM and VRAM used by system (Transferring Data to LCD Controller) */
    274#define STATF_BUSY    0b00000010  /**< When set, VRAM access is unsafe */
    275#define STATF_B_LYC     6         /**< Bit for STAT Interrupt: LYC=LY Coincidence Source Enable */
    276#define STATF_B_MODE10  5         /**< Bit for STAT Interrupt: Mode 2 OAM Source Enable */
    277#define STATF_B_MODE01  4         /**< Bit for STAT Interrupt: Mode 1 VBlank Source Enable */
    278#define STATF_B_MODE00  3         /**< Bit for STAT Interrupt: Mode 0 HBlank Source Enable  */
    279#define STATF_B_LYCF    2         /**< Bit for LYC=LY Coincidence Status Flag */
    280#define STATF_B_VBL     0         /**< */
    281#define STATF_B_OAM     1         /**< */
    282#define STATF_B_BUSY    1         /**< Bit for when VRAM access is unsafe */
    283#endif
    284
    285__REG SCY_REG;          /**< Scroll Y */
    286#define rSCY
    287__REG SCX_REG;          /**< Scroll X */
    288#define rSCX SCX_REG
    289__REG LY_REG;           /**< LCDC Y-coordinate */
    290#define rLY LY_REG
    291__REG LYC_REG;          /**< LY compare */
    292#define rLYC LYC_REG
    293__REG DMA_REG;          /**< DMA transfer */
    294#define rDMA DMA_REG
    295__REG BGP_REG;          /**< BG palette data */
    296#define rBGP BGP_REG
    297__REG OBP0_REG;         /**< OBJ palette 0 data */
    298#define rOBP0 OBP0_REG
    299__REG OBP1_REG;         /**< OBJ palette 1 data */
    300#define rOBP1 OBP1_REG
    301__REG WY_REG;           /**< Window Y coordinate */
    302#define rWY WY_REG
    303__REG WX_REG;           /**< Window X coordinate */
    304#define rWX WX_REG
    305__REG KEY1_REG;         /**< CPU speed */
    306#define rKEY1 KEY1_REG
    307#define rSPD  KEY1_REG
    308
    309#define KEY1F_DBLSPEED 0b10000000
    310#define KEY1F_PREPARE  0b00000001
    311
    312__REG VBK_REG;          /**< VRAM bank select */
    313#define rVBK VBK_REG
    314__REG HDMA1_REG;        /**< DMA control 1 */
    315#define rHDMA1 HDMA1_REG
    316__REG HDMA2_REG;        /**< DMA control 2 */
    317#define rHDMA2 HDMA2_REG
    318__REG HDMA3_REG;        /**< DMA control 3 */
    319#define rHDMA3 HDMA3_REG
    320__REG HDMA4_REG;        /**< DMA control 4 */
    321#define rHDMA4 HDMA4_REG
    322__REG HDMA5_REG;        /**< DMA control 5 */
    323#define rHDMA5 HDMA5_REG
    324
    325#define HDMA5F_MODE_GP  0b00000000
    326#define HDMA5F_MODE_HBL 0b10000000
    327
    328#define HDMA5F_BUSY 0b10000000
    329
    330__REG RP_REG;           /**< IR port */
    331#define rRP RP_REG
    332
    333#define RPF_ENREAD   0b11000000
    334#define RPF_DATAIN   0b00000010
    335#define RPF_WRITE_HI 0b00000001
    336#define RPF_WRITE_LO 0b00000000
    337
    338__REG BCPS_REG;         /**< BG color palette specification */
    339#define rBCPS BCPS_REG
    340
    341#define BCPSF_AUTOINC 0b10000000
    342__REG BCPD_REG;         /**< BG color palette data */
    343#define rBCPD BCPD_REG
    344__REG OCPS_REG;         /**< OBJ color palette specification */
    345#define rOCPS OCPS_REG
    346
    347#define OCPSF_AUTOINC 0b10000000
    348__REG OCPD_REG;         /**< OBJ color palette data */
    349#define rOCPD OCPD_REG
    350__REG SVBK_REG;         /**< WRAM bank */
    351#define rSVBK SVBK_REG
    352#define rSMBK SVBK_REG
    353
    354__REG PCM12_REG;        /**< Sound channel 1&2 PCM amplitude (R) */
    355#define rPCM12 PCM12_REG
    356
    357__REG PCM34_REG;        /**< Sound channel 3&4 PCM amplitude (R) */
    358#define rPCM34 PCM34_REG
    359
    360__REG IE_REG;           /**< Interrupt enable */
    361#define rIE IE_REG
    362
    363#define IEF_HILO   0b00010000
    364#define IEF_SERIAL 0b00001000
    365#define IEF_TIMER  0b00000100
    366#define IEF_STAT   0b00000010
    367#define IEF_VBLANK 0b00000001
    368
    369
    370/* Square wave duty cycle */
    371#define AUDLEN_DUTY_12_5 0b00000000
    372#define AUDLEN_DUTY_25   0b01000000
    373#define AUDLEN_DUTY_50   0b10000000
    374#define AUDLEN_DUTY_75   0b11000000
    375#define AUDLEN_LENGTH(x) (x)
    376
    377/* Audio envelope flags */
    378#define AUDENV_VOL(x)    ((x) << 4)
    379#define AUDENV_UP        0b00001000
    380#define AUDENV_DOWN      0b00000000
    381#define AUDENV_LENGTH(x) (x)
    382
    383/* Audio trigger flags */
    384#define AUDHIGH_RESTART    0b10000000
    385#define AUDHIGH_LENGTH_ON  0b01000000
    386#define AUDHIGH_LENGTH_OFF 0b00000000
    387
    388/* OAM attributes flags */
    389#define OAMF_PRI      0b10000000  /**< BG and Window over Sprite Enabled */
    390#define OAMF_YFLIP    0b01000000  /**< Sprite Y axis flip: Vertically mirrored */
    391#define OAMF_XFLIP    0b00100000  /**< Sprite X axis flip: Horizontally mirrored */
    392#define OAMF_PAL0     0b00000000  /**< Sprite Palette number: use OBP0 (Non-CGB Mode Only) */
    393#define OAMF_PAL1     0b00010000  /**< Sprite Palette number: use OBP1 (Non-CGB Mode Only) */
    394#define OAMF_BANK0    0b00000000  /**< Sprite Tile VRAM-Bank: Use Bank 0 (CGB Mode Only) */
    395#define OAMF_BANK1    0b00001000  /**< Sprite Tile VRAM-Bank: Use Bank 1 (CGB Mode Only) */
    396
    397#define OAMF_CGB_PAL0 0b00000000  /**< Sprite CGB Palette number: use OCP0 (CGB Mode Only) */
    398#define OAMF_CGB_PAL1 0b00000001  /**< Sprite CGB Palette number: use OCP1 (CGB Mode Only) */
    399#define OAMF_CGB_PAL2 0b00000010  /**< Sprite CGB Palette number: use OCP2 (CGB Mode Only) */
    400#define OAMF_CGB_PAL3 0b00000011  /**< Sprite CGB Palette number: use OCP3 (CGB Mode Only) */
    401#define OAMF_CGB_PAL4 0b00000100  /**< Sprite CGB Palette number: use OCP4 (CGB Mode Only) */
    402#define OAMF_CGB_PAL5 0b00000101  /**< Sprite CGB Palette number: use OCP5 (CGB Mode Only) */
    403#define OAMF_CGB_PAL6 0b00000110  /**< Sprite CGB Palette number: use OCP6 (CGB Mode Only) */
    404#define OAMF_CGB_PAL7 0b00000111  /**< Sprite CGB Palette number: use OCP7 (CGB Mode Only) */
    405
    406#define OAMF_PALMASK 0b00000111   /**< Mask for Sprite CGB Palette number (CGB Mode Only) */
    407
    408#define DEVICE_SCREEN_X_OFFSET 0        /**< Offset of visible screen (in tile units) from left edge of hardware map */
    409#define DEVICE_SCREEN_Y_OFFSET 0        /**< Offset of visible screen (in tile units) from top edge of hardware map */
    410#define DEVICE_SCREEN_WIDTH 20          /**< Width of visible screen in tile units */
    411#define DEVICE_SCREEN_HEIGHT 18         /**< Height of visible screen in tile units */
    412#define DEVICE_SCREEN_BUFFER_WIDTH 32   /**< Width of hardware map buffer in tile units */
    413#define DEVICE_SCREEN_BUFFER_HEIGHT 32  /**< Height of hardware map buffer in tile units */
    414#define DEVICE_SCREEN_MAP_ENTRY_SIZE 1  /**< Number of bytes per hardware map entry */
    415#define DEVICE_SPRITE_PX_OFFSET_X 8     /**< Offset of sprite X coordinate origin (in pixels) from left edge of visible screen */
    416#define DEVICE_SPRITE_PX_OFFSET_Y 16    /**< Offset of sprite Y coordinate origin (in pixels) from top edge of visible screen */
    417#define DEVICE_SCREEN_PX_WIDTH (DEVICE_SCREEN_WIDTH * 8)   /**< Width of visible screen in pixels */
    418#define DEVICE_SCREEN_PX_HEIGHT (DEVICE_SCREEN_HEIGHT * 8) /**< Height of visible screen in pixels */
    419
    420#endif