Skip to content

SpencerCDixon/SpenceBoy

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

SpenceBoy - A GameBoy Emulator

This project is a GameBoy emulator. The primary objective is for educational purposes. No external dependencies are allowed other than SDL2 and the C standard library.

Getting Started

There are a number of Scripts which can be used as an example for how to run the emulator. To get bootstrapped quickly try running:

$ ./Scripts/bootstrap.sh
$ ./Scripts/run.sh

Roadmap

Emulator

  • Get a GameBoy "development environment" (meaning a GameBoy assembler and disassembler)
  • Write a test program in GameBoy assembly that loops 3 times and then halts execution
  • Build a simple CPU instruction interpreter that can read instructions from a stream of bytes and call an appropriate handler for each instruction (no need to implement all instructions yet!)
  • Get your program from (1) to run in the interpreter from (2), printing out the state of the CPU at every step of execution
  • Add RAM (really just a byte buffer) to your CPU and implement instructions for moving memory in/out of RAM
  • Figure out how the GameBoy ROM file format works, and parse_rom a ROM into your emulator's memory at startup
  • Build a simple PPU renderer that looks at all the PPU state in the emulator and renders the "screen" into an SDL window
  • Stack push/pop
  • Call/return from ASM 'functions'
  • Implement the GameBoy buttons (D-pad, A, B, Select and Start). Listening for SDL keyboard events and update the appropriate memory location in the Emulator to reflect the button states. Then write a GB program that requires you to input a specific button sequence.
  • Write a program that fills the screen with a striped pattern.
  • Add a GUI window that displays the button states (or perhaps: add a togglable button state overlay to the game window)
  • Write a program that scrolls the background layer using the SCX and SCY registers.
  • Write a program that puts a sprite on screen and animates its movement
  • Add a GUI window that displays the contents of tile memory rendered as a tile map. This will give you fast visual clues later if/when something goes wrong in emulation.
  • Add a GUI window that displays outlines of all the moving surfaces (without content, i.e a "wireframe" view) so you can see how things move around separately from the main emulator screen.
  • Proper boot up sequence
  • Load one of the older ROMs into your emulator (something like Tetris, Tennis or Super Mario Land) and see if you can get it to render the title screen.
  • Interrupts
  • Sprite OAM procedure
  • All unprefixed raw op codes
  • All prefixed cb opcodes
  • Render title properly
  • Be able to set window title based on title in ROM
  • Proper 'halt' which can unhalt if an interrupt occurs and continues to execute instructions

Game Targets

  • Super Mario Land
  • Tetris
  • Snake
  • Pokemon Red

Chores

  • Get CMake script for SDL working on Linux
  • Get CMake script for SDL working on Windows
  • Get Clang Tidy set up
  • Set up UBSan to ensure no UB is leaking into the codebase

Op Codes

  • ADC_A_A (0x8F)
  • ADC_A_B (0x88)
  • ADC_A_C (0x89)
  • ADC_A_D (0x8A)
  • ADC_A_E (0x8B)
  • ADC_A_H (0x8C)
  • ADC_A_HL_ADDR (0x8E)
  • ADC_A_L (0x8D)
  • ADC_A_d8 (0xCE)
  • ADD_A_A (0x87)
  • ADD_A_B (0x80)
  • ADD_A_C (0x81)
  • ADD_A_D (0x82)
  • ADD_A_E (0x83)
  • ADD_A_H (0x84)
  • ADD_A_HL_ADDR (0x86)
  • ADD_A_L (0x85)
  • ADD_A_d8 (0xC6)
  • ADD_HL_BC (0x09)
  • ADD_HL_DE (0x19)
  • ADD_HL_HL (0x29)
  • ADD_HL_SP (0x39)
  • ADD_SP_r8 (0xE8)
  • AND_A (0xA7)
  • AND_B (0xA0)
  • AND_C (0xA1)
  • AND_D (0xA2)
  • AND_E (0xA3)
  • AND_H (0xA4)
  • AND_HL_ADDR (0xA6)
  • AND_L (0xA5)
  • AND_d8 (0xE6)
  • CALL_C_a16 (0xDC)
  • CALL_NC_a16 (0xD4)
  • CALL_NZ_a16 (0xC4)
  • CALL_Z_a16 (0xCC)
  • CALL_a16 (0xCD)
  • CCF (0x3F)
  • CPL (0x2F)
  • CP_A (0xBF)
  • CP_B (0xB8)
  • CP_C (0xB9)
  • CP_D (0xBA)
  • CP_E (0xBB)
  • CP_H (0xBC)
  • CP_HL_ADDR (0xBE)
  • CP_L (0xBD)
  • CP_d8 (0xFE)
  • DAA (0x27)
  • DEC_A (0x3D)
  • DEC_B (0x05)
  • DEC_BC (0x0B)
  • DEC_C (0x0D)
  • DEC_D (0x15)
  • DEC_DE (0x1B)
  • DEC_E (0x1D)
  • DEC_H (0x25)
  • DEC_HL (0x2B)
  • DEC_HL_ADDR (0x35)
  • DEC_L (0x2D)
  • DEC_SP (0x3B)
  • DI (0xF3)
  • EI (0xFB)
  • HALT (0x76)
  • ILLEGAL_D3 (0xD3)
  • ILLEGAL_E3 (0xE3)
  • ILLEGAL_E4 (0xE4)
  • ILLEGAL_EB (0xEB)
  • ILLEGAL_EC (0xEC)
  • ILLEGAL_ED (0xED)
  • ILLEGAL_F4 (0xF4)
  • ILLEGAL_FC (0xFC)
  • ILLEGAL_FD (0xFD)
  • INC_A (0x3C)
  • INC_B (0x04)
  • INC_BC (0x03)
  • INC_C (0x0C)
  • INC_D (0x14)
  • INC_DE (0x13)
  • INC_E (0x1C)
  • INC_H (0x24)
  • INC_HL (0x23)
  • INC_HL_ADDR (0x34)
  • INC_L (0x2C)
  • INC_SP (0x33)
  • JP_C_a16 (0xDA)
  • JP_HL (0xE9)
  • JP_NC_a16 (0xD2)
  • JP_NZ_a16 (0xC2)
  • JP_Z_a16 (0xCA)
  • JP_a16 (0xC3)
  • JR_C_r8 (0x38)
  • JR_NC_r8 (0x30)
  • JR_NZ_r8 (0x20)
  • JR_Z_r8 (0x28)
  • JR_r8 (0x18)
  • LDH_A_a8_ADDR (0xF0)
  • LDH_a8_ADDR_A (0xE0)
  • LD_A_A (0x7F)
  • LD_A_B (0x78)
  • LD_A_BC_ADDR (0x0A)
  • LD_A_C (0x79)
  • LD_A_C_ADDR (0xF2)
  • LD_A_D (0x7A)
  • LD_A_DE_ADDR (0x1A)
  • LD_A_E (0x7B)
  • LD_A_H (0x7C)
  • LD_A_HL_ADDR (0x7E)
  • LD_A_HL_ADDR_DEC (0x3A)
  • LD_A_HL_ADDR_INC (0x2A)
  • LD_A_L (0x7D)
  • LD_A_a16_ADDR (0xFA)
  • LD_A_d8 (0x3E)
  • LD_BC_ADDR_A (0x02)
  • LD_BC_d16 (0x01)
  • LD_B_A (0x47)
  • LD_B_B (0x40)
  • LD_B_C (0x41)
  • LD_B_D (0x42)
  • LD_B_E (0x43)
  • LD_B_H (0x44)
  • LD_B_HL_ADDR (0x46)
  • LD_B_L (0x45)
  • LD_B_d8 (0x06)
  • LD_C_A (0x4F)
  • LD_C_ADDR_A (0xE2)
  • LD_C_B (0x48)
  • LD_C_C (0x49)
  • LD_C_D (0x4A)
  • LD_C_E (0x4B)
  • LD_C_H (0x4C)
  • LD_C_HL_ADDR (0x4E)
  • LD_C_L (0x4D)
  • LD_C_d8 (0x0E)
  • LD_DE_ADDR_A (0x12)
  • LD_DE_d16 (0x11)
  • LD_D_A (0x57)
  • LD_D_B (0x50)
  • LD_D_C (0x51)
  • LD_D_D (0x52)
  • LD_D_E (0x53)
  • LD_D_H (0x54)
  • LD_D_HL_ADDR (0x56)
  • LD_D_L (0x55)
  • LD_D_d8 (0x16)
  • LD_E_A (0x5F)
  • LD_E_B (0x58)
  • LD_E_C (0x59)
  • LD_E_D (0x5A)
  • LD_E_E (0x5B)
  • LD_E_H (0x5C)
  • LD_E_HL_ADDR (0x5E)
  • LD_E_L (0x5D)
  • LD_E_d8 (0x1E)
  • LD_HL_ADDR_A (0x77)
  • LD_HL_ADDR_B (0x70)
  • LD_HL_ADDR_C (0x71)
  • LD_HL_ADDR_D (0x72)
  • LD_HL_ADDR_DEC_A (0x32)
  • LD_HL_ADDR_E (0x73)
  • LD_HL_ADDR_H (0x74)
  • LD_HL_ADDR_INC_A (0x22)
  • LD_HL_ADDR_L (0x75)
  • LD_HL_ADDR_d8 (0x36)
  • LD_HL_SP_INC (0xF8)
  • LD_HL_d16 (0x21)
  • LD_H_A (0x67)
  • LD_H_B (0x60)
  • LD_H_C (0x61)
  • LD_H_D (0x62)
  • LD_H_E (0x63)
  • LD_H_H (0x64)
  • LD_H_HL_ADDR (0x66)
  • LD_H_L (0x65)
  • LD_H_d8 (0x26)
  • LD_L_A (0x6F)
  • LD_L_B (0x68)
  • LD_L_C (0x69)
  • LD_L_D (0x6A)
  • LD_L_E (0x6B)
  • LD_L_H (0x6C)
  • LD_L_HL_ADDR (0x6E)
  • LD_L_L (0x6D)
  • LD_L_d8 (0x2E)
  • LD_SP_HL (0xF9)
  • LD_SP_d16 (0x31)
  • LD_a16_ADDR_A (0xEA)
  • LD_a16_ADDR_SP (0x08)
  • NOP (0x00)
  • OR_A (0xB7)
  • OR_B (0xB0)
  • OR_C (0xB1)
  • OR_D (0xB2)
  • OR_E (0xB3)
  • OR_H (0xB4)
  • OR_HL_ADDR (0xB6)
  • OR_L (0xB5)
  • OR_d8 (0xF6)
  • POP_AF (0xF1)
  • POP_BC (0xC1)
  • POP_DE (0xD1)
  • POP_HL (0xE1)
  • PREFIX (0xCB)
  • PUSH_AF (0xF5)
  • PUSH_BC (0xC5)
  • PUSH_DE (0xD5)
  • PUSH_HL (0xE5)
  • RET (0xC9)
  • RETI (0xD9)
  • RET_C (0xD8)
  • RET_NC (0xD0)
  • RET_NZ (0xC0)
  • RET_Z (0xC8)
  • RLA (0x17)
  • RLCA (0x07)
  • RRA (0x1F)
  • RRCA (0x0F)
  • RST_00H (0xC7)
  • RST_08H (0xCF)
  • RST_10H (0xD7)
  • RST_18H (0xDF)
  • RST_20H (0xE7)
  • RST_28H (0xEF)
  • RST_30H (0xF7)
  • RST_38H (0xFF)
  • SBC_A_A (0x9F)
  • SBC_A_B (0x98)
  • SBC_A_C (0x99)
  • SBC_A_D (0x9A)
  • SBC_A_E (0x9B)
  • SBC_A_H (0x9C)
  • SBC_A_HL_ADDR (0x9E)
  • SBC_A_L (0x9D)
  • SBC_A_d8 (0xDE)
  • SCF (0x37)
  • STOP (0x10)
  • SUB_A (0x97)
  • SUB_B (0x90)
  • SUB_C (0x91)
  • SUB_D (0x92)
  • SUB_E (0x93)
  • SUB_H (0x94)
  • SUB_HL_ADDR (0x96)
  • SUB_L (0x95)
  • SUB_d8 (0xD6)
  • XOR_A (0xAF)
  • XOR_B (0xA8)
  • XOR_C (0xA9)
  • XOR_D (0xAA)
  • XOR_E (0xAB)
  • XOR_H (0xAC)
  • XOR_HL_ADDR (0xAE)
  • XOR_L (0xAD)
  • XOR_d8 (0xEE)

About

A gameboy emulator for educational purposes

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published