From 12c30453d357bf34a664c74794a083090d56f2a8 Mon Sep 17 00:00:00 2001 From: 0kmg <9137159+0kmg@users.noreply.github.com> Date: Sat, 25 Sep 2021 21:21:19 -0800 Subject: bus/nes: Updates for BMC-70IN1 and BMC-800IN1 boards. (#8609) * Reimplemented these related boards as class/subclass. * Corrected missing iNES loader support. New working software list additions (nes.xml) ----------------------------------- 35 in 1 (HM5511) [anonymous] 68 in 1 (HM5511) [anonymous] Software list items promoted to working (nes.xml) --------------------------------------- 70 in 1 800 in 1 --- hash/nes.xml | 45 +++++++-- src/devices/bus/nes/event.h | 6 +- src/devices/bus/nes/mmc3_clones.cpp | 37 ++++---- src/devices/bus/nes/mmc3_clones.h | 7 +- src/devices/bus/nes/multigame.cpp | 181 +++++++++++++++--------------------- src/devices/bus/nes/multigame.h | 53 +++++------ src/devices/bus/nes/nes_ines.hxx | 12 ++- src/devices/bus/nes/pirate.cpp | 4 +- 8 files changed, 174 insertions(+), 171 deletions(-) diff --git a/hash/nes.xml b/hash/nes.xml index d9a201dda87..8cc97a2d7ad 100644 --- a/hash/nes.xml +++ b/hash/nes.xml @@ -78594,7 +78594,7 @@ be better to redump them properly. --> - + 15 in 1 19?? <pirate> @@ -79211,7 +79211,7 @@ be better to redump them properly. --> - + 3 in 1 19?? <pirate> @@ -79400,6 +79400,21 @@ be better to redump them properly. --> + + 35 in 1 (HM5511) + 19?? + <pirate> + + + + + + + + + + + 35 in 1 (K-3036) 19?? @@ -80877,6 +80892,21 @@ be better to redump them properly. --> + + 68 in 1 (HM5511) + 19?? + <pirate> + + + + + + + + + + + 7 in 1 (K7603) 19?? @@ -80941,7 +80971,7 @@ be better to redump them properly. --> - + 70 in 1 19?? <unknown> @@ -81076,13 +81106,12 @@ be better to redump them properly. --> - - 76 in 1 (Alt Games) + + 76 in 1 (alt games) 19?? <pirate> - - + @@ -81285,7 +81314,7 @@ be better to redump them properly. --> - + 800 in 1 19?? <unknown> diff --git a/src/devices/bus/nes/event.h b/src/devices/bus/nes/event.h index b4b67614b50..c1ba24d179d 100644 --- a/src/devices/bus/nes/event.h +++ b/src/devices/bus/nes/event.h @@ -1,7 +1,7 @@ // license:BSD-3-Clause // copyright-holders:Fabio Priuli -#ifndef MAEM_BUS_NES_EVENT_H -#define MAEM_BUS_NES_EVENT_H +#ifndef MAME_BUS_NES_EVENT_H +#define MAME_BUS_NES_EVENT_H #pragma once @@ -46,4 +46,4 @@ protected: // device type definition DECLARE_DEVICE_TYPE(NES_EVENT, nes_event_device) -#endif // MAEM_BUS_NES_EVENT_H +#endif // MAME_BUS_NES_EVENT_H diff --git a/src/devices/bus/nes/mmc3_clones.cpp b/src/devices/bus/nes/mmc3_clones.cpp index 8aac9112b91..42ff5edd7c9 100644 --- a/src/devices/bus/nes/mmc3_clones.cpp +++ b/src/devices/bus/nes/mmc3_clones.cpp @@ -278,8 +278,8 @@ nes_bmc_8in1_device::nes_bmc_8in1_device(const machine_config &mconfig, const ch { } -nes_bmc_15in1_device::nes_bmc_15in1_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : nes_txrom_device(mconfig, NES_BMC_15IN1, tag, owner, clock) +nes_bmc_15in1_device::nes_bmc_15in1_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : nes_txrom_device(mconfig, NES_BMC_15IN1, tag, owner, clock), m_jumper(0) { } @@ -673,10 +673,7 @@ void nes_bmc_8in1_device::pcb_reset() void nes_bmc_15in1_device::pcb_reset() { m_chr_source = m_vrom_chunks ? CHRROM : CHRRAM; - mmc3_common_initialize(0x1f, 0xff, 0); - m_prg_base = 0x10; // this board has a diff prg_base - set_prg(m_prg_base, m_prg_mask); } void nes_bmc_sbig7_device::pcb_reset() @@ -2326,30 +2323,32 @@ void nes_bmc_8in1_device::write_h(offs_t offset, u8 data) /*------------------------------------------------- - BMC-15IN1 + BMC-15IN1 (PCB JC-016-2?) - Unknown Bootleg Multigame Board Games: 3 in 1, 15 in 1 - iNES: mapper 205, MMC3 clone + MMC3 clone with banking for multigame menu. + + iNES: mapper 205 - In MESS: Supported. + In MAME: Supported. -------------------------------------------------*/ -void nes_bmc_15in1_device::write_m(offs_t offset, uint8_t data) +void nes_bmc_15in1_device::write_m(offs_t offset, u8 data) { LOG_MMC(("bmc_15in1 write_m, offset: %04x, data: %02x\n", offset, data)); - if (offset & 0x0800) - { - m_prg_base = (data & 0x03) << 4; - m_prg_mask = (data & 0x02) ? 0x0f : 0x1f; - m_chr_base = (data & 0x03) << 7; - m_chr_mask = (data & 0x02) ? 0x7f : 0xff; - set_prg(m_prg_base, m_prg_mask); - set_chr(m_chr_source, m_chr_base, m_chr_mask); - } + if (data & 1) + data |= m_jumper; // TODO: add jumper settings, m_jumper is 0 for now + + m_prg_base = (data & 0x03) << 4; + m_prg_mask = 0x1f >> BIT(data, 1); + set_prg(m_prg_base, m_prg_mask); + + m_chr_base = m_prg_base << 3; + m_chr_mask = 0xff >> BIT(data, 1); + set_chr(m_chr_source, m_chr_base, m_chr_mask); } /*------------------------------------------------- diff --git a/src/devices/bus/nes/mmc3_clones.h b/src/devices/bus/nes/mmc3_clones.h index 0c75312bda4..bbcd9f2e834 100644 --- a/src/devices/bus/nes/mmc3_clones.h +++ b/src/devices/bus/nes/mmc3_clones.h @@ -649,12 +649,15 @@ class nes_bmc_15in1_device : public nes_txrom_device { public: // construction/destruction - nes_bmc_15in1_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + nes_bmc_15in1_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); // device-level overrides - virtual void write_m(offs_t offset, uint8_t data) override; + virtual void write_m(offs_t offset, u8 data) override; virtual void pcb_reset() override; + +private: + u8 m_jumper; }; diff --git a/src/devices/bus/nes/multigame.cpp b/src/devices/bus/nes/multigame.cpp index 58679f5ea1e..bb4d6d90ac0 100644 --- a/src/devices/bus/nes/multigame.cpp +++ b/src/devices/bus/nes/multigame.cpp @@ -340,8 +340,18 @@ nes_bmc_64in1_device::nes_bmc_64in1_device(const machine_config &mconfig, const { } -nes_bmc_70in1_device::nes_bmc_70in1_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : nes_nrom_device(mconfig, NES_BMC_70IN1, tag, owner, clock), m_mode(0) +nes_bmc_70in1_device::nes_bmc_70in1_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock) + : nes_nrom_device(mconfig, type, tag, owner, clock), m_jumper(type == NES_BMC_70IN1 ? 0x0d : 0x06) +{ +} + +nes_bmc_70in1_device::nes_bmc_70in1_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : nes_bmc_70in1_device(mconfig, NES_BMC_70IN1, tag, owner, clock) +{ +} + +nes_bmc_800in1_device::nes_bmc_800in1_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : nes_bmc_70in1_device(mconfig, NES_BMC_800IN1, tag, owner, clock) { } @@ -365,11 +375,6 @@ nes_bmc_500in1_device::nes_bmc_500in1_device(const machine_config &mconfig, cons { } -nes_bmc_800in1_device::nes_bmc_800in1_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : nes_nrom_device(mconfig, NES_BMC_800IN1, tag, owner, clock), m_mode(0) -{ -} - nes_bmc_1200in1_device::nes_bmc_1200in1_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : nes_nrom_device(mconfig, NES_BMC_1200IN1, tag, owner, clock), m_vram_protect(0) { @@ -878,18 +883,16 @@ void nes_bmc_64in1_device::pcb_reset() void nes_bmc_70in1_device::device_start() { common_start(); - save_item(NAME(m_reg)); - save_item(NAME(m_mode)); + save_item(NAME(m_latch)); } void nes_bmc_70in1_device::pcb_reset() { - prg16_89ab(m_prg_chunks - 1); - prg16_cdef(m_prg_chunks - 1); - chr8(0, CHRROM); - m_reg[0] = 0; - m_reg[1] = 0; - m_mode = 0; + m_chr_source = m_vrom_chunks ? CHRROM : CHRRAM; + chr8(0, m_chr_source); + + m_latch[0] = m_latch[1] = 0; + update_banks(); } void nes_bmc_72in1_device::device_start() @@ -919,24 +922,6 @@ void nes_bmc_150in1_device::pcb_reset() chr8(0, CHRROM); } -void nes_bmc_800in1_device::device_start() -{ - common_start(); - save_item(NAME(m_reg)); - save_item(NAME(m_mode)); -} - -void nes_bmc_800in1_device::pcb_reset() -{ - m_chr_source = m_vrom_chunks ? CHRROM : CHRRAM; - prg16_89ab(m_prg_chunks - 1); - prg16_cdef(m_prg_chunks - 1); - chr8(0, m_chr_source); - m_reg[0] = 0; - m_reg[1] = 0; - m_mode = 0; -} - void nes_bmc_1200in1_device::device_start() { common_start(); @@ -2432,54 +2417,84 @@ void nes_bmc_64in1_device::write_h(offs_t offset, uint8_t data) /*------------------------------------------------- - BMC-70IN1 + BMC-70IN1 (FIXME: according to NesDev the boards for this + and BMC-800IN1 are Realtec 8031 and 8155. Which is which?) - Unknown Bootleg Multigame Board - Games: + Games: 35 in 1, 68 in 1, 70 in 1 - iNES: mapper + iNES: mapper 236 - This is same hardware as BMC-800IN1 below, but this - cart has CHR and slightly diff bankswitch. - DSW not emulated yet. + This is the same hardware as BMC-800IN1 below, but + these carts have CHRROM and lack the extended PRG + bank switching. Solder pads/jumpers not emulated yet. - In MESS: Preliminary Supported. + In MAME: Supported. + + TODO: Determine if Excitebike on 68 in 1 is actually + bugged on the real cartridge. It sets mirroring bit + to horizontal when it should be vertical. -------------------------------------------------*/ -void nes_bmc_70in1_device::write_h(offs_t offset, uint8_t data) +void nes_bmc_70in1_device::update_banks() { - LOG_MMC(("bmc70in1 write_h, offset: %04x, data: %02x\n", offset, data)); + update_prg(m_latch[1] & 0x07); + chr8(m_latch[0] & 0x07, CHRROM); +} - if (offset < 0x4000) +void nes_bmc_70in1_device::update_prg(u8 bank) +{ + if (BIT(m_latch[1], 5)) // NROM mode { - set_nt_mirroring(BIT(offset, 5) ? PPU_MIRROR_HORZ: PPU_MIRROR_VERT); - chr8(offset & 7, CHRROM); + u8 mode = !BIT(m_latch[1], 4); + prg16_89ab(bank & ~mode); + prg16_cdef(bank | mode); } - else + else // UNROM mode { - switch (offset & 0x30) - { - case 0x00: m_mode = 0x0; m_reg[0] = (m_reg[0] & 0x38) | (offset & 0x7); m_reg[1] = m_reg[0] | 0x7; break; - case 0x10: m_mode = 0x1; m_reg[0] = (m_reg[0] & 0x38) | (offset & 0x7); m_reg[1] = m_reg[0] | 0x7; break; - case 0x20: m_mode = 0x0; m_reg[0] = (m_reg[0] & 0x38) | (offset & 0x6); m_reg[1] = m_reg[0] | 0x1; break; - case 0x30: m_mode = 0x0; m_reg[0] = (m_reg[0] & 0x38) | (offset & 0x7); m_reg[1] = m_reg[0] | 0x0; break; - } - prg16_89ab(m_reg[0]); - prg16_cdef(m_reg[1]); + prg16_89ab(bank); + prg16_cdef(bank | 0x07); } } +void nes_bmc_70in1_device::write_h(offs_t offset, u8 data) +{ + LOG_MMC(("bmc70in1 write_h, offset: %04x, data: %02x\n", offset, data)); + m_latch[BIT(offset, 14)] = offset; + update_banks(); + set_nt_mirroring(BIT(m_latch[0], 5) ? PPU_MIRROR_HORZ: PPU_MIRROR_VERT); +} + uint8_t nes_bmc_70in1_device::read_h(offs_t offset) { LOG_MMC(("bmc70in1 read_h, offset: %04x\n", offset)); - if (m_mode) - offset = (offset & 0x7ff0) | m_mode; + if ((m_latch[1] & 0x30) == 0x10) + offset = (offset & ~0x0f) | m_jumper; // TODO: make jumper selectable return hi_access_rom(offset); } +/*------------------------------------------------- + + BMC-800IN1 + + Games: 800 in 1 + + iNES: mapper 236 + + This is the same hardware as BMC-70IN1, but this + cart supports larger PRG and has unbanked CHRRAM. + + In MAME: Supported. + + -------------------------------------------------*/ + +void nes_bmc_800in1_device::update_banks() +{ + update_prg((m_latch[0] & 0x07) << 3 | (m_latch[1] & 0x07)); +} + /*------------------------------------------------- BMC-72IN1, BMC-110IN1 @@ -2607,56 +2622,6 @@ void nes_bmc_500in1_device::write_h(offs_t offset, u8 data) chr8(offset & 0x07, CHRROM); } -/*------------------------------------------------- - - BMC-800IN1 - - Unknown Bootleg Multigame Board - Games: - - iNES: mapper - - DSW not emulated yet. - - In MESS: Preliminary Supported. - - -------------------------------------------------*/ - -void nes_bmc_800in1_device::write_h(offs_t offset, uint8_t data) -{ - LOG_MMC(("bmc800in1 write_h, offset: %04x, data: %02x\n", offset, data)); - - if (offset < 0x4000) - { - set_nt_mirroring(BIT(offset, 5) ? PPU_MIRROR_HORZ: PPU_MIRROR_VERT); - - m_reg[0] = (m_reg[0]) | ((offset << 3) & 0x38); - m_reg[1] = (m_reg[1]) | ((offset << 3) & 0x38); - } - else - { - switch (offset & 0x30) - { - case 0x00: m_mode = 0x0; m_reg[0] = (m_reg[0] & 0x38) | (offset & 0x7); m_reg[1] = m_reg[0] | 0x7; break; - case 0x10: m_mode = 0x1; m_reg[0] = (m_reg[0] & 0x38) | (offset & 0x7); m_reg[1] = m_reg[0] | 0x7; break; - case 0x20: m_mode = 0x0; m_reg[0] = (m_reg[0] & 0x38) | (offset & 0x6); m_reg[1] = m_reg[0] | 0x1; break; - case 0x30: m_mode = 0x0; m_reg[0] = (m_reg[0] & 0x38) | (offset & 0x7); m_reg[1] = m_reg[0] | 0x0; break; - } - } - prg16_89ab(m_reg[0]); - prg16_cdef(m_reg[1]); -} - -uint8_t nes_bmc_800in1_device::read_h(offs_t offset) -{ - LOG_MMC(("bmc800in1 read_h, offset: %04x\n", offset)); - - if (m_mode) - offset = (offset & 0x7ff0) | m_mode; - - return hi_access_rom(offset); -} - /*------------------------------------------------- BMC-1200IN1 diff --git a/src/devices/bus/nes/multigame.h b/src/devices/bus/nes/multigame.h index fe4a780691c..54056689f5b 100644 --- a/src/devices/bus/nes/multigame.h +++ b/src/devices/bus/nes/multigame.h @@ -790,20 +790,40 @@ class nes_bmc_70in1_device : public nes_nrom_device { public: // construction/destruction - nes_bmc_70in1_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + nes_bmc_70in1_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); - virtual uint8_t read_h(offs_t offset) override; - virtual void write_h(offs_t offset, uint8_t data) override; + virtual u8 read_h(offs_t offset) override; + virtual void write_h(offs_t offset, u8 data) override; virtual void pcb_reset() override; protected: + // construction/destruction + nes_bmc_70in1_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock); + // device-level overrides virtual void device_start() override; + virtual void update_banks(); + void update_prg(u8 bank); + + u8 m_latch[2]; + private: - uint8_t m_mode; - uint8_t m_reg[2]; + u8 m_jumper; +}; + + +// ======================> nes_bmc_800in1_device + +class nes_bmc_800in1_device : public nes_bmc_70in1_device +{ +public: + // construction/destruction + nes_bmc_800in1_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); + +protected: + virtual void update_banks() override; }; @@ -877,29 +897,6 @@ public: }; -// ======================> nes_bmc_800in1_device - -class nes_bmc_800in1_device : public nes_nrom_device -{ -public: - // construction/destruction - nes_bmc_800in1_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - - virtual uint8_t read_h(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; - -private: - uint8_t m_mode; - uint8_t m_reg[2]; -}; - - // ======================> nes_bmc_1200in1_device class nes_bmc_1200in1_device : public nes_nrom_device diff --git a/src/devices/bus/nes/nes_ines.hxx b/src/devices/bus/nes/nes_ines.hxx index 9de292f5225..a028aafdbae 100644 --- a/src/devices/bus/nes/nes_ines.hxx +++ b/src/devices/bus/nes/nes_ines.hxx @@ -269,7 +269,7 @@ static const nes_mmc mmc_list[] = { 233, BMC_42IN1RESET }, { 234, AVE_MAXI15 }, { 235, BMC_GOLD150 }, // 235 Golden Game x-in-1 - Unsupported - // 236 Game 800-in-1 - Unsupported, Realtec boards 8031 and 8155 + { 236, BMC_70IN1 }, // 237 Teletubbies 420-in-1 multicart. Dump available? { 238, UNL_603_5052 }, // 239 Unused @@ -906,6 +906,11 @@ void nes_cart_slot_device::call_load_ines() m_pcb_id = UNL_8237A; break; + case BMC_70IN1: + if (vrom_size == 0) + m_pcb_id = BMC_800IN1; + break; + case RCM_GS2004: if (prg_size >= 0x50000) m_pcb_id = RCM_GS2013; @@ -1242,6 +1247,11 @@ const char * nes_cart_slot_device::get_default_card_ines(get_default_card_softwa pcb_id = UNL_8237A; break; + case BMC_70IN1: // Mapper 236 is used for 2 diff boards + if (ROM[5] == 0) + pcb_id = BMC_800IN1; + break; + case RCM_GS2004: // Mapper 283 is used for 2 diff boards if (ROM[4] >= 20) pcb_id = RCM_GS2013; diff --git a/src/devices/bus/nes/pirate.cpp b/src/devices/bus/nes/pirate.cpp index c6a68d48b98..fdc48fdc66b 100644 --- a/src/devices/bus/nes/pirate.cpp +++ b/src/devices/bus/nes/pirate.cpp @@ -36,8 +36,8 @@ DEFINE_DEVICE_TYPE(NES_AGCI_50282, nes_agci_device, "nes_agci50282", "NES Cart AGCI 50282 PCB") DEFINE_DEVICE_TYPE(NES_DREAMTECH01, nes_dreamtech_device, "nes_dreamtech", "NES Cart Dreamtech01 PCB") -DEFINE_DEVICE_TYPE(NES_FUKUTAKE, nes_fukutake_device, "nes_futuremedia", "NES Cart Fukutake Study Box PCB") -DEFINE_DEVICE_TYPE(NES_FUTUREMEDIA, nes_futuremedia_device, "nes_fukutake", "NES Cart FutureMedia PCB") +DEFINE_DEVICE_TYPE(NES_FUKUTAKE, nes_fukutake_device, "nes_fukutake", "NES Cart Fukutake Study Box PCB") +DEFINE_DEVICE_TYPE(NES_FUTUREMEDIA, nes_futuremedia_device, "nes_futuremedia", "NES Cart FutureMedia PCB") DEFINE_DEVICE_TYPE(NES_MAGSERIES, nes_magseries_device, "nes_magseries", "NES Cart Magical Series PCB") DEFINE_DEVICE_TYPE(NES_DAOU306, nes_daou306_device, "nes_daou306", "NES Cart Daou 306 PCB") DEFINE_DEVICE_TYPE(NES_CC21, nes_cc21_device, "nes_cc21", "NES Cart CC-21 PCB") -- cgit v1.2.3