From a66835c091b824978c940ff70047bfe3cc587792 Mon Sep 17 00:00:00 2001 From: sin365 <353374337@qq.com> Date: Wed, 11 Sep 2024 16:04:55 +0800 Subject: [PATCH] =?UTF-8?q?=E8=A1=A5=E5=85=85Mapper=20from=20VirtuaNESex?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Assets/VirtualNes.Core/MMU.cs | 17 +- .../VirtualNes.Core/Mapper/Mapper004.cs | 48 +++- .../VirtualNes.Core/Mapper/Mapper052.cs | 198 ++++++++++++++ .../VirtualNes.Core/Mapper/Mapper052.cs.meta | 11 + .../VirtualNes.Core/Mapper/Mapper168.cs | 166 ++++++++++++ .../VirtualNes.Core/Mapper/Mapper168.cs.meta | 11 + .../VirtualNes.Core/Mapper/Mapper173.cs | 244 ++++++++++++++++++ .../VirtualNes.Core/Mapper/Mapper173.cs.meta | 11 + .../VirtualNes.Core/Mapper/Mapper222.cs | 10 + .../Assets/VirtualNes.Core/Mapper/_Mapper.cs | 6 +- 10 files changed, 719 insertions(+), 3 deletions(-) create mode 100644 AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper052.cs create mode 100644 AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper052.cs.meta create mode 100644 AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper168.cs create mode 100644 AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper168.cs.meta create mode 100644 AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper173.cs create mode 100644 AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper173.cs.meta diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/MMU.cs b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/MMU.cs index fbd63ef..ee95c16 100644 --- a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/MMU.cs +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/MMU.cs @@ -1,4 +1,5 @@ -using VirtualNes.Core; +using Codice.CM.Client.Differences; +using VirtualNes.Core; namespace VirtualNes { @@ -84,6 +85,20 @@ namespace VirtualNes CPU_MEM_PAGE[page] = 0; } + internal static void SetPROM_4K_Bank(ushort addr, int bank) + { + throw new System.NotImplementedException(); + + bank %= (PROM_8K_SIZE * 2); + + //TODO + //memcpy(&CPU_MEM_BANK[addr >> 13][addr & 0x1FFF], PROM + 0x1000 * bank, 0x1000); + //// memcpy( &CPU_MEM_BANK[addr>>13][addr&0x1FFF], YSRAM+0x1000*bank, 0x1000); + CPU_MEM_TYPE[addr >> 13] = BANKTYPE_ROM; + CPU_MEM_PAGE[addr >> 13] = 0; + } + + internal static void SetPROM_8K_Bank(byte page, int bank) { bank %= PROM_8K_SIZE; diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper004.cs b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper004.cs index 59d786e..c97e478 100644 --- a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper004.cs +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper004.cs @@ -1,4 +1,6 @@ -namespace VirtualNes.Core +using System; + +namespace VirtualNes.Core { public class Mapper004 : Mapper { @@ -569,5 +571,49 @@ MMU.SetPROM_32K_Bank(prg0, prg1, MMU.PROM_8K_SIZE - 2, MMU.PROM_8K_SIZE - 1); } } + + public override void SaveState(byte[] p) + { + for (int i = 0; i < 8; i++) + { + p[i] = reg[i]; + } + p[8] = prg0; + p[9] = prg1; + p[10] = chr01; + p[11] = chr23; + p[12] = chr4; + p[13] = chr5; + p[14] = chr6; + p[15] = chr7; + p[16] = irq_enable; + p[17] = (byte)irq_counter; + p[18] = irq_latch; + p[19] = irq_request; + p[20] = irq_preset; + p[21] = irq_preset_vbl; + } + + public override void LoadState(byte[] p) + { + for (int i = 0; i < 8; i++) + { + reg[i] = p[i]; + } + prg0 = p[8]; + prg1 = p[9]; + chr01 = p[10]; + chr23 = p[11]; + chr4 = p[12]; + chr5 = p[13]; + chr6 = p[14]; + chr7 = p[15]; + irq_enable = p[16]; + irq_counter = (Byte)p[17]; + irq_latch = p[18]; + irq_request = p[19]; + irq_preset = p[20]; + irq_preset_vbl = p[21]; + } } } diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper052.cs b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper052.cs new file mode 100644 index 0000000..6f0793f --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper052.cs @@ -0,0 +1,198 @@ +////////////////////////////////////////////////////////////////////////// +// Mapper052 Konami VRC2 type B // +////////////////////////////////////////////////////////////////////////// +using VirtualNes.Core.Debug; +using static VirtualNes.MMU; +using BYTE = System.Byte; +using INT = System.Int32; + +namespace VirtualNes.Core +{ + public class Mapper052 : Mapper + { + + BYTE[] reg = new byte[9]; + BYTE irq_enable; + BYTE irq_counter; + BYTE irq_latch; + INT irq_clock; + public Mapper052(NES parent) : base(parent) { } + + public override void Reset() + { + for (byte i = 0; i < 8; i++) + { + reg[i] = i; + } + reg[8] = 0; + + irq_enable = 0; + irq_counter = 0; + irq_latch = 0; + irq_clock = 0; + + SetPROM_32K_Bank(0, 1, PROM_8K_SIZE - 2, PROM_8K_SIZE - 1); + SetVROM_8K_Bank(0); + + nes.SetRenderMethod(EnumRenderMethod.PRE_ALL_RENDER); + // nes->SetRenderMethod( NES::POST_RENDER ); + // nes->SetRenderMethod( NES::POST_ALL_RENDER ); + + } + + public override void Write(ushort addr, byte data) + { + if (addr >= 0xf000) Debuger.Log($"MPRWR A={addr & 0xFFFF} D={data & 0xFF} L={nes.GetScanline()} CYC={nes.cpu.GetTotalCycles()}\n"); + if (addr >= 0xf000) Debuger.Log($"MPRWR A={addr & 0xFFFF} RAM={RAM[0x1c0] & 0xFF} L={nes.GetScanline()} CYC={nes.cpu.GetTotalCycles()}\n"); + switch (addr & 0xFFFF) + { + case 0x8000: + if (reg[8] != 0) SetPROM_8K_Bank(6, data); + else SetPROM_8K_Bank(4, data); + break; + case 0x9002: + reg[8] = (byte)(data & 0x02); + break; + + case 0x9004: + data &= 0x03; + if (data == 0) SetVRAM_Mirror(VRAM_VMIRROR); + else if (data == 1) SetVRAM_Mirror(VRAM_HMIRROR); + else if (data == 2) SetVRAM_Mirror(VRAM_MIRROR4L); + else SetVRAM_Mirror(VRAM_MIRROR4H); + break; + + case 0xA000: + SetPROM_8K_Bank(5, data); + break; + + case 0xB000: + reg[0] = (byte)((reg[0] & 0xF0) | (data & 0x0F)); + SetVROM_1K_Bank(0, reg[0]); + break; + case 0xB001: + reg[0] = (byte)((reg[0] & 0x0F) | ((data & 0x0F) << 4)); + SetVROM_1K_Bank(0, reg[0]); + break; + case 0xB002: + reg[1] = (byte)((reg[1] & 0xF0) | (data & 0x0F)); + SetVROM_1K_Bank(1, reg[1]); + break; + case 0xB003: + reg[1] = (byte)((reg[1] & 0x0F) | ((data & 0x0F) << 4)); + SetVROM_1K_Bank(1, reg[1]); + break; + + case 0xC000: + reg[2] = (byte)((reg[2] & 0xF0) | (data & 0x0F)); + SetVROM_1K_Bank(2, reg[2]); + break; + case 0xC001: + reg[2] = (byte)((reg[2] & 0x0F) | ((data & 0x0F) << 4)); + SetVROM_1K_Bank(2, reg[2]); + break; + case 0xC002: + reg[3] = (byte)((reg[3] & 0xF0) | (data & 0x0F)); + SetVROM_1K_Bank(3, reg[3]); + break; + case 0xC003: + reg[3] = (byte)((reg[3] & 0x0F) | ((data & 0x0F) << 4)); + SetVROM_1K_Bank(3, reg[3]); + break; + + case 0xD000: + reg[4] = (byte)((reg[4] & 0xF0) | (data & 0x0F)); + SetVROM_1K_Bank(4, reg[4]); + break; + case 0xD001: + reg[4] = (byte)((reg[4] & 0x0F) | ((data & 0x0F) << 4)); + SetVROM_1K_Bank(4, reg[4]); + break; + case 0xD002: + reg[5] = (byte)((reg[5] & 0xF0) | (data & 0x0F)); + SetVROM_1K_Bank(5, reg[5]); + break; + case 0xD003: + reg[5] = (byte)((reg[5] & 0x0F) | ((data & 0x0F) << 4)); + SetVROM_1K_Bank(5, reg[5]); + break; + + case 0xE000: + reg[6] = (byte)((reg[6] & 0xF0) | (data & 0x0F)); + SetVROM_1K_Bank(6, reg[6]); + break; + case 0xE001: + reg[6] = (byte)((reg[6] & 0x0F) | ((data & 0x0F) << 4)); + SetVROM_1K_Bank(6, reg[6]); + break; + case 0xE002: + reg[7] = (byte)((reg[7] & 0xF0) | (data & 0x0F)); + SetVROM_1K_Bank(7, reg[7]); + break; + case 0xE003: + reg[7] = (byte)((reg[7] & 0x0F) | ((data & 0x0F) << 4)); + SetVROM_1K_Bank(7, reg[7]); + break; + + case 0xF000: + break; + case 0xF004: + case 0xFF04: + RAM[0x7f8] = 1; + break; + case 0xF008: + case 0xFF08: + irq_enable = 1; + // irq_latch = ((RAM[0x7f8]*2)+0x11)^0xFF; //Akumajou Special - Boku Dracula-kun + irq_latch = (byte)(((RAM[0x1c0] * 2) + 0x11) ^ 0xFF); //Teenage Mutant Ninja Turtles + irq_counter = irq_latch; + irq_clock = 0; + nes.cpu.ClrIRQ(CPU.IRQ_MAPPER); + break; + case 0xF00C: + irq_enable = 0; + nes.cpu.ClrIRQ(CPU.IRQ_MAPPER); + break; + } + } + + public override void HSync(int scanline) + { + // + } + + public override void Clock(int cycles) + { + if (irq_enable != null) + { + irq_clock += cycles * 3; + while (irq_clock >= 341) + { + irq_clock -= 341; + irq_counter++; + if (irq_counter == 0) + { + irq_counter = irq_latch; + nes.cpu.SetIRQ(CPU.IRQ_MAPPER); + } + } + } + } + + public override void SaveState(byte[] p) + { + // + } + + public override void LoadState(byte[] p) + { + // + } + + + public override bool IsStateSave() + { + return true; + } + } +} diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper052.cs.meta b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper052.cs.meta new file mode 100644 index 0000000..9fb38b9 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper052.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: bbcd8b5589ac667448a1be830aac1d4a +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper168.cs b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper168.cs new file mode 100644 index 0000000..a7595a7 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper168.cs @@ -0,0 +1,166 @@ +////////////////////////////////////////////////////////////////////////// +// Mapper168 Subor (PPUExtLatch) // +////////////////////////////////////////////////////////////////////////// +using VirtualNes.Core.Debug; +using static VirtualNes.MMU; +using BYTE = System.Byte; +using INT = System.Int32; + +namespace VirtualNes.Core +{ + public class Mapper168 : Mapper + { + byte reg5000, reg5200, reg5300; + byte PPU_SW, NT_data; + byte Rom_Type; + public Mapper168(NES parent) : base(parent) { } + + public override bool IsStateSave() + { + return true; + } + public override void Reset() + { + reg5000 = 0; + reg5200 = 0; + reg5300 = 0; + PPU_SW = 0; + NT_data = 0; + nes.ppu.SetExtLatchMode(true); + SetPROM_16K_Bank(4, 0); + SetPROM_16K_Bank(6, 0); + + Rom_Type = 0; + uint crc = nes.rom.GetPROM_CRC(); + if (crc == 0x0A9808AE) //[Subor] Karaoke (C) + { + Rom_Type = 1; + SetPROM_32K_Bank(0); + nes.SetVideoMode(2 != 0); + } + if (crc == 0x12D61CE8) //[Subor] Subor V11.0 (C) + { + Rom_Type = 2; + } + } + + public override byte ReadLow(ushort addr) + { + if (addr == 0x5300) return 0x8F; //返回0x8F,跳过真人语音发声有关的程序段 + return base.ReadLow(addr); + } + + public override void WriteLow(ushort addr, byte data) + { + if (addr == 0x5000) + { + reg5000 = data; + SetBank_CPU(); + } + else if (addr == 0x5200) + { + reg5200 = (byte)(data & 0x7); + SetBank_CPU(); + } + else if (addr == 0x5300) + { + reg5300 = data; + } + else if (addr >= 0x6000) + { + CPU_MEM_BANK[addr >> 13][addr & 0x1FFF] = data; + } + } + + + public override void Write(ushort addr, byte data) + { + if (Rom_Type == 1) + { //[Subor] Karaoke (C) + SetPROM_32K_Bank(data & 0x1F); + if ((data & 0x40) != 0) SetVRAM_Mirror(VRAM_HMIRROR); + else SetVRAM_Mirror(VRAM_VMIRROR); + if ((data & 0xC0) != 0) PPU_SW = 1; + else PPU_SW = 0; + } + } + + void SetBank_CPU() + { + if (reg5200 < 4) SetPROM_16K_Bank(4, reg5000); + else SetPROM_32K_Bank(reg5000); + switch (reg5200) + { + case 0: + SetVRAM_Mirror(VRAM_VMIRROR); + PPU_SW = 0; + break; + case 2: + SetVRAM_Mirror(VRAM_VMIRROR); + PPU_SW = 1; + break; + case 1: + case 3: + SetVRAM_Mirror(VRAM_HMIRROR); + PPU_SW = 0; + break; + case 5: + if (reg5000 == 4 && Rom_Type == 2) + { //Special for [Subor] Subor V11.0 (C) - Tank (坦克大战) + nes.ppu.SetExtLatchMode(false); + SetVRAM_Mirror(VRAM_HMIRROR); + } + break; + } + } + + public override void PPU_Latch(ushort addr) + { + if ((addr & 0xF000) == 0x2000) + { + NT_data = (byte)((addr >> 8) & 0x03); + } + } + + public override void PPU_ExtLatch(ushort ntbladr, ref byte chr_l, ref byte chr_h, ref byte attr) + { + INT loopy_v = nes.ppu.GetPPUADDR(); + INT loopy_y = nes.ppu.GetTILEY(); + INT tileofs = (PPUREG[0] & PPU.PPU_BGTBL_BIT) << 8; + INT attradr = 0x23C0 + (loopy_v & 0x0C00) + ((loopy_v & 0x0380) >> 4); + INT attrsft = (ntbladr & 0x0040) >> 4; + ArrayRef pNTBL = PPU_MEM_BANK[ntbladr >> 10]; + INT ntbl_x = ntbladr & 0x001F; + INT tileadr, ntb; + + ntb = (ntbladr >> 10) & 3; + + if (ntb == 2) + tileofs |= 0x1000; + else if (ntb != 0 && PPU_SW != 0) + tileofs |= 0x1000; + else + tileofs |= 0x0000; + + attradr &= 0x3FF; + attr = (byte)(((pNTBL[attradr + (ntbl_x >> 2)] >> ((ntbl_x & 2) + attrsft)) & 3) << 2); + tileadr = tileofs + pNTBL[ntbladr & 0x03FF] * 0x10 + loopy_y; + + chr_l = PPU_MEM_BANK[tileadr >> 10][tileadr & 0x03FF]; + chr_h = PPU_MEM_BANK[tileadr >> 10][(tileadr & 0x03FF) + 8]; + } + + public override void SaveState(byte[] p) + { + p[0] = reg5000; + p[1] = reg5200; + } + + public override void LoadState(byte[] p) + { + reg5000 = p[0]; + reg5200 = p[1]; + } + + } +} diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper168.cs.meta b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper168.cs.meta new file mode 100644 index 0000000..67a2634 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper168.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: f468229e616f1cd41aba98252208fbf7 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper173.cs b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper173.cs new file mode 100644 index 0000000..fb1fd60 --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper173.cs @@ -0,0 +1,244 @@ +////////////////////////////////////////////////////////////////////////// +// Mapper173 Subor // +////////////////////////////////////////////////////////////////////////// +using Codice.CM.Client.Differences; +using VirtualNes.Core.Debug; +using static VirtualNes.MMU; +using BYTE = System.Byte; +using INT = System.Int32; +namespace VirtualNes.Core +{ + public class Mapper173 : Mapper + { + + BYTE[] reg = new BYTE[10]; + + INT irq_counter, irq_latch; + BYTE irq_enable, irq_repeat; + BYTE irq_occur; + public Mapper173(NES parent) : base(parent) { } + + public override bool IsStateSave() + { + return true; + } + public override void Reset() + { + // nes.ppu.SetExtLatchMode( TRUE ); + for (INT i = 0; i < 11; i++) reg[i] = 0x00; + + irq_enable = irq_repeat = 0; + irq_counter = irq_latch = 0; + irq_occur = 0; + + SetPROM_32K_Bank(0); + nes.SetVideoMode(2 != 0); + } + + public override byte ExRead(ushort addr) + { + Debuger.Log($"ExRead - addr= {addr}\n"); + + return 0x00; + + switch (addr) + { + case 0x4026: + // + break; + case 0x4033: + //D7: + //D6: + //D5: + //D4: + //D3: + //D2: + //D1: + //D0: + // + break; + case 0x4204: //FDC主状态寄存器(STATUS) + // + break; + case 0x4205: //FDC数据寄存器(DATA)(读???) + // + break; + } + } + + public override void ExWrite(ushort addr, byte data) + { + Debuger.Log($"ExWrite - addr= {addr} ; dat= {data}\n"); + switch (addr) + { + case 0x4020: + reg[0] = data; + break; + case 0x4022: + reg[1] = data; + break; + case 0x4023: + reg[2] = data; + break; + case 0x4026: + reg[3] = data; + break; + case 0x4031: + reg[4] = data; + break; + case 0x4032: + reg[5] = data; + + irq_repeat = (byte)(data & 0x01); + irq_enable = (byte)(data & 0x02); + irq_occur = 0; + if (irq_enable!= null) + { + irq_counter = irq_latch; + } + else + { + nes.cpu.ClrIRQ(CPU.IRQ_MAPPER); + } + break; + case 0x4034: + reg[6] = data; + + irq_latch = (irq_latch & 0xFF00) | data; + break; + case 0x4035: + reg[7] = data; + + irq_latch = (irq_latch & 0x00FF) | ((ushort)data << 8); + break; + case 0x4040: + SetPROM_4K_Bank(0x8000, data & 0x7F); + break; + case 0x4041: + SetPROM_4K_Bank(0x9000, data & 0x7F); + break; + case 0x4042: + SetPROM_4K_Bank(0xa000, data & 0x7F); + break; + case 0x4043: + SetPROM_4K_Bank(0xb000, data & 0x7F); + break; + case 0x4044: + SetPROM_4K_Bank(0xc000, data & 0x7F); + break; + case 0x4045: + SetPROM_4K_Bank(0xd000, data & 0x7F); + break; + case 0x4046: + SetPROM_4K_Bank(0xe000, data & 0x7F); + break; + case 0x4047: + SetPROM_4K_Bank(0xf000, data & 0x7F); + break; + + case 0x4205: //FDC数据寄存器(DATA)(写???) + // + break; + } + } + + public override byte ReadLow(ushort addr) + { + // DEBUGOUT( "ReadLow - addr= %04x\n", addr ); + + return CPU_MEM_BANK[addr >> 13][addr & 0x1FFF]; + } + + public override void WriteLow(ushort addr, byte data) + { + // DEBUGOUT( "WriteLow - addr= %04x ; dat= %03x\n", addr, data ); + + CPU_MEM_BANK[addr >> 13][addr & 0x1FFF] = data; + } + + public override void Write(ushort addr, byte data) + { + // DEBUGOUT( "Write - addr= %04x ; dat= %03x\n", addr, data ); + } + + + public override void HSync(int scanline) + { + // if( (scanline >= 0 && scanline <= 239) ) { + // if( nes.ppu.IsDispON() ) { + // if( irq_enable ) { + // irq_enable = 0; + /// nes.cpu.SetIRQ( IRQ_MAPPER ); + // } + // } + // } + } + + public override void Clock(int cycles) + { + + if (irq_enable!= 0) + { + irq_counter -= cycles; + if (irq_counter <= 0) + { + //// irq_counter &= 0xFFFF; + irq_counter += irq_latch; + + if (irq_occur == 0) + { + irq_occur = 0xFF; + if (irq_repeat == 0) + { + irq_enable = 0; + } + nes.cpu.SetIRQ(CPU.IRQ_MAPPER); + } + } + } + } + + public override void PPU_Latch(ushort addr) + { + // + } + + public override void PPU_ExtLatch(ushort ntbladr, ref byte chr_l, ref byte chr_h, ref byte attr) + { + INT loopy_v = nes.ppu.GetPPUADDR(); + INT loopy_y = nes.ppu.GetTILEY(); + INT tileofs = (PPUREG[0] & PPU.PPU_BGTBL_BIT) << 8; + INT attradr = 0x23C0 + (loopy_v & 0x0C00) + ((loopy_v & 0x0380) >> 4); + INT attrsft = (ntbladr & 0x0040) >> 4; + ArrayRef pNTBL = PPU_MEM_BANK[ntbladr >> 10]; + INT ntbl_x = ntbladr & 0x001F; + INT tileadr, ntb; + + ntb = (ntbladr >> 10) & 3; + + if (ntb == 2) + tileofs |= 0x1000; + // else if(ntb && PPU_SW) + tileofs |= 0x1000; + // else + tileofs |= 0x0000; + + attradr &= 0x3FF; + attr = (byte)(((pNTBL[attradr + (ntbl_x >> 2)] >> ((ntbl_x & 2) + attrsft)) & 3) << 2); + tileadr = tileofs + pNTBL[ntbladr & 0x03FF] * 0x10 + loopy_y; + + chr_l = PPU_MEM_BANK[tileadr >> 10][tileadr & 0x03FF]; + chr_h = PPU_MEM_BANK[tileadr >> 10][(tileadr & 0x03FF) + 8]; + } + + public override void SaveState(byte[] p) + { + // + } + + public override void LoadState(byte[] p) + { + // + } + } +} diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper173.cs.meta b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper173.cs.meta new file mode 100644 index 0000000..e58d2ab --- /dev/null +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper173.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: c98a3c4204201144eb348e0d2f1f7076 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper222.cs b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper222.cs index f017d99..c6386b5 100644 --- a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper222.cs +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/Mapper222.cs @@ -60,6 +60,16 @@ namespace VirtualNes.Core } } + public override void LoadState(byte[] p) + { + // + } + + public override void SaveState(byte[] p) + { + // + } + } diff --git a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/_Mapper.cs b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/_Mapper.cs index deaf871..41807f7 100644 --- a/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/_Mapper.cs +++ b/AxibugEmuOnline.Client/Assets/VirtualNes.Core/Mapper/_Mapper.cs @@ -1,4 +1,8 @@ -namespace VirtualNes.Core +using VirtualNes.Core.Debug; +using static VirtualNes.MMU; +using BYTE = System.Byte; +using INT = System.Int32; +namespace VirtualNes.Core { public class _Mapper : Mapper {