mirror of https://github.com/mgba-emu/mgba.git
GB: Start MBCs
This commit is contained in:
parent
7c989fd818
commit
b711432a5e
24
src/gb/gb.h
24
src/gb/gb.h
|
@ -52,6 +52,30 @@ struct GB {
|
|||
const char* activeFile;
|
||||
};
|
||||
|
||||
struct GBCartridge {
|
||||
uint8_t entry[4];
|
||||
uint8_t logo[48];
|
||||
union {
|
||||
char titleLong[16];
|
||||
struct {
|
||||
char titleShort[11];
|
||||
char maker[4];
|
||||
uint8_t cgb;
|
||||
};
|
||||
};
|
||||
char licensee[2];
|
||||
uint8_t sgb;
|
||||
uint8_t type;
|
||||
uint8_t romSize;
|
||||
uint8_t ramSize;
|
||||
uint8_t region;
|
||||
uint8_t oldLicensee;
|
||||
uint8_t version;
|
||||
uint8_t headerChecksum;
|
||||
uint16_t globalChecksum;
|
||||
// And ROM data...
|
||||
};
|
||||
|
||||
void GBCreate(struct GB* gb);
|
||||
void GBDestroy(struct GB* gb);
|
||||
|
||||
|
|
125
src/gb/memory.c
125
src/gb/memory.c
|
@ -10,6 +10,19 @@
|
|||
|
||||
#include "util/memory.h"
|
||||
|
||||
static void _GBMBCNone(struct GBMemory* memory, uint16_t address, uint8_t value) {
|
||||
// TODO: Log game error
|
||||
UNUSED(memory);
|
||||
UNUSED(address);
|
||||
UNUSED(value);
|
||||
}
|
||||
|
||||
static void _GBMBC1(struct GBMemory*, uint16_t address, uint8_t value);
|
||||
static void _GBMBC2(struct GBMemory*, uint16_t address, uint8_t value);
|
||||
static void _GBMBC3(struct GBMemory*, uint16_t address, uint8_t value);
|
||||
static void _GBMBC4(struct GBMemory*, uint16_t address, uint8_t value);
|
||||
static void _GBMBC5(struct GBMemory*, uint16_t address, uint8_t value);
|
||||
|
||||
static void GBSetActiveRegion(struct LR35902Core* cpu, uint16_t address) {
|
||||
// TODO
|
||||
}
|
||||
|
@ -27,6 +40,8 @@ void GBMemoryInit(struct GB* gb) {
|
|||
gb->memory.rom = 0;
|
||||
gb->memory.romBank = 0;
|
||||
gb->memory.romSize = 0;
|
||||
gb->memory.mbcType = GB_MBC_NONE;
|
||||
gb->memory.mbc = 0;
|
||||
|
||||
memset(gb->memory.hram, 0, sizeof(gb->memory.hram));
|
||||
|
||||
|
@ -48,6 +63,52 @@ void GBMemoryReset(struct GB* gb) {
|
|||
gb->memory.wramBank = &gb->memory.wram[GB_SIZE_WORKING_RAM_BANK0];
|
||||
gb->memory.romBank = &gb->memory.rom[GB_SIZE_CART_BANK0];
|
||||
|
||||
const struct GBCartridge* cart = &gb->memory.rom[0x100];
|
||||
switch (cart->type) {
|
||||
case 0:
|
||||
case 8:
|
||||
case 9:
|
||||
gb->memory.mbc = _GBMBCNone;
|
||||
gb->memory.mbcType = GB_MBC_NONE;
|
||||
break;
|
||||
case 1:
|
||||
case 2:
|
||||
case 3:
|
||||
gb->memory.mbc = _GBMBC1;
|
||||
gb->memory.mbcType = GB_MBC1;
|
||||
break;
|
||||
case 5:
|
||||
case 6:
|
||||
gb->memory.mbc = _GBMBC2;
|
||||
gb->memory.mbcType = GB_MBC2;
|
||||
break;
|
||||
case 0x0F:
|
||||
case 0x10:
|
||||
case 0x11:
|
||||
case 0x12:
|
||||
case 0x13:
|
||||
gb->memory.mbc = _GBMBC3;
|
||||
gb->memory.mbcType = GB_MBC3;
|
||||
break;
|
||||
case 0x15:
|
||||
case 0x16:
|
||||
case 0x17:
|
||||
gb->memory.mbc = _GBMBC4;
|
||||
gb->memory.mbcType = GB_MBC4;
|
||||
break;
|
||||
default:
|
||||
// TODO: Log
|
||||
case 0x19:
|
||||
case 0x1A:
|
||||
case 0x1B:
|
||||
case 0x1C:
|
||||
case 0x1D:
|
||||
case 0x1E:
|
||||
gb->memory.mbc = _GBMBC5;
|
||||
gb->memory.mbcType = GB_MBC5;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!gb->memory.wram) {
|
||||
GBMemoryDeinit(gb);
|
||||
}
|
||||
|
@ -114,13 +175,11 @@ void GBStore8(struct LR35902Core* cpu, uint16_t address, int8_t value) {
|
|||
case GB_REGION_CART_BANK0 + 1:
|
||||
case GB_REGION_CART_BANK0 + 2:
|
||||
case GB_REGION_CART_BANK0 + 3:
|
||||
// TODO
|
||||
return;
|
||||
case GB_REGION_CART_BANK1:
|
||||
case GB_REGION_CART_BANK1 + 1:
|
||||
case GB_REGION_CART_BANK1 + 2:
|
||||
case GB_REGION_CART_BANK1 + 3:
|
||||
// TODO
|
||||
memory->mbc(memory, address, value);
|
||||
return;
|
||||
case GB_REGION_VRAM:
|
||||
case GB_REGION_VRAM + 1:
|
||||
|
@ -157,3 +216,63 @@ uint8_t GBView8(struct LR35902Core* cpu, uint16_t address);
|
|||
|
||||
void GBPatch16(struct LR35902Core* cpu, uint16_t address, int16_t value, int16_t* old);
|
||||
void GBPatch8(struct LR35902Core* cpu, uint16_t address, int8_t value, int8_t* old);
|
||||
|
||||
static void _switchBank(struct GBMemory* memory, int bank) {
|
||||
size_t bankStart = bank * GB_SIZE_CART_BANK0;
|
||||
if (bankStart + GB_SIZE_CART_BANK0 > memory->romSize) {
|
||||
// TODO: Log
|
||||
return;
|
||||
}
|
||||
memory->romBank = &memory->rom[bankStart];
|
||||
memory->currentBank = bank;
|
||||
}
|
||||
|
||||
void _GBMBC1(struct GBMemory* memory, uint16_t address, uint8_t value) {
|
||||
int bank = value & 0x1F;
|
||||
switch (address >> 13) {
|
||||
case 0x0:
|
||||
// TODO
|
||||
break;
|
||||
case 0x1:
|
||||
if (!bank) {
|
||||
++bank;
|
||||
}
|
||||
_switchBank(memory, bank | (memory->currentBank & 0x60));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void _GBMBC2(struct GBMemory* memory, uint16_t address, uint8_t value) {
|
||||
// TODO
|
||||
}
|
||||
|
||||
void _GBMBC3(struct GBMemory* memory, uint16_t address, uint8_t value) {
|
||||
int bank = value & 0x7F;
|
||||
switch (address >> 13) {
|
||||
case 0x0:
|
||||
// TODO
|
||||
break;
|
||||
case 0x1:
|
||||
if (!bank) {
|
||||
++bank;
|
||||
}
|
||||
_switchBank(memory, bank);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void _GBMBC4(struct GBMemory* memory, uint16_t address, uint8_t value) {
|
||||
// TODO
|
||||
}
|
||||
|
||||
void _GBMBC5(struct GBMemory* memory, uint16_t address, uint8_t value) {
|
||||
int bank = value & 0x7F;
|
||||
switch (address >> 13) {
|
||||
case 0x0:
|
||||
// TODO
|
||||
break;
|
||||
case 0x1:
|
||||
_switchBank(memory, bank);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -47,9 +47,26 @@ enum {
|
|||
GB_SIZE_HRAM = 0x7F,
|
||||
};
|
||||
|
||||
enum GBMemoryBankControllerType {
|
||||
GB_MBC_NONE = 0,
|
||||
GB_MBC1 = 1,
|
||||
GB_MBC2 = 2,
|
||||
GB_MBC3 = 3,
|
||||
GB_MBC4 = 4,
|
||||
GB_MBC5 = 5,
|
||||
GB_MMM01 = 0x10,
|
||||
GB_HuC1 = 0x11
|
||||
};
|
||||
|
||||
struct GBMemory;
|
||||
typedef void (*GBMemoryBankController)(struct GBMemory*, uint16_t address, uint8_t value);
|
||||
|
||||
struct GBMemory {
|
||||
uint8_t* rom;
|
||||
uint8_t* romBank;
|
||||
enum GBMemoryBankControllerType mbcType;
|
||||
GBMemoryBankController mbc;
|
||||
int currentBank;
|
||||
|
||||
uint8_t* wram;
|
||||
uint8_t* wramBank;
|
||||
|
|
Loading…
Reference in New Issue