__attribute__((section(".mapper_001_0"), hot)) static uint8_t mapper_001_0_prg_read(struct nes_state *state, uint32_t addr) { struct mapper_001_0 *mapper = (struct mapper_001_0 *)&state->map; if(addr >= 0x8000) { if(addr < 0xc000) { return mapper->prg_rom_0[addr & 0x3fff]; } else { return mapper->prg_rom_1[addr & 0x3fff]; } } return 0; } __attribute__((section(".mapper_001_0"), hot)) static void mapper_001_0_prg_write(struct nes_state *state, uint32_t addr, uint8_t value) { struct mapper_001_0 *mapper = (struct mapper_001_0 *)&state->map; if(addr < 0x8000) return; if(value & 0x80) { mapper->shift = 0; mapper->shift_count = 0; mapper->control |= 0x0c; return; } mapper->shift |= (value & 1) << mapper->shift_count; mapper->shift_count++; if(mapper->shift_count == 5) { uint32_t bank; uint8_t reg = (addr >> 13) & 0x03; switch(reg) { case 0: {// Control mapper->control = mapper->shift; } break; case 1: { // CHR bank 0 mapper->chr_bank0 = mapper->shift; mapper->chr_bank_0 = state->chr_rom + (mapper->chr_bank0 * 0x1000); } break; case 2: { // CHR bank 1 mapper->chr_bank1 = mapper->shift; mapper->chr_bank_1 = state->chr_rom + (mapper->chr_bank1 * 0x1000); } break; case 3: { // PRG bank mapper->prg_bank = mapper->shift & 0x0f; if(mapper->control & 0x08) { // 16KB bank switching if(mapper->control & 0x04) { mapper->prg_rom_0 = state->prg_rom + 0x4000 * 0; mapper->prg_rom_1 = state->prg_rom + 0x4000 * mapper->prg_bank; } else { mapper->prg_rom_0 = state->prg_rom + 0x4000 * mapper->prg_bank; mapper->prg_rom_1 = state->prg_rom + 0x4000 * (state->ines.prg_size / 0x4000 - 1); } } else { // 32KB mode bank = (mapper->prg_bank & 0x0e) * 0x4000; mapper->prg_rom_0 = state->prg_rom + bank; mapper->prg_rom_1 = state->prg_rom + bank + 0x4000; } } break; } mapper->shift = 0; mapper->shift_count = 0; } } __attribute__((section(".mapper_001_0"), hot)) static uint8_t mapper_001_0_chr_read(struct nes_state *state, uint32_t addr) { struct mapper_001_0 *mapper = (struct mapper_001_0 *)&state->map; if(mapper->control & 0x10) { // 4KB mode if(addr < 0x1000) { return mapper->chr_bank_0[addr]; } else { return mapper->chr_bank_1[addr - 0x1000]; } } else { // 8KB mode return mapper->chr_bank_0[addr]; } } __attribute__((section(".mapper_001_0"), hot)) static void mapper_001_0_chr_write(struct nes_state *state, uint32_t addr, uint8_t value) { // CHR RAM write (if present) state->chr_ram[addr] = value; } __attribute__((section(".mapper_001_0"), hot)) static uint8_t mapper_001_0_ciram_read(struct nes_state *state, uint32_t addr) { return state->ciram[addr & 0x3ff]; } __attribute__((section(".mapper_001_0"), hot)) static void mapper_001_0_ciram_write(struct nes_state *state, uint32_t addr, uint8_t value) { state->ciram[addr & 0x3ff] = value; } __attribute__((section(".mapper_001_0"))) static void mapper_001_0_init(struct nes_state *state) { struct mapper_001_0 *mapper = (struct mapper_001_0 *)&state->map; mapper->control = 0x0c; mapper->prg_rom_0 = state->prg_rom; mapper->prg_rom_1 = state->prg_rom + (state->ines.prg_size - 0x4000); mapper->chr_bank_0 = state->chr_rom; mapper->chr_bank_1 = state->chr_rom + 0x1000; state->mapper.prg_read = mapper_001_0_prg_read; state->mapper.prg_write = mapper_001_0_prg_write; state->mapper.chr_read = mapper_001_0_chr_read; state->mapper.chr_write = mapper_001_0_chr_write; state->mapper.ciram_read = mapper_001_0_ciram_read; state->mapper.ciram_write = mapper_001_0_ciram_write; }