コード例 #1
0
void NES_mapper230::MemoryWrite(uint32 addr, uint8 data)
{
  if(rom_switch)
  {
    set_CPU_bank4((data & 0x07)*2+0);
    set_CPU_bank5((data & 0x07)*2+1);
  }
  else
  {
    if(data & 0x40)
    {
      set_mirroring(NES_PPU::MIRROR_VERT);
    }
    else
    {
      set_mirroring(NES_PPU::MIRROR_HORIZ);
    }
    if(data & 0x20)
    {
      set_CPU_bank4((data & 0x1F)*2+16);
      set_CPU_bank5((data & 0x1F)*2+17);
      set_CPU_bank6((data & 0x1F)*2+16);
      set_CPU_bank7((data & 0x1F)*2+17);
    }
    else
    {
      set_CPU_bank4((data & 0x1E)*2+16);
      set_CPU_bank5((data & 0x1E)*2+17);
      set_CPU_bank6((data & 0x1E)*2+18);
      set_CPU_bank7((data & 0x1E)*2+19);
    }
  }
}
コード例 #2
0
ファイル: multigam.c プロジェクト: stuartcarnie/MAME-OS-X
static WRITE8_HANDLER(multigm3_switch_gfx_rom)
{
	multigam_state *state = space->machine().driver_data<multigam_state>();
	set_videorom_bank(space->machine(), 0, 8, data & 0x3f, 8);
	set_mirroring(state, data & 0x40 ? PPU_MIRROR_HORZ : PPU_MIRROR_VERT);
	state->m_game_gfx_bank = data;
};
コード例 #3
0
ファイル: ppu.cpp プロジェクト: zoibot/knes
PPU::PPU(Machine *mach, wxWindow* wind) {
    this->mach = mach;
    this->wind = wind;
    screen.Create(256, 240);
    screen_data = screen.GetData();
    vaddr = 0;
    taddr = next_taddr = false;
    obj_addr = 0;
    mem = new byte[0x4000];
    obj_mem = new byte[0x100];
    cycle_count = 0;
    odd_frame = false;
    last_nmi = 0;
    vbl_off = 0;
    nmi_occurred = false;
    a12high = false;
    horiz_scroll = vert_scroll = false;
    sl = -2;
    cyc = 0;
    pmask = 0;
    pctrl = 0;
    pstat = 0;
    last_vblank_end = last_vblank_start = 0;
    memset(mem, 0xff, 0x4000);
    memset(obj_mem, 0xff, 0x100);
    mirror_table = new word[0x4000];
    for(int i = 0; i < 0x4000; i++)
        mirror_table[i] = i;
    set_mirror(0x3000, 0x2000, 0xf00);
    if(mach->rom->flags6 & 8) {
        cout << "4 screen!!!!" << endl;
    }
    current_mirroring = FOUR_SCREEN;
    set_mirroring(mach->rom->mirror);
}
コード例 #4
0
ファイル: multigam.c プロジェクト: stuartcarnie/MAME-OS-X
static WRITE8_HANDLER(multigam_switch_gfx_rom)
{
	multigam_state *state = space->machine().driver_data<multigam_state>();
	memory_set_bankptr(space->machine(), "bank1", space->machine().region("gfx1")->base() + (0x2000 * (data & 0x3f)));
	set_mirroring(state, data & 0x40 ? PPU_MIRROR_HORZ : PPU_MIRROR_VERT);
	state->m_game_gfx_bank = data;
};
コード例 #5
0
ファイル: mapper.cpp プロジェクト: AndreaOrru/LaiNES
Mapper::Mapper(u8* rom) : rom(rom)
{
    // Read infos from header:
    prgSize      = rom[4] * 0x4000;
    chrSize      = rom[5] * 0x2000;
    prgRamSize   = rom[8] ? rom[8] * 0x2000 : 0x2000;
    set_mirroring((rom[6] & 1) ? PPU::VERTICAL : PPU::HORIZONTAL);

    this->prg    = rom + 16;
    this->prgRam = new u8[prgRamSize];

    // CHR ROM:
    if (chrSize)
        this->chr = rom + 16 + prgSize;
    // CHR RAM:
    else
    {
        chrRam = true;
        chrSize = 0x2000;
        this->chr = new u8[chrSize];
    }
}
コード例 #6
0
void NES_mapper16::MemoryWrite2(uint32 addr, uint8 data)
{
  switch(addr & 0x000F)
  {
    case 0x0000:
      {
        set_PPU_bank0(data);
      }
      break;

    case 0x0001:
      {
        set_PPU_bank1(data);
      }
      break;

    case 0x0002:
      {
        set_PPU_bank2(data);
      }
      break;

    case 0x0003:
      {
        set_PPU_bank3(data);
      }
      break;

    case 0x0004:
      {
        set_PPU_bank4(data);
      }
      break;

    case 0x0005:
      {
        set_PPU_bank5(data);
      }
      break;

    case 0x0006:
      {
        set_PPU_bank6(data);
      }
      break;

    case 0x0007:
      {
        set_PPU_bank7(data);
      }
      break;

    case 0x0008:
      {
        set_CPU_bank4(data*2+0);
        set_CPU_bank5(data*2+1);
      }
      break;

    case 0x0009:
      {
        data &= 0x03;
        if(data == 0)
        {
          set_mirroring(NES_PPU::MIRROR_VERT);
        }
        else if(data == 1)
        {
          set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
        else if(data == 2)
        {
          set_mirroring(0,0,0,0);
        }
        else
        {
          set_mirroring(1,1,1,1);
        }
      }
      break;

    case 0x000A:
      {
        irq_enabled = data & 0x01;
        irq_counter = irq_latch;
      }
      break;

    case 0x000B:
      {
        irq_latch = (irq_latch & 0xFF00) | data;
      }
      break;

    case 0x000C:
      {
         irq_latch = ((uint32)data << 8) | (irq_latch & 0x00FF);
      }
      break;

    case 0x000D:
      {
        if(data == 0x80)
        {
          // reset
          eeprom_addr = 0x00;
          eeprom_mode = 0x00;
          eeprom_wbit = 0x00;
          eeprom_rbit = 0x00;
        }
        else if(eeprom_cmd[3] == 0x00 && eeprom_cmd[2] == 0x20 &&
                eeprom_cmd[1] == 0x60 && eeprom_cmd[0] == 0x40 && data == 0x00)
        {
          // reset ?
        }
        else if(eeprom_cmd[3] == 0x00 && eeprom_cmd[2] == 0x40 &&
                eeprom_cmd[1] == 0x60 && eeprom_cmd[0] == 0x20 && data == 0x00)
        {
          // start
          eeprom_wbit = 0x01;
          eeprom_rbit = 0x01;
          eeprom_data = 0;
          eeprom_mode = 0;
        }
        else if (eeprom_cmd[0] == 0x60 && data == 0xE0)
        {
          if(!eeprom_mode)
          {
            // sync
            eeprom_wbit = 0x01;
            eeprom_rbit = 0x01;
            eeprom_data = 0;
            eeprom_mode = 1;
            eeprom_status = 0x00;
            //memset(serial_out, eeprom_status | barcode_status, 0x2000);
            serial_out[0] = eeprom_status | barcode_status;
          }
          else
          {
            // read
            eeprom_data = parent_NES->ReadSaveRAM(eeprom_addr);
            if(eeprom_data & eeprom_rbit)
            {
              eeprom_status = 0x10;
              //memset(serial_out, eeprom_status | barcode_status, 0x2000);
              serial_out[0] = eeprom_status | barcode_status;
            }
            else
            {
              eeprom_status = 0x00;
              //memset(serial_out, eeprom_status | barcode_status, 0x2000);
              serial_out[0] = eeprom_status | barcode_status;
            }
            eeprom_rbit <<= 1;
            eeprom_wbit = 0x00;
          }
        }
        else if(eeprom_cmd[1] == 0x00 && eeprom_cmd[0] == 0x20 && data == 0x00)
        {
          // write 0
          eeprom_data &= 0xFF - eeprom_wbit;
          if(eeprom_wbit == 0x80)
          {
            if(eeprom_mode)
            {
              parent_NES->WriteSaveRAM(eeprom_addr, eeprom_data);
            }
            else
            {
              eeprom_addr = eeprom_data & 0x7F;
            }
            eeprom_wbit = 0x00;
          }
          else
          {
            eeprom_wbit <<= 1;
          }
          eeprom_rbit = 0x00;
        }
        else if(eeprom_cmd[3] == 0x00 && eeprom_cmd[2] == 0x40 &&
                eeprom_cmd[1] == 0x60 && eeprom_cmd[0] == 0x40 && data == 0x00)
        {
          // write 1
          eeprom_data |= eeprom_wbit;
          if(eeprom_wbit == 0x80)
          {
            if(eeprom_mode)
            {
              parent_NES->WriteSaveRAM(eeprom_addr, eeprom_data);
            }
            else
            {
              eeprom_addr = eeprom_data & 0x7F;
            }
            eeprom_wbit = 0x00;
          }
          else
          {
            eeprom_wbit <<= 1;
          }
          eeprom_rbit = 0x00;
        }
        eeprom_cmd[3] = eeprom_cmd[2];
        eeprom_cmd[2] = eeprom_cmd[1];
        eeprom_cmd[1] = eeprom_cmd[0];
        eeprom_cmd[0] = data;
      }
      break;
  }
}
コード例 #7
0
ファイル: multigam.c プロジェクト: stuartcarnie/MAME-OS-X
static WRITE8_HANDLER( multigam3_mmc3_rom_switch_w )
{
	multigam_state *state = space->machine().driver_data<multigam_state>();
	device_t *ppu = space->machine().device("ppu");

	/* basically, a MMC3 mapper from the nes */
	int bankmask = state->m_multigam3_mmc3_prg_size == 0x40000 ? 0x1f : 0x0f;

	switch(offset & 0x7001)
	{
		case 0x0000:
			state->m_multigam3_mmc3_command = data;

			if (state->m_multigam3_mmc3_last_bank != (data & 0xc0))
			{
				int bank;
				UINT8 *prg = space->machine().region("maincpu")->base();

				/* reset the banks */
				if (state->m_multigam3_mmc3_command & 0x40)
				{
					/* high bank */
					bank = (state->m_multigam3_mmc3_banks[0] & bankmask) * 0x2000;

					memcpy(&prg[0x0c000], &state->m_multigam3_mmc3_prg_base[bank], 0x2000);
					memcpy(&prg[0x08000], &state->m_multigam3_mmc3_prg_base[state->m_multigam3_mmc3_prg_size - 0x4000], 0x2000);
				}
				else
				{
					/* low bank */
					bank = (state->m_multigam3_mmc3_banks[0] & bankmask) * 0x2000;

					memcpy(&prg[0x08000], &state->m_multigam3_mmc3_prg_base[bank], 0x2000);
					memcpy(&prg[0x0c000], &state->m_multigam3_mmc3_prg_base[state->m_multigam3_mmc3_prg_size - 0x4000], 0x2000);
				}

				/* mid bank */
				bank = (state->m_multigam3_mmc3_banks[1] & bankmask) * 0x2000;
				memcpy(&prg[0x0a000], &state->m_multigam3_mmc3_prg_base[bank], 0x2000);

				state->m_multigam3_mmc3_last_bank = data & 0xc0;
			}
		break;

		case 0x0001:
			{
				UINT8 cmd = state->m_multigam3_mmc3_command & 0x07;
				int page = (state->m_multigam3_mmc3_command & 0x80) >> 5;
				int bank;

				switch (cmd)
				{
					case 0:	/* char banking */
					case 1: /* char banking */
						data &= 0xfe;
						page ^= (cmd << 1);
						set_videorom_bank(space->machine(), page, 2, state->m_multigam3_mmc3_chr_bank_base + data, 1);
					break;

					case 2: /* char banking */
					case 3: /* char banking */
					case 4: /* char banking */
					case 5: /* char banking */
						page ^= cmd + 2;
						set_videorom_bank(space->machine(), page, 1, state->m_multigam3_mmc3_chr_bank_base + data, 1);
					break;

					case 6: /* program banking */
					{
						UINT8 *prg = space->machine().region("maincpu")->base();
						if (state->m_multigam3_mmc3_command & 0x40)
						{
							/* high bank */
							state->m_multigam3_mmc3_banks[0] = data & bankmask;
							bank = (state->m_multigam3_mmc3_banks[0]) * 0x2000;

							memcpy(&prg[0x0c000], &state->m_multigam3_mmc3_prg_base[bank], 0x2000);
							memcpy(&prg[0x08000], &state->m_multigam3_mmc3_prg_base[state->m_multigam3_mmc3_prg_size - 0x4000], 0x2000);
						}
						else
						{
							/* low bank */
							state->m_multigam3_mmc3_banks[0] = data & bankmask;
							bank = (state->m_multigam3_mmc3_banks[0]) * 0x2000;

							memcpy(&prg[0x08000], &state->m_multigam3_mmc3_prg_base[bank], 0x2000);
							memcpy(&prg[0x0c000], &state->m_multigam3_mmc3_prg_base[state->m_multigam3_mmc3_prg_size - 0x4000], 0x2000);
						}
					}
					break;

					case 7: /* program banking */
						{
							/* mid bank */
							UINT8 *prg = space->machine().region("maincpu")->base();

							state->m_multigam3_mmc3_banks[1] = data & bankmask;
							bank = state->m_multigam3_mmc3_banks[1] * 0x2000;

							memcpy(&prg[0x0a000], &state->m_multigam3_mmc3_prg_base[bank], 0x2000);
						}
					break;
				}
			}
		break;

		case 0x2000: /* mirroring */
			if (!state->m_multigam3_mmc3_4screen)
			{
				if (data & 0x40)
					set_mirroring(state, PPU_MIRROR_HIGH);
				else
					set_mirroring(state, (data & 1) ? PPU_MIRROR_HORZ : PPU_MIRROR_VERT);
			}
		break;

		case 0x2001: /* enable ram at $6000 */
			if (data & 0x80)
			{
				memory_set_bankptr(space->machine(), "bank10", state->m_multigmc_mmc3_6000_ram);
			}
			else
			{
				memory_set_bankptr(space->machine(), "bank10", space->machine().region("maincpu")->base() + 0x6000);
			}
			if (data & 0x40)
			{
				logerror("Write protect for 6000 enabled\n");
			}
		break;

		case 0x4000: /* scanline counter */
			state->m_multigam3_mmc3_scanline_counter = data;
		break;

		case 0x4001: /* scanline latch */
			state->m_multigam3_mmc3_scanline_latch = data;
		break;

		case 0x6000: /* disable irqs */
			ppu2c0x_set_scanline_callback(ppu, 0);
		break;

		case 0x6001: /* enable irqs */
			ppu2c0x_set_scanline_callback(ppu, multigam3_mmc3_scanline_cb);
		break;
	}
}
コード例 #8
0
void NES_mapper17::MemoryWriteLow(uint32 addr, uint8 data)
{
  switch(addr)
  {
    case 0x42FE:
      {
        if((data & 0x10) == 0)
        {
          set_mirroring(0,0,0,0);
        }
        else
        {
          set_mirroring(1,1,1,1);
        }
      }
      break;

    case 0x42FF:
      {
        if((data & 0x10) == 0)
        {
          set_mirroring(NES_PPU::MIRROR_VERT);
        }
        else
        {
          set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
      }
      break;

    case 0x4501:
      {
        irq_enabled = 0;
      }
      break;

    case 0x4502:
      {
        irq_latch = (irq_latch & 0xFF00) | data;
      }
      break;

    case 0x4503:
      {
        irq_latch = (irq_latch & 0x00FF) | ((uint32)data << 8);
        irq_counter = irq_latch;
        irq_enabled = 1;
      }
      break;

    case 0x4504:
      {
        set_CPU_bank4(data);
      }
      break;

    case 0x4505:
      {
        set_CPU_bank5(data);
      }
      break;

    case 0x4506:
      {
        set_CPU_bank6(data);
      }
      break;

    case 0x4507:
      {
        set_CPU_bank7(data);
      }
      break;

    case 0x4510:
      {
        set_PPU_bank0(data);
      }
      break;

    case 0x4511:
      {
        set_PPU_bank1(data);
      }
      break;

    case 0x4512:
      {
        set_PPU_bank2(data);
      }
      break;

    case 0x4513:
      {
        set_PPU_bank3(data);
      }
      break;

    case 0x4514:
      {
        set_PPU_bank4(data);
      }
      break;

    case 0x4515:
      {
        set_PPU_bank5(data);
      }
      break;

    case 0x4516:
      {
        set_PPU_bank6(data);
      }
      break;

    case 0x4517:
      {
        set_PPU_bank7(data);
      }
      break;
  }
}
コード例 #9
0
void NES_mapper24::MemoryWrite(uint32 addr, uint8 data)
{
  switch(addr & 0xF003)
  {
    case 0x8000:
      {
        set_CPU_bank4(data*2+0);
        set_CPU_bank5(data*2+1);
      }
      break;

    //DCR
    case 0x9000:
    case 0x9001:
    case 0x9002:
    case 0xA000:
    case 0xA001:
    case 0xA002:
    case 0xB000:
    case 0xB001:
    case 0xB002:
      parent_NES->apu->Write(addr, data);
      break;

    case 0xB003:
      {
        data = data & 0x0C;
        if(data == 0x00)
        {
          set_mirroring(NES_PPU::MIRROR_VERT);
        }
        else if(data == 0x04)
        {
          set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
        else if(data == 0x08)
        {
          set_mirroring(0,0,0,0);
        }
        else if(data == 0x0C)
        {
          set_mirroring(1,1,1,1);
        }
      }
      break;

    case 0xC000:
      {
        set_CPU_bank6(data);
      }
      break;

    case 0xD000:
      {
        set_PPU_bank0(data);
      }
      break;

    case 0xD001:
      {
        set_PPU_bank1(data);
      }
      break;

    case 0xD002:
      {
        set_PPU_bank2(data);
      }
      break;

    case 0xD003:
      {
        set_PPU_bank3(data);
      }
      break;

    case 0xE000:
      {
        set_PPU_bank4(data);
      }
      break;

    case 0xE001:
      {
        set_PPU_bank5(data);
      }
      break;

    case 0xE002:
      {
        set_PPU_bank6(data);
      }
      break;

    case 0xE003:
      {
        set_PPU_bank7(data);
      }
      break;

    case 0xF000:
      {
        irq_latch = data;
      }
      break;

    case 0xF001:
      {
        irq_enabled = data & 0x03;
        if(irq_enabled & 0x02)
        {
          irq_counter = irq_latch;
        }
      }
      break;

    case 0xF002:
      {
        if(irq_enabled & 0x01)
        {
          irq_enabled |= 0x02;
        }
        else
        {
          irq_enabled &= 0x01;
        }
      }
      break;
  }
}
コード例 #10
0
static WRITE8_HANDLER(multigm3_switch_gfx_rom)
{
	set_videorom_bank(space->machine, 0, 8, data & 0x3f, 8);
	set_mirroring(data & 0x40 ? PPU_MIRROR_HORZ : PPU_MIRROR_VERT);
	multigam_game_gfx_bank = data;
};
コード例 #11
0
static WRITE8_HANDLER(multigam_switch_gfx_rom)
{
	memory_set_bankptr(space->machine, "bank1", space->machine->region("gfx1")->base() + (0x2000 * (data & 0x3f)));
	set_mirroring(data & 0x40 ? PPU_MIRROR_HORZ : PPU_MIRROR_VERT);
	multigam_game_gfx_bank = data;
};
コード例 #12
0
void NES_mapper69::MemoryWrite(uint32 addr, uint8 data)
{
  switch(addr & 0xE000)
  {
    case 0x8000:
      {
        regs[0] = data;
      }
      break;

    case 0xA000:
      {
        switch(regs[0] & 0x0F)
        {
          case 0x00:
            {
              set_PPU_bank0(data);
            }
            break;

          case 0x01:
            {
              set_PPU_bank1(data);
            }
            break;

          case 0x02:
            {
              set_PPU_bank2(data);
            }
            break;

          case 0x03:
            {
              set_PPU_bank3(data);
            }
            break;

          case 0x04:
            {
              set_PPU_bank4(data);
            }
            break;

          case 0x05:
            {
              set_PPU_bank5(data);
            }
            break;

          case 0x06:
            {
              set_PPU_bank6(data);
            }
            break;

          case 0x07:
            {
              set_PPU_bank7(data);
            }
            break;

          case 0x08:
            {
              if(!patch)
              {
                if(!(data & 0x40))
                {
                  set_CPU_bank3(data);
                }
              }
            }
            break;

          case 0x09:
            {
              set_CPU_bank4(data);
            }
            break;

          case 0x0A:
            {
              set_CPU_bank5(data);
            }
            break;

          case 0x0B:
            {
              set_CPU_bank6(data);
            }
            break;

          case 0x0C:
            {
              data &= 0x03;
              if(data == 0)
              {
                set_mirroring(NES_PPU::MIRROR_VERT);
              }
              else if(data == 1)
              {
                set_mirroring(NES_PPU::MIRROR_HORIZ);
              }
              else if(data == 2)
              {
                set_mirroring(0,0,0,0);
              }
              else
              {
                set_mirroring(1,1,1,1);
              }
            }
            break;

          case 0x0D:
            {
              irq_enabled = data;
            }
            break;

          case 0x0E:
            {
              irq_counter = (irq_counter & 0xFF00) | data;
            }
            break;

          case 0x0F:
            {
              irq_counter = (irq_counter & 0x00FF) | (data << 8);
            }
            break;
        }
      }
      break;

    case 0xC000:
    case 0xE000:
      {
        parent_NES->apu->ExWrite(addr, data);
      }
      break;
  }
}
コード例 #13
0
void NES_mapper1::MemoryWrite(uint32 addr, uint8 data)
{
  if(patch && addr == 0xBFFF)
  {
    wram_count++;
    wram_flag += data & 0x01;
    if(wram_count == 5)
    {
      if(wram_flag)
      {
        wram_bank = 1;
        (nes6502_get_current_context())->mem_page[3] = wram + 0x2000;
        nes6502_setcontext();
      }
      else
      {
        wram_bank = 0;
        (nes6502_get_current_context())->mem_page[3] = wram;
        nes6502_setcontext();
      }
      wram_flag = 0;
      wram_count = 0;
    }
  }

  uint32 reg_num;

  // if write is to a different reg, reset
  if((addr & 0x6000) != (last_write_addr & 0x6000))
  {
    write_count = 0;
    bits = 0x00;
  }
  last_write_addr = addr;

  // if bit 7 set, reset and return
  if(data & 0x80)
  {
    write_count = 0;
    bits = 0x00;
    return;
  }

  bits |= (data & 0x01) << write_count;
  if (++write_count < 5) return;
  
  reg_num = (addr & 0x7FFF) >> 13;
  regs[reg_num] = bits;

  write_count = 0;
  bits = 0x00;

//  LOG("MAP1 REG" << reg_num << ": " << HEX(regs[reg_num],2) << endl);

  switch(reg_num)
  {
    case 0:
      {
//        LOG("REG0: " << HEX(reg[0],2) << endl);

        // set mirroring
        if(regs[0] & 0x02)
        {
          if(regs[0] & 0x01)
          {
            set_mirroring(NES_PPU::MIRROR_HORIZ);
          }
          else
          {
            set_mirroring(NES_PPU::MIRROR_VERT);
          }
        }
        else
        {
          // one-screen mirroring
          if(regs[0] & 0x01)
          {
            set_mirroring(1,1,1,1);
          }
          else
          {
            set_mirroring(0,0,0,0);
          }
        }
      }
      break;

    case 1:
      {
        uint8 bank_num = regs[1];

//        LOG("REG1: " << HEX(reg[1],2) << endl);

        if(MMC1_Size == MMC1_1024K)
        {
          if(regs[0] & 0x10)
          {
            if(MMC1_swap)
            {
              MMC1_256K_base = (regs[1] & 0x10) >> 4;
              if(regs[0] & 0x08)
              {
                MMC1_256K_base |= ((regs[2] & 0x10) >> 3);
              }
              MMC1_set_CPU_banks();
              MMC1_swap = 0;
            }
            else
            {
              MMC1_swap = 1;
            }
          }
          else
          {
            // use 1st or 4th 256K banks
            MMC1_256K_base = (regs[1] & 0x10) ? 3 : 0;
            MMC1_set_CPU_banks();
          }
        }
コード例 #14
0
void NES_mapper20::MemoryWriteLow(uint32 addr, uint8 data)
{
  switch (addr)
  {
    case 0x4020:
      {
        irq_latch = (irq_latch & 0xFF00) | data;
      }
      break;

    case 0x4021:
      {
        irq_latch = (irq_latch & 0x00FF) | ((uint32)data << 8);
      }
      break;

    case 0x4022:
      {
        irq_counter = irq_latch;
        irq_enabled = data & 0x03;
      }
      break;

    case 0x4023:
      {
        disk_enabled = data & 0x01;
      }
      break;

    case 0x4024:
      {
        if((current_side != 0) && (current_side == last_side))
        {
          if(disk_enabled && !(write_reg & 0x04) && head_position < 65000)
          {
            if(write_skip)
            {
              write_skip--;
            }
            else if(head_position >= 2)
            {
              disk[(current_side-1)*0x10000+head_position-2] = data;
              access_flag = 1;
            }
          }
        }
      }
      break;

    case 0x4025:
      {
        if(data & 0x08)
        {
          set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
        else
        {
          set_mirroring(NES_PPU::MIRROR_VERT);
        }
        if((current_side != 0) && (current_side == last_side))
        {
          if((write_reg & 0x40) && !(data & 0x10) && !(data & 0x40))
          {
            head_position = (head_position < 2) ? 0 : head_position - 2;
          }
          if(!(data & 0x04))
          {
            write_skip = 2;
          }
          if(data & 0x02)
          {
            head_position = 0;
            irq_wait = 2;
          }
          if(data & 0x80)
          {
            irq_wait = 2;
          }
        }
        write_reg = data;
      }
      break;
      
    default:
      {
        parent_NES->apu->ExWrite(addr, data);
      }
      break;
  }
}
コード例 #15
0
void NES_mapper65::MemoryWrite(uint32 addr, uint8 data)
{
    switch(addr)
    {
    case 0x8000:
    {
        set_CPU_bank4(data);
    }
    break;

    case 0x9000:
    {
        if(!patch)
        {
            if(data & 0x40)
            {
                set_mirroring(NES_PPU::MIRROR_VERT);
            }
            else
            {
                set_mirroring(NES_PPU::MIRROR_HORIZ);
            }
        }
    }
    break;

    case 0x9001:
    {
        if(patch)
        {
            if(data & 0x80)
            {
                set_mirroring(NES_PPU::MIRROR_HORIZ);
            }
            else
            {
                set_mirroring(NES_PPU::MIRROR_VERT);
            }
        }
    }
    break;

    case 0x9003:
    {
        if(!patch)
        {
            irq_enabled = data & 0x80;
        }
    }
    break;

    case 0x9004:
    {
        if(!patch)
        {
            irq_counter = irq_latch;
        }
    }
    break;

    case 0x9005:
    {
        if(patch)
        {
            irq_counter = (uint8)(data << 1);
            irq_enabled = data;
        }
        else
        {
            irq_latch = (irq_latch & 0x00FF) | ((uint32)data << 8);
        }
    }
    break;

    case 0x9006:
    {
        if(patch)
        {
            irq_enabled = 1;
        }
        else
        {
            irq_latch = (irq_latch & 0xFF00) | data;
        }
    }
    break;

    case 0xB000:
    {
        set_PPU_bank0(data);
    }
    break;

    case 0xB001:
    {
        set_PPU_bank1(data);
    }
    break;

    case 0xB002:
    {
        set_PPU_bank2(data);
    }
    break;

    case 0xB003:
    {
        set_PPU_bank3(data);
    }
    break;

    case 0xB004:
    {
        set_PPU_bank4(data);
    }
    break;

    case 0xB005:
    {
        set_PPU_bank5(data);
    }
    break;

    case 0xB006:
    {
        set_PPU_bank6(data);
    }
    break;

    case 0xB007:
    {
        set_PPU_bank7(data);
    }
    break;

    case 0xA000:
    {
        set_CPU_bank5(data);
    }
    break;

    case 0xC000:
    {
        set_CPU_bank6(data);
    }
    break;
    }
}
コード例 #16
0
void NES_mapper21::MemoryWrite(uint32 addr, uint8 data)
{
    // regs[0] ... 1K VROM bank at PPU $0000
    // regs[1] ... 1K VROM bank at PPU $0400
    // regs[2] ... 1K VROM bank at PPU $0800
    // regs[3] ... 1K VROM bank at PPU $0C00
    // regs[4] ... 1K VROM bank at PPU $1000
    // regs[5] ... 1K VROM bank at PPU $1400
    // regs[6] ... 1K VROM bank at PPU $1800
    // regs[7] ... 1K VROM bank at PPU $1C00
    // regs[8] ... $8000 Switching Mode

    switch (addr & 0xF0CF)
    {
    case 0x8000:
    {
        if(regs[8] & 0x02)
        {
            set_CPU_bank6(data);
        }
        else
        {
            set_CPU_bank4(data);
        }
    }
    break;

    case 0xA000:
    {
        set_CPU_bank5(data);
    }
    break;

    case 0x9000:
    {
        data &= 0x03;
        if(data == 0)
        {
            set_mirroring(NES_PPU::MIRROR_VERT);
        }
        else if(data == 1)
        {
            set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
        else if(data == 2)
        {
            set_mirroring(0,0,0,0);
        }
        else
        {
            set_mirroring(1,1,1,1);
        }
    }
    break;

    case 0x9002:
    case 0x9080:
    {
        regs[8] = data;
    }
    break;

    case 0xB000:
    {
        regs[0] = (regs[0] & 0xF0) | (data & 0x0F);
        set_PPU_bank0(regs[0]);
    }
    break;

    case 0xB002:
    case 0xB040:
    {
        regs[0] = (regs[0] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank0(regs[0]);
    }
    break;

    case 0xB001:
    case 0xB004:
    case 0xB080:
    {
        regs[1] = (regs[1] & 0xF0) | (data & 0x0F);
        set_PPU_bank1(regs[1]);
    }
    break;

    case 0xB003:
    case 0xB006:
    case 0xB0C0:
    {
        regs[1] = (regs[1] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank1(regs[1]);
    }
    break;

    case 0xC000:
    {
        regs[2] = (regs[2] & 0xF0) | (data & 0x0F);
        set_PPU_bank2(regs[2]);
    }
    break;

    case 0xC002:
    case 0xC040:
    {
        regs[2] = (regs[2] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank2(regs[2]);
    }
    break;

    case 0xC001:
    case 0xC004:
    case 0xC080:
    {
        regs[3] = (regs[3] & 0xF0) | (data & 0x0F);
        set_PPU_bank3(regs[3]);
    }
    break;

    case 0xC003:
    case 0xC006:
    case 0xC0C0:
    {
        regs[3] = (regs[3] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank3(regs[3]);
    }
    break;

    case 0xD000:
    {
        regs[4] = (regs[4] & 0xF0) | (data & 0x0F);
        set_PPU_bank4(regs[4]);
    }
    break;

    case 0xD002:
    case 0xD040:
    {
        regs[4] = (regs[4] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank4(regs[4]);
    }
    break;

    case 0xD001:
    case 0xD004:
    case 0xD080:
    {
        regs[5] = (regs[5] & 0xF0) | (data & 0x0F);
        set_PPU_bank5(regs[5]);
    }
    break;

    case 0xD003:
    case 0xD006:
    case 0xD0C0:
    {
        regs[5] = (regs[5] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank5(regs[5]);
    }
    break;

    case 0xE000:
    {
        regs[6] = (regs[6] & 0xF0) | (data & 0x0F);
        set_PPU_bank6(regs[6]);
    }
    break;

    case 0xE002:
    case 0xE040:
    {
        regs[6] = (regs[6] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank6(regs[6]);
    }
    break;

    case 0xE001:
    case 0xE004:
    case 0xE080:
    {
        regs[7] = (regs[7] & 0xF0) | (data & 0x0F);
        set_PPU_bank7(regs[7]);
    }
    break;

    case 0xE003:
    case 0xE006:
    case 0xE0C0:
    {
        regs[7] = (regs[7] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank7(regs[7]);
    }
    break;

    case 0xF000:
    {
        irq_latch = (irq_latch & 0xF0) | (data & 0x0F);
    }
    break;

    case 0xF002:
    case 0xF040:
    {
        irq_latch = (irq_latch & 0x0F) | ((data & 0x0F) << 4);
    }
    break;

    case 0xF003:
    case 0xF0C0:
    {
        irq_enabled = (irq_enabled & 0x01) * 3;
    }
    break;

    case 0xF004:
    case 0xF080:
    {
        irq_enabled = data & 0x03;
        if(irq_enabled & 0x02)
        {
            irq_counter = irq_latch;
        }
    }
    break;
    }
}
コード例 #17
0
void NES_mapper64::MemoryWrite(uint32 addr, uint8 data)
{
    switch(addr & 0xF003)
    {
    case 0x8000:
    {
        regs[0] = data & 0x0F;
        regs[1] = data & 0x40;
        regs[2] = data & 0x80;
    }
    break;

    case 0x8001:
    {
        switch(regs[0])
        {
        case 0x00:
        {
            if(regs[2])
            {
                set_PPU_bank4(data+0);
                set_PPU_bank5(data+1);
            }
            else
            {
                set_PPU_bank0(data+0);
                set_PPU_bank1(data+1);
            }
        }
        break;

        case 0x01:
        {
            if(regs[2])
            {
                set_PPU_bank6(data+0);
                set_PPU_bank7(data+1);
            }
            else
            {
                set_PPU_bank2(data+0);
                set_PPU_bank3(data+1);
            }
        }
        break;

        case 0x02:
        {
            if(regs[2])
            {
                set_PPU_bank0(data);
            }
            else
            {
                set_PPU_bank4(data);
            }
        }
        break;

        case 0x03:
        {
            if(regs[2])
            {
                set_PPU_bank1(data);
            }
            else
            {
                set_PPU_bank5(data);
            }
        }
        break;

        case 0x04:
        {
            if(regs[2])
            {
                set_PPU_bank2(data);
            }
            else
            {
                set_PPU_bank6(data);
            }
        }
        break;

        case 0x05:
        {
            if(regs[2])
            {
                set_PPU_bank3(data);
            }
            else
            {
                set_PPU_bank7(data);
            }
        }
        break;

        case 0x06:
        {
            if(regs[1])
            {
                set_CPU_bank5(data);
            }
            else
            {
                set_CPU_bank4(data);
            }
        }
        break;

        case 0x07:
        {
            if(regs[1])
            {
                set_CPU_bank6(data);
            }
            else
            {
                set_CPU_bank5(data);
            }
        }
        break;

        case 0x08:
        {
            //if(regs[2])
            //{
            //  set_PPU_bank5(data);
            //}
            //else
            {
                set_PPU_bank1(data);
            }
        }
        break;

        case 0x09:
        {
            //if(regs[2])
            //{
            //  set_PPU_bank7(data);
            //}
            //else
            {
                set_PPU_bank3(data);
            }
        }
        break;

        case 0x0F:
        {
            if(regs[1])
            {
                set_CPU_bank4(data);
            }
            else
            {
                set_CPU_bank6(data);
            }
        }
        break;
        }
    }
    break;

    case 0xA000:
    {
        if(!(data & 0x01))
        {
            set_mirroring(NES_PPU::MIRROR_VERT);
        }
        else
        {
            set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
    }
    break;

    case 0xC000:
    {
        irq_latch = data;
        irq_counter = irq_latch;
    }
    break;

    case 0xC001:
    {
        irq_counter = irq_latch;
    }
    break;

    case 0xE000:
    {
        irq_enabled = 0;
        irq_counter = irq_latch;
    }
    break;

    case 0xE001:
    {
        irq_enabled = 1;
        irq_counter = irq_latch;
    }
    break;
    }
}
コード例 #18
0
void NES_mapper248::MemoryWrite(uint32 addr, uint8 data)
{
  switch(addr & 0xE001)
  {
    case 0x8000:
      {
        regs[0] = data;
        MMC3_set_PPU_banks();
        MMC3_set_CPU_banks();
      }
      break;

    case 0x8001:
      {
        uint32 bank_num;

        regs[1] = data;
        bank_num = regs[1];

        switch(regs[0] & 0x07)
        {
          case 0x00:
            {
              //if(num_1k_VROM_banks)
              {
                bank_num &= 0xfe;
                chr01 = bank_num;
                MMC3_set_PPU_banks();
              }
            }
            break;

          case 0x01:
            {
              //if(num_1k_VROM_banks)
              {
                bank_num &= 0xfe;
                chr23 = bank_num;
                MMC3_set_PPU_banks();
              }
            }
            break;

          case 0x02:
            {
              //if(num_1k_VROM_banks)
              {
                chr4 = bank_num;
                MMC3_set_PPU_banks();
              }
            }
            break;

          case 0x03:
            {
              //if(num_1k_VROM_banks)
              {
                chr5 = bank_num;
                MMC3_set_PPU_banks();
              }
            }
            break;

          case 0x04:
            {
              //if(num_1k_VROM_banks)
              {
                chr6 = bank_num;
                MMC3_set_PPU_banks();
              }
            }
            break;

          case 0x05:
            {
              //if(num_1k_VROM_banks)
              {
                chr7 = bank_num;
                MMC3_set_PPU_banks();
              }
            }
            break;

          case 0x06:
            {
              prg0 = bank_num;
              MMC3_set_CPU_banks();
            }
            break;

          case 0x07:
            {
              prg1 = bank_num;
              MMC3_set_CPU_banks();
            }
            break;
        }
      }
      break;

    case 0xA000:
      {
        regs[2] = data;

        if(parent_NES->ROM->get_mirroring() != NES_PPU::MIRROR_FOUR_SCREEN)
        {
          if(data & 0x01)
          {
            set_mirroring(NES_PPU::MIRROR_HORIZ);
          }
          else
          {
            set_mirroring(NES_PPU::MIRROR_VERT);
          }
        }
      }
      break;

    case 0xA001:
      {
        if(data & 0x80)
        {
          // enable save RAM $6000-$7FFF
        }
        else
        {
          // disable save RAM $6000-$7FFF
        }
      }
      break;

    case 0xC000:
      {
        irq_counter = irq_latch = 0xbe;
        irq_enabled = 0;
      }
      break;

    case 0xC001:
      {
        irq_counter = irq_latch = 0xbe;
        irq_enabled = 1;
      }
      break;

    case 0xE000:
      {
        irq_enabled = 0;
      }
      break;

    case 0xE001:
      {
        irq_enabled = 1;
      }
      break;
  }
}
コード例 #19
0
void NES_mapper237::MemoryWrite(uint32 addr, uint8 data)
{
    if(addr & 0x4000)
    {
        if((addr & 0x0030) == 0x00)
        {
            set_CPU_bank4((addr&0x07)*2+0);
            set_CPU_bank5((addr&0x07)*2+1);
            set_CPU_bank6(num_8k_ROM_banks-2);
            set_CPU_bank7(num_8k_ROM_banks-1);
        }
        else if((addr & 0x0030) == 0x10)
        {
            for(uint32 i = 0; i < 0x2000; i++)
            {
                wram[i+0x0000] = ROM_banks[((addr&0x07)*2+0)*0x2000+(i&0x1ff0)+0x0d]; // 0x0b?
                wram[i+0x2000] = ROM_banks[((addr&0x07)*2+1)*0x2000+(i&0x1ff0)+0x0d]; // 0x0b?
                wram[i+0x4000] = ROM_banks[(num_8k_ROM_banks-2)*0x2000+(i&0x1ff0)+0x0d]; // 0x0b?
                wram[i+0x6000] = ROM_banks[(num_8k_ROM_banks-1)*0x2000+(i&0x1ff0)+0x0d]; // 0x0b?
            }
            nes6502_context *context;
            context = nes6502_get_current_context ();

            context->mem_page[4] = wram + 0x0000;
            context->mem_page[5] = wram + 0x2000;
            context->mem_page[6] = wram + 0x4000;
            context->mem_page[7] = wram + 0x6000;

            nes6502_setcontext();
        }
        else if((addr & 0x0030) == 0x20)
        {
            set_CPU_bank4((addr&0x06)*2+0);
            set_CPU_bank5((addr&0x06)*2+1);
            set_CPU_bank6((addr&0x06)*2+2);
            set_CPU_bank7((addr&0x06)*2+3);
        }
        else if((addr & 0x0030) == 0x30)
        {
            set_CPU_bank4((addr&0x07)*2+0);
            set_CPU_bank5((addr&0x07)*2+1);
            set_CPU_bank6((addr&0x07)*2+0);
            set_CPU_bank7((addr&0x07)*2+1);
        }
    }
    else
    {
        if(addr & 0x0020)
        {
            set_mirroring(NES_PPU::MIRROR_VERT);
        }
        else
        {
            set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
        set_PPU_bank0((addr&0x07)*8+0);
        set_PPU_bank1((addr&0x07)*8+1);
        set_PPU_bank2((addr&0x07)*8+2);
        set_PPU_bank3((addr&0x07)*8+3);
        set_PPU_bank4((addr&0x07)*8+4);
        set_PPU_bank5((addr&0x07)*8+5);
        set_PPU_bank6((addr&0x07)*8+6);
        set_PPU_bank7((addr&0x07)*8+7);
    }
}
コード例 #20
0
void NES_mapper16::MemoryWrite3(uint32 addr, uint8 data)
{
  switch(addr)
  {
    case 0x8000:
    case 0x8001:
    case 0x8002:
    case 0x8003:
      {
        regs[0] = data & 0x01;
        set_CPU_bank4(regs[0]*0x20+regs[2]*2+0);
        set_CPU_bank5(regs[0]*0x20+regs[2]*2+1);
      }
      break;

    case 0x8004:
    case 0x8005:
    case 0x8006:
    case 0x8007:
      {
        regs[1] = data & 0x01;
        set_CPU_bank6(regs[1]*0x20+0x1E);
        set_CPU_bank7(regs[1]*0x20+0x1F);
      }
      break;

    case 0x8008:
      {
        regs[2] = data;
        set_CPU_bank4(regs[0]*0x20+regs[2]*2+0);
        set_CPU_bank5(regs[0]*0x20+regs[2]*2+1);
        set_CPU_bank6(regs[1]*0x20+0x1E);
        set_CPU_bank7(regs[1]*0x20+0x1F);
      }
      break;

    case 0x8009:
      {
        data &= 0x03;
        if(data == 0)
        {
          set_mirroring(NES_PPU::MIRROR_VERT);
        }
        else if(data == 1)
        {
          set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
        else if(data == 2)
        {
          set_mirroring(0,0,0,0);
        }
        else
        {
          set_mirroring(1,1,1,1);
        }
      }
      break;

    case 0x800A:
      {
        irq_enabled = data & 0x01;
        irq_counter = irq_latch;
      }
      break;

    case 0x800B:
      {
        irq_latch = (irq_latch & 0xFF00) | data;
      }
      break;

    case 0x800C:
      {
         irq_latch = ((uint32)data << 8) | (irq_latch & 0x00FF);
      }
      break;

    case 0x800D:
      {
        //write protect
      }
      break;
  }
}
コード例 #21
0
void NES_mapper25::MemoryWrite(uint32 addr, uint8 data)
{
  // regs[0] ... 1K VROM bank at PPU $0000
  // regs[1] ... 1K VROM bank at PPU $0400
  // regs[2] ... 1K VROM bank at PPU $0800
  // regs[3] ... 1K VROM bank at PPU $0C00
  // regs[4] ... 1K VROM bank at PPU $1000
  // regs[5] ... 1K VROM bank at PPU $1400
  // regs[6] ... 1K VROM bank at PPU $1800
  // regs[7] ... 1K VROM bank at PPU $1C00
  // regs[8] ... 8K ROM bank at CPU $8000
  // regs[9] ... 8K ROM bank at CPU $C000
  // regs[10] .. ROM Swap flag

  switch(addr & 0xF000)
  {
    case 0x8000:
      {
        if(regs[10] & 0x02)
        {
          regs[9] = data;
          set_CPU_bank6(data);
        }
        else
        {
          regs[8] = data;
          set_CPU_bank4(data);
        }
      }
      break;

    case 0xA000:
      {
        set_CPU_bank5(data);
      }
      break;
  }

  switch(addr & 0xF00F)
  {
    case 0x9000:
      {
        data &= 0x03;
        if(data == 0)
        {
          set_mirroring(NES_PPU::MIRROR_VERT);
        }
        else if(data == 1)
        {
          set_mirroring(NES_PPU::MIRROR_HORIZ);
        }
        else if(data == 2)
        {
          set_mirroring(0,0,0,0);
        }
        else
        {
          set_mirroring(1,1,1,1);
        }
      }
      break;

    case 0x9001:
    case 0x9004:
      {
        if((regs[10] & 0x02) != (data & 0x02))
        {
          uint8 swap = regs[8];
          regs[8] = regs[9];
          regs[9] = swap;
          set_CPU_bank4(regs[8]);
          set_CPU_bank6(regs[9]);
        }
        regs[10] = data;
      }
      break;

    case 0xB000:
      {
        regs[0] = (regs[0] & 0xF0) | (data & 0x0F);
        set_PPU_bank0(regs[0]);
      }
      break;

    case 0xB001:
    case 0xB004:
      {
        regs[1] = (regs[1] & 0xF0) | (data & 0x0F);
        set_PPU_bank1(regs[1]);
      }
      break;

    case 0xB002:
    case 0xB008:
      {
        regs[0] = (regs[0] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank0(regs[0]);
      }
      break;

    case 0xB003:
    case 0xB00C:
      {
        regs[1] = (regs[1] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank1(regs[1]);
      }
      break;

    case 0xC000:
      {
        regs[2] = (regs[2] & 0xF0) | (data & 0x0F);
        set_PPU_bank2(regs[2]);
      }
      break;

    case 0xC001:
    case 0xC004:
      {
        regs[3] = (regs[3] & 0xF0) | (data & 0x0F);
        set_PPU_bank3(regs[3]);
      }
      break;

    case 0xC002:
    case 0xC008:
      {
        regs[2] = (regs[2] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank2(regs[2]);
      }
      break;

    case 0xC003:
    case 0xC00C:
      {
        regs[3] = (regs[3] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank3(regs[3]);
      }
      break;

    case 0xD000:
      {
        regs[4] = (regs[4] & 0xF0) | (data & 0x0F);
        set_PPU_bank4(regs[4]);
      }
      break;

    case 0xD001:
    case 0xD004:
      {
        regs[5] = (regs[5] & 0xF0) | (data & 0x0F);
        set_PPU_bank5(regs[5]);
      }
      break;

    case 0xD002:
    case 0xD008:
      {
        regs[4] = (regs[4] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank4(regs[4]);
      }
      break;

    case 0xD003:
    case 0xD00C:
      {
        regs[5] = (regs[5] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank5(regs[5]);
      }
      break;

    case 0xE000:
      {
        regs[6] = (regs[6] & 0xF0) | (data & 0x0F);
        set_PPU_bank6(regs[6]);
      }
      break;

    case 0xE001:
    case 0xE004:
      {
        regs[7] = (regs[7] & 0xF0) | (data & 0x0F);
        set_PPU_bank7(regs[7]);
      }
      break;

    case 0xE002:
    case 0xE008:
      {
        regs[6] = (regs[6] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank6(regs[6]);
      }
      break;

    case 0xE003:
    case 0xE00C:
      {
        regs[7] = (regs[7] & 0x0F) | ((data & 0x0F) << 4);
        set_PPU_bank7(regs[7]);
      }
      break;

    case 0xF000:
      {
        irq_latch = (irq_latch & 0xF0) | (data & 0x0F);
      }
      break;

    case 0xF001:
    case 0xF004:
      {
        irq_enabled = data & 0x03;
        if(irq_enabled & 0x02)
        {
          irq_counter = irq_latch;
        }
      }
      break;

    case 0xF002:
    case 0xF008:
      {
        irq_latch = (irq_latch & 0x0F) | ((data & 0x0F) << 4);
      }
      break;

    case 0xF003:
    case 0xF00C:
      {
        irq_enabled = (irq_enabled & 0x01) * 3;
      }
      break;
  }
}