diff options
author | 0kmg <9137159+0kmg@users.noreply.github.com> | 2021-10-11 04:49:37 -0800 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-10-11 23:49:37 +1100 |
commit | 32574013d259d40e4cc1137e7d498e60493babac (patch) | |
tree | a0069d2235f302f25af770c97c4e825db73cb80f /src/devices/bus/nes | |
parent | c4979ef8d1daa847af76aa8f828f3422c16ab791 (diff) |
bus/nes: Improved support for various VRC clone boards. (#8687)
* Expanded VRC4 CHR bank regs to 9-bit. This functionality is verified on Konami VRC4 hardware as well but is only used by clones (World Hero here).
* Removed board for World Hero. Its VRC4 clone chip is under a glop top but is thought to be identical to Konami's.
* Reimplemented TF1201 (Lethal Weapon) as a VRC4 subclass. Its clone chip is only known to differ by the IRQ reload bit, which it ignores.
* Reimplemented Shui Guan Pipe as a VRC4 subclass. Its clone chip has different PRG banking but is otherwise standard.
Software list items promoted to working (nes.xml)
---------------------------------------
Gimmick! (Asia, pirate)
Lethal Weapon (China)
World Hero (Asia)
World Hero (Asia, alt)
Diffstat (limited to 'src/devices/bus/nes')
-rw-r--r-- | src/devices/bus/nes/bootleg.cpp | 113 | ||||
-rw-r--r-- | src/devices/bus/nes/bootleg.h | 29 | ||||
-rw-r--r-- | src/devices/bus/nes/konami.cpp | 6 | ||||
-rw-r--r-- | src/devices/bus/nes/konami.h | 2 | ||||
-rw-r--r-- | src/devices/bus/nes/nes_carts.cpp | 2 | ||||
-rw-r--r-- | src/devices/bus/nes/nes_ines.hxx | 10 | ||||
-rw-r--r-- | src/devices/bus/nes/nes_pcb.hxx | 1 | ||||
-rw-r--r-- | src/devices/bus/nes/nes_slot.h | 4 | ||||
-rw-r--r-- | src/devices/bus/nes/pirate.cpp | 241 | ||||
-rw-r--r-- | src/devices/bus/nes/pirate.h | 56 | ||||
-rw-r--r-- | src/devices/bus/nes/vrc_clones.cpp | 160 | ||||
-rw-r--r-- | src/devices/bus/nes/vrc_clones.h | 54 |
12 files changed, 226 insertions, 452 deletions
diff --git a/src/devices/bus/nes/bootleg.cpp b/src/devices/bus/nes/bootleg.cpp index 842b932869f..a5262503ebd 100644 --- a/src/devices/bus/nes/bootleg.cpp +++ b/src/devices/bus/nes/bootleg.cpp @@ -70,7 +70,6 @@ DEFINE_DEVICE_TYPE(NES_LH53, nes_lh53_device, "nes_lh53", "N DEFINE_DEVICE_TYPE(NES_2708, nes_2708_device, "nes_2708", "NES Cart BTL-2708 Pirate PCB") DEFINE_DEVICE_TYPE(NES_AC08, nes_ac08_device, "nes_ac08", "NES Cart AC08 Pirate PCB") DEFINE_DEVICE_TYPE(NES_MMALEE, nes_mmalee_device, "nes_mmalee", "NES Cart Super Mario Bros. Malee 2 Pirate PCB") -DEFINE_DEVICE_TYPE(NES_SHUIGUAN, nes_shuiguan_device, "nes_shuiguan", "NES Cart Shui Guan Pipe Pirate PCB") DEFINE_DEVICE_TYPE(NES_RT01, nes_rt01_device, "nes_rt01", "NES Cart RT-01 PCB") DEFINE_DEVICE_TYPE(NES_YUNG08, nes_yung08_device, "nes_yung08", "NES Cart Super Mario Bros. 2 YUNG-08 PCB") @@ -235,11 +234,6 @@ nes_mmalee_device::nes_mmalee_device(const machine_config &mconfig, const char * { } -nes_shuiguan_device::nes_shuiguan_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : nes_nrom_device(mconfig, NES_SHUIGUAN, tag, owner, clock), m_irq_count(0), m_irq_enable(0), irq_timer(nullptr) -{ -} - nes_rt01_device::nes_rt01_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : nes_nrom_device(mconfig, NES_RT01, tag, owner, clock) { @@ -704,29 +698,6 @@ void nes_mmalee_device::pcb_reset() prg32(0); } -void nes_shuiguan_device::device_start() -{ - common_start(); - irq_timer = timer_alloc(TIMER_IRQ); - // always running and checking for IRQ every 114 cycles? or resetting every frame? - irq_timer->adjust(attotime::zero, 0, clocks_to_attotime(114)); - - save_item(NAME(m_irq_enable)); - save_item(NAME(m_irq_count)); - save_item(NAME(m_mmc_vrom_bank)); -} - -void nes_shuiguan_device::pcb_reset() -{ - m_chr_source = m_vrom_chunks ? CHRROM : CHRRAM; - prg32((m_prg_chunks << 1) - 1); - chr8(0, m_chr_source); - - m_irq_enable = 0; - m_irq_count = 0; - memset(m_mmc_vrom_bank, 0, sizeof(m_mmc_vrom_bank)); -} - void nes_rt01_device::device_start() { common_start(); @@ -2220,90 +2191,6 @@ void nes_mmalee_device::write_m(offs_t offset, uint8_t data) /*------------------------------------------------- - BTL-SHUIGUANPIPE - - Games: Shui Guan Pipe (Gimmick Pirate) - - iNES: mapper 183 - - In MAME: Supported, but there are glitches (PPU or IRQ?) - - -------------------------------------------------*/ - -// timer always running and checking IRQ every 114 CPU cycles? -void nes_shuiguan_device::device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr) -{ - if (id == TIMER_IRQ) - { - m_irq_count++; - m_irq_count &= 0xff; - - if (m_irq_enable && !m_irq_count) - hold_irq_line(); - } -} - -void nes_shuiguan_device::write_h(offs_t offset, uint8_t data) -{ - int bank; - LOG_MMC(("shuiguan write_h, offset: %04x, data: %02x\n", offset, data)); - - switch (offset & 0x7000) - { - case 0x0000: - if (offset & 0x800 && !(offset & 0x0c)) // 0x8800-0x8803 + N*0x10 - prg8_89(data); - break; - case 0x1000: - if (offset & 0x800 && !(offset & 0x0c)) // 0x9800-0x9803 + N*0x10 - { - switch (data & 0x03) - { - case 0: set_nt_mirroring(PPU_MIRROR_VERT); break; - case 1: set_nt_mirroring(PPU_MIRROR_HORZ); break; - case 2: set_nt_mirroring(PPU_MIRROR_LOW); break; - case 3: set_nt_mirroring(PPU_MIRROR_HIGH); break; - } - } - break; - case 0x2000: - if (!(offset & 0x800) && !(offset & 0x0c)) // 0xa000-0xa003 + N*0x10 - prg8_cd(data); - if (offset & 0x800 && !(offset & 0x0c)) // 0xa800-0xa803 + N*0x10 - prg8_ab(data); - break; - case 0x3000: - case 0x4000: - case 0x5000: - case 0x6000: - bank = (((offset + 0x1000) >> 11) | (offset >> 3)) & 0x07; - if (offset & 4) - m_mmc_vrom_bank[bank] = (m_mmc_vrom_bank[bank] & 0x0f) | ((data & 0x0f) << 4); - else - m_mmc_vrom_bank[bank] = (m_mmc_vrom_bank[bank] & 0xf0) | ((data & 0x0f) << 0); - chr1_x(bank, m_mmc_vrom_bank[bank], m_chr_source); - break; - case 0x7000: - switch (offset & 0x0c) - { - case 0x00: m_irq_count = (m_irq_count & 0xf0) | ((data & 0x0f) << 0); break; - case 0x04: m_irq_count = (m_irq_count & 0x0f) | ((data & 0x0f) << 4); break; - case 0x08: m_irq_enable = data; break; - case 0x0c: break; - } - break; - } -} - -uint8_t nes_shuiguan_device::read_m(offs_t offset) -{ - // always first bank?? - LOG_MMC(("shuiguan read_m, offset: %04x\n", offset)); - return m_prg[offset & 0x1fff]; -} - -/*------------------------------------------------- - RT-01 Games: Russian test cart diff --git a/src/devices/bus/nes/bootleg.h b/src/devices/bus/nes/bootleg.h index 081173d3e2e..f26ad81af4d 100644 --- a/src/devices/bus/nes/bootleg.h +++ b/src/devices/bus/nes/bootleg.h @@ -686,34 +686,6 @@ protected: }; -// ======================> nes_shuiguan_device - -class nes_shuiguan_device : public nes_nrom_device -{ -public: - // construction/destruction - nes_shuiguan_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - - virtual uint8_t read_m(offs_t offset) override; - virtual void write_h(offs_t offset, uint8_t data) override; - - virtual void pcb_reset() override; - -protected: - // device-level overrides - virtual void device_start() override; - virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr) override; - -private: - uint16_t m_irq_count; - int m_irq_enable; - uint8_t m_mmc_vrom_bank[8]; - - static const device_timer_id TIMER_IRQ = 0; - emu_timer *irq_timer; -}; - - // ======================> nes_rt01_device class nes_rt01_device : public nes_nrom_device @@ -794,7 +766,6 @@ DECLARE_DEVICE_TYPE(NES_LH53, nes_lh53_device) DECLARE_DEVICE_TYPE(NES_2708, nes_2708_device) DECLARE_DEVICE_TYPE(NES_AC08, nes_ac08_device) DECLARE_DEVICE_TYPE(NES_MMALEE, nes_mmalee_device) -DECLARE_DEVICE_TYPE(NES_SHUIGUAN, nes_shuiguan_device) DECLARE_DEVICE_TYPE(NES_RT01, nes_rt01_device) DECLARE_DEVICE_TYPE(NES_YUNG08, nes_yung08_device) diff --git a/src/devices/bus/nes/konami.cpp b/src/devices/bus/nes/konami.cpp index 2f77b855205..64b8d92d1f0 100644 --- a/src/devices/bus/nes/konami.cpp +++ b/src/devices/bus/nes/konami.cpp @@ -484,7 +484,7 @@ void nes_konami_vrc4_device::set_prg() void nes_konami_vrc4_device::write_h(offs_t offset, uint8_t data) { - uint8_t bank, shift, mask; + int bank, shift, mask; uint16_t add_lines = ((offset << (9 - m_vrc_ls_prg_a)) & 0x200) | ((offset << (8 - m_vrc_ls_prg_b)) & 0x100); LOG_MMC(("VRC-4 write_h, offset: %04x, data: %02x\n", offset, data)); @@ -520,8 +520,8 @@ void nes_konami_vrc4_device::write_h(offs_t offset, uint8_t data) case 0x6000: bank = ((offset & 0x7000) - 0x3000) / 0x0800 + BIT(add_lines, 9); shift = BIT(add_lines, 8) * 4; - mask = (0xf0 >> shift); - m_mmc_vrom_bank[bank] = (m_mmc_vrom_bank[bank] & mask) | ((data & 0x0f) << shift); + mask = shift ? 0x1f0 : 0x0f; + m_mmc_vrom_bank[bank] = (m_mmc_vrom_bank[bank] & ~mask) | ((data << shift) & mask); chr1_x(bank, m_mmc_vrom_bank[bank], CHRROM); break; case 0x7000: diff --git a/src/devices/bus/nes/konami.h b/src/devices/bus/nes/konami.h index 7f7e7448938..1a451b00733 100644 --- a/src/devices/bus/nes/konami.h +++ b/src/devices/bus/nes/konami.h @@ -105,7 +105,7 @@ protected: virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr) override; void set_prg(); - uint8_t m_mmc_vrom_bank[8]; + uint16_t m_mmc_vrom_bank[8]; uint8_t m_latch, m_mmc_prg_bank; void irq_tick(); diff --git a/src/devices/bus/nes/nes_carts.cpp b/src/devices/bus/nes/nes_carts.cpp index 6deb671cf2f..cff3176786a 100644 --- a/src/devices/bus/nes/nes_carts.cpp +++ b/src/devices/bus/nes/nes_carts.cpp @@ -65,6 +65,7 @@ #include "pirate.h" #include "mmc1_clones.h" #include "mmc3_clones.h" +#include "vrc_clones.h" void nes_cart(device_slot_interface &device) @@ -293,7 +294,6 @@ void nes_cart(device_slot_interface &device) device.option_add_internal("edu2k", NES_EDU2K); device.option_add_internal("t230", NES_T230); device.option_add_internal("mk2", NES_MK2); - device.option_add_internal("unl_whero", NES_WHERO); // mapper 27 device.option_add_internal("unl_43272", NES_43272); // used in Gaau Hok Gwong Cheung device.option_add_internal("tf1201", NES_TF1201); device.option_add_internal("unl_cfight", NES_CITYFIGHT); // used by City Fighter IV diff --git a/src/devices/bus/nes/nes_ines.hxx b/src/devices/bus/nes/nes_ines.hxx index b70b8156f4c..506f4e25553 100644 --- a/src/devices/bus/nes/nes_ines.hxx +++ b/src/devices/bus/nes/nes_ines.hxx @@ -59,11 +59,11 @@ static const nes_mmc mmc_list[] = { 24, KONAMI_VRC6 }, { 25, KONAMI_VRC4 }, { 26, KONAMI_VRC6 }, - { 27, UNL_WORLDHERO }, // 27 World Hero board - Unsupported - { 28, UNL_ACTION53 }, // 28 - Multi-discrete PCB designed by Tepples for Action 53 - { 29, UNL_CUFROM }, // 29 - homebrew PCB used by Glider - { 30, UNL_UNROM512 }, // 30 - UNROM 512 + Flash - { 31, UNL_2A03PURITANS }, // 31 - PCB designed by infinitelives & rainwarrior for 2A03 Puritans Album + { 27, UNL_CC21 }, // Mihunche, but previously used for World Hero + { 28, UNL_ACTION53 }, // Multi-discrete PCB designed by Tepples for Action 53 + { 29, UNL_CUFROM }, // homebrew PCB used by Glider + { 30, UNL_UNROM512 }, // UNROM 512 + Flash + { 31, UNL_2A03PURITANS }, // PCB designed by infinitelives & rainwarrior for 2A03 Puritans Album { 32, IREM_G101 }, { 33, TAITO_TC0190FMC }, { 34, STD_BXROM }, diff --git a/src/devices/bus/nes/nes_pcb.hxx b/src/devices/bus/nes/nes_pcb.hxx index 95b55264383..f79a8e09512 100644 --- a/src/devices/bus/nes/nes_pcb.hxx +++ b/src/devices/bus/nes/nes_pcb.hxx @@ -364,7 +364,6 @@ static const nes_pcb pcb_list[] = { "unl_malisb", UNL_MALISB }, { "sgpipe", BTL_SHUIGUAN }, { "rt01", UNL_RT01 }, // Russian Test Cart - { "unl_whero", UNL_WORLDHERO }, { "unl_43272", UNL_43272 }, { "tf1201", UNL_TF1201 }, { "unl_cfight", UNL_CITYFIGHT }, diff --git a/src/devices/bus/nes/nes_slot.h b/src/devices/bus/nes/nes_slot.h index e9d02522bce..98a48335128 100644 --- a/src/devices/bus/nes/nes_slot.h +++ b/src/devices/bus/nes/nes_slot.h @@ -114,8 +114,8 @@ enum UNL_UXROM, UNL_MK2, UNL_XIAOZY, UNL_KOF96, UNL_FS6, UNL_SF3, UNL_RACERMATE, UNL_EDU2K, UNL_STUDYNGAME, UNL_603_5052, UNL_H2288, UNL_158B, UNL_2708, - UNL_MALISB, UNL_AC08, UNL_A9746, UNL_WORLDHERO, - UNL_43272, UNL_TF1201, UNL_CITYFIGHT, UNL_NINJARYU, UNL_EH8813A, UNL_RT01, + UNL_MALISB, UNL_AC08, UNL_A9746, UNL_43272, UNL_TF1201, + UNL_CITYFIGHT, UNL_NINJARYU, UNL_EH8813A, UNL_RT01, // Bootleg boards BTL_0353, BTL_09034A, BTL_AISENSHINICOL, BTL_BATMANFS, BTL_CONTRAJ, BTL_DRAGONNINJA, BTL_L001, BTL_MARIOBABY, diff --git a/src/devices/bus/nes/pirate.cpp b/src/devices/bus/nes/pirate.cpp index ddfc93ae258..69cf7b08ad1 100644 --- a/src/devices/bus/nes/pirate.cpp +++ b/src/devices/bus/nes/pirate.cpp @@ -45,9 +45,7 @@ DEFINE_DEVICE_TYPE(NES_XIAOZY, nes_xiaozy_device, "nes_xiaozy", " DEFINE_DEVICE_TYPE(NES_EDU2K, nes_edu2k_device, "nes_edu2k", "NES Cart Educational Computer 2000 PCB") DEFINE_DEVICE_TYPE(NES_T230, nes_t230_device, "nes_t230", "NES Cart T-230 PCB") DEFINE_DEVICE_TYPE(NES_MK2, nes_mk2_device, "nes_mk2", "NES Cart Mortal Kombat 2 PCB") -DEFINE_DEVICE_TYPE(NES_WHERO, nes_whero_device, "nes_whero", "NES Cart World Heroes PCB") DEFINE_DEVICE_TYPE(NES_43272, nes_43272_device, "nes_43272", "NES Cart UNL-43272 PCB") -DEFINE_DEVICE_TYPE(NES_TF1201, nes_tf1201_device, "nes_tf1201", "NES Cart UNL-TF1201 PCB") DEFINE_DEVICE_TYPE(NES_CITYFIGHT, nes_cityfight_device, "nes_cityfight", "NES Cart City Fighter PCB") DEFINE_DEVICE_TYPE(NES_EH8813A, nes_eh8813a_device, "nes_eh8813a", "NES Cart UNL-EH8813A PCB") @@ -107,21 +105,11 @@ nes_mk2_device::nes_mk2_device(const machine_config &mconfig, const char *tag, d { } -nes_whero_device::nes_whero_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : nes_nrom_device(mconfig, NES_WHERO, tag, owner, clock), m_reg(0), m_irq_count(0), m_irq_count_latch(0), m_irq_enable(0), m_irq_enable_latch(0) -{ -} - nes_43272_device::nes_43272_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : nes_nrom_device(mconfig, NES_43272, tag, owner, clock), m_latch(0) { } -nes_tf1201_device::nes_tf1201_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : nes_nrom_device(mconfig, NES_TF1201, tag, owner, clock), m_prg(0), m_swap(0), m_irq_count(0), m_irq_enable(0), m_irq_enable_latch(0) -{ -} - nes_cityfight_device::nes_cityfight_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : nes_nrom_device(mconfig, NES_CITYFIGHT, tag, owner, clock), m_prg_reg(0), m_prg_mode(0), m_irq_count(0), m_irq_enable(0), irq_timer(nullptr) { @@ -303,34 +291,6 @@ void nes_mk2_device::pcb_reset() m_irq_count = m_irq_count_latch = 0; } - -void nes_whero_device::device_start() -{ - common_start(); - save_item(NAME(m_irq_enable)); - save_item(NAME(m_irq_enable_latch)); - save_item(NAME(m_irq_count)); - save_item(NAME(m_irq_count_latch)); - save_item(NAME(m_reg)); - save_item(NAME(m_mmc_vrom_bank)); -} - -void nes_whero_device::pcb_reset() -{ - m_chr_source = m_vrom_chunks ? CHRROM : CHRRAM; - prg16_89ab(0); - prg16_cdef(m_prg_chunks - 1); - chr8(0x100, m_chr_source); - - m_irq_enable = 0; - m_irq_enable_latch = 0; - m_irq_count = 0; - m_irq_count_latch = 0; - - m_reg = 0; - memset(m_mmc_vrom_bank, 0, sizeof(m_mmc_vrom_bank)); -} - void nes_43272_device::device_start() { common_start(); @@ -346,32 +306,6 @@ void nes_43272_device::pcb_reset() m_latch = 0x81; } -void nes_tf1201_device::device_start() -{ - common_start(); - save_item(NAME(m_prg)); - save_item(NAME(m_swap)); - save_item(NAME(m_irq_enable)); - save_item(NAME(m_irq_enable_latch)); - save_item(NAME(m_irq_count)); - save_item(NAME(m_mmc_vrom_bank)); -} - -void nes_tf1201_device::pcb_reset() -{ - m_chr_source = m_vrom_chunks ? CHRROM : CHRRAM; - prg16_89ab(0); - prg16_cdef(m_prg_chunks - 1); - chr8(0, m_chr_source); - - memset(m_mmc_vrom_bank, 0, sizeof(m_mmc_vrom_bank)); - m_prg = 0; - m_swap = 0; - m_irq_enable = 0; - m_irq_enable_latch = 0; - m_irq_count = 0; -} - void nes_cityfight_device::device_start() { common_start(); @@ -915,102 +849,6 @@ void nes_mk2_device::write_m(offs_t offset, uint8_t data) } } - -/*------------------------------------------------- - - UNL-WORLDHERO board emulation - - - iNES: - - -------------------------------------------------*/ - -// Same as Konami VRC IRQ... -void nes_whero_device::hblank_irq(int scanline, int vblank, int blanked) -{ - /* Increment & check the IRQ scanline counter */ - if (m_irq_enable && (++m_irq_count == 0x100)) - { - m_irq_count = m_irq_count_latch; - m_irq_enable = m_irq_enable_latch; - hold_irq_line(); - } -} - -void nes_whero_device::write_h(offs_t offset, uint8_t data) -{ - int bank, shift, mask1, mask2; - LOG_MMC(("World Hero write_h, offset: %04x, data: %02x\n", offset, data)); - - switch (offset & 0x70c3) - { - case 0x0000: - if (!m_reg) - prg8_89(data); - else - prg8_cd(data); - break; - - case 0x1000: - switch (data & 0x03) - { - case 0x00: set_nt_mirroring(PPU_MIRROR_VERT); break; - case 0x01: set_nt_mirroring(PPU_MIRROR_HORZ); break; - case 0x02: set_nt_mirroring(PPU_MIRROR_LOW); break; - case 0x03: set_nt_mirroring(PPU_MIRROR_HIGH); break; - } - break; - - case 0x1002: - case 0x1080: - if (m_reg != (data & 2)) - { - m_reg = data & 2; - // swap banks! - prg8_89(m_prg_bank[2]); - prg8_cd(m_prg_bank[0]); - } - break; - - case 0x2000: - prg8_ab(data); - break; - - case 0x3000: case 0x3001: case 0x3002: case 0x3003: - case 0x4000: case 0x4001: case 0x4002: case 0x4003: - case 0x5000: case 0x5001: case 0x5002: case 0x5003: - case 0x6000: case 0x6001: case 0x6002: case 0x6003: - bank = ((offset & 0x7000) - 0x3000) / 0x0800 + BIT(offset, 1); - shift = (offset & 1) << 2; - mask1 = shift ? 0x00f : 0xff0; - mask2 = shift ? 0xff0 : 0x00f; - m_mmc_vrom_bank[bank] = (m_mmc_vrom_bank[bank] & mask1) | ((data << shift) & mask2); - chr1_x(bank, m_mmc_vrom_bank[bank], CHRROM); - break; - - case 0x7000: - m_irq_count_latch = (m_irq_count_latch & 0xf0) | (data & 0x0f); - break; - - case 0x7001: - m_irq_count_latch = (m_irq_count_latch & 0x0f) | ((data & 0x0f) << 4); - break; - - case 0x7002: - // m_irq_mode = data & 0x04; // currently not implemented: 0 = prescaler mode / 1 = CPU mode - m_irq_enable = data & 0x02; - m_irq_enable_latch = data & 0x01; - if (data & 0x02) - m_irq_count = m_irq_count_latch; - break; - - case 0x7003: - m_irq_enable = m_irq_enable_latch; - break; - } -} - - /*------------------------------------------------- UNL-43272 @@ -1040,85 +878,6 @@ uint8_t nes_43272_device::read_h(offs_t offset) return hi_access_rom(offset & mask); } - -/*------------------------------------------------- - - UNL-TF1201 - - Games: - - In MESS: Preliminary Supported - - -------------------------------------------------*/ - -void nes_tf1201_device::hblank_irq(int scanline, int vblank, int blanked) -{ - if (m_irq_enable_latch != m_irq_enable && scanline < 240) - m_irq_count -= 8; - - if (m_irq_enable) - { - m_irq_count++; - if ((m_irq_count & 0xff) == 238) - hold_irq_line(); - } -} - -void nes_tf1201_device::update_prg() -{ - prg8_89(m_swap ? 0xff : m_prg); - prg8_cd(m_swap ? m_prg : 0xff ); -} - -void nes_tf1201_device::write_h(offs_t offset, uint8_t data) -{ - int bank; - LOG_MMC(("unl_tf1201 write_h, offset: %04x, data: %02x\n", offset, data)); - - offset = (offset & 0x7003) | ((offset & 0x0c) >> 2); // nestopia does not OR here... - - switch (offset & 0x7003) - { - case 0x0000: - m_prg = data; - update_prg(); - break; - case 0x1000: - set_nt_mirroring(BIT(data, 0) ? PPU_MIRROR_HORZ : PPU_MIRROR_VERT); - break; - case 0x1001: - m_swap = data & 0x03; - update_prg(); - break; - case 0x2000: - prg8_ab(data); - break; - case 0x3000: case 0x3001: case 0x3002: case 0x3003: - case 0x4000: case 0x4001: case 0x4002: case 0x4003: - case 0x5000: case 0x5001: case 0x5002: case 0x5003: - case 0x6000: case 0x6001: case 0x6002: case 0x6003: - bank = (((offset - 0x3000) >> 11) | (offset & 0x1)) & 0x7; - if (offset & 2) - m_mmc_vrom_bank[bank] = (m_mmc_vrom_bank[bank] & 0x0f) | ((data & 0x0f) << 4); - else - m_mmc_vrom_bank[bank] = (m_mmc_vrom_bank[bank] & 0xf0) | ((data & 0x0f) << 0); - chr1_x(bank, m_mmc_vrom_bank[bank], m_chr_source); - break; - case 0x7000: - m_irq_count = (m_irq_count & 0xf0) | (data & 0x0f); - break; - case 0x7001: - case 0x7003: - m_irq_enable_latch = m_irq_enable; - m_irq_enable = BIT(data, 1); - break; - case 0x7002: - m_irq_count = (m_irq_count & 0x0f) | ((data & 0x0f) << 4); - break; - } -} - - /*------------------------------------------------- UNL-CITYFIGHT diff --git a/src/devices/bus/nes/pirate.h b/src/devices/bus/nes/pirate.h index 9f54fc778ca..1b0766f9d92 100644 --- a/src/devices/bus/nes/pirate.h +++ b/src/devices/bus/nes/pirate.h @@ -235,33 +235,6 @@ private: }; -// ======================> nes_whero_device - -class nes_whero_device : public nes_nrom_device -{ -public: - // construction/destruction - nes_whero_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - - virtual void write_h(offs_t offset, uint8_t data) override; - - virtual void hblank_irq(int scanline, int vblank, int blanked) override; - virtual void pcb_reset() override; - -protected: - // device-level overrides - virtual void device_start() override; - -private: - uint8_t m_reg; - uint8_t m_mmc_vrom_bank[8]; - - uint16_t m_irq_count, m_irq_count_latch; - int m_irq_enable, m_irq_enable_latch; -// int m_irq_mode; -}; - - // ======================> nes_43272_device class nes_43272_device : public nes_nrom_device @@ -284,33 +257,6 @@ private: }; -// ======================> nes_tf1201_device - -class nes_tf1201_device : public nes_nrom_device -{ -public: - // construction/destruction - nes_tf1201_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - - virtual void write_h(offs_t offset, uint8_t data) override; - - virtual void hblank_irq(int scanline, int vblank, int blanked) override; - virtual void pcb_reset() override; - -protected: - // device-level overrides - virtual void device_start() override; - -private: - void update_prg(); - uint8_t m_prg, m_swap; - uint16_t m_irq_count; - int m_irq_enable, m_irq_enable_latch; - - uint8_t m_mmc_vrom_bank[8]; -}; - - // ======================> nes_cityfight_device class nes_cityfight_device : public nes_nrom_device @@ -404,9 +350,7 @@ DECLARE_DEVICE_TYPE(NES_XIAOZY, nes_xiaozy_device) DECLARE_DEVICE_TYPE(NES_EDU2K, nes_edu2k_device) DECLARE_DEVICE_TYPE(NES_T230, nes_t230_device) DECLARE_DEVICE_TYPE(NES_MK2, nes_mk2_device) -DECLARE_DEVICE_TYPE(NES_WHERO, nes_whero_device) DECLARE_DEVICE_TYPE(NES_43272, nes_43272_device) -DECLARE_DEVICE_TYPE(NES_TF1201, nes_tf1201_device) DECLARE_DEVICE_TYPE(NES_CITYFIGHT, nes_cityfight_device) DECLARE_DEVICE_TYPE(NES_EH8813A, nes_eh8813a_device) //DECLARE_DEVICE_TYPE(NES_FUJIYA, nes_fujiya_device) diff --git a/src/devices/bus/nes/vrc_clones.cpp b/src/devices/bus/nes/vrc_clones.cpp new file mode 100644 index 00000000000..e961b20ffb9 --- /dev/null +++ b/src/devices/bus/nes/vrc_clones.cpp @@ -0,0 +1,160 @@ +// license:BSD-3-Clause +// copyright-holders: kmg, Fabio Priuli +/*********************************************************************************************************** + + + NES/Famicom cartridge emulation for Konami VRC clone PCBs + + + Here we emulate several pirate PCBs based on VRC2/4 boards + + ***********************************************************************************************************/ + + +#include "emu.h" +#include "vrc_clones.h" + + +#ifdef NES_PCB_DEBUG +#define VERBOSE 1 +#else +#define VERBOSE 0 +#endif + +#define LOG_MMC(x) do { if (VERBOSE) logerror x; } while (0) + + +//------------------------------------------------- +// constructor +//------------------------------------------------- + +DEFINE_DEVICE_TYPE(NES_SHUIGUAN, nes_shuiguan_device, "nes_shuiguan", "NES Cart Shui Guan Pipe Pirate PCB") +DEFINE_DEVICE_TYPE(NES_TF1201, nes_tf1201_device, "nes_tf1201", "NES Cart UNL-TF1201 PCB") + + +nes_shuiguan_device::nes_shuiguan_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : nes_konami_vrc4_device(mconfig, NES_SHUIGUAN, tag, owner, clock) +{ +} + +nes_tf1201_device::nes_tf1201_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : nes_konami_vrc4_device(mconfig, NES_TF1201, tag, owner, clock) +{ +} + + + +void nes_shuiguan_device::device_start() +{ + nes_konami_vrc4_device::device_start(); + save_item(NAME(m_reg)); + + // VRC4 pins 3 and 4 + m_vrc_ls_prg_a = 3; // A3 + m_vrc_ls_prg_b = 2; // A2 +} + +void nes_shuiguan_device::pcb_reset() +{ + nes_konami_vrc4_device::pcb_reset(); + m_reg = 0; +} + +void nes_tf1201_device::device_start() +{ + nes_konami_vrc4_device::device_start(); + + // VRC4 pins 3 and 4 + m_vrc_ls_prg_a = 0; // A0 + m_vrc_ls_prg_b = 1; // A1 +} + + + +/*------------------------------------------------- + mapper specific handlers + -------------------------------------------------*/ + +/*------------------------------------------------- + + BTL-SHUIGUANPIPE + + Games: Shui Guan Pipe (Gimmick Pirate) + + VRC4 clone that differs in its PRG banking only. + + iNES: mapper 183 + + In MAME: Supported. + + -------------------------------------------------*/ + +u8 nes_shuiguan_device::read_m(offs_t offset) +{ +// LOG_MMC(("shuiguan read_m, offset: %04x\n", offset)); + return m_prg[(m_reg * 0x2000 + offset) & (m_prg_size - 1)]; +} + +void nes_shuiguan_device::write_m(offs_t offset, u8 data) +{ + LOG_MMC(("shuiguan write_m, offset: %04x, data: %02x\n", offset, data)); + if ((offset & 0x1800) == 0x800) + m_reg = offset & 0x1f; +} + +void nes_shuiguan_device::write_h(offs_t offset, u8 data) +{ + LOG_MMC(("shuiguan write_h, offset: %04x, data: %02x\n", offset, data)); + + switch (offset & 0x7800) + { + case 0x0000: + case 0x1000: + break; // writes to $8000 and $9000 ignored + case 0x0800: + prg8_89(data); + break; + case 0x2000: + prg8_cd(data); + break; + case 0x2800: + prg8_ab(data); + break; + default: + nes_konami_vrc4_device::write_h(offset, data); + break; + } +} + +/*------------------------------------------------- + + UNL-TF1201 + + Games: Leathal Weapon (Leathal Enforcers clone) + + VRC4 clone where the only known difference is in the + IRQ behavior. This clone does not copy the IRQ reload + bit to the enable bit on writes to IRQ acknowledge. + + NES 2.0: mapper 298 + + In MAME: Supported. + + -------------------------------------------------*/ + +void nes_tf1201_device::write_h(offs_t offset, u8 data) +{ + LOG_MMC(("unl_tf1201 write_h, offset: %04x, data: %02x\n", offset, data)); + + if ((offset & 0x7003) == 0x7003) + set_irq_line(CLEAR_LINE); + else + nes_konami_vrc4_device::write_h(offset, data); +} + + +/*------------------------------------------------- + + MULTIGAME CARTS BASED ON VRC + + -------------------------------------------------*/ diff --git a/src/devices/bus/nes/vrc_clones.h b/src/devices/bus/nes/vrc_clones.h new file mode 100644 index 00000000000..6fb950c1c7e --- /dev/null +++ b/src/devices/bus/nes/vrc_clones.h @@ -0,0 +1,54 @@ +// license:BSD-3-Clause +// copyright-holders: kmg, Fabio Priuli +#ifndef MAME_BUS_NES_VRC_CLONES_H +#define MAME_BUS_NES_VRC_CLONES_H + +#pragma once + +#include "konami.h" + + +// ======================> nes_shuiguan_device + +class nes_shuiguan_device : public nes_konami_vrc4_device +{ +public: + // construction/destruction + nes_shuiguan_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); + + virtual u8 read_m(offs_t offset) override; + virtual void write_m(offs_t offset, u8 data) override; + virtual void write_h(offs_t offset, u8 data) override; + + virtual void pcb_reset() override; + +protected: + // device-level overrides + virtual void device_start() override; + +private: + u8 m_reg; +}; + + +// ======================> nes_tf1201_device + +class nes_tf1201_device : public nes_konami_vrc4_device +{ +public: + // construction/destruction + nes_tf1201_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); + + virtual void write_h(offs_t offset, u8 data) override; + +protected: + // device-level overrides + virtual void device_start() override; +}; + + +// device type definition +DECLARE_DEVICE_TYPE(NES_SHUIGUAN, nes_shuiguan_device) +DECLARE_DEVICE_TYPE(NES_TF1201, nes_tf1201_device) + +#endif // MAME_BUS_NES_VRC_CLONES_H |